mirror of
https://github.com/drone/drone-cli.git
synced 2024-11-26 06:07:05 +01:00
Merge branch 'master' into secret-info
This commit is contained in:
commit
5400456c24
14
.drone.sh
14
.drone.sh
@ -6,17 +6,19 @@ set -x
|
|||||||
export CGO_ENABLED=0
|
export CGO_ENABLED=0
|
||||||
|
|
||||||
# compile for all architectures
|
# compile for all architectures
|
||||||
GOOS=linux GOARCH=amd64 go build -ldflags "-X main.version=${DRONE_TAG##v}" -o release/linux/amd64/drone github.com/drone/drone-cli/drone
|
GOOS=linux GOARCH=amd64 go build -ldflags "-X main.version=${DRONE_TAG##v}" -o release/linux/amd64/drone ./drone
|
||||||
GOOS=linux GOARCH=arm64 go build -ldflags "-X main.version=${DRONE_TAG##v}" -o release/linux/arm64/drone github.com/drone/drone-cli/drone
|
GOOS=linux GOARCH=arm64 go build -ldflags "-X main.version=${DRONE_TAG##v}" -o release/linux/arm64/drone ./drone
|
||||||
GOOS=linux GOARCH=arm go build -ldflags "-X main.version=${DRONE_TAG##v}" -o release/linux/arm/drone github.com/drone/drone-cli/drone
|
GOOS=linux GOARCH=ppc64le go build -ldflags "-X main.version=${DRONE_TAG##v}" -o release/linux/ppc64le/drone ./drone
|
||||||
GOOS=windows GOARCH=amd64 go build -ldflags "-X main.version=${DRONE_TAG##v}" -o release/windows/amd64/drone github.com/drone/drone-cli/drone
|
GOOS=linux GOARCH=arm go build -ldflags "-X main.version=${DRONE_TAG##v}" -o release/linux/arm/drone ./drone
|
||||||
GOOS=darwin GOARCH=amd64 go build -ldflags "-X main.version=${DRONE_TAG##v}" -o release/darwin/amd64/drone github.com/drone/drone-cli/drone
|
GOOS=windows GOARCH=amd64 go build -ldflags "-X main.version=${DRONE_TAG##v}" -o release/windows/amd64/drone.exe ./drone
|
||||||
|
GOOS=darwin GOARCH=amd64 go build -ldflags "-X main.version=${DRONE_TAG##v}" -o release/darwin/amd64/drone ./drone
|
||||||
|
|
||||||
# tar binary files prior to upload
|
# tar binary files prior to upload
|
||||||
tar -cvzf release/drone_linux_amd64.tar.gz -C release/linux/amd64 drone
|
tar -cvzf release/drone_linux_amd64.tar.gz -C release/linux/amd64 drone
|
||||||
tar -cvzf release/drone_linux_arm64.tar.gz -C release/linux/arm64 drone
|
tar -cvzf release/drone_linux_arm64.tar.gz -C release/linux/arm64 drone
|
||||||
|
tar -cvzf release/drone_linux_ppc64le.tar.gz -C release/linux/ppc64le drone
|
||||||
tar -cvzf release/drone_linux_arm.tar.gz -C release/linux/arm drone
|
tar -cvzf release/drone_linux_arm.tar.gz -C release/linux/arm drone
|
||||||
tar -cvzf release/drone_windows_amd64.tar.gz -C release/windows/amd64 drone
|
tar -cvzf release/drone_windows_amd64.tar.gz -C release/windows/amd64 drone.exe
|
||||||
tar -cvzf release/drone_darwin_amd64.tar.gz -C release/darwin/amd64 drone
|
tar -cvzf release/drone_darwin_amd64.tar.gz -C release/darwin/amd64 drone
|
||||||
|
|
||||||
# generate shas for tar files
|
# generate shas for tar files
|
||||||
|
99
.drone.yml
99
.drone.yml
@ -1,57 +1,88 @@
|
|||||||
workspace:
|
kind: pipeline
|
||||||
base: /go
|
type: docker
|
||||||
path: src/github.com/drone/drone-cli
|
name: default
|
||||||
|
|
||||||
pipeline:
|
steps:
|
||||||
build:
|
- name: build
|
||||||
image: golang:1.9
|
image: golang:1.13
|
||||||
commands: sh .drone.sh
|
commands:
|
||||||
|
- sh .drone.sh
|
||||||
|
|
||||||
publish_latest:
|
- name: publish_latest
|
||||||
image: plugins/docker
|
image: plugins/docker
|
||||||
|
settings:
|
||||||
repo: drone/cli
|
repo: drone/cli
|
||||||
secrets: [docker_username, docker_password]
|
username:
|
||||||
|
from_secret: docker_username
|
||||||
|
password:
|
||||||
|
from_secret: docker_password
|
||||||
auto_tag: true
|
auto_tag: true
|
||||||
when:
|
when:
|
||||||
event: [push, tag]
|
event: [push, tag]
|
||||||
|
|
||||||
publish_alpine:
|
- name: publish_alpine
|
||||||
image: plugins/docker
|
image: plugins/docker
|
||||||
|
settings:
|
||||||
repo: drone/cli
|
repo: drone/cli
|
||||||
secrets: [docker_username, docker_password]
|
username:
|
||||||
|
from_secret: docker_username
|
||||||
|
password:
|
||||||
|
from_secret: docker_password
|
||||||
auto_tag: true
|
auto_tag: true
|
||||||
auto_tag_suffix: alpine
|
auto_tag_suffix: alpine
|
||||||
dockerfile: Dockerfile.alpine
|
dockerfile: Dockerfile.alpine
|
||||||
when:
|
when:
|
||||||
event: [push, tag]
|
event: [push, tag]
|
||||||
|
|
||||||
publish_linux_arm:
|
- name: publish_linux_arm
|
||||||
image: plugins/docker
|
image: plugins/docker
|
||||||
|
settings:
|
||||||
repo: drone/cli
|
repo: drone/cli
|
||||||
secrets: [docker_username, docker_password]
|
username:
|
||||||
|
from_secret: docker_username
|
||||||
|
password:
|
||||||
|
from_secret: docker_password
|
||||||
auto_tag: true
|
auto_tag: true
|
||||||
auto_tag_suffix: linux-arm
|
auto_tag_suffix: linux-arm
|
||||||
dockerfile: Dockerfile.linux.arm
|
dockerfile: Dockerfile.linux.arm
|
||||||
when:
|
when:
|
||||||
event: [push, tag]
|
event: [push, tag]
|
||||||
|
|
||||||
publish_linux_arm64:
|
- name: publish_linux_arm64
|
||||||
image: plugins/docker
|
image: plugins/docker
|
||||||
|
settings:
|
||||||
repo: drone/cli
|
repo: drone/cli
|
||||||
secrets: [docker_username, docker_password]
|
username:
|
||||||
|
from_secret: docker_username
|
||||||
|
password:
|
||||||
|
from_secret: docker_password
|
||||||
auto_tag: true
|
auto_tag: true
|
||||||
auto_tag_suffix: linux-arm64
|
auto_tag_suffix: linux-arm64
|
||||||
dockerfile: Dockerfile.linux.arm64
|
dockerfile: Dockerfile.linux.arm64
|
||||||
when:
|
when:
|
||||||
event: [push, tag]
|
event: [push, tag]
|
||||||
|
|
||||||
release:
|
- name: publish_linux_ppc64le
|
||||||
image: plugins/github-release
|
image: plugins/docker
|
||||||
|
settings:
|
||||||
|
repo: drone/cli
|
||||||
|
username:
|
||||||
|
from_secret: docker_username
|
||||||
|
password:
|
||||||
|
from_secret: docker_password
|
||||||
|
auto_tag: true
|
||||||
|
auto_tag_suffix: linux-ppc64le
|
||||||
|
dockerfile: Dockerfile.linux.ppc64le
|
||||||
|
when:
|
||||||
|
event: [push, tag]
|
||||||
|
|
||||||
|
- name: release
|
||||||
|
image: plugins/github-release
|
||||||
|
settings:
|
||||||
files:
|
files:
|
||||||
- release/drone_*.tar.gz
|
- release/drone_*.tar.gz
|
||||||
- release/drone_checksums.txt
|
- release/drone_checksums.txt
|
||||||
secrets:
|
api_key:
|
||||||
- source: github_token
|
from_secret: github_token
|
||||||
target: github_release_api_key
|
when:
|
||||||
when:
|
event: tag
|
||||||
event: tag
|
|
||||||
|
1
.gitignore
vendored
1
.gitignore
vendored
@ -1,2 +1,3 @@
|
|||||||
|
drone/drone
|
||||||
release
|
release
|
||||||
.env
|
.env
|
||||||
|
6
Dockerfile.linux.ppc64le
Normal file
6
Dockerfile.linux.ppc64le
Normal file
@ -0,0 +1,6 @@
|
|||||||
|
FROM drone/ca-certs
|
||||||
|
|
||||||
|
COPY release/linux/ppc64le/drone /bin/
|
||||||
|
|
||||||
|
ENTRYPOINT ["/bin/drone"]
|
||||||
|
|
250
Gopkg.lock
generated
250
Gopkg.lock
generated
@ -1,250 +0,0 @@
|
|||||||
# This file is autogenerated, do not edit; changes may be undone by the next 'dep ensure'.
|
|
||||||
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/Microsoft/go-winio"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "7da180ee92d8bd8bb8c37fc560e673e6557c392f"
|
|
||||||
version = "v0.4.7"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/Sirupsen/logrus"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "d682213848ed68c0a260ca37d6dd5ace8423f5ba"
|
|
||||||
version = "v1.0.4"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
branch = "master"
|
|
||||||
name = "github.com/cncd/pipeline"
|
|
||||||
packages = [
|
|
||||||
"pipeline",
|
|
||||||
"pipeline/backend",
|
|
||||||
"pipeline/backend/docker",
|
|
||||||
"pipeline/frontend",
|
|
||||||
"pipeline/frontend/yaml",
|
|
||||||
"pipeline/frontend/yaml/compiler",
|
|
||||||
"pipeline/frontend/yaml/linter",
|
|
||||||
"pipeline/frontend/yaml/types",
|
|
||||||
"pipeline/interrupt",
|
|
||||||
"pipeline/multipart"
|
|
||||||
]
|
|
||||||
revision = "3a09486affc9215ba52f55b1f6e10182458d1aba"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/docker/distribution"
|
|
||||||
packages = ["reference"]
|
|
||||||
revision = "7dba427612198a11b161a27f9d40bb2dca1ccd20"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/docker/docker"
|
|
||||||
packages = [
|
|
||||||
"api/types",
|
|
||||||
"api/types/blkiodev",
|
|
||||||
"api/types/container",
|
|
||||||
"api/types/events",
|
|
||||||
"api/types/filters",
|
|
||||||
"api/types/mount",
|
|
||||||
"api/types/network",
|
|
||||||
"api/types/reference",
|
|
||||||
"api/types/registry",
|
|
||||||
"api/types/strslice",
|
|
||||||
"api/types/swarm",
|
|
||||||
"api/types/time",
|
|
||||||
"api/types/versions",
|
|
||||||
"api/types/volume",
|
|
||||||
"client",
|
|
||||||
"pkg/ioutils",
|
|
||||||
"pkg/longpath",
|
|
||||||
"pkg/random",
|
|
||||||
"pkg/stdcopy",
|
|
||||||
"pkg/stringid",
|
|
||||||
"pkg/tlsconfig",
|
|
||||||
"reference"
|
|
||||||
]
|
|
||||||
revision = "f645ffca04abf2dd6c89ac9057a1eb7d2b0ac338"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/docker/go-connections"
|
|
||||||
packages = [
|
|
||||||
"nat",
|
|
||||||
"sockets",
|
|
||||||
"tlsconfig"
|
|
||||||
]
|
|
||||||
revision = "eb315e36415380e7c2fdee175262560ff42359da"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/docker/go-units"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "f2145db703495b2e525c59662db69a7344b00bb8"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/docker/libcompose"
|
|
||||||
packages = ["yaml"]
|
|
||||||
revision = "1c4bd4542afb20db0b51afd71d9ebceaf206e2dd"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/drone/drone-go"
|
|
||||||
packages = ["drone"]
|
|
||||||
revision = "7f20e6c113d3ffa2af80401c4eba7d510c8fd875"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
branch = "master"
|
|
||||||
name = "github.com/drone/envsubst"
|
|
||||||
packages = [
|
|
||||||
".",
|
|
||||||
"parse"
|
|
||||||
]
|
|
||||||
revision = "f4d1a8ef8670afc9eea1fb95ee09a979fd2763a3"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/fatih/color"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "507f6050b8568533fb3f5504de8e5205fa62a114"
|
|
||||||
version = "v1.6.0"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
branch = "master"
|
|
||||||
name = "github.com/flynn/go-shlex"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "3f9db97f856818214da2e1057f8ad84803971cff"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/ghodss/yaml"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "0ca9ea5df5451ffdf184b4428c902747c2c11cd7"
|
|
||||||
version = "v1.0.0"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/golang/protobuf"
|
|
||||||
packages = ["proto"]
|
|
||||||
revision = "925541529c1fa6821df4e44ce2723319eb2be768"
|
|
||||||
version = "v1.0.0"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
branch = "master"
|
|
||||||
name = "github.com/google/go-jsonnet"
|
|
||||||
packages = [
|
|
||||||
".",
|
|
||||||
"ast",
|
|
||||||
"parser"
|
|
||||||
]
|
|
||||||
revision = "0274286eef945e5e24be6ebfc13a9deefdd312ee"
|
|
||||||
source = "https://github.com/drone/go-jsonnet.git"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
branch = "master"
|
|
||||||
name = "github.com/jackspirou/syscerts"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "b68f5469dff16e102bd6a2d5b3e79341c938d736"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/joho/godotenv"
|
|
||||||
packages = [
|
|
||||||
".",
|
|
||||||
"autoload"
|
|
||||||
]
|
|
||||||
revision = "a79fa1e548e2c689c241d10173efd51e5d689d5b"
|
|
||||||
version = "v1.2.0"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/mattn/go-colorable"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "167de6bfdfba052fa6b2d3664c8f5272e23c9072"
|
|
||||||
version = "v0.0.9"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/mattn/go-isatty"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "0360b2af4f38e8d38c7fce2a9f4e702702d73a39"
|
|
||||||
version = "v0.0.3"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/opencontainers/go-digest"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "279bed98673dd5bef374d3b6e4b09e2af76183bf"
|
|
||||||
version = "v1.0.0-rc1"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
branch = "master"
|
|
||||||
name = "github.com/pkg/browser"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "c90ca0c84f15f81c982e32665bffd8d7aac8f097"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/pkg/errors"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "645ef00459ed84a119197bfb8d8205042c6df63d"
|
|
||||||
version = "v0.8.0"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "github.com/urfave/cli"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "cfb38830724cc34fedffe9a2a29fb54fa9169cd1"
|
|
||||||
version = "v1.20.0"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
branch = "master"
|
|
||||||
name = "golang.org/x/crypto"
|
|
||||||
packages = ["ssh/terminal"]
|
|
||||||
revision = "650f4a345ab4e5b245a3034b110ebc7299e68186"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
branch = "master"
|
|
||||||
name = "golang.org/x/net"
|
|
||||||
packages = [
|
|
||||||
"context",
|
|
||||||
"context/ctxhttp",
|
|
||||||
"proxy"
|
|
||||||
]
|
|
||||||
revision = "f5dfe339be1d06f81b22525fe34671ee7d2c8904"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
branch = "master"
|
|
||||||
name = "golang.org/x/oauth2"
|
|
||||||
packages = [
|
|
||||||
".",
|
|
||||||
"internal"
|
|
||||||
]
|
|
||||||
revision = "543e37812f10c46c622c9575afd7ad22f22a12ba"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
branch = "master"
|
|
||||||
name = "golang.org/x/sync"
|
|
||||||
packages = ["errgroup"]
|
|
||||||
revision = "fd80eb99c8f653c847d294a001bdf2a3a6f768f5"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
branch = "master"
|
|
||||||
name = "golang.org/x/sys"
|
|
||||||
packages = [
|
|
||||||
"unix",
|
|
||||||
"windows"
|
|
||||||
]
|
|
||||||
revision = "37707fdb30a5b38865cfb95e5aab41707daec7fd"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
name = "google.golang.org/appengine"
|
|
||||||
packages = [
|
|
||||||
"internal",
|
|
||||||
"internal/base",
|
|
||||||
"internal/datastore",
|
|
||||||
"internal/log",
|
|
||||||
"internal/remote_api",
|
|
||||||
"internal/urlfetch",
|
|
||||||
"urlfetch"
|
|
||||||
]
|
|
||||||
revision = "150dc57a1b433e64154302bdc40b6bb8aefa313a"
|
|
||||||
version = "v1.0.0"
|
|
||||||
|
|
||||||
[[projects]]
|
|
||||||
branch = "v2"
|
|
||||||
name = "gopkg.in/yaml.v2"
|
|
||||||
packages = ["."]
|
|
||||||
revision = "d670f9405373e636a5a2765eea47fac0c9bc91a4"
|
|
||||||
|
|
||||||
[solve-meta]
|
|
||||||
analyzer-name = "dep"
|
|
||||||
analyzer-version = 1
|
|
||||||
inputs-digest = "3c2492a2f392e0e4d42f2247aca5631e020aed1e2dea238bb56e27739866927a"
|
|
||||||
solver-name = "gps-cdcl"
|
|
||||||
solver-version = 1
|
|
74
Gopkg.toml
74
Gopkg.toml
@ -1,74 +0,0 @@
|
|||||||
# required = ["github.com/user/thing/cmd/thing"]
|
|
||||||
# ignored = ["github.com/user/project/pkgX", "bitbucket.org/user/project/pkgA/pkgY"]
|
|
||||||
|
|
||||||
[[constraint]]
|
|
||||||
name = "github.com/cncd/pipeline"
|
|
||||||
branch = "master"
|
|
||||||
|
|
||||||
[[constraint]]
|
|
||||||
name = "github.com/drone/drone-go"
|
|
||||||
revision = "7f20e6c113d3ffa2af80401c4eba7d510c8fd875"
|
|
||||||
|
|
||||||
[[constraint]]
|
|
||||||
branch = "master"
|
|
||||||
name = "github.com/drone/envsubst"
|
|
||||||
|
|
||||||
[[constraint]]
|
|
||||||
branch = "master"
|
|
||||||
name = "github.com/jackspirou/syscerts"
|
|
||||||
|
|
||||||
[[constraint]]
|
|
||||||
name = "github.com/joho/godotenv"
|
|
||||||
version = "1.2.0"
|
|
||||||
|
|
||||||
[[constraint]]
|
|
||||||
branch = "master"
|
|
||||||
name = "github.com/pkg/browser"
|
|
||||||
|
|
||||||
[[constraint]]
|
|
||||||
name = "github.com/urfave/cli"
|
|
||||||
version = "1.20.0"
|
|
||||||
|
|
||||||
[[constraint]]
|
|
||||||
branch = "master"
|
|
||||||
name = "golang.org/x/net"
|
|
||||||
|
|
||||||
[[constraint]]
|
|
||||||
branch = "master"
|
|
||||||
name = "golang.org/x/oauth2"
|
|
||||||
|
|
||||||
[[constraint]]
|
|
||||||
branch = "master"
|
|
||||||
name = "github.com/google/go-jsonnet"
|
|
||||||
source = "https://github.com/drone/go-jsonnet.git"
|
|
||||||
|
|
||||||
#
|
|
||||||
# Some project dependencies hale from the dark ages
|
|
||||||
# of Go dependnecy management and require that we point
|
|
||||||
# to specific revisions.
|
|
||||||
#
|
|
||||||
|
|
||||||
[[override]]
|
|
||||||
name = "github.com/docker/docker"
|
|
||||||
revision = "f645ffca04abf2dd6c89ac9057a1eb7d2b0ac338"
|
|
||||||
|
|
||||||
[[override]]
|
|
||||||
name = "github.com/docker/distribution"
|
|
||||||
revision = "7dba427612198a11b161a27f9d40bb2dca1ccd20"
|
|
||||||
|
|
||||||
[[override]]
|
|
||||||
name = "github.com/docker/go-connections"
|
|
||||||
revision = "eb315e36415380e7c2fdee175262560ff42359da"
|
|
||||||
|
|
||||||
[[override]]
|
|
||||||
name = "github.com/docker/go-units"
|
|
||||||
revision = "f2145db703495b2e525c59662db69a7344b00bb8"
|
|
||||||
|
|
||||||
[[override]]
|
|
||||||
name = "github.com/docker/libcompose"
|
|
||||||
revision = "1c4bd4542afb20db0b51afd71d9ebceaf206e2dd"
|
|
||||||
|
|
||||||
[prune]
|
|
||||||
go-tests = true
|
|
||||||
unused-packages = true
|
|
||||||
non-go = true
|
|
13
README.md
13
README.md
@ -1 +1,12 @@
|
|||||||
Command line client for the Drone continuous integration server. Please see the official documentation at http://docs.drone.io/cli-installation/
|
# drone-cli
|
||||||
|
|
||||||
|
Command line client for the Drone continuous integration server.
|
||||||
|
|
||||||
|
Documentation:<br/>
|
||||||
|
https://docs.drone.io/cli
|
||||||
|
|
||||||
|
Technical Support:<br/>
|
||||||
|
https://discourse.drone.io
|
||||||
|
|
||||||
|
Bug Tracker:<br/>
|
||||||
|
https://discourse.drone.io/c/bugs
|
||||||
|
@ -4,9 +4,9 @@ import (
|
|||||||
"os"
|
"os"
|
||||||
"text/template"
|
"text/template"
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
var autoscaleVersionCmd = cli.Command{
|
var autoscaleVersionCmd = cli.Command{
|
||||||
@ -15,10 +15,9 @@ var autoscaleVersionCmd = cli.Command{
|
|||||||
Action: autoscaleVersion,
|
Action: autoscaleVersion,
|
||||||
Flags: []cli.Flag{
|
Flags: []cli.Flag{
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "format",
|
Name: "format",
|
||||||
Usage: "format output",
|
Usage: "format output",
|
||||||
Value: tmplAutoscaleVersion,
|
Value: tmplAutoscaleVersion,
|
||||||
Hidden: true,
|
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
@ -34,7 +33,7 @@ func autoscaleVersion(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format") + "\n")
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format") + "\n")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -9,14 +9,14 @@ var Command = cli.Command{
|
|||||||
Subcommands: []cli.Command{
|
Subcommands: []cli.Command{
|
||||||
buildListCmd,
|
buildListCmd,
|
||||||
buildLastCmd,
|
buildLastCmd,
|
||||||
buildLogsCmd,
|
|
||||||
buildInfoCmd,
|
buildInfoCmd,
|
||||||
|
buildCreateCmd,
|
||||||
buildStopCmd,
|
buildStopCmd,
|
||||||
buildStartCmd,
|
buildStartCmd,
|
||||||
buildApproveCmd,
|
buildApproveCmd,
|
||||||
buildDeclineCmd,
|
buildDeclineCmd,
|
||||||
|
buildPromoteCmd,
|
||||||
|
buildRollbackCmd,
|
||||||
buildQueueCmd,
|
buildQueueCmd,
|
||||||
buildKillCmd,
|
|
||||||
buildPsCmd,
|
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
@ -10,8 +10,8 @@ import (
|
|||||||
|
|
||||||
var buildApproveCmd = cli.Command{
|
var buildApproveCmd = cli.Command{
|
||||||
Name: "approve",
|
Name: "approve",
|
||||||
Usage: "approve a build",
|
Usage: "approve a build stage",
|
||||||
ArgsUsage: "<repo/name> <build>",
|
ArgsUsage: "<repo/name> <build> <stage>",
|
||||||
Action: buildApprove,
|
Action: buildApprove,
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -25,13 +25,17 @@ func buildApprove(c *cli.Context) (err error) {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
stage, err := strconv.Atoi(c.Args().Get(2))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
client, err := internal.NewClient(c)
|
client, err := internal.NewClient(c)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
_, err = client.BuildApprove(owner, name, number)
|
err = client.Approve(owner, name, number, stage)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
56
drone/build/build_create.go
Normal file
56
drone/build/build_create.go
Normal file
@ -0,0 +1,56 @@
|
|||||||
|
package build
|
||||||
|
|
||||||
|
import (
|
||||||
|
"os"
|
||||||
|
"text/template"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var buildCreateCmd = cli.Command{
|
||||||
|
Name: "create",
|
||||||
|
Usage: "create a build",
|
||||||
|
ArgsUsage: "<repo/name>",
|
||||||
|
Action: buildCreate,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "commit",
|
||||||
|
Usage: "source commit",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "branch",
|
||||||
|
Usage: "source branch",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "format output",
|
||||||
|
Value: tmplBuildInfo,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func buildCreate(c *cli.Context) (err error) {
|
||||||
|
repo := c.Args().First()
|
||||||
|
owner, name, err := internal.ParseRepo(repo)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
build, err := client.BuildCreate(owner, name, c.String("commit"), c.String("branch"))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format"))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return tmpl.Execute(os.Stdout, build)
|
||||||
|
}
|
@ -10,8 +10,8 @@ import (
|
|||||||
|
|
||||||
var buildDeclineCmd = cli.Command{
|
var buildDeclineCmd = cli.Command{
|
||||||
Name: "decline",
|
Name: "decline",
|
||||||
Usage: "decline a build",
|
Usage: "decline a build stage",
|
||||||
ArgsUsage: "<repo/name> <build>",
|
ArgsUsage: "<repo/name> <build> <stage>",
|
||||||
Action: buildDecline,
|
Action: buildDecline,
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -25,13 +25,17 @@ func buildDecline(c *cli.Context) (err error) {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
stage, err := strconv.Atoi(c.Args().Get(2))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
client, err := internal.NewClient(c)
|
client, err := internal.NewClient(c)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
_, err = client.BuildDecline(owner, name, number)
|
err = client.Decline(owner, name, number, stage)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -6,6 +6,7 @@ import (
|
|||||||
"text/template"
|
"text/template"
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
"github.com/urfave/cli"
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -43,7 +44,7 @@ func buildInfo(c *cli.Context) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
number = build.Number
|
number = int(build.Number)
|
||||||
} else {
|
} else {
|
||||||
number, err = strconv.Atoi(buildArg)
|
number, err = strconv.Atoi(buildArg)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
@ -56,7 +57,7 @@ func buildInfo(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format"))
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format"))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -67,9 +68,9 @@ func buildInfo(c *cli.Context) error {
|
|||||||
var tmplBuildInfo = `Number: {{ .Number }}
|
var tmplBuildInfo = `Number: {{ .Number }}
|
||||||
Status: {{ .Status }}
|
Status: {{ .Status }}
|
||||||
Event: {{ .Event }}
|
Event: {{ .Event }}
|
||||||
Commit: {{ .Commit }}
|
Commit: {{ .After }}
|
||||||
Branch: {{ .Branch }}
|
Branch: {{ .Target }}
|
||||||
Ref: {{ .Ref }}
|
Ref: {{ .Ref }}
|
||||||
|
Author: {{ .Author }} {{ if .AuthorEmail }}<{{.AuthorEmail}}>{{ end }}
|
||||||
Message: {{ .Message }}
|
Message: {{ .Message }}
|
||||||
Author: {{ .Author }}
|
|
||||||
`
|
`
|
||||||
|
@ -1,42 +0,0 @@
|
|||||||
package build
|
|
||||||
|
|
||||||
import (
|
|
||||||
"fmt"
|
|
||||||
"strconv"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
)
|
|
||||||
|
|
||||||
var buildKillCmd = cli.Command{
|
|
||||||
Name: "kill",
|
|
||||||
Usage: "force kill a build",
|
|
||||||
ArgsUsage: "<repo/name> <build>",
|
|
||||||
Action: buildKill,
|
|
||||||
Hidden: true,
|
|
||||||
}
|
|
||||||
|
|
||||||
func buildKill(c *cli.Context) (err error) {
|
|
||||||
repo := c.Args().First()
|
|
||||||
owner, name, err := internal.ParseRepo(repo)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
number, err := strconv.Atoi(c.Args().Get(1))
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
client, err := internal.NewClient(c)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
err = client.BuildKill(owner, name, number)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
fmt.Printf("Force killing build %s/%s#%d\n", owner, name, number)
|
|
||||||
return nil
|
|
||||||
}
|
|
@ -5,6 +5,7 @@ import (
|
|||||||
"text/template"
|
"text/template"
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
"github.com/urfave/cli"
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -44,7 +45,7 @@ func buildLast(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format"))
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format"))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -5,6 +5,8 @@ import (
|
|||||||
"text/template"
|
"text/template"
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
"github.com/urfave/cli"
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -36,6 +38,11 @@ var buildListCmd = cli.Command{
|
|||||||
Usage: "limit the list size",
|
Usage: "limit the list size",
|
||||||
Value: 25,
|
Value: 25,
|
||||||
},
|
},
|
||||||
|
cli.IntFlag{
|
||||||
|
Name: "page",
|
||||||
|
Usage: "page number",
|
||||||
|
Value: 1,
|
||||||
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -51,12 +58,12 @@ func buildList(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
builds, err := client.BuildList(owner, name)
|
builds, err := client.BuildList(owner, name, drone.ListOptions{Page: c.Int("page")})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format") + "\n")
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format") + "\n")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -71,7 +78,7 @@ func buildList(c *cli.Context) error {
|
|||||||
if count >= limit {
|
if count >= limit {
|
||||||
break
|
break
|
||||||
}
|
}
|
||||||
if branch != "" && build.Branch != branch {
|
if branch != "" && build.Target != branch {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
if event != "" && build.Event != event {
|
if event != "" && build.Event != event {
|
||||||
@ -90,9 +97,9 @@ func buildList(c *cli.Context) error {
|
|||||||
var tmplBuildList = "\x1b[33mBuild #{{ .Number }} \x1b[0m" + `
|
var tmplBuildList = "\x1b[33mBuild #{{ .Number }} \x1b[0m" + `
|
||||||
Status: {{ .Status }}
|
Status: {{ .Status }}
|
||||||
Event: {{ .Event }}
|
Event: {{ .Event }}
|
||||||
Commit: {{ .Commit }}
|
Commit: {{ .After }}
|
||||||
Branch: {{ .Branch }}
|
Branch: {{ .Target }}
|
||||||
Ref: {{ .Ref }}
|
Ref: {{ .Ref }}
|
||||||
Author: {{ .Author }} {{ if .Email }}<{{.Email}}>{{ end }}
|
Author: {{ .Author }} {{ if .AuthorEmail }}<{{.AuthorEmail}}>{{ end }}
|
||||||
Message: {{ .Message }}
|
Message: {{ .Message }}
|
||||||
`
|
`
|
||||||
|
@ -1,18 +0,0 @@
|
|||||||
package build
|
|
||||||
|
|
||||||
import (
|
|
||||||
"fmt"
|
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
)
|
|
||||||
|
|
||||||
var buildLogsCmd = cli.Command{
|
|
||||||
Name: "logs",
|
|
||||||
Usage: "show build logs",
|
|
||||||
ArgsUsage: "<repo/name> [build] [job]",
|
|
||||||
Action: buildLogs,
|
|
||||||
}
|
|
||||||
|
|
||||||
func buildLogs(c *cli.Context) error {
|
|
||||||
return fmt.Errorf("Command temporarily disabled. See https://github.com/drone/drone/issues/2005")
|
|
||||||
}
|
|
59
drone/build/build_promote.go
Normal file
59
drone/build/build_promote.go
Normal file
@ -0,0 +1,59 @@
|
|||||||
|
package build
|
||||||
|
|
||||||
|
import (
|
||||||
|
"os"
|
||||||
|
"strconv"
|
||||||
|
"text/template"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var buildPromoteCmd = cli.Command{
|
||||||
|
Name: "promote",
|
||||||
|
Usage: "promote a build",
|
||||||
|
ArgsUsage: "<repo/name> <build> <environment>",
|
||||||
|
Action: buildPromote,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringSliceFlag{
|
||||||
|
Name: "param, p",
|
||||||
|
Usage: "custom parameters to be injected into the job environment. Format: KEY=value",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "format output",
|
||||||
|
Value: tmplBuildInfo,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func buildPromote(c *cli.Context) (err error) {
|
||||||
|
repo := c.Args().First()
|
||||||
|
owner, name, err := internal.ParseRepo(repo)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
number, err := strconv.Atoi(c.Args().Get(1))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
target := c.Args().Get(2)
|
||||||
|
params := internal.ParseKeyPair(c.StringSlice("param"))
|
||||||
|
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
build, err := client.Promote(owner, name, number, target, params)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format"))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return tmpl.Execute(os.Stdout, build)
|
||||||
|
}
|
@ -1,82 +0,0 @@
|
|||||||
package build
|
|
||||||
|
|
||||||
import (
|
|
||||||
"os"
|
|
||||||
"strconv"
|
|
||||||
"text/template"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
)
|
|
||||||
|
|
||||||
var buildPsCmd = cli.Command{
|
|
||||||
Name: "ps",
|
|
||||||
Usage: "show build steps",
|
|
||||||
ArgsUsage: "<repo/name> [build]",
|
|
||||||
Action: buildPs,
|
|
||||||
Flags: []cli.Flag{
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "format",
|
|
||||||
Usage: "format output",
|
|
||||||
Value: tmplBuildPs,
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
func buildPs(c *cli.Context) error {
|
|
||||||
repo := c.Args().First()
|
|
||||||
|
|
||||||
owner, name, err := internal.ParseRepo(repo)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
client, err := internal.NewClient(c)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
buildArg := c.Args().Get(1)
|
|
||||||
var number int
|
|
||||||
|
|
||||||
if buildArg == "last" || len(buildArg) == 0 {
|
|
||||||
// Fetch the build number from the last build
|
|
||||||
build, err := client.BuildLast(owner, name, "")
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
number = build.Number
|
|
||||||
} else {
|
|
||||||
number, err = strconv.Atoi(buildArg)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
build, err := client.Build(owner, name, number)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format") + "\n")
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
for _, proc := range build.Procs {
|
|
||||||
for _, child := range proc.Children {
|
|
||||||
if err := tmpl.Execute(os.Stdout, child); err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// template for build ps information
|
|
||||||
var tmplBuildPs = "\x1b[33mProc #{{ .PID }} \x1b[0m" + `
|
|
||||||
Step: {{ .Name }}
|
|
||||||
State: {{ .State }}
|
|
||||||
`
|
|
@ -1,18 +1,18 @@
|
|||||||
package build
|
package build
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
|
||||||
"os"
|
"os"
|
||||||
"text/template"
|
"text/template"
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
"github.com/urfave/cli"
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
var buildQueueCmd = cli.Command{
|
var buildQueueCmd = cli.Command{
|
||||||
Name: "queue",
|
Name: "queue",
|
||||||
Usage: "show build queue",
|
Usage: "show build queue",
|
||||||
ArgsUsage: " ",
|
ArgsUsage: "",
|
||||||
Action: buildQueue,
|
Action: buildQueue,
|
||||||
Flags: []cli.Flag{
|
Flags: []cli.Flag{
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
@ -20,44 +20,74 @@ var buildQueueCmd = cli.Command{
|
|||||||
Usage: "format output",
|
Usage: "format output",
|
||||||
Value: tmplBuildQueue,
|
Value: tmplBuildQueue,
|
||||||
},
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "repo",
|
||||||
|
Usage: "repo filter",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "branch",
|
||||||
|
Usage: "branch filter",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "event",
|
||||||
|
Usage: "event filter",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "status",
|
||||||
|
Usage: "status filter",
|
||||||
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
func buildQueue(c *cli.Context) error {
|
func buildQueue(c *cli.Context) error {
|
||||||
|
|
||||||
client, err := internal.NewClient(c)
|
client, err := internal.NewClient(c)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
builds, err := client.BuildQueue()
|
repos, err := client.Incomplete()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
if len(builds) == 0 {
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format") + "\n")
|
||||||
fmt.Println("there are no pending or running builds")
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format") + "\n")
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
for _, build := range builds {
|
slug := c.String("repo")
|
||||||
tmpl.Execute(os.Stdout, build)
|
branch := c.String("branch")
|
||||||
|
event := c.String("event")
|
||||||
|
status := c.String("status")
|
||||||
|
|
||||||
|
for _, repo := range repos {
|
||||||
|
if slug != "" && repo.Slug != slug {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if branch != "" && repo.Build.Target != branch {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if event != "" && repo.Build.Event != event {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if status != "" && repo.Build.Status != status {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
tmpl.Execute(os.Stdout, repo)
|
||||||
}
|
}
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// template for build list information
|
// template for build queue information
|
||||||
var tmplBuildQueue = "\x1b[33m{{ .FullName }} #{{ .Number }} \x1b[0m" + `
|
var tmplBuildQueue = "\x1b[33m{{ .Slug }}#{{ .Build.Number }} \x1b[0m" + `
|
||||||
Status: {{ .Status }}
|
Name: {{ .Slug }}
|
||||||
Event: {{ .Event }}
|
Build: {{ .Build.Number }}
|
||||||
Commit: {{ .Commit }}
|
Status: {{ .Build.Status }}
|
||||||
Branch: {{ .Branch }}
|
Event: {{ .Build.Event }}
|
||||||
Ref: {{ .Ref }}
|
Branch: {{ .Build.Target }}
|
||||||
Author: {{ .Author }} {{ if .Email }}<{{.Email}}>{{ end }}
|
Ref: {{ .Build.Ref }}
|
||||||
Message: {{ .Message }}
|
Author: {{ .Build.Author }}{{ if .Build.AuthorEmail }} <{{ .Build.AuthorEmail }}>{{ end }}
|
||||||
|
Created: {{ .Build.Created | time }}
|
||||||
|
Started: {{ .Build.Started | time }}
|
||||||
|
Updated: {{ .Build.Updated | time }}
|
||||||
`
|
`
|
||||||
|
47
drone/build/build_rollback.go
Normal file
47
drone/build/build_rollback.go
Normal file
@ -0,0 +1,47 @@
|
|||||||
|
package build
|
||||||
|
|
||||||
|
import (
|
||||||
|
"strconv"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var buildRollbackCmd = cli.Command{
|
||||||
|
Name: "rollback",
|
||||||
|
Usage: "rollback a build",
|
||||||
|
ArgsUsage: "<repo/name> <build> <environment>",
|
||||||
|
Action: buildRollback,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringSliceFlag{
|
||||||
|
Name: "param, p",
|
||||||
|
Usage: "custom parameters to be injected into the job environment. Format: KEY=value",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func buildRollback(c *cli.Context) (err error) {
|
||||||
|
repo := c.Args().First()
|
||||||
|
owner, name, err := internal.ParseRepo(repo)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
number, err := strconv.Atoi(c.Args().Get(1))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
target := c.Args().Get(2)
|
||||||
|
params := internal.ParseKeyPair(c.StringSlice("param"))
|
||||||
|
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
_, err = client.Rollback(owner, name, number, target, params)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
@ -2,16 +2,18 @@ package build
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"os"
|
||||||
"strconv"
|
"strconv"
|
||||||
|
"text/template"
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
"github.com/urfave/cli"
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
var buildStartCmd = cli.Command{
|
var buildStartCmd = cli.Command{
|
||||||
Name: "start",
|
Name: "restart",
|
||||||
Usage: "start a build",
|
Usage: "restart a build",
|
||||||
ArgsUsage: "<repo/name> [build]",
|
ArgsUsage: "<repo/name> [build]",
|
||||||
Action: buildStart,
|
Action: buildStart,
|
||||||
Flags: []cli.Flag{
|
Flags: []cli.Flag{
|
||||||
@ -19,6 +21,11 @@ var buildStartCmd = cli.Command{
|
|||||||
Name: "param, p",
|
Name: "param, p",
|
||||||
Usage: "custom parameters to be injected into the job environment. Format: KEY=value",
|
Usage: "custom parameters to be injected into the job environment. Format: KEY=value",
|
||||||
},
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "format output",
|
||||||
|
Value: tmplBuildInfo,
|
||||||
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -42,7 +49,7 @@ func buildStart(c *cli.Context) (err error) {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
number = build.Number
|
number = int(build.Number)
|
||||||
} else {
|
} else {
|
||||||
if len(buildArg) == 0 {
|
if len(buildArg) == 0 {
|
||||||
return errors.New("missing job number")
|
return errors.New("missing job number")
|
||||||
@ -55,11 +62,14 @@ func buildStart(c *cli.Context) (err error) {
|
|||||||
|
|
||||||
params := internal.ParseKeyPair(c.StringSlice("param"))
|
params := internal.ParseKeyPair(c.StringSlice("param"))
|
||||||
|
|
||||||
build, err := client.BuildStart(owner, name, number, params)
|
build, err := client.BuildRestart(owner, name, number, params)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
fmt.Printf("Starting build %s/%s#%d\n", owner, name, build.Number)
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format"))
|
||||||
return nil
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return tmpl.Execute(os.Stdout, build)
|
||||||
}
|
}
|
||||||
|
@ -11,7 +11,7 @@ import (
|
|||||||
var buildStopCmd = cli.Command{
|
var buildStopCmd = cli.Command{
|
||||||
Name: "stop",
|
Name: "stop",
|
||||||
Usage: "stop a build",
|
Usage: "stop a build",
|
||||||
ArgsUsage: "<repo/name> [build] [job]",
|
ArgsUsage: "<repo/name> [build]",
|
||||||
Action: buildStop,
|
Action: buildStop,
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -25,21 +25,17 @@ func buildStop(c *cli.Context) (err error) {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
job, _ := strconv.Atoi(c.Args().Get(2))
|
|
||||||
if job == 0 {
|
|
||||||
job = 1
|
|
||||||
}
|
|
||||||
|
|
||||||
client, err := internal.NewClient(c)
|
client, err := internal.NewClient(c)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
err = client.BuildStop(owner, name, number, job)
|
err = client.BuildCancel(owner, name, number)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
fmt.Printf("Stopping build %s/%s#%d.%d\n", owner, name, number, job)
|
fmt.Printf("Stopping build %s/%s#%d\n", owner, name, number)
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
49
drone/convert/convert.go
Normal file
49
drone/convert/convert.go
Normal file
@ -0,0 +1,49 @@
|
|||||||
|
package convert
|
||||||
|
|
||||||
|
import (
|
||||||
|
"bytes"
|
||||||
|
"io"
|
||||||
|
"io/ioutil"
|
||||||
|
"os"
|
||||||
|
|
||||||
|
"github.com/drone/drone-yaml/yaml/converter"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Command exports the convert command.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "convert",
|
||||||
|
Usage: "convert legacy format",
|
||||||
|
ArgsUsage: "<source>",
|
||||||
|
Action: convert,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "save",
|
||||||
|
Usage: "save result to source",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func convert(c *cli.Context) error {
|
||||||
|
path := c.Args().First()
|
||||||
|
if path == "" {
|
||||||
|
path = ".drone.yml"
|
||||||
|
}
|
||||||
|
|
||||||
|
raw, err := ioutil.ReadFile(path)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
res, err := converter.Convert(raw, converter.Metadata{Filename: path})
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
if c.Bool("save") {
|
||||||
|
return ioutil.WriteFile(path, res, 0644)
|
||||||
|
}
|
||||||
|
|
||||||
|
_, err = io.Copy(os.Stderr, bytes.NewReader(res))
|
||||||
|
return err
|
||||||
|
}
|
16
drone/cron/cron.go
Normal file
16
drone/cron/cron.go
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
package cron
|
||||||
|
|
||||||
|
import "github.com/urfave/cli"
|
||||||
|
|
||||||
|
// Command exports the registry command set.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "cron",
|
||||||
|
Usage: "manage cron jobs",
|
||||||
|
Subcommands: []cli.Command{
|
||||||
|
cronListCmd,
|
||||||
|
cronInfoCmd,
|
||||||
|
cronCreateCmd,
|
||||||
|
cronDisableCmd,
|
||||||
|
cronEnableCmd,
|
||||||
|
},
|
||||||
|
}
|
44
drone/cron/cron_add.go
Normal file
44
drone/cron/cron_add.go
Normal file
@ -0,0 +1,44 @@
|
|||||||
|
package cron
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var cronCreateCmd = cli.Command{
|
||||||
|
Name: "add",
|
||||||
|
Usage: "adds a cronjob",
|
||||||
|
ArgsUsage: "[repo/name] [cronjob] [cronexpr]",
|
||||||
|
Action: cronCreate,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "branch",
|
||||||
|
Usage: "branch name",
|
||||||
|
Value: "master",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func cronCreate(c *cli.Context) error {
|
||||||
|
slug := c.Args().First()
|
||||||
|
owner, name, err := internal.ParseRepo(slug)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
cron := &drone.Cron{
|
||||||
|
Name: c.Args().Get(1),
|
||||||
|
Expr: c.Args().Get(2),
|
||||||
|
Branch: c.String("branch"),
|
||||||
|
}
|
||||||
|
_, err = client.CronCreate(owner, name, cron)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
39
drone/cron/cron_disable.go
Normal file
39
drone/cron/cron_disable.go
Normal file
@ -0,0 +1,39 @@
|
|||||||
|
package cron
|
||||||
|
|
||||||
|
import (
|
||||||
|
"errors"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var cronDisableCmd = cli.Command{
|
||||||
|
Name: "disable",
|
||||||
|
Usage: "disable cron jobs",
|
||||||
|
ArgsUsage: "[repo/name] [cronjob]",
|
||||||
|
Action: cronDisable,
|
||||||
|
}
|
||||||
|
|
||||||
|
func cronDisable(c *cli.Context) error {
|
||||||
|
slug := c.Args().First()
|
||||||
|
owner, name, err := internal.ParseRepo(slug)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
cron := c.Args().Get(1)
|
||||||
|
if cron == "" {
|
||||||
|
return errors.New("missing cronjob name")
|
||||||
|
}
|
||||||
|
disabled := true
|
||||||
|
in := &drone.CronPatch{
|
||||||
|
Disabled: &disabled,
|
||||||
|
}
|
||||||
|
_, err = client.CronUpdate(owner, name, cron, in)
|
||||||
|
return err
|
||||||
|
}
|
39
drone/cron/cron_enable.go
Normal file
39
drone/cron/cron_enable.go
Normal file
@ -0,0 +1,39 @@
|
|||||||
|
package cron
|
||||||
|
|
||||||
|
import (
|
||||||
|
"errors"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var cronEnableCmd = cli.Command{
|
||||||
|
Name: "enable",
|
||||||
|
Usage: "enable cron jobs",
|
||||||
|
ArgsUsage: "[repo/name] [cronjob]",
|
||||||
|
Action: cronEnable,
|
||||||
|
}
|
||||||
|
|
||||||
|
func cronEnable(c *cli.Context) error {
|
||||||
|
slug := c.Args().First()
|
||||||
|
owner, name, err := internal.ParseRepo(slug)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
cron := c.Args().Get(1)
|
||||||
|
if cron == "" {
|
||||||
|
return errors.New("missing cronjob name")
|
||||||
|
}
|
||||||
|
disabled := false
|
||||||
|
in := &drone.CronPatch{
|
||||||
|
Disabled: &disabled,
|
||||||
|
}
|
||||||
|
_, err = client.CronUpdate(owner, name, cron, in)
|
||||||
|
return err
|
||||||
|
}
|
47
drone/cron/cron_info.go
Normal file
47
drone/cron/cron_info.go
Normal file
@ -0,0 +1,47 @@
|
|||||||
|
package cron
|
||||||
|
|
||||||
|
import (
|
||||||
|
"html/template"
|
||||||
|
"os"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var cronInfoCmd = cli.Command{
|
||||||
|
Name: "info",
|
||||||
|
Usage: "display cron info",
|
||||||
|
ArgsUsage: "[repo/name]",
|
||||||
|
Action: cronInfo,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "format output",
|
||||||
|
Value: tmplCronList,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func cronInfo(c *cli.Context) error {
|
||||||
|
slug := c.Args().First()
|
||||||
|
owner, name, err := internal.ParseRepo(slug)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
cronjob := c.Args().Get(1)
|
||||||
|
cron, err := client.Cron(owner, name, cronjob)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
format := c.String("format")
|
||||||
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(format)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return tmpl.Execute(os.Stdout, cron)
|
||||||
|
}
|
59
drone/cron/cron_list.go
Normal file
59
drone/cron/cron_list.go
Normal file
@ -0,0 +1,59 @@
|
|||||||
|
package cron
|
||||||
|
|
||||||
|
import (
|
||||||
|
"html/template"
|
||||||
|
"os"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var cronListCmd = cli.Command{
|
||||||
|
Name: "ls",
|
||||||
|
Usage: "list cron jobs",
|
||||||
|
ArgsUsage: "[repo/name]",
|
||||||
|
Action: cronList,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "format output",
|
||||||
|
Value: tmplCronList,
|
||||||
|
Hidden: true,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func cronList(c *cli.Context) error {
|
||||||
|
slug := c.Args().First()
|
||||||
|
owner, name, err := internal.ParseRepo(slug)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
list, err := client.CronList(owner, name)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
format := c.String("format") + "\n"
|
||||||
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(format)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
for _, cron := range list {
|
||||||
|
tmpl.Execute(os.Stdout, cron)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// template for build list information
|
||||||
|
var tmplCronList = "\x1b[33m{{ .Name }} \x1b[0m" + `
|
||||||
|
Expr: {{ .Expr }}
|
||||||
|
Next: {{ .Next | time }}
|
||||||
|
{{- if .Disabled }}
|
||||||
|
Disabled: true
|
||||||
|
{{- end }}
|
||||||
|
`
|
@ -1,125 +0,0 @@
|
|||||||
package deploy
|
|
||||||
|
|
||||||
import (
|
|
||||||
"fmt"
|
|
||||||
"html/template"
|
|
||||||
"os"
|
|
||||||
"strconv"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
|
||||||
"github.com/drone/drone-go/drone"
|
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
)
|
|
||||||
|
|
||||||
// Command exports the deploy command.
|
|
||||||
var Command = cli.Command{
|
|
||||||
Name: "deploy",
|
|
||||||
Usage: "deploy code",
|
|
||||||
ArgsUsage: "<repo/name> <build> <environment>",
|
|
||||||
Action: deploy,
|
|
||||||
Flags: []cli.Flag{
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "format",
|
|
||||||
Usage: "format output",
|
|
||||||
Value: tmplDeployInfo,
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "branch",
|
|
||||||
Usage: "branch filter",
|
|
||||||
Value: "master",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "event",
|
|
||||||
Usage: "event filter",
|
|
||||||
Value: drone.EventPush,
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "status",
|
|
||||||
Usage: "status filter",
|
|
||||||
Value: drone.StatusSuccess,
|
|
||||||
},
|
|
||||||
cli.StringSliceFlag{
|
|
||||||
Name: "param, p",
|
|
||||||
Usage: "custom parameters to be injected into the job environment. Format: KEY=value",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
func deploy(c *cli.Context) error {
|
|
||||||
repo := c.Args().First()
|
|
||||||
owner, name, err := internal.ParseRepo(repo)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
client, err := internal.NewClient(c)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
branch := c.String("branch")
|
|
||||||
event := c.String("event")
|
|
||||||
status := c.String("status")
|
|
||||||
|
|
||||||
buildArg := c.Args().Get(1)
|
|
||||||
var number int
|
|
||||||
if buildArg == "last" {
|
|
||||||
// Fetch the build number from the last build
|
|
||||||
builds, berr := client.BuildList(owner, name)
|
|
||||||
if berr != nil {
|
|
||||||
return berr
|
|
||||||
}
|
|
||||||
for _, build := range builds {
|
|
||||||
if branch != "" && build.Branch != branch {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
if event != "" && build.Event != event {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
if status != "" && build.Status != status {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
if build.Number > number {
|
|
||||||
number = build.Number
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if number == 0 {
|
|
||||||
return fmt.Errorf("Cannot deploy failure build")
|
|
||||||
}
|
|
||||||
} else {
|
|
||||||
number, err = strconv.Atoi(buildArg)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
env := c.Args().Get(2)
|
|
||||||
if env == "" {
|
|
||||||
return fmt.Errorf("Please specify the target environment (ie production)")
|
|
||||||
}
|
|
||||||
|
|
||||||
params := internal.ParseKeyPair(c.StringSlice("param"))
|
|
||||||
|
|
||||||
deploy, err := client.Deploy(owner, name, number, env, params)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format"))
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
return tmpl.Execute(os.Stdout, deploy)
|
|
||||||
}
|
|
||||||
|
|
||||||
// template for deployment information
|
|
||||||
var tmplDeployInfo = `Number: {{ .Number }}
|
|
||||||
Status: {{ .Status }}
|
|
||||||
Commit: {{ .Commit }}
|
|
||||||
Branch: {{ .Branch }}
|
|
||||||
Ref: {{ .Ref }}
|
|
||||||
Message: {{ .Message }}
|
|
||||||
Author: {{ .Author }}
|
|
||||||
Target: {{ .Deploy }}
|
|
||||||
`
|
|
65
drone/encrypt/encrypt.go
Normal file
65
drone/encrypt/encrypt.go
Normal file
@ -0,0 +1,65 @@
|
|||||||
|
package encrypt
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"io/ioutil"
|
||||||
|
"strings"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Command is an encryption cli.Command
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "encrypt",
|
||||||
|
Usage: "encrypt a secret",
|
||||||
|
ArgsUsage: "<repo/name> <string>",
|
||||||
|
Action: encryptSecret,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "allow-pull-request",
|
||||||
|
Usage: "permit read access to pull requests",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "allow-push-on-pull-request",
|
||||||
|
Usage: "permit write access to pull requests (e.g. allow docker push)",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func encryptSecret(c *cli.Context) error {
|
||||||
|
repo := c.Args().First()
|
||||||
|
owner, name, err := internal.ParseRepo(repo)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
plaintext := c.Args().Get(1)
|
||||||
|
if strings.HasPrefix(plaintext, "@") {
|
||||||
|
path := strings.TrimPrefix(plaintext, "@")
|
||||||
|
data, err := ioutil.ReadFile(path)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
plaintext = string(data)
|
||||||
|
}
|
||||||
|
|
||||||
|
secret := &drone.Secret{
|
||||||
|
Data: plaintext,
|
||||||
|
PullRequest: c.Bool("allow-pull-request"),
|
||||||
|
PullRequestPush: c.Bool("allow-push-on-pull-request"),
|
||||||
|
}
|
||||||
|
encrypted, err := client.Encrypt(owner, name, secret)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
fmt.Println(encrypted)
|
||||||
|
return nil
|
||||||
|
}
|
77
drone/encrypt/registry.go
Normal file
77
drone/encrypt/registry.go
Normal file
@ -0,0 +1,77 @@
|
|||||||
|
package encrypt
|
||||||
|
|
||||||
|
// import (
|
||||||
|
// "fmt"
|
||||||
|
// "io/ioutil"
|
||||||
|
// "strings"
|
||||||
|
|
||||||
|
// "github.com/drone/drone-cli/drone/internal"
|
||||||
|
// "github.com/drone/drone-go/drone"
|
||||||
|
|
||||||
|
// "github.com/urfave/cli"
|
||||||
|
// )
|
||||||
|
|
||||||
|
// var encryptRegistryCommand = cli.Command{
|
||||||
|
// Name: "registry",
|
||||||
|
// Usage: "encrypt registry credentials",
|
||||||
|
// ArgsUsage: "<repo/name> <string>",
|
||||||
|
// Action: encryptRegistry,
|
||||||
|
// Flags: []cli.Flag{
|
||||||
|
// cli.StringFlag{
|
||||||
|
// Name: "username",
|
||||||
|
// Usage: "registry username",
|
||||||
|
// },
|
||||||
|
// cli.StringFlag{
|
||||||
|
// Name: "password",
|
||||||
|
// Usage: "registry password",
|
||||||
|
// },
|
||||||
|
// cli.StringFlag{
|
||||||
|
// Name: "server",
|
||||||
|
// Usage: "registry server",
|
||||||
|
// Value: "docker.io",
|
||||||
|
// },
|
||||||
|
// },
|
||||||
|
// }
|
||||||
|
|
||||||
|
// func encryptRegistry(c *cli.Context) error {
|
||||||
|
// repo := c.Args().First()
|
||||||
|
// owner, name, err := internal.ParseRepo(repo)
|
||||||
|
// if err != nil {
|
||||||
|
// return err
|
||||||
|
// }
|
||||||
|
|
||||||
|
// client, err := internal.NewClient(c)
|
||||||
|
// if err != nil {
|
||||||
|
// return err
|
||||||
|
// }
|
||||||
|
|
||||||
|
// password := c.String("password")
|
||||||
|
// if strings.HasPrefix(password, "@") {
|
||||||
|
// data, err := ioutil.ReadFile(password)
|
||||||
|
// if err != nil {
|
||||||
|
// return err
|
||||||
|
// }
|
||||||
|
// password = string(data)
|
||||||
|
// }
|
||||||
|
|
||||||
|
// policy := "pull"
|
||||||
|
// switch {
|
||||||
|
// case c.Bool("push"):
|
||||||
|
// policy = "push"
|
||||||
|
// case c.Bool("push-pull-request"):
|
||||||
|
// policy = "push-pull-request"
|
||||||
|
// }
|
||||||
|
|
||||||
|
// registry := &drone.Registry{
|
||||||
|
// Address: c.String("server"),
|
||||||
|
// Username: c.String("username"),
|
||||||
|
// Password: password,
|
||||||
|
// Policy: policy,
|
||||||
|
// }
|
||||||
|
// encrypted, err := client.EncryptRegistry(owner, name, registry)
|
||||||
|
// if err != nil {
|
||||||
|
// return err
|
||||||
|
// }
|
||||||
|
// fmt.Println(encrypted)
|
||||||
|
// return nil
|
||||||
|
// }
|
493
drone/exec/_backup/exec.go
Normal file
493
drone/exec/_backup/exec.go
Normal file
@ -0,0 +1,493 @@
|
|||||||
|
package exec
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"io"
|
||||||
|
"log"
|
||||||
|
"os"
|
||||||
|
"path"
|
||||||
|
"path/filepath"
|
||||||
|
"runtime"
|
||||||
|
"strings"
|
||||||
|
"time"
|
||||||
|
|
||||||
|
"github.com/cncd/pipeline/pipeline"
|
||||||
|
"github.com/cncd/pipeline/pipeline/backend"
|
||||||
|
"github.com/cncd/pipeline/pipeline/backend/docker"
|
||||||
|
"github.com/cncd/pipeline/pipeline/frontend"
|
||||||
|
"github.com/cncd/pipeline/pipeline/frontend/yaml"
|
||||||
|
"github.com/cncd/pipeline/pipeline/frontend/yaml/compiler"
|
||||||
|
"github.com/cncd/pipeline/pipeline/frontend/yaml/linter"
|
||||||
|
"github.com/cncd/pipeline/pipeline/interrupt"
|
||||||
|
"github.com/cncd/pipeline/pipeline/multipart"
|
||||||
|
"github.com/drone/envsubst"
|
||||||
|
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Command exports the exec command.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "exec",
|
||||||
|
Usage: "execute a local build",
|
||||||
|
ArgsUsage: "[path/to/.drone.yml]",
|
||||||
|
Action: func(c *cli.Context) {
|
||||||
|
if err := exec(c); err != nil {
|
||||||
|
log.Fatalln(err)
|
||||||
|
}
|
||||||
|
},
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.BoolTFlag{
|
||||||
|
Name: "local",
|
||||||
|
Usage: "build from local directory",
|
||||||
|
EnvVar: "DRONE_LOCAL",
|
||||||
|
},
|
||||||
|
cli.DurationFlag{
|
||||||
|
Name: "timeout",
|
||||||
|
Usage: "build timeout",
|
||||||
|
Value: time.Hour,
|
||||||
|
EnvVar: "DRONE_TIMEOUT",
|
||||||
|
},
|
||||||
|
cli.StringSliceFlag{
|
||||||
|
Name: "volumes",
|
||||||
|
Usage: "build volumes",
|
||||||
|
EnvVar: "DRONE_VOLUMES",
|
||||||
|
},
|
||||||
|
cli.StringSliceFlag{
|
||||||
|
Name: "network",
|
||||||
|
Usage: "external networks",
|
||||||
|
EnvVar: "DRONE_NETWORKS",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "prefix",
|
||||||
|
Value: "drone",
|
||||||
|
Usage: "prefix containers created by drone",
|
||||||
|
EnvVar: "DRONE_DOCKER_PREFIX",
|
||||||
|
Hidden: true,
|
||||||
|
},
|
||||||
|
cli.StringSliceFlag{
|
||||||
|
Name: "privileged",
|
||||||
|
Usage: "privileged plugins",
|
||||||
|
Value: &cli.StringSlice{
|
||||||
|
"plugins/docker",
|
||||||
|
"plugins/acr",
|
||||||
|
"plugins/ecr",
|
||||||
|
"plugins/gcr",
|
||||||
|
"plugins/heroku",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
|
||||||
|
//
|
||||||
|
// workspace default
|
||||||
|
//
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "workspace-base",
|
||||||
|
Value: "/drone",
|
||||||
|
EnvVar: "DRONE_WORKSPACE_BASE",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "workspace-path",
|
||||||
|
Value: "src",
|
||||||
|
EnvVar: "DRONE_WORKSPACE_PATH",
|
||||||
|
},
|
||||||
|
//
|
||||||
|
// netrc parameters
|
||||||
|
//
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "netrc-username",
|
||||||
|
EnvVar: "DRONE_NETRC_USERNAME",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "netrc-password",
|
||||||
|
EnvVar: "DRONE_NETRC_PASSWORD",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "netrc-machine",
|
||||||
|
EnvVar: "DRONE_NETRC_MACHINE",
|
||||||
|
},
|
||||||
|
//
|
||||||
|
// metadata parameters
|
||||||
|
//
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "system-arch",
|
||||||
|
Value: "linux/amd64",
|
||||||
|
EnvVar: "DRONE_SYSTEM_ARCH",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "system-name",
|
||||||
|
Value: "pipec",
|
||||||
|
EnvVar: "DRONE_SYSTEM_NAME",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "system-link",
|
||||||
|
Value: "https://github.com/cncd/pipec",
|
||||||
|
EnvVar: "DRONE_SYSTEM_LINK",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "repo-name",
|
||||||
|
EnvVar: "DRONE_REPO_NAME",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "repo-link",
|
||||||
|
EnvVar: "DRONE_REPO_LINK",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "repo-remote-url",
|
||||||
|
EnvVar: "DRONE_REPO_REMOTE",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "repo-private",
|
||||||
|
EnvVar: "DRONE_REPO_PRIVATE",
|
||||||
|
},
|
||||||
|
cli.IntFlag{
|
||||||
|
Name: "build-number",
|
||||||
|
EnvVar: "DRONE_BUILD_NUMBER",
|
||||||
|
},
|
||||||
|
cli.IntFlag{
|
||||||
|
Name: "parent-build-number",
|
||||||
|
EnvVar: "DRONE_PARENT_BUILD_NUMBER",
|
||||||
|
},
|
||||||
|
cli.Int64Flag{
|
||||||
|
Name: "build-created",
|
||||||
|
EnvVar: "DRONE_BUILD_CREATED",
|
||||||
|
},
|
||||||
|
cli.Int64Flag{
|
||||||
|
Name: "build-started",
|
||||||
|
EnvVar: "DRONE_BUILD_STARTED",
|
||||||
|
},
|
||||||
|
cli.Int64Flag{
|
||||||
|
Name: "build-finished",
|
||||||
|
EnvVar: "DRONE_BUILD_FINISHED",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "build-status",
|
||||||
|
EnvVar: "DRONE_BUILD_STATUS",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "build-event",
|
||||||
|
EnvVar: "DRONE_BUILD_EVENT",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "build-link",
|
||||||
|
EnvVar: "DRONE_BUILD_LINK",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "build-target",
|
||||||
|
EnvVar: "DRONE_BUILD_TARGET",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "commit-sha",
|
||||||
|
EnvVar: "DRONE_COMMIT_SHA",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "commit-ref",
|
||||||
|
EnvVar: "DRONE_COMMIT_REF",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "commit-refspec",
|
||||||
|
EnvVar: "DRONE_COMMIT_REFSPEC",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "commit-branch",
|
||||||
|
EnvVar: "DRONE_COMMIT_BRANCH",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "commit-message",
|
||||||
|
EnvVar: "DRONE_COMMIT_MESSAGE",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "commit-author-name",
|
||||||
|
EnvVar: "DRONE_COMMIT_AUTHOR_NAME",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "commit-author-avatar",
|
||||||
|
EnvVar: "DRONE_COMMIT_AUTHOR_AVATAR",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "commit-author-email",
|
||||||
|
EnvVar: "DRONE_COMMIT_AUTHOR_EMAIL",
|
||||||
|
},
|
||||||
|
cli.IntFlag{
|
||||||
|
Name: "prev-build-number",
|
||||||
|
EnvVar: "DRONE_PREV_BUILD_NUMBER",
|
||||||
|
},
|
||||||
|
cli.Int64Flag{
|
||||||
|
Name: "prev-build-created",
|
||||||
|
EnvVar: "DRONE_PREV_BUILD_CREATED",
|
||||||
|
},
|
||||||
|
cli.Int64Flag{
|
||||||
|
Name: "prev-build-started",
|
||||||
|
EnvVar: "DRONE_PREV_BUILD_STARTED",
|
||||||
|
},
|
||||||
|
cli.Int64Flag{
|
||||||
|
Name: "prev-build-finished",
|
||||||
|
EnvVar: "DRONE_PREV_BUILD_FINISHED",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "prev-build-status",
|
||||||
|
EnvVar: "DRONE_PREV_BUILD_STATUS",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "prev-build-event",
|
||||||
|
EnvVar: "DRONE_PREV_BUILD_EVENT",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "prev-build-link",
|
||||||
|
EnvVar: "DRONE_PREV_BUILD_LINK",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "prev-commit-sha",
|
||||||
|
EnvVar: "DRONE_PREV_COMMIT_SHA",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "prev-commit-ref",
|
||||||
|
EnvVar: "DRONE_PREV_COMMIT_REF",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "prev-commit-refspec",
|
||||||
|
EnvVar: "DRONE_PREV_COMMIT_REFSPEC",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "prev-commit-branch",
|
||||||
|
EnvVar: "DRONE_PREV_COMMIT_BRANCH",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "prev-commit-message",
|
||||||
|
EnvVar: "DRONE_PREV_COMMIT_MESSAGE",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "prev-commit-author-name",
|
||||||
|
EnvVar: "DRONE_PREV_COMMIT_AUTHOR_NAME",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "prev-commit-author-avatar",
|
||||||
|
EnvVar: "DRONE_PREV_COMMIT_AUTHOR_AVATAR",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "prev-commit-author-email",
|
||||||
|
EnvVar: "DRONE_PREV_COMMIT_AUTHOR_EMAIL",
|
||||||
|
},
|
||||||
|
cli.IntFlag{
|
||||||
|
Name: "job-number",
|
||||||
|
EnvVar: "DRONE_JOB_NUMBER",
|
||||||
|
},
|
||||||
|
cli.StringSliceFlag{
|
||||||
|
Name: "env, e",
|
||||||
|
EnvVar: "DRONE_ENV",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func exec(c *cli.Context) error {
|
||||||
|
file := c.Args().First()
|
||||||
|
if file == "" {
|
||||||
|
file = ".drone.yml"
|
||||||
|
}
|
||||||
|
|
||||||
|
metadata := metadataFromContext(c)
|
||||||
|
environ := metadata.Environ()
|
||||||
|
secrets := []compiler.Secret{}
|
||||||
|
for k, v := range metadata.EnvironDrone() {
|
||||||
|
environ[k] = v
|
||||||
|
}
|
||||||
|
for key, val := range metadata.Job.Matrix {
|
||||||
|
environ[key] = val
|
||||||
|
secrets = append(secrets, compiler.Secret{
|
||||||
|
Name: key,
|
||||||
|
Value: val,
|
||||||
|
})
|
||||||
|
}
|
||||||
|
|
||||||
|
droneEnv := make(map[string]string)
|
||||||
|
for _, env := range c.StringSlice("env") {
|
||||||
|
envs := strings.SplitN(env, "=", 2)
|
||||||
|
droneEnv[envs[0]] = envs[1]
|
||||||
|
}
|
||||||
|
|
||||||
|
tmpl, err := envsubst.ParseFile(file)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
confstr, err := tmpl.Execute(func(name string) string {
|
||||||
|
return environ[name]
|
||||||
|
})
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
conf, err := yaml.ParseString(confstr)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
// configure volumes for local execution
|
||||||
|
volumes := c.StringSlice("volumes")
|
||||||
|
if c.Bool("local") {
|
||||||
|
var (
|
||||||
|
workspaceBase = conf.Workspace.Base
|
||||||
|
workspacePath = conf.Workspace.Path
|
||||||
|
)
|
||||||
|
if workspaceBase == "" {
|
||||||
|
workspaceBase = c.String("workspace-base")
|
||||||
|
}
|
||||||
|
if workspacePath == "" {
|
||||||
|
workspacePath = c.String("workspace-path")
|
||||||
|
}
|
||||||
|
dir, _ := filepath.Abs(filepath.Dir(file))
|
||||||
|
|
||||||
|
if runtime.GOOS == "windows" {
|
||||||
|
dir = convertPathForWindows(dir)
|
||||||
|
}
|
||||||
|
volumes = append(volumes, c.String("prefix")+"_default:"+workspaceBase)
|
||||||
|
volumes = append(volumes, dir+":"+path.Join(workspaceBase, workspacePath))
|
||||||
|
}
|
||||||
|
|
||||||
|
// lint the yaml file
|
||||||
|
if lerr := linter.New(linter.WithTrusted(true)).Lint(conf); lerr != nil {
|
||||||
|
return lerr
|
||||||
|
}
|
||||||
|
|
||||||
|
// compiles the yaml file
|
||||||
|
compiled := compiler.New(
|
||||||
|
compiler.WithEscalated(
|
||||||
|
c.StringSlice("privileged")...,
|
||||||
|
),
|
||||||
|
compiler.WithVolumes(volumes...),
|
||||||
|
compiler.WithWorkspace(
|
||||||
|
c.String("workspace-base"),
|
||||||
|
c.String("workspace-path"),
|
||||||
|
),
|
||||||
|
compiler.WithNetworks(
|
||||||
|
c.StringSlice("network")...,
|
||||||
|
),
|
||||||
|
compiler.WithPrefix(
|
||||||
|
c.String("prefix"),
|
||||||
|
),
|
||||||
|
compiler.WithProxy(),
|
||||||
|
compiler.WithLocal(
|
||||||
|
c.Bool("local"),
|
||||||
|
),
|
||||||
|
compiler.WithNetrc(
|
||||||
|
c.String("netrc-username"),
|
||||||
|
c.String("netrc-password"),
|
||||||
|
c.String("netrc-machine"),
|
||||||
|
),
|
||||||
|
compiler.WithMetadata(metadata),
|
||||||
|
compiler.WithSecret(secrets...),
|
||||||
|
compiler.WithEnviron(droneEnv),
|
||||||
|
).Compile(conf)
|
||||||
|
|
||||||
|
engine, err := docker.NewEnv()
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
ctx, cancel := context.WithTimeout(context.Background(), c.Duration("timeout"))
|
||||||
|
defer cancel()
|
||||||
|
ctx = interrupt.WithContext(ctx)
|
||||||
|
|
||||||
|
return pipeline.New(compiled,
|
||||||
|
pipeline.WithContext(ctx),
|
||||||
|
pipeline.WithTracer(pipeline.DefaultTracer),
|
||||||
|
pipeline.WithLogger(defaultLogger),
|
||||||
|
pipeline.WithEngine(engine),
|
||||||
|
).Run()
|
||||||
|
}
|
||||||
|
|
||||||
|
// return the metadata from the cli context.
|
||||||
|
func metadataFromContext(c *cli.Context) frontend.Metadata {
|
||||||
|
return frontend.Metadata{
|
||||||
|
Repo: frontend.Repo{
|
||||||
|
Name: c.String("repo-name"),
|
||||||
|
Link: c.String("repo-link"),
|
||||||
|
Remote: c.String("repo-remote-url"),
|
||||||
|
Private: c.Bool("repo-private"),
|
||||||
|
},
|
||||||
|
Curr: frontend.Build{
|
||||||
|
Number: c.Int("build-number"),
|
||||||
|
Parent: c.Int("parent-build-number"),
|
||||||
|
Created: c.Int64("build-created"),
|
||||||
|
Started: c.Int64("build-started"),
|
||||||
|
Finished: c.Int64("build-finished"),
|
||||||
|
Status: c.String("build-status"),
|
||||||
|
Event: c.String("build-event"),
|
||||||
|
Link: c.String("build-link"),
|
||||||
|
Target: c.String("build-target"),
|
||||||
|
Commit: frontend.Commit{
|
||||||
|
Sha: c.String("commit-sha"),
|
||||||
|
Ref: c.String("commit-ref"),
|
||||||
|
Refspec: c.String("commit-refspec"),
|
||||||
|
Branch: c.String("commit-branch"),
|
||||||
|
Message: c.String("commit-message"),
|
||||||
|
Author: frontend.Author{
|
||||||
|
Name: c.String("commit-author-name"),
|
||||||
|
Email: c.String("commit-author-email"),
|
||||||
|
Avatar: c.String("commit-author-avatar"),
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
Prev: frontend.Build{
|
||||||
|
Number: c.Int("prev-build-number"),
|
||||||
|
Created: c.Int64("prev-build-created"),
|
||||||
|
Started: c.Int64("prev-build-started"),
|
||||||
|
Finished: c.Int64("prev-build-finished"),
|
||||||
|
Status: c.String("prev-build-status"),
|
||||||
|
Event: c.String("prev-build-event"),
|
||||||
|
Link: c.String("prev-build-link"),
|
||||||
|
Commit: frontend.Commit{
|
||||||
|
Sha: c.String("prev-commit-sha"),
|
||||||
|
Ref: c.String("prev-commit-ref"),
|
||||||
|
Refspec: c.String("prev-commit-refspec"),
|
||||||
|
Branch: c.String("prev-commit-branch"),
|
||||||
|
Message: c.String("prev-commit-message"),
|
||||||
|
Author: frontend.Author{
|
||||||
|
Name: c.String("prev-commit-author-name"),
|
||||||
|
Email: c.String("prev-commit-author-email"),
|
||||||
|
Avatar: c.String("prev-commit-author-avatar"),
|
||||||
|
},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
Job: frontend.Job{
|
||||||
|
Number: c.Int("job-number"),
|
||||||
|
Matrix: availableEnvironment(),
|
||||||
|
},
|
||||||
|
Sys: frontend.System{
|
||||||
|
Name: c.String("system-name"),
|
||||||
|
Link: c.String("system-link"),
|
||||||
|
Arch: c.String("system-arch"),
|
||||||
|
},
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
func availableEnvironment() map[string]string {
|
||||||
|
result := make(map[string]string, 0)
|
||||||
|
|
||||||
|
for _, env := range os.Environ() {
|
||||||
|
pair := strings.SplitN(env, "=", 2)
|
||||||
|
result[pair[0]] = pair[1]
|
||||||
|
}
|
||||||
|
|
||||||
|
return result
|
||||||
|
}
|
||||||
|
|
||||||
|
func convertPathForWindows(path string) string {
|
||||||
|
base := filepath.VolumeName(path)
|
||||||
|
if len(base) == 2 {
|
||||||
|
path = strings.TrimPrefix(path, base)
|
||||||
|
base = strings.ToLower(strings.TrimSuffix(base, ":"))
|
||||||
|
return "/" + base + filepath.ToSlash(path)
|
||||||
|
}
|
||||||
|
|
||||||
|
return filepath.ToSlash(path)
|
||||||
|
}
|
||||||
|
|
||||||
|
var defaultLogger = pipeline.LogFunc(func(proc *backend.Step, rc multipart.Reader) error {
|
||||||
|
part, err := rc.NextPart()
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
logstream := NewLineWriter(proc.Alias)
|
||||||
|
io.Copy(logstream, part)
|
||||||
|
|
||||||
|
return nil
|
||||||
|
})
|
73
drone/exec/env.go
Normal file
73
drone/exec/env.go
Normal file
@ -0,0 +1,73 @@
|
|||||||
|
package exec
|
||||||
|
|
||||||
|
import (
|
||||||
|
"os"
|
||||||
|
"strings"
|
||||||
|
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
func getEnv(c *cli.Context) map[string]string {
|
||||||
|
env := prefixedEnviron(
|
||||||
|
os.Environ(),
|
||||||
|
)
|
||||||
|
if c.IsSet("branch") {
|
||||||
|
v := c.String("branch")
|
||||||
|
env["DRONE_BRANCH"] = v
|
||||||
|
env["DRONE_COMMIT_BRANCH"] = v
|
||||||
|
env["DRONE_TARGET_BRANCH"] = v
|
||||||
|
}
|
||||||
|
if c.IsSet("event") {
|
||||||
|
v := c.String("event")
|
||||||
|
env["DRONE_EVENT"] = v
|
||||||
|
}
|
||||||
|
if c.IsSet("instance") {
|
||||||
|
v := c.String("instance")
|
||||||
|
env["DRONE_SYSTEM_HOST"] = v
|
||||||
|
env["DRONE_SYSTEM_HOSTNAME"] = v
|
||||||
|
}
|
||||||
|
if c.IsSet("ref") {
|
||||||
|
v := c.String("ref")
|
||||||
|
env["DRONE_COMMIT_REF"] = v
|
||||||
|
}
|
||||||
|
if c.IsSet("repo") {
|
||||||
|
v := c.String("repo")
|
||||||
|
env["DRONE_REPO"] = v
|
||||||
|
}
|
||||||
|
if c.IsSet("deploy-to") {
|
||||||
|
v := c.String("deploy-to")
|
||||||
|
env["DRONE_DEPLOY_TO"] = v
|
||||||
|
}
|
||||||
|
return env
|
||||||
|
}
|
||||||
|
|
||||||
|
// helper function returns all environment variables
|
||||||
|
// prefixed with DRONE_.
|
||||||
|
func prefixedEnviron(environ []string) map[string]string {
|
||||||
|
envs := map[string]string{}
|
||||||
|
for _, env := range environ {
|
||||||
|
if !strings.HasPrefix(env, "DRONE_") {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
parts := strings.SplitN(env, "=", 2)
|
||||||
|
if len(parts) != 2 {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
key := parts[0]
|
||||||
|
val := parts[1]
|
||||||
|
envs[key] = val
|
||||||
|
}
|
||||||
|
return envs
|
||||||
|
}
|
||||||
|
|
||||||
|
// helper function combines one or more maps of environment
|
||||||
|
// variables into a single map.
|
||||||
|
func combineEnviron(env ...map[string]string) map[string]string {
|
||||||
|
c := map[string]string{}
|
||||||
|
for _, e := range env {
|
||||||
|
for k, v := range e {
|
||||||
|
c[k] = v
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return c
|
||||||
|
}
|
@ -2,29 +2,35 @@ package exec
|
|||||||
|
|
||||||
import (
|
import (
|
||||||
"context"
|
"context"
|
||||||
"io"
|
"errors"
|
||||||
|
"io/ioutil"
|
||||||
"log"
|
"log"
|
||||||
|
"net/url"
|
||||||
"os"
|
"os"
|
||||||
"path"
|
"strconv"
|
||||||
"path/filepath"
|
|
||||||
"runtime"
|
|
||||||
"strings"
|
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/cncd/pipeline/pipeline"
|
|
||||||
"github.com/cncd/pipeline/pipeline/backend"
|
|
||||||
"github.com/cncd/pipeline/pipeline/backend/docker"
|
|
||||||
"github.com/cncd/pipeline/pipeline/frontend"
|
|
||||||
"github.com/cncd/pipeline/pipeline/frontend/yaml"
|
|
||||||
"github.com/cncd/pipeline/pipeline/frontend/yaml/compiler"
|
|
||||||
"github.com/cncd/pipeline/pipeline/frontend/yaml/linter"
|
|
||||||
"github.com/cncd/pipeline/pipeline/interrupt"
|
|
||||||
"github.com/cncd/pipeline/pipeline/multipart"
|
|
||||||
"github.com/drone/envsubst"
|
"github.com/drone/envsubst"
|
||||||
|
|
||||||
|
"github.com/drone/drone-runtime/engine"
|
||||||
|
"github.com/drone/drone-runtime/engine/docker"
|
||||||
|
"github.com/drone/drone-runtime/runtime"
|
||||||
|
"github.com/drone/drone-runtime/runtime/term"
|
||||||
|
"github.com/drone/drone-yaml/yaml"
|
||||||
|
"github.com/drone/drone-yaml/yaml/compiler"
|
||||||
|
"github.com/drone/drone-yaml/yaml/compiler/transform"
|
||||||
|
"github.com/drone/drone-yaml/yaml/converter"
|
||||||
|
"github.com/drone/drone-yaml/yaml/linter"
|
||||||
|
"github.com/drone/signal"
|
||||||
|
|
||||||
|
"github.com/joho/godotenv"
|
||||||
|
"github.com/mattn/go-colorable"
|
||||||
|
"github.com/mattn/go-isatty"
|
||||||
"github.com/urfave/cli"
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
var tty = isatty.IsTerminal(os.Stdout.Fd())
|
||||||
|
|
||||||
// Command exports the exec command.
|
// Command exports the exec command.
|
||||||
var Command = cli.Command{
|
var Command = cli.Command{
|
||||||
Name: "exec",
|
Name: "exec",
|
||||||
@ -36,247 +42,107 @@ var Command = cli.Command{
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
Flags: []cli.Flag{
|
Flags: []cli.Flag{
|
||||||
cli.BoolTFlag{
|
cli.StringFlag{
|
||||||
Name: "local",
|
Name: "pipeline",
|
||||||
Usage: "build from local directory",
|
Usage: "Name of the pipeline to execute",
|
||||||
EnvVar: "DRONE_LOCAL",
|
|
||||||
},
|
|
||||||
cli.DurationFlag{
|
|
||||||
Name: "timeout",
|
|
||||||
Usage: "build timeout",
|
|
||||||
Value: time.Hour,
|
|
||||||
EnvVar: "DRONE_TIMEOUT",
|
|
||||||
},
|
},
|
||||||
cli.StringSliceFlag{
|
cli.StringSliceFlag{
|
||||||
Name: "volumes",
|
Name: "include",
|
||||||
Usage: "build volumes",
|
Usage: "Name of steps to include",
|
||||||
EnvVar: "DRONE_VOLUMES",
|
|
||||||
},
|
},
|
||||||
cli.StringSliceFlag{
|
cli.StringSliceFlag{
|
||||||
Name: "network",
|
Name: "exclude",
|
||||||
Usage: "external networks",
|
Usage: "Name of steps to exclude",
|
||||||
EnvVar: "DRONE_NETWORKS",
|
|
||||||
},
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "prefix",
|
Name: "resume-at",
|
||||||
Value: "drone",
|
Usage: "Name of start to resume at",
|
||||||
Usage: "prefix containers created by drone",
|
},
|
||||||
EnvVar: "DRONE_DOCKER_PREFIX",
|
cli.BoolFlag{
|
||||||
Hidden: true,
|
Name: "clone",
|
||||||
|
Usage: "enable the clone step",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "trusted",
|
||||||
|
Usage: "build is trusted",
|
||||||
|
},
|
||||||
|
cli.DurationFlag{
|
||||||
|
Name: "timeout",
|
||||||
|
Usage: "build timeout",
|
||||||
|
Value: time.Hour,
|
||||||
|
},
|
||||||
|
cli.StringSliceFlag{
|
||||||
|
Name: "volume",
|
||||||
|
Usage: "build volumes",
|
||||||
|
},
|
||||||
|
cli.StringSliceFlag{
|
||||||
|
Name: "network",
|
||||||
|
Usage: "external networks",
|
||||||
|
},
|
||||||
|
cli.StringSliceFlag{
|
||||||
|
Name: "registry",
|
||||||
|
Usage: "registry",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "secret-file",
|
||||||
|
Usage: "secret file, define values that can be used with from_secret",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "env-file",
|
||||||
|
Usage: "env file",
|
||||||
},
|
},
|
||||||
cli.StringSliceFlag{
|
cli.StringSliceFlag{
|
||||||
Name: "privileged",
|
Name: "privileged",
|
||||||
Usage: "privileged plugins",
|
Usage: "privileged plugins",
|
||||||
Value: &cli.StringSlice{
|
Value: &cli.StringSlice{
|
||||||
"plugins/docker",
|
"plugins/docker",
|
||||||
"plugins/gcr",
|
"plugins/acr",
|
||||||
"plugins/ecr",
|
"plugins/ecr",
|
||||||
|
"plugins/gcr",
|
||||||
|
"plugins/heroku",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
|
|
||||||
//
|
|
||||||
// Please note the below flags are mirrored in the pipec and
|
|
||||||
// should be kept synchronized. Do not edit directly
|
|
||||||
// https://github.com/cncd/pipeline/pipec
|
|
||||||
//
|
|
||||||
|
|
||||||
//
|
|
||||||
// workspace default
|
|
||||||
//
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "workspace-base",
|
|
||||||
Value: "/drone",
|
|
||||||
EnvVar: "DRONE_WORKSPACE_BASE",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "workspace-path",
|
|
||||||
Value: "src",
|
|
||||||
EnvVar: "DRONE_WORKSPACE_PATH",
|
|
||||||
},
|
|
||||||
//
|
//
|
||||||
// netrc parameters
|
// netrc parameters
|
||||||
//
|
//
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "netrc-username",
|
Name: "netrc-username",
|
||||||
EnvVar: "DRONE_NETRC_USERNAME",
|
|
||||||
},
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "netrc-password",
|
Name: "netrc-password",
|
||||||
EnvVar: "DRONE_NETRC_PASSWORD",
|
|
||||||
},
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "netrc-machine",
|
Name: "netrc-machine",
|
||||||
EnvVar: "DRONE_NETRC_MACHINE",
|
|
||||||
},
|
},
|
||||||
|
|
||||||
//
|
//
|
||||||
// metadata parameters
|
// trigger parameters
|
||||||
//
|
//
|
||||||
|
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "system-arch",
|
Name: "branch",
|
||||||
Value: "linux/amd64",
|
Usage: "branch name",
|
||||||
EnvVar: "DRONE_SYSTEM_ARCH",
|
|
||||||
},
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "system-name",
|
Name: "event",
|
||||||
Value: "pipec",
|
Usage: "build event name (push, pull_request, etc)",
|
||||||
EnvVar: "DRONE_SYSTEM_NAME",
|
|
||||||
},
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "system-link",
|
Name: "instance",
|
||||||
Value: "https://github.com/cncd/pipec",
|
Usage: "instance hostname (e.g. drone.company.com)",
|
||||||
EnvVar: "DRONE_SYSTEM_LINK",
|
|
||||||
},
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "repo-name",
|
Name: "ref",
|
||||||
EnvVar: "DRONE_REPO_NAME",
|
Usage: "git reference",
|
||||||
},
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "repo-link",
|
Name: "repo",
|
||||||
EnvVar: "DRONE_REPO_LINK",
|
Usage: "git repository name (e.g. octocat/hello-world)",
|
||||||
},
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "repo-remote-url",
|
Name: "deploy-to",
|
||||||
EnvVar: "DRONE_REPO_REMOTE",
|
Usage: "deployment target (e.g. production)",
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "repo-private",
|
|
||||||
EnvVar: "DRONE_REPO_PRIVATE",
|
|
||||||
},
|
|
||||||
cli.IntFlag{
|
|
||||||
Name: "build-number",
|
|
||||||
EnvVar: "DRONE_BUILD_NUMBER",
|
|
||||||
},
|
|
||||||
cli.IntFlag{
|
|
||||||
Name: "parent-build-number",
|
|
||||||
EnvVar: "DRONE_PARENT_BUILD_NUMBER",
|
|
||||||
},
|
|
||||||
cli.Int64Flag{
|
|
||||||
Name: "build-created",
|
|
||||||
EnvVar: "DRONE_BUILD_CREATED",
|
|
||||||
},
|
|
||||||
cli.Int64Flag{
|
|
||||||
Name: "build-started",
|
|
||||||
EnvVar: "DRONE_BUILD_STARTED",
|
|
||||||
},
|
|
||||||
cli.Int64Flag{
|
|
||||||
Name: "build-finished",
|
|
||||||
EnvVar: "DRONE_BUILD_FINISHED",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "build-status",
|
|
||||||
EnvVar: "DRONE_BUILD_STATUS",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "build-event",
|
|
||||||
EnvVar: "DRONE_BUILD_EVENT",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "build-link",
|
|
||||||
EnvVar: "DRONE_BUILD_LINK",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "build-target",
|
|
||||||
EnvVar: "DRONE_BUILD_TARGET",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "commit-sha",
|
|
||||||
EnvVar: "DRONE_COMMIT_SHA",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "commit-ref",
|
|
||||||
EnvVar: "DRONE_COMMIT_REF",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "commit-refspec",
|
|
||||||
EnvVar: "DRONE_COMMIT_REFSPEC",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "commit-branch",
|
|
||||||
EnvVar: "DRONE_COMMIT_BRANCH",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "commit-message",
|
|
||||||
EnvVar: "DRONE_COMMIT_MESSAGE",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "commit-author-name",
|
|
||||||
EnvVar: "DRONE_COMMIT_AUTHOR_NAME",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "commit-author-avatar",
|
|
||||||
EnvVar: "DRONE_COMMIT_AUTHOR_AVATAR",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "commit-author-email",
|
|
||||||
EnvVar: "DRONE_COMMIT_AUTHOR_EMAIL",
|
|
||||||
},
|
|
||||||
cli.IntFlag{
|
|
||||||
Name: "prev-build-number",
|
|
||||||
EnvVar: "DRONE_PREV_BUILD_NUMBER",
|
|
||||||
},
|
|
||||||
cli.Int64Flag{
|
|
||||||
Name: "prev-build-created",
|
|
||||||
EnvVar: "DRONE_PREV_BUILD_CREATED",
|
|
||||||
},
|
|
||||||
cli.Int64Flag{
|
|
||||||
Name: "prev-build-started",
|
|
||||||
EnvVar: "DRONE_PREV_BUILD_STARTED",
|
|
||||||
},
|
|
||||||
cli.Int64Flag{
|
|
||||||
Name: "prev-build-finished",
|
|
||||||
EnvVar: "DRONE_PREV_BUILD_FINISHED",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "prev-build-status",
|
|
||||||
EnvVar: "DRONE_PREV_BUILD_STATUS",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "prev-build-event",
|
|
||||||
EnvVar: "DRONE_PREV_BUILD_EVENT",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "prev-build-link",
|
|
||||||
EnvVar: "DRONE_PREV_BUILD_LINK",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "prev-commit-sha",
|
|
||||||
EnvVar: "DRONE_PREV_COMMIT_SHA",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "prev-commit-ref",
|
|
||||||
EnvVar: "DRONE_PREV_COMMIT_REF",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "prev-commit-refspec",
|
|
||||||
EnvVar: "DRONE_PREV_COMMIT_REFSPEC",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "prev-commit-branch",
|
|
||||||
EnvVar: "DRONE_PREV_COMMIT_BRANCH",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "prev-commit-message",
|
|
||||||
EnvVar: "DRONE_PREV_COMMIT_MESSAGE",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "prev-commit-author-name",
|
|
||||||
EnvVar: "DRONE_PREV_COMMIT_AUTHOR_NAME",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "prev-commit-author-avatar",
|
|
||||||
EnvVar: "DRONE_PREV_COMMIT_AUTHOR_AVATAR",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "prev-commit-author-email",
|
|
||||||
EnvVar: "DRONE_PREV_COMMIT_AUTHOR_EMAIL",
|
|
||||||
},
|
|
||||||
cli.IntFlag{
|
|
||||||
Name: "job-number",
|
|
||||||
EnvVar: "DRONE_JOB_NUMBER",
|
|
||||||
},
|
|
||||||
cli.StringSliceFlag{
|
|
||||||
Name: "env, e",
|
|
||||||
EnvVar: "DRONE_ENV",
|
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
@ -287,211 +153,204 @@ func exec(c *cli.Context) error {
|
|||||||
file = ".drone.yml"
|
file = ".drone.yml"
|
||||||
}
|
}
|
||||||
|
|
||||||
metadata := metadataFromContext(c)
|
data, err := ioutil.ReadFile(file)
|
||||||
environ := metadata.Environ()
|
|
||||||
secrets := []compiler.Secret{}
|
|
||||||
for k, v := range metadata.EnvironDrone() {
|
|
||||||
environ[k] = v
|
|
||||||
}
|
|
||||||
for key, val := range metadata.Job.Matrix {
|
|
||||||
environ[key] = val
|
|
||||||
secrets = append(secrets, compiler.Secret{
|
|
||||||
Name: key,
|
|
||||||
Value: val,
|
|
||||||
})
|
|
||||||
}
|
|
||||||
|
|
||||||
drone_env := make(map[string]string)
|
|
||||||
for _, env := range c.StringSlice("env") {
|
|
||||||
envs := strings.SplitN(env, "=", 2)
|
|
||||||
drone_env[envs[0]] = envs[1]
|
|
||||||
}
|
|
||||||
|
|
||||||
tmpl, err := envsubst.ParseFile(file)
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
confstr, err := tmpl.Execute(func(name string) string {
|
|
||||||
|
environ := getEnv(c)
|
||||||
|
dataS, err := envsubst.Eval(string(data), func(name string) string {
|
||||||
return environ[name]
|
return environ[name]
|
||||||
})
|
})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
conf, err := yaml.ParseString(confstr)
|
// this code is temporarily in place to detect and convert
|
||||||
|
// the legacy yaml configuration file to the new format.
|
||||||
|
dataS, err = converter.ConvertString(dataS, converter.Metadata{
|
||||||
|
Filename: file,
|
||||||
|
Ref: c.String("ref"),
|
||||||
|
})
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
// configure volumes for local execution
|
manifest, err := yaml.ParseString(dataS)
|
||||||
volumes := c.StringSlice("volumes")
|
if err != nil {
|
||||||
if c.Bool("local") {
|
return err
|
||||||
var (
|
|
||||||
workspaceBase = conf.Workspace.Base
|
|
||||||
workspacePath = conf.Workspace.Path
|
|
||||||
)
|
|
||||||
if workspaceBase == "" {
|
|
||||||
workspaceBase = c.String("workspace-base")
|
|
||||||
}
|
|
||||||
if workspacePath == "" {
|
|
||||||
workspacePath = c.String("workspace-path")
|
|
||||||
}
|
|
||||||
dir, _ := filepath.Abs(filepath.Dir(file))
|
|
||||||
|
|
||||||
if runtime.GOOS == "windows" {
|
|
||||||
dir = convertPathForWindows(dir)
|
|
||||||
}
|
|
||||||
volumes = append(volumes, c.String("prefix")+"_default:"+workspaceBase)
|
|
||||||
volumes = append(volumes, dir+":"+path.Join(workspaceBase, workspacePath))
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// lint the yaml file
|
var pipeline *yaml.Pipeline
|
||||||
if lerr := linter.New(linter.WithTrusted(true)).Lint(conf); lerr != nil {
|
filter := c.String("pipeline")
|
||||||
return lerr
|
for _, resource := range manifest.Resources {
|
||||||
|
v, ok := resource.(*yaml.Pipeline)
|
||||||
|
if !ok {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if filter == "" || filter == v.Name {
|
||||||
|
pipeline = v
|
||||||
|
break
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if pipeline == nil {
|
||||||
|
return errors.New("cannot find pipeline")
|
||||||
}
|
}
|
||||||
|
|
||||||
// compiles the yaml file
|
trusted := c.Bool("trusted")
|
||||||
compiled := compiler.New(
|
err = linter.Lint(pipeline, trusted)
|
||||||
compiler.WithEscalated(
|
if err != nil {
|
||||||
c.StringSlice("privileged")...,
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
// the user has the option to disable the git clone
|
||||||
|
// if the pipeline is being executed on the local
|
||||||
|
// codebase.
|
||||||
|
if c.Bool("clone") == false {
|
||||||
|
pipeline.Clone.Disable = true
|
||||||
|
}
|
||||||
|
|
||||||
|
comp := new(compiler.Compiler)
|
||||||
|
comp.PrivilegedFunc = compiler.DindFunc(
|
||||||
|
c.StringSlice("privileged"),
|
||||||
|
)
|
||||||
|
comp.SkipFunc = compiler.SkipFunc(
|
||||||
|
compiler.SkipData{
|
||||||
|
Branch: environ["DRONE_BRANCH"],
|
||||||
|
Event: environ["DRONE_EVENT"],
|
||||||
|
Instance: environ["DRONE_SYSTEM_HOST"],
|
||||||
|
Ref: environ["DRONE_COMMIT_REF"],
|
||||||
|
Repo: environ["DRONE_REPO"],
|
||||||
|
Target: environ["DRONE_DEPLOY_TO"],
|
||||||
|
},
|
||||||
|
)
|
||||||
|
transforms := []func(*engine.Spec){
|
||||||
|
transform.Include(
|
||||||
|
c.StringSlice("include"),
|
||||||
),
|
),
|
||||||
compiler.WithVolumes(volumes...),
|
transform.Exclude(
|
||||||
compiler.WithWorkspace(
|
c.StringSlice("exclude"),
|
||||||
c.String("workspace-base"),
|
|
||||||
c.String("workspace-path"),
|
|
||||||
),
|
),
|
||||||
compiler.WithNetworks(
|
transform.ResumeAt(
|
||||||
c.StringSlice("network")...,
|
c.String("resume-at"),
|
||||||
),
|
),
|
||||||
compiler.WithPrefix(
|
transform.WithAuths(
|
||||||
c.String("prefix"),
|
toRegistry(
|
||||||
|
c.StringSlice("registry"),
|
||||||
|
),
|
||||||
),
|
),
|
||||||
compiler.WithProxy(),
|
transform.WithEnviron(
|
||||||
compiler.WithLocal(
|
readParams(
|
||||||
c.Bool("local"),
|
c.String("env-file"),
|
||||||
|
),
|
||||||
),
|
),
|
||||||
compiler.WithNetrc(
|
transform.WithEnviron(environ),
|
||||||
|
transform.WithLables(nil),
|
||||||
|
transform.WithLimits(0, 0),
|
||||||
|
transform.WithNetrc(
|
||||||
|
c.String("netrc-machine"),
|
||||||
c.String("netrc-username"),
|
c.String("netrc-username"),
|
||||||
c.String("netrc-password"),
|
c.String("netrc-password"),
|
||||||
c.String("netrc-machine"),
|
|
||||||
),
|
),
|
||||||
compiler.WithMetadata(metadata),
|
transform.WithNetworks(
|
||||||
compiler.WithSecret(secrets...),
|
c.StringSlice("network"),
|
||||||
compiler.WithEnviron(drone_env),
|
),
|
||||||
).Compile(conf)
|
transform.WithProxy(),
|
||||||
|
transform.WithSecrets(
|
||||||
|
readParams(
|
||||||
|
c.String("secret-file"),
|
||||||
|
),
|
||||||
|
),
|
||||||
|
transform.WithVolumeSlice(
|
||||||
|
c.StringSlice("volume"),
|
||||||
|
),
|
||||||
|
}
|
||||||
|
if c.Bool("clone") == false {
|
||||||
|
pwd, _ := os.Getwd()
|
||||||
|
comp.WorkspaceMountFunc = compiler.MountHostWorkspace
|
||||||
|
comp.WorkspaceFunc = compiler.CreateHostWorkspace(pwd)
|
||||||
|
}
|
||||||
|
comp.TransformFunc = transform.Combine(transforms...)
|
||||||
|
ir := comp.Compile(pipeline)
|
||||||
|
|
||||||
|
ctx, cancel := context.WithTimeout(
|
||||||
|
context.Background(),
|
||||||
|
c.Duration("timeout"),
|
||||||
|
)
|
||||||
|
ctx = signal.WithContext(ctx)
|
||||||
|
defer cancel()
|
||||||
|
|
||||||
|
// creates a docker-based engine. eventually we will
|
||||||
|
// include the kubernetes and vmware fusion engines.
|
||||||
engine, err := docker.NewEnv()
|
engine, err := docker.NewEnv()
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
ctx, cancel := context.WithTimeout(context.Background(), c.Duration("timeout"))
|
// creates a hook to print the step output to stdout,
|
||||||
defer cancel()
|
// with per-step color coding if a tty.
|
||||||
ctx = interrupt.WithContext(ctx)
|
hooks := &runtime.Hook{}
|
||||||
|
hooks.BeforeEach = func(s *runtime.State) error {
|
||||||
|
s.Step.Envs["CI_BUILD_STATUS"] = "success"
|
||||||
|
s.Step.Envs["CI_BUILD_STARTED"] = strconv.FormatInt(s.Runtime.Time, 10)
|
||||||
|
s.Step.Envs["CI_BUILD_FINISHED"] = strconv.FormatInt(time.Now().Unix(), 10)
|
||||||
|
s.Step.Envs["DRONE_BUILD_STATUS"] = "success"
|
||||||
|
s.Step.Envs["DRONE_BUILD_STARTED"] = strconv.FormatInt(s.Runtime.Time, 10)
|
||||||
|
s.Step.Envs["DRONE_BUILD_FINISHED"] = strconv.FormatInt(time.Now().Unix(), 10)
|
||||||
|
|
||||||
return pipeline.New(compiled,
|
s.Step.Envs["CI_JOB_STATUS"] = "success"
|
||||||
pipeline.WithContext(ctx),
|
s.Step.Envs["CI_JOB_STARTED"] = strconv.FormatInt(s.Runtime.Time, 10)
|
||||||
pipeline.WithTracer(pipeline.DefaultTracer),
|
s.Step.Envs["CI_JOB_FINISHED"] = strconv.FormatInt(time.Now().Unix(), 10)
|
||||||
pipeline.WithLogger(defaultLogger),
|
s.Step.Envs["DRONE_JOB_STATUS"] = "success"
|
||||||
pipeline.WithEngine(engine),
|
s.Step.Envs["DRONE_JOB_STARTED"] = strconv.FormatInt(s.Runtime.Time, 10)
|
||||||
).Run()
|
s.Step.Envs["DRONE_JOB_FINISHED"] = strconv.FormatInt(time.Now().Unix(), 10)
|
||||||
}
|
|
||||||
|
|
||||||
// return the metadata from the cli context.
|
if s.Runtime.Error != nil {
|
||||||
func metadataFromContext(c *cli.Context) frontend.Metadata {
|
s.Step.Envs["CI_BUILD_STATUS"] = "failure"
|
||||||
return frontend.Metadata{
|
s.Step.Envs["CI_JOB_STATUS"] = "failure"
|
||||||
Repo: frontend.Repo{
|
s.Step.Envs["DRONE_BUILD_STATUS"] = "failure"
|
||||||
Name: c.String("repo-name"),
|
s.Step.Envs["DRONE_JOB_STATUS"] = "failure"
|
||||||
Link: c.String("repo-link"),
|
}
|
||||||
Remote: c.String("repo-remote-url"),
|
return nil
|
||||||
Private: c.Bool("repo-private"),
|
|
||||||
},
|
|
||||||
Curr: frontend.Build{
|
|
||||||
Number: c.Int("build-number"),
|
|
||||||
Parent: c.Int("parent-build-number"),
|
|
||||||
Created: c.Int64("build-created"),
|
|
||||||
Started: c.Int64("build-started"),
|
|
||||||
Finished: c.Int64("build-finished"),
|
|
||||||
Status: c.String("build-status"),
|
|
||||||
Event: c.String("build-event"),
|
|
||||||
Link: c.String("build-link"),
|
|
||||||
Target: c.String("build-target"),
|
|
||||||
Commit: frontend.Commit{
|
|
||||||
Sha: c.String("commit-sha"),
|
|
||||||
Ref: c.String("commit-ref"),
|
|
||||||
Refspec: c.String("commit-refspec"),
|
|
||||||
Branch: c.String("commit-branch"),
|
|
||||||
Message: c.String("commit-message"),
|
|
||||||
Author: frontend.Author{
|
|
||||||
Name: c.String("commit-author-name"),
|
|
||||||
Email: c.String("commit-author-email"),
|
|
||||||
Avatar: c.String("commit-author-avatar"),
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
Prev: frontend.Build{
|
|
||||||
Number: c.Int("prev-build-number"),
|
|
||||||
Created: c.Int64("prev-build-created"),
|
|
||||||
Started: c.Int64("prev-build-started"),
|
|
||||||
Finished: c.Int64("prev-build-finished"),
|
|
||||||
Status: c.String("prev-build-status"),
|
|
||||||
Event: c.String("prev-build-event"),
|
|
||||||
Link: c.String("prev-build-link"),
|
|
||||||
Commit: frontend.Commit{
|
|
||||||
Sha: c.String("prev-commit-sha"),
|
|
||||||
Ref: c.String("prev-commit-ref"),
|
|
||||||
Refspec: c.String("prev-commit-refspec"),
|
|
||||||
Branch: c.String("prev-commit-branch"),
|
|
||||||
Message: c.String("prev-commit-message"),
|
|
||||||
Author: frontend.Author{
|
|
||||||
Name: c.String("prev-commit-author-name"),
|
|
||||||
Email: c.String("prev-commit-author-email"),
|
|
||||||
Avatar: c.String("prev-commit-author-avatar"),
|
|
||||||
},
|
|
||||||
},
|
|
||||||
},
|
|
||||||
Job: frontend.Job{
|
|
||||||
Number: c.Int("job-number"),
|
|
||||||
Matrix: availableEnvironment(),
|
|
||||||
},
|
|
||||||
Sys: frontend.System{
|
|
||||||
Name: c.String("system-name"),
|
|
||||||
Link: c.String("system-link"),
|
|
||||||
Arch: c.String("system-arch"),
|
|
||||||
},
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
func availableEnvironment() map[string]string {
|
|
||||||
result := make(map[string]string, 0)
|
|
||||||
|
|
||||||
for _, env := range os.Environ() {
|
|
||||||
pair := strings.SplitN(env, "=", 2)
|
|
||||||
result[pair[0]] = pair[1]
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return result
|
hooks.GotLine = term.WriteLine(os.Stdout)
|
||||||
}
|
if tty {
|
||||||
|
hooks.GotLine = term.WriteLinePretty(
|
||||||
func convertPathForWindows(path string) string {
|
colorable.NewColorableStdout(),
|
||||||
base := filepath.VolumeName(path)
|
)
|
||||||
if len(base) == 2 {
|
|
||||||
path = strings.TrimPrefix(path, base)
|
|
||||||
base = strings.ToLower(strings.TrimSuffix(base, ":"))
|
|
||||||
return "/" + base + filepath.ToSlash(path)
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return filepath.ToSlash(path)
|
return runtime.New(
|
||||||
|
runtime.WithEngine(engine),
|
||||||
|
runtime.WithConfig(ir),
|
||||||
|
runtime.WithHooks(hooks),
|
||||||
|
).Run(ctx)
|
||||||
}
|
}
|
||||||
|
|
||||||
var defaultLogger = pipeline.LogFunc(func(proc *backend.Step, rc multipart.Reader) error {
|
// helper function converts a slice of urls to a slice
|
||||||
part, err := rc.NextPart()
|
// of docker registry credentials.
|
||||||
if err != nil {
|
func toRegistry(items []string) []*engine.DockerAuth {
|
||||||
return err
|
auths := []*engine.DockerAuth{}
|
||||||
|
for _, item := range items {
|
||||||
|
uri, err := url.Parse(item)
|
||||||
|
if err != nil {
|
||||||
|
continue // skip invalid
|
||||||
|
}
|
||||||
|
user := uri.User.Username()
|
||||||
|
pass, _ := uri.User.Password()
|
||||||
|
uri.User = nil
|
||||||
|
auths = append(auths, &engine.DockerAuth{
|
||||||
|
Address: uri.String(),
|
||||||
|
Username: user,
|
||||||
|
Password: pass,
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
return auths
|
||||||
|
}
|
||||||
|
|
||||||
logstream := NewLineWriter(proc.Alias)
|
// helper function reads secrets from a key-value file.
|
||||||
io.Copy(logstream, part)
|
func readParams(path string) map[string]string {
|
||||||
|
data, _ := godotenv.Read(path)
|
||||||
return nil
|
return data
|
||||||
})
|
}
|
||||||
|
47
drone/format/format.go
Normal file
47
drone/format/format.go
Normal file
@ -0,0 +1,47 @@
|
|||||||
|
package format
|
||||||
|
|
||||||
|
import (
|
||||||
|
"bytes"
|
||||||
|
"io"
|
||||||
|
"io/ioutil"
|
||||||
|
"os"
|
||||||
|
|
||||||
|
"github.com/drone/drone-yaml/yaml"
|
||||||
|
"github.com/drone/drone-yaml/yaml/pretty"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Command exports the fmt command.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "fmt",
|
||||||
|
Usage: "format the yaml file",
|
||||||
|
ArgsUsage: "<source>",
|
||||||
|
Action: format,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "save",
|
||||||
|
Usage: "save result to source",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func format(c *cli.Context) error {
|
||||||
|
path := c.Args().First()
|
||||||
|
if path == "" {
|
||||||
|
path = ".drone.yml"
|
||||||
|
}
|
||||||
|
|
||||||
|
manifest, err := yaml.ParseFile(path)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
buf := new(bytes.Buffer)
|
||||||
|
pretty.Print(buf, manifest)
|
||||||
|
|
||||||
|
if c.Bool("save") {
|
||||||
|
return ioutil.WriteFile(path, buf.Bytes(), 0644)
|
||||||
|
}
|
||||||
|
_, err = io.Copy(os.Stderr, buf)
|
||||||
|
return err
|
||||||
|
}
|
@ -4,9 +4,9 @@ import (
|
|||||||
"os"
|
"os"
|
||||||
"text/template"
|
"text/template"
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
// Command exports the info command.
|
// Command exports the info command.
|
||||||
@ -17,10 +17,9 @@ var Command = cli.Command{
|
|||||||
Action: info,
|
Action: info,
|
||||||
Flags: []cli.Flag{
|
Flags: []cli.Flag{
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "format",
|
Name: "format",
|
||||||
Usage: "format output",
|
Usage: "format output",
|
||||||
Value: tmplInfo,
|
Value: tmplInfo,
|
||||||
Hidden: true,
|
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
@ -36,7 +35,7 @@ func info(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format") + "\n")
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format") + "\n")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -49,6 +49,10 @@ func NewClient(c *cli.Context) (drone.Client, error) {
|
|||||||
},
|
},
|
||||||
)
|
)
|
||||||
|
|
||||||
|
auther.CheckRedirect = func(*http.Request, []*http.Request) error {
|
||||||
|
return fmt.Errorf("Attempting to redirect the requests. Did you configure the correct drone server address?")
|
||||||
|
}
|
||||||
|
|
||||||
trans, _ := auther.Transport.(*oauth2.Transport)
|
trans, _ := auther.Transport.(*oauth2.Transport)
|
||||||
|
|
||||||
if len(socks) != 0 && !socksoff {
|
if len(socks) != 0 && !socksoff {
|
||||||
@ -79,7 +83,7 @@ func NewAutoscaleClient(c *cli.Context) (drone.Client, error) {
|
|||||||
}
|
}
|
||||||
autoscaler := c.GlobalString("autoscaler")
|
autoscaler := c.GlobalString("autoscaler")
|
||||||
if autoscaler == "" {
|
if autoscaler == "" {
|
||||||
return nil, fmt.Errorf("Please provide the autoscaler address")
|
return nil, fmt.Errorf("Please provide the autoscaler address.")
|
||||||
}
|
}
|
||||||
client.SetAddress(
|
client.SetAddress(
|
||||||
strings.TrimSuffix(autoscaler, "/"),
|
strings.TrimSuffix(autoscaler, "/"),
|
||||||
@ -91,7 +95,7 @@ func NewAutoscaleClient(c *cli.Context) (drone.Client, error) {
|
|||||||
func ParseRepo(str string) (user, repo string, err error) {
|
func ParseRepo(str string) (user, repo string, err error) {
|
||||||
var parts = strings.Split(str, "/")
|
var parts = strings.Split(str, "/")
|
||||||
if len(parts) != 2 {
|
if len(parts) != 2 {
|
||||||
err = fmt.Errorf("Error: Invalid or missing repository. eg octocat/hello-world.")
|
err = fmt.Errorf("Error: Invalid or missing repository (e.g. octocat/hello-world).")
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
user = parts[0]
|
user = parts[0]
|
||||||
|
@ -1,9 +1,16 @@
|
|||||||
package jsonnet
|
package jsonnet
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"bytes"
|
||||||
|
"fmt"
|
||||||
|
"io"
|
||||||
"io/ioutil"
|
"io/ioutil"
|
||||||
"log"
|
"log"
|
||||||
|
"os"
|
||||||
|
"strings"
|
||||||
|
|
||||||
|
"github.com/drone/drone-yaml/yaml"
|
||||||
|
"github.com/drone/drone-yaml/yaml/pretty"
|
||||||
"github.com/fatih/color"
|
"github.com/fatih/color"
|
||||||
"github.com/google/go-jsonnet"
|
"github.com/google/go-jsonnet"
|
||||||
"github.com/urfave/cli"
|
"github.com/urfave/cli"
|
||||||
@ -20,67 +27,120 @@ var Command = cli.Command{
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
Flags: []cli.Flag{
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "source",
|
||||||
|
Usage: "Source file",
|
||||||
|
Value: ".drone.jsonnet",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "target",
|
||||||
|
Usage: "target file",
|
||||||
|
Value: ".drone.yml",
|
||||||
|
},
|
||||||
cli.BoolFlag{
|
cli.BoolFlag{
|
||||||
Name: "string",
|
Name: "stream",
|
||||||
Hidden: true,
|
Usage: "Write output as a YAML stream.",
|
||||||
},
|
},
|
||||||
cli.IntFlag{
|
cli.BoolTFlag{
|
||||||
Name: "max-stack",
|
Name: "format",
|
||||||
Usage: "number of allowed stack frames",
|
Usage: "Write output as formatted YAML",
|
||||||
Value: 500,
|
|
||||||
},
|
|
||||||
cli.IntFlag{
|
|
||||||
Name: "max-trace",
|
|
||||||
Usage: "max length of stack trace before cropping",
|
|
||||||
Value: 20,
|
|
||||||
},
|
},
|
||||||
cli.BoolFlag{
|
cli.BoolFlag{
|
||||||
Name: "stdout",
|
Name: "stdout",
|
||||||
Usage: "write the json document to stdout",
|
Usage: "Write output to stdout",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "string",
|
||||||
|
Usage: "Expect a string, manifest as plain text",
|
||||||
|
},
|
||||||
|
cli.StringSliceFlag{
|
||||||
|
Name: "extVar, V",
|
||||||
|
Usage: "Pass extVars to Jsonnet (can be specified multiple times)",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
func generate(c *cli.Context) error {
|
func generate(c *cli.Context) error {
|
||||||
input := c.Args().Get(0)
|
source := c.String("source")
|
||||||
if input == "" {
|
target := c.String("target")
|
||||||
input = ".drone.jsonnet"
|
|
||||||
}
|
|
||||||
output := c.Args().Get(1)
|
|
||||||
if output == "" {
|
|
||||||
output = ".drone.yml"
|
|
||||||
}
|
|
||||||
|
|
||||||
snippet, err := ioutil.ReadFile(input)
|
data, err := ioutil.ReadFile(source)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
vm := jsonnet.MakeVM()
|
vm := jsonnet.MakeVM()
|
||||||
vm.KeepOrder = true
|
vm.MaxStack = 500
|
||||||
vm.StringOutput = c.Bool("string")
|
vm.StringOutput = c.Bool("string")
|
||||||
vm.MaxStack = c.Int("max-stack")
|
vm.ErrorFormatter.SetMaxStackTraceSize(20)
|
||||||
// vm.ExtVar
|
|
||||||
// vm.ExtCode
|
|
||||||
// vm.TLAVar
|
|
||||||
// vm.TLACode
|
|
||||||
// vm.Importer(&jsonnet.FileImporter{})
|
|
||||||
|
|
||||||
vm.ErrorFormatter.SetMaxStackTraceSize(
|
|
||||||
c.Int("max-trace"),
|
|
||||||
)
|
|
||||||
vm.ErrorFormatter.SetColorFormatter(
|
vm.ErrorFormatter.SetColorFormatter(
|
||||||
color.New(color.FgRed).Fprintf,
|
color.New(color.FgRed).Fprintf,
|
||||||
)
|
)
|
||||||
|
|
||||||
raw, err := vm.EvaluateSnippet(input, string(snippet))
|
// register native functions
|
||||||
if err != nil {
|
RegisterNativeFuncs(vm)
|
||||||
return err
|
|
||||||
|
// extVars
|
||||||
|
vars := c.StringSlice("extVar")
|
||||||
|
for _, v := range vars {
|
||||||
|
name, value, err := getVarVal(v)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
vm.ExtVar(name, value)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
buf := new(bytes.Buffer)
|
||||||
|
if c.Bool("stream") {
|
||||||
|
docs, err := vm.EvaluateSnippetStream(source, string(data))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
for _, doc := range docs {
|
||||||
|
buf.WriteString("---")
|
||||||
|
buf.WriteString("\n")
|
||||||
|
buf.WriteString(doc)
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
result, err := vm.EvaluateSnippet(source, string(data))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
buf.WriteString(result)
|
||||||
|
}
|
||||||
|
|
||||||
|
// the yaml file is parsed and formatted by default. This
|
||||||
|
// can be disabled for --format=false.
|
||||||
|
if c.BoolT("format") {
|
||||||
|
manifest, err := yaml.Parse(buf)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
buf.Reset()
|
||||||
|
pretty.Print(buf, manifest)
|
||||||
|
}
|
||||||
|
|
||||||
|
// the user can optionally write the yaml to stdout. This
|
||||||
|
// is useful for debugging purposes without mutating an
|
||||||
|
// existing file.
|
||||||
if c.Bool("stdout") {
|
if c.Bool("stdout") {
|
||||||
println(raw)
|
io.Copy(os.Stdout, buf)
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
return ioutil.WriteFile(output, []byte(raw), 0644)
|
|
||||||
|
return ioutil.WriteFile(target, buf.Bytes(), 0644)
|
||||||
|
}
|
||||||
|
|
||||||
|
// https://github.com/google/go-jsonnet/blob/master/cmd/jsonnet/cmd.go#L149
|
||||||
|
func getVarVal(s string) (string, string, error) {
|
||||||
|
parts := strings.SplitN(s, "=", 2)
|
||||||
|
name := parts[0]
|
||||||
|
if len(parts) == 1 {
|
||||||
|
content, exists := os.LookupEnv(name)
|
||||||
|
if exists {
|
||||||
|
return name, content, nil
|
||||||
|
}
|
||||||
|
return "", "", fmt.Errorf("environment variable %v was undefined", name)
|
||||||
|
}
|
||||||
|
return name, parts[1], nil
|
||||||
}
|
}
|
||||||
|
45
drone/jsonnet/nativefuncs.go
Normal file
45
drone/jsonnet/nativefuncs.go
Normal file
@ -0,0 +1,45 @@
|
|||||||
|
package jsonnet
|
||||||
|
|
||||||
|
import (
|
||||||
|
// "bytes"
|
||||||
|
// "encoding/json"
|
||||||
|
// "io"
|
||||||
|
|
||||||
|
jsonnet "github.com/google/go-jsonnet"
|
||||||
|
// jsonnetAst "github.com/google/go-jsonnet/ast"
|
||||||
|
// "k8s.io/apimachinery/pkg/util/yaml"
|
||||||
|
)
|
||||||
|
|
||||||
|
// RegisterNativeFuncs adds kubecfg's native jsonnet functions to provided VM
|
||||||
|
func RegisterNativeFuncs(vm *jsonnet.VM) {
|
||||||
|
// vm.NativeFunction(&jsonnet.NativeFunction{
|
||||||
|
// Name: "parseJson",
|
||||||
|
// Params: []jsonnetAst.Identifier{"json"},
|
||||||
|
// Func: func(args []interface{}) (res interface{}, err error) {
|
||||||
|
// data := []byte(args[0].(string))
|
||||||
|
// err = json.Unmarshal(data, &res)
|
||||||
|
// return
|
||||||
|
// },
|
||||||
|
// })
|
||||||
|
|
||||||
|
// vm.NativeFunction(&jsonnet.NativeFunction{
|
||||||
|
// Name: "parseYaml",
|
||||||
|
// Params: []jsonnetAst.Identifier{"yaml"},
|
||||||
|
// Func: func(args []interface{}) (res interface{}, err error) {
|
||||||
|
// ret := []interface{}{}
|
||||||
|
// data := []byte(args[0].(string))
|
||||||
|
// d := yaml.NewYAMLToJSONDecoder(bytes.NewReader(data))
|
||||||
|
// for {
|
||||||
|
// var doc interface{}
|
||||||
|
// if err := d.Decode(&doc); err != nil {
|
||||||
|
// if err == io.EOF {
|
||||||
|
// break
|
||||||
|
// }
|
||||||
|
// return nil, err
|
||||||
|
// }
|
||||||
|
// ret = append(ret, doc)
|
||||||
|
// }
|
||||||
|
// return ret, nil
|
||||||
|
// },
|
||||||
|
// })
|
||||||
|
}
|
41
drone/lint/lint.go
Normal file
41
drone/lint/lint.go
Normal file
@ -0,0 +1,41 @@
|
|||||||
|
package lint
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/drone/drone-yaml/yaml"
|
||||||
|
"github.com/drone/drone-yaml/yaml/linter"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Command exports the linter command.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "lint",
|
||||||
|
Usage: "lint the yaml file",
|
||||||
|
ArgsUsage: "<source>",
|
||||||
|
Action: lint,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "trusted",
|
||||||
|
Usage: "is the yaml trustable",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func lint(c *cli.Context) error {
|
||||||
|
path := c.Args().First()
|
||||||
|
if path == "" {
|
||||||
|
path = ".drone.yml"
|
||||||
|
}
|
||||||
|
|
||||||
|
manifest, err := yaml.ParseFile(path)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, resource := range manifest.Resources {
|
||||||
|
if err := linter.Lint(resource, c.Bool("trusted")); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
@ -8,5 +8,6 @@ var Command = cli.Command{
|
|||||||
Usage: "manage logs",
|
Usage: "manage logs",
|
||||||
Subcommands: []cli.Command{
|
Subcommands: []cli.Command{
|
||||||
logPurgeCmd,
|
logPurgeCmd,
|
||||||
|
logViewCmd,
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
@ -11,7 +11,7 @@ import (
|
|||||||
var logPurgeCmd = cli.Command{
|
var logPurgeCmd = cli.Command{
|
||||||
Name: "purge",
|
Name: "purge",
|
||||||
Usage: "purge a log",
|
Usage: "purge a log",
|
||||||
ArgsUsage: "<repo/name> <build>",
|
ArgsUsage: "<repo/name> <build> <stage> <step>",
|
||||||
Action: logPurge,
|
Action: logPurge,
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -25,13 +25,21 @@ func logPurge(c *cli.Context) (err error) {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
stage, err := strconv.Atoi(c.Args().Get(2))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
step, err := strconv.Atoi(c.Args().Get(3))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
client, err := internal.NewClient(c)
|
client, err := internal.NewClient(c)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
err = client.LogsPurge(owner, name, number)
|
err = client.LogsPurge(owner, name, number, stage, step)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
50
drone/log/log_view.go
Normal file
50
drone/log/log_view.go
Normal file
@ -0,0 +1,50 @@
|
|||||||
|
package log
|
||||||
|
|
||||||
|
import (
|
||||||
|
"strconv"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var logViewCmd = cli.Command{
|
||||||
|
Name: "view",
|
||||||
|
Usage: "display the step logs",
|
||||||
|
ArgsUsage: "<repo/name> <build> <stage> <step>",
|
||||||
|
Action: logView,
|
||||||
|
}
|
||||||
|
|
||||||
|
func logView(c *cli.Context) (err error) {
|
||||||
|
repo := c.Args().First()
|
||||||
|
owner, name, err := internal.ParseRepo(repo)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
number, err := strconv.Atoi(c.Args().Get(1))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
stage, err := strconv.Atoi(c.Args().Get(2))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
step, err := strconv.Atoi(c.Args().Get(3))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
lines, err := client.Logs(owner, name, number, stage, step)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, line := range lines {
|
||||||
|
print(line.Message)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
@ -6,15 +6,23 @@ import (
|
|||||||
|
|
||||||
"github.com/drone/drone-cli/drone/autoscale"
|
"github.com/drone/drone-cli/drone/autoscale"
|
||||||
"github.com/drone/drone-cli/drone/build"
|
"github.com/drone/drone-cli/drone/build"
|
||||||
"github.com/drone/drone-cli/drone/deploy"
|
"github.com/drone/drone-cli/drone/convert"
|
||||||
|
"github.com/drone/drone-cli/drone/cron"
|
||||||
|
"github.com/drone/drone-cli/drone/encrypt"
|
||||||
"github.com/drone/drone-cli/drone/exec"
|
"github.com/drone/drone-cli/drone/exec"
|
||||||
|
"github.com/drone/drone-cli/drone/format"
|
||||||
"github.com/drone/drone-cli/drone/info"
|
"github.com/drone/drone-cli/drone/info"
|
||||||
"github.com/drone/drone-cli/drone/jsonnet"
|
"github.com/drone/drone-cli/drone/jsonnet"
|
||||||
|
"github.com/drone/drone-cli/drone/lint"
|
||||||
"github.com/drone/drone-cli/drone/log"
|
"github.com/drone/drone-cli/drone/log"
|
||||||
"github.com/drone/drone-cli/drone/registry"
|
"github.com/drone/drone-cli/drone/orgsecret"
|
||||||
|
"github.com/drone/drone-cli/drone/plugins"
|
||||||
|
"github.com/drone/drone-cli/drone/queue"
|
||||||
"github.com/drone/drone-cli/drone/repo"
|
"github.com/drone/drone-cli/drone/repo"
|
||||||
"github.com/drone/drone-cli/drone/secret"
|
"github.com/drone/drone-cli/drone/secret"
|
||||||
"github.com/drone/drone-cli/drone/server"
|
"github.com/drone/drone-cli/drone/server"
|
||||||
|
"github.com/drone/drone-cli/drone/sign"
|
||||||
|
"github.com/drone/drone-cli/drone/starlark"
|
||||||
"github.com/drone/drone-cli/drone/user"
|
"github.com/drone/drone-cli/drone/user"
|
||||||
|
|
||||||
_ "github.com/joho/godotenv/autoload"
|
_ "github.com/joho/godotenv/autoload"
|
||||||
@ -68,17 +76,25 @@ func main() {
|
|||||||
}
|
}
|
||||||
app.Commands = []cli.Command{
|
app.Commands = []cli.Command{
|
||||||
build.Command,
|
build.Command,
|
||||||
|
cron.Command,
|
||||||
log.Command,
|
log.Command,
|
||||||
deploy.Command,
|
encrypt.Command,
|
||||||
exec.Command,
|
exec.Command,
|
||||||
info.Command,
|
info.Command,
|
||||||
registry.Command,
|
|
||||||
secret.Command,
|
|
||||||
repo.Command,
|
repo.Command,
|
||||||
user.Command,
|
user.Command,
|
||||||
|
secret.Command,
|
||||||
server.Command,
|
server.Command,
|
||||||
|
queue.Command,
|
||||||
|
orgsecret.Command,
|
||||||
autoscale.Command,
|
autoscale.Command,
|
||||||
|
format.Command,
|
||||||
|
convert.Command,
|
||||||
|
lint.Command,
|
||||||
|
sign.Command,
|
||||||
jsonnet.Command,
|
jsonnet.Command,
|
||||||
|
starlark.Command,
|
||||||
|
plugins.Command,
|
||||||
}
|
}
|
||||||
|
|
||||||
if err := app.Run(os.Args); err != nil {
|
if err := app.Run(os.Args); err != nil {
|
||||||
|
24
drone/node/node.go
Normal file
24
drone/node/node.go
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
package node
|
||||||
|
|
||||||
|
import "github.com/urfave/cli"
|
||||||
|
|
||||||
|
// Command exports the registry command set.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "node",
|
||||||
|
Usage: "manage nodes",
|
||||||
|
Hidden: true,
|
||||||
|
Subcommands: []cli.Command{
|
||||||
|
nodeListCmd,
|
||||||
|
nodeInfoCmd,
|
||||||
|
nodeCreateCmd,
|
||||||
|
// nodeUpdateCmd,
|
||||||
|
// nodeDeleteCmd,
|
||||||
|
// nodePauseCmd,
|
||||||
|
// nodeUnpauseCmd,
|
||||||
|
// nodeLockCmd,
|
||||||
|
// nodeUnlockCmd,
|
||||||
|
// nodeInitCmd,
|
||||||
|
nodeImportCmd,
|
||||||
|
// nodeKeygenCmd,
|
||||||
|
},
|
||||||
|
}
|
149
drone/node/node_create.go
Normal file
149
drone/node/node_create.go
Normal file
@ -0,0 +1,149 @@
|
|||||||
|
package node
|
||||||
|
|
||||||
|
import (
|
||||||
|
"html/template"
|
||||||
|
"io/ioutil"
|
||||||
|
"os"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var nodeCreateCmd = cli.Command{
|
||||||
|
Name: "add",
|
||||||
|
Usage: "adds a node",
|
||||||
|
Action: nodeCreate,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "name",
|
||||||
|
Usage: "node name",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "hostname",
|
||||||
|
Usage: "node hostname or ip address",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "ca-key",
|
||||||
|
Usage: "path to ca key",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "ca-cert",
|
||||||
|
Usage: "path to ca cert",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "tls-key",
|
||||||
|
Usage: "path to tls key",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "tls-cert",
|
||||||
|
Usage: "path to tls cert",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "tls-server-name",
|
||||||
|
Usage: "tls server name",
|
||||||
|
},
|
||||||
|
cli.IntFlag{
|
||||||
|
Name: "capacity",
|
||||||
|
Usage: "node capacity",
|
||||||
|
Value: 2,
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "os",
|
||||||
|
Usage: "node os",
|
||||||
|
Value: "linux",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "arch",
|
||||||
|
Usage: "node arch",
|
||||||
|
Value: "amd64",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "region",
|
||||||
|
Usage: "node region",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "instance",
|
||||||
|
Usage: "node instance type",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "image",
|
||||||
|
Usage: "node image (i.e. ami)",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "provider",
|
||||||
|
Usage: "node hosting provider (e.g. amazon)",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "paused",
|
||||||
|
Usage: "node is paused",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "protected",
|
||||||
|
Usage: "node is protected from deletion",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "format output",
|
||||||
|
Value: tmplNodeInfo,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func nodeCreate(c *cli.Context) error {
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
cakey, err := ioutil.ReadFile(c.String("ca-key"))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
cacert, err := ioutil.ReadFile(c.String("ca-cert"))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
tlskey, err := ioutil.ReadFile(c.String("tls-key"))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
tlscert, err := ioutil.ReadFile(c.String("tls-cert"))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
node := &drone.Node{
|
||||||
|
UID: c.String("id"),
|
||||||
|
Provider: c.String("provider"),
|
||||||
|
State: c.String("state"),
|
||||||
|
Name: c.String("name"),
|
||||||
|
Image: c.String("image"),
|
||||||
|
Region: c.String("region"),
|
||||||
|
Size: c.String("instance"),
|
||||||
|
OS: c.String("os"),
|
||||||
|
Arch: c.String("arch"),
|
||||||
|
Address: c.String("hostname"),
|
||||||
|
Capacity: c.Int("capacity"),
|
||||||
|
CAKey: cakey,
|
||||||
|
CACert: cacert,
|
||||||
|
TLSKey: tlskey,
|
||||||
|
TLSCert: tlscert,
|
||||||
|
TLSName: c.String("tls-server-name"),
|
||||||
|
Paused: c.Bool("paused"),
|
||||||
|
Protected: c.Bool("protected"),
|
||||||
|
}
|
||||||
|
|
||||||
|
_, err = client.NodeCreate(node)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
format := c.String("format")
|
||||||
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(format)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return tmpl.Execute(os.Stdout, node)
|
||||||
|
}
|
1
drone/node/node_delete.go
Normal file
1
drone/node/node_delete.go
Normal file
@ -0,0 +1 @@
|
|||||||
|
package node
|
192
drone/node/node_import.go
Normal file
192
drone/node/node_import.go
Normal file
@ -0,0 +1,192 @@
|
|||||||
|
package node
|
||||||
|
|
||||||
|
import (
|
||||||
|
"encoding/json"
|
||||||
|
"fmt"
|
||||||
|
"html/template"
|
||||||
|
"io/ioutil"
|
||||||
|
"os"
|
||||||
|
"os/user"
|
||||||
|
"path/filepath"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
func getMachineHome() (path string) {
|
||||||
|
user, err := user.Current()
|
||||||
|
if err == nil {
|
||||||
|
return filepath.Join(user.HomeDir, ".docker", "machine")
|
||||||
|
}
|
||||||
|
return
|
||||||
|
}
|
||||||
|
|
||||||
|
var nodeImportCmd = cli.Command{
|
||||||
|
Name: "import",
|
||||||
|
Usage: "import a node from docker-machine",
|
||||||
|
Action: nodeImport,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "name",
|
||||||
|
Usage: "node name",
|
||||||
|
},
|
||||||
|
cli.IntFlag{
|
||||||
|
Name: "capacity",
|
||||||
|
Usage: "node capacity",
|
||||||
|
Value: 2,
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "os",
|
||||||
|
Usage: "node os",
|
||||||
|
Value: "linux",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "arch",
|
||||||
|
Usage: "node arch",
|
||||||
|
Value: "amd64",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "paused",
|
||||||
|
Usage: "node is paused",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "protected",
|
||||||
|
Usage: "node is protected from deletion",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "storage-path",
|
||||||
|
Usage: "docker machine storage path",
|
||||||
|
Value: getMachineHome(),
|
||||||
|
EnvVar: "MACHINE_STORAGE_PATH",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "format output",
|
||||||
|
Value: tmplNodeInfo,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func nodeImport(c *cli.Context) error {
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
name := c.String("name")
|
||||||
|
if name == "" {
|
||||||
|
name = c.Args().First()
|
||||||
|
}
|
||||||
|
|
||||||
|
home := c.String("storage-path")
|
||||||
|
base := filepath.Join(home, "machines", name)
|
||||||
|
|
||||||
|
conf := new(machine)
|
||||||
|
confpath := filepath.Join(base, "config.json")
|
||||||
|
confdata, err := ioutil.ReadFile(confpath)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
err = json.Unmarshal(confdata, conf)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
cakey, err := ioutil.ReadFile(conf.HostOptions.AuthOptions.CaPrivateKeyPath)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
cacert, err := ioutil.ReadFile(conf.HostOptions.AuthOptions.CaCertPath)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
tlskey, err := ioutil.ReadFile(conf.HostOptions.AuthOptions.ClientKeyPath)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
tlscert, err := ioutil.ReadFile(conf.HostOptions.AuthOptions.ClientCertPath)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
node := &drone.Node{
|
||||||
|
UID: fmt.Sprint(conf.Driver.DropletID),
|
||||||
|
Provider: c.String("provider"),
|
||||||
|
State: c.String("state"),
|
||||||
|
Name: conf.Driver.MachineName,
|
||||||
|
Image: conf.Driver.Image,
|
||||||
|
Region: conf.Driver.Region,
|
||||||
|
Size: conf.Driver.Size,
|
||||||
|
OS: c.String("os"),
|
||||||
|
Arch: c.String("arch"),
|
||||||
|
Address: conf.Driver.IPAddress,
|
||||||
|
Capacity: 2,
|
||||||
|
CAKey: cakey,
|
||||||
|
CACert: cacert,
|
||||||
|
TLSKey: tlskey,
|
||||||
|
TLSCert: tlscert,
|
||||||
|
Paused: c.Bool("paused"),
|
||||||
|
Protected: c.Bool("protected"),
|
||||||
|
}
|
||||||
|
|
||||||
|
_, err = client.NodeCreate(node)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
format := c.String("format")
|
||||||
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(format)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return tmpl.Execute(os.Stdout, node)
|
||||||
|
}
|
||||||
|
|
||||||
|
type machine struct {
|
||||||
|
DriverName string
|
||||||
|
Driver struct {
|
||||||
|
IPAddress string `json:"IPAddress"`
|
||||||
|
MachineName string `json:"MachineName"`
|
||||||
|
SSHUser string `json:"SSHUser"`
|
||||||
|
SSHPort int `json:"SSHPort"`
|
||||||
|
SSHKeyPath string `json:"SSHKeyPath"`
|
||||||
|
StorePath string `json:"StorePath"`
|
||||||
|
SwarmMaster bool `json:"SwarmMaster"`
|
||||||
|
SwarmHost string `json:"SwarmHost"`
|
||||||
|
SwarmDiscovery string `json:"SwarmDiscovery"`
|
||||||
|
AccessToken string `json:"AccessToken"`
|
||||||
|
DropletID int `json:"DropletID"`
|
||||||
|
DropletName string `json:"DropletName"`
|
||||||
|
Image string `json:"Image"`
|
||||||
|
Region string `json:"Region"`
|
||||||
|
SSHKeyID int `json:"SSHKeyID"`
|
||||||
|
SSHKeyFingerprint string `json:"SSHKeyFingerprint"`
|
||||||
|
SSHKey string `json:"SSHKey"`
|
||||||
|
Size string `json:"Size"`
|
||||||
|
IPv6 bool `json:"IPv6"`
|
||||||
|
Backups bool `json:"Backups"`
|
||||||
|
PrivateNetworking bool `json:"PrivateNetworking"`
|
||||||
|
UserDataFile string `json:"UserDataFile"`
|
||||||
|
Monitoring bool `json:"Monitoring"`
|
||||||
|
Tags string `json:"Tags"`
|
||||||
|
}
|
||||||
|
HostOptions struct {
|
||||||
|
AuthOptions struct {
|
||||||
|
CertDir string `json:"CertDir"`
|
||||||
|
CaCertPath string `json:"CaCertPath"`
|
||||||
|
CaPrivateKeyPath string `json:"CaPrivateKeyPath"`
|
||||||
|
CaCertRemotePath string `json:"CaCertRemotePath"`
|
||||||
|
ServerCertPath string `json:"ServerCertPath"`
|
||||||
|
ServerKeyPath string `json:"ServerKeyPath"`
|
||||||
|
ClientKeyPath string `json:"ClientKeyPath"`
|
||||||
|
ServerCertRemotePath string `json:"ServerCertRemotePath"`
|
||||||
|
ServerKeyRemotePath string `json:"ServerKeyRemotePath"`
|
||||||
|
ClientCertPath string `json:"ClientCertPath"`
|
||||||
|
ServerCertSANs []interface{} `json:"ServerCertSANs"`
|
||||||
|
StorePath string `json:"StorePath"`
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
155
drone/node/node_import_all.go
Normal file
155
drone/node/node_import_all.go
Normal file
@ -0,0 +1,155 @@
|
|||||||
|
package node
|
||||||
|
|
||||||
|
import (
|
||||||
|
"encoding/json"
|
||||||
|
"fmt"
|
||||||
|
"html/template"
|
||||||
|
"io/ioutil"
|
||||||
|
"os"
|
||||||
|
"path/filepath"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var nodeImportAllCmd = cli.Command{
|
||||||
|
Name: "import-all",
|
||||||
|
Usage: "import all node from docker-machine",
|
||||||
|
Action: nodeImportAll,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.IntFlag{
|
||||||
|
Name: "capacity",
|
||||||
|
Usage: "node capacity",
|
||||||
|
Value: 2,
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "os",
|
||||||
|
Usage: "node os",
|
||||||
|
Value: "linux",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "arch",
|
||||||
|
Usage: "node arch",
|
||||||
|
Value: "amd64",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "paused",
|
||||||
|
Usage: "node is paused",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "protected",
|
||||||
|
Usage: "node is protected from deletion",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "storage-path",
|
||||||
|
Usage: "docker machine storage path",
|
||||||
|
Value: getMachineHome(),
|
||||||
|
EnvVar: "MACHINE_STORAGE_PATH",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "format output",
|
||||||
|
Value: tmplNodeInfo,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func nodeImportAll(c *cli.Context) error {
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
home := c.String("storage-path")
|
||||||
|
|
||||||
|
matches, err := filepath.Glob(filepath.Join(home, "machines", "*"))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
nodes, err := client.NodeList()
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
nodeIndex := map[string]*drone.Node{}
|
||||||
|
for _, node := range nodes {
|
||||||
|
nodeIndex[node.Name] = node
|
||||||
|
}
|
||||||
|
|
||||||
|
format := c.String("format") + "\n"
|
||||||
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(format)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, name := range matches {
|
||||||
|
base := filepath.Join(home, "machines", name)
|
||||||
|
|
||||||
|
// if the node already exists it should be
|
||||||
|
// ignored by the system.
|
||||||
|
existing, ok := nodeIndex[name]
|
||||||
|
if ok {
|
||||||
|
tmpl.Execute(os.Stdout, existing)
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
|
conf := new(machine)
|
||||||
|
confpath := filepath.Join(base, "config.json")
|
||||||
|
confdata, err := ioutil.ReadFile(confpath)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
err = json.Unmarshal(confdata, conf)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
cakey, err := ioutil.ReadFile(conf.HostOptions.AuthOptions.CaPrivateKeyPath)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
cacert, err := ioutil.ReadFile(conf.HostOptions.AuthOptions.CaCertPath)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
tlskey, err := ioutil.ReadFile(conf.HostOptions.AuthOptions.ClientKeyPath)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
tlscert, err := ioutil.ReadFile(conf.HostOptions.AuthOptions.ClientCertPath)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
node := &drone.Node{
|
||||||
|
UID: fmt.Sprint(conf.Driver.DropletID),
|
||||||
|
Provider: c.String("provider"),
|
||||||
|
State: c.String("state"),
|
||||||
|
Name: conf.Driver.MachineName,
|
||||||
|
Image: conf.Driver.Image,
|
||||||
|
Region: conf.Driver.Region,
|
||||||
|
Size: conf.Driver.Size,
|
||||||
|
OS: c.String("os"),
|
||||||
|
Arch: c.String("arch"),
|
||||||
|
Address: conf.Driver.IPAddress,
|
||||||
|
Capacity: 2,
|
||||||
|
CAKey: cakey,
|
||||||
|
CACert: cacert,
|
||||||
|
TLSKey: tlskey,
|
||||||
|
TLSCert: tlscert,
|
||||||
|
Paused: c.Bool("paused"),
|
||||||
|
Protected: c.Bool("protected"),
|
||||||
|
}
|
||||||
|
|
||||||
|
_, err = client.NodeCreate(node)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
tmpl.Execute(os.Stdout, node)
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
51
drone/node/node_info.go
Normal file
51
drone/node/node_info.go
Normal file
@ -0,0 +1,51 @@
|
|||||||
|
package node
|
||||||
|
|
||||||
|
import (
|
||||||
|
"html/template"
|
||||||
|
"os"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var nodeInfoCmd = cli.Command{
|
||||||
|
Name: "info",
|
||||||
|
Usage: "display node info",
|
||||||
|
Action: nodeInfo,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "format output",
|
||||||
|
Value: tmplNodeInfo,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func nodeInfo(c *cli.Context) error {
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
name := c.Args().First()
|
||||||
|
node, err := client.Node(name)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
format := c.String("format")
|
||||||
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(format)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return tmpl.Execute(os.Stdout, node)
|
||||||
|
}
|
||||||
|
|
||||||
|
var tmplNodeInfo = "\x1b[33m{{ .Name }} \x1b[0m" + `
|
||||||
|
Address: {{ .Address }}
|
||||||
|
Region: {{ .Region }}
|
||||||
|
Instance: {{ .Size }}
|
||||||
|
OS: {{ .OS }}
|
||||||
|
Arch: {{ .Arch }}
|
||||||
|
Locked: {{ .Protected }}
|
||||||
|
Paused: {{ .Paused }}
|
||||||
|
`
|
1
drone/node/node_init.go
Normal file
1
drone/node/node_init.go
Normal file
@ -0,0 +1 @@
|
|||||||
|
package node
|
1
drone/node/node_keygen.go
Normal file
1
drone/node/node_keygen.go
Normal file
@ -0,0 +1 @@
|
|||||||
|
package node
|
49
drone/node/node_list.go
Normal file
49
drone/node/node_list.go
Normal file
@ -0,0 +1,49 @@
|
|||||||
|
package node
|
||||||
|
|
||||||
|
import (
|
||||||
|
"html/template"
|
||||||
|
"os"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var nodeListCmd = cli.Command{
|
||||||
|
Name: "ls",
|
||||||
|
Usage: "list nodes",
|
||||||
|
Action: nodeList,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "format output",
|
||||||
|
Value: tmplNodeList,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func nodeList(c *cli.Context) error {
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
list, err := client.NodeList()
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
format := c.String("format") + "\n"
|
||||||
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(format)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
for _, cron := range list {
|
||||||
|
tmpl.Execute(os.Stdout, cron)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// template for node list information
|
||||||
|
var tmplNodeList = "\x1b[33m{{ .Name }} \x1b[0m" + `
|
||||||
|
Address: {{ .Address }}
|
||||||
|
Platform: {{ .OS }}/{{ .Arch }}
|
||||||
|
`
|
1
drone/node/node_update.go
Normal file
1
drone/node/node_update.go
Normal file
@ -0,0 +1 @@
|
|||||||
|
package node
|
16
drone/orgsecret/secret.go
Normal file
16
drone/orgsecret/secret.go
Normal file
@ -0,0 +1,16 @@
|
|||||||
|
package orgsecret
|
||||||
|
|
||||||
|
import "github.com/urfave/cli"
|
||||||
|
|
||||||
|
// Command exports the secret command.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "orgsecret",
|
||||||
|
Usage: "manage organization secrets",
|
||||||
|
Subcommands: []cli.Command{
|
||||||
|
secretCreateCmd,
|
||||||
|
secretDeleteCmd,
|
||||||
|
secretUpdateCmd,
|
||||||
|
secretInfoCmd,
|
||||||
|
secretListCmd,
|
||||||
|
},
|
||||||
|
}
|
57
drone/orgsecret/secret_add.go
Normal file
57
drone/orgsecret/secret_add.go
Normal file
@ -0,0 +1,57 @@
|
|||||||
|
package orgsecret
|
||||||
|
|
||||||
|
import (
|
||||||
|
"io/ioutil"
|
||||||
|
"strings"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var secretCreateCmd = cli.Command{
|
||||||
|
Name: "add",
|
||||||
|
Usage: "adds a secret",
|
||||||
|
ArgsUsage: "[organization] [name] [data]",
|
||||||
|
Action: secretCreate,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "allow-pull-request",
|
||||||
|
Usage: "permit read access to pull requests",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "allow-push-on-pull-request",
|
||||||
|
Usage: "permit write access to pull requests (e.g. allow docker push)",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func secretCreate(c *cli.Context) error {
|
||||||
|
var (
|
||||||
|
namespace = c.Args().First()
|
||||||
|
name = c.Args().Get(1)
|
||||||
|
data = c.Args().Get(2)
|
||||||
|
)
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
secret := &drone.Secret{
|
||||||
|
Name: name,
|
||||||
|
Data: data,
|
||||||
|
PullRequest: c.Bool("allow-pull-request"),
|
||||||
|
PullRequestPush: c.Bool("allow-push-on-pull-request"),
|
||||||
|
}
|
||||||
|
|
||||||
|
if strings.HasPrefix(secret.Data, "@") {
|
||||||
|
path := strings.TrimPrefix(secret.Data, "@")
|
||||||
|
out, ferr := ioutil.ReadFile(path)
|
||||||
|
if ferr != nil {
|
||||||
|
return ferr
|
||||||
|
}
|
||||||
|
secret.Data = string(out)
|
||||||
|
}
|
||||||
|
_, err = client.OrgSecretCreate(namespace, secret)
|
||||||
|
return err
|
||||||
|
}
|
45
drone/orgsecret/secret_info.go
Normal file
45
drone/orgsecret/secret_info.go
Normal file
@ -0,0 +1,45 @@
|
|||||||
|
package orgsecret
|
||||||
|
|
||||||
|
import (
|
||||||
|
"html/template"
|
||||||
|
"os"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var secretInfoCmd = cli.Command{
|
||||||
|
Name: "info",
|
||||||
|
Usage: "display secret info",
|
||||||
|
ArgsUsage: "[organization] [name]",
|
||||||
|
Action: secretInfo,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "format output",
|
||||||
|
Value: tmplSecretList,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func secretInfo(c *cli.Context) error {
|
||||||
|
var (
|
||||||
|
namespace = c.Args().First()
|
||||||
|
name = c.Args().Get(1)
|
||||||
|
format = c.String("format") + "\n"
|
||||||
|
)
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
secret, err := client.OrgSecret(namespace, name)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(format)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return tmpl.Execute(os.Stdout, secret)
|
||||||
|
}
|
62
drone/orgsecret/secret_list.go
Normal file
62
drone/orgsecret/secret_list.go
Normal file
@ -0,0 +1,62 @@
|
|||||||
|
package orgsecret
|
||||||
|
|
||||||
|
import (
|
||||||
|
"html/template"
|
||||||
|
"os"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var secretListCmd = cli.Command{
|
||||||
|
Name: "ls",
|
||||||
|
Usage: "list secrets",
|
||||||
|
ArgsUsage: "",
|
||||||
|
Action: secretList,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "filter",
|
||||||
|
Usage: "filter output by organization",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "format output",
|
||||||
|
Value: tmplSecretList,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func secretList(c *cli.Context) error {
|
||||||
|
filter := c.String("filter")
|
||||||
|
format := c.String("format") + "\n"
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
var list []*drone.Secret
|
||||||
|
if filter == "" {
|
||||||
|
list, err = client.OrgSecretListAll()
|
||||||
|
} else {
|
||||||
|
list, err = client.OrgSecretList(filter)
|
||||||
|
}
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(format)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
for _, secret := range list {
|
||||||
|
tmpl.Execute(os.Stdout, secret)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// template for secret list items
|
||||||
|
var tmplSecretList = "\x1b[33m{{ .Name }} \x1b[0m" + `
|
||||||
|
Organization: {{ .Namespace }}
|
||||||
|
Pull Request Read: {{ .PullRequest }}
|
||||||
|
Pull Request Write: {{ .PullRequestPush }}
|
||||||
|
`
|
27
drone/orgsecret/secret_rm.go
Normal file
27
drone/orgsecret/secret_rm.go
Normal file
@ -0,0 +1,27 @@
|
|||||||
|
package orgsecret
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
)
|
||||||
|
|
||||||
|
var secretDeleteCmd = cli.Command{
|
||||||
|
Name: "rm",
|
||||||
|
Usage: "remove a secret",
|
||||||
|
ArgsUsage: "[organization] [name]",
|
||||||
|
Action: secretDelete,
|
||||||
|
Flags: []cli.Flag{},
|
||||||
|
}
|
||||||
|
|
||||||
|
func secretDelete(c *cli.Context) error {
|
||||||
|
var (
|
||||||
|
namespace = c.Args().First()
|
||||||
|
name = c.Args().Get(1)
|
||||||
|
)
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return client.OrgSecretDelete(namespace, name)
|
||||||
|
}
|
56
drone/orgsecret/secret_set.go
Normal file
56
drone/orgsecret/secret_set.go
Normal file
@ -0,0 +1,56 @@
|
|||||||
|
package orgsecret
|
||||||
|
|
||||||
|
import (
|
||||||
|
"io/ioutil"
|
||||||
|
"strings"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var secretUpdateCmd = cli.Command{
|
||||||
|
Name: "update",
|
||||||
|
Usage: "update a secret",
|
||||||
|
ArgsUsage: "[organization] [name] [data]",
|
||||||
|
Action: secretUpdate,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "allow-pull-request",
|
||||||
|
Usage: "permit read access to pull requests",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "allow-push-on-pull-request",
|
||||||
|
Usage: "permit write access to pull requests (e.g. allow docker push)",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func secretUpdate(c *cli.Context) error {
|
||||||
|
var (
|
||||||
|
namespace = c.Args().First()
|
||||||
|
name = c.Args().Get(1)
|
||||||
|
data = c.Args().Get(2)
|
||||||
|
)
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
secret := &drone.Secret{
|
||||||
|
Name: name,
|
||||||
|
Data: data,
|
||||||
|
PullRequest: c.Bool("allow-pull-request"),
|
||||||
|
PullRequestPush: c.Bool("allow-push-on-pull-request"),
|
||||||
|
}
|
||||||
|
if strings.HasPrefix(secret.Data, "@") {
|
||||||
|
path := strings.TrimPrefix(secret.Data, "@")
|
||||||
|
out, ferr := ioutil.ReadFile(path)
|
||||||
|
if ferr != nil {
|
||||||
|
return ferr
|
||||||
|
}
|
||||||
|
secret.Data = string(out)
|
||||||
|
}
|
||||||
|
_, err = client.OrgSecretUpdate(namespace, secret)
|
||||||
|
return err
|
||||||
|
}
|
64
drone/plugins/admit/admit.go
Normal file
64
drone/plugins/admit/admit.go
Normal file
@ -0,0 +1,64 @@
|
|||||||
|
package admit
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
"github.com/drone/drone-go/plugin/admission"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Command exports the admission command set.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "admit",
|
||||||
|
Usage: "test user admission",
|
||||||
|
ArgsUsage: "user",
|
||||||
|
Action: admit,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "user",
|
||||||
|
Usage: "username",
|
||||||
|
},
|
||||||
|
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "endpoint",
|
||||||
|
Usage: "plugin endpoint",
|
||||||
|
EnvVar: "DRONE_ADMISSION_ENDPOINT",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "secret",
|
||||||
|
Usage: "plugin secret",
|
||||||
|
EnvVar: "DRONE_ADMISSION_SECRET",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "ssl-skip-verify",
|
||||||
|
Usage: "plugin ssl verification disabled",
|
||||||
|
EnvVar: "DRONE_ADMISSION_SKIP_VERIFY",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func admit(c *cli.Context) error {
|
||||||
|
login := c.String("user")
|
||||||
|
if login == "" {
|
||||||
|
login = c.Args().First()
|
||||||
|
}
|
||||||
|
|
||||||
|
req := &admission.Request{
|
||||||
|
User: drone.User{
|
||||||
|
Login: login,
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
client := admission.Client(
|
||||||
|
c.String("endpoint"),
|
||||||
|
c.String("secret"),
|
||||||
|
c.Bool("ssl-skip-verify"),
|
||||||
|
)
|
||||||
|
_, err := client.Admit(context.Background(), req)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
return nil
|
||||||
|
}
|
12
drone/plugins/config/config.go
Normal file
12
drone/plugins/config/config.go
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
package config
|
||||||
|
|
||||||
|
import "github.com/urfave/cli"
|
||||||
|
|
||||||
|
// Command exports the registry command set.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "config",
|
||||||
|
Usage: "config plugin helpers",
|
||||||
|
Subcommands: []cli.Command{
|
||||||
|
configFindCmd,
|
||||||
|
},
|
||||||
|
}
|
106
drone/plugins/config/get.go
Normal file
106
drone/plugins/config/get.go
Normal file
@ -0,0 +1,106 @@
|
|||||||
|
package config
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
"github.com/drone/drone-go/plugin/config"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var configFindCmd = cli.Command{
|
||||||
|
Name: "get",
|
||||||
|
Usage: "get the pipeline configuration",
|
||||||
|
ArgsUsage: "[repo/name]",
|
||||||
|
Action: configFind,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "ref",
|
||||||
|
Usage: "git reference",
|
||||||
|
Value: "refs/heads/master",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "source",
|
||||||
|
Usage: "source branch",
|
||||||
|
Value: "master",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "target",
|
||||||
|
Usage: "target branch",
|
||||||
|
Value: "master",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "before",
|
||||||
|
Usage: "commit sha before the change",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "after",
|
||||||
|
Usage: "commit sha after the change",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "path",
|
||||||
|
Usage: "configuration file path",
|
||||||
|
Value: ".drone.jsonnet",
|
||||||
|
},
|
||||||
|
|
||||||
|
// TODO(bradrydzewski) these parameters should
|
||||||
|
// be defined globally for all plugin commands.
|
||||||
|
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "endpoint",
|
||||||
|
Usage: "plugin endpoint",
|
||||||
|
EnvVar: "DRONE_YAML_ENDPOINT",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "secret",
|
||||||
|
Usage: "plugin secret",
|
||||||
|
EnvVar: "DRONE_YAML_SECRET",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "ssl-skip-verify",
|
||||||
|
Usage: "plugin ssl verification disabled",
|
||||||
|
EnvVar: "DRONE_YAML_SKIP_VERIFY",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func configFind(c *cli.Context) error {
|
||||||
|
slug := c.Args().First()
|
||||||
|
owner, name, err := internal.ParseRepo(slug)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
repo := drone.Repo{
|
||||||
|
Namespace: owner,
|
||||||
|
Name: name,
|
||||||
|
Slug: slug,
|
||||||
|
Config: c.String("path"),
|
||||||
|
}
|
||||||
|
|
||||||
|
build := drone.Build{
|
||||||
|
Ref: c.String("ref"),
|
||||||
|
Before: c.String("before"),
|
||||||
|
After: c.String("after"),
|
||||||
|
Source: c.String("source"),
|
||||||
|
Target: c.String("target"),
|
||||||
|
}
|
||||||
|
|
||||||
|
req := &config.Request{
|
||||||
|
Repo: repo,
|
||||||
|
Build: build,
|
||||||
|
}
|
||||||
|
|
||||||
|
client := config.Client(
|
||||||
|
c.String("endpoint"),
|
||||||
|
c.String("secret"),
|
||||||
|
c.Bool("ssl-skip-verify"),
|
||||||
|
)
|
||||||
|
res, err := client.Find(context.Background(), req)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
println(res.Data)
|
||||||
|
return nil
|
||||||
|
}
|
122
drone/plugins/convert/convert.go
Normal file
122
drone/plugins/convert/convert.go
Normal file
@ -0,0 +1,122 @@
|
|||||||
|
package convert
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"io/ioutil"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
"github.com/drone/drone-go/plugin/converter"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Command exports the registry command set.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "convert",
|
||||||
|
Usage: "convert the pipeline configuration",
|
||||||
|
ArgsUsage: "[repo/name]",
|
||||||
|
Action: convert,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "path",
|
||||||
|
Usage: "path to the configuration file",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "ref",
|
||||||
|
Usage: "git reference",
|
||||||
|
Value: "refs/heads/master",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "source",
|
||||||
|
Usage: "source branch",
|
||||||
|
Value: "master",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "target",
|
||||||
|
Usage: "target branch",
|
||||||
|
Value: "master",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "before",
|
||||||
|
Usage: "commit sha before the change",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "after",
|
||||||
|
Usage: "commit sha after the change",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "repository",
|
||||||
|
Usage: "repository name",
|
||||||
|
},
|
||||||
|
|
||||||
|
// TODO(bradrydzewski) these parameters should
|
||||||
|
// be defined globally for all plugin commands.
|
||||||
|
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "endpoint",
|
||||||
|
Usage: "plugin endpoint",
|
||||||
|
EnvVar: "DRONE_CONVERT_ENDPOINT",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "secret",
|
||||||
|
Usage: "plugin secret",
|
||||||
|
EnvVar: "DRONE_CONVERT_SECRET",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "ssl-skip-verify",
|
||||||
|
Usage: "plugin ssl verification disabled",
|
||||||
|
EnvVar: "DRONE_CONVERT_SKIP_VERIFY",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func convert(c *cli.Context) error {
|
||||||
|
slug := c.String("repository")
|
||||||
|
owner, name, _ := internal.ParseRepo(slug)
|
||||||
|
|
||||||
|
path := c.String("path")
|
||||||
|
if path == "" {
|
||||||
|
path = c.Args().First()
|
||||||
|
}
|
||||||
|
|
||||||
|
raw, err := ioutil.ReadFile(path)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
req := &converter.Request{
|
||||||
|
Repo: drone.Repo{
|
||||||
|
Namespace: owner,
|
||||||
|
Name: name,
|
||||||
|
Slug: slug,
|
||||||
|
Config: path,
|
||||||
|
},
|
||||||
|
Build: drone.Build{
|
||||||
|
Ref: c.String("ref"),
|
||||||
|
Before: c.String("before"),
|
||||||
|
After: c.String("after"),
|
||||||
|
Source: c.String("source"),
|
||||||
|
Target: c.String("target"),
|
||||||
|
},
|
||||||
|
Config: drone.Config{
|
||||||
|
Data: string(raw),
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
client := converter.Client(
|
||||||
|
c.String("endpoint"),
|
||||||
|
c.String("secret"),
|
||||||
|
c.Bool("ssl-skip-verify"),
|
||||||
|
)
|
||||||
|
res, err := client.Convert(context.Background(), req)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
switch {
|
||||||
|
case res == nil:
|
||||||
|
println(string(raw))
|
||||||
|
case res != nil:
|
||||||
|
println(res.Data)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
24
drone/plugins/plugins.go
Normal file
24
drone/plugins/plugins.go
Normal file
@ -0,0 +1,24 @@
|
|||||||
|
package plugins
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/drone/drone-cli/drone/plugins/admit"
|
||||||
|
"github.com/drone/drone-cli/drone/plugins/config"
|
||||||
|
"github.com/drone/drone-cli/drone/plugins/convert"
|
||||||
|
"github.com/drone/drone-cli/drone/plugins/registry"
|
||||||
|
"github.com/drone/drone-cli/drone/plugins/secret"
|
||||||
|
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Command exports the registry command set.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "plugins",
|
||||||
|
Usage: "plugin helper functions",
|
||||||
|
Subcommands: []cli.Command{
|
||||||
|
admit.Command,
|
||||||
|
config.Command,
|
||||||
|
convert.Command,
|
||||||
|
secret.Command,
|
||||||
|
registry.Command,
|
||||||
|
},
|
||||||
|
}
|
123
drone/plugins/registry/list.go
Normal file
123
drone/plugins/registry/list.go
Normal file
@ -0,0 +1,123 @@
|
|||||||
|
package registry
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
"os"
|
||||||
|
"text/template"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
"github.com/drone/drone-go/plugin/registry"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var registryListCmd = cli.Command{
|
||||||
|
Name: "list",
|
||||||
|
Usage: "list the registry credentials",
|
||||||
|
Action: registryList,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "ref",
|
||||||
|
Usage: "git reference",
|
||||||
|
Value: "refs/heads/master",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "source",
|
||||||
|
Usage: "source branch",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "target",
|
||||||
|
Usage: "target branch",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "before",
|
||||||
|
Usage: "commit sha before the change",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "after",
|
||||||
|
Usage: "commit sha after the change",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "event",
|
||||||
|
Usage: "build event",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "repo",
|
||||||
|
Usage: "repository name",
|
||||||
|
},
|
||||||
|
|
||||||
|
// TODO(bradrydzewski) these parameters should
|
||||||
|
// be defined globally for all plugin commands.
|
||||||
|
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "endpoint",
|
||||||
|
Usage: "plugin endpoint",
|
||||||
|
EnvVar: "DRONE_REGISTRY_ENDPOINT",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "secret",
|
||||||
|
Usage: "plugin secret",
|
||||||
|
EnvVar: "DRONE_REGISTRY_SECRET",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "ssl-skip-verify",
|
||||||
|
Usage: "plugin ssl verification disabled",
|
||||||
|
EnvVar: "DRONE_REGISTRY_VERIFY",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Value: tmplList,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func registryList(c *cli.Context) error {
|
||||||
|
slug := c.String("repo")
|
||||||
|
owner, name, _ := internal.ParseRepo(slug)
|
||||||
|
|
||||||
|
repo := drone.Repo{
|
||||||
|
Namespace: owner,
|
||||||
|
Name: name,
|
||||||
|
Slug: slug,
|
||||||
|
}
|
||||||
|
|
||||||
|
build := drone.Build{
|
||||||
|
Ref: c.String("ref"),
|
||||||
|
Before: c.String("before"),
|
||||||
|
After: c.String("after"),
|
||||||
|
Source: c.String("source"),
|
||||||
|
Target: c.String("target"),
|
||||||
|
Event: c.String("event"),
|
||||||
|
}
|
||||||
|
|
||||||
|
req := ®istry.Request{
|
||||||
|
Repo: repo,
|
||||||
|
Build: build,
|
||||||
|
}
|
||||||
|
|
||||||
|
client := registry.Client(
|
||||||
|
c.String("endpoint"),
|
||||||
|
c.String("secret"),
|
||||||
|
c.Bool("ssl-skip-verify"),
|
||||||
|
)
|
||||||
|
list, err := client.List(context.Background(), req)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
format := c.String("format") + "\n"
|
||||||
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(format)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
for _, item := range list {
|
||||||
|
tmpl.Execute(os.Stdout, item)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
var tmplList = "\x1b[33m{{ .Address }} \x1b[0m" + `
|
||||||
|
Username: {{ .Username }}
|
||||||
|
Password: {{ .Password }}
|
||||||
|
`
|
@ -5,12 +5,8 @@ import "github.com/urfave/cli"
|
|||||||
// Command exports the registry command set.
|
// Command exports the registry command set.
|
||||||
var Command = cli.Command{
|
var Command = cli.Command{
|
||||||
Name: "registry",
|
Name: "registry",
|
||||||
Usage: "manage registries",
|
Usage: "registry plugin helpers",
|
||||||
Subcommands: []cli.Command{
|
Subcommands: []cli.Command{
|
||||||
registryCreateCmd,
|
|
||||||
registryDeleteCmd,
|
|
||||||
registryUpdateCmd,
|
|
||||||
registryInfoCmd,
|
|
||||||
registryListCmd,
|
registryListCmd,
|
||||||
},
|
},
|
||||||
}
|
}
|
112
drone/plugins/secret/get.go
Normal file
112
drone/plugins/secret/get.go
Normal file
@ -0,0 +1,112 @@
|
|||||||
|
package secret
|
||||||
|
|
||||||
|
import (
|
||||||
|
"context"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-go/drone"
|
||||||
|
"github.com/drone/drone-go/plugin/secret"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var secretFindCmd = cli.Command{
|
||||||
|
Name: "get",
|
||||||
|
Usage: "get the named secret",
|
||||||
|
ArgsUsage: "secret",
|
||||||
|
Action: secretFind,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "ref",
|
||||||
|
Usage: "git reference",
|
||||||
|
Value: "refs/heads/master",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "source",
|
||||||
|
Usage: "source branch",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "target",
|
||||||
|
Usage: "target branch",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "before",
|
||||||
|
Usage: "commit sha before the change",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "after",
|
||||||
|
Usage: "commit sha after the change",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "event",
|
||||||
|
Usage: "build event",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "repo",
|
||||||
|
Usage: "repository name",
|
||||||
|
},
|
||||||
|
|
||||||
|
// TODO(bradrydzewski) these parameters should
|
||||||
|
// be defined globally for all plugin commands.
|
||||||
|
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "endpoint",
|
||||||
|
Usage: "plugin endpoint",
|
||||||
|
EnvVar: "DRONE_SECRET_ENDPOINT",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "secret",
|
||||||
|
Usage: "plugin secret",
|
||||||
|
EnvVar: "DRONE_SECRET_SECRET",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "ssl-skip-verify",
|
||||||
|
Usage: "plugin ssl verification disabled",
|
||||||
|
EnvVar: "DRONE_SECRET_VERIFY",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func secretFind(c *cli.Context) error {
|
||||||
|
path := c.Args().First()
|
||||||
|
key := c.Args().Get(1)
|
||||||
|
|
||||||
|
slug := c.String("repo")
|
||||||
|
owner, name, err := internal.ParseRepo(slug)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
repo := drone.Repo{
|
||||||
|
Namespace: owner,
|
||||||
|
Name: name,
|
||||||
|
Slug: slug,
|
||||||
|
}
|
||||||
|
|
||||||
|
build := drone.Build{
|
||||||
|
Ref: c.String("ref"),
|
||||||
|
Before: c.String("before"),
|
||||||
|
After: c.String("after"),
|
||||||
|
Source: c.String("source"),
|
||||||
|
Target: c.String("target"),
|
||||||
|
Event: c.String("event"),
|
||||||
|
}
|
||||||
|
|
||||||
|
req := &secret.Request{
|
||||||
|
Path: path,
|
||||||
|
Name: key,
|
||||||
|
Repo: repo,
|
||||||
|
Build: build,
|
||||||
|
}
|
||||||
|
|
||||||
|
client := secret.Client(
|
||||||
|
c.String("endpoint"),
|
||||||
|
c.String("secret"),
|
||||||
|
c.Bool("ssl-skip-verify"),
|
||||||
|
)
|
||||||
|
res, err := client.Find(context.Background(), req)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
println(res.Data)
|
||||||
|
return nil
|
||||||
|
}
|
12
drone/plugins/secret/secret.go
Normal file
12
drone/plugins/secret/secret.go
Normal file
@ -0,0 +1,12 @@
|
|||||||
|
package secret
|
||||||
|
|
||||||
|
import "github.com/urfave/cli"
|
||||||
|
|
||||||
|
// Command exports the registry command set.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "secret",
|
||||||
|
Usage: "secret plugin helpers",
|
||||||
|
Subcommands: []cli.Command{
|
||||||
|
secretFindCmd,
|
||||||
|
},
|
||||||
|
}
|
14
drone/queue/queue.go
Normal file
14
drone/queue/queue.go
Normal file
@ -0,0 +1,14 @@
|
|||||||
|
package queue
|
||||||
|
|
||||||
|
import "github.com/urfave/cli"
|
||||||
|
|
||||||
|
// Command exports the queue command set.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "queue",
|
||||||
|
Usage: "queue operations",
|
||||||
|
Subcommands: []cli.Command{
|
||||||
|
queueListCmd,
|
||||||
|
queuePauseCmd,
|
||||||
|
queueResumeCmd,
|
||||||
|
},
|
||||||
|
}
|
59
drone/queue/queue_list.go
Normal file
59
drone/queue/queue_list.go
Normal file
@ -0,0 +1,59 @@
|
|||||||
|
package queue
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"os"
|
||||||
|
"text/template"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var queueListCmd = cli.Command{
|
||||||
|
Name: "ls",
|
||||||
|
Usage: "list queue items",
|
||||||
|
Action: queueList,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "format output",
|
||||||
|
Value: tmplStage,
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func queueList(c *cli.Context) (err error) {
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
builds, err := client.Queue()
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
if len(builds) == 0 {
|
||||||
|
fmt.Println("there are no pending or running builds")
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format") + "\n")
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
for _, build := range builds {
|
||||||
|
tmpl.Execute(os.Stdout, build)
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
var tmplStage = "\x1b[33mitem #{{ .ID }} \x1b[0m" + `
|
||||||
|
Status: {{ .Status }}
|
||||||
|
Machine: {{ .Machine }}
|
||||||
|
OS: {{ .OS }}
|
||||||
|
Arch: {{ .Arch }}
|
||||||
|
Variant: {{ .Variant }}
|
||||||
|
Version: {{ .Kernel }}
|
||||||
|
`
|
20
drone/queue/queue_pause.go
Normal file
20
drone/queue/queue_pause.go
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
package queue
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var queuePauseCmd = cli.Command{
|
||||||
|
Name: "pause",
|
||||||
|
Usage: "pause queue operations",
|
||||||
|
Action: queuePause,
|
||||||
|
}
|
||||||
|
|
||||||
|
func queuePause(c *cli.Context) (err error) {
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return client.QueuePause()
|
||||||
|
}
|
20
drone/queue/queue_resume.go
Normal file
20
drone/queue/queue_resume.go
Normal file
@ -0,0 +1,20 @@
|
|||||||
|
package queue
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
var queueResumeCmd = cli.Command{
|
||||||
|
Name: "resume",
|
||||||
|
Usage: "resume queue operations",
|
||||||
|
Action: queueResume,
|
||||||
|
}
|
||||||
|
|
||||||
|
func queueResume(c *cli.Context) (err error) {
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return client.QueueResume()
|
||||||
|
}
|
@ -1,75 +0,0 @@
|
|||||||
package registry
|
|
||||||
|
|
||||||
import (
|
|
||||||
"io/ioutil"
|
|
||||||
"strings"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
|
||||||
"github.com/drone/drone-go/drone"
|
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
)
|
|
||||||
|
|
||||||
var registryCreateCmd = cli.Command{
|
|
||||||
Name: "add",
|
|
||||||
Usage: "adds a registry",
|
|
||||||
ArgsUsage: "[repo/name]",
|
|
||||||
Action: registryCreate,
|
|
||||||
Flags: []cli.Flag{
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "repository",
|
|
||||||
Usage: "repository name (e.g. octocat/hello-world)",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "hostname",
|
|
||||||
Usage: "registry hostname",
|
|
||||||
Value: "docker.io",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "username",
|
|
||||||
Usage: "registry username",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "password",
|
|
||||||
Usage: "registry password",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
func registryCreate(c *cli.Context) error {
|
|
||||||
var (
|
|
||||||
hostname = c.String("hostname")
|
|
||||||
username = c.String("username")
|
|
||||||
password = c.String("password")
|
|
||||||
reponame = c.String("repository")
|
|
||||||
)
|
|
||||||
if reponame == "" {
|
|
||||||
reponame = c.Args().First()
|
|
||||||
}
|
|
||||||
owner, name, err := internal.ParseRepo(reponame)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
client, err := internal.NewClient(c)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
registry := &drone.Registry{
|
|
||||||
Address: hostname,
|
|
||||||
Username: username,
|
|
||||||
Password: password,
|
|
||||||
}
|
|
||||||
if strings.HasPrefix(registry.Password, "@") {
|
|
||||||
path := strings.TrimPrefix(registry.Password, "@")
|
|
||||||
out, ferr := ioutil.ReadFile(path)
|
|
||||||
if ferr != nil {
|
|
||||||
return ferr
|
|
||||||
}
|
|
||||||
registry.Password = string(out)
|
|
||||||
}
|
|
||||||
_, err = client.RegistryCreate(owner, name, registry)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
return nil
|
|
||||||
}
|
|
@ -1,62 +0,0 @@
|
|||||||
package registry
|
|
||||||
|
|
||||||
import (
|
|
||||||
"html/template"
|
|
||||||
"os"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
)
|
|
||||||
|
|
||||||
var registryInfoCmd = cli.Command{
|
|
||||||
Name: "info",
|
|
||||||
Usage: "display registry info",
|
|
||||||
ArgsUsage: "[repo/name]",
|
|
||||||
Action: registryInfo,
|
|
||||||
Flags: []cli.Flag{
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "repository",
|
|
||||||
Usage: "repository name (e.g. octocat/hello-world)",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "hostname",
|
|
||||||
Usage: "registry hostname",
|
|
||||||
Value: "docker.io",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "format",
|
|
||||||
Usage: "format output",
|
|
||||||
Value: tmplRegistryList,
|
|
||||||
Hidden: true,
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
func registryInfo(c *cli.Context) error {
|
|
||||||
var (
|
|
||||||
hostname = c.String("hostname")
|
|
||||||
reponame = c.String("repository")
|
|
||||||
format = c.String("format") + "\n"
|
|
||||||
)
|
|
||||||
if reponame == "" {
|
|
||||||
reponame = c.Args().First()
|
|
||||||
}
|
|
||||||
owner, name, err := internal.ParseRepo(reponame)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
client, err := internal.NewClient(c)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
registry, err := client.Registry(owner, name, hostname)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
tmpl, err := template.New("_").Parse(format)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
return tmpl.Execute(os.Stdout, registry)
|
|
||||||
}
|
|
@ -1,65 +0,0 @@
|
|||||||
package registry
|
|
||||||
|
|
||||||
import (
|
|
||||||
"html/template"
|
|
||||||
"os"
|
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
|
||||||
)
|
|
||||||
|
|
||||||
var registryListCmd = cli.Command{
|
|
||||||
Name: "ls",
|
|
||||||
Usage: "list registries",
|
|
||||||
ArgsUsage: "[repo/name]",
|
|
||||||
Action: registryList,
|
|
||||||
Flags: []cli.Flag{
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "repository",
|
|
||||||
Usage: "repository name (e.g. octocat/hello-world)",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "format",
|
|
||||||
Usage: "format output",
|
|
||||||
Value: tmplRegistryList,
|
|
||||||
Hidden: true,
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
func registryList(c *cli.Context) error {
|
|
||||||
var (
|
|
||||||
format = c.String("format") + "\n"
|
|
||||||
reponame = c.String("repository")
|
|
||||||
)
|
|
||||||
if reponame == "" {
|
|
||||||
reponame = c.Args().First()
|
|
||||||
}
|
|
||||||
owner, name, err := internal.ParseRepo(reponame)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
client, err := internal.NewClient(c)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
list, err := client.RegistryList(owner, name)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
tmpl, err := template.New("_").Parse(format)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
for _, registry := range list {
|
|
||||||
tmpl.Execute(os.Stdout, registry)
|
|
||||||
}
|
|
||||||
return nil
|
|
||||||
}
|
|
||||||
|
|
||||||
// template for build list information
|
|
||||||
var tmplRegistryList = "\x1b[33m{{ .Address }} \x1b[0m" + `
|
|
||||||
Username: {{ .Username }}
|
|
||||||
Email: {{ .Email }}
|
|
||||||
`
|
|
@ -1,44 +0,0 @@
|
|||||||
package registry
|
|
||||||
|
|
||||||
import (
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
)
|
|
||||||
|
|
||||||
var registryDeleteCmd = cli.Command{
|
|
||||||
Name: "rm",
|
|
||||||
Usage: "remove a registry",
|
|
||||||
ArgsUsage: "[repo/name]",
|
|
||||||
Action: registryDelete,
|
|
||||||
Flags: []cli.Flag{
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "repository",
|
|
||||||
Usage: "repository name (e.g. octocat/hello-world)",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "hostname",
|
|
||||||
Usage: "registry hostname",
|
|
||||||
Value: "docker.io",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
func registryDelete(c *cli.Context) error {
|
|
||||||
var (
|
|
||||||
hostname = c.String("hostname")
|
|
||||||
reponame = c.String("repository")
|
|
||||||
)
|
|
||||||
if reponame == "" {
|
|
||||||
reponame = c.Args().First()
|
|
||||||
}
|
|
||||||
owner, name, err := internal.ParseRepo(reponame)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
client, err := internal.NewClient(c)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
return client.RegistryDelete(owner, name, hostname)
|
|
||||||
}
|
|
@ -1,75 +0,0 @@
|
|||||||
package registry
|
|
||||||
|
|
||||||
import (
|
|
||||||
"io/ioutil"
|
|
||||||
"strings"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
|
||||||
"github.com/drone/drone-go/drone"
|
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
)
|
|
||||||
|
|
||||||
var registryUpdateCmd = cli.Command{
|
|
||||||
Name: "update",
|
|
||||||
Usage: "update a registry",
|
|
||||||
ArgsUsage: "[repo/name]",
|
|
||||||
Action: registryUpdate,
|
|
||||||
Flags: []cli.Flag{
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "repository",
|
|
||||||
Usage: "repository name (e.g. octocat/hello-world)",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "hostname",
|
|
||||||
Usage: "registry hostname",
|
|
||||||
Value: "docker.io",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "username",
|
|
||||||
Usage: "registry username",
|
|
||||||
},
|
|
||||||
cli.StringFlag{
|
|
||||||
Name: "password",
|
|
||||||
Usage: "registry password",
|
|
||||||
},
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
|
||||||
func registryUpdate(c *cli.Context) error {
|
|
||||||
var (
|
|
||||||
hostname = c.String("hostname")
|
|
||||||
username = c.String("username")
|
|
||||||
password = c.String("password")
|
|
||||||
reponame = c.String("repository")
|
|
||||||
)
|
|
||||||
if reponame == "" {
|
|
||||||
reponame = c.Args().First()
|
|
||||||
}
|
|
||||||
owner, name, err := internal.ParseRepo(reponame)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
client, err := internal.NewClient(c)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
registry := &drone.Registry{
|
|
||||||
Address: hostname,
|
|
||||||
Username: username,
|
|
||||||
Password: password,
|
|
||||||
}
|
|
||||||
if strings.HasPrefix(registry.Password, "@") {
|
|
||||||
path := strings.TrimPrefix(registry.Password, "@")
|
|
||||||
out, ferr := ioutil.ReadFile(path)
|
|
||||||
if ferr != nil {
|
|
||||||
return ferr
|
|
||||||
}
|
|
||||||
registry.Password = string(out)
|
|
||||||
}
|
|
||||||
_, err = client.RegistryUpdate(owner, name, registry)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
return nil
|
|
||||||
}
|
|
@ -8,8 +8,8 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
var repoAddCmd = cli.Command{
|
var repoAddCmd = cli.Command{
|
||||||
Name: "add",
|
Name: "enable",
|
||||||
Usage: "add a repository",
|
Usage: "enable a repository",
|
||||||
ArgsUsage: "<repo/name>",
|
ArgsUsage: "<repo/name>",
|
||||||
Action: repoAdd,
|
Action: repoAdd,
|
||||||
}
|
}
|
||||||
@ -26,7 +26,7 @@ func repoAdd(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
if _, err := client.RepoPost(owner, name); err != nil {
|
if _, err := client.RepoEnable(owner, name); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
fmt.Printf("Successfully activated repository %s/%s\n", owner, name)
|
fmt.Printf("Successfully activated repository %s/%s\n", owner, name)
|
||||||
|
@ -5,6 +5,7 @@ import (
|
|||||||
"text/template"
|
"text/template"
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
"github.com/urfave/cli"
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -39,7 +40,7 @@ func repoInfo(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format"))
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format"))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -47,13 +48,12 @@ func repoInfo(c *cli.Context) error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// template for repo information
|
// template for repo information
|
||||||
var tmplRepoInfo = `Owner: {{ .Owner }}
|
var tmplRepoInfo = `Owner: {{ .Namespace }}
|
||||||
Repo: {{ .Name }}
|
Repo: {{ .Name }}
|
||||||
Type: {{ .Kind }}
|
|
||||||
Config: {{ .Config }}
|
Config: {{ .Config }}
|
||||||
Visibility: {{ .Visibility }}
|
Visibility: {{ .Visibility }}
|
||||||
Private: {{ .IsPrivate }}
|
Private: {{ .Private }}
|
||||||
Trusted: {{ .IsTrusted }}
|
Trusted: {{ .Trusted }}
|
||||||
Gated: {{ .IsGated }}
|
Protected: {{ .Protected }}
|
||||||
Remote: {{ .Clone }}
|
Remote: {{ .HTTPURL }}
|
||||||
`
|
`
|
||||||
|
@ -5,6 +5,7 @@ import (
|
|||||||
"text/template"
|
"text/template"
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
"github.com/urfave/cli"
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -23,6 +24,10 @@ var repoListCmd = cli.Command{
|
|||||||
Name: "org",
|
Name: "org",
|
||||||
Usage: "filter by organization",
|
Usage: "filter by organization",
|
||||||
},
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "active",
|
||||||
|
Usage: "filter active repositories only",
|
||||||
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -37,14 +42,17 @@ func repoList(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format") + "\n")
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format") + "\n")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
org := c.String("org")
|
org, active := c.String("org"), c.Bool("active")
|
||||||
for _, repo := range repos {
|
for _, repo := range repos {
|
||||||
if org != "" && org != repo.Owner {
|
if org != "" && org != repo.Namespace {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
if !repo.Active && active {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
tmpl.Execute(os.Stdout, repo)
|
tmpl.Execute(os.Stdout, repo)
|
||||||
@ -53,4 +61,4 @@ func repoList(c *cli.Context) error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// template for repository list items
|
// template for repository list items
|
||||||
var tmplRepoList = `{{ .FullName }}`
|
var tmplRepoList = `{{ .Slug }}`
|
||||||
|
@ -9,8 +9,8 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
var repoRemoveCmd = cli.Command{
|
var repoRemoveCmd = cli.Command{
|
||||||
Name: "rm",
|
Name: "disable",
|
||||||
Usage: "remove a repository",
|
Usage: "disable a repository",
|
||||||
ArgsUsage: "<repo/name>",
|
ArgsUsage: "<repo/name>",
|
||||||
Action: repoRemove,
|
Action: repoRemove,
|
||||||
}
|
}
|
||||||
@ -27,7 +27,7 @@ func repoRemove(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
if err := client.RepoDel(owner, name); err != nil {
|
if err := client.RepoDisable(owner, name); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
fmt.Printf("Successfully removed repository %s/%s\n", owner, name)
|
fmt.Printf("Successfully removed repository %s/%s\n", owner, name)
|
||||||
|
@ -5,6 +5,7 @@ import (
|
|||||||
"text/template"
|
"text/template"
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
"github.com/urfave/cli"
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -28,21 +29,17 @@ func repoSync(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
repos, err := client.RepoListOpts(true, true)
|
repos, err := client.RepoListSync()
|
||||||
if err != nil || len(repos) == 0 {
|
if err != nil || len(repos) == 0 {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format") + "\n")
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format") + "\n")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
org := c.String("org")
|
|
||||||
for _, repo := range repos {
|
for _, repo := range repos {
|
||||||
if org != "" && org != repo.Owner {
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
tmpl.Execute(os.Stdout, repo)
|
tmpl.Execute(os.Stdout, repo)
|
||||||
}
|
}
|
||||||
return nil
|
return nil
|
||||||
|
@ -21,8 +21,8 @@ var repoUpdateCmd = cli.Command{
|
|||||||
Usage: "repository is trusted",
|
Usage: "repository is trusted",
|
||||||
},
|
},
|
||||||
cli.BoolFlag{
|
cli.BoolFlag{
|
||||||
Name: "gated",
|
Name: "protected",
|
||||||
Usage: "repository is gated",
|
Usage: "repository is protected",
|
||||||
},
|
},
|
||||||
cli.DurationFlag{
|
cli.DurationFlag{
|
||||||
Name: "timeout",
|
Name: "timeout",
|
||||||
@ -32,6 +32,22 @@ var repoUpdateCmd = cli.Command{
|
|||||||
Name: "visibility",
|
Name: "visibility",
|
||||||
Usage: "repository visibility",
|
Usage: "repository visibility",
|
||||||
},
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "ignore-forks",
|
||||||
|
Usage: "ignore forks",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "ignore-pull-requests",
|
||||||
|
Usage: "ignore pull requests",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "auto-cancel-pull-requests",
|
||||||
|
Usage: "automatically cancel pending pull request builds",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "auto-cancel-pushes",
|
||||||
|
Usage: "automatically cancel pending push builds",
|
||||||
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "config",
|
Name: "config",
|
||||||
Usage: "repository configuration path (e.g. .drone.yml)",
|
Usage: "repository configuration path (e.g. .drone.yml)",
|
||||||
@ -64,17 +80,21 @@ func repoUpdate(c *cli.Context) error {
|
|||||||
config = c.String("config")
|
config = c.String("config")
|
||||||
timeout = c.Duration("timeout")
|
timeout = c.Duration("timeout")
|
||||||
trusted = c.Bool("trusted")
|
trusted = c.Bool("trusted")
|
||||||
gated = c.Bool("gated")
|
protected = c.Bool("protected")
|
||||||
|
ignoreForks = c.Bool("ignore-forks")
|
||||||
|
ignorePulls = c.Bool("ignore-pull-requests")
|
||||||
|
cancelPulls = c.Bool("auto-cancel-pull-requests")
|
||||||
|
cancelPush = c.Bool("auto-cancel-pushes")
|
||||||
buildCounter = c.Int("build-counter")
|
buildCounter = c.Int("build-counter")
|
||||||
unsafe = c.Bool("unsafe")
|
unsafe = c.Bool("unsafe")
|
||||||
)
|
)
|
||||||
|
|
||||||
patch := new(drone.RepoPatch)
|
patch := new(drone.RepoPatch)
|
||||||
if c.IsSet("trusted") {
|
if c.IsSet("trusted") {
|
||||||
patch.IsTrusted = &trusted
|
patch.Trusted = &trusted
|
||||||
}
|
}
|
||||||
if c.IsSet("gated") {
|
if c.IsSet("protected") {
|
||||||
patch.IsGated = &gated
|
patch.Protected = &protected
|
||||||
}
|
}
|
||||||
if c.IsSet("timeout") {
|
if c.IsSet("timeout") {
|
||||||
v := int64(timeout / time.Minute)
|
v := int64(timeout / time.Minute)
|
||||||
@ -83,6 +103,18 @@ func repoUpdate(c *cli.Context) error {
|
|||||||
if c.IsSet("config") {
|
if c.IsSet("config") {
|
||||||
patch.Config = &config
|
patch.Config = &config
|
||||||
}
|
}
|
||||||
|
if c.IsSet("ignore-forks") {
|
||||||
|
patch.IgnoreForks = &ignoreForks
|
||||||
|
}
|
||||||
|
if c.IsSet("ignore-pull-requests") {
|
||||||
|
patch.IgnorePulls = &ignorePulls
|
||||||
|
}
|
||||||
|
if c.IsSet("auto-cancel-pull-requests") {
|
||||||
|
patch.CancelPulls = &cancelPulls
|
||||||
|
}
|
||||||
|
if c.IsSet("auto-cancel-pushes") {
|
||||||
|
patch.CancelPush = &cancelPush
|
||||||
|
}
|
||||||
if c.IsSet("visibility") {
|
if c.IsSet("visibility") {
|
||||||
switch visibility {
|
switch visibility {
|
||||||
case "public", "private", "internal":
|
case "public", "private", "internal":
|
||||||
@ -93,10 +125,10 @@ func repoUpdate(c *cli.Context) error {
|
|||||||
fmt.Printf("Setting the build counter is an unsafe operation that could put your repository in an inconsistent state. Please use --unsafe to proceed")
|
fmt.Printf("Setting the build counter is an unsafe operation that could put your repository in an inconsistent state. Please use --unsafe to proceed")
|
||||||
}
|
}
|
||||||
if c.IsSet("build-counter") && unsafe {
|
if c.IsSet("build-counter") && unsafe {
|
||||||
patch.BuildCounter = &buildCounter
|
patch.Counter = &buildCounter
|
||||||
}
|
}
|
||||||
|
|
||||||
if _, err := client.RepoPatch(owner, name, patch); err != nil {
|
if _, err := client.RepoUpdate(owner, name, patch); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
fmt.Printf("Successfully updated repository %s/%s\n", owner, name)
|
fmt.Printf("Successfully updated repository %s/%s\n", owner, name)
|
||||||
|
@ -25,16 +25,16 @@ var secretCreateCmd = cli.Command{
|
|||||||
Usage: "secret name",
|
Usage: "secret name",
|
||||||
},
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "value",
|
Name: "data",
|
||||||
Usage: "secret value",
|
Usage: "secret value",
|
||||||
},
|
},
|
||||||
cli.StringSliceFlag{
|
cli.BoolFlag{
|
||||||
Name: "event",
|
Name: "allow-pull-request",
|
||||||
Usage: "secret limited to these events",
|
Usage: "permit read access to pull requests",
|
||||||
},
|
},
|
||||||
cli.StringSliceFlag{
|
cli.BoolFlag{
|
||||||
Name: "image",
|
Name: "allow-push-on-pull-request",
|
||||||
Usage: "secret limited to these images",
|
Usage: "permit write access to pull requests (e.g. allow docker push)",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
@ -53,28 +53,20 @@ func secretCreate(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
secret := &drone.Secret{
|
secret := &drone.Secret{
|
||||||
Name: c.String("name"),
|
Name: c.String("name"),
|
||||||
Value: c.String("value"),
|
Data: c.String("data"),
|
||||||
Images: c.StringSlice("image"),
|
PullRequest: c.Bool("allow-pull-request"),
|
||||||
Events: c.StringSlice("event"),
|
PullRequestPush: c.Bool("allow-push-on-pull-request"),
|
||||||
}
|
}
|
||||||
if len(secret.Events) == 0 {
|
|
||||||
secret.Events = defaultSecretEvents
|
if strings.HasPrefix(secret.Data, "@") {
|
||||||
}
|
path := strings.TrimPrefix(secret.Data, "@")
|
||||||
if strings.HasPrefix(secret.Value, "@") {
|
|
||||||
path := strings.TrimPrefix(secret.Value, "@")
|
|
||||||
out, ferr := ioutil.ReadFile(path)
|
out, ferr := ioutil.ReadFile(path)
|
||||||
if ferr != nil {
|
if ferr != nil {
|
||||||
return ferr
|
return ferr
|
||||||
}
|
}
|
||||||
secret.Value = string(out)
|
secret.Data = string(out)
|
||||||
}
|
}
|
||||||
_, err = client.SecretCreate(owner, name, secret)
|
_, err = client.SecretCreate(owner, name, secret)
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
var defaultSecretEvents = []string{
|
|
||||||
drone.EventPush,
|
|
||||||
drone.EventTag,
|
|
||||||
drone.EventDeploy,
|
|
||||||
}
|
|
||||||
|
@ -5,9 +5,9 @@ import (
|
|||||||
"html/template"
|
"html/template"
|
||||||
"os"
|
"os"
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
var secretInfoCmd = cli.Command{
|
var secretInfoCmd = cli.Command{
|
||||||
@ -25,10 +25,9 @@ var secretInfoCmd = cli.Command{
|
|||||||
Usage: "secret name",
|
Usage: "secret name",
|
||||||
},
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "format",
|
Name: "format",
|
||||||
Usage: "format output",
|
Usage: "format output",
|
||||||
Value: tmplSecretList,
|
Value: tmplSecretList,
|
||||||
Hidden: true,
|
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
@ -57,7 +56,7 @@ func secretInfo(c *cli.Context) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
tmpl, err := template.New("_").Funcs(secretFuncMap).Parse(format)
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(format)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -3,11 +3,10 @@ package secret
|
|||||||
import (
|
import (
|
||||||
"html/template"
|
"html/template"
|
||||||
"os"
|
"os"
|
||||||
"strings"
|
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
var secretListCmd = cli.Command{
|
var secretListCmd = cli.Command{
|
||||||
@ -21,10 +20,9 @@ var secretListCmd = cli.Command{
|
|||||||
Usage: "repository name (e.g. octocat/hello-world)",
|
Usage: "repository name (e.g. octocat/hello-world)",
|
||||||
},
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "format",
|
Name: "format",
|
||||||
Usage: "format output",
|
Usage: "format output",
|
||||||
Value: tmplSecretList,
|
Value: tmplSecretList,
|
||||||
Hidden: true,
|
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
@ -49,28 +47,18 @@ func secretList(c *cli.Context) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
tmpl, err := template.New("_").Funcs(secretFuncMap).Parse(format)
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(format)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
for _, registry := range list {
|
for _, secret := range list {
|
||||||
tmpl.Execute(os.Stdout, registry)
|
tmpl.Execute(os.Stdout, secret)
|
||||||
}
|
}
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
// template for secret list items
|
// template for secret list items
|
||||||
var tmplSecretList = "\x1b[33m{{ .Name }} \x1b[0m" + `
|
var tmplSecretList = "\x1b[33m{{ .Name }} \x1b[0m" + `
|
||||||
Events: {{ list .Events }}
|
Pull Request Read: {{ .PullRequest }}
|
||||||
{{- if .Images }}
|
Pull Request Write: {{ .PullRequestPush }}
|
||||||
Images: {{ list .Images }}
|
|
||||||
{{- else }}
|
|
||||||
Images: <any>
|
|
||||||
{{- end }}
|
|
||||||
`
|
`
|
||||||
|
|
||||||
var secretFuncMap = template.FuncMap{
|
|
||||||
"list": func(s []string) string {
|
|
||||||
return strings.Join(s, ", ")
|
|
||||||
},
|
|
||||||
}
|
|
||||||
|
@ -25,16 +25,16 @@ var secretUpdateCmd = cli.Command{
|
|||||||
Usage: "secret name",
|
Usage: "secret name",
|
||||||
},
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "value",
|
Name: "data",
|
||||||
Usage: "secret value",
|
Usage: "secret value",
|
||||||
},
|
},
|
||||||
cli.StringSliceFlag{
|
cli.BoolFlag{
|
||||||
Name: "event",
|
Name: "allow-pull-request",
|
||||||
Usage: "secret limited to these events",
|
Usage: "permit read access to pull requests",
|
||||||
},
|
},
|
||||||
cli.StringSliceFlag{
|
cli.BoolFlag{
|
||||||
Name: "image",
|
Name: "allow-push-on-pull-request",
|
||||||
Usage: "secret limited to these images",
|
Usage: "permit write access to pull requests (e.g. allow docker push)",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
@ -53,18 +53,18 @@ func secretUpdate(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
secret := &drone.Secret{
|
secret := &drone.Secret{
|
||||||
Name: c.String("name"),
|
Name: c.String("name"),
|
||||||
Value: c.String("value"),
|
Data: c.String("data"),
|
||||||
Images: c.StringSlice("image"),
|
PullRequest: c.Bool("allow-pull-request"),
|
||||||
Events: c.StringSlice("event"),
|
PullRequestPush: c.Bool("allow-push-on-pull-request"),
|
||||||
}
|
}
|
||||||
if strings.HasPrefix(secret.Value, "@") {
|
if strings.HasPrefix(secret.Data, "@") {
|
||||||
path := strings.TrimPrefix(secret.Value, "@")
|
path := strings.TrimPrefix(secret.Data, "@")
|
||||||
out, ferr := ioutil.ReadFile(path)
|
out, ferr := ioutil.ReadFile(path)
|
||||||
if ferr != nil {
|
if ferr != nil {
|
||||||
return ferr
|
return ferr
|
||||||
}
|
}
|
||||||
secret.Value = string(out)
|
secret.Data = string(out)
|
||||||
}
|
}
|
||||||
_, err = client.SecretUpdate(owner, name, secret)
|
_, err = client.SecretUpdate(owner, name, secret)
|
||||||
return err
|
return err
|
||||||
|
@ -4,21 +4,20 @@ import (
|
|||||||
"os"
|
"os"
|
||||||
"text/template"
|
"text/template"
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
var serverCreateCmd = cli.Command{
|
var serverCreateCmd = cli.Command{
|
||||||
Name: "create",
|
Name: "create",
|
||||||
Usage: "crate a new server",
|
Usage: "create a new server",
|
||||||
Action: serverCreate,
|
Action: serverCreate,
|
||||||
Flags: []cli.Flag{
|
Flags: []cli.Flag{
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "format",
|
Name: "format",
|
||||||
Usage: "format output",
|
Usage: "format output",
|
||||||
Value: tmplServerCreate,
|
Value: tmplServerCreate,
|
||||||
Hidden: true,
|
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
@ -34,7 +33,7 @@ func serverCreate(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format") + "\n")
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format") + "\n")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -5,9 +5,9 @@ import (
|
|||||||
"os"
|
"os"
|
||||||
"text/template"
|
"text/template"
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
var serverDestroyCmd = cli.Command{
|
var serverDestroyCmd = cli.Command{
|
||||||
@ -17,10 +17,13 @@ var serverDestroyCmd = cli.Command{
|
|||||||
Action: serverDestroy,
|
Action: serverDestroy,
|
||||||
Flags: []cli.Flag{
|
Flags: []cli.Flag{
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "format",
|
Name: "format",
|
||||||
Usage: "format output",
|
Usage: "format output",
|
||||||
Value: tmplServerDestroy,
|
Value: tmplServerDestroy,
|
||||||
Hidden: true,
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "force",
|
||||||
|
Usage: "force destroy",
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
@ -36,7 +39,7 @@ func serverDestroy(c *cli.Context) error {
|
|||||||
return fmt.Errorf("Missing or invalid server name")
|
return fmt.Errorf("Missing or invalid server name")
|
||||||
}
|
}
|
||||||
|
|
||||||
err = client.ServerDelete(name)
|
err = client.ServerDelete(name, c.Bool("force"))
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -46,7 +49,7 @@ func serverDestroy(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format") + "\n")
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format") + "\n")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -9,10 +9,10 @@ import (
|
|||||||
"path"
|
"path"
|
||||||
"text/template"
|
"text/template"
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
"github.com/drone/drone-go/drone"
|
"github.com/drone/drone-go/drone"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
var serverEnvCmd = cli.Command{
|
var serverEnvCmd = cli.Command{
|
||||||
@ -108,7 +108,7 @@ func serverEnv(c *cli.Context) error {
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
var shellT = template.Must(template.New("_").Parse(`
|
var shellT = template.Must(template.New("_").Funcs(funcmap.Funcs).Parse(`
|
||||||
{{- if eq .Shell "fish" -}}
|
{{- if eq .Shell "fish" -}}
|
||||||
sex -x DOCKER_TLS "1";
|
sex -x DOCKER_TLS "1";
|
||||||
set -x DOCKER_TLS_VERIFY "";
|
set -x DOCKER_TLS_VERIFY "";
|
||||||
|
@ -5,9 +5,9 @@ import (
|
|||||||
"os"
|
"os"
|
||||||
"text/template"
|
"text/template"
|
||||||
|
|
||||||
"github.com/urfave/cli"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
var serverInfoCmd = cli.Command{
|
var serverInfoCmd = cli.Command{
|
||||||
@ -17,10 +17,9 @@ var serverInfoCmd = cli.Command{
|
|||||||
Action: serverInfo,
|
Action: serverInfo,
|
||||||
Flags: []cli.Flag{
|
Flags: []cli.Flag{
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "format",
|
Name: "format",
|
||||||
Usage: "format output",
|
Usage: "format output",
|
||||||
Value: tmplServerInfo,
|
Value: tmplServerInfo,
|
||||||
Hidden: true,
|
|
||||||
},
|
},
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
@ -41,7 +40,7 @@ func serverInfo(c *cli.Context) error {
|
|||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format") + "\n")
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format") + "\n")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
@ -8,10 +8,10 @@ import (
|
|||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/docker/go-units"
|
"github.com/docker/go-units"
|
||||||
"github.com/urfave/cli"
|
|
||||||
|
|
||||||
"github.com/drone/drone-cli/drone/internal"
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
"github.com/drone/drone-go/drone"
|
"github.com/drone/drone-go/drone"
|
||||||
|
"github.com/drone/funcmap"
|
||||||
|
"github.com/urfave/cli"
|
||||||
)
|
)
|
||||||
|
|
||||||
var serverListCmd = cli.Command{
|
var serverListCmd = cli.Command{
|
||||||
@ -20,23 +20,26 @@ var serverListCmd = cli.Command{
|
|||||||
ArgsUsage: " ",
|
ArgsUsage: " ",
|
||||||
Action: serverList,
|
Action: serverList,
|
||||||
Flags: []cli.Flag{
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "s, state",
|
||||||
|
Usage: "filter by state",
|
||||||
|
},
|
||||||
cli.BoolFlag{
|
cli.BoolFlag{
|
||||||
Name: "a",
|
Name: "a, all",
|
||||||
Usage: "include stopped servers",
|
Usage: "include stopped servers",
|
||||||
},
|
},
|
||||||
cli.BoolFlag{
|
cli.BoolFlag{
|
||||||
Name: "l",
|
Name: "l, long",
|
||||||
Usage: "list in long format",
|
Usage: "list in long format",
|
||||||
},
|
},
|
||||||
cli.BoolTFlag{
|
cli.BoolTFlag{
|
||||||
Name: "H",
|
Name: "H, headers",
|
||||||
Usage: "include columne headers",
|
Usage: "include column headers",
|
||||||
},
|
},
|
||||||
cli.StringFlag{
|
cli.StringFlag{
|
||||||
Name: "format",
|
Name: "format",
|
||||||
Usage: "format output",
|
Usage: "format output",
|
||||||
Value: tmplServerList,
|
Value: tmplServerList,
|
||||||
Hidden: true,
|
|
||||||
},
|
},
|
||||||
cli.BoolFlag{
|
cli.BoolFlag{
|
||||||
Name: "la",
|
Name: "la",
|
||||||
@ -50,6 +53,7 @@ func serverList(c *cli.Context) error {
|
|||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
s := c.String("s")
|
||||||
a := c.Bool("a")
|
a := c.Bool("a")
|
||||||
l := c.Bool("l")
|
l := c.Bool("l")
|
||||||
h := c.BoolT("H")
|
h := c.BoolT("H")
|
||||||
@ -65,11 +69,11 @@ func serverList(c *cli.Context) error {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if l && h {
|
if l && h {
|
||||||
printLong(servers, a, h)
|
printLong(servers, s, a, h)
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
tmpl, err := template.New("_").Parse(c.String("format") + "\n")
|
tmpl, err := template.New("_").Funcs(funcmap.Funcs).Parse(c.String("format") + "\n")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
@ -78,12 +82,17 @@ func serverList(c *cli.Context) error {
|
|||||||
if !a && server.State == "stopped" {
|
if !a && server.State == "stopped" {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if s != "" && s != server.State {
|
||||||
|
continue
|
||||||
|
}
|
||||||
|
|
||||||
tmpl.Execute(os.Stdout, server)
|
tmpl.Execute(os.Stdout, server)
|
||||||
}
|
}
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func printLong(servers []*drone.Server, a, h bool) {
|
func printLong(servers []*drone.Server, s string, a, h bool) {
|
||||||
w := tabwriter.NewWriter(os.Stdout, 0, 0, 4, ' ', 0)
|
w := tabwriter.NewWriter(os.Stdout, 0, 0, 4, ' ', 0)
|
||||||
if h {
|
if h {
|
||||||
fmt.Fprintln(w, "Name\tAddress\tState\tCreated")
|
fmt.Fprintln(w, "Name\tAddress\tState\tCreated")
|
||||||
@ -92,6 +101,9 @@ func printLong(servers []*drone.Server, a, h bool) {
|
|||||||
if !a && server.State == "stopped" {
|
if !a && server.State == "stopped" {
|
||||||
continue
|
continue
|
||||||
}
|
}
|
||||||
|
if s != "" && s != server.State {
|
||||||
|
continue
|
||||||
|
}
|
||||||
fmt.Fprintf(w, "%s\t%s\t%s\t%s ago\n",
|
fmt.Fprintf(w, "%s\t%s\t%s\t%s ago\n",
|
||||||
server.Name,
|
server.Name,
|
||||||
server.Address,
|
server.Address,
|
||||||
|
63
drone/sign/sign.go
Normal file
63
drone/sign/sign.go
Normal file
@ -0,0 +1,63 @@
|
|||||||
|
package sign
|
||||||
|
|
||||||
|
import (
|
||||||
|
"fmt"
|
||||||
|
"io/ioutil"
|
||||||
|
|
||||||
|
"github.com/drone/drone-cli/drone/internal"
|
||||||
|
"github.com/drone/drone-yaml/yaml/signer"
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Command exports the sign command.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "sign",
|
||||||
|
Usage: "sign the yaml file",
|
||||||
|
ArgsUsage: "<source>",
|
||||||
|
Action: format,
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "save",
|
||||||
|
Usage: "save result to source",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func format(c *cli.Context) error {
|
||||||
|
repo := c.Args().First()
|
||||||
|
owner, name, err := internal.ParseRepo(repo)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
client, err := internal.NewClient(c)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
path := c.Args().Get(1)
|
||||||
|
if path == "" {
|
||||||
|
path = ".drone.yml"
|
||||||
|
}
|
||||||
|
|
||||||
|
data, err := ioutil.ReadFile(path)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
hmac, err := client.Sign(owner, name, string(data))
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
if c.Bool("save") == false {
|
||||||
|
fmt.Println(hmac)
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
data, err = signer.WriteTo(data, hmac)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
return ioutil.WriteFile(path, data, 0644)
|
||||||
|
}
|
8
drone/starlark/samples/docker.py
Normal file
8
drone/starlark/samples/docker.py
Normal file
@ -0,0 +1,8 @@
|
|||||||
|
def docker(repo):
|
||||||
|
return {
|
||||||
|
'name': 'docker',
|
||||||
|
'image': 'plugins/docker',
|
||||||
|
'settings': {
|
||||||
|
'repo': repo,
|
||||||
|
},
|
||||||
|
}
|
33
drone/starlark/samples/pipeline.py
Normal file
33
drone/starlark/samples/pipeline.py
Normal file
@ -0,0 +1,33 @@
|
|||||||
|
# cd drone/starlark/samples
|
||||||
|
# drone script --source pipeline.py --stdout
|
||||||
|
|
||||||
|
load('docker.py', 'docker')
|
||||||
|
|
||||||
|
def build(version):
|
||||||
|
return {
|
||||||
|
'name': 'build',
|
||||||
|
'image': 'golang:%s' % version,
|
||||||
|
'commands': [
|
||||||
|
'go build',
|
||||||
|
'go test',
|
||||||
|
]
|
||||||
|
}
|
||||||
|
|
||||||
|
def main(ctx):
|
||||||
|
if ctx['build']['message'].find('[skip build]'):
|
||||||
|
return {
|
||||||
|
'kind': 'pipeline',
|
||||||
|
'name': 'publish_only',
|
||||||
|
'steps': [
|
||||||
|
docker('octocat/hello-world'),
|
||||||
|
],
|
||||||
|
}
|
||||||
|
return {
|
||||||
|
'kind': 'pipeline',
|
||||||
|
'name': 'build_and_publish',
|
||||||
|
'steps': [
|
||||||
|
build('1.11'),
|
||||||
|
build('1.12'),
|
||||||
|
docker('octocat/hello-world'),
|
||||||
|
],
|
||||||
|
}
|
317
drone/starlark/starlark.go
Normal file
317
drone/starlark/starlark.go
Normal file
@ -0,0 +1,317 @@
|
|||||||
|
package starlark
|
||||||
|
|
||||||
|
import (
|
||||||
|
"bytes"
|
||||||
|
"encoding/json"
|
||||||
|
"fmt"
|
||||||
|
"io"
|
||||||
|
"io/ioutil"
|
||||||
|
"log"
|
||||||
|
"os"
|
||||||
|
|
||||||
|
"github.com/drone/drone-yaml/yaml"
|
||||||
|
"github.com/drone/drone-yaml/yaml/pretty"
|
||||||
|
|
||||||
|
"github.com/urfave/cli"
|
||||||
|
"go.starlark.net/starlark"
|
||||||
|
"go.starlark.net/starlarkstruct"
|
||||||
|
)
|
||||||
|
|
||||||
|
// Command exports the jsonnet command.
|
||||||
|
var Command = cli.Command{
|
||||||
|
Name: "starlark",
|
||||||
|
Usage: "generate .drone.yml from starlark",
|
||||||
|
ArgsUsage: "[path/to/.drone.star]",
|
||||||
|
Action: func(c *cli.Context) {
|
||||||
|
if err := generate(c); err != nil {
|
||||||
|
if err, ok := err.(*starlark.EvalError); ok {
|
||||||
|
log.Fatalf("starlark evaluation error:\n%s", err.Backtrace())
|
||||||
|
}
|
||||||
|
log.Fatalln(err)
|
||||||
|
}
|
||||||
|
},
|
||||||
|
Flags: []cli.Flag{
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "source",
|
||||||
|
Usage: "Source file",
|
||||||
|
Value: ".drone.star",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "target",
|
||||||
|
Usage: "target file",
|
||||||
|
Value: ".drone.yml",
|
||||||
|
},
|
||||||
|
cli.BoolTFlag{
|
||||||
|
Name: "format",
|
||||||
|
Usage: "Write output as formatted YAML",
|
||||||
|
},
|
||||||
|
cli.BoolFlag{
|
||||||
|
Name: "stdout",
|
||||||
|
Usage: "Write output to stdout",
|
||||||
|
},
|
||||||
|
//
|
||||||
|
// Drone Parameters
|
||||||
|
//
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "repo.name",
|
||||||
|
Usage: "repository name",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "repo.namespace",
|
||||||
|
Usage: "repository namespace",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "repo.slug",
|
||||||
|
Usage: "repository slug",
|
||||||
|
},
|
||||||
|
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "build.event",
|
||||||
|
Usage: "build event",
|
||||||
|
Value: "push",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "build.branch",
|
||||||
|
Usage: "build branch",
|
||||||
|
Value: "master",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "build.source",
|
||||||
|
Usage: "build source branch",
|
||||||
|
Value: "master",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "build.target",
|
||||||
|
Usage: "build target branch",
|
||||||
|
Value: "master",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "build.ref",
|
||||||
|
Usage: "build ref",
|
||||||
|
Value: "refs/heads/master",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "build.commit",
|
||||||
|
Usage: "build commit sha",
|
||||||
|
},
|
||||||
|
cli.StringFlag{
|
||||||
|
Name: "build.message",
|
||||||
|
Usage: "build commit message",
|
||||||
|
},
|
||||||
|
},
|
||||||
|
}
|
||||||
|
|
||||||
|
func generate(c *cli.Context) error {
|
||||||
|
source := c.String("source")
|
||||||
|
target := c.String("target")
|
||||||
|
|
||||||
|
data, err := ioutil.ReadFile(source)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
thread := &starlark.Thread{
|
||||||
|
Name: "drone",
|
||||||
|
Print: func(_ *starlark.Thread, msg string) { fmt.Println(msg) },
|
||||||
|
Load: makeLoad(),
|
||||||
|
}
|
||||||
|
globals, err := starlark.ExecFile(thread, source, data, nil)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
mainVal, ok := globals["main"]
|
||||||
|
if !ok {
|
||||||
|
return fmt.Errorf("no main function found")
|
||||||
|
}
|
||||||
|
main, ok := mainVal.(starlark.Callable)
|
||||||
|
if !ok {
|
||||||
|
return fmt.Errorf("main must be a function")
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO this needs to be flushed out.
|
||||||
|
repo := starlark.StringDict{
|
||||||
|
"name": starlark.String(c.String("repo.name")),
|
||||||
|
"namespace": starlark.String(c.String("repo.namespace")),
|
||||||
|
"slug": starlark.String(c.String("repo.slug")),
|
||||||
|
}
|
||||||
|
|
||||||
|
build := starlark.StringDict{
|
||||||
|
"event": starlark.String(c.String("build.event")),
|
||||||
|
"branch": starlark.String(c.String("build.branch")),
|
||||||
|
"source": starlark.String(c.String("build.source_branch")),
|
||||||
|
"target": starlark.String(c.String("build.target_branch")),
|
||||||
|
"ref": starlark.String(c.String("build.ref")),
|
||||||
|
"commit": starlark.String(c.String("build.commit")),
|
||||||
|
"message": starlark.String(c.String("build.message")),
|
||||||
|
}
|
||||||
|
|
||||||
|
args := starlark.Tuple([]starlark.Value{
|
||||||
|
starlarkstruct.FromStringDict(
|
||||||
|
starlark.String("context"),
|
||||||
|
starlark.StringDict{
|
||||||
|
"repo": starlarkstruct.FromStringDict(starlark.String("repo"), repo),
|
||||||
|
"build": starlarkstruct.FromStringDict(starlark.String("build"), build),
|
||||||
|
},
|
||||||
|
),
|
||||||
|
})
|
||||||
|
mainVal, err = starlark.Call(thread, main, args, nil)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
|
||||||
|
buf := new(bytes.Buffer)
|
||||||
|
switch v := mainVal.(type) {
|
||||||
|
case *starlark.List:
|
||||||
|
for i := 0; i < v.Len(); i++ {
|
||||||
|
item := v.Index(i)
|
||||||
|
buf.WriteString("---\n")
|
||||||
|
err = writeJSON(buf, item)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
buf.WriteString("\n")
|
||||||
|
}
|
||||||
|
case *starlark.Dict:
|
||||||
|
buf.WriteString("---\n")
|
||||||
|
err = writeJSON(buf, v)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
default:
|
||||||
|
return fmt.Errorf("invalid return type (got a %s)", mainVal.Type())
|
||||||
|
}
|
||||||
|
|
||||||
|
// if the user disables pretty printing, the yaml is printed
|
||||||
|
// to the console or written to the file in json format.
|
||||||
|
if c.BoolT("format") == false {
|
||||||
|
if c.Bool("stdout") {
|
||||||
|
io.Copy(os.Stdout, buf)
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
return ioutil.WriteFile(target, buf.Bytes(), 0644)
|
||||||
|
}
|
||||||
|
|
||||||
|
manifest, err := yaml.Parse(buf)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
buf.Reset()
|
||||||
|
pretty.Print(buf, manifest)
|
||||||
|
|
||||||
|
// the user can optionally write the yaml to stdout. This
|
||||||
|
// is useful for debugging purposes without mutating an
|
||||||
|
// existing file.
|
||||||
|
if c.Bool("stdout") {
|
||||||
|
io.Copy(os.Stdout, buf)
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
return ioutil.WriteFile(target, buf.Bytes(), 0644)
|
||||||
|
}
|
||||||
|
|
||||||
|
// Adapted from skycfg:
|
||||||
|
// https://github.com/stripe/skycfg/blob/eaa524101c2a0807c13ed5d2e52576fefc146ec3/internal/go/skycfg/json_write.go#L45
|
||||||
|
func writeJSON(out *bytes.Buffer, v starlark.Value) error {
|
||||||
|
if marshaler, ok := v.(json.Marshaler); ok {
|
||||||
|
jsonData, err := marshaler.MarshalJSON()
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
out.Write(jsonData)
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
switch v := v.(type) {
|
||||||
|
case starlark.NoneType:
|
||||||
|
out.WriteString("null")
|
||||||
|
case starlark.Bool:
|
||||||
|
fmt.Fprintf(out, "%t", v)
|
||||||
|
case starlark.Int:
|
||||||
|
out.WriteString(v.String())
|
||||||
|
case starlark.Float:
|
||||||
|
fmt.Fprintf(out, "%g", v)
|
||||||
|
case starlark.String:
|
||||||
|
s := string(v)
|
||||||
|
if goQuoteIsSafe(s) {
|
||||||
|
fmt.Fprintf(out, "%q", s)
|
||||||
|
} else {
|
||||||
|
// vanishingly rare for text strings
|
||||||
|
data, _ := json.Marshal(s)
|
||||||
|
out.Write(data)
|
||||||
|
}
|
||||||
|
case starlark.Indexable: // Tuple, List
|
||||||
|
out.WriteByte('[')
|
||||||
|
for i, n := 0, starlark.Len(v); i < n; i++ {
|
||||||
|
if i > 0 {
|
||||||
|
out.WriteString(", ")
|
||||||
|
}
|
||||||
|
if err := writeJSON(out, v.Index(i)); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
out.WriteByte(']')
|
||||||
|
case *starlark.Dict:
|
||||||
|
out.WriteByte('{')
|
||||||
|
for i, itemPair := range v.Items() {
|
||||||
|
key := itemPair[0]
|
||||||
|
value := itemPair[1]
|
||||||
|
if i > 0 {
|
||||||
|
out.WriteString(", ")
|
||||||
|
}
|
||||||
|
if err := writeJSON(out, key); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
out.WriteString(": ")
|
||||||
|
if err := writeJSON(out, value); err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
out.WriteByte('}')
|
||||||
|
default:
|
||||||
|
return fmt.Errorf("TypeError: value %s (type `%s') can't be converted to JSON.", v.String(), v.Type())
|
||||||
|
}
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func goQuoteIsSafe(s string) bool {
|
||||||
|
for _, r := range s {
|
||||||
|
// JSON doesn't like Go's \xHH escapes for ASCII control codes,
|
||||||
|
// nor its \UHHHHHHHH escapes for runes >16 bits.
|
||||||
|
if r < 0x20 || r >= 0x10000 {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return true
|
||||||
|
}
|
||||||
|
|
||||||
|
// https://github.com/google/starlark-go/blob/4eb76950c5f02ec5bcfd3ca898231a6543942fd9/repl/repl.go#L175
|
||||||
|
func makeLoad() func(thread *starlark.Thread, module string) (starlark.StringDict, error) {
|
||||||
|
type entry struct {
|
||||||
|
globals starlark.StringDict
|
||||||
|
err error
|
||||||
|
}
|
||||||
|
|
||||||
|
var cache = make(map[string]*entry)
|
||||||
|
|
||||||
|
return func(thread *starlark.Thread, module string) (starlark.StringDict, error) {
|
||||||
|
e, ok := cache[module]
|
||||||
|
if e == nil {
|
||||||
|
if ok {
|
||||||
|
// request for package whose loading is in progress
|
||||||
|
return nil, fmt.Errorf("cycle in load graph")
|
||||||
|
}
|
||||||
|
|
||||||
|
// Add a placeholder to indicate "load in progress".
|
||||||
|
cache[module] = nil
|
||||||
|
|
||||||
|
// Load it.
|
||||||
|
thread := &starlark.Thread{Name: "exec " + module, Load: thread.Load}
|
||||||
|
globals, err := starlark.ExecFile(thread, module, nil, nil)
|
||||||
|
e = &entry{globals, err}
|
||||||
|
|
||||||
|
// Update the cache.
|
||||||
|
cache[module] = e
|
||||||
|
}
|
||||||
|
return e.globals, e.err
|
||||||
|
}
|
||||||
|
}
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user