diff --git a/.goreleaser.yml b/.goreleaser.yml deleted file mode 100644 index 94ab732..0000000 --- a/.goreleaser.yml +++ /dev/null @@ -1,27 +0,0 @@ -builds: -- env: - - CGO_ENABLED=0 - goos: - - darwin - - linux - - windows -archive: - replacements: - darwin: Darwin - linux: Linux - windows: Windows - 386: i386 - amd64: x86_64 - format_overrides: - - goos: windows - format: zip -checksum: - name_template: 'checksums.txt' -snapshot: - name_template: "{{ .Tag }}-next" -changelog: - sort: asc - filters: - exclude: - - '^docs:' - - '^test:' diff --git a/VERSION b/VERSION index 8b95abd..fd9620c 100644 --- a/VERSION +++ b/VERSION @@ -1 +1 @@ -0.24.2 +0.32.1 diff --git a/codefresh.yaml b/codefresh.yaml index 593c51c..406005b 100644 --- a/codefresh.yaml +++ b/codefresh.yaml @@ -1,46 +1,28 @@ version: '1.0' stages: +- Prepare - Release -mode: parallel - steps: - CreatingGitTag: - title: Push tag to git - image: codefresh/cli - stage: Release - commands: - - export VERSION=$(cat VERSION) - - export OLD_ORIGIN=$(git remote get-url origin) - - git remote rm origin - - git remote add origin https://${{GITHUB_TOKEN}}@github.com/codefresh-io/go-sdk.git - - git tag v$VERSION - - git push --tags - - git remote rm origin - - git remote add origin $OLD_ORIGIN - fail_fast: false - when: - steps: - - name: main_clone - branch: - only: - - master + main_clone: + stage: Prepare + title: clone repository + type: git-clone + git: cf_github + repo: ${{CF_REPO_OWNER}}/${{CF_REPO_NAME}} + revision: ${{CF_BRANCH}} ReleasingBinaries: title: Create release in Github - image: goreleaser/goreleaser + image: quay.io/codefresh/golang-ci-helper:latest stage: Release - fail_fast: false commands: - - go mod download - - goreleaser release -f .goreleaser.yml --rm-dist --skip-validate + - export VERSION=$(cat VERSION) + - VERSION=$(if [[ ${VERSION:0:1} == "v" ]] ; then echo $VERSION; else echo "v${VERSION}"; fi ) + - gh release create --repo ${{CF_REPO_OWNER}}/${{CF_REPO_NAME}} -t $VERSION -n $VERSION $VERSION when: - steps: - - name: CreatingGitTag - on: - - finished branch: only: - - master \ No newline at end of file + - master diff --git a/go.mod b/go.mod index 624a230..71fb9e5 100644 --- a/go.mod +++ b/go.mod @@ -3,16 +3,20 @@ module github.com/codefresh-io/go-sdk require ( github.com/BurntSushi/toml v0.3.1 // indirect github.com/dustin/go-humanize v1.0.0 + github.com/google/go-querystring v1.1.0 github.com/inconshreveable/mousetrap v1.0.0 // indirect + github.com/kr/pretty v0.1.0 // indirect github.com/mattn/go-runewidth v0.0.4 // indirect github.com/mitchellh/go-homedir v1.0.0 github.com/olekukonko/tablewriter v0.0.1 github.com/spf13/afero v1.2.0 // indirect github.com/spf13/cobra v0.0.3 github.com/spf13/viper v1.3.1 - github.com/stretchr/testify v1.7.0 // indirect - golang.org/x/sys v0.0.0-20181228144115-9a3f9b0469bb // indirect - gopkg.in/yaml.v2 v2.2.2 + github.com/stretchr/objx v0.3.0 // indirect + github.com/stretchr/testify v1.4.0 + golang.org/x/sys v0.0.0-20200116001909-b77594299b42 // indirect + gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15 // indirect + gopkg.in/yaml.v2 v2.2.4 ) go 1.13 diff --git a/go.sum b/go.sum index da23de9..1b7872f 100644 --- a/go.sum +++ b/go.sum @@ -11,10 +11,19 @@ github.com/dustin/go-humanize v1.0.0 h1:VSnTsYCnlFHaM2/igO1h6X3HA71jcobQuxemgkq4 github.com/dustin/go-humanize v1.0.0/go.mod h1:HtrtbFcZ19U5GC7JDqmcUSB87Iq5E25KnS6fMYU6eOk= github.com/fsnotify/fsnotify v1.4.7 h1:IXs+QLmnXW2CcXuY+8Mzv/fWEsPGWxqefPtCP5CnV9I= github.com/fsnotify/fsnotify v1.4.7/go.mod h1:jwhsz4b93w/PPRr/qN1Yymfu8t87LnFCMoQvtojpjFo= +github.com/google/go-cmp v0.5.2 h1:X2ev0eStA3AbceY54o37/0PQ/UWqKEiiO2dKL5OPaFM= +github.com/google/go-cmp v0.5.2/go.mod h1:v8dTdLbMG2kIc/vJvl+f65V22dbkXbowE6jgT/gNBxE= +github.com/google/go-querystring v1.1.0 h1:AnCroh3fv4ZBgVIf1Iwtovgjaw/GiKJo8M8yD/fhyJ8= +github.com/google/go-querystring v1.1.0/go.mod h1:Kcdr2DB4koayq7X8pmAG4sNG59So17icRSOU623lUBU= github.com/hashicorp/hcl v1.0.0 h1:0Anlzjpi4vEasTeNFn2mLJgTSwt0+6sfsiTG8qcWGx4= github.com/hashicorp/hcl v1.0.0/go.mod h1:E5yfLk+7swimpb2L/Alb/PJmXilQ/rhwaUYs4T20WEQ= github.com/inconshreveable/mousetrap v1.0.0 h1:Z8tu5sraLXCXIcARxBp/8cbvlwVa7Z1NHg9XEKhtSvM= github.com/inconshreveable/mousetrap v1.0.0/go.mod h1:PxqpIevigyE2G7u3NXJIT2ANytuPF1OarO4DADm73n8= +github.com/kr/pretty v0.1.0 h1:L/CwN0zerZDmRFUapSPitk6f+Q3+0za1rQkzVuMiMFI= +github.com/kr/pretty v0.1.0/go.mod h1:dAy3ld7l9f0ibDNOQOHHMYYIIbhfbHSm3C4ZsoJORNo= +github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= +github.com/kr/text v0.1.0 h1:45sCR5RtlFHMR4UwH9sdQ5TC8v0qDQCHnXt+kaKSTVE= +github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= github.com/magiconair/properties v1.8.0 h1:LLgXmsheXeRoUOBOjtwPQCWIYqM/LU1ayDtDePerRcY= github.com/magiconair/properties v1.8.0/go.mod h1:PppfXfuXeibc/6YijjN8zIbojt8czPbwD3XqdrwzmxQ= github.com/mattn/go-runewidth v0.0.4 h1:2BvfKmzob6Bmd4YsL0zygOqfdFnK7GR4QL06Do4/p7Y= @@ -42,23 +51,26 @@ github.com/spf13/pflag v1.0.3 h1:zPAT6CGy6wXeQ7NtTnaTerfKOsV6V6F8agHXFiazDkg= github.com/spf13/pflag v1.0.3/go.mod h1:DYY7MBk1bdzusC3SYhjObp+wFpr4gzcvqqNjLnInEg4= github.com/spf13/viper v1.3.1 h1:5+8j8FTpnFV4nEImW/ofkzEt8VoOiLXxdYIDsB73T38= github.com/spf13/viper v1.3.1/go.mod h1:ZiWeW+zYFKm7srdB9IoDzzZXaJaI5eL9QjNiN/DMA2s= -github.com/stretchr/objx v0.1.0 h1:4G4v2dO3VZwixGIRoQ5Lfboy6nUhCyYzaqnIAPPhYs4= github.com/stretchr/objx v0.1.0/go.mod h1:HFkY916IF+rwdDfMAkV7OtwuqBVzrE8GR6GFx+wExME= -github.com/stretchr/testify v1.2.2 h1:bSDNvY7ZPG5RlJ8otE/7V6gMiyenm9RtJ7IUVIAoJ1w= +github.com/stretchr/objx v0.3.0 h1:NGXK3lHquSN08v5vWalVI/L8XU9hdzE/G6xsrze47As= +github.com/stretchr/objx v0.3.0/go.mod h1:qt09Ya8vawLte6SNmTgCsAVtYtaKzEcn8ATUoHMkEqE= github.com/stretchr/testify v1.2.2/go.mod h1:a8OnRcib4nhh0OaRAV+Yts87kKdq0PP7pXfy6kDkUVs= -github.com/stretchr/testify v1.7.0 h1:nwc3DEeHmmLAfoZucVR881uASk0Mfjw8xYJ99tb5CcY= -github.com/stretchr/testify v1.7.0/go.mod h1:6Fq8oRcR53rry900zMqJjRRixrwX3KX962/h/Wwjteg= +github.com/stretchr/testify v1.3.0/go.mod h1:M5WIy9Dh21IEIfnGCwXGc5bZfKNJtfHm1UVUgZn+9EI= +github.com/stretchr/testify v1.4.0 h1:2E4SXV/wtOkTonXsotYi4li6zVWxYlZuYNCXe9XRJyk= +github.com/stretchr/testify v1.4.0/go.mod h1:j7eGeouHqKxXV5pUuKE4zz7dFj8WfuZ+81PSLYec5m4= github.com/ugorji/go/codec v0.0.0-20181204163529-d75b2dcb6bc8/go.mod h1:VFNgLljTbGfSG7qAOspJ7OScBnGdDN/yBr0sguwnwf0= github.com/xordataexchange/crypt v0.0.3-0.20170626215501-b2862e3d0a77/go.mod h1:aYKd//L2LvnjZzWKhF00oedf4jCCReLcmhLdhm1A27Q= golang.org/x/crypto v0.0.0-20181203042331-505ab145d0a9/go.mod h1:6SG95UA2DQfeDnfUPMdvaQW0Q7yPrPDi9nlGo2tz2b4= golang.org/x/sys v0.0.0-20181205085412-a5c9d58dba9a/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= -golang.org/x/sys v0.0.0-20181228144115-9a3f9b0469bb h1:pf3XwC90UUdNPYWZdFjhGBE7DUFuK3Ct1zWmZ65QN30= -golang.org/x/sys v0.0.0-20181228144115-9a3f9b0469bb/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= +golang.org/x/sys v0.0.0-20200116001909-b77594299b42 h1:vEOn+mP2zCOVzKckCZy6YsCtDblrpj/w7B9nxGNELpg= +golang.org/x/sys v0.0.0-20200116001909-b77594299b42/go.mod h1:h1NjWce9XRLGQEsW7wpKNCjG9DtNlClVuFLEZdDNbEs= golang.org/x/text v0.3.0 h1:g61tztE5qeGQ89tm6NTjjM9VPIm088od1l6aSorWRWg= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= -gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405 h1:yhCVgyC4o1eVCa2tZl7eS0r+SDo693bJlVdllGtEeKM= +golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543 h1:E7g+9GITq07hpfrRu66IVDexMakfv52eLZ2CXBWiKr4= +golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= gopkg.in/check.v1 v0.0.0-20161208181325-20d25e280405/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= -gopkg.in/yaml.v2 v2.2.2 h1:ZCJp+EgiOT7lHqUV2J862kp8Qj64Jo6az82+3Td9dZw= +gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15 h1:YR8cESwS4TdDjEe65xsg0ogRM/Nc3DYOhEAlW+xobZo= +gopkg.in/check.v1 v1.0.0-20190902080502-41f04d3bba15/go.mod h1:Co6ibVJAznAaIkqp8huTwlJQCZ016jof/cbN4VW5Yz0= gopkg.in/yaml.v2 v2.2.2/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= -gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c h1:dUUwHk2QECo/6vqA44rthZ8ie2QXMNeKRTHCNY2nXvo= -gopkg.in/yaml.v3 v3.0.0-20200313102051-9f266ea9e77c/go.mod h1:K4uyk7z7BCEPqu6E+C64Yfv1cQ7kz7rIZviUmN+EgEM= +gopkg.in/yaml.v2 v2.2.4 h1:/eiJrUcujPVeJ3xlSWaiNi3uSVmDGBK1pDHUHAnao1I= +gopkg.in/yaml.v2 v2.2.4/go.mod h1:hI93XBmqTisBFMUTm0b8Fm+jr3Dg1NNxqwp+5A1VGuI= diff --git a/pkg/codefresh/argo.go b/pkg/codefresh/argo.go index b21649a..02d5044 100644 --- a/pkg/codefresh/argo.go +++ b/pkg/codefresh/argo.go @@ -14,7 +14,7 @@ type ( } argo struct { - codefresh Codefresh + codefresh *codefresh } IntegrationItem struct { @@ -50,7 +50,7 @@ type ( } ) -func newArgoAPI(codefresh Codefresh) ArgoAPI { +func newArgoAPI(codefresh *codefresh) ArgoAPI { return &argo{codefresh} } diff --git a/pkg/codefresh/argo_runtime.go b/pkg/codefresh/argo_runtime.go new file mode 100644 index 0000000..f08d303 --- /dev/null +++ b/pkg/codefresh/argo_runtime.go @@ -0,0 +1,110 @@ +package codefresh + +import ( + "context" + "fmt" + + "github.com/codefresh-io/go-sdk/pkg/codefresh/model" +) + +type ( + IRuntimeAPI interface { + List(ctx context.Context) ([]model.Runtime, error) + Create(ctx context.Context, runtimeName, cluster, runtimeVersion string) (*model.RuntimeCreationResponse, error) + } + + argoRuntime struct { + codefresh *codefresh + } + + graphqlRuntimesResponse struct { + Data struct { + Runtimes model.RuntimePage + } + Errors []graphqlError + } + + graphQlRuntimeCreationResponse struct { + Data struct { + Runtime model.RuntimeCreationResponse + } + Errors []graphqlError + } +) + +func newArgoRuntimeAPI(codefresh *codefresh) IRuntimeAPI { + return &argoRuntime{codefresh: codefresh} +} + +func (r *argoRuntime) List(ctx context.Context) ([]model.Runtime, error) { + jsonData := map[string]interface{}{ + "query": `{ + runtimes { + edges { + node { + metadata { + name + namespace + } + self { + healthStatus + version + } + cluster + } + } + } + }`, + } + + res := &graphqlRuntimesResponse{} + err := r.codefresh.graphqlAPI(ctx, jsonData, res) + if err != nil { + return nil, fmt.Errorf("failed getting runtime list: %w", err) + } + + if len(res.Errors) > 0 { + return nil, graphqlErrorResponse{errors: res.Errors} + } + + runtimes := make([]model.Runtime, len(res.Data.Runtimes.Edges)) + for i := range res.Data.Runtimes.Edges { + runtimes[i] = *res.Data.Runtimes.Edges[i].Node + } + + return runtimes, nil +} + +func (r *argoRuntime) Create(ctx context.Context, runtimeName, cluster, runtimeVersion string) (*model.RuntimeCreationResponse, error) { + jsonData := map[string]interface{}{ + "query": ` + mutation CreateRuntime( + $name: String! + $cluster: String! + $runtimeVersion: String! + ) { + runtime(name: $name, cluster: $cluster, runtimeVersion: $runtimeVersion) { + name + newAccessToken + } + } + `, + "variables": map[string]interface{}{ + "name": runtimeName, + "cluster": cluster, + "runtimeVersion": runtimeVersion, + }, + } + + res := &graphQlRuntimeCreationResponse{} + err := r.codefresh.graphqlAPI(ctx, jsonData, res) + if err != nil { + return nil, fmt.Errorf("failed getting runtime list: %w", err) + } + + if len(res.Errors) > 0 { + return nil, graphqlErrorResponse{errors: res.Errors} + } + + return &res.Data.Runtime, nil +} diff --git a/pkg/codefresh/cluster.go b/pkg/codefresh/cluster.go index 4254cdc..6e6ec62 100644 --- a/pkg/codefresh/cluster.go +++ b/pkg/codefresh/cluster.go @@ -9,7 +9,7 @@ type ( } cluster struct { - codefresh Codefresh + codefresh *codefresh } Cluster struct { @@ -31,7 +31,7 @@ type ( } ) -func newClusterAPI(codefresh Codefresh) IClusterAPI { +func newClusterAPI(codefresh *codefresh) IClusterAPI { return &cluster{codefresh} } diff --git a/pkg/codefresh/codefresh.go b/pkg/codefresh/codefresh.go index 1ba5816..e6b20db 100644 --- a/pkg/codefresh/codefresh.go +++ b/pkg/codefresh/codefresh.go @@ -2,19 +2,23 @@ package codefresh import ( "bytes" + "context" "encoding/json" + "errors" "fmt" "io/ioutil" "net/http" "strings" + + "github.com/google/go-querystring/query" ) +//go:generate mockery -name Codefresh -filename codefresh.go + +//go:generate mockery -name UsersAPI -filename users.go + type ( Codefresh interface { - requestAPI(*requestOptions) (*http.Response, error) - decodeResponseInto(*http.Response, interface{}) error - getBodyAsString(*http.Response) (string, error) - getBodyAsBytes(*http.Response) ([]byte, error) Pipelines() IPipelineAPI Tokens() ITokenAPI RuntimeEnvironments() IRuntimeEnvironmentAPI @@ -22,9 +26,17 @@ type ( Progresses() IProgressAPI Clusters() IClusterAPI Contexts() IContextAPI + Users() UsersAPI Argo() ArgoAPI Gitops() GitopsAPI Projects() IProjectAPI + V2() V2API + } + + V2API interface { + Runtime() IRuntimeAPI + GitSource() IGitSourceAPI + Component() IComponentAPI } ) @@ -45,6 +57,10 @@ func (c *codefresh) Pipelines() IPipelineAPI { return newPipelineAPI(c) } +func (c *codefresh) Users() UsersAPI { + return newUsersAPI(c) +} + func (c *codefresh) Tokens() ITokenAPI { return newTokenAPI(c) } @@ -80,7 +96,27 @@ func (c *codefresh) Projects() IProjectAPI { return newProjectAPI(c) } +func (c *codefresh) V2() V2API { + return c +} + +func (c *codefresh) Runtime() IRuntimeAPI { + return newArgoRuntimeAPI(c) +} + +func (c *codefresh) GitSource() IGitSourceAPI { + return newGitSourceAPI(c) +} + +func (c *codefresh) Component() IComponentAPI { + return newComponentAPI(c) +} + func (c *codefresh) requestAPI(opt *requestOptions) (*http.Response, error) { + return c.requestAPIWithContext(context.Background(), opt) +} + +func (c *codefresh) requestAPIWithContext(ctx context.Context, opt *requestOptions) (*http.Response, error) { var body []byte finalURL := fmt.Sprintf("%s%s", c.host, opt.path) if opt.qs != nil { @@ -89,9 +125,13 @@ func (c *codefresh) requestAPI(opt *requestOptions) (*http.Response, error) { if opt.body != nil { body, _ = json.Marshal(opt.body) } - request, err := http.NewRequest(opt.method, finalURL, bytes.NewBuffer(body)) + request, err := http.NewRequestWithContext(ctx, opt.method, finalURL, bytes.NewBuffer(body)) + if err != nil { + return nil, err + } request.Header.Set("Authorization", c.token) request.Header.Set("Content-Type", "application/json") + request.Header.Set("origin", c.host) response, err := c.client.Do(request) if err != nil { @@ -100,7 +140,31 @@ func (c *codefresh) requestAPI(opt *requestOptions) (*http.Response, error) { return response, nil } -func toQS(qs map[string]string) string { +func (c *codefresh) graphqlAPI(ctx context.Context, body map[string]interface{}, res interface{}) error { + response, err := c.requestAPIWithContext(ctx, &requestOptions{ + method: "POST", + path: "/2.0/api/graphql", + body: body, + }) + if err != nil { + return fmt.Errorf("The HTTP request failed: %w", err) + } + defer response.Body.Close() + + statusOK := response.StatusCode >= 200 && response.StatusCode < 300 + if !statusOK { + return errors.New(response.Status) + } + + data, err := ioutil.ReadAll(response.Body) + if err != nil { + return fmt.Errorf("failed to read from response body: %w", err) + } + + return json.Unmarshal(data, res) +} + +func buildQSFromMap(qs map[string]string) string { var arr = []string{} for k, v := range qs { arr = append(arr, fmt.Sprintf("%s=%s", k, v)) @@ -108,6 +172,21 @@ func toQS(qs map[string]string) string { return "?" + strings.Join(arr, "&") } +func toQS(qs interface{}) string { + v, _ := query.Values(qs) + qsStr := v.Encode() + if qsStr != "" { + return "?" + qsStr + } + var qsMap map[string]string + rs, _ := json.Marshal(qs) + err := json.Unmarshal(rs, &qsMap) + if err != nil { + return "" + } + return buildQSFromMap(qsMap) +} + func (c *codefresh) decodeResponseInto(resp *http.Response, target interface{}) error { return json.NewDecoder(resp.Body).Decode(target) } diff --git a/pkg/codefresh/common.go b/pkg/codefresh/common.go new file mode 100644 index 0000000..b26ce59 --- /dev/null +++ b/pkg/codefresh/common.go @@ -0,0 +1,40 @@ +package codefresh + +import ( + "fmt" + "strings" + +) + +type graphqlError struct { + Message string + Locations [] struct { + Line int + Column int + } + Extensions struct { + Code string + Exception struct { + Stacktrace []string + } + } +} + +type graphqlErrorResponse struct { + errors []graphqlError + concatenatedErrors string +} + + +func (e graphqlErrorResponse) Error() string { + + if e.concatenatedErrors != "" { + return e.concatenatedErrors + } + var sb strings.Builder + for _, err := range e.errors { + sb.WriteString(fmt.Sprintln(err.Message)) + } + e.concatenatedErrors = sb.String() + return e.concatenatedErrors +} \ No newline at end of file diff --git a/pkg/codefresh/component.go b/pkg/codefresh/component.go new file mode 100644 index 0000000..27003c0 --- /dev/null +++ b/pkg/codefresh/component.go @@ -0,0 +1,73 @@ +package codefresh + +import ( + "context" + "fmt" + + "github.com/codefresh-io/go-sdk/pkg/codefresh/model" +) + +type ( + IComponentAPI interface { + List(ctx context.Context, runtimeName string) ([]model.Component, error) + } + + component struct { + codefresh *codefresh + } + + graphqlComponentsResponse struct { + Data struct { + Components model.ComponentPage + } + Errors []graphqlError + } +) + +func newComponentAPI(codefresh *codefresh) IComponentAPI { + return &component{codefresh: codefresh} +} + +func (r *component) List(ctx context.Context, runtimeName string) ([]model.Component, error) { + jsonData := map[string]interface{}{ + "query": ` + query Components($runtime: String!) { + components(runtime: $runtime) { + edges { + node { + metadata { + name + } + version + self { + status { + syncStatus + healthStatus + } + } + } + } + } + }`, + "variables": map[string]interface{}{ + "runtime": runtimeName, + }, + } + + res := &graphqlComponentsResponse{} + err := r.codefresh.graphqlAPI(ctx, jsonData, res) + if err != nil { + return nil, fmt.Errorf("failed getting components list: %w", err) + } + + if len(res.Errors) > 0 { + return nil, graphqlErrorResponse{errors: res.Errors} + } + + components := make([]model.Component, len(res.Data.Components.Edges)) + for i := range res.Data.Components.Edges { + components[i] = *res.Data.Components.Edges[i].Node + } + + return components, nil +} diff --git a/pkg/codefresh/contexts.go b/pkg/codefresh/contexts.go index 7799956..210efc7 100644 --- a/pkg/codefresh/contexts.go +++ b/pkg/codefresh/contexts.go @@ -7,8 +7,8 @@ type ( GetDefaultGitContext() (error, *ContextPayload) } - context struct { - codefresh Codefresh + contexts struct { + codefresh *codefresh } ContextPayload struct { @@ -19,27 +19,38 @@ type ( Type string `json:"type"` Data struct { Auth struct { - Type string `json:"type"` - Username string `json:"username"` - Password string `json:"password"` - ApiHost string `json:"apiHost"` - ApiPathPrefix string `json:"apiPathPrefix"` - SshPrivateKey string `json:"sshPrivateKey"` + Type string `json:"type"` + Username string `json:"username"` + Password string `json:"password"` + ApiHost string `json:"apiHost"` + // for gitlab + ApiURL string `json:"apiURL"` + ApiPathPrefix string `json:"apiPathPrefix"` + SshPrivateKey string `json:"sshPrivateKey"` + AppId string `json:"appId"` + InstallationId string `json:"installationId"` + PrivateKey string `json:"privateKey"` } `json:"auth"` } `json:"data"` } `json:"spec"` } + + GitContextsQs struct { + Type []string `url:"type"` + Decrypt string `url:"decrypt"` + } ) -func newContextAPI(codefresh Codefresh) IContextAPI { - return &context{codefresh} +func newContextAPI(codefresh *codefresh) IContextAPI { + return &contexts{codefresh} } -func (c context) GetGitContexts() (error, *[]ContextPayload) { +func (c contexts) GetGitContexts() (error, *[]ContextPayload) { var result []ContextPayload - var qs = map[string]string{ - "type": "git.github", - "decrypt": "true", + + qs := GitContextsQs{ + Type: []string{"git.github", "git.gitlab", "git.github-app"}, + Decrypt: "true", } resp, err := c.codefresh.requestAPI(&requestOptions{ @@ -56,7 +67,7 @@ func (c context) GetGitContexts() (error, *[]ContextPayload) { return err, &result } -func (c context) GetGitContextByName(name string) (error, *ContextPayload) { +func (c contexts) GetGitContextByName(name string) (error, *ContextPayload) { var result ContextPayload var qs = map[string]string{ "decrypt": "true", @@ -76,7 +87,7 @@ func (c context) GetGitContextByName(name string) (error, *ContextPayload) { return nil, &result } -func (c context) GetDefaultGitContext() (error, *ContextPayload) { +func (c contexts) GetDefaultGitContext() (error, *ContextPayload) { var result ContextPayload resp, err := c.codefresh.requestAPI(&requestOptions{ diff --git a/pkg/codefresh/git-source.go b/pkg/codefresh/git-source.go new file mode 100644 index 0000000..4b36b03 --- /dev/null +++ b/pkg/codefresh/git-source.go @@ -0,0 +1,74 @@ +package codefresh + +import ( + "context" + "fmt" + + "github.com/codefresh-io/go-sdk/pkg/codefresh/model" +) + +type ( + IGitSourceAPI interface { + List(ctc context.Context, runtimeName string) ([]model.GitSource, error) + } + + gitSource struct { + codefresh *codefresh + } + + graphQlGitSourcesListResponse struct { + Data struct { + GitSources model.GitSourcePage + } + Errors []graphqlError + } +) + +func newGitSourceAPI(codefresh *codefresh) IGitSourceAPI { + return &gitSource{codefresh: codefresh} +} + +func (g *gitSource) List(ctx context.Context, runtimeName string) ([]model.GitSource, error) { + jsonData := map[string]interface{}{ + "query": ` + query GitSources($runtime: String) { + gitSources(runtime: $runtime) { + edges { + node { + metadata { + name + } + self { + path + repoURL + status { + syncStatus + healthStatus + } + } + } + } + } + }`, + "variables": map[string]interface{}{ + "runtime": runtimeName, + }, + } + + res := &graphQlGitSourcesListResponse{} + err := g.codefresh.graphqlAPI(ctx, jsonData, res) + if err != nil { + return nil, fmt.Errorf("failed getting git-source list: %w", err) + } + + gitSources := make([]model.GitSource, len(res.Data.GitSources.Edges)) + for i := range res.Data.GitSources.Edges { + gitSources[i] = *res.Data.GitSources.Edges[i].Node + } + + if len(res.Errors) > 0 { + return nil, graphqlErrorResponse{errors: res.Errors} + } + + return gitSources, nil +} diff --git a/pkg/codefresh/gitops.go b/pkg/codefresh/gitops.go index 1eeed79..191cec7 100644 --- a/pkg/codefresh/gitops.go +++ b/pkg/codefresh/gitops.go @@ -1,6 +1,8 @@ package codefresh -import "fmt" +import ( + "fmt" +) type ( GitopsAPI interface { @@ -13,7 +15,7 @@ type ( } gitops struct { - codefresh Codefresh + codefresh *codefresh } CodefreshEvent struct { Event string `json:"event"` @@ -69,17 +71,19 @@ type ( Current int64 `json:"current"` Desired int64 `json:"desired"` } - User struct { - Name string `json:"name"` - Avatar string `json:"avatar"` - } + Annotation struct { Key string `json:"key"` Value string `json:"value"` } + GitopsUser struct { + Name string `json:"name"` + Avatar string `json:"avatar"` + } + Gitops struct { - Comitters []User `json:"comitters"` + Comitters []GitopsUser `json:"comitters"` Prs []Annotation `json:"prs"` Issues []Annotation `json:"issues"` } @@ -99,6 +103,9 @@ type ( SyncPolicy SyncPolicy `json:"syncPolicy"` Date string `json:"date"` ParentApp string `json:"parentApp"` + Namespace string `json:"namespace"` + Server string `json:"server"` + Context *string `json:"context"` } EnvironmentActivity struct { @@ -114,10 +121,11 @@ type ( HistoryId int64 `json:"historyId"` Revision string `json:"revision, omitempty"` Resources interface{} `json:"resources"` + Context *string `json:"context"` } ) -func newGitopsAPI(codefresh Codefresh) GitopsAPI { +func newGitopsAPI(codefresh *codefresh) GitopsAPI { return &gitops{codefresh} } @@ -146,11 +154,19 @@ func (a *gitops) CreateEnvironment(name string, project string, application stri } func (a *gitops) SendEnvironment(environment Environment) (map[string]interface{}, error) { - _, err := a.codefresh.requestAPI(&requestOptions{method: "POST", path: "/api/gitops/rollout", body: environment}) + var result map[string]interface{} + resp, err := a.codefresh.requestAPI(&requestOptions{method: "POST", path: "/api/environments-v2/argo/events", body: environment}) + if err != nil { + return nil, err + } + + err = a.codefresh.decodeResponseInto(resp, &result) + if err != nil { return nil, err } - return nil, nil + + return result, nil } func (a *gitops) DeleteEnvironment(name string) error { diff --git a/pkg/codefresh/mocks/codefresh.go b/pkg/codefresh/mocks/codefresh.go new file mode 100644 index 0000000..caea0d8 --- /dev/null +++ b/pkg/codefresh/mocks/codefresh.go @@ -0,0 +1,189 @@ +// Code generated by mockery v1.1.1. DO NOT EDIT. + +package mocks + +import ( + codefresh "github.com/codefresh-io/go-sdk/pkg/codefresh" + mock "github.com/stretchr/testify/mock" +) + +// Codefresh is an autogenerated mock type for the Codefresh type +type Codefresh struct { + mock.Mock +} + +// Argo provides a mock function with given fields: +func (_m *Codefresh) Argo() codefresh.ArgoAPI { + ret := _m.Called() + + var r0 codefresh.ArgoAPI + if rf, ok := ret.Get(0).(func() codefresh.ArgoAPI); ok { + r0 = rf() + } else { + if ret.Get(0) != nil { + r0 = ret.Get(0).(codefresh.ArgoAPI) + } + } + + return r0 +} + +// Clusters provides a mock function with given fields: +func (_m *Codefresh) Clusters() codefresh.IClusterAPI { + ret := _m.Called() + + var r0 codefresh.IClusterAPI + if rf, ok := ret.Get(0).(func() codefresh.IClusterAPI); ok { + r0 = rf() + } else { + if ret.Get(0) != nil { + r0 = ret.Get(0).(codefresh.IClusterAPI) + } + } + + return r0 +} + +// Contexts provides a mock function with given fields: +func (_m *Codefresh) Contexts() codefresh.IContextAPI { + ret := _m.Called() + + var r0 codefresh.IContextAPI + if rf, ok := ret.Get(0).(func() codefresh.IContextAPI); ok { + r0 = rf() + } else { + if ret.Get(0) != nil { + r0 = ret.Get(0).(codefresh.IContextAPI) + } + } + + return r0 +} + +// Gitops provides a mock function with given fields: +func (_m *Codefresh) Gitops() codefresh.GitopsAPI { + ret := _m.Called() + + var r0 codefresh.GitopsAPI + if rf, ok := ret.Get(0).(func() codefresh.GitopsAPI); ok { + r0 = rf() + } else { + if ret.Get(0) != nil { + r0 = ret.Get(0).(codefresh.GitopsAPI) + } + } + + return r0 +} + +// Pipelines provides a mock function with given fields: +func (_m *Codefresh) Pipelines() codefresh.IPipelineAPI { + ret := _m.Called() + + var r0 codefresh.IPipelineAPI + if rf, ok := ret.Get(0).(func() codefresh.IPipelineAPI); ok { + r0 = rf() + } else { + if ret.Get(0) != nil { + r0 = ret.Get(0).(codefresh.IPipelineAPI) + } + } + + return r0 +} + +// Progresses provides a mock function with given fields: +func (_m *Codefresh) Progresses() codefresh.IProgressAPI { + ret := _m.Called() + + var r0 codefresh.IProgressAPI + if rf, ok := ret.Get(0).(func() codefresh.IProgressAPI); ok { + r0 = rf() + } else { + if ret.Get(0) != nil { + r0 = ret.Get(0).(codefresh.IProgressAPI) + } + } + + return r0 +} + +// RuntimeEnvironments provides a mock function with given fields: +func (_m *Codefresh) RuntimeEnvironments() codefresh.IRuntimeEnvironmentAPI { + ret := _m.Called() + + var r0 codefresh.IRuntimeEnvironmentAPI + if rf, ok := ret.Get(0).(func() codefresh.IRuntimeEnvironmentAPI); ok { + r0 = rf() + } else { + if ret.Get(0) != nil { + r0 = ret.Get(0).(codefresh.IRuntimeEnvironmentAPI) + } + } + + return r0 +} + +// Tokens provides a mock function with given fields: +func (_m *Codefresh) Tokens() codefresh.ITokenAPI { + ret := _m.Called() + + var r0 codefresh.ITokenAPI + if rf, ok := ret.Get(0).(func() codefresh.ITokenAPI); ok { + r0 = rf() + } else { + if ret.Get(0) != nil { + r0 = ret.Get(0).(codefresh.ITokenAPI) + } + } + + return r0 +} + +// Users provides a mock function with given fields: +func (_m *Codefresh) Users() codefresh.UsersAPI { + ret := _m.Called() + + var r0 codefresh.UsersAPI + if rf, ok := ret.Get(0).(func() codefresh.UsersAPI); ok { + r0 = rf() + } else { + if ret.Get(0) != nil { + r0 = ret.Get(0).(codefresh.UsersAPI) + } + } + + return r0 +} + +// V2 provides a mock function with given fields: +func (_m *Codefresh) V2() codefresh.V2API { + ret := _m.Called() + + var r0 codefresh.V2API + if rf, ok := ret.Get(0).(func() codefresh.V2API); ok { + r0 = rf() + } else { + if ret.Get(0) != nil { + r0 = ret.Get(0).(codefresh.V2API) + } + } + + return r0 +} + +// Workflows provides a mock function with given fields: +func (_m *Codefresh) Workflows() codefresh.IWorkflowAPI { + ret := _m.Called() + + var r0 codefresh.IWorkflowAPI + if rf, ok := ret.Get(0).(func() codefresh.IWorkflowAPI); ok { + r0 = rf() + } else { + if ret.Get(0) != nil { + r0 = ret.Get(0).(codefresh.IWorkflowAPI) + } + } + + return r0 +} diff --git a/pkg/codefresh/mocks/users.go b/pkg/codefresh/mocks/users.go new file mode 100644 index 0000000..700d911 --- /dev/null +++ b/pkg/codefresh/mocks/users.go @@ -0,0 +1,39 @@ +// Code generated by mockery v1.1.1. DO NOT EDIT. + +package mocks + +import ( + context "context" + + codefresh "github.com/codefresh-io/go-sdk/pkg/codefresh" + + mock "github.com/stretchr/testify/mock" +) + +// UsersAPI is an autogenerated mock type for the UsersAPI type +type UsersAPI struct { + mock.Mock +} + +// GetCurrent provides a mock function with given fields: ctx +func (_m *UsersAPI) GetCurrent(ctx context.Context) (*codefresh.User, error) { + ret := _m.Called(ctx) + + var r0 *codefresh.User + if rf, ok := ret.Get(0).(func(context.Context) *codefresh.User); ok { + r0 = rf(ctx) + } else { + if ret.Get(0) != nil { + r0 = ret.Get(0).(*codefresh.User) + } + } + + var r1 error + if rf, ok := ret.Get(1).(func(context.Context) error); ok { + r1 = rf(ctx) + } else { + r1 = ret.Error(1) + } + + return r0, r1 +} diff --git a/pkg/codefresh/model/models_gen.go b/pkg/codefresh/model/models_gen.go new file mode 100644 index 0000000..f5021ee --- /dev/null +++ b/pkg/codefresh/model/models_gen.go @@ -0,0 +1,2019 @@ +// Code generated by github.com/99designs/gqlgen, DO NOT EDIT. + +package model + +import ( + "fmt" + "io" + "strconv" +) + +// Base entity +type BaseEntity interface { + IsBaseEntity() +} + +// "Common events properties +type CommonGitEventPayloadData interface { + IsCommonGitEventPayloadData() +} + +// Customer +type Customer interface { + IsCustomer() +} + +// Generic edge to allow cursors +type Edge interface { + IsEdge() +} + +// Entity types +type Entity interface { + IsEntity() +} + +// Event +type Event interface { + IsEvent() +} + +// Event payload data types +type EventPayloadData interface { + IsEventPayloadData() +} + +// Gitops entity +type GitopsEntity interface { + IsGitopsEntity() +} + +// K8s logic entity +type K8sLogicEntity interface { + IsK8sLogicEntity() +} + +// Base entity +type K8sStandardEntity interface { + IsK8sStandardEntity() +} + +// Page +type Page interface { + IsPage() +} + +// Project based entity +type ProjectBasedEntity interface { + IsProjectBasedEntity() +} + +// EventName +type PushPayload interface { + IsPushPayload() +} + +// Sensor trigger +type SensorTrigger interface { + IsSensorTrigger() +} + +// Slice +type Slice interface { + IsSlice() +} + +// Workflow spec template +type WorkflowSpecTemplate interface { + IsWorkflowSpecTemplate() +} + +// Account is logical entity that group together users pipeliens and more +type Account struct { + // The account id + ID string `json:"id"` + // The account unique name + Name string `json:"name"` +} + +// "Generate api token result +type APIToken struct { + // The token to use in runtime installation and other requests + Token *string `json:"token"` +} + +// AppProject entity +type AppProject struct { + // Object metadata + Metadata *ObjectMeta `json:"metadata"` + // Errors + Errors []*Error `json:"errors"` + // Entities referencing this entity + ReferencedBy []BaseEntity `json:"referencedBy"` + // Entities referenced by this enitity + References []BaseEntity `json:"references"` + // Version of the entity + Version *int `json:"version"` + // Is this the latest version of this entity + Latest *bool `json:"latest"` + // Entity source + Source *GitopsEntitySource `json:"source"` + // Sync status + SyncStatus SyncStatus `json:"syncStatus"` + // Health status + HealthStatus *HealthStatus `json:"healthStatus"` + // Health message + HealthMessage *string `json:"healthMessage"` + // Desired manifest + DesiredManifest *string `json:"desiredManifest"` + // Actual manifest + ActualManifest *string `json:"actualManifest"` + // Projects + Projects []string `json:"projects"` +} + +func (AppProject) IsGitopsEntity() {} +func (AppProject) IsBaseEntity() {} +func (AppProject) IsProjectBasedEntity() {} +func (AppProject) IsEntity() {} + +// AppProject Edge +type AppProjectEdge struct { + // Node contains the actual app-project data + Node *AppProject `json:"node"` + // Cursor + Cursor string `json:"cursor"` +} + +func (AppProjectEdge) IsEdge() {} + +// AppProject Page +type AppProjectPage struct { + // Total amount of app-projects + TotalCount int `json:"totalCount"` + // App project edges + Edges []*AppProjectEdge `json:"edges"` + // Page information + PageInfo *PageInfo `json:"pageInfo"` +} + +func (AppProjectPage) IsPage() {} + +// AppProject Slice +type AppProjectSlice struct { + // AppProject edges + Edges []*AppProjectEdge `json:"edges"` + // Slice information + PageInfo *SliceInfo `json:"pageInfo"` +} + +func (AppProjectSlice) IsSlice() {} + +// Application entity +type Application struct { + // Object metadata + Metadata *ObjectMeta `json:"metadata"` + // Errors + Errors []*Error `json:"errors"` + // Entities referencing this entity + ReferencedBy []BaseEntity `json:"referencedBy"` + // Entities referenced by this enitity + References []BaseEntity `json:"references"` + // Version of the entity + Version *int `json:"version"` + // Is this the latest version of this entity + Latest *bool `json:"latest"` + // Entity source + Source *GitopsEntitySource `json:"source"` + // Sync status + SyncStatus SyncStatus `json:"syncStatus"` + // Health status + HealthStatus *HealthStatus `json:"healthStatus"` + // Health message + HealthMessage *string `json:"healthMessage"` + // Desired manifest + DesiredManifest *string `json:"desiredManifest"` + // Actual manifest + ActualManifest *string `json:"actualManifest"` + // Projects + Projects []string `json:"projects"` + // Updated At + UpdatedAt *string `json:"updatedAt"` + // Path + Path string `json:"path"` + // RepoURL + RepoURL string `json:"repoURL"` + // Number of resources + Size *int `json:"size"` + // Revision + Revision string `json:"revision"` + // Status + Status *ArgoCDApplicationStatus `json:"status"` +} + +func (Application) IsGitopsEntity() {} +func (Application) IsBaseEntity() {} +func (Application) IsProjectBasedEntity() {} +func (Application) IsEntity() {} + +// Application Edge +type ApplicationEdge struct { + // Node contains the actual application data + Node *Application `json:"node"` + // Cursor + Cursor string `json:"cursor"` +} + +func (ApplicationEdge) IsEdge() {} + +// Application Page +type ApplicationPage struct { + // Total amount of applications + TotalCount int `json:"totalCount"` + // Application edges + Edges []*ApplicationEdge `json:"edges"` + // Page information + PageInfo *PageInfo `json:"pageInfo"` +} + +func (ApplicationPage) IsPage() {} + +// Application Slice +type ApplicationSlice struct { + // Application edges + Edges []*ApplicationEdge `json:"edges"` + // Slice information + PageInfo *SliceInfo `json:"pageInfo"` +} + +func (ApplicationSlice) IsSlice() {} + +// Argo CD Application status +type ArgoCDApplicationStatus struct { + // Sync status + SyncStatus SyncStatus `json:"syncStatus"` + // Sync started at + SyncStartedAt string `json:"syncStartedAt"` + // Sync finished at + SyncFinishedAt *string `json:"syncFinishedAt"` + // Health status + HealthStatus *HealthStatus `json:"healthStatus"` + // Health message + HealthMessage *string `json:"healthMessage"` + // Revision + Revision string `json:"revision"` +} + +// Calendar event payload data +type CalendarEventPayloadData struct { + // Event payload type + Type PayloadDataTypes `json:"type"` + // TBD + Schedule string `json:"schedule"` + // TBD + Interval string `json:"interval"` + // TBD + Timezone string `json:"timezone"` + // TBD + Metadata string `json:"metadata"` +} + +func (CalendarEventPayloadData) IsEventPayloadData() {} + +// Component entity +type Component struct { + // Object metadata + Metadata *ObjectMeta `json:"metadata"` + // Errors + Errors []*Error `json:"errors"` + // Entities referencing this entity + ReferencedBy []BaseEntity `json:"referencedBy"` + // Entities referenced by this enitity + References []BaseEntity `json:"references"` + // Self entity reference for the real k8s entity in case of codefresh logical entity + Self *Application `json:"self"` + // Projects + Projects []string `json:"projects"` + // Component's version + Version string `json:"version"` +} + +func (Component) IsBaseEntity() {} +func (Component) IsK8sLogicEntity() {} +func (Component) IsProjectBasedEntity() {} +func (Component) IsEntity() {} + +// Component Edge +type ComponentEdge struct { + // Node contains the actual component data + Node *Component `json:"node"` + // Cursor + Cursor string `json:"cursor"` +} + +func (ComponentEdge) IsEdge() {} + +// Component Page +type ComponentPage struct { + // Total amount of components + TotalCount int `json:"totalCount"` + // Component edges + Edges []*ComponentEdge `json:"edges"` + // Page information + PageInfo *PageInfo `json:"pageInfo"` +} + +func (ComponentPage) IsPage() {} + +// Component Slice +type ComponentSlice struct { + // Component edges + Edges []*ComponentEdge `json:"edges"` + // Slice information + PageInfo *SliceInfo `json:"pageInfo"` +} + +func (ComponentSlice) IsSlice() {} + +// Error +type Error struct { + // Type + Type *ErrorTypes `json:"type"` + // Code + Code *int `json:"code"` + // Title + Title *string `json:"title"` + // Message + Message *string `json:"message"` + // Suggestion + Suggestion *string `json:"suggestion"` +} + +// Remove this later +type EventB struct { + // Name of event + Name *string `json:"name"` +} + +func (EventB) IsPushPayload() {} + +// Event payload entity +type EventPayload struct { + // UID of event + UID *string `json:"uid"` + // Content of the event + Data *string `json:"data"` + // Time + Time *string `json:"time"` + // Event source + EventSource *EventSource `json:"eventSource"` + // Event name + EventName *string `json:"eventName"` + // Event type + EventType *string `json:"eventType"` + // Account + Account *string `json:"account"` + // Runtime + Runtime *string `json:"runtime"` +} + +func (EventPayload) IsEntity() {} + +// EventPayload Edge +type EventPayloadEdge struct { + // Node contains the actual event payload data + Node *EventPayload `json:"node"` + // Cursor + Cursor string `json:"cursor"` +} + +func (EventPayloadEdge) IsEdge() {} + +// EventPayload Page +type EventPayloadPage struct { + // Total amount of EventPayload + TotalCount int `json:"totalCount"` + // EventPayload edges + Edges []*EventPayloadEdge `json:"edges"` + // Page information + PageInfo *PageInfo `json:"pageInfo"` +} + +func (EventPayloadPage) IsPage() {} + +// EventPayload Slice +type EventPayloadSlice struct { + // EventPayload edges + Edges []*EventPayloadEdge `json:"edges"` + // Slice information + PageInfo *SliceInfo `json:"pageInfo"` +} + +func (EventPayloadSlice) IsSlice() {} + +// EventResponse +type EventResponse struct { + // Account ID + AccountID string `json:"accountId"` + // Time of event + Time string `json:"time"` + // Payload of event + Payload PushPayload `json:"payload"` +} + +// Event source entity +type EventSource struct { + // Object metadata + Metadata *ObjectMeta `json:"metadata"` + // Errors + Errors []*Error `json:"errors"` + // Entities referencing this entity + ReferencedBy []BaseEntity `json:"referencedBy"` + // Entities referenced by this enitity + References []BaseEntity `json:"references"` + // Version of the entity + Version *int `json:"version"` + // Is this the latest version of this entity + Latest *bool `json:"latest"` + // Entity source + Source *GitopsEntitySource `json:"source"` + // Sync status + SyncStatus SyncStatus `json:"syncStatus"` + // Health status + HealthStatus *HealthStatus `json:"healthStatus"` + // Health message + HealthMessage *string `json:"healthMessage"` + // Desired manifest + DesiredManifest *string `json:"desiredManifest"` + // Actual manifest + ActualManifest *string `json:"actualManifest"` + // Projects + Projects []string `json:"projects"` +} + +func (EventSource) IsBaseEntity() {} +func (EventSource) IsGitopsEntity() {} +func (EventSource) IsProjectBasedEntity() {} +func (EventSource) IsEntity() {} + +// Event source Edge +type EventSourceEdge struct { + // Node contains the actual event source data + Node *EventSource `json:"node"` + // Cursor + Cursor string `json:"cursor"` +} + +func (EventSourceEdge) IsEdge() {} + +// Event source Page +type EventSourcePage struct { + // Total amount of event sources + TotalCount int `json:"totalCount"` + // Event source edges + Edges []*EventSourceEdge `json:"edges"` + // Page information + PageInfo *PageInfo `json:"pageInfo"` +} + +func (EventSourcePage) IsPage() {} + +// Event source Slice +type EventSourceSlice struct { + // Event source edges + Edges []*EventSourceEdge `json:"edges"` + // Slice information + PageInfo *SliceInfo `json:"pageInfo"` +} + +func (EventSourceSlice) IsSlice() {} + +// "Commit data +type GitCommit struct { + // Commit message + Message string `json:"message"` + // Commit url + URL string `json:"url"` + // Commit head + Head *GitRevision `json:"head"` + // Modified files + ModifiedFiles []string `json:"modifiedFiles"` +} + +// "Commit event +type GitCommitEventPayloadData struct { + // Event payload type + Type PayloadDataTypes `json:"type"` + // Name of the git event + Event string `json:"event"` + // Git provider + Provider string `json:"provider"` + // Repository + Repository *Repository `json:"repository"` + // Event initiator + Initiator *Initiator `json:"initiator"` + // Commit data + Commit *GitCommit `json:"commit"` +} + +func (GitCommitEventPayloadData) IsEventPayloadData() {} +func (GitCommitEventPayloadData) IsCommonGitEventPayloadData() {} + +// Git integration entity +type GitIntegration struct { + // Object metadata + Metadata *ObjectMeta `json:"metadata"` + // Errors + Errors []*Error `json:"errors"` + // Entities referencing this entity + ReferencedBy []BaseEntity `json:"referencedBy"` + // Entities referenced by this enitity + References []BaseEntity `json:"references"` + // Version of the entity + Version *int `json:"version"` + // Is this the latest version of this entity + Latest *bool `json:"latest"` + // Entity source + Source *GitopsEntitySource `json:"source"` + // Sync status + SyncStatus SyncStatus `json:"syncStatus"` + // Health status + HealthStatus *HealthStatus `json:"healthStatus"` + // Health message + HealthMessage *string `json:"healthMessage"` + // Desired manifest + DesiredManifest *string `json:"desiredManifest"` + // Actual manifest + ActualManifest *string `json:"actualManifest"` + // Projects + Projects []string `json:"projects"` + // Git provider + Provider *GitProviders `json:"provider"` + // API URL of the git provider + APIURL string `json:"apiUrl"` +} + +func (GitIntegration) IsGitopsEntity() {} +func (GitIntegration) IsBaseEntity() {} +func (GitIntegration) IsProjectBasedEntity() {} +func (GitIntegration) IsEntity() {} + +// Git integration Edge +type GitIntegrationEdge struct { + // Node contains the actual git integration data + Node *GitIntegration `json:"node"` + // Cursor + Cursor string `json:"cursor"` +} + +func (GitIntegrationEdge) IsEdge() {} + +// Git integration Page +type GitIntegrationPage struct { + // Total amount of git integration + TotalCount int `json:"totalCount"` + // Git integration edges + Edges []*GitIntegrationEdge `json:"edges"` + // Git integration information + PageInfo *PageInfo `json:"pageInfo"` +} + +func (GitIntegrationPage) IsPage() {} + +// Git integration Slice +type GitIntegrationSlice struct { + // Git integration edges + Edges []*GitIntegrationEdge `json:"edges"` + // Slice information + PageInfo *SliceInfo `json:"pageInfo"` +} + +func (GitIntegrationSlice) IsSlice() {} + +// "PR data +type GitPr struct { + // PR action + Action string `json:"action"` + // PR id + ID string `json:"id"` + // PR title + Title string `json:"title"` + // PR url + URL string `json:"url"` + // PR number + Number int `json:"number"` + // PR labels + Labels []string `json:"labels"` + // PR head + Head *GitRevision `json:"head"` + // PR target + Target *GitRevision `json:"target"` + // Indicates if a PR was merged + Merged *bool `json:"merged"` + // Merge commit SHA + MergeCommitSha *string `json:"mergeCommitSHA"` + // Indicates if a PR comes from forked repo + Fork *bool `json:"fork"` + // PR comment + Comment *GitPRComment `json:"comment"` + // Modified files + ModifiedFiles []string `json:"modifiedFiles"` +} + +// "PR Comment data +type GitPRComment struct { + // Comment message + Message string `json:"message"` + // Comment author + Author string `json:"author"` + // Comment author association + AuthorAssociation *string `json:"authorAssociation"` +} + +// "PR event +type GitPREventPayloadData struct { + // Event payload type + Type PayloadDataTypes `json:"type"` + // Name of the git event + Event string `json:"event"` + // Git provider + Provider string `json:"provider"` + // Repository + Repository *Repository `json:"repository"` + // Event initiator + Initiator *Initiator `json:"initiator"` + // PR data + Pr *GitPr `json:"pr"` +} + +func (GitPREventPayloadData) IsEventPayloadData() {} +func (GitPREventPayloadData) IsCommonGitEventPayloadData() {} + +// "Release data +type GitRelease struct { + // Release action + Action string `json:"action"` + // Release id + ID string `json:"id"` + // Release name + Name string `json:"name"` + // Release tag name + TagName string `json:"tagName"` + // Indicates if current release is a pre release + IsPreRelease bool `json:"isPreRelease"` +} + +// "Release event +type GitReleaseEventPayloadData struct { + // Event payload type + Type PayloadDataTypes `json:"type"` + // Name of the git event + Event string `json:"event"` + // Git provider + Provider string `json:"provider"` + // Repository + Repository *Repository `json:"repository"` + // Event initiator + Initiator *Initiator `json:"initiator"` + // Release data + Release *GitRelease `json:"release"` +} + +func (GitReleaseEventPayloadData) IsEventPayloadData() {} +func (GitReleaseEventPayloadData) IsCommonGitEventPayloadData() {} + +// "Revision data +type GitRevision struct { + // Branch name + Branch string `json:"branch"` + // Branch url + BranchURL string `json:"branchURL"` + // Revision SHA + Sha string `json:"sha"` +} + +// Git source entity +type GitSource struct { + // Object metadata + Metadata *ObjectMeta `json:"metadata"` + // Errors + Errors []*Error `json:"errors"` + // Entities referencing this entity + ReferencedBy []BaseEntity `json:"referencedBy"` + // Entities referenced by this enitity + References []BaseEntity `json:"references"` + // Self entity reference for the real k8s entity in case of codefresh logical entity + Self *Application `json:"self"` + // Projects + Projects []string `json:"projects"` +} + +func (GitSource) IsK8sLogicEntity() {} +func (GitSource) IsBaseEntity() {} +func (GitSource) IsProjectBasedEntity() {} +func (GitSource) IsEntity() {} + +// Git source Edge +type GitSourceEdge struct { + // Node contains the actual git source data + Node *GitSource `json:"node"` + // Cursor + Cursor string `json:"cursor"` +} + +func (GitSourceEdge) IsEdge() {} + +// Git source Page +type GitSourcePage struct { + // Total amount of git sources + TotalCount int `json:"totalCount"` + // Git source edges + Edges []*GitSourceEdge `json:"edges"` + // Page information + PageInfo *PageInfo `json:"pageInfo"` +} + +func (GitSourcePage) IsPage() {} + +// Git source Slice +type GitSourceSlice struct { + // Git source edges + Edges []*GitSourceEdge `json:"edges"` + // Slice information + PageInfo *SliceInfo `json:"pageInfo"` +} + +func (GitSourceSlice) IsSlice() {} + +// Github event +type GithubEvent struct { + // Name + Name string `json:"name"` + // Repository owner + Owner string `json:"owner"` + // Repository names + Repositories []string `json:"repositories"` + // Webhook events + Events []string `json:"events"` +} + +func (GithubEvent) IsEvent() {} + +// Gitops entity source +type GitopsEntitySource struct { + // Entity source + GitSource *GitSource `json:"gitSource"` + // Path + Path string `json:"path"` + // Git revision + Revision string `json:"revision"` + // Git manifest + GitManifest string `json:"gitManifest"` +} + +// Http Trigger +type HTTPTrigger struct { + // Name + Name string `json:"name"` + // Conditions + Conditions string `json:"conditions"` + // Url + URL string `json:"url"` + // Method + Method string `json:"method"` +} + +func (HTTPTrigger) IsSensorTrigger() {} + +// "Event initiator +type Initiator struct { + // Git user username + UserName string `json:"userName"` + // Git user id + UserID string `json:"userId"` + // Git user email + UserEmail string `json:"userEmail"` + // Link to the user avatar image + UserAvatarURL string `json:"userAvatarUrl"` + // Link to the user git profile + UserProfileURL string `json:"userProfileUrl"` +} + +// Me +type Me struct { + // The user id + ID string `json:"id"` + // The roles of the user provide specific permission for the current user + Roles []*UserRole `json:"roles"` + // The accounts the this user have acsess to + Accounts []*Account `json:"accounts"` + // The default account for this user + ActiveAccount *Account `json:"activeAccount"` + // The customers that this user is in + Customers []Customer `json:"customers"` + // The current status of this user + Status *UserStatus `json:"status"` + // Provide details about this user + Details *UserDetails `json:"details"` + // Provide info on user + Info *UserInfo `json:"info"` +} + +// Node status +type NodeStatus struct { + // Type + Type string `json:"type"` + // Name + Name string `json:"name"` + // Display name + DisplayName string `json:"displayName"` + // Template Name + TemplateName string `json:"templateName"` + // Node children + Children []*string `json:"children"` + // Current step phase + Phase *Phases `json:"phase"` + // Progress + Progress *Progress `json:"progress"` + // Message + Message *string `json:"message"` + // Start time + StartedAt *string `json:"startedAt"` + // Finish time + FinishedAt *string `json:"finishedAt"` + // Inputs + Inputs *string `json:"inputs"` + // Previous statuses + Statuses []*StatusHistoryItem `json:"statuses"` +} + +// Object metadata +type ObjectMeta struct { + // Group + Group string `json:"group"` + // Version + Version string `json:"version"` + // Kind + Kind string `json:"kind"` + // Name + Name string `json:"name"` + // Description + Description *string `json:"description"` + // Namespace + Namespace *string `json:"namespace"` + // Runtime + Runtime string `json:"runtime"` + // Account name + Account string `json:"account"` + // Labels + Labels []*StringPair `json:"labels"` + // Annotations + Annotations []*StringPair `json:"annotations"` + // Last updated + LastUpdated *string `json:"lastUpdated"` + // Created + Created *string `json:"created"` +} + +// Information about current page +type PageInfo struct { + // Cursor for the first result in the page + StartCursor *string `json:"startCursor"` + // Cursor for the last result in the page + EndCursor *string `json:"endCursor"` + // Indicate if there is next page + HasNextPage bool `json:"hasNextPage"` + // Indicate if there is previous page + HasPrevPage bool `json:"hasPrevPage"` +} + +// Pipeline entity +type Pipeline struct { + // Object metadata + Metadata *ObjectMeta `json:"metadata"` + // Errors + Errors []*Error `json:"errors"` + // Entities referencing this entity + ReferencedBy []BaseEntity `json:"referencedBy"` + // Entities referenced by this enitity + References []BaseEntity `json:"references"` + // Self entity reference for the real k8s entity in case of codefresh logical entity + Self *Sensor `json:"self"` + // Projects + Projects []string `json:"projects"` + // Dependencies + Dependencies []*SensorDependency `json:"dependencies"` + // Trigger name + Trigger string `json:"trigger"` +} + +func (Pipeline) IsBaseEntity() {} +func (Pipeline) IsK8sLogicEntity() {} +func (Pipeline) IsProjectBasedEntity() {} +func (Pipeline) IsEntity() {} + +// Pipeline Edge +type PipelineEdge struct { + // Node contains the actual pipeline data + Node *Pipeline `json:"node"` + // Cursor + Cursor string `json:"cursor"` +} + +func (PipelineEdge) IsEdge() {} + +// Pipeline Page +type PipelinePage struct { + // Total amount of pipelines + TotalCount int `json:"totalCount"` + // Pipeline edges + Edges []*PipelineEdge `json:"edges"` + // Page information + PageInfo *PageInfo `json:"pageInfo"` +} + +func (PipelinePage) IsPage() {} + +// Pipeline Slice +type PipelineSlice struct { + // Pipeline edges + Edges []*PipelineEdge `json:"edges"` + // Slice information + PageInfo *SliceInfo `json:"pageInfo"` +} + +func (PipelineSlice) IsSlice() {} + +// Progress +type Progress struct { + // Total + Total *int `json:"total"` + // Done + Done *int `json:"done"` +} + +// Project entity +type Project struct { + // Project name + Name string `json:"name"` + // Project description + Description *string `json:"description"` +} + +func (Project) IsEntity() {} + +// Project Edge +type ProjectEdge struct { + // Node contains the actual project data + Node *Project `json:"node"` + // Cursor + Cursor string `json:"cursor"` +} + +func (ProjectEdge) IsEdge() {} + +// Project Page +type ProjectPage struct { + // Total amount of Projects + TotalCount int `json:"totalCount"` + // Project edges + Edges []*ProjectEdge `json:"edges"` + // Page information + PageInfo *PageInfo `json:"pageInfo"` +} + +func (ProjectPage) IsPage() {} + +// Project Slice +type ProjectSlice struct { + // Project edges + Edges []*ProjectEdge `json:"edges"` + // Slice information + PageInfo *SliceInfo `json:"pageInfo"` +} + +func (ProjectSlice) IsSlice() {} + +// Release Entity +type Release struct { + // Release version + Version string `json:"version"` +} + +// "Repository +type Repository struct { + // Repository name + Name string `json:"name"` + // Repository owner + Owner string `json:"owner"` + // Repository name in format {owner}/{name} + FullName string `json:"fullName"` + // Repository URL + URL string `json:"url"` +} + +// Resource event +type ResourceEvent struct { + // Name + Name string `json:"name"` + // Group + Group string `json:"group"` + // Version + Version string `json:"version"` + // Kind + Kind string `json:"kind"` + // Namespace + Namespace string `json:"namespace"` +} + +func (ResourceEvent) IsEvent() {} + +// Runtime entity +type Runtime struct { + // Object metadata + Metadata *ObjectMeta `json:"metadata"` + // Errors + Errors []*Error `json:"errors"` + // Entities referencing this entity + ReferencedBy []BaseEntity `json:"referencedBy"` + // Entities referenced by this enitity + References []BaseEntity `json:"references"` + // Self entity reference for the real k8s entity in case of codefresh logical entity + Self *AppProject `json:"self"` + // Projects + Projects []string `json:"projects"` + // Cluster + Cluster *string `json:"cluster"` + // Runtime version + RuntimeVersion *string `json:"runtimeVersion"` +} + +func (Runtime) IsBaseEntity() {} +func (Runtime) IsProjectBasedEntity() {} +func (Runtime) IsK8sLogicEntity() {} +func (Runtime) IsEntity() {} + +// Response for creating a runtime +type RuntimeCreationResponse struct { + // The runtime access token that will be used for requests from the runtime + NewAccessToken string `json:"newAccessToken"` + // The name of the newly created runtime + Name string `json:"name"` +} + +// Runtime Edge +type RuntimeEdge struct { + // Node contains the actual runtime data + Node *Runtime `json:"node"` + // Cursor + Cursor string `json:"cursor"` +} + +func (RuntimeEdge) IsEdge() {} + +// Runtime Page +type RuntimePage struct { + // Total amount of runtimes + TotalCount int `json:"totalCount"` + // Runtime edges + Edges []*RuntimeEdge `json:"edges"` + // Page information + PageInfo *PageInfo `json:"pageInfo"` +} + +func (RuntimePage) IsPage() {} + +// RuntimePushPayload +type RuntimePushPayload struct { + // Name of event + Name *string `json:"name"` +} + +func (RuntimePushPayload) IsPushPayload() {} + +// Runtime Slice +type RuntimeSlice struct { + // Runtime edges + Edges []*RuntimeEdge `json:"edges"` + // Slice information + PageInfo *SliceInfo `json:"pageInfo"` +} + +func (RuntimeSlice) IsSlice() {} + +// Sensor entity +type Sensor struct { + // Object metadata + Metadata *ObjectMeta `json:"metadata"` + // Errors + Errors []*Error `json:"errors"` + // Entities referencing this entity + ReferencedBy []BaseEntity `json:"referencedBy"` + // Entities referenced by this enitity + References []BaseEntity `json:"references"` + // Version of the entity + Version *int `json:"version"` + // Is this the latest version of this entity + Latest *bool `json:"latest"` + // Entity source + Source *GitopsEntitySource `json:"source"` + // Sync status + SyncStatus SyncStatus `json:"syncStatus"` + // Health status + HealthStatus *HealthStatus `json:"healthStatus"` + // Health message + HealthMessage *string `json:"healthMessage"` + // Desired manifest + DesiredManifest *string `json:"desiredManifest"` + // Actual manifest + ActualManifest *string `json:"actualManifest"` + // Projects + Projects []string `json:"projects"` + // Dependencies + Dependencies []*SensorDependency `json:"dependencies"` + // Triggers + Triggers []SensorTrigger `json:"triggers"` +} + +func (Sensor) IsGitopsEntity() {} +func (Sensor) IsBaseEntity() {} +func (Sensor) IsProjectBasedEntity() {} +func (Sensor) IsEntity() {} + +// Sensor dependency +type SensorDependency struct { + // Name + Name string `json:"name"` + // EventSource name + EventSource string `json:"eventSource"` + // Event name + Event string `json:"event"` +} + +// Sensor Edge +type SensorEdge struct { + // Node contains the actual sensor data + Node *Sensor `json:"node"` + // Cursor + Cursor string `json:"cursor"` +} + +func (SensorEdge) IsEdge() {} + +// Sensor Page +type SensorPage struct { + // Total amount of sensors + TotalCount int `json:"totalCount"` + // Sensor edges + Edges []*SensorEdge `json:"edges"` + // Page information + PageInfo *PageInfo `json:"pageInfo"` +} + +func (SensorPage) IsPage() {} + +// Sensor Slice +type SensorSlice struct { + // Sensor edges + Edges []*SensorEdge `json:"edges"` + // Slice information + PageInfo *SliceInfo `json:"pageInfo"` +} + +func (SensorSlice) IsSlice() {} + +// Information about current slice +type SliceInfo struct { + // Cursor for the first result in the slice + StartCursor *string `json:"startCursor"` + // Cursor for the last result in the slice + EndCursor *string `json:"endCursor"` + // Indicate if there is next slice + HasNextPage bool `json:"hasNextPage"` + // Indicate if there is previous slice + HasPrevPage bool `json:"hasPrevPage"` +} + +// Pagination arguments to request slice +type SlicePaginationArgs struct { + // Returns workflow templates after the provided cursor + After *string `json:"after"` + // Returns workflow templates before the provided cursor + Before *string `json:"before"` + // Returns the first X workflow templates + First *int `json:"first"` + // Returns the last X workflow templates + Last *int `json:"last"` +} + +// Workflow status history item +type StatusHistoryItem struct { + // The time the status started + Since string `json:"since"` + // Phase + Phase Phases `json:"phase"` + // Message + Message *string `json:"message"` +} + +// Lable +type StringPair struct { + // Key + Key string `json:"key"` + // Value + Value string `json:"value"` +} + +// "response for request to switch account +type SwitchAccountResponse struct { + // The token to use for the next requests + NewAccessToken *string `json:"newAccessToken"` +} + +// Calendar event payload data +type UnknownEventPayloadData struct { + // Event payload type + Type PayloadDataTypes `json:"type"` + // Event name + Event string `json:"event"` +} + +func (UnknownEventPayloadData) IsEventPayloadData() {} + +// "User Details +type UserDetails struct { + // The user name + Name string `json:"name"` + // User image url + Image *string `json:"image"` +} + +// "User statistics +type UserInfo struct { + // The user name + Name *string `json:"name"` + // Register date + RegisterDate *string `json:"registerDate"` + // Last time user logged in to the system + LastLoginDate *string `json:"lastLoginDate"` +} + +// Workflow entity +type Workflow struct { + // Object metadata + Metadata *ObjectMeta `json:"metadata"` + // Errors + Errors []*Error `json:"errors"` + // Entities referencing this entity + ReferencedBy []BaseEntity `json:"referencedBy"` + // Entities referenced by this enitity + References []BaseEntity `json:"references"` + // Projects + Projects []string `json:"projects"` + // Workflow spec + Spec *WorkflowSpec `json:"spec"` + // Workflow status + Status *WorkflowStatus `json:"status"` + // Events payload Data + EventsPayloadData []EventPayloadData `json:"eventsPayloadData"` + // Events payload references + EventsPayload []*EventPayload `json:"eventsPayload"` + // Pipeline refernece + Pipeline *Pipeline `json:"pipeline"` + // Actual manifest + ActualManifest *string `json:"actualManifest"` +} + +func (Workflow) IsProjectBasedEntity() {} +func (Workflow) IsBaseEntity() {} +func (Workflow) IsK8sStandardEntity() {} +func (Workflow) IsEntity() {} + +// Workflow step +type WorkflowContainerSpec struct { + // Name + Name *string `json:"name"` + // Image + Image *string `json:"image"` + // Command array + Command []*string `json:"command"` + // Args + Args []*string `json:"args"` + // Env map + Env []*StringPair `json:"env"` +} + +// Workflow container template +type WorkflowContainerTemplate struct { + // Name + Name string `json:"name"` + // Daemon + Daemon *bool `json:"daemon"` + // Container + Container *WorkflowContainerSpec `json:"container"` +} + +func (WorkflowContainerTemplate) IsWorkflowSpecTemplate() {} + +// Workflow DAG task +type WorkflowDAGTask struct { + // Name + Name string `json:"name"` + // Template to execute + TemplateName *string `json:"templateName"` + // Workflow template ref + WorkflowTemplateRef *WorkflowTemplateRef `json:"workflowTemplateRef"` +} + +// Workflow DAG template +type WorkflowDAGTemplate struct { + // Name + Name string `json:"name"` + // Tasks + Tasks []*WorkflowDAGTask `json:"tasks"` + // Fail on first failed task + FailFast *bool `json:"failFast"` +} + +func (WorkflowDAGTemplate) IsWorkflowSpecTemplate() {} + +// Workflow Edge +type WorkflowEdge struct { + // Node contains the actual workflow data + Node *Workflow `json:"node"` + // Cursor + Cursor string `json:"cursor"` +} + +func (WorkflowEdge) IsEdge() {} + +// Workflow Page +type WorkflowPage struct { + // Total amount of workflows + TotalCount int `json:"totalCount"` + // Workflow edges + Edges []*WorkflowEdge `json:"edges"` + // Page information + PageInfo *PageInfo `json:"pageInfo"` +} + +func (WorkflowPage) IsPage() {} + +// Workflow Resource template +type WorkflowResourceTemplate struct { + // Name + Name string `json:"name"` +} + +func (WorkflowResourceTemplate) IsWorkflowSpecTemplate() {} + +// Workflow script template +type WorkflowScriptTemplate struct { + // Name + Name string `json:"name"` +} + +func (WorkflowScriptTemplate) IsWorkflowSpecTemplate() {} + +// Workflow Slice +type WorkflowSlice struct { + // Workflow edges + Edges []*WorkflowEdge `json:"edges"` + // Slice information + PageInfo *SliceInfo `json:"pageInfo"` +} + +func (WorkflowSlice) IsSlice() {} + +// Workflow spec +type WorkflowSpec struct { + // Entrypoint + Entrypoint *string `json:"entrypoint"` + // Templates + Templates []WorkflowSpecTemplate `json:"templates"` + // Workflow template reference + WorkflowTemplateRef *WorkflowTemplateRef `json:"workflowTemplateRef"` +} + +// Workflow spec name only template +type WorkflowSpecNameOnlyTemplate struct { + // Name + Name string `json:"name"` +} + +func (WorkflowSpecNameOnlyTemplate) IsWorkflowSpecTemplate() {} + +// Workflow status +type WorkflowStatus struct { + // Creation time + CreatedAt string `json:"createdAt"` + // Start time + StartedAt *string `json:"startedAt"` + // Finish time + FinishedAt *string `json:"finishedAt"` + // Current workflow phase + Phase Phases `json:"phase"` + // Progress + Progress *Progress `json:"progress"` + // Current workflow nodes status + Nodes []*NodeStatus `json:"nodes"` + // Message + Message *string `json:"message"` + // Previous statuses + Statuses []*StatusHistoryItem `json:"statuses"` +} + +// Workflow step +type WorkflowStep struct { + // Name + Name string `json:"name"` + // Template to execute + TemplateName *string `json:"templateName"` + // Workflow template ref + WorkflowTemplateRef *WorkflowTemplateRef `json:"workflowTemplateRef"` +} + +// Workflow steps template +type WorkflowStepsTemplate struct { + // Name + Name string `json:"name"` + // Steps + Steps [][]*WorkflowStep `json:"steps"` +} + +func (WorkflowStepsTemplate) IsWorkflowSpecTemplate() {} + +// Workflow Resource template +type WorkflowSuspendedTemplate struct { + // Name + Name string `json:"name"` +} + +func (WorkflowSuspendedTemplate) IsWorkflowSpecTemplate() {} + +// Workflow template entity +type WorkflowTemplate struct { + // Object metadata + Metadata *ObjectMeta `json:"metadata"` + // Errors + Errors []*Error `json:"errors"` + // Entities referencing this entity + ReferencedBy []BaseEntity `json:"referencedBy"` + // Entities referenced by this enitity + References []BaseEntity `json:"references"` + // Version of the entity + Version *int `json:"version"` + // Is this the latest version of this entity + Latest *bool `json:"latest"` + // Entity source + Source *GitopsEntitySource `json:"source"` + // Sync status + SyncStatus SyncStatus `json:"syncStatus"` + // Health status + HealthStatus *HealthStatus `json:"healthStatus"` + // Health message + HealthMessage *string `json:"healthMessage"` + // Desired manifest + DesiredManifest *string `json:"desiredManifest"` + // Actual manifest + ActualManifest *string `json:"actualManifest"` + // Projects + Projects []string `json:"projects"` + // Workflow spec + Spec *WorkflowSpec `json:"spec"` +} + +func (WorkflowTemplate) IsGitopsEntity() {} +func (WorkflowTemplate) IsBaseEntity() {} +func (WorkflowTemplate) IsProjectBasedEntity() {} +func (WorkflowTemplate) IsEntity() {} + +// Workflow template Edge +type WorkflowTemplateEdge struct { + // Node contains the actual workflow template data + Node *WorkflowTemplate `json:"node"` + // Cursor + Cursor string `json:"cursor"` +} + +func (WorkflowTemplateEdge) IsEdge() {} + +// WorkflowTemplate Page +type WorkflowTemplatePage struct { + // Total amount of workflow templates + TotalCount int `json:"totalCount"` + // Workflow template edges + Edges []*WorkflowTemplateEdge `json:"edges"` + // Page information + PageInfo *PageInfo `json:"pageInfo"` +} + +func (WorkflowTemplatePage) IsPage() {} + +// Workflow template ref +type WorkflowTemplateRef struct { + // Name + Name *string `json:"name"` + // Group + Group string `json:"group"` + // Kind + Kind string `json:"kind"` + // Version + Version string `json:"version"` + // Namespace + Namespace *string `json:"namespace"` +} + +// WorkflowTemplate Slice +type WorkflowTemplateSlice struct { + // Workflow template edges + Edges []*WorkflowTemplateEdge `json:"edges"` + // Slice information + PageInfo *SliceInfo `json:"pageInfo"` +} + +func (WorkflowTemplateSlice) IsSlice() {} + +// Http Trigger +type WorkflowTrigger struct { + // Name + Name string `json:"name"` + // Conditions + Conditions string `json:"conditions"` + // Workflow manifest + Workflow string `json:"workflow"` + // Operation + Op WorkflowTriggerOperation `json:"op"` +} + +func (WorkflowTrigger) IsSensorTrigger() {} + +// Workflow filter arguments +type WorkflowsFilterArgs struct { + // Filter workflows from a specific project + Project *string `json:"project"` + // Filter workflows from a specific runtime + Runtime *string `json:"runtime"` + // Filter workflows from a specific pipeline + Pipeline *string `json:"pipeline"` + // Filter workflows from a specific repositories + Repositories []*string `json:"repositories"` + // Filter workflows from a specific branches + Branches []*string `json:"branches"` + // Filter workflows from a specific event types + EventTypes []*string `json:"eventTypes"` + // Filter workflows from a specific initiators + Initiators []*string `json:"initiators"` + // Filter workflows from a specific statuses + Statuses []*Phases `json:"statuses"` + // Filter workflows from a specific start date + StartDate *string `json:"startDate"` +} + +// Error types +type ErrorTypes string + +const ( + // Permission error + ErrorTypesPermission ErrorTypes = "PERMISSION" + // Syntax error + ErrorTypesSyntax ErrorTypes = "SYNTAX" +) + +var AllErrorTypes = []ErrorTypes{ + ErrorTypesPermission, + ErrorTypesSyntax, +} + +func (e ErrorTypes) IsValid() bool { + switch e { + case ErrorTypesPermission, ErrorTypesSyntax: + return true + } + return false +} + +func (e ErrorTypes) String() string { + return string(e) +} + +func (e *ErrorTypes) UnmarshalGQL(v interface{}) error { + str, ok := v.(string) + if !ok { + return fmt.Errorf("enums must be strings") + } + + *e = ErrorTypes(str) + if !e.IsValid() { + return fmt.Errorf("%s is not a valid ErrorTypes", str) + } + return nil +} + +func (e ErrorTypes) MarshalGQL(w io.Writer) { + fmt.Fprint(w, strconv.Quote(e.String())) +} + +// Git Providers +type GitProviders string + +const ( + // Github + GitProvidersGithub GitProviders = "GITHUB" + // Gitlab + GitProvidersGitlab GitProviders = "GITLAB" +) + +var AllGitProviders = []GitProviders{ + GitProvidersGithub, + GitProvidersGitlab, +} + +func (e GitProviders) IsValid() bool { + switch e { + case GitProvidersGithub, GitProvidersGitlab: + return true + } + return false +} + +func (e GitProviders) String() string { + return string(e) +} + +func (e *GitProviders) UnmarshalGQL(v interface{}) error { + str, ok := v.(string) + if !ok { + return fmt.Errorf("enums must be strings") + } + + *e = GitProviders(str) + if !e.IsValid() { + return fmt.Errorf("%s is not a valid GitProviders", str) + } + return nil +} + +func (e GitProviders) MarshalGQL(w io.Writer) { + fmt.Fprint(w, strconv.Quote(e.String())) +} + +// Health Status +type HealthStatus string + +const ( + // resource status indicates failure + HealthStatusDegraded HealthStatus = "DEGRADED" + // resource is healthy + HealthStatusHealthy HealthStatus = "HEALTHY" + // resource is missing from the cluster + HealthStatusMissing HealthStatus = "MISSING" + // resource not yet healthy but has a chance to become healthy + HealthStatusProgressing HealthStatus = "PROGRESSING" + // resource is suspended (for example: cronjob) + HealthStatusSuspended HealthStatus = "SUSPENDED" + // health assessment failed + HealthStatusUnknown HealthStatus = "UNKNOWN" +) + +var AllHealthStatus = []HealthStatus{ + HealthStatusDegraded, + HealthStatusHealthy, + HealthStatusMissing, + HealthStatusProgressing, + HealthStatusSuspended, + HealthStatusUnknown, +} + +func (e HealthStatus) IsValid() bool { + switch e { + case HealthStatusDegraded, HealthStatusHealthy, HealthStatusMissing, HealthStatusProgressing, HealthStatusSuspended, HealthStatusUnknown: + return true + } + return false +} + +func (e HealthStatus) String() string { + return string(e) +} + +func (e *HealthStatus) UnmarshalGQL(v interface{}) error { + str, ok := v.(string) + if !ok { + return fmt.Errorf("enums must be strings") + } + + *e = HealthStatus(str) + if !e.IsValid() { + return fmt.Errorf("%s is not a valid HealthStatus", str) + } + return nil +} + +func (e HealthStatus) MarshalGQL(w io.Writer) { + fmt.Fprint(w, strconv.Quote(e.String())) +} + +// Types of event payload +type PayloadDataTypes string + +const ( + PayloadDataTypesCalendar PayloadDataTypes = "CALENDAR" + PayloadDataTypesGitPr PayloadDataTypes = "GIT_PR" + PayloadDataTypesGitPush PayloadDataTypes = "GIT_PUSH" + PayloadDataTypesGitRelease PayloadDataTypes = "GIT_RELEASE" + PayloadDataTypesUnknown PayloadDataTypes = "UNKNOWN" +) + +var AllPayloadDataTypes = []PayloadDataTypes{ + PayloadDataTypesCalendar, + PayloadDataTypesGitPr, + PayloadDataTypesGitPush, + PayloadDataTypesGitRelease, + PayloadDataTypesUnknown, +} + +func (e PayloadDataTypes) IsValid() bool { + switch e { + case PayloadDataTypesCalendar, PayloadDataTypesGitPr, PayloadDataTypesGitPush, PayloadDataTypesGitRelease, PayloadDataTypesUnknown: + return true + } + return false +} + +func (e PayloadDataTypes) String() string { + return string(e) +} + +func (e *PayloadDataTypes) UnmarshalGQL(v interface{}) error { + str, ok := v.(string) + if !ok { + return fmt.Errorf("enums must be strings") + } + + *e = PayloadDataTypes(str) + if !e.IsValid() { + return fmt.Errorf("%s is not a valid PayloadDataTypes", str) + } + return nil +} + +func (e PayloadDataTypes) MarshalGQL(w io.Writer) { + fmt.Fprint(w, strconv.Quote(e.String())) +} + +// Workflow phases +type Phases string + +const ( + // Error + PhasesError Phases = "Error" + // Failed + PhasesFailed Phases = "Failed" + // Pending + PhasesPending Phases = "Pending" + // Running + PhasesRunning Phases = "Running" + // Succeeded + PhasesSucceeded Phases = "Succeeded" + // Terminated + PhasesTerminated Phases = "Terminated" +) + +var AllPhases = []Phases{ + PhasesError, + PhasesFailed, + PhasesPending, + PhasesRunning, + PhasesSucceeded, + PhasesTerminated, +} + +func (e Phases) IsValid() bool { + switch e { + case PhasesError, PhasesFailed, PhasesPending, PhasesRunning, PhasesSucceeded, PhasesTerminated: + return true + } + return false +} + +func (e Phases) String() string { + return string(e) +} + +func (e *Phases) UnmarshalGQL(v interface{}) error { + str, ok := v.(string) + if !ok { + return fmt.Errorf("enums must be strings") + } + + *e = Phases(str) + if !e.IsValid() { + return fmt.Errorf("%s is not a valid Phases", str) + } + return nil +} + +func (e Phases) MarshalGQL(w io.Writer) { + fmt.Fprint(w, strconv.Quote(e.String())) +} + +// Sync status +type SyncStatus string + +const ( + // Out of sync + SyncStatusOutOfSync SyncStatus = "OUT_OF_SYNC" + // Synced + SyncStatusSynced SyncStatus = "SYNCED" + // Unknown + SyncStatusUnknown SyncStatus = "UNKNOWN" +) + +var AllSyncStatus = []SyncStatus{ + SyncStatusOutOfSync, + SyncStatusSynced, + SyncStatusUnknown, +} + +func (e SyncStatus) IsValid() bool { + switch e { + case SyncStatusOutOfSync, SyncStatusSynced, SyncStatusUnknown: + return true + } + return false +} + +func (e SyncStatus) String() string { + return string(e) +} + +func (e *SyncStatus) UnmarshalGQL(v interface{}) error { + str, ok := v.(string) + if !ok { + return fmt.Errorf("enums must be strings") + } + + *e = SyncStatus(str) + if !e.IsValid() { + return fmt.Errorf("%s is not a valid SyncStatus", str) + } + return nil +} + +func (e SyncStatus) MarshalGQL(w io.Writer) { + fmt.Fprint(w, strconv.Quote(e.String())) +} + +// "User role provide specific permission for the current user +type UserRole string + +const ( + // Account Admin role can control codefresh + UserRoleAccountAdmin UserRole = "ACCOUNT_ADMIN" + // Admin role can control the entire system + UserRoleAdmin UserRole = "ADMIN" + // Regular user can do basic operations the current account + UserRoleUser UserRole = "USER" +) + +var AllUserRole = []UserRole{ + UserRoleAccountAdmin, + UserRoleAdmin, + UserRoleUser, +} + +func (e UserRole) IsValid() bool { + switch e { + case UserRoleAccountAdmin, UserRoleAdmin, UserRoleUser: + return true + } + return false +} + +func (e UserRole) String() string { + return string(e) +} + +func (e *UserRole) UnmarshalGQL(v interface{}) error { + str, ok := v.(string) + if !ok { + return fmt.Errorf("enums must be strings") + } + + *e = UserRole(str) + if !e.IsValid() { + return fmt.Errorf("%s is not a valid UserRole", str) + } + return nil +} + +func (e UserRole) MarshalGQL(w io.Writer) { + fmt.Fprint(w, strconv.Quote(e.String())) +} + +// "User status active or disable +type UserStatus string + +const ( + // New user + UserStatusNew UserStatus = "NEW" + // Pending user + UserStatusPending UserStatus = "PENDING" + // Suspended + UserStatusSuspended UserStatus = "SUSPENDED" + // Unverifed user + UserStatusUnverifed UserStatus = "UNVERIFED" +) + +var AllUserStatus = []UserStatus{ + UserStatusNew, + UserStatusPending, + UserStatusSuspended, + UserStatusUnverifed, +} + +func (e UserStatus) IsValid() bool { + switch e { + case UserStatusNew, UserStatusPending, UserStatusSuspended, UserStatusUnverifed: + return true + } + return false +} + +func (e UserStatus) String() string { + return string(e) +} + +func (e *UserStatus) UnmarshalGQL(v interface{}) error { + str, ok := v.(string) + if !ok { + return fmt.Errorf("enums must be strings") + } + + *e = UserStatus(str) + if !e.IsValid() { + return fmt.Errorf("%s is not a valid UserStatus", str) + } + return nil +} + +func (e UserStatus) MarshalGQL(w io.Writer) { + fmt.Fprint(w, strconv.Quote(e.String())) +} + +// Workflow Trigger Operation +type WorkflowTriggerOperation string + +const ( + // Resubmit + WorkflowTriggerOperationResubmit WorkflowTriggerOperation = "RESUBMIT" + // Resume + WorkflowTriggerOperationResume WorkflowTriggerOperation = "RESUME" + // Retry + WorkflowTriggerOperationRetry WorkflowTriggerOperation = "RETRY" + // Submit + WorkflowTriggerOperationSubmit WorkflowTriggerOperation = "SUBMIT" + // Suspend + WorkflowTriggerOperationSuspend WorkflowTriggerOperation = "SUSPEND" + // Terminate + WorkflowTriggerOperationTerminate WorkflowTriggerOperation = "TERMINATE" +) + +var AllWorkflowTriggerOperation = []WorkflowTriggerOperation{ + WorkflowTriggerOperationResubmit, + WorkflowTriggerOperationResume, + WorkflowTriggerOperationRetry, + WorkflowTriggerOperationSubmit, + WorkflowTriggerOperationSuspend, + WorkflowTriggerOperationTerminate, +} + +func (e WorkflowTriggerOperation) IsValid() bool { + switch e { + case WorkflowTriggerOperationResubmit, WorkflowTriggerOperationResume, WorkflowTriggerOperationRetry, WorkflowTriggerOperationSubmit, WorkflowTriggerOperationSuspend, WorkflowTriggerOperationTerminate: + return true + } + return false +} + +func (e WorkflowTriggerOperation) String() string { + return string(e) +} + +func (e *WorkflowTriggerOperation) UnmarshalGQL(v interface{}) error { + str, ok := v.(string) + if !ok { + return fmt.Errorf("enums must be strings") + } + + *e = WorkflowTriggerOperation(str) + if !e.IsValid() { + return fmt.Errorf("%s is not a valid WorkflowTriggerOperation", str) + } + return nil +} + +func (e WorkflowTriggerOperation) MarshalGQL(w io.Writer) { + fmt.Fprint(w, strconv.Quote(e.String())) +} diff --git a/pkg/codefresh/pipeline.go b/pkg/codefresh/pipeline.go index 067cfb9..e26d4c7 100644 --- a/pkg/codefresh/pipeline.go +++ b/pkg/codefresh/pipeline.go @@ -61,7 +61,7 @@ type ( } pipeline struct { - codefresh Codefresh + codefresh *codefresh } RunOptions struct { @@ -70,7 +70,7 @@ type ( } ) -func newPipelineAPI(codefresh Codefresh) IPipelineAPI { +func newPipelineAPI(codefresh *codefresh) IPipelineAPI { return &pipeline{codefresh} } diff --git a/pkg/codefresh/progress.go b/pkg/codefresh/progress.go index ae03e92..ac58e71 100644 --- a/pkg/codefresh/progress.go +++ b/pkg/codefresh/progress.go @@ -10,7 +10,7 @@ type ( } progress struct { - codefresh Codefresh + codefresh *codefresh } Progress struct { @@ -25,7 +25,7 @@ type ( } ) -func newProgressAPI(codefresh Codefresh) IProgressAPI { +func newProgressAPI(codefresh *codefresh) IProgressAPI { return &progress{codefresh} } diff --git a/pkg/codefresh/project.go b/pkg/codefresh/project.go index 65db04d..701a387 100644 --- a/pkg/codefresh/project.go +++ b/pkg/codefresh/project.go @@ -5,11 +5,11 @@ type ( List() ([]*Project, error) } project struct { - codefresh Codefresh + codefresh *codefresh } Project struct { ProjectName string `json:"projectName"` - pipelineNumber int `json:"pipelineNumber"` + PipelineNumber int `json:"pipelineNumber"` } getProjectResponse struct { Total int `json:"limit"` @@ -17,12 +17,13 @@ type ( } ) -func newProjectAPI(codefresh Codefresh) IProjectAPI { +func newProjectAPI(codefresh *codefresh) IProjectAPI { return &project{codefresh} } func (p *project) List() ([]*Project, error) { r := &getProjectResponse{} + resp, err := p.codefresh.requestAPI(&requestOptions{ path: "/api/projects", method: "GET", diff --git a/pkg/codefresh/project_test.go b/pkg/codefresh/project_test.go index a1b639d..9d60c6b 100644 --- a/pkg/codefresh/project_test.go +++ b/pkg/codefresh/project_test.go @@ -14,7 +14,7 @@ var clientOptions = ClientOptions{ Host: "https://g.codefresh.io", } -func TestProject(t *testing.T) { +func SampleTestProject(t *testing.T) { cf := New(&clientOptions) projects, err := cf.Projects().List() diff --git a/pkg/codefresh/runtime_enrionment.go b/pkg/codefresh/runtime_enrionment.go index 349397a..6e6e924 100644 --- a/pkg/codefresh/runtime_enrionment.go +++ b/pkg/codefresh/runtime_enrionment.go @@ -98,11 +98,11 @@ type ( } runtimeEnvironment struct { - codefresh Codefresh + codefresh *codefresh } ) -func newRuntimeEnvironmentAPI(codefresh Codefresh) IRuntimeEnvironmentAPI { +func newRuntimeEnvironmentAPI(codefresh *codefresh) IRuntimeEnvironmentAPI { return &runtimeEnvironment{codefresh} } diff --git a/pkg/codefresh/tokens.go b/pkg/codefresh/tokens.go index 0f3d601..3112a44 100644 --- a/pkg/codefresh/tokens.go +++ b/pkg/codefresh/tokens.go @@ -30,7 +30,7 @@ type ( } token struct { - codefresh Codefresh + codefresh *codefresh } ) @@ -38,7 +38,7 @@ const ( runtimeEnvironmentSubject tokenSubjectType = 0 ) -func newTokenAPI(codefresh Codefresh) ITokenAPI { +func newTokenAPI(codefresh *codefresh) ITokenAPI { return &token{codefresh} } diff --git a/pkg/codefresh/types.go b/pkg/codefresh/types.go index f9d89d8..157ad48 100644 --- a/pkg/codefresh/types.go +++ b/pkg/codefresh/types.go @@ -28,6 +28,6 @@ type ( path string method string body interface{} - qs map[string]string + qs interface{} } ) diff --git a/pkg/codefresh/users.go b/pkg/codefresh/users.go new file mode 100644 index 0000000..ca73af9 --- /dev/null +++ b/pkg/codefresh/users.go @@ -0,0 +1,65 @@ +package codefresh + +import ( + "context" + "fmt" +) + +type ( + UsersAPI interface { + GetCurrent(ctx context.Context) (*User, error) + } + + User struct { + ID string `json:"_id"` + Name string `json:"userName"` + Email string `json:"email"` + Accounts []Account `json:"account"` + ActiveAccountName string `json:"activeAccountName"` + Roles []string `json:"roles"` + UserData struct { + Avatar string `json:"image"` + } `json:"user_data"` + } + + Account struct { + Name string `json:"name"` + } + + users struct { + *codefresh + } +) + +func newUsersAPI(codefresh *codefresh) UsersAPI { + return &users{codefresh} +} + +func (u *users) GetCurrent(ctx context.Context) (*User, error) { + result := &User{} + resp, err := u.codefresh.requestAPIWithContext(ctx, &requestOptions{ + method: "GET", + path: "/api/user", + }) + if err != nil { + return nil, err + } + if resp.StatusCode >= 400 { + return nil, fmt.Errorf(resp.Status) + } + + if err := u.codefresh.decodeResponseInto(resp, &result); err != nil { + return nil, err + } + + return result, nil +} + +func (u *User) GetActiveAccount() *Account { + for i := 0; i < len(u.Accounts); i++ { + if u.Accounts[i].Name == u.ActiveAccountName { + return &u.Accounts[i] + } + } + return nil +} diff --git a/pkg/codefresh/workflow.go b/pkg/codefresh/workflow.go index 7c26c4d..56ea61a 100644 --- a/pkg/codefresh/workflow.go +++ b/pkg/codefresh/workflow.go @@ -13,7 +13,7 @@ type ( } workflow struct { - codefresh Codefresh + codefresh *codefresh } Workflow struct { @@ -27,7 +27,7 @@ type ( } ) -func newWorkflowAPI(codefresh Codefresh) IWorkflowAPI { +func newWorkflowAPI(codefresh *codefresh) IWorkflowAPI { return &workflow{codefresh} }