feat: add /images image listing page
							parent
							
								
									39a15bb094
								
							
						
					
					
						commit
						fc02399e78
					
				| 
						 | 
				
			
			@ -12,7 +12,7 @@ use serde::Deserialize;
 | 
			
		|||
use std::{error::Error, fmt, path::Path};
 | 
			
		||||
 | 
			
		||||
pub use models::event::{Event, NewEvent, EVENT_TYPES};
 | 
			
		||||
pub use models::image::{Image, NewImage};
 | 
			
		||||
pub use models::image::{Image, ImageFilter, NewImage};
 | 
			
		||||
pub use models::plant::{NewPlant, Plant};
 | 
			
		||||
pub use models::session::Session;
 | 
			
		||||
pub use models::user::{NewUser, User};
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -1,14 +1,16 @@
 | 
			
		|||
use axum::{
 | 
			
		||||
    extract::{DefaultBodyLimit, Multipart, Path, Request, State},
 | 
			
		||||
    extract::{DefaultBodyLimit, Multipart, Path, Query, Request, State},
 | 
			
		||||
    handler::Handler,
 | 
			
		||||
    http::HeaderMap,
 | 
			
		||||
    response::{Html, IntoResponse},
 | 
			
		||||
    routing::{get, post},
 | 
			
		||||
    routing::get,
 | 
			
		||||
    Router,
 | 
			
		||||
};
 | 
			
		||||
use chrono::NaiveDate;
 | 
			
		||||
use futures::TryStreamExt;
 | 
			
		||||
use image::{codecs::jpeg::JpegEncoder, ImageReader};
 | 
			
		||||
use mime::Mime;
 | 
			
		||||
use tera::Context;
 | 
			
		||||
use tokio_util::io::StreamReader;
 | 
			
		||||
use tower::ServiceExt;
 | 
			
		||||
use tower_http::services::ServeFile;
 | 
			
		||||
| 
						 | 
				
			
			@ -17,7 +19,7 @@ use std::{io::BufWriter, path::PathBuf};
 | 
			
		|||
 | 
			
		||||
use super::error::AppError;
 | 
			
		||||
use crate::{
 | 
			
		||||
    db::{Image, NewImage},
 | 
			
		||||
    db::{self, Image, NewImage, Pagination},
 | 
			
		||||
    IMG_DIR,
 | 
			
		||||
};
 | 
			
		||||
 | 
			
		||||
| 
						 | 
				
			
			@ -27,7 +29,7 @@ pub fn app() -> axum::Router<crate::Context> {
 | 
			
		|||
    Router::new()
 | 
			
		||||
        .route(
 | 
			
		||||
            "/",
 | 
			
		||||
            post(post_image.layer(DefaultBodyLimit::max(1024 * 1024 * 20))),
 | 
			
		||||
            get(get_images).post(post_image.layer(DefaultBodyLimit::max(1024 * 1024 * 20))),
 | 
			
		||||
        )
 | 
			
		||||
        .route("/{id}/original", get(get_image_original))
 | 
			
		||||
        .route("/{id}/thumb", get(get_image_thumb))
 | 
			
		||||
| 
						 | 
				
			
			@ -58,6 +60,27 @@ async fn get_image(
 | 
			
		|||
    Ok(ServeFile::new_with_mime(path, &mime).oneshot(req).await)
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
async fn get_images(
 | 
			
		||||
    State(ctx): State<crate::Context>,
 | 
			
		||||
    Query(page): Query<Pagination>,
 | 
			
		||||
    Query(filter): Query<db::ImageFilter>,
 | 
			
		||||
    headers: HeaderMap,
 | 
			
		||||
) -> super::Result<Html<String>> {
 | 
			
		||||
    let images = tokio::task::spawn_blocking(move || db::Image::page(&ctx.pool, page, filter))
 | 
			
		||||
        .await
 | 
			
		||||
        .unwrap()?;
 | 
			
		||||
 | 
			
		||||
    let mut context = Context::new();
 | 
			
		||||
    context.insert("images", &images);
 | 
			
		||||
 | 
			
		||||
    Ok(Html(super::render_view(
 | 
			
		||||
        &ctx.tera,
 | 
			
		||||
        "views/images.html",
 | 
			
		||||
        &context,
 | 
			
		||||
        &headers,
 | 
			
		||||
    )?))
 | 
			
		||||
}
 | 
			
		||||
 | 
			
		||||
async fn get_image_original(
 | 
			
		||||
    State(ctx): State<crate::Context>,
 | 
			
		||||
    Path(id): Path<i32>,
 | 
			
		||||
| 
						 | 
				
			
			
 | 
			
		|||
| 
						 | 
				
			
			@ -0,0 +1,10 @@
 | 
			
		|||
<h1>Images</h1>
 | 
			
		||||
{% for image in images %}
 | 
			
		||||
<article>
 | 
			
		||||
    <p>Date taken: {{ image.date_taken }}</p>
 | 
			
		||||
    <p>Note: {{ image.note }}</p>
 | 
			
		||||
    <a href="/images/{{ image.id }}/original" target="_blank">
 | 
			
		||||
        <img src="/images/{{ image.id }}/thumb">
 | 
			
		||||
    </a>
 | 
			
		||||
</article>
 | 
			
		||||
{% endfor %}
 | 
			
		||||
		Loading…
	
		Reference in New Issue