use tramlines_core::grammar::{Scope, derivation, str_of};
use super::MdLowerer;
use crate::{
Spanned,
grammar::{Heading, Shape, Text, has_hole},
};
impl MdLowerer<'_> {
pub(super) fn heading(&mut self, section: &Spanned) -> Heading {
let plain = |shape| Heading {
shape,
key: None,
unique: Scope::Document,
key_derives_from: None,
example: None,
};
let Some(node) = section.get("heading") else {
return plain(Shape::Text(Text::Literal(String::new())));
};
if let Some(s) = node.as_str() {
if has_hole(s) {
self.fail(
node.line,
"TL_66",
format!(
"heading `{s}` holds a hole: write `heading: {{ template: …, example: … }}`, since a template carries an example"
),
);
}
return plain(Shape::Text(Text::Literal(s.to_string())));
}
if let Some(key) = node
.as_map()
.filter(|m| m.len() == 1)
.and_then(|_| str_of(node, "from"))
{
return plain(Shape::Text(Text::From(key)));
}
self.explained(node, &["template", "pattern"], true);
let shape = self
.shape(node)
.unwrap_or_else(|| Shape::Text(Text::Literal(String::new())));
if let Some(r) = section.get("renamed-from") {
self.fail(
r.line,
"TLMD_143",
"`renamed-from` beside a heading that varies: a former heading is rewritten to exact text",
);
}
let key = str_of(node, "key");
if let Some(k) = &key {
self.check_key(node.line, k, Some(&shape), None);
}
Heading {
shape,
key,
unique: Scope::parse(str_of(node, "unique").as_deref()),
key_derives_from: node.get("key-derives-from").map(derivation),
example: str_of(node, "example"),
}
}
}