Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1tx7aD-003Be6-I4 for pgsql-general@arkaria.postgresql.org; Tue, 25 Mar 2025 16:56:57 +0000 Received: from localhost ([127.0.0.1] helo=malur.postgresql.org) by malur.postgresql.org with esmtp (Exim 4.94.2) (envelope-from ) id 1tx7aC-006yRX-44 for pgsql-general@arkaria.postgresql.org; Tue, 25 Mar 2025 16:56:56 +0000 Received: from magus.postgresql.org ([2a02:c0:301:0:ffff::29]) by malur.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1tx7aB-006yRO-OW for pgsql-general@lists.postgresql.org; Tue, 25 Mar 2025 16:56:55 +0000 Received: from mail-pj1-x1031.google.com ([2607:f8b0:4864:20::1031]) by magus.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 (Exim 4.96) (envelope-from ) id 1tx7a9-00179e-2L for pgsql-general@postgresql.org; Tue, 25 Mar 2025 16:56:55 +0000 Received: by mail-pj1-x1031.google.com with SMTP id 98e67ed59e1d1-301302a328bso11161272a91.2 for ; Tue, 25 Mar 2025 09:56:53 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20230601; t=1742921811; x=1743526611; darn=postgresql.org; h=to:subject:message-id:date:from:mime-version:from:to:cc:subject :date:message-id:reply-to; bh=Zrd+9KkooOoafhjHsip79eVn/wGT6tGHPTtt2Qc20W4=; b=aWomrh//5N6DNWgfGENY2nFu/F1pJ3gzxALZazaFe4L+yZXOO1KJaN8fR1QrLWgdQ+ bmQXipR6FdM1j8RLU/T2Zc5+K/rf3xD7lwvZrcAyh2/h6IEHkF3I8v858V4h6kUa/WoH G+x25RlLPBiXgGa00caKS/+IRI7PGjVp9ttfHBW9QR015dnmwqZcJyVEolwERO6z4yO/ vlO/xXKwmMDKKySrq76KQVmv4nIMVst/1HY9w3koRaouZ5HYCvL5LpsZTSnO3HxsgpU4 V6L3dUJCV6HeiQUu1p0/0WSjmx0ykJ/jXWRsijJoN26Rdz7vuzxHl0bTuNMFd3CtLF1C fe8A== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1742921811; x=1743526611; h=to:subject:message-id:date:from:mime-version:x-gm-message-state :from:to:cc:subject:date:message-id:reply-to; bh=Zrd+9KkooOoafhjHsip79eVn/wGT6tGHPTtt2Qc20W4=; b=w2xNArN+XaVCg099w+bY3urK5rsIvFRlOAjy36TgzM14hbA2YegqvlXwHLsv8fta/K 67Zb2zJqPDNKUWsKdnebzPRoHSjjwbqtI7gVdPIHepXMAbQCKHlmPrFvNdM3Ez+YQVda QKi5SAEHyw0hoYLIExoonzMeJOfJnXY+HQopJIsJIiZad5btzgVTk66J1FyrfNODYYX1 cOQoeZSiRWtasy28UiIsRxpC8hJPTmaAoiRgBnfAwX5TmHb84/krgDxRn9imQ4ciwFZi EnUbFM/EF7OPoCiPQOn8Wx/WhoMPf1Ba49RcfvK6ddwJsBsdTzZvTxlwwjcJKUj5xbpk XvKA== X-Gm-Message-State: AOJu0YxT3s2sTxu++D6TO2vGX9fp+exjcw+qFgSkKog8OxIHMk2Ixjil PfLuBY7roYeNr3yrnw6o8pBUzsZVZuzYzdfIokqsabku4ahtPsmGbUXvyatNRPyOznPefiTmMXR h8HLKivrORiEWDcfHoWDB7nqxkIvOY/61KnVGhA== X-Gm-Gg: ASbGncvVAKSwvW4ouN9SWohnT7BgZdZNHbEhp4KCi1VQbx7VUxNoGOJkg2PtVkJTOw/ HvSMlo6XacayaxqYPBSKDzBD8v+PCYvz/DhjIJRQalQU7cSfisafpJgCwVkC1IRWqNkLQ/jadE8 CTSrlG5Q7V52PXy6jLzmM7anc6 X-Google-Smtp-Source: AGHT+IGRcnZ6rI12W3r+5+nA43wtswS80EzSc6fE3T7EfKpcRseaMtlb4mQUnsGW0rEbrfJ5YkguJ+IqiZNE7CpCBn0= X-Received: by 2002:a17:90b:54cf:b0:2ff:6fc3:79c3 with SMTP id 98e67ed59e1d1-3030fe83a34mr30850031a91.9.1742921811151; Tue, 25 Mar 2025 09:56:51 -0700 (PDT) MIME-Version: 1.0 From: Phillip Diffley Date: Tue, 25 Mar 2025 11:56:39 -0500 X-Gm-Features: AQ5f1JqlLenrbdxq8otZ9JgF1RlAc8kp5EUcUI9zjW-PmV3BHqf4b3FJ1nscrzc Message-ID: Subject: Replication slot WAL reservation To: pgsql-general@postgresql.org Content-Type: multipart/alternative; boundary="0000000000006cd46e06312d9ba3" List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Archived-At: Precedence: bulk --0000000000006cd46e06312d9ba3 Content-Type: text/plain; charset="UTF-8" I am trying to understand how logical replication slots work, specifically in regard to how WAL is reserved and freed by a replication slot. My current understanding of the WAL (set to wal_level logical) is that: 1. Every DML operation (insert, update, delete, truncate) will have a row in the WAL and that row will have an LSN assigned to it. 2. The LSNs are assigned when the operation happens. 3. Operations within a transaction are written to the WAL in a contiguous block when the transaction commits. 4. Each transaction block in the WAL has a commit timestamp associated with it, and these timestamps are monotonically increasing (I'm only inferring this, so please correct me if this is not always the case). A result of an operation being assigned an LSN when the operation occurs but not being recorded to the WAL until it's transaction commits is that LSNs in the WAL are not necessarily in order. But when processing data from a replication slot, we confirm rows that have been processed and can be deleted from the WAL based on the LSN (eg. with pg_replication_slot_advance). How does postgres identify what parts of the WAL can be freed? --0000000000006cd46e06312d9ba3 Content-Type: text/html; charset="UTF-8" Content-Transfer-Encoding: quoted-printable
I am trying to understand how l= ogical replication slots work, specifically in regard to how WAL is reserve= d and freed by a replication slot.

My current unde= rstanding of the WAL (set to wal_level logical) is that:
1. Every= DML operation (insert, update, delete, truncate) will have a row in the WA= L and that row will have an LSN assigned to it.=C2=A0
2. The LSNs= are assigned when the operation happens.
3. Operations within a = transaction are written to the WAL in a contiguous block when the transacti= on commits.
4. Each transaction block in the WAL has a commit tim= estamp associated with it, and these timestamps are monotonically increasin= g (I'm only inferring this, so please correct me if this is not always = the case).

A result of an operation being assigned= an LSN when the operation occurs but not being recorded to the WAL until i= t's transaction commits is that LSNs in the WAL are not necessarily in = order.

But when processing data from a replication= slot, we confirm rows that have been processed and can be deleted from the= WAL based on the LSN (eg. with pg_replication_slot_advance). How does post= gres identify what parts of the WAL can be freed?

--0000000000006cd46e06312d9ba3--