diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 5947ea68e..c3bd31b9e 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -85,16 +85,13 @@ jobs: - name: Check the code is good run: task check - - name: Run unit tests - run: task test-unit - - name: Build the Agent for linux - run: task build + run: task go:build if: matrix.os == 'ubuntu-18.04' # build the agent without GUI support (no tray icon) - name: Build the Agent-cli - run: task build-cli + run: task go:build-cli if: matrix.os == 'ubuntu-18.04' # the manifest is required by windows GUI apps, otherwise the binary will crash with: "Unable to create main window: TTM_ADDTOOL failed" (for reference https://github.com/lxn/walk/issues/28) @@ -108,11 +105,11 @@ jobs: env: GOARCH: 386 # 32bit architecture (for support) GO386: 387 # support old instruction sets without MMX (used in the Pentium 4) (will be deprecated in GO > 1.15 https://golang.org/doc/go1.15) - run: task build-win + run: task go:build-win if: matrix.os == 'windows-2019' && matrix.arch == '-386' - name: Build the Agent for win64 - run: task build-win # GOARCH=amd64 by default on the runners + run: task go:build-win # GOARCH=amd64 by default on the runners if: matrix.os == 'windows-2019' && matrix.arch == '-amd64' - name: Build the Agent for macos @@ -120,20 +117,7 @@ jobs: MACOSX_DEPLOYMENT_TARGET: 10.11 # minimum supported version for mac CGO_CFLAGS: -mmacosx-version-min=10.11 CGO_LDFLAGS: -mmacosx-version-min=10.11 - run: task build - if: matrix.os == 'macos-10.15' - - - name: Install Python - uses: actions/setup-python@v2 - with: - python-version: '3.9' - architecture: 'x64' - if: matrix.os == 'macos-10.15' - - - name: Run e2e tests - run: | - pip install poetry - task test-e2e + run: task go:build if: matrix.os == 'macos-10.15' # this will create `public/` dir with compressed full bin (/-.gz) and a json file diff --git a/.github/workflows/test-go-integration-task.yml b/.github/workflows/test-go-integration-task.yml new file mode 100644 index 000000000..9502a756b --- /dev/null +++ b/.github/workflows/test-go-integration-task.yml @@ -0,0 +1,106 @@ +# Source: https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/test-go-integration-task.md +name: Test Integration + +env: + # See: https://github.com/actions/setup-go/tree/v2#readme + GO_VERSION: "1.14" + # See: https://github.com/actions/setup-python/tree/v2#available-versions-of-python + PYTHON_VERSION: "3.9" + +# See: https://docs.github.com/en/free-pro-team@latest/actions/reference/events-that-trigger-workflows +on: + create: + push: + paths: + - ".github/workflows/test-go-integration-task.ya?ml" + - "Taskfile.ya?ml" + - "**.go" + - "go.mod" + - "go.sum" + - "poetry.lock" + - "pyproject.toml" + - "tests/**" + pull_request: + paths: + - ".github/workflows/test-go-integration-task.ya?ml" + - "Taskfile.ya?ml" + - "**.go" + - "go.mod" + - "go.sum" + - "poetry.lock" + - "pyproject.toml" + - "tests/**" + workflow_dispatch: + repository_dispatch: + +jobs: + run-determination: + runs-on: ubuntu-latest + outputs: + result: ${{ steps.determination.outputs.result }} + steps: + - name: Determine if the rest of the workflow should run + id: determination + run: | + RELEASE_BRANCH_REGEX="refs/heads/[0-9]+.[0-9]+.x" + # The `create` event trigger doesn't support `branches` filters, so it's necessary to use Bash instead. + if [[ \ + "${{ github.event_name }}" != "create" || \ + "${{ github.ref }}" =~ $RELEASE_BRANCH_REGEX \ + ]]; then + # Run the other jobs. + RESULT="true" + else + # There is no need to run the other jobs. + RESULT="false" + fi + + echo "::set-output name=result::$RESULT" + + test: + needs: run-determination + if: needs.run-determination.outputs.result == 'true' + + strategy: + matrix: + operating-system: + - ubuntu-latest + - windows-latest + - macos-latest + + runs-on: ${{ matrix.operating-system }} + + steps: + - name: Checkout repository + uses: actions/checkout@v2 + + - name: Install Go + uses: actions/setup-go@v2 + with: + go-version: ${{ env.GO_VERSION }} + + - name: Install Python + uses: actions/setup-python@v2 + with: + python-version: ${{ env.PYTHON_VERSION }} + + - name: Install Poetry + run: pip install poetry + + - name: Install Task + uses: arduino/setup-task@v1 + with: + repo-token: ${{ secrets.GITHUB_TOKEN }} + version: 3.x + + # build the agent without GUI support (no tray icon) for integration testing + - name: Build the Agent-cli + run: task go:build-cli + if: matrix.operating-system != 'windows-latest' + + - name: Build the Agent-cli for win + run: task go:build-win-cli + if: matrix.operating-system == 'windows-latest' + + - name: Run integration tests + run: task go:test-integration diff --git a/.github/workflows/test-go-task.yml b/.github/workflows/test-go-task.yml new file mode 100644 index 000000000..c88772d36 --- /dev/null +++ b/.github/workflows/test-go-task.yml @@ -0,0 +1,110 @@ +# Source: https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/test-go-task.md +name: Test Go + +env: + # See: https://github.com/actions/setup-go/tree/v2#readme + GO_VERSION: "1.14" + +# See: https://docs.github.com/en/free-pro-team@latest/actions/reference/events-that-trigger-workflows +on: + create: + push: + paths: + - ".github/workflows/test-go-task.ya?ml" + - "codecov.ya?ml" + - "**/go.mod" + - "**/go.sum" + - "Taskfile.ya?ml" + - "**.go" + - "**/testdata/**" + pull_request: + paths: + - ".github/workflows/test-go-task.ya?ml" + - "codecov.ya?ml" + - "**/go.mod" + - "**/go.sum" + - "Taskfile.ya?ml" + - "**.go" + - "**/testdata/**" + workflow_dispatch: + repository_dispatch: + +jobs: + run-determination: + runs-on: ubuntu-latest + outputs: + result: ${{ steps.determination.outputs.result }} + steps: + - name: Determine if the rest of the workflow should run + id: determination + run: | + RELEASE_BRANCH_REGEX="refs/heads/[0-9]+.[0-9]+.x" + # The `create` event trigger doesn't support `branches` filters, so it's necessary to use Bash instead. + if [[ \ + "${{ github.event_name }}" != "create" || \ + "${{ github.ref }}" =~ $RELEASE_BRANCH_REGEX \ + ]]; then + # Run the other jobs. + RESULT="true" + else + # There is no need to run the other jobs. + RESULT="false" + fi + + echo "::set-output name=result::$RESULT" + + test: + name: test (${{ matrix.module.path }} - ${{ matrix.operating-system }}) + needs: run-determination + if: needs.run-determination.outputs.result == 'true' + + strategy: + fail-fast: false + + matrix: + operating-system: + - ubuntu-latest + - windows-latest + - macos-latest + module: + - path: ./ + codecov-flags: unit + + runs-on: ${{ matrix.operating-system }} + + steps: + # By default, actions/checkout converts the repo's LF line endings to CRLF on the Windows runner. + - name: Disable EOL conversions + run: git config --global core.autocrlf false + + - name: Checkout repository + uses: actions/checkout@v2 + + - name: Install Go + uses: actions/setup-go@v2 + with: + go-version: ${{ env.GO_VERSION }} + + - name: Install Task + uses: arduino/setup-task@v1 + with: + repo-token: ${{ secrets.GITHUB_TOKEN }} + version: 3.x + + # https://github.com/getlantern/systray#linux + - name: Install Dependencies (Linux) + run: sudo apt update && sudo apt install -y --no-install-recommends build-essential libgtk-3-dev libwebkit2gtk-4.0-dev libappindicator3-dev + if: matrix.operating-system == 'ubuntu-latest' + + - name: Run tests + env: + GO_MODULE_PATH: ${{ matrix.module.path }} + run: task go:test + + - name: Send unit tests coverage to Codecov + if: runner.os == 'Linux' + uses: codecov/codecov-action@v2 + with: + file: ${{ matrix.module.path }}coverage_unit.txt + flags: ${{ matrix.module.codecov-flags }} + fail_ci_if_error: ${{ github.repository == 'arduino/arduino-create-agent' }} diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml deleted file mode 100644 index 3c29107fb..000000000 --- a/.github/workflows/test.yml +++ /dev/null @@ -1,115 +0,0 @@ -name: test - -on: - pull_request: - -jobs: - test-matrix: - strategy: - matrix: - os: [ubuntu-18.04, windows-2019, macos-10.15] - arch: [-amd64] - include: - - os: windows-2019 - arch: -386 - - defaults: - run: - shell: bash - - runs-on: ${{ matrix.os }} - - steps: - - name: Disable EOL conversions - run: git config --global core.autocrlf false - - - name: Checkout - uses: actions/checkout@v2 - - - name: Install Go - uses: actions/setup-go@v2 - with: - go-version: "1.14" - - # dependencies used for compiling the GUI - - name: Install Dependencies (Linux) - run: sudo apt update && sudo apt install -y --no-install-recommends build-essential libgtk-3-dev libwebkit2gtk-4.0-dev libappindicator3-dev - if: matrix.os == 'ubuntu-18.04' - - - name: Install Go deps - # Since 10/23/2019 pwsh is the default shell - # on Windows, but pwsh fails to install protoc-gen-go so - # we force bash as default shell for all OSes in this task - run: | - go get github.com/golangci/govet - go get golang.org/x/lint/golint - - - name: Install Taskfile - uses: arduino/setup-task@v1 - with: - version: '3.x' - repo-token: ${{ secrets.GITHUB_TOKEN }} - - - name: Check the code is good - run: task check - - - name: Run unit tests - run: task test-unit - - - name: Build the Agent for linux - run: task build - if: matrix.os == 'ubuntu-18.04' - - # build the agent without GUI support (no tray icon) - - name: Build the Agent-cli - run: task build-cli - if: matrix.os == 'ubuntu-18.04' - - # the manifest is required by windows GUI apps, otherwise the binary will crash with: "Unable to create main window: TTM_ADDTOOL failed" (for reference https://github.com/lxn/walk/issues/28) - # rsrc will produce a *.syso file that should get automatically recognized by go build command and linked into an executable. - - name: Download tool to embed manifest in win binary - run: go get github.com/akavel/rsrc - if: matrix.os == 'windows-2019' - - # building the agent for win requires a different task because of an extra flag - - name: Build the Agent for win32 - env: - GOARCH: 386 # 32bit architecture (for support) - GO386: 387 # support old instruction sets without MMX (used in the Pentium 4) (will be deprecated in GO > 1.15 https://golang.org/doc/go1.15) - run: task build-win - if: matrix.os == 'windows-2019' && matrix.arch == '-386' - - - name: Build the Agent for win64 - run: task build-win # GOARCH=amd64 by default on the runners - if: matrix.os == 'windows-2019' && matrix.arch == '-amd64' - - - name: Build the Agent for macos - env: - MACOSX_DEPLOYMENT_TARGET: 10.11 # minimum supported version for mac - CGO_CFLAGS: -mmacosx-version-min=10.11 - CGO_LDFLAGS: -mmacosx-version-min=10.11 - run: task build - if: matrix.os == 'macos-10.15' - - - name: Install Python - uses: actions/setup-python@v2 - with: - python-version: '3.9' - architecture: 'x64' - if: matrix.os == 'macos-10.15' - - - name: Run e2e tests - run: | - pip install poetry - task test-e2e - if: matrix.os == 'macos-10.15' - - # config.ini is required by the executable when it's run - - name: Upload artifacts - uses: actions/upload-artifact@v2 - with: - name: arduino-create-agent-${{ matrix.os }}${{ matrix.arch }} - path: | - arduino-create-agent* - config.ini - if-no-files-found: error diff --git a/README.md b/README.md index e6b456c22..3fa8dd07d 100644 --- a/README.md +++ b/README.md @@ -1,4 +1,7 @@ [![License: GPL v2](https://img.shields.io/badge/License-GPL%20v2-blue.svg)](https://www.gnu.org/licenses/old-licenses/gpl-2.0.en.html) +[![Test Go status](https://github.com/arduino/arduino-create-agent/actions/workflows/test-go-task.yml/badge.svg)](https://github.com/arduino/arduino-create-agent/actions/workflows/test-go-task.yml) +[![Codecov](https://codecov.io/gh/arduino/arduino-create-agent/branch/main/graph/badge.svg)](https://codecov.io/gh/arduino/arduino-create-agent) +[![Test Integration status](https://github.com/arduino/arduino-create-agent/actions/workflows/test-go-integration-task.yml/badge.svg)](https://github.com/arduino/arduino-create-agent/actions/workflows/test-go-integration-task.yml) arduino-create-agent ==================== diff --git a/Taskfile.yml b/Taskfile.yml index 48c6fb534..c1f70e5ec 100644 --- a/Taskfile.yml +++ b/Taskfile.yml @@ -1,43 +1,76 @@ version: '3' tasks: - - build: + # Source: https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/assets/go-task/Taskfile.yml + go:build: desc: Build the project, to use a specific version use `task build TAG_VERSION=x.x.x` + dir: "{{.DEFAULT_GO_MODULE_PATH}}" cmds: - go build -v -i {{default "" .ADDITIONAL_FLAGS}} -o {{default "arduino-create-agent" .APP_NAME}} -ldflags '-X main.version={{default .TAG_TEST .TAG_VERSION}} -X main.git_revision={{.COMMIT}} {{default "" .WIN_FLAGS}}' vars: COMMIT: sh: git log -n 1 --format=%h - build-cli: - desc: Build the project without tray support + go:build-cli: + desc: Build the project without tray icon support cmds: - - task: build + - task: go:build vars: APP_NAME: arduino-create-agent_cli ADDITIONAL_FLAGS: -tags cli - build-win: + go:build-win: desc: Build the project for win, to build 32bit `export GOARCH=386` and for 64 bit `export GOARCH=amd64` before `task build-win` cmds: - rsrc -arch {{.GOARCH}} -manifest manifest.xml # GOARCH shoud be either amd64 or 386 - - task: build + - task: go:build vars: APP_NAME: arduino-create-agent.exe WIN_FLAGS: -H=windowsgui - rm *.syso # rm file to avoid compilation problems on other platforms - test-unit: - desc: Run unit tests only + go:build-win-cli: + desc: Build the project fow win without tray icon support + cmds: + - task: go:build + vars: + APP_NAME: arduino-create-agent_cli.exe + ADDITIONAL_FLAGS: -tags cli + + # Source: https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/assets/test-go-task/Taskfile.yml + go:test: + desc: Run unit tests + dir: "{{default .DEFAULT_GO_MODULE_PATH .GO_MODULE_PATH}}" cmds: - - go test -short -run '{{ default ".*" .TEST_REGEX }}' {{ default "-v" .GOFLAGS }} -coverprofile=coverage_unit.txt {{ default .DEFAULT_TARGETS .TARGETS }} {{.TEST_LDFLAGS}} + - | + go test \ + -v \ + -short \ + -run '{{default ".*" .GO_TEST_REGEX}}' \ + {{default "-timeout 10m -coverpkg=./... -covermode=atomic" .GO_TEST_FLAGS}} \ + -coverprofile=coverage_unit.txt \ + {{default .DEFAULT_GO_PACKAGES .GO_PACKAGES}} - test-e2e: - desc: Run end 2 end tests + # Source: https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/assets/test-go-integration-task/Taskfile.yml + go:test-integration: + desc: Run integration tests + deps: + # - task: go:build # we build it in the CI and not in the task because _cli version is required and build procedure is different on win + - task: poetry:install-deps + cmds: + - poetry run pytest tests + + # Source: https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/assets/poetry-task/Taskfile.yml + poetry:install-deps: + desc: Install dependencies managed by Poetry cmds: - poetry install --no-root - - poetry run pytest test + + # Source: https://github.com/arduino/tooling-project-assets/blob/main/workflow-templates/assets/poetry-task/Taskfile.yml + poetry:update-deps: + desc: Update all dependencies managed by Poetry to their newest versions + cmds: + - poetry update check: desc: Check fmt and lint @@ -63,7 +96,10 @@ vars: # all modules of this project except for "gen/..." module DEFAULT_TARGETS: sh: echo `go list ./... | grep -v 'arduino-create-agent/gen/' | tr '\n' ' '` - GOFLAGS: "-timeout 10m -v -coverpkg=./... -covermode=atomic" + DEFAULT_GO_MODULE_PATH: ./ + DEFAULT_GO_PACKAGES: + sh: | + echo $(cd {{default .DEFAULT_GO_MODULE_PATH .GO_MODULE_PATH}} && go list ./... | tr '\n' ' ' || echo '"ERROR: Unable to discover Go packages"') # check-lint vars GOLINTBIN: sh: go list -f {{"{{"}}".Target{{"}}"}}" golang.org/x/lint/golint diff --git a/main_test.go b/main_test.go index 2bd292562..46ba1bcf1 100644 --- a/main_test.go +++ b/main_test.go @@ -10,7 +10,7 @@ import ( ) func TestValidSignatureKey(t *testing.T) { - testfile := filepath.Join("test", "testdata", "test.ini") + testfile := filepath.Join("tests", "testdata", "test.ini") args, err := parseIni(testfile) require.NoError(t, err) require.NotNil(t, args) diff --git a/test/common.py b/tests/common.py similarity index 100% rename from test/common.py rename to tests/common.py diff --git a/test/conftest.py b/tests/conftest.py similarity index 99% rename from test/conftest.py rename to tests/conftest.py index 3f1b185f2..a5d7f1018 100644 --- a/test/conftest.py +++ b/tests/conftest.py @@ -12,7 +12,7 @@ @pytest.fixture(scope="function") def agent(pytestconfig): - agent_cli = str(Path(pytestconfig.rootdir) / "arduino-create-agent") + agent_cli = str(Path(pytestconfig.rootdir) / "arduino-create-agent_cli") env = { # "ARDUINO_DATA_DIR": data_dir, # "ARDUINO_DOWNLOADS_DIR": downloads_dir, diff --git a/test/test_certs.py b/tests/test_certs.py similarity index 100% rename from test/test_certs.py rename to tests/test_certs.py diff --git a/test/test_info.py b/tests/test_info.py similarity index 100% rename from test/test_info.py rename to tests/test_info.py diff --git a/test/test_update.py b/tests/test_update.py similarity index 100% rename from test/test_update.py rename to tests/test_update.py diff --git a/test/test_v2.py b/tests/test_v2.py similarity index 100% rename from test/test_v2.py rename to tests/test_v2.py diff --git a/test/test_ws.py b/tests/test_ws.py similarity index 98% rename from test/test_ws.py rename to tests/test_ws.py index 8a7143e74..52c83867d 100644 --- a/test/test_ws.py +++ b/tests/test_ws.py @@ -46,7 +46,7 @@ def test_open_serial_timedraw(socketio, serial_port, baudrate, message): general_open_serial(socketio, serial_port, baudrate, message, "timedraw") -# NOTE run the following tests with a board connected to the PC and with the sketch found in test/testdata/SerialEcho.ino on it be sure to change serial_address in conftest.py +# NOTE run the following tests with a board connected to the PC and with the sketch found in tests/testdata/SerialEcho.ino on it be sure to change serial_address in conftest.py @pytest.mark.skipif( running_on_ci(), reason="VMs have no serial ports", diff --git a/test/testdata/SerialEcho/SerialEcho.ino b/tests/testdata/SerialEcho/SerialEcho.ino similarity index 100% rename from test/testdata/SerialEcho/SerialEcho.ino rename to tests/testdata/SerialEcho/SerialEcho.ino diff --git a/test/testdata/test.ini b/tests/testdata/test.ini similarity index 100% rename from test/testdata/test.ini rename to tests/testdata/test.ini