Skip to content

Commit

Permalink
Merge pull request #6 from mohe2015/attribute-with-dash
Browse files Browse the repository at this point in the history
implement attributes with dash
  • Loading branch information
mohe2015 authored Oct 17, 2024
2 parents 389e645 + 9e0e6e4 commit c46f618
Show file tree
Hide file tree
Showing 5 changed files with 98 additions and 12 deletions.
16 changes: 16 additions & 0 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions async-zero-cost-templating-proc-macro2/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -18,3 +18,4 @@ syn = { default-features = false, version = "2.0", features = [
] }
tracing = "0.1"
tracing-subscriber = "0.3"
itertools = "0.13"
17 changes: 13 additions & 4 deletions async-zero-cost-templating-proc-macro2/src/intermediate.rs
Original file line number Diff line number Diff line change
@@ -1,12 +1,12 @@
use itertools::Itertools as _;
use proc_macro2::{Span, TokenStream};
use syn::{
spanned::Spanned,
token::{Brace, Paren},
};

use crate::parse::{
HtmlElement, HtmlForLoop, HtmlIf, HtmlInAttributeContext, HtmlInAttributeValueContext,
HtmlInElementContext, HtmlWhile,
DashOrColon, HtmlElement, HtmlForLoop, HtmlIf, HtmlInAttributeContext, HtmlInAttributeValueContext, HtmlInElementContext, HtmlWhile
};

pub enum Intermediate {
Expand All @@ -23,8 +23,17 @@ impl From<HtmlInAttributeContext> for Vec<Intermediate> {
match value {
HtmlInAttributeContext::Literal(key, value) => Vec::from_iter(
[Intermediate::Literal(
" ".to_owned() + &key.to_string(),
key.span(),
" ".to_owned() + &key.pairs()
.map(|p| {
p.value().to_string()
+ match p.punct() {
Some(DashOrColon::Colon(_)) => ":",
Some(DashOrColon::Dash(_)) => "-",
None => "",
}
})
.join(""),
key.first().unwrap().span(),
)]
.into_iter()
.chain(
Expand Down
60 changes: 52 additions & 8 deletions async-zero-cost-templating-proc-macro2/src/parse.rs
Original file line number Diff line number Diff line change
Expand Up @@ -7,13 +7,7 @@ use std::{
use proc_macro2::{Delimiter, TokenStream, TokenTree};
use proc_macro2_diagnostics::{Diagnostic, SpanDiagnosticExt};
use syn::{
braced, bracketed,
ext::IdentExt,
parenthesized,
parse::{Parse, ParseStream},
spanned::Spanned,
token::{Brace, Bracket, Else, For, If, In, Paren, While},
Ident, LitStr, Token,
braced, bracketed, ext::IdentExt, parenthesized, parse::{Parse, ParseStream}, punctuated::Punctuated, spanned::Spanned, token::{Brace, Bracket, Else, For, If, In, Paren, While}, Ident, LitStr, Token
};
use tracing::instrument;
use tracing::{error, level_filters::LevelFilter};
Expand Down Expand Up @@ -197,9 +191,16 @@ pub enum HtmlInAttributeValueContext {
For(HtmlForLoop<Vec<HtmlInAttributeValueContext>>),
}


#[derive(Debug)]
pub enum DashOrColon {
Dash(Token![-]),
Colon(Token![:]),
}

#[derive(Debug)]
pub enum HtmlInAttributeContext {
Literal(Ident, Option<(Token![=], Vec<HtmlInAttributeValueContext>)>),
Literal(Punctuated<Ident, DashOrColon>, Option<(Token![=], Vec<HtmlInAttributeValueContext>)>),
Computation((Brace, TokenStream)),
If(HtmlIf<Vec<HtmlInAttributeContext>>),
While(HtmlWhile<Vec<HtmlInAttributeContext>>),
Expand Down Expand Up @@ -422,6 +423,48 @@ impl MyParse<HtmlInAttributeValueContext> for ParseStream<'_> {
}
}

impl MyParse<DashOrColon> for ParseStream<'_> {
fn inner_my_parse(self) -> Result<(DashOrColon, Vec<Diagnostic>), Vec<Diagnostic>> {
let lookahead = self.lookahead1();
let dash_or_colon = if lookahead.peek(Token![-]) {
self.parse().map(DashOrColon::Dash).map_err(|err| Vec::from([Diagnostic::from(err)]))?
} else if lookahead.peek(Token![:]) {
self.parse().map(DashOrColon::Colon).map_err(|err| Vec::from([Diagnostic::from(err)]))?
} else {
return Err(Vec::from([Diagnostic::from(lookahead.error())]))
};
Ok((dash_or_colon, vec![]))
}
}

impl MyParse<Punctuated<Ident, DashOrColon>> for ParseStream<'_> {
fn inner_my_parse(self) -> Result<(Punctuated<Ident, DashOrColon>, Vec<Diagnostic>), Vec<Diagnostic>> {
let mut diagnostics = Vec::new();
let mut ident: Punctuated<Ident, DashOrColon> = Punctuated::new();
ident.push_value({
let value: Ident;
(value, diagnostics) =
MyParse::my_parse(self, identity, identity, diagnostics)?;
value
});
while self.peek(Token![-]) || self.peek(Token![:]) {
ident.push_punct({
let value: DashOrColon;
(value, diagnostics) =
MyParse::my_parse(self, identity, identity, diagnostics)?;
value
});
ident.push_value({
let value: Ident;
(value, diagnostics) =
MyParse::my_parse(self, identity, identity, diagnostics)?;
value
});
}
Ok((ident, diagnostics))
}
}

impl MyParse<HtmlInAttributeContext> for ParseStream<'_> {
#[instrument(err(Debug), ret, name = "Html<Inner>")]
fn inner_my_parse(self) -> Result<(HtmlInAttributeContext, Vec<Diagnostic>), Vec<Diagnostic>> {
Expand Down Expand Up @@ -452,6 +495,7 @@ impl MyParse<HtmlInAttributeContext> for ParseStream<'_> {
diagnostics,
)?)
} else if lookahead.peek(Ident::peek_any) {
// here
Ok((
HtmlInAttributeContext::Literal(
{
Expand Down
16 changes: 16 additions & 0 deletions async-zero-cost-templating/tests/attribute_with_dash.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
extern crate alloc;

use async_zero_cost_templating::html;
use async_zero_cost_templating::TemplateToStream;
use core::pin::pin;
use futures_util::stream::StreamExt;

#[tokio::test]
async fn test() {
let stream = html! {
<a aria-current="true">
</a>
};
let result: String = stream.collect().await;
assert_eq!(result, r#"<a aria-current="true"></a>"#)
}

0 comments on commit c46f618

Please sign in to comment.