From 1c8fc91b04a68e346a5410fff1310abc1890563e Mon Sep 17 00:00:00 2001 From: MitaWinata <9963516+MitaWinata@users.noreply.github.com> Date: Mon, 8 Jan 2024 13:39:41 +0100 Subject: [PATCH] feat: add new model --- .github/config/commitlint.config.js | 6 +++ .github/config/markdown-lint.config | 7 +++ .github/config/yaml-lint-config.yml | 31 +++++++++++ .github/scripts/install-agent-tools.sh | 6 +++ .github/workflows/a/deploy_a.yml | 23 ++++++++ .github/workflows/a/pr_a.yml | 24 +++++++++ .github/workflows/b/deploy_b.yml | 23 ++++++++ .github/workflows/b/pr_b.yml | 24 +++++++++ .github/workflows/docker.yml | 74 ++++++++++++++++++++++++++ .github/workflows/python_style.yml | 50 +++++++++++++++++ .github/workflows/release.yaml | 67 +++++++++++++++++++++++ .github/workflows/style.yml | 46 ++++++++++++++++ .github/workflows/tests.yml | 45 ++++++++++++++++ .release-please-manifest.json | 1 + README.md | 12 ++++- model/a/Dockerfile | 31 +++++++++++ model/a/README.md | 21 ++++++++ model/a/pyproject.toml | 30 +++++++++++ model/a/src/a/__init__.py | 0 model/a/src/a/main.py | 2 + model/a/tests/test_dummy.py | 2 + model/b/Dockerfile | 31 +++++++++++ model/b/README.md | 21 ++++++++ model/b/pyproject.toml | 29 ++++++++++ model/b/src/b/__init__.py | 0 model/b/src/b/main.py | 2 + model/b/tests/test_dummy.py | 2 + release-please-config.json | 14 +++++ 28 files changed, 623 insertions(+), 1 deletion(-) create mode 100644 .github/config/commitlint.config.js create mode 100644 .github/config/markdown-lint.config create mode 100644 .github/config/yaml-lint-config.yml create mode 100644 .github/scripts/install-agent-tools.sh create mode 100644 .github/workflows/a/deploy_a.yml create mode 100644 .github/workflows/a/pr_a.yml create mode 100644 .github/workflows/b/deploy_b.yml create mode 100644 .github/workflows/b/pr_b.yml create mode 100644 .github/workflows/docker.yml create mode 100644 .github/workflows/python_style.yml create mode 100644 .github/workflows/release.yaml create mode 100644 .github/workflows/style.yml create mode 100644 .github/workflows/tests.yml create mode 100644 .release-please-manifest.json create mode 100644 model/a/Dockerfile create mode 100644 model/a/README.md create mode 100644 model/a/pyproject.toml create mode 100644 model/a/src/a/__init__.py create mode 100644 model/a/src/a/main.py create mode 100644 model/a/tests/test_dummy.py create mode 100644 model/b/Dockerfile create mode 100644 model/b/README.md create mode 100644 model/b/pyproject.toml create mode 100644 model/b/src/b/__init__.py create mode 100644 model/b/src/b/main.py create mode 100644 model/b/tests/test_dummy.py create mode 100644 release-please-config.json diff --git a/.github/config/commitlint.config.js b/.github/config/commitlint.config.js new file mode 100644 index 0000000..edc13ff --- /dev/null +++ b/.github/config/commitlint.config.js @@ -0,0 +1,6 @@ +module.exports = { + extends: ['@commitlint/config-conventional'], + // Ignore defaults from https://github.com/conventional-changelog/commitlint/blob/master/%40commitlint/is-ignored/src/defaults.ts#L20-L26 + // to have warnings for fixup! etc. + defaultIgnores: false, +}; diff --git a/.github/config/markdown-lint.config b/.github/config/markdown-lint.config new file mode 100644 index 0000000..33cbe16 --- /dev/null +++ b/.github/config/markdown-lint.config @@ -0,0 +1,7 @@ +{ + "MD013": false, + "MD024": { + "siblings_only": true + }, + "MD012": false +} diff --git a/.github/config/yaml-lint-config.yml b/.github/config/yaml-lint-config.yml new file mode 100644 index 0000000..ad5abd1 --- /dev/null +++ b/.github/config/yaml-lint-config.yml @@ -0,0 +1,31 @@ +--- + +yaml-files: + - '*.yaml' + - '*.yml' + +ignore: + - '**/.deploy/charts/*/templates' + +rules: + braces: enable + brackets: enable + colons: enable + commas: enable + comments: enable + comments-indentation: enable + document-end: disable + document-start: disable + empty-lines: enable + empty-values: disable + hyphens: enable + indentation: enable + key-duplicates: enable + key-ordering: disable + line-length: disable + new-line-at-end-of-file: enable + new-lines: disable + octal-values: enable + quoted-strings: disable + trailing-spaces: enable + truthy: disable diff --git a/.github/scripts/install-agent-tools.sh b/.github/scripts/install-agent-tools.sh new file mode 100644 index 0000000..c01b7d4 --- /dev/null +++ b/.github/scripts/install-agent-tools.sh @@ -0,0 +1,6 @@ +#!/bin/bash + +# Installs tools needed for the agent + +sudo npm install -g markdownlint-cli +sudo pip install yamllint diff --git a/.github/workflows/a/deploy_a.yml b/.github/workflows/a/deploy_a.yml new file mode 100644 index 0000000..d6ee6ee --- /dev/null +++ b/.github/workflows/a/deploy_a.yml @@ -0,0 +1,23 @@ +name: FullWorkflow-Deploy-a + +on: + push: + branches: + - main + paths: + - 'model/a/**' + +jobs: + style: + uses: ./../.github/workflows/style.yml + tests_a: + uses: ./../.github/workflows/tests.yml + with: + src_path: "model/a" + python_style_a: + uses: ./../.github/workflows/python_style.yml + with: + src_path: "model/a" + release: + needs: [style, tests_a, python_style_a] + uses: ./../.github/workflows/release.yaml diff --git a/.github/workflows/a/pr_a.yml b/.github/workflows/a/pr_a.yml new file mode 100644 index 0000000..e413b41 --- /dev/null +++ b/.github/workflows/a/pr_a.yml @@ -0,0 +1,24 @@ +name: FullWorkflow-PR-a + +on: + pull_request: + branches: + - main + paths: + - 'model/a/**' + +jobs: + style: + uses: ./../.github/workflows/style.yml + tests_a: + uses: ./../.github/workflows/tests.yml + with: + src_path: "model/a" + python_style_a: + uses: ./../.github/workflows/python_style.yml + with: + src_path: "model/a" + docker_a: + uses: ./../.github/workflows/docker.yml + with: + build_context: "a" diff --git a/.github/workflows/b/deploy_b.yml b/.github/workflows/b/deploy_b.yml new file mode 100644 index 0000000..0326731 --- /dev/null +++ b/.github/workflows/b/deploy_b.yml @@ -0,0 +1,23 @@ +name: FullWorkflow-Deploy-b + +on: + push: + branches: + - main + paths: + - 'model/b/**' + +jobs: + style: + uses: ./../.github/workflows/style.yml + tests_b: + uses: ./../.github/workflows/tests.yml + with: + src_path: "model/b" + python_style_b: + uses: ./../.github/workflows/python_style.yml + with: + src_path: "model/b" + release: + needs: [style, tests_b, python_style_b] + uses: ./../.github/workflows/release.yaml diff --git a/.github/workflows/b/pr_b.yml b/.github/workflows/b/pr_b.yml new file mode 100644 index 0000000..c065a08 --- /dev/null +++ b/.github/workflows/b/pr_b.yml @@ -0,0 +1,24 @@ +name: FullWorkflow-PR-b + +on: + pull_request: + branches: + - main + paths: + - 'model/b/**' + +jobs: + style: + uses: ./../.github/workflows/style.yml + tests_b: + uses: ./../.github/workflows/tests.yml + with: + src_path: "model/b" + python_style_b: + uses: ./../.github/workflows/python_style.yml + with: + src_path: "model/b" + docker_b: + uses: ./../.github/workflows/docker.yml + with: + build_context: "b" diff --git a/.github/workflows/docker.yml b/.github/workflows/docker.yml new file mode 100644 index 0000000..df42a16 --- /dev/null +++ b/.github/workflows/docker.yml @@ -0,0 +1,74 @@ +name: BuildPublishImage + +on: + workflow_call: + inputs: + build_context: + description: 'build_context' + required: false + type: string + image_tag: + description: 'Image tag' + required: false + type: string + +permissions: + id-token: write + contents: read + packages: write + +env: + ACR_NAME: "monorepopwin.azurecr.io" + +jobs: + BuildDocker: + runs-on: ubuntu-latest + steps: + - name: Checkout repository + uses: actions/checkout@v4 + with: + fetch-depth: 0 + + - name: 'Az CLI login' + uses: azure/login@v1 + with: + client-id: ${{ vars.AZURE_CLIENT_ID }} + tenant-id: ${{ vars.AZURE_TENANT_ID }} + allow-no-subscriptions: true + + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v3 + + - name: Docker meta + id: meta + uses: docker/metadata-action@v5 + with: + images: | + ${{ env.ACR_NAME }}/${{ inputs.build_context }} + tags: | + type=edge,branch=main + type=ref,event=tag + type=ref,event=pr + type=raw, ${{ inputs.image_tag}} + + - name: Log into azurecr registry + run: | + TOKEN=$(az acr login --name ${{ env.ACR_NAME }} --expose-token --output tsv --query accessToken) + echo "::add-mask::${TOKEN}" + docker login ${{ env.ACR_NAME }} --username 00000000-0000-0000-0000-000000000000 --password-stdin <<< $TOKEN + shell: bash + + - name: Build, push if not PR + uses: docker/build-push-action@v5 + with: + context: model/${{ inputs.build_context }} + push: ${{ github.event_name != 'pull_request' }} + tags: ${{ steps.meta.outputs.tags }} + + - name: Azure Logout + if: always() + run: | + az logout + az cache purge + az account clear + shell: bash diff --git a/.github/workflows/python_style.yml b/.github/workflows/python_style.yml new file mode 100644 index 0000000..46cafd5 --- /dev/null +++ b/.github/workflows/python_style.yml @@ -0,0 +1,50 @@ +name: CheckStyle + +on: + workflow_call: + inputs: + src_path: + description: 'src_path' + required: false + type: string + +permissions: + contents: read + +jobs: + CheckCodeStyle: + runs-on: ubuntu-latest + strategy: + fail-fast: false + matrix: + version: ["3.9", "3.10"] + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + - name: Install Poetry + uses: snok/install-poetry@v1 + + - name: Set up Python + uses: actions/setup-python@v5 + with: + python-version: ${{matrix.version}} + cache: 'poetry' + + - name: Install dependencies + run: | + cd ${{ inputs.src_path }} + poetry install --only dev + shell: bash + + - name: Run isort + run: | + cd ${{ inputs.src_path }} + poetry run isort --check --profile black . + shell: bash + + - name: Run black + run: | + cd ${{ inputs.src_path }} + poetry run black --check --diff . + shell: bash diff --git a/.github/workflows/release.yaml b/.github/workflows/release.yaml new file mode 100644 index 0000000..c19f5e2 --- /dev/null +++ b/.github/workflows/release.yaml @@ -0,0 +1,67 @@ +name: Release Workflow + +on: + workflow_call: + outputs: + a-release_created: + value: ${{ jobs.release_job.outputs.a-release_created }} + a-tag_name: + value: ${{ jobs.release_job.outputs.a-tag_name }} + b-release_created: + value: ${{ jobs.release_job.outputs.b-release_created }} + b-tag_name: + value: ${{ jobs.release_job.outputs.b-tag_name }} + +permissions: + contents: write + pull-requests: write + id-token: write + packages: write + +concurrency: + group: release + +jobs: + release_job: + runs-on: ubuntu-latest + outputs: + a-release_created: ${{ steps.create_output.outputs.a-release_created }} + a-tag_name: ${{ steps.create_output.outputs.a-tag_name }} + b-release_created: ${{ steps.create_output.outputs.b-release_created }} + b-tag_name: ${{ steps.create_output.outputs.b-tag_name }} + steps: + - name: Checkout repository + uses: actions/checkout@v4 + with: + fetch-depth: 0 + - name: Release with release-please + uses: google-github-actions/release-please-action@v3 + id: release + with: + command: manifest + monorepo-tags: true + pull-request-header: ":robot: I have created a release" + - name: "Generate release-please output" + id: create_output + shell: bash + run: | + echo "a-release_created=$(echo ${{ steps.release.outputs['model/a--release_created'] }})" >> "$GITHUB_OUTPUT" + echo "a-tag_name=$(echo ${{ steps.release.outputs['model/a--tag_name'] }})" >> "$GITHUB_OUTPUT" + echo "b-release_created=$(echo ${{ steps.release.outputs['model/b--release_created'] }})" >> "$GITHUB_OUTPUT" + echo "b-tag_name=$(echo ${{ steps.release.outputs['model/b--tag_name'] }})" >> "$GITHUB_OUTPUT" + build_publish_a_image: + name: Build Publish a Image + uses: ./.github/workflows/docker.yml + needs: release_job + if: needs.release_job.outputs.a-release_created == 'true' + with: + image_tag: ${{ needs.release_job.outputs.a-tag_name }} + build_context: "a" + build_publish_b_image: + name: Build Publish b Image + uses: ./.github/workflows/docker.yml + needs: release_job + if: needs.release_job.outputs.b-release_created == 'true' + with: + image_tag: ${{ needs.release_job.outputs.b-tag_name }} + build_context: "b" diff --git a/.github/workflows/style.yml b/.github/workflows/style.yml new file mode 100644 index 0000000..bd52791 --- /dev/null +++ b/.github/workflows/style.yml @@ -0,0 +1,46 @@ +name: CheckStyle + +on: + pull_request: + branches: + - main + workflow_call: + +permissions: + contents: read + +jobs: + CheckCommitStyle: + runs-on: ubuntu-latest + if: ${{ github.event_name == 'pull_request' }} + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + - name: Install commitlint dependencies + run: | + npm i --global "@commitlint/config-conventional@17" "@commitlint/cli@17" + shell: bash + - name: Conventional Commit Linting + run: | + # Linting commits from source branch tip to target branch tip + commitlint --from ${{ github.event.pull_request.base.sha }} --to ${{ github.event.pull_request.head.sha }} --verbose --config ./.github/config/commitlint.config.js + shell: bash + CheckYamlMarkdownStyle: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + - name: Install tools + run: | + ./.github/scripts/install-agent-tools.sh + shell: bash + - name: Lint Markdown + run: | + markdownlint . -c ./.github/config/markdown-lint.config + shell: bash + - name: Lint YAML + run: | + yamllint -c ./.github/config/yaml-lint-config.yml --strict . + shell: bash diff --git a/.github/workflows/tests.yml b/.github/workflows/tests.yml new file mode 100644 index 0000000..c53f519 --- /dev/null +++ b/.github/workflows/tests.yml @@ -0,0 +1,45 @@ +name: UnitTests + +on: + workflow_call: + inputs: + src_path: + description: 'src_path' + required: false + type: string + +permissions: + id-token: write + contents: read + +jobs: + UnitTests: + runs-on: ubuntu-latest + strategy: + fail-fast: false + matrix: + version: ["3.9", "3.10"] + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + + - name: Install Poetry + uses: snok/install-poetry@v1 + + - name: Set up Python + uses: actions/setup-python@v5 + with: + python-version: ${{matrix.version}} + cache: 'poetry' + - name: Install dependencies + run: | + cd ${{ inputs.src_path }} + poetry install + shell: bash + + - name: Run tests + run: | + cd ${{ inputs.src_path }} + poetry run pytest tests + shell: bash diff --git a/.release-please-manifest.json b/.release-please-manifest.json new file mode 100644 index 0000000..9e26dfe --- /dev/null +++ b/.release-please-manifest.json @@ -0,0 +1 @@ +{} \ No newline at end of file diff --git a/README.md b/README.md index be41fe3..cbbde0c 100644 --- a/README.md +++ b/README.md @@ -1 +1,11 @@ -# monorepo_independent_releases \ No newline at end of file +# Monorepo with independent release cycle + +This repository is a sample repository for monorepo with independent release cycle using release-please action. + +## Model a + +This folder contains the source code for model a. + +## Model b + +This folder contains the source code for model b. diff --git a/model/a/Dockerfile b/model/a/Dockerfile new file mode 100644 index 0000000..da39d74 --- /dev/null +++ b/model/a/Dockerfile @@ -0,0 +1,31 @@ +FROM python:3.9.18-slim AS base + +RUN apt-get update \ + apt-get clean && apt-get autoclean && apt-get autoremove + +ENV PYTHONUNBUFFERED=1 +ENV PYTHONPATH=/code + +RUN pip install --upgrade pip && \ + pip install poetry && \ + poetry config virtualenvs.create false + +WORKDIR /code + +COPY pyproject.toml pyproject.toml +COPY poetry.lock poetry.lock +WORKDIR /code + +RUN poetry config installer.max-workers 10 +RUN poetry install --without dev + +COPY src src +WORKDIR /code/src +RUN poetry install --only-root + +RUN chown -R 1001 /code +RUN chmod 755 /code/src + +USER 1001 + +CMD ["a"] diff --git a/model/a/README.md b/model/a/README.md new file mode 100644 index 0000000..a801c73 --- /dev/null +++ b/model/a/README.md @@ -0,0 +1,21 @@ +# Model + +This python project will run model a. + +## Build + +```bash +poetry install +``` + +## Test + +```bash +poetry run pytest . +``` + +## Run + +```bash +a +``` diff --git a/model/a/pyproject.toml b/model/a/pyproject.toml new file mode 100644 index 0000000..c80c14d --- /dev/null +++ b/model/a/pyproject.toml @@ -0,0 +1,30 @@ +[tool.poetry] +name = 'a' +version = "0.0.0" +description = "model a" +authors = ["Mita Winata"] + +[tool.poetry.dependencies] +python = ">=3.9.10, <3.11.0" + +[tool.poetry.group.dev.dependencies] +isort = "^5.12.0" +black = "^23.3.0" +pytest = "^7.3.1" +openpyxl = "^3.1.2" +debugpy = "^1.8.0" +ruff = "^0.1.4" + +[build-system] +requires = ["poetry-core>=1.0.0"] +build-backend = "poetry.core.masonry.api" + +[[tool.poetry.source]] +name = "PyPI" +priority = "primary" + +[tool.isort] +profile = "black" + +[tool.poetry.scripts] +a = "a.main:main" diff --git a/model/a/src/a/__init__.py b/model/a/src/a/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/model/a/src/a/main.py b/model/a/src/a/main.py new file mode 100644 index 0000000..ab479da --- /dev/null +++ b/model/a/src/a/main.py @@ -0,0 +1,2 @@ +def main(): + print("Model A!") \ No newline at end of file diff --git a/model/a/tests/test_dummy.py b/model/a/tests/test_dummy.py new file mode 100644 index 0000000..f4f5361 --- /dev/null +++ b/model/a/tests/test_dummy.py @@ -0,0 +1,2 @@ +def test_dummy(): + assert True diff --git a/model/b/Dockerfile b/model/b/Dockerfile new file mode 100644 index 0000000..9160856 --- /dev/null +++ b/model/b/Dockerfile @@ -0,0 +1,31 @@ +FROM python:3.9.18-slim AS base + +RUN apt-get update \ + apt-get clean && apt-get autoclean && apt-get autoremove + +ENV PYTHONUNBUFFERED=1 +ENV PYTHONPATH=/code + +RUN pip install --upgrade pip && \ + pip install poetry && \ + poetry config virtualenvs.create false + +WORKDIR /code + +COPY pyproject.toml pyproject.toml +COPY poetry.lock poetry.lock +WORKDIR /code + +RUN poetry config installer.max-workers 10 +RUN poetry install --without dev + +COPY src src +WORKDIR /code/src +RUN poetry install --only-root + +RUN chown -R 1001 /code +RUN chmod 755 /code/src + +USER 1001 + +CMD ["b"] diff --git a/model/b/README.md b/model/b/README.md new file mode 100644 index 0000000..1c6d531 --- /dev/null +++ b/model/b/README.md @@ -0,0 +1,21 @@ +# Model + +This python project will run model a. + +## Build + +```bash +poetry install +``` + +## Test + +```bash +poetry run pytest . +``` + +## Run + +```bash +b +``` diff --git a/model/b/pyproject.toml b/model/b/pyproject.toml new file mode 100644 index 0000000..a90c477 --- /dev/null +++ b/model/b/pyproject.toml @@ -0,0 +1,29 @@ +[tool.poetry] +name = 'b' +version = "0.1.0" +description = "model b" +authors = ["Mita Winata"] + +[tool.poetry.dependencies] +python = ">=3.9.10, <3.11.0" + +[tool.poetry.group.dev.dependencies] +isort = "^5.12.0" +black = "^23.3.0" +pytest = "^7.3.1" +debugpy = "^1.8.0" +ruff = "^0.1.4" + +[build-system] +requires = ["poetry-core>=1.0.0"] +build-backend = "poetry.core.masonry.api" + +[[tool.poetry.source]] +name = "PyPI" +priority = "primary" + +[tool.isort] +profile = "black" + +[tool.poetry.scripts] +b = "b.main:main" diff --git a/model/b/src/b/__init__.py b/model/b/src/b/__init__.py new file mode 100644 index 0000000..e69de29 diff --git a/model/b/src/b/main.py b/model/b/src/b/main.py new file mode 100644 index 0000000..3ab4a64 --- /dev/null +++ b/model/b/src/b/main.py @@ -0,0 +1,2 @@ +def main(): + print("Model B!") diff --git a/model/b/tests/test_dummy.py b/model/b/tests/test_dummy.py new file mode 100644 index 0000000..f4f5361 --- /dev/null +++ b/model/b/tests/test_dummy.py @@ -0,0 +1,2 @@ +def test_dummy(): + assert True diff --git a/release-please-config.json b/release-please-config.json new file mode 100644 index 0000000..b422278 --- /dev/null +++ b/release-please-config.json @@ -0,0 +1,14 @@ +{ + "packages": { + "model/a": { + "changelog-path": "CHANGELOG.md", + "release-type": "python", + "component": "a" + }, + "model/b": { + "changelog-path": "CHANGELOG.md", + "release-type": "python", + "component": "b" + } + } +} \ No newline at end of file