summaryrefslogtreecommitdiff
path: root/packages/backend/src
diff options
context:
space:
mode:
authorHazelnoot <acomputerdog@gmail.com>2025-05-06 11:20:46 -0400
committerHazelnoot <acomputerdog@gmail.com>2025-05-06 11:20:46 -0400
commit95cd19b049804a7a773bdf70b7f72333a38e32be (patch)
tree6591dc241c5c04af0bb07a426b21a9f3f4f76108 /packages/backend/src
parentMerge branch 'develop' into merge/2025-03-24 (diff)
parentmerge: remove http/https protocol in uri on masto api (!980) (diff)
downloadsharkey-95cd19b049804a7a773bdf70b7f72333a38e32be.tar.gz
sharkey-95cd19b049804a7a773bdf70b7f72333a38e32be.tar.bz2
sharkey-95cd19b049804a7a773bdf70b7f72333a38e32be.zip
Merge branch 'develop' into merge/2025-03-24
Diffstat (limited to 'packages/backend/src')
-rw-r--r--packages/backend/src/core/UtilityService.ts13
-rw-r--r--packages/backend/src/server/ActivityPubServerService.ts29
-rw-r--r--packages/backend/src/server/api/mastodon/endpoints/instance.ts2
3 files changed, 38 insertions, 6 deletions
diff --git a/packages/backend/src/core/UtilityService.ts b/packages/backend/src/core/UtilityService.ts
index 5209cf7a3d..f8d04c0592 100644
--- a/packages/backend/src/core/UtilityService.ts
+++ b/packages/backend/src/core/UtilityService.ts
@@ -116,13 +116,22 @@ export class UtilityService {
@bindThis
public toPuny(host: string): string {
- return domainToASCII(host.toLowerCase());
+ // domainToASCII will return an empty string if we give it a
+ // string like `name:123`, but `host` may well be in that form
+ // (e.g. when testing locally, you'll get `localhost:3000`); split
+ // the port off, and add it back later
+ const hostParts = host.toLowerCase().match(/^(.+?)(:.+)?$/);
+ if (!hostParts) return '';
+ const hostname = hostParts[1];
+ const port = hostParts[2] ?? '';
+
+ return domainToASCII(hostname) + port;
}
@bindThis
public toPunyNullable(host: string | null | undefined): string | null {
if (host == null) return null;
- return domainToASCII(host.toLowerCase());
+ return this.toPuny(host);
}
@bindThis
diff --git a/packages/backend/src/server/ActivityPubServerService.ts b/packages/backend/src/server/ActivityPubServerService.ts
index 95ee78d660..41beadb56d 100644
--- a/packages/backend/src/server/ActivityPubServerService.ts
+++ b/packages/backend/src/server/ActivityPubServerService.ts
@@ -179,7 +179,7 @@ export class ActivityPubServerService {
this is also inspired by FireFish's `checkFetch`
*/
- let signature;
+ let signature: httpSignature.IParsedSignature;
try {
signature = httpSignature.parseRequest(request.raw, {
@@ -232,14 +232,37 @@ export class ActivityPubServerService {
return `${logPrefix} signer is suspended: refuse`;
}
- let httpSignatureValidated = httpSignature.verifySignature(signature, authUser.key.keyPem);
+ // some fedi implementations include the query (`?foo=bar`) in the
+ // signature, some don't, so we have to handle both cases
+ function verifyWithOrWithoutQuery() {
+ const httpSignatureValidated = httpSignature.verifySignature(signature, authUser!.key!.keyPem);
+ if (httpSignatureValidated) return true;
+
+ const requestUrl = new URL(`http://whatever${request.raw.url}`);
+ if (! requestUrl.search) return false;
+
+ // verification failed, the request URL contained a query, let's try without
+ const semiRawRequest = request.raw;
+ semiRawRequest.url = requestUrl.pathname;
+
+ // no need for try/catch, if the original request parsed, this
+ // one will, too
+ const signatureWithoutQuery = httpSignature.parseRequest(semiRawRequest, {
+ headers: ['(request-target)', 'host', 'date'],
+ authorizationHeaderName: 'signature',
+ });
+
+ return httpSignature.verifySignature(signatureWithoutQuery, authUser!.key!.keyPem);
+ }
+
+ let httpSignatureValidated = verifyWithOrWithoutQuery();
// maybe they changed their key? refetch it
// TODO rate-limit this using lastFetchedAt
if (!httpSignatureValidated) {
authUser.key = await this.apDbResolverService.refetchPublicKeyForApId(authUser.user);
if (authUser.key != null) {
- httpSignatureValidated = httpSignature.verifySignature(signature, authUser.key.keyPem);
+ httpSignatureValidated = verifyWithOrWithoutQuery();
}
}
diff --git a/packages/backend/src/server/api/mastodon/endpoints/instance.ts b/packages/backend/src/server/api/mastodon/endpoints/instance.ts
index 0e363446a4..a168339ac6 100644
--- a/packages/backend/src/server/api/mastodon/endpoints/instance.ts
+++ b/packages/backend/src/server/api/mastodon/endpoints/instance.ts
@@ -39,7 +39,7 @@ export class ApiInstanceMastodon {
const instance = data.data;
const response: MastodonEntity.Instance = {
- uri: this.config.url,
+ uri: this.config.host,
title: this.meta.name || 'Sharkey',
description: this.meta.description || 'This is a vanilla Sharkey Instance. It doesn\'t seem to have a description.',
email: instance.email || '',