diff --git a/.docker/selfhost/schema.json b/.docker/selfhost/schema.json index 20c33777ca..1916587d3f 100644 --- a/.docker/selfhost/schema.json +++ b/.docker/selfhost/schema.json @@ -825,6 +825,11 @@ "description": "Indexer search service endpoint\n@default \"http://localhost:9308\"\n@environment `AFFINE_INDEXER_SEARCH_ENDPOINT`", "default": "http://localhost:9308" }, + "provider.apiKey": { + "type": "string", + "description": "Indexer search service api key. Optional for elasticsearch\n@default \"\"\n@environment `AFFINE_INDEXER_SEARCH_API_KEY`\n@link https://www.elastic.co/guide/server/current/api-key.html", + "default": "" + }, "provider.username": { "type": "string", "description": "Indexer search service auth username, if not set, basic auth will be disabled. Optional for elasticsearch\n@default \"\"\n@environment `AFFINE_INDEXER_SEARCH_USERNAME`\n@link https://www.elastic.co/guide/en/elasticsearch/reference/current/http-clients.html", diff --git a/.github/actions/deploy/deploy.mjs b/.github/actions/deploy/deploy.mjs index 33d85e60dd..3a374fad86 100644 --- a/.github/actions/deploy/deploy.mjs +++ b/.github/actions/deploy/deploy.mjs @@ -18,8 +18,7 @@ const { STATIC_IP_NAME, AFFINE_INDEXER_SEARCH_PROVIDER, AFFINE_INDEXER_SEARCH_ENDPOINT, - AFFINE_INDEXER_SEARCH_USERNAME, - AFFINE_INDEXER_SEARCH_PASSWORD, + AFFINE_INDEXER_SEARCH_API_KEY, } = process.env; const buildType = BUILD_TYPE || 'canary'; @@ -88,8 +87,7 @@ const createHelmCommand = ({ isDryRun }) => { const indexerOptions = [ `--set-string global.indexer.provider="${AFFINE_INDEXER_SEARCH_PROVIDER}"`, `--set-string global.indexer.endpoint="${AFFINE_INDEXER_SEARCH_ENDPOINT}"`, - `--set-string global.indexer.username="${AFFINE_INDEXER_SEARCH_USERNAME}"`, - `--set-string global.indexer.password="${AFFINE_INDEXER_SEARCH_PASSWORD}"`, + `--set-string global.indexer.apiKey="${AFFINE_INDEXER_SEARCH_API_KEY}"`, ]; const serviceAnnotations = [ `--set-json web.serviceAccount.annotations="{ \\"iam.gke.io/gcp-service-account\\": \\"${APP_IAM_ACCOUNT}\\" }"`, diff --git a/.github/helm/affine/charts/doc/templates/deployment.yaml b/.github/helm/affine/charts/doc/templates/deployment.yaml index f755c04338..246b1a55cd 100644 --- a/.github/helm/affine/charts/doc/templates/deployment.yaml +++ b/.github/helm/affine/charts/doc/templates/deployment.yaml @@ -73,13 +73,11 @@ spec: value: "{{ .Values.global.indexer.provider }}" - name: AFFINE_INDEXER_SEARCH_ENDPOINT value: "{{ .Values.global.indexer.endpoint }}" - - name: AFFINE_INDEXER_SEARCH_USERNAME - value: "{{ .Values.global.indexer.username }}" - - name: AFFINE_INDEXER_SEARCH_PASSWORD + - name: AFFINE_INDEXER_SEARCH_API_KEY valueFrom: secretKeyRef: name: indexer - key: indexer-password + key: indexer-apiKey - name: AFFINE_SERVER_PORT value: "{{ .Values.global.docService.port }}" - name: AFFINE_SERVER_SUB_PATH diff --git a/.github/helm/affine/charts/graphql/templates/deployment.yaml b/.github/helm/affine/charts/graphql/templates/deployment.yaml index 8c01049ca8..598cca53dd 100644 --- a/.github/helm/affine/charts/graphql/templates/deployment.yaml +++ b/.github/helm/affine/charts/graphql/templates/deployment.yaml @@ -71,13 +71,11 @@ spec: value: "{{ .Values.global.indexer.provider }}" - name: AFFINE_INDEXER_SEARCH_ENDPOINT value: "{{ .Values.global.indexer.endpoint }}" - - name: AFFINE_INDEXER_SEARCH_USERNAME - value: "{{ .Values.global.indexer.username }}" - - name: AFFINE_INDEXER_SEARCH_PASSWORD + - name: AFFINE_INDEXER_SEARCH_API_KEY valueFrom: secretKeyRef: name: indexer - key: indexer-password + key: indexer-apiKey - name: AFFINE_SERVER_PORT value: "{{ .Values.service.port }}" - name: AFFINE_SERVER_SUB_PATH diff --git a/.github/helm/affine/charts/graphql/templates/migration.yaml b/.github/helm/affine/charts/graphql/templates/migration.yaml index 288151fb8c..4b2f2cb687 100644 --- a/.github/helm/affine/charts/graphql/templates/migration.yaml +++ b/.github/helm/affine/charts/graphql/templates/migration.yaml @@ -48,13 +48,11 @@ spec: value: "{{ .Values.global.indexer.provider }}" - name: AFFINE_INDEXER_SEARCH_ENDPOINT value: "{{ .Values.global.indexer.endpoint }}" - - name: AFFINE_INDEXER_SEARCH_USERNAME - value: "{{ .Values.global.indexer.username }}" - - name: AFFINE_INDEXER_SEARCH_PASSWORD + - name: AFFINE_INDEXER_SEARCH_API_KEY valueFrom: secretKeyRef: name: indexer - key: indexer-password + key: indexer-apiKey resources: requests: cpu: '100m' diff --git a/.github/helm/affine/charts/renderer/templates/deployment.yaml b/.github/helm/affine/charts/renderer/templates/deployment.yaml index d671d07fa6..8ba3174f5d 100644 --- a/.github/helm/affine/charts/renderer/templates/deployment.yaml +++ b/.github/helm/affine/charts/renderer/templates/deployment.yaml @@ -73,13 +73,11 @@ spec: value: "{{ .Values.global.indexer.provider }}" - name: AFFINE_INDEXER_SEARCH_ENDPOINT value: "{{ .Values.global.indexer.endpoint }}" - - name: AFFINE_INDEXER_SEARCH_USERNAME - value: "{{ .Values.global.indexer.username }}" - - name: AFFINE_INDEXER_SEARCH_PASSWORD + - name: AFFINE_INDEXER_SEARCH_API_KEY valueFrom: secretKeyRef: name: indexer - key: indexer-password + key: indexer-apiKey - name: AFFINE_SERVER_PORT value: "{{ .Values.service.port }}" - name: AFFINE_SERVER_SUB_PATH diff --git a/.github/helm/affine/charts/sync/templates/deployment.yaml b/.github/helm/affine/charts/sync/templates/deployment.yaml index be03d89c37..3c0da73db4 100644 --- a/.github/helm/affine/charts/sync/templates/deployment.yaml +++ b/.github/helm/affine/charts/sync/templates/deployment.yaml @@ -73,13 +73,11 @@ spec: value: "{{ .Values.global.indexer.provider }}" - name: AFFINE_INDEXER_SEARCH_ENDPOINT value: "{{ .Values.global.indexer.endpoint }}" - - name: AFFINE_INDEXER_SEARCH_USERNAME - value: "{{ .Values.global.indexer.username }}" - - name: AFFINE_INDEXER_SEARCH_PASSWORD + - name: AFFINE_INDEXER_SEARCH_API_KEY valueFrom: secretKeyRef: name: indexer - key: indexer-password + key: indexer-apiKey - name: AFFINE_SERVER_PORT value: "{{ .Values.service.port }}" - name: AFFINE_SERVER_HOST diff --git a/.github/helm/affine/templates/indexer-secret.yaml b/.github/helm/affine/templates/indexer-secret.yaml index d36fe7dc97..711e683510 100644 --- a/.github/helm/affine/templates/indexer-secret.yaml +++ b/.github/helm/affine/templates/indexer-secret.yaml @@ -1,4 +1,4 @@ -{{- if .Values.global.indexer.password -}} +{{- if .Values.global.indexer.apiKey -}} apiVersion: v1 kind: Secret metadata: @@ -9,5 +9,5 @@ metadata: "helm.sh/hook-delete-policy": before-hook-creation type: Opaque data: - indexer-password: {{ .Values.global.indexer.password | b64enc }} + indexer-apiKey: {{ .Values.global.indexer.apiKey | b64enc }} {{- end }} diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index 65e94e47ac..e956e067a4 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -105,8 +105,7 @@ jobs: STATIC_IP_NAME: ${{ secrets.STATIC_IP_NAME }} AFFINE_INDEXER_SEARCH_PROVIDER: ${{ secrets.AFFINE_INDEXER_SEARCH_PROVIDER }} AFFINE_INDEXER_SEARCH_ENDPOINT: ${{ secrets.AFFINE_INDEXER_SEARCH_ENDPOINT }} - AFFINE_INDEXER_SEARCH_USERNAME: ${{ secrets.AFFINE_INDEXER_SEARCH_USERNAME }} - AFFINE_INDEXER_SEARCH_PASSWORD: ${{ secrets.AFFINE_INDEXER_SEARCH_PASSWORD }} + AFFINE_INDEXER_SEARCH_API_KEY: ${{ secrets.AFFINE_INDEXER_SEARCH_API_KEY }} deploy-done: needs: diff --git a/packages/backend/server/src/plugins/indexer/config.ts b/packages/backend/server/src/plugins/indexer/config.ts index 6ef7649b7c..b04855bb48 100644 --- a/packages/backend/server/src/plugins/indexer/config.ts +++ b/packages/backend/server/src/plugins/indexer/config.ts @@ -16,6 +16,7 @@ declare global { provider: { type: SearchProviderType; endpoint: string; + apiKey: string; username: string; password: string; }; @@ -50,6 +51,12 @@ defineModuleConfig('indexer', { return z.string().url().safeParse(val); }, }, + 'provider.apiKey': { + desc: 'Indexer search service api key. Optional for elasticsearch', + link: 'https://www.elastic.co/guide/server/current/api-key.html', + default: '', + env: ['AFFINE_INDEXER_SEARCH_API_KEY', 'string'], + }, 'provider.username': { desc: 'Indexer search service auth username, if not set, basic auth will be disabled. Optional for elasticsearch', link: 'https://www.elastic.co/guide/en/elasticsearch/reference/current/http-clients.html', diff --git a/packages/backend/server/src/plugins/indexer/providers/elasticsearch.ts b/packages/backend/server/src/plugins/indexer/providers/elasticsearch.ts index 1df0c38d1a..7e50700b7d 100644 --- a/packages/backend/server/src/plugins/indexer/providers/elasticsearch.ts +++ b/packages/backend/server/src/plugins/indexer/providers/elasticsearch.ts @@ -248,7 +248,9 @@ export class ElasticsearchProvider extends SearchProvider { const headers = { 'Content-Type': contentType, } as Record; - if (this.config.provider.password) { + if (this.config.provider.apiKey) { + headers.Authorization = `ApiKey ${this.config.provider.apiKey}`; + } else if (this.config.provider.password) { headers.Authorization = `Basic ${Buffer.from(`${this.config.provider.username}:${this.config.provider.password}`).toString('base64')}`; } const response = await fetch(url, { diff --git a/packages/frontend/admin/src/config.json b/packages/frontend/admin/src/config.json index 3033a8a2be..944c86d9d3 100644 --- a/packages/frontend/admin/src/config.json +++ b/packages/frontend/admin/src/config.json @@ -279,6 +279,12 @@ "desc": "Indexer search service endpoint", "env": "AFFINE_INDEXER_SEARCH_ENDPOINT" }, + "provider.apiKey": { + "type": "String", + "desc": "Indexer search service api key. Optional for elasticsearch", + "link": "https://www.elastic.co/guide/server/current/api-key.html", + "env": "AFFINE_INDEXER_SEARCH_API_KEY" + }, "provider.username": { "type": "String", "desc": "Indexer search service auth username, if not set, basic auth will be disabled. Optional for elasticsearch",