Skip to content
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.

Commit 4f9d1e6

Browse files
committedApr 3, 2023
feat: add the ability to order articles
1 parent d3c66c3 commit 4f9d1e6

File tree

2 files changed

+102
-2
lines changed

2 files changed

+102
-2
lines changed
 

‎src/parser.rs

+100
Original file line numberDiff line numberDiff line change
@@ -107,6 +107,7 @@ impl ParserStateMachine {
107107

108108
#[derive(Debug, Clone)]
109109
pub struct Article {
110+
pub order: i16,
110111
pub topic: String,
111112
pub content: String,
112113
pub path: String,
@@ -150,6 +151,27 @@ enum Keyword {
150151
* ```
151152
*/
152153
Article,
154+
/**
155+
* @Article Syntax
156+
* `@Order <Order of the Article>` is for controlling the order of the article sections.
157+
*
158+
* Example:
159+
*
160+
* ```rust
161+
* /**
162+
* * @Article Usage example
163+
* * @Order 2
164+
* * ## Header2
165+
* */
166+
*
167+
* /**
168+
* * @Article Usage example
169+
* * @Order 1
170+
* * # Header1
171+
* */
172+
* ```
173+
*/
174+
Order,
153175
/**
154176
* @Article Syntax
155177
* `@FileArticle` allows you to mark a whole file is a source of documentation for a specified
@@ -229,6 +251,7 @@ enum Keyword {
229251
impl Keyword {
230252
fn as_str(&self) -> &'static str {
231253
match *self {
254+
Keyword::Order => "@Order",
232255
Keyword::Article => "@Article",
233256
Keyword::FileArticle => "@FileArticle",
234257
Keyword::Ignore => "@Ignore",
@@ -262,6 +285,7 @@ impl Parser {
262285

263286
let articles: Vec<Article> = vec![];
264287
let current_article = Article {
288+
order: 0,
265289
topic: String::from(""),
266290
content: String::from(""),
267291
path: String::from(""),
@@ -327,6 +351,14 @@ impl Parser {
327351
result
328352
}
329353

354+
fn parse_article_order(&self, order_block_line: String) -> i16 {
355+
order_block_line
356+
.replace(Keyword::Order.as_str(), "")
357+
.trim()
358+
.parse()
359+
.unwrap_or(0)
360+
}
361+
330362
fn trim_article_line(&self, line: String) -> String {
331363
line.trim_start()
332364
.trim_start_matches(self.comment_symbol)
@@ -336,6 +368,7 @@ impl Parser {
336368

337369
fn new_article(&self) -> Article {
338370
Article {
371+
order: 0,
339372
topic: String::from(""),
340373
content: String::from(""),
341374
path: String::from(""),
@@ -350,6 +383,7 @@ impl Parser {
350383
let topic = name_chunks[2..].join(".");
351384

352385
vec![Article {
386+
order: 0,
353387
topic,
354388
content: String::from(file_content),
355389
path: String::from(file_path),
@@ -429,6 +463,13 @@ impl Parser {
429463
self.current_article.topic = self.trim_article_line(topic);
430464
self.current_article.start_line = line_number;
431465
self.state_machine.to_article_mut();
466+
} else if trimmed_line.starts_with(Keyword::Order.as_str())
467+
&& self.state_machine.is_in(ParserState::ArticleParsing)
468+
{
469+
let parsed_order = self.parse_article_order(trimmed_line);
470+
471+
self.current_article.order = parsed_order;
472+
self.current_article.start_line = line_number;
432473
} else if trimmed_line.starts_with(Keyword::Ignore.as_str()) {
433474
self.state_machine.to_skippintg_mut();
434475
self.current_article = self.new_article();
@@ -484,6 +525,7 @@ impl Parser {
484525
line_number += 1;
485526
}
486527

528+
self.articles.sort_by_key(|a| a.order);
487529
self.articles.clone()
488530
}
489531

@@ -559,6 +601,7 @@ pub fn test () {}
559601

560602
let articles = parser.parse_file(file_content, "");
561603
let expected_result = vec![Article {
604+
order: 0,
562605
topic: String::from("Test article"),
563606
content: String::from("some text"),
564607
path: "".to_string(),
@@ -569,6 +612,48 @@ pub fn test () {}
569612
assert_eq!(articles, expected_result);
570613
}
571614

615+
#[test]
616+
fn parse_articles_with_custom_order() {
617+
let mut parser = Parser::new(get_test_config());
618+
let file_content = "
619+
/**
620+
* @Article Test article3
621+
* @Order 3
622+
* some text3
623+
*/
624+
pub fn test () {}
625+
626+
/**
627+
* @Article Test article1
628+
* @Order 1
629+
* some text
630+
*/
631+
pub fn test2 () {}
632+
";
633+
634+
let articles = parser.parse_file(file_content, "");
635+
let expected_result = vec![
636+
Article {
637+
order: 1,
638+
topic: String::from("Test article1"),
639+
content: String::from("some text"),
640+
path: "".to_string(),
641+
start_line: 11,
642+
end_line: 12,
643+
},
644+
Article {
645+
order: 3,
646+
topic: String::from("Test article3"),
647+
content: String::from("some text3"),
648+
path: "".to_string(),
649+
start_line: 4,
650+
end_line: 5,
651+
},
652+
];
653+
654+
assert_eq!(articles, expected_result);
655+
}
656+
572657
#[test]
573658
fn ignore_comments_with_ignore_mark() {
574659
let mut parser = Parser::new(get_test_config());
@@ -604,6 +689,7 @@ pub fn test () {}
604689

605690
let articles = parser.parse_file(file_content, "");
606691
let expected_result = vec![Article {
692+
order: 0,
607693
topic: String::from("Test article"),
608694
content: String::from("some multiline\nawesome text"),
609695
path: "".to_string(),
@@ -650,6 +736,7 @@ pub fn test () {}
650736

651737
let articles = parser.parse_file(file_content, "");
652738
let expected_result = vec![Article {
739+
order: 0,
653740
topic: String::from("Test article"),
654741
content: String::from("```rust\nfn main() {\n println!(\"Hello world!\");\n}\n```\n\n```rust\nfn test() {\n println!(\"Hello world!\");\n}\n```"),
655742
path: "".to_string(),
@@ -684,6 +771,7 @@ fn parse_documentation_with_indentation_before_comments() {
684771

685772
let articles = parser.parse_file(file_content, "");
686773
let expected_result = vec![Article {
774+
order: 0,
687775
topic: String::from("Test article"),
688776
content: String::from("#### [no-implicit-coercion](https://eslint.org/docs/rules/no-implicit-coercion)\nAll implicit coercions except `!!` are disallowed:\n```js\n// Fail\n+foo\n1 * foo\n\'\' + foo\n`${foo}`\n~foo.indexOf(bar)\n\n// Pass\n!!foo\n```"),
689777
path: "".to_string(),
@@ -714,6 +802,7 @@ pub fn test () {}
714802

715803
let articles = parser.parse_file(file_content, "");
716804
let expected_result = vec![Article {
805+
order: 0,
717806
topic: String::from("Test article"),
718807
content: String::from("List:\n* Item 1\n* Item 2\n\n Item 2 subtext\n* Item 3"),
719808
path: "".to_string(),
@@ -738,6 +827,7 @@ use std::io::prelude::*;
738827

739828
let articles = parser.parse_file(file_content, "");
740829
let expected_result = vec![Article {
830+
order: 0,
741831
topic: String::from("Test article"),
742832
content: String::from(""),
743833
path: "".to_string(),
@@ -760,6 +850,7 @@ test
760850

761851
let articles = parser.parse_file(file_content, "");
762852
let expected_result = vec![Article {
853+
order: 0,
763854
topic: String::from("Test article"),
764855
content: String::from("test"),
765856
path: "".to_string(),
@@ -784,6 +875,7 @@ const b = 2
784875

785876
let articles = parser.parse_file(file_content, "");
786877
let expected_result = vec![Article {
878+
order: 0,
787879
topic: String::from("Test article"),
788880
content: String::from("test"),
789881
path: "".to_string(),
@@ -816,13 +908,15 @@ fn use_global_article_attribute() {
816908
let articles = parser.parse_file(file_content, "");
817909
let expected_result = vec![
818910
Article {
911+
order: 0,
819912
topic: String::from("Test article"),
820913
content: String::from("test"),
821914
path: "".to_string(),
822915
start_line: 6,
823916
end_line: 7,
824917
},
825918
Article {
919+
order: 0,
826920
topic: String::from("Test article"),
827921
content: String::from("test"),
828922
path: "".to_string(),
@@ -856,6 +950,7 @@ fn ignore_sections_in_case_of_global_article() {
856950

857951
let articles = parser.parse_file(file_content, "");
858952
let expected_result = vec![Article {
953+
order: 0,
859954
topic: String::from("Test article"),
860955
content: String::from("test"),
861956
path: "".to_string(),
@@ -881,6 +976,7 @@ const TIMEOUT = 3000
881976

882977
let articles = parser.parse_file(file_content, "");
883978
let expected_result = vec![Article {
979+
order: 0,
884980
topic: String::from("Test article"),
885981
content: String::from("Request timeout:\n```js/\nconst TIMEOUT = 3000\n```"),
886982
path: "".to_string(),
@@ -908,6 +1004,7 @@ const TIMEOUT = 3000
9081004

9091005
let articles = parser.parse_file(file_content, "");
9101006
let expected_result = vec![Article {
1007+
order: 0,
9111008
topic: String::from("Test article"),
9121009
content: String::from("Request timeout:\n```js/\nconst TIMEOUT = 3000\n```"),
9131010
path: "".to_string(),
@@ -933,6 +1030,7 @@ fn parse_code_block_attribute_from_ending_comment_only() {
9331030

9341031
let articles = parser.parse_file(file_content, "");
9351032
let expected_result = vec![Article {
1033+
order: 0,
9361034
topic: String::from("Test article"),
9371035
content: String::from("Should ignore @CodeBlockEnd in a text block\n```rust/\n...\n```"),
9381036
path: "".to_string(),
@@ -960,6 +1058,7 @@ fn parse_nested_commends() {
9601058

9611059
let articles = parser.parse_file(file_content, "");
9621060
let expected_result = vec![Article {
1061+
order: 0,
9631062
topic: String::from("Test article"),
9641063
content: String::from("Example:\n/**\n* @Article Example article\n* Example\n*/\ntest"),
9651064
path: "".to_string(),
@@ -998,6 +1097,7 @@ fn parse_fdoc_file_check() {
9981097
let parser = Parser::new(get_test_config());
9991098
let result = parser.parse_fdoc_file("test", "/some/long/path/to/file.fdoc.md");
10001099
let expected_result = vec![Article {
1100+
order: 0,
10011101
topic: String::from("file"),
10021102
content: String::from("test"),
10031103
path: "/some/long/path/to/file.fdoc.md".to_string(),

‎src/plugins.rs

+2-2
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@ pub struct Plugins {
2828
* {{ #your-plugin-name
2929
* any text here
3030
* }}
31-
*
31+
*
3232
* ```
3333
*
3434
* To create a plugin for parsing these blocks, you should add a file called `your-plugin-name.html.lua` into the plugins folder. By default, it's `./plugins`, but it's possible to change it in the config file.
@@ -44,7 +44,7 @@ pub struct Plugins {
4444
*
4545
* ```lua
4646
* function transform(text)
47-
* result = 'transformted text'
47+
* result = 'transformted text'
4848
* end
4949
* ```
5050
*

0 commit comments

Comments
 (0)
Please sign in to comment.