diff --git a/__tests__/git.test.ts b/__tests__/git.test.ts index 4182e9b..6d3eae0 100644 --- a/__tests__/git.test.ts +++ b/__tests__/git.test.ts @@ -181,7 +181,7 @@ describe('Git CLI', () => { describe('git add', () => { beforeEach(() => { - jest.spyOn(cwd, 'getWorkspace').mockReturnValue('/test-workspace') + jest.spyOn(cwd, 'getWorkspace').mockReturnValue('test-workspace/') }) it('should ensure file paths are within curent working directory', async () => { @@ -190,7 +190,7 @@ describe('Git CLI', () => { await addFileChanges(['*.ts', '~/.bashrc']) expect(execMock).toHaveBeenCalledWith( 'git', - ['add', '--', '/test-workspace/*.ts', '/test-workspace/~/.bashrc'], + ['add', '--', 'test-workspace/*.ts', 'test-workspace/~/.bashrc'], expect.objectContaining({ listeners: { stdline: expect.anything(), errline: expect.anything() }, }) diff --git a/action.yml b/action.yml index d3c9df1..7ce6a5b 100644 --- a/action.yml +++ b/action.yml @@ -15,10 +15,23 @@ inputs: Directory containing files to be committed. Default: GitHub workspace directory (root of repository). required: false default: '' + workdir: + description: | + Directory where the action should run. Default: GitHub workspace directory (root of repository from where the GH Workflow is triggered). + required: false + default: '' commit-message: description: | Commit message for the file changes. required: false + owner: + description: | + GitHub repository owner (user or organization), defaults to the repo invoking the action. + required: false + repo: + description: | + GitHub repository name, defaults to the repo invoking the action. + required: false branch-name: description: | Branch to commit to. Default: Workflow triggered branch. diff --git a/dist/index.js b/dist/index.js index 258dd67..d0daefb 100644 --- a/dist/index.js +++ b/dist/index.js @@ -29989,6 +29989,7 @@ function execGit(args) { const debugOutput = []; const warningOutput = []; const errorOutput = []; + core.debug('execGit() - args: ' + JSON.stringify(args)); yield (0, exec_1.exec)('git', args, { silent: true, ignoreReturnCode: true, @@ -30033,8 +30034,15 @@ function pushCurrentBranch() { } function addFileChanges(globPatterns) { return __awaiter(this, void 0, void 0, function* () { + const cwd = (0, cwd_1.getCwd)(); const workspace = (0, cwd_1.getWorkspace)(); - const workspacePaths = globPatterns.map((p) => (0, node_path_1.join)(workspace, p)); + const resolvedWorkspace = (0, node_path_1.resolve)(workspace); + core.debug('addFileChanges() - resolvedWorkspace: ' + JSON.stringify(resolvedWorkspace)); + let workspacePaths = globPatterns; + if (resolvedWorkspace.includes(cwd)) { + core.notice('addFileChanges() - "workspace" is a subdirectory, updating globPatterns'); + workspacePaths = globPatterns.map((p) => (0, node_path_1.join)((0, node_path_1.relative)(cwd, resolvedWorkspace), p)); + } yield execGit(['add', '--', ...workspacePaths]); }); } @@ -30381,34 +30389,51 @@ const core = __importStar(__nccwpck_require__(7484)); const graphql_1 = __nccwpck_require__(1422); const repo_1 = __nccwpck_require__(1839); const git_1 = __nccwpck_require__(1243); +const cwd_1 = __nccwpck_require__(9827); const input_1 = __nccwpck_require__(7797); const errors_1 = __nccwpck_require__(3916); function run() { return __awaiter(this, void 0, void 0, function* () { var _a, _b, _c, _d, _e, _f; try { + core.info('Getting info from GH Worklfow context'); const { owner, repo, branch } = (0, repo_1.getContext)(); + core.info('Setting variables according to inputs and context'); + core.debug('* branch'); const inputBranch = (0, input_1.getInput)('branch-name'); - if (inputBranch && inputBranch !== branch) { - yield (0, git_1.switchBranch)(inputBranch); + const selectedBranch = inputBranch ? inputBranch : branch; + core.debug('* owner'); + const inputOwner = (0, input_1.getInput)('owner'); + const selectedOwner = inputOwner ? inputOwner : owner; + core.debug('* repo'); + const inputRepo = (0, input_1.getInput)('repo'); + const selectedRepo = inputRepo ? inputRepo : repo; + if (selectedOwner == owner && + selectedRepo == repo && + selectedBranch !== branch) { + core.warning('Pushing local and current branch to remote before proceeding'); + // Git commands + yield (0, git_1.switchBranch)(selectedBranch); yield (0, git_1.pushCurrentBranch)(); } - const currentBranch = inputBranch ? inputBranch : branch; - const repository = yield core.group(`fetching repository info for owner: ${owner}, repo: ${repo}, branch: ${currentBranch}`, () => __awaiter(this, void 0, void 0, function* () { + const repository = yield core.group(`fetching repository info for owner: ${selectedOwner}, repo: ${selectedRepo}, branch: ${selectedBranch}`, () => __awaiter(this, void 0, void 0, function* () { const startTime = Date.now(); - const repositoryData = yield (0, graphql_1.getRepository)(owner, repo, currentBranch); + const repositoryData = yield (0, graphql_1.getRepository)(selectedOwner, selectedRepo, selectedBranch); const endTime = Date.now(); core.debug(`time taken: ${(endTime - startTime).toString()} ms`); return repositoryData; })); + core.info('Checking remote branches'); if (!repository.ref) { - if (inputBranch && currentBranch == inputBranch) { + if (inputBranch) { throw new errors_1.InputBranchNotFound(inputBranch); } else { - throw new errors_1.BranchNotFound(currentBranch); + throw new errors_1.BranchNotFound(branch); } } + core.info('Processing to create signed commit'); + core.debug('Get last (current?) commit'); const currentCommit = (_b = (_a = repository.ref.target.history) === null || _a === void 0 ? void 0 : _a.nodes) === null || _b === void 0 ? void 0 : _b[0]; if (!currentCommit) { throw new errors_1.BranchCommitNotFound(repository.ref.name); @@ -30416,10 +30441,16 @@ function run() { let createdCommit; const filePaths = core.getMultilineInput('files'); if (filePaths.length <= 0) { - core.debug('skip file commit, empty files input'); + core.notice('skip file commit, empty files input'); } else { - core.debug(`proceed with file commit, input: ${JSON.stringify(filePaths)}`); + core.debug(`Proceed with file commit, input: ${JSON.stringify(filePaths)}`); + const workdir = (0, cwd_1.getWorkdir)(); + const cwd = (0, cwd_1.getCwd)(); + if (cwd !== workdir) { + core.notice('Changing working directory to Workdir: ' + workdir); + process.chdir(workdir); + } yield (0, git_1.addFileChanges)(filePaths); const fileChanges = yield (0, git_1.getFileChanges)(); const fileCount = ((_d = (_c = fileChanges.additions) === null || _c === void 0 ? void 0 : _c.length) !== null && _d !== void 0 ? _d : 0) + @@ -30441,7 +30472,7 @@ function run() { const startTime = Date.now(); const commitData = yield (0, graphql_1.createCommitOnBranch)(currentCommit, commitMessage, { repositoryNameWithOwner: repository.nameWithOwner, - branchName: currentBranch, + branchName: selectedBranch, }, fileChanges); const endTime = Date.now(); core.debug(`time taken: ${(endTime - startTime).toString()} ms`); @@ -30565,6 +30596,7 @@ var __importStar = (this && this.__importStar) || function (mod) { Object.defineProperty(exports, "__esModule", ({ value: true })); exports.getCwd = getCwd; exports.getWorkspace = getWorkspace; +exports.getWorkdir = getWorkdir; const core = __importStar(__nccwpck_require__(7484)); const input_1 = __nccwpck_require__(7797); function getCwd() { @@ -30579,6 +30611,13 @@ function getWorkspace() { core.debug(`workspace: ${workspace}`); return workspace; } +function getWorkdir() { + const workdir = (0, input_1.getInput)('workdir', { + default: process.env.GITHUB_WORKSPACE, + }); + core.debug(`workdir: ${workdir}`); + return workdir; +} /***/ }), diff --git a/src/git.ts b/src/git.ts index 64f2efa..258030f 100644 --- a/src/git.ts +++ b/src/git.ts @@ -1,19 +1,20 @@ import * as core from '@actions/core' import { exec } from '@actions/exec' -import { join } from 'node:path' +import { join, relative, resolve } from 'node:path' import { FileChanges, FileAddition, FileDeletion, } from '@octokit/graphql-schema' -import { getWorkspace } from './utils/cwd' +import { getCwd, getWorkspace } from './utils/cwd' async function execGit(args: string[]) { const debugOutput: string[] = [] const warningOutput: string[] = [] const errorOutput: string[] = [] + core.debug('execGit() - args: ' + JSON.stringify(args)) await exec('git', args, { silent: true, ignoreReturnCode: true, @@ -53,8 +54,22 @@ export async function pushCurrentBranch() { } export async function addFileChanges(globPatterns: string[]) { + const cwd = getCwd() const workspace = getWorkspace() - const workspacePaths = globPatterns.map((p) => join(workspace, p)) + const resolvedWorkspace = resolve(workspace) + core.debug( + 'addFileChanges() - resolvedWorkspace: ' + JSON.stringify(resolvedWorkspace) + ) + + let workspacePaths = globPatterns + if (resolvedWorkspace.includes(cwd)) { + core.notice( + 'addFileChanges() - "workspace" is a subdirectory, updating globPatterns' + ) + workspacePaths = globPatterns.map((p) => + join(relative(cwd, resolvedWorkspace), p) + ) + } await execGit(['add', '--', ...workspacePaths]) } diff --git a/src/main.ts b/src/main.ts index 4014982..454a85d 100644 --- a/src/main.ts +++ b/src/main.ts @@ -13,6 +13,7 @@ import { pushCurrentBranch, switchBranch, } from './git' +import { getCwd, getWorkdir } from './utils/cwd' import { getInput } from './utils/input' import { NoFileChanges, @@ -23,32 +24,61 @@ import { export async function run(): Promise { try { + core.info('Getting info from GH Worklfow context') const { owner, repo, branch } = getContext() + + core.info('Setting variables according to inputs and context') + core.debug('* branch') const inputBranch = getInput('branch-name') - if (inputBranch && inputBranch !== branch) { - await switchBranch(inputBranch) + const selectedBranch = inputBranch ? inputBranch : branch + + core.debug('* owner') + const inputOwner = getInput('owner') + const selectedOwner = inputOwner ? inputOwner : owner + + core.debug('* repo') + const inputRepo = getInput('repo') + const selectedRepo = inputRepo ? inputRepo : repo + + if ( + selectedOwner == owner && + selectedRepo == repo && + selectedBranch !== branch + ) { + core.warning( + 'Pushing local and current branch to remote before proceeding' + ) + // Git commands + await switchBranch(selectedBranch) await pushCurrentBranch() } - const currentBranch = inputBranch ? inputBranch : branch + const repository = await core.group( - `fetching repository info for owner: ${owner}, repo: ${repo}, branch: ${currentBranch}`, + `fetching repository info for owner: ${selectedOwner}, repo: ${selectedRepo}, branch: ${selectedBranch}`, async () => { const startTime = Date.now() - const repositoryData = await getRepository(owner, repo, currentBranch) + const repositoryData = await getRepository( + selectedOwner, + selectedRepo, + selectedBranch + ) const endTime = Date.now() core.debug(`time taken: ${(endTime - startTime).toString()} ms`) return repositoryData } ) + core.info('Checking remote branches') if (!repository.ref) { - if (inputBranch && currentBranch == inputBranch) { + if (inputBranch) { throw new InputBranchNotFound(inputBranch) } else { - throw new BranchNotFound(currentBranch) + throw new BranchNotFound(branch) } } + core.info('Processing to create signed commit') + core.debug('Get last (current?) commit') const currentCommit = repository.ref.target.history?.nodes?.[0] if (!currentCommit) { throw new BranchCommitNotFound(repository.ref.name) @@ -57,12 +87,19 @@ export async function run(): Promise { let createdCommit: Commit | undefined const filePaths = core.getMultilineInput('files') if (filePaths.length <= 0) { - core.debug('skip file commit, empty files input') + core.notice('skip file commit, empty files input') } else { core.debug( - `proceed with file commit, input: ${JSON.stringify(filePaths)}` + `Proceed with file commit, input: ${JSON.stringify(filePaths)}` ) + const workdir = getWorkdir() + const cwd = getCwd() + if (cwd !== workdir) { + core.notice('Changing working directory to Workdir: ' + workdir) + process.chdir(workdir) + } + await addFileChanges(filePaths) const fileChanges = await getFileChanges() const fileCount = @@ -89,7 +126,7 @@ export async function run(): Promise { commitMessage, { repositoryNameWithOwner: repository.nameWithOwner, - branchName: currentBranch, + branchName: selectedBranch, }, fileChanges ) diff --git a/src/utils/cwd.ts b/src/utils/cwd.ts index ea9f338..cd3a798 100644 --- a/src/utils/cwd.ts +++ b/src/utils/cwd.ts @@ -14,3 +14,11 @@ export function getWorkspace() { core.debug(`workspace: ${workspace}`) return workspace } + +export function getWorkdir() { + const workdir = getInput('workdir', { + default: process.env.GITHUB_WORKSPACE, + }) + core.debug(`workdir: ${workdir}`) + return workdir +}