From 7a3e7414f99bab65523e225f86f5373945c0e272 Mon Sep 17 00:00:00 2001 From: "akk1to.dev" Date: Thu, 9 Jan 2025 20:21:22 +0700 Subject: [PATCH 01/80] Create wiki.chuyentinorz.is-a.dev --- domains/wiki.chuyentinorz.is-a.dev | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 domains/wiki.chuyentinorz.is-a.dev diff --git a/domains/wiki.chuyentinorz.is-a.dev b/domains/wiki.chuyentinorz.is-a.dev new file mode 100644 index 000000000..d0783ba19 --- /dev/null +++ b/domains/wiki.chuyentinorz.is-a.dev @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "akk1to", + "email": "akk1to.dev@gmail.com", + "discord": "727497287777124414" + }, + "record": { + "CNAME": "akk1to.github.io/orz-wikipedia" +} From 4c1f1e620c153738b87b168447167b65b2e84721 Mon Sep 17 00:00:00 2001 From: "akk1to.dev" Date: Thu, 9 Jan 2025 20:30:40 +0700 Subject: [PATCH 02/80] Rename wiki.chuyentinorz.is-a.dev to wiki.chuyentinorz.json --- domains/{wiki.chuyentinorz.is-a.dev => wiki.chuyentinorz.json} | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename domains/{wiki.chuyentinorz.is-a.dev => wiki.chuyentinorz.json} (100%) diff --git a/domains/wiki.chuyentinorz.is-a.dev b/domains/wiki.chuyentinorz.json similarity index 100% rename from domains/wiki.chuyentinorz.is-a.dev rename to domains/wiki.chuyentinorz.json From 81b12b942dcb1a128e27bad19c617d24d346ea4e Mon Sep 17 00:00:00 2001 From: "akk1to.dev" Date: Thu, 9 Jan 2025 20:46:43 +0700 Subject: [PATCH 03/80] Update wiki.chuyentinorz.json --- domains/wiki.chuyentinorz.json | 1 + 1 file changed, 1 insertion(+) diff --git a/domains/wiki.chuyentinorz.json b/domains/wiki.chuyentinorz.json index d0783ba19..0c66cbc06 100644 --- a/domains/wiki.chuyentinorz.json +++ b/domains/wiki.chuyentinorz.json @@ -6,4 +6,5 @@ }, "record": { "CNAME": "akk1to.github.io/orz-wikipedia" + } } From 279fcf329bf3938c50659293835eabc77a7e18f2 Mon Sep 17 00:00:00 2001 From: "akk1to.dev" Date: Thu, 9 Jan 2025 20:54:23 +0700 Subject: [PATCH 04/80] Update wiki.chuyentinorz.json --- domains/wiki.chuyentinorz.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/domains/wiki.chuyentinorz.json b/domains/wiki.chuyentinorz.json index 0c66cbc06..6b2ef87e4 100644 --- a/domains/wiki.chuyentinorz.json +++ b/domains/wiki.chuyentinorz.json @@ -5,6 +5,6 @@ "discord": "727497287777124414" }, "record": { - "CNAME": "akk1to.github.io/orz-wikipedia" + "CNAME": "akk1to.github.io" } } From 97ea9a2eaf5cfbbda4ef5feb2421f6ea0cbaad07 Mon Sep 17 00:00:00 2001 From: "John Aerial J. Azcune" <65322242+STICKnoLOGIC@users.noreply.github.com> Date: Fri, 10 Jan 2025 12:05:18 +0800 Subject: [PATCH 05/80] Create sticknologic.json --- domains/sticknologic.json | 14 ++++++++++++++ 1 file changed, 14 insertions(+) create mode 100644 domains/sticknologic.json diff --git a/domains/sticknologic.json b/domains/sticknologic.json new file mode 100644 index 000000000..68cd5f782 --- /dev/null +++ b/domains/sticknologic.json @@ -0,0 +1,14 @@ +{ + "description": "Simple Portfolio and Blog Website", + "repo": "https://github.com/sticknologic", + "owner": { + "username": "sticknologic", + "email": "jobeth.llame@gmail.com" + }, + "record": { + "NS": [ + "ns1.heliohost.org", + "ns2.heliohost.org" + ] + } +} From 59cbf025b7445c37a1ed64c87feae7aa654281e7 Mon Sep 17 00:00:00 2001 From: "Vishal Kr." <53997539+ItzYoVishal@users.noreply.github.com> Date: Fri, 10 Jan 2025 15:16:23 +0530 Subject: [PATCH 06/80] Create callcon --- domains/callcon | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 domains/callcon diff --git a/domains/callcon b/domains/callcon new file mode 100644 index 000000000..2cc2ac6c8 --- /dev/null +++ b/domains/callcon @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "ItzYoVishal", + "email": "rockstarelitecoc@gmail.com" + }, + "record": { + "A": "4.157.244.201" + } +} From e5e3cd4eeac7950a318d7bda3b1b02a3340ad113 Mon Sep 17 00:00:00 2001 From: "NTBK-MARCOS\\mtora" Date: Fri, 10 Jan 2025 11:51:26 -0300 Subject: [PATCH 07/80] add marcos.is-a.dev --- domains/marcos.json | 11 +++++++++++ 1 file changed, 11 insertions(+) create mode 100644 domains/marcos.json diff --git a/domains/marcos.json b/domains/marcos.json new file mode 100644 index 000000000..44a678890 --- /dev/null +++ b/domains/marcos.json @@ -0,0 +1,11 @@ +{ + "description": "Describe the use of this subdomain", + "repo": "https://github.com/mtoranzo", + "owner": { + "username": "mtoranzo", + "email": "mtoranzo@gmail.com" + }, + "record": { + "TXT": "345c2e905e6bb6fd03343af2a4eb2e" + } +} \ No newline at end of file From d9db38b3bfcaadfcec6c086d98b10c53b3cd7174 Mon Sep 17 00:00:00 2001 From: Hammed Oyedele Date: Fri, 10 Jan 2025 15:52:32 +0100 Subject: [PATCH 08/80] Create hammed.json --- domains/hammed.json | 12 ++++++++++++ 1 file changed, 12 insertions(+) create mode 100644 domains/hammed.json diff --git a/domains/hammed.json b/domains/hammed.json new file mode 100644 index 000000000..7a86e4421 --- /dev/null +++ b/domains/hammed.json @@ -0,0 +1,12 @@ +{ + "description": "Link to my portfolio site.", + "repo": "https://github.com/devhammed/devhammed.github.io", + "owner": { + "username": "devhammed", + "email": "hey@hammed.dev" + }, + "record": { + "CNAME": "devhammed.github.io", + "TXT": "7672b068b3140a9fbaaf9bfe0ab136" + } +} From f0a22c1b0e1006eb7e2c13fd1ccd90c01ced9377 Mon Sep 17 00:00:00 2001 From: "John Aerial J. Azcune" <65322242+STICKnoLOGIC@users.noreply.github.com> Date: Fri, 10 Jan 2025 23:29:00 +0800 Subject: [PATCH 09/80] Create sticknologic.json --- domains/sticknologic.json | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/domains/sticknologic.json b/domains/sticknologic.json index 68cd5f782..04e7cba94 100644 --- a/domains/sticknologic.json +++ b/domains/sticknologic.json @@ -6,6 +6,12 @@ "email": "jobeth.llame@gmail.com" }, "record": { + "A":[ + "65.19.154.90" + ], + "AAAA":[ + "2001:470:1:1ee::1002" + ], "NS": [ "ns1.heliohost.org", "ns2.heliohost.org" From 17eca28d38d0bc636dd0fe82eb138267b1a326c4 Mon Sep 17 00:00:00 2001 From: "Vishal Kr." <53997539+ItzYoVishal@users.noreply.github.com> Date: Fri, 10 Jan 2025 23:09:16 +0530 Subject: [PATCH 10/80] Rename callcon to callcon.json --- domains/{callcon => callcon.json} | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename domains/{callcon => callcon.json} (100%) diff --git a/domains/callcon b/domains/callcon.json similarity index 100% rename from domains/callcon rename to domains/callcon.json From cc8d52801b33045de2c4243ce8e6291271cdc0f2 Mon Sep 17 00:00:00 2001 From: "John Aerial J. Azcune" <65322242+STICKnoLOGIC@users.noreply.github.com> Date: Sat, 11 Jan 2025 14:08:53 +0800 Subject: [PATCH 11/80] Update sticknologic.json --- domains/sticknologic.json | 4 ---- 1 file changed, 4 deletions(-) diff --git a/domains/sticknologic.json b/domains/sticknologic.json index 04e7cba94..2dd20d094 100644 --- a/domains/sticknologic.json +++ b/domains/sticknologic.json @@ -11,10 +11,6 @@ ], "AAAA":[ "2001:470:1:1ee::1002" - ], - "NS": [ - "ns1.heliohost.org", - "ns2.heliohost.org" ] } } From 6a41f591753920920cce606aefe7bf3429622ec5 Mon Sep 17 00:00:00 2001 From: Alireza Mohebbi Date: Sat, 11 Jan 2025 11:28:56 +0330 Subject: [PATCH 12/80] Create aasoft.json domain --- domains/aasoft.json | 11 +++++++++++ 1 file changed, 11 insertions(+) create mode 100644 domains/aasoft.json diff --git a/domains/aasoft.json b/domains/aasoft.json new file mode 100644 index 000000000..e9c124a64 --- /dev/null +++ b/domains/aasoft.json @@ -0,0 +1,11 @@ +{ + "description": "alireza mohebbi threejs project - aasoft.ir", + "repo": "https://github.com/is-a-dev/docs", + "owner": { + "username": "aasoftir", + "email": "aasoftmohebbi@gmail.com" + }, + "record": { + "URL": "https://glitch-text-threejs.vercel.app/" + } +} From 9086b4377cc47c75e6c31e215b333c725e7c9a2f Mon Sep 17 00:00:00 2001 From: Alireza Mohebbi Date: Sat, 11 Jan 2025 11:32:15 +0330 Subject: [PATCH 13/80] Update aasoft.json domain --- domains/aasoft.json | 1 - 1 file changed, 1 deletion(-) diff --git a/domains/aasoft.json b/domains/aasoft.json index e9c124a64..7a1b6c67c 100644 --- a/domains/aasoft.json +++ b/domains/aasoft.json @@ -1,6 +1,5 @@ { "description": "alireza mohebbi threejs project - aasoft.ir", - "repo": "https://github.com/is-a-dev/docs", "owner": { "username": "aasoftir", "email": "aasoftmohebbi@gmail.com" From 375bfecb469559928e41e738d95293d4eb625c3d Mon Sep 17 00:00:00 2001 From: "John Aerial J. Azcune" <65322242+STICKnoLOGIC@users.noreply.github.com> Date: Sat, 11 Jan 2025 17:37:55 +0800 Subject: [PATCH 14/80] Update sticknologic.json --- domains/sticknologic.json | 8 +++----- 1 file changed, 3 insertions(+), 5 deletions(-) diff --git a/domains/sticknologic.json b/domains/sticknologic.json index 2dd20d094..68cd5f782 100644 --- a/domains/sticknologic.json +++ b/domains/sticknologic.json @@ -6,11 +6,9 @@ "email": "jobeth.llame@gmail.com" }, "record": { - "A":[ - "65.19.154.90" - ], - "AAAA":[ - "2001:470:1:1ee::1002" + "NS": [ + "ns1.heliohost.org", + "ns2.heliohost.org" ] } } From 8586b252a5fd0e90e52e9e2ab7e402631434adbf Mon Sep 17 00:00:00 2001 From: Hammed Oyedele Date: Sat, 11 Jan 2025 15:36:44 +0100 Subject: [PATCH 15/80] Update hammed.json --- domains/hammed.json | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/domains/hammed.json b/domains/hammed.json index 7a86e4421..8db9ef285 100644 --- a/domains/hammed.json +++ b/domains/hammed.json @@ -6,7 +6,6 @@ "email": "hey@hammed.dev" }, "record": { - "CNAME": "devhammed.github.io", - "TXT": "7672b068b3140a9fbaaf9bfe0ab136" + "CNAME": "devhammed.github.io" } } From 5c8e689c8c01b874d7c0bd5932c79ce06c40d78e Mon Sep 17 00:00:00 2001 From: Hammed Oyedele Date: Sat, 11 Jan 2025 15:44:52 +0100 Subject: [PATCH 16/80] Create _github-pages-challenge-devhammed.hammed.json --- domains/_github-pages-challenge-devhammed.hammed.json | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 domains/_github-pages-challenge-devhammed.hammed.json diff --git a/domains/_github-pages-challenge-devhammed.hammed.json b/domains/_github-pages-challenge-devhammed.hammed.json new file mode 100644 index 000000000..44413c068 --- /dev/null +++ b/domains/_github-pages-challenge-devhammed.hammed.json @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "devhammed", + "email": "hey@hammed.dev" + }, + "record": { + "TXT": "7672b068b3140a9fbaaf9bfe0ab136" + } +} From 325a1c762b57b9cc76dd21d44020dd828d6fae5b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Nguy=E1=BB=85n=20Xu=C3=A2n=20Minh=20Tu=E1=BA=A5n?= <81414860+tuannguyen2002@users.noreply.github.com> Date: Sat, 11 Jan 2025 23:22:25 +0700 Subject: [PATCH 17/80] Create minhtuan_1.json --- domains/minhtuan_1.json | 11 +++++++++++ 1 file changed, 11 insertions(+) create mode 100644 domains/minhtuan_1.json diff --git a/domains/minhtuan_1.json b/domains/minhtuan_1.json new file mode 100644 index 000000000..fc3fdec81 --- /dev/null +++ b/domains/minhtuan_1.json @@ -0,0 +1,11 @@ +{ +"description": "profile-tuan.dev", +"owner": { +"username": "tuannguyen2002", +"email": "nxmtuan.2002@gmail.com", +"discord": "nightfury06749" +}, +"record": { +"CNAME": "cname.vercel-dns.com" +} +} From f15e51f754fec6200a6dee9209ce2b4ae95d1bfa Mon Sep 17 00:00:00 2001 From: "John Aerial J. Azcune" <65322242+STICKnoLOGIC@users.noreply.github.com> Date: Sun, 12 Jan 2025 03:01:29 +0800 Subject: [PATCH 18/80] update owner information --- domains/sticknologic.json | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/domains/sticknologic.json b/domains/sticknologic.json index 68cd5f782..b96359579 100644 --- a/domains/sticknologic.json +++ b/domains/sticknologic.json @@ -3,7 +3,9 @@ "repo": "https://github.com/sticknologic", "owner": { "username": "sticknologic", - "email": "jobeth.llame@gmail.com" + "x": "https://x.com/sticknologic", + "facebook":"https://www.facebook.com/STICKnoLOGIC", + "bsky":"https://bsky.app/profile/sticknologic.bsky.social" }, "record": { "NS": [ From 3c1d62293aac0ba1534947684cca58cf30b773ac Mon Sep 17 00:00:00 2001 From: "Vishal Kr." <53997539+ItzYoVishal@users.noreply.github.com> Date: Sun, 12 Jan 2025 00:33:06 +0530 Subject: [PATCH 19/80] Apply suggestions from code review Co-authored-by: iostpa --- domains/callcon.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/domains/callcon.json b/domains/callcon.json index 2cc2ac6c8..9db82545c 100644 --- a/domains/callcon.json +++ b/domains/callcon.json @@ -4,6 +4,6 @@ "email": "rockstarelitecoc@gmail.com" }, "record": { - "A": "4.157.244.201" + "A": ["4.157.244.201"] } } From 271cfa93c8d1c0e56557d5da8dce14e49d2b8dee Mon Sep 17 00:00:00 2001 From: Willy Joao Mateo Espinoza <67135809+willymateo@users.noreply.github.com> Date: Sat, 11 Jan 2025 21:15:21 -0500 Subject: [PATCH 20/80] Create willymateo.json --- domains/willymateo.json | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 domains/willymateo.json diff --git a/domains/willymateo.json b/domains/willymateo.json new file mode 100644 index 000000000..a9129f016 --- /dev/null +++ b/domains/willymateo.json @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "willymateo", + "email": "matheoowilly@gmail.com" + }, + "record": { + "RECORDTYPE": "RECORDCONTENT" + } +} From dff570a42aab47baf58c378c76657c2468257471 Mon Sep 17 00:00:00 2001 From: "John Aerial J. Azcune" <65322242+STICKnoLOGIC@users.noreply.github.com> Date: Sun, 12 Jan 2025 14:57:08 +0800 Subject: [PATCH 21/80] Fix: Social media Handler --- domains/sticknologic.json | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/domains/sticknologic.json b/domains/sticknologic.json index b96359579..0a6a40d50 100644 --- a/domains/sticknologic.json +++ b/domains/sticknologic.json @@ -3,9 +3,9 @@ "repo": "https://github.com/sticknologic", "owner": { "username": "sticknologic", - "x": "https://x.com/sticknologic", - "facebook":"https://www.facebook.com/STICKnoLOGIC", - "bsky":"https://bsky.app/profile/sticknologic.bsky.social" + "x": "STICKnoLOGIC", + "facebook":"STICKnoLOGIC", + "bsky":"STICKnoLOGIC" }, "record": { "NS": [ From f0094680e7177eb44c4ffbb0e9365cf23fb7b482 Mon Sep 17 00:00:00 2001 From: Willy Joao Mateo Espinoza <67135809+willymateo@users.noreply.github.com> Date: Sun, 12 Jan 2025 12:12:20 -0500 Subject: [PATCH 22/80] Create _vercel.willymateo.json --- domains/_vercel.willymateo.json | 10 ++++++++++ 1 file changed, 10 insertions(+) create mode 100644 domains/_vercel.willymateo.json diff --git a/domains/_vercel.willymateo.json b/domains/_vercel.willymateo.json new file mode 100644 index 000000000..e04aa1f68 --- /dev/null +++ b/domains/_vercel.willymateo.json @@ -0,0 +1,10 @@ +{ + "owner": { + "username": "willymateo", + "email": "matheoowilly@gmail.com", + "discord": "willycocolon" + }, + "record": { + "TXT": "vc-domain-verify=willymateo.is-a.dev,6c7018f1721c84a520df" + } +} From 203d0190dc53482af057cace480e137f4d0b758b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Peme969=20=E2=9A=A1?= Date: Sun, 12 Jan 2025 11:18:42 -0600 Subject: [PATCH 23/80] Update peme969.json Added an alias to my email address. (I encrypted it with their encryption service) --- domains/peme969.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/domains/peme969.json b/domains/peme969.json index 0e3f8b38d..f0b522281 100644 --- a/domains/peme969.json +++ b/domains/peme969.json @@ -11,7 +11,7 @@ "185.199.111.153" ], "TXT":[ - "forward-email=NjNhNjJlMjMzOGJhMWUxNy1hOTk2MzljYmY0ZDczZWViZDY2NTljZmUwMDc4OTM5MmQ3YmVjN2RmYWEyMjFlN2VhODAxZWUwOWI5ODhhNDY2" + "forward-email=MzY4NGZhMjBlZjg4YjBhOC1lZjllYjNhOWE3YzFiNzE0ZWU5OGYwOTdmN2E0YTUzMWFmYjk5M2NhNTA1NGRjZTQ2ZmZlNjA4NWY3ODMyNzNh" ], "MX":[ "mx1.forwardemail.net", From 943cc0392530517e1654eac69d011fac6389ca91 Mon Sep 17 00:00:00 2001 From: Willy Joao Mateo Espinoza <67135809+willymateo@users.noreply.github.com> Date: Sun, 12 Jan 2025 12:24:16 -0500 Subject: [PATCH 24/80] Update willymateo.json --- domains/willymateo.json | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/domains/willymateo.json b/domains/willymateo.json index a9129f016..6816fa297 100644 --- a/domains/willymateo.json +++ b/domains/willymateo.json @@ -1,9 +1,10 @@ { "owner": { "username": "willymateo", - "email": "matheoowilly@gmail.com" + "email": "matheoowilly@gmail.com", + "discord": "willycocolon" }, "record": { - "RECORDTYPE": "RECORDCONTENT" + "CNAME": "willymateo.vercel.app" } } From 0341788cf14a43b02b2bb79ecc71036e95e690aa Mon Sep 17 00:00:00 2001 From: ALEXX <114208686+ALEXXHUMILDE@users.noreply.github.com> Date: Sun, 12 Jan 2025 11:35:32 -0600 Subject: [PATCH 25/80] Create enlaces.alexxhumilde.json --- domains/enlaces.alexxhumilde.json | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 domains/enlaces.alexxhumilde.json diff --git a/domains/enlaces.alexxhumilde.json b/domains/enlaces.alexxhumilde.json new file mode 100644 index 000000000..664a71d3b --- /dev/null +++ b/domains/enlaces.alexxhumilde.json @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "ALEXXHUMILDE", + "email": "alexxcrack3@gmail.com" + }, + "record": { + "CNAME": "enlaces-alexxhumilde.netlify.app" + } +} From 16f9f0e6b161b2c8fb811e2ac277f021c6b39e89 Mon Sep 17 00:00:00 2001 From: Narasima Pandiyan <35830653+NarasimaPandiyan@users.noreply.github.com> Date: Sun, 12 Jan 2025 23:06:18 +0530 Subject: [PATCH 26/80] Create _github-pages-challenge-narasimapandiyan.narasima.json --- ...github-pages-challenge-narasimapandiyan.narasima.json | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 domains/_github-pages-challenge-narasimapandiyan.narasima.json diff --git a/domains/_github-pages-challenge-narasimapandiyan.narasima.json b/domains/_github-pages-challenge-narasimapandiyan.narasima.json new file mode 100644 index 000000000..8b779a899 --- /dev/null +++ b/domains/_github-pages-challenge-narasimapandiyan.narasima.json @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "NarasimaPandiyan", + "email": "cs42059@gmail.com" + }, + "record": { + "TXT": "0cd2fb39489f7652da9a4942df4a75" + } +} From 845ead7c7bdf3d063926e0c2257bff5d1edc952d Mon Sep 17 00:00:00 2001 From: Marcos Toranzo Date: Sun, 12 Jan 2025 14:49:46 -0300 Subject: [PATCH 27/80] Fix: marcos.json --- domains/marcos.json | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/domains/marcos.json b/domains/marcos.json index 44a678890..472e8ffc5 100644 --- a/domains/marcos.json +++ b/domains/marcos.json @@ -1,11 +1,11 @@ { - "description": "Describe the use of this subdomain", + "description": "Developer portfolio", "repo": "https://github.com/mtoranzo", "owner": { "username": "mtoranzo", "email": "mtoranzo@gmail.com" }, "record": { - "TXT": "345c2e905e6bb6fd03343af2a4eb2e" + "CNAME": "mtoranzo.github.io", } } \ No newline at end of file From 4210090e6669f72ae136d438d4b6137913e2125f Mon Sep 17 00:00:00 2001 From: nilsraccoon <87526178+nilsraccoon@users.noreply.github.com> Date: Sun, 12 Jan 2025 19:15:46 +0100 Subject: [PATCH 28/80] Create _atproto.raccoon.json --- domains/_atproto.raccoon.json | 10 ++++++++++ 1 file changed, 10 insertions(+) create mode 100644 domains/_atproto.raccoon.json diff --git a/domains/_atproto.raccoon.json b/domains/_atproto.raccoon.json new file mode 100644 index 000000000..fffc1ce78 --- /dev/null +++ b/domains/_atproto.raccoon.json @@ -0,0 +1,10 @@ +{ + "owner": { + "username": "nilsraccoon", + "email": "", + "discord": "1129507464589627512" + }, + "record": { + "TXT": "did=did:plc:25w7vwbzb2e3h7cnflqskp37" + } +} From d69d66e743fc64bf294c62e9c2fb544d4237f06e Mon Sep 17 00:00:00 2001 From: Fabian <103263394+fabianf4@users.noreply.github.com> Date: Sun, 12 Jan 2025 13:40:21 -0500 Subject: [PATCH 29/80] Create fabianf4.json New Domain --- domains/fabianf4.json | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 domains/fabianf4.json diff --git a/domains/fabianf4.json b/domains/fabianf4.json new file mode 100644 index 000000000..c50d834f8 --- /dev/null +++ b/domains/fabianf4.json @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "fabianf4", + "email": "fabianfa.munoz@gmail.com" + }, + "record": { + "CNAME": "fabianf4.github.io" + } +} From cae8151bce5155d566b1da555a6b7ea8a019dfb3 Mon Sep 17 00:00:00 2001 From: Yousef Yasser <121342403+yys-yss@users.noreply.github.com> Date: Mon, 13 Jan 2025 02:52:41 +0800 Subject: [PATCH 30/80] Create yousef.json --- domains/yousef.json | 11 +++++++++++ 1 file changed, 11 insertions(+) create mode 100644 domains/yousef.json diff --git a/domains/yousef.json b/domains/yousef.json new file mode 100644 index 000000000..f89584f9e --- /dev/null +++ b/domains/yousef.json @@ -0,0 +1,11 @@ +{ + "description": "Portfolio for Yousef Yasser", + "repo": "https://github.com/yys-yss/yys-yss.github.io, + "owner": { + "username": "yys-yss", + "email": "yousefyassersalah@gmail.com" + }, + "record": { + "CNAME": "yys-yss.github.io" + } +} From 4fecc1f325753f5e40aa102b7d464c111b888f49 Mon Sep 17 00:00:00 2001 From: iostpa Date: Sun, 12 Jan 2025 21:35:09 +0200 Subject: [PATCH 31/80] Remove email line since it isn't mandatory to have it anymore. --- domains/_atproto.raccoon.json | 1 - 1 file changed, 1 deletion(-) diff --git a/domains/_atproto.raccoon.json b/domains/_atproto.raccoon.json index fffc1ce78..2fdc4f971 100644 --- a/domains/_atproto.raccoon.json +++ b/domains/_atproto.raccoon.json @@ -1,7 +1,6 @@ { "owner": { "username": "nilsraccoon", - "email": "", "discord": "1129507464589627512" }, "record": { From e4997b3a05ef728e54575f5497c5b70a98ff048c Mon Sep 17 00:00:00 2001 From: iostpa Date: Sun, 12 Jan 2025 21:39:27 +0200 Subject: [PATCH 32/80] Update domains/yousef.json --- domains/yousef.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/domains/yousef.json b/domains/yousef.json index f89584f9e..28ce8749c 100644 --- a/domains/yousef.json +++ b/domains/yousef.json @@ -1,6 +1,6 @@ { "description": "Portfolio for Yousef Yasser", - "repo": "https://github.com/yys-yss/yys-yss.github.io, + "repo": "https://github.com/yys-yss/yys-yss.github.io", "owner": { "username": "yys-yss", "email": "yousefyassersalah@gmail.com" From b1c9a32f3691aed55f6e3ac182eca8a5486a7dc5 Mon Sep 17 00:00:00 2001 From: Marcos Toranzo <926024+mtoranzo@users.noreply.github.com> Date: Sun, 12 Jan 2025 16:59:18 -0300 Subject: [PATCH 33/80] Update domains/marcos.json Co-authored-by: iostpa --- domains/marcos.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/domains/marcos.json b/domains/marcos.json index 472e8ffc5..ee2c00027 100644 --- a/domains/marcos.json +++ b/domains/marcos.json @@ -6,6 +6,6 @@ "email": "mtoranzo@gmail.com" }, "record": { - "CNAME": "mtoranzo.github.io", + "CNAME": "mtoranzo.github.io" } } \ No newline at end of file From de7741b5a7d833ddf1acf2e5e18b405d4bbe8537 Mon Sep 17 00:00:00 2001 From: Marcos Toranzo Date: Sun, 12 Jan 2025 17:02:04 -0300 Subject: [PATCH 34/80] fix: comma delimiter --- domains/marcos.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/domains/marcos.json b/domains/marcos.json index 472e8ffc5..ee2c00027 100644 --- a/domains/marcos.json +++ b/domains/marcos.json @@ -6,6 +6,6 @@ "email": "mtoranzo@gmail.com" }, "record": { - "CNAME": "mtoranzo.github.io", + "CNAME": "mtoranzo.github.io" } } \ No newline at end of file From 342af88a6dcd4566914d9d09d39a0c7a849474ae Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?G=C3=BCl=C5=9Fah=20D=C3=BCzg=C3=BCn?= <65841330+GulsahDuzgun@users.noreply.github.com> Date: Sun, 12 Jan 2025 23:08:44 +0300 Subject: [PATCH 35/80] Create gulsah.json --- domains/gulsah.json | 11 +++++++++++ 1 file changed, 11 insertions(+) create mode 100644 domains/gulsah.json diff --git a/domains/gulsah.json b/domains/gulsah.json new file mode 100644 index 000000000..a2b1f07bc --- /dev/null +++ b/domains/gulsah.json @@ -0,0 +1,11 @@ +{ + "description": "The portfolio site of Gülşah Düzgün", + "repo": "https://github.com/GulsahDuzgun/Portfolio", + "owner": { + "username": "GulsahDuzgun", + "email": "duzgun.gulsah27@gmail.com" + }, + "record": { + "CNAME": "gulsah.netlify.app" + } +} From 81f6380d9568c259282d7435f6a6611f8d2adc90 Mon Sep 17 00:00:00 2001 From: JumanJi <90971841+heyjumanji@users.noreply.github.com> Date: Mon, 13 Jan 2025 01:57:56 +0530 Subject: [PATCH 36/80] Rename _vercel.jumanji.json to _vercel.blog.jumanji.json Rename the file. --- domains/{_vercel.jumanji.json => _vercel.blog.jumanji.json} | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename domains/{_vercel.jumanji.json => _vercel.blog.jumanji.json} (100%) diff --git a/domains/_vercel.jumanji.json b/domains/_vercel.blog.jumanji.json similarity index 100% rename from domains/_vercel.jumanji.json rename to domains/_vercel.blog.jumanji.json From 06f5573835b37027b71fe3c9b2ee012e60a6c5de Mon Sep 17 00:00:00 2001 From: boudjo <142155728+Boudjoo@users.noreply.github.com> Date: Sun, 12 Jan 2025 22:18:36 +0100 Subject: [PATCH 37/80] Create boudjo.json --- domains/boudjo.json | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 domains/boudjo.json diff --git a/domains/boudjo.json b/domains/boudjo.json new file mode 100644 index 000000000..f7f82317a --- /dev/null +++ b/domains/boudjo.json @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "boudjoo", + "email": "abdouboudjo1@gmail.com" + }, + "record": { + "CNAME": "boudjoo.github.io" + } +} From 347cbf553222962c4570c56c0e2c7d1c683c73c4 Mon Sep 17 00:00:00 2001 From: Joe Date: Mon, 13 Jan 2025 00:18:44 +0200 Subject: [PATCH 38/80] Create www.fungaming.joe50097.json --- www.fungaming.joe50097.json | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 www.fungaming.joe50097.json diff --git a/www.fungaming.joe50097.json b/www.fungaming.joe50097.json new file mode 100644 index 000000000..50a39e83b --- /dev/null +++ b/www.fungaming.joe50097.json @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "Joe50097", + "email": "zcell9500@gmail.com" + }, + "record": { + "CNAME": "fungaming-discord-server.netlify.app" + } +} From 75ce354a3b849698512b99eef98dca78df54e030 Mon Sep 17 00:00:00 2001 From: krunchiekrunch <75719839+RadioactivePotato@users.noreply.github.com> Date: Sun, 12 Jan 2025 22:24:09 +0000 Subject: [PATCH 39/80] Updated my information and deleted 1 subdomain --- domains/_discord.krunch.json | 2 +- ..._github-pages-challenge-radioactivepotato.krunch.json | 2 +- domains/krunch.json | 2 +- domains/link.krunch.json | 9 --------- domains/mail.krunch.json | 4 ++-- 5 files changed, 5 insertions(+), 14 deletions(-) delete mode 100644 domains/link.krunch.json diff --git a/domains/_discord.krunch.json b/domains/_discord.krunch.json index 1a376298a..200efe570 100644 --- a/domains/_discord.krunch.json +++ b/domains/_discord.krunch.json @@ -1,7 +1,7 @@ { "owner": { "username": "RadioactivePotato", - "discord": "krunchiekrunch._." + "discord": "1166013268008120340" }, "record": { "TXT": "dh=df2bf9fb87a1dc3ee29c6ddfa51ed86da28581c5" diff --git a/domains/_github-pages-challenge-radioactivepotato.krunch.json b/domains/_github-pages-challenge-radioactivepotato.krunch.json index f8c99bf1d..2ddd73ce0 100644 --- a/domains/_github-pages-challenge-radioactivepotato.krunch.json +++ b/domains/_github-pages-challenge-radioactivepotato.krunch.json @@ -1,7 +1,7 @@ { "owner": { "username": "RadioactivePotato", - "discord": "krunchiekrunch._." + "discord": "1166013268008120340" }, "record": { "TXT": "05dc6febabf44f8decab35d01609ee" diff --git a/domains/krunch.json b/domains/krunch.json index fa6655cf6..80350c61e 100644 --- a/domains/krunch.json +++ b/domains/krunch.json @@ -3,7 +3,7 @@ "repo": "https://github.com/RadioactivePotato/krunch-is-a-dev", "owner": { "username": "RadioactivePotato", - "discord": "krunchiekrunch._." + "discord": "1166013268008120340" }, "record": { "CNAME": "krunch.pages.dev" diff --git a/domains/link.krunch.json b/domains/link.krunch.json deleted file mode 100644 index 75476d8e7..000000000 --- a/domains/link.krunch.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "owner": { - "username": "RadioactivePotato", - "discord": "krunchiekrunch._." - }, - "record": { - "CNAME": "cname.short.io" - } -} diff --git a/domains/mail.krunch.json b/domains/mail.krunch.json index 45b36bb29..cdeedf725 100644 --- a/domains/mail.krunch.json +++ b/domains/mail.krunch.json @@ -1,8 +1,8 @@ { - "description": "ImprovMX Email", + "description": "ImprovMX Mail Forwarding", "owner": { "username": "RadioactivePotato", - "discord": "krunchiekrunch._." + "discord": "1166013268008120340" }, "record": { "MX": ["mx1.improvmx.com", "mx2.improvmx.com"], From c42184ff009b33b3d952d8d8b96cac69de1ba6d6 Mon Sep 17 00:00:00 2001 From: DIBSTER <76603072+DEV-DIBSTER@users.noreply.github.com> Date: Sun, 12 Jan 2025 18:56:54 -0500 Subject: [PATCH 40/80] Update and rename minhtuan_1.json to minhtuan-1.json --- domains/minhtuan-1.json | 11 +++++++++++ domains/minhtuan_1.json | 11 ----------- 2 files changed, 11 insertions(+), 11 deletions(-) create mode 100644 domains/minhtuan-1.json delete mode 100644 domains/minhtuan_1.json diff --git a/domains/minhtuan-1.json b/domains/minhtuan-1.json new file mode 100644 index 000000000..b7f2b9ffc --- /dev/null +++ b/domains/minhtuan-1.json @@ -0,0 +1,11 @@ +{ + "description": "profile-tuan.dev", + "owner": { + "username": "tuannguyen2002", + "email": "nxmtuan.2002@gmail.com", + "discord": "nightfury06749" + }, + "record": { + "CNAME": "cname.vercel-dns.com" + } +} diff --git a/domains/minhtuan_1.json b/domains/minhtuan_1.json deleted file mode 100644 index fc3fdec81..000000000 --- a/domains/minhtuan_1.json +++ /dev/null @@ -1,11 +0,0 @@ -{ -"description": "profile-tuan.dev", -"owner": { -"username": "tuannguyen2002", -"email": "nxmtuan.2002@gmail.com", -"discord": "nightfury06749" -}, -"record": { -"CNAME": "cname.vercel-dns.com" -} -} From e232c4bd6f95a2b3a5071f88a6810d4274389971 Mon Sep 17 00:00:00 2001 From: meccar Date: Mon, 13 Jan 2025 08:19:28 +0700 Subject: [PATCH 41/80] Create tafviet --- domains/tafviet | 11 +++++++++++ 1 file changed, 11 insertions(+) create mode 100644 domains/tafviet diff --git a/domains/tafviet b/domains/tafviet new file mode 100644 index 000000000..e28823b63 --- /dev/null +++ b/domains/tafviet @@ -0,0 +1,11 @@ +{ + "description": "Landing page for tafviet.is-a.dev", + "repo": "https://github.com/is-a-dev/docs", + "owner": { + "username": "is-a-dev", + "email": "meccar@protonmail.com" + }, + "record": { + "CNAME": "meccar.github.io" + } +} From e0f466f3c5cf783a9c08174ecad771de18159c9f Mon Sep 17 00:00:00 2001 From: meccar Date: Mon, 13 Jan 2025 09:28:32 +0700 Subject: [PATCH 42/80] Update and rename tafviet to tafviet.json --- domains/{tafviet => tafviet.json} | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename domains/{tafviet => tafviet.json} (100%) diff --git a/domains/tafviet b/domains/tafviet.json similarity index 100% rename from domains/tafviet rename to domains/tafviet.json From dbce5c58fc60554c1fae6a8da9311930b5b7f523 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 10:56:48 +0800 Subject: [PATCH 43/80] stop URL records being combined with other records --- tests/records.test.js | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/tests/records.test.js b/tests/records.test.js index de5ecbadc..819c70d1a 100644 --- a/tests/records.test.js +++ b/tests/records.test.js @@ -83,7 +83,6 @@ t("All files should have valid record types", (t) => { t.true(validateRecordType(key), `${file}: Invalid record type: ${key}`); }); - // Specific record rules for CNAME, NS, and DS if (recordKeys.includes("CNAME") && !data.proxied) { t.is(recordKeys.length, 1, `${file}: CNAME records cannot be combined with other records unless proxied`); } @@ -98,7 +97,13 @@ t("All files should have valid record types", (t) => { if (recordKeys.includes("DS")) { t.true(recordKeys.includes("NS"), `${file}: DS records must be combined with NS records`); } + + if (recordKeys.includes("URL") { + t.true(!recordKeys.includes("A") && !recordKeys.includes("AAAA") && !recordKeys.includes("CNAME"), `${file}: URL records cannot be combined with A, AAAA, or CNAME records`); + } }); + + t.pass(); }); t("All files should not have duplicate record keys", (t) => { From f99b7a15431a67c5ee384b4dd82c515ffc9c8321 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 10:57:41 +0800 Subject: [PATCH 44/80] fix syntax --- tests/records.test.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/records.test.js b/tests/records.test.js index 819c70d1a..fdf2a17e9 100644 --- a/tests/records.test.js +++ b/tests/records.test.js @@ -98,7 +98,7 @@ t("All files should have valid record types", (t) => { t.true(recordKeys.includes("NS"), `${file}: DS records must be combined with NS records`); } - if (recordKeys.includes("URL") { + if (recordKeys.includes("URL")) { t.true(!recordKeys.includes("A") && !recordKeys.includes("AAAA") && !recordKeys.includes("CNAME"), `${file}: URL records cannot be combined with A, AAAA, or CNAME records`); } }); From a4a0cc1ec25bf2ffac14dd9ae049006e4d8676c5 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 10:58:56 +0800 Subject: [PATCH 45/80] Update luisandre.json --- domains/luisandre.json | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/domains/luisandre.json b/domains/luisandre.json index d6accd1e9..e8cdec4bd 100644 --- a/domains/luisandre.json +++ b/domains/luisandre.json @@ -4,7 +4,6 @@ "email": "luis073094@gmail.com" }, "record": { - "URL": "https://portafolioluisandre.azurewebsites.net", - "A": ["20.206.176.7"] + "URL": "https://portafolioluisandre.azurewebsites.net" } } From 593c55b03328acdc620fbb414da1189776c08ed2 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 11:03:25 +0800 Subject: [PATCH 46/80] Update validation.yml --- .github/workflows/validation.yml | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-) diff --git a/.github/workflows/validation.yml b/.github/workflows/validation.yml index f24d6052d..fa0fa8f5f 100644 --- a/.github/workflows/validation.yml +++ b/.github/workflows/validation.yml @@ -19,14 +19,13 @@ concurrency: cancel-in-progress: true jobs: - dns: - name: DNS + dnscontrol: + name: DNSControl runs-on: ubuntu-latest steps: - uses: actions/checkout@v4 - - name: Check - uses: is-a-dev/dnscontrol-action@main + - uses: is-a-dev/dnscontrol-action@main with: args: check @@ -38,5 +37,4 @@ jobs: - run: npm install - - name: Run tests - run: npx ava tests/*.test.js + - run: npx ava tests/*.test.js From 0387e0c55aeaec8f7148eb6bfdb69d6640b3021a Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 11:04:46 +0800 Subject: [PATCH 47/80] Update publish.yml --- .github/workflows/publish.yml | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index 9622ebd4a..ac9c92abd 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -21,10 +21,15 @@ jobs: steps: - uses: actions/checkout@v4 + - name: Run tests + run: | + npm install + npx ava tests/*.test.js + - name: Generate creds.json run: echo '{"cloudflare":{"TYPE":"CLOUDFLAREAPI","apitoken":"$CLOUDFLARE_API_TOKEN"}}' > ./creds.json - - name: Publish + - name: Push DNS records uses: is-a-dev/dnscontrol-action@main env: CLOUDFLARE_API_TOKEN: ${{ secrets.CLOUDFLARE_API_TOKEN }} From cfd0e7d7599aa06b55f115e60965bdca33113d96 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Peme969=20=E2=9A=A1?= Date: Sun, 12 Jan 2025 21:18:14 -0600 Subject: [PATCH 48/80] Update peme969.json Added another alias :) --- domains/peme969.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/domains/peme969.json b/domains/peme969.json index f0b522281..7c7bf68f5 100644 --- a/domains/peme969.json +++ b/domains/peme969.json @@ -11,7 +11,7 @@ "185.199.111.153" ], "TXT":[ - "forward-email=MzY4NGZhMjBlZjg4YjBhOC1lZjllYjNhOWE3YzFiNzE0ZWU5OGYwOTdmN2E0YTUzMWFmYjk5M2NhNTA1NGRjZTQ2ZmZlNjA4NWY3ODMyNzNh" + "forward-email=NTQwMmZhNmI3ZmRiMzQxNC1mOTU1YmRmOGJhMTQxMzhkMGRiNzUwMzg0MzFhOTI4OGE0ZmUwZDYyZTZmZDMyODkwYTE4OGE0ZmQ2YjFjOTk4MjkxN2NlMTUzMTgyNDZlYzE4ZWFkNDllYTBmNDNjY2M4NWVmZGFhMjdhNmY0ODFhZWM0ZWM4ZjhiMzJiMTIyMA==" ], "MX":[ "mx1.forwardemail.net", From bcf071b6f2ea43c9416d6e3535b1e0d98c664273 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 12:11:37 +0800 Subject: [PATCH 49/80] optimise + improve tests --- tests/domains.test.js | 111 +++++----------------- tests/json.test.js | 149 +++++++++++++++++++----------- tests/proxy.test.js | 23 ++++- tests/records.test.js | 209 +++++++++++++++++++++--------------------- 4 files changed, 244 insertions(+), 248 deletions(-) diff --git a/tests/domains.test.js b/tests/domains.test.js index f43b05254..ce2c3817d 100644 --- a/tests/domains.test.js +++ b/tests/domains.test.js @@ -5,72 +5,52 @@ const path = require("path"); const domainsPath = path.resolve("domains"); const files = fs.readdirSync(domainsPath); -function getParentSubdomain(subdomain) { - const parts = subdomain.split("."); - - if (parts.length <= 1) return null; // No parent for top-level subdomains - - // Attempt to find the parent subdomain by removing the last part - for (let i = parts.length - 1; i > 0; i--) { - const potentialParent = parts.slice(i - 1).join("."); - if (files.includes(`${potentialParent}.json`)) { - return potentialParent; // Return the parent subdomain if it exists - } - } - - return null; // Return null if no valid parent is found -} +const domainCache = {}; function getDomainData(subdomain) { + if (domainCache[subdomain]) { + return domainCache[subdomain]; + } + try { - return fs.readJsonSync(path.join(domainsPath, `${subdomain}.json`)); + const data = fs.readJsonSync(path.join(domainsPath, `${subdomain}.json`)); + domainCache[subdomain] = data; // Cache the domain data + return data; } catch (error) { throw new Error(`Failed to read JSON for ${subdomain}: ${error.message}`); } } -function expandReservedDomains() { - const reserved = require("../util/reserved-domains.json"); - const expandedList = [...reserved]; +function getParentSubdomain(subdomain) { + const parts = subdomain.split("."); - for (const item of reserved) { - const rangeMatch = item.match(/\[(\d+)-(\d+)\]/); // Matches [min-max] + if (parts.length <= 1) return null; // No parent for top-level subdomains - if (rangeMatch) { - const prefix = item.split("[")[0]; - const start = parseInt(rangeMatch[1], 10); - const end = parseInt(rangeMatch[2], 10); + // Try to find the parent subdomain by iterating over the parts + for (let i = parts.length - 1; i > 0; i--) { + const potentialParent = parts.slice(i - 1).join("."); - if (start < end) { - for (let i = start; i <= end; i++) { - expandedList.push(prefix + i); - } - - expandedList.splice(expandedList.indexOf(item), 1); - } else { - throw new Error(`[util/reserved-domains.json] Invalid range [${start}-${end}] in "${item}"`); - } + if (files.includes(`${potentialParent}.json`)) { + return potentialParent; } } - return expandedList; + return null; } t("Nested subdomains should not exist without a parent subdomain", (t) => { - for (const file of files) { + files.forEach((file) => { const subdomain = file.replace(/\.json$/, ""); if (subdomain.split(".").length > 1) { const parentSubdomain = getParentSubdomain(subdomain); - t.true(files.includes(`${parentSubdomain}.json`), `${file}: Parent subdomain does not exist`); + t.true(parentSubdomain && files.includes(`${parentSubdomain}.json`), `${file}: Parent subdomain does not exist`); } - } - - t.pass(); + }); }); t("Nested subdomains should not exist if the parent subdomain has NS records", (t) => { - for (const file of files) { + files.forEach((file) => { const subdomain = file.replace(/\.json$/, ""); if (subdomain.split(".").length > 1) { @@ -79,18 +59,15 @@ t("Nested subdomains should not exist if the parent subdomain has NS records", ( t.true(!parentDomain.record.NS, `${file}: Parent subdomain has NS records`); } - } - - t.pass(); + }); }); t("Nested subdomains should be owned by the parent subdomain's owner", (t) => { - for (const file of files) { + files.forEach((file) => { const subdomain = file.replace(/\.json$/, ""); if (subdomain.split(".").length > 1) { const data = getDomainData(subdomain); - const parentSubdomain = getParentSubdomain(subdomain); const parentDomain = getDomainData(parentSubdomain); @@ -99,45 +76,5 @@ t("Nested subdomains should be owned by the parent subdomain's owner", (t) => { `${file}: Owner does not match the parent subdomain` ); } - } + }); }); - -const reservedDomains = expandReservedDomains(); - -t("Subdomain names must not be reserved", (t) => { - for (const file of files) { - const subdomain = file.replace(/\.json$/, ""); - - t.true(!reservedDomains.includes(subdomain), `${file}: Subdomain name is reserved`); - } - - t.pass(); -}); - -t("Reserved domains file should be valid", (t) => { - const subdomainRegex = /^_?[a-zA-Z0-9]+([-\.][a-zA-Z0-9]+)*(\[\d+-\d+\])?$/; - - for (const item of reservedDomains) { - t.regex( - item, - subdomainRegex, - `[util/reserved-domains.json] Invalid subdomain name "${item}" at index ${reservedDomains.indexOf(item)}` - ); - } - - t.pass(); -}); - -const exceptedDomains = require("../util/excepted-domains.json"); - -t("Subdomains on the root should not start with an underscore", (t) => { - for (const file of files) { - const subdomain = file.replace(/\.json$/, ""); - - if (subdomain.split(".").length === 1 && !exceptedDomains.includes(subdomain)) { - t.true(subdomain[0] !== "_", `${file}: Root subdomains should not start with an underscore`); - } - } - - t.pass(); -}) diff --git a/tests/json.test.js b/tests/json.test.js index 4dab0ede7..80d83c9ab 100644 --- a/tests/json.test.js +++ b/tests/json.test.js @@ -2,13 +2,16 @@ const t = require("ava"); const fs = require("fs-extra"); const path = require("path"); +const ignoredRootJSONFiles = ["package-lock.json", "package.json"]; + const requiredFields = { owner: "object", record: "object" }; const optionalFields = { - proxied: "boolean" + proxied: "boolean", + redirect_config: "object" }; const requiredOwnerFields = { @@ -19,31 +22,87 @@ const optionalOwnerFields = { email: "string" }; +const optionalRedirectConfigFields = { + custom_paths: "object", + redirect_paths: "boolean" +}; + const emailRegex = /^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$/; const hostnameRegex = /^(?=.{1,253}$)(?:(?:[_a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)\.)+[a-zA-Z]{2,63}$/; +const exceptedDomains = require("../util/excepted-domains.json"); +const reservedDomains = require("../util/reserved-domains.json"); const domainsPath = path.resolve("domains"); const files = fs.readdirSync(domainsPath); -function validateRequiredFields(t, obj, requiredFields, file) { - Object.keys(requiredFields).forEach((key) => { - t.true(obj.hasOwnProperty(key), `${file}: Missing required field: ${key}`); - t.is(typeof obj[key], requiredFields[key], `${file}: Field ${key} should be of type ${requiredFields[key]}`); +const expandReservedDomains = (reserved) => { + const expandedList = [...reserved]; + + reserved.forEach((item) => { + const rangeMatch = item.match(/\[(\d+)-(\d+)\]/); + + if (rangeMatch) { + const prefix = item.split("[")[0]; + const start = parseInt(rangeMatch[1], 10); + const end = parseInt(rangeMatch[2], 10); + + if (start < end) { + for (let i = start; i <= end; i++) { + expandedList.push(prefix + i); + } + expandedList.splice(expandedList.indexOf(item), 1); + } else { + throw new Error(`[util/reserved-domains.json] Invalid range [${start}-${end}] in "${item}"`); + } + } }); -} + + return expandedList; +}; + +const expandedReservedDomains = expandReservedDomains(reservedDomains); + +function validateFields(t, obj, fields, file, prefix = "") { + Object.keys(fields).forEach((key) => { + const fieldPath = prefix ? `${prefix}.${key}` : key; -function validateOptionalFields(t, obj, optionalFields, file) { - Object.keys(optionalFields).forEach((key) => { if (obj.hasOwnProperty(key)) { - t.is( - typeof obj[key], - optionalFields[key], - `${file}: Field ${key} should be of type ${optionalFields[key]}` - ); + t.is(typeof obj[key], fields[key], `${file}: Field ${fieldPath} should be of type ${fields[key]}`); + } else if (fields === requiredFields) { + t.true(false, `${file}: Missing required field: ${fieldPath}`); } }); } +function validateFileName(t, file) { + t.true(file.endsWith(".json"), `${file}: File does not have .json extension`); + t.false(file.includes(".is-a.dev"), `${file}: File name should not contain .is-a.dev`); + t.true(file === file.toLowerCase(), `${file}: File name should be all lowercase`); + + // Ignore root domain + if (file !== "@.json") { + const subdomain = file.replace(/\.json$/, ""); + + t.regex( + subdomain + ".is-a.dev", + hostnameRegex, + `${file}: FQDN must be 1-253 characters, use letters, numbers, dots, or hyphens, and not start or end with a hyphen.` + ); + t.true(!expandedReservedDomains.includes(subdomain), `${file}: Subdomain name is reserved`); + + if (subdomain.split(".").length === 1 && !exceptedDomains.includes(subdomain)) { + t.false(subdomain.startsWith("_"), `${file}: Root subdomains should not start with an underscore`); + } + } +} + +t("JSON files should not be in the root directory", (t) => { + const rootFiles = fs + .readdirSync(path.resolve()) + .filter((file) => file.endsWith(".json") && !ignoredRootJSONFiles.includes(file)); + t.is(rootFiles.length, 0, "JSON files should not be in the root directory"); +}); + t("All files should be valid JSON", (t) => { files.forEach((file) => { t.notThrows(() => fs.readJsonSync(path.join(domainsPath, file)), `${file}: Invalid JSON file`); @@ -52,59 +111,47 @@ t("All files should be valid JSON", (t) => { t("All files should have valid file names", (t) => { files.forEach((file) => { - t.true(file.endsWith(".json"), `${file}: File does not have .json extension`); - t.false(file.includes(".is-a.dev"), `${file}: File name should not contain .is-a.dev`); - t.true(file === file.toLowerCase(), `${file}: File name should be lowercase`); - - // Ignore root domain - if (file !== "@.json") { - const subdomain = file.replace(/\.json$/, ""); - t.regex( - subdomain + ".is-a.dev", - hostnameRegex, - `${file}: FQDN must be 1-253 characters, use letters, numbers, dots, or hyphens, and not start or end with a hyphen.` - ); - } + validateFileName(t, file); }); }); -t("All files should have the required fields", (t) => { +t("All files should have valid required and optional fields", (t) => { files.forEach((file) => { const data = fs.readJsonSync(path.join(domainsPath, file)); // Validate top-level required fields - validateRequiredFields(t, data, requiredFields, file); + validateFields(t, data, requiredFields, file); - // Validate owner object fields - validateRequiredFields(t, data.owner, requiredOwnerFields, file); + // Validate owner fields + validateFields(t, data.owner, requiredOwnerFields, file, "owner"); + validateFields(t, data.owner, optionalOwnerFields, file, "owner"); + + // Validate optional fields for top-level and redirect config + validateFields(t, data, optionalFields, file); + if (data.redirect_config) { + validateFields(t, data.redirect_config, optionalRedirectConfigFields, file, "redirect_config"); + } + + // Validate email format + if (data.owner.email) { + t.regex(data.owner.email, emailRegex, `${file}: Owner email should be a valid email address`); + } // Ensure 'record' field is not empty t.true(Object.keys(data.record).length > 0, `${file}: Missing DNS records`); }); }); -t("All files should have valid optional fields", (t) => { - files.forEach((file) => { - const data = fs.readJsonSync(path.join(domainsPath, file)); +t("Reserved domains file should be valid", (t) => { + const subdomainRegex = /^_?[a-zA-Z0-9]+([-\.][a-zA-Z0-9]+)*(\[\d+-\d+\])?$/; - // Validate optional fields at top level - validateOptionalFields(t, data, optionalFields, file); - - // Validate optional fields for owner object - validateOptionalFields(t, data.owner, optionalOwnerFields, file); - - // Email validation (if provided) - if (data.owner.email) { - t.regex(data.owner.email, emailRegex, `${file}: Owner email should be a valid email address`); - } + expandedReservedDomains.forEach((item, index) => { + t.regex( + item, + subdomainRegex, + `[util/reserved-domains.json] Invalid subdomain name "${item}" at index ${index}` + ); }); -}); -const ignoredJSONFiles = ["package-lock.json", "package.json"]; - -t("JSON files should not be in the root directory", (t) => { - const rootFiles = fs - .readdirSync(path.resolve()) - .filter((file) => file.endsWith(".json") && !ignoredJSONFiles.includes(file)); - t.is(rootFiles.length, 0, "JSON files should not be in the root directory"); + t.pass(); }); diff --git a/tests/proxy.test.js b/tests/proxy.test.js index 2bb64b48c..d7c73bc5b 100644 --- a/tests/proxy.test.js +++ b/tests/proxy.test.js @@ -3,10 +3,25 @@ const fs = require("fs-extra"); const path = require("path"); const requiredRecordsToProxy = new Set(["A", "AAAA", "CNAME"]); -// URL records are not listed here because they are proxied by default, so they don't need the proxied flag + +const domainCache = {}; + +function getDomainData(file) { + if (domainCache[file]) { + return domainCache[file]; + } + + try { + const data = fs.readJsonSync(path.join(domainsPath, file)); + domainCache[file] = data; + return data; + } catch (error) { + throw new Error(`Failed to read JSON for ${file}: ${error.message}`); + } +} function validateProxiedRecords(t, data, file) { - // Convert the Set to an array for message display + // Convert the Set to an array for message display (moved outside the loop to optimize performance) const recordTypes = Array.from(requiredRecordsToProxy).join(", "); if (data.proxied) { @@ -22,9 +37,9 @@ function validateProxiedRecords(t, data, file) { const domainsPath = path.resolve("domains"); const files = fs.readdirSync(domainsPath).filter((file) => file.endsWith(".json")); -t("Domains with proxy enabled should have at least one record that can be proxied", (t) => { +t("Domains with proxy enabled must have at least one proxy-able record", (t) => { files.forEach((file) => { - const domain = fs.readJsonSync(path.join(domainsPath, file)); + const domain = getDomainData(file); validateProxiedRecords(t, domain, file); }); diff --git a/tests/records.test.js b/tests/records.test.js index fdf2a17e9..d9b8b66f0 100644 --- a/tests/records.test.js +++ b/tests/records.test.js @@ -3,18 +3,32 @@ const fs = require("fs-extra"); const path = require("path"); const validRecordTypes = new Set(["A", "AAAA", "CAA", "CNAME", "DS", "MX", "NS", "SRV", "TXT", "URL"]); - const hostnameRegex = /^(?=.{1,253}$)(?:(?:[_a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)\.)+[a-zA-Z]{2,63}$/; const ipv4Regex = /^(25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9]?[0-9])(\.(25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9]?[0-9])){3}$/; const ipv6Regex = /^(?:[0-9a-fA-F]{1,4}:){7}[0-9a-fA-F]{1,4}$|^::(?:[0-9a-fA-F]{1,4}:){0,6}[0-9a-fA-F]{1,4}$|^(?:[0-9a-fA-F]{1,4}:){1,7}:$|^(?:[0-9a-fA-F]{1,4}:){0,6}::(?:[0-9a-fA-F]{1,4}:){0,5}[0-9a-fA-F]{1,4}$/; const domainsPath = path.resolve("domains"); -const files = fs.readdirSync(domainsPath); +const files = fs.readdirSync(domainsPath).filter((file) => file.endsWith(".json")); + +const domainCache = {}; + +function getDomainData(file) { + if (domainCache[file]) { + return domainCache[file]; + } + + try { + const data = fs.readJsonSync(path.join(domainsPath, file)); + domainCache[file] = data; + return data; + } catch (error) { + throw new Error(`Failed to read JSON for ${file}: ${error.message}`); + } +} function expandIPv6(ip) { let segments = ip.split(":"); - const emptyIndex = segments.indexOf(""); if (emptyIndex !== -1) { @@ -31,7 +45,7 @@ function expandIPv6(ip) { return segments.map((segment) => segment.padStart(4, "0")).join(":"); } -function validateIPv4(ip, proxied, file, index) { +function validateIPv4(ip, proxied, file) { const parts = ip.split(".").map(Number); if (parts.length !== 4 || parts.some((part) => isNaN(part) || part < 0 || part > 255)) return false; @@ -74,33 +88,112 @@ function isValidHexadecimal(value) { return /^[0-9a-fA-F]+$/.test(value); } +function validateRecordValues(t, data, file) { + Object.keys(data.record).forEach((key) => { + const value = data.record[key]; + + // Validate A, AAAA, MX, NS records: Array of strings + if (["A", "AAAA", "MX", "NS"].includes(key)) { + t.true(Array.isArray(value), `${file}: Record value for ${key} should be an array`); + value.forEach((record, idx) => { + t.true( + typeof record === "string", + `${file}: Record value for ${key} should be a string at index ${idx}` + ); + if (key === "A") { + t.regex(record, ipv4Regex, `${file}: Invalid IPv4 address for ${key} at index ${idx}`); + t.true( + validateIPv4(record, data.proxied, file, idx), + `${file}: Invalid IPv4 address for ${key} at index ${idx}` + ); + } + if (key === "AAAA") { + t.regex(expandIPv6(record), ipv6Regex, `${file}: Invalid IPv6 address for ${key} at index ${idx}`); + t.true(validateIPv6(record), `${file}: Invalid IPv6 address for ${key} at index ${idx}`); + } + if (["MX", "NS"].includes(key)) { + t.true(isValidHostname(record), `${file}: Invalid hostname for ${key} at index ${idx}`); + } + }); + } + + // Validate CNAME and URL records: Single string + if (["CNAME", "URL"].includes(key)) { + t.true(typeof value === "string", `${file}: Record value for ${key} should be a string`); + if (key === "CNAME") { + t.true(isValidHostname(value), `${file}: Invalid hostname for ${key}`); + t.true(value !== file, `${file}: CNAME cannot point to itself`); + } + if (key === "URL") { + t.true( + value.startsWith("http://") || value.startsWith("https://"), + `${file}: Record value for ${key} must start with http:// or https://` + ); + t.notThrows(() => new URL(value), `${file}: Invalid URL for ${key}`); + } + } + + // Validate CAA, DS, SRV records: Array of objects + if (["CAA", "DS", "SRV"].includes(key)) { + t.true(Array.isArray(value), `${file}: Record value for ${key} should be an array`); + value.forEach((record, idx) => { + t.true( + typeof record === "object", + `${file}: Record value for ${key} should be an object at index ${idx}` + ); + if (key === "DS") { + t.true( + Number.isInteger(record.key_tag) && record.key_tag >= 0 && record.key_tag <= 65535, + `${file}: Invalid key_tag for DS at index ${idx}` + ); + t.true(isValidHexadecimal(record.digest), `${file}: Invalid digest for DS at index ${idx}`); + } + }); + } + + // TXT: Single string or array of strings + if (key === "TXT") { + if (Array.isArray(value)) { + value.forEach((record, idx) => { + t.true(typeof record === "string", `${file}: TXT record value should be a string at index ${idx}`); + }); + } else { + t.true(typeof value === "string", `${file}: TXT record value should be a string`); + } + } + }); +} + t("All files should have valid record types", (t) => { files.forEach((file) => { - const data = fs.readJsonSync(path.join(domainsPath, file)); + const data = getDomainData(file); const recordKeys = Object.keys(data.record); recordKeys.forEach((key) => { t.true(validateRecordType(key), `${file}: Invalid record type: ${key}`); }); + // Record type combinations validation if (recordKeys.includes("CNAME") && !data.proxied) { t.is(recordKeys.length, 1, `${file}: CNAME records cannot be combined with other records unless proxied`); } - if (recordKeys.includes("NS")) { t.true( recordKeys.length === 1 || (recordKeys.length === 2 && recordKeys.includes("DS")), `${file}: NS records cannot be combined with other records, except for DS records` ); } - if (recordKeys.includes("DS")) { t.true(recordKeys.includes("NS"), `${file}: DS records must be combined with NS records`); } - if (recordKeys.includes("URL")) { - t.true(!recordKeys.includes("A") && !recordKeys.includes("AAAA") && !recordKeys.includes("CNAME"), `${file}: URL records cannot be combined with A, AAAA, or CNAME records`); + t.true( + !recordKeys.includes("A") && !recordKeys.includes("AAAA") && !recordKeys.includes("CNAME"), + `${file}: URL records cannot be combined with A, AAAA, or CNAME records` + ); } + + validateRecordValues(t, data, file); }); t.pass(); @@ -108,106 +201,10 @@ t("All files should have valid record types", (t) => { t("All files should not have duplicate record keys", (t) => { files.forEach((file) => { - const data = fs.readJsonSync(path.join(domainsPath, file)); + const data = getDomainData(file); const recordKeys = Object.keys(data.record); const uniqueRecordKeys = new Set(recordKeys); t.is(recordKeys.length, uniqueRecordKeys.size, `${file}: Duplicate record keys found`); }); }); - -t("All files should have valid record values", (t) => { - files.forEach((file) => { - const data = fs.readJsonSync(path.join(domainsPath, file)); - - Object.keys(data.record).forEach((key) => { - const value = data.record[key]; - const subdomain = file.replace(/\.json$/, ""); // Get the subdomain from the filename - - // Validate A, AAAA, MX, NS records: Array of strings - if (["A", "AAAA", "MX", "NS"].includes(key)) { - t.true(Array.isArray(value), `${file}: Record value for ${key} should be an array`); - - value.forEach((record, idx) => { - t.true( - typeof record === "string", - `${file}: Record value for ${key} should be a string at index ${idx}` - ); - - if (key === "A") { - t.regex(record, ipv4Regex, `${file}: Invalid IPv4 address for ${key} at index ${idx}`); - t.true( - validateIPv4(record, data.proxied, file, idx), - `${file}: Invalid IPv4 address for ${key} at index ${idx}` - ); - } - - if (key === "AAAA") { - t.regex( - expandIPv6(record), - ipv6Regex, - `${file}: Invalid IPv6 address for ${key} at index ${idx}` - ); - t.true(validateIPv6(record), `${file}: Invalid IPv6 address for ${key} at index ${idx}`); - } - - if (["MX", "NS"].includes(key)) { - t.true(isValidHostname(record), `${file}: Invalid hostname for ${key} at index ${idx}`); - } - }); - } - - // Validate CNAME and URL records: Single string - if (["CNAME", "URL"].includes(key)) { - t.true(typeof value === "string", `${file}: Record value for ${key} should be a string`); - - if (key === "CNAME") { - t.true(isValidHostname(value), `${file}: Invalid hostname for ${key}`); - t.true(value !== file, `${file}: CNAME cannot point to itself`); - if (file === "@.json") { - t.true(value !== "is-a.dev", `${file}: CNAME cannot point to itself`); - } - } - - if (key === "URL") { - t.true(value.startsWith("http://") || value.startsWith("https://"), `${file}: Record value for ${key} must start with http:// or https://`) - t.notThrows(() => new URL(value), `${file}: Invalid URL for ${key}`); - } - } - - // Validate CAA, DS, SRV records: Array of objects - if (["CAA", "DS", "SRV"].includes(key)) { - t.true(Array.isArray(value), `${file}: Record value for ${key} should be an array`); - - value.forEach((record, idx) => { - t.true( - typeof record === "object", - `${file}: Record value for ${key} should be an object at index ${idx}` - ); - - if (key === "DS") { - t.true( - Number.isInteger(record.key_tag) && record.key_tag >= 0 && record.key_tag <= 65535, - `${file}: Invalid key_tag for DS at index ${idx}` - ); - t.true(isValidHexadecimal(record.digest), `${file}: Invalid digest for DS at index ${idx}`); - } - }); - } - - // TXT: Single string or array of strings - if (key === "TXT") { - if (Array.isArray(value)) { - value.forEach((record, idx) => { - t.true( - typeof record === "string", - `${file}: TXT record value should be a string at index ${idx}` - ); - }); - } else { - t.true(typeof value === "string", `${file}: TXT record value should be a string`); - } - } - }); - }); -}); From 8f68428416a0a24481b540a57eb3f0326f703747 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 12:13:55 +0800 Subject: [PATCH 50/80] Update william.json --- domains/william.json | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-) diff --git a/domains/william.json b/domains/william.json index 6f3d1268b..fcec296e5 100644 --- a/domains/william.json +++ b/domains/william.json @@ -4,6 +4,12 @@ "email": "william@is-a.dev" }, "record": { - "URL": "https://github.com/wdhdev" + "URL": "https://wharrison.com.au" + }, + "redirect_config": { + "custom_paths": { + "/github": "https://github.com/wdhdev" + }, + "redirect_paths": true } } From cbce32e31f27cc24c0c8b87a2b56208882082acf Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 12:22:01 +0800 Subject: [PATCH 51/80] redirect config must have URL record --- tests/records.test.js | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/tests/records.test.js b/tests/records.test.js index d9b8b66f0..bb17aa8bf 100644 --- a/tests/records.test.js +++ b/tests/records.test.js @@ -45,7 +45,7 @@ function expandIPv6(ip) { return segments.map((segment) => segment.padStart(4, "0")).join(":"); } -function validateIPv4(ip, proxied, file) { +function validateIPv4(ip, proxied) { const parts = ip.split(".").map(Number); if (parts.length !== 4 || parts.some((part) => isNaN(part) || part < 0 || part > 255)) return false; @@ -192,6 +192,9 @@ t("All files should have valid record types", (t) => { `${file}: URL records cannot be combined with A, AAAA, or CNAME records` ); } + if (data.redirect_config) { + t.true(recordKeys.includes("URL"), `${file}: Redirect config must be combined with a URL record`); + } validateRecordValues(t, data, file); }); From 3bf34a62be932a6d01f848de5985733ecea2fcac Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 12:22:54 +0800 Subject: [PATCH 52/80] Update w.json --- domains/w.json | 3 +++ 1 file changed, 3 insertions(+) diff --git a/domains/w.json b/domains/w.json index 159f1b048..55dcef36b 100644 --- a/domains/w.json +++ b/domains/w.json @@ -5,5 +5,8 @@ }, "record": { "URL": "https://william.is-a.dev" + }, + "redirect_config": { + "redirect_paths": true } } From c6654294f31987d2854053ceeccdbce0a7845a1a Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 12:45:55 +0800 Subject: [PATCH 53/80] Update records.test.js --- tests/records.test.js | 71 ++++++++++++++++++++++++++++--------------- 1 file changed, 47 insertions(+), 24 deletions(-) diff --git a/tests/records.test.js b/tests/records.test.js index bb17aa8bf..69a42feb0 100644 --- a/tests/records.test.js +++ b/tests/records.test.js @@ -89,10 +89,8 @@ function isValidHexadecimal(value) { } function validateRecordValues(t, data, file) { - Object.keys(data.record).forEach((key) => { - const value = data.record[key]; - - // Validate A, AAAA, MX, NS records: Array of strings + Object.entries(data.record).forEach(([key, value]) => { + // General validation for arrays if (["A", "AAAA", "MX", "NS"].includes(key)) { t.true(Array.isArray(value), `${file}: Record value for ${key} should be an array`); value.forEach((record, idx) => { @@ -101,30 +99,28 @@ function validateRecordValues(t, data, file) { `${file}: Record value for ${key} should be a string at index ${idx}` ); if (key === "A") { - t.regex(record, ipv4Regex, `${file}: Invalid IPv4 address for ${key} at index ${idx}`); + t.true(ipv4Regex.test(record), `${file}: Invalid IPv4 address for ${key} at index ${idx}`); t.true( - validateIPv4(record, data.proxied, file, idx), + validateIPv4(record, data.proxied), `${file}: Invalid IPv4 address for ${key} at index ${idx}` ); - } - if (key === "AAAA") { - t.regex(expandIPv6(record), ipv6Regex, `${file}: Invalid IPv6 address for ${key} at index ${idx}`); - t.true(validateIPv6(record), `${file}: Invalid IPv6 address for ${key} at index ${idx}`); - } - if (["MX", "NS"].includes(key)) { + } else if (key === "AAAA") { + const expandedIPv6 = expandIPv6(record); + t.true(ipv6Regex.test(expandedIPv6), `${file}: Invalid IPv6 address for ${key} at index ${idx}`); + t.true(validateIPv6(expandedIPv6), `${file}: Invalid IPv6 address for ${key} at index ${idx}`); + } else if (["MX", "NS"].includes(key)) { t.true(isValidHostname(record), `${file}: Invalid hostname for ${key} at index ${idx}`); } }); } - // Validate CNAME and URL records: Single string + // CNAME and URL validations if (["CNAME", "URL"].includes(key)) { t.true(typeof value === "string", `${file}: Record value for ${key} should be a string`); if (key === "CNAME") { t.true(isValidHostname(value), `${file}: Invalid hostname for ${key}`); t.true(value !== file, `${file}: CNAME cannot point to itself`); - } - if (key === "URL") { + } else if (key === "URL") { t.true( value.startsWith("http://") || value.startsWith("https://"), `${file}: Record value for ${key} must start with http:// or https://` @@ -133,7 +129,7 @@ function validateRecordValues(t, data, file) { } } - // Validate CAA, DS, SRV records: Array of objects + // CAA, DS, SRV validations if (["CAA", "DS", "SRV"].includes(key)) { t.true(Array.isArray(value), `${file}: Record value for ${key} should be an array`); value.forEach((record, idx) => { @@ -151,17 +147,44 @@ function validateRecordValues(t, data, file) { }); } - // TXT: Single string or array of strings + // TXT validation if (key === "TXT") { - if (Array.isArray(value)) { - value.forEach((record, idx) => { - t.true(typeof record === "string", `${file}: TXT record value should be a string at index ${idx}`); - }); - } else { - t.true(typeof value === "string", `${file}: TXT record value should be a string`); - } + const values = Array.isArray(value) ? value : [value]; + values.forEach((record, idx) => { + t.true(typeof record === "string", `${file}: TXT record value should be a string at index ${idx}`); + }); } }); + + if (data.redirect_config) { + const customPaths = Object.keys(data.redirect_config.custom_paths || {}); + const pathRegex = /^\/[a-zA-Z0-9\-_\.\/]+(? { + const customRedirectURL = data.redirect_config.custom_paths[customPath]; + + t.true( + pathRegex.test(customPath), + `${file}: Custom path in redirect_config must start with a slash, contain only alphanumeric characters, hyphens, underscores, periods, and slashes, and cannot end with a slash at index ${idx}` + ); + t.true( + customPath.length >= 2 && customPath.length <= 255, + `${file}: Custom path in redirect_config should be 2-255 characters long at index ${idx}` + ); + t.true( + data.record.URL !== customRedirectURL, + `${file}: Custom path in redirect_config should be different from the URL record at index ${idx}` + ); + t.true( + customRedirectURL.startsWith("http://") || customRedirectURL.startsWith("https://"), + `${file}: Custom path in redirect_config must start with http:// or https:// at index ${idx}` + ); + t.notThrows( + () => new URL(customRedirectURL), + `${file}: Invalid URL for custom path in redirect_config at index ${idx}` + ); + }); + } } t("All files should have valid record types", (t) => { From e338370219a5585d7bf51624c52acb2f450019a2 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 13:26:28 +0800 Subject: [PATCH 54/80] optimisations + test mailto redirects --- domains/william.json | 1 + tests/records.test.js | 35 ++++++++++++++++++++++++----------- 2 files changed, 25 insertions(+), 11 deletions(-) diff --git a/domains/william.json b/domains/william.json index fcec296e5..6950dc060 100644 --- a/domains/william.json +++ b/domains/william.json @@ -8,6 +8,7 @@ }, "redirect_config": { "custom_paths": { + "/email": "mailto:will@hrsn.dev", "/github": "https://github.com/wdhdev" }, "redirect_paths": true diff --git a/tests/records.test.js b/tests/records.test.js index 69a42feb0..13aa8e1ec 100644 --- a/tests/records.test.js +++ b/tests/records.test.js @@ -89,6 +89,8 @@ function isValidHexadecimal(value) { } function validateRecordValues(t, data, file) { + const subdomain = file.replace(/\.json$/, ""); + Object.entries(data.record).forEach(([key, value]) => { // General validation for arrays if (["A", "AAAA", "MX", "NS"].includes(key)) { @@ -126,6 +128,11 @@ function validateRecordValues(t, data, file) { `${file}: Record value for ${key} must start with http:// or https://` ); t.notThrows(() => new URL(value), `${file}: Invalid URL for ${key}`); + + const urlHost = new URL(value).host; + const isSelfReferencing = + file === "@.json" ? urlHost === "is-a.dev" : urlHost === `${subdomain}.is-a.dev`; + t.true(!isSelfReferencing, `${file}: URL cannot point to itself`); } } @@ -162,27 +169,33 @@ function validateRecordValues(t, data, file) { customPaths.forEach((customPath, idx) => { const customRedirectURL = data.redirect_config.custom_paths[customPath]; + const urlMessage = `${file}: Custom path in redirect_config`; + // Validate the custom path t.true( pathRegex.test(customPath), - `${file}: Custom path in redirect_config must start with a slash, contain only alphanumeric characters, hyphens, underscores, periods, and slashes, and cannot end with a slash at index ${idx}` + `${urlMessage} must start with a slash, contain only alphanumeric characters, hyphens, underscores, periods, and slashes, and cannot end with a slash at index ${idx}` ); t.true( customPath.length >= 2 && customPath.length <= 255, - `${file}: Custom path in redirect_config should be 2-255 characters long at index ${idx}` + `${urlMessage} should be 2-255 characters long at index ${idx}` ); + + // Validate the redirect URL t.true( data.record.URL !== customRedirectURL, - `${file}: Custom path in redirect_config should be different from the URL record at index ${idx}` - ); - t.true( - customRedirectURL.startsWith("http://") || customRedirectURL.startsWith("https://"), - `${file}: Custom path in redirect_config must start with http:// or https:// at index ${idx}` - ); - t.notThrows( - () => new URL(customRedirectURL), - `${file}: Invalid URL for custom path in redirect_config at index ${idx}` + `${urlMessage} should be different from the URL record at index ${idx}` ); + // t.true( + // customRedirectURL.startsWith("http://") || customRedirectURL.startsWith("https://"), + // `${urlMessage} must start with http:// or https:// at index ${idx}` + // ); + t.notThrows(() => new URL(customRedirectURL), `${urlMessage} contains an invalid URL at index ${idx}`); + + // Check for self-referencing redirects + const urlHost = new URL(customRedirectURL).host; + const isSelfReferencing = file === "@.json" ? urlHost === "is-a.dev" : urlHost === `${subdomain}.is-a.dev`; + t.true(!isSelfReferencing, `${urlMessage} cannot point to itself at index ${idx}`); }); } } From 961a85dd0877432f5ce5fe90da40d0a18852682e Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 13:29:46 +0800 Subject: [PATCH 55/80] remove mailto test --- domains/william.json | 1 - tests/records.test.js | 8 ++++---- 2 files changed, 4 insertions(+), 5 deletions(-) diff --git a/domains/william.json b/domains/william.json index 6950dc060..fcec296e5 100644 --- a/domains/william.json +++ b/domains/william.json @@ -8,7 +8,6 @@ }, "redirect_config": { "custom_paths": { - "/email": "mailto:will@hrsn.dev", "/github": "https://github.com/wdhdev" }, "redirect_paths": true diff --git a/tests/records.test.js b/tests/records.test.js index 13aa8e1ec..4d03a0e75 100644 --- a/tests/records.test.js +++ b/tests/records.test.js @@ -186,10 +186,10 @@ function validateRecordValues(t, data, file) { data.record.URL !== customRedirectURL, `${urlMessage} should be different from the URL record at index ${idx}` ); - // t.true( - // customRedirectURL.startsWith("http://") || customRedirectURL.startsWith("https://"), - // `${urlMessage} must start with http:// or https:// at index ${idx}` - // ); + t.true( + customRedirectURL.startsWith("http://") || customRedirectURL.startsWith("https://"), + `${urlMessage} must start with http:// or https:// at index ${idx}` + ); t.notThrows(() => new URL(customRedirectURL), `${urlMessage} contains an invalid URL at index ${idx}`); // Check for self-referencing redirects From e5d0614435bd2cb4c26c108206326bb51f1d88e0 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 14:10:06 +0800 Subject: [PATCH 56/80] beta: email forwarding --- dnsconfig.js | 8 ++++++++ 1 file changed, 8 insertions(+) diff --git a/dnsconfig.js b/dnsconfig.js index 5ee924a87..78a19680d 100644 --- a/dnsconfig.js +++ b/dnsconfig.js @@ -140,6 +140,14 @@ for (var subdomain in domains) { if (domainData.record.URL) { records.push(A(subdomainName, IP("192.0.2.1"), CF_PROXY_ON)); } + + // Handle Email Forwarding + if (domainData.email_forwarding) { + records.push(MX(subdomainName, 34, "route1.mx.cloudflare.net.")); + records.push(MX(subdomainName, 62, "route2.mx.cloudflare.net.")); + records.push(MX(subdomainName, 36, "route3.mx.cloudflare.net.")); + records.push(TXT(subdomainName, "\"" + "v=spf1 include:_spf.mx.cloudflare.net ~all" + "\"")); + } } var options = { From cd20653d7e447c160d91e5696f058007e308a6d2 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 14:21:32 +0800 Subject: [PATCH 57/80] Update dnsconfig.js --- dnsconfig.js | 9 --------- 1 file changed, 9 deletions(-) diff --git a/dnsconfig.js b/dnsconfig.js index 78a19680d..91d9437f7 100644 --- a/dnsconfig.js +++ b/dnsconfig.js @@ -51,7 +51,6 @@ for (var subdomain in domains) { records.push( CAA( subdomainName, - caaRecord.flags, caaRecord.tag, caaRecord.value ) @@ -140,14 +139,6 @@ for (var subdomain in domains) { if (domainData.record.URL) { records.push(A(subdomainName, IP("192.0.2.1"), CF_PROXY_ON)); } - - // Handle Email Forwarding - if (domainData.email_forwarding) { - records.push(MX(subdomainName, 34, "route1.mx.cloudflare.net.")); - records.push(MX(subdomainName, 62, "route2.mx.cloudflare.net.")); - records.push(MX(subdomainName, 36, "route3.mx.cloudflare.net.")); - records.push(TXT(subdomainName, "\"" + "v=spf1 include:_spf.mx.cloudflare.net ~all" + "\"")); - } } var options = { From 17777884528610a41a502cbb2fbc47ee637c03d9 Mon Sep 17 00:00:00 2001 From: JumanJi <90971841+heyjumanji@users.noreply.github.com> Date: Mon, 13 Jan 2025 11:55:10 +0530 Subject: [PATCH 58/80] Create _vercel.jumanji.json --- domains/_vercel.jumanji.json | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 domains/_vercel.jumanji.json diff --git a/domains/_vercel.jumanji.json b/domains/_vercel.jumanji.json new file mode 100644 index 000000000..cf5987dea --- /dev/null +++ b/domains/_vercel.jumanji.json @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "heyjumanji", + "email": "madhuchutiya.unhinge50@silomails.com" + }, + "record": { + "TXT": "vc-domain-verify=jumanji.is-a.dev,291766e76a7ab5de1bc7" + } +} From 429ce273b87339aee743c0e369b21acdde6635d0 Mon Sep 17 00:00:00 2001 From: JumanJi <90971841+heyjumanji@users.noreply.github.com> Date: Mon, 13 Jan 2025 11:57:42 +0530 Subject: [PATCH 59/80] Update jumanji.json --- domains/jumanji.json | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/domains/jumanji.json b/domains/jumanji.json index b3ef5c086..e6bb22ab4 100644 --- a/domains/jumanji.json +++ b/domains/jumanji.json @@ -6,6 +6,7 @@ "record": { "A": ["172.66.47.44", "172.66.44.212"], "MX": ["mx1.improvmx.com", "mx2.improvmx.com"], - "TXT": "v=spf1 include:spf.improvmx.com ~all" + "TXT": "v=spf1 include:spf.improvmx.com ~all", + "CNAME": "jumanji.vercel.app" } } From 94b4e497a88268288b9eb31f49aac63b460fe725 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 14:29:51 +0800 Subject: [PATCH 60/80] more validations --- dnsconfig.js | 52 +++++++------------------------------------ tests/records.test.js | 40 ++++++++++++++++++++++++++++++++- 2 files changed, 47 insertions(+), 45 deletions(-) diff --git a/dnsconfig.js b/dnsconfig.js index 91d9437f7..3cd55b011 100644 --- a/dnsconfig.js +++ b/dnsconfig.js @@ -29,18 +29,14 @@ for (var subdomain in domains) { // Handle A records if (domainData.record.A) { for (var a in domainData.record.A) { - records.push( - A(subdomainName, IP(domainData.record.A[a]), proxyState) - ); + records.push(A(subdomainName, IP(domainData.record.A[a]), proxyState)); } } // Handle AAAA records if (domainData.record.AAAA) { for (var aaaa in domainData.record.AAAA) { - records.push( - AAAA(subdomainName, domainData.record.AAAA[aaaa], proxyState) - ); + records.push(AAAA(subdomainName, domainData.record.AAAA[aaaa], proxyState)); } } @@ -48,28 +44,14 @@ for (var subdomain in domains) { if (domainData.record.CAA) { for (var caa in domainData.record.CAA) { var caaRecord = domainData.record.CAA[caa]; - records.push( - CAA( - subdomainName, - caaRecord.tag, - caaRecord.value - ) - ); + records.push(CAA(subdomainName, caaRecord.tag, caaRecord.value)); } } // Handle CNAME records if (domainData.record.CNAME) { - // Allow CNAME record on root - if (subdomainName === "@") { - records.push( - ALIAS(subdomainName, domainData.record.CNAME + ".", proxyState) - ); - } else { - records.push( - CNAME(subdomainName, domainData.record.CNAME + ".", proxyState) - ); - } + // Use ALIAS instead of CNAME to support CNAME flattening on the root domain + records.push(ALIAS(subdomainName, domainData.record.CNAME + ".", proxyState)); } // Handle DS records @@ -77,13 +59,7 @@ for (var subdomain in domains) { for (var ds in domainData.record.DS) { var dsRecord = domainData.record.DS[ds]; records.push( - DS( - subdomainName, - dsRecord.key_tag, - dsRecord.algorithm, - dsRecord.digest_type, - dsRecord.digest - ) + DS(subdomainName, dsRecord.key_tag, dsRecord.algorithm, dsRecord.digest_type, dsRecord.digest) ); } } @@ -91,13 +67,7 @@ for (var subdomain in domains) { // Handle MX records if (domainData.record.MX) { for (var mx in domainData.record.MX) { - records.push( - MX( - subdomainName, - 10 + parseInt(mx), - domainData.record.MX[mx] + "." - ) - ); + records.push(MX(subdomainName, 10 + parseInt(mx), domainData.record.MX[mx] + ".")); } } @@ -113,13 +83,7 @@ for (var subdomain in domains) { for (var srv in domainData.record.SRV) { var srvRecord = domainData.record.SRV[srv]; records.push( - SRV( - subdomainName, - srvRecord.priority, - srvRecord.weight, - srvRecord.port, - srvRecord.target + "." - ) + SRV(subdomainName, srvRecord.priority, srvRecord.weight, srvRecord.port, srvRecord.target + ".") ); } } diff --git a/tests/records.test.js b/tests/records.test.js index 4d03a0e75..a13530cf5 100644 --- a/tests/records.test.js +++ b/tests/records.test.js @@ -95,11 +95,13 @@ function validateRecordValues(t, data, file) { // General validation for arrays if (["A", "AAAA", "MX", "NS"].includes(key)) { t.true(Array.isArray(value), `${file}: Record value for ${key} should be an array`); + value.forEach((record, idx) => { t.true( typeof record === "string", `${file}: Record value for ${key} should be a string at index ${idx}` ); + if (key === "A") { t.true(ipv4Regex.test(record), `${file}: Invalid IPv4 address for ${key} at index ${idx}`); t.true( @@ -119,6 +121,7 @@ function validateRecordValues(t, data, file) { // CNAME and URL validations if (["CNAME", "URL"].includes(key)) { t.true(typeof value === "string", `${file}: Record value for ${key} should be a string`); + if (key === "CNAME") { t.true(isValidHostname(value), `${file}: Invalid hostname for ${key}`); t.true(value !== file, `${file}: CNAME cannot point to itself`); @@ -132,6 +135,7 @@ function validateRecordValues(t, data, file) { const urlHost = new URL(value).host; const isSelfReferencing = file === "@.json" ? urlHost === "is-a.dev" : urlHost === `${subdomain}.is-a.dev`; + t.true(!isSelfReferencing, `${file}: URL cannot point to itself`); } } @@ -139,17 +143,51 @@ function validateRecordValues(t, data, file) { // CAA, DS, SRV validations if (["CAA", "DS", "SRV"].includes(key)) { t.true(Array.isArray(value), `${file}: Record value for ${key} should be an array`); + value.forEach((record, idx) => { t.true( typeof record === "object", `${file}: Record value for ${key} should be an object at index ${idx}` ); - if (key === "DS") { + + if (key === "CAA") { + t.true( + ["issue", "issuewild", "iodef"].includes(record.tag), + `${file}: Invalid tag for CAA at index ${idx}` + ); + t.true(typeof record.value === "string", `${file}: Invalid value for CAA at index ${idx}`); + t.true( + isValidHostname(record.value) || record.value === ";", + `${file}: Value must be a hostname or semicolon for CAA at index ${idx}` + ); + } else if (key === "DS") { t.true( Number.isInteger(record.key_tag) && record.key_tag >= 0 && record.key_tag <= 65535, `${file}: Invalid key_tag for DS at index ${idx}` ); + t.true( + Number.isInteger(record.algorithm) && record.algorithm >= 0 && record.algorithm <= 255, + `${file}: Invalid algorithm for DS at index ${idx}` + ); + t.true( + Number.isInteger(record.digest_type) && record.digest_type >= 0 && record.digest_type <= 255, + `${file}: Invalid digest_type for DS at index ${idx}` + ); t.true(isValidHexadecimal(record.digest), `${file}: Invalid digest for DS at index ${idx}`); + } else if (key === "SRV") { + t.true( + Number.isInteger(record.priority) && record.priority >= 0 && record.priority <= 65535, + `${file}: Invalid priority for SRV at index ${idx}` + ); + t.true( + Number.isInteger(record.weight) && record.weight >= 0 && record.weight <= 65535, + `${file}: Invalid weight for SRV at index ${idx}` + ); + t.true( + Number.isInteger(record.port) && record.port >= 0 && record.port <= 65535, + `${file}: Invalid port for SRV at index ${idx}` + ); + t.true(isValidHostname(record.target), `${file}: Invalid target for SRV at index ${idx}`); } }); } From 2249355301b12434a3de17e57aced36bdc356cb4 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 14:31:28 +0800 Subject: [PATCH 61/80] reserve _zone-updated --- util/reserved-domains.json | 1 + 1 file changed, 1 insertion(+) diff --git a/util/reserved-domains.json b/util/reserved-domains.json index 797806d1b..0d2de4bd3 100644 --- a/util/reserved-domains.json +++ b/util/reserved-domains.json @@ -1,6 +1,7 @@ [ "_atproto", "_vercel", + "_zone-updated", "account", "accounts", "admin", From 5ca8e5bdbb86de30a289f8c2de2c1514b8c888a5 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 14:31:53 +0800 Subject: [PATCH 62/80] no need to reserve domains starting with _ --- util/reserved-domains.json | 3 --- 1 file changed, 3 deletions(-) diff --git a/util/reserved-domains.json b/util/reserved-domains.json index 0d2de4bd3..16b3293c7 100644 --- a/util/reserved-domains.json +++ b/util/reserved-domains.json @@ -1,7 +1,4 @@ [ - "_atproto", - "_vercel", - "_zone-updated", "account", "accounts", "admin", From 93c16befbae62e89b7dfc055e55580d5e3c9c946 Mon Sep 17 00:00:00 2001 From: Sisyphus_666 <139012668+Umer-Islam@users.noreply.github.com> Date: Mon, 13 Jan 2025 12:13:18 +0500 Subject: [PATCH 63/80] Create umerislam.json --- domains/umerislam.json | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 domains/umerislam.json diff --git a/domains/umerislam.json b/domains/umerislam.json new file mode 100644 index 000000000..9e46ad79b --- /dev/null +++ b/domains/umerislam.json @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "umer-islam", + "email": "umer.islam474@gmail.com" + }, + "record": { + "CNAME": "umerislam.netlify.app" + } +} From 9544528c9e8c68febf85c7fb8c555bd3360e91c3 Mon Sep 17 00:00:00 2001 From: Muhammad Sami Shoukat <88966319+samishoukat12@users.noreply.github.com> Date: Mon, 13 Jan 2025 12:20:06 +0500 Subject: [PATCH 64/80] samishoukat.is-a.dev --- domains/_vercel.samishoukat.json | 9 +++++++++ domains/samishoukat.json | 9 +++++++++ 2 files changed, 18 insertions(+) create mode 100644 domains/_vercel.samishoukat.json create mode 100644 domains/samishoukat.json diff --git a/domains/_vercel.samishoukat.json b/domains/_vercel.samishoukat.json new file mode 100644 index 000000000..df08f3129 --- /dev/null +++ b/domains/_vercel.samishoukat.json @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "samishoukat12", + "email": "samishoukat12@gmail.com" + }, + "record": { + "TXT": "vc-domain-verify=samishoukat.is-a.dev,f7c3cb972c650104d507" + } + } \ No newline at end of file diff --git a/domains/samishoukat.json b/domains/samishoukat.json new file mode 100644 index 000000000..c88531d66 --- /dev/null +++ b/domains/samishoukat.json @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "samishoukat12", + "email": "samishoukat12@gmail.com" + }, + "record": { + "CNAME": "portfolio2-0-lime.vercel.app" + } + } \ No newline at end of file From ca853b3ac3a7ebfa1939a55628e61997fa7ed57d Mon Sep 17 00:00:00 2001 From: Muhammad Sami Shoukat <88966319+samishoukat12@users.noreply.github.com> Date: Mon, 13 Jan 2025 12:24:54 +0500 Subject: [PATCH 65/80] fix websiste url --- domains/samishoukat.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/domains/samishoukat.json b/domains/samishoukat.json index c88531d66..0b683aab6 100644 --- a/domains/samishoukat.json +++ b/domains/samishoukat.json @@ -4,6 +4,6 @@ "email": "samishoukat12@gmail.com" }, "record": { - "CNAME": "portfolio2-0-lime.vercel.app" + "CNAME": "dev-samishoukat.vercel.app" } } \ No newline at end of file From 24a81b4860c0dbb7b8ccb65354f63a80bdaf2a2c Mon Sep 17 00:00:00 2001 From: suryababus <53492132+suryababus@users.noreply.github.com> Date: Mon, 13 Jan 2025 13:05:26 +0530 Subject: [PATCH 66/80] Create suryababu.json --- domains/suryababu.json | 11 +++++++++++ 1 file changed, 11 insertions(+) create mode 100644 domains/suryababu.json diff --git a/domains/suryababu.json b/domains/suryababu.json new file mode 100644 index 000000000..f78668dd8 --- /dev/null +++ b/domains/suryababu.json @@ -0,0 +1,11 @@ +{ + "description": "Landing page for suryababu.is-a.dev", + "repo": "https://github.com/is-a-dev/docs", + "owner": { + "username": "Suryababu", + "email": "suryababu.k.s@gmail.com" + }, + "record": { + "CNAME": "suryababus.github.io" + } +} From 8177843b95c3e598a566de132246790e571d9e00 Mon Sep 17 00:00:00 2001 From: suryababus <53492132+suryababus@users.noreply.github.com> Date: Mon, 13 Jan 2025 13:17:26 +0530 Subject: [PATCH 67/80] Update suryababu.json --- domains/suryababu.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/domains/suryababu.json b/domains/suryababu.json index f78668dd8..1c87608b8 100644 --- a/domains/suryababu.json +++ b/domains/suryababu.json @@ -2,7 +2,7 @@ "description": "Landing page for suryababu.is-a.dev", "repo": "https://github.com/is-a-dev/docs", "owner": { - "username": "Suryababu", + "username": "suryababu", "email": "suryababu.k.s@gmail.com" }, "record": { From 613548e4f4b6c4890d3569cfffc2d171df43f932 Mon Sep 17 00:00:00 2001 From: JumanJi <90971841+heyjumanji@users.noreply.github.com> Date: Mon, 13 Jan 2025 13:26:56 +0530 Subject: [PATCH 68/80] Update jumanji.json --- domains/jumanji.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/domains/jumanji.json b/domains/jumanji.json index e6bb22ab4..5fa79d9c1 100644 --- a/domains/jumanji.json +++ b/domains/jumanji.json @@ -7,6 +7,6 @@ "A": ["172.66.47.44", "172.66.44.212"], "MX": ["mx1.improvmx.com", "mx2.improvmx.com"], "TXT": "v=spf1 include:spf.improvmx.com ~all", - "CNAME": "jumanji.vercel.app" + "A": ["76.76.21.21"] } } From 9c5b7c440b40a47be7b94084a7137c5a8ad50c3d Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 17:07:55 +0800 Subject: [PATCH 69/80] Rename www.fungaming.joe50097.json to domains/www.fungaming.joe50097.json --- .../www.fungaming.joe50097.json | 0 1 file changed, 0 insertions(+), 0 deletions(-) rename www.fungaming.joe50097.json => domains/www.fungaming.joe50097.json (100%) diff --git a/www.fungaming.joe50097.json b/domains/www.fungaming.joe50097.json similarity index 100% rename from www.fungaming.joe50097.json rename to domains/www.fungaming.joe50097.json From 1aef4b980fca4fb124e69bd5c15df24bb465f823 Mon Sep 17 00:00:00 2001 From: Mohammad Usman Date: Mon, 13 Jan 2025 14:13:04 +0500 Subject: [PATCH 70/80] Add mu.is-a.dev --- domains/mu.json | 9 +++++++++ 1 file changed, 9 insertions(+) create mode 100644 domains/mu.json diff --git a/domains/mu.json b/domains/mu.json new file mode 100644 index 000000000..6edd3c514 --- /dev/null +++ b/domains/mu.json @@ -0,0 +1,9 @@ +{ + "owner": { + "username": "mohammadusman666", + "email": "mohammadusman666@gmail.com" + }, + "record": { + "CNAME": "1d0b4a10.portfolio-1cw.pages.dev" + } +} From d005ee7fc7634314d9d638b4fc3e56b7a497c4d4 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 17:20:25 +0800 Subject: [PATCH 71/80] so close, yet so far --- domains/suryababu.json | 1 - 1 file changed, 1 deletion(-) diff --git a/domains/suryababu.json b/domains/suryababu.json index 1c87608b8..51e6e007d 100644 --- a/domains/suryababu.json +++ b/domains/suryababu.json @@ -1,6 +1,5 @@ { "description": "Landing page for suryababu.is-a.dev", - "repo": "https://github.com/is-a-dev/docs", "owner": { "username": "suryababu", "email": "suryababu.k.s@gmail.com" From 0be1de0efc18900e3370b60100bc59042201444f Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 17:33:45 +0800 Subject: [PATCH 72/80] fix + move duplicate keys check --- tests/json.test.js | 34 ++++++++++++++++++++++++++++++++-- tests/records.test.js | 10 ---------- 2 files changed, 32 insertions(+), 12 deletions(-) diff --git a/tests/json.test.js b/tests/json.test.js index 80d83c9ab..16dd360a2 100644 --- a/tests/json.test.js +++ b/tests/json.test.js @@ -35,7 +35,7 @@ const reservedDomains = require("../util/reserved-domains.json"); const domainsPath = path.resolve("domains"); const files = fs.readdirSync(domainsPath); -const expandReservedDomains = (reserved) => { +function expandReservedDomains(reserved) { const expandedList = [...reserved]; reserved.forEach((item) => { @@ -58,10 +58,30 @@ const expandReservedDomains = (reserved) => { }); return expandedList; -}; +} const expandedReservedDomains = expandReservedDomains(reservedDomains); +function findDuplicateKeys(jsonString) { + const keyPattern = /"([^"]+)"(?=\s*:)/g; + const keys = []; + let match; + + // Find all keys in the JSON string + while ((match = keyPattern.exec(jsonString)) !== null) { + keys.push(match[1]); + } + + // Count occurrences of each key + const keyCount = {}; + keys.forEach((key) => { + keyCount[key] = (keyCount[key] || 0) + 1; + }); + + // Return keys that occur more than once + return Object.keys(keyCount).filter((key) => keyCount[key] > 1); +} + function validateFields(t, obj, fields, file, prefix = "") { Object.keys(fields).forEach((key) => { const fieldPath = prefix ? `${prefix}.${key}` : key; @@ -109,6 +129,16 @@ t("All files should be valid JSON", (t) => { }); }); +t("All files should not have duplicate keys", (t) => { + files.forEach((file) => { + // Parse JSON as a string because JS automatically gets the last key if there are duplicates + const rawData = fs.readFileSync(`${domainsPath}/${file}`, "utf8"); + const duplicateKeys = findDuplicateKeys(rawData); + + t.true(!duplicateKeys.length, `${file}: Duplicate keys found: ${duplicateKeys.join(", ")}`); + }); +}); + t("All files should have valid file names", (t) => { files.forEach((file) => { validateFileName(t, file); diff --git a/tests/records.test.js b/tests/records.test.js index a13530cf5..8a1bbabbc 100644 --- a/tests/records.test.js +++ b/tests/records.test.js @@ -275,13 +275,3 @@ t("All files should have valid record types", (t) => { t.pass(); }); - -t("All files should not have duplicate record keys", (t) => { - files.forEach((file) => { - const data = getDomainData(file); - const recordKeys = Object.keys(data.record); - const uniqueRecordKeys = new Set(recordKeys); - - t.is(recordKeys.length, uniqueRecordKeys.size, `${file}: Duplicate record keys found`); - }); -}); From c0b1e9daa8d1ca1d6475c0332ed392f179176c9f Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 17:35:18 +0800 Subject: [PATCH 73/80] Update mu.json --- domains/mu.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/domains/mu.json b/domains/mu.json index 6edd3c514..1e8929625 100644 --- a/domains/mu.json +++ b/domains/mu.json @@ -4,6 +4,6 @@ "email": "mohammadusman666@gmail.com" }, "record": { - "CNAME": "1d0b4a10.portfolio-1cw.pages.dev" + "CNAME": "portfolio-1cw.pages.dev" } } From d653945689ec18c388e783d690a335809306d1ef Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 17:35:49 +0800 Subject: [PATCH 74/80] Update jumanji.json --- domains/jumanji.json | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/domains/jumanji.json b/domains/jumanji.json index 5fa79d9c1..99f81d324 100644 --- a/domains/jumanji.json +++ b/domains/jumanji.json @@ -4,9 +4,8 @@ "email": "madhuchutiya.unhinge650@silomails.com" }, "record": { - "A": ["172.66.47.44", "172.66.44.212"], + "A": ["76.76.21.21"], "MX": ["mx1.improvmx.com", "mx2.improvmx.com"], - "TXT": "v=spf1 include:spf.improvmx.com ~all", - "A": ["76.76.21.21"] + "TXT": "v=spf1 include:spf.improvmx.com ~all" } } From b948f175c9f2d9bb833639adfcc931f9b91bd6c5 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 17:37:58 +0800 Subject: [PATCH 75/80] Create wh.json --- domains/wh.json | 12 ++++++++++++ 1 file changed, 12 insertions(+) create mode 100644 domains/wh.json diff --git a/domains/wh.json b/domains/wh.json new file mode 100644 index 000000000..55dcef36b --- /dev/null +++ b/domains/wh.json @@ -0,0 +1,12 @@ +{ + "owner": { + "username": "wdhdev", + "email": "william@is-a.dev" + }, + "record": { + "URL": "https://william.is-a.dev" + }, + "redirect_config": { + "redirect_paths": true + } +} From c01bea88f463d031fac8dfac2519aec90aae2afb Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 17:39:11 +0800 Subject: [PATCH 76/80] Create bypassed-usernames.json --- util/bypassed-usernames.json | 4 ++++ 1 file changed, 4 insertions(+) create mode 100644 util/bypassed-usernames.json diff --git a/util/bypassed-usernames.json b/util/bypassed-usernames.json new file mode 100644 index 000000000..ed9a583ce --- /dev/null +++ b/util/bypassed-usernames.json @@ -0,0 +1,4 @@ +[ + "is-a-dev", + "wdhdev" +] From b159edb6c361dca4c109cd7a458a588c2fd8ffe2 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 17:59:09 +0800 Subject: [PATCH 77/80] add special tests + remove n.is-a.dev as dupe single letter --- domains/_vercel.n.json | 9 -------- domains/n.json | 9 -------- tests/domains.test.js | 2 +- tests/special.test.js | 49 ++++++++++++++++++++++++++++++++++++++++++ 4 files changed, 50 insertions(+), 19 deletions(-) delete mode 100644 domains/_vercel.n.json delete mode 100644 domains/n.json create mode 100644 tests/special.test.js diff --git a/domains/_vercel.n.json b/domains/_vercel.n.json deleted file mode 100644 index e93beb20b..000000000 --- a/domains/_vercel.n.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "owner": { - "username": "syedtahseen", - "email": "itxtahseen@gmail.com" - }, - "record": { - "TXT": ["vc-domain-verify=n.is-a.dev,8435c76be2d4e8aaa229"] - } -} diff --git a/domains/n.json b/domains/n.json deleted file mode 100644 index d0ef77563..000000000 --- a/domains/n.json +++ /dev/null @@ -1,9 +0,0 @@ -{ - "owner": { - "username": "syedtahseen", - "email": "itxtahseen@gmail.com" - }, - "record": { - "CNAME": "xproject-xi.vercel.app" - } -} diff --git a/tests/domains.test.js b/tests/domains.test.js index ce2c3817d..46a4339fb 100644 --- a/tests/domains.test.js +++ b/tests/domains.test.js @@ -3,7 +3,7 @@ const fs = require("fs-extra"); const path = require("path"); const domainsPath = path.resolve("domains"); -const files = fs.readdirSync(domainsPath); +const files = fs.readdirSync(domainsPath).filter((file) => file.endsWith(".json")); const domainCache = {}; diff --git a/tests/special.test.js b/tests/special.test.js new file mode 100644 index 000000000..3ebe59a47 --- /dev/null +++ b/tests/special.test.js @@ -0,0 +1,49 @@ +const t = require("ava"); +const fs = require("fs-extra"); +const path = require("path"); + +const domainsPath = path.resolve("domains"); +const files = fs.readdirSync(domainsPath).filter((file) => file.endsWith(".json")); + +const bypassedUsernames = require("../util/bypassed-usernames.json").map((username) => username.toLowerCase()); + +function getDomainData(subdomain) { + try { + const data = fs.readJsonSync(path.join(domainsPath, `${subdomain}.json`)); + return data; + } catch (error) { + throw new Error(`Failed to read JSON for ${subdomain}: ${error.message}`); + } +} + +t("Users are limited to one single character subdomain", (t) => { + const results = []; + + files.forEach((file) => { + const subdomain = file.replace(/\.json$/, ""); + const data = getDomainData(subdomain); + + if (subdomain.length === 1 && !bypassedUsernames.includes(data.owner.username.toLowerCase())) { + results.push({ + subdomain, + owner: data.owner.username.toLowerCase(), + }) + } + }); + + const duplicates = results.filter((result) => results.filter((r) => r.owner === result.owner).length > 1); + + // Combine duplicates into multiple strings, only one per user, with list of their domains + const output = duplicates.reduce((acc, curr) => { + if (!acc[curr.owner]) { + acc[curr.owner] = []; + } + + acc[curr.owner].push(`${curr.subdomain}.is-a.dev`); + return acc; + }, {}); + + t.is(duplicates.length, 0, Object.keys(output).map((owner) => `${owner} - ${output[owner].join(", ")}`).join("\n")); + + t.pass(); +}) From 358c3a8b235104c1c16b1b4972b29ca2824e7965 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 18:00:00 +0800 Subject: [PATCH 78/80] refactor special tests to remove redundant comments --- tests/special.test.js | 2 -- 1 file changed, 2 deletions(-) diff --git a/tests/special.test.js b/tests/special.test.js index 3ebe59a47..b0cfa99a4 100644 --- a/tests/special.test.js +++ b/tests/special.test.js @@ -32,8 +32,6 @@ t("Users are limited to one single character subdomain", (t) => { }); const duplicates = results.filter((result) => results.filter((r) => r.owner === result.owner).length > 1); - - // Combine duplicates into multiple strings, only one per user, with list of their domains const output = duplicates.reduce((acc, curr) => { if (!acc[curr.owner]) { acc[curr.owner] = []; From 83b803ed0c70a73257603686b7fc4bfa13a59f63 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 18:00:15 +0800 Subject: [PATCH 79/80] refactor special test for improved readability and formatting --- tests/special.test.js | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/tests/special.test.js b/tests/special.test.js index b0cfa99a4..9861a0519 100644 --- a/tests/special.test.js +++ b/tests/special.test.js @@ -26,8 +26,8 @@ t("Users are limited to one single character subdomain", (t) => { if (subdomain.length === 1 && !bypassedUsernames.includes(data.owner.username.toLowerCase())) { results.push({ subdomain, - owner: data.owner.username.toLowerCase(), - }) + owner: data.owner.username.toLowerCase() + }); } }); @@ -41,7 +41,13 @@ t("Users are limited to one single character subdomain", (t) => { return acc; }, {}); - t.is(duplicates.length, 0, Object.keys(output).map((owner) => `${owner} - ${output[owner].join(", ")}`).join("\n")); + t.is( + duplicates.length, + 0, + Object.keys(output) + .map((owner) => `${owner} - ${output[owner].join(", ")}`) + .join("\n") + ); t.pass(); -}) +}); From 74323a67856b81ef4eeb62c6dea5f621ce5ff3d6 Mon Sep 17 00:00:00 2001 From: William Harrison <87287585+wdhdev@users.noreply.github.com> Date: Mon, 13 Jan 2025 18:02:35 +0800 Subject: [PATCH 80/80] shorten util JSON file names --- tests/json.test.js | 6 +- tests/special.test.js | 2 +- ...{bypassed-usernames.json => bypassed.json} | 0 util/{excepted-domains.json => excepted.json} | 0 util/{reserved-domains.json => reserved.json} | 240 +++++++++--------- 5 files changed, 124 insertions(+), 124 deletions(-) rename util/{bypassed-usernames.json => bypassed.json} (100%) rename util/{excepted-domains.json => excepted.json} (100%) rename util/{reserved-domains.json => reserved.json} (93%) diff --git a/tests/json.test.js b/tests/json.test.js index 16dd360a2..39d293f81 100644 --- a/tests/json.test.js +++ b/tests/json.test.js @@ -30,8 +30,8 @@ const optionalRedirectConfigFields = { const emailRegex = /^[a-zA-Z0-9._%+-]+@[a-zA-Z0-9.-]+\.[a-zA-Z]{2,}$/; const hostnameRegex = /^(?=.{1,253}$)(?:(?:[_a-zA-Z0-9](?:[a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?)\.)+[a-zA-Z]{2,63}$/; -const exceptedDomains = require("../util/excepted-domains.json"); -const reservedDomains = require("../util/reserved-domains.json"); +const exceptedDomains = require("../util/excepted.json"); +const reservedDomains = require("../util/reserved.json"); const domainsPath = path.resolve("domains"); const files = fs.readdirSync(domainsPath); @@ -52,7 +52,7 @@ function expandReservedDomains(reserved) { } expandedList.splice(expandedList.indexOf(item), 1); } else { - throw new Error(`[util/reserved-domains.json] Invalid range [${start}-${end}] in "${item}"`); + throw new Error(`[util/reserved.json] Invalid range [${start}-${end}] in "${item}"`); } } }); diff --git a/tests/special.test.js b/tests/special.test.js index 9861a0519..bd18e3e00 100644 --- a/tests/special.test.js +++ b/tests/special.test.js @@ -5,7 +5,7 @@ const path = require("path"); const domainsPath = path.resolve("domains"); const files = fs.readdirSync(domainsPath).filter((file) => file.endsWith(".json")); -const bypassedUsernames = require("../util/bypassed-usernames.json").map((username) => username.toLowerCase()); +const bypassedUsernames = require("../util/bypassed.json").map((username) => username.toLowerCase()); function getDomainData(subdomain) { try { diff --git a/util/bypassed-usernames.json b/util/bypassed.json similarity index 100% rename from util/bypassed-usernames.json rename to util/bypassed.json diff --git a/util/excepted-domains.json b/util/excepted.json similarity index 100% rename from util/excepted-domains.json rename to util/excepted.json diff --git a/util/reserved-domains.json b/util/reserved.json similarity index 93% rename from util/reserved-domains.json rename to util/reserved.json index 16b3293c7..eccc9738c 100644 --- a/util/reserved-domains.json +++ b/util/reserved.json @@ -1,120 +1,120 @@ -[ - "account", - "accounts", - "admin", - "administrator", - "alert", - "alerts", - "api", - "auth", - "authentication", - "authorisation", - "authorise", - "authorization", - "authorize", - "aux", - "billing", - "blog", - "calendar", - "cart", - "catalog", - "checkout", - "co", - "com", - "com[1-9]", - "con", - "confirm", - "confirmation", - "dashboard", - "default", - "dns", - "doc", - "documentation", - "email", - "error", - "errors", - "event", - "events", - "example", - "feedback", - "finance", - "forgot", - "forgot-password", - "gtld", - "guest", - "help", - "helpdesk", - "hostmaster", - "info", - "infos", - "login", - "logout", - "lpt[1-9]", - "m", - "mail", - "maintainer", - "maintainers", - "marketing", - "media", - "mobile", - "net", - "news", - "noc", - "notification", - "notifications", - "notify", - "ns", - "ns[1-99]", - "nul", - "oauth", - "official", - "operations", - "ops", - "org", - "organisation", - "pay", - "payment", - "payments", - "portal", - "postmaster", - "recovery", - "redirect", - "registrar", - "registry", - "reset", - "reset-password", - "root", - "sales", - "schedule", - "secure", - "security", - "service", - "services", - "session", - "sessions", - "shop", - "signin", - "signout", - "signup", - "staff", - "store", - "superuser", - "support", - "sys", - "system", - "teams", - "test", - "test[1-9999]", - "tld", - "token", - "tokens", - "url", - "url[1-9999]", - "user", - "users", - "webmaster", - "whois", - "www[1-99]", - "wwww", - "your-domain-name" -] +[ + "account", + "accounts", + "admin", + "administrator", + "alert", + "alerts", + "api", + "auth", + "authentication", + "authorisation", + "authorise", + "authorization", + "authorize", + "aux", + "billing", + "blog", + "calendar", + "cart", + "catalog", + "checkout", + "co", + "com", + "com[1-9]", + "con", + "confirm", + "confirmation", + "dashboard", + "default", + "dns", + "doc", + "documentation", + "email", + "error", + "errors", + "event", + "events", + "example", + "feedback", + "finance", + "forgot", + "forgot-password", + "gtld", + "guest", + "help", + "helpdesk", + "hostmaster", + "info", + "infos", + "login", + "logout", + "lpt[1-9]", + "m", + "mail", + "maintainer", + "maintainers", + "marketing", + "media", + "mobile", + "net", + "news", + "noc", + "notification", + "notifications", + "notify", + "ns", + "ns[1-99]", + "nul", + "oauth", + "official", + "operations", + "ops", + "org", + "organisation", + "pay", + "payment", + "payments", + "portal", + "postmaster", + "recovery", + "redirect", + "registrar", + "registry", + "reset", + "reset-password", + "root", + "sales", + "schedule", + "secure", + "security", + "service", + "services", + "session", + "sessions", + "shop", + "signin", + "signout", + "signup", + "staff", + "store", + "superuser", + "support", + "sys", + "system", + "teams", + "test", + "test[1-9999]", + "tld", + "token", + "tokens", + "url", + "url[1-9999]", + "user", + "users", + "webmaster", + "whois", + "www[1-99]", + "wwww", + "your-domain-name" +]