diff --git a/docker/organic_test/foreign_document_test_entrypoint.sh b/docker/organic_test/foreign_document_test_entrypoint.sh index 429554a4..3a51ce94 100644 --- a/docker/organic_test/foreign_document_test_entrypoint.sh +++ b/docker/organic_test/foreign_document_test_entrypoint.sh @@ -41,9 +41,9 @@ function main { set -e if [ "$all_status" -ne 0 ]; then - echo "$(red_text "Some tests failed.")" + red_text "Some tests failed." else - echo "$(green_text "All tests passed.")" + green_text "All tests passed." fi return "$all_status" } @@ -64,8 +64,9 @@ function indent { local depth="$1" local scaled_depth=$((depth * 2)) shift 1 - local prefix=$(printf -- "%${scaled_depth}s") - while read l; do + local prefix + prefix=$(printf -- "%${scaled_depth}s") + while read -r l; do (IFS=' '; printf -- '%s%s\n' "$prefix" "$l") done } @@ -93,12 +94,13 @@ function compare_all_org_document { local target_document local all_status=0 while read target_document; do - local relative_path=$($REALPATH --relative-to "$root_dir" "$target_document") + local relative_path + relative_path=$($REALPATH --relative-to "$root_dir" "$target_document") set +e (run_compare "$relative_path" "$target_document") if [ "$?" -ne 0 ]; then all_status=1; fi set -e - done<<<$(find "$root_dir" -type f -iname '*.org') + done<<<"$(find "$root_dir" -type f -iname '*.org' | sort)" return "$all_status" } diff --git a/org_mode_samples/sections_and_headings/odd_level_depth.org b/org_mode_samples/sections_and_headings/odd_level_depth.org index c46b3f10..f92f920b 100644 --- a/org_mode_samples/sections_and_headings/odd_level_depth.org +++ b/org_mode_samples/sections_and_headings/odd_level_depth.org @@ -5,3 +5,4 @@ *** Lorem * Ipsum **** Dolar +***** Cat diff --git a/src/parser/headline.rs b/src/parser/headline.rs index b85ae6a3..d6e57bb3 100644 --- a/src/parser/headline.rs +++ b/src/parser/headline.rs @@ -34,12 +34,13 @@ use crate::parser::object_parser::standard_set_object; use crate::parser::util::blank_line; use crate::types::DocumentElement; use crate::types::Heading; +use crate::types::HeadlineLevel; use crate::types::Object; use crate::types::PriorityCookie; use crate::types::TodoKeywordType; pub(crate) const fn heading( - parent_level: usize, + parent_level: HeadlineLevel, ) -> impl for<'b, 'g, 'r, 's> Fn( RefContext<'b, 'g, 'r, 's>, OrgSource<'s>, @@ -51,15 +52,23 @@ pub(crate) const fn heading( fn _heading<'b, 'g, 'r, 's>( context: RefContext<'b, 'g, 'r, 's>, input: OrgSource<'s>, - parent_level: usize, + parent_star_count: HeadlineLevel, ) -> Res, Heading<'s>> { not(|i| context.check_exit_matcher(i))(input)?; let ( remaining, - (headline_level, maybe_todo_keyword, maybe_priority, maybe_comment, title, heading_tags), - ) = headline(context, input, parent_level)?; + ( + headline_level, + star_count, + maybe_todo_keyword, + maybe_priority, + maybe_comment, + title, + heading_tags, + ), + ) = headline(context, input, parent_star_count)?; let section_matcher = parser_with_context!(section)(context); - let heading_matcher = parser_with_context!(heading(headline_level))(context); + let heading_matcher = parser_with_context!(heading(star_count))(context); let (remaining, maybe_section) = opt(map(section_matcher, DocumentElement::Section))(remaining)?; let (remaining, _ws) = opt(tuple((start_of_line, many0(blank_line))))(remaining)?; @@ -106,11 +115,12 @@ pub(crate) fn detect_headline<'s>(input: OrgSource<'s>) -> Res, () fn headline<'b, 'g, 'r, 's>( context: RefContext<'b, 'g, 'r, 's>, input: OrgSource<'s>, - parent_level: usize, + parent_star_count: HeadlineLevel, ) -> Res< OrgSource<'s>, ( - usize, + HeadlineLevel, + HeadlineLevel, Option<(TodoKeywordType, OrgSource<'s>)>, Option<(OrgSource<'s>, PriorityCookie)>, Option>, @@ -124,11 +134,11 @@ fn headline<'b, 'g, 'r, 's>( }); let parser_context = context.with_additional_node(&parser_context); - let (remaining, (_, (star_count, _), _)) = tuple(( + let (remaining, (_, (headline_level, star_count, _), _)) = tuple(( start_of_line, verify( parser_with_context!(headline_level)(&parser_context), - |(level, _)| *level > parent_level, + |(_, count, _)| *count > parent_star_count, ), peek(org_space), ))(input)?; @@ -159,6 +169,7 @@ fn headline<'b, 'g, 'r, 's>( Ok(( remaining, ( + headline_level, star_count, maybe_todo_keyword.map(|(_, todo, _)| todo), maybe_priority, @@ -261,9 +272,9 @@ fn priority_cookie<'s>(input: OrgSource<'s>) -> Res, PriorityCooki fn headline_level<'b, 'g, 'r, 's>( context: RefContext<'b, 'g, 'r, 's>, input: OrgSource<'s>, -) -> Res, (usize, OrgSource<'s>)> { +) -> Res, (HeadlineLevel, HeadlineLevel, OrgSource<'s>)> { let (remaining, stars) = is_a("*")(input)?; - let count = stars.len(); + let count = stars.len().try_into().unwrap(); let level = match context.get_global_settings().odd_levels_only { crate::context::HeadlineLevelFilter::Odd => { if count % 2 == 0 { @@ -274,5 +285,5 @@ fn headline_level<'b, 'g, 'r, 's>( } crate::context::HeadlineLevelFilter::OddEven => count, }; - Ok((remaining, (level, stars))) + Ok((remaining, (level, count, stars))) } diff --git a/src/types/document.rs b/src/types/document.rs index 72614f1f..1acc4688 100644 --- a/src/types/document.rs +++ b/src/types/document.rs @@ -3,6 +3,7 @@ use super::Object; use super::Source; pub type PriorityCookie = u8; +pub type HeadlineLevel = u16; #[derive(Debug)] pub struct Document<'s> { @@ -14,7 +15,7 @@ pub struct Document<'s> { #[derive(Debug)] pub struct Heading<'s> { pub source: &'s str, - pub level: usize, + pub level: HeadlineLevel, pub todo_keyword: Option<(TodoKeywordType, &'s str)>, pub priority_cookie: Option, pub title: Vec>, diff --git a/src/types/mod.rs b/src/types/mod.rs index 83666107..af286cdc 100644 --- a/src/types/mod.rs +++ b/src/types/mod.rs @@ -7,6 +7,7 @@ mod source; pub use document::Document; pub use document::DocumentElement; pub use document::Heading; +pub use document::HeadlineLevel; pub use document::PriorityCookie; pub use document::Section; pub use document::TodoKeywordType;