From 43ca760291c7eec0635e2211740342de87be1def Mon Sep 17 00:00:00 2001
From: "dobby-yivi-agent[bot]"
<275734547+dobby-yivi-agent[bot]@users.noreply.github.com>
Date: Sat, 9 May 2026 13:35:53 +0000
Subject: [PATCH 1/5] fix: opt RSS link out of client-side navigation
Closes #183
The blog RSS button used a SvelteKit anchor with no reload hint. The
(marketing) layout sets trailingSlash: 'always', which causes the
client router to redirect /blog/rss.xml to /blog/rss.xml/ on
client-side navigation. The +server.js endpoint is prerendered to a
file at /blog/rss.xml, so the trailing-slash form falls through to
the SPA shell (or errors), and visitors saw a 500.
Adding data-sveltekit-reload makes the browser perform a full
navigation, bypassing the client router so the static file is served
directly. Direct URLs already worked because they are not subject to
the router's trailing-slash rewrite.
---
src/routes/(marketing)/blog/+page.svelte | 1 +
1 file changed, 1 insertion(+)
diff --git a/src/routes/(marketing)/blog/+page.svelte b/src/routes/(marketing)/blog/+page.svelte
index 3fa05dd..7b73e53 100644
--- a/src/routes/(marketing)/blog/+page.svelte
+++ b/src/routes/(marketing)/blog/+page.svelte
@@ -70,6 +70,7 @@
class="rss-link"
href={resolve('/(marketing)/blog/rss.xml')}
aria-label="RSS feed"
+ data-sveltekit-reload
>
Date: Sat, 9 May 2026 13:36:42 +0000
Subject: [PATCH 2/5] fix: extend cryptify retry budget to cover restart window
MIME-Version: 1.0
Content-Type: text/plain; charset=UTF-8
Content-Transfer-Encoding: 8bit
The default pg-js retry policy (5 attempts, 500ms initial delay,
multiplier 2) exhausts in ~7.5s of total wait time. That's shorter
than a typical cryptify service restart, so users see a hard failure
during what should be a recoverable outage.
Bump maxAttempts to 8 and initialDelayMs to 1000ms so the retry
budget covers ~90s of total wait — long enough to ride out a
restart while still failing fast for genuinely down backends.
Closes #181
---
src/lib/postguard.ts | 6 ++++++
1 file changed, 6 insertions(+)
diff --git a/src/lib/postguard.ts b/src/lib/postguard.ts
index e161af0..1c8f2fc 100644
--- a/src/lib/postguard.ts
+++ b/src/lib/postguard.ts
@@ -19,6 +19,12 @@ export const pg = new PostGuard({
cryptifyUrl: FILEHOST_URL,
...(CHUNK_SIZE !== undefined && { uploadChunkSize: CHUNK_SIZE }),
retry: {
+ // Defaults (5 attempts, 500ms initial) exhaust the retry budget in
+ // ~7.5s — shorter than a typical cryptify restart, so a brief outage
+ // surfaces as a hard failure to the user. Stretch the budget so the
+ // total wait covers a realistic restart window (~90s).
+ maxAttempts: 8,
+ initialDelayMs: 1000,
onRetry: (event) => retryStatus.set(event),
},
})
From e9777bde6c9b39c30277aa14bbabea3d3f7bff50 Mon Sep 17 00:00:00 2001
From: "dobby-yivi-agent[bot]"
<275734547+dobby-yivi-agent[bot]@users.noreply.github.com>
Date: Sat, 9 May 2026 13:36:42 +0000
Subject: [PATCH 3/5] fix: prevent light-mode flash on initial page load
Add a synchronous inline script in app.html that reads the user's theme
preference (localStorage 'preferredtheme', falling back to
prefers-color-scheme) and applies the .dark class to before the
browser paints. Previously the class was only set during Svelte
hydration, causing a brief light-mode flash on every refresh in dark
mode.
Closes #180
---
src/app.html | 13 +++++++++++++
1 file changed, 13 insertions(+)
diff --git a/src/app.html b/src/app.html
index 72d4d9f..8c848ef 100644
--- a/src/app.html
+++ b/src/app.html
@@ -5,6 +5,19 @@
+
%sveltekit.head%
From fd3984c33f59f1a01f513e7506f275eeba0fd8a8 Mon Sep 17 00:00:00 2001
From: "dobby-yivi-agent[bot]"
<275734547+dobby-yivi-agent[bot]@users.noreply.github.com>
Date: Sat, 9 May 2026 13:37:29 +0000
Subject: [PATCH 4/5] fix: add cancel button during file upload (#182)
Closes #182. The encryption/upload progress UI rendered by SendButton
exposed only a spinner and progress bar; users had no in-app way to
abort a long upload. Adds a Cancel button to the upload-info-box that
calls AbortController.abort() on the existing encryption/upload signal,
flips selfAborted so the catch path resets to FileSelection, and
provisions a fresh AbortController for the next attempt.
---
.../components/filesharing/SendButton.svelte | 25 +++++++++++++++++++
1 file changed, 25 insertions(+)
diff --git a/src/lib/components/filesharing/SendButton.svelte b/src/lib/components/filesharing/SendButton.svelte
index f2db706..9be62ac 100644
--- a/src/lib/components/filesharing/SendButton.svelte
+++ b/src/lib/components/filesharing/SendButton.svelte
@@ -266,6 +266,18 @@
}
}
+ function onCancelUpload(): void {
+ if (!browser) return
+ // Mark before aborting so the catch in startEncryption() takes the
+ // self-aborted path and resets to FileSelection rather than showing
+ // the generic Error panel.
+ encryptState.selfAborted = true
+ encryptState.abort.abort()
+ // AbortController is single-use — provide a fresh one so a subsequent
+ // send attempt can be cancelled too.
+ encryptState.abort = new AbortController()
+ }
+
function updateProgress(pct: number) {
const totalSize = encryptState.files.reduce((a, f) => a + f.size, 0)
if (totalSize === 0) return
@@ -365,6 +377,14 @@
{/if}
+
+ {$_('filesharing.cancel')}
+
{:else}
Date: Sat, 9 May 2026 14:07:27 +0000
Subject: [PATCH 5/5] fix(blog): tone down exclamation marks in May update post
Closes #184
---
src/content/blog/postguard-may-update.svx | 6 +++---
1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/src/content/blog/postguard-may-update.svx b/src/content/blog/postguard-may-update.svx
index 8a1f5de..f11c942 100644
--- a/src/content/blog/postguard-may-update.svx
+++ b/src/content/blog/postguard-may-update.svx
@@ -11,10 +11,10 @@ image: "/blog/may_update.png"
We've been hard at work turning PostGuard from a research project into a usable service for everyone. Let me walk you through all the exciting changes from the past few months.
## Infrastructure Move
-We used to be hosted at the Radboud University and at Procolix. We have modernized everything into containers and moved to the Yivi Kubernetes cluster on Scaleway. We also renewed our deal with Procolix, who generously provides us with the fileshare server. We are very grateful for that! We've also finished moving all the domains and the email server.
+We used to be hosted at the Radboud University and at Procolix. We have modernized everything into containers and moved to the Yivi Kubernetes cluster on Scaleway. We also renewed our deal with Procolix, who generously provides us with the fileshare server. We are very grateful for that. We've also finished moving all the domains and the email server.
## Soft launch of PostGuard for Business
-We officially launched PostGuard for Business! We currently have two proof-of-concept partners with the Dutch government to programmatically send encrypted emails to citizens.
+We officially launched PostGuard for Business. We currently have two proof-of-concept partners with the Dutch government to programmatically send encrypted emails to citizens.
To support these partners, we’ve made the Business portal fully bilingual (Dutch and English) and ensured it hits WCAG 2.2 AA accessibility standards. Whether you're using a screen reader or just prefer a specific language, PostGuard for Business is ready for you. If you want to try it out, just head on over to https://business.postguard.eu/ and press register.
@@ -49,7 +49,7 @@ var sealed = pg.Encrypt(new EncryptInput
```
## Brand new add-ins for Thunderbird and Outlook
-We released the alpha version of our Thunderbird and Outlook add-ins. There is still some work to do, but sending email through Thunderbird or Outlook for Mac, Windows, or online is now possible. Our goal is to make it the smoothest way to send encrypted email. Check it out at https://postguard.eu/addons!
+We released the alpha version of our Thunderbird and Outlook add-ins. There is still some work to do, but sending email through Thunderbird or Outlook for Mac, Windows, or online is now possible. Our goal is to make it the smoothest way to send encrypted email. Check it out at https://postguard.eu/addons.
