From b1091bbb450092efab9ce15c3a91e9b14efbbb32 Mon Sep 17 00:00:00 2001 From: Vladislav Nikonov Date: Fri, 30 Oct 2020 18:02:07 +0200 Subject: [PATCH] Implemented emoji aliases support in markdown files (#1194) * Implemented emoji aliases support in markdown files * Added emoji aliases rendering unit tests * Added bench for emoji --- Cargo.lock | 11 +++++++ components/config/src/config/mod.rs | 4 +++ components/rendering/Cargo.toml | 1 + components/rendering/benches/all.rs | 29 ++++++++++++++----- components/rendering/src/markdown.rs | 13 +++++++-- components/rendering/tests/markdown.rs | 25 ++++++++++++++++ .../getting-started/configuration.md | 4 +++ 7 files changed, 77 insertions(+), 10 deletions(-) diff --git a/Cargo.lock b/Cargo.lock index c552723e..82ab5c02 100644 --- a/Cargo.lock +++ b/Cargo.lock @@ -761,6 +761,16 @@ dependencies = [ "wasi 0.9.0+wasi-snapshot-preview1", ] +[[package]] +name = "gh-emoji" +version = "1.0.3" +source = "registry+https://github.com/rust-lang/crates.io-index" +checksum = "a17a050b7eb420553344e1cf1db648e8b584c79e98b74e6e6d119eeedd9ddcbc" +dependencies = [ + "phf", + "regex", +] + [[package]] name = "gif" version = "0.11.1" @@ -1975,6 +1985,7 @@ dependencies = [ "config", "errors", "front_matter", + "gh-emoji", "lazy_static", "link_checker", "pest", diff --git a/components/config/src/config/mod.rs b/components/config/src/config/mod.rs index 07236282..36ca1386 100644 --- a/components/config/src/config/mod.rs +++ b/components/config/src/config/mod.rs @@ -106,6 +106,9 @@ pub struct Config { /// The search config, telling what to include in the search index pub search: search::Search, + /// Whether to render emoji aliases (e.g.: :smile: => 😄) in the markdown files + pub emoji_rendering: bool, + /// All user params set in [extra] in the config pub extra: HashMap, } @@ -337,6 +340,7 @@ impl Default for Config { slugify: slugify::Slugify::default(), search: search::Search::default(), extra: HashMap::new(), + emoji_rendering: false, } } } diff --git a/components/rendering/Cargo.toml b/components/rendering/Cargo.toml index 9cca92fb..a8496aa0 100644 --- a/components/rendering/Cargo.toml +++ b/components/rendering/Cargo.toml @@ -15,6 +15,7 @@ pest = "2" pest_derive = "2" regex = "1" lazy_static = "1" +gh-emoji = "1.0" errors = { path = "../errors" } front_matter = { path = "../front_matter" } diff --git a/components/rendering/benches/all.rs b/components/rendering/benches/all.rs index ea16e63f..3f2dda15 100644 --- a/components/rendering/benches/all.rs +++ b/components/rendering/benches/all.rs @@ -17,12 +17,12 @@ Lorem markdownum litora, care ponto nomina, et ut aspicit gelidas sui et purpureo genuit. Tamen colla venientis [delphina](http://nil-sol.com/ecquis) Tusci et temptata citaeque curam isto ubi vult vulnere reppulit. -- Seque vidit flendoque de quodam -- Dabit minimos deiecto caputque noctis pluma -- Leti coniunx est Helicen -- Illius pulvereumque Icare inpositos -- Vivunt pereo pluvio tot ramos Olenios gelidis -- Quater teretes natura inde +- :one: Seque vidit flendoque de quodam +- :two: Dabit minimos deiecto caputque noctis pluma +- :three: Leti coniunx est Helicen +- :four: Illius pulvereumque Icare inpositos +- :five: Vivunt pereo pluvio tot ramos Olenios gelidis +- :six: Quater teretes natura inde ### A subsection @@ -35,7 +35,7 @@ granum captantur potuisse Minervae, frugum. > Clivo sub inprovisoque nostrum minus fama est, discordia patrem petebat precatur absumitur, poena per sit. Foramina *tamen cupidine* memor supplex tollentes dictum unam orbem, Anubis caecae. Viderat formosior tegebat satis, Aethiopasque -sit submisso coniuge tristis ubi! +sit submisso coniuge tristis ubi! :exclamation: ## Praeceps Corinthus totidem quem crus vultum cape @@ -68,7 +68,7 @@ And a shortcode: ### Another subsection Gotta make the toc do a little bit of work -# A big title +# A big title :fire: - hello - world @@ -123,3 +123,16 @@ fn bench_render_shortcodes_one_present(b: &mut test::Bencher) { b.iter(|| render_shortcodes(CONTENT, &context)); } + +#[bench] +fn bench_render_content_no_shortcode_with_emoji(b: &mut test::Bencher) { + let tera = Tera::default(); + let content2 = CONTENT.replace(r#"{{ youtube(id="my_youtube_id") }}"#, ""); + let mut config = Config::default(); + config.highlight_code = false; + config.emoji_rendering = true; + let permalinks_ctx = HashMap::new(); + let context = RenderContext::new(&tera, &config, "", &permalinks_ctx, InsertAnchor::None); + + b.iter(|| render_content(&content2, &context).unwrap()); +} diff --git a/components/rendering/src/markdown.rs b/components/rendering/src/markdown.rs index b60dc0ed..e0aa0277 100644 --- a/components/rendering/src/markdown.rs +++ b/components/rendering/src/markdown.rs @@ -168,6 +168,10 @@ fn get_heading_refs(events: &[Event]) -> Vec { } pub fn markdown_to_html(content: &str, context: &RenderContext) -> Result { + lazy_static! { + static ref EMOJI_REPLACER: gh_emoji::Replacer = gh_emoji::Replacer::new(); + } + // the rendered html let mut html = String::with_capacity(content.len()); // Set while parsing @@ -198,8 +202,13 @@ pub fn markdown_to_html(content: &str, context: &RenderContext) -> Result { diff --git a/components/rendering/tests/markdown.rs b/components/rendering/tests/markdown.rs index 6dea602e..fb344bf7 100644 --- a/components/rendering/tests/markdown.rs +++ b/components/rendering/tests/markdown.rs @@ -1036,3 +1036,28 @@ Again more text"#; let res = render_content(markdown_string, &context).unwrap(); assert_eq!(res.body, expected); } + +#[test] +fn can_render_emoji_alias() { + let permalinks_ctx = HashMap::new(); + let mut config = Config::default(); + config.emoji_rendering = true; + let context = RenderContext::new(&ZOLA_TERA, &config, "", &permalinks_ctx, InsertAnchor::None); + let res = render_content("Hello, World! :smile:", &context).unwrap(); + assert_eq!( + res.body, + "

Hello, World! 😄

\n" + ); +} + +#[test] +fn emoji_aliases_are_ignored_when_disabled_in_config() { + let permalinks_ctx = HashMap::new(); + let config = Config::default(); + let context = RenderContext::new(&ZOLA_TERA, &config, "", &permalinks_ctx, InsertAnchor::None); + let res = render_content("Hello, World! :smile:", &context).unwrap(); + assert_eq!( + res.body, + "

Hello, World! :smile:

\n" + ); +} \ No newline at end of file diff --git a/docs/content/documentation/getting-started/configuration.md b/docs/content/documentation/getting-started/configuration.md index 028f0a4d..c881bbcc 100644 --- a/docs/content/documentation/getting-started/configuration.md +++ b/docs/content/documentation/getting-started/configuration.md @@ -61,6 +61,10 @@ generate_feed = false # files are always copied, regardless of this setting. # hard_link_static = false +# When set to "true", emoji aliases translated to their corresponding +# Unicode emoji equivalent in the rendered Markdown files. (e.g.: :smile: => 😄) +# emoji_rendering = false + # The taxonomies to be rendered for the site and their configuration. # Example: # taxonomies = [