From 5f5c4d13bb841cb5e8958c8cc3654bdcef9be720 Mon Sep 17 00:00:00 2001
From: Michael Kriese <michael.kriese@visualon.de>
Date: Mon, 27 Jan 2025 15:46:47 +0100
Subject: [PATCH] fix(gitea): platform automerge only fully works on Gitea
 v1.24 and Forgejo v10 (#33871)

---
 lib/modules/platform/gitea/index.spec.ts | 26 ++++++++++--------------
 lib/modules/platform/gitea/index.ts      | 12 ++++++-----
 lib/modules/platform/gitea/readme.md     |  2 +-
 lib/modules/platform/gitea/types.ts      |  1 +
 4 files changed, 20 insertions(+), 21 deletions(-)

diff --git a/lib/modules/platform/gitea/index.spec.ts b/lib/modules/platform/gitea/index.spec.ts
index 23494f1ed8..53ce4256ad 100644
--- a/lib/modules/platform/gitea/index.spec.ts
+++ b/lib/modules/platform/gitea/index.spec.ts
@@ -1679,7 +1679,7 @@ describe('modules/platform/gitea/index', () => {
         .reply(200, mockNewPR)
         .post('/repos/some/repo/pulls/42/merge')
         .reply(200);
-      await initFakePlatform(scope, '1.17.0');
+      await initFakePlatform(scope, '1.24.0');
       await initFakeRepo(scope);
 
       const res = await gitea.createPr({
@@ -1697,16 +1697,14 @@ describe('modules/platform/gitea/index', () => {
       expect(mergePR).toHaveBeenCalled();
     });
 
-    it('should use platform automerge on forgejo v7', async () => {
+    it('should not use platform automerge on forgejo v7', async () => {
       memCache.set('gitea-pr-cache-synced', true);
       const helper = await import('./gitea-helper');
       const mergePR = jest.spyOn(helper, 'mergePR');
       const scope = httpMock
         .scope('https://gitea.com/api/v1')
         .post('/repos/some/repo/pulls')
-        .reply(200, mockNewPR)
-        .post('/repos/some/repo/pulls/42/merge')
-        .reply(200);
+        .reply(200, mockNewPR);
       await initFakePlatform(scope, '7.0.0-dev-2136-f075579c95+gitea-1.22.0');
       await initFakeRepo(scope);
 
@@ -1722,19 +1720,17 @@ describe('modules/platform/gitea/index', () => {
         number: 42,
         title: 'pr-title',
       });
-      expect(mergePR).toHaveBeenCalled();
+      expect(mergePR).not.toHaveBeenCalled();
     });
 
-    it('should use platform automerge on forgejo v7 LTS', async () => {
+    it('should not use platform automerge on forgejo v7 LTS', async () => {
       memCache.set('gitea-pr-cache-synced', true);
       const helper = await import('./gitea-helper');
       const mergePR = jest.spyOn(helper, 'mergePR');
       const scope = httpMock
         .scope('https://gitea.com/api/v1')
         .post('/repos/some/repo/pulls')
-        .reply(200, mockNewPR)
-        .post('/repos/some/repo/pulls/42/merge')
-        .reply(200);
+        .reply(200, mockNewPR);
       await initFakePlatform(scope, '7.0.0+LTS-gitea-1.22.0');
       await initFakeRepo(scope);
 
@@ -1750,7 +1746,7 @@ describe('modules/platform/gitea/index', () => {
         number: 42,
         title: 'pr-title',
       });
-      expect(mergePR).toHaveBeenCalled();
+      expect(mergePR).not.toHaveBeenCalled();
     });
 
     it('continues on platform automerge error', async () => {
@@ -1761,7 +1757,7 @@ describe('modules/platform/gitea/index', () => {
         .reply(200, mockNewPR)
         .post('/repos/some/repo/pulls/42/merge')
         .replyWithError('unknown error');
-      await initFakePlatform(scope, '1.17.0');
+      await initFakePlatform(scope, '1.24.0');
       await initFakeRepo(scope);
 
       const res = await gitea.createPr({
@@ -1805,7 +1801,7 @@ describe('modules/platform/gitea/index', () => {
       });
       expect(logger.debug).toHaveBeenCalledWith(
         expect.objectContaining({ prNumber: 42 }),
-        'Gitea-native automerge: not supported on this version of Gitea. Use 1.17.0 or newer.',
+        'Gitea-native automerge: not supported on this version of Gitea. Use 1.24.0 or newer.',
       );
     });
 
@@ -1817,7 +1813,7 @@ describe('modules/platform/gitea/index', () => {
         .reply(200, mockNewPR)
         .post('/repos/some/repo/pulls/42/merge')
         .reply(200);
-      await initFakePlatform(scope, '1.17.0');
+      await initFakePlatform(scope, '10.0.0+gitea-1.22.0');
       await initFakeRepo(scope);
 
       const res = await gitea.createPr({
@@ -1856,7 +1852,7 @@ describe('modules/platform/gitea/index', () => {
             Do: prMergeStrategy,
             merge_when_checks_succeed: true,
           });
-        await initFakePlatform(scope, '1.17.0');
+        await initFakePlatform(scope, '1.24.0');
         await initFakeRepo(scope);
 
         const res = await gitea.createPr({
diff --git a/lib/modules/platform/gitea/index.ts b/lib/modules/platform/gitea/index.ts
index 73b5b6a442..369edaad36 100644
--- a/lib/modules/platform/gitea/index.ts
+++ b/lib/modules/platform/gitea/index.ts
@@ -214,9 +214,6 @@ const platform: Platform = {
       botUserName = user.username;
       defaults.version = await helper.getVersion({ token });
       if (defaults.version?.includes('gitea-')) {
-        defaults.version = defaults.version.substring(
-          defaults.version.indexOf('gitea-') + 6,
-        );
         defaults.isForgejo = true;
       }
     } catch (err) {
@@ -551,13 +548,18 @@ const platform: Platform = {
       });
 
       if (platformPrOptions?.usePlatformAutomerge) {
-        if (semver.gte(defaults.version, '1.17.0')) {
+        // Only Gitea v1.24.0+ and Forgejo v10.0.0+ support delete_branch_after_merge.
+        // This is required to not have undesired behavior when renovate finds existing branches on next run.
+        if (
+          semver.gte(defaults.version, defaults.isForgejo ? '10.0.0' : '1.24.0')
+        ) {
           try {
             await helper.mergePR(config.repository, gpr.number, {
               Do:
                 getMergeMethod(platformPrOptions?.automergeStrategy) ??
                 config.mergeMethod,
               merge_when_checks_succeed: true,
+              delete_branch_after_merge: true,
             });
 
             logger.debug(
@@ -573,7 +575,7 @@ const platform: Platform = {
         } else {
           logger.debug(
             { prNumber: gpr.number },
-            'Gitea-native automerge: not supported on this version of Gitea. Use 1.17.0 or newer.',
+            `Gitea-native automerge: not supported on this version of ${defaults.isForgejo ? 'Forgejo' : 'Gitea'}. Use ${defaults.isForgejo ? '10.0.0' : '1.24.0'} or newer.`,
           );
         }
       }
diff --git a/lib/modules/platform/gitea/readme.md b/lib/modules/platform/gitea/readme.md
index 8159630fc6..4e88c42739 100644
--- a/lib/modules/platform/gitea/readme.md
+++ b/lib/modules/platform/gitea/readme.md
@@ -31,7 +31,7 @@ If you use Gitea packages, add the `read:packages` scope.
 ## Unsupported platform features/concepts
 
 - **Adding reviewers to PRs not supported**: Gitea versions older than `v1.14.0` do not have the required API.
-- **`platformAutomerge` (`true` by default) for platform-native automerge not supported**: Gitea versions older than v1.17.0 do not have the required API.
+- **`platformAutomerge` (`true` by default) for platform-native automerge not supported**: Gitea versions older than v1.24.0 and Forgejo versions older than v10.0.0 don't support required branch autodelete for automerge.
 - **Git upload filters**: If you're using a Gitea version older than `v1.16.0` then you must enable [clone filters](https://docs.gitea.io/en-us/clone-filters/).
 
 ## Features awaiting implementation
diff --git a/lib/modules/platform/gitea/types.ts b/lib/modules/platform/gitea/types.ts
index 9a20bad147..dd383c57de 100644
--- a/lib/modules/platform/gitea/types.ts
+++ b/lib/modules/platform/gitea/types.ts
@@ -199,6 +199,7 @@ export interface PRUpdateParams {
 export interface PRMergeParams {
   Do: PRMergeMethod;
   merge_when_checks_succeed?: boolean;
+  delete_branch_after_merge?: boolean;
 }
 
 export type CommentCreateParams = CommentUpdateParams;
-- 
GitLab