Skip to content

Commit 63dfbc2

Browse files
authored
chore: release prep for v1.25.6 (#156)
1 parent cd42582 commit 63dfbc2

File tree

12 files changed

+216
-162
lines changed

12 files changed

+216
-162
lines changed

.github/workflows/probely-scan.yml

Lines changed: 35 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -21,39 +21,58 @@ jobs:
2121

2222
env:
2323
PROBELY_API_KEY: ${{ secrets.PROBELY_API_KEY }}
24-
TARGET_ID: 3by8xa6kzArN
25-
API_BASE: https://api.probely.com/v2 # Always include /v2
24+
TARGET_ID: ${{ secrets.PROBELY_TARGET_ID }}
25+
API_BASE: https://api.probely.com
2626
MAX_WAIT_MINUTES: 60 # configurable
2727

2828
steps:
2929
- name: Start Probely Scan
3030
id: start-scan
3131
run: |
32+
curl_retry() {
33+
curl --fail-with-body --retry 3 --retry-delay 5 --retry-max-time 30 "$@"
34+
}
35+
3236
echo "🧪 Triggering Probely scan for target $TARGET_ID ..."
33-
response=$(curl -s -X POST "$API_BASE/targets/$TARGET_ID/scans/" \
37+
38+
response_file=$(mktemp)
39+
http_code=$(curl_retry -s -w "%{http_code}" -o "$response_file" -X POST "$API_BASE/targets/$TARGET_ID/scan_now/" \
3440
-H "Authorization: JWT $PROBELY_API_KEY" \
3541
-H "Content-Type: application/json" \
3642
-d '{}')
3743
38-
echo "Raw API response:"
39-
echo "$response" | jq .
44+
echo "🌐 HTTP status: $http_code"
45+
echo "📄 Raw API response:"
46+
cat "$response_file"
47+
48+
if [ "$http_code" -ne 201 ]; then
49+
echo "::error ::Unexpected HTTP response from Probely API: $http_code"
50+
exit 1
51+
fi
52+
53+
if ! jq . "$response_file" >/dev/null 2>&1; then
54+
echo "::error ::Invalid JSON response from Probely API."
55+
cat "$response_file"
56+
exit 1
57+
fi
4058
41-
scan_id=$(echo "$response" | jq -r '.id // empty')
59+
jq . "$response_file"
60+
scan_id=$(jq -r '.id // empty' "$response_file")
4261
4362
if [ -z "$scan_id" ]; then
44-
echo "::error ::Failed to start scan — check API key, target ID, or base URL."
63+
echo "::error ::Scan ID not found in response. Check API key, target ID, or base URL."
4564
exit 1
4665
fi
4766
48-
echo "scan_id=$scan_id" >> $GITHUB_ENV
67+
echo "scan_id=$scan_id" >> "$GITHUB_ENV"
4968
echo "✅ Scan started with ID: $scan_id"
5069
5170
- name: Wait for Scan Completion
5271
run: |
5372
echo "⏳ Waiting for scan $scan_id to complete..."
5473
elapsed=0
5574
while [ $elapsed -lt $((MAX_WAIT_MINUTES * 60)) ]; do
56-
status=$(curl -s "$API_BASE/scans/$scan_id/" \
75+
status=$(curl --fail-with-body -s "$API_BASE/targets/$TARGET_ID/scans/$scan_id/" \
5776
-H "Authorization: JWT $PROBELY_API_KEY" | jq -r '.status // empty')
5877
5978
echo "⏱️ Status: $status (elapsed $elapsed sec)"
@@ -78,18 +97,19 @@ jobs:
7897
- name: Download Probely HTML Report
7998
run: |
8099
echo "📥 Downloading report for scan $scan_id ..."
81-
curl -s "$API_BASE/scans/$scan_id/report/" \
100+
curl -s "$API_BASE/targets/$TARGET_ID/scans/$scan_id/endpoints/" \
82101
-H "Authorization: JWT $PROBELY_API_KEY" \
83-
-o probely-report.html
102+
-o probely-scan-coverage.csv
84103
85-
if [ ! -s probely-report.html ]; then
104+
if [ ! -s probely-scan-coverage.csv ]; then
86105
echo "::error ::Report file is empty or missing."
87106
exit 1
88107
fi
89-
echo "✅ Report saved as probely-report.html"
108+
echo "✅ Report saved as probely-scan-coverage.csv"
90109
91110
- name: Upload report artifact
92111
uses: actions/upload-artifact@v5
93112
with:
94-
name: probely-report
95-
path: probely-report.html
113+
name: probely-scan-coverage
114+
path: probely-scan-coverage.csv
115+
# cspell:ignore mktemp

.vscode/settings.json

Lines changed: 1 addition & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -41,40 +41,5 @@
4141
"css.customData": [
4242
".vscode/customData.json" // Path to your custom data file
4343
],
44-
"markdown.validate.enabled": false,
45-
"markdown.validate.ignoredLinks": [
46-
"#bugs",
47-
"#features",
48-
"#top",
49-
"#ownership",
50-
"#trademark",
51-
"#branding",
52-
"#licensed-material",
53-
"#licenses",
54-
"#dlnotes",
55-
"#cc-by",
56-
"#gnu-gpl",
57-
"#third-party",
58-
"#prohibited-uses",
59-
"#disclaimer",
60-
"#contact",
61-
"#revisions",
62-
"#pledge",
63-
"#standards",
64-
"#response",
65-
"#enforce",
66-
"#attribute",
67-
"#version",
68-
"#structure",
69-
"#getting-started",
70-
"#configuration",
71-
"#sw-utilities",
72-
"#cspreport",
73-
"#testing",
74-
"#toolchain",
75-
"#toolconfig",
76-
"#scripts",
77-
"#license",
78-
"#questions"
79-
]
44+
"markdown.validate.enabled": false
8045
}

CHANGELOG.md

Lines changed: 31 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,35 @@ This project attempts to follow [Keep a Changelog](https://keepachangelog.com/en
2222

2323
---
2424

25+
## [1.25.6] - 2025-11-04
26+
27+
### Security
28+
29+
- Hardened `Content-Security-Policy (CSP)` in `hooks.server.js`:
30+
- Environment-specific policies for `production`, `audit`, `dev`, and `test`
31+
- Added real CSP reporting endpoint (`csp.netwk.pro`) in production
32+
- Report-only mode enabled in non-prod for safer diagnostics
33+
- Added `/api/mock-csp` endpoint to capture and log CSP violation reports in non-prod environments
34+
35+
### Changed
36+
37+
- Updated `README.md` with detailed explanation of the CSP enforcement strategy and future nonce-based roadmap
38+
- Moved inline styles from `Badges.svelte` and `Logo.svelte` to external stylesheet (`default.css`)
39+
- Regenerated `global.min.css` using LightningCSS to reflect updated external styles
40+
- Bumped project version to `v1.25.6`
41+
- Updated dependencies:
42+
- `@eslint/js` `^9.39.0``^9.39.1`
43+
- `eslint` `^9.39.0``^9.39.1`
44+
- `eslint-plugin-jsdoc` `^61.1.11``^61.1.12`
45+
- `svelte` `5.43.2``5.43.3`
46+
- `posthog-js` `^1.284.0``^1.285.1`
47+
48+
### Fixed
49+
50+
- Updated `probely-scan.yml` GitHub workflow to utilize the correct API endpoint and cURL requests.
51+
52+
---
53+
2554
## [1.25.5] - 2025-11-03
2655

2756
### Added
@@ -1702,7 +1731,8 @@ This enables analytics filtering and CSP hardening for the audit environment.
17021731

17031732
<!-- Link references -->
17041733

1705-
[Unreleased]: https://github.com/netwk-pro/netwk-pro.github.io/compare/v1.25.5...HEAD
1734+
[Unreleased]: https://github.com/netwk-pro/netwk-pro.github.io/compare/v1.25.6...HEAD
1735+
[1.25.6]: https://github.com/netwk-pro/netwk-pro.github.io/releases/tag/v1.25.6
17061736
[1.25.5]: https://github.com/netwk-pro/netwk-pro.github.io/releases/tag/v1.25.5
17071737
[1.25.4]: https://github.com/netwk-pro/netwk-pro.github.io/releases/tag/v1.25.4
17081738
[1.25.3]: https://github.com/netwk-pro/netwk-pro.github.io/releases/tag/v1.25.3

README.md

Lines changed: 43 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -173,23 +173,55 @@ This project includes custom runtime configuration files for enhancing security,
173173

174174
### 🔐 `hooks.server.js`
175175

176-
Located at `src/hooks.server.js`, this file is responsible for injecting dynamic security headers. It includes:
176+
Located at `src/hooks.server.js`, this file dynamically injects security headers depending on the environment. It includes:
177+
178+
- A **Content Security Policy (CSP)** with environment-based directives:
179+
- **Production/Audit**: Enforced, hardened CSP
180+
- **Test/Dev**: Uses `Content-Security-Policy-Report-Only` for safe diagnostics
181+
- A **Permissions Policy** that disables nonessential browser APIs
182+
- Standard HTTP security headers:
183+
- `X-Content-Type-Options`
184+
- `X-Frame-Options`
185+
- `Referrer-Policy`
186+
- `Strict-Transport-Security` (in non-test environments)
177187

178-
- A Content Security Policy (CSP) configured with relaxed directives to permit inline scripts and styles (`'unsafe-inline'`)
179-
- A Permissions Policy to explicitly disable unnecessary browser APIs
180-
- Standard security headers such as `X-Content-Type-Options`, `X-Frame-Options`, and `Referrer-Policy`
188+
---
189+
190+
### ⚙️ CSP Behavior by Environment
191+
192+
| Environment | Header | Analytics Enabled | CSP Reporting |
193+
| ------------ | ------------------------------------- | ----------------- | ------------- |
194+
| `production` | `Content-Security-Policy` | ✅ Yes | ✅ Yes |
195+
| `audit` | `Content-Security-Policy` | ❌ No | ❌ No |
196+
| `dev` | `Content-Security-Policy-Report-Only` | ❌ No | ✅ Yes (mock) |
197+
| `test` | `Content-Security-Policy-Report-Only` | ❌ No | ✅ Yes (mock) |
198+
199+
---
200+
201+
### 🧪 Reporting & Debugging
181202

182-
> ℹ️ A stricter CSP (excluding `'unsafe-inline'`) was attempted but reverted due to framework-level and third-party script compatibility issues. The current policy allows inline scripts to ensure stability across SvelteKit and analytics features such as PostHog.
203+
- In **non-production environments**, CSP headers are set to `report-only` mode.
204+
- Violations are POSTed to `/api/mock-csp`, which logs reports to the console.
205+
- In **production**, violations are sent to a real CSP collection endpoint (`https://csp.netwk.pro/.netlify/functions/csp-report`).
206+
207+
---
208+
209+
### ⚠️ Current Trade-Off
210+
211+
> Due to limitations in PostHog and certain SvelteKit internals, the current policy allows `'unsafe-inline'` for scripts and styles. A strict CSP using nonces was previously attempted but blocked critical functionality.
212+
213+
---
183214

184-
#### Future Improvements
215+
### 📈 Future Improvements (Strict CSP Plan)
185216

186-
To implement a strict nonce-based CSP in the future:
217+
To move toward a strict, nonce-based CSP:
187218

188-
1. Add nonce generation and injection logic in `hooks.server.js`
189-
2. Update all inline `<script>` tags (e.g. in `app.html`) to include `nonce="__cspNonce__"`
190-
3. Ensure any analytics libraries or dynamic scripts support nonced or external loading
219+
1. Ensure **all inline scripts** are updated to include injected nonces (`nonce="%nonce%"`)
220+
2. Confirm **PostHog** or future analytics platforms support nonced or external scripts/stylesheets
221+
3. Review and refactor any components that rely on dynamic `style=` or `<style>` blocks without support for CSP nonces
222+
4. Move third-party scripts out of inline `<script>` tags where possible
191223

192-
Note: Strict CSP adoption may require restructuring third-party integrations and deeper framework coordination.
224+
> ℹ️ Nonce-based CSP is the most secure long-term path but requires cooperation from all dependencies — and possibly upstream fixes to analytics tooling or SvelteKit itself.
193225
194226
&nbsp;
195227

0 commit comments

Comments
 (0)