cirruslabs / cirrus-ci-docs

Documentation for Cirrus CI 📚
https://cirrus-ci.org
MIT License
351 stars 109 forks source link

better way to set job level working directory? #1185

Open geekflyer opened 1 year ago

geekflyer commented 1 year ago

Description

I'm running some tasks in a monorepo where all the relevant code for the job is in the ui subdirectory. Is there a more elegant / more DRY way to change the working directory to a subdirectory of the repo than this?

load("github.com/cirrus-modules/helpers", "cache", "container", "script", "task")

def main(ctx):
    return [
        task(
            name = "ts-checks",
            instance = container("node:18"),
            instructions = [
                script("corepack", "cd ui && corepack enable"),
                cache(
                    name = "node_modules",
                    folder = "ui/node_modules",
                    fingerprint_script = "cat ui/pnpm-lock.yaml",
                    populate_script = "cd ui && pnpm install --frozen-lockfile",
                ),
                script("lint", "cd ui && pnpm lint"),
                script("build", "cd ui && pnpm build"),
            ],
        ),
    ]
fkorotkov commented 1 year ago

After thinking about it, it seems it's possible to override CIRRUS_WORKING_DIR via CIRRUS_ENV file:

task:
  container:
    image: alpine:latest
  change_dir_script:
    - mkdir -p foo
    - cd foo
    - echo "Hello, Bar!" >> bar.txt
    - echo "CIRRUS_WORKING_DIR=$CIRRUS_WORKING_DIR/foo" >> $CIRRUS_ENV
  print_script:
    - cat bar.txt

The example above will override the working directory in change_dir_script and every following instruction will respect it.

This behaviour was not intended when we added CIRRUS_ENV but it works. I've added an integration test to make sure the behaviour from the example above won't break.

geekflyer commented 1 year ago

cool thanks - that seems to work! I wrote a small starlark utility function to make this less verbose if anyone comes by this:

def change_working_dir(path):
    return script("change working directory to {}".format(path), 'echo "CIRRUS_WORKING_DIR=$CIRRUS_WORKING_DIR/{}" >> $CIRRUS_ENV'.format(path))

can be used like this:


task(
   instructions = [
       change_working_dir("my-sub-dir"),
       script("run stuff in sub dir", "echo stuff"),
   ]
)