diff --git a/.github/FUNDING.yml b/.github/FUNDING.yml new file mode 100644 index 0000000..33390a1 --- /dev/null +++ b/.github/FUNDING.yml @@ -0,0 +1,3 @@ +# These are supported funding model platforms + +github: openfoodfacts diff --git a/.github/ISSUE_TEMPLATE/bug_report.md b/.github/ISSUE_TEMPLATE/bug_report.md new file mode 100644 index 0000000..83b070c --- /dev/null +++ b/.github/ISSUE_TEMPLATE/bug_report.md @@ -0,0 +1,37 @@ +--- +name: Bug report +about: Create a report to help us improve +title: '' +labels: '' +assignees: '' + +--- + +**Describe the bug** +A clear and concise description of what the bug is. + +**To Reproduce** +Steps to reproduce the behavior: +1. Go to '...' +2. Click on '....' +3. See error + +**Expected behavior** +A clear and concise description of what you expected to happen. + +**Screenshots** +If applicable, add screenshots to help explain your problem. + +**Desktop (please complete the following information):** + - OS: [e.g. iOS] + - Browser [e.g. chrome, safari] + - Version [e.g. 22] + +**Smartphone (please complete the following information):** + - Device: [e.g. iPhone6] + - OS: [e.g. iOS8.1] + - Browser [e.g. stock browser, safari] + - Version [e.g. 22] + +**Additional context** +Add any other context about the problem here. diff --git a/.github/ISSUE_TEMPLATE/epic.md b/.github/ISSUE_TEMPLATE/epic.md new file mode 100644 index 0000000..798958d --- /dev/null +++ b/.github/ISSUE_TEMPLATE/epic.md @@ -0,0 +1,17 @@ +--- +name: Epic +about: Template for epics. Epics group several user stories together into a main piece + of added value. +title: '' +labels: "♞ epic" +assignees: '' + +--- + +### Who for + +### What + +### Why + +### Part of diff --git a/.github/ISSUE_TEMPLATE/feature_request.md b/.github/ISSUE_TEMPLATE/feature_request.md new file mode 100644 index 0000000..bbcbbe7 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/feature_request.md @@ -0,0 +1,20 @@ +--- +name: Feature request +about: Suggest an idea for this project +title: '' +labels: '' +assignees: '' + +--- + +**Is your feature request related to a problem? Please describe.** +A clear and concise description of what the problem is. Ex. I'm always frustrated when [...] + +**Describe the solution you'd like** +A clear and concise description of what you want to happen. + +**Describe alternatives you've considered** +A clear and concise description of any alternative solutions or features you've considered. + +**Additional context** +Add any other context or screenshots about the feature request here. diff --git a/.github/dependabot.yml b/.github/dependabot.yml new file mode 100644 index 0000000..d04a624 --- /dev/null +++ b/.github/dependabot.yml @@ -0,0 +1,10 @@ +version: 2 +updates: +- package-ecosystem: github-actions + directory: "/" + schedule: + interval: daily +- package-ecosystem: pip + directory: "/" + schedule: + interval: daily diff --git a/.github/workflows/autoblack.yml b/.github/workflows/autoblack.yml new file mode 100644 index 0000000..fd6e60f --- /dev/null +++ b/.github/workflows/autoblack.yml @@ -0,0 +1,30 @@ +# GitHub Action that uses Black to reformat the Python code in an incoming pull request. +# If all Python code in the pull request is compliant with Black then this Action does nothing. +# Otherwise, Black is run and its changes are committed back to the incoming pull request. +# https://github.com/cclauss/autoblack + +name: autoblack +on: [pull_request] +jobs: + black: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v1 + - name: Set up Python 3.7 + uses: actions/setup-python@v1 + with: + python-version: 3.7 + - name: Install Black + run: pip install black + - name: Run black --check . + run: black --check . + - name: If needed, commit black changes to the pull request + if: failure() + run: | + black . + git config --global user.name 'autoblack' + git config --global user.email 'actions@github.com' + git remote set-url origin https://x-access-token:${{ secrets.GITHUB_TOKEN }}@github.com/$GITHUB_REPOSITORY + git checkout $GITHUB_HEAD_REF + git commit -am "fixup: Format Python code with Black" + git push diff --git a/.github/workflows/codeql-analysis.yml b/.github/workflows/codeql-analysis.yml new file mode 100644 index 0000000..9a5954f --- /dev/null +++ b/.github/workflows/codeql-analysis.yml @@ -0,0 +1,51 @@ +name: "Code scanning - action" + +on: + push: + pull_request: + schedule: + - cron: '0 9 * * 1' + +jobs: + CodeQL-Build: + + runs-on: ubuntu-latest + + steps: + - name: Checkout repository + uses: actions/checkout@v2 + with: + # We must fetch at least the immediate parents so that if this is + # a pull request then we can checkout the head. + fetch-depth: 2 + + # If this run was triggered by a pull request event, then checkout + # the head of the pull request instead of the merge commit. + - run: git checkout HEAD^2 + if: ${{ github.event_name == 'pull_request' }} + + # Initializes the CodeQL tools for scanning. + - name: Initialize CodeQL + uses: github/codeql-action/init@v1 + # Override language selection by uncommenting this and choosing your languages + # with: + # languages: go, javascript, csharp, python, cpp, java + + # Autobuild attempts to build any compiled languages (C/C++, C#, or Java). + # If this step fails, then you should remove it and run the build manually (see below) + - name: Autobuild + uses: github/codeql-action/autobuild@v1 + + # ℹī¸ Command-line programs to run using the OS shell. + # 📚 https://git.io/JvXDl + + # ✏ī¸ If the Autobuild fails above, remove it and uncomment the following three lines + # and modify them (or add more) to build your code if your project + # uses a compiled language + + #- run: | + # make bootstrap + # make release + + - name: Perform CodeQL Analysis + uses: github/codeql-action/analyze@v1 diff --git a/.github/workflows/container-build.yml b/.github/workflows/container-build.yml new file mode 100644 index 0000000..6ea69f1 --- /dev/null +++ b/.github/workflows/container-build.yml @@ -0,0 +1,53 @@ +name: Container Image Build CI + +on: + push: + branches: + - main + - deploy-* + - release-v*.*.* + tags: + - v*.*.* + +jobs: + build: + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v2 + with: + fetch-depth: 1 + + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v1 + with: + version: v0.6.0 + buildkitd-flags: --debug + + - name: Login to DockerHub + uses: docker/login-action@v1 + with: + registry: ghcr.io + username: ${{ github.actor }} + password: ${{ secrets.GITHUB_TOKEN }} + + - name: Docker meta + id: meta + uses: docker/metadata-action@v3 + with: + images: | + ghcr.io/${{ github.repository }} + tags: | + type=semver,pattern={{version}} + type=ref,event=pr + type=ref,event=branch + type=sha,format=long + + - name: Build and push + uses: docker/build-push-action@v2 + with: + context: . + push: true + cache-from: type=registry,ref=ghcr.io/${{ github.repository }}:buildcache + cache-to: type=registry,ref=ghcr.io/${{ github.repository }}:buildcache,mode=max + tags: ${{ steps.meta.outputs.tags }} + labels: ${{ steps.meta.outputs.labels }} diff --git a/.github/workflows/container-deploy.yml b/.github/workflows/container-deploy.yml new file mode 100644 index 0000000..39c7aab --- /dev/null +++ b/.github/workflows/container-deploy.yml @@ -0,0 +1,133 @@ +name: Container Image Deployment CI + +on: + push: + branches: + - main + - deploy-* + - release-v*.*.* + tags: + - v*.*.* + +jobs: + deploy: + runs-on: ubuntu-latest + environment: ${{ startsWith(github.ref, 'refs/tags/v') && 'robotoff-ann-org' || 'robotoff-ann-net' }} + steps: + - name: Wait for container build workflow + uses: tomchv/wait-my-workflow@v1.1.0 + id: wait-build + with: + token: ${{ secrets.GITHUB_TOKEN }} + checkName: build + ref: ${{ github.event.pull_request.head.sha || github.sha }} + intervalSeconds: 10 + timeoutSeconds: 600 # 10m + + - name: Do something if build fail + if: steps.wait-build.outputs.conclusion == 'failure' + run: echo fail && false # fail if build fail + + - name: Do something if build timeout + if: steps.wait-build.outputs.conclusion == 'timed_out' + run: echo Timeout && false # fail if build time out + + - name: Checkout git repository + uses: appleboy/ssh-action@master + with: + host: ${{ secrets.HOST }} + username: ${{ secrets.USERNAME }} + key: ${{ secrets.SSH_PRIVATE_KEY }} + proxy_host: ${{ secrets.PROXY_HOST }} + proxy_username: ${{ secrets.USERNAME }} + proxy_key: ${{ secrets.SSH_PRIVATE_KEY }} + script_stop: false + script: | + # Clone Git repository if not already there + [ ! -d 'robotoff-ann' ] && git clone --depth 1 https://github.com/openfoodfacts/robotoff-ann/ --no-single-branch 2>&1 + + # Go to repository directory + cd robotoff-ann/ + + # Fetch newest commits (in case it wasn't freshly cloned) + git fetch --depth 1 + + # Checkout current commit SHA + git checkout -qf ${{ github.sha }} + + - name: Set environment variables + uses: appleboy/ssh-action@master + with: + host: ${{ secrets.HOST }} + username: ${{ secrets.USERNAME }} + key: ${{ secrets.SSH_PRIVATE_KEY }} + proxy_host: ${{ secrets.PROXY_HOST }} + proxy_username: ${{ secrets.USERNAME }} + proxy_key: ${{ secrets.SSH_PRIVATE_KEY }} + script_stop: false + script: | + # Go to repository directory + cd robotoff-ann/ + + # Set Docker Compose variables + echo "DOCKER_CLIENT_TIMEOUT=120" > .env + echo "COMPOSE_HTTP_TIMEOUT=120" >> .env + echo "COMPOSE_PATH_SEPARATOR=;" >> .env + echo "COMPOSE_FILE=docker-compose.yml" >> .env + echo "TAG=${{ github.sha }}" >> .env + + - name: Start services + uses: appleboy/ssh-action@master + env: + DOCKER_CLIENT_TIMEOUT: 120 + COMPOSE_HTTP_TIMEOUT: 120 + with: + host: ${{ secrets.HOST }} + username: ${{ secrets.USERNAME }} + key: ${{ secrets.SSH_PRIVATE_KEY }} + proxy_host: ${{ secrets.PROXY_HOST }} + proxy_username: ${{ secrets.USERNAME }} + proxy_key: ${{ secrets.SSH_PRIVATE_KEY }} + envs: DOCKER_CLIENT_TIMEOUT,COMPOSE_HTTP_TIMEOUT + script_stop: false + script: | + cd robotoff-ann/ + docker-compose up -d --remove-orphans 2>&1 + + - name: Check services are up + uses: appleboy/ssh-action@master + if: ${{ always() }} + with: + host: ${{ secrets.HOST }} + username: ${{ secrets.USERNAME }} + key: ${{ secrets.SSH_PRIVATE_KEY }} + proxy_host: ${{ secrets.PROXY_HOST }} + proxy_username: ${{ secrets.USERNAME }} + proxy_key: ${{ secrets.SSH_PRIVATE_KEY }} + script_stop: false + script: | + cd robotoff-ann/ + exit_code=0 + for service in robotoff; do + if [ -z `docker-compose ps -q $service` ] || [ -z `docker ps -q --no-trunc | grep $(docker-compose ps -q $service)` ]; then + echo "$service: DOWN" + exit_code=1 + else + echo "$service: UP" + fi + done; + exit $exit_code; + + - name: Cleanup obsolete Docker objects + uses: appleboy/ssh-action@master + if: ${{ always() }} + with: + host: ${{ secrets.HOST }} + username: ${{ secrets.USERNAME }} + key: ${{ secrets.SSH_PRIVATE_KEY }} + proxy_host: ${{ secrets.PROXY_HOST }} + proxy_username: ${{ secrets.USERNAME }} + proxy_key: ${{ secrets.SSH_PRIVATE_KEY }} + script_stop: false + script: | + docker system prune -af diff --git a/docker-compose.yml b/docker-compose.yml new file mode 100644 index 0000000..77d7585 --- /dev/null +++ b/docker-compose.yml @@ -0,0 +1,10 @@ +version: "3.9" + +services: + ann: + restart: always + image: ghcr.io/openfoodfacts/robotoff-ann:${TAG} + ports: + - 5501:5501 + volumes: + - ./ann_data:/opt/ann/data