Compare commits

..

20 Commits

Author SHA1 Message Date
a1df20e448
make action rely on gitea CPR
Some checks failed
CI / validate (push) Successful in 6s
CI / typescript-action (push) Failing after 3m11s
update-flake-lock / lockfile (push) Failing after 11m54s
Rebase Upstream / sync (push) Failing after 12m9s
Signed-off-by: ahuston-0 <aliceghuston@gmail.com>
2025-02-01 16:45:41 -05:00
74d7f019a7
add upstream sync
Some checks failed
CI / validate (push) Successful in 1m0s
CI / typescript-action (push) Has been cancelled
Signed-off-by: ahuston-0 <aliceghuston@gmail.com>
2025-02-01 16:41:46 -05:00
Graham Christensen
0ba1118664
Merge pull request #144 from detsys-pr-bot/detsys-ts-update-eb87094f35072ac911526ad052c3437c9e0c42d6
Update `detsys-ts`: Merge pull request #69 from DeterminateSystems/update-deps
2024-11-26 11:31:58 -05:00
grahamc
236c0fa397 Update detsys-ts for: Merge pull request #69 from DeterminateSystems/update-deps (eb87094f35072ac911526ad052c3437c9e0c42d6) 2024-11-20 18:57:29 +00:00
Graham Christensen
8fa6d41e3f
Merge pull request #141 from DeterminateSystems/colemickens/pr-url
action.yml: expose pull-request-url from create-pr action
2024-11-08 14:50:46 -05:00
Cole Mickens
1360662aa3 action.yml: expose pull-request-url from create-pr action 2024-11-08 11:34:36 -08:00
Graham Christensen
531bd45244
Merge pull request #139 from detsys-pr-bot/detsys-ts-update-4280bc94c9545f31ccf08001cc16f20ccb91b770
Update `detsys-ts`: Merge pull request #67 from DeterminateSystems/allow-obliterating-id-token-privs
2024-11-06 14:56:02 -05:00
grahamc
1afac295f9 Update detsys-ts for: Merge pull request #67 from DeterminateSystems/allow-obliterating-id-token-privs (4280bc94c9545f31ccf08001cc16f20ccb91b770) 2024-11-06 19:43:49 +00:00
dependabot[bot]
965531f332
build(deps-dev): bump vite from 5.2.12 to 5.4.6 (#131)
* build(deps-dev): bump vite from 5.2.12 to 5.4.6

Bumps [vite](https://github.com/vitejs/vite/tree/HEAD/packages/vite) from 5.2.12 to 5.4.6.
- [Release notes](https://github.com/vitejs/vite/releases)
- [Changelog](https://github.com/vitejs/vite/blob/v5.4.6/packages/vite/CHANGELOG.md)
- [Commits](https://github.com/vitejs/vite/commits/v5.4.6/packages/vite)

---
updated-dependencies:
- dependency-name: vite
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>

* pnpm i

---------

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Cole Helbling <cole.helbling@determinate.systems>
2024-09-19 16:42:07 +00:00
Graham Christensen
a2bbe0274e
Merge pull request #128 from detsys-pr-bot/detsys-ts-update-65dd73c562ac60a068340f8e0c040bdcf2c59afe
Update `detsys-ts`: Merge pull request #63 from DeterminateSystems/retry-streams
2024-09-04 14:14:50 -04:00
grahamc
802501548e Update detsys-ts for: Merge pull request #63 from DeterminateSystems/retry-streams (65dd73c562ac60a068340f8e0c040bdcf2c59afe) 2024-09-04 18:05:28 +00:00
Graham Christensen
7d80c329b4
Merge pull request #126 from detsys-pr-bot/detsys-ts-update-817e4d4123b6fb4eae5aa557658f25f8539e7240
Update `detsys-ts`: Merge pull request #62 from DeterminateSystems/dont-pull-microstackshots
2024-08-26 19:46:57 -04:00
grahamc
7bc6ec59cc Update detsys-ts for: Merge pull request #62 from DeterminateSystems/dont-pull-microstackshots (817e4d4123b6fb4eae5aa557658f25f8539e7240) 2024-08-26 15:26:03 +00:00
Graham Christensen
4cf6b19203
Merge pull request #125 from detsys-pr-bot/detsys-ts-update-e8f6e8f54d85aa0fd3d0b694dd3279a21497a33b
Update `detsys-ts`: Merge pull request #61 from DeterminateSystems/use-coalesce-for-array
2024-08-26 10:09:12 -04:00
grahamc
73ba0ca899 Update detsys-ts for: Merge pull request #61 from DeterminateSystems/use-coalesce-for-array (e8f6e8f54d85aa0fd3d0b694dd3279a21497a33b) 2024-08-26 14:05:27 +00:00
Graham Christensen
24f53daa86
Merge pull request #124 from detsys-pr-bot/detsys-ts-update-cf1897a891edc164a8240f469cd56d14364e6be1
Update `detsys-ts`: Merge pull request #58 from DeterminateSystems/collect-crash-logs
2024-08-26 09:41:53 -04:00
grahamc
420fb2aaf7 Update detsys-ts for: Merge pull request #58 from DeterminateSystems/collect-crash-logs (cf1897a891edc164a8240f469cd56d14364e6be1) 2024-08-26 13:31:25 +00:00
Cole Helbling
db4ee38117 Fixup support for Nix 2.23.0 and later 2024-06-28 14:11:30 -07:00
Pierre Penninckx
b0723e0fae Add instructions for new fine grained GitHub PAT 2024-06-18 09:23:51 -07:00
Arian van Putten
af9a980c7d Lock third-party actions
A caller of this action can lock this action to a specific commit. However because the action itself does not lock its dependent actions to a specific commit this opens the end-user up to possible supply-chain attacks if the dependent actions rewrite their tags.

This PR changes all third party actions to be explicitly locked.

Dependabot will still work and update these hashes for you


I also suggest installing https://github.com/ossf/scorecard in this repo. It will report about these kind of issues.

Note that you should in turn have to audit all the third party deps of the actions that your action depends on. In general this is all a bit of a mess and GitHub's security model is very meh

e.g. see https://github.com/ossf/scorecard/issues/2189
2024-06-18 09:17:15 -07:00
12 changed files with 28746 additions and 48302 deletions

18
.github/workflows/upstream_sync.yml vendored Normal file
View File

@ -0,0 +1,18 @@
# .github/workflows/sync.yml
name: Rebase Upstream
on:
schedule:
- cron: "0 0 * * 0" # run once a week
workflow_dispatch: # run manually
jobs:
sync:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@master
with:
fetch-depth: 10 # greater than the number of commits you made
- uses: imba-tjd/rebase-upstream-action@master
with: # all args are optional
upstream: DeterminateSystems/update-flake-lock
branch: main

View File

@ -138,23 +138,6 @@ jobs:
path-to-flake-dir: 'nix/' # in this example our flake doesn't sit at the root of the repository, it sits under 'nix/flake.nix' path-to-flake-dir: 'nix/' # in this example our flake doesn't sit at the root of the repository, it sits under 'nix/flake.nix'
``` ```
You can also run the update operation in multiple directories, provided that each directory is a valid flake:
```yaml
- name: Update flake.lock
uses: DeterminateSystems/update-flake-lock@vX
with:
flake-dirs: |
flake1
flake2
flake3
```
> **Warning**: If you choose multiple directories, `update-flake-lock` can only update all flake inputs,
> meaning that you can't set the `inputs` parameter. This is due to limitations in input handling in
> GitHub Actions, which only allows for strings, numbers, Booleans, and arrays but not objects, which
> would be the much preferred data type for expressing per-directory inputs.
## Example using a different Git user ## Example using a different Git user
If you want to change the author and / or committer of the flake.lock update commit, you can tweak the `git-{author,committer}-{name,email}` options: If you want to change the author and / or committer of the flake.lock update commit, you can tweak the `git-{author,committer}-{name,email}` options:
@ -202,7 +185,7 @@ git push origin update_flake_lock_action --force
### With a Personal Authentication Token ### With a Personal Authentication Token
By providing a Personal Authentication Token, the PR will be submitted in a way that bypasses this limitation (GitHub will essentially think it is the owner of the PAT submitting the PR, and not an Action). By providing a Personal Authentication Token, the PR will be submitted in a way that bypasses this limitation (GitHub will essentially think it is the owner of the PAT submitting the PR, and not an Action).
You can create a token by visiting https://github.com/settings/tokens and select at least the `repo` scope. Then, store this token in your repository secrets (i.e. `https://github.com/<USER>/<REPO>/settings/secrets/actions`) as `GH_TOKEN_FOR_UPDATES` and set up your workflow file like the following: You can create a token by visiting https://github.com/settings/tokens and select at least the `repo` scope. For the new fine-grained tokens, you need to enable read and write access for "Contents" and "Pull Requests" permissions. Then, store this token in your repository secrets (i.e. `https://github.com/<USER>/<REPO>/settings/secrets/actions`) as `GH_TOKEN_FOR_UPDATES` and set up your workflow file like the following:
```yaml ```yaml
name: update-flake-lock name: update-flake-lock

View File

@ -9,21 +9,10 @@ inputs:
description: "GITHUB_TOKEN or a `repo` scoped Personal Access Token (PAT)" description: "GITHUB_TOKEN or a `repo` scoped Personal Access Token (PAT)"
required: false required: false
default: ${{ github.token }} default: ${{ github.token }}
commit-msg-template:
description: |
The commit message template to use. You can use these variables in your template:
* `{{ flake_dot_lock }}` is the path to the `flake.lock` file being updated
* `{{ flake_dot_lock_dir }}` is the `flake.lock` file's directory
If you set both this and `commit-msg`, the `commit-msg` setting is used (it does not support templating).
required: false
default: |
flake.lock: Updated in {{ flake_dot_lock_dir }}
commit-msg: commit-msg:
description: | description: "The message provided with the commit"
The message provided with the commit.
required: false required: false
default: "flake.lock: Update"
base: base:
description: "Sets the pull request base branch. Defaults to the branch checked out in the workflow." description: "Sets the pull request base branch. Defaults to the branch checked out in the workflow."
required: false required: false
@ -32,32 +21,12 @@ inputs:
required: false required: false
default: "update_flake_lock_action" default: "update_flake_lock_action"
path-to-flake-dir: path-to-flake-dir:
description: | description: "The path of the directory containing `flake.nix` file within your repository. Useful when `flake.nix` cannot reside at the root of your repository."
The path of the directory containing `flake.nix` file within your repository.
Useful when `flake.nix` cannot reside at the root of your repository.
required: false required: false
flake-dirs:
description: |
A space-separated list of directories containing `flake.nix` files within your repository.
Useful when you have multiple flakes in your repository.
required: false
default: ""
pr-title: pr-title:
description: "The title of the PR to be created" description: "The title of the PR to be created"
required: false required: false
default: "flake.lock: Update" default: "flake.lock: Update"
pr-body-template:
description: |
The pull request body template to use. You can use these variables in your template:
* `{{ comma_separated_dirs }}` is the flake directories that were updated separated by comma
* `{{ space_separated_dirs }}` is the flake directories that were updated separated by space
* `{{ updated_dirs_list }}` is the flake directories that were updated as a Markdown list
If you set both this and `pr-body`, the `pr-body` setting is used (it does not support templating).
required: false
default: |
Just testing.
pr-body: pr-body:
description: "The body of the PR to be created" description: "The body of the PR to be created"
required: false required: false
@ -137,6 +106,9 @@ outputs:
pull-request-number: pull-request-number:
description: "The number of the opened pull request" description: "The number of the opened pull request"
value: ${{ steps.create-pr.outputs.pull-request-number }} value: ${{ steps.create-pr.outputs.pull-request-number }}
pull-request-url:
description: "The The URL of the opened pull request."
value: ${{ steps.create-pr.outputs.pull-request-url }}
pull-request-operation: pull-request-operation:
description: "The pull request operation performed by the action, `created`, `updated` or `closed`." description: "The pull request operation performed by the action, `created`, `updated` or `closed`."
value: ${{ steps.create-pr.outputs.pull-request-operation }} value: ${{ steps.create-pr.outputs.pull-request-operation }}
@ -146,7 +118,7 @@ runs:
- name: Import bot's GPG key for signing commits - name: Import bot's GPG key for signing commits
if: ${{ inputs.sign-commits == 'true' }} if: ${{ inputs.sign-commits == 'true' }}
id: import-gpg id: import-gpg
uses: crazy-max/ghaction-import-gpg@v6 uses: crazy-max/ghaction-import-gpg@01dd5d3ca463c7f10f7f4f7b4f177225ac661ee4 # v6.1.0
with: with:
gpg_private_key: ${{ inputs.gpg-private-key }} gpg_private_key: ${{ inputs.gpg-private-key }}
fingerprint: ${{ inputs.gpg-fingerprint }} fingerprint: ${{ inputs.gpg-fingerprint }}
@ -177,7 +149,6 @@ runs:
echo "GIT_COMMITTER_NAME=${{ inputs.git-committer-name }}" >> $GITHUB_ENV echo "GIT_COMMITTER_NAME=${{ inputs.git-committer-name }}" >> $GITHUB_ENV
echo "GIT_COMMITTER_EMAIL=<${{ inputs.git-committer-email }}>" >> $GITHUB_ENV echo "GIT_COMMITTER_EMAIL=<${{ inputs.git-committer-email }}>" >> $GITHUB_ENV
- name: Run update-flake-lock - name: Run update-flake-lock
id: update-flake-lock
shell: bash shell: bash
run: node "$GITHUB_ACTION_PATH/dist/index.js" run: node "$GITHUB_ACTION_PATH/dist/index.js"
env: env:
@ -186,7 +157,6 @@ runs:
INPUT_BASE: ${{ inputs.base }} INPUT_BASE: ${{ inputs.base }}
INPUT_BRANCH: ${{ inputs.branch }} INPUT_BRANCH: ${{ inputs.branch }}
INPUT_COMMIT-MSG: ${{ inputs.commit-msg }} INPUT_COMMIT-MSG: ${{ inputs.commit-msg }}
INPUT_COMMIT-MSG-TEMPLATE: ${{ inputs.commit-msg-template }}
INPUT_GIT-AUTHOR-EMAIL: ${{ inputs.git-author-email }} INPUT_GIT-AUTHOR-EMAIL: ${{ inputs.git-author-email }}
INPUT_GIT-AUTHOR-NAME: ${{ inputs.git-author-name }} INPUT_GIT-AUTHOR-NAME: ${{ inputs.git-author-name }}
INPUT_GIT-COMMITTER-EMAIL: ${{ inputs.git-committer-email }} INPUT_GIT-COMMITTER-EMAIL: ${{ inputs.git-committer-email }}
@ -197,10 +167,8 @@ runs:
INPUT_INPUTS: ${{ inputs.inputs }} INPUT_INPUTS: ${{ inputs.inputs }}
INPUT_NIX-OPTIONS: ${{ inputs.nix-options }} INPUT_NIX-OPTIONS: ${{ inputs.nix-options }}
INPUT_PATH-TO-FLAKE-DIR: ${{ inputs.path-to-flake-dir }} INPUT_PATH-TO-FLAKE-DIR: ${{ inputs.path-to-flake-dir }}
INPUT_FLAKE-DIRS: ${{ inputs.flake-dirs }}
INPUT_PR-ASSIGNEES: ${{ inputs.pr-assignees }} INPUT_PR-ASSIGNEES: ${{ inputs.pr-assignees }}
INPUT_PR-BODY: ${{ inputs.pr-body }} INPUT_PR-BODY: ${{ inputs.pr-body }}
INPUT_PR-BODY-TEMPLATE: ${{ inputs.pr-body-template }}
INPUT_PR-LABELS: ${{ inputs.pr-labels }} INPUT_PR-LABELS: ${{ inputs.pr-labels }}
INPUT_PR-REVIEWERS: ${{ inputs.pr-reviewers }} INPUT_PR-REVIEWERS: ${{ inputs.pr-reviewers }}
INPUT_PR-TITLE: ${{ inputs.pr-title }} INPUT_PR-TITLE: ${{ inputs.pr-title }}
@ -213,7 +181,7 @@ runs:
uses: DamianReeves/write-file-action@v1.3 uses: DamianReeves/write-file-action@v1.3
with: with:
path: pr_body.template path: pr_body.template
contents: ${{ steps.update-flake-lock.outputs.pr-body }} contents: ${{ inputs.pr-body }}
env: {} env: {}
- name: Set additional env variables (GIT_COMMIT_MESSAGE) - name: Set additional env variables (GIT_COMMIT_MESSAGE)
shell: bash shell: bash
@ -225,7 +193,7 @@ runs:
echo "$DELIMITER" >> $GITHUB_ENV echo "$DELIMITER" >> $GITHUB_ENV
echo "GIT_COMMIT_MESSAGE is: ${COMMIT_MESSAGE}" echo "GIT_COMMIT_MESSAGE is: ${COMMIT_MESSAGE}"
- name: Interpolate PR Body - name: Interpolate PR Body
uses: pedrolamas/handlebars-action@v2.4.0 uses: pedrolamas/handlebars-action@2995d7eadacbc8f2f6ab8431a01d84a5fa3b8bb4 # v2.4.0
with: with:
files: "pr_body.template" files: "pr_body.template"
output-filename: "pr_body.txt" output-filename: "pr_body.txt"
@ -242,7 +210,7 @@ runs:
run: rm -f pr_body.txt pr_body.template run: rm -f pr_body.txt pr_body.template
- name: Create PR - name: Create PR
id: create-pr id: create-pr
uses: peter-evans/create-pull-request@v6 uses: https://nayeonie.com/ahuston-0/create-pull-request@6b3a86bf8bfe10eb458b00968a8fefe2f5f5a6c1 # v6.0.5
with: with:
base: ${{ inputs.base }} base: ${{ inputs.base }}
branch: ${{ inputs.branch }} branch: ${{ inputs.branch }}

74587
dist/index.js vendored

File diff suppressed because one or more lines are too long

2
dist/index.js.map vendored

File diff suppressed because one or more lines are too long

View File

@ -12,7 +12,6 @@
"lint": "eslint src/**/*.ts --ignore-pattern *.test.ts", "lint": "eslint src/**/*.ts --ignore-pattern *.test.ts",
"package": "ncc build", "package": "ncc build",
"test": "vitest --watch false", "test": "vitest --watch false",
"test-dev": "vitest",
"all": "pnpm run format && pnpm run lint && pnpm run build && pnpm run package" "all": "pnpm run format && pnpm run lint && pnpm run build && pnpm run package"
}, },
"repository": { "repository": {
@ -27,23 +26,22 @@
}, },
"homepage": "https://github.com/DeterminateSystems/update-flake-lock#readme", "homepage": "https://github.com/DeterminateSystems/update-flake-lock#readme",
"dependencies": { "dependencies": {
"@actions/core": "^1.10.1", "@actions/core": "^1.11.1",
"@actions/exec": "^1.1.1", "@actions/exec": "^1.1.1",
"detsys-ts": "github:DeterminateSystems/detsys-ts", "detsys-ts": "github:DeterminateSystems/detsys-ts"
"handlebars": "^4.7.8"
}, },
"devDependencies": { "devDependencies": {
"@trivago/prettier-plugin-sort-imports": "^4.3.0", "@trivago/prettier-plugin-sort-imports": "^4.3.0",
"@typescript-eslint/eslint-plugin": "^7.11.0", "@typescript-eslint/eslint-plugin": "^7.18.0",
"@vercel/ncc": "^0.38.1", "@vercel/ncc": "^0.38.3",
"eslint": "^8.57.0", "eslint": "^8.57.1",
"eslint-import-resolver-typescript": "^3.6.1", "eslint-import-resolver-typescript": "^3.6.3",
"eslint-plugin-github": "^4.10.2", "eslint-plugin-github": "^4.10.2",
"eslint-plugin-import": "^2.29.1", "eslint-plugin-import": "^2.31.0",
"eslint-plugin-prettier": "^5.1.3", "eslint-plugin-prettier": "^5.2.1",
"prettier": "^3.2.5", "prettier": "^3.3.3",
"tsup": "^8.0.2", "tsup": "^8.3.5",
"typescript": "^5.4.5", "typescript": "^5.6.3",
"vitest": "^1.6.0" "vitest": "^1.6.0"
} }
} }

2064
pnpm-lock.yaml generated

File diff suppressed because it is too large Load Diff

View File

@ -1,26 +1,15 @@
import { makeNixCommandArgs } from "./nix.js"; import { makeNixCommandArgs } from "./nix.js";
import { renderCommitMessage, renderPullRequestBody } from "./template.js";
import * as actionsCore from "@actions/core"; import * as actionsCore from "@actions/core";
import * as actionsExec from "@actions/exec"; import * as actionsExec from "@actions/exec";
import { DetSysAction, inputs } from "detsys-ts"; import { DetSysAction, inputs } from "detsys-ts";
import * as fs from "fs";
const DEFAULT_FLAKE_DIR = ".";
const PR_BODY_OUTPUT_KEY = "pr-body";
const EVENT_EXECUTION_FAILURE = "execution_failure"; const EVENT_EXECUTION_FAILURE = "execution_failure";
class UpdateFlakeLockAction extends DetSysAction { class UpdateFlakeLockAction extends DetSysAction {
private commitMessage: string; private commitMessage: string;
private commitMessageTemplate: string;
private prBody: string;
private prBodyTemplate: string;
private nixOptions: string[]; private nixOptions: string[];
private flakeInputs: string[]; private flakeInputs: string[];
private pathToFlakeDir: string | null; private pathToFlakeDir: string | null;
private flakeDirsInput: string[] | null;
private flakeDirs: string[];
constructor() { constructor() {
super({ super({
@ -30,55 +19,19 @@ class UpdateFlakeLockAction extends DetSysAction {
}); });
this.commitMessage = inputs.getString("commit-msg"); this.commitMessage = inputs.getString("commit-msg");
this.commitMessageTemplate = inputs.getString("commit-msg-template");
this.prBody = inputs.getString("pr-body");
this.prBodyTemplate = inputs.getString("pr-body-template");
this.flakeInputs = inputs.getArrayOfStrings("inputs", "space"); this.flakeInputs = inputs.getArrayOfStrings("inputs", "space");
this.nixOptions = inputs.getArrayOfStrings("nix-options", "space"); this.nixOptions = inputs.getArrayOfStrings("nix-options", "space");
this.pathToFlakeDir = inputs.getStringOrNull("path-to-flake-dir"); this.pathToFlakeDir = inputs.getStringOrNull("path-to-flake-dir");
this.flakeDirsInput = inputs.getArrayOfStringsOrNull("flake-dirs", "space");
this.validateInputs();
if (this.flakeDirsInput !== null && this.flakeDirsInput.length > 0) {
this.flakeDirs = this.flakeDirsInput;
} else {
this.flakeDirs = [this.pathToFlakeDir ?? DEFAULT_FLAKE_DIR];
}
} }
async main(): Promise<void> { async main(): Promise<void> {
for (const directory of this.flakeDirs) { await this.update();
await this.updateFlakeInDirectory(directory);
}
const prBody =
this.prBody !== ""
? this.prBody
: renderPullRequestBody(this.prBodyTemplate, this.flakeDirs);
actionsCore.setOutput(PR_BODY_OUTPUT_KEY, prBody);
} }
// No post phase // No post phase
async post(): Promise<void> {} async post(): Promise<void> {}
private async updateFlakeInDirectory(flakeDir: string): Promise<void> { async update(): Promise<void> {
this.ensureDirectoryExists(flakeDir);
this.ensureDirectoryIsFlake(flakeDir);
actionsCore.debug(`Running flake lock update in directory \`${flakeDir}\``);
const flakeDotLock = `${flakeDir}/flake.lock`;
const commitMessage =
this.commitMessage !== ""
? this.commitMessage
: renderCommitMessage(
this.commitMessageTemplate,
flakeDir,
flakeDotLock,
);
// Nix command of this form: // Nix command of this form:
// nix ${maybe nix options} flake ${"update" or "lock"} ${maybe --update-input flags} --commit-lock-file --commit-lockfile-summary ${commit message} // nix ${maybe nix options} flake ${"update" or "lock"} ${maybe --update-input flags} --commit-lock-file --commit-lockfile-summary ${commit message}
// Example commands: // Example commands:
@ -87,12 +40,11 @@ class UpdateFlakeLockAction extends DetSysAction {
const nixCommandArgs: string[] = makeNixCommandArgs( const nixCommandArgs: string[] = makeNixCommandArgs(
this.nixOptions, this.nixOptions,
this.flakeInputs, this.flakeInputs,
commitMessage, this.commitMessage,
); );
actionsCore.debug( actionsCore.debug(
JSON.stringify({ JSON.stringify({
directory: flakeDir,
options: this.nixOptions, options: this.nixOptions,
inputs: this.flakeInputs, inputs: this.flakeInputs,
message: this.commitMessage, message: this.commitMessage,
@ -101,7 +53,7 @@ class UpdateFlakeLockAction extends DetSysAction {
); );
const execOptions: actionsExec.ExecOptions = { const execOptions: actionsExec.ExecOptions = {
cwd: flakeDir, cwd: this.pathToFlakeDir !== null ? this.pathToFlakeDir : undefined,
}; };
const exitCode = await actionsExec.exec("nix", nixCommandArgs, execOptions); const exitCode = await actionsExec.exec("nix", nixCommandArgs, execOptions);
@ -110,69 +62,9 @@ class UpdateFlakeLockAction extends DetSysAction {
this.recordEvent(EVENT_EXECUTION_FAILURE, { this.recordEvent(EVENT_EXECUTION_FAILURE, {
exitCode, exitCode,
}); });
actionsCore.setFailed( actionsCore.setFailed(`non-zero exit code of ${exitCode} detected`);
`non-zero exit code of ${exitCode} detected while updating directory \`${flakeDir}\``,
);
} else { } else {
actionsCore.info( actionsCore.info(`flake.lock file was successfully updated`);
`flake.lock file in \`${flakeDir}\` was successfully updated`,
);
}
}
private validateInputs(): void {
// Ensure that either `path-to-flake-dir` or `flake-dirs` is set to a meaningful value but not both
if (
this.flakeDirsInput !== null &&
this.flakeDirsInput.length > 0 &&
this.pathToFlakeDir !== null &&
this.pathToFlakeDir !== ""
) {
throw new Error(
"Both `path-to-flake-dir` and `flake-dirs` are set, whereas only one can be",
);
}
// Ensure that `flake-dirs` isn't an empty array if set
if (this.flakeDirsInput !== null && this.flakeDirsInput.length === 0) {
throw new Error(
"The `flake-dirs` input is set to an empty array; it must contain at least one directory",
);
}
// Ensure that both `flake-dirs` and `inputs` aren't set at the same time
if (
this.flakeDirsInput !== null &&
this.flakeDirsInput.length > 0 &&
this.flakeInputs.length > 0
) {
throw new Error(
`You've set both \`flake-dirs\` and \`inputs\` but you can only set one`,
);
}
}
private ensureDirectoryExists(flakeDir: string): void {
actionsCore.debug(`Checking that flake directory \`${flakeDir}\` exists`);
// Ensure the directory exists
fs.access(flakeDir, fs.constants.F_OK, (err) => {
if (err !== null) {
throw new Error(`Directory \`${flakeDir}\` doesn't exist`);
} else {
actionsCore.debug(`Flake directory \`${flakeDir}\` exists`);
}
});
}
private ensureDirectoryIsFlake(flakeDir: string): void {
const flakeDotNix = `${flakeDir}/flake.nix`;
if (!fs.existsSync(flakeDotNix)) {
throw new Error(
`Directory \`${flakeDir}\` is not a valid flake as it doesn't contain a \`flake.nix\``,
);
} else {
actionsCore.debug(`Directory \`${flakeDir}\` is a valid flake`);
} }
} }
} }

View File

@ -1,16 +1,16 @@
import { makeNixCommandArgs } from "./nix.js"; import { makeNixCommandArgs } from "./nix.js";
import { expect, test } from "vitest"; import { expect, test } from "vitest";
test("Nix command arguments", () => { type TestCase = {
type TestCase = { inputs: {
inputs: { nixOptions: string[];
nixOptions: string[]; flakeInputs: string[];
flakeInputs: string[]; commitMessage: string;
commitMessage: string;
};
expected: string[];
}; };
expected: string[];
};
test("Nix command arguments", () => {
const testCases: TestCase[] = [ const testCases: TestCase[] = [
{ {
inputs: { inputs: {
@ -24,7 +24,8 @@ test("Nix command arguments", () => {
"flake", "flake",
"update", "update",
"--commit-lock-file", "--commit-lock-file",
"--commit-lockfile-summary", "--option",
"commit-lockfile-summary",
"just testing", "just testing",
], ],
}, },
@ -42,7 +43,8 @@ test("Nix command arguments", () => {
"--update-input", "--update-input",
"rust-overlay", "rust-overlay",
"--commit-lock-file", "--commit-lock-file",
"--commit-lockfile-summary", "--option",
"commit-lockfile-summary",
"just testing", "just testing",
], ],
}, },
@ -57,7 +59,8 @@ test("Nix command arguments", () => {
"flake", "flake",
"update", "update",
"--commit-lock-file", "--commit-lock-file",
"--commit-lockfile-summary", "--option",
"commit-lockfile-summary",
"just testing", "just testing",
], ],
}, },

View File

@ -9,10 +9,23 @@ export function makeNixCommandArgs(
input, input,
]); ]);
// NOTE(cole-h): In Nix versions 2.23.0 and later, `commit-lockfile-summary` became an alias to
// the setting `commit-lock-file-summary` (https://github.com/NixOS/nix/pull/10691), and Nix does
// not treat aliases the same as their "real" setting by requiring setting aliases to be
// configured via `--option <alias name> <option value>`
// (https://github.com/NixOS/nix/issues/10989).
// So, we go the long way so that we can support versions both before and after Nix 2.23.0.
const lockfileSummaryFlags = [
"--option",
"commit-lockfile-summary",
commitMessage,
];
const updateLockMechanism = flakeInputFlags.length === 0 ? "update" : "lock"; const updateLockMechanism = flakeInputFlags.length === 0 ? "update" : "lock";
return nixOptions return nixOptions
.concat(["flake", updateLockMechanism]) .concat(["flake", updateLockMechanism])
.concat(flakeInputFlags) .concat(flakeInputFlags)
.concat(["--commit-lock-file", "--commit-lockfile-summary", commitMessage]); .concat(["--commit-lock-file"])
.concat(lockfileSummaryFlags);
} }

View File

@ -1,75 +0,0 @@
import { renderCommitMessage, renderPullRequestBody } from "./template.js";
import { template } from "handlebars";
import { Test, describe, expect, test } from "vitest";
describe("templating", () => {
test("commit message", () => {
type TestCase = {
template: string;
flakeDotLockDir: string;
flakeDotLock: string;
expected: string;
};
const testCases: TestCase[] = [
{
template: "Updating flake.lock in dir {{ flake_dot_lock_dir }}",
flakeDotLockDir: ".",
flakeDotLock: "./flake.lock",
expected: "Updating flake.lock in dir .",
},
{
template:
"Here I go doing some updating of my pristine flake.lock at {{ flake_dot_lock }}",
flakeDotLockDir: "subflake",
flakeDotLock: "subflake/flake.lock",
expected:
"Here I go doing some updating of my pristine flake.lock at subflake/flake.lock",
},
{
template: "This variable doesn't exist: {{ foo }}",
flakeDotLockDir: ".",
flakeDotLock: "./flake.lock",
expected: "This variable doesn't exist: ",
},
];
testCases.forEach(
({ template, flakeDotLockDir, flakeDotLock, expected }) => {
expect(
renderCommitMessage(template, flakeDotLockDir, flakeDotLock),
).toEqual(expected);
},
);
});
test("pull request body", () => {
type TestCase = {
template: string;
dirs: string[];
expected: string;
};
const testCases: TestCase[] = [
{
template: "Updated inputs: {{ comma_separated_dirs }}",
dirs: ["."],
expected: "Updated inputs: .",
},
{
template: "Updated inputs: {{ space_separated_dirs }}",
dirs: ["subflake", "subflake2"],
expected: "Updated inputs: subflake subflake2",
},
{
template: "Updated inputs:\n{{ updated_dirs_list }}",
dirs: ["flake1", "flake2"],
expected: `Updated inputs:\n* flake1\n* flake2`,
},
];
testCases.forEach(({ template, dirs, expected }) => {
expect(renderPullRequestBody(template, dirs)).toEqual(expected);
});
});
});

View File

@ -1,39 +0,0 @@
import Handlebars from "handlebars";
export function renderPullRequestBody(
template: string,
dirs: string[],
): string {
const commaSeparated = dirs.join(", ");
const spaceSeparated = dirs.join(" ");
const dirsList = dirs.map((d: string) => `* ${d}`).join("\n");
const tpl = Handlebars.compile(template);
return tpl({
// eslint-disable-next-line camelcase
comma_separated_dirs: commaSeparated,
// eslint-disable-next-line camelcase
space_separated_dirs: spaceSeparated,
// eslint-disable-next-line camelcase
updated_dirs_list: dirsList,
});
}
export function renderCommitMessage(
template: string,
flakeDotLockDir: string,
flakeDotLock: string,
): string {
return render(template, {
// eslint-disable-next-line camelcase
flake_dot_lock_dir: flakeDotLockDir,
// eslint-disable-next-line camelcase
flake_dot_lock: flakeDotLock,
});
}
function render(template: string, inputs: Record<string, string>): string {
const tpl = Handlebars.compile(template);
return tpl(inputs);
}