Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
8 changes: 8 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -47,3 +47,11 @@ and native GitHub squash auto-merge. Sensitive changes remain manual-only.
[Setup, required checks, trust assumptions and first-run procedure](docs/guarded-auto-merge.md)
include the required OpenAI key, branch protection and downstream deployment-event
limitation. Repository settings and production are not changed by installing it.

### Shared asset cache versions

After changing `script.js` or `style.css`, run `npm run assets:version` and commit
the updated HTML files with the asset changes. Each page uses a content-derived
query parameter so browsers and Cloudflare request the matching release assets.
The test suite rejects missing or stale versions. This does not change the
protected deployment process or require a Cloudflare cache purge.
2 changes: 1 addition & 1 deletion cancel.html
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800&display=swap" rel="stylesheet">

<link rel="stylesheet" href="style.css">
<link rel="stylesheet" href="style.css?v=8287724f17f5">
<link rel="icon" href="favicon.png" type="image/png">
</head>
<body>
Expand Down
4 changes: 2 additions & 2 deletions computer-help-henderson.html
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800&display=swap" rel="stylesheet">

<link rel="stylesheet" href="style.css">
<link rel="stylesheet" href="style.css?v=8287724f17f5">
<link rel="icon" href="favicon.png" type="image/png">
<link rel="icon" href="favicon.png" type="image/png" sizes="32x32">

Expand Down Expand Up @@ -138,6 +138,6 @@ <h4 class="footer-title">Support</h4>
</div>
</footer>

<script src="/script.js" defer></script>
<script src="/script.js?v=fb2d384af22c" defer></script>
</body>
</html>
4 changes: 2 additions & 2 deletions custom-pc-builds-henderson.html
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800&display=swap" rel="stylesheet">

<link rel="stylesheet" href="style.css">
<link rel="stylesheet" href="style.css?v=8287724f17f5">
<link rel="icon" href="favicon.png" type="image/png">
<link rel="icon" href="favicon.png" type="image/png" sizes="32x32">

Expand Down Expand Up @@ -138,6 +138,6 @@ <h4 class="footer-title">Support</h4>
</div>
</footer>

<script src="/script.js" defer></script>
<script src="/script.js?v=fb2d384af22c" defer></script>
</body>
</html>
4 changes: 2 additions & 2 deletions index.html
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800&display=swap" rel="stylesheet">

<link rel="stylesheet" href="style.css">
<link rel="stylesheet" href="style.css?v=8287724f17f5">
<link rel="icon" href="favicon.png" type="image/png">
<link rel="icon" href="favicon.png" type="image/png" sizes="32x32">

Expand Down Expand Up @@ -669,6 +669,6 @@ <h4 class="footer-title">Support</h4>
</div>
</footer>

<script src="script.js" defer></script>
<script src="script.js?v=fb2d384af22c" defer></script>
</body>
</html>
1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@
"description": "Dex Tech - Henderson NV Tech Support Website",
"main": "server.js",
"scripts": {
"assets:version": "node scripts/version-static-assets.js",
"test": "node --test test/*.test.js",
"start": "node server.js",
"dev": "node --watch server.js",
Expand Down
2 changes: 1 addition & 1 deletion privacy.html
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
<link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800&display=swap" rel="stylesheet">
<link rel="stylesheet" href="style.css">
<link rel="stylesheet" href="style.css?v=8287724f17f5">
<link rel="icon" href="favicon.png" type="image/png">
<style>
.legal-hero {
Expand Down
15 changes: 15 additions & 0 deletions scripts/version-static-assets.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
// Refresh HTML cache keys after editing shared CSS or JavaScript.
const fs = require('node:fs');
const path = require('node:path');
const { createHash } = require('node:crypto');
const root = path.resolve(__dirname, '..');
const versions = Object.fromEntries(['style.css', 'script.js'].map(file => [
file, createHash('sha256').update(fs.readFileSync(path.join(root, file))).digest('hex').slice(0, 12),
]));
for (const file of fs.readdirSync(root).filter(file => file.endsWith('.html'))) {
const location = path.join(root, file);
const original = fs.readFileSync(location, 'utf8');
const updated = original.replace(/(\b(?:src|href)=["'])(\/?)(style\.css|script\.js)(?:\?[^"']*)?(["'])/g,
(_, prefix, slash, asset, quote) => `${prefix}${slash}${asset}?v=${versions[asset]}${quote}`);
if (updated !== original) fs.writeFileSync(location, updated);
}
4 changes: 2 additions & 2 deletions small-business-tech-support-henderson.html
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800&display=swap" rel="stylesheet">

<link rel="stylesheet" href="style.css">
<link rel="stylesheet" href="style.css?v=8287724f17f5">
<link rel="icon" href="favicon.png" type="image/png">
<link rel="icon" href="favicon.png" type="image/png" sizes="32x32">

Expand Down Expand Up @@ -138,6 +138,6 @@ <h4 class="footer-title">Support</h4>
</div>
</footer>

<script src="/script.js" defer></script>
<script src="/script.js?v=fb2d384af22c" defer></script>
</body>
</html>
4 changes: 2 additions & 2 deletions support.html
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800&display=swap" rel="stylesheet">

<link rel="stylesheet" href="style.css">
<link rel="stylesheet" href="style.css?v=8287724f17f5">
<link rel="icon" href="favicon.png" type="image/png">
</head>
<body>
Expand Down Expand Up @@ -167,6 +167,6 @@ <h3>Solana</h3>
</div>
</footer>

<script src="script.js" defer></script>
<script src="script.js?v=fb2d384af22c" defer></script>
</body>
</html>
2 changes: 1 addition & 1 deletion terms.html
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
<link rel="preconnect" href="https://fonts.googleapis.com">
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800&display=swap" rel="stylesheet">
<link rel="stylesheet" href="style.css">
<link rel="stylesheet" href="style.css?v=8287724f17f5">
<link rel="icon" href="favicon.png" type="image/png">
<style>
.legal-hero {
Expand Down
25 changes: 25 additions & 0 deletions test/static-assets.test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
const assert = require('node:assert/strict');
const fs = require('node:fs');
const path = require('node:path');
const { createHash } = require('node:crypto');
const { test } = require('node:test');
const { JSDOM } = require('jsdom');
const root = path.resolve(__dirname, '..');

test('every shared script and stylesheet URL identifies the current asset content', () => {
let references = 0;
for (const file of fs.readdirSync(root).filter(file => file.endsWith('.html'))) {
const dom = new JSDOM(fs.readFileSync(path.join(root, file), 'utf8'), { url: 'https://dextech.cloud/' });
for (const element of dom.window.document.querySelectorAll('script[src], link[rel="stylesheet"][href]')) {
const url = new URL(element.src || element.href);
if (url.origin !== 'https://dextech.cloud') continue;
const asset = url.pathname.slice(1);
if (!['style.css', 'script.js'].includes(asset)) continue;
const version = createHash('sha256').update(fs.readFileSync(path.join(root, asset))).digest('hex').slice(0, 12);
assert.equal(url.searchParams.get('v'), version, `${file}: run npm run assets:version after editing ${asset}`);
references++;
}
dom.window.close();
}
assert.ok(references >= 10, 'Must check the shared assets across the public site');
});
4 changes: 2 additions & 2 deletions wifi-setup-henderson.html
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
<link rel="preconnect" href="https://fonts.gstatic.com" crossorigin>
<link href="https://fonts.googleapis.com/css2?family=Inter:wght@400;500;600;700;800&display=swap" rel="stylesheet">

<link rel="stylesheet" href="style.css">
<link rel="stylesheet" href="style.css?v=8287724f17f5">
<link rel="icon" href="favicon.png" type="image/png">
<link rel="icon" href="favicon.png" type="image/png" sizes="32x32">

Expand Down Expand Up @@ -138,6 +138,6 @@ <h4 class="footer-title">Support</h4>
</div>
</footer>

<script src="/script.js" defer></script>
<script src="/script.js?v=fb2d384af22c" defer></script>
</body>
</html>