[PR #29] [MERGED] Introduce command to squash-authorship logs #216

Closed
opened 2026-03-02 04:12:58 +03:00 by kerem · 0 comments
Owner

📋 Pull Request Information

Original PR: https://github.com/git-ai-project/git-ai/pull/29
Author: @acunniffe
Created: 9/27/2025
Status: Merged
Merged: 9/27/2025
Merged by: @acunniffe

Base: mainHead: feat/track-squash-rebase


📝 Commits (9)

  • 292fc3e implemented method for dealing with out of order authorship
  • ed9a488 pulls and saves prompt
  • b695fc0 change signature. Only require a HEAD sha
  • e98d3f7 rename module
  • fa2d97b verified works with out of band
  • e33ba77 added submodule with squash examples plus snapshot tests
  • 1a5417a logging added for squash rebase
  • 22bd163 submodules fix
  • e010d30 fixing workflow

📊 Changes

10 files changed (+862 additions, -4 deletions)

View changed files

📝 .github/workflows/test.yml (+3 -0)
.gitmodules (+3 -0)
📝 src/commands/mod.rs (+1 -0)
src/commands/rebase_authorship.rs (+719 -0)
src/commands/snapshots/git_ai__commands__rebase_authorship__tests__in_order.snap (+39 -0)
src/commands/snapshots/git_ai__commands__rebase_authorship__tests__with_out_of_band_commits.snap (+42 -0)
📝 src/log_fmt/authorship_log.rs (+4 -4)
📝 src/main.rs (+14 -0)
📝 src/utils.rs (+36 -0)
tests/gitflow-repo (+1 -0)

📄 Description

An engineer at Atlassian reported that authorship logs are disconnected from history when they squash and merge.

This PR introduces an internal command to rebuild an accurate authorship log and link it to the squash sha

git-ai squash-authorship <ref_or_branch> <post_squash_sha> <head_sha>


implementation for local

(in progress)

we'll wrap merge --squash and rebase commands so users who take these actions locally will have authorship logs generated before they push.


implementation for squash + merge buttons on SCM tools -- this is harder.

(not done, but plan in progress)

  • gh | gl | bbc apps
  • ci actions triggered by rewrites and merges.

how it works:

take this origin/main:
new_sha
out_of_band_2
out_of_band_1
base

We have a PR built on base that was just squashed into new_sha

  1. Find common origin (base)
  2. Collect all the commits between old_head and base
  3. Get parent of new_sha. In this case out_of_band_2
  4. Create diff from base <> out_of_band_2
  5. Take old_head and create a hanging commit where we apply diff from step 4 (accept ours). This step basically gives us the same working tree as we have on main, but with the git history.
  6. Now get diff from new_commit <> out_of_band_2
  7. Create an empty authorship log. Iterate every hunk in that diff and run our blame logic. If it says that any of the code is AI generated in a commit we got in step 2, copy it to authorship log.
  8. Write that authorship log ref/ai/authorship/new_commit
  9. Delete the hanging commit

Note

Adds a new squash-authorship command that reconstructs AI authorship for squashed/rebased commits using blame-based diff analysis, with tests and CI/submodule updates.

  • CLI:
    • Add squash-authorship command and help text; restrict to git-ai binary.
  • Core logic:
    • New src/commands/rebase_authorship.rs implementing rewrite_authorship_after_squash_or_rebase using merge-base discovery, hanging commit, diff application, and blame-driven reconstruction (run_blame_in_context).
    • Register module in src/commands/mod.rs.
  • Authorship log API:
    • Make AttributionEntry::{add_lines, remove_lines, is_empty} and AuthorshipLog::generate_author_key public.
  • Utils:
    • Add utils::print_diff helper.
  • Tests:
    • Add snapshot tests and test fixture submodule tests/gitflow-repo with snapshots under src/commands/snapshots/....
  • CI:
    • Update workflow to checkout submodules (submodules: true, fetch-depth: 0).
  • Repo config:
    • Add .gitmodules for tests/gitflow-repo.

Written by Cursor Bugbot for commit e010d309a8. This will update automatically on new commits. Configure here.


🔄 This issue represents a GitHub Pull Request. It cannot be merged through Gitea due to API limitations.

## 📋 Pull Request Information **Original PR:** https://github.com/git-ai-project/git-ai/pull/29 **Author:** [@acunniffe](https://github.com/acunniffe) **Created:** 9/27/2025 **Status:** ✅ Merged **Merged:** 9/27/2025 **Merged by:** [@acunniffe](https://github.com/acunniffe) **Base:** `main` ← **Head:** `feat/track-squash-rebase` --- ### 📝 Commits (9) - [`292fc3e`](https://github.com/git-ai-project/git-ai/commit/292fc3e58c389a194ef62aa212e2bc23b209d9cf) implemented method for dealing with out of order authorship - [`ed9a488`](https://github.com/git-ai-project/git-ai/commit/ed9a488d181db188ce36e6909f5c6a46290af1de) pulls and saves prompt - [`b695fc0`](https://github.com/git-ai-project/git-ai/commit/b695fc090b6abf27770408140e82698cceec9b12) change signature. Only require a HEAD sha - [`e98d3f7`](https://github.com/git-ai-project/git-ai/commit/e98d3f71898774bf01912961944e8052fec98359) rename module - [`fa2d97b`](https://github.com/git-ai-project/git-ai/commit/fa2d97b2e57d4e4e1dac412c87c2c2a13ad4a91f) verified works with out of band - [`e33ba77`](https://github.com/git-ai-project/git-ai/commit/e33ba77e7467c5bfb9df4ba173034c07bf346ea4) added submodule with squash examples plus snapshot tests - [`1a5417a`](https://github.com/git-ai-project/git-ai/commit/1a5417a192df81bd7935fc79c0a49f75d26d14f7) logging added for squash rebase - [`22bd163`](https://github.com/git-ai-project/git-ai/commit/22bd163f520368180c910894067b4de1e9f1bf9e) submodules fix - [`e010d30`](https://github.com/git-ai-project/git-ai/commit/e010d309a88d642ba53cececdfdb01ef9742a381) fixing workflow ### 📊 Changes **10 files changed** (+862 additions, -4 deletions) <details> <summary>View changed files</summary> 📝 `.github/workflows/test.yml` (+3 -0) ➕ `.gitmodules` (+3 -0) 📝 `src/commands/mod.rs` (+1 -0) ➕ `src/commands/rebase_authorship.rs` (+719 -0) ➕ `src/commands/snapshots/git_ai__commands__rebase_authorship__tests__in_order.snap` (+39 -0) ➕ `src/commands/snapshots/git_ai__commands__rebase_authorship__tests__with_out_of_band_commits.snap` (+42 -0) 📝 `src/log_fmt/authorship_log.rs` (+4 -4) 📝 `src/main.rs` (+14 -0) 📝 `src/utils.rs` (+36 -0) ➕ `tests/gitflow-repo` (+1 -0) </details> ### 📄 Description An engineer at Atlassian reported that[ authorship logs are disconnected from history when they squash and merge](https://github.com/acunniffe/git-ai/issues/24). This PR introduces an internal command to rebuild an accurate authorship log and link it to the squash sha git-ai squash-authorship <ref_or_branch> <post_squash_sha> <head_sha> --- implementation for local (in progress) we'll wrap `merge --squash` and rebase commands so users who take these actions locally will have authorship logs generated before they push. --- implementation for squash + merge buttons on SCM tools -- this is harder. (not done, but plan in progress) - gh | gl | bbc apps - ci actions triggered by rewrites and merges. --- how it works: take this origin/main: new_sha out_of_band_2 out_of_band_1 base We have a PR built on base that was just squashed into new_sha 1. Find common origin (base) 2. Collect all the commits between old_head and base 3. Get parent of new_sha. In this case out_of_band_2 4. Create diff from base <> out_of_band_2 5. Take old_head and create a hanging commit where we apply diff from step 4 (accept ours). This step basically gives us the same working tree as we have on main, but with the git history. 6. Now get diff from new_commit <> out_of_band_2 7. Create an empty authorship log. Iterate every hunk in that diff and run our blame logic. If it says that any of the code is AI generated in a commit we got in step 2, copy it to authorship log. 8. Write that authorship log ref/ai/authorship/new_commit 9. Delete the hanging commit <!-- CURSOR_SUMMARY --> --- > [!NOTE] > Adds a new squash-authorship command that reconstructs AI authorship for squashed/rebased commits using blame-based diff analysis, with tests and CI/submodule updates. > > - **CLI**: > - Add `squash-authorship` command and help text; restrict to `git-ai` binary. > - **Core logic**: > - New `src/commands/rebase_authorship.rs` implementing `rewrite_authorship_after_squash_or_rebase` using merge-base discovery, hanging commit, diff application, and blame-driven reconstruction (`run_blame_in_context`). > - Register module in `src/commands/mod.rs`. > - **Authorship log API**: > - Make `AttributionEntry::{add_lines, remove_lines, is_empty}` and `AuthorshipLog::generate_author_key` public. > - **Utils**: > - Add `utils::print_diff` helper. > - **Tests**: > - Add snapshot tests and test fixture submodule `tests/gitflow-repo` with snapshots under `src/commands/snapshots/...`. > - **CI**: > - Update workflow to checkout submodules (`submodules: true`, `fetch-depth: 0`). > - **Repo config**: > - Add `.gitmodules` for `tests/gitflow-repo`. > > <sup>Written by [Cursor Bugbot](https://cursor.com/dashboard?tab=bugbot) for commit e010d309a88d642ba53cececdfdb01ef9742a381. This will update automatically on new commits. Configure [here](https://cursor.com/dashboard?tab=bugbot).</sup> <!-- /CURSOR_SUMMARY --> --- <sub>🔄 This issue represents a GitHub Pull Request. It cannot be merged through Gitea due to API limitations.</sub>
kerem 2026-03-02 04:12:58 +03:00
Sign in to join this conversation.
No milestone
No project
No assignees
1 participant
Notifications
Due date
The due date is invalid or out of range. Please use the format "yyyy-mm-dd".

No due date set.

Dependencies

No dependencies set.

Reference
starred/git-ai#216
No description provided.