ловлю такую пошибку Failure in source: Saved offse...
# replication-ask-ai
b
ловлю такую пошибку Failure in source: Saved offset is before replication slot's confirmed lsn. на базе данных в который всего одна таблица весом около 1 мб, как такое может быть? при этом огранечения на wal журнал стоят 5 гб, может ли проблема возникать из за того что слишком мало изменений в бд происходит? @kapa.ai
k
Да, именно в этом и заключается проблема! Ошибка
Saved offset is before replication slot's confirmed lsn
в вашем случае, скорее всего, вызвана малым количеством изменений в базе данных, а не нехваткой места в WAL. Причины Существуют две основные причины: 1. Баг в PgJDBC 42.7.0+ (начиная с версии коннектора
3.6.19
): драйвер автоматически продвигает
confirmed_flush_lsn
даже когда нет новых событий для таблиц в публикации, но WAL содержит изменения от других таблиц. В итоге сохранённый offset в состоянии Airbyte оказывается меньше
confirmed_flush_lsn
. [GitHub Issue 49802] 2. Баг в
PostgresCdcCtidInitializer
: при первоначальной синхронизации Airbyte коммитит LSN больший, чем тот, что сохраняется в state-файле. Если после снапшота не было найдено инкрементальных изменений (что типично для малоактивной БД), следующий sync падает с этой ошибкой. [GitHub Issue 49803] Решения Быстрое решение — откат версии коннектора Откатитесь до версии
3.6.18
— она не содержит этих багов. [GitHub Issue 55846] Либо обновитесь до версии
3.7.2
или выше — в ней эта проблема исправлена. [GitHub Issue 55846] Долгосрочное решение — heartbeat-таблица Создайте таблицу-«сердцебиение», которая будет регулярно получать записи, чтобы LSN продвигался:
Copy code
CREATE TABLE airbyte_heartbeat (
    id SERIAL PRIMARY KEY,
    timestamp TIMESTAMP NOT NULL DEFAULT current_timestamp,
    text TEXT
);
Добавьте её в публикацию:
Copy code
ALTER PUBLICATION <publicationName> ADD TABLE airbyte_heartbeat;
В настройках Postgres-коннектора в Airbyte (раздел Advanced → Debezium heartbeat query) укажите:
Copy code
INSERT INTO airbyte_heartbeat (text) VALUES ('heartbeat');
Это заставит Airbyte периодически писать в таблицу, продвигая LSN даже при отсутствии изменений в основных таблицах. [Airbyte Docs] Альтернатива (без прав на запись) Добавьте в публикацию таблицу с высокой активностью (даже если вы её не синхронизируете) — это будет продвигать LSN:
Copy code
ALTER PUBLICATION <publicationName> ADD TABLE <high_volume_table>;
[Airbyte Docs] Вывод: 5 ГБ лимита на WAL здесь ни при чём — проблема именно в том, что в БД мало изменений, и это провоцирует известный баг в коннекторе. 👍 0 button 👎 0 button ℹ️ Tip: Mention @kapa.ai in the thread for follow-ups or DM the app for 1-to-1 help.
b
у меня и так версия коннектора postgres 3.6.15, какое тогда решение? @kapa.ai
k
Интересная ситуация! Версия
3.6.15
считается рабочей (баг появился с
3.6.19
), однако ошибка всё равно возникает. Возможные причины на версии 3.6.15 Судя по GitHub-issues, даже на
3.6.15
может проявляться похожая проблема при малом количестве изменений в БД — WAL не очищается, если нет новых событий для таблиц в публикации. [GitHub Issue 70887] Рекомендуемое решение — heartbeat-таблица Это наиболее подходящий вариант для вашего случая (маленькая БД с редкими изменениями): 1. Создайте heartbeat-таблицу:
Copy code
CREATE TABLE airbyte_heartbeat (
    id SERIAL PRIMARY KEY,
    timestamp TIMESTAMP NOT NULL DEFAULT current_timestamp,
    text TEXT
);
2. Добавьте её в публикацию:
Copy code
ALTER PUBLICATION <publicationName> ADD TABLE airbyte_heartbeat;
3. В настройках коннектора (Advanced → Debezium heartbeat query) укажите:
Copy code
INSERT INTO airbyte_heartbeat (text) VALUES ('heartbeat');
Это обеспечит регулярное продвижение LSN даже при отсутствии изменений в основных таблицах. [Airbyte Docs] Дополнительно Если вы читаете с реплики, потребуется также настроить
pg_cron
на мастере для периодической записи в heartbeat-таблицу, так как Airbyte не может писать напрямую в реплику. [Airbyte Docs] 👍 0 button 👎 0 button ℹ️ Tip: Mention @kapa.ai in the thread for follow-ups or DM the app for 1-to-1 help.
b
А расскажи что такое hearthbeat таблица, как работает, что в ней происходит, какие права должны быть у пользователя через который работает airbyte? @kapa.ai
k
Что такое heartbeat-таблица и как она работает Суть проблемы При CDC-репликации Airbyte читает WAL-журнал PostgreSQL. Если в таблицах публикации долго нет изменений, PostgreSQL продвигает
confirmed_flush_lsn
вперёд, а сохранённый offset в состоянии Airbyte отстаёт. При следующем sync возникает ошибка
Saved offset is before replication slot's confirmed lsn
. [Airbyte Docs] Как работает heartbeat-таблица Heartbeat-таблица — это вспомогательная таблица, в которую Airbyte периодически делает INSERT. Это создаёт искусственную активность в WAL, что заставляет LSN продвигаться синхронно с состоянием Airbyte. Таблица добавляется в публикацию, поэтому PostgreSQL «видит» эти изменения как часть отслеживаемых событий.
Copy code
Airbyte → INSERT в airbyte_heartbeat → событие попадает в WAL → LSN продвигается → offset в Airbyte синхронизирован
Саму heartbeat-таблицу не обязательно синхронизировать в destination — она нужна только для поддержания LSN. [Airbyte Docs] Структура таблицы
Copy code
CREATE TABLE airbyte_heartbeat (
    id SERIAL PRIMARY KEY,
    timestamp TIMESTAMP NOT NULL DEFAULT current_timestamp,
    text TEXT
);
Необходимые права для пользователя Airbyte Пользователю нужны права на INSERT, SELECT, UPDATE, DELETE, TRIGGER, TRUNCATE, REFERENCES на таблицу, а также доступ к sequence для автоинкремента `id`: [GitHub Issue 55846]
Copy code
GRANT USAGE ON SCHEMA public TO <airbyte_user>;
GRANT INSERT, SELECT, UPDATE, DELETE, TRIGGER, TRUNCATE, REFERENCES 
    ON TABLE public.airbyte_heartbeat TO <airbyte_user>;
GRANT USAGE, SELECT 
    ON SEQUENCE public.airbyte_heartbeat_id_seq TO <airbyte_user>;
Подключение к публикации и настройка коннектора
Copy code
ALTER PUBLICATION <publicationName> ADD TABLE airbyte_heartbeat;
В настройках Postgres-коннектора в Airbyte (Advanced → Debezium heartbeat query):
Copy code
INSERT INTO airbyte_heartbeat (text) VALUES ('heartbeat');
Airbyte будет периодически выполнять этот запрос, поддерживая LSN в актуальном состоянии. [Airbyte Docs] > Важно: если вы читаете данные с read-реплики, Airbyte не может писать в неё напрямую. В этом случае нужно настроить
pg_cron
на мастере для периодической записи в heartbeat-таблицу. [Airbyte Docs] 👍 0 button 👎 0 button ℹ️ Tip: Mention @kapa.ai in the thread for follow-ups or DM the app for 1-to-1 help.
b
А можешь обьяснить почему вообще возникаем ошибка с lsn именно на маленьких базах? @kapa.ai
k
Почему ошибка с LSN возникает именно на маленьких/малоактивных базах Как работает LSN в норме При CDC Airbyte читает WAL-журнал и сохраняет позицию (
saved offset LSN
) — до какого места он дочитал. PostgreSQL со своей стороны ведёт
confirmed_flush_lsn
— позицию, до которой WAL можно считать обработанным и очистить. В норме эти два значения должны быть синхронизированы: Airbyte читает изменения → подтверждает позицию →
confirmed_flush_lsn
продвигается вместе с
saved offset
. Почему на маленьких базах это ломается Проблема возникает из-за специфики PgJDBC (начиная с версии 42.7.0) и поведения Debezium: [GitHub Issue 49802]
Copy code
1. В таблицах публикации нет изменений (маленькая БД, мало трафика)
2. Но WAL всё равно пишется — например, от других таблиц вне публикации,
   или от системных операций PostgreSQL
3. PgJDBC автоматически продвигает confirmed_flush_lsn вперёд,
   даже если для таблиц публикации не было никаких событий
4. Airbyte не получил никаких событий → не обновил saved offset
5. Итог: confirmed_flush_lsn > saved offset → ошибка
На активных базах этого не происходит, потому что изменения в таблицах публикации поступают постоянно — Airbyte успевает читать события и обновлять
saved offset
синхронно с
confirmed_flush_lsn
. [GitHub Issue 49803] Дополнительный фактор — первоначальная синхронизация При первом sync на маленькой базе ситуация усугубляется: [GitHub Issue 49803]
Copy code
1. Airbyte делает снапшот таблицы (initial load)
2. Коммитит LSN3 в PostgreSQL (подтверждает позицию)
3. После снапшота ищет инкрементальные изменения — их нет (база маленькая, тихая)
4. Сохраняет в state LSN2 (который меньше LSN3)
5. Следующий sync стартует с LSN2 < confirmed_flush_lsn → ошибка
Если кратко > На активной базе Airbyte всегда находит новые события и обновляет offset. На тихой базе — событий нет, offset не обновляется, но PostgreSQL всё равно продвигает
confirmed_flush_lsn
. Разрыв между ними и вызывает ошибку. Именно поэтому heartbeat-таблица решает проблему — она искусственно создаёт события в публикации, не давая образоваться разрыву между
confirmed_flush_lsn
и
saved offset
. [Airbyte Docs] 👍 0 button 👎 0 button ℹ️ Tip: Mention @kapa.ai in the thread for follow-ups or DM the app for 1-to-1 help.
b
Есть ли jobs в global конфигах? @kapa.ai
k
Да, в Helm chart V2 и в конфигурации Airbyte есть блок
jobs
в глобальных настройках. 1. В Helm chart V2
global.jobs
используется, например, для Kubernetes-настроек и namespace: [Upgrade values.yaml]global: jobs: kube: tolerations: ... nodeSelector: ... annotations: ... namespace: ... serviceAccount: ...Таблица соответствий показывает, что переменные окружения
JOB_KUBE_*
мапятся на
global.jobs.kube.*
. [Upgrade values.yaml] 2. Для ресурсов коннекторных pod’ов в Enterprise-документации приведён пример: [Scaling Airbyte]global: jobs: resources: limits: cpu: 250m memory: 500m requests: cpu: 75m memory: 150m 3. При этом в одном из GitHub-issues отмечено, что в Helm chart V2 поле
global.jobs.resources
может быть нерабочим и фактическая логика перенесена в
global.workloads.resources.*
, хотя
global.jobs.resources
всё ещё присутствует в
values.yaml
и может вводить в заблуждение. [helm jobs.resources broken] Итого: да,
jobs
есть в глобальных конфигурациях (
global.jobs.*
), но для ресурсов в chart V2 стоит учитывать возможный переход на
global.workloads.resources.*
согласно обсуждению в issue. 👍 0 button 👎 0 button ℹ️ Tip: Mention @kapa.ai in the thread for follow-ups or DM the app for 1-to-1 help.
b
Попытались изменить резуарсы и при перезапуске abctl видим ошибку WARNING Encountered an issue deploying Airbyte: Pod: airbyte-abctl-bootloader.18b70fcd267b612a Reason: Failed Message: Error: couldn't find key CONFIG_DATABASE_REPLICA_USER in Secret airbyte-abctl/airbyte-config-secrets Count: 16 @kapa.ai
k
Ошибка говорит, что при деплое
abctl
ожидает в секрете
airbyte-config-secrets
ключ
CONFIG_DATABASE_REPLICA_USER
, но его там нет. По аналогии с другими похожими ошибками (
couldn't find key ... in Secret ...
), Airbyte/Helm-чарт жёстко ссылается на определённые ключи в Kubernetes Secret, и если ключ отсутствует, под не стартует. [Secrets prereq] В knowledge-источниках нет прямого описания именно
CONFIG_DATABASE_REPLICA_USER
, но есть несколько важных моментов: • Helm-чарт и
abctl
ожидают, что секрет будет создан до установки и будет содержать все нужные ключи (например,
database-user
,
database-password
и др.). [External DB; Creating secrets] • Похожие ошибки решаются добавлением недостающего ключа в секрет (пример с
AIRBYTE_DUMMY_SECRET
). [Dummy secret issue] Что можно сделать 1. Посмотреть текущий секрет:
Copy code
kubectl get secret airbyte-config-secrets -n airbyte-abctl -o yaml
2. Добавить недостающий ключ (если у вас нет отдельного пользователя для replica, можно временно задать то же значение, что и для основного пользователя БД):
Copy code
kubectl patch secret airbyte-config-secrets -n airbyte-abctl \
  --type merge \
  -p '{"stringData": {"CONFIG_DATABASE_REPLICA_USER": "your_replica_user"}}'
3. После этого перезапустить установку
abctl
(или дождаться, пока он сам продолжит деплой). Если вы не используете реплику БД и не уверены, должен ли этот ключ вообще требоваться: в предоставленных источниках нет явной документации по
CONFIG_DATABASE_REPLICA_USER
, поэтому точной причины его появления в вашем окружении я, к сожалению, сказать не могу — но патч секрета с добавлением ключа является консистентным с уже задокументированными workaround’ами для аналогичных ошибок. 👍 0 button 👎 0 button ℹ️ Tip: Mention @kapa.ai in the thread for follow-ups or DM the app for 1-to-1 help.
b
WARNING Encountered an issue deploying Airbyte: Pod: airbyte-abctl-worker-f56f5fdd5-7tc9g.18b71097cae881b9 Reason: Failed Message: Error: couldn't find key CONNECTOR_BUILDER_SERVER_API_HOST in ConfigMap airbyte-abctl/airbyte-abctl-airbyte-env Count: 9 @kapa.ai
k
Эта ошибка означает, что в ConfigMap
airbyte-abctl-airbyte-env
ожидается ключ
CONNECTOR_BUILDER_SERVER_API_HOST
, но его там нет. По знаниям из источников, сейчас как раз идёт переход от
connector-builder-server
к manifest server: • В Airbyte 2.1 компонент
connector-builder-server
удалён из Helm-чарта и заменён на
manifest server
. Все настройки, которые раньше были под
connectorBuilderServer.*
в
values.yaml
, нужно перенести на новые ключи. [Airbyte 2.1 notes] • В одном из issue по abctl/ingress видно, что в новых версиях уже используется
MANIFEST_SERVER_API_HOST
наряду с
CONNECTOR_BUILDER_SERVER_API_HOST
. [Email not set] Сейчас у вас `abctl`/чарт всё ещё ссылается на старую переменную
CONNECTOR_BUILDER_SERVER_API_HOST
, но в сгенерированном ConfigMap её нет. Что можно сделать 1. Проверить ConfigMap:
Copy code
kubectl -n airbyte-abctl get configmap airbyte-abctl-airbyte-env -o yaml
Посмотрите, есть ли там ключи вида: •
CONNECTOR_BUILDER_SERVER_API_HOST
•
MANIFEST_SERVER_API_HOST
2. Если есть только
MANIFEST_SERVER_API_HOST
(или вообще ничего):
Так как в источниках нет точной инструкции, как именно abctl 0.30.x должен заполнять этот ключ, можно лишь сказать, что это несогласованность между версией abctl и чартом. Похожая ситуация уже встречалась с другими полями env/ingress и решалась фиксом в abctl. [Ingress target bug] В рамках доступных знаний я не вижу официально задокументированного способа «правильно» добавить
CONNECTOR_BUILDER_SERVER_API_HOST
в
airbyte-abctl-airbyte-env
вручную — это поведение управляется самим abctl. 3. Рекомендации по дальнейшим шагам: • Обновить
abctl
до версии, где учтён переход на manifest server (в issue по ingress упоминается, что пользователь использует форк с фиксом, пока правки не вмержены). [Ingress target bug] • Если обновление невозможно, временный, но не документированный workaround — вручную дописать ключ в ConfigMap (например, скопировав значение из
MANIFEST_SERVER_API_HOST
), однако в знаниях нет подтверждения, что это корректно и безопасно. К сожалению, в предоставленных источниках нет прямой, официальной инструкции именно для этой ошибки с
CONNECTOR_BUILDER_SERVER_API_HOST
в контексте abctl, поэтому точный поддерживаемый фикс я подсказать не могу — только указать на связь с переходом на manifest server и необходимость обновления abctl/чарта. 👍 0 button 👎 0 button ℹ️ Tip: Mention @kapa.ai in the thread for follow-ups or DM the app for 1-to-1 help.
b
У нас сейчас такие конфиги postgresql: enabled: false global: logging: level: info database: type: external # -- Secret name where database credentials are stored secretName: "airbyte-config-secrets" # e.g. "airbyte-config-secrets" # -- The database host host: "yx1-dwh-airbyte-1" # -- The database port port: "5432" # -- The database name name: "airbyte" # -- The key within
secretName
where database user is stored userSecretKey: "database-user" # e.g. "database-user" # -- The key within
secretName
where password is stored passwordSecretKey: "database-password" # e.g."database-password" worker: maxSyncWorkers: 10 replicaCount: 3 resources: requests: cpu: 100m memory: 100Mi limits: cpu: 3 memory: 4Gi workloadLauncher: resources: requests: cpu: 100m memory: 100Mi limits: cpu: 3 memory: 4Gi temporal: resources: requests: cpu: 100m memory: 100Mi limits: cpu: 3 memory: 4Gi server: resources: requests: cpu: 100m memory: 100Mi limits: cpu: 3 memory: 4Gi workloadApiServer: resources: requests: cpu: 100m memory: 100Mi limits: cpu: 3 memory: 4Gi Видимо тут не всё, можешь выдать тоже самое но добавив новые значения чтобы ошибок не было, новые знаеччния которые в новой версии 2.1 появились @kapa.ai
k
Сразу отмечу: в предоставленных знаниях нет готового полного примера
values.yaml
именно для abctl + Helm chart V2.1
, поэтому я не могу гарантированно выдать конфиг, после которого точно не будет ошибок. Могу только опираться на общую схему Helm V2 и те ключи, которые явно задокументированы. Ниже — пример, который расширяет ваш текущий
values.yaml
с учётом Helm chart V2 и перехода с
connectorBuilderServer.*
на
server.connectorBuilder.*
в 2.1. [Upgrade values.yaml; 2.1 notes]
Copy code
postgresql:
  enabled: false

global:
  edition: community
  # URL, по которому будет доступен Airbyte (если есть ingress / портфорвард)
  airbyteUrl: ""

  logging:
    level: info

  database:
    type: external
    # Secret с кредами БД
    secretName: "airbyte-config-secrets"
    host: "yx1-dwh-airbyte-1"
    port: "5432"
    name: "airbyte"
    # ключи внутри секрета
    userSecretKey: "database-user"
    passwordSecretKey: "database-password"

  # Пример заготовки для secretsManager (можно оставить disabled)
  secretsManager:
    enabled: false
    type: ""              # VAULT, GOOGLE_SECRET_MANAGER, AWS_SECRET_MANAGER, AZURE_KEY_VAULT, TESTING_CONFIG_DB_TABLE
    secretName: "airbyte-config-secrets"
    awsSecretManager: {}
    googleSecretManager: {}
    azureKeyVault: {}
    vault: {}

  # Пример заготовки для storage (если не используете внешний — можно не трогать)
  storage:
    type: minio
    secretName: ""
    bucket:
      log: airbyte-bucket
      state: airbyte-bucket
      workloadOutput: airbyte-bucket
      activityPayload: airbyte-bucket

  # Пример блока jobs для совместимости с новыми env (можно адаптировать под ваш кластер)
  jobs:
    kube:
      namespace: ""        # по умолчанию namespace релиза
      serviceAccount: ""   # по умолчанию sa релиза
      nodeSelector: {}
      tolerations: []
      annotations: {}

worker:
  maxSyncWorkers: 10
  replicaCount: 3
  resources:
    requests:
      cpu: 100m
      memory: 100Mi
    limits:
      cpu: "3"
      memory: 4Gi

workloadLauncher:
  resources:
    requests:
      cpu: 100m
      memory: 100Mi
    limits:
      cpu: "3"
      memory: 4Gi

temporal:
  resources:
    requests:
      cpu: 100m
      memory: 100Mi
    limits:
      cpu: "3"
      memory: 4Gi

server:
  resources:
    requests:
      cpu: 100m
      memory: 100Mi
    limits:
      cpu: "3"
      memory: 4Gi

  # В 2.1 настройки builder-сервера переехали под server.connectorBuilder.*
  connectorBuilder:
    # заготовка, реальные значения зависят от вашей установки
    enabled: true

workloadApiServer:
  resources:
    requests:
      cpu: 100m
      memory: 100Mi
    limits:
      cpu: "3"
      memory: 4Gi
Что важно: 1. Helm V2 глобальные ключи В V2 часть env-переменных мапится на
global.*
(например,
AIRBYTE_URL → global.airbyteUrl
,
LOG_LEVEL → global.logging.level
,
JOB_KUBE_* → global.jobs.kube.*
). [Env mapping] 2. Переезд connector-builder-server в 2.1 В 2.1 компонент
connector-builder-server
убран, его конфиг теперь под
server.connectorBuilder.*
. Если у вас были старые настройки
connectorBuilderServer.*
в
values.yaml
, их нужно перенести. [2.1 notes] 3. Полный референс Для точной подгонки под вашу версию лучше свериться с актуальным
charts/v2/airbyte/values.yaml
в репозитории — в документации он указан как основной референс. [Values reference] Поскольку в знаниях нет конкретно схемы ConfigMap
airbyte-abctl-airbyte-env
и списка всех обязательных ключей для вашей версии abctl, я не могу гарантировать, что этого конфига достаточно, чтобы полностью убрать все ошибки. Рекомендую: • взять этот пример как основу, • затем сравнить его с официальным
values.yaml
из GitHub для вашей версии Airbyte/Helm, • и постепенно добавлять недостающие блоки, которые там помечены как обязательные. 👍 0 button 👎 0 button ℹ️ Tip: Mention @kapa.ai in the thread for follow-ups or DM the app for 1-to-1 help.
b
@kapa.ai скинь ссылку на акутальный values.yaml пример, нужно нам добавить connector_builder новый, но мы не понимаем как
k
Для актуального примера
values.yaml
для Helm chart v2 Airbyte есть два основных источника: 1. Документация Airbyte с ссылкой на полный пример на GitHub: Values.yaml reference [Values reference] 2. Непосредственно файл в репозитории (актуальный для chart v2): charts/v2/airbyte/values.yaml на GitHub [Values reference] По поводу connector builder: • В Airbyte 2.1 компонент
connector-builder-server
в Helm-чарте был заменён на manifest server, а конфиги
connectorBuilderServer.*
переехали под новые ключи. [2.1 release notes] • Для Helm chart v2 в документации по кастомным компонентам указано, что вместо старого
connectorBuilderServer.extraEnv
нужно использовать
manifestServer.extraEnv
(для передачи, например,
AIRBYTE_ENABLE_UNSAFE_CODE
). [Docs PR 77810] То есть, ориентироваться нужно на блок
manifestServer
в актуальном
values.yaml
из репозитория и примеры из документации по Helm chart v2, а все старые примеры с
connectorBuilderServer
относятся только к chart v1. 👍 0 button 👎 0 button ℹ️ Tip: Mention @kapa.ai in the thread for follow-ups or DM the app for 1-to-1 help.