credence_lib/render/catalog/
create.rs

1use super::{
2    super::{
3        super::{configuration::*, util::*},
4        constants::*,
5        rendered_page::*,
6    },
7    annotation::*,
8};
9
10use {
11    ::axum::http::*,
12    compris::{annotate::*, normal::*},
13    kutil::{http::*, std::immutable::*},
14    std::{path::*, result::Result},
15    tokio::fs::*,
16};
17
18/// Create catalog.
19pub async fn create_catalog<'annotation, PathT>(
20    annotation: CatalogAnnotation<'annotation>,
21    uri_path: &str,
22    directory: PathT,
23    configuration: &RenderConfiguration,
24) -> Result<Vec<Variant<WithAnnotations>>, StatusCode>
25where
26    PathT: AsRef<Path>,
27{
28    let mut catalog = Vec::default();
29
30    let mut files = read_dir(directory).await.map_err_internal_server("read directory")?;
31    while let Some(file) = files.next_entry().await.map_err_internal_server("directory entry")? {
32        let file_path = file.path();
33        let (file_name, file_name_without_extension) = file_name(&file_path);
34        if file_name_without_extension != INDEX {
35            if let Some(rendered_page_type) = configuration.is_rendered_page(&file_name) {
36                let rendered_page = RenderedPage::new_from_file(rendered_page_type, &file_path, configuration)
37                    .await
38                    .map_err_internal_server("read render file")?;
39
40                let title = rendered_page.title(configuration)?;
41                let title: &str = title.as_ref().map(|title| title.as_ref()).unwrap_or(&file_name_without_extension);
42
43                let href = uri_path_join(uri_path, &file_name_without_extension);
44
45                let created = rendered_page
46                    .annotations
47                    .created
48                    .as_ref()
49                    .map(|date_time| date_time.inner.timestamp())
50                    .unwrap_or_default();
51
52                let updated = rendered_page
53                    .annotations
54                    .updated
55                    .as_ref()
56                    .map(|date_time| date_time.inner.timestamp())
57                    .unwrap_or_default();
58
59                let mut item = Map::default();
60
61                item.into_insert("title", ByteString::from(title));
62                item.into_insert("href", href);
63                item.into_insert("created", created);
64                item.into_insert("updated", updated);
65
66                for (key, column) in &annotation.extra_columns {
67                    if let Some(value) = rendered_page.annotations.traverse_variable(column) {
68                        item.into_insert(ByteString::from(*key), value.clone());
69                    }
70                }
71
72                catalog.push(item.into());
73            }
74        }
75    }
76
77    annotation.sort(&mut catalog);
78
79    Ok(catalog)
80}