Compare commits

...

272 Commits

Author SHA1 Message Date
Alicia Sykes
4b4bf20a6f Bump version from 2.0.1 to 2.0.2 2025-11-14 21:54:24 +00:00
Alicia Sykes
9407f5c4b0 Merge pull request #252 from jayrizon/patch-1
adds ports to check environment variable.
2025-08-03 14:08:31 +01:00
jayrizon
8715274c9a adds ports to check environment variable.
Checks if the env PORTS_TO_CHECK is set, if so the string is split via "," to get an array of ports to check.
If the env is not set, return the default commonly used ports.
2025-08-01 08:27:15 +02:00
Alicia Sykes
6ef6720ec0 Merge pull request #249 from tnga/fixes
fix: Fix navigation links and add smooth scrolling to hash fragments
2025-06-28 22:46:21 +01:00
tnga
c0c146b2b9 fix: handle undefined robots data and improve object destructuring in RobotsTxt component 2025-06-16 07:20:26 +01:00
tnga
64510f7e7e fix: add toString() to prevent title attribute TypeError on non-string values 2025-06-16 07:15:01 +01:00
tnga
4603828b92 fix: change web-check.zyz link to expected web-check.xyz 2025-06-12 19:54:33 +01:00
tnga
cdf7875ddb fix: Fix navigation links and add smooth scrolling to hash fragments
- Update Link components in Home.tsx to use correct /check prefix for routing
- Add useEffect hook in About.tsx to handle smooth scrolling to hash fragments
- Add delay to ensure page renders before scrolling to target element
2025-06-12 14:09:52 +01:00
Alicia Sykes
50a11a5f50 Merge pull request #243 from Lissy93/sec/fix-com-inj-vul
security: Replace exec with execFile
2025-04-12 12:13:01 +01:00
Alicia Sykes
145711bdc7 ref: Bump version to 2.0.1 2025-04-12 12:12:51 +01:00
Alicia Sykes
0e4958aa10 security: Replace exec with execFile 2025-04-12 12:11:11 +01:00
Alicia Sykes
99653868c7 ref: Update data-domain 2025-04-03 13:05:33 +01:00
Alicia Sykes
20d08290af Merge pull request #228 from CrazyWolf13/patch-1
Really fix the screenshot api endpoint
2025-03-29 10:51:22 +00:00
Alicia Sykes
90883843e6 Merge pull request #237 from Lissy93/contributors-readme-action-8zk_vySnji
docs(contributor): contributors readme action update
2025-03-29 10:48:40 +00:00
liss-bot
eb63741e04 docs: Updates contributors list 2025-03-23 02:18:05 +00:00
Tobias
bbf519e110 fix screenshot.js 2025-02-26 13:55:48 +01:00
Alicia Sykes
f233de9bca Merge pull request #205 from Lissy93/sad/disable-everything-temporarily
feat: Temporarily disable, because I am poor.
2024-12-17 20:16:57 +00:00
Alicia Sykes
da0204c156 feat: Temporarily disable, because I am poor. 2024-12-17 20:16:36 +00:00
Alicia Sykes
7ca22daa9a Merge pull request #162 from 34bits/patch-2
Update AdditionalResources.tsx
2024-08-17 15:26:13 +01:00
Alicia Sykes
7ca8412cc9 Merge pull request #170 from Lissy93/contributors-readme-action-YNmkpszRFZ
docs(contributor): contributors readme action update
2024-08-17 15:20:20 +01:00
liss-bot
bc6afa635c docs: Updates contributors list 2024-08-11 03:06:52 +01:00
Alicia Sykes
1627bed25c Merge pull request #163 from Lissy93/feat/hudson-rock
rf: Adds ref to hudson rock link
2024-07-23 16:39:25 +01:00
Alicia Sykes
00af9f35cd rf: Adds ref to hudson rock link 2024-07-23 16:38:52 +01:00
NGN
95469b971f Update AdditionalResources.tsx
I changed the URL in MDN HTTP Observatory from  link: 'https://observatory.mozilla.org/', to link: 'https://developer.mozilla.org/en-US/observatory', because

MDN HTTP Observatory is launched, and Mozilla Observatory is now deprecated.

Here is the article: https://developer.mozilla.org/en-US/blog/mdn-http-observatory-launch/
2024-07-23 08:29:48 +03:00
Alicia Sykes
c30bea943b Merge pull request #161 from Lissy93/feat/hudson-rock
Feat/hudson rock
2024-07-22 17:29:15 +01:00
Alicia Sykes
2bcf0bc670 rf: Update protocol for hudson rock 2024-07-22 17:28:46 +01:00
Alicia Sykes
15d32a5551 feat: Adds Hudson Rock 2024-07-22 17:27:36 +01:00
liss-bot
42ecdd9ef6 docs: Updates contributors list 2024-07-21 03:05:46 +01:00
liss-bot
89cdbedf11 docs: Updates contributors list 2024-07-07 03:05:43 +01:00
Alicia Sykes
27f719078a Merge pull request #154 from dimitri-kandassamy/fix-footer-github-link
fix: Fix 404 errors for github repository and license urls in the footer
2024-06-30 22:40:14 +01:00
Alicia Sykes
67cc4c5275 Merge pull request #156 from Its-Just-Nans/fix-cover
Social Tags: change cover img code
2024-06-30 22:40:01 +01:00
n4n5
db242fb980 change cover img 2024-06-30 19:21:39 +02:00
liss-bot
9512595e21 docs: Updates contributors list 2024-06-30 03:05:28 +01:00
Dimitri Kandassamy
7ee81a14e7 fix: Fix 404 errors for github repository and license urls in the footer 2024-06-24 21:24:31 +02:00
liss-bot
c63adc6678 docs: Updates contributors list 2024-06-23 03:04:37 +01:00
Alicia Sykes
21ab305c43 Merge pull request #150 from Lissy93/FIX/links-api-spec-and-sponsor
Fix/links api spec and sponsor
2024-06-22 20:41:56 +01:00
Alicia Sykes
2445381b8e bump: 2.0.0 2024-06-22 20:40:55 +01:00
Alicia Sykes
09efe9904e fix: Hyperlink to homepage not use React Link 2024-06-22 20:40:30 +01:00
Alicia Sykes
203a634f7c fix: Update clas for sponsor block 2024-06-22 20:40:04 +01:00
Alicia Sykes
2186fff4dc fix: Loading of API docs 2024-06-22 20:39:33 +01:00
Alicia Sykes
07b6ca3222 Merge pull request #139 from Lissy93/FEAT/astroify
FEAT - Astroify
2024-06-22 11:40:40 +01:00
Alicia Sykes
abab9f1940 fix: Revert esbuild as the node bundler for netlify 2024-06-22 11:36:14 +01:00
Alicia Sykes
99f1e2768f fix: Uses esbuild as the node bundler for netlify 2024-06-22 00:35:35 +01:00
Alicia Sykes
2ff8155a35 fix: Netlify include axios for function runtime 2024-06-21 23:28:52 +01:00
Alicia Sykes
c0f7ef1079 fix: Netlify include node_modules 2024-06-21 22:55:58 +01:00
Alicia Sykes
9bb8b3f46d dep: Temp downgrade of axios, for netlify 2024-06-21 22:48:59 +01:00
Alicia Sykes
ce9201594e fix: Remove the redirect from netlify config 2024-06-21 22:43:21 +01:00
Alicia Sykes
0ff76de682 dep: Adds Chromium 2024-06-21 22:08:30 +01:00
Alicia Sykes
cee06c987a feat: Specify API destination for netlify 2024-06-21 22:08:04 +01:00
Alicia Sykes
0a419045c0 feat: Styling for error logs 2024-06-21 22:07:48 +01:00
Alicia Sykes
ba8880cff7 feat: Add old-school export option for Netlify 2024-06-18 22:07:27 +01:00
Alicia Sykes
a6bc8d790e feat: Dynamically import SSR handler 2024-06-18 22:06:59 +01:00
Alicia Sykes
8c17303179 feat: Deploy target to lowercase 2024-06-18 22:06:34 +01:00
Alicia Sykes
e529a2e229 feat: Adds coming soon to account 2024-06-16 21:40:06 +01:00
Alicia Sykes
43fb27eade Merge branch 'master' of github.com:lissy93/web-check into FEAT/astroify 2024-06-16 21:18:41 +01:00
Alicia Sykes
aea93fedeb feat: styles, nav, home, and stuff 2024-06-16 21:04:56 +01:00
Alicia Sykes
7d4eab28b4 feat: improved err messaging for netlify 2024-06-16 21:04:36 +01:00
Alicia Sykes
316e0d97fd feat: Adds screenshots to homepage 2024-06-16 21:04:09 +01:00
Alicia Sykes
ad9ea9137b feat: Initial landing page for API docs 2024-06-16 21:03:49 +01:00
Alicia Sykes
2628655cdd assets: adds swagger and webauthn imgs 2024-06-16 21:03:28 +01:00
Alicia Sykes
7c0f750f6f Merge pull request #147 from HeroGamers/external-tools
Add more additional resources / external tools
2024-06-16 12:05:11 +01:00
Alicia Sykes
0716ff5265 Update resource links 2024-06-16 12:04:21 +01:00
Alicia Sykes
ff18904d6c feat: Updates nav, icon, colors, background and homepage 2024-06-15 22:46:13 +01:00
Alicia Sykes
0172de829c feat: Adds self-hosting docs page 2024-06-15 22:45:47 +01:00
Alicia Sykes
4fd5ff4315 assets: Adds image assets 2024-06-15 22:45:34 +01:00
Alicia Sykes
8feb67de38 styles: Updates theme of V1 check to match homepage 2024-06-15 22:44:58 +01:00
Alicia Sykes
d3cbc50fb7 docs: Updates domains in Swagger docs 2024-06-15 22:43:20 +01:00
Alicia Sykes
82be27c263 docs: Updates samples 2024-06-15 20:04:19 +01:00
Alicia Sykes
f0ec686f23 revert: Docker workflow 2024-06-09 16:47:51 +01:00
Alicia Sykes
6773e61a89 chore: Update default branch in Docker workflow 2024-06-09 16:45:01 +01:00
Alicia Sykes
73d1c248ca build: Create DockerHub tag, when new GitHub tag is created 2024-06-09 16:44:19 +01:00
liss-bot
80bcd1d619 docs: Updates contributors list 2024-06-09 03:04:56 +01:00
Alicia Sykes
6207157da7 Builds footer, and updates new homepage 2024-06-08 15:23:25 +01:00
Alicia Sykes
8013a0a445 feat: Adds new favicon 2024-06-08 15:23:09 +01:00
Alicia Sykes
2f1bab569d feat: Adds new feature components for new homepage 2024-06-08 15:22:45 +01:00
Alicia Sykes
e2d83b627a ref: Improves few of the older React components 2024-06-08 15:21:10 +01:00
Alicia Sykes
03e980eafc dep: Adds Font Awesome, and builds an Icon component 2024-06-08 15:20:39 +01:00
Alicia Sykes
f4196c79d4 chore: Redirect /about to /check/about 2024-06-08 15:20:14 +01:00
Marcus Sand
6a04cdef46 Fixes some URL site errors when visiting 2024-06-07 14:06:10 +02:00
Marcus Sand
2fe645fa37 Add more additional resources 2024-06-07 13:36:55 +02:00
Alicia Sykes
8f552147ed Updates base layout 2024-06-03 23:39:36 +01:00
Alicia Sykes
a12e7c5c22 Astro pages build up 2024-06-03 23:39:22 +01:00
Alicia Sykes
f9e6878cea Global and reusable stylings 2024-06-03 23:39:10 +01:00
Alicia Sykes
50cc152491 Adds nav scafold component 2024-06-03 23:38:52 +01:00
Alicia Sykes
68f95d503c Adds interactive animated components for homepage 2024-06-03 23:38:35 +01:00
Alicia Sykes
fa6ef6f929 Removes old fonts location 2024-06-03 23:38:12 +01:00
Alicia Sykes
c46ec14cb1 Updates to new icon 2024-06-03 23:37:48 +01:00
Alicia Sykes
10cbc2a738 Adds Hubot Sans fonts 2024-06-03 23:37:38 +01:00
liss-bot
ed1d33d81a docs: Updates contributors list 2024-06-02 03:03:52 +01:00
Alicia Sykes
5b71ba96c5 Merge pull request #146 from n0a/patch-3
Sort openPorts and failedPorts before returning
2024-05-28 17:35:31 +01:00
Denis Simonov
b55a1cc1b3 Sort openPorts and failedPorts before returning 2024-05-28 02:59:30 +03:00
Alicia Sykes
ca3f8a4235 Adds Svelte, Framer and starts work on homepage 2024-05-26 22:15:29 +01:00
Alicia Sykes
fd49c488b1 Merge pull request #145 from vitalykarasik/CICD/gha-updates
CICD: bumped GHA versions
2024-05-26 18:03:33 +01:00
liss-bot
3d6539b673 docs: Updates contributors list 2024-05-26 03:03:26 +01:00
vitalykarasik
17696d80cc CICD: bumped GHA versions 2024-05-24 06:21:47 +03:00
Alicia Sykes
322ef5e0ea Removes old swagger location 2024-05-20 22:44:42 +01:00
Alicia Sykes
d826e97c4d Adds aliases for styles and assets 2024-05-20 22:44:29 +01:00
Alicia Sykes
b090dcadb1 Astro app 2024-05-20 22:44:09 +01:00
Alicia Sykes
34ca09fc20 Fix catch-all when GUI is disabled 2024-05-20 22:43:53 +01:00
Alicia Sykes
97fd19492e Updates links to use Link instead of anchor 2024-05-20 22:43:12 +01:00
Alicia Sykes
a2f5bcb263 Adds Swagger docs and assets 2024-05-20 22:42:43 +01:00
Alicia Sykes
5de879be9f All-in-one dev command 2024-05-20 22:40:09 +01:00
Alicia Sykes
8a0ec5a7a7 Use Link tag, instead of anchor tag 2024-05-20 22:34:50 +01:00
Alicia Sykes
d2f58f40b5 Adds API docs route 2024-05-19 11:55:00 +01:00
Alicia Sykes
891982321c Updates Vercel and adds SASS 2024-05-19 11:50:04 +01:00
liss-bot
bf41ce0466 docs: Updates contributors list 2024-05-19 03:02:59 +01:00
Alicia Sykes
cb8db0b1f5 JSON parsing in API endpoints 2024-05-18 15:01:52 +01:00
Alicia Sykes
cc510bd281 Adds Swagger docs for API 2024-05-18 15:01:31 +01:00
Alicia Sykes
c30e3a015c Merge pull request #143 from n0a/patch-2
Update firewall.js, add ddos-guard WAF
2024-05-18 14:37:40 +01:00
Denis Simonov
7125eeff5d Update firewall.js, add ddos-guard WAF
Add ddos-guard WAF
https://ddos-guard.net/en
2024-05-17 00:00:56 +03:00
Alicia Sykes
a59c33571a Merge pull request #137 from n0a/patch-1
Update firewall.js, add QRATOR WAF
2024-05-15 22:34:02 +01:00
liss-bot
26d51708eb docs: Updates contributors list 2024-05-12 03:02:39 +01:00
Alicia Sykes
37f711d95b Builds base layout, and head tags 2024-05-11 23:14:20 +01:00
Alicia Sykes
9f82e19957 Sets aliases for astro imports 2024-05-11 23:14:07 +01:00
Alicia Sykes
a5a277c20a Adds JS fallback for redirection 2024-05-11 23:13:50 +01:00
Alicia Sykes
91404d1c44 Adds a fly.toml for deploying to fly.io 2024-05-11 23:13:25 +01:00
Alicia Sykes
7557cb9b3a Update condidional for skipping wc homepage for self-hosted users 2024-05-11 23:11:53 +01:00
Alicia Sykes
8a7e431af5 Fix link to about docs 2024-05-08 21:38:58 +01:00
Alicia Sykes
70724be65a Fix correct param name 2024-05-08 21:37:44 +01:00
Alicia Sykes
7e27143a90 Rename v1 to web-check-live 2024-05-08 21:23:03 +01:00
Alicia Sykes
e5738d1f5b Update start command, and remove --prod flag from dev install script in Dockerfile 2024-05-08 21:19:20 +01:00
Alicia Sykes
69abef34c5 Adds PM2 for no-crash server 2024-05-08 21:18:56 +01:00
Alicia Sykes
32138847dd Redirect if URL param present on home 2024-05-08 21:18:33 +01:00
Alicia Sykes
22cf1244c7 Update PLATFORM env var 2024-05-07 12:47:37 +01:00
Alicia Sykes
1478fa738d Update publish directory for Netlify 2024-05-07 12:38:56 +01:00
Alicia Sykes
de75d1c71f Ignore built files 2024-05-07 12:03:28 +01:00
Alicia Sykes
390b8b9df7 Improved UX for self-hosted users 2024-05-06 23:30:09 +01:00
Alicia Sykes
42d6e0394f Send user direct to check page, if self-hosted 2024-05-06 23:29:30 +01:00
Alicia Sykes
d9135883de Server working with Astro and all API endpoints 2024-05-06 21:51:46 +01:00
Alicia Sykes
c9e57400fd Convert all API endpoints into ESM modules 2024-05-06 21:51:32 +01:00
Alicia Sykes
e255c358cb Updates configration for Vercel and Typescript 2024-05-05 17:45:23 +01:00
Alicia Sykes
e6eb91a33a Update path to GUI 2024-05-05 17:45:00 +01:00
Alicia Sykes
e3214660d0 Configuration for Vite 2024-05-05 17:44:14 +01:00
Alicia Sykes
bb6845d044 Move assets into /public 2024-05-05 17:44:03 +01:00
Alicia Sykes
fd0b1e7d7f Writes configuration file for multi-adapter Astro site 2024-05-05 17:41:47 +01:00
Alicia Sykes
9a59d12a00 Dependencies for Astro 2024-05-05 17:41:26 +01:00
Alicia Sykes
20ef316081 Specify platform 2024-05-05 17:41:13 +01:00
Alicia Sykes
45bf452f17 Migrate to Astro base 2024-05-05 17:39:47 +01:00
liss-bot
7234e11e87 docs: Updates contributors list 2024-05-05 03:01:51 +01:00
Denis Simonov
9609cd3701 Update firewall.js, add QRATOR WAF
Add new firewall: https://qrator.net/
2024-05-03 18:23:04 +03:00
Alicia Sykes
031b0e37bb Merge pull request #133 from GreyXor/master
style: consistency between additional resources descriptions
2024-04-30 20:20:37 +01:00
liss-bot
f1fff427f8 docs: Updates contributors list 2024-04-28 03:02:20 +01:00
Alicia Sykes
584c145b15 Merge pull request #135 from bolens/external-links
External links open in new tab
2024-04-25 13:41:33 +01:00
liss-bot
d9e7bb57f3 docs: Updates contributors list 2024-04-21 03:01:19 +01:00
Alicia Sykes
c9631e6848 Merge pull request #121 from KostLinux/FIX/json-doctype
Fix bug with JSON Doctype
2024-04-21 00:26:37 +01:00
bolens
06965b0e82 Update additional page links 2024-04-17 09:27:01 -06:00
bolens
be741a1087 Fix: External links now open in a new tab 2024-04-17 09:08:42 -06:00
GreyXor
52b3960ce3 style: consistency between additional resources descriptions 2024-04-16 10:58:53 +02:00
liss-bot
d7bcbcb5b4 docs: Updates contributors list 2024-04-14 03:21:40 +01:00
Alicia Sykes
4d54cdccac Merge pull request #131 from Myzel394/patch-1
Add darkreader lock meta tag
2024-04-12 21:27:05 +01:00
Alicia Sykes
da75fb25d7 Merge pull request #122 from GreyXor/master
feat: add external mozilla observatory tool
2024-04-12 21:26:33 +01:00
Myzel394
42023039c1 fix: Add darkreader lock meta tag 2024-04-08 10:21:52 +02:00
liss-bot
affec03d6c docs: Updates contributors list 2024-04-07 03:00:47 +01:00
liss-bot
ecaffda777 docs: Updates contributors list 2024-03-31 03:00:42 +01:00
GreyXor
0d484e3ffa feat: add external mozilla observatory tool 2024-03-27 12:50:13 +01:00
KostLinux
38d6b5b97e Fix bug with JSON Doctype #120 2024-03-26 15:35:24 +02:00
liss-bot
728a8237aa docs: Updates contributors list 2024-03-24 02:00:56 +00:00
Alicia Sykes
24ca677021 Fix timeout parsing, and show timeout on Vercel 2024-03-22 06:40:36 +00:00
Alicia Sykes
ed53c29a55 Reduce Vercel function timeout to 10 seconds 2024-03-21 12:10:52 +00:00
Alicia Sykes
c4e29fda0f Merge pull request #118 from Lissy93/FEAT/override-timeout
FEAT: Override timeout
2024-03-20 21:49:51 +00:00
Alicia Sykes
ff65696729 Bump to V 1.1.2 2024-03-20 21:43:04 +00:00
Alicia Sykes
2304aaf17c Adds unique keys to itteratbles, remove react warn 2024-03-20 21:20:41 +00:00
Alicia Sykes
d43a05a0ed Show timeout seperatley 2024-03-20 21:20:23 +00:00
Alicia Sykes
ada1dccc5b Update timeout message for sitemap 2024-03-20 21:19:58 +00:00
Alicia Sykes
7a8e694abc Logging for timeout info, and adds key to map 2024-03-20 20:45:13 +00:00
Alicia Sykes
c764bbfcd4 If response is a timeout, set type to timeout 2024-03-20 20:44:37 +00:00
Alicia Sykes
523419df11 Adds timeout functionality 2024-03-20 20:43:51 +00:00
liss-bot
62a213d74d docs: Updates contributors list 2024-03-17 01:58:43 +00:00
Alicia Sykes
7fc8ba4c15 Merge pull request #111 from Lissy93/FEAT/optional-rate-limiting
Feat/optional rate limiting
2024-03-15 11:44:04 +00:00
Alicia Sykes
f63418039a Adds docs for rate limit env var 2024-03-14 07:59:44 +00:00
Alicia Sykes
3f80d58085 Adds optional rate-limiting functionality 2024-03-14 07:59:19 +00:00
Alicia Sykes
ee74c5866a Slight improvments to error messaging for sitemap and quality report 2024-03-14 07:59:03 +00:00
Alicia Sykes
41cd379805 Bumps to V 1.1.0 2024-03-14 07:58:35 +00:00
Alicia Sykes
0c5dbd66a3 Adds express-rate-limit 2024-03-14 07:57:59 +00:00
Alicia Sykes
18f72788aa Updates Terminal Trove logo in README.md 2024-03-12 19:18:13 +00:00
Alicia Sykes
cd3ab4a264 Merge pull request #109 from Lissy93/DOCS/adds-terminal-trove-sponsorship
DOCS: adds terminal trove sponsorship
2024-03-12 18:50:02 +00:00
Alicia Sykes
ab66def695 Adds link to terminal trove in homepage 2024-03-12 18:39:29 +00:00
Alicia Sykes
68778d3824 Updates Terminal Trove in about page 2024-03-12 16:23:22 +00:00
Alicia Sykes
43851ae0fb Adds Terminal Trove to about page 2024-03-12 16:17:01 +00:00
Alicia Sykes
91a6e6221c docs: Adds Terminal Trove 2024-03-12 15:53:12 +00:00
liss-bot
7f2da1905c docs: Updates contributors list 2024-03-10 02:00:35 +00:00
Alicia Sykes
7583843e80 Merge pull request #106 from Gertje823/master
Added Mimecast as mail provider
2024-03-09 22:22:24 +00:00
Gertje823
e77075764e Added Mimecast as mail provider 2024-03-09 13:49:38 +01:00
Alicia Sykes
195577fe0c Merge pull request #91 from ChrisCarini/patch-1
Adding linux/arm64 platform to docker build-push-action
2024-03-06 00:11:51 +00:00
Alicia Sykes
29398665b0 Merge pull request #100 from epreston/chore-caniuse-lite
chore(deps): update browserlist db
2024-03-03 16:16:45 +00:00
liss-bot
1780b2323d docs: Updates contributors list 2024-03-03 01:59:09 +00:00
Alicia Sykes
1e6802afbf Merge pull request #97 from 0xflotus/patch-1
chore: fixed small error
2024-03-02 11:27:03 +00:00
Ed Preston
2cd68c5b98 chore(deps): update browserlist db
Remove "Browserslist: caniuse-lite is outdated." warning by updating browserlist db.
2024-03-02 14:26:44 +11:00
0xflotus
ac3a70ae0d chore: fixed small error 2024-03-01 17:08:23 +01:00
ChrisCarini
761f9dab81 Install python + increase yarn install timeout
(cherry picked from commit 4e70e1621e7c44dc5e3c51edd0b5f3577b846eed)
2024-02-29 08:36:11 -08:00
ChrisCarini
64fbcb3f7d Merge remote-tracking branch 'origin/FIX/chromium-docker' into patch-1
# Conflicts:
#	Dockerfile
2024-02-29 08:35:56 -08:00
ChrisCarini
2fb7dc9a2b Add linux/arm64/v8 platform 2024-02-29 08:34:57 -08:00
Alicia Sykes
0a1023ce19 Merge pull request #72 from PhiRequiem/patch-1
Update SslCert.tsx
2024-02-28 20:06:25 +00:00
Alicia Sykes
f4dd5d7a31 Remove commented out duplicate line 2024-02-28 20:06:07 +00:00
Alicia Sykes
aff5ea5f52 Merge pull request #74 from brianteeman/typos
Typos
2024-02-28 16:56:05 +00:00
Alicia Sykes
4c4813620d Merge pull request #85 from eltociear/patch-1
Update README.md
2024-02-28 16:55:53 +00:00
Ikko Eltociear Ashimine
b9bc24156b Update README.md
minor fix
2024-02-29 00:27:53 +09:00
Alicia Sykes
13d0e4ac9f Fix typo in about page (#81) 2024-02-26 17:59:42 +00:00
Alicia Sykes
01fb32e43c Merge pull request #78 from robinson/master
multi stage build docker, to minimize the docker image
2024-02-26 17:46:11 +00:00
liss-bot
ec30ef7b8b docs: Updates contributors list 2024-02-25 01:59:26 +00:00
lth
af70930be2 multi stage build docker, to minimize the docker image file 2024-02-19 17:16:29 +01:00
liss-bot
55299f001f docs: Updates contributors list 2024-02-18 01:59:13 +00:00
liss-bot
7e51239c8d docs: Updates contributors list 2024-02-11 01:59:38 +00:00
liss-bot
cb6a008680 docs: Updates contributors list 2024-02-04 02:00:45 +00:00
Brian Teeman
55f30f5537 Update docs.ts 2024-01-28 10:56:56 +00:00
Brian Teeman
cc3ca64f25 Update netlify.toml 2024-01-28 10:55:18 +00:00
liss-bot
8c0cf5f870 docs: Updates contributors list 2024-01-28 01:59:30 +00:00
liss-bot
2f46de124d docs: Updates contributors list 2024-01-21 02:04:01 +00:00
PhiRequiem
0db0b044b2 Update SslCert.tsx
esta línea está repetida
2024-01-18 17:51:22 -06:00
liss-bot
299925d22e docs: Updates contributors list 2024-01-14 02:03:54 +00:00
liss-bot
db9b69fac3 docs: Updates contributors list 2024-01-07 02:03:38 +00:00
liss-bot
be307e6876 docs: Updates contributors list 2023-12-31 02:02:28 +00:00
liss-bot
e44f8e73aa docs: Updates contributors list 2023-12-24 02:02:14 +00:00
liss-bot
9c4335f2af docs: Updates contributors list 2023-12-17 02:02:55 +00:00
liss-bot
44cbe47983 docs: Updates contributors list 2023-12-10 02:02:58 +00:00
liss-bot
5924d89f54 docs: Updates contributors list 2023-12-03 02:02:19 +00:00
liss-bot
b5ec08da8b docs: Updates contributors list 2023-11-26 02:02:21 +00:00
liss-bot
184b962731 docs: Updates contributors list 2023-11-19 02:03:01 +00:00
liss-bot
d6035b8e9c docs: Updates contributors list 2023-11-12 02:01:46 +00:00
liss-bot
2988486a65 docs: Updates contributors list 2023-11-05 02:01:26 +00:00
Alicia Sykes
5616b71564 Updates the readme 2023-10-27 21:23:23 +01:00
liss-bot
5348175b5e docs: Updates contributors list 2023-10-15 03:01:08 +01:00
liss-bot
f9b4edda01 docs: Updates contributors list 2023-10-08 03:00:49 +01:00
liss-bot
50590334be docs: Updates contributors list 2023-09-24 02:59:42 +01:00
liss-bot
33a35b94f5 docs: Updates contributors list 2023-09-17 02:59:36 +01:00
Alicia Sykes
a6711aeb63 Update Dockerfile (#43)
Updates the Dockerfile with changes suggested by @GWnbsp  in https://github.com/Lissy93/web-check/issues/43#issuecomment-1719212234

### Summary of Changes
1. **ARG Statements:** Introduced `ARG` statements for Node.js and Debian versions, making the Dockerfile more customizable.
2. **SHELL Command:** Changed the default shell to Bash with certain options enabled, improving robustness.
3. **Chromium Installation:** Updated Chromium installation to use Google's signing keys and repositories, aiming for more secure and up-to-date packages.
4. **Chromium Version:** Added a step to save Chromium's version into `/etc/chromium-version` for reference.
5. **Directory Creation:** Added a new directory /app/data in the container's filesystem.
6. **CMD Change:** Changed the CMD to start Node.js server (server.js) instead of using yarn serve.
7. **General Cleanup and Comments:** Code has been refactored for better readability and detailed comments have been added for clarity.
8. **Dependency Installation:** Kept yarn install and the removal of the Yarn cache, but the command is more streamlined.
9. **Other Minor Changes:**
  - Added flags like `-qq` and `--no-install-recommends` for quieter and optimized installation.
  - Enhanced cleanup with `rm -rf /var/lib/apt/lists/*.`
2023-09-14 20:59:09 +01:00
Alicia Sykes
f36ac56370 Merge pull request #53 from murrple-1/murrple-1-patch-1
Check the correct header for the `strictTransportPolicy` property - Fixes #52
2023-09-14 20:34:44 +01:00
Murray Christopherson
09e5b5d888 Check the correct header for the strictTransportPolicy property
See https://developer.mozilla.org/en-US/docs/Web/HTTP/Headers/Strict-Transport-Security
2023-09-13 19:29:58 -07:00
Alicia Sykes
ad57aaa7f8 Merge pull request #51 from t3chn0m4g3/master
Allow for screenshot within Docker
2023-09-12 17:37:12 +01:00
Marco Ochse
2bce29e3cb Allow for Screenshot within Docker
Chromium in Docker needs to be startet without sandbox or screenshot will fail.
2023-09-12 11:01:49 +02:00
Alicia Sykes
6b9aad81fd docs: Simplified the configuring docs 2023-09-11 22:05:03 +01:00
liss-bot
afc5b54207 docs: Updates contributors list 2023-09-10 02:58:58 +01:00
Alicia Sykes
71ce9a6623 Merge branch 'master' of github.com:lissy93/web-check 2023-09-09 20:30:48 +01:00
Alicia Sykes
d8bb822a4e Updated TLS components, to refresh when new data comes in 2023-09-09 20:30:09 +01:00
Alicia Sykes
5297b2ffe7 Fixes block-lists job (#50) 2023-09-09 20:29:19 +01:00
Alicia Sykes
79c88a5d9a Updates docs 2023-09-08 20:28:51 +01:00
Alicia Sykes
0e022f97a2 Adds status badges into readme 2023-09-03 22:51:36 +01:00
Alicia Sykes
0d4942738d Update public URL, from web-check.as93.net to web-check.xyz 2023-09-03 20:35:27 +01:00
Alicia Sykes
32d5962dc3 Merge pull request #48 from Lissy93/FEAT/vercel-support
[FEAT] Vercel support
2023-09-03 17:01:06 +01:00
Alicia Sykes
8a7b024e99 Return plain JSON, to be handled by middleware instead 2023-09-03 16:58:46 +01:00
Alicia Sykes
c169a3762d Updates .gitignore, to ignore build assets 2023-09-03 16:28:43 +01:00
Alicia Sykes
d26f5b26a7 Renders error page, if there was an error 2023-09-03 16:23:07 +01:00
Alicia Sykes
c2a937ac8e Adds placeholder and error pages 2023-09-03 16:22:33 +01:00
Alicia Sykes
59203acdfa Update the env check, to determine what handler format to use 2023-09-03 15:32:58 +01:00
Alicia Sykes
63db1dbd85 Removed the need for lambda handler, added status message to server, refactored 2023-09-03 15:30:11 +01:00
Alicia Sykes
e23347a936 Adds cors support to server 2023-09-03 14:11:15 +01:00
Alicia Sykes
d41af54513 Updates dev and deployment docs 2023-09-03 14:06:58 +01:00
Alicia Sykes
73c44e39de Adds Deploy to Vercel section 2023-09-03 12:56:45 +01:00
Alicia Sykes
7dd398a9c3 Merge branch 'master' of github.com:lissy93/web-check 2023-09-03 12:27:49 +01:00
Alicia Sykes
1a95a42853 Updates all API functions, to work on both Vercel & Netlify 2023-09-03 12:27:04 +01:00
Alicia Sykes
3695c82472 Updates middleware, with both AWS and Express support 2023-09-03 12:26:41 +01:00
liss-bot
6a4eb5aa8e docs: Updates contributors list 2023-09-03 02:58:42 +01:00
Alicia Sykes
1630f2a050 Temp remove env vars from param store 2023-09-02 16:51:24 +01:00
Alicia Sykes
b1f8c0144b Use env var for AWS_ACCOUNT_ID 2023-09-02 15:39:26 +01:00
Alicia Sykes
76cce7ef9a Read env vars from AWS secret manager 2023-09-02 15:21:36 +01:00
Alicia Sykes
393dafbf84 Updates .env template 2023-09-02 15:13:20 +01:00
Alicia Sykes
6bd353273a Merge pull request #47 from JinnaBalu/master
Updated Dockerfile for layer cache before COPY
2023-09-01 20:31:30 +01:00
JinnaBalu
8a60b77135 Getting latest before merge Merge branch 'master' of https://github.com/JinnaBalu/web-check 2023-09-01 16:13:20 +05:30
JinnaBalu
ab59afc150 Updated dockerfile for optimization 2023-09-01 16:12:53 +05:30
Alicia Sykes
b314168da1 Add caching for node_modules and rename environment deploy status 2023-08-31 20:46:01 +01:00
Alicia Sykes
33e1adb974 Update AWS workflow to update the deployment state for environments 2023-08-31 20:33:31 +01:00
Alicia Sykes
8688fd23f5 Use native AWS CLI to upload to S3 2023-08-30 20:07:28 +01:00
Alicia Sykes
cd2681fd84 Set src_dir in upload to S3 deploy action 2023-08-30 19:52:09 +01:00
Alicia Sykes
0cb9cedd8c Set dependency version 2023-08-30 19:48:59 +01:00
Alicia Sykes
20762dc3ad Tries switching S3 upload action provider 2023-08-30 19:42:21 +01:00
Alicia Sykes
359c6ca476 Ignore node_modules when uploading to S3 2023-08-30 18:58:02 +01:00
Alicia Sykes
f7573572e5 Remove ACL flag from S3 upload 2023-08-30 18:22:38 +01:00
Alicia Sykes
975c73fd2b Fix tag for invalidating cloudfront cache 2023-08-30 18:11:53 +01:00
Alicia Sykes
acf4f90aee Bump version used for invalidating cloudfront cache 2023-08-30 18:07:40 +01:00
Alicia Sykes
daf6850052 Updates AWS action, to also build + deploy frontend, to S3 + Cloudfront 2023-08-30 18:01:33 +01:00
Alicia Sykes
3aa385cf41 Use NPM for gloabl dep 2023-08-30 15:46:34 +01:00
Alicia Sykes
394b68fa29 Automate deployment to AWS lambda (cheaper than Netlify) 2023-08-30 15:40:48 +01:00
343 changed files with 13057 additions and 17605 deletions

31
.env
View File

@@ -2,11 +2,26 @@
# Be sure to uncomment any line you populate
# Everything is optional, but some features won't work without external API access
# GOOGLE_CLOUD_API_KEY=''
# SHODAN_API_KEY=''
# REACT_APP_SHODAN_API_KEY=''
# WHO_API_KEY=''
# REACT_APP_WHO_API_KEY=''
# SECURITY_TRAILS_API_KEY=''
# BUILT_WITH_API_KEY=''
# CI=false
# API Keys for external services (backend)
GOOGLE_CLOUD_API_KEY=''
TORRENT_IP_API_KEY=''
SECURITY_TRAILS_API_KEY=''
BUILT_WITH_API_KEY=''
URL_SCAN_API_KEY=''
TRANCO_USERNAME=''
TRANCO_API_KEY=''
CLOUDMERSIVE_API_KEY=''
# API Keys for external services (frontend)
REACT_APP_SHODAN_API_KEY=''
REACT_APP_WHO_API_KEY=''
# Configuration settings
# CHROME_PATH='/usr/bin/chromium' # The path the the Chromium executable
# PORT='3000' # Port to serve the API, when running server.js
# DISABLE_GUI='false' # Disable the GUI, and only serve the API
# API_TIMEOUT_LIMIT='10000' # The timeout limit for API requests, in milliseconds
# API_CORS_ORIGIN='*' # Enable CORS, by setting your allowed hostname(s) here
# API_ENABLE_RATE_LIMIT='true' # Enable rate limiting for the API
# REACT_APP_API_ENDPOINT='/api' # The endpoint for the API (can be local or remote)
# ENABLE_ANALYTICS='false' # Enable Plausible hit counter for the frontend

711
.github/README.md vendored
View File

@@ -9,6 +9,22 @@
</p>
---
<p align="center">
<sup>Kindly supported by:</sup><br>
<a href="https://terminaltrove.com/?utm_campaign=github&utm_medium=referral&utm_content=web-check&utm_source=wcgh">
<img src="https://i.ibb.co/8jrrcZ0/IMG-7210.jpg" width="300" alt="Terminal Trove">
<br>
<strong>The $HOME of all things in the terminal.</strong>
</a>
<br>
<a href="https://terminaltrove.com/newsletter?utm_campaign=github&utm_medium=referral&utm_content=web-check&utm_source=wcgh">
<sub>Find your next CLI / TUI tool and more at Terminal Trove,</sub>
<br>
<sup>Get updates on new tools on our newsletter.</sup>
</a>
</p>
---
#### Contents
@@ -19,11 +35,13 @@
- [Mirror](#mirror)
- [Features](#features)
- **[Usage](#usage)**
- [Developer Setup](#developing)
- [Deploying, Option#1: Netlify](#deploying---option-1-netlify)
- [Deploying, Option#2: Docker](#deploying---option-2-docker)
- [Deploying, Option#3: Source](#deploying---option-3-from-source)
- [Deployment](#deployment)
- [Option#1: Netlify](#deploying---option-1-netlify)
- [Option#2: Vercel](#deploying---option-2-vercel)
- [Option#3: Docker](#deploying---option-3-docker)
- [Option#4: Source](#deploying---option-4-from-source)
- [Configuration Options](#configuring)
- [Developer Setup](#developing)
- **[Community](#community)**
- [Contributing](#contributing)
- [Bugs](#reporting-bugs)
@@ -56,18 +74,27 @@ A hosted version can be accessed at: **[web-check.as93.net](https://web-check.as
### Mirror
The source for this repo is mirrored to CodeBerg, available at: **[codeberg.org/alicia/web-check](https://codeberg.org/alicia/web-check)**
### Motivation
Often when you're looking into a website, there's several things you always initially check.
### Status
Build & Deploys: [![Netlify Status](https://api.netlify.com/api/v1/badges/c43453c1-5333-4df7-889b-c1d2b52183c0/deploy-status)](https://app.netlify.com/sites/web-check/deploys)
[![Vercel Status](https://therealsujitk-vercel-badge.vercel.app/?app=web-check-ten)](https://vercel.com/as93/web-check/)
[![🐳 Build + Publish Docker Image](https://github.com/Lissy93/web-check/actions/workflows/docker.yml/badge.svg)](https://github.com/Lissy93/web-check/actions/workflows/docker.yml)
[![🚀 Deploy to AWS](https://github.com/Lissy93/web-check/actions/workflows/deploy-aws.yml/badge.svg)](https://github.com/Lissy93/web-check/actions/workflows/deploy-aws.yml)
<br />
Repo Management & Miscellaneous: [![🪞 Mirror to Codeberg](https://github.com/Lissy93/web-check/actions/workflows/mirror.yml/badge.svg)](https://github.com/Lissy93/web-check/actions/workflows/mirror.yml)
[![💓 Inserts Contributors & Sponsors](https://github.com/Lissy93/web-check/actions/workflows/credits.yml/badge.svg)](https://github.com/Lissy93/web-check/actions/workflows/credits.yml)
None of this is hard to find with a series of basic curl commands and NPMAP plus a combination of online tools. But it's just so much easier to have everything done all at once, presented clearly and visible in one place :)
### Features
<details>
<summary><h4>Expand to see all features</h4></summary>
<details open>
<summary><b>Click to expand / collapse section</b></summary>
<sup>**Note** _this list needs updating, many more jobs have been added since..._</sup>
The following section outlines the core features, and briefly explains why this data might be useful for you to know, as well as linking to further resources for learning more.
<details>
<summary><b>IP Info</b></summary>
@@ -730,14 +757,104 @@ This may be useful to see what a given website looks like, free of the constrain
</details>
Read more here: **[web-check.as93.net/about](https://web-check.as93.net/about)**
_Note that not all checks will work for all sites. Sometimes it's not possible to determine some information, and the demo instance has some limitations imposed by Netlify for the lambda functions._
Read more here: **[web-check.xyz/about](https://web-check.xyz/about)**
---
## Usage
### Deployment
### Deploying - Option #1: Netlify
Click the button below, to deploy to Netlify 👇
[![Deploy to Netlify](https://img.shields.io/badge/Deploy-Netlify-%2330c8c9?style=for-the-badge&logo=netlify&labelColor=1e0e41 'Deploy Web-Check to Netlify, via 1-Click Script')](https://app.netlify.com/start/deploy?repository=https://github.com/lissy93/web-check)
### Deploying - Option #2: Vercel
Click the button below, to deploy to Vercel 👇
[![Deploy with Vercel](https://img.shields.io/badge/Deploy-Vercel-%23ffffff?style=for-the-badge&logo=vercel&labelColor=1e0e41)](https://vercel.com/new/clone?repository-url=https%3A%2F%2Fgithub.com%2Flissy93%2Fweb-check&project-name=web-check&repository-name=web-check-fork&demo-title=Web-Check%20Demo&demo-description=Check%20out%20web-check.xyz%20to%20see%20a%20live%20demo%20of%20this%20application%20running.&demo-url=https%3A%2F%2Fweb-check.xyz&demo-image=https%3A%2F%2Fraw.githubusercontent.com%2FLissy93%2Fweb-check%2Fmaster%2F.github%2Fscreenshots%2Fweb-check-screenshot10.png)
### Deploying - Option #3: Docker
Run `docker run -p 3000:3000 lissy93/web-check`, then open [`localhost:3000`](http://localhost:3000)
<details>
<summary>Docker Options</summary>
You can get the Docker image from:
- DockerHub: [`lissy93/web-check`](https://hub.docker.com/r/lissy93/web-check)
- GHCR: [`ghcr.io/lissy93/web-check`](https://github.com/Lissy93/web-check/pkgs/container/web-check)
- Or build the image yourself by cloning the repo and running `docker build -t web-check .`
</details>
### Deploying - Option #4: From Source
Install the prerequisites listed in the [Developing](#developing) section, then run:
```bash
git clone https://github.com/Lissy93/web-check.git # Download the code from GitHub
cd web-check # Navigate into the project dir
yarn install # Install the NPM dependencies
yarn build # Build the app for production
yarn serve # Start the app (API and GUI)
```
---
### Configuring
By default, no configuration is needed.
But there are some optional environmental variables that you can set to give you access to some additional checks, or to increase rate-limits for some checks that use external APIs.
**API Keys & Credentials**:
Key | Value
---|---
`GOOGLE_CLOUD_API_KEY` | A Google API key ([get here](https://cloud.google.com/api-gateway/docs/authenticate-api-keys)). This can be used to return quality metrics for a site
`REACT_APP_SHODAN_API_KEY` | A Shodan API key ([get here](https://account.shodan.io/)). This will show associated host names for a given domain
`REACT_APP_WHO_API_KEY` | A WhoAPI key ([get here](https://whoapi.com/)). This will show more comprehensive WhoIs records than the default job
<details>
<summary><small>Full / Upcoming Vals</small></summary>
- `GOOGLE_CLOUD_API_KEY` - A Google API key ([get here](https://cloud.google.com/api-gateway/docs/authenticate-api-keys)). This can be used to return quality metrics for a site
- `REACT_APP_SHODAN_API_KEY` - A Shodan API key ([get here](https://account.shodan.io/)). This will show associated host names for a given domain
- `REACT_APP_WHO_API_KEY` - A WhoAPI key ([get here](https://whoapi.com/)). This will show more comprehensive WhoIs records than the default job
- `SECURITY_TRAILS_API_KEY` - A Security Trails API key ([get here](https://securitytrails.com/corp/api)). This will show org info associated with the IP
- `CLOUDMERSIVE_API_KEY` - API key for Cloudmersive ([get here](https://account.cloudmersive.com/)). This will show known threats associated with the IP
- `TRANCO_USERNAME` - A Tranco email ([get here](https://tranco-list.eu/)). This will show the rank of a site, based on traffic
- `TRANCO_API_KEY` - A Tranco API key ([get here](https://tranco-list.eu/)). This will show the rank of a site, based on traffic
- `URL_SCAN_API_KEY` - A URLScan API key ([get here](https://urlscan.io/)). This will fetch miscalanious info about a site
- `BUILT_WITH_API_KEY` - A BuiltWith API key ([get here](https://api.builtwith.com/)). This will show the main features of a site
- `TORRENT_IP_API_KEY` - A torrent API key ([get here](https://iknowwhatyoudownload.com/en/api/)). This will show torrents downloaded by an IP
</details>
**Configuration Settings**:
Key | Value
---|---
`PORT` | Port to serve the API, when running server.js (e.g. `3000`)
`API_ENABLE_RATE_LIMIT` | Enable rate-limiting for the /api endpoints (e.g. `true`)
`API_TIMEOUT_LIMIT` | The timeout limit for API requests, in milliseconds (e.g. `10000`)
`API_CORS_ORIGIN` | Enable CORS, by setting your allowed hostname(s) here (e.g. `example.com`)
`CHROME_PATH` | The path the Chromium executable (e.g. `/usr/bin/chromium`)
`DISABLE_GUI` | Disable the GUI, and only serve the API (e.g. `false`)
`REACT_APP_API_ENDPOINT` | The endpoint for the API, either local or remote (e.g. `/api`)
All values are optional.
You can add these as environmental variables. Either put them directly into an `.env` file in the projects root, or via the Netlify / Vercel UI, or by passing to the Docker container with the --env flag, or using your own environmental variable management system
Note that keys that are prefixed with `REACT_APP_` are used client-side, and as such they must be scoped correctly with minimum privileges, since may be made visible when intercepting browser <-> server network requests
---
### Developing
1. Clone the repo, `git clone git@github.com:Lissy93/web-check.git`
@@ -748,64 +865,6 @@ _Note that not all checks will work for all sites. Sometimes it's not possible t
You'll need [Node.js](https://nodejs.org/en) (V 18.16.1 or later) installed, plus [yarn](https://yarnpkg.com/getting-started/install) as well as [git](https://git-scm.com/).
Some checks also require `chromium`, `traceroute` and `dns` to be installed within your environment. These jobs will just be skipped if those packages aren't present.
### Deploying - Option #1: Netlify
Click the button below, to deploy to Netlify 👇
[![Deploy to Netlify](https://img.shields.io/badge/Deploy-Netlify-%2330c8c9?style=for-the-badge&logo=netlify&labelColor=1e0e41 'Deploy Web-Check to Netlify, via 1-Click Script')](https://app.netlify.com/start/deploy?repository=https://github.com/lissy93/web-check)
### Deploying - Option #2: Docker
Run `docker run -p 8888:3000 lissy93/web-check`, then open `http://localhost:3000`
You can get the Docker image from:
- DockerHub: [`lissy93/web-check`](https://hub.docker.com/r/lissy93/web-check)
- GHCR: [`ghcr.io/lissy93/web-check`](https://github.com/Lissy93/web-check/pkgs/container/web-check)
- Or build the image yourself by cloning the repo and running `docker build -t web-check .`
### Deploying - Option #3: From Source
Follow the instructions in the [Developing](#developing) section above, then run `yarn build` && `yarn serve` to build and serve the application.
The following commands will work:
```bash
git clone https://github.com/Lissy93/web-check.git # Grab the code
cd web-check # Move into the project directory
yarn install # Install dependencies
yarn build # Build the app for production
yarn serve # Start the app (API and GUI)
```
### Configuring
By default, no configuration is needed.
But there are some optional environmental variables that you can set to give you access to some additional checks, or to increase rate-limits for some checks that use external APIs.
Note that keys that are prefixed with `REACT_APP_` are used client-side, and as such they must be scoped correctly with minimum privileges.
**API Keys & Credentials**:
- `GOOGLE_CLOUD_API_KEY` - A Google API key ([get here](https://cloud.google.com/api-gateway/docs/authenticate-api-keys)). This can be used to return quality metrics for a site
- `REACT_APP_SHODAN_API_KEY` - A Shodan API key ([get here](https://account.shodan.io/)). This will show associated host names for a given domain
- `REACT_APP_WHO_API_KEY` - A WhoAPI key ([get here](https://whoapi.com/)). This will show more comprehensive WhoIs records than the default job
- `SECURITY_TRAILS_API_KEY` - A Security Trails API key ([get here](https://securitytrails.com/corp/api)). This will show org info associated with the IP
- `CLOUDMERSIVE_API_KEY` - API key for Cloudmersive ([get here](https://account.cloudmersive.com/)). This will show known threats associated with the IP
- `TRANCO_USERNAME` - A Tranco email ([get here](https://tranco-list.eu/)). This will show the rank of a site, based on traffic
- `TRANCO_API_KEY` - A Tranco API key ([get here](https://tranco-list.eu/)). This will show the rank of a site, based on traffic
- `URL_SCAN_API_KEY` - A URLScan API key ([get here](https://urlscan.io/)). This will fetch miscalanious info about a site
- `BUILT_WITH_API_KEY` - A BuiltWith API key ([get here](https://api.builtwith.com/)). This will show the main features of a site
- `TORRENT_IP_API_KEY` - A torrent API key ([get here](https://iknowwhatyoudownload.com/en/api/)). This will show torrents downloaded by an IP
**Configuration Settings**:
- `CHROME_PATH` (e.g. `/usr/bin/chromium`) - The path the the Chromium executable
- `PORT` (e.g. `3000`) - Port to serve the API, when running server.js
- `DISABLE_GUI` (e.g. `false`) - Disable the GUI, and only serve the API
- `API_TIMEOUT_LIMIT` (e.g. `10000`) - The timeout limit for API requests, in milliseconds
- `REACT_APP_API_ENDPOINT` (e.g. `/api`) - The endpoint for the API (can be local or remote)
The above can be added into an `.env` file in the projects root, or via the Netlify UI, or by passing directly to the Docker container with the --env flag.
All variables are optional.
---
@@ -831,8 +890,9 @@ For bugs, please outline the steps needed to reproduce, and include relevant inf
### Supporting
The app will remain 100% free and open source.
But due to the amount of traffic that the hosted instance gets, the lambda function usage is costing about $25/month. Any help with covering the costs via GitHub Sponsorship would be much appreciated. It's thanks to the support of the community that this project is able to be freely available for everyone :)
But due to the amount of traffic that the hosted instance gets, the lambda function usage is costing about $25/month.
Any help with covering the costs via GitHub Sponsorship would be much appreciated.
It's thanks to the support of the community that this project is able to be freely available for everyone :)
[![Sponsor Lissy93 on GitHub](https://img.shields.io/badge/Sponsor_on_GitHub-Lissy93-%23ff4dda?style=for-the-badge&logo=githubsponsors&logoColor=ff4dda)](https://github.com/sponsors/Lissy93)
@@ -843,49 +903,200 @@ Credit to the following users for contributing to Web-Check
<!-- readme: contributors -start -->
<table>
<tr>
<td align="center">
<a href="https://github.com/Lissy93">
<img src="https://avatars.githubusercontent.com/u/1862727?v=4" width="80;" alt="Lissy93"/>
<br />
<sub><b>Alicia Sykes</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/muni106">
<img src="https://avatars.githubusercontent.com/u/65845442?v=4" width="80;" alt="muni106"/>
<br />
<sub><b>Mounir Samite</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/gso-trifork-security">
<img src="https://avatars.githubusercontent.com/u/69247026?v=4" width="80;" alt="gso-trifork-security"/>
<br />
<sub><b>Gustav Soelberg</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/treatmesubj">
<img src="https://avatars.githubusercontent.com/u/39680353?v=4" width="80;" alt="treatmesubj"/>
<br />
<sub><b>John Hupperts</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/UlisesGascon">
<img src="https://avatars.githubusercontent.com/u/5110813?v=4" width="80;" alt="UlisesGascon"/>
<br />
<sub><b>Ulises Gascón</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/abhishekMuge">
<img src="https://avatars.githubusercontent.com/u/49590582?v=4" width="80;" alt="abhishekMuge"/>
<br />
<sub><b>Abhishek Muge</b></sub>
</a>
</td></tr>
<tbody>
<tr>
<td align="center">
<a href="https://github.com/Lissy93">
<img src="https://avatars.githubusercontent.com/u/1862727?v=4" width="80;" alt="Lissy93"/>
<br />
<sub><b>Alicia Sykes</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/liss-bot">
<img src="https://avatars.githubusercontent.com/u/87835202?v=4" width="80;" alt="liss-bot"/>
<br />
<sub><b>Alicia Bot</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/n0a">
<img src="https://avatars.githubusercontent.com/u/14150948?v=4" width="80;" alt="n0a"/>
<br />
<sub><b>Denis Simonov</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/muni106">
<img src="https://avatars.githubusercontent.com/u/65845442?v=4" width="80;" alt="muni106"/>
<br />
<sub><b>Mounir Samite</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/ChrisCarini">
<img src="https://avatars.githubusercontent.com/u/6374067?v=4" width="80;" alt="ChrisCarini"/>
<br />
<sub><b>Chris Carini</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/bolens">
<img src="https://avatars.githubusercontent.com/u/1218380?v=4" width="80;" alt="bolens"/>
<br />
<sub><b>Michael Bolens</b></sub>
</a>
</td>
</tr>
<tr>
<td align="center">
<a href="https://github.com/HeroGamers">
<img src="https://avatars.githubusercontent.com/u/15278940?v=4" width="80;" alt="HeroGamers"/>
<br />
<sub><b>Marcus Sand</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/jinnabaalu">
<img src="https://avatars.githubusercontent.com/u/11784253?v=4" width="80;" alt="jinnabaalu"/>
<br />
<sub><b>Jinna Baalu</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/GreyXor">
<img src="https://avatars.githubusercontent.com/u/79602273?v=4" width="80;" alt="GreyXor"/>
<br />
<sub><b>GreyXor</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/brianteeman">
<img src="https://avatars.githubusercontent.com/u/1296369?v=4" width="80;" alt="brianteeman"/>
<br />
<sub><b>Brian Teeman</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/vitalykarasik">
<img src="https://avatars.githubusercontent.com/u/7628795?v=4" width="80;" alt="vitalykarasik"/>
<br />
<sub><b>Vitaly Karasik</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/Its-Just-Nans">
<img src="https://avatars.githubusercontent.com/u/56606507?v=4" width="80;" alt="Its-Just-Nans"/>
<br />
<sub><b>n4n5</b></sub>
</a>
</td>
</tr>
<tr>
<td align="center">
<a href="https://github.com/robinson">
<img src="https://avatars.githubusercontent.com/u/237874?v=4" width="80;" alt="robinson"/>
<br />
<sub><b>Lth</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/abhishekMuge">
<img src="https://avatars.githubusercontent.com/u/49590582?v=4" width="80;" alt="abhishekMuge"/>
<br />
<sub><b>Abhishek Muge</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/UlisesGascon">
<img src="https://avatars.githubusercontent.com/u/5110813?v=4" width="80;" alt="UlisesGascon"/>
<br />
<sub><b>Ulises Gascón</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/PhiRequiem">
<img src="https://avatars.githubusercontent.com/u/1323576?v=4" width="80;" alt="PhiRequiem"/>
<br />
<sub><b>PhiRequiem</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/ntaiko">
<img src="https://avatars.githubusercontent.com/u/108784453?v=4" width="80;" alt="ntaiko"/>
<br />
<sub><b>Nikolaos G. Ntaiko</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/Myzel394">
<img src="https://avatars.githubusercontent.com/u/50424412?v=4" width="80;" alt="Myzel394"/>
<br />
<sub><b>Myzel394</b></sub>
</a>
</td>
</tr>
<tr>
<td align="center">
<a href="https://github.com/murrple-1">
<img src="https://avatars.githubusercontent.com/u/5559656?v=4" width="80;" alt="murrple-1"/>
<br />
<sub><b>Murray Christopherson</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/t3chn0m4g3">
<img src="https://avatars.githubusercontent.com/u/4318452?v=4" width="80;" alt="t3chn0m4g3"/>
<br />
<sub><b>Marco Ochse</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/treatmesubj">
<img src="https://avatars.githubusercontent.com/u/39680353?v=4" width="80;" alt="treatmesubj"/>
<br />
<sub><b>John Hupperts</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/eltociear">
<img src="https://avatars.githubusercontent.com/u/22633385?v=4" width="80;" alt="eltociear"/>
<br />
<sub><b>Ikko Eltociear Ashimine</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/Gertje823">
<img src="https://avatars.githubusercontent.com/u/36937387?v=4" width="80;" alt="Gertje823"/>
<br />
<sub><b>Gertje823</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/epreston">
<img src="https://avatars.githubusercontent.com/u/347224?v=4" width="80;" alt="epreston"/>
<br />
<sub><b>Ed Preston</b></sub>
</a>
</td>
</tr>
<tr>
<td align="center">
<a href="https://github.com/dimitri-kandassamy">
<img src="https://avatars.githubusercontent.com/u/21193806?v=4" width="80;" alt="dimitri-kandassamy"/>
<br />
<sub><b>Dimitri Kandassamy</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/0xflotus">
<img src="https://avatars.githubusercontent.com/u/26602940?v=4" width="80;" alt="0xflotus"/>
<br />
<sub><b>0xflotus</b></sub>
</a>
</td>
</tr>
<tbody>
</table>
<!-- readme: contributors -end -->
@@ -895,114 +1106,163 @@ Huge thanks to these wonderful people, who sponsor me on GitHub, their support h
<!-- readme: sponsors -start -->
<table>
<tr>
<td align="center">
<a href="https://github.com/emlazzarin">
<img src="https://avatars.githubusercontent.com/u/1141361?v=4" width="80;" alt="emlazzarin"/>
<br />
<sub><b>Eddy Lazzarin</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/AnandChowdhary">
<img src="https://avatars.githubusercontent.com/u/2841780?v=4" width="80;" alt="AnandChowdhary"/>
<br />
<sub><b>Anand Chowdhary</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/shrippen">
<img src="https://avatars.githubusercontent.com/u/2873570?v=4" width="80;" alt="shrippen"/>
<br />
<sub><b>shrippen</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/davidpaulyoung">
<img src="https://avatars.githubusercontent.com/u/3418369?v=4" width="80;" alt="davidpaulyoung"/>
<br />
<sub><b>David Young</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/k-rol">
<img src="https://avatars.githubusercontent.com/u/4050412?v=4" width="80;" alt="k-rol"/>
<br />
<sub><b>Carol Ouellet</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/bile0026">
<img src="https://avatars.githubusercontent.com/u/5022496?v=4" width="80;" alt="bile0026"/>
<br />
<sub><b>Zach Biles</b></sub>
</a>
</td></tr>
<tr>
<td align="center">
<a href="https://github.com/UlisesGascon">
<img src="https://avatars.githubusercontent.com/u/5110813?v=4" width="80;" alt="UlisesGascon"/>
<br />
<sub><b>Ulises Gascón</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/digitalarche">
<img src="https://avatars.githubusercontent.com/u/6546135?v=4" width="80;" alt="digitalarche"/>
<br />
<sub><b>Digital Archeology</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/bmcgonag">
<img src="https://avatars.githubusercontent.com/u/7346620?v=4" width="80;" alt="bmcgonag"/>
<br />
<sub><b>Brian McGonagill</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/vlad-timofeev">
<img src="https://avatars.githubusercontent.com/u/11474041?v=4" width="80;" alt="vlad-timofeev"/>
<br />
<sub><b>Vlad Timofeev</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/iJasonWade">
<img src="https://avatars.githubusercontent.com/u/12824479?v=4" width="80;" alt="iJasonWade"/>
<br />
<sub><b>Jason Ash</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/DRXAquosus">
<img src="https://avatars.githubusercontent.com/u/45409262?v=4" width="80;" alt="DRXAquosus"/>
<br />
<sub><b>DRXAquosus</b></sub>
</a>
</td></tr>
<tr>
<td align="center">
<a href="https://github.com/Bastii717">
<img src="https://avatars.githubusercontent.com/u/53431819?v=4" width="80;" alt="Bastii717"/>
<br />
<sub><b>Bastii717</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/ratty222">
<img src="https://avatars.githubusercontent.com/u/92832598?v=4" width="80;" alt="ratty222"/>
<br />
<sub><b>Brent</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/jtfinley72">
<img src="https://avatars.githubusercontent.com/u/96497997?v=4" width="80;" alt="jtfinley72"/>
<br />
<sub><b>jtfinley72</b></sub>
</a>
</td></tr>
<tbody>
<tr>
<td align="center">
<a href="https://github.com/vincentkoc">
<img src="https://avatars.githubusercontent.com/u/25068?v=4" width="80;" alt="vincentkoc"/>
<br />
<sub><b>Vincent Koc</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/AnandChowdhary">
<img src="https://avatars.githubusercontent.com/u/2841780?u=747e554b3a7f12eb20b7910e1c87d817844f714f&v=4" width="80;" alt="AnandChowdhary"/>
<br />
<sub><b>Anand Chowdhary</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/shrippen">
<img src="https://avatars.githubusercontent.com/u/2873570?v=4" width="80;" alt="shrippen"/>
<br />
<sub><b>Shrippen</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/bile0026">
<img src="https://avatars.githubusercontent.com/u/5022496?u=aec96ad173c0ea9baaba93807efa8a848af6595c&v=4" width="80;" alt="bile0026"/>
<br />
<sub><b>Zach Biles</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/UlisesGascon">
<img src="https://avatars.githubusercontent.com/u/5110813?u=3c41facd8aa26154b9451de237c34b0f78d672a5&v=4" width="80;" alt="UlisesGascon"/>
<br />
<sub><b>Ulises Gascón</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/digitalarche">
<img src="https://avatars.githubusercontent.com/u/6546135?u=564756d7f44ab2206819eb3148f6d822673f5066&v=4" width="80;" alt="digitalarche"/>
<br />
<sub><b>Digital Archeology</b></sub>
</a>
</td>
</tr>
<tr>
<td align="center">
<a href="https://github.com/InDieTasten">
<img src="https://avatars.githubusercontent.com/u/7047377?u=8d8f8017628b38bc46dcbf3620e194b01d3fb2d1&v=4" width="80;" alt="InDieTasten"/>
<br />
<sub><b>InDieTasten</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/araguaci">
<img src="https://avatars.githubusercontent.com/u/7318668?v=4" width="80;" alt="araguaci"/>
<br />
<sub><b>Araguaci</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/bmcgonag">
<img src="https://avatars.githubusercontent.com/u/7346620?u=2a0f9284f3e12ac1cc15288c254d1ec68a5081e8&v=4" width="80;" alt="bmcgonag"/>
<br />
<sub><b>Brian McGonagill</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/arcestia">
<img src="https://avatars.githubusercontent.com/u/7936962?v=4" width="80;" alt="arcestia"/>
<br />
<sub><b>Laurensius Jeffrey</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/vlad-tim">
<img src="https://avatars.githubusercontent.com/u/11474041?u=eee43705b54d2ec9f51fc4fcce5ad18dd17c87e4&v=4" width="80;" alt="vlad-tim"/>
<br />
<sub><b>Vlad</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/helixzz">
<img src="https://avatars.githubusercontent.com/u/12218889?u=d06d0c103dfbdb99450623064f7da3c5a3675fb6&v=4" width="80;" alt="helixzz"/>
<br />
<sub><b>HeliXZz</b></sub>
</a>
</td>
</tr>
<tr>
<td align="center">
<a href="https://github.com/mryesiller">
<img src="https://avatars.githubusercontent.com/u/24632172?u=0d20f2d615158f87cd60a3398d3efb026c32f291&v=4" width="80;" alt="mryesiller"/>
<br />
<sub><b>Göksel Yeşiller</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/sushibait">
<img src="https://avatars.githubusercontent.com/u/26634535?v=4" width="80;" alt="sushibait"/>
<br />
<sub><b>Shiverme Timbers</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/getumbrel">
<img src="https://avatars.githubusercontent.com/u/59408891?v=4" width="80;" alt="getumbrel"/>
<br />
<sub><b>Umbrel</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/OlliVHH">
<img src="https://avatars.githubusercontent.com/u/84959562?v=4" width="80;" alt="OlliVHH"/>
<br />
<sub><b>HamburgerJung</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/frankdez93">
<img src="https://avatars.githubusercontent.com/u/87549420?v=4" width="80;" alt="frankdez93"/>
<br />
<sub><b>Frankdez93</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/terminaltrove">
<img src="https://avatars.githubusercontent.com/u/121595180?v=4" width="80;" alt="terminaltrove"/>
<br />
<sub><b>Terminal Trove</b></sub>
</a>
</td>
</tr>
<tr>
<td align="center">
<a href="https://github.com/st617">
<img src="https://avatars.githubusercontent.com/u/128325650?v=4" width="80;" alt="st617"/>
<br />
<sub><b>st617</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/hudsonrock-partnerships">
<img src="https://avatars.githubusercontent.com/u/163282900?u=5f2667f7fe5d284ac7a2da6b0800ea8970b0fcbf&v=4" width="80;" alt="hudsonrock-partnerships"/>
<br />
<sub><b>hudsonrock-partnerships</b></sub>
</a>
</td>
<td align="center">
<a href="https://github.com/CarterPerez-dev">
<img src="https://avatars.githubusercontent.com/u/188120068?v=4" width="80;" alt="CarterPerez-dev"/>
<br />
<sub><b>Carter Perez</b></sub>
</a>
</td>
</tr>
<tbody>
</table>
<!-- readme: sponsors -end -->
@@ -1038,8 +1298,11 @@ OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
```
[![View Dependency Licenses & SBOM on FOSSA](https://app.fossa.com/api/projects/git%2Bgithub.com%2FLissy93%2Fweb-check.svg?type=large&issueType=license)](https://app.fossa.com/projects/git%2Bgithub.com%2FLissy93%2Fweb-check?ref=badge_large&issueType=license)
</details>
<!-- License + Copyright -->
<p align="center">
<i>© <a href="https://aliciasykes.com">Alicia Sykes</a> 2023</i><br>
@@ -1048,7 +1311,7 @@ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
<sup>Thanks for visiting :)</sup>
</p>
<!-- Dinosaur -->
<!-- Dinosaurs are Awesome -->
<!--
. - ~ ~ ~ - .
.. _ .-~ ~-.

View File

@@ -12,9 +12,9 @@ jobs:
name: Inserts Sponsors 💓
steps:
- name: Checkout
uses: actions/checkout@v2
uses: actions/checkout@v4
- name: Updates readme with sponsors
uses: JamesIves/github-sponsors-readme-action@1.0.5
uses: JamesIves/github-sponsors-readme-action@v1
with:
token: ${{ secrets.BOT_TOKEN || secrets.GITHUB_TOKEN }}
file: .github/README.md
@@ -25,7 +25,7 @@ jobs:
name: Inserts Contributors 💓
steps:
- name: Updates readme with contributors
uses: akhilmhdh/contributors-readme-action@v2.3.4
uses: akhilmhdh/contributors-readme-action@v2.3.10
env:
GITHUB_TOKEN: ${{ secrets.BOT_TOKEN || secrets.GITHUB_TOKEN }}
with:

128
.github/workflows/deploy-aws.yml vendored Normal file
View File

@@ -0,0 +1,128 @@
name: 🚀 Deploy to AWS
on:
workflow_dispatch:
push:
branches:
- master
tags:
- '*'
paths:
- api/**
- serverless.yml
- package.json
- .github/workflows/deploy-aws.yml
jobs:
deploy-api:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Setup Node.js
uses: actions/setup-node@v4
with:
node-version: 16
- name: Cache node_modules
uses: actions/cache@v4
with:
path: node_modules
key: ${{ runner.os }}-yarn-${{ hashFiles('**/yarn.lock') }}
restore-keys: |
${{ runner.os }}-yarn-
- name: Create GitHub deployment for API
uses: chrnorm/deployment-action@releases/v2
id: deployment_api
with:
token: ${{ secrets.BOT_TOKEN || secrets.GITHUB_TOKEN }}
environment: AWS (Backend API)
ref: ${{ github.ref }}
- name: Install Serverless CLI and dependencies
run: |
npm i -g serverless
yarn
- name: Deploy to AWS
env:
AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }}
AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
AWS_ACCOUNT_ID: ${{ secrets.AWS_ACCOUNT_ID }}
run: serverless deploy
- name: Update GitHub deployment status (API)
if: always()
uses: chrnorm/deployment-status@v2
with:
token: ${{ secrets.BOT_TOKEN || secrets.GITHUB_TOKEN }}
state: "${{ job.status }}"
deployment_id: ${{ steps.deployment_api.outputs.deployment_id }}
ref: ${{ github.ref }}
deploy-frontend:
runs-on: ubuntu-latest
steps:
- name: Checkout code
uses: actions/checkout@v4
- name: Setup Node.js
uses: actions/setup-node@v4
with:
node-version: 16
- name: Cache node_modules
uses: actions/cache@v4
with:
path: node_modules
key: ${{ runner.os }}-yarn-${{ hashFiles('**/yarn.lock') }}
restore-keys: |
${{ runner.os }}-yarn-
- name: Create GitHub deployment for Frontend
uses: chrnorm/deployment-action@v2
id: deployment_frontend
with:
token: ${{ secrets.BOT_TOKEN || secrets.GITHUB_TOKEN }}
environment: AWS (Frontend Web UI)
ref: ${{ github.ref }}
- name: Install dependencies and build
run: |
yarn install
yarn build
- name: Setup AWS
uses: aws-actions/configure-aws-credentials@v4
with:
aws-access-key-id: ${{ secrets.AWS_ACCESS_KEY_ID }}
aws-secret-access-key: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
aws-region: us-east-1
- name: Upload to S3
env:
AWS_S3_BUCKET: 'web-check-frontend'
run: aws s3 sync ./build/ s3://$AWS_S3_BUCKET/ --delete
- name: Invalidate CloudFront cache
uses: chetan/invalidate-cloudfront-action@v2
env:
DISTRIBUTION: E30XKAM2TG9FD8
PATHS: '/*'
AWS_REGION: 'us-east-1'
AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID }}
AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY }}
- name: Update GitHub deployment status (Frontend)
if: always()
uses: chrnorm/deployment-status@v2
with:
token: ${{ secrets.BOT_TOKEN || secrets.GITHUB_TOKEN }}
state: "${{ job.status }}"
deployment_id: ${{ steps.deployment_frontend.outputs.deployment_id }}
ref: ${{ github.ref }}

View File

@@ -23,14 +23,14 @@ jobs:
docker:
runs-on: ubuntu-latest
steps:
- name: Checkout
- name: Checkout 🛎️
uses: actions/checkout@v2
- name: Extract tag name
- name: Extract tag name 🏷️
shell: bash
run: echo "GIT_TAG=$(echo ${GITHUB_REF#refs/tags/} | sed 's/\//_/g')" >> $GITHUB_ENV
- name: Compute tags
- name: Compute tags 🔖
id: compute-tags
run: |
if [[ "${{ github.ref }}" == "refs/heads/master" ]]; then
@@ -41,33 +41,33 @@ jobs:
echo "DOCKERHUB_TAG=${DOCKERHUB_REGISTRY}/${DOCKER_USER}/${IMAGE_NAME}:${GIT_TAG}" >> $GITHUB_ENV
fi
- name: Set up QEMU
- name: Set up QEMU 🐧
uses: docker/setup-qemu-action@v1
- name: Set up Docker Buildx
- name: Set up Docker Buildx 🐳
uses: docker/setup-buildx-action@v1
- name: Login to GitHub Container Registry
- name: Login to GitHub Container Registry 🔑
uses: docker/login-action@v1
with:
registry: ${{ env.GHCR_REGISTRY }}
username: ${{ github.actor }}
password: ${{ secrets.GITHUB_TOKEN }}
- name: Login to DockerHub
- name: Login to DockerHub 🔑
uses: docker/login-action@v1
with:
registry: ${{ env.DOCKERHUB_REGISTRY }}
username: ${{ env.DOCKER_USER }}
password: ${{ secrets.DOCKERHUB_PASSWORD }}
- name: Build and push Docker images
- name: Build and push Docker images 🛠️
uses: docker/build-push-action@v2
with:
context: .
file: ./Dockerfile
push: true
platforms: linux/amd64
platforms: linux/amd64,linux/arm64/v8
tags: |
${{ env.GHCR_TAG }}
${{ env.DOCKERHUB_TAG }}

View File

@@ -8,7 +8,7 @@ jobs:
codeberg:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v2
- uses: actions/checkout@v4
with: { fetch-depth: 0 }
- uses: pixta-dev/repository-mirroring-action@v1
with:

71
.gitignore vendored
View File

@@ -1,27 +1,62 @@
# keys
# ------------------------
# ENVIRONMENT SETTINGS
# ------------------------
.env
# dependencies
/node_modules
/.pnp
.pnp.js
# ------------------------
# PRODUCTION
# ------------------------
/build/
# logs
# ------------------------
# BUILT FILES
# ------------------------
dist/
.vercel/
.netlify/
.webpack/
.serverless/
.astro/
# ------------------------
# DEPENDENCIES
# ------------------------
node_modules/
.yarn/cache/
.yarn/unplugged/
.yarn/build-state.yml
.yarn/install-state.gz
.pnpm/
.pnp.*
# ------------------------
# LOGS
# ------------------------
logs/
*.log
npm-debug.log*
yarn-debug.log*
yarn-error.log*
lerna-debug.log*
.pnpm-debug.log*
# testing
/coverage
# ------------------------
# TESTING
# ------------------------
coverage/
.nyc_output/
# production
/build
# Random AWS and Netlify crap
.netlify
.serverless
.webpack
# OS generated files
# ------------------------
# OS SPECIFIC
# ------------------------
.DS_Store
Thumbs.db
# ------------------------
# EDITORS
# ------------------------
.idea/
.vscode/
*.swp
*.swo

View File

@@ -1,13 +1,62 @@
FROM node:16-buster-slim AS base
# Specify the Node.js version to use
ARG NODE_VERSION=21
# Specify the Debian version to use, the default is "bullseye"
ARG DEBIAN_VERSION=bullseye
# Use Node.js Docker image as the base image, with specific Node and Debian versions
FROM node:${NODE_VERSION}-${DEBIAN_VERSION} AS build
# Set the container's default shell to Bash and enable some options
SHELL ["/bin/bash", "-euo", "pipefail", "-c"]
# Install Chromium browser and Download and verify Google Chromes signing key
RUN apt-get update -qq --fix-missing && \
apt-get -qqy install --allow-unauthenticated gnupg wget && \
wget --quiet --output-document=- https://dl-ssl.google.com/linux/linux_signing_key.pub | gpg --dearmor > /etc/apt/trusted.gpg.d/google-archive.gpg && \
echo "deb [arch=amd64] http://dl.google.com/linux/chrome/deb/ stable main" > /etc/apt/sources.list.d/google.list && \
apt-get update -qq && \
apt-get -qqy --no-install-recommends install chromium traceroute python make g++ && \
rm -rf /var/lib/apt/lists/*
# Run the Chromium browser's version command and redirect its output to the /etc/chromium-version file
RUN /usr/bin/chromium --no-sandbox --version > /etc/chromium-version
# Set the working directory to /app
WORKDIR /app
FROM base AS builder
COPY . .
# Copy package.json and yarn.lock to the working directory
COPY package.json yarn.lock ./
# Run yarn install to install dependencies and clear yarn cache
RUN apt-get update && \
apt-get install -y chromium traceroute && \
yarn install --frozen-lockfile --network-timeout 100000 && \
rm -rf /app/node_modules/.cache
# Copy all files to working directory
COPY . .
# Run yarn build to build the application
RUN yarn build --production
# Final stage
FROM node:${NODE_VERSION}-${DEBIAN_VERSION} AS final
WORKDIR /app
COPY package.json yarn.lock ./
COPY --from=build /app .
RUN apt-get update && \
apt-get install -y --no-install-recommends chromium traceroute && \
chmod 755 /usr/bin/chromium && \
rm -rf /var/lib/apt/lists/*
RUN npm install --force
RUN npm run build
rm -rf /var/lib/apt/lists/* /app/node_modules/.cache
# Exposed container port, the default is 3000, which can be modified through the environment variable PORT
EXPOSE ${PORT:-3000}
# Set the environment variable CHROME_PATH to specify the path to the Chromium binaries
ENV CHROME_PATH='/usr/bin/chromium'
CMD ["npm", "run", "serve"]
# Define the command executed when the container starts and start the server.js of the Node.js application
CMD ["yarn", "start"]

View File

@@ -2,37 +2,154 @@ const normalizeUrl = (url) => {
return url.startsWith('http') ? url : `https://${url}`;
};
// If present, set a shorter timeout for API requests
const TIMEOUT = process.env.API_TIMEOUT_LIMIT ? parseInt(process.env.API_TIMEOUT_LIMIT, 10) : 60000;
// If present, set CORS allowed origins for responses
const ALLOWED_ORIGINS = process.env.API_CORS_ORIGIN || '*';
// Disable everything :( Setting this env var will turn off the instance, and show message
const DISABLE_EVERYTHING = !!process.env.VITE_DISABLE_EVERYTHING;
// Set the platform currently being used
let PLATFORM = 'NETLIFY';
if (process.env.PLATFORM) { PLATFORM = process.env.PLATFORM.toUpperCase(); }
else if (process.env.VERCEL) { PLATFORM = 'VERCEL'; }
else if (process.env.WC_SERVER) { PLATFORM = 'NODE'; }
// Define the headers to be returned with each response
const headers = {
'Access-Control-Allow-Origin': ALLOWED_ORIGINS,
'Access-Control-Allow-Credentials': true,
'Content-Type': 'application/json;charset=UTF-8',
};
const timeoutErrorMsg = 'You can re-trigger this request, by clicking "Retry"\n'
+ 'If you\'re running your own instance of Web Check, then you can '
+ 'resolve this issue, by increasing the timeout limit in the '
+ '`API_TIMEOUT_LIMIT` environmental variable to a higher value (in milliseconds), '
+ 'or if you\'re hosting on Vercel increase the maxDuration in vercel.json.\n\n'
+ `The public instance currently has a lower timeout of ${TIMEOUT}ms `
+ 'in order to keep running costs affordable, so that Web Check can '
+ 'remain freely available for everyone.';
const disabledErrorMsg = 'Error - WebCheck Temporarily Disabled.\n\n'
+ 'We\'re sorry, but due to the increased cost of running Web Check '
+ 'we\'ve had to temporatily disable the public instand. '
+ 'We\'re activley looking for affordable ways to keep Web Check running, '
+ 'while free to use for everybody.\n'
+ 'In the meantime, since we\'ve made our code free and open source, '
+ 'you can get Web Check running on your own system, by following the instructions in our GitHub repo';
// A middleware function used by all API routes on all platforms
const commonMiddleware = (handler) => {
return async (event, context, callback) => {
const queryParams = event.queryStringParameters || event.query || {};
// Create a timeout promise, to throw an error if a request takes too long
const createTimeoutPromise = (timeoutMs) => {
return new Promise((_, reject) => {
setTimeout(() => {
reject(new Error(`Request timed-out after ${timeoutMs} ms`));
}, timeoutMs);
});
};
// Vercel
const vercelHandler = async (request, response) => {
if (DISABLE_EVERYTHING) {
response.status(503).json({ error: disabledErrorMsg });
}
const queryParams = request.query || {};
const rawUrl = queryParams.url;
if (!rawUrl) {
callback(null, {
statusCode: 500,
body: JSON.stringify({ error: 'No URL specified' }),
});
return response.status(500).json({ error: 'No URL specified' });
}
const url = normalizeUrl(rawUrl);
try {
const response = await handler(url, event, context);
if (response.body && response.statusCode) {
callback(null, response);
// Race the handler against the timeout
const handlerResponse = await Promise.race([
handler(url, request),
createTimeoutPromise(TIMEOUT)
]);
if (handlerResponse.body && handlerResponse.statusCode) {
response.status(handlerResponse.statusCode).json(handlerResponse.body);
} else {
response.status(200).json(
typeof handlerResponse === 'object' ? handlerResponse : JSON.parse(handlerResponse)
);
}
} catch (error) {
let errorCode = 500;
if (error.message.includes('timed-out') || response.statusCode === 504) {
errorCode = 408;
error.message = `${error.message}\n\n${timeoutErrorMsg}`;
}
response.status(errorCode).json({ error: error.message });
}
};
// Netlify
const netlifyHandler = async (event, context, callback) => {
const queryParams = event.queryStringParameters || event.query || {};
const rawUrl = queryParams.url;
if (DISABLE_EVERYTHING) {
callback(null, {
statusCode: 503,
body: JSON.stringify({ error: 'Web-Check is temporarily disabled. Please try again later.' }),
headers,
});
return;
}
if (!rawUrl) {
callback(null, {
statusCode: 500,
body: JSON.stringify({ error: 'No URL specified' }),
headers,
});
return;
}
const url = normalizeUrl(rawUrl);
try {
// Race the handler against the timeout
const handlerResponse = await Promise.race([
handler(url, event, context),
createTimeoutPromise(TIMEOUT)
]);
if (handlerResponse.body && handlerResponse.statusCode) {
callback(null, handlerResponse);
} else {
callback(null, {
statusCode: 200,
body: typeof response === 'object' ? JSON.stringify(response) : response,
body: typeof handlerResponse === 'object' ? JSON.stringify(handlerResponse) : handlerResponse,
headers,
});
}
} catch (error) {
callback(null, {
statusCode: 500,
body: JSON.stringify({ error: error.message }),
headers,
});
}
};
// The format of the handlers varies between platforms
const nativeMode = (['VERCEL', 'NODE'].includes(PLATFORM));
return nativeMode ? vercelHandler : netlifyHandler;
};
module.exports = commonMiddleware;
if (PLATFORM === 'NETLIFY') {
module.exports = commonMiddleware;
}
export default commonMiddleware;

View File

@@ -1,5 +1,5 @@
const axios = require('axios');
const middleware = require('./_common/middleware');
import axios from 'axios';
import middleware from './_common/middleware.js';
const convertTimestampToDate = (timestamp) => {
const [year, month, day, hour, minute, second] = [
@@ -46,7 +46,7 @@ const getScanFrequency = (firstScan, lastScan, totalScans, changeCount) => {
};
};
const getWaybackData = async (url) => {
const wayBackHandler = async (url) => {
const cdxUrl = `https://web.archive.org/cdx/search/cdx?url=${url}&output=json&fl=timestamp,statuscode,digest,length,offset`;
try {
@@ -80,4 +80,5 @@ const getWaybackData = async (url) => {
}
};
exports.handler = middleware(getWaybackData);
export const handler = middleware(wayBackHandler);
export default handler;

View File

@@ -1,6 +1,6 @@
const dns = require('dns');
const { URL } = require('url');
const middleware = require('./_common/middleware');
import dns from 'dns';
import { URL } from 'url';
import middleware from './_common/middleware.js';
const DNS_SERVERS = [
{ name: 'AdGuard', ip: '176.103.130.130' },
@@ -94,12 +94,12 @@ const checkDomainAgainstDnsServers = async (domain) => {
return results;
};
exports.handler = middleware(async (url) => {
export const blockListHandler = async (url) => {
const domain = new URL(url).hostname;
const results = await checkDomainAgainstDnsServers(domain);
return {
statusCode: 200,
body: JSON.stringify({ blocklists: results })
};
});
return { blocklists: results };
};
export const handler = middleware(blockListHandler);
export default handler;

View File

@@ -1,7 +1,7 @@
const https = require('https');
const middleware = require('./_common/middleware');
import https from 'https';
import middleware from './_common/middleware.js';
const handler = async (url) => {
const carbonHandler = async (url) => {
// First, get the size of the website's HTML
const getHtmlSize = (url) => new Promise((resolve, reject) => {
@@ -48,4 +48,5 @@ const handler = async (url) => {
}
};
exports.handler = middleware(handler);
export const handler = middleware(carbonHandler);
export default handler;

View File

@@ -1,6 +1,6 @@
const axios = require('axios');
const puppeteer = require('puppeteer');
const middleware = require('./_common/middleware');
import axios from 'axios';
import puppeteer from 'puppeteer';
import middleware from './_common/middleware.js';
const getPuppeteerCookies = async (url) => {
const browser = await puppeteer.launch({
@@ -21,7 +21,7 @@ const getPuppeteerCookies = async (url) => {
}
};
const handler = async (url) => {
const cookieHandler = async (url) => {
let headerCookies = null;
let clientCookies = null;
@@ -54,4 +54,5 @@ const handler = async (url) => {
return { headerCookies, clientCookies };
};
exports.handler = middleware(handler);
export const handler = middleware(cookieHandler);
export default handler;

View File

@@ -1,9 +1,8 @@
const dns = require('dns');
const dnsPromises = dns.promises;
const axios = require('axios');
const commonMiddleware = require('./_common/middleware');
import { promises as dnsPromises, lookup } from 'dns';
import axios from 'axios';
import middleware from './_common/middleware.js';
const handler = async (url) => {
const dnsHandler = async (url) => {
try {
const domain = url.replace(/^(?:https?:\/\/)?/i, "");
const addresses = await dnsPromises.resolve4(domain);
@@ -41,4 +40,7 @@ const handler = async (url) => {
}
};
exports.handler = commonMiddleware(handler);
export const handler = middleware(dnsHandler);
export default handler;

View File

@@ -1,8 +1,8 @@
const dns = require('dns');
const util = require('util');
const middleware = require('./_common/middleware');
import dns from 'dns';
import util from 'util';
import middleware from './_common/middleware.js';
const handler = async (url) => {
const dnsHandler = async (url) => {
let hostname = url;
// Handle URLs by extracting hostname
@@ -51,4 +51,5 @@ const handler = async (url) => {
}
};
exports.handler = middleware(handler);
export const handler = middleware(dnsHandler);
export default handler;

View File

@@ -1,7 +1,7 @@
const https = require('https');
const commonMiddleware = require('./_common/middleware'); // Make sure this path is correct
import https from 'https';
import middleware from './_common/middleware.js';
const fetchDNSRecords = async (domain, event, context) => {
const dnsSecHandler = async (domain) => {
const dnsTypes = ['DNSKEY', 'DS', 'RRSIG'];
const records = {};
@@ -25,7 +25,11 @@ const fetchDNSRecords = async (domain, event, context) => {
});
res.on('end', () => {
resolve(JSON.parse(data));
try {
resolve(JSON.parse(data));
} catch (error) {
reject(new Error('Invalid JSON response'));
}
});
res.on('error', error => {
@@ -49,4 +53,5 @@ const fetchDNSRecords = async (domain, event, context) => {
return records;
};
exports.handler = commonMiddleware(fetchDNSRecords);
export const handler = middleware(dnsSecHandler);
export default handler;

View File

@@ -1,7 +1,7 @@
const https = require('https');
const middleware = require('./_common/middleware');
import https from 'https';
import middleware from './_common/middleware.js';
const builtWithHandler = async (url) => {
const featuresHandler = async (url) => {
const apiKey = process.env.BUILT_WITH_API_KEY;
if (!url) {
@@ -45,4 +45,5 @@ const builtWithHandler = async (url) => {
}
};
exports.handler = middleware(builtWithHandler);
export const handler = middleware(featuresHandler);
export default handler;

View File

@@ -1,5 +1,5 @@
const axios = require('axios');
const middleware = require('./_common/middleware');
import axios from 'axios';
import middleware from './_common/middleware.js';
const hasWaf = (waf) => {
return {
@@ -7,7 +7,7 @@ const hasWaf = (waf) => {
}
};
const handler = async (url) => {
const firewallHandler = async (url) => {
const fullUrl = url.startsWith('http') ? url : `http://${url}`;
try {
@@ -91,6 +91,14 @@ const handler = async (url) => {
return hasWaf('IBM WebSphere DataPower');
}
if (headers['server'] && headers['server'].includes('QRATOR')) {
return hasWaf('QRATOR WAF');
}
if (headers['server'] && headers['server'].includes('ddos-guard')) {
return hasWaf('DDoS-Guard WAF');
}
return {
hasWaf: false,
}
@@ -102,4 +110,5 @@ const handler = async (url) => {
}
};
exports.handler = middleware(handler);
export const handler = middleware(firewallHandler);
export default handler;

View File

@@ -1,5 +1,5 @@
const dns = require('dns');
const middleware = require('./_common/middleware');
import dns from 'dns';
import middleware from './_common/middleware.js';
const lookupAsync = (address) => {
return new Promise((resolve, reject) => {
@@ -13,9 +13,11 @@ const lookupAsync = (address) => {
});
};
const handler = async (url) => {
const ipHandler = async (url) => {
const address = url.replaceAll('https://', '').replaceAll('http://', '');
return await lookupAsync(address);
};
exports.handler = middleware(handler);
export const handler = middleware(ipHandler);
export default handler;

View File

@@ -1,7 +1,7 @@
const axios = require('axios');
const middleware = require('./_common/middleware');
import axios from 'axios';
import middleware from './_common/middleware.js';
const handler = async (url, event, context) => {
const headersHandler = async (url, event, context) => {
try {
const response = await axios.get(url, {
validateStatus: function (status) {
@@ -15,4 +15,5 @@ const handler = async (url, event, context) => {
}
};
exports.handler = middleware(handler);
export const handler = middleware(headersHandler);
export default handler;

View File

@@ -1,18 +1,15 @@
const https = require('https');
const middleware = require('./_common/middleware');
import https from 'https';
import middleware from './_common/middleware.js';
exports.handler = middleware(async (url, event, context) => {
const hstsHandler = async (url, event, context) => {
const errorResponse = (message, statusCode = 500) => {
return {
statusCode: statusCode,
body: JSON.stringify({ error: message }),
};
};
const hstsIncompatible = (message, statusCode = 200) => {
return {
statusCode: statusCode,
body: JSON.stringify({ message, compatible: false }),
};
const hstsIncompatible = (message, compatible = false, hstsHeader = null ) => {
return { message, compatible, hstsHeader };
};
@@ -35,14 +32,7 @@ exports.handler = middleware(async (url, event, context) => {
} else if (!preload) {
resolve(hstsIncompatible(`HSTS header does not contain the preload directive.`));
} else {
resolve({
statusCode: 200,
body: JSON.stringify({
message: "Site is compatible with the HSTS preload list!",
compatible: true,
hstsHeader: hstsHeader,
}),
});
resolve(hstsIncompatible(`Site is compatible with the HSTS preload list!`, true, hstsHeader));
}
}
});
@@ -53,5 +43,7 @@ exports.handler = middleware(async (url, event, context) => {
req.end();
});
});
};
export const handler = middleware(hstsHandler);
export default handler;

View File

@@ -1,14 +1,14 @@
const axios = require('axios');
const middleware = require('./_common/middleware');
import axios from 'axios';
import middleware from './_common/middleware.js';
const handler = async (url) => {
const httpsSecHandler = async (url) => {
const fullUrl = url.startsWith('http') ? url : `http://${url}`;
try {
const response = await axios.get(fullUrl);
const headers = response.headers;
return {
strictTransportPolicy: headers['strict-transport-policy'] ? true : false,
strictTransportPolicy: headers['strict-transport-security'] ? true : false,
xFrameOptions: headers['x-frame-options'] ? true : false,
xContentTypeOptions: headers['x-content-type-options'] ? true : false,
xXSSProtection: headers['x-xss-protection'] ? true : false,
@@ -22,4 +22,5 @@ const handler = async (url) => {
}
};
exports.handler = middleware(handler);
export const handler = middleware(httpsSecHandler);
export default handler;

View File

@@ -1,8 +1,8 @@
const axios = require('axios');
const unzipper = require('unzipper');
const csv = require('csv-parser');
const fs = require('fs');
const middleware = require('./_common/middleware');
import axios from 'axios';
import unzipper from 'unzipper';
import csv from 'csv-parser';
import fs from 'fs';
import middleware from './_common/middleware.js';
// Should also work with the following sources:
// https://www.domcop.com/files/top/top10milliondomains.csv.zip
@@ -14,7 +14,7 @@ const middleware = require('./_common/middleware');
const FILE_URL = 'https://s3-us-west-1.amazonaws.com/umbrella-static/top-1m.csv.zip';
const TEMP_FILE_PATH = '/tmp/top-1m.csv';
const handler = async (url) => {
const rankHandler = async (url) => {
let domain = null;
try {
@@ -66,5 +66,5 @@ return new Promise((resolve, reject) => {
});
};
exports.handler = middleware(handler);
export const handler = middleware(rankHandler);
export default handler;

View File

@@ -1,9 +1,9 @@
const axios = require('axios');
const cheerio = require('cheerio');
const urlLib = require('url');
const commonMiddleware = require('./_common/middleware');
import axios from 'axios';
import cheerio from 'cheerio';
import urlLib from 'url';
import middleware from './_common/middleware.js';
const handler = async (url) => {
const linkedPagesHandler = async (url) => {
const response = await axios.get(url);
const html = response.data;
const $ = cheerio.load(html);
@@ -33,16 +33,17 @@ const handler = async (url) => {
if (internalLinks.length === 0 && externalLinks.length === 0) {
return {
statusCode: 400,
body: JSON.stringify({
body: {
skipped: 'No internal or external links found. '
+ 'This may be due to the website being dynamically rendered, using a client-side framework (like React), and without SSR enabled. '
+ 'That would mean that the static HTML returned from the HTTP request doesn\'t contain any meaningful content for Web-Check to analyze. '
+ 'You can rectify this by using a headless browser to render the page instead.',
}),
},
};
}
return { internal: internalLinks, external: externalLinks };
};
exports.handler = commonMiddleware(handler);
export const handler = middleware(linkedPagesHandler);
export default handler;

View File

@@ -1,9 +1,10 @@
const commonMiddleware = require('./_common/middleware');
import dns from 'dns';
import URL from 'url-parse';
import middleware from './_common/middleware.js';
const dns = require('dns').promises;
const URL = require('url-parse');
// TODO: Fix.
const handler = async (url, event, context) => {
const mailConfigHandler = async (url, event, context) => {
try {
const domain = new URL(url).hostname || new URL(url).pathname;
@@ -54,6 +55,11 @@ const handler = async (url, event, context) => {
if (yahooMx.length > 0) {
mailServices.push({ provider: 'Yahoo', value: yahooMx[0].exchange });
}
// Check MX records for Mimecast
const mimecastMx = mxRecords.filter(record => record.exchange.includes('mimecast.com'));
if (mimecastMx.length > 0) {
mailServices.push({ provider: 'Mimecast', value: mimecastMx[0].exchange });
}
return {
mxRecords,
@@ -66,10 +72,11 @@ const handler = async (url, event, context) => {
} else {
return {
statusCode: 500,
body: JSON.stringify({ error: error.message }),
body: { error: error.message },
};
}
}
};
module.exports.handler = commonMiddleware(handler);
export const handler = middleware(mailConfigHandler);
export default handler;

View File

@@ -1,13 +1,18 @@
const net = require('net');
const middleware = require('./_common/middleware');
import net from 'net';
import middleware from './_common/middleware.js';
// A list of commonly used ports.
const PORTS = [
const DEFAULT_PORTS_TO_CHECK = [
20, 21, 22, 23, 25, 53, 80, 67, 68, 69,
110, 119, 123, 143, 156, 161, 162, 179, 194,
389, 443, 587, 993, 995,
3000, 3306, 3389, 5060, 5900, 8000, 8080, 8888
];
/*
* Checks if the env PORTS_TO_CHECK is set, if so the string is split via "," to get an array of ports to check.
* If the env is not set, return the default commonly used ports.
*/
const PORTS = process.env.PORTS_TO_CHECK ? process.env.PORTS_TO_CHECK.split(",") : DEFAULT_PORTS_TO_CHECK
async function checkPort(port, domain) {
return new Promise((resolve, reject) => {
@@ -34,7 +39,7 @@ async function checkPort(port, domain) {
});
}
const handler = async (url, event, context) => {
const portsHandler = async (url, event, context) => {
const domain = url.replace(/(^\w+:|^)\/\//, '');
const delay = ms => new Promise(res => setTimeout(res, ms));
@@ -72,18 +77,17 @@ const handler = async (url, event, context) => {
if(timeoutReached){
return errorResponse('The function timed out before completing.');
}
return {
statusCode: 200,
body: JSON.stringify({ openPorts, failedPorts }),
};
// Sort openPorts and failedPorts before returning
openPorts.sort((a, b) => a - b);
failedPorts.sort((a, b) => a - b);
return { openPorts, failedPorts };
};
const errorResponse = (message, statusCode = 444) => {
return {
statusCode: statusCode,
body: JSON.stringify({ error: message }),
};
return { error: message };
};
exports.handler = middleware(handler);
export const handler = middleware(portsHandler);
export default handler;

View File

@@ -1,22 +1,22 @@
const axios = require('axios');
const middleware = require('./_common/middleware');
import axios from 'axios';
import middleware from './_common/middleware.js';
const handler = async (url, event, context) => {
const qualityHandler = async (url, event, context) => {
const apiKey = process.env.GOOGLE_CLOUD_API_KEY;
if (!url) {
throw new Error('URL param is required');
}
if (!apiKey) {
throw new Error('API key (GOOGLE_CLOUD_API_KEY) not set');
throw new Error(
'Missing Google API. You need to set the `GOOGLE_CLOUD_API_KEY` environment variable'
);
}
const endpoint = `https://www.googleapis.com/pagespeedonline/v5/runPagespeed?url=${encodeURIComponent(url)}&category=PERFORMANCE&category=ACCESSIBILITY&category=BEST_PRACTICES&category=SEO&category=PWA&strategy=mobile&key=${apiKey}`;
const endpoint = `https://www.googleapis.com/pagespeedonline/v5/runPagespeed?`
+ `url=${encodeURIComponent(url)}&category=PERFORMANCE&category=ACCESSIBILITY`
+ `&category=BEST_PRACTICES&category=SEO&category=PWA&strategy=mobile`
+ `&key=${apiKey}`;
const response = await axios.get(endpoint);
return response.data;
return (await axios.get(endpoint)).data;
};
exports.handler = middleware(handler);
export const handler = middleware(qualityHandler);
export default handler;

View File

@@ -1,7 +1,7 @@
const axios = require('axios');
const middleware = require('./_common/middleware');
import axios from 'axios';
import middleware from './_common/middleware.js';
const handler = async (url) => {
const rankHandler = async (url) => {
const domain = url ? new URL(url).hostname : null;
if (!domain) throw new Error('Invalid URL');
@@ -10,7 +10,7 @@ const handler = async (url) => {
{ auth: { username: process.env.TRANCO_USERNAME, password: process.env.TRANCO_API_KEY } }
: {};
const response = await axios.get(
`https://tranco-list.eu/api/ranks/domain/${domain}`, { timeout: 2000 }, auth,
`https://tranco-list.eu/api/ranks/domain/${domain}`, { timeout: 5000 }, auth,
);
if (!response.data || !response.data.ranks || response.data.ranks.length === 0) {
return { skipped: `Skipping, as ${domain} isn't ranked in the top 100 million sites yet.`};
@@ -21,4 +21,6 @@ const handler = async (url) => {
}
};
exports.handler = middleware(handler);
export const handler = middleware(rankHandler);
export default handler;

View File

@@ -1,9 +1,10 @@
const handler = async (url) => {
const redirects = [url];
const got = await import('got');
import got from 'got';
import middleware from './_common/middleware.js';
const redirectsHandler = async (url) => {
const redirects = [url];
try {
await got.default(url, {
await got(url, {
followRedirect: true,
maxRedirects: 12,
hooks: {
@@ -23,5 +24,5 @@ const handler = async (url) => {
}
};
const middleware = require('./_common/middleware');
exports.handler = middleware(handler);
export const handler = middleware(redirectsHandler);
export default handler;

View File

@@ -1,5 +1,5 @@
const axios = require('axios');
const middleware = require('./_common/middleware');
import axios from 'axios';
import middleware from './_common/middleware.js';
const parseRobotsTxt = (content) => {
const lines = content.split('\n');
@@ -31,7 +31,7 @@ const parseRobotsTxt = (content) => {
return { robots: rules };
}
const handler = async function(url) {
const robotsHandler = async function(url) {
let parsedURL;
try {
parsedURL = new URL(url);
@@ -67,4 +67,5 @@ const handler = async function(url) {
}
};
exports.handler = middleware(handler);
export const handler = middleware(robotsHandler);
export default handler;

View File

@@ -1,40 +1,116 @@
const puppeteer = require('puppeteer-core');
const chromium = require('chrome-aws-lambda');
const middleware = require('./_common/middleware');
import puppeteer from 'puppeteer-core';
import chromium from 'chrome-aws-lambda';
import middleware from './_common/middleware.js';
import { execFile } from 'child_process';
import { promises as fs } from 'fs';
import path from 'path';
import pkg from 'uuid';
const { v4: uuidv4 } = pkg;
// Helper function for direct chromium screenshot as fallback
const directChromiumScreenshot = async (url) => {
console.log(`[DIRECT-SCREENSHOT] Starting direct screenshot process for URL: ${url}`);
// Create a tmp filename
const tmpDir = '/tmp';
const uuid = uuidv4();
const screenshotPath = path.join(tmpDir, `screenshot-${uuid}.png`);
console.log(`[DIRECT-SCREENSHOT] Will save screenshot to: ${screenshotPath}`);
return new Promise((resolve, reject) => {
const chromePath = process.env.CHROME_PATH || '/usr/bin/chromium';
const args = [
'--headless',
'--disable-gpu',
'--no-sandbox',
`--screenshot=${screenshotPath}`,
url
];
console.log(`[DIRECT-SCREENSHOT] Executing: ${chromePath} ${args.join(' ')}`);
execFile(chromePath, args, async (error, stdout, stderr) => {
if (error) {
console.error(`[DIRECT-SCREENSHOT] Chromium error: ${error.message}`);
return reject(error);
}
try {
// Read the screenshot file
const screenshotData = await fs.readFile(screenshotPath);
console.log(`[DIRECT-SCREENSHOT] Screenshot read successfully`);
// Convert to base64
const base64Data = screenshotData.toString('base64');
await fs.unlink(screenshotPath).catch(err =>
console.warn(`[DIRECT-SCREENSHOT] Failed to delete temp file: ${err.message}`)
);
resolve(base64Data);
} catch (readError) {
console.error(`[DIRECT-SCREENSHOT] Failed reading screenshot: ${readError.message}`);
reject(readError);
}
});
});
};
const screenshotHandler = async (targetUrl) => {
console.log(`[SCREENSHOT] Request received for URL: ${targetUrl}`);
if (!targetUrl) {
console.error('[SCREENSHOT] URL is missing from queryStringParameters');
throw new Error('URL is missing from queryStringParameters');
}
if (!targetUrl.startsWith('http://') && !targetUrl.startsWith('https://')) {
targetUrl = 'http://' + targetUrl;
}
try {
new URL(targetUrl);
} catch (error) {
console.error(`[SCREENSHOT] URL provided is invalid: ${targetUrl}`);
throw new Error('URL provided is invalid');
}
// First try direct Chromium
try {
console.log(`[SCREENSHOT] Using direct Chromium method for URL: ${targetUrl}`);
const base64Screenshot = await directChromiumScreenshot(targetUrl);
console.log(`[SCREENSHOT] Direct screenshot successful`);
return { image: base64Screenshot };
} catch (directError) {
console.error(`[SCREENSHOT] Direct screenshot method failed: ${directError.message}`);
console.log(`[SCREENSHOT] Falling back to puppeteer method...`);
}
// fall back puppeteer
let browser = null;
try {
browser = await puppeteer.launch({
args: chromium.args,
console.log(`[SCREENSHOT] Launching puppeteer browser`);
browser = await puppeteer.launch({
args: [...chromium.args, '--no-sandbox'], // Add --no-sandbox flag
defaultViewport: { width: 800, height: 600 },
executablePath: process.env.CHROME_PATH || await chromium.executablePath,
headless: chromium.headless,
executablePath: process.env.CHROME_PATH || '/usr/bin/chromium',
headless: true,
ignoreHTTPSErrors: true,
ignoreDefaultArgs: ['--disable-extensions'],
});
console.log(`[SCREENSHOT] Creating new page`);
let page = await browser.newPage();
console.log(`[SCREENSHOT] Setting page preferences`);
await page.emulateMediaFeatures([{ name: 'prefers-color-scheme', value: 'dark' }]);
page.setDefaultNavigationTimeout(8000);
console.log(`[SCREENSHOT] Navigating to URL: ${targetUrl}`);
await page.goto(targetUrl, { waitUntil: 'domcontentloaded' });
console.log(`[SCREENSHOT] Checking if body element exists`);
await page.evaluate(() => {
const selector = 'body';
return new Promise((resolve, reject) => {
@@ -45,17 +121,25 @@ const screenshotHandler = async (targetUrl) => {
resolve();
});
});
console.log(`[SCREENSHOT] Taking screenshot`);
const screenshotBuffer = await page.screenshot();
console.log(`[SCREENSHOT] Converting screenshot to base64`);
const base64Screenshot = screenshotBuffer.toString('base64');
console.log(`[SCREENSHOT] Screenshot complete, returning image`);
return { image: base64Screenshot };
} catch (error) {
console.error(`[SCREENSHOT] Puppeteer screenshot failed: ${error.message}`);
throw error;
} finally {
if (browser !== null) {
console.log(`[SCREENSHOT] Closing browser`);
await browser.close();
}
}
};
exports.handler = middleware(screenshotHandler);
export const handler = middleware(screenshotHandler);
export default handler;

View File

@@ -1,6 +1,8 @@
const { https } = require('follow-redirects');
const { URL } = require('url');
const middleware = require('./_common/middleware');
import { URL } from 'url';
import followRedirects from 'follow-redirects';
import middleware from './_common/middleware.js';
const { https } = followRedirects;
const SECURITY_TXT_PATHS = [
'/security.txt',
@@ -69,8 +71,6 @@ const securityTxtHandler = async (urlParam) => {
return { isPresent: false };
};
exports.handler = middleware(securityTxtHandler);
async function fetchSecurityTxt(baseURL, path) {
return new Promise((resolve, reject) => {
const url = new URL(path, baseURL);
@@ -91,3 +91,6 @@ async function fetchSecurityTxt(baseURL, path) {
});
});
}
export const handler = middleware(securityTxtHandler);
export default handler;

View File

@@ -1,20 +1,21 @@
const commonMiddleware = require('./_common/middleware');
import axios from 'axios';
import xml2js from 'xml2js';
import middleware from './_common/middleware.js';
const axios = require('axios');
const xml2js = require('xml2js');
const handler = async (url) => {
const sitemapHandler = async (url) => {
let sitemapUrl = `${url}/sitemap.xml`;
const hardTimeOut = 5000;
try {
// Try to fetch sitemap directly
let sitemapRes;
try {
sitemapRes = await axios.get(sitemapUrl, { timeout: 5000 });
sitemapRes = await axios.get(sitemapUrl, { timeout: hardTimeOut });
} catch (error) {
if (error.response && error.response.status === 404) {
// If sitemap not found, try to fetch it from robots.txt
const robotsRes = await axios.get(`${url}/robots.txt`, { timeout: 5000 });
const robotsRes = await axios.get(`${url}/robots.txt`, { timeout: hardTimeOut });
const robotsTxt = robotsRes.data.split('\n');
for (let line of robotsTxt) {
@@ -25,13 +26,10 @@ const handler = async (url) => {
}
if (!sitemapUrl) {
return {
statusCode: 404,
body: JSON.stringify({ skipped: 'No sitemap found' }),
};
return { skipped: 'No sitemap found' };
}
sitemapRes = await axios.get(sitemapUrl, { timeout: 5000 });
sitemapRes = await axios.get(sitemapUrl, { timeout: hardTimeOut });
} else {
throw error; // If other error, throw it
}
@@ -40,25 +38,16 @@ const handler = async (url) => {
const parser = new xml2js.Parser();
const sitemap = await parser.parseStringPromise(sitemapRes.data);
return {
statusCode: 200,
body: JSON.stringify(sitemap),
};
return sitemap;
} catch (error) {
// If error occurs
console.log(error.message);
if (error.code === 'ECONNABORTED') {
return {
statusCode: 500,
body: JSON.stringify({ error: 'Request timed out' }),
};
return { error: `Request timed-out after ${hardTimeOut}ms` };
} else {
return {
statusCode: 500,
body: JSON.stringify({ error: error.message }),
};
return { error: error.message };
}
}
};
exports.handler = commonMiddleware(handler);
export const handler = middleware(sitemapHandler);
export default handler;

View File

@@ -1,9 +1,8 @@
const commonMiddleware = require('./_common/middleware');
import axios from 'axios';
import cheerio from 'cheerio';
import middleware from './_common/middleware.js';
const axios = require('axios');
const cheerio = require('cheerio');
const handler = async (url) => {
const socialTagsHandler = async (url) => {
// Check if url includes protocol
if (!url.startsWith('http://') && !url.startsWith('https://')) {
@@ -50,16 +49,9 @@ const handler = async (url) => {
};
if (Object.keys(metadata).length === 0) {
return {
statusCode: 200,
body: JSON.stringify({ skipped: 'No metadata found' }),
};
return { skipped: 'No metadata found' };
}
return {
statusCode: 200,
body: JSON.stringify(metadata),
};
return metadata;
} catch (error) {
return {
statusCode: 500,
@@ -68,4 +60,5 @@ const handler = async (url) => {
}
};
exports.handler = commonMiddleware(handler);
export const handler = middleware(socialTagsHandler);
export default handler;

View File

@@ -1,7 +1,7 @@
const tls = require('tls');
const middleware = require('./_common/middleware');
import tls from 'tls';
import middleware from './_common/middleware.js';
const fetchSiteCertificateHandler = async (urlString) => {
const sslHandler = async (urlString) => {
try {
const parsedUrl = new URL(urlString);
const options = {
@@ -40,4 +40,5 @@ const fetchSiteCertificateHandler = async (urlString) => {
}
};
exports.handler = middleware(fetchSiteCertificateHandler);
export const handler = middleware(sslHandler);
export default handler;

View File

@@ -1,8 +1,8 @@
const https = require('https');
const { performance, PerformanceObserver } = require('perf_hooks');
const middleware = require('./_common/middleware');
import https from 'https';
import { performance, PerformanceObserver } from 'perf_hooks';
import middleware from './_common/middleware.js';
const checkURLHandler = async (url) => {
const statusHandler = async (url) => {
if (!url) {
throw new Error('You must provide a URL query parameter!');
}
@@ -55,4 +55,5 @@ const checkURLHandler = async (url) => {
}
};
exports.handler = middleware(checkURLHandler);
export const handler = middleware(statusHandler);
export default handler;

View File

@@ -1,7 +1,7 @@
const Wappalyzer = require('wappalyzer');
const middleware = require('./_common/middleware');
import Wappalyzer from 'wappalyzer';
import middleware from './_common/middleware.js';
const analyzeSiteTechnologies = async (url) => {
const techStackHandler = async (url) => {
const options = {};
const wappalyzer = new Wappalyzer(options);
@@ -27,4 +27,5 @@ const analyzeSiteTechnologies = async (url) => {
}
};
exports.handler = middleware(analyzeSiteTechnologies);
export const handler = middleware(techStackHandler);
export default handler;

View File

@@ -1,10 +1,13 @@
const axios = require('axios');
const xml2js = require('xml2js');
const middleware = require('./_common/middleware');
import axios from 'axios';
import xml2js from 'xml2js';
import middleware from './_common/middleware.js';
const getGoogleSafeBrowsingResult = async (url) => {
try {
const apiKey = process.env.GOOGLE_CLOUD_API_KEY;
if (!apiKey) {
return { error: 'GOOGLE_CLOUD_API_KEY is required for the Google Safe Browsing check' };
}
const apiEndpoint = `https://safebrowsing.googleapis.com/v4/threatMatches:find?key=${apiKey}`;
const requestBody = {
@@ -63,11 +66,15 @@ const getPhishTankResult = async (url) => {
}
const getCloudmersiveResult = async (url) => {
const apiKey = process.env.CLOUDMERSIVE_API_KEY;
if (!apiKey) {
return { error: 'CLOUDMERSIVE_API_KEY is required for the Cloudmersive check' };
}
try {
const endpoint = 'https://api.cloudmersive.com/virus/scan/website';
const headers = {
'Content-Type': 'application/x-www-form-urlencoded',
'Apikey': process.env.CLOUDMERSIVE_API_KEY,
'Apikey': apiKey,
};
const data = `Url=${encodeURIComponent(url)}`;
const response = await axios.post(endpoint, data, { headers });
@@ -77,7 +84,7 @@ const getCloudmersiveResult = async (url) => {
}
};
const handler = async (url) => {
const threatsHandler = async (url) => {
try {
const urlHaus = await getUrlHausResult(url);
const phishTank = await getPhishTankResult(url);
@@ -92,4 +99,5 @@ const handler = async (url) => {
}
};
exports.handler = middleware(handler);
export const handler = middleware(threatsHandler);
export default handler;

View File

@@ -1,9 +1,9 @@
const axios = require('axios');
const middleware = require('./_common/middleware');
import axios from 'axios';
import middleware from './_common/middleware.js';
const MOZILLA_TLS_OBSERVATORY_API = 'https://tls-observatory.services.mozilla.com/api/v1';
const handler = async (url) => {
const tlsHandler = async (url) => {
try {
const domain = new URL(url).hostname;
const scanResponse = await axios.post(`${MOZILLA_TLS_OBSERVATORY_API}/scan?target=${domain}`);
@@ -12,17 +12,18 @@ const handler = async (url) => {
if (typeof scanId !== 'number') {
return {
statusCode: 500,
body: JSON.stringify({ error: 'Failed to get scan_id from TLS Observatory' }),
body: { error: 'Failed to get scan_id from TLS Observatory' },
};
}
const resultResponse = await axios.get(`${MOZILLA_TLS_OBSERVATORY_API}/results?id=${scanId}`);
return {
statusCode: 200,
body: JSON.stringify(resultResponse.data),
body: resultResponse.data,
};
} catch (error) {
return { error: error.message };
}
};
exports.handler = middleware(handler);
export const handler = middleware(tlsHandler);
export default handler;

View File

@@ -1,8 +1,8 @@
const traceroute = require('traceroute');
const url = require('url');
const middleware = require('./_common/middleware');
import url from 'url';
import traceroute from 'traceroute';
import middleware from './_common/middleware.js';
const executeTraceroute = async (urlString, context) => {
const traceRouteHandler = async (urlString, context) => {
// Parse the URL and get the hostname
const urlObject = url.parse(urlString);
const host = urlObject.hostname;
@@ -28,4 +28,5 @@ const executeTraceroute = async (urlString, context) => {
};
};
exports.handler = middleware(executeTraceroute);
export const handler = middleware(traceRouteHandler);
export default handler;

View File

@@ -1,7 +1,7 @@
const dns = require('dns').promises;
const middleware = require('./_common/middleware');
import dns from 'dns/promises';
import middleware from './_common/middleware.js';
const handler = async (url, event, context) => {
const txtRecordHandler = async (url, event, context) => {
try {
const parsedUrl = new URL(url);
@@ -29,4 +29,5 @@ const handler = async (url, event, context) => {
}
};
exports.handler = middleware(handler);
export const handler = middleware(txtRecordHandler);
export default handler;

View File

@@ -1,7 +1,7 @@
const net = require('net');
const psl = require('psl');
const axios = require('axios');
const middleware = require('./_common/middleware');
import net from 'net';
import psl from 'psl';
import axios from 'axios';
import middleware from './_common/middleware.js';
const getBaseDomain = (url) => {
let protocol = '';
@@ -83,7 +83,7 @@ const fetchFromMyAPI = async (hostname) => {
}
};
const fetchWhoisData = async (url) => {
const whoisHandler = async (url) => {
if (!url.startsWith('http://') && !url.startsWith('https://')) {
url = 'http://' + url;
}
@@ -106,4 +106,6 @@ const fetchWhoisData = async (url) => {
};
};
exports.handler = middleware(fetchWhoisData);
export const handler = middleware(whoisHandler);
export default handler;

79
astro.config.mjs Normal file
View File

@@ -0,0 +1,79 @@
import { defineConfig } from 'astro/config';
// Integrations
import svelte from '@astrojs/svelte';
import react from "@astrojs/react";
import partytown from '@astrojs/partytown';
import sitemap from '@astrojs/sitemap';
// Adapters
import vercelAdapter from '@astrojs/vercel/serverless';
import netlifyAdapter from '@astrojs/netlify';
import nodeAdapter from '@astrojs/node';
import cloudflareAdapter from '@astrojs/cloudflare';
// Helper function to unwrap both Vite and Node environment variables
const unwrapEnvVar = (varName, fallbackValue) => {
const classicEnvVar = process?.env && process.env[varName];
const viteEnvVar = import.meta.env[varName];
return classicEnvVar || viteEnvVar || fallbackValue;
}
// Determine the deploy target (vercel, netlify, cloudflare, node)
const deployTarget = unwrapEnvVar('PLATFORM', 'node').toLowerCase();
// Determine the output mode (server, hybrid or static)
const output = unwrapEnvVar('OUTPUT', 'hybrid');
// The FQDN of where the site is hosted (used for sitemaps & canonical URLs)
const site = unwrapEnvVar('SITE_URL', 'https://web-check.xyz');
// The base URL of the site (if serving from a subdirectory)
const base = unwrapEnvVar('BASE_URL', '/');
// Should run the app in boss-mode (requires extra configuration)
const isBossServer = unwrapEnvVar('BOSS_SERVER', false);
// Initialize Astro integrations
const integrations = [svelte(), react(), partytown(), sitemap()];
// Set the appropriate adapter, based on the deploy target
function getAdapter(target) {
switch(target) {
case 'vercel':
return vercelAdapter();
case 'netlify':
return netlifyAdapter();
case 'cloudflare':
return cloudflareAdapter();
case 'node':
return nodeAdapter({ mode: 'middleware' });
default:
throw new Error(`Unsupported deploy target: ${target}`);
}
}
const adapter = getAdapter(deployTarget);
// Print build information to console
console.log(
`\n\x1b[1m\x1b[35m Preparing to start build of Web Check.... \x1b[0m\n`,
`\x1b[35m\x1b[2mCompiling for "${deployTarget}" using "${output}" mode, `
+ `to deploy to "${site}" at "${base}"\x1b[0m\n`,
`\x1b[2m\x1b[36m🛟 For documentation and support, visit the GitHub repo: ` +
`https://github.com/lissy93/web-check \n`,
`💖 Found Web-Check useful? Consider sponsoring us on GitHub ` +
`to help fund maintenance & development.\x1b[0m\n`,
);
const redirects = {
'/about': '/check/about',
};
// Skip the marketing homepage for self-hosted users
if (!isBossServer && isBossServer !== true) {
redirects['/'] = '/check';
}
// Export Astro configuration
export default defineConfig({ output, base, integrations, site, adapter, redirects });

17
fly.toml Normal file
View File

@@ -0,0 +1,17 @@
app = 'web-check'
primary_region = 'lhr'
[build]
[http_service]
internal_port = 3000
force_https = true
auto_stop_machines = true
auto_start_machines = true
min_machines_running = 0
processes = ['app']
[[vm]]
memory = '1gb'
cpu_kind = 'shared'
cpus = 1

View File

@@ -2,11 +2,13 @@
[build]
base = "/"
command = "yarn build"
publish = "build"
publish = "dist"
functions = "api"
# Environmental variables and optioanl secrets
# Environmental variables and optional secrets
[build.environment]
PLATFORM = "netlify"
PUBLIC_API_ENDPOINT = "/.netlify/functions"
# Build configuration env vars (uncomment if you want to conigure these)
# CI="false" # Set CI to false, to prevent warnings from exiting the build
# CHROME_PATH='/usr/bin/chromium' # Path to Chromium binary
@@ -25,12 +27,6 @@
status = 301
force = true
# For router history mode, ensure pages land on index
[[redirects]]
from = "/*"
to = "/index.html"
status = 200
# Plugins
[[plugins]]
package = "netlify-plugin-chromium"

View File

@@ -1,100 +1,73 @@
{
"name": "web-check",
"version": "1.0.0",
"private": false,
"description": "All-in-one OSINT tool for analyzing any website",
"repository": "github:lissy93/web-check",
"homepage": "https://web-check.as93.net",
"license": "MIT",
"author": {
"name": "Alicia Sykes",
"email": "alicia@omg.lol"
},
"funding": {
"type": "github",
"url": "https://github.com/sponsors/Lissy93"
},
"type": "module",
"version": "2.0.2",
"homepage": "https://web-check.xyz",
"scripts": {
"dev": "netlify dev",
"serve": "node server",
"start": "react-scripts start",
"build": "react-scripts build",
"test": "react-scripts test",
"eject": "react-scripts eject"
"start": "node server",
"start-pm": "pm2 start server.js -i max",
"build": "astro check && astro build",
"dev:vercel": "PLATFORM='vercel' npx vercel dev",
"dev:netlify": "PLATFORM='netlify' npx netlify dev",
"dev:api": "DISABLE_GUI='true' PORT='3001' nodemon server",
"dev:astro": "PUBLIC_API_ENDPOINT=http://localhost:3001/api astro dev",
"dev": "concurrently -c magenta,cyan -n backend,frontend 'yarn dev:api' 'yarn dev:astro'"
},
"dependencies": {
"@netlify/functions": "^1.6.0",
"@sentry/react": "^7.60.0",
"@testing-library/jest-dom": "^5.17.0",
"@testing-library/react": "^14.0.0",
"@testing-library/user-event": "^14.4.3",
"@types/jest": "^29.5.3",
"@types/node": "^20.4.4",
"@types/react": "^18.2.15",
"@types/react-dom": "^18.2.7",
"@types/react-router-dom": "^5.3.3",
"@types/react-simple-maps": "^3.0.0",
"@types/styled-components": "^5.1.26",
"aws-serverless-express": "^3.4.0",
"axios": "^1.4.0",
"@astrojs/check": "^0.5.10",
"@astrojs/react": "^3.3.2",
"@emotion/react": "^11.11.4",
"@emotion/styled": "^11.11.5",
"@fortawesome/fontawesome-svg-core": "^6.5.2",
"@fortawesome/free-brands-svg-icons": "^6.5.2",
"@fortawesome/free-regular-svg-icons": "^6.5.2",
"@fortawesome/free-solid-svg-icons": "^6.5.2",
"@fortawesome/svelte-fontawesome": "^0.2.2",
"@types/react": "^18.3.1",
"@types/react-dom": "^18.3.0",
"astro": "^4.7.1",
"axios": "^1.4.8",
"cheerio": "^1.0.0-rc.12",
"chrome-aws-lambda": "^10.1.0",
"chromium": "^3.0.3",
"connect-history-api-fallback": "^2.0.0",
"cors": "^2.8.5",
"csv-parser": "^3.0.0",
"dotenv": "^16.3.1",
"flatted": "^3.2.7",
"follow-redirects": "^1.15.2",
"got": "^13.0.0",
"jest-styled-components": "^7.1.1",
"netlify-cli": "^15.9.1",
"perf_hooks": "^0.0.1",
"dotenv": "^16.4.5",
"express": "^4.19.2",
"express-rate-limit": "^7.2.0",
"framer-motion": "^11.2.6",
"got": "^14.2.1",
"pm2": "^5.3.1",
"psl": "^1.9.0",
"puppeteer": "^20.9.0",
"puppeteer-core": "^21.0.3",
"react": "^18.2.0",
"react-dom": "^18.2.0",
"puppeteer": "^22.8.0",
"puppeteer-core": "^22.8.0",
"react": "^18.3.1",
"react-dom": "^18.3.1",
"react-masonry-css": "^1.0.16",
"react-router-dom": "^6.14.2",
"react-scripts": "5.0.1",
"react-router-dom": "^6.23.0",
"react-simple-maps": "^3.0.0",
"react-toastify": "^9.1.3",
"recharts": "^2.7.3",
"styled-components": "^6.0.5",
"react-toastify": "^10.0.5",
"recharts": "^2.12.6",
"svelte": "^4.2.17",
"traceroute": "^1.0.0",
"typescript": "^5.1.6",
"unzipper": "^0.10.14",
"typescript": "^5.4.5",
"unzipper": "^0.11.5",
"url-parse": "^1.5.10",
"wappalyzer": "^6.10.65",
"web-vitals": "^3.4.0",
"xml2js": "^0.6.2"
},
"eslintConfig": {
"extends": [
"react-app",
"react-app/jest"
]
},
"browserslist": {
"production": [
">0.2%",
"not dead",
"not op_mini all"
],
"development": [
"last 1 chrome version",
"last 1 firefox version",
"last 1 safari version"
]
},
"compilerOptions": {
"allowJs": true,
"outDir": "./dist"
},
"devDependencies": {
"serverless-domain-manager": "^7.1.1",
"serverless-offline": "^12.0.4",
"serverless-webpack": "^5.13.0",
"webpack": "^5.88.2",
"webpack-node-externals": "^3.0.0"
"@astrojs/cloudflare": "^10.2.5",
"@astrojs/netlify": "^5.2.0",
"@astrojs/node": "^8.2.5",
"@astrojs/partytown": "^2.1.0",
"@astrojs/sitemap": "^3.1.4",
"@astrojs/svelte": "^5.4.0",
"@astrojs/ts-plugin": "^1.6.1",
"@astrojs/vercel": "^7.5.4",
"concurrently": "^8.2.2",
"nodemon": "^3.1.0",
"sass": "^1.77.1"
}
}

View File

@@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="205" height="20" role="img" aria-label="DockerHub: Lissy93/Web Check"><title>DockerHub: Lissy93/Web Check</title><linearGradient id="s" x2="0" y2="100%"><stop offset="0" stop-color="#bbb" stop-opacity=".1"/><stop offset="1" stop-opacity=".1"/></linearGradient><clipPath id="r"><rect width="205" height="20" rx="3" fill="#fff"/></clipPath><g clip-path="url(#r)"><rect width="88" height="20" fill="#1c1d28"/><rect x="88" width="117" height="20" fill="#1fb1f4"/><rect width="205" height="20" fill="url(#s)"/></g><g fill="#fff" text-anchor="middle" font-family="Verdana,Geneva,DejaVu Sans,sans-serif" text-rendering="geometricPrecision" font-size="110"><image x="5" y="3" width="14" height="14" xlink:href="data:image/svg+xml;base64,PHN2ZyBmaWxsPSJ3aGl0ZSIgcm9sZT0iaW1nIiB2aWV3Qm94PSIwIDAgMjQgMjQiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyI+PHRpdGxlPkRvY2tlcjwvdGl0bGU+PHBhdGggZD0iTTEzLjk4MyAxMS4wNzhoMi4xMTlhLjE4Ni4xODYgMCAwMC4xODYtLjE4NVY5LjAwNmEuMTg2LjE4NiAwIDAwLS4xODYtLjE4NmgtMi4xMTlhLjE4NS4xODUgMCAwMC0uMTg1LjE4NXYxLjg4OGMwIC4xMDIuMDgzLjE4NS4xODUuMTg1bS0yLjk1NC01LjQzaDIuMTE4YS4xODYuMTg2IDAgMDAuMTg2LS4xODZWMy41NzRhLjE4Ni4xODYgMCAwMC0uMTg2LS4xODVoLTIuMTE4YS4xODUuMTg1IDAgMDAtLjE4NS4xODV2MS44ODhjMCAuMTAyLjA4Mi4xODUuMTg1LjE4NW0wIDIuNzE2aDIuMTE4YS4xODcuMTg3IDAgMDAuMTg2LS4xODZWNi4yOWEuMTg2LjE4NiAwIDAwLS4xODYtLjE4NWgtMi4xMThhLjE4NS4xODUgMCAwMC0uMTg1LjE4NXYxLjg4N2MwIC4xMDIuMDgyLjE4NS4xODUuMTg2bS0yLjkzIDBoMi4xMmEuMTg2LjE4NiAwIDAwLjE4NC0uMTg2VjYuMjlhLjE4NS4xODUgMCAwMC0uMTg1LS4xODVIOC4xYS4xODUuMTg1IDAgMDAtLjE4NS4xODV2MS44ODdjMCAuMTAyLjA4My4xODUuMTg1LjE4Nm0tMi45NjQgMGgyLjExOWEuMTg2LjE4NiAwIDAwLjE4NS0uMTg2VjYuMjlhLjE4NS4xODUgMCAwMC0uMTg1LS4xODVINS4xMzZhLjE4Ni4xODYgMCAwMC0uMTg2LjE4NXYxLjg4N2MwIC4xMDIuMDg0LjE4NS4xODYuMTg2bTUuODkzIDIuNzE1aDIuMTE4YS4xODYuMTg2IDAgMDAuMTg2LS4xODVWOS4wMDZhLjE4Ni4xODYgMCAwMC0uMTg2LS4xODZoLTIuMTE4YS4xODUuMTg1IDAgMDAtLjE4NS4xODV2MS44ODhjMCAuMTAyLjA4Mi4xODUuMTg1LjE4NW0tMi45MyAwaDIuMTJhLjE4NS4xODUgMCAwMC4xODQtLjE4NVY5LjAwNmEuMTg1LjE4NSAwIDAwLS4xODQtLjE4NmgtMi4xMmEuMTg1LjE4NSAwIDAwLS4xODQuMTg1djEuODg4YzAgLjEwMi4wODMuMTg1LjE4NS4xODVtLTIuOTY0IDBoMi4xMTlhLjE4NS4xODUgMCAwMC4xODUtLjE4NVY5LjAwNmEuMTg1LjE4NSAwIDAwLS4xODQtLjE4NmgtMi4xMmEuMTg2LjE4NiAwIDAwLS4xODYuMTg2djEuODg3YzAgLjEwMi4wODQuMTg1LjE4Ni4xODVtLTIuOTIgMGgyLjEyYS4xODUuMTg1IDAgMDAuMTg0LS4xODVWOS4wMDZhLjE4NS4xODUgMCAwMC0uMTg0LS4xODZoLTIuMTJhLjE4NS4xODUgMCAwMC0uMTg0LjE4NXYxLjg4OGMwIC4xMDIuMDgyLjE4NS4xODUuMTg1TTIzLjc2MyA5Ljg5Yy0uMDY1LS4wNTEtLjY3Mi0uNTEtMS45NTQtLjUxLS4zMzguMDAxLS42NzYuMDMtMS4wMS4wODctLjI0OC0xLjctMS42NTMtMi41My0xLjcxNi0yLjU2NmwtLjM0NC0uMTk5LS4yMjYuMzI3Yy0uMjg0LjQzOC0uNDkuOTIyLS42MTIgMS40My0uMjMuOTctLjA5IDEuODgyLjQwMyAyLjY2MS0uNTk1LjMzMi0xLjU1LjQxMy0xLjc0NC40MkguNzUxYS43NTEuNzUxIDAgMDAtLjc1Ljc0OCAxMS4zNzYgMTEuMzc2IDAgMDAuNjkyIDQuMDYyYy41NDUgMS40MjggMS4zNTUgMi40OCAyLjQxIDMuMTI0IDEuMTguNzIzIDMuMSAxLjEzNyA1LjI3NSAxLjEzNy45ODMuMDAzIDEuOTYzLS4wODYgMi45My0uMjY2YTEyLjI0OCAxMi4yNDggMCAwMDMuODIzLTEuMzg5Yy45OC0uNTY3IDEuODYtMS4yODggMi42MS0yLjEzNiAxLjI1Mi0xLjQxOCAxLjk5OC0yLjk5NyAyLjU1My00LjRoLjIyMWMxLjM3MiAwIDIuMjE1LS41NDkgMi42OC0xLjAwOS4zMDktLjI5My41NS0uNjUuNzA3LTEuMDQ2bC4wOTgtLjI4OFoiLz48L3N2Zz4="/><text aria-hidden="true" x="535" y="150" fill="#010101" fill-opacity=".3" transform="scale(.1)" textLength="610">DockerHub</text><text x="535" y="140" transform="scale(.1)" fill="#fff" textLength="610">DockerHub</text><text aria-hidden="true" x="1455" y="150" fill="#010101" fill-opacity=".3" transform="scale(.1)" textLength="1070">Lissy93/Web Check</text><text x="1455" y="140" transform="scale(.1)" fill="#fff" textLength="1070">Lissy93/Web Check</text></g></svg>

After

Width:  |  Height:  |  Size: 3.6 KiB

View File

@@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="181" height="20" role="img" aria-label="GitHub: Lissy93/Web Check"><title>GitHub: Lissy93/Web Check</title><linearGradient id="s" x2="0" y2="100%"><stop offset="0" stop-color="#bbb" stop-opacity=".1"/><stop offset="1" stop-opacity=".1"/></linearGradient><clipPath id="r"><rect width="181" height="20" rx="3" fill="#fff"/></clipPath><g clip-path="url(#r)"><rect width="64" height="20" fill="#1c1d28"/><rect x="64" width="117" height="20" fill="#a832fc"/><rect width="181" height="20" fill="url(#s)"/></g><g fill="#fff" text-anchor="middle" font-family="Verdana,Geneva,DejaVu Sans,sans-serif" text-rendering="geometricPrecision" font-size="110"><image x="5" y="3" width="14" height="14" xlink:href="data:image/svg+xml;base64,PHN2ZyBmaWxsPSJ3aGl0ZSIgcm9sZT0iaW1nIiB2aWV3Qm94PSIwIDAgMjQgMjQiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyI+PHRpdGxlPkdpdEh1YjwvdGl0bGU+PHBhdGggZD0iTTEyIC4yOTdjLTYuNjMgMC0xMiA1LjM3My0xMiAxMiAwIDUuMzAzIDMuNDM4IDkuOCA4LjIwNSAxMS4zODUuNi4xMTMuODItLjI1OC44Mi0uNTc3IDAtLjI4NS0uMDEtMS4wNC0uMDE1LTIuMDQtMy4zMzguNzI0LTQuMDQyLTEuNjEtNC4wNDItMS42MUM0LjQyMiAxOC4wNyAzLjYzMyAxNy43IDMuNjMzIDE3LjdjLTEuMDg3LS43NDQuMDg0LS43MjkuMDg0LS43MjkgMS4yMDUuMDg0IDEuODM4IDEuMjM2IDEuODM4IDEuMjM2IDEuMDcgMS44MzUgMi44MDkgMS4zMDUgMy40OTUuOTk4LjEwOC0uNzc2LjQxNy0xLjMwNS43Ni0xLjYwNS0yLjY2NS0uMy01LjQ2Ni0xLjMzMi01LjQ2Ni01LjkzIDAtMS4zMS40NjUtMi4zOCAxLjIzNS0zLjIyLS4xMzUtLjMwMy0uNTQtMS41MjMuMTA1LTMuMTc2IDAgMCAxLjAwNS0uMzIyIDMuMyAxLjIzLjk2LS4yNjcgMS45OC0uMzk5IDMtLjQwNSAxLjAyLjAwNiAyLjA0LjEzOCAzIC40MDUgMi4yOC0xLjU1MiAzLjI4NS0xLjIzIDMuMjg1LTEuMjMuNjQ1IDEuNjUzLjI0IDIuODczLjEyIDMuMTc2Ljc2NS44NCAxLjIzIDEuOTEgMS4yMyAzLjIyIDAgNC42MS0yLjgwNSA1LjYyNS01LjQ3NSA1LjkyLjQyLjM2LjgxIDEuMDk2LjgxIDIuMjIgMCAxLjYwNi0uMDE1IDIuODk2LS4wMTUgMy4yODYgMCAuMzE1LjIxLjY5LjgyNS41N0MyMC41NjUgMjIuMDkyIDI0IDE3LjU5MiAyNCAxMi4yOTdjMC02LjYyNy01LjM3My0xMi0xMi0xMiIvPjwvc3ZnPg=="/><text aria-hidden="true" x="415" y="150" fill="#010101" fill-opacity=".3" transform="scale(.1)" textLength="370">GitHub</text><text x="415" y="140" transform="scale(.1)" fill="#fff" textLength="370">GitHub</text><text aria-hidden="true" x="1215" y="150" fill="#010101" fill-opacity=".3" transform="scale(.1)" textLength="1070">Lissy93/Web Check</text><text x="1215" y="140" transform="scale(.1)" fill="#fff" textLength="1070">Lissy93/Web Check</text></g></svg>

After

Width:  |  Height:  |  Size: 2.3 KiB

View File

@@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="147" height="20" role="img" aria-label="Sponsor: Alicia Sykes"><title>Sponsor: Alicia Sykes</title><linearGradient id="s" x2="0" y2="100%"><stop offset="0" stop-color="#bbb" stop-opacity=".1"/><stop offset="1" stop-opacity=".1"/></linearGradient><clipPath id="r"><rect width="147" height="20" rx="3" fill="#fff"/></clipPath><g clip-path="url(#r)"><rect width="72" height="20" fill="#1c1d28"/><rect x="72" width="75" height="20" fill="#f2159a"/><rect width="147" height="20" fill="url(#s)"/></g><g fill="#fff" text-anchor="middle" font-family="Verdana,Geneva,DejaVu Sans,sans-serif" text-rendering="geometricPrecision" font-size="110"><image x="5" y="3" width="14" height="14" xlink:href="data:image/svg+xml;base64,PHN2ZyBmaWxsPSJ3aGl0ZSIgcm9sZT0iaW1nIiB2aWV3Qm94PSIwIDAgMjQgMjQiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyI+PHRpdGxlPkdpdEh1YiBTcG9uc29yczwvdGl0bGU+PHBhdGggZD0iTTE3LjYyNSAxLjQ5OWMtMi4zMiAwLTQuMzU0IDEuMjAzLTUuNjI1IDMuMDMtMS4yNzEtMS44MjctMy4zMDUtMy4wMy01LjYyNS0zLjAzQzMuMTI5IDEuNDk5IDAgNC4yNTMgMCA4LjI0OWMwIDQuMjc1IDMuMDY4IDcuODQ3IDUuODI4IDEwLjIyN2EzMy4xNCAzMy4xNCAwIDAgMCA1LjYxNiAzLjg3NmwuMDI4LjAxNy4wMDguMDAzLS4wMDEuMDAzYy4xNjMuMDg1LjM0Mi4xMjYuNTIxLjEyNS4xNzkuMDAxLjM1OC0uMDQxLjUyMS0uMTI1bC0uMDAxLS4wMDMuMDA4LS4wMDMuMDI4LS4wMTdhMzMuMTQgMzMuMTQgMCAwIDAgNS42MTYtMy44NzZDMjAuOTMyIDE2LjA5NiAyNCAxMi41MjQgMjQgOC4yNDljMC0zLjk5Ni0zLjEyOS02Ljc1LTYuMzc1LTYuNzV6bS0uOTE5IDE1LjI3NWEzMC43NjYgMzAuNzY2IDAgMCAxLTQuNzAzIDMuMzE2bC0uMDA0LS4wMDItLjAwNC4wMDJhMzAuOTU1IDMwLjk1NSAwIDAgMS00LjcwMy0zLjMxNmMtMi42NzctMi4zMDctNS4wNDctNS4yOTgtNS4wNDctOC41MjMgMC0yLjc1NCAyLjEyMS00LjUgNC4xMjUtNC41IDIuMDYgMCAzLjkxNCAxLjQ3OSA0LjU0NCAzLjY4NC4xNDMuNDk1LjU5Ni43OTcgMS4wODYuNzk2LjQ5LjAwMS45NDMtLjMwMiAxLjA4NS0uNzk2LjYzLTIuMjA1IDIuNDg0LTMuNjg0IDQuNTQ0LTMuNjg0IDIuMDA0IDAgNC4xMjUgMS43NDYgNC4xMjUgNC41IDAgMy4yMjUtMi4zNyA2LjIxNi01LjA0OCA4LjUyM3oiLz48L3N2Zz4="/><text aria-hidden="true" x="455" y="150" fill="#010101" fill-opacity=".3" transform="scale(.1)" textLength="450">Sponsor</text><text x="455" y="140" transform="scale(.1)" fill="#fff" textLength="450">Sponsor</text><text aria-hidden="true" x="1085" y="150" fill="#010101" fill-opacity=".3" transform="scale(.1)" textLength="650">Alicia Sykes</text><text x="1085" y="140" transform="scale(.1)" fill="#fff" textLength="650">Alicia Sykes</text></g></svg>

After

Width:  |  Height:  |  Size: 2.3 KiB

View File

@@ -0,0 +1 @@
<svg xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" width="155" height="20" role="img" aria-label="Website: web-check.xyz"><title>Website: web-check.xyz</title><linearGradient id="s" x2="0" y2="100%"><stop offset="0" stop-color="#bbb" stop-opacity=".1"/><stop offset="1" stop-opacity=".1"/></linearGradient><clipPath id="r"><rect width="155" height="20" rx="3" fill="#fff"/></clipPath><g clip-path="url(#r)"><rect width="70" height="20" fill="#1c1d28"/><rect x="70" width="85" height="20" fill="#9fef00"/><rect width="155" height="20" fill="url(#s)"/></g><g fill="#fff" text-anchor="middle" font-family="Verdana,Geneva,DejaVu Sans,sans-serif" text-rendering="geometricPrecision" font-size="110"><image x="5" y="3" width="14" height="14" xlink:href="data:image/svg+xml;base64,PHN2ZyBmaWxsPSJ3aGl0ZSIgcm9sZT0iaW1nIiB2aWV3Qm94PSIwIDAgMjQgMjQiIHhtbG5zPSJodHRwOi8vd3d3LnczLm9yZy8yMDAwL3N2ZyI+PHRpdGxlPkdvb2dsZSBDbG91ZCBTdG9yYWdlPC90aXRsZT48cGF0aCBkPSJNMjQgMi40djguNGgtMi40VjIuNEgyNHpNMCAxMC44aDIuNFYyLjRIMHY4LjR6bTMtOC40aDE4djguNEgzVjIuNHptMTIuNiA0LjJhMS44IDEuOCAwIDEgMCAzLjYgMCAxLjggMS44IDAgMCAwLTMuNiAwem0tMTAuOC42SDEyVjZINC44djEuMnptMTYuOCAxNC40SDI0di04LjRoLTIuNHY4LjR6TTAgMjEuNmgyLjR2LTguNEgwdjguNHptMy04LjRoMTh2OC40SDN2LTguNHptMTIuNiA0LjJhMS44IDEuOCAwIDEgMCAzLjYgMCAxLjggMS44IDAgMCAwLTMuNiAwek00LjggMThIMTJ2LTEuMkg0LjhWMTh6Ii8+PC9zdmc+"/><text aria-hidden="true" x="445" y="150" fill="#010101" fill-opacity=".3" transform="scale(.1)" textLength="430">Website</text><text x="445" y="140" transform="scale(.1)" fill="#fff" textLength="430">Website</text><text aria-hidden="true" x="1115" y="150" fill="#ccc" fill-opacity=".3" transform="scale(.1)" textLength="750">web-check.xyz</text><text x="1115" y="140" transform="scale(.1)" fill="#333" textLength="750">webcheck.zyz</text></g></svg>

After

Width:  |  Height:  |  Size: 1.8 KiB

View File

@@ -0,0 +1,9 @@
<svg width="100%" height="100%" xmlns="http://www.w3.org/2000/svg">
<defs>
<pattern id="a" patternUnits="userSpaceOnUse" width="30" height="30">
<rect width="100%" height="100%" fill="var(--background, #111211)" />
<circle cx="5" cy="5" r="1.75" fill="var(--background-lighter, #3A3B3A)" opacity="0.3" />
</pattern>
</defs>
<rect width="100%" height="100%" fill="url(#a)" />
</svg>

After

Width:  |  Height:  |  Size: 408 B

View File

@@ -0,0 +1 @@
<svg role="img" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"><title>Docker</title><path d="M13.983 11.078h2.119a.186.186 0 00.186-.185V9.006a.186.186 0 00-.186-.186h-2.119a.185.185 0 00-.185.185v1.888c0 .102.083.185.185.185m-2.954-5.43h2.118a.186.186 0 00.186-.186V3.574a.186.186 0 00-.186-.185h-2.118a.185.185 0 00-.185.185v1.888c0 .102.082.185.185.185m0 2.716h2.118a.187.187 0 00.186-.186V6.29a.186.186 0 00-.186-.185h-2.118a.185.185 0 00-.185.185v1.887c0 .102.082.185.185.186m-2.93 0h2.12a.186.186 0 00.184-.186V6.29a.185.185 0 00-.185-.185H8.1a.185.185 0 00-.185.185v1.887c0 .102.083.185.185.186m-2.964 0h2.119a.186.186 0 00.185-.186V6.29a.185.185 0 00-.185-.185H5.136a.186.186 0 00-.186.185v1.887c0 .102.084.185.186.186m5.893 2.715h2.118a.186.186 0 00.186-.185V9.006a.186.186 0 00-.186-.186h-2.118a.185.185 0 00-.185.185v1.888c0 .102.082.185.185.185m-2.93 0h2.12a.185.185 0 00.184-.185V9.006a.185.185 0 00-.184-.186h-2.12a.185.185 0 00-.184.185v1.888c0 .102.083.185.185.185m-2.964 0h2.119a.185.185 0 00.185-.185V9.006a.185.185 0 00-.184-.186h-2.12a.186.186 0 00-.186.186v1.887c0 .102.084.185.186.185m-2.92 0h2.12a.185.185 0 00.184-.185V9.006a.185.185 0 00-.184-.186h-2.12a.185.185 0 00-.184.185v1.888c0 .102.082.185.185.185M23.763 9.89c-.065-.051-.672-.51-1.954-.51-.338.001-.676.03-1.01.087-.248-1.7-1.653-2.53-1.716-2.566l-.344-.199-.226.327c-.284.438-.49.922-.612 1.43-.23.97-.09 1.882.403 2.661-.595.332-1.55.413-1.744.42H.751a.751.751 0 00-.75.748 11.376 11.376 0 00.692 4.062c.545 1.428 1.355 2.48 2.41 3.124 1.18.723 3.1 1.137 5.275 1.137.983.003 1.963-.086 2.93-.266a12.248 12.248 0 003.823-1.389c.98-.567 1.86-1.288 2.61-2.136 1.252-1.418 1.998-2.997 2.553-4.4h.221c1.372 0 2.215-.549 2.68-1.009.309-.293.55-.65.707-1.046l.098-.288Z"/></svg>

After

Width:  |  Height:  |  Size: 1.7 KiB

File diff suppressed because one or more lines are too long

After

Width:  |  Height:  |  Size: 6.2 KiB

View File

@@ -0,0 +1 @@
<svg role="img" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"><title>GitHub</title><path d="M12 .297c-6.63 0-12 5.373-12 12 0 5.303 3.438 9.8 8.205 11.385.6.113.82-.258.82-.577 0-.285-.01-1.04-.015-2.04-3.338.724-4.042-1.61-4.042-1.61C4.422 18.07 3.633 17.7 3.633 17.7c-1.087-.744.084-.729.084-.729 1.205.084 1.838 1.236 1.838 1.236 1.07 1.835 2.809 1.305 3.495.998.108-.776.417-1.305.76-1.605-2.665-.3-5.466-1.332-5.466-5.93 0-1.31.465-2.38 1.235-3.22-.135-.303-.54-1.523.105-3.176 0 0 1.005-.322 3.3 1.23.96-.267 1.98-.399 3-.405 1.02.006 2.04.138 3 .405 2.28-1.552 3.285-1.23 3.285-1.23.645 1.653.24 2.873.12 3.176.765.84 1.23 1.91 1.23 3.22 0 4.61-2.805 5.625-5.475 5.92.42.36.81 1.096.81 2.22 0 1.606-.015 2.896-.015 3.286 0 .315.21.69.825.57C20.565 22.092 24 17.592 24 12.297c0-6.627-5.373-12-12-12"/></svg>

After

Width:  |  Height:  |  Size: 823 B

View File

@@ -0,0 +1 @@
<svg role="img" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"><title>Netlify</title><path d="M6.49 19.04h-.23L5.13 17.9v-.23l1.73-1.71h1.2l.15.15v1.2L6.5 19.04ZM5.13 6.31V6.1l1.13-1.13h.23L8.2 6.68v1.2l-.15.15h-1.2L5.13 6.31Zm9.96 9.09h-1.65l-.14-.13v-3.83c0-.68-.27-1.2-1.1-1.23-.42 0-.9 0-1.43.02l-.07.08v4.96l-.14.14H8.9l-.13-.14V8.73l.13-.14h3.7a2.6 2.6 0 0 1 2.61 2.6v4.08l-.13.14Zm-8.37-2.44H.14L0 12.82v-1.64l.14-.14h6.58l.14.14v1.64l-.14.14Zm17.14 0h-6.58l-.14-.14v-1.64l.14-.14h6.58l.14.14v1.64l-.14.14ZM11.05 6.55V1.64l.14-.14h1.65l.14.14v4.9l-.14.14h-1.65l-.14-.13Zm0 15.81v-4.9l.14-.14h1.65l.14.13v4.91l-.14.14h-1.65l-.14-.14Z"/></svg>

After

Width:  |  Height:  |  Size: 657 B

View File

@@ -0,0 +1 @@
<svg role="img" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"><title>Swagger</title><path d="M12 0C5.383 0 0 5.383 0 12s5.383 12 12 12c6.616 0 12-5.383 12-12S18.616 0 12 0zm0 1.144c5.995 0 10.856 4.86 10.856 10.856 0 5.995-4.86 10.856-10.856 10.856-5.996 0-10.856-4.86-10.856-10.856C1.144 6.004 6.004 1.144 12 1.144zM8.37 5.868a6.707 6.707 0 0 0-.423.005c-.983.056-1.573.517-1.735 1.472-.115.665-.096 1.348-.143 2.017-.013.35-.05.697-.115 1.038-.134.609-.397.798-1.016.83a2.65 2.65 0 0 0-.244.042v1.463c1.126.055 1.278.452 1.37 1.629.033.429-.013.858.015 1.287.018.406.073.808.156 1.2.259 1.075 1.307 1.435 2.575 1.218v-1.283c-.203 0-.383.005-.558 0-.43-.013-.591-.12-.632-.535-.056-.535-.042-1.08-.075-1.62-.064-1.001-.175-1.988-1.153-2.625.503-.37.868-.812.983-1.398.083-.41.134-.821.166-1.237.028-.415-.023-.84.014-1.25.06-.665.102-.937.9-.91.12 0 .235-.017.369-.027v-1.31c-.16 0-.31-.004-.454-.006zm7.593.009a4.247 4.247 0 0 0-.813.06v1.274c.245 0 .434 0 .623.005.328.004.577.13.61.494.032.332.031.669.064 1.006.065.669.101 1.347.217 2.007.102.544.475.95.941 1.283-.817.549-1.057 1.333-1.098 2.215-.023.604-.037 1.213-.069 1.822-.028.554-.222.734-.78.748-.157.004-.31.018-.484.028v1.305c.327 0 .627.019.927 0 .932-.055 1.495-.507 1.68-1.412.078-.498.124-1 .138-1.504.032-.461.028-.927.074-1.384.069-.715.397-1.01 1.112-1.057a.972.972 0 0 0 .199-.046v-1.463c-.12-.014-.204-.027-.291-.032-.536-.023-.804-.203-.937-.71a5.146 5.146 0 0 1-.152-.993c-.037-.618-.033-1.241-.074-1.86-.08-1.192-.794-1.753-1.887-1.786zm-6.89 5.28a.844.844 0 0 0-.083 1.684h.055a.83.83 0 0 0 .877-.78v-.046a.845.845 0 0 0-.83-.858zm2.911 0a.808.808 0 0 0-.834.78c0 .027 0 .05.004.078 0 .503.342.826.859.826.507 0 .826-.332.826-.853-.005-.503-.342-.836-.855-.831zm2.963 0a.861.861 0 0 0-.876.835c0 .47.378.849.849.849h.009c.425.074.853-.337.881-.83.023-.457-.392-.854-.863-.854z"/></svg>

After

Width:  |  Height:  |  Size: 1.8 KiB

View File

@@ -0,0 +1 @@
<svg role="img" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"><title>Vercel</title><path d="M24 22.525H0l12-21.05 12 21.05z"/></svg>

After

Width:  |  Height:  |  Size: 142 B

View File

@@ -0,0 +1 @@
<svg role="img" viewBox="0 0 24 24" xmlns="http://www.w3.org/2000/svg"><title>WebAuthn</title><path d="M15.2872 3.641a8.407 8.407 0 00-8.05 7.593h.55a7.805 7.805 0 012.24-4.713 5.825 5.825 0 00.923.695c-.608 1.177-.98 2.556-1.082 4.018h.135c.105-1.467.485-2.819 1.065-3.947.745.434 1.623.754 2.577.94a27.83 27.83 0 00-.25 3.763h-.847v.135h.847c.003 1.334.09 2.617.25 3.764-.954.185-1.832.506-2.577.94a9.997 9.997 0 01-.978-3.137h-.137c.164 1.16.502 2.25.997 3.208a5.825 5.825 0 00-.924.695 7.805 7.805 0 01-2.255-4.875h-.55a8.407 8.407 0 0016.779-.675 8.398 8.398 0 00-.689-3.333 8.407 8.407 0 00-8.025-5.072zm.315.546c.155 0 .31.005.464.014.365.34.708 1.07.983 2.114a16.518 16.518 0 01.357 1.79 10.173 10.173 0 01-1.804.16 10.173 10.173 0 01-1.805-.16 16.519 16.519 0 01.357-1.79c.275-1.045.618-1.775.983-2.114a7.97 7.97 0 01.465-.014zm-.665.028c-.345.392-.658 1.093-.913 2.065a16.639 16.639 0 00-.36 1.8c-.939-.183-1.802-.498-2.533-.926.686-1.283 1.635-2.264 2.73-2.775a7.874 7.874 0 011.076-.164zm1.33 0a7.856 7.856 0 011.084.168c1.092.513 2.037 1.492 2.721 2.771-.73.428-1.594.743-2.533.927a16.64 16.64 0 00-.36-1.8c-.255-.972-.568-1.673-.912-2.066zm-2.972.314c-.655.407-1.257.989-1.776 1.73a8.166 8.166 0 00-.506.825 5.69 5.69 0 01-.89-.67 7.814 7.814 0 013.172-1.885zm4.624.006a7.862 7.862 0 013.164 1.877 5.692 5.692 0 01-.893.672 8.166 8.166 0 00-.506-.825c-.516-.738-1.115-1.318-1.765-1.724zm3.26 1.985a7.858 7.858 0 011.638 2.419 7.802 7.802 0 01.642 3.051h-2.095c-.01-1.74-.398-3.396-1.11-4.774a5.823 5.823 0 00.925-.696zm-1.044.767c.68 1.32 1.084 2.945 1.094 4.703h-3.42a27.863 27.863 0 00-.25-3.763c.953-.186 1.832-.506 2.576-.94zm-6.357.965a10.299 10.299 0 001.824.16 10.299 10.299 0 001.823-.16c.16 1.138.246 2.413.25 3.738h-1.179a1.03 1.03 0 01-.093.135h1.27a27.71 27.71 0 01-.248 3.739 10.397 10.397 0 00-3.647 0 27.733 27.733 0 01-.248-3.739h1.294a.99.99 0 01-.09-.135h-1.204c.003-1.325.088-2.6.248-3.738zm-11.22 1.129a2.585 2.585 0 00-2.547 2.35c-.142 1.541 1.064 2.842 2.566 2.842 1.26 0 2.312-.917 2.533-2.124h4.44v.972h.946v-.972h.837v1.431h.945v-2.376h-7.168a2.586 2.586 0 00-2.552-2.123zm-.058.965a1.639 1.639 0 011.707 1.637 1.64 1.64 0 01-1.639 1.638 1.639 1.639 0 01-.068-3.275zm13.09.388a.75.75 0 00-.345 1.404l-.383 1.958h1.5l-.383-1.958a.75.75 0 00.384-.654.75.75 0 00-.773-.75zm2.218 1.391h3.421c-.01 1.758-.415 3.384-1.094 4.704-.744-.434-1.623-.755-2.577-.94a27.81 27.81 0 00.25-3.764zm3.556 0h2.095a7.805 7.805 0 01-2.28 5.47 5.825 5.825 0 00-.925-.696c.712-1.378 1.1-3.033 1.11-4.774zm-5.52 3.703a10.284 10.284 0 011.562.156 16.518 16.518 0 01-.357 1.791c-.275 1.045-.618 1.774-.982 2.114a7.972 7.972 0 01-.93 0c-.365-.34-.708-1.07-.983-2.114a16.519 16.519 0 01-.357-1.79 10.284 10.284 0 012.048-.157zm1.695.181c.94.184 1.803.5 2.533.926-.686 1.284-1.635 2.265-2.73 2.776a7.874 7.874 0 01-1.075.164c.344-.393.657-1.094.913-2.065a16.64 16.64 0 00.36-1.8zm-3.874 0a16.648 16.648 0 00.36 1.8c.254.973.567 1.674.912 2.066a7.873 7.873 0 01-1.075-.164c-1.096-.511-2.045-1.492-2.73-2.775.73-.428 1.593-.743 2.533-.927zm-2.652.997a8.16 8.16 0 00.506.825c.52.741 1.121 1.323 1.776 1.73a7.814 7.814 0 01-3.174-1.884 5.694 5.694 0 01.892-.67zm9.178 0a5.694 5.694 0 01.891.67 7.814 7.814 0 01-3.173 1.885c.654-.407 1.256-.989 1.775-1.73a8.16 8.16 0 00.507-.825z"/></svg>

After

Width:  |  Height:  |  Size: 3.2 KiB

39
public/error.html Normal file
View File

@@ -0,0 +1,39 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Web-Check</title>
</head>
<body>
<section>
<a class="t" href="/"><h1><img src="https://i.ibb.co/q1gZN2p/web-check-logo.png" width="48" />Web-Check</h1></a>
<p class="moji">😪</p>
<p>There was an error finding this route.</p>
<span>Docs and Source: <a href="https://github.com/lissy93/web-check">github.com/lissy93/web-check</a></span>
</section>
<style>
body { background: #141d2b; color: #fff; }
h1 {
color: #9fef00; text-shadow: #0f1620 2px 2px 0px;
font-size: 3rem; margin: 1rem auto; flex-wrap: wrap;
display: flex; align-items: flex-start; gap: 1rem;
}
section {
display: flex; flex-direction: column; align-items: center; margin: 1rem; gap: 0.5rem;
background: #1a2332; box-shadow: #0f1620 4px 4px 0px; border-radius: 8px; padding: 1rem;
max-width: 800px; margin: 1rem auto;
}
p { font-size: 1.2rem; }
a { color: #9fef00; font-family: monospace; }
a.t { text-decoration: none; margin: 0;}
span { opacity: 0.8; font-size: 0.85rem; }
h1 {
font-family: PTMono, Ubuntu, Fira Sans, Helvetica, sans-serif;
}
p, span, a, section, div { font-family: source-code-pro, Menlo, Monaco, Consolas, 'Courier New', monospace; }
code { color: #9fef00cc;}
.moji { font-size: 8rem; margin: 0; }
</style>
</body>
</html>

6
public/favicon.svg Normal file
View File

@@ -0,0 +1,6 @@
<svg xmlns="http://www.w3.org/2000/svg" fill="none" viewBox="8.424 15.685618729096989 38.844 37.92642140468227" style="max-height: 500px" width="38.844" height="37.92642140468227">
<path stroke-linejoin="round" stroke-linecap="round" stroke-width="2.8" stroke="white" d="M43.3 30.1V20.3C43.3 19.9287 43.1525 19.5726 42.89 19.31C42.6274 19.0475 42.2713 18.9 41.9 18.9H13.9C13.5287 18.9 13.1726 19.0475 12.9101 19.31C12.6475 19.5726 12.5 19.9287 12.5 20.3V30.1C12.5 46.9 27.9 51.1 27.9 51.1C27.9 51.1 43.3 46.9 43.3 30.1Z"/>
<path stroke-linejoin="round" stroke-linecap="round" stroke-width="2.8" stroke="#D6FB41" d="M20.8999 34.3L25.0999 38.5L34.8999 28.7"/>
<path fill="white" d="M60.07 45.5L55.78 23.63H61.6L63.76 37.82L64.12 40.28H64.36L67.66 23.63H73.7801L77.08 40.28H77.35L77.62 38.21L79.7801 23.63H85.63L81.4001 45.5H73.72L71.1701 33.05L70.84 31.22H70.63L70.3 33.05L67.72 45.5H60.07ZM94.42 45.8C92.58 45.8 91.05 45.45 89.83 44.75C88.63 44.05 87.72 43.08 87.1 41.84C86.5 40.58 86.2 39.12 86.2 37.46V37.13C86.2 35.39 86.53 33.91 87.19 32.69C87.85 31.47 88.76 30.54 89.92 29.9C91.1 29.26 92.45 28.94 93.97 28.94C95.67 28.94 97.11 29.26 98.29 29.9C99.49 30.52 100.4 31.4 101.02 32.54C101.64 33.68 101.95 35 101.95 36.5V38.72H91.57V39.47C91.57 40.17 91.82 40.74 92.32 41.18C92.82 41.6 93.46 41.81 94.24 41.81C94.94 41.81 95.51 41.67 95.95 41.39C96.39 41.09 96.65 40.7 96.73 40.22H101.77C101.71 41.34 101.36 42.32 100.72 43.16C100.08 43.98 99.22 44.63 98.14 45.11C97.06 45.57 95.82 45.8 94.42 45.8ZM91.57 35.36V35.51H96.73V35.36C96.73 34.5 96.49 33.87 96.01 33.47C95.55 33.05 94.93 32.84 94.15 32.84C93.39 32.84 92.77 33.06 92.29 33.5C91.81 33.92 91.57 34.54 91.57 35.36ZM114.879 45.8C113.859 45.8 112.929 45.58 112.089 45.14C111.269 44.7 110.659 44.08 110.259 43.28H110.019L109.719 45.5H104.709V23.63H110.019V31.49H110.259C110.659 30.69 111.269 30.07 112.089 29.63C112.929 29.17 113.859 28.94 114.879 28.94C116.359 28.94 117.549 29.28 118.449 29.96C119.349 30.62 120.009 31.55 120.429 32.75C120.849 33.95 121.059 35.36 121.059 36.98V37.76C121.059 40.62 120.499 42.68 119.379 43.94C118.259 45.18 116.759 45.8 114.879 45.8ZM112.719 41.51C113.579 41.51 114.239 41.27 114.699 40.79C115.179 40.29 115.419 39.6 115.419 38.72V36.05C115.419 35.17 115.179 34.48 114.699 33.98C114.239 33.48 113.579 33.23 112.719 33.23C111.899 33.23 111.249 33.48 110.769 33.98C110.289 34.46 110.049 35.15 110.049 36.05V38.69C110.049 39.61 110.289 40.31 110.769 40.79C111.249 41.27 111.899 41.51 112.719 41.51Z"/>
<path fill="#D6FB41" d="M133.77 45.8C131.61 45.8 129.77 45.41 128.25 44.63C126.73 43.83 125.56 42.71 124.74 41.27C123.94 39.83 123.54 38.15 123.54 36.23V35.96C123.54 33.38 123.99 31.15 124.89 29.27C125.79 27.37 127.1 25.91 128.82 24.89C130.54 23.85 132.61 23.33 135.03 23.33C136.99 23.33 138.71 23.67 140.19 24.35C141.67 25.01 142.83 25.94 143.67 27.14C144.51 28.34 144.96 29.75 145.02 31.37H139.17C139.05 30.41 138.59 29.64 137.79 29.06C137.01 28.48 136.02 28.19 134.82 28.19C133.4 28.19 132.27 28.52 131.43 29.18C130.59 29.82 130.05 30.83 129.81 32.21L129.24 35.36C128.94 37.1 129.21 38.47 130.05 39.47C130.89 40.45 132.13 40.94 133.77 40.94C134.99 40.94 135.97 40.69 136.71 40.19C137.47 39.67 137.97 38.97 138.21 38.09H144C143.7 39.73 143.08 41.13 142.14 42.29C141.2 43.43 140.01 44.3 138.57 44.9C137.13 45.5 135.53 45.8 133.77 45.8ZM145.633 45.5L149.503 23.63H154.873L153.553 31.19H153.883C154.343 30.49 154.973 29.95 155.773 29.57C156.593 29.17 157.463 28.97 158.383 28.97C160.283 28.97 161.693 29.62 162.613 30.92C163.553 32.2 163.813 34.02 163.393 36.38L161.773 45.5H156.373L157.963 36.47C158.163 35.41 158.063 34.6 157.663 34.04C157.263 33.48 156.603 33.2 155.683 33.2C154.843 33.2 154.173 33.47 153.673 34.01C153.173 34.53 152.843 35.22 152.683 36.08L151.063 45.5H145.633ZM173.599 45.8C171.219 45.8 169.339 45.14 167.959 43.82C166.599 42.5 165.919 40.67 165.919 38.33V38.09C165.919 36.25 166.249 34.65 166.909 33.29C167.569 31.91 168.539 30.85 169.819 30.11C171.099 29.35 172.639 28.97 174.439 28.97C176.179 28.97 177.649 29.32 178.849 30.02C180.069 30.7 180.949 31.67 181.489 32.93C182.049 34.17 182.209 35.63 181.969 37.31L181.759 38.72H171.049C171.049 38.78 171.039 38.85 171.019 38.93C171.019 38.99 171.019 39.06 171.019 39.14C170.899 39.94 171.099 40.59 171.619 41.09C172.139 41.57 172.849 41.81 173.749 41.81C174.429 41.81 174.999 41.68 175.459 41.42C175.939 41.16 176.259 40.78 176.419 40.28H181.489C181.209 41.98 180.379 43.33 178.999 44.33C177.619 45.31 175.819 45.8 173.599 45.8ZM171.679 35.21L171.619 35.51H176.989C177.049 34.63 176.849 33.97 176.389 33.53C175.949 33.07 175.299 32.84 174.439 32.84C173.579 32.84 172.929 33.07 172.489 33.53C172.049 33.97 171.779 34.53 171.679 35.21ZM191.498 45.8C189.098 45.8 187.218 45.14 185.858 43.82C184.518 42.5 183.848 40.75 183.848 38.57V38.33C183.848 36.43 184.178 34.78 184.838 33.38C185.518 31.98 186.488 30.9 187.748 30.14C189.028 29.36 190.568 28.97 192.368 28.97C194.648 28.97 196.478 29.55 197.858 30.71C199.258 31.87 199.988 33.44 200.048 35.42H194.918C194.878 34.68 194.618 34.14 194.138 33.8C193.678 33.46 193.088 33.29 192.368 33.29C191.528 33.29 190.878 33.51 190.418 33.95C189.958 34.37 189.668 34.97 189.548 35.75L189.158 38.15C188.978 39.21 189.118 40.03 189.578 40.61C190.038 41.19 190.738 41.48 191.678 41.48C192.378 41.48 192.958 41.3 193.418 40.94C193.878 40.58 194.178 40.1 194.318 39.5H199.478C199.398 40.76 199.008 41.86 198.308 42.8C197.628 43.74 196.708 44.48 195.548 45.02C194.388 45.54 193.038 45.8 191.498 45.8ZM201.092 45.5L204.932 23.63H210.332L208.232 35.42L214.622 29.27H221.222L214.052 35.69L218.402 45.5H212.552L209.852 38.96L207.212 41.27L206.462 45.5H201.092Z"/>
</svg>

After

Width:  |  Height:  |  Size: 5.5 KiB

Binary file not shown.

Binary file not shown.

View File

@@ -0,0 +1,93 @@
Copyright (c) 2022, GitHub https://github.com/github/hubot-sans
with Reserved Font Name "Hubot Sans"
This Font Software is licensed under the SIL Open Font License, Version 1.1.
This license is copied below, and is also available with a FAQ at:
http://scripts.sil.org/OFL
-----------------------------------------------------------
SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007
-----------------------------------------------------------
PREAMBLE
The goals of the Open Font License (OFL) are to stimulate worldwide
development of collaborative font projects, to support the font creation
efforts of academic and linguistic communities, and to provide a free and
open framework in which fonts may be shared and improved in partnership
with others.
The OFL allows the licensed fonts to be used, studied, modified and
redistributed freely as long as they are not sold by themselves. The
fonts, including any derivative works, can be bundled, embedded,
redistributed and/or sold with any software provided that any reserved
names are not used by derivative works. The fonts and derivatives,
however, cannot be released under any other type of license. The
requirement for fonts to remain under this license does not apply
to any document created using the fonts or their derivatives.
DEFINITIONS
"Font Software" refers to the set of files released by the Copyright
Holder(s) under this license and clearly marked as such. This may
include source files, build scripts and documentation.
"Reserved Font Name" refers to any names specified as such after the
copyright statement(s).
"Original Version" refers to the collection of Font Software components as
distributed by the Copyright Holder(s).
"Modified Version" refers to any derivative made by adding to, deleting,
or substituting — in part or in whole — any of the components of the
Original Version, by changing formats or by porting the Font Software to a
new environment.
"Author" refers to any designer, engineer, programmer, technical
writer or other person who contributed to the Font Software.
PERMISSION & CONDITIONS
Permission is hereby granted, free of charge, to any person obtaining
a copy of the Font Software, to use, study, copy, merge, embed, modify,
redistribute, and sell modified and unmodified copies of the Font
Software, subject to the following conditions:
1) Neither the Font Software nor any of its individual components,
in Original or Modified Versions, may be sold by itself.
2) Original or Modified Versions of the Font Software may be bundled,
redistributed and/or sold with any software, provided that each copy
contains the above copyright notice and this license. These can be
included either as stand-alone text files, human-readable headers or
in the appropriate machine-readable metadata fields within text or
binary files as long as those fields can be easily viewed by the user.
3) No Modified Version of the Font Software may use the Reserved Font
Name(s) unless explicit written permission is granted by the corresponding
Copyright Holder. This restriction only applies to the primary font name as
presented to the users.
4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font
Software shall not be used to promote, endorse or advertise any
Modified Version, except to acknowledge the contribution(s) of the
Copyright Holder(s) and the Author(s) or with their explicit written
permission.
5) The Font Software, modified or unmodified, in part or in whole,
must be distributed entirely under this license, and must not be
distributed under any other license. The requirement for fonts to
remain under this license does not apply to any document created
using the Font Software.
TERMINATION
This license becomes null and void if any of the above conditions are
not met.
DISCLAIMER
THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT
OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE
COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL
DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM
OTHER DEALINGS IN THE FONT SOFTWARE.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

Some files were not shown because too many files have changed in this diff Show More