diff --git a/app-config.yaml b/app-config.yaml index c0bea41b34..b50de963ed 100644 --- a/app-config.yaml +++ b/app-config.yaml @@ -250,11 +250,10 @@ catalog: target: ../catalog-model/examples/acme-corp.yaml scaffolder: - # Use to customize commit author info used when new components are created - # git: - # author: - # name: Scaffolder - # email: scaffolder@backstage.io + # Use to customize default commit author info used when new components are created + # defaultAuthor: + # name: Scaffolder + # email: scaffolder@backstage.io github: token: ${GITHUB_TOKEN} visibility: public # or 'internal' or 'private' diff --git a/plugins/scaffolder-backend/config.d.ts b/plugins/scaffolder-backend/config.d.ts index 07602b649a..795fe5b112 100644 --- a/plugins/scaffolder-backend/config.d.ts +++ b/plugins/scaffolder-backend/config.d.ts @@ -17,14 +17,12 @@ export interface Config { /** Configuration options for the scaffolder plugin */ scaffolder?: { - git?: { - /** - * The commit author info used when new components are created. - */ - author?: { - name?: string; - email?: string; - }; + /** + * The commit author info used when new components are created. + */ + defaultAuthor?: { + name?: string; + email?: string; }; github?: { [key: string]: string; diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/azure.test.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/azure.test.ts index 6a1c8fdc55..b5c9bdcd89 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/azure.test.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/azure.test.ts @@ -191,6 +191,45 @@ describe('publish:azure', () => { }); }); + it('should call initRepoAndPush with the configured defaultAuthor', async () => { + const customAuthorConfig = new ConfigReader({ + integrations: { + azure: [ + { host: 'dev.azure.com', token: 'tokenlols' }, + { host: 'myazurehostnotoken.com' }, + ], + }, + scaffolder: { + defaultAuthor: { + name: 'Test', + email: 'example@example.com', + }, + }, + }); + + const customAuthorIntegrations = ScmIntegrations.fromConfig( + customAuthorConfig, + ); + const customAuthorAction = createPublishAzureAction({ + integrations: customAuthorIntegrations, + config: customAuthorConfig, + }); + + mockGitClient.createRepository.mockImplementation(() => ({ + remoteUrl: 'https://dev.azure.com/organization/project/_git/repo', + })); + + await customAuthorAction.handler(mockContext); + + expect(initRepoAndPush).toHaveBeenCalledWith({ + dir: mockContext.workspacePath, + remoteUrl: 'https://dev.azure.com/organization/project/_git/repo', + auth: { username: 'notempty', password: 'tokenlols' }, + logger: mockContext.logger, + gitAuthorInfo: { name: 'Test', email: 'example@example.com' }, + }); + }); + it('should call output with the remoteUrl and the repoContentsUrl', async () => { mockGitClient.createRepository.mockImplementation(() => ({ remoteUrl: 'https://dev.azure.com/organization/project/_git/repo', diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/azure.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/azure.ts index 677abc3a08..8b8f6ce3e5 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/azure.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/azure.ts @@ -126,8 +126,8 @@ export function createPublishAzureAction(options: { const repoContentsUrl = remoteUrl; const gitAuthorInfo = { - name: config.getOptionalString('scaffolder.git.author.name'), - email: config.getOptionalString('scaffolder.git.author.email'), + name: config.getOptionalString('scaffolder.defaultAuthor.name'), + email: config.getOptionalString('scaffolder.defaultAuthor.email'), }; await initRepoAndPush({ diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/bitbucket.test.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/bitbucket.test.ts index f173959aa0..6a72cf1bc3 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/bitbucket.test.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/bitbucket.test.ts @@ -335,6 +335,75 @@ describe('publish:bitbucket', () => { }); }); + it('should call initAndPush with the configured defaultAuthor', async () => { + const customAuthorConfig = new ConfigReader({ + integrations: { + bitbucket: [ + { + host: 'bitbucket.org', + token: 'tokenlols', + }, + { + host: 'hosted.bitbucket.com', + token: 'thing', + apiBaseUrl: 'https://hosted.bitbucket.com/rest/api/1.0', + }, + { + host: 'notoken.bitbucket.com', + }, + ], + }, + scaffolder: { + defaultAuthor: { + name: 'Test', + email: 'example@example.com', + }, + }, + }); + + const customAuthorIntegrations = ScmIntegrations.fromConfig( + customAuthorConfig, + ); + const customAuthorAction = createPublishBitbucketAction({ + integrations: customAuthorIntegrations, + config: customAuthorConfig, + }); + + server.use( + rest.post( + 'https://api.bitbucket.org/2.0/repositories/owner/repo', + (_, res, ctx) => + res( + ctx.status(200), + ctx.set('Content-Type', 'application/json'), + ctx.json({ + links: { + html: { + href: 'https://bitbucket.org/owner/repo', + }, + clone: [ + { + name: 'https', + href: 'https://bitbucket.org/owner/cloneurl', + }, + ], + }, + }), + ), + ), + ); + + await customAuthorAction.handler(mockContext); + + expect(initRepoAndPush).toHaveBeenCalledWith({ + dir: mockContext.workspacePath, + remoteUrl: 'https://bitbucket.org/owner/cloneurl', + auth: { username: 'x-token-auth', password: 'tokenlols' }, + logger: mockContext.logger, + gitAuthorInfo: { name: 'Test', email: 'example@example.com' }, + }); + }); + it('should call outputs with the correct urls', async () => { server.use( rest.post( diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/bitbucket.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/bitbucket.ts index b05b51a7eb..1dc80f370c 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/bitbucket.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/bitbucket.ts @@ -287,8 +287,8 @@ export function createPublishBitbucketAction(options: { }); const gitAuthorInfo = { - name: config.getOptionalString('scaffolder.git.author.name'), - email: config.getOptionalString('scaffolder.git.author.email'), + name: config.getOptionalString('scaffolder.defaultAuthor.name'), + email: config.getOptionalString('scaffolder.defaultAuthor.email'), }; await initRepoAndPush({ diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/github.test.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/github.test.ts index 058168d666..0b277c4739 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/github.test.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/github.test.ts @@ -212,6 +212,53 @@ describe('publish:github', () => { }); }); + it('should call initRepoAndPush with the configured defaultAuthor', async () => { + const customAuthorConfig = new ConfigReader({ + integrations: { + github: [ + { host: 'github.com', token: 'tokenlols' }, + { host: 'ghe.github.com' }, + ], + }, + scaffolder: { + defaultAuthor: { + name: 'Test', + email: 'example@example.com', + }, + }, + }); + + const customAuthorIntegrations = ScmIntegrations.fromConfig( + customAuthorConfig, + ); + const customAuthorAction = createPublishGithubAction({ + integrations: customAuthorIntegrations, + config: customAuthorConfig, + }); + + mockGithubClient.users.getByUsername.mockResolvedValue({ + data: { type: 'User' }, + }); + + mockGithubClient.repos.createForAuthenticatedUser.mockResolvedValue({ + data: { + clone_url: 'https://github.com/clone/url.git', + html_url: 'https://github.com/html/url', + }, + }); + + await customAuthorAction.handler(mockContext); + + expect(initRepoAndPush).toHaveBeenCalledWith({ + dir: mockContext.workspacePath, + remoteUrl: 'https://github.com/clone/url.git', + defaultBranch: 'master', + auth: { username: 'x-access-token', password: 'tokenlols' }, + logger: mockContext.logger, + gitAuthorInfo: { name: 'Test', email: 'example@example.com' }, + }); + }); + it('should add access for the team when it starts with the owner', async () => { mockGithubClient.users.getByUsername.mockResolvedValue({ data: { type: 'User' }, diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/github.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/github.ts index f14dd817b0..9f693a96d8 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/github.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/github.ts @@ -251,8 +251,8 @@ export function createPublishGithubAction(options: { const repoContentsUrl = `${newRepo.html_url}/blob/${defaultBranch}`; const gitAuthorInfo = { - name: config.getOptionalString('scaffolder.git.author.name'), - email: config.getOptionalString('scaffolder.git.author.email'), + name: config.getOptionalString('scaffolder.defaultAuthor.name'), + email: config.getOptionalString('scaffolder.defaultAuthor.email'), }; await initRepoAndPush({ diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlab.test.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlab.test.ts index 427056454c..08ab87c271 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlab.test.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlab.test.ts @@ -170,6 +170,53 @@ describe('publish:gitlab', () => { }); }); + it('should call initRepoAndPush with the configured defaultAuthor', async () => { + const customAuthorConfig = new ConfigReader({ + integrations: { + gitlab: [ + { + host: 'gitlab.com', + token: 'tokenlols', + apiBaseUrl: 'https://api.gitlab.com', + }, + { + host: 'hosted.gitlab.com', + apiBaseUrl: 'https://api.hosted.gitlab.com', + }, + ], + }, + scaffolder: { + defaultAuthor: { + name: 'Test', + email: 'example@example.com', + }, + }, + }); + + const customAuthorIntegrations = ScmIntegrations.fromConfig( + customAuthorConfig, + ); + const customAuthorAction = createPublishGitlabAction({ + integrations: customAuthorIntegrations, + config: customAuthorConfig, + }); + + mockGitlabClient.Namespaces.show.mockResolvedValue({ id: 1234 }); + mockGitlabClient.Projects.create.mockResolvedValue({ + http_url_to_repo: 'http://mockurl.git', + }); + + await customAuthorAction.handler(mockContext); + + expect(initRepoAndPush).toHaveBeenCalledWith({ + dir: mockContext.workspacePath, + remoteUrl: 'http://mockurl.git', + auth: { username: 'oauth2', password: 'tokenlols' }, + logger: mockContext.logger, + gitAuthorInfo: { name: 'Test', email: 'example@example.com' }, + }); + }); + it('should call output with the remoteUrl and repoContentsUrl', async () => { mockGitlabClient.Namespaces.show.mockResolvedValue({ id: 1234 }); mockGitlabClient.Projects.create.mockResolvedValue({ diff --git a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlab.ts b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlab.ts index 6d7384294d..1cd77ebe2a 100644 --- a/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlab.ts +++ b/plugins/scaffolder-backend/src/scaffolder/actions/builtin/publish/gitlab.ts @@ -124,8 +124,8 @@ export function createPublishGitlabAction(options: { const repoContentsUrl = `${remoteUrl}/-/blob/master`; const gitAuthorInfo = { - name: config.getOptionalString('scaffolder.git.author.name'), - email: config.getOptionalString('scaffolder.git.author.email'), + name: config.getOptionalString('scaffolder.defaultAuthor.name'), + email: config.getOptionalString('scaffolder.defaultAuthor.email'), }; await initRepoAndPush({