diff --git a/.dockerignore b/.dockerignore index a5d8f7237..e660fd93d 100644 --- a/.dockerignore +++ b/.dockerignore @@ -1,2 +1 @@ bin/ -dist/ diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index 4f73eaaca..e7af40b02 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -1,9 +1,15 @@ -name: Continuous integration +name: ci + +concurrency: + group: ${{ github.workflow }}-${{ github.ref }} + cancel-in-progress: true on: push: branches: - - v2 + - 'v2' + tags: + - 'v*' pull_request: workflow_dispatch: inputs: @@ -11,115 +17,201 @@ on: description: 'To run with tmate enter "debug_enabled"' required: false default: "false" + env: - GO_VERSION: 1.18.5 - DOCKER_CLI_VERSION: 20.10.17 + GO_VERSION: "1.18.5" # for non sandboxed e2e tests + DESTDIR: "./bin" + DOCKER_CLI_VERSION: "20.10.17" + jobs: - lint: - name: Lint + prepare: + runs-on: ubuntu-latest + outputs: + matrix: ${{ steps.platforms.outputs.matrix }} + steps: + - + name: Checkout + uses: actions/checkout@v3 + - + name: Create matrix + id: platforms + run: | + echo ::set-output name=matrix::$(docker buildx bake binary-cross --print | jq -cr '.target."binary-cross".platforms') + - + name: Show matrix + run: | + echo ${{ steps.platforms.outputs.matrix }} + + validate: + runs-on: ubuntu-latest + strategy: + fail-fast: false + matrix: + target: + - lint + - validate-go-mod + - validate-headers + - validate-docs + steps: + - + name: Checkout + uses: actions/checkout@v3 + - + name: Set up Docker Buildx + uses: docker/setup-buildx-action@v2 + - + name: Run + run: | + make ${{ matrix.target }} + + binary: + runs-on: ubuntu-latest + needs: + - prepare + strategy: + fail-fast: false + matrix: + platform: ${{ fromJson(needs.prepare.outputs.matrix) }} + steps: + - + name: Prepare + run: | + platform=${{ matrix.platform }} + echo "PLATFORM_PAIR=${platform//\//-}" >> $GITHUB_ENV + - + name: Checkout + uses: actions/checkout@v3 + - + name: Set up QEMU + uses: docker/setup-qemu-action@v2 + - + name: Set up Docker Buildx + uses: docker/setup-buildx-action@v2 + - + name: Build + uses: docker/bake-action@v2 + with: + targets: release + set: | + *.platform=${{ matrix.platform }} + *.cache-from=type=gha,scope=binary-${{ env.PLATFORM_PAIR }} + *.cache-to=type=gha,scope=binary-${{ env.PLATFORM_PAIR }},mode=max + - + name: Upload artifacts + uses: actions/upload-artifact@v3 + with: + name: compose + path: ${{ env.DESTDIR }}/* + if-no-files-found: error + + test: runs-on: ubuntu-latest steps: - - name: Checkout code into the Go module directory + - + name: Checkout uses: actions/checkout@v3 + - + name: Set up Docker Buildx + uses: docker/setup-buildx-action@v2 + - + name: Test + uses: docker/bake-action@v2 + with: + targets: test + set: | + *.cache-from=type=gha,scope=test + *.cache-to=type=gha,scope=test - - name: Set up Go ${{ env.GO_VERSION }} + e2e: + runs-on: ubuntu-latest + env: + DESTDIR: "./bin/build" + strategy: + fail-fast: false + matrix: + mode: + - plugin + - standalone + steps: + - + name: Checkout + uses: actions/checkout@v3 + - + name: Set up Docker Buildx + uses: docker/setup-buildx-action@v2 + - + name: Set up Go uses: actions/setup-go@v3 with: go-version: ${{ env.GO_VERSION }} cache: true - - - name: Validate go-mod, license headers and docs are up-to-date - run: make validate - - - name: Run golangci-lint - env: - BUILD_TAGS: e2e - uses: golangci/golangci-lint-action@v3 - with: - version: v1.47.3 - args: --timeout=180s - - # only on main branch, costs too much for the gain on every PR - validate-cross-build: - name: Validate cross build - runs-on: ubuntu-latest - if: github.ref == 'refs/heads/main' - steps: - - name: Checkout code into the Go module directory - uses: actions/checkout@v3 - - - name: Set up Go ${{ env.GO_VERSION }} - uses: actions/setup-go@v3 - with: - go-version: ${{ env.GO_VERSION }} - cache: true - - # Ensure we don't discover cross platform build issues at release time. - # Time used to build linux here is gained back in the build for local E2E step - - name: Build packages - run: make -f builder.Makefile cross - - build-plugin: - name: Build and tests in plugin mode - runs-on: ubuntu-latest - steps: - - name: Checkout code into the Go module directory - uses: actions/checkout@v3 - - - name: Set up Go ${{ env.GO_VERSION }} - uses: actions/setup-go@v3 - with: - go-version: ${{ env.GO_VERSION }} - cache: true - - - name: Setup docker CLI + - + name: Setup docker CLI run: | curl https://download.docker.com/linux/static/stable/x86_64/docker-${DOCKER_CLI_VERSION}.tgz | tar xz sudo cp ./docker/docker /usr/bin/ && rm -rf docker && docker version - - - name: Test - run: make -f builder.Makefile test - - - name: Build for local E2E - env: - BUILD_TAGS: e2e - run: make GIT_TAG=e2e-PR-${{ github.event.pull_request.number }}-${{ github.event.pull_request.head.sha }} -f builder.Makefile compose-plugin - - - name: E2E Test in plugin mode - run: make e2e-compose - - build-standalone: - name: Build and tests in standalone mode - runs-on: ubuntu-latest - steps: - - name: Checkout code into the Go module directory - uses: actions/checkout@v3 - - - name: Set up Go ${{ env.GO_VERSION }} - uses: actions/setup-go@v3 + - + name: Build + uses: docker/bake-action@v2 with: - go-version: ${{ env.GO_VERSION }} - cache: true - - - name: Setup docker CLI - run: | - curl https://download.docker.com/linux/static/stable/x86_64/docker-${DOCKER_CLI_VERSION}.tgz | tar xz - sudo cp ./docker/docker /usr/bin/ && rm -rf docker && docker version - - - name: Build for local E2E + targets: binary + set: | + *.cache-from=type=gha,scope=binary-linux-amd64 + *.cache-from=type=gha,scope=binary-e2e-${{ matrix.mode }} + *.cache-to=type=gha,scope=binary-e2e-${{ matrix.mode }},mode=max env: BUILD_TAGS: e2e - run: make GIT_TAG=e2e-PR-${{ github.event.pull_request.number }}-${{ github.event.pull_request.head.sha }} -f builder.Makefile compose-plugin - - - name: Setup tmate session - uses: mxschmitt/action-tmate@v3 + - + name: Setup tmate session + if: ${{ github.event_name == 'workflow_dispatch' && github.event.inputs.debug_enabled }} + uses: mxschmitt/action-tmate@8b4e4ac71822ed7e0ad5fb3d1c33483e9e8fb270 # v3.11 with: limit-access-to-actor: true github-token: ${{ secrets.GITHUB_TOKEN }} - if: ${{ github.event_name == 'workflow_dispatch' && github.event.inputs.debug_enabled }} - - - name: E2E Test in standalone mode + - + name: Test plugin mode + if: ${{ matrix.mode == 'plugin' }} + run: | + make e2e-compose + - + name: Test standalone mode + if: ${{ matrix.mode == 'standalone' }} run: | rm -f /usr/local/bin/docker-compose - cp bin/docker-compose /usr/local/bin + cp bin/build/docker-compose /usr/local/bin make e2e-compose-standalone + + release: + runs-on: ubuntu-latest + needs: + - binary + steps: + - + name: Checkout + uses: actions/checkout@v3 + - + name: Download artifacts + uses: actions/download-artifact@v3 + with: + name: compose + path: ${{ env.DESTDIR }} + - + name: License + run: cp packaging/* ${{ env.DESTDIR }}/ + - + name: List artifacts + run: | + tree -nh ${{ env.DESTDIR }} + - + name: Check artifacts + run: | + find ${{ env.DESTDIR }} -type f -exec file -e ascii -- {} + + - + name: GitHub Release + if: startsWith(github.ref, 'refs/tags/v') + uses: ncipollo/release-action@58ae73b360456532aafd58ee170c045abbeaee37 # v1.10.0 + with: + artifacts: ${{ env.DESTDIR }}/* + generateReleaseNotes: true + draft: true + token: ${{ secrets.GITHUB_TOKEN }} diff --git a/.github/workflows/release.yaml b/.github/workflows/release.yaml deleted file mode 100644 index 002c105be..000000000 --- a/.github/workflows/release.yaml +++ /dev/null @@ -1,45 +0,0 @@ -name: Releaser - -on: - workflow_dispatch: - inputs: - tag: - description: "Release Tag" - required: true -env: - GO_VERSION: 1.18.5 -jobs: - upload-release: - runs-on: ubuntu-latest - steps: - - name: Checkout code into the Go module directory - uses: actions/checkout@v3 - - - name: Set up Go ${{ env.GO_VERSION }} - uses: actions/setup-go@v3 - with: - go-version: ${{ env.GO_VERSION }} - cache: true - - - name: Setup docker CLI - run: | - curl https://download.docker.com/linux/static/stable/x86_64/docker-20.10.17.tgz | tar xz - sudo cp ./docker/docker /usr/bin/ && rm -rf docker && docker version - - - name: Build - run: make GIT_TAG=${{ github.event.inputs.tag }} -f builder.Makefile cross - - - name: Compute checksums - run: cd bin; for f in *; do shasum --binary --algorithm 256 $f | tee -a checksums.txt > $f.sha256; done - - - name: License - run: cp packaging/* bin/ - - - uses: ncipollo/release-action@v1 - with: - artifacts: "bin/*" - generateReleaseNotes: true - draft: true - commit: "v2" - token: ${{ secrets.GITHUB_TOKEN }} - tag: ${{ github.event.inputs.tag }} diff --git a/.gitignore b/.gitignore index 480478873..c04e81c4d 100644 --- a/.gitignore +++ b/.gitignore @@ -1,3 +1,2 @@ bin/ -dist/ /.vscode/ diff --git a/.golangci.yml b/.golangci.yml index 434b92875..40dda7281 100644 --- a/.golangci.yml +++ b/.golangci.yml @@ -1,5 +1,6 @@ run: concurrency: 2 + timeout: 10m linters: enable-all: false disable-all: true @@ -18,6 +19,7 @@ linters: - lll - misspell - nakedret + - nolintlint - staticcheck - structcheck - typecheck diff --git a/BUILDING.md b/BUILDING.md index c51a1a3eb..9e8458306 100644 --- a/BUILDING.md +++ b/BUILDING.md @@ -19,7 +19,8 @@ Once you have the prerequisites installed, you can build the CLI using: make ``` -This will output a `docker-compose` CLI plugin for your host machine in `./bin`. +This will output a `docker-compose` CLI plugin for your host machine in +`./bin/build`. You can statically cross compile the CLI for Windows, macOS, and Linux using the `cross` target. @@ -38,7 +39,6 @@ If you need to update a golden file simply do `go test ./... -test.update-golden To run e2e tests, the Compose CLI binary need to be build. All the commands to run e2e tests propose a version with the prefix `build-and-e2e` to first build the CLI before executing tests. - Note that this requires a local Docker Engine to be running. #### Whole end-to-end tests suite @@ -76,6 +76,7 @@ make e2e-compose-standalone ``` Or if you need to build the CLI, run: + ```console make build-and-e2e-compose-standalone ``` diff --git a/Dockerfile b/Dockerfile index adfe3f965..856b6a0a6 100644 --- a/Dockerfile +++ b/Dockerfile @@ -15,98 +15,173 @@ # See the License for the specific language governing permissions and # limitations under the License. -ARG GO_VERSION=1.18.5-alpine -ARG GOLANGCI_LINT_VERSION=v1.47.3-alpine -ARG PROTOC_GEN_GO_VERSION=v1.4.3 +ARG GO_VERSION=1.18.5 +ARG XX_VERSION=1.1.2 +ARG GOLANGCI_LINT_VERSION=v1.47.3 +ARG ADDLICENSE_VERSION=v1.0.0 -FROM --platform=${BUILDPLATFORM} golangci/golangci-lint:${GOLANGCI_LINT_VERSION} AS local-golangci-lint +ARG BUILD_TAGS="e2e,kube" +ARG DOCS_FORMATS="md,yaml" +ARG LICENSE_FILES=".*\(Dockerfile\|Makefile\|\.go\|\.hcl\|\.sh\)" -FROM --platform=${BUILDPLATFORM} golang:${GO_VERSION} AS base -WORKDIR /compose-cli -RUN apk add --no-cache -vv \ - git \ - docker \ - make \ - protoc \ - protobuf-dev +# xx is a helper for cross-compilation +FROM --platform=${BUILDPLATFORM} tonistiigi/xx:${XX_VERSION} AS xx + +FROM golangci/golangci-lint:${GOLANGCI_LINT_VERSION}-alpine AS golangci-lint +FROM ghcr.io/google/addlicense:${ADDLICENSE_VERSION} AS addlicense + +FROM --platform=${BUILDPLATFORM} golang:${GO_VERSION}-alpine AS base +COPY --from=xx / / +RUN apk add --no-cache \ + docker \ + file \ + git \ + protoc \ + protobuf-dev +WORKDIR /src +ENV CGO_ENABLED=0 + +FROM base AS build-base COPY go.* . RUN --mount=type=cache,target=/go/pkg/mod \ --mount=type=cache,target=/root/.cache/go-build \ go mod download -FROM base AS lint -ENV CGO_ENABLED=0 -COPY --from=local-golangci-lint /usr/bin/golangci-lint /usr/bin/golangci-lint -ARG BUILD_TAGS -ARG GIT_TAG -RUN --mount=target=. \ +FROM build-base AS vendored +RUN --mount=type=bind,target=.,rw \ --mount=type=cache,target=/go/pkg/mod \ - --mount=type=cache,target=/root/.cache/go-build \ - --mount=type=cache,target=/root/.cache/golangci-lint \ - BUILD_TAGS=${BUILD_TAGS} \ - GIT_TAG=${GIT_TAG} \ - make -f builder.Makefile lint + go mod tidy && mkdir /out && cp go.mod go.sum /out -FROM base AS make-compose-plugin -ENV CGO_ENABLED=0 +FROM scratch AS vendor-update +COPY --from=vendored /out / + +FROM vendored AS vendor-validate +RUN --mount=type=bind,target=.,rw <&2 'ERROR: Vendor result differs. Please vendor your package with "make go-mod-tidy"' + echo "$diff" + exit 1 + fi +EOT + +FROM base AS version +RUN --mount=target=. \ + PKG=github.com/docker/compose/v2 VERSION=$(git describe --match 'v[0-9]*' --dirty='.m' --always --tags); \ + echo "-X ${PKG}/internal.Version=${VERSION}" | tee /tmp/.ldflags; \ + echo -n "${VERSION}" | tee /tmp/.version; + +FROM build-base AS build +ARG BUILD_TAGS +ARG TARGETPLATFORM +RUN --mount=type=bind,target=. \ + --mount=type=cache,target=/root/.cache \ + --mount=type=cache,target=/go/pkg/mod \ + --mount=type=bind,source=/tmp/.ldflags,target=/tmp/.ldflags,from=version \ + set -x; xx-go build -trimpath -tags "$BUILD_TAGS" -ldflags "$(cat /tmp/.ldflags) -w -s" -o /usr/bin/docker-compose ./cmd && \ + xx-verify --static /usr/bin/docker-compose + +FROM build-base AS lint +ARG BUILD_TAGS +RUN --mount=type=bind,target=. \ + --mount=type=cache,target=/root/.cache \ + --mount=from=golangci-lint,source=/usr/bin/golangci-lint,target=/usr/bin/golangci-lint \ + golangci-lint run --build-tags "$BUILD_TAGS" ./... + +FROM build-base AS test +ARG CGO_ENABLED=0 +ARG BUILD_TAGS +RUN --mount=type=bind,target=. \ + --mount=type=cache,target=/root/.cache \ + --mount=type=cache,target=/go/pkg/mod \ + go test -tags "$BUILD_TAGS" -v -coverprofile=/tmp/coverage.txt -covermode=atomic $(go list $(TAGS) ./... | grep -vE 'e2e') && \ + go tool cover -func=/tmp/coverage.txt + +FROM scratch AS test-coverage +COPY --from=test /tmp/coverage.txt /coverage.txt + +FROM base AS license-set +ARG LICENSE_FILES +RUN --mount=type=bind,target=.,rw \ + --mount=from=addlicense,source=/app/addlicense,target=/usr/bin/addlicense \ + find . -regex "${LICENSE_FILES}" | xargs addlicense -c 'Docker Compose CLI' -l apache && \ + mkdir /out && \ + find . -regex "${LICENSE_FILES}" | cpio -pdm /out + +FROM scratch AS license-update +COPY --from=set /out / + +FROM base AS license-validate +ARG LICENSE_FILES +RUN --mount=type=bind,target=. \ + --mount=from=addlicense,source=/app/addlicense,target=/usr/bin/addlicense \ + find . -regex "${LICENSE_FILES}" | xargs addlicense -check -c 'Docker Compose CLI' -l apache -ignore validate -ignore testdata -ignore resolvepath -v + +FROM base AS docsgen +WORKDIR /src +RUN --mount=target=. \ + --mount=target=/root/.cache,type=cache \ + go build -o /out/docsgen ./docs/yaml/main/generate.go + +FROM --platform=${BUILDPLATFORM} alpine AS docs-build +RUN apk add --no-cache rsync git +WORKDIR /src +COPY --from=docsgen /out/docsgen /usr/bin +ARG DOCS_FORMATS +RUN --mount=target=/context \ + --mount=target=.,type=tmpfs <&2 'ERROR: Docs result differs. Please update with "make docs"' + git status --porcelain -- docs/reference + exit 1 + fi +EOT + +FROM scratch AS binary-unix +COPY --link --from=build /usr/bin/docker-compose / +FROM binary-unix AS binary-darwin +FROM binary-unix AS binary-linux +FROM scratch AS binary-windows +COPY --link --from=build /usr/bin/docker-compose /docker-compose.exe +FROM binary-$TARGETOS AS binary + +FROM --platform=$BUILDPLATFORM alpine AS releaser +RUN apk add --no-cache file perl-utils +WORKDIR /work ARG TARGETOS ARG TARGETARCH -ARG BUILD_TAGS -ARG GIT_TAG -RUN --mount=target=. \ - --mount=type=cache,target=/go/pkg/mod \ - --mount=type=cache,target=/root/.cache/go-build \ - GOOS=${TARGETOS} \ - GOARCH=${TARGETARCH} \ - BUILD_TAGS=${BUILD_TAGS} \ - GIT_TAG=${GIT_TAG} \ - make COMPOSE_BINARY=/out/docker-compose -f builder.Makefile compose-plugin +ARG TARGETVARIANT +RUN --mount=from=binary \ + mkdir -p /out && \ + # TODO: should just use standard arch + TARGETARCH=$([ "$TARGETARCH" = "amd64" ] && echo "x86_64" || echo "$TARGETARCH"); \ + TARGETARCH=$([ "$TARGETARCH" = "arm64" ] && echo "aarch64" || echo "$TARGETARCH"); \ + cp docker-compose* "/out/docker-compose-${TARGETOS}-${TARGETARCH}${TARGETVARIANT}$(ls docker-compose* | sed -e 's/^docker-compose//')" && \ + (cd /out ; for f in *; do shasum --binary --algorithm 256 $f | tee -a /out/checksums.txt > $f.sha256; done) -FROM base AS make-cross -ARG BUILD_TAGS -ARG GIT_TAG -RUN --mount=target=. \ - --mount=type=cache,target=/go/pkg/mod \ - --mount=type=cache,target=/root/.cache/go-build \ - BUILD_TAGS=${BUILD_TAGS} \ - GIT_TAG=${GIT_TAG} \ - make COMPOSE_BINARY=/out/docker-compose -f builder.Makefile cross - -FROM scratch AS compose-plugin -COPY --from=make-compose-plugin /out/* . - -FROM scratch AS cross -COPY --from=make-cross /out/* . - -FROM base AS test -ENV CGO_ENABLED=0 -ARG BUILD_TAGS -ARG GIT_TAG -RUN --mount=target=. \ - --mount=type=cache,target=/go/pkg/mod \ - --mount=type=cache,target=/root/.cache/go-build \ - BUILD_TAGS=${BUILD_TAGS} \ - GIT_TAG=${GIT_TAG} \ - make -f builder.Makefile test - -FROM base AS check-license-headers -RUN go install github.com/google/addlicense@latest -RUN --mount=target=. \ - make -f builder.Makefile check-license-headers - -FROM base AS make-go-mod-tidy -COPY . . -RUN --mount=type=cache,target=/go/pkg/mod \ - --mount=type=cache,target=/root/.cache/go-build \ - go mod tidy - -FROM scratch AS go-mod-tidy -COPY --from=make-go-mod-tidy /compose-cli/go.mod . -COPY --from=make-go-mod-tidy /compose-cli/go.sum . - -FROM base AS check-go-mod -COPY . . -RUN make -f builder.Makefile check-go-mod +FROM scratch AS release +COPY --from=releaser /out/ / # docs-reference is a target used as remote context to update docs on release # with latest changes on docker.github.io. diff --git a/Makefile b/Makefile index 2556adbfb..b72a7f5c1 100644 --- a/Makefile +++ b/Makefile @@ -12,7 +12,15 @@ # See the License for the specific language governing permissions and # limitations under the License. -export DOCKER_BUILDKIT=1 +ifneq (, $(BUILDX_BIN)) + export BUILDX_CMD = $(BUILDX_BIN) +else ifneq (, $(shell docker buildx version)) + export BUILDX_CMD = docker buildx +else ifneq (, $(shell which buildx)) + export BUILDX_CMD = $(which buildx) +else + $(error "Buildx is required: https://github.com/docker/buildx#installing") +endif UNAME_S := $(shell uname -s) ifeq ($(UNAME_S),Linux) @@ -35,11 +43,12 @@ all: compose-plugin .PHONY: compose-plugin compose-plugin: ## Compile the compose cli-plugin - @docker build . --target compose-plugin \ - --platform local \ - --build-arg BUILD_TAGS=e2e,kube \ - --build-arg GIT_TAG=$(GIT_TAG) \ - --output ./bin + $(BUILDX_CMD) bake binary + +.PHONY: install +install: compose-plugin + mkdir -p ~/.docker/cli-plugins + install bin/build/docker-compose ~/.docker/cli-plugins/docker-compose .PHONY: e2e-compose e2e-compose: ## Run end to end local tests in plugin mode. Set E2E_TEST=TestName to run a single test @@ -71,45 +80,31 @@ build-and-e2e: compose-plugin e2e-compose e2e-compose-standalone ## Compile the .PHONY: cross cross: ## Compile the CLI for linux, darwin and windows - @docker build . --target cross \ - --build-arg BUILD_TAGS \ - --build-arg GIT_TAG=$(GIT_TAG) \ - --output ./bin \ + $(BUILDX_CMD) bake binary .PHONY: test test: ## Run unit tests - @docker build --progress=plain . \ - --build-arg BUILD_TAGS=kube \ - --build-arg GIT_TAG=$(GIT_TAG) \ - --target test + $(BUILDX_CMD) bake test .PHONY: cache-clear cache-clear: ## Clear the builder cache - @docker builder prune --force --filter type=exec.cachemount --filter=unused-for=24h + $(BUILDX_CMD) prune --force --filter type=exec.cachemount --filter=unused-for=24h .PHONY: lint lint: ## run linter(s) - @docker build . \ - --build-arg BUILD_TAGS=kube,e2e \ - --build-arg GIT_TAG=$(GIT_TAG) \ - --target lint + $(BUILDX_CMD) bake lint .PHONY: docs docs: ## generate documentation - $(eval $@_TMP_OUT := $(shell mktemp -d -t dockercli-output.XXXXXXXXXX)) - docker build . \ - --output type=local,dest=$($@_TMP_OUT) \ - -f ./docs/Dockerfile \ - --target update + $(eval $@_TMP_OUT := $(shell mktemp -d -t compose-output.XXXXXXXXXX)) + $(BUILDX_CMD) bake --set "*.output=type=local,dest=$($@_TMP_OUT)" docs-update rm -rf ./docs/internal cp -R "$($@_TMP_OUT)"/out/* ./docs/ rm -rf "$($@_TMP_OUT)"/* .PHONY: validate-docs validate-docs: ## validate the doc does not change - @docker build . \ - -f ./docs/Dockerfile \ - --target validate + $(BUILDX_CMD) bake docs-validate .PHONY: check-dependencies check-dependencies: ## check dependency updates @@ -117,15 +112,15 @@ check-dependencies: ## check dependency updates .PHONY: validate-headers validate-headers: ## Check license header for all files - @docker build . --target check-license-headers + $(BUILDX_CMD) bake license-validate .PHONY: go-mod-tidy go-mod-tidy: ## Run go mod tidy in a container and output resulting go.mod and go.sum - @docker build . --target go-mod-tidy --output . + $(BUILDX_CMD) bake vendor-update .PHONY: validate-go-mod validate-go-mod: ## Validate go.mod and go.sum are up-to-date - @docker build . --target check-go-mod + $(BUILDX_CMD) bake vendor-validate validate: validate-go-mod validate-headers validate-docs ## Validate sources diff --git a/README.md b/README.md index 8e6871b24..2007d9987 100644 --- a/README.md +++ b/README.md @@ -1,6 +1,9 @@ # Docker Compose v2 -[![Actions Status](https://github.com/docker/compose/workflows/Continuous%20integration/badge.svg)](https://github.com/docker/compose/actions) +[![GitHub release](https://img.shields.io/github/release/docker/compose.svg?style=flat-square)](https://github.com/docker/compose/releases/latest) +[![PkgGoDev](https://img.shields.io/badge/go.dev-docs-007d9c?style=flat-square&logo=go&logoColor=white)](https://pkg.go.dev/github.com/docker/compose/v2) +[![Build Status](https://img.shields.io/github/workflow/status/docker/compose/ci?label=ci&logo=github&style=flat-square)](https://github.com/docker/compose/actions?query=workflow%3Aci) +[![Go Report Card](https://goreportcard.com/badge/github.com/docker/compose/v2?style=flat-square)](https://goreportcard.com/report/github.com/docker/compose/v2) ![Docker Compose](logo.png?raw=true "Docker Compose Logo") diff --git a/builder.Makefile b/builder.Makefile deleted file mode 100644 index 0f525adb3..000000000 --- a/builder.Makefile +++ /dev/null @@ -1,73 +0,0 @@ -# Copyright 2020 Docker Compose CLI authors - -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at - -# http://www.apache.org/licenses/LICENSE-2.0 - -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. - -GOOS?=$(shell go env GOOS) -GOARCH?=$(shell go env GOARCH) - -PKG_NAME := github.com/docker/compose/v2 - -EXTENSION:= -ifeq ($(GOOS),windows) - EXTENSION:=.exe -endif - -STATIC_FLAGS=CGO_ENABLED=0 - -GIT_TAG?=$(shell git describe --tags --match "v[0-9]*") - -LDFLAGS="-s -w -X $(PKG_NAME)/internal.Version=${GIT_TAG}" -GO_BUILD=$(STATIC_FLAGS) go build -trimpath -ldflags=$(LDFLAGS) - -COMPOSE_BINARY?=bin/docker-compose -COMPOSE_BINARY_WITH_EXTENSION=$(COMPOSE_BINARY)$(EXTENSION) - -WORK_DIR:=$(shell mktemp -d) - -TAGS:= -ifdef BUILD_TAGS - TAGS=-tags $(BUILD_TAGS) - LINT_TAGS=--build-tags $(BUILD_TAGS) -endif - -.PHONY: compose-plugin -compose-plugin: - GOOS=${GOOS} GOARCH=${GOARCH} $(GO_BUILD) $(TAGS) -o $(COMPOSE_BINARY_WITH_EXTENSION) ./cmd - -.PHONY: cross -cross: - GOOS=linux GOARCH=amd64 $(GO_BUILD) $(TAGS) -o $(COMPOSE_BINARY)-linux-x86_64 ./cmd - GOOS=linux GOARCH=ppc64le $(GO_BUILD) $(TAGS) -o $(COMPOSE_BINARY)-linux-ppc64le ./cmd - GOOS=linux GOARCH=arm64 $(GO_BUILD) $(TAGS) -o $(COMPOSE_BINARY)-linux-aarch64 ./cmd - GOOS=linux GOARM=6 GOARCH=arm $(GO_BUILD) $(TAGS) -o $(COMPOSE_BINARY)-linux-armv6 ./cmd - GOOS=linux GOARM=7 GOARCH=arm $(GO_BUILD) $(TAGS) -o $(COMPOSE_BINARY)-linux-armv7 ./cmd - GOOS=linux GOARCH=s390x $(GO_BUILD) $(TAGS) -o $(COMPOSE_BINARY)-linux-s390x ./cmd - GOOS=darwin GOARCH=amd64 $(GO_BUILD) $(TAGS) -o $(COMPOSE_BINARY)-darwin-x86_64 ./cmd - GOOS=darwin GOARCH=arm64 $(GO_BUILD) $(TAGS) -o $(COMPOSE_BINARY)-darwin-aarch64 ./cmd - GOOS=windows GOARCH=amd64 $(GO_BUILD) $(TAGS) -o $(COMPOSE_BINARY)-windows-x86_64.exe ./cmd - -.PHONY: test -test: - go test $(TAGS) -cover $(shell go list $(TAGS) ./... | grep -vE 'e2e') - -.PHONY: lint -lint: - golangci-lint run $(LINT_TAGS) --timeout 10m0s ./... - -.PHONY: check-license-headers -check-license-headers: - ./scripts/validate/fileheader - -.PHONY: check-go-mod -check-go-mod: - ./scripts/validate/check-go-mod diff --git a/cmd/compose/compose.go b/cmd/compose/compose.go index cfa5154a1..10d110884 100644 --- a/cmd/compose/compose.go +++ b/cmd/compose/compose.go @@ -28,6 +28,7 @@ import ( "github.com/compose-spec/compose-go/cli" "github.com/compose-spec/compose-go/types" composegoutils "github.com/compose-spec/compose-go/utils" + "github.com/docker/buildx/util/logutil" dockercli "github.com/docker/cli/cli" "github.com/docker/cli/cli-plugins/manager" "github.com/docker/cli/cli/command" @@ -250,6 +251,16 @@ func RunningAsStandalone() bool { // RootCommand returns the compose command with its child commands func RootCommand(dockerCli command.Cli, backend api.Service) *cobra.Command { + // filter out useless commandConn.CloseWrite warning message that can occur + // when using a remote context that is unreachable: "commandConn.CloseWrite: commandconn: failed to wait: signal: killed" + // https://github.com/docker/cli/blob/e1f24d3c93df6752d3c27c8d61d18260f141310c/cli/connhelper/commandconn/commandconn.go#L203-L215 + logrus.AddHook(logutil.NewFilter([]logrus.Level{ + logrus.WarnLevel, + }, + "commandConn.CloseWrite:", + "commandConn.CloseRead:", + )) + opts := projectOptions{} var ( ansi string diff --git a/cmd/formatter/logs.go b/cmd/formatter/logs.go index b5bc37361..74ac6e056 100644 --- a/cmd/formatter/logs.go +++ b/cmd/formatter/logs.go @@ -89,7 +89,7 @@ func (l *logConsumer) Log(container, service, message string) { } p := l.getPresenter(container) for _, line := range strings.Split(message, "\n") { - fmt.Fprintf(l.writer, "%s%s\n", p.prefix, line) //nolint:errcheck + fmt.Fprintf(l.writer, "%s%s\n", p.prefix, line) } } diff --git a/docker-bake.hcl b/docker-bake.hcl new file mode 100644 index 000000000..80d6b0546 --- /dev/null +++ b/docker-bake.hcl @@ -0,0 +1,124 @@ +// Copyright 2022 Docker Compose CLI authors +// +// Licensed under the Apache License, Version 2.0 (the "License"); +// you may not use this file except in compliance with the License. +// You may obtain a copy of the License at +// +// http://www.apache.org/licenses/LICENSE-2.0 +// +// Unless required by applicable law or agreed to in writing, software +// distributed under the License is distributed on an "AS IS" BASIS, +// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +// See the License for the specific language governing permissions and +// limitations under the License. + +variable "GO_VERSION" { + default = "1.18.5" +} + +variable "BUILD_TAGS" { + default = "e2e,kube" +} + +variable "DOCS_FORMATS" { + default = "md,yaml" +} + +# Defines the output folder +variable "DESTDIR" { + default = "" +} +function "bindir" { + params = [defaultdir] + result = DESTDIR != "" ? DESTDIR : "./bin/${defaultdir}" +} + +target "_common" { + args = { + GO_VERSION = GO_VERSION + BUILD_TAGS = BUILD_TAGS + BUILDKIT_CONTEXT_KEEP_GIT_DIR = 1 + } +} + +group "default" { + targets = ["binary"] +} + +group "validate" { + targets = ["lint", "vendor-validate", "license-validate"] +} + +target "lint" { + inherits = ["_common"] + target = "lint" + output = ["type=cacheonly"] +} + +target "license-validate" { + target = "license-validate" + output = ["type=cacheonly"] +} + +target "license-update" { + target = "license-update" + output = ["."] +} + +target "vendor-validate" { + inherits = ["_common"] + target = "vendor-validate" + output = ["type=cacheonly"] +} + +target "vendor" { + inherits = ["_common"] + target = "vendor-update" + output = ["."] +} + +target "test" { + inherits = ["_common"] + target = "test-coverage" + output = [bindir("coverage")] +} + +target "binary" { + inherits = ["_common"] + target = "binary" + output = [bindir("build")] + platforms = ["local"] +} + +target "binary-cross" { + inherits = ["binary"] + platforms = [ + "darwin/amd64", + "darwin/arm64", + "linux/amd64", + "linux/arm/v6", + "linux/arm/v7", + "linux/arm64", + "linux/ppc64le", + "linux/s390x", + "windows/amd64" + ] +} + +target "release" { + inherits = ["binary-cross"] + target = "release" + output = [bindir("release")] +} + +target "docs-validate" { + inherits = ["_common"] + target = "docs-validate" + output = ["type=cacheonly"] +} + +target "docs-update" { + inherits = ["_common"] + target = "docs-update" + output = ["./docs"] +} diff --git a/docs/Dockerfile b/docs/Dockerfile deleted file mode 100644 index b23217608..000000000 --- a/docs/Dockerfile +++ /dev/null @@ -1,57 +0,0 @@ -# syntax=docker/dockerfile:1 - - -# Copyright 2020 Docker Compose CLI authors - -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at - -# http://www.apache.org/licenses/LICENSE-2.0 - -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. - -ARG GO_VERSION=1.18.5 -ARG FORMATS=md,yaml - -FROM --platform=${BUILDPLATFORM} golang:${GO_VERSION}-alpine AS docsgen -WORKDIR /src -RUN --mount=target=. \ - --mount=target=/root/.cache,type=cache \ - go build -o /out/docsgen ./docs/yaml/main/generate.go - -FROM --platform=${BUILDPLATFORM} alpine AS gen -RUN apk add --no-cache rsync git -WORKDIR /src -COPY --from=docsgen /out/docsgen /usr/bin -ARG FORMATS -RUN --mount=target=/context \ - --mount=target=.,type=tmpfs <&2 'ERROR: Docs result differs. Please update with "make docs"' - git status --porcelain -- docs/reference - exit 1 -fi -EOT diff --git a/go.mod b/go.mod index a6024a3de..97b04f592 100644 --- a/go.mod +++ b/go.mod @@ -8,7 +8,7 @@ require ( github.com/cnabio/cnab-to-oci v0.3.6 github.com/compose-spec/compose-go v1.4.0 github.com/containerd/console v1.0.3 - github.com/containerd/containerd v1.6.7 + github.com/containerd/containerd v1.6.8 github.com/distribution/distribution/v3 v3.0.0-20220729163034-26163d82560f github.com/docker/buildx v0.8.2 // when updating, also update the replace rules accordingly github.com/docker/cli v20.10.17+incompatible diff --git a/go.sum b/go.sum index 7f04cbf40..0e7dbbab5 100644 --- a/go.sum +++ b/go.sum @@ -330,8 +330,8 @@ github.com/containerd/containerd v1.5.1/go.mod h1:0DOxVqwDy2iZvrZp2JUx/E+hS0UNTV github.com/containerd/containerd v1.5.7/go.mod h1:gyvv6+ugqY25TiXxcZC3L5yOeYgEw0QMhscqVp1AR9c= github.com/containerd/containerd v1.5.8/go.mod h1:YdFSv5bTFLpG2HIYmfqDpSYYTDX+mc5qtSuYx1YUb/s= github.com/containerd/containerd v1.6.1/go.mod h1:1nJz5xCZPusx6jJU8Frfct988y0NpumIq9ODB0kLtoE= -github.com/containerd/containerd v1.6.7 h1:IVikHEHEMZ5SXpUa80tNGNIV7fBigjp+sOcrlzAkPCc= -github.com/containerd/containerd v1.6.7/go.mod h1:By6p5KqPK0/7/CgO/A6t/Gz+CUYUu2zf1hUaaymVXB0= +github.com/containerd/containerd v1.6.8 h1:h4dOFDwzHmqFEP754PgfgTeVXFnLiRc6kiqC7tplDJs= +github.com/containerd/containerd v1.6.8/go.mod h1:By6p5KqPK0/7/CgO/A6t/Gz+CUYUu2zf1hUaaymVXB0= github.com/containerd/continuity v0.0.0-20190426062206-aaeac12a7ffc/go.mod h1:GL3xCUCBDV3CZiTSEKksMWbLE66hEyuu9qyDOOqM47Y= github.com/containerd/continuity v0.0.0-20190815185530-f2a389ac0a02/go.mod h1:GL3xCUCBDV3CZiTSEKksMWbLE66hEyuu9qyDOOqM47Y= github.com/containerd/continuity v0.0.0-20191127005431-f65d91d395eb/go.mod h1:GL3xCUCBDV3CZiTSEKksMWbLE66hEyuu9qyDOOqM47Y= diff --git a/pkg/compose/build_classic.go b/pkg/compose/build_classic.go index dc88dee3f..e362ae247 100644 --- a/pkg/compose/build_classic.go +++ b/pkg/compose/build_classic.go @@ -29,7 +29,6 @@ import ( "github.com/compose-spec/compose-go/types" buildx "github.com/docker/buildx/build" "github.com/docker/cli/cli/command/image/build" - "github.com/docker/compose/v2/pkg/api" dockertypes "github.com/docker/docker/api/types" "github.com/docker/docker/cli" "github.com/docker/docker/pkg/archive" @@ -40,6 +39,8 @@ import ( "github.com/docker/docker/pkg/urlutil" "github.com/hashicorp/go-multierror" "github.com/pkg/errors" + + "github.com/docker/compose/v2/pkg/api" ) func (s *composeService) doBuildClassic(ctx context.Context, project *types.Project, opts map[string]buildx.Options) (map[string]string, error) { @@ -65,7 +66,7 @@ func (s *composeService) doBuildClassic(ctx context.Context, project *types.Proj return nameDigests, errs } -//nolint: gocyclo +//nolint:gocyclo func (s *composeService) doBuildClassicSimpleImage(ctx context.Context, options buildx.Options) (string, error) { var ( buildCtx io.ReadCloser diff --git a/pkg/compose/container.go b/pkg/compose/container.go index 954aed727..004ac4167 100644 --- a/pkg/compose/container.go +++ b/pkg/compose/container.go @@ -30,13 +30,13 @@ const ( // ContainerRunning running status ContainerRunning = "running" // ContainerRemoving removing status - ContainerRemoving = "removing" //nolint + ContainerRemoving = "removing" // ContainerPaused paused status - ContainerPaused = "paused" //nolint + ContainerPaused = "paused" // ContainerExited exited status - ContainerExited = "exited" //nolint + ContainerExited = "exited" // ContainerDead dead status - ContainerDead = "dead" //nolint + ContainerDead = "dead" ) var _ io.ReadCloser = ContainerStdout{} diff --git a/pkg/compose/dependencies_test.go b/pkg/compose/dependencies_test.go index 5d5871a54..61bf0fd9c 100644 --- a/pkg/compose/dependencies_test.go +++ b/pkg/compose/dependencies_test.go @@ -21,7 +21,7 @@ import ( "testing" "github.com/compose-spec/compose-go/types" - "gotest.tools/v3/assert" + "github.com/stretchr/testify/require" ) var project = types.Project{ @@ -45,25 +45,27 @@ var project = types.Project{ } func TestInDependencyUpCommandOrder(t *testing.T) { - order := make(chan string) - //nolint:errcheck, unparam - go InDependencyOrder(context.TODO(), &project, func(ctx context.Context, config string) error { - order <- config + ctx, cancel := context.WithCancel(context.Background()) + t.Cleanup(cancel) + + var order []string + err := InDependencyOrder(ctx, &project, func(ctx context.Context, service string) error { + order = append(order, service) return nil }) - assert.Equal(t, <-order, "test3") - assert.Equal(t, <-order, "test2") - assert.Equal(t, <-order, "test1") + require.NoError(t, err, "Error during iteration") + require.Equal(t, []string{"test3", "test2", "test1"}, order) } func TestInDependencyReverseDownCommandOrder(t *testing.T) { - order := make(chan string) - //nolint:errcheck, unparam - go InReverseDependencyOrder(context.TODO(), &project, func(ctx context.Context, config string) error { - order <- config + ctx, cancel := context.WithCancel(context.Background()) + t.Cleanup(cancel) + + var order []string + err := InReverseDependencyOrder(ctx, &project, func(ctx context.Context, service string) error { + order = append(order, service) return nil }) - assert.Equal(t, <-order, "test1") - assert.Equal(t, <-order, "test2") - assert.Equal(t, <-order, "test3") + require.NoError(t, err, "Error during iteration") + require.Equal(t, []string{"test1", "test2", "test3"}, order) } diff --git a/pkg/compose/logs.go b/pkg/compose/logs.go index 7d26c815a..e8a16e780 100644 --- a/pkg/compose/logs.go +++ b/pkg/compose/logs.go @@ -21,11 +21,12 @@ import ( "io" "strings" - "github.com/docker/compose/v2/pkg/api" - "github.com/docker/compose/v2/pkg/utils" "github.com/docker/docker/api/types" "github.com/docker/docker/pkg/stdcopy" "golang.org/x/sync/errgroup" + + "github.com/docker/compose/v2/pkg/api" + "github.com/docker/compose/v2/pkg/utils" ) func (s *composeService) Logs(ctx context.Context, projectName string, consumer api.LogConsumer, options api.LogOptions) error { @@ -95,7 +96,7 @@ func (s *composeService) logContainers(ctx context.Context, consumer api.LogCons if err != nil { return err } - defer r.Close() //nolint errcheck + defer r.Close() //nolint:errcheck name := getContainerNameWithoutProject(c) w := utils.GetWriter(func(line string) { diff --git a/pkg/e2e/compose_test.go b/pkg/e2e/compose_test.go index 43c36ae02..7d7945f18 100644 --- a/pkg/e2e/compose_test.go +++ b/pkg/e2e/compose_test.go @@ -172,7 +172,7 @@ func TestDownComposefileInParentFolder(t *testing.T) { tmpFolder, err := os.MkdirTemp("fixtures/simple-composefile", "test-tmp") assert.NilError(t, err) - defer os.Remove(tmpFolder) // nolint: errcheck + defer os.Remove(tmpFolder) //nolint:errcheck projectName := filepath.Base(tmpFolder) res := c.RunDockerComposeCmd(t, "--project-directory", tmpFolder, "up", "-d") diff --git a/pkg/e2e/framework.go b/pkg/e2e/framework.go index 66a6233a7..2fa263505 100644 --- a/pkg/e2e/framework.go +++ b/pkg/e2e/framework.go @@ -129,7 +129,7 @@ func initializePlugins(t testing.TB, configDir string) { require.NoError(t, os.MkdirAll(filepath.Join(configDir, "cli-plugins"), 0o755), "Failed to create cli-plugins directory") - composePlugin, err := findExecutable(DockerComposeExecutableName, []string{"../../bin", "../../../bin"}) + composePlugin, err := findExecutable(DockerComposeExecutableName, []string{"../../bin/build", "../../../bin/build"}) if os.IsNotExist(err) { t.Logf("WARNING: docker-compose cli-plugin not found") } @@ -172,12 +172,12 @@ func CopyFile(t testing.TB, sourceFile string, destinationFile string) { src, err := os.Open(sourceFile) require.NoError(t, err, "Failed to open source file: %s") - //nolint: errcheck + //nolint:errcheck defer src.Close() dst, err := os.OpenFile(destinationFile, os.O_RDWR|os.O_CREATE|os.O_TRUNC, 0o755) require.NoError(t, err, "Failed to open destination file: %s", destinationFile) - //nolint: errcheck + //nolint:errcheck defer dst.Close() _, err = io.Copy(dst, src) @@ -302,7 +302,7 @@ func ComposeStandalonePath(t testing.TB) string { if !composeStandaloneMode { require.Fail(t, "Not running in standalone mode") } - composeBinary, err := findExecutable(DockerComposeExecutableName, []string{"../../bin", "../../../bin"}) + composeBinary, err := findExecutable(DockerComposeExecutableName, []string{"../../bin/build", "../../../bin/build"}) require.NoError(t, err, "Could not find standalone Compose binary (%q)", DockerComposeExecutableName) return composeBinary diff --git a/pkg/e2e/volumes_test.go b/pkg/e2e/volumes_test.go index 604b3ba6c..76a9094b9 100644 --- a/pkg/e2e/volumes_test.go +++ b/pkg/e2e/volumes_test.go @@ -50,7 +50,6 @@ func TestLocalComposeVolume(t *testing.T) { t.Run("check container volume specs", func(t *testing.T) { res := c.RunDockerCmd(t, "inspect", "compose-e2e-volume-nginx2-1", "--format", "{{ json .Mounts }}") output := res.Stdout() - //nolint assert.Assert(t, strings.Contains(output, `"Destination":"/usr/src/app/node_modules","Driver":"local","Mode":"z","RW":true,"Propagation":""`), output) assert.Assert(t, strings.Contains(output, `"Destination":"/myconfig","Mode":"","RW":false,"Propagation":"rprivate"`), output) }) @@ -68,7 +67,6 @@ func TestLocalComposeVolume(t *testing.T) { t.Run("check container bind-mounts specs", func(t *testing.T) { res := c.RunDockerCmd(t, "inspect", "compose-e2e-volume-nginx-1", "--format", "{{ json .Mounts }}") output := res.Stdout() - //nolint assert.Assert(t, strings.Contains(output, `"Type":"bind"`)) assert.Assert(t, strings.Contains(output, `"Destination":"/usr/share/nginx/html"`)) }) diff --git a/pkg/progress/tty.go b/pkg/progress/tty.go index 0dc95b906..09338fb83 100644 --- a/pkg/progress/tty.go +++ b/pkg/progress/tty.go @@ -164,14 +164,12 @@ func (w *ttyWriter) print() { continue } line := lineText(event, "", terminalWidth, statusPadding, runtime.GOOS != "windows") - //nolint: errcheck fmt.Fprint(w.out, line) numLines++ for _, v := range w.eventIDs { ev := w.events[v] if ev.ParentID == event.ID { line := lineText(ev, " ", terminalWidth, statusPadding, runtime.GOOS != "windows") - //nolint: errcheck fmt.Fprint(w.out, line) numLines++ } diff --git a/pkg/utils/writer_test.go b/pkg/utils/writer_test.go index 7eedb844f..7383a3e87 100644 --- a/pkg/utils/writer_test.go +++ b/pkg/utils/writer_test.go @@ -22,18 +22,19 @@ import ( "gotest.tools/v3/assert" ) +//nolint:errcheck func TestSplitWriter(t *testing.T) { var lines []string w := GetWriter(func(line string) { lines = append(lines, line) }) - w.Write([]byte("h")) //nolint: errcheck - w.Write([]byte("e")) //nolint: errcheck - w.Write([]byte("l")) //nolint: errcheck - w.Write([]byte("l")) //nolint: errcheck - w.Write([]byte("o")) //nolint: errcheck - w.Write([]byte("\n")) //nolint: errcheck - w.Write([]byte("world!\n")) //nolint: errcheck + w.Write([]byte("h")) + w.Write([]byte("e")) + w.Write([]byte("l")) + w.Write([]byte("l")) + w.Write([]byte("o")) + w.Write([]byte("\n")) + w.Write([]byte("world!\n")) assert.DeepEqual(t, lines, []string{"hello", "world!"}) } diff --git a/scripts/validate/check-go-mod b/scripts/validate/check-go-mod deleted file mode 100755 index ad45b563b..000000000 --- a/scripts/validate/check-go-mod +++ /dev/null @@ -1,32 +0,0 @@ -#!/bin/sh - -# Copyright Docker Compose CLI authors - -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at - -# http://www.apache.org/licenses/LICENSE-2.0 - -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. - - -set -uo pipefail -mkdir -p /tmp/gomod -cp go.* /tmp/gomod/ -go mod tidy -DIFF=$(diff go.mod /tmp/gomod/go.mod && diff go.sum /tmp/gomod/go.sum) -if [ "$DIFF" ]; then - echo - echo "go.mod and go.sum are not up to date" - echo - echo "$DIFF" - echo - exit 1 -else - echo "go.mod is correct" -fi; diff --git a/scripts/validate/fileheader b/scripts/validate/fileheader deleted file mode 100755 index abb30b03f..000000000 --- a/scripts/validate/fileheader +++ /dev/null @@ -1,27 +0,0 @@ -#!/usr/bin/env sh - -# Copyright 2020,2022 Docker Compose CLI authors - -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at - -# http://www.apache.org/licenses/LICENSE-2.0 - -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. - -set -eu -o pipefail - -if ! command -v addlicense; then - >&2 echo "ERROR: addlicense not found. Install with:" - >&2 echo " go install -u github.com/google/addlicense@latest" - exit 1 -fi - -BASEPATH="${1-}" - -find . -regex '.*\.sh' -o -regex '.*\.go' -o -regex '.*Makefile' -o -regex '.*Dockerfile' | xargs addlicense -check -l apache -c 'Docker Compose CLI authors' -ignore validate -ignore testdata -ignore resolvepath -v 1>&2 \ No newline at end of file diff --git a/scripts/validate/template/bash.txt b/scripts/validate/template/bash.txt deleted file mode 100644 index 31e00001c..000000000 --- a/scripts/validate/template/bash.txt +++ /dev/null @@ -1,13 +0,0 @@ -# Copyright 2020 Docker Compose CLI authors - -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at - -# http://www.apache.org/licenses/LICENSE-2.0 - -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. diff --git a/scripts/validate/template/dockerfile.txt b/scripts/validate/template/dockerfile.txt deleted file mode 100644 index 31e00001c..000000000 --- a/scripts/validate/template/dockerfile.txt +++ /dev/null @@ -1,13 +0,0 @@ -# Copyright 2020 Docker Compose CLI authors - -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at - -# http://www.apache.org/licenses/LICENSE-2.0 - -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License. diff --git a/scripts/validate/template/go.txt b/scripts/validate/template/go.txt deleted file mode 100644 index a3ee08615..000000000 --- a/scripts/validate/template/go.txt +++ /dev/null @@ -1,16 +0,0 @@ -/* - Copyright 2020 Docker Compose CLI authors - - Licensed under the Apache License, Version 2.0 (the "License"); - you may not use this file except in compliance with the License. - You may obtain a copy of the License at - - http://www.apache.org/licenses/LICENSE-2.0 - - Unless required by applicable law or agreed to in writing, software - distributed under the License is distributed on an "AS IS" BASIS, - WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. - See the License for the specific language governing permissions and - limitations under the License. -*/ - diff --git a/scripts/validate/template/makefile.txt b/scripts/validate/template/makefile.txt deleted file mode 100644 index 31e00001c..000000000 --- a/scripts/validate/template/makefile.txt +++ /dev/null @@ -1,13 +0,0 @@ -# Copyright 2020 Docker Compose CLI authors - -# Licensed under the Apache License, Version 2.0 (the "License"); -# you may not use this file except in compliance with the License. -# You may obtain a copy of the License at - -# http://www.apache.org/licenses/LICENSE-2.0 - -# Unless required by applicable law or agreed to in writing, software -# distributed under the License is distributed on an "AS IS" BASIS, -# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. -# See the License for the specific language governing permissions and -# limitations under the License.