---
metadata:
  - name: generator
    content: Diplodoc Platform v5.50.6
alternate:
  - https://sourcecraft.dev/portal/docs/en/sourcecraft/operations/ci-cd.md
  - https://sourcecraft.dev/portal/docs/ru/sourcecraft/operations/ci-cd.md
---
> **Documentation Index:** Fetch the complete configuration index at https://sourcecraft.dev/portal/docs/en/llms.txt

# Configuring CI/CD in a SourceCraft repository

<!-- source: en/_includes/sourcecraft/configuration-tip.md -->
{% note tip %}

You can set up and view repository configurations in the SourceCraft interface under <svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="none" viewBox="0 0 16 16"><path fill="currentColor" fill-rule="evenodd" d="M7.199 2H8.8a.2.2 0 0 1 .2.2c0 1.808 1.958 2.939 3.524 2.034a.2.2 0 0 1 .271.073l.802 1.388a.2.2 0 0 1-.073.272c-1.566.904-1.566 3.164 0 4.069a.2.2 0 0 1 .073.271l-.802 1.388a.2.2 0 0 1-.271.073C10.958 10.863 9 11.993 9 13.8a.2.2 0 0 1-.199.2H7.2a.2.2 0 0 1-.2-.2c0-1.808-1.958-2.938-3.524-2.034a.2.2 0 0 1-.272-.073l-.8-1.388a.2.2 0 0 1 .072-.271c1.566-.905 1.566-3.165 0-4.07a.2.2 0 0 1-.073-.27l.801-1.389a.2.2 0 0 1 .272-.072C5.042 5.138 7 4.007 7 2.199c0-.11.089-.199.199-.199M5.5 2.2c0-.94.76-1.7 1.699-1.7H8.8c.94 0 1.7.76 1.7 1.7a.85.85 0 0 0 1.274.735 1.7 1.7 0 0 1 2.32.622l.802 1.388c.469.813.19 1.851-.622 2.32a.85.85 0 0 0 0 1.472 1.7 1.7 0 0 1 .622 2.32l-.802 1.388a1.7 1.7 0 0 1-2.32.622.85.85 0 0 0-1.274.735c0 .939-.76 1.7-1.699 1.7H7.2a1.7 1.7 0 0 1-1.699-1.7.85.85 0 0 0-1.274-.735 1.7 1.7 0 0 1-2.32-.622l-.802-1.388a1.7 1.7 0 0 1 .622-2.32.85.85 0 0 0 0-1.471 1.7 1.7 0 0 1-.622-2.32l.801-1.389a1.7 1.7 0 0 1 2.32-.622A.85.85 0 0 0 5.5 2.2m4 5.8a1.5 1.5 0 1 1-3 0 1.5 1.5 0 0 1 3 0M11 8a3 3 0 1 1-6 0 3 3 0 0 1 6 0" clip-rule="evenodd"/></svg> **Repository settings** in the <svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="none" viewBox="0 0 16 16"><path fill="currentColor" fill-rule="evenodd" d="m13.874 8.25-2.72 4.712a.5.5 0 0 1-.434.25H5.28a.5.5 0 0 1-.433-.25L2.127 8.25a.5.5 0 0 1 0-.5l2.72-4.712a.5.5 0 0 1 .433-.25h5.44a.5.5 0 0 1 .433.25l2.72 4.712a.5.5 0 0 1 0 .5m1.3-1.25a2 2 0 0 1 0 2l-2.72 4.712a2 2 0 0 1-1.733 1H5.28a2 2 0 0 1-1.732-1L.828 9a2 2 0 0 1 0-2l2.72-4.712a2 2 0 0 1 1.732-1h5.44a2 2 0 0 1 1.732 1zM9.5 8a1.5 1.5 0 1 1-3 0 1.5 1.5 0 0 1 3 0M11 8a3 3 0 1 1-6 0 3 3 0 0 1 6 0" clip-rule="evenodd"/></svg> **Configurations** section. Learn more in [this article](https://sourcecraft.dev/portal/docs/en/sourcecraft/operations/configuration-edit.md).

{% endnote %}
<!-- endsource: en/_includes/sourcecraft/configuration-tip.md -->

SourceCraft has an in-built [CI/CD workflow](https://sourcecraft.dev/portal/docs/en/sourcecraft/concepts/ci-cd.md) management mechanism.

<!-- source: en/_includes/sourcecraft/ci-cd/config-file-description.md -->
The CI/CD configuration is set up for a particular repository and stored in a file named `.sourcecraft/ci.yaml`.

General format of the `.sourcecraft/ci.yaml` configuration file:

```yaml
on:
  pull_request:
    - workflows: [<list_of_workflows>]
      filter:
        source_branches: [<list_of_source_branches>]
        target_branches: [<list_of_target_branches>]
        paths: [<list_of_paths>]

  push:
    - workflows: [<list_of_workflows>]
      filter:
        branches: [<list_of_branches>]
        paths: [<list_of_paths>]
    - workflows: [<list_of_workflows>]
      filter:
        tags: [<list_of_tags>]

  schedule:
    - workflows: [<list_of_workflows>]
      interval: <execution_interval_in_hours_or_minutes>
      description: <random description>
    - workflows: [<list_of_workflows>]
      cron: "<cron_expression>"
      description: <random description>

workflows:
  <workflow_name>:

    tasks:
      - name: <task_name>
        
        cubes:
          - name: <cube_name>
            image: <Docker_image_path>
            script:
              - <executed_script>
...
```

The configuration may include the following elements:
* [Trigger events](https://sourcecraft.dev/portal/docs/en/sourcecraft/ci-cd-ref/on.md) (`on` section)
* [Workflows](https://sourcecraft.dev/portal/docs/en/sourcecraft/ci-cd-ref/workflows.md) (`workflows` section)
* [Jobs](https://sourcecraft.dev/portal/docs/en/sourcecraft/ci-cd-ref/tasks.md) (`tasks` section)
* [Cubes](https://sourcecraft.dev/portal/docs/en/sourcecraft/ci-cd-ref/cubes.md) (`cubes` section)
* [Service connections](https://sourcecraft.dev/portal/docs/en/sourcecraft/ci-cd-ref/tokens.md) (`tokens` section)
* [Environment variables](https://sourcecraft.dev/portal/docs/en/sourcecraft/ci-cd-ref/env.md) (`env` section)

{% note tip %}

The `.sourcecraft/ci.yaml` file supports file structure output as well as search for declarations and element usages. For more information, see [Navigating and searching by code in SourceCraft](https://sourcecraft.dev/portal/docs/en/sourcecraft/operations/code-navigation.md).

{% endnote %}

You can either use nested structure for configuration elements or mark them up as separate sections.

{% cut "Example of CI/CD configuration marked up as separate sections" %}

```yaml
on:
  pull_request:
    - workflows: my-test-workflow
      filter:
        source_branches: ["**", "!test**"]
        target_branches: "main"

workflows:
  my-test-workflow:
    tasks:
      - my-test-task

tasks:
  - name: my-test-task
    cubes:
      - name: my-test-cube
        uses: hello-cube

cubes:
  - name: hello-cube
    script:
      - echo "Hello, world!"
```

{% endcut %}

The configuration file supports [secrets](https://sourcecraft.dev/portal/docs/en/sourcecraft/concepts/index.md#secrets). Learn more in [Using the value of a secret in CI/CD](https://sourcecraft.dev/portal/docs/en/sourcecraft/operations/secrets.md#use-secret-in-ci-cd).
<!-- endsource: en/_includes/sourcecraft/ci-cd/config-file-description.md -->

CI/CD workflows are run by trigger events. Such events may include pushing changes to a remote repository branch (`push`), creating a pull request (`pull_request`), or running a scheduled execution (`schedule`).

You can configure different workflows for different events. You can also configure triggers for specific branches or paths in the repository.

For a description of the configuration elements, see the [CI/CD reference](https://sourcecraft.dev/portal/docs/en/sourcecraft/ci-cd-ref/index.md).

You can configure CI/CD [when creating a new repository](#when-creating) or in an [existing one](#existing).

## Configuring CI/CD when creating a repository {#when-creating}

1. Open the SourceCraft [home page](https://sourcecraft.dev).
1. In the left-hand panel, click <svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="none" viewBox="0 0 16 16"><path fill="currentColor" fill-rule="evenodd" d="M8 1.75a.75.75 0 0 1 .75.75v4.75h4.75a.75.75 0 0 1 0 1.5H8.75v4.75a.75.75 0 0 1-1.5 0V8.75H2.5a.75.75 0 0 1 0-1.5h4.75V2.5A.75.75 0 0 1 8 1.75" clip-rule="evenodd"/></svg> **Create repository**.
1. In the window that opens, set the repository parameters.
1. Under **Configuration**, select **Add a CI/CD template**.
1. Select the CI/CD configuration template from the **YAML** drop-down list:
    * `Docker`
    * `HelloWorld`
    * `Java`
    * `NodeJS`
    * `Python`

    For the contents of the templates, see [Examples](#examples).

1. Click **Create repository**.

    The root of the created repository will contain the `.sourcecraft/ci.yaml` file with the CI/CD configuration template.

## Configuring CI/CD in an existing repository {#existing}

1. Clone the repository:

    <!-- source: en/_includes/sourcecraft/clone-repo-workflow.md -->
    1. [Install Git](https://git-scm.com/downloads).
    1. Open the SourceCraft [home page](https://sourcecraft.dev).
    1. On the <svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="none" viewBox="0 0 16 16"><path fill="currentColor" fill-rule="evenodd" d="M12.5 12.618c.307-.275.5-.674.5-1.118V6.977a1.5 1.5 0 0 0-.585-1.189l-3.5-2.692a1.5 1.5 0 0 0-1.83 0l-3.5 2.692A1.5 1.5 0 0 0 3 6.978V11.5A1.496 1.496 0 0 0 4.493 13H5V9.5a2 2 0 0 1 2-2h2a2 2 0 0 1 2 2V13h.507c.381-.002.73-.146.993-.382m2-1.118a3 3 0 0 1-3 3h-7a3 3 0 0 1-3-3V6.977A3 3 0 0 1 2.67 4.6l3.5-2.692a3 3 0 0 1 3.66 0l3.5 2.692a3 3 0 0 1 1.17 2.378zm-5-2A.5.5 0 0 0 9 9H7a.5.5 0 0 0-.5.5V13h3z" clip-rule="evenodd"/></svg> **Home** tab, under <svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="none" viewBox="0 0 16 16"><path fill="currentColor" fill-rule="evenodd" d="M3.999 3.5h.242c.559 0 1.049.37 1.202.907l.171.598A2.75 2.75 0 0 0 8.26 7h5.24v4a1.5 1.5 0 0 1-1.5 1.5H4A1.5 1.5 0 0 1 2.5 11V5a1.5 1.5 0 0 1 1.499-1.5m9.501 2h-1.242a1.25 1.25 0 0 1-1.201-.907l-.171-.598a3 3 0 0 0-.195-.495H12A1.5 1.5 0 0 1 13.5 5zM8.241 2H4a3 3 0 0 0-.457.035A3 3 0 0 0 2 2.764 3 3 0 0 0 1 5v6a3 3 0 0 0 3 3h8a3 3 0 0 0 3-3V5a3 3 0 0 0-3-3zM7 3.5h1.242c.559 0 1.049.37 1.202.907l.171.598q.075.261.195.495H8.26a1.25 1.25 0 0 1-1.202-.907l-.171-.598A3 3 0 0 0 6.69 3.5z" clip-rule="evenodd"/></svg> **Your craftspace**, navigate to <svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="none" viewBox="0 0 16 16"><path fill="currentColor" fill-rule="evenodd" d="M2.5 8h11v3a1.5 1.5 0 0 1-1.5 1.5H4A1.5 1.5 0 0 1 2.5 11zm10.697-1.5-1.851-2.777a.5.5 0 0 0-.416-.223H5.07a.5.5 0 0 0-.416.223L2.803 6.5zM15 7.408V11a3 3 0 0 1-3 3H4a3 3 0 0 1-3-3V7.408a3 3 0 0 1 .504-1.664l1.902-2.853A2 2 0 0 1 5.07 2h5.86a2 2 0 0 1 1.664.89l1.902 2.854A3 3 0 0 1 15 7.408M9.25 11a.75.75 0 0 0 0-1.5h-2.5a.75.75 0 0 0 0 1.5z" clip-rule="evenodd"/></svg> **Repositories** and select your repository.

        Also, you can open any public repository.

    1. In the top-right corner of the repository page, click <svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="none" viewBox="0 0 16 16"><path fill="currentColor" fill-rule="evenodd" d="M1.867 6.097a.75.75 0 0 1 1.036-.23L8 9.111l5.097-3.244a.75.75 0 0 1 .806 1.266l-5.5 3.5a.75.75 0 0 1-.806 0l-5.5-3.5a.75.75 0 0 1-.23-1.036" clip-rule="evenodd"/></svg> **Clone**.
    1. From the **HTTPS** or **SSH** field, copy the <svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="none" viewBox="0 0 16 16"><path fill="currentColor" fill-rule="evenodd" d="M12 2.5H8A1.5 1.5 0 0 0 6.5 4v1H8a3 3 0 0 1 3 3v1.5h1A1.5 1.5 0 0 0 13.5 8V4A1.5 1.5 0 0 0 12 2.5M11 11h1a3 3 0 0 0 3-3V4a3 3 0 0 0-3-3H8a3 3 0 0 0-3 3v1H4a3 3 0 0 0-3 3v4a3 3 0 0 0 3 3h4a3 3 0 0 0 3-3zM4 6.5h4A1.5 1.5 0 0 1 9.5 8v4A1.5 1.5 0 0 1 8 13.5H4A1.5 1.5 0 0 1 2.5 12V8A1.5 1.5 0 0 1 4 6.5" clip-rule="evenodd"/></svg> repository cloning link.

        Depending on the cloning connection protocol, different domains are used:

        #|
        || **Protocol** | **Domain** | **Cloning link** ||
        || HTTPS | `git.sourcecraft.dev` | `https://git@git.sourcecraft.dev/<organization_slug>/<repository_slug>.git` ||
        || SSH | `ssh.sourcecraft.dev` | `ssh://ssh.sourcecraft.dev/<organization_slug>/<repository_slug>.git` ||
        |#

    1. In the terminal, run this command:

        ```bash
        git clone <link_for_cloning_repository>
        ```

        {% cut "Example of a command for cloning a repository with SourceCraft documentation" %}

        ```bash
        git clone https://git@git.sourcecraft.dev/sourcecraft/documentation.git
        ```

        {% endcut %}

        <!-- source: en/_includes/sourcecraft/private-repo-clone-note.md -->
        {% note warning %}

        To clone a [private or internal repository](https://sourcecraft.dev/portal/docs/en/sourcecraft/concepts/index.md#repos), authenticate with a [personal access token (PAT)](https://sourcecraft.dev/portal/docs/en/sourcecraft/security/pat.md) or [SSH key](https://sourcecraft.dev/portal/docs/en/sourcecraft/security/ssh.md).

        {% endnote %}
        <!-- endsource: en/_includes/sourcecraft/private-repo-clone-note.md -->

    1. Go to your cloned repository:
        
        ```bash
        cd <repository_name>
        ```
    <!-- endsource: en/_includes/sourcecraft/clone-repo-workflow.md -->

1. Generate a CI/CD `.sourcecraft/ci.yaml` configuration file as described in the [CI/CD reference](#examples) or use the templates in [Examples](https://sourcecraft.dev/portal/docs/en/sourcecraft/ci-cd-ref/index.md).

1. Add the CI/CD configuration file to the `git` index, commit, and push the changes to the `main` branch:

    ```bash
    git add .sourcecraft/ci.yaml
    git commit -m "Added CI/CD configuration"
    git push -u origin main
    ```

## Checking CI/CD workflow execution {#check-ci-cd} 

1. Depending on the settings specified in `.sourcecraft/ci.yaml`, run a trigger event.
1. Check CI/CD workflow execution:

    <!-- source: en/_includes/sourcecraft/ci-cd/ui-overview.md -->
    1. Under <svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="none" viewBox="0 0 16 16"><path fill="currentColor" fill-rule="evenodd" d="M10.218 3.216a.75.75 0 0 0-1.436-.431l-3 10a.75.75 0 0 0 1.436.43zM4.53 4.97a.75.75 0 0 1 0 1.06L2.56 8l1.97 1.97a.75.75 0 0 1-1.06 1.06l-2.5-2.5a.75.75 0 0 1 0-1.06l2.5-2.5a.75.75 0 0 1 1.06 0m6.94 6.06a.75.75 0 0 1 0-1.06L13.44 8l-1.97-1.97a.75.75 0 0 1 1.06-1.06l2.5 2.5a.75.75 0 0 1 0 1.06l-2.5 2.5a.75.75 0 0 1-1.06 0" clip-rule="evenodd"/></svg> **Code** on the repository page, go to <svg xmlns="http://www.w3.org/2000/svg" width="16" height="16" fill="none" viewBox="0 0 16 16"><g clip-path="url(#svg-cy5hb3wj__a)"><path fill="currentColor" fill-rule="evenodd" d="M4.61 2.503a6.47 6.47 0 0 1 3.383-.984 6.48 6.48 0 0 1 4.515 1.77l-.004-.559a.75.75 0 1 1 1.5-.013l.021 2.5a.75.75 0 0 1-.743.756l-2.497.022a.75.75 0 1 1-.013-1.5l.817-.007a4.98 4.98 0 0 0-3.583-1.469 4.97 4.97 0 0 0-2.602.756.75.75 0 0 1-.795-1.272m9.097 8.716a6.5 6.5 0 0 0 .84-3.422.75.75 0 1 0-1.5.053 4.97 4.97 0 0 1-.646 2.63 4.98 4.98 0 0 1-3.064 2.37l.403-.712a.75.75 0 0 0-1.306-.738l-1.229 2.173a.75.75 0 0 0 .283 1.022l2.176 1.23a.75.75 0 1 0 .739-1.305l-.487-.275a6.48 6.48 0 0 0 3.79-3.026m-11.258.099a6.47 6.47 0 0 0 2.544 2.438.75.75 0 0 0 .704-1.325 4.97 4.97 0 0 1-1.955-1.875 4.98 4.98 0 0 1-.52-3.838l.415.705a.75.75 0 1 0 1.292-.762L3.66 4.511a.75.75 0 0 0-1.027-.266L.481 5.513a.75.75 0 1 0 .761 1.293l.483-.284a6.48 6.48 0 0 0 .724 4.796" clip-rule="evenodd"/></g><defs><clipPath id="svg-cy5hb3wj__a"><path fill="currentColor" d="M0 0h16v16H0z"/></clipPath></defs></svg> **CI/CD**.
    1. Select a running workflow.
    1. The page that opens will display all workflow tasks, cubes (task steps), as well as statuses and execution results.
    <!-- endsource: en/_includes/sourcecraft/ci-cd/ui-overview.md -->

## Examples {#examples}

{% list tabs %}
  
  Open the config.json file. It already contains a basic VM configuration, but you can customize it:

- Hello World

  ```yaml
  # This basic workflow 
  # will help you get started with SourceCraft CI/CD

  # Configuring a trigger event to execute a workflow
  on:
    # Executing a workflow triggered by sending changes to the remote repository's main branch
    # or by creating a pull request for the main branch
    pull_request:
      - workflows: [sample-workflow]
        filter:
          source_branches: ["**", "!test**"]
          target_branches: "main"

    push:
      - workflows: [sample-workflow]
        filter:
          branches: ["main"]

  workflows:
    sample-workflow:
      tasks:
        - name: sample-task
        
          cubes:
            # Starting a set of commands 
            - name: sample-cube1
              image: docker.io/library/node
              script:
                - echo Hello, world!
             
            - name: sample-cube2
              script:
                - echo Add other cubes to build,
                - echo test, and deploy your project.
  ```

- Docker

  ```yaml
  on:
    push:
      - workflows: build-workflow 
        filter: 
          branches: ["main"]

  workflows:
    build-workflow:
      tasks:
        - build-task

  tasks:
    - name: build-task
      env:
          IMAGE_URI: dockerhub_account/hello-world
      cubes:
        - name: docker-build
          script:
            - docker build . --file Dockerfile --tag $IMAGE_URI:$(date +%s)
        # Optional: sending a Docker image to a registry
        # Provide to the cube the credentials for authentication in the registry,
        # e.g., DockerHub or Yandex Container Registry
        # - name: push-dockerhub
        #   env:
        #     USER: username
        #     PAT: personal_access_token
        #   script:
        #     - echo $PAT | docker login --username $USER --password-stdin
        #     - docker push $IMAGE_URI
  ```

  To test the CI\CD process, send a commit with `Dockerfile` to the `main` branch:

  ```dockerfile
  FROM alpine
  CMD ["echo", "Hello World!!"]
  ```

- Python

  ```yaml
  on:
    push:
      - workflows: [sample-workflow]
        filter:
          branches: ["main"]

  workflows:
    sample-workflow:
      tasks:
        - name: sample-task
          cubes:
            - name: sample-cube1
              image: docker.io/library/python
              script:
                - python -m pip install --upgrade pip
                - if [ -f requirements.txt ]; then pip install -r requirements.txt; fi
  ```

  Add data specific to testing Python applications to the `.gitignore` file.

  {% cut ".gitignore example" %}

  <!-- source: en/_includes/sourcecraft/ci-cd/python-gitignore.md -->
  ```text
  # Byte-compiled / optimized / DLL files
  __pycache__/
  *.py[cod]
  *$py.class

  # C extensions
  *.so

  # Distribution / packaging
  .Python
  build/
  develop-eggs/
  dist/
  downloads/
  eggs/
  .eggs/
  lib/
  lib64/
  parts/
  sdist/
  var/
  wheels/
  share/python-wheels/
  *.egg-info/
  .installed.cfg
  *.egg
  MANIFEST

  # PyInstaller
  #  Usually these files are written by a python script from a template
  #  before PyInstaller builds the exe, so as to inject date/other infos into it.
  *.manifest
  *.spec

  # Installer logs
  pip-log.txt
  pip-delete-this-directory.txt

  # Unit test / coverage reports
  htmlcov/
  .tox/
  .nox/
  .coverage
  .coverage.*
  .cache
  nosetests.xml
  coverage.xml
  *.cover
  *.py,cover
  .hypothesis/
  .pytest_cache/
  cover/

  # Translations
  *.mo
  *.pot

  # Django stuff:
  *.log
  local_settings.py
  db.sqlite3
  db.sqlite3-journal

  # Flask stuff:
  instance/
  .webassets-cache

  # Scrapy stuff:
  .scrapy

  # Sphinx documentation
  docs/_build/

  # PyBuilder
  .pybuilder/
  target/

  # Jupyter Notebook
  .ipynb_checkpoints

  # IPython
  profile_default/
  ipython_config.py

  # pyenv
  #   For a library or package, you might want to ignore these files since the code is
  #   intended to run in multiple environments; otherwise, check them in:
  # .python-version

  # pipenv
  #   According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
  #   However, in case of collaboration, if having platform-specific dependencies or dependencies
  #   having no cross-platform support, pipenv may install dependencies that don't work, or not
  #   install all needed dependencies.
  #Pipfile.lock

  # UV
  #   Similar to Pipfile.lock, it is generally recommended to include uv.lock in version control.
  #   This is especially recommended for binary packages to ensure reproducibility, and is more
  #   commonly ignored for libraries.
  #uv.lock

  # poetry
  #   Similar to Pipfile.lock, it is generally recommended to include poetry.lock in version control.
  #   This is especially recommended for binary packages to ensure reproducibility, and is more
  #   commonly ignored for libraries.
  #   https://python-poetry.org/docs/basic-usage/#commit-your-poetrylock-file-to-version-control
  #poetry.lock

  # pdm
  #   Similar to Pipfile.lock, it is generally recommended to include pdm.lock in version control.
  #pdm.lock
  #   pdm stores project-wide configurations in .pdm.toml, but it is recommended to not include it
  #   in version control.
  #   https://pdm.fming.dev/latest/usage/project/#working-with-version-control
  .pdm.toml
  .pdm-python
  .pdm-build/

  # PEP 582; used by e.g. github.com/David-OConnor/pyflow and github.com/pdm-project/pdm
  __pypackages__/

  # Celery stuff
  celerybeat-schedule
  celerybeat.pid

  # SageMath parsed files
  *.sage.py

  # Environments
  .env
  .venv
  env/
  venv/
  ENV/
  env.bak/
  venv.bak/

  # Spyder project settings
  .spyderproject
  .spyproject

  # Rope project settings
  .ropeproject

  # mkdocs documentation
  /site

  # mypy
  .mypy_cache/
  .dmypy.json
  dmypy.json

  # Pyre type checker
  .pyre/

  # pytype static type analyzer
  .pytype/

  # Cython debug symbols
  cython_debug/

  # PyCharm
  #  JetBrains specific template is maintained in a separate JetBrains.gitignore that can
  #  be found at https://github.com/github/gitignore/blob/main/Global/JetBrains.gitignore
  #  and can be added to the global gitignore or merged into this file. For a more nuclear
  #  option (not recommended) you can uncomment the following to ignore the entire idea folder.
  #.idea/

  # PyPI configuration file
  .pypirc
  ```
  <!-- endsource: en/_includes/sourcecraft/ci-cd/python-gitignore.md -->

  {% endcut %}

  To test the CI\CD process, send a commit with a `main.py` file to the `main` branch:

  ```python
  print('Hello SourceCraft')
  print('Hello SourceCraft')

  for i in range(10):
      print(i)

  # input 
  hi = input()
  print(hi)
  ```

- Node.js

  ```yaml
  on:
    push:
      - workflows: build-workflow 
        filter: 
          branches: ["main"]

  workflows:
    build-workflow:
      tasks:
        - build-task

  tasks:
    - name: build-task
      cubes:
        - name: build-npm
          image: docker.io/library/node
          script:
            - npm ci
            - npm run build --if-present
            - npm test
  ```

  To test the CI\CD process, send a commit with the following files to the `main` branch:
  * `index.js`:

    ```js
    //index.js

    function helloNpm() {
        return "hello SourceCraft CI/CD"
    }

    module.exports = helloNpm
    ```

  * `package.json`:

    ```json
    {
        "name": "sourcecraft-samples-nodejs",
        "version": "1.0.0",
        "description": "Sample for SourceCraft CI/CD",
        "license": "MIT",
        "author": "SourceCraft Team",
        "type": "commonjs",
        "main": "index.js",
        "scripts": {
          "test": "echo \"test passed\""
        }
    }
    ```

  * `package-lock.json`:

    ```json
    {
        "name": "sourcecraft-samples-nodejs",
        "version": "1.0.0",
        "lockfileVersion": 3,
        "requires": true,
        "packages": {
          "": {
            "name": "sourcecraft-samples-nodejs",
            "version": "1.0.0",
            "license": "MIT"
          }
        }
    }
    ```

- Java

  ```yaml
  # This workflow will build a Java project using Maven
  on:
    push:
      - workflows: publish-package-workflow
        filter:
          branches: ["main"]

  workflows:
    publish-package-workflow:
      settings:
        max_cube_duration: 10m
      tasks:
        - build-publish-task

  tasks:
    - name: build-publish-task
      cubes:
        - name: setup-jdk-maven
          script:
            - sudo apt install openjdk-21-jdk -y
            - sudo apt install maven -y
            - java --version
            - mvn --version
        - name: test
          script:
            - echo 'test'
        - name: package
          script:
            - mvn package
          # Optional: Export the artifact named
          # `sourcecraft-sample-maven-1.0-SNAPSHOT.jar` from the target directory.
          # You can download this artifact from the cube in the CI/CD section
          #artifacts: 
          #  paths:
          #    - target/sourcecraft-sample-maven-1.0-SNAPSHOT.jar
  ```

  Add data specific to testing Java applications to the `.gitignore` file.

  {% cut ".gitignore example" %}

  <!-- source: en/_includes/sourcecraft/ci-cd/java-gitignore.md -->
  ```text
  ##############################
  ## Java
  ##############################
  .mtj.tmp/
  *.class
  *.jar
  *.war
  *.ear
  *.nar
  hs_err_pid*
  replay_pid*

  ##############################
  ## Maven
  ##############################
  target/
  pom.xml.tag
  pom.xml.releaseBackup
  pom.xml.versionsBackup
  pom.xml.next
  pom.xml.bak
  release.properties
  dependency-reduced-pom.xml
  buildNumber.properties
  .mvn/timing.properties
  .mvn/wrapper/maven-wrapper.jar

  ##############################
  ## Gradle
  ##############################
  bin/
  build/
  .gradle
  .gradletasknamecache
  gradle-app.setting
  !gradle-wrapper.jar

  ##############################
  ## IntelliJ
  ##############################
  out/
  .idea/
  .idea_modules/
  *.iml
  *.ipr
  *.iws

  ##############################
  ## Eclipse
  ##############################
  .settings/
  bin/
  tmp/
  .metadata
  .classpath
  .project
  *.tmp
  *.bak
  *.swp
  *~.nib
  local.properties
  .loadpath
  .factorypath

  ##############################
  ## NetBeans
  ##############################
  nbproject/private/
  build/
  nbbuild/
  dist/
  nbdist/
  nbactions.xml
  nb-configuration.xml

  ##############################
  ## Visual Studio Code
  ##############################
  .vscode/
  .code-workspace

  ##############################
  ## OS X
  ##############################
  .DS_Store

  ##############################
  ## Miscellaneous
  ##############################
  *.log
  ```
  <!-- endsource: en/_includes/sourcecraft/ci-cd/java-gitignore.md -->

  {% endcut %}

  To test the CI\CD process, send a commit with the following files to the `main` branch:

  * `pom.xml`:

    <!-- source: en/_includes/sourcecraft/ci-cd/pom-xml-for-java.md -->
    ```xml
    <?xml version="1.0" encoding="UTF-8"?>
    <project xmlns="http://maven.apache.org/POM/4.0.0" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
      xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd">
      <modelVersion>4.0.0</modelVersion>

      <groupId>com.mycompany.app</groupId>
      <artifactId>sourcecraft-sample-maven</artifactId>
      <version>1.0-SNAPSHOT</version>

      <name>bondarevsky-maven</name>
      <!-- FIXME change it to the project's website -->
      <url>http://www.example.com</url>

      <properties>
        <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding>
        <maven.compiler.release>17</maven.compiler.release>
      </properties>

      <dependencyManagement>
        <dependencies>
          <dependency>
            <groupId>org.junit</groupId>
            <artifactId>junit-bom</artifactId>
            <version>5.11.0</version>
            <type>pom</type>
            <scope>import</scope>
          </dependency>
        </dependencies>
      </dependencyManagement>

      <dependencies>
        <dependency>
          <groupId>org.junit.jupiter</groupId>
          <artifactId>junit-jupiter-api</artifactId>
          <scope>test</scope>
        </dependency>
        <!-- Optionally: parameterized tests support -->
        <dependency>
          <groupId>org.junit.jupiter</groupId>
          <artifactId>junit-jupiter-params</artifactId>
          <scope>test</scope>
        </dependency>
      </dependencies>

      <build>
        <pluginManagement><!-- lock down plugins versions to avoid using Maven defaults (may be moved to parent pom) -->
          <plugins>
            <!-- clean lifecycle, see https://maven.apache.org/ref/current/maven-core/lifecycles.html#clean_Lifecycle -->
            <plugin>
              <artifactId>maven-clean-plugin</artifactId>
              <version>3.4.0</version>
            </plugin>
            <!-- default lifecycle, jar packaging: see https://maven.apache.org/ref/current/maven-core/default-bindings.html#Plugin_bindings_for_jar_packaging -->
            <plugin>
              <artifactId>maven-resources-plugin</artifactId>
              <version>3.3.1</version>
            </plugin>
            <plugin>
              <artifactId>maven-compiler-plugin</artifactId>
              <version>3.13.0</version>
            </plugin>
            <plugin>
              <artifactId>maven-surefire-plugin</artifactId>
              <version>3.3.0</version>
            </plugin>
            <plugin>
              <artifactId>maven-jar-plugin</artifactId>
              <version>3.4.2</version>
            </plugin>
            <plugin>
              <artifactId>maven-install-plugin</artifactId>
              <version>3.1.2</version>
            </plugin>
            <plugin>
              <artifactId>maven-deploy-plugin</artifactId>
              <version>3.1.2</version>
            </plugin>
            <!-- site lifecycle, see https://maven.apache.org/ref/current/maven-core/lifecycles.html#site_Lifecycle -->
            <plugin>
              <artifactId>maven-site-plugin</artifactId>
              <version>3.12.1</version>
            </plugin>
            <plugin>
              <artifactId>maven-project-info-reports-plugin</artifactId>
              <version>3.6.1</version>
            </plugin>
          </plugins>
        </pluginManagement>
      </build>
    </project>
    ```
    <!-- endsource: en/_includes/sourcecraft/ci-cd/pom-xml-for-java.md -->

  * `src/test/java/com/mycompany/app/AppTest.java`:

    ```java
    package com.mycompany.app;

    import static org.junit.jupiter.api.Assertions.assertTrue;

    import org.junit.jupiter.api.Test;

    /**
     * Unit test for simple App.
     */
    public class AppTest {

        /**
         * Rigorous Test :-)
         */
        @Test
        public void shouldAnswerWithTrue() {
            assertTrue(true);
        }
    }
    ```

  * `src/main/java/com/mycompany/app/App.java`:

    ```java
    package com.mycompany.app;

    /**
     * Hello world!
     */
    public class App {
        public static void main(String[] args) {
            System.out.println("Hello World!");
        }
    }
    ```

{% endlist %}

#### Useful links {#see-also}

* [Repository templates](https://sourcecraft.dev/sourcecraft/repos)
* [Getting started with SourceCraft](https://sourcecraft.dev/portal/docs/en/sourcecraft/quickstart.md)
* [Continuous integration and continuous deployment in SourceCraft](https://sourcecraft.dev/portal/docs/en/sourcecraft/concepts/ci-cd.md)
* [CI/CD reference](https://sourcecraft.dev/portal/docs/en/sourcecraft/ci-cd-ref/index.md)
* [Configuring CI/CD with Yandex Cloud Functions](https://sourcecraft.dev/portal/docs/en/sourcecraft/tutorials/ci-cd-sourcecraft-functions.md)
* [Starting a workflow manually in a SourceCraft repository](https://sourcecraft.dev/portal/docs/en/sourcecraft/operations/run-workflow-manually.md)
* [Configuring a webhook in a SourceCraft repository](https://sourcecraft.dev/portal/docs/en/sourcecraft/operations/webhooks.md)
