github.com/google/go-github/v42@v42.0.0/github/repos_environments.go (about) 1 // Copyright 2021 The go-github AUTHORS. All rights reserved. 2 // 3 // Use of this source code is governed by a BSD-style 4 // license that can be found in the LICENSE file. 5 6 package github 7 8 import ( 9 "context" 10 "encoding/json" 11 "fmt" 12 ) 13 14 // Environment represents a single environment in a repository. 15 type Environment struct { 16 Owner *string `json:"owner,omitempty"` 17 Repo *string `json:"repo,omitempty"` 18 EnvironmentName *string `json:"environment_name,omitempty"` 19 WaitTimer *int `json:"wait_timer,omitempty"` 20 Reviewers []*EnvReviewers `json:"reviewers,omitempty"` 21 DeploymentBranchPolicy *BranchPolicy `json:"deployment_branch_policy,omitempty"` 22 // Return/response only values 23 ID *int64 `json:"id,omitempty"` 24 NodeID *string `json:"node_id,omitempty"` 25 Name *string `json:"name,omitempty"` 26 URL *string `json:"url,omitempty"` 27 HTMLURL *string `json:"html_url,omitempty"` 28 CreatedAt *Timestamp `json:"created_at,omitempty"` 29 UpdatedAt *Timestamp `json:"updated_at,omitempty"` 30 ProtectionRules []*ProtectionRule `json:"protection_rules,omitempty"` 31 } 32 33 // EnvReviewers represents a single environment reviewer entry. 34 type EnvReviewers struct { 35 Type *string `json:"type,omitempty"` 36 ID *int64 `json:"id,omitempty"` 37 } 38 39 // BranchPolicy represents the options for whether a branch deployment policy is applied to this environment. 40 type BranchPolicy struct { 41 ProtectedBranches *bool `json:"protected_branches,omitempty"` 42 CustomBranchPolicies *bool `json:"custom_branch_policies,omitempty"` 43 } 44 45 // EnvResponse represents the slightly different format of response that comes back when you list an environment. 46 type EnvResponse struct { 47 TotalCount *int `json:"total_count,omitempty"` 48 Environments []*Environment `json:"environments,omitempty"` 49 } 50 51 // ProtectionRule represents a single protection rule applied to the environment. 52 type ProtectionRule struct { 53 ID *int64 `json:"id,omitempty"` 54 NodeID *string `json:"node_id,omitempty"` 55 Type *string `json:"type,omitempty"` 56 WaitTimer *int `json:"wait_timer,omitempty"` 57 Reviewers []*RequiredReviewer `json:"reviewers,omitempty"` 58 } 59 60 // RequiredReviewer represents a required reviewer. 61 type RequiredReviewer struct { 62 Type *string `json:"type,omitempty"` 63 Reviewer interface{} `json:"reviewer,omitempty"` 64 } 65 66 // UnmarshalJSON implements the json.Unmarshaler interface. 67 // This helps us handle the fact that RequiredReviewer can have either a User or Team type reviewer field. 68 func (r *RequiredReviewer) UnmarshalJSON(data []byte) error { 69 type aliasReviewer RequiredReviewer 70 var reviewer aliasReviewer 71 if err := json.Unmarshal(data, &reviewer); err != nil { 72 return err 73 } 74 75 r.Type = reviewer.Type 76 77 switch *reviewer.Type { 78 case "User": 79 reviewer.Reviewer = &User{} 80 if err := json.Unmarshal(data, &reviewer); err != nil { 81 return err 82 } 83 r.Reviewer = reviewer.Reviewer 84 case "Team": 85 reviewer.Reviewer = &Team{} 86 if err := json.Unmarshal(data, &reviewer); err != nil { 87 return err 88 } 89 r.Reviewer = reviewer.Reviewer 90 default: 91 r.Type = nil 92 r.Reviewer = nil 93 return fmt.Errorf("reviewer.Type is %T, not a string of 'User' or 'Team', unable to unmarshal", reviewer.Type) 94 } 95 96 return nil 97 } 98 99 // ListEnvironments lists all environments for a repository. 100 // 101 // GitHub API docs: https://docs.github.com/en/rest/reference/repos#get-all-environments 102 func (s *RepositoriesService) ListEnvironments(ctx context.Context, owner, repo string) (*EnvResponse, *Response, error) { 103 u := fmt.Sprintf("repos/%s/%s/environments", owner, repo) 104 105 req, err := s.client.NewRequest("GET", u, nil) 106 if err != nil { 107 return nil, nil, err 108 } 109 110 var list *EnvResponse 111 resp, err := s.client.Do(ctx, req, &list) 112 if err != nil { 113 return nil, resp, err 114 } 115 return list, resp, nil 116 } 117 118 // GetEnvironment get a single environment for a repository. 119 // 120 // GitHub API docs: https://docs.github.com/en/rest/reference/repos#get-an-environment 121 func (s *RepositoriesService) GetEnvironment(ctx context.Context, owner, repo, name string) (*Environment, *Response, error) { 122 u := fmt.Sprintf("repos/%s/%s/environments/%s", owner, repo, name) 123 124 req, err := s.client.NewRequest("GET", u, nil) 125 if err != nil { 126 return nil, nil, err 127 } 128 129 var env *Environment 130 resp, err := s.client.Do(ctx, req, &env) 131 if err != nil { 132 return nil, resp, err 133 } 134 return env, resp, nil 135 } 136 137 // MarshalJSON implements the json.Marshaler interface. 138 // As the only way to clear a WaitTimer is to set it to 0, a missing WaitTimer object should default to 0, not null. 139 func (c *CreateUpdateEnvironment) MarshalJSON() ([]byte, error) { 140 type Alias CreateUpdateEnvironment 141 if c.WaitTimer == nil { 142 c.WaitTimer = Int(0) 143 } 144 return json.Marshal(&struct { 145 *Alias 146 }{ 147 Alias: (*Alias)(c), 148 }) 149 } 150 151 // CreateUpdateEnvironment represents the fields required for the create/update operation 152 // following the Create/Update release example. 153 // See https://github.com/google/go-github/issues/992 for more information. 154 // Removed omitempty here as the API expects null values for reviewers and deployment_branch_policy to clear them. 155 type CreateUpdateEnvironment struct { 156 WaitTimer *int `json:"wait_timer"` 157 Reviewers []*EnvReviewers `json:"reviewers"` 158 DeploymentBranchPolicy *BranchPolicy `json:"deployment_branch_policy"` 159 } 160 161 // CreateUpdateEnvironment create or update a new environment for a repository. 162 // 163 // GitHub API docs: https://docs.github.com/en/rest/reference/repos#create-or-update-an-environment 164 func (s *RepositoriesService) CreateUpdateEnvironment(ctx context.Context, owner, repo, name string, environment *CreateUpdateEnvironment) (*Environment, *Response, error) { 165 u := fmt.Sprintf("repos/%s/%s/environments/%s", owner, repo, name) 166 167 req, err := s.client.NewRequest("PUT", u, environment) 168 if err != nil { 169 return nil, nil, err 170 } 171 172 e := new(Environment) 173 resp, err := s.client.Do(ctx, req, e) 174 if err != nil { 175 return nil, resp, err 176 } 177 return e, resp, nil 178 } 179 180 // DeleteEnvironment delete an environment from a repository. 181 // 182 // GitHub API docs: https://docs.github.com/en/rest/reference/repos#delete-an-environment 183 func (s *RepositoriesService) DeleteEnvironment(ctx context.Context, owner, repo, name string) (*Response, error) { 184 u := fmt.Sprintf("repos/%s/%s/environments/%s", owner, repo, name) 185 186 req, err := s.client.NewRequest("DELETE", u, nil) 187 if err != nil { 188 return nil, err 189 } 190 return s.client.Do(ctx, req, nil) 191 }