diff options
author | Lars Wirzenius <liw@liw.fi> | 2023-05-10 09:10:25 +0300 |
---|---|---|
committer | Lars Wirzenius <liw@liw.fi> | 2023-05-10 09:14:34 +0300 |
commit | ace211d2c2e9c775872c4a23087763afff5a5bb2 (patch) | |
tree | f6884f4b6c3ee43c9c736f7f91e12d8a5ec98c49 /src | |
parent | 0a81c16df535853c68d5c833a213a81c2a1a9388 (diff) | |
download | subplot-ace211d2c2e9c775872c4a23087763afff5a5bb2.tar.gz |
feat! allow multiple markdown files for a subplot
Sponsored-by: author
Diffstat (limited to 'src')
-rw-r--r-- | src/bin/subplot.rs | 14 | ||||
-rw-r--r-- | src/doc.rs | 68 | ||||
-rw-r--r-- | src/metadata.rs | 16 |
3 files changed, 71 insertions, 27 deletions
diff --git a/src/bin/subplot.rs b/src/bin/subplot.rs index 41d8894..8da6c2b 100644 --- a/src/bin/subplot.rs +++ b/src/bin/subplot.rs @@ -264,8 +264,18 @@ impl Docgen { } else if let Some(date) = doc.meta().date() { date.to_string() } else { - let filename = doc.meta().basedir().join(doc.meta().markdown_filename()); - Self::mtime_formatted(Self::mtime(&filename)?) + let mut newest = None; + for filename in doc.meta().markdown_filenames() { + let mtime = Self::mtime(filename)?; + if let Some(so_far) = newest { + if mtime > so_far { + newest = Some(mtime); + } + } else { + newest = Some(mtime); + } + } + Self::mtime_formatted(newest.unwrap()) }; if Self::need_output(&mut doc, self.template.as_deref(), &self.output) { @@ -66,7 +66,7 @@ static KNOWN_BLOCK_CLASSES: &[&str] = &["numberLines", "noNumberLines"]; #[derive(Debug)] pub struct Document { subplot: PathBuf, - md: Markdown, + markdowns: Vec<Markdown>, meta: Metadata, files: EmbeddedFiles, style: Style, @@ -75,14 +75,14 @@ pub struct Document { impl Document { fn new( subplot: PathBuf, - md: Markdown, + markdowns: Vec<Markdown>, meta: Metadata, files: EmbeddedFiles, style: Style, ) -> Document { let doc = Document { subplot, - md, + markdowns, meta, files, style, @@ -95,7 +95,7 @@ impl Document { basedir: P, subplot: PathBuf, yamlmeta: &YamlMetadata, - md: Markdown, + markdowns: Vec<Markdown>, style: Style, template: Option<&str>, ) -> Result<Document, SubplotError> @@ -104,12 +104,22 @@ impl Document { { let meta = Metadata::from_yaml_metadata(basedir, yamlmeta, template)?; trace!("metadata from YAML: {:#?}", meta); - let files = md.embedded_files(); - let doc = Document::new(subplot, md, meta, files, style); + let files = Self::all_files(&markdowns); + let doc = Document::new(subplot, markdowns, meta, files, style); trace!("Loaded from JSON OK"); Ok(doc) } + fn all_files(markdowns: &[Markdown]) -> EmbeddedFiles { + let mut files = EmbeddedFiles::default(); + for md in markdowns { + for file in md.embedded_files().files() { + files.push(file.clone()); + } + } + files + } + /// Construct a Document from a named file. pub fn from_file( basedir: &Path, @@ -126,11 +136,13 @@ impl Document { let meta = load_metadata_from_yaml_file(filename)?; trace!("metadata from YAML file: {:#?}", meta); - let mdfile = meta.markdown(); - let mdfile = basedir.join(mdfile); - let md = Markdown::load_file(mdfile.as_path())?; + let mut markdowns = vec![]; + for filename in meta.markdowns() { + let filename = basedir.join(filename); + markdowns.push(Markdown::load_file(&filename)?); + } - let doc = Self::from_ast(basedir, filename.into(), &meta, md, style, template)?; + let doc = Self::from_ast(basedir, filename.into(), &meta, markdowns, style, template)?; trace!("Loaded document OK"); Ok(doc) @@ -146,7 +158,9 @@ impl Document { self.meta.set_date(date.into()); let mut body = self.typeset_meta(); - body.push_child(Content::Elt(self.md.root_element().clone())); + for md in self.markdowns.iter() { + body.push_child(Content::Elt(md.root_element().clone())); + } let page = HtmlPage::new(head, body); page.serialize().unwrap() // FIXME } @@ -230,10 +244,14 @@ impl Document { names.push(PathBuf::from(x)) } - names.push(self.meta().markdown_filename().to_path_buf()); + for name in self.meta().markdown_filenames() { + names.push(name.into()); + } - let mut images = self.md.images(); - names.append(&mut images); + for md in self.markdowns.iter() { + let mut images = md.images(); + names.append(&mut images); + } names } @@ -276,7 +294,7 @@ impl Document { /// Check that all the block classes in the document are known fn check_block_classes(&self) -> Result<(), SubplotError> { - let classes_in_doc = self.md.block_classes(); + let classes_in_doc = self.all_block_classes(); // Build the set of known good classes let mut known_classes: HashSet<String> = HashSet::new(); @@ -299,6 +317,16 @@ impl Document { } } + fn all_block_classes(&self) -> HashSet<String> { + let mut set = HashSet::new(); + for md in self.markdowns.iter() { + for class in md.block_classes() { + set.insert(class); + } + } + set + } + /// Check that all named files (in matched steps) are actually present in the /// document. pub fn check_named_files_exist( @@ -402,12 +430,18 @@ impl Document { /// Typeset a Subplot document. pub fn typeset(&mut self, warnings: &mut Warnings) { - warnings.push_all(self.md.typeset(self.style.clone(), self.meta.bindings())); + for md in self.markdowns.iter_mut() { + warnings.push_all(md.typeset(self.style.clone(), self.meta.bindings())); + } } /// Return all scenarios in a document. pub fn scenarios(&self) -> Result<Vec<Scenario>, SubplotError> { - self.md.scenarios() + let mut scenarios = vec![]; + for md in self.markdowns.iter() { + scenarios.append(&mut md.scenarios()?); + } + Ok(scenarios) } /// Return matched scenarios in a document. diff --git a/src/metadata.rs b/src/metadata.rs index d569b40..e4d3d53 100644 --- a/src/metadata.rs +++ b/src/metadata.rs @@ -63,9 +63,9 @@ impl YamlMetadata { Ok(meta) } - /// Name of file with the Markdown for the subplot document. - pub fn markdown(&self) -> &Path { - &self.markdowns[0] + /// Names of files with the Markdown for the subplot document. + pub fn markdowns(&self) -> &[PathBuf] { + &self.markdowns } /// Title. @@ -177,7 +177,7 @@ pub struct Metadata { title: String, date: Option<String>, authors: Option<Vec<String>>, - markdown_filename: PathBuf, + markdown_filenames: Vec<PathBuf>, bindings_filenames: Vec<PathBuf>, bindings: Bindings, impls: HashMap<String, DocumentImpl>, @@ -236,7 +236,7 @@ impl Metadata { title: yaml.title().into(), date: yaml.date().map(|s| s.into()), authors: yaml.authors().map(|a| a.into()), - markdown_filename: yaml.markdown().into(), + markdown_filenames: yaml.markdowns().into(), bindings_filenames, bindings, impls, @@ -273,9 +273,9 @@ impl Metadata { &self.basedir } - /// Return filename of the markdown file. - pub fn markdown_filename(&self) -> &Path { - &self.markdown_filename + /// Return filenames of the markdown files. + pub fn markdown_filenames(&self) -> &[PathBuf] { + &self.markdown_filenames } /// Return filename where bindings are specified. |