Compare commits

...

25 Commits

Author SHA1 Message Date
Tom Alexander
ff57242434
Merge branch 'footnote' 2023-10-29 22:29:38 -04:00
Tom Alexander
0da37b25e3
Assign the reference counts. 2023-10-29 22:29:29 -04:00
Tom Alexander
ff03140007
Order the footnotes based on when they start processing rather than when they finish.
This has the benefit of making the output order make sense when footnote definitions reference footnote references but I mostly did it to match the behavior of upstream org-mode.
2023-10-29 22:29:29 -04:00
Tom Alexander
0ae492f8d3
Promote waiting footnote definitions. 2023-10-29 22:29:29 -04:00
Tom Alexander
613d49c6ec
Record on-deck footnote definitions. 2023-10-29 22:29:29 -04:00
Tom Alexander
0f7e5eea25
no-op the template for footnote definitions. 2023-10-29 22:29:29 -04:00
Tom Alexander
2e7cfd5637
Only parse footnote definitions if they target a reference that exists. 2023-10-29 22:29:28 -04:00
Tom Alexander
afe62de2b6
Re-enable AstNode. 2023-10-29 22:29:28 -04:00
Tom Alexander
1f3b5262b8
Fix build by making the registry guarded by an ArcMutex. 2023-10-29 22:29:28 -04:00
Tom Alexander
f63620b547
Registry being mutuably borrowed. 2023-10-29 22:29:28 -04:00
Tom Alexander
671159cb82
Does not work even without IntoAstNode. 2023-10-29 22:29:28 -04:00
Tom Alexander
f1e985fb32
Lifetime issue. 2023-10-29 22:29:28 -04:00
Tom Alexander
a966be8122
Remove closures from iselector macro. 2023-10-29 22:29:28 -04:00
Tom Alexander
24b9782146
Avoid closures for the intermediate macro. 2023-10-29 22:29:28 -04:00
Tom Alexander
3d44d20384
Running into borrow issue on intermediate. 2023-10-29 18:46:14 -04:00
Tom Alexander
f98a09bc59
Use macros for creating the intermediate stage.
This is to make it easier to change function signatures by consolidating the places where the signatures exist.
2023-10-29 18:46:14 -04:00
Tom Alexander
ba511b7f9e
Add another test for footnote definitions. 2023-10-29 18:46:13 -04:00
Tom Alexander
3720558d93
Render the footnote definitions. 2023-10-29 18:46:13 -04:00
Tom Alexander
b66ec507ef
Create a render ast node type. 2023-10-29 18:46:13 -04:00
Tom Alexander
645ae26701
Remove intermediate lifetime. 2023-10-29 14:53:11 -04:00
Tom Alexander
6109902945
Create an intermediate ast node type. 2023-10-29 14:45:02 -04:00
Tom Alexander
cd27869122
Populate render context for footnote references. 2023-10-29 14:45:02 -04:00
Tom Alexander
795945f0da
Register footnote definitions. 2023-10-29 14:45:02 -04:00
Tom Alexander
cb7c28c1ae
Add intermediate lifetime. 2023-10-29 12:24:49 -04:00
Tom Alexander
52ca300de3
Beginning to hand out footnote ids. 2023-10-29 12:24:49 -04:00
83 changed files with 1864 additions and 1006 deletions

View File

@ -0,0 +1,57 @@
{@select key=.type}
{@eq value="heading"}{>heading/}{/eq}
{@eq value="section"}{>section/}{/eq}
{@eq value="paragraph"}{>paragraph/}{/eq}
{@eq value="plain_list"}{>plain_list/}{/eq}
{@eq value="center_block"}{>center_block/}{/eq}
{@eq value="quote_block"}{>quote_block/}{/eq}
{@eq value="special_block"}{>special_block/}{/eq}
{@eq value="dynamic_block"}{>dynamic_block/}{/eq}
{@eq value="footnote_definition"}{>footnote_definition/}{/eq}
{@eq value="comment"}{>comment/}{/eq}
{@eq value="drawer"}{>drawer/}{/eq}
{@eq value="property_drawer"}{>property_drawer/}{/eq}
{@eq value="table"}{>table/}{/eq}
{@eq value="verse_block"}{>verse_block/}{/eq}
{@eq value="comment_block"}{>comment_block/}{/eq}
{@eq value="example_block"}{>example_block/}{/eq}
{@eq value="export_block"}{>export_block/}{/eq}
{@eq value="src_block"}{>src_block/}{/eq}
{@eq value="clock"}{>clock/}{/eq}
{@eq value="diary_sexp"}{>diary_sexp/}{/eq}
{@eq value="planning"}{>planning/}{/eq}
{@eq value="fixed_width_area"}{>fixed_width_area/}{/eq}
{@eq value="horizontal_rule"}{>horizontal_rule/}{/eq}
{@eq value="keyword"}{>keyword/}{/eq}
{@eq value="babel_call"}{>babel_call/}{/eq}
{@eq value="latex_environment"}{>latex_environment/}{/eq}
{@eq value="bold"}{>bold/}{/eq}
{@eq value="italic"}{>italic/}{/eq}
{@eq value="underline"}{>underline/}{/eq}
{@eq value="strike_through"}{>strike_through/}{/eq}
{@eq value="code"}{>code/}{/eq}
{@eq value="verbatim"}{>verbatim/}{/eq}
{@eq value="plain_text"}{>plain_text/}{/eq}
{@eq value="regular_link"}{>regular_link/}{/eq}
{@eq value="radio_link"}{>radio_link/}{/eq}
{@eq value="radio_target"}{>radio_target/}{/eq}
{@eq value="plain_link"}{>plain_link/}{/eq}
{@eq value="angle_link"}{>angle_link/}{/eq}
{@eq value="org_macro"}{>org_macro/}{/eq}
{@eq value="entity"}{>entity/}{/eq}
{@eq value="latex_fragment"}{>latex_fragment/}{/eq}
{@eq value="export_snippet"}{>export_snippet/}{/eq}
{@eq value="footnote_reference"}{>footnote_reference/}{/eq}
{@eq value="citation"}{>citation/}{/eq}
{@eq value="citation_reference"}{>citation_reference/}{/eq}
{@eq value="inline_babel_call"}{>inline_babel_call/}{/eq}
{@eq value="inline_source_block"}{>inline_source_block/}{/eq}
{@eq value="line_break"}{>line_break/}{/eq}
{@eq value="target"}{>target/}{/eq}
{@eq value="statistics_cookie"}{>statistics_cookie/}{/eq}
{@eq value="subscript"}{>subscript/}{/eq}
{@eq value="superscript"}{>superscript/}{/eq}
{@eq value="timestamp"}{>timestamp/}{/eq}
{@none}{!TODO: make this panic!}ERROR: Unrecognized type {.type}.{/none}
{/select}
{! TODO: Maybe the final space should be conditional on end blank in the org source !}

View File

@ -10,5 +10,12 @@
{#.children}
{>document_element/}
{/.children}
{?.footnotes}
<h2>Footnotes:</h2>
{#.footnotes}
{>real_footnote_definition/}
{/.footnotes}
{/.footnotes}
</div>
</div>

View File

@ -1 +1 @@
!!!!!!!! footnote_definition
{! noop !}

View File

@ -1 +1 @@
!!!!!!!! footnote_reference
<sup><a id="{.reference_id}" href="{.definition_link}">{.label}</a></sup>

View File

@ -0,0 +1 @@
<div><sup><a id="{.definition_id}" href="{.reference_link}">{.label}</a></sup><div>{#.contents}{>ast_node/}{/.contents}</div></div>

View File

@ -0,0 +1,21 @@
# This test shows that footnote references only count if the definition containing them is rendered.
foo[fn:a:bar]
[fn:a] lorem
[fn:b] ipsum
[fn:d] fizz
[fn:c] dolar
yo[fn:b]
hello[fn:c]
[fn:e] buzz
sup[fn:d]

View File

@ -0,0 +1,25 @@
# Test proves that:
#
# - Anonymous references with identical content get unique IDs.
# - Unreferenced footnote definitions are dropped.
# - Footnote definitions that come before their first reference are dropped.
foo[fn:2:something]
bar[fn::something]
baz[fn::something]
cat[fn::something]
dog[fn:3]
[fn:3] ipsum
[fn:4] lorem
[fn:3] dolar
[fn:5] not referenced
stuff[fn:4] and things

407
src/context/ast_node.rs Normal file
View File

@ -0,0 +1,407 @@
use std::path::Path;
use serde::Serialize;
use crate::config::Config;
use crate::error::CustomError;
use crate::intermediate::IAstNode;
use super::angle_link::RenderAngleLink;
use super::babel_call::RenderBabelCall;
use super::bold::RenderBold;
use super::center_block::RenderCenterBlock;
use super::citation::RenderCitation;
use super::citation_reference::RenderCitationReference;
use super::clock::RenderClock;
use super::code::RenderCode;
use super::comment::RenderComment;
use super::comment_block::RenderCommentBlock;
use super::diary_sexp::RenderDiarySexp;
use super::drawer::RenderDrawer;
use super::dynamic_block::RenderDynamicBlock;
use super::entity::RenderEntity;
use super::example_block::RenderExampleBlock;
use super::export_block::RenderExportBlock;
use super::export_snippet::RenderExportSnippet;
use super::fixed_width_area::RenderFixedWidthArea;
use super::footnote_definition::RenderFootnoteDefinition;
use super::footnote_reference::RenderFootnoteReference;
use super::horizontal_rule::RenderHorizontalRule;
use super::inline_babel_call::RenderInlineBabelCall;
use super::inline_source_block::RenderInlineSourceBlock;
use super::italic::RenderItalic;
use super::keyword::RenderKeyword;
use super::latex_environment::RenderLatexEnvironment;
use super::latex_fragment::RenderLatexFragment;
use super::line_break::RenderLineBreak;
use super::org_macro::RenderOrgMacro;
use super::paragraph::RenderParagraph;
use super::plain_link::RenderPlainLink;
use super::plain_list::RenderPlainList;
use super::plain_text::RenderPlainText;
use super::planning::RenderPlanning;
use super::property_drawer::RenderPropertyDrawer;
use super::quote_block::RenderQuoteBlock;
use super::radio_link::RenderRadioLink;
use super::radio_target::RenderRadioTarget;
use super::regular_link::RenderRegularLink;
use super::special_block::RenderSpecialBlock;
use super::src_block::RenderSrcBlock;
use super::statistics_cookie::RenderStatisticsCookie;
use super::strike_through::RenderStrikeThrough;
use super::subscript::RenderSubscript;
use super::superscript::RenderSuperscript;
use super::table::RenderTable;
use super::target::RenderTarget;
use super::timestamp::RenderTimestamp;
use super::underline::RenderUnderline;
use super::verbatim::RenderVerbatim;
use super::verse_block::RenderVerseBlock;
use super::RenderHeading;
use super::RenderSection;
#[derive(Debug, Serialize)]
#[serde(untagged)]
pub(crate) enum RenderAstNode {
Heading(RenderHeading),
Section(RenderSection),
Paragraph(RenderParagraph),
PlainList(RenderPlainList),
CenterBlock(RenderCenterBlock),
QuoteBlock(RenderQuoteBlock),
SpecialBlock(RenderSpecialBlock),
DynamicBlock(RenderDynamicBlock),
FootnoteDefinition(RenderFootnoteDefinition),
Comment(RenderComment),
Drawer(RenderDrawer),
PropertyDrawer(RenderPropertyDrawer),
Table(RenderTable),
VerseBlock(RenderVerseBlock),
CommentBlock(RenderCommentBlock),
ExampleBlock(RenderExampleBlock),
ExportBlock(RenderExportBlock),
SrcBlock(RenderSrcBlock),
Clock(RenderClock),
DiarySexp(RenderDiarySexp),
Planning(RenderPlanning),
FixedWidthArea(RenderFixedWidthArea),
HorizontalRule(RenderHorizontalRule),
Keyword(RenderKeyword),
BabelCall(RenderBabelCall),
LatexEnvironment(RenderLatexEnvironment),
Bold(RenderBold),
Italic(RenderItalic),
Underline(RenderUnderline),
StrikeThrough(RenderStrikeThrough),
Code(RenderCode),
Verbatim(RenderVerbatim),
PlainText(RenderPlainText),
RegularLink(RenderRegularLink),
RadioLink(RenderRadioLink),
RadioTarget(RenderRadioTarget),
PlainLink(RenderPlainLink),
AngleLink(RenderAngleLink),
OrgMacro(RenderOrgMacro),
Entity(RenderEntity),
LatexFragment(RenderLatexFragment),
ExportSnippet(RenderExportSnippet),
FootnoteReference(RenderFootnoteReference),
Citation(RenderCitation),
CitationReference(RenderCitationReference),
InlineBabelCall(RenderInlineBabelCall),
InlineSourceBlock(RenderInlineSourceBlock),
LineBreak(RenderLineBreak),
Target(RenderTarget),
StatisticsCookie(RenderStatisticsCookie),
Subscript(RenderSubscript),
Superscript(RenderSuperscript),
Timestamp(RenderTimestamp),
}
pub(crate) trait IntoRenderAstNode {
fn into_render_ast_node(
&self,
config: &Config,
output_directory: &Path,
output_file: &Path,
) -> Result<RenderAstNode, CustomError>;
}
impl IntoRenderAstNode for IAstNode {
fn into_render_ast_node(
&self,
config: &Config,
output_directory: &Path,
output_file: &Path,
) -> Result<RenderAstNode, CustomError> {
match self {
IAstNode::Heading(inner) => Ok(RenderAstNode::Heading(RenderHeading::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::Section(inner) => Ok(RenderAstNode::Section(RenderSection::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::Paragraph(inner) => Ok(RenderAstNode::Paragraph(RenderParagraph::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::PlainList(inner) => Ok(RenderAstNode::PlainList(RenderPlainList::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::CenterBlock(inner) => Ok(RenderAstNode::CenterBlock(RenderCenterBlock::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::QuoteBlock(inner) => Ok(RenderAstNode::QuoteBlock(RenderQuoteBlock::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::SpecialBlock(inner) => Ok(RenderAstNode::SpecialBlock(
RenderSpecialBlock::new(config, output_directory, output_file, inner)?,
)),
IAstNode::DynamicBlock(inner) => Ok(RenderAstNode::DynamicBlock(
RenderDynamicBlock::new(config, output_directory, output_file, inner)?,
)),
IAstNode::FootnoteDefinition(inner) => Ok(RenderAstNode::FootnoteDefinition(
RenderFootnoteDefinition::new(config, output_directory, output_file, inner)?,
)),
IAstNode::Comment(inner) => Ok(RenderAstNode::Comment(RenderComment::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::Drawer(inner) => Ok(RenderAstNode::Drawer(RenderDrawer::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::PropertyDrawer(inner) => Ok(RenderAstNode::PropertyDrawer(
RenderPropertyDrawer::new(config, output_directory, output_file, inner)?,
)),
IAstNode::Table(inner) => Ok(RenderAstNode::Table(RenderTable::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::VerseBlock(inner) => Ok(RenderAstNode::VerseBlock(RenderVerseBlock::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::CommentBlock(inner) => Ok(RenderAstNode::CommentBlock(
RenderCommentBlock::new(config, output_directory, output_file, inner)?,
)),
IAstNode::ExampleBlock(inner) => Ok(RenderAstNode::ExampleBlock(
RenderExampleBlock::new(config, output_directory, output_file, inner)?,
)),
IAstNode::ExportBlock(inner) => Ok(RenderAstNode::ExportBlock(RenderExportBlock::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::SrcBlock(inner) => Ok(RenderAstNode::SrcBlock(RenderSrcBlock::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::Clock(inner) => Ok(RenderAstNode::Clock(RenderClock::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::DiarySexp(inner) => Ok(RenderAstNode::DiarySexp(RenderDiarySexp::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::Planning(inner) => Ok(RenderAstNode::Planning(RenderPlanning::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::FixedWidthArea(inner) => Ok(RenderAstNode::FixedWidthArea(
RenderFixedWidthArea::new(config, output_directory, output_file, inner)?,
)),
IAstNode::HorizontalRule(inner) => Ok(RenderAstNode::HorizontalRule(
RenderHorizontalRule::new(config, output_directory, output_file, inner)?,
)),
IAstNode::Keyword(inner) => Ok(RenderAstNode::Keyword(RenderKeyword::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::BabelCall(inner) => Ok(RenderAstNode::BabelCall(RenderBabelCall::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::LatexEnvironment(inner) => Ok(RenderAstNode::LatexEnvironment(
RenderLatexEnvironment::new(config, output_directory, output_file, inner)?,
)),
IAstNode::Bold(inner) => Ok(RenderAstNode::Bold(RenderBold::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::Italic(inner) => Ok(RenderAstNode::Italic(RenderItalic::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::Underline(inner) => Ok(RenderAstNode::Underline(RenderUnderline::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::StrikeThrough(inner) => Ok(RenderAstNode::StrikeThrough(
RenderStrikeThrough::new(config, output_directory, output_file, inner)?,
)),
IAstNode::Code(inner) => Ok(RenderAstNode::Code(RenderCode::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::Verbatim(inner) => Ok(RenderAstNode::Verbatim(RenderVerbatim::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::PlainText(inner) => Ok(RenderAstNode::PlainText(RenderPlainText::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::RegularLink(inner) => Ok(RenderAstNode::RegularLink(RenderRegularLink::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::RadioLink(inner) => Ok(RenderAstNode::RadioLink(RenderRadioLink::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::RadioTarget(inner) => Ok(RenderAstNode::RadioTarget(RenderRadioTarget::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::PlainLink(inner) => Ok(RenderAstNode::PlainLink(RenderPlainLink::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::AngleLink(inner) => Ok(RenderAstNode::AngleLink(RenderAngleLink::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::OrgMacro(inner) => Ok(RenderAstNode::OrgMacro(RenderOrgMacro::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::Entity(inner) => Ok(RenderAstNode::Entity(RenderEntity::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::LatexFragment(inner) => Ok(RenderAstNode::LatexFragment(
RenderLatexFragment::new(config, output_directory, output_file, inner)?,
)),
IAstNode::ExportSnippet(inner) => Ok(RenderAstNode::ExportSnippet(
RenderExportSnippet::new(config, output_directory, output_file, inner)?,
)),
IAstNode::FootnoteReference(inner) => Ok(RenderAstNode::FootnoteReference(
RenderFootnoteReference::new(config, output_directory, output_file, inner)?,
)),
IAstNode::Citation(inner) => Ok(RenderAstNode::Citation(RenderCitation::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::CitationReference(inner) => Ok(RenderAstNode::CitationReference(
RenderCitationReference::new(config, output_directory, output_file, inner)?,
)),
IAstNode::InlineBabelCall(inner) => Ok(RenderAstNode::InlineBabelCall(
RenderInlineBabelCall::new(config, output_directory, output_file, inner)?,
)),
IAstNode::InlineSourceBlock(inner) => Ok(RenderAstNode::InlineSourceBlock(
RenderInlineSourceBlock::new(config, output_directory, output_file, inner)?,
)),
IAstNode::LineBreak(inner) => Ok(RenderAstNode::LineBreak(RenderLineBreak::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::Target(inner) => Ok(RenderAstNode::Target(RenderTarget::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::StatisticsCookie(inner) => Ok(RenderAstNode::StatisticsCookie(
RenderStatisticsCookie::new(config, output_directory, output_file, inner)?,
)),
IAstNode::Subscript(inner) => Ok(RenderAstNode::Subscript(RenderSubscript::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::Superscript(inner) => Ok(RenderAstNode::Superscript(RenderSuperscript::new(
config,
output_directory,
output_file,
inner,
)?)),
IAstNode::Timestamp(inner) => Ok(RenderAstNode::Timestamp(RenderTimestamp::new(
config,
output_directory,
output_file,
inner,
)?)),
}
}
}

View File

@ -1,5 +1,6 @@
use serde::Serialize;
use super::footnote_definition::RenderRealFootnoteDefinition;
use super::GlobalSettings;
use super::RenderDocumentElement;
@ -15,6 +16,8 @@ pub(crate) struct RenderBlogPostPage {
self_link: Option<String>,
children: Vec<RenderDocumentElement>,
footnotes: Vec<RenderRealFootnoteDefinition>,
}
impl RenderBlogPostPage {
@ -23,12 +26,14 @@ impl RenderBlogPostPage {
title: Option<String>,
self_link: Option<String>,
children: Vec<RenderDocumentElement>,
footnotes: Vec<RenderRealFootnoteDefinition>,
) -> RenderBlogPostPage {
RenderBlogPostPage {
global_settings,
title,
self_link,
children,
footnotes,
}
}
}

View File

@ -5,6 +5,10 @@ use serde::Serialize;
use crate::config::Config;
use crate::error::CustomError;
use crate::intermediate::IFootnoteDefinition;
use crate::intermediate::IRealFootnoteDefinition;
use super::ast_node::IntoRenderAstNode;
use super::ast_node::RenderAstNode;
#[derive(Debug, Serialize)]
#[serde(tag = "type")]
@ -21,3 +25,37 @@ impl RenderFootnoteDefinition {
Ok(RenderFootnoteDefinition {})
}
}
#[derive(Debug, Serialize)]
#[serde(tag = "type")]
#[serde(rename = "footnote_reference")]
pub(crate) struct RenderRealFootnoteDefinition {
definition_id: String,
reference_link: String,
label: String,
contents: Vec<RenderAstNode>,
}
impl RenderRealFootnoteDefinition {
pub(crate) fn new(
config: &Config,
output_directory: &Path,
output_file: &Path,
original: &IRealFootnoteDefinition,
) -> Result<RenderRealFootnoteDefinition, CustomError> {
let contents = {
let mut ret = Vec::new();
for obj in original.contents.iter() {
ret.push(obj.into_render_ast_node(config, output_directory, output_file)?);
}
ret
};
Ok(RenderRealFootnoteDefinition {
definition_id: original.get_definition_id(),
reference_link: format!("#{}", original.get_reference_id()),
label: original.get_display_label(),
contents,
})
}
}

View File

@ -9,15 +9,23 @@ use crate::intermediate::IFootnoteReference;
#[derive(Debug, Serialize)]
#[serde(tag = "type")]
#[serde(rename = "footnote_reference")]
pub(crate) struct RenderFootnoteReference {}
pub(crate) struct RenderFootnoteReference {
reference_id: String,
definition_link: String,
label: String,
}
impl RenderFootnoteReference {
pub(crate) fn new(
config: &Config,
output_directory: &Path,
output_file: &Path,
comment: &IFootnoteReference,
original: &IFootnoteReference,
) -> Result<RenderFootnoteReference, CustomError> {
Ok(RenderFootnoteReference {})
Ok(RenderFootnoteReference {
reference_id: original.get_reference_id(),
definition_link: format!("#{}", original.get_definition_id()),
label: original.get_display_label(),
})
}
}

View File

@ -30,8 +30,8 @@ impl RenderHeading {
for obj in heading.title.iter() {
ret.push(RenderObject::new(
config,
&output_directory,
&output_file,
output_directory,
output_file,
obj,
)?);
}
@ -43,8 +43,8 @@ impl RenderHeading {
for obj in heading.children.iter() {
ret.push(RenderDocumentElement::new(
config,
&output_directory,
&output_file,
output_directory,
output_file,
obj,
)?);
}

View File

@ -1,4 +1,5 @@
mod angle_link;
mod ast_node;
mod babel_call;
mod blog_post_page;
mod bold;
@ -61,6 +62,7 @@ mod verse_block;
pub(crate) use blog_post_page::RenderBlogPostPage;
pub(crate) use document_element::RenderDocumentElement;
pub(crate) use element::RenderElement;
pub(crate) use footnote_definition::RenderRealFootnoteDefinition;
pub(crate) use global_settings::GlobalSettings;
pub(crate) use heading::RenderHeading;
pub(crate) use object::RenderObject;

View File

@ -27,8 +27,8 @@ impl RenderParagraph {
for obj in paragraph.children.iter() {
ret.push(RenderObject::new(
config,
&output_directory,
&output_file,
output_directory,
output_file,
obj,
)?);
}

View File

@ -33,8 +33,8 @@ impl RenderPlainList {
for obj in original.children.iter() {
ret.push(RenderPlainListItem::new(
config,
&output_directory,
&output_file,
output_directory,
output_file,
obj,
)?);
}

View File

@ -29,8 +29,8 @@ impl RenderPlainListItem {
for obj in original.tag.iter() {
ret.push(RenderObject::new(
config,
&output_directory,
&output_file,
output_directory,
output_file,
obj,
)?);
}
@ -42,8 +42,8 @@ impl RenderPlainListItem {
for obj in original.children.iter() {
ret.push(RenderElement::new(
config,
&output_directory,
&output_file,
output_directory,
output_file,
obj,
)?);
}

View File

@ -27,8 +27,8 @@ impl RenderQuoteBlock {
for obj in original.children.iter() {
ret.push(RenderElement::new(
config,
&output_directory,
&output_file,
output_directory,
output_file,
obj,
)?);
}

View File

@ -28,8 +28,8 @@ impl RenderRegularLink {
for obj in regular_link.children.iter() {
ret.push(RenderObject::new(
config,
&output_directory,
&output_file,
output_directory,
output_file,
obj,
)?);
}

View File

@ -27,8 +27,8 @@ impl RenderSection {
for obj in section.children.iter() {
ret.push(RenderElement::new(
config,
&output_directory,
&output_file,
output_directory,
output_file,
obj,
)?);
}

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IAngleLink {}
impl IAngleLink {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::AngleLink<'parse>,
) -> Result<IAngleLink, CustomError> {
Ok(IAngleLink {})
}
}
inoop!(IAngleLink, AngleLink);

View File

@ -0,0 +1,319 @@
use super::angle_link::IAngleLink;
use super::bold::IBold;
use super::citation::ICitation;
use super::citation_reference::ICitationReference;
use super::code::ICode;
use super::comment::IComment;
use super::entity::IEntity;
use super::export_snippet::IExportSnippet;
use super::footnote_reference::IFootnoteReference;
use super::inline_babel_call::IInlineBabelCall;
use super::inline_source_block::IInlineSourceBlock;
use super::italic::IItalic;
use super::keyword::IKeyword;
use super::latex_fragment::ILatexFragment;
use super::line_break::ILineBreak;
use super::org_macro::IOrgMacro;
use super::plain_link::IPlainLink;
use super::plain_text::IPlainText;
use super::radio_link::IRadioLink;
use super::radio_target::IRadioTarget;
use super::registry::Registry;
use super::regular_link::IRegularLink;
use super::statistics_cookie::IStatisticsCookie;
use super::strike_through::IStrikeThrough;
use super::subscript::ISubscript;
use super::superscript::ISuperscript;
use super::IBabelCall;
use super::ICenterBlock;
use super::IClock;
use super::ICommentBlock;
use super::IDiarySexp;
use super::IDrawer;
use super::IDynamicBlock;
use super::IExampleBlock;
use super::IExportBlock;
use super::IFixedWidthArea;
use super::IFootnoteDefinition;
use super::IHeading;
use super::IHorizontalRule;
use super::ILatexEnvironment;
use super::IParagraph;
use super::IPlainList;
use super::IPlanning;
use super::IPropertyDrawer;
use super::IQuoteBlock;
use super::ISection;
use super::ISpecialBlock;
use super::ISrcBlock;
use super::ITable;
use super::ITarget;
use super::ITimestamp;
use super::IUnderline;
use super::IVerbatim;
use super::IVerseBlock;
use super::RefRegistry;
use crate::error::CustomError;
use futures::future::{BoxFuture, FutureExt};
#[derive(Debug, Clone)]
pub(crate) enum IAstNode {
Heading(IHeading),
Section(ISection),
Paragraph(IParagraph),
PlainList(IPlainList),
CenterBlock(ICenterBlock),
QuoteBlock(IQuoteBlock),
SpecialBlock(ISpecialBlock),
DynamicBlock(IDynamicBlock),
FootnoteDefinition(IFootnoteDefinition),
Comment(IComment),
Drawer(IDrawer),
PropertyDrawer(IPropertyDrawer),
Table(ITable),
VerseBlock(IVerseBlock),
CommentBlock(ICommentBlock),
ExampleBlock(IExampleBlock),
ExportBlock(IExportBlock),
SrcBlock(ISrcBlock),
Clock(IClock),
DiarySexp(IDiarySexp),
Planning(IPlanning),
FixedWidthArea(IFixedWidthArea),
HorizontalRule(IHorizontalRule),
Keyword(IKeyword),
BabelCall(IBabelCall),
LatexEnvironment(ILatexEnvironment),
Bold(IBold),
Italic(IItalic),
Underline(IUnderline),
StrikeThrough(IStrikeThrough),
Code(ICode),
Verbatim(IVerbatim),
PlainText(IPlainText),
RegularLink(IRegularLink),
RadioLink(IRadioLink),
RadioTarget(IRadioTarget),
PlainLink(IPlainLink),
AngleLink(IAngleLink),
OrgMacro(IOrgMacro),
Entity(IEntity),
LatexFragment(ILatexFragment),
ExportSnippet(IExportSnippet),
FootnoteReference(IFootnoteReference),
Citation(ICitation),
CitationReference(ICitationReference),
InlineBabelCall(IInlineBabelCall),
InlineSourceBlock(IInlineSourceBlock),
LineBreak(ILineBreak),
Target(ITarget),
StatisticsCookie(IStatisticsCookie),
Subscript(ISubscript),
Superscript(ISuperscript),
Timestamp(ITimestamp),
}
pub(crate) trait IntoIAstNode<'parse> {
fn into_ast_node<'orig>(
&'orig self,
registry: RefRegistry<'orig, 'parse>,
) -> BoxFuture<'orig, Result<IAstNode, CustomError>>;
}
impl<'parse> IntoIAstNode<'parse> for organic::types::DocumentElement<'parse> {
fn into_ast_node<'orig>(
&'orig self,
registry: RefRegistry<'orig, 'parse>,
) -> BoxFuture<'orig, Result<IAstNode, CustomError>> {
async move {
match self {
organic::types::DocumentElement::Heading(inner) => {
Ok(IAstNode::Heading(IHeading::new(registry, inner).await?))
}
organic::types::DocumentElement::Section(inner) => {
Ok(IAstNode::Section(ISection::new(registry, inner).await?))
}
}
}
.boxed()
}
}
impl<'parse> IntoIAstNode<'parse> for organic::types::Element<'parse> {
fn into_ast_node<'orig>(
&'orig self,
registry: RefRegistry<'orig, 'parse>,
) -> BoxFuture<'orig, Result<IAstNode, CustomError>> {
async move {
match self {
organic::types::Element::Paragraph(inner) => {
Ok(IAstNode::Paragraph(IParagraph::new(registry, inner).await?))
}
organic::types::Element::PlainList(inner) => {
Ok(IAstNode::PlainList(IPlainList::new(registry, inner).await?))
}
organic::types::Element::CenterBlock(inner) => Ok(IAstNode::CenterBlock(
ICenterBlock::new(registry, inner).await?,
)),
organic::types::Element::QuoteBlock(inner) => Ok(IAstNode::QuoteBlock(
IQuoteBlock::new(registry, inner).await?,
)),
organic::types::Element::SpecialBlock(inner) => Ok(IAstNode::SpecialBlock(
ISpecialBlock::new(registry, inner).await?,
)),
organic::types::Element::DynamicBlock(inner) => Ok(IAstNode::DynamicBlock(
IDynamicBlock::new(registry, inner).await?,
)),
organic::types::Element::FootnoteDefinition(inner) => Ok(
IAstNode::FootnoteDefinition(IFootnoteDefinition::new(registry, inner).await?),
),
organic::types::Element::Comment(inner) => {
Ok(IAstNode::Comment(IComment::new(registry, inner).await?))
}
organic::types::Element::Drawer(inner) => {
Ok(IAstNode::Drawer(IDrawer::new(registry, inner).await?))
}
organic::types::Element::PropertyDrawer(inner) => Ok(IAstNode::PropertyDrawer(
IPropertyDrawer::new(registry, inner).await?,
)),
organic::types::Element::Table(inner) => {
Ok(IAstNode::Table(ITable::new(registry, inner).await?))
}
organic::types::Element::VerseBlock(inner) => Ok(IAstNode::VerseBlock(
IVerseBlock::new(registry, inner).await?,
)),
organic::types::Element::CommentBlock(inner) => Ok(IAstNode::CommentBlock(
ICommentBlock::new(registry, inner).await?,
)),
organic::types::Element::ExampleBlock(inner) => Ok(IAstNode::ExampleBlock(
IExampleBlock::new(registry, inner).await?,
)),
organic::types::Element::ExportBlock(inner) => Ok(IAstNode::ExportBlock(
IExportBlock::new(registry, inner).await?,
)),
organic::types::Element::SrcBlock(inner) => {
Ok(IAstNode::SrcBlock(ISrcBlock::new(registry, inner).await?))
}
organic::types::Element::Clock(inner) => {
Ok(IAstNode::Clock(IClock::new(registry, inner).await?))
}
organic::types::Element::DiarySexp(inner) => {
Ok(IAstNode::DiarySexp(IDiarySexp::new(registry, inner).await?))
}
organic::types::Element::Planning(inner) => {
Ok(IAstNode::Planning(IPlanning::new(registry, inner).await?))
}
organic::types::Element::FixedWidthArea(inner) => Ok(IAstNode::FixedWidthArea(
IFixedWidthArea::new(registry, inner).await?,
)),
organic::types::Element::HorizontalRule(inner) => Ok(IAstNode::HorizontalRule(
IHorizontalRule::new(registry, inner).await?,
)),
organic::types::Element::Keyword(inner) => {
Ok(IAstNode::Keyword(IKeyword::new(registry, inner).await?))
}
organic::types::Element::BabelCall(inner) => {
Ok(IAstNode::BabelCall(IBabelCall::new(registry, inner).await?))
}
organic::types::Element::LatexEnvironment(inner) => Ok(IAstNode::LatexEnvironment(
ILatexEnvironment::new(registry, inner).await?,
)),
}
}
.boxed()
}
}
impl<'parse> IntoIAstNode<'parse> for organic::types::Object<'parse> {
fn into_ast_node<'orig>(
&'orig self,
registry: RefRegistry<'orig, 'parse>,
) -> BoxFuture<'orig, Result<IAstNode, CustomError>> {
async move {
match self {
organic::types::Object::Bold(inner) => {
Ok(IAstNode::Bold(IBold::new(registry, inner).await?))
}
organic::types::Object::Italic(inner) => {
Ok(IAstNode::Italic(IItalic::new(registry, inner).await?))
}
organic::types::Object::Underline(inner) => {
Ok(IAstNode::Underline(IUnderline::new(registry, inner).await?))
}
organic::types::Object::StrikeThrough(inner) => Ok(IAstNode::StrikeThrough(
IStrikeThrough::new(registry, inner).await?,
)),
organic::types::Object::Code(inner) => {
Ok(IAstNode::Code(ICode::new(registry, inner).await?))
}
organic::types::Object::Verbatim(inner) => {
Ok(IAstNode::Verbatim(IVerbatim::new(registry, inner).await?))
}
organic::types::Object::PlainText(inner) => {
Ok(IAstNode::PlainText(IPlainText::new(registry, inner).await?))
}
organic::types::Object::RegularLink(inner) => Ok(IAstNode::RegularLink(
IRegularLink::new(registry, inner).await?,
)),
organic::types::Object::RadioLink(inner) => {
Ok(IAstNode::RadioLink(IRadioLink::new(registry, inner).await?))
}
organic::types::Object::RadioTarget(inner) => Ok(IAstNode::RadioTarget(
IRadioTarget::new(registry, inner).await?,
)),
organic::types::Object::PlainLink(inner) => {
Ok(IAstNode::PlainLink(IPlainLink::new(registry, inner).await?))
}
organic::types::Object::AngleLink(inner) => {
Ok(IAstNode::AngleLink(IAngleLink::new(registry, inner).await?))
}
organic::types::Object::OrgMacro(inner) => {
Ok(IAstNode::OrgMacro(IOrgMacro::new(registry, inner).await?))
}
organic::types::Object::Entity(inner) => {
Ok(IAstNode::Entity(IEntity::new(registry, inner).await?))
}
organic::types::Object::LatexFragment(inner) => Ok(IAstNode::LatexFragment(
ILatexFragment::new(registry, inner).await?,
)),
organic::types::Object::ExportSnippet(inner) => Ok(IAstNode::ExportSnippet(
IExportSnippet::new(registry, inner).await?,
)),
organic::types::Object::FootnoteReference(inner) => Ok(
IAstNode::FootnoteReference(IFootnoteReference::new(registry, inner).await?),
),
organic::types::Object::Citation(inner) => {
Ok(IAstNode::Citation(ICitation::new(registry, inner).await?))
}
organic::types::Object::CitationReference(inner) => Ok(
IAstNode::CitationReference(ICitationReference::new(registry, inner).await?),
),
organic::types::Object::InlineBabelCall(inner) => Ok(IAstNode::InlineBabelCall(
IInlineBabelCall::new(registry, inner).await?,
)),
organic::types::Object::InlineSourceBlock(inner) => Ok(
IAstNode::InlineSourceBlock(IInlineSourceBlock::new(registry, inner).await?),
),
organic::types::Object::LineBreak(inner) => {
Ok(IAstNode::LineBreak(ILineBreak::new(registry, inner).await?))
}
organic::types::Object::Target(inner) => {
Ok(IAstNode::Target(ITarget::new(registry, inner).await?))
}
organic::types::Object::StatisticsCookie(inner) => Ok(IAstNode::StatisticsCookie(
IStatisticsCookie::new(registry, inner).await?,
)),
organic::types::Object::Subscript(inner) => {
Ok(IAstNode::Subscript(ISubscript::new(registry, inner).await?))
}
organic::types::Object::Superscript(inner) => Ok(IAstNode::Superscript(
ISuperscript::new(registry, inner).await?,
)),
organic::types::Object::Timestamp(inner) => {
Ok(IAstNode::Timestamp(ITimestamp::new(registry, inner).await?))
}
}
}
.boxed()
}
}

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IBabelCall {}
impl IBabelCall {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::BabelCall<'parse>,
) -> Result<IBabelCall, CustomError> {
Ok(IBabelCall {})
}
}
inoop!(IBabelCall, BabelCall);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IBold {}
impl IBold {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Bold<'parse>,
) -> Result<IBold, CustomError> {
Ok(IBold {})
}
}
inoop!(IBold, Bold);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct ICenterBlock {}
impl ICenterBlock {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::CenterBlock<'parse>,
) -> Result<ICenterBlock, CustomError> {
Ok(ICenterBlock {})
}
}
inoop!(ICenterBlock, CenterBlock);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct ICitation {}
impl ICitation {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Citation<'parse>,
) -> Result<ICitation, CustomError> {
Ok(ICitation {})
}
}
inoop!(ICitation, Citation);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct ICitationReference {}
impl ICitationReference {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::CitationReference<'parse>,
) -> Result<ICitationReference, CustomError> {
Ok(ICitationReference {})
}
}
inoop!(ICitationReference, CitationReference);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IClock {}
impl IClock {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Clock<'parse>,
) -> Result<IClock, CustomError> {
Ok(IClock {})
}
}
inoop!(IClock, Clock);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct ICode {}
impl ICode {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Code<'parse>,
) -> Result<ICode, CustomError> {
Ok(ICode {})
}
}
inoop!(ICode, Code);

View File

@ -1,16 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
/// Essentially a no-op since the comment is not rendered.
#[derive(Debug)]
pub(crate) struct IComment {}
impl IComment {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
comment: &organic::types::Comment<'parse>,
) -> Result<IComment, CustomError> {
Ok(IComment {})
}
}
inoop!(IComment, Comment);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct ICommentBlock {}
impl ICommentBlock {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::CommentBlock<'parse>,
) -> Result<ICommentBlock, CustomError> {
Ok(ICommentBlock {})
}
}
inoop!(ICommentBlock, CommentBlock);

View File

@ -6,6 +6,7 @@ use crate::config::Config;
use crate::context::GlobalSettings;
use crate::context::RenderBlogPostPage;
use crate::context::RenderDocumentElement;
use crate::context::RenderRealFootnoteDefinition;
use crate::error::CustomError;
use super::BlogPost;
@ -55,11 +56,27 @@ pub(crate) fn convert_blog_post_page_to_render_context<D: AsRef<Path>, F: AsRef<
children
};
let footnotes = {
let mut ret = Vec::new();
for footnote in page.footnotes.iter() {
ret.push(RenderRealFootnoteDefinition::new(
config,
output_directory,
output_file,
footnote,
)?);
}
ret
};
let ret = RenderBlogPostPage::new(
global_settings,
page.title.clone(),
Some(link_to_blog_post),
children,
footnotes,
);
Ok(ret)
}

View File

@ -1,5 +1,7 @@
use std::path::Path;
use std::path::PathBuf;
use std::sync::Arc;
use std::sync::Mutex;
use tokio::task::JoinHandle;
use walkdir::WalkDir;
@ -43,31 +45,26 @@ impl BlogPost {
ret
};
let mut registry = Registry::new();
// Assign IDs to the targets
for (_real_path, _contents, parsed_document) in parsed_org_files.iter() {
organic::types::AstNode::from(parsed_document)
.iter_all_ast_nodes()
.for_each(|node| match node {
organic::types::AstNode::Target(target) => {
registry.get_target(target.value);
}
_ => {}
});
}
let pages = {
let mut ret = Vec::new();
for (real_path, _contents, parsed_document) in parsed_org_files.iter() {
let mut registry = Registry::new();
// Assign IDs to the targets
organic::types::AstNode::from(parsed_document)
.iter_all_ast_nodes()
.for_each(|node| match node {
organic::types::AstNode::Target(target) => {
registry.get_target(target.value);
}
_ => {}
});
let registry = Arc::new(Mutex::new(registry));
let relative_to_post_dir_path = real_path.strip_prefix(post_dir)?;
ret.push(
BlogPostPage::new(
relative_to_post_dir_path,
&mut registry,
parsed_document,
)
.await?,
BlogPostPage::new(relative_to_post_dir_path, registry, parsed_document)
.await?,
);
}
ret

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IDiarySexp {}
impl IDiarySexp {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::DiarySexp<'parse>,
) -> Result<IDiarySexp, CustomError> {
Ok(IDiarySexp {})
}
}
inoop!(IDiarySexp, DiarySexp);

View File

@ -1,31 +1,30 @@
use crate::error::CustomError;
use super::macros::iitem;
use super::macros::iselector;
use super::registry::Registry;
use super::IHeading;
use super::ISection;
use crate::error::CustomError;
use futures::future::{BoxFuture, FutureExt};
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) enum IDocumentElement {
Heading(IHeading),
Section(ISection),
}
impl IDocumentElement {
pub(crate) fn new<'parse, 'b>(
registry: &'b mut Registry<'parse>,
original: &'b organic::types::DocumentElement<'parse>,
) -> BoxFuture<'b, Result<IDocumentElement, CustomError>> {
async move {
match original {
organic::types::DocumentElement::Heading(inner) => Ok(IDocumentElement::Heading(
IHeading::new(registry, inner).await?,
)),
organic::types::DocumentElement::Section(inner) => Ok(IDocumentElement::Section(
ISection::new(registry, inner).await?,
)),
}
}
.boxed()
}
}
iselector!(IDocumentElement, DocumentElement, original, registry, {
iitem!(
registry,
original,
(
organic::types::DocumentElement::Heading,
IDocumentElement::Heading,
IHeading
),
(
organic::types::DocumentElement::Section,
IDocumentElement::Section,
ISection
),
)
});

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IDrawer {}
impl IDrawer {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Drawer<'parse>,
) -> Result<IDrawer, CustomError> {
Ok(IDrawer {})
}
}
inoop!(IDrawer, Drawer);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IDynamicBlock {}
impl IDynamicBlock {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::DynamicBlock<'parse>,
) -> Result<IDynamicBlock, CustomError> {
Ok(IDynamicBlock {})
}
}
inoop!(IDynamicBlock, DynamicBlock);

View File

@ -1,7 +1,6 @@
use crate::error::CustomError;
use super::comment::IComment;
use super::keyword::IKeyword;
use super::macros::iselector;
use super::registry::Registry;
use super::IBabelCall;
use super::ICenterBlock;
@ -25,9 +24,11 @@ use super::ISpecialBlock;
use super::ISrcBlock;
use super::ITable;
use super::IVerseBlock;
use crate::error::CustomError;
use crate::intermediate::macros::iitem;
use futures::future::{BoxFuture, FutureExt};
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) enum IElement {
Paragraph(IParagraph),
PlainList(IPlainList),
@ -55,87 +56,117 @@ pub(crate) enum IElement {
LatexEnvironment(ILatexEnvironment),
}
impl IElement {
pub(crate) fn new<'parse, 'b>(
registry: &'b mut Registry<'parse>,
elem: &'b organic::types::Element<'parse>,
) -> BoxFuture<'b, Result<IElement, CustomError>> {
async move {
match elem {
organic::types::Element::Paragraph(inner) => {
Ok(IElement::Paragraph(IParagraph::new(registry, inner).await?))
}
organic::types::Element::PlainList(inner) => {
Ok(IElement::PlainList(IPlainList::new(registry, inner).await?))
}
organic::types::Element::CenterBlock(inner) => Ok(IElement::CenterBlock(
ICenterBlock::new(registry, inner).await?,
)),
organic::types::Element::QuoteBlock(inner) => Ok(IElement::QuoteBlock(
IQuoteBlock::new(registry, inner).await?,
)),
organic::types::Element::SpecialBlock(inner) => Ok(IElement::SpecialBlock(
ISpecialBlock::new(registry, inner).await?,
)),
organic::types::Element::DynamicBlock(inner) => Ok(IElement::DynamicBlock(
IDynamicBlock::new(registry, inner).await?,
)),
organic::types::Element::FootnoteDefinition(inner) => Ok(
IElement::FootnoteDefinition(IFootnoteDefinition::new(registry, inner).await?),
),
organic::types::Element::Comment(inner) => {
Ok(IElement::Comment(IComment::new(registry, inner).await?))
}
organic::types::Element::Drawer(inner) => {
Ok(IElement::Drawer(IDrawer::new(registry, inner).await?))
}
organic::types::Element::PropertyDrawer(inner) => Ok(IElement::PropertyDrawer(
IPropertyDrawer::new(registry, inner).await?,
)),
organic::types::Element::Table(inner) => {
Ok(IElement::Table(ITable::new(registry, inner).await?))
}
organic::types::Element::VerseBlock(inner) => Ok(IElement::VerseBlock(
IVerseBlock::new(registry, inner).await?,
)),
organic::types::Element::CommentBlock(inner) => Ok(IElement::CommentBlock(
ICommentBlock::new(registry, inner).await?,
)),
organic::types::Element::ExampleBlock(inner) => Ok(IElement::ExampleBlock(
IExampleBlock::new(registry, inner).await?,
)),
organic::types::Element::ExportBlock(inner) => Ok(IElement::ExportBlock(
IExportBlock::new(registry, inner).await?,
)),
organic::types::Element::SrcBlock(inner) => {
Ok(IElement::SrcBlock(ISrcBlock::new(registry, inner).await?))
}
organic::types::Element::Clock(inner) => {
Ok(IElement::Clock(IClock::new(registry, inner).await?))
}
organic::types::Element::DiarySexp(inner) => {
Ok(IElement::DiarySexp(IDiarySexp::new(registry, inner).await?))
}
organic::types::Element::Planning(inner) => {
Ok(IElement::Planning(IPlanning::new(registry, inner).await?))
}
organic::types::Element::FixedWidthArea(inner) => Ok(IElement::FixedWidthArea(
IFixedWidthArea::new(registry, inner).await?,
)),
organic::types::Element::HorizontalRule(inner) => Ok(IElement::HorizontalRule(
IHorizontalRule::new(registry, inner).await?,
)),
organic::types::Element::Keyword(inner) => {
Ok(IElement::Keyword(IKeyword::new(registry, inner).await?))
}
organic::types::Element::BabelCall(inner) => {
Ok(IElement::BabelCall(IBabelCall::new(registry, inner).await?))
}
organic::types::Element::LatexEnvironment(inner) => Ok(IElement::LatexEnvironment(
ILatexEnvironment::new(registry, inner).await?,
)),
}
}
.boxed()
}
}
iselector!(IElement, Element, original, registry, {
iitem!(
registry,
original,
(
organic::types::Element::Paragraph,
IElement::Paragraph,
IParagraph
),
(
organic::types::Element::PlainList,
IElement::PlainList,
IPlainList
),
(
organic::types::Element::CenterBlock,
IElement::CenterBlock,
ICenterBlock
),
(
organic::types::Element::QuoteBlock,
IElement::QuoteBlock,
IQuoteBlock
),
(
organic::types::Element::SpecialBlock,
IElement::SpecialBlock,
ISpecialBlock
),
(
organic::types::Element::DynamicBlock,
IElement::DynamicBlock,
IDynamicBlock
),
(
organic::types::Element::FootnoteDefinition,
IElement::FootnoteDefinition,
IFootnoteDefinition
),
(
organic::types::Element::Comment,
IElement::Comment,
IComment
),
(organic::types::Element::Drawer, IElement::Drawer, IDrawer),
(
organic::types::Element::PropertyDrawer,
IElement::PropertyDrawer,
IPropertyDrawer
),
(organic::types::Element::Table, IElement::Table, ITable),
(
organic::types::Element::VerseBlock,
IElement::VerseBlock,
IVerseBlock
),
(
organic::types::Element::CommentBlock,
IElement::CommentBlock,
ICommentBlock
),
(
organic::types::Element::ExampleBlock,
IElement::ExampleBlock,
IExampleBlock
),
(
organic::types::Element::ExportBlock,
IElement::ExportBlock,
IExportBlock
),
(
organic::types::Element::SrcBlock,
IElement::SrcBlock,
ISrcBlock
),
(organic::types::Element::Clock, IElement::Clock, IClock),
(
organic::types::Element::DiarySexp,
IElement::DiarySexp,
IDiarySexp
),
(
organic::types::Element::Planning,
IElement::Planning,
IPlanning
),
(
organic::types::Element::FixedWidthArea,
IElement::FixedWidthArea,
IFixedWidthArea
),
(
organic::types::Element::HorizontalRule,
IElement::HorizontalRule,
IHorizontalRule
),
(
organic::types::Element::Keyword,
IElement::Keyword,
IKeyword
),
(
organic::types::Element::BabelCall,
IElement::BabelCall,
IBabelCall
),
(
organic::types::Element::LatexEnvironment,
IElement::LatexEnvironment,
ILatexEnvironment
),
)
});

View File

@ -1,19 +1,14 @@
use super::macros::intermediate;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) struct IEntity {
pub(crate) html: String,
}
impl IEntity {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Entity<'parse>,
) -> Result<IEntity, CustomError> {
Ok(IEntity {
html: original.html.to_owned(),
})
}
}
intermediate!(IEntity, Entity, original, registry, {
Ok(IEntity {
html: original.html.to_owned(),
})
});

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IExampleBlock {}
impl IExampleBlock {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::ExampleBlock<'parse>,
) -> Result<IExampleBlock, CustomError> {
Ok(IExampleBlock {})
}
}
inoop!(IExampleBlock, ExampleBlock);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IExportBlock {}
impl IExportBlock {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::ExportBlock<'parse>,
) -> Result<IExportBlock, CustomError> {
Ok(IExportBlock {})
}
}
inoop!(IExportBlock, ExportBlock);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IExportSnippet {}
impl IExportSnippet {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::ExportSnippet<'parse>,
) -> Result<IExportSnippet, CustomError> {
Ok(IExportSnippet {})
}
}
inoop!(IExportSnippet, ExportSnippet);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IFixedWidthArea {}
impl IFixedWidthArea {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::FixedWidthArea<'parse>,
) -> Result<IFixedWidthArea, CustomError> {
Ok(IFixedWidthArea {})
}
}
inoop!(IFixedWidthArea, FixedWidthArea);

View File

@ -1,15 +1,57 @@
use crate::error::CustomError;
use super::macros::intermediate;
use super::registry::register_footnote_definition;
use super::registry::Registry;
use super::IAstNode;
use crate::error::CustomError;
use crate::intermediate::RefRegistry;
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) struct IFootnoteDefinition {}
impl IFootnoteDefinition {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::FootnoteDefinition<'parse>,
) -> Result<IFootnoteDefinition, CustomError> {
intermediate!(
IFootnoteDefinition,
FootnoteDefinition,
original,
registry,
{
register_footnote_definition(registry, original.label, &original.children).await?;
Ok(IFootnoteDefinition {})
}
);
#[derive(Debug)]
pub(crate) struct IRealFootnoteDefinition {
pub(crate) footnote_id: usize,
pub(crate) contents: Vec<IAstNode>,
}
impl IRealFootnoteDefinition {
pub(crate) async fn new<'orig, 'parse>(
registry: RefRegistry<'orig, 'parse>,
footnote_id: usize,
contents: Vec<IAstNode>,
) -> Result<IRealFootnoteDefinition, CustomError> {
Ok(IRealFootnoteDefinition {
footnote_id,
contents,
})
}
pub(crate) fn get_display_label(&self) -> String {
format!("{}", self.footnote_id + 1)
}
/// Get an ID to refer to the first reference to this footnote definition.
///
/// This ID could, for example, be used for the id attribute in HTML for the reference anchor tag.
pub(crate) fn get_reference_id(&self) -> String {
format!("fnr.{}", self.get_display_label())
}
/// Get an ID to refer to the footnote definition.
///
/// This ID could, for example, be used for the id attribute in HTML for the definition anchor tag.
pub(crate) fn get_definition_id(&self) -> String {
format!("fn.{}", self.get_display_label())
}
}

View File

@ -1,15 +1,45 @@
use super::macros::intermediate;
use super::registry::get_footnote_reference_id;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug, Clone)]
pub(crate) struct IFootnoteReference {
footnote_id: usize,
duplicate_offset: usize,
}
#[derive(Debug)]
pub(crate) struct IFootnoteReference {}
intermediate!(IFootnoteReference, FootnoteReference, original, registry, {
let (footnote_id, reference_count) =
get_footnote_reference_id(registry, original.label, &original.definition).await?;
Ok(IFootnoteReference {
footnote_id,
duplicate_offset: reference_count,
})
});
impl IFootnoteReference {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::FootnoteReference<'parse>,
) -> Result<IFootnoteReference, CustomError> {
Ok(IFootnoteReference {})
pub(crate) fn get_display_label(&self) -> String {
format!("{}", self.footnote_id + 1)
}
/// Get an ID to refer to this footnote reference.
///
/// This ID could, for example, be used for the id attribute in HTML for the reference anchor tag.
pub(crate) fn get_reference_id(&self) -> String {
if self.duplicate_offset == 0 {
format!("fnr.{}", self.get_display_label())
} else {
// Org-mode makes all duplicates use "100" but I figure there is no harm in giving each a unique ID.
let append = 100 + self.duplicate_offset - 1;
format!("fnr.{}.{}", self.get_display_label(), append)
}
}
/// Get an ID to refer to the footnote definition this footnote reference references.
///
/// This ID could, for example, be used for the id attribute in HTML for the definition anchor tag.
pub(crate) fn get_definition_id(&self) -> String {
format!("fn.{}", self.get_display_label())
}
}

View File

@ -1,39 +1,34 @@
use crate::error::CustomError;
use super::macros::intermediate;
use super::registry::Registry;
use super::IDocumentElement;
use super::IObject;
use crate::error::CustomError;
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) struct IHeading {
pub(crate) level: organic::types::HeadlineLevel,
pub(crate) title: Vec<IObject>,
pub(crate) children: Vec<IDocumentElement>,
}
impl IHeading {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
heading: &organic::types::Heading<'parse>,
) -> Result<IHeading, CustomError> {
let title = {
let mut ret = Vec::new();
for obj in heading.title.iter() {
ret.push(IObject::new(registry, obj).await?);
}
ret
};
let children = {
let mut ret = Vec::new();
for obj in heading.children.iter() {
ret.push(IDocumentElement::new(registry, obj).await?);
}
ret
};
Ok(IHeading {
title,
level: heading.level,
children,
})
}
}
intermediate!(IHeading, Heading, original, registry, {
let title = {
let mut ret = Vec::new();
for obj in original.title.iter() {
ret.push(IObject::new(registry.clone(), obj).await?);
}
ret
};
let children = {
let mut ret = Vec::new();
for obj in original.children.iter() {
ret.push(IDocumentElement::new(registry.clone(), obj).await?);
}
ret
};
Ok(IHeading {
title,
level: original.level,
children,
})
});

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IHorizontalRule {}
impl IHorizontalRule {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::HorizontalRule<'parse>,
) -> Result<IHorizontalRule, CustomError> {
Ok(IHorizontalRule {})
}
}
inoop!(IHorizontalRule, HorizontalRule);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IInlineBabelCall {}
impl IInlineBabelCall {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::InlineBabelCall<'parse>,
) -> Result<IInlineBabelCall, CustomError> {
Ok(IInlineBabelCall {})
}
}
inoop!(IInlineBabelCall, InlineBabelCall);

View File

@ -1,19 +1,14 @@
use super::macros::intermediate;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) struct IInlineSourceBlock {
pub(crate) value: String,
}
impl IInlineSourceBlock {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::InlineSourceBlock<'parse>,
) -> Result<IInlineSourceBlock, CustomError> {
Ok(IInlineSourceBlock {
value: original.value.to_owned(),
})
}
}
intermediate!(IInlineSourceBlock, InlineSourceBlock, original, registry, {
Ok(IInlineSourceBlock {
value: original.value.to_owned(),
})
});

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IItalic {}
impl IItalic {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Italic<'parse>,
) -> Result<IItalic, CustomError> {
Ok(IItalic {})
}
}
inoop!(IItalic, Italic);

View File

@ -1,16 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
/// Essentially a no-op since the keyword is not rendered and any relevant impact on other elements is pulled from the parsed form of keyword.
#[derive(Debug)]
pub(crate) struct IKeyword {}
impl IKeyword {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
keyword: &organic::types::Keyword<'parse>,
) -> Result<IKeyword, CustomError> {
Ok(IKeyword {})
}
}
inoop!(IKeyword, Keyword);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct ILatexEnvironment {}
impl ILatexEnvironment {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::LatexEnvironment<'parse>,
) -> Result<ILatexEnvironment, CustomError> {
Ok(ILatexEnvironment {})
}
}
inoop!(ILatexEnvironment, LatexEnvironment);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct ILatexFragment {}
impl ILatexFragment {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::LatexFragment<'parse>,
) -> Result<ILatexFragment, CustomError> {
Ok(ILatexFragment {})
}
}
inoop!(ILatexFragment, LatexFragment);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct ILineBreak {}
impl ILineBreak {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::LineBreak<'parse>,
) -> Result<ILineBreak, CustomError> {
Ok(ILineBreak {})
}
}
inoop!(ILineBreak, LineBreak);

View File

@ -0,0 +1,74 @@
/// Write the implementation for the intermediate ast node for a type that is a noop or is not yet implemented.
///
/// This exists to make changing the type signature easier.
macro_rules! inoop {
($istruct:ident, $pstruct:ident) => {
#[derive(Debug, Clone)]
pub(crate) struct $istruct {}
impl $istruct {
pub(crate) async fn new<'reg, 'orig, 'parse>(
registry: crate::intermediate::RefRegistry<'orig, 'parse>,
original: &'orig organic::types::$pstruct<'parse>,
) -> Result<$istruct, CustomError> {
Ok($istruct {})
}
}
};
}
pub(crate) use inoop;
/// Write the implementation for the intermediate ast node.
///
/// This exists to make changing the type signature easier.
macro_rules! intermediate {
($istruct:ident, $pstruct:ident, $original:ident, $registry:ident, $fnbody:tt) => {
impl $istruct {
pub(crate) async fn new<'orig, 'parse>(
registry: crate::intermediate::RefRegistry<'orig, 'parse>,
original: &'orig organic::types::$pstruct<'parse>,
) -> Result<$istruct, CustomError> {
let $original = original;
let $registry = registry;
$fnbody
}
}
};
}
pub(crate) use intermediate;
/// Write the implementation for the intermediate ast node.
///
/// This exists to make changing the type signature easier.
macro_rules! iselector {
($istruct:ident, $pstruct:ident, $original:ident, $registry:ident, $fnbody:tt) => {
impl $istruct {
pub(crate) fn new<'orig, 'parse>(
registry: crate::intermediate::RefRegistry<'orig, 'parse>,
original: &'orig organic::types::$pstruct<'parse>,
) -> BoxFuture<'orig, Result<$istruct, CustomError>> {
let $registry = registry;
let $original = original;
async move { $fnbody }.boxed()
}
}
};
}
pub(crate) use iselector;
macro_rules! iitem {
($registry:expr, $original:expr, $(($penum:path, $ienum:path, $istruct:ident),)*) => {
match $original {
$(
$penum(inner) => Ok($ienum(
$istruct::new($registry.clone(), inner).await?,
)),
)*
}
};
}
pub(crate) use iitem;

View File

@ -1,4 +1,5 @@
mod angle_link;
mod ast_node;
mod babel_call;
mod bold;
mod center_block;
@ -31,6 +32,7 @@ mod keyword;
mod latex_environment;
mod latex_fragment;
mod line_break;
mod macros;
mod object;
mod org_macro;
mod page;
@ -61,6 +63,7 @@ mod util;
mod verbatim;
mod verse_block;
pub(crate) use angle_link::IAngleLink;
pub(crate) use ast_node::IAstNode;
pub(crate) use babel_call::IBabelCall;
pub(crate) use bold::IBold;
pub(crate) use center_block::ICenterBlock;
@ -83,6 +86,7 @@ pub(crate) use export_block::IExportBlock;
pub(crate) use export_snippet::IExportSnippet;
pub(crate) use fixed_width_area::IFixedWidthArea;
pub(crate) use footnote_definition::IFootnoteDefinition;
pub(crate) use footnote_definition::IRealFootnoteDefinition;
pub(crate) use footnote_reference::IFootnoteReference;
pub(crate) use heading::IHeading;
pub(crate) use horizontal_rule::IHorizontalRule;
@ -120,3 +124,6 @@ pub(crate) use timestamp::ITimestamp;
pub(crate) use underline::IUnderline;
pub(crate) use verbatim::IVerbatim;
pub(crate) use verse_block::IVerseBlock;
pub(crate) type RefRegistry<'orig, 'parse> =
std::sync::Arc<std::sync::Mutex<registry::Registry<'orig, 'parse>>>;

View File

@ -1,4 +1,5 @@
use crate::error::CustomError;
use crate::intermediate::macros::iitem;
use super::angle_link::IAngleLink;
use super::bold::IBold;
@ -13,6 +14,7 @@ use super::inline_source_block::IInlineSourceBlock;
use super::italic::IItalic;
use super::latex_fragment::ILatexFragment;
use super::line_break::ILineBreak;
use super::macros::iselector;
use super::org_macro::IOrgMacro;
use super::plain_link::IPlainLink;
use super::plain_text::IPlainText;
@ -30,7 +32,7 @@ use super::verbatim::IVerbatim;
use super::ITarget;
use futures::future::{BoxFuture, FutureExt};
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) enum IObject {
Bold(IBold),
Italic(IItalic),
@ -61,96 +63,124 @@ pub(crate) enum IObject {
Timestamp(ITimestamp),
}
impl IObject {
pub(crate) fn new<'parse, 'b>(
registry: &'b mut Registry<'parse>,
obj: &'b organic::types::Object<'parse>,
) -> BoxFuture<'b, Result<IObject, CustomError>> {
async move {
match obj {
organic::types::Object::Bold(inner) => {
Ok(IObject::Bold(IBold::new(registry, inner).await?))
}
organic::types::Object::Italic(inner) => {
Ok(IObject::Italic(IItalic::new(registry, inner).await?))
}
organic::types::Object::Underline(inner) => {
Ok(IObject::Underline(IUnderline::new(registry, inner).await?))
}
organic::types::Object::StrikeThrough(inner) => Ok(IObject::StrikeThrough(
IStrikeThrough::new(registry, inner).await?,
)),
organic::types::Object::Code(inner) => {
Ok(IObject::Code(ICode::new(registry, inner).await?))
}
organic::types::Object::Verbatim(inner) => {
Ok(IObject::Verbatim(IVerbatim::new(registry, inner).await?))
}
organic::types::Object::PlainText(inner) => {
Ok(IObject::PlainText(IPlainText::new(registry, inner).await?))
}
organic::types::Object::RegularLink(inner) => Ok(IObject::RegularLink(
IRegularLink::new(registry, inner).await?,
)),
organic::types::Object::RadioLink(inner) => {
Ok(IObject::RadioLink(IRadioLink::new(registry, inner).await?))
}
organic::types::Object::RadioTarget(inner) => Ok(IObject::RadioTarget(
IRadioTarget::new(registry, inner).await?,
)),
organic::types::Object::PlainLink(inner) => {
Ok(IObject::PlainLink(IPlainLink::new(registry, inner).await?))
}
organic::types::Object::AngleLink(inner) => {
Ok(IObject::AngleLink(IAngleLink::new(registry, inner).await?))
}
organic::types::Object::OrgMacro(inner) => {
Ok(IObject::OrgMacro(IOrgMacro::new(registry, inner).await?))
}
organic::types::Object::Entity(inner) => {
Ok(IObject::Entity(IEntity::new(registry, inner).await?))
}
organic::types::Object::LatexFragment(inner) => Ok(IObject::LatexFragment(
ILatexFragment::new(registry, inner).await?,
)),
organic::types::Object::ExportSnippet(inner) => Ok(IObject::ExportSnippet(
IExportSnippet::new(registry, inner).await?,
)),
organic::types::Object::FootnoteReference(inner) => Ok(IObject::FootnoteReference(
IFootnoteReference::new(registry, inner).await?,
)),
organic::types::Object::Citation(inner) => {
Ok(IObject::Citation(ICitation::new(registry, inner).await?))
}
organic::types::Object::CitationReference(inner) => Ok(IObject::CitationReference(
ICitationReference::new(registry, inner).await?,
)),
organic::types::Object::InlineBabelCall(inner) => Ok(IObject::InlineBabelCall(
IInlineBabelCall::new(registry, inner).await?,
)),
organic::types::Object::InlineSourceBlock(inner) => Ok(IObject::InlineSourceBlock(
IInlineSourceBlock::new(registry, inner).await?,
)),
organic::types::Object::LineBreak(inner) => {
Ok(IObject::LineBreak(ILineBreak::new(registry, inner).await?))
}
organic::types::Object::Target(inner) => {
Ok(IObject::Target(ITarget::new(registry, inner).await?))
}
organic::types::Object::StatisticsCookie(inner) => Ok(IObject::StatisticsCookie(
IStatisticsCookie::new(registry, inner).await?,
)),
organic::types::Object::Subscript(inner) => {
Ok(IObject::Subscript(ISubscript::new(registry, inner).await?))
}
organic::types::Object::Superscript(inner) => Ok(IObject::Superscript(
ISuperscript::new(registry, inner).await?,
)),
organic::types::Object::Timestamp(inner) => {
Ok(IObject::Timestamp(ITimestamp::new(registry, inner).await?))
}
}
}
.boxed()
}
}
iselector!(IObject, Object, original, registry, {
iitem!(
registry,
original,
(organic::types::Object::Bold, IObject::Bold, IBold),
(organic::types::Object::Italic, IObject::Italic, IItalic),
(
organic::types::Object::Underline,
IObject::Underline,
IUnderline
),
(
organic::types::Object::StrikeThrough,
IObject::StrikeThrough,
IStrikeThrough
),
(organic::types::Object::Code, IObject::Code, ICode),
(
organic::types::Object::Verbatim,
IObject::Verbatim,
IVerbatim
),
(
organic::types::Object::PlainText,
IObject::PlainText,
IPlainText
),
(
organic::types::Object::RegularLink,
IObject::RegularLink,
IRegularLink
),
(
organic::types::Object::RadioLink,
IObject::RadioLink,
IRadioLink
),
(
organic::types::Object::RadioTarget,
IObject::RadioTarget,
IRadioTarget
),
(
organic::types::Object::PlainLink,
IObject::PlainLink,
IPlainLink
),
(
organic::types::Object::AngleLink,
IObject::AngleLink,
IAngleLink
),
(
organic::types::Object::OrgMacro,
IObject::OrgMacro,
IOrgMacro
),
(organic::types::Object::Entity, IObject::Entity, IEntity),
(
organic::types::Object::LatexFragment,
IObject::LatexFragment,
ILatexFragment
),
(
organic::types::Object::ExportSnippet,
IObject::ExportSnippet,
IExportSnippet
),
(
organic::types::Object::FootnoteReference,
IObject::FootnoteReference,
IFootnoteReference
),
(
organic::types::Object::Citation,
IObject::Citation,
ICitation
),
(
organic::types::Object::CitationReference,
IObject::CitationReference,
ICitationReference
),
(
organic::types::Object::InlineBabelCall,
IObject::InlineBabelCall,
IInlineBabelCall
),
(
organic::types::Object::InlineSourceBlock,
IObject::InlineSourceBlock,
IInlineSourceBlock
),
(
organic::types::Object::LineBreak,
IObject::LineBreak,
ILineBreak
),
(organic::types::Object::Target, IObject::Target, ITarget),
(
organic::types::Object::StatisticsCookie,
IObject::StatisticsCookie,
IStatisticsCookie
),
(
organic::types::Object::Subscript,
IObject::Subscript,
ISubscript
),
(
organic::types::Object::Superscript,
IObject::Superscript,
ISuperscript
),
(
organic::types::Object::Timestamp,
IObject::Timestamp,
ITimestamp
),
)
});

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IOrgMacro {}
impl IOrgMacro {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::OrgMacro<'parse>,
) -> Result<IOrgMacro, CustomError> {
Ok(IOrgMacro {})
}
}
inoop!(IOrgMacro, OrgMacro);

View File

@ -2,10 +2,12 @@ use std::path::PathBuf;
use crate::error::CustomError;
use super::footnote_definition::IRealFootnoteDefinition;
use super::registry::Registry;
use super::IDocumentElement;
use super::IHeading;
use super::ISection;
use super::RefRegistry;
#[derive(Debug)]
pub(crate) struct BlogPostPage {
@ -15,31 +17,51 @@ pub(crate) struct BlogPostPage {
pub(crate) title: Option<String>,
pub(crate) children: Vec<IDocumentElement>,
pub(crate) footnotes: Vec<IRealFootnoteDefinition>,
}
impl BlogPostPage {
pub(crate) async fn new<'parse, P: Into<PathBuf>>(
// TODO: Move path into the registry so I can give this a standard interface like the others.
pub(crate) async fn new<'a, 'b, 'parse, P: Into<PathBuf>>(
path: P,
registry: &mut Registry<'parse>,
document: &organic::types::Document<'parse>,
registry: RefRegistry<'b, 'parse>,
document: &'b organic::types::Document<'parse>,
) -> Result<BlogPostPage, CustomError> {
let path = path.into();
let mut children = Vec::new();
if let Some(section) = document.zeroth_section.as_ref() {
children.push(IDocumentElement::Section(
ISection::new(registry, section).await?,
ISection::new(registry.clone(), section).await?,
));
}
for heading in document.children.iter() {
children.push(IDocumentElement::Heading(
IHeading::new(registry, heading).await?,
IHeading::new(registry.clone(), heading).await?,
));
}
let footnotes = {
let footnote_definitions: Vec<_> = {
let registry = registry.lock().unwrap();
let ret = registry
.get_footnote_ids()
.map(|(id, def)| (id, def.clone()))
.collect();
ret
};
let mut ret = Vec::new();
for (id, def) in footnote_definitions.into_iter() {
ret.push(IRealFootnoteDefinition::new(registry.clone(), id, def).await?);
}
ret
};
Ok(BlogPostPage {
path,
title: get_title(&document),
children,
footnotes,
})
}

View File

@ -1,26 +1,21 @@
use crate::error::CustomError;
use super::macros::intermediate;
use super::registry::Registry;
use super::IObject;
use crate::error::CustomError;
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) struct IParagraph {
pub(crate) children: Vec<IObject>,
}
impl IParagraph {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
paragraph: &organic::types::Paragraph<'parse>,
) -> Result<IParagraph, CustomError> {
let children = {
let mut ret = Vec::new();
for obj in paragraph.children.iter() {
ret.push(IObject::new(registry, obj).await?);
}
ret
};
intermediate!(IParagraph, Paragraph, original, registry, {
let children = {
let mut ret = Vec::new();
for obj in original.children.iter() {
ret.push(IObject::new(registry.clone(), obj).await?);
}
ret
};
Ok(IParagraph { children })
}
}
Ok(IParagraph { children })
});

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IPlainLink {}
impl IPlainLink {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::PlainLink<'parse>,
) -> Result<IPlainLink, CustomError> {
Ok(IPlainLink {})
}
}
inoop!(IPlainLink, PlainLink);

View File

@ -1,30 +1,25 @@
use crate::error::CustomError;
use super::macros::intermediate;
use super::registry::Registry;
use super::IPlainListItem;
use crate::error::CustomError;
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) struct IPlainList {
pub(crate) list_type: organic::types::PlainListType,
pub(crate) children: Vec<IPlainListItem>,
}
impl IPlainList {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
plain_list: &organic::types::PlainList<'parse>,
) -> Result<IPlainList, CustomError> {
let children = {
let mut ret = Vec::new();
for obj in plain_list.children.iter() {
ret.push(IPlainListItem::new(registry, obj).await?);
}
ret
};
intermediate!(IPlainList, PlainList, original, registry, {
let children = {
let mut ret = Vec::new();
for obj in original.children.iter() {
ret.push(IPlainListItem::new(registry.clone(), obj).await?);
}
ret
};
Ok(IPlainList {
list_type: plain_list.list_type,
children,
})
}
}
Ok(IPlainList {
list_type: original.list_type,
children,
})
});

View File

@ -1,36 +1,31 @@
use crate::error::CustomError;
use super::macros::intermediate;
use super::registry::Registry;
use super::IElement;
use super::IObject;
use crate::error::CustomError;
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) struct IPlainListItem {
pub(crate) tag: Vec<IObject>,
pub(crate) children: Vec<IElement>,
}
impl IPlainListItem {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
plain_list_item: &organic::types::PlainListItem<'parse>,
) -> Result<IPlainListItem, CustomError> {
let tag = {
let mut ret = Vec::new();
for obj in plain_list_item.tag.iter() {
ret.push(IObject::new(registry, obj).await?);
}
ret
};
intermediate!(IPlainListItem, PlainListItem, original, registry, {
let tag = {
let mut ret = Vec::new();
for obj in original.tag.iter() {
ret.push(IObject::new(registry.clone(), obj).await?);
}
ret
};
let children = {
let mut ret = Vec::new();
for elem in plain_list_item.children.iter() {
ret.push(IElement::new(registry, elem).await?);
}
ret
};
let children = {
let mut ret = Vec::new();
for elem in original.children.iter() {
ret.push(IElement::new(registry.clone(), elem).await?);
}
ret
};
Ok(IPlainListItem { tag, children })
}
}
Ok(IPlainListItem { tag, children })
});

View File

@ -1,20 +1,15 @@
use crate::error::CustomError;
use crate::intermediate::util::coalesce_whitespace;
use super::macros::intermediate;
use super::registry::Registry;
use super::util::coalesce_whitespace;
use crate::error::CustomError;
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) struct IPlainText {
pub(crate) source: String,
}
impl IPlainText {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
plain_text: &organic::types::PlainText<'parse>,
) -> Result<IPlainText, CustomError> {
Ok(IPlainText {
source: coalesce_whitespace(plain_text.source).into_owned(),
})
}
}
intermediate!(IPlainText, PlainText, original, registry, {
Ok(IPlainText {
source: coalesce_whitespace(original.source).into_owned(),
})
});

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IPlanning {}
impl IPlanning {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Planning<'parse>,
) -> Result<IPlanning, CustomError> {
Ok(IPlanning {})
}
}
inoop!(IPlanning, Planning);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IPropertyDrawer {}
impl IPropertyDrawer {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::PropertyDrawer<'parse>,
) -> Result<IPropertyDrawer, CustomError> {
Ok(IPropertyDrawer {})
}
}
inoop!(IPropertyDrawer, PropertyDrawer);

View File

@ -1,26 +1,21 @@
use crate::error::CustomError;
use super::macros::intermediate;
use super::registry::Registry;
use super::IElement;
use crate::error::CustomError;
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) struct IQuoteBlock {
pub(crate) children: Vec<IElement>,
}
impl IQuoteBlock {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::QuoteBlock<'parse>,
) -> Result<IQuoteBlock, CustomError> {
let children = {
let mut ret = Vec::new();
for obj in original.children.iter() {
ret.push(IElement::new(registry, obj).await?);
}
ret
};
intermediate!(IQuoteBlock, QuoteBlock, original, registry, {
let children = {
let mut ret = Vec::new();
for obj in original.children.iter() {
ret.push(IElement::new(registry.clone(), obj).await?);
}
ret
};
Ok(IQuoteBlock { children })
}
}
Ok(IQuoteBlock { children })
});

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IRadioLink {}
impl IRadioLink {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::RadioLink<'parse>,
) -> Result<IRadioLink, CustomError> {
Ok(IRadioLink {})
}
}
inoop!(IRadioLink, RadioLink);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IRadioTarget {}
impl IRadioTarget {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::RadioTarget<'parse>,
) -> Result<IRadioTarget, CustomError> {
Ok(IRadioTarget {})
}
}
inoop!(IRadioTarget, RadioTarget);

View File

@ -1,24 +1,201 @@
use crate::error::CustomError;
use organic::types::Element;
use organic::types::Object;
use std::collections::HashMap;
use super::ast_node::IAstNode;
use super::ast_node::IntoIAstNode;
use super::RefRegistry;
type IdCounter = u16;
pub(crate) struct Registry<'parse> {
pub(crate) struct Registry<'orig, 'parse> {
id_counter: IdCounter,
targets: HashMap<&'parse str, String>,
footnote_ids: Vec<(Option<&'parse str>, Vec<IAstNode>)>,
footnote_reference_counts: HashMap<&'parse str, usize>,
on_deck_footnote_ids: HashMap<&'parse str, &'orig Vec<Element<'parse>>>,
}
impl<'parse> Registry<'parse> {
pub(crate) fn new() -> Registry<'parse> {
impl<'orig, 'parse> Registry<'orig, 'parse> {
pub(crate) fn new() -> Registry<'orig, 'parse> {
Registry {
id_counter: 0,
targets: HashMap::new(),
footnote_ids: Vec::new(),
footnote_reference_counts: HashMap::new(),
on_deck_footnote_ids: HashMap::new(),
}
}
pub(crate) fn get_target<'b>(&'b mut self, body: &'parse str) -> &'b String {
pub(crate) fn get_target<'reg>(&'reg mut self, body: &'parse str) -> &'reg String {
self.targets.entry(body).or_insert_with(|| {
self.id_counter += 1;
format!("target_{}", self.id_counter)
})
}
pub(crate) fn get_footnote_ids(&self) -> impl Iterator<Item = (usize, &Vec<IAstNode>)> {
self.footnote_ids
.iter()
.map(|(_label, definition)| definition)
.enumerate()
}
}
/// Get a 0-indexed ID for a footnote.
///
/// This needs to be incremented to be 1-indexed for render.
pub(crate) async fn get_footnote_reference_id<'orig, 'parse>(
registry: RefRegistry<'orig, 'parse>,
label: Option<&'parse str>,
definition: &'orig Vec<Object<'parse>>,
) -> Result<(usize, usize), CustomError> {
if let None = label {
// If it has no label then it must always get a new ID.
let contents = convert_reference_contents(registry.clone(), definition).await?;
let pos = {
let mut registry = registry.lock().unwrap();
registry.footnote_ids.push((None, contents));
registry.footnote_ids.len() - 1
};
return Ok((pos, 0));
}
let reference_count = if let Some(label) = label {
promote_footnote_definition(registry.clone(), label).await?;
let mut registry = registry.lock().unwrap();
let reference_count = registry
.footnote_reference_counts
.entry(label)
.and_modify(|count| *count += 1)
.or_insert(0);
*reference_count
} else {
0
};
let existing_index = registry
.lock()
.unwrap()
.footnote_ids
.iter()
.position(|(id, _definition)| *id == label);
if let Some(existing_id) = existing_index {
if !definition.is_empty() {
let contents = convert_reference_contents(registry.clone(), definition).await?;
let mut registry = registry.lock().unwrap();
let entry = registry
.footnote_ids
.get_mut(existing_id)
.expect("If-statement proves this to be Some.");
entry.1 = contents;
}
Ok((existing_id, reference_count))
} else {
let existing_id = {
let mut registry = registry.lock().unwrap();
registry.footnote_ids.push((label, Vec::new()));
registry.footnote_ids.len() - 1
};
let contents = convert_reference_contents(registry.clone(), definition).await?;
{
let mut registry = registry.lock().unwrap();
let entry = registry
.footnote_ids
.get_mut(existing_id)
.expect("If-statement proves this to be Some.");
entry.1 = contents;
}
Ok((existing_id, reference_count))
}
}
/// Update the definition to a footnote but do not mark it as referenced.
pub(crate) async fn register_footnote_definition<'orig, 'parse>(
registry: RefRegistry<'orig, 'parse>,
label: &'parse str,
definition: &'orig Vec<Element<'parse>>,
) -> Result<(), CustomError> {
let has_existing: bool = {
let mut registry = registry.lock().unwrap();
registry
.footnote_ids
.iter_mut()
.any(|(id, _definition)| *id == Some(label))
};
if !has_existing {
let mut registry = registry.lock().unwrap();
registry.on_deck_footnote_ids.insert(label, definition);
return Ok(());
}
let contents = convert_definition_contents(registry.clone(), definition).await?;
let mut registry = registry.lock().unwrap();
if let Some((_existing_id, existing_definition)) = registry
.footnote_ids
.iter_mut()
.find(|(id, _definition)| *id == Some(label))
{
*existing_definition = contents;
}
Ok(())
}
async fn convert_reference_contents<'orig, 'parse>(
registry: RefRegistry<'orig, 'parse>,
contents: &'orig Vec<Object<'parse>>,
) -> Result<Vec<IAstNode>, CustomError> {
let contents = {
let mut ret = Vec::new();
for obj in contents.iter() {
ret.push(obj.into_ast_node(registry.clone()).await?);
}
ret
};
Ok(contents)
}
async fn convert_definition_contents<'orig, 'parse>(
registry: RefRegistry<'orig, 'parse>,
contents: &'orig Vec<Element<'parse>>,
) -> Result<Vec<IAstNode>, CustomError> {
let contents = {
let mut ret = Vec::new();
for obj in contents.iter() {
ret.push(obj.into_ast_node(registry.clone()).await?);
}
ret
};
Ok(contents)
}
/// Take a footnote definition that has not yet received a reference and move it into the active footnotes.
pub(crate) async fn promote_footnote_definition<'orig, 'parse>(
registry: RefRegistry<'orig, 'parse>,
label: &'parse str,
) -> Result<(), CustomError> {
let definition = {
let mut registry = registry.lock().unwrap();
let definition = registry.on_deck_footnote_ids.remove(label);
definition
};
if let Some(elements) = definition {
let existing_id = {
let mut registry = registry.lock().unwrap();
registry.footnote_ids.push((Some(label), Vec::new()));
registry.footnote_ids.len() - 1
};
let contents = convert_definition_contents(registry.clone(), elements).await?;
{
let mut registry = registry.lock().unwrap();
let entry = registry
.footnote_ids
.get_mut(existing_id)
.expect("If-statement proves this to be Some.");
entry.1 = contents;
}
}
Ok(())
}

View File

@ -1,29 +1,24 @@
use crate::error::CustomError;
use super::macros::intermediate;
use super::registry::Registry;
use super::IObject;
use crate::error::CustomError;
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) struct IRegularLink {
pub(crate) raw_link: String,
pub(crate) children: Vec<IObject>,
}
impl IRegularLink {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::RegularLink<'parse>,
) -> Result<IRegularLink, CustomError> {
let children = {
let mut ret = Vec::new();
for obj in original.children.iter() {
ret.push(IObject::new(registry, obj).await?);
}
ret
};
Ok(IRegularLink {
raw_link: original.get_raw_link().into_owned(),
children,
})
}
}
intermediate!(IRegularLink, RegularLink, original, registry, {
let children = {
let mut ret = Vec::new();
for obj in original.children.iter() {
ret.push(IObject::new(registry.clone(), obj).await?);
}
ret
};
Ok(IRegularLink {
raw_link: original.get_raw_link().into_owned(),
children,
})
});

View File

@ -1,26 +1,21 @@
use crate::error::CustomError;
use super::macros::intermediate;
use super::registry::Registry;
use super::IElement;
use crate::error::CustomError;
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) struct ISection {
pub(crate) children: Vec<IElement>,
}
impl ISection {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
section: &organic::types::Section<'parse>,
) -> Result<ISection, CustomError> {
let children = {
let mut ret = Vec::new();
for elem in section.children.iter() {
ret.push(IElement::new(registry, elem).await?);
}
ret
};
intermediate!(ISection, Section, original, registry, {
let children = {
let mut ret = Vec::new();
for elem in original.children.iter() {
ret.push(IElement::new(registry.clone(), elem).await?);
}
ret
};
Ok(ISection { children })
}
}
Ok(ISection { children })
});

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct ISpecialBlock {}
impl ISpecialBlock {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::SpecialBlock<'parse>,
) -> Result<ISpecialBlock, CustomError> {
Ok(ISpecialBlock {})
}
}
inoop!(ISpecialBlock, SpecialBlock);

View File

@ -1,22 +1,17 @@
use super::macros::intermediate;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) struct ISrcBlock {
pub(crate) lines: Vec<String>,
}
impl ISrcBlock {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::SrcBlock<'parse>,
) -> Result<ISrcBlock, CustomError> {
let lines = original
.contents
.split_inclusive('\n')
.map(|s| s.to_owned())
.collect();
Ok(ISrcBlock { lines })
}
}
intermediate!(ISrcBlock, SrcBlock, original, registry, {
let lines = original
.contents
.split_inclusive('\n')
.map(|s| s.to_owned())
.collect();
Ok(ISrcBlock { lines })
});

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IStatisticsCookie {}
impl IStatisticsCookie {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::StatisticsCookie<'parse>,
) -> Result<IStatisticsCookie, CustomError> {
Ok(IStatisticsCookie {})
}
}
inoop!(IStatisticsCookie, StatisticsCookie);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IStrikeThrough {}
impl IStrikeThrough {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::StrikeThrough<'parse>,
) -> Result<IStrikeThrough, CustomError> {
Ok(IStrikeThrough {})
}
}
inoop!(IStrikeThrough, StrikeThrough);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct ISubscript {}
impl ISubscript {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Subscript<'parse>,
) -> Result<ISubscript, CustomError> {
Ok(ISubscript {})
}
}
inoop!(ISubscript, Subscript);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct ISuperscript {}
impl ISuperscript {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Superscript<'parse>,
) -> Result<ISuperscript, CustomError> {
Ok(ISuperscript {})
}
}
inoop!(ISuperscript, Superscript);

View File

@ -1,15 +1,5 @@
use super::macros::inoop;
use super::registry::Registry;
use crate::error::CustomError;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct ITable {}
impl ITable {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Table<'parse>,
) -> Result<ITable, CustomError> {
Ok(ITable {})
}
}
inoop!(ITable, Table);

View File

@ -1,23 +1,18 @@
use crate::error::CustomError;
use crate::intermediate::util::coalesce_whitespace;
use super::macros::intermediate;
use super::registry::Registry;
use crate::error::CustomError;
#[derive(Debug)]
#[derive(Debug, Clone)]
pub(crate) struct ITarget {
pub(crate) id: String,
value: String,
}
impl ITarget {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
target: &organic::types::Target<'parse>,
) -> Result<ITarget, CustomError> {
let id = registry.get_target(target.value);
Ok(ITarget {
id: id.clone(),
value: target.value.to_owned(),
})
}
}
intermediate!(ITarget, Target, original, registry, {
let mut registry = registry.lock().unwrap();
let id = registry.get_target(original.value);
Ok(ITarget {
id: id.clone(),
value: original.value.to_owned(),
})
});

View File

@ -1,15 +1,6 @@
use crate::error::CustomError;
use super::macros::inoop;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct ITimestamp {}
impl ITimestamp {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Timestamp<'parse>,
) -> Result<ITimestamp, CustomError> {
Ok(ITimestamp {})
}
}
inoop!(ITimestamp, Timestamp);

View File

@ -1,15 +1,6 @@
use crate::error::CustomError;
use super::macros::inoop;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IUnderline {}
impl IUnderline {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Underline<'parse>,
) -> Result<IUnderline, CustomError> {
Ok(IUnderline {})
}
}
inoop!(IUnderline, Underline);

View File

@ -1,15 +1,6 @@
use crate::error::CustomError;
use super::macros::inoop;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IVerbatim {}
impl IVerbatim {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::Verbatim<'parse>,
) -> Result<IVerbatim, CustomError> {
Ok(IVerbatim {})
}
}
inoop!(IVerbatim, Verbatim);

View File

@ -1,15 +1,6 @@
use crate::error::CustomError;
use super::macros::inoop;
use super::registry::Registry;
#[derive(Debug)]
pub(crate) struct IVerseBlock {}
impl IVerseBlock {
pub(crate) async fn new<'parse>(
registry: &mut Registry<'parse>,
original: &organic::types::VerseBlock<'parse>,
) -> Result<IVerseBlock, CustomError> {
Ok(IVerseBlock {})
}
}
inoop!(IVerseBlock, VerseBlock);