From: Karthik Nayak <karthik.188@gmail.com>
To: git@vger.kernel.org
Cc: Karthik Nayak <karthik.188@gmail.com>, ps@pks.im, toon@iotcl.com
Subject: [PATCH v3 0/9] refs: move some of the generic logic out of the backends
Date: Mon, 27 Apr 2026 12:42:01 +0200 [thread overview]
Message-ID: <20260427-refs-move-to-generic-layer-v3-0-e4638dfb7897@gmail.com> (raw)
In-Reply-To: <20260420-refs-move-to-generic-layer-v1-0-513e354f376b@gmail.com>
This series came together while I was working on other reference related
code and realized that some of the individual logic implemented with the
reference backends can be moved to the generic layer.
Moving code to the generic layer, simplifies the responsibility of
individual backends and avoids deviation in logic between the backends.
The biggest changes are related to moving out usage of `parse_object()`
and `peel_object()` from reference transactions. The former is used to
validate that the OID provided points to a commit object. The latter is
an optimization technique where the packed/reftable backend store the
peeled OID whenever available, so reading such references provides the
peeled OID without having to call the ODB.
Moving object parsing to the generic layout involves moving it out of
the prepare stage of the transaction and into `ref_transaction_update()`
where every added update is checked. As such, this also involves
modifying update-ref(1) and receive-pack(1) to follow this paradigm.
---
Changes in v3:
- Remove an unwanted change which creeped up during a rebase.
- Add information in the commit message around how the order of errors
in git-update-ref(1) will change while maintaining functionality.
- Change up the order of an `if..else` to make it clearer.
- Other small typos and fixes.
- Link to v2: https://patch.msgid.link/20260423-refs-move-to-generic-layer-v2-0-ae5a4f146d7d@gmail.com
Changes in v2:
- Split the second commit into two: one introducing
`ref_store_init_options` and the second to use it for reflog config.
- Use opts as the variable name consistently.
- A bunch of grammar fixes.
- Link to v1: https://patch.msgid.link/20260420-refs-move-to-generic-layer-v1-0-513e354f376b@gmail.com
---
builtin/receive-pack.c | 22 ++++---
builtin/update-ref.c | 151 +++++++++++++++++++++++++++++++-----------------
refs.c | 60 ++++++++++++++-----
refs.h | 16 ++---
refs/files-backend.c | 58 +++++++------------
refs/packed-backend.c | 10 ++--
refs/packed-backend.h | 3 +-
refs/refs-internal.h | 35 +++++++++--
refs/reftable-backend.c | 40 +++----------
9 files changed, 231 insertions(+), 164 deletions(-)
Karthik Nayak (9):
refs: remove unused typedef 'ref_transaction_commit_fn'
refs: introduce `ref_store_init_options`
refs: extract out reflog config to generic layer
refs: return `ref_transaction_error` from `ref_transaction_update()`
update-ref: move `print_rejected_refs()` up
update-ref: handle rejections while adding updates
refs: move object parsing to the generic layer
refs: add peeled object ID to the `ref_update` struct
refs: use peeled tag values in reference backends
Range-diff versus v2:
1: b8ab8a6c8b = 1: 704a218bce refs: remove unused typedef 'ref_transaction_commit_fn'
2: dd419614e0 ! 2: f3e0caa8e4 refs: introduce `ref_store_init_options`
@@ refs/files-backend.c: static struct ref_store *files_ref_store_init(struct repos
refs->gitcommondir = strbuf_detach(&ref_common_dir, NULL);
refs->packed_ref_store =
- packed_ref_store_init(repo, NULL, refs->gitcommondir, flags);
-+ packed_ref_store_init(repo, payload, refs->gitcommondir, opts);
++ packed_ref_store_init(repo, NULL, refs->gitcommondir, opts);
+ refs->store_flags = opts->access_flags;
refs->log_all_ref_updates = repo_settings_get_log_all_ref_updates(repo);
+
3: 337e5c8c5b ! 3: 48ebcc2438 refs: extract out reflog config to generic layer
@@ refs.c: static struct ref_store *ref_store_init(struct repository *repo,
## refs/files-backend.c ##
@@ refs/files-backend.c: static struct ref_store *files_ref_store_init(struct repository *repo,
refs->packed_ref_store =
- packed_ref_store_init(repo, payload, refs->gitcommondir, opts);
+ packed_ref_store_init(repo, NULL, refs->gitcommondir, opts);
refs->store_flags = opts->access_flags;
- refs->log_all_ref_updates = repo_settings_get_log_all_ref_updates(repo);
+ refs->log_all_ref_updates = opts->log_all_ref_updates;
4: cdb4aad11e = 4: d4c120ab28 refs: return `ref_transaction_error` from `ref_transaction_update()`
5: 454549240a = 5: 6e3b16258c update-ref: move `print_rejected_refs()` up
6: 1f224fb868 ! 6: 505c5b8edb update-ref: handle rejections while adding updates
@@ Commit message
rejected, and also checking for rejections and only dying for generic
failures.
+ Errors encountered during updates will be shown to the user immediately
+ unlike other errors encountered only when the transaction is
+ prepared/committed. As the verification of object IDs and peeled tag
+ objects will move into `ref_transaction_update()` in the following
+ commit, this means that those errors will be shown to the user before
+ other errors, this changes the order of errors, but the functionality
+ remains the same.
+
Signed-off-by: Karthik Nayak <karthik.188@gmail.com>
## builtin/update-ref.c ##
@@ builtin/update-ref.c: static void parse_cmd_update(struct ref_transaction *trans
+ update_flags | create_reflog_flag,
+ msg, &err);
+
-+ if (tx_err && tx_err != REF_TRANSACTION_ERROR_GENERIC &&
-+ opts->allow_update_failures) {
++ /*
++ * Generic errors are non-recoverable, so we cannot skip the update
++ * or mark it as rejected.
++ */
++ if (tx_err == REF_TRANSACTION_ERROR_GENERIC)
+ die("%s", err.buf);
+
++ if (tx_err && opts->allow_update_failures)
+ print_rejected_refs(refname, have_old ? &old_oid : NULL,
+ &new_oid, NULL, NULL, tx_err, err.buf,
+ NULL);
-+ } else if (tx_err) {
- die("%s", err.buf);
-+ }
-
++
update_flags = default_flags;
free(refname);
-@@ builtin/update-ref.c: static void parse_cmd_update(struct ref_transaction *transaction,
+ strbuf_release(&err);
}
static void parse_cmd_symref_update(struct ref_transaction *transaction,
@@ builtin/update-ref.c: static void parse_cmd_symref_update(struct ref_transaction
+ update_flags | create_reflog_flag,
+ msg, &err);
+
-+ if (tx_err && tx_err != REF_TRANSACTION_ERROR_GENERIC &&
-+ opts->allow_update_failures) {
++ /*
++ * Generic errors are non-recoverable, so we cannot skip the update
++ * or mark it as rejected.
++ */
++ if (tx_err == REF_TRANSACTION_ERROR_GENERIC)
+ die("%s", err.buf);
+
++ if (tx_err && opts->allow_update_failures)
+ print_rejected_refs(refname, have_old_oid ? &old_oid : NULL,
+ NULL, have_old_oid ? NULL : old_target,
+ new_target, tx_err, err.buf, NULL);
-+ } else if (tx_err) {
- die("%s", err.buf);
-+ }
-
++
update_flags = default_flags;
free(refname);
+ free(old_arg);
@@ builtin/update-ref.c: static void parse_cmd_symref_update(struct ref_transaction *transaction,
}
7: a52b019afa ! 7: ad1aae6b35 refs: move object parsing to the generic layer
@@ builtin/receive-pack.c: static const char *update(struct command *cmd, struct sh
- }
- else {
+ } else {
-+ enum ref_transaction_error err_type;
++ enum ref_transaction_error tx_err;
struct strbuf err = STRBUF_INIT;
if (shallow_update && si->shallow_ref[cmd->index] &&
update_shallow_ref(cmd, si)) {
@@ builtin/receive-pack.c: static const char *update(struct command *cmd, struct sh
- NULL, NULL,
- 0, "push",
- &err)) {
-+ err_type = ref_transaction_update(transaction,
++ tx_err = ref_transaction_update(transaction,
+ namespaced_name,
+ new_oid, old_oid,
+ NULL, NULL,
+ 0, "push",
+ &err);
-+ if (err_type) {
++ if (tx_err) {
rp_error("%s", err.buf);
- ret = "failed to update ref";
-+ if (err_type == REF_TRANSACTION_ERROR_GENERIC)
++ if (tx_err == REF_TRANSACTION_ERROR_GENERIC)
+ ret = "failed to update ref";
+ else
-+ ret = ref_transaction_error_msg(err_type);
++ ret = ref_transaction_error_msg(tx_err);
} else {
ret = NULL; /* good */
}
8: aa5fd09831 ! 8: 5cb7ee9853 refs: add peeled object ID to the `ref_update` struct
@@ Metadata
## Commit message ##
refs: add peeled object ID to the `ref_update` struct
- Certain reference backend {packed, reftable}, have the ability to also
+ Certain reference backends {packed, reftable}, have the ability to also
store the peeled object ID for a reference pointing to a tag object.
This has the added benefit that during retrieval of such references, we
also obtain the peeled object ID without having to use the ODB.
9: 96146b5083 = 9: ba34e10548 refs: use peeled tag values in reference backends
base-commit: f65aba1e87db64413b6d1ed5ae5a45b5a84a0997
change-id: 20260417-refs-move-to-generic-layer-f7525c5e8764
Thanks
- Karthik
next prev parent reply other threads:[~2026-04-27 10:42 UTC|newest]
Thread overview: 68+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-04-20 10:11 [PATCH 0/8] refs: move some of the generic logic out of the backends Karthik Nayak
2026-04-20 10:11 ` [PATCH 1/8] refs: remove unused typedef 'ref_transaction_commit_fn' Karthik Nayak
2026-04-22 11:15 ` Patrick Steinhardt
2026-04-22 12:20 ` Karthik Nayak
2026-04-20 10:12 ` [PATCH 2/8] refs: extract out reflog config to generic layer Karthik Nayak
2026-04-22 11:15 ` Patrick Steinhardt
2026-04-22 13:13 ` Karthik Nayak
2026-04-20 10:12 ` [PATCH 3/8] refs: return `ref_transaction_error` from `ref_transaction_update()` Karthik Nayak
2026-04-22 11:15 ` Patrick Steinhardt
2026-04-22 13:14 ` Karthik Nayak
2026-04-20 10:12 ` [PATCH 4/8] update-ref: move `print_rejected_refs()` up Karthik Nayak
2026-04-22 11:15 ` Patrick Steinhardt
2026-04-22 13:16 ` Karthik Nayak
2026-04-20 10:12 ` [PATCH 5/8] update-ref: handle rejections while adding updates Karthik Nayak
2026-04-22 11:15 ` Patrick Steinhardt
2026-04-22 14:13 ` Karthik Nayak
2026-04-20 10:12 ` [PATCH 6/8] refs: move object parsing to the generic layer Karthik Nayak
2026-04-22 11:15 ` Patrick Steinhardt
2026-04-22 15:03 ` Karthik Nayak
2026-04-20 10:12 ` [PATCH 7/8] refs: add peeled object ID to the `ref_update` struct Karthik Nayak
2026-04-20 10:12 ` [PATCH 8/8] refs: use peeled tag values in reference backends Karthik Nayak
2026-04-23 8:40 ` [PATCH v2 0/9] refs: move some of the generic logic out of the backends Karthik Nayak
2026-04-23 8:40 ` [PATCH v2 1/9] refs: remove unused typedef 'ref_transaction_commit_fn' Karthik Nayak
2026-04-23 8:40 ` [PATCH v2 2/9] refs: introduce `ref_store_init_options` Karthik Nayak
2026-04-23 8:52 ` Patrick Steinhardt
2026-04-24 9:34 ` Karthik Nayak
2026-04-23 8:40 ` [PATCH v2 3/9] refs: extract out reflog config to generic layer Karthik Nayak
2026-04-23 8:52 ` Patrick Steinhardt
2026-04-23 8:40 ` [PATCH v2 4/9] refs: return `ref_transaction_error` from `ref_transaction_update()` Karthik Nayak
2026-04-24 11:01 ` Toon Claes
2026-04-23 8:40 ` [PATCH v2 5/9] update-ref: move `print_rejected_refs()` up Karthik Nayak
2026-04-23 8:40 ` [PATCH v2 6/9] update-ref: handle rejections while adding updates Karthik Nayak
2026-04-23 8:52 ` Patrick Steinhardt
2026-04-24 9:35 ` Karthik Nayak
2026-04-24 11:22 ` Toon Claes
2026-04-27 8:47 ` Karthik Nayak
2026-04-23 8:40 ` [PATCH v2 7/9] refs: move object parsing to the generic layer Karthik Nayak
2026-04-24 12:06 ` Toon Claes
2026-04-27 9:32 ` Karthik Nayak
2026-04-23 8:40 ` [PATCH v2 8/9] refs: add peeled object ID to the `ref_update` struct Karthik Nayak
2026-04-24 16:44 ` Toon Claes
2026-04-27 9:33 ` Karthik Nayak
2026-04-23 8:40 ` [PATCH v2 9/9] refs: use peeled tag values in reference backends Karthik Nayak
2026-04-27 10:42 ` Karthik Nayak [this message]
2026-04-27 10:42 ` [PATCH v3 1/9] refs: remove unused typedef 'ref_transaction_commit_fn' Karthik Nayak
2026-04-27 10:42 ` [PATCH v3 2/9] refs: introduce `ref_store_init_options` Karthik Nayak
2026-04-27 10:42 ` [PATCH v3 3/9] refs: extract out reflog config to generic layer Karthik Nayak
2026-04-27 10:42 ` [PATCH v3 4/9] refs: return `ref_transaction_error` from `ref_transaction_update()` Karthik Nayak
2026-04-27 10:42 ` [PATCH v3 5/9] update-ref: move `print_rejected_refs()` up Karthik Nayak
2026-04-27 10:42 ` [PATCH v3 6/9] update-ref: handle rejections while adding updates Karthik Nayak
2026-04-29 12:24 ` Toon Claes
2026-04-30 9:52 ` Karthik Nayak
2026-04-27 10:42 ` [PATCH v3 7/9] refs: move object parsing to the generic layer Karthik Nayak
2026-04-27 10:42 ` [PATCH v3 8/9] refs: add peeled object ID to the `ref_update` struct Karthik Nayak
2026-04-27 10:42 ` [PATCH v3 9/9] refs: use peeled tag values in reference backends Karthik Nayak
2026-05-04 17:44 ` [PATCH v4 0/9] refs: move some of the generic logic out of the backends Karthik Nayak
2026-05-04 17:44 ` [PATCH v4 1/9] refs: remove unused typedef 'ref_transaction_commit_fn' Karthik Nayak
2026-05-04 17:44 ` [PATCH v4 2/9] refs: introduce `ref_store_init_options` Karthik Nayak
2026-05-04 17:44 ` [PATCH v4 3/9] refs: extract out reflog config to generic layer Karthik Nayak
2026-05-04 17:44 ` [PATCH v4 4/9] refs: return `ref_transaction_error` from `ref_transaction_update()` Karthik Nayak
2026-05-04 17:44 ` [PATCH v4 5/9] update-ref: move `print_rejected_refs()` up Karthik Nayak
2026-05-04 17:44 ` [PATCH v4 6/9] update-ref: handle rejections while adding updates Karthik Nayak
2026-05-05 5:52 ` Patrick Steinhardt
2026-05-05 8:23 ` Karthik Nayak
2026-05-06 19:44 ` Toon Claes
2026-05-04 17:44 ` [PATCH v4 7/9] refs: move object parsing to the generic layer Karthik Nayak
2026-05-04 17:44 ` [PATCH v4 8/9] refs: add peeled object ID to the `ref_update` struct Karthik Nayak
2026-05-04 17:44 ` [PATCH v4 9/9] refs: use peeled tag values in reference backends Karthik Nayak
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20260427-refs-move-to-generic-layer-v3-0-e4638dfb7897@gmail.com \
--to=karthik.188@gmail.com \
--cc=git@vger.kernel.org \
--cc=ps@pks.im \
--cc=toon@iotcl.com \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox