github.com/akamai/AkamaiOPEN-edgegrid-golang/v8@v8.1.0/pkg/botman/challenge_action.go (about) 1 package botman 2 3 import ( 4 "context" 5 "encoding/json" 6 "fmt" 7 "net/http" 8 9 validation "github.com/go-ozzo/ozzo-validation/v4" 10 ) 11 12 type ( 13 // The ChallengeAction interface supports creating, retrieving, modifying and removing challenge action as well as 14 // updating google recaptcha secret key for challenge action for a configuration. 15 ChallengeAction interface { 16 // GetChallengeActionList https://techdocs.akamai.com/bot-manager/reference/get-challenge-actions 17 GetChallengeActionList(ctx context.Context, params GetChallengeActionListRequest) (*GetChallengeActionListResponse, error) 18 19 // GetChallengeAction https://techdocs.akamai.com/bot-manager/reference/get-challenge-action 20 GetChallengeAction(ctx context.Context, params GetChallengeActionRequest) (map[string]interface{}, error) 21 22 // CreateChallengeAction https://techdocs.akamai.com/bot-manager/reference/post-challenge-action 23 CreateChallengeAction(ctx context.Context, params CreateChallengeActionRequest) (map[string]interface{}, error) 24 25 // UpdateChallengeAction https://techdocs.akamai.com/bot-manager/reference/put-challenge-action 26 UpdateChallengeAction(ctx context.Context, params UpdateChallengeActionRequest) (map[string]interface{}, error) 27 28 // RemoveChallengeAction https://techdocs.akamai.com/bot-manager/reference/delete-challenge-action 29 RemoveChallengeAction(ctx context.Context, params RemoveChallengeActionRequest) error 30 31 // UpdateGoogleReCaptchaSecretKey https://techdocs.akamai.com/bot-manager/reference/put-google-recaptch-secret-key 32 UpdateGoogleReCaptchaSecretKey(ctx context.Context, params UpdateGoogleReCaptchaSecretKeyRequest) error 33 } 34 35 // GetChallengeActionListRequest is used to retrieve challenge actions for a configuration. 36 GetChallengeActionListRequest struct { 37 ConfigID int64 38 Version int64 39 ActionID string 40 } 41 42 // GetChallengeActionListResponse is used to retrieve challenge actions for a configuration. 43 GetChallengeActionListResponse struct { 44 ChallengeActions []map[string]interface{} `json:"challengeActions"` 45 } 46 47 // GetChallengeActionRequest is used to retrieve a specific challenge action 48 GetChallengeActionRequest struct { 49 ConfigID int64 50 Version int64 51 ActionID string 52 } 53 54 // CreateChallengeActionRequest is used to create a new challenge action for a specific configuration. 55 CreateChallengeActionRequest struct { 56 ConfigID int64 57 Version int64 58 JsonPayload json.RawMessage 59 } 60 61 // UpdateChallengeActionRequest is used to update an existing challenge action 62 UpdateChallengeActionRequest struct { 63 ConfigID int64 64 Version int64 65 ActionID string 66 JsonPayload json.RawMessage 67 } 68 69 // RemoveChallengeActionRequest is used to remove an existing challenge action 70 RemoveChallengeActionRequest struct { 71 ConfigID int64 72 Version int64 73 ActionID string 74 } 75 76 // UpdateGoogleReCaptchaSecretKeyRequest is used to update google reCaptcha secret key 77 UpdateGoogleReCaptchaSecretKeyRequest struct { 78 ConfigID int64 `json:"-"` 79 Version int64 `json:"-"` 80 ActionID string `json:"-"` 81 SecretKey string `json:"googleReCaptchaSecretKey"` 82 } 83 ) 84 85 // Validate validates a GetChallengeActionRequest. 86 func (v GetChallengeActionRequest) Validate() error { 87 return validation.Errors{ 88 "ConfigID": validation.Validate(v.ConfigID, validation.Required), 89 "Version": validation.Validate(v.Version, validation.Required), 90 "ActionID": validation.Validate(v.ActionID, validation.Required), 91 }.Filter() 92 } 93 94 // Validate validates a GetChallengeActionListRequest. 95 func (v GetChallengeActionListRequest) Validate() error { 96 return validation.Errors{ 97 "ConfigID": validation.Validate(v.ConfigID, validation.Required), 98 "Version": validation.Validate(v.Version, validation.Required), 99 }.Filter() 100 } 101 102 // Validate validates a CreateChallengeActionRequest. 103 func (v CreateChallengeActionRequest) Validate() error { 104 return validation.Errors{ 105 "ConfigID": validation.Validate(v.ConfigID, validation.Required), 106 "Version": validation.Validate(v.Version, validation.Required), 107 "JsonPayload": validation.Validate(v.JsonPayload, validation.Required), 108 }.Filter() 109 } 110 111 // Validate validates an UpdateChallengeActionRequest. 112 func (v UpdateChallengeActionRequest) Validate() error { 113 return validation.Errors{ 114 "ConfigID": validation.Validate(v.ConfigID, validation.Required), 115 "Version": validation.Validate(v.Version, validation.Required), 116 "ActionID": validation.Validate(v.ActionID, validation.Required), 117 "JsonPayload": validation.Validate(v.JsonPayload, validation.Required), 118 }.Filter() 119 } 120 121 // Validate validates a RemoveChallengeActionRequest. 122 func (v RemoveChallengeActionRequest) Validate() error { 123 return validation.Errors{ 124 "ConfigID": validation.Validate(v.ConfigID, validation.Required), 125 "Version": validation.Validate(v.Version, validation.Required), 126 "ActionID": validation.Validate(v.ActionID, validation.Required), 127 }.Filter() 128 } 129 130 // Validate validates a UpdateGoogleReCaptchaSecretKeyRequest. 131 func (v UpdateGoogleReCaptchaSecretKeyRequest) Validate() error { 132 return validation.Errors{ 133 "ConfigID": validation.Validate(v.ConfigID, validation.Required), 134 "Version": validation.Validate(v.Version, validation.Required), 135 "ActionID": validation.Validate(v.ActionID, validation.Required), 136 "SecretKey": validation.Validate(v.SecretKey, validation.Required), 137 }.Filter() 138 } 139 140 func (b *botman) GetChallengeAction(ctx context.Context, params GetChallengeActionRequest) (map[string]interface{}, error) { 141 logger := b.Log(ctx) 142 logger.Debug("GetChallengeAction") 143 144 if err := params.Validate(); err != nil { 145 return nil, fmt.Errorf("%w: %s", ErrStructValidation, err.Error()) 146 } 147 148 uri := fmt.Sprintf( 149 "/appsec/v1/configs/%d/versions/%d/response-actions/challenge-actions/%s", 150 params.ConfigID, 151 params.Version, 152 params.ActionID) 153 154 req, err := http.NewRequestWithContext(ctx, http.MethodGet, uri, nil) 155 if err != nil { 156 return nil, fmt.Errorf("failed to create GetChallengeAction request: %w", err) 157 } 158 159 var result map[string]interface{} 160 resp, err := b.Exec(req, &result) 161 if err != nil { 162 return nil, fmt.Errorf("GetChallengeAction request failed: %w", err) 163 } 164 165 if resp.StatusCode != http.StatusOK { 166 return nil, b.Error(resp) 167 } 168 169 return result, nil 170 } 171 172 func (b *botman) GetChallengeActionList(ctx context.Context, params GetChallengeActionListRequest) (*GetChallengeActionListResponse, error) { 173 logger := b.Log(ctx) 174 logger.Debug("GetChallengeActionList") 175 176 if err := params.Validate(); err != nil { 177 return nil, fmt.Errorf("%w: %s", ErrStructValidation, err.Error()) 178 } 179 180 uri := fmt.Sprintf( 181 "/appsec/v1/configs/%d/versions/%d/response-actions/challenge-actions", 182 params.ConfigID, 183 params.Version, 184 ) 185 186 req, err := http.NewRequestWithContext(ctx, http.MethodGet, uri, nil) 187 if err != nil { 188 return nil, fmt.Errorf("failed to create GetlustomDenyList request: %w", err) 189 } 190 191 var result GetChallengeActionListResponse 192 resp, err := b.Exec(req, &result) 193 if err != nil { 194 return nil, fmt.Errorf("GetChallengeActionList request failed: %w", err) 195 } 196 197 if resp.StatusCode != http.StatusOK { 198 return nil, b.Error(resp) 199 } 200 201 var filteredResult GetChallengeActionListResponse 202 if params.ActionID != "" { 203 for _, val := range result.ChallengeActions { 204 if val["actionId"].(string) == params.ActionID { 205 filteredResult.ChallengeActions = append(filteredResult.ChallengeActions, val) 206 } 207 } 208 } else { 209 filteredResult = result 210 } 211 return &filteredResult, nil 212 } 213 214 func (b *botman) UpdateChallengeAction(ctx context.Context, params UpdateChallengeActionRequest) (map[string]interface{}, error) { 215 logger := b.Log(ctx) 216 logger.Debug("UpdateChallengeAction") 217 218 if err := params.Validate(); err != nil { 219 return nil, fmt.Errorf("%w: %s", ErrStructValidation, err.Error()) 220 } 221 222 putURL := fmt.Sprintf( 223 "/appsec/v1/configs/%d/versions/%d/response-actions/challenge-actions/%s", 224 params.ConfigID, 225 params.Version, 226 params.ActionID, 227 ) 228 229 req, err := http.NewRequestWithContext(ctx, http.MethodPut, putURL, nil) 230 if err != nil { 231 return nil, fmt.Errorf("failed to create UpdateChallengeAction request: %w", err) 232 } 233 234 var result map[string]interface{} 235 resp, err := b.Exec(req, &result, params.JsonPayload) 236 if err != nil { 237 return nil, fmt.Errorf("UpdateChallengeAction request failed: %w", err) 238 } 239 240 if resp.StatusCode != http.StatusOK { 241 return nil, b.Error(resp) 242 } 243 244 return result, nil 245 } 246 247 func (b *botman) CreateChallengeAction(ctx context.Context, params CreateChallengeActionRequest) (map[string]interface{}, error) { 248 logger := b.Log(ctx) 249 logger.Debug("CreateChallengeAction") 250 251 if err := params.Validate(); err != nil { 252 return nil, fmt.Errorf("%w: %s", ErrStructValidation, err.Error()) 253 } 254 255 uri := fmt.Sprintf( 256 "/appsec/v1/configs/%d/versions/%d/response-actions/challenge-actions", 257 params.ConfigID, 258 params.Version, 259 ) 260 261 req, err := http.NewRequestWithContext(ctx, http.MethodPost, uri, nil) 262 if err != nil { 263 return nil, fmt.Errorf("failed to create CreateChallengeAction request: %w", err) 264 } 265 266 var result map[string]interface{} 267 resp, err := b.Exec(req, &result, params.JsonPayload) 268 if err != nil { 269 return nil, fmt.Errorf("CreateChallengeAction request failed: %w", err) 270 } 271 272 if resp.StatusCode != http.StatusCreated { 273 return nil, b.Error(resp) 274 } 275 276 return result, nil 277 } 278 279 func (b *botman) RemoveChallengeAction(ctx context.Context, params RemoveChallengeActionRequest) error { 280 logger := b.Log(ctx) 281 logger.Debug("RemoveChallengeAction") 282 283 if err := params.Validate(); err != nil { 284 return fmt.Errorf("%w: %s", ErrStructValidation, err.Error()) 285 } 286 287 uri := fmt.Sprintf("/appsec/v1/configs/%d/versions/%d/response-actions/challenge-actions/%s", 288 params.ConfigID, 289 params.Version, 290 params.ActionID) 291 292 req, err := http.NewRequestWithContext(ctx, http.MethodDelete, uri, nil) 293 if err != nil { 294 return fmt.Errorf("failed to create RemoveChallengeAction request: %w", err) 295 } 296 297 var result map[string]interface{} 298 resp, err := b.Exec(req, &result) 299 if err != nil { 300 return fmt.Errorf("RemoveChallengeAction request failed: %w", err) 301 } 302 303 if resp.StatusCode != http.StatusNoContent { 304 return b.Error(resp) 305 } 306 307 return nil 308 } 309 310 func (b *botman) UpdateGoogleReCaptchaSecretKey(ctx context.Context, params UpdateGoogleReCaptchaSecretKeyRequest) error { 311 logger := b.Log(ctx) 312 logger.Debug("UpdateGoogleReCaptchaSecretKey") 313 314 if err := params.Validate(); err != nil { 315 return fmt.Errorf("%w: %s", ErrStructValidation, err.Error()) 316 } 317 318 putURL := fmt.Sprintf( 319 "/appsec/v1/configs/%d/versions/%d/response-actions/challenge-actions/%s/google-recaptcha-secret-key", 320 params.ConfigID, 321 params.Version, 322 params.ActionID, 323 ) 324 325 req, err := http.NewRequestWithContext(ctx, http.MethodPut, putURL, nil) 326 if err != nil { 327 return fmt.Errorf("failed to create UpdateGoogleReCaptchaSecretKey request: %w", err) 328 } 329 330 var result map[string]interface{} 331 resp, err := b.Exec(req, &result, params) 332 if err != nil { 333 return fmt.Errorf("UpdateGoogleReCaptchaSecretKey request failed: %w", err) 334 } 335 336 if resp.StatusCode != http.StatusNoContent { 337 return b.Error(resp) 338 } 339 340 return nil 341 }