From 3e59aced00958cc7d7b7f6b582ed46e91b01bfca Mon Sep 17 00:00:00 2001 From: Syndamia Date: Tue, 31 Dec 2024 19:10:22 +0200 Subject: feat(single): Implement autolinks --- single.awk | 37 +++++++++++++++++++++++++++++++++++-- 1 file changed, 35 insertions(+), 2 deletions(-) (limited to 'single.awk') diff --git a/single.awk b/single.awk index 3568844..0add85e 100644 --- a/single.awk +++ b/single.awk @@ -18,8 +18,8 @@ # [x] Images # [x] Inline # [x] Reference -# [ ] Other -# [ ] Autolinks +# [.] Other +# [x] Autolinks # [ ] Escapes # # [ ] Non-standard features @@ -72,6 +72,15 @@ function restore_match() { RLENGTH = backup_rlength } +BEGIN { + ## This is used to convert email autolinks into a series of hex values + ## Escaped output of: awk 'BEGIN {for (i = 32; i <= 126; ++i){ printf("%c", i) } }' + ascii = " !\"#$%&'()*+,-./0123456789:;<=>?@ABCDEFGHIJKLMNOPQRSTUVWXYZ[\\]^_`abcdefghijklmnopqrstuvwxyz{|}~" + for (i = 1; i < 97; ++i) { + char_to_dec[char(ascii, i)] = 31 + i + } +} + { not_paragraph_p1 = not_paragraph not_paragraph = 0 @@ -95,6 +104,30 @@ function restore_match() { next } +# Automatic links +/<[^ \t<>]+>/ { + ## URL: + while (match($0, /<[A-Za-z][-A-Za-z0-9+.]*:[^ \t<>]+>/)) { + href = substr($0, RSTART + 1, RLENGTH - 2) + sub_match("" href "") + } + + ## Email addresses, with support for quoted local part "..."@... + ## and ip address literal ...@[...] + while (match($0, /<([^ \t<>]+|".+")@([-A-Za-z0-9]+\.[^ \t<>]+|\[[0-9A-Fa-f.:]+\])>/)) { + href = substr($0, RSTART + 1, RLENGTH - 2) + href_masked = "" + ## The original markdown blogpost calls for convertions of all + ## email characters into their hex values. Allegedly, this fools + ## many autoharvesting spam bots. + for (i = length(href); i > 0; --i) { + href_masked = sprintf("&#x%X;", char_to_dec[char(href, i)]) href_masked + } + ## href="mailto:..." + sub_match("" href_masked "") + } +} + # Blockquotes blockquote_level > 0 && empty0 { for (P1 = P1 ORS; blockquote_level > 0; --blockquote_level) { -- cgit v1.3.1-23-gd82d