Make calendar general

This commit is contained in:
Chris Jean-Marie 2024-12-07 22:00:58 +00:00
parent 2ead3f79c3
commit ea0d26e4dd
5 changed files with 104 additions and 35 deletions

View File

@ -1,7 +1,7 @@
use askama::Template;
use askama_axum::{IntoResponse, Response};
use axum::{
extract::State,
extract::{Path, State},
response::{Html, Json, Redirect},
Extension,
};
@ -31,15 +31,21 @@ where
}
}
struct Calendar {
name: String,
colour: String,
}
#[derive(Template)]
#[template(path = "cottagecalendar.html")]
struct CottageCalendarTemplate {
#[template(path = "calendar.html")]
struct CalendarTemplate {
logged_in: bool,
user: UserData,
user_roles: Vec<crate::user::UserRolesDisplay>,
calendars: Vec<Calendar>,
}
pub async fn cottagecalendar(
pub async fn calendar(
Extension(user_data): Extension<Option<UserData>>,
State(db_pool): State<SqlitePool>,
) -> impl IntoResponse {
@ -51,14 +57,26 @@ pub async fn cottagecalendar(
let user = user_data.as_ref().unwrap().clone();
let userid = user_data.as_ref().map(|s| s.id.clone()).unwrap_or_default();
if is_authorized("/cottagecalendar", user_data, db_pool.clone()).await {
if is_authorized("/calendar", user_data, db_pool.clone()).await {
// Get user roles
let user_roles = get_user_roles_display(userid, &db_pool.clone()).await;
let template = CottageCalendarTemplate {
let calendars: Vec<Calendar> = vec![
Calendar {
name: "Cottage".to_string(),
colour: "green".to_string(),
},
Calendar {
name: "Personal".to_string(),
colour: "blue".to_string(),
},
];
let template = CalendarTemplate {
logged_in,
user,
user_roles,
calendars,
};
HtmlTemplate(template).into_response()
} else {
@ -70,12 +88,27 @@ pub async fn cottagecalendar(
}
pub async fn get_events(
Extension(user_data): Extension<Option<UserData>>,
Path(calendar): Path<String>,
State(db_pool): State<SqlitePool>,
Extension(user_data): Extension<Option<UserData>>,
) -> String {
let events = "[{\"title\": \"Chris and Terri\", \"start\": \"2024-12-23T14:00:00\", \"end\": \"2024-12-27T10:00:00\", \"allDay\": false}, {\"title\": \"Stephen\", \"start\": \"2024-12-27T14:00:00\", \"end\": \"2024-12-31T10:00:00\", \"allDay\": false}]";
println!("Calendar: {}", calendar);
// Is the user logged in?
let logged_in = user_data.is_some();
println!("{}", events);
// Set default events
let mut events = "[]";
if logged_in {
// Extract the user data.
let user = user_data.as_ref().unwrap().clone();
let userid = user_data.as_ref().map(|s| s.id.clone()).unwrap_or_default();
if is_authorized("/calendar", user_data, db_pool.clone()).await {
// Get requested calendar events from database
events = "[{\"title\": \"Chris and Terri\", \"start\": \"2024-12-23T14:00:00\", \"end\": \"2024-12-27T10:00:00\", \"allDay\": false}, {\"title\": \"Stephen\", \"start\": \"2024-12-27T14:00:00\", \"end\": \"2024-12-31T10:00:00\", \"allDay\": false}]";
}
}
events.to_string()
}

View File

@ -4,7 +4,6 @@ use axum::{
Extension, Router,
};
use secret_gift_exchange::{giftexchange, giftexchange_save, giftexchanges};
use calendar::cottagecalendar;
use sqlx::migrate::Migrator;
use sqlx::{sqlite::SqlitePoolOptions, SqlitePool};
use std::net::SocketAddr;
@ -25,6 +24,7 @@ use google_oauth::{google_auth_return, login, logout};
use middlewares::inject_user_data;
use routes::{about, contact, dashboard, index, profile, user_profile, useradmin};
use user::{add_user_role, delete_user_role, UserData};
use calendar::{calendar, get_events};
use wishlist::{user_wishlist, user_wishlist_add, user_wishlist_add_item, user_wishlist_bought_item, user_wishlist_delete_item, user_wishlist_edit_item, user_wishlist_received_item, user_wishlist_returned_item, user_wishlist_save_item, wishlists};
//use email::send_emails;
@ -68,8 +68,8 @@ async fn main() {
.route("/roles/:user_id/:user_role_id/delete", get(delete_user_role))
// Calendar
.route("/cottagecalendar", get(cottagecalendar))
.route("/getevents", get(calendar::get_events))
.route("/calendar", get(calendar))
.route("/getevents/:calendar", get(get_events))
// Wishlist
.route("/wishlists", get(wishlists))

View File

@ -254,8 +254,23 @@ pub async fn about(Extension(user_data): Extension<Option<UserData>>) -> impl In
// Is the user logged in?
let logged_in = user_data.is_some();
// Extract the user data.
let user = user_data.as_ref().unwrap().clone();
// Set empty user
let mut user = UserData {
id: 0,
email: "".to_string(),
created_at: 0,
created_by: 0,
updated_at: 0,
updated_by: 0,
name: "".to_string(),
family_name: "".to_string(),
given_name: "".to_string(),
};
if logged_in {
// Extract the user data.
user = user_data.as_ref().unwrap().clone();
}
let template = AboutTemplate { logged_in, user };
HtmlTemplate(template)
@ -272,8 +287,23 @@ pub async fn contact(Extension(user_data): Extension<Option<UserData>>) -> impl
// Is the user logged in?
let logged_in = user_data.is_some();
// Extract the user data.
let user = user_data.as_ref().unwrap().clone();
// Set empty user
let mut user = UserData {
id: 0,
email: "".to_string(),
created_at: 0,
created_by: 0,
updated_at: 0,
updated_by: 0,
name: "".to_string(),
family_name: "".to_string(),
given_name: "".to_string(),
};
if logged_in {
// Extract the user data.
user = user_data.as_ref().unwrap().clone();
}
let template = ContactTemplate { logged_in, user };
HtmlTemplate(template)

View File

@ -6,7 +6,7 @@
<h2>Menu</h2>
<ul>
<li><a href="/dashboard">Web links</a></li>
<li><a href="/cottagecalendar">Cottage Calendar</a></li>
<li><a href="/calendar">Calendar</a></li>
<li><a href="/wishlists">Wish lists</a></li>
</ul>
{% for user_role in user_roles %}

View File

@ -4,7 +4,7 @@
<link rel='stylesheet' href='https://cdn.jsdelivr.net/npm/@fullcalendar/daygrid@4.3.0/main.min.css'>
{% endblock links %}
{% block center %}
<h1>Cottage Calendar</h1>
<h1>Calendar</h1>
<div class="mh-100">
<div id="calendar" class="fc"></div>
</div>
@ -22,30 +22,36 @@
selectable: true,
displayEventTime: true,
displayEventEnd: true,
slotDuration: {hours: 12},
slotLabelInterval: {hours: 24},
slotDuration: { hours: 12 },
slotLabelInterval: { hours: 24 },
headerToolbar: {
left: 'prev,next today',
center: 'title',
right: 'dayGridMonth,timeGridWeek,timeGridDay,multiMonthYear'
},
events: '/getevents',
select: function (info) {
alert('selected ' + info.startStr + ' to ' + info.endStr);
let enddate = new Date(info.endStr);
enddate.setDate(enddate.getDate() - 1);
info.view.calendar.addEvent({
id: uuidv4(),
title: 'New Event',
start: info.startStr+'T14:00:00',
end: info.endStr+'T10:00:00',
allDay: false
});
}
eventSources: [
{% for calendar in calendars %}
{
url: '/getevents/{{calendar.name}}',
color: '{{calendar.colour}}',
},
{% endfor %}
],
select: function (info) {
alert('selected ' + info.startStr + ' to ' + info.endStr);
let enddate = new Date(info.endStr);
enddate.setDate(enddate.getDate() - 1);
info.view.calendar.addEvent({
id: uuidv4(),
title: 'New Event',
start: info.startStr + 'T14:00:00',
end: info.endStr + 'T10:00:00',
allDay: false
});
}
});
calendar.render();
calendar.render();
});
</script>
{% endblock scripts %}