diff --git a/.github/helm/affine/charts/front/templates/deployment.yaml b/.github/helm/affine/charts/front/templates/deployment.yaml index 910428734b..6efdc80199 100644 --- a/.github/helm/affine/charts/front/templates/deployment.yaml +++ b/.github/helm/affine/charts/front/templates/deployment.yaml @@ -96,12 +96,20 @@ spec: httpGet: path: /info port: http - initialDelaySeconds: {{ .Values.probe.initialDelaySeconds }} + initialDelaySeconds: {{ default .Values.probe.initialDelaySeconds .Values.probe.liveness.initialDelaySeconds }} + timeoutSeconds: {{ default .Values.probe.timeoutSeconds .Values.probe.liveness.timeoutSeconds }} + periodSeconds: {{ default .Values.probe.periodSeconds .Values.probe.liveness.periodSeconds }} + failureThreshold: {{ default .Values.probe.failureThreshold .Values.probe.liveness.failureThreshold }} + successThreshold: {{ default .Values.probe.successThreshold .Values.probe.liveness.successThreshold }} readinessProbe: httpGet: path: /info port: http - initialDelaySeconds: {{ .Values.probe.initialDelaySeconds }} + initialDelaySeconds: {{ default .Values.probe.initialDelaySeconds .Values.probe.readiness.initialDelaySeconds }} + timeoutSeconds: {{ default .Values.probe.timeoutSeconds .Values.probe.readiness.timeoutSeconds }} + periodSeconds: {{ default .Values.probe.periodSeconds .Values.probe.readiness.periodSeconds }} + failureThreshold: {{ default .Values.probe.failureThreshold .Values.probe.readiness.failureThreshold }} + successThreshold: {{ default .Values.probe.successThreshold .Values.probe.readiness.successThreshold }} resources: {{- toYaml .Values.resources | nindent 12 }} {{- with .Values.nodeSelector }} diff --git a/.github/helm/affine/charts/front/values.yaml b/.github/helm/affine/charts/front/values.yaml index 47a86cd5b8..08933d27d1 100644 --- a/.github/helm/affine/charts/front/values.yaml +++ b/.github/helm/affine/charts/front/values.yaml @@ -31,13 +31,21 @@ podSecurityContext: resources: limits: cpu: '1' - memory: 2Gi + memory: 4Gi requests: cpu: '1' memory: 2Gi probe: initialDelaySeconds: 20 + timeoutSeconds: 5 + periodSeconds: 10 + failureThreshold: 6 + successThreshold: 1 + liveness: + initialDelaySeconds: 60 + failureThreshold: 12 + readiness: {} services: sync: diff --git a/packages/backend/server/src/base/cors.ts b/packages/backend/server/src/base/cors.ts index 29e84351dc..7b8231f858 100644 --- a/packages/backend/server/src/base/cors.ts +++ b/packages/backend/server/src/base/cors.ts @@ -7,7 +7,12 @@ const MOBILE_CLIENT_ORIGINS = new Set([ 'capacitor://localhost', 'ionic://localhost', ]); -const DESKTOP_CLIENT_ORIGINS = new Set(['assets://.', 'assets://another-host']); +const DESKTOP_CLIENT_ORIGINS = new Set([ + 'assets://.', + 'assets://another-host', + // for old versions of client, which use file:// as origin + 'file://', +]); export const CORS_ALLOWED_METHODS = [ 'GET', @@ -55,6 +60,19 @@ function isDevLoopbackOrigin(origin: string) { } } +function normalizeCorsOrigin(origin: string) { + try { + const parsed = new URL(origin); + // Some websocket clients send ws:// or wss:// as Origin. + if (parsed.protocol === 'ws:' || parsed.protocol === 'wss:') { + parsed.protocol = parsed.protocol === 'wss:' ? 'https:' : 'http:'; + } + return parsed.origin; + } catch { + return null; + } +} + export function buildCorsAllowedOrigins(url: URLHelper) { return new Set([ ...url.allowedOrigins, @@ -75,6 +93,11 @@ export function isCorsOriginAllowed( return true; } + const normalizedOrigin = normalizeCorsOrigin(origin); + if (normalizedOrigin && allowedOrigins.has(normalizedOrigin)) { + return true; + } + if ((env.dev || env.testing) && isDevLoopbackOrigin(origin)) { return true; } diff --git a/packages/backend/server/src/base/helpers/__tests__/url.spec.ts b/packages/backend/server/src/base/helpers/__tests__/url.spec.ts index dfa19e9486..655d26703f 100644 --- a/packages/backend/server/src/base/helpers/__tests__/url.spec.ts +++ b/packages/backend/server/src/base/helpers/__tests__/url.spec.ts @@ -1,6 +1,7 @@ import ava, { TestFn } from 'ava'; import Sinon from 'sinon'; +import { buildCorsAllowedOrigins, isCorsOriginAllowed } from '../../cors'; import { ActionForbidden } from '../../error'; import { URLHelper } from '../url'; @@ -193,3 +194,19 @@ test('can get request base url with multiple hosts', t => { t.is(url.requestOrigin, 'https://app.affine.local2'); t.is(url.requestBaseUrl, 'https://app.affine.local2'); }); + +test('should allow websocket secure origin by normalizing wss to https', t => { + const allowedOrigins = buildCorsAllowedOrigins({ + allowedOrigins: ['https://app.affine.pro'], + } as any); + + t.true(isCorsOriginAllowed('wss://app.affine.pro', allowedOrigins)); +}); + +test('should allow desktop file origin', t => { + const allowedOrigins = buildCorsAllowedOrigins({ + allowedOrigins: [], + } as any); + + t.true(isCorsOriginAllowed('file://', allowedOrigins)); +});