From 9e55102816e42ab299f0a4281d2d01e0f3cd69aa Mon Sep 17 00:00:00 2001 From: Maidul Islam Date: Sun, 15 Jan 2023 23:56:06 -0800 Subject: [PATCH] Switch to v2/secrets CURD api for cli --- cli/packages/api/api.go | 34 +++++++++----- cli/packages/api/model.go | 86 ++++++++++++++++++++---------------- cli/packages/cmd/root.go | 2 +- cli/packages/cmd/secrets.go | 12 ++--- cli/packages/util/secrets.go | 11 ++--- 5 files changed, 82 insertions(+), 63 deletions(-) diff --git a/cli/packages/api/api.go b/cli/packages/api/api.go index 782fa143c..a414b03d3 100644 --- a/cli/packages/api/api.go +++ b/cli/packages/api/api.go @@ -7,18 +7,21 @@ import ( "github.com/go-resty/resty/v2" ) +const USER_AGENT = "cli" + func CallBatchModifySecretsByWorkspaceAndEnv(httpClient *resty.Client, request BatchModifySecretsByWorkspaceAndEnvRequest) error { - endpoint := fmt.Sprintf("%v/v2/secret/batch-modify/workspace/%v/environment/%v", config.INFISICAL_URL, request.WorkspaceId, request.EnvironmentName) + endpoint := fmt.Sprintf("%v/v2/secrets", config.INFISICAL_URL) response, err := httpClient. R(). SetBody(request). + SetHeader("User-Agent", USER_AGENT). Patch(endpoint) if err != nil { return fmt.Errorf("CallBatchModifySecretsByWorkspaceAndEnv: Unable to complete api request [err=%s]", err) } - if response.StatusCode() > 299 { + if response.IsError() { return fmt.Errorf("CallBatchModifySecretsByWorkspaceAndEnv: Unsuccessful response: [response=%s]", response) } @@ -26,17 +29,18 @@ func CallBatchModifySecretsByWorkspaceAndEnv(httpClient *resty.Client, request B } func CallBatchCreateSecretsByWorkspaceAndEnv(httpClient *resty.Client, request BatchCreateSecretsByWorkspaceAndEnvRequest) error { - endpoint := fmt.Sprintf("%v/v2/secret/batch-create/workspace/%v/environment/%v", config.INFISICAL_URL, request.WorkspaceId, request.EnvironmentName) + endpoint := fmt.Sprintf("%v/v2/secrets/", config.INFISICAL_URL) response, err := httpClient. R(). SetBody(request). + SetHeader("User-Agent", USER_AGENT). Post(endpoint) if err != nil { return fmt.Errorf("CallBatchCreateSecretsByWorkspaceAndEnv: Unable to complete api request [err=%s]", err) } - if response.StatusCode() > 299 { + if response.IsError() { return fmt.Errorf("CallBatchCreateSecretsByWorkspaceAndEnv: Unsuccessful response: [response=%s]", response) } @@ -44,17 +48,18 @@ func CallBatchCreateSecretsByWorkspaceAndEnv(httpClient *resty.Client, request B } func CallBatchDeleteSecretsByWorkspaceAndEnv(httpClient *resty.Client, request BatchDeleteSecretsBySecretIdsRequest) error { - endpoint := fmt.Sprintf("%v/v2/secret/batch/workspace/%v/environment/%v", config.INFISICAL_URL, request.WorkspaceId, request.EnvironmentName) + endpoint := fmt.Sprintf("%v/v2/secrets", config.INFISICAL_URL) response, err := httpClient. R(). SetBody(request). + SetHeader("User-Agent", USER_AGENT). Delete(endpoint) if err != nil { return fmt.Errorf("CallBatchDeleteSecretsByWorkspaceAndEnv: Unable to complete api request [err=%s]", err) } - if response.StatusCode() > 299 { + if response.IsError() { return fmt.Errorf("CallBatchDeleteSecretsByWorkspaceAndEnv: Unsuccessful response: [response=%s]", response) } @@ -67,13 +72,14 @@ func CallGetEncryptedWorkspaceKey(httpClient *resty.Client, request GetEncrypted response, err := httpClient. R(). SetResult(&result). + SetHeader("User-Agent", USER_AGENT). Get(endpoint) if err != nil { return GetEncryptedWorkspaceKeyResponse{}, fmt.Errorf("CallGetEncryptedWorkspaceKey: Unable to complete api request [err=%s]", err) } - if response.StatusCode() > 299 { + if response.IsError() { return GetEncryptedWorkspaceKeyResponse{}, fmt.Errorf("CallGetEncryptedWorkspaceKey: Unsuccessful response: [response=%s]", response) } @@ -85,13 +91,14 @@ func CallGetServiceTokenDetailsV2(httpClient *resty.Client) (GetServiceTokenDeta response, err := httpClient. R(). SetResult(&tokenDetailsResponse). + SetHeader("User-Agent", USER_AGENT). Get(fmt.Sprintf("%v/v2/service-token", config.INFISICAL_URL)) if err != nil { return GetServiceTokenDetailsResponse{}, fmt.Errorf("CallGetServiceTokenDetails: Unable to complete api request [err=%s]", err) } - if response.StatusCode() > 299 { + if response.IsError() { return GetServiceTokenDetailsResponse{}, fmt.Errorf("CallGetServiceTokenDetails: Unsuccessful response: [response=%s]", response) } @@ -103,14 +110,16 @@ func CallGetSecretsV2(httpClient *resty.Client, request GetEncryptedSecretsV2Req response, err := httpClient. R(). SetResult(&secretsResponse). - SetQueryParam("environment", request.EnvironmentName). - Get(fmt.Sprintf("%v/v2/secret/workspace/%v", config.INFISICAL_URL, request.WorkspaceId)) + SetHeader("User-Agent", USER_AGENT). + SetQueryParam("environment", request.Environment). + SetQueryParam("workspaceId", request.WorkspaceId). + Get(fmt.Sprintf("%v/v2/secrets", config.INFISICAL_URL)) if err != nil { return GetEncryptedSecretsV2Response{}, fmt.Errorf("CallGetSecretsV2: Unable to complete api request [err=%s]", err) } - if response.StatusCode() > 299 { + if response.IsError() { return GetEncryptedSecretsV2Response{}, fmt.Errorf("CallGetSecretsV2: Unsuccessful response: [response=%s]", response) } @@ -122,13 +131,14 @@ func CallGetAllWorkSpacesUserBelongsTo(httpClient *resty.Client) (GetWorkSpacesR response, err := httpClient. R(). SetResult(&workSpacesResponse). + SetHeader("User-Agent", USER_AGENT). Get(fmt.Sprintf("%v/v1/workspace", config.INFISICAL_URL)) if err != nil { return GetWorkSpacesResponse{}, err } - if response.StatusCode() > 299 { + if response.IsError() { return GetWorkSpacesResponse{}, fmt.Errorf("CallGetAllWorkSpacesUserBelongsTo: Unsuccessful response: [response=%v]", response) } diff --git a/cli/packages/api/model.go b/cli/packages/api/model.go index b891a4af0..698d41408 100644 --- a/cli/packages/api/model.go +++ b/cli/packages/api/model.go @@ -142,19 +142,19 @@ type Secret struct { SecretCommentTag string `json:"secretCommentTag,omitempty"` SecretCommentHash string `json:"secretCommentHash,omitempty"` Type string `json:"type,omitempty"` - ID string `json:"_id,omitempty"` + ID string `json:"id,omitempty"` } type BatchCreateSecretsByWorkspaceAndEnvRequest struct { - EnvironmentName string `json:"environmentName"` - WorkspaceId string `json:"workspaceId"` - Secrets []Secret `json:"secrets"` + Environment string `json:"environment"` + WorkspaceId string `json:"workspaceId"` + Secrets []Secret `json:"secrets"` } type BatchModifySecretsByWorkspaceAndEnvRequest struct { - EnvironmentName string `json:"environmentName"` - WorkspaceId string `json:"workspaceId"` - Secrets []Secret `json:"secrets"` + Environment string `json:"environment"` + WorkspaceId string `json:"workspaceId"` + Secrets []Secret `json:"secrets"` } type BatchDeleteSecretsBySecretIdsRequest struct { @@ -195,41 +195,49 @@ type GetSecretsByWorkspaceIdAndEnvironmentRequest struct { } type GetEncryptedSecretsV2Request struct { - EnvironmentName string `json:"environmentName"` - WorkspaceId string `json:"workspaceId"` + Environment string `json:"environment"` + WorkspaceId string `json:"workspaceId"` } -type GetEncryptedSecretsV2Response []struct { - ID string `json:"_id"` - Version int `json:"version"` - Workspace string `json:"workspace"` - Type string `json:"type"` - Environment string `json:"environment"` - SecretKeyCiphertext string `json:"secretKeyCiphertext"` - SecretKeyIV string `json:"secretKeyIV"` - SecretKeyTag string `json:"secretKeyTag"` - SecretKeyHash string `json:"secretKeyHash"` - SecretValueCiphertext string `json:"secretValueCiphertext"` - SecretValueIV string `json:"secretValueIV"` - SecretValueTag string `json:"secretValueTag"` - SecretValueHash string `json:"secretValueHash"` - SecretCommentCiphertext string `json:"secretCommentCiphertext"` - SecretCommentIV string `json:"secretCommentIV"` - SecretCommentTag string `json:"secretCommentTag"` - SecretCommentHash string `json:"secretCommentHash"` - V int `json:"__v"` - CreatedAt time.Time `json:"createdAt"` - UpdatedAt time.Time `json:"updatedAt"` - User string `json:"user,omitempty"` +type GetEncryptedSecretsV2Response struct { + Secrets []struct { + ID string `json:"_id"` + Version int `json:"version"` + Workspace string `json:"workspace"` + Type string `json:"type"` + Environment string `json:"environment"` + SecretKeyCiphertext string `json:"secretKeyCiphertext"` + SecretKeyIV string `json:"secretKeyIV"` + SecretKeyTag string `json:"secretKeyTag"` + SecretValueCiphertext string `json:"secretValueCiphertext"` + SecretValueIV string `json:"secretValueIV"` + SecretValueTag string `json:"secretValueTag"` + V int `json:"__v"` + CreatedAt time.Time `json:"createdAt"` + UpdatedAt time.Time `json:"updatedAt"` + User string `json:"user,omitempty"` + } `json:"secrets"` } type GetServiceTokenDetailsResponse struct { - ID string `json:"_id"` - Name string `json:"name"` - Workspace string `json:"workspace"` - Environment string `json:"environment"` - User string `json:"user"` - EncryptedKey string `json:"encryptedKey"` - Iv string `json:"iv"` - Tag string `json:"tag"` + ID string `json:"_id"` + Name string `json:"name"` + Workspace string `json:"workspace"` + Environment string `json:"environment"` + User struct { + ID string `json:"_id"` + Email string `json:"email"` + CreatedAt time.Time `json:"createdAt"` + UpdatedAt time.Time `json:"updatedAt"` + V int `json:"__v"` + FirstName string `json:"firstName"` + LastName string `json:"lastName"` + } `json:"user"` + ExpiresAt time.Time `json:"expiresAt"` + EncryptedKey string `json:"encryptedKey"` + Iv string `json:"iv"` + Tag string `json:"tag"` + CreatedAt time.Time `json:"createdAt"` + UpdatedAt time.Time `json:"updatedAt"` + V int `json:"__v"` } diff --git a/cli/packages/cmd/root.go b/cli/packages/cmd/root.go index 708982a22..adbe265b9 100644 --- a/cli/packages/cmd/root.go +++ b/cli/packages/cmd/root.go @@ -30,7 +30,7 @@ func Execute() { func init() { rootCmd.Flags().BoolP("toggle", "t", false, "Help message for toggle") rootCmd.PersistentFlags().BoolVarP(&debugLogging, "debug", "d", false, "Enable verbose logging") - rootCmd.PersistentFlags().StringVar(&config.INFISICAL_URL, "domain", "https://app.infisical.com/api", "Point the CLI to your own backend") + rootCmd.PersistentFlags().StringVar(&config.INFISICAL_URL, "domain", "http://localhost:8080/api", "Point the CLI to your own backend") // rootCmd.PersistentPreRun = func(cmd *cobra.Command, args []string) { // } } diff --git a/cli/packages/cmd/secrets.go b/cli/packages/cmd/secrets.go index 5a9ce2724..912801f5d 100644 --- a/cli/packages/cmd/secrets.go +++ b/cli/packages/cmd/secrets.go @@ -205,9 +205,9 @@ var secretsSetCmd = &cobra.Command{ if len(secretsToCreate) > 0 { batchCreateRequest := api.BatchCreateSecretsByWorkspaceAndEnvRequest{ - WorkspaceId: workspaceFile.WorkspaceId, - EnvironmentName: environmentName, - Secrets: secretsToCreate, + WorkspaceId: workspaceFile.WorkspaceId, + Environment: environmentName, + Secrets: secretsToCreate, } err = api.CallBatchCreateSecretsByWorkspaceAndEnv(httpClient, batchCreateRequest) @@ -219,9 +219,9 @@ var secretsSetCmd = &cobra.Command{ if len(secretsToModify) > 0 { batchModifyRequest := api.BatchModifySecretsByWorkspaceAndEnvRequest{ - WorkspaceId: workspaceFile.WorkspaceId, - EnvironmentName: environmentName, - Secrets: secretsToModify, + WorkspaceId: workspaceFile.WorkspaceId, + Environment: environmentName, + Secrets: secretsToModify, } err = api.CallBatchModifySecretsByWorkspaceAndEnv(httpClient, batchModifyRequest) diff --git a/cli/packages/util/secrets.go b/cli/packages/util/secrets.go index 131a8e66d..aa431d7b5 100644 --- a/cli/packages/util/secrets.go +++ b/cli/packages/util/secrets.go @@ -24,6 +24,7 @@ func GetPlainTextSecretsViaServiceToken(fullServiceToken string) ([]models.Singl serviceToken := fmt.Sprintf("%v.%v.%v", serviceTokenParts[0], serviceTokenParts[1], serviceTokenParts[2]) httpClient := resty.New() + httpClient.SetAuthToken(serviceToken). SetHeader("Accept", "application/json") @@ -33,8 +34,8 @@ func GetPlainTextSecretsViaServiceToken(fullServiceToken string) ([]models.Singl } encryptedSecrets, err := api.CallGetSecretsV2(httpClient, api.GetEncryptedSecretsV2Request{ - WorkspaceId: serviceTokenDetails.Workspace, - EnvironmentName: serviceTokenDetails.Environment, + WorkspaceId: serviceTokenDetails.Workspace, + Environment: serviceTokenDetails.Environment, }) if err != nil { @@ -80,8 +81,8 @@ func GetPlainTextSecretsViaJTW(JTWToken string, receiversPrivateKey string, work plainTextWorkspaceKey := crypto.DecryptAsymmetric(encryptedWorkspaceKey, encryptedWorkspaceKeyNonce, encryptedWorkspaceKeySenderPublicKey, currentUsersPrivateKey) encryptedSecrets, err := api.CallGetSecretsV2(httpClient, api.GetEncryptedSecretsV2Request{ - WorkspaceId: workspaceId, - EnvironmentName: environmentName, + WorkspaceId: workspaceId, + Environment: environmentName, }) if err != nil { @@ -226,7 +227,7 @@ func OverrideWithPersonalSecrets(secrets []models.SingleEnvironmentVariable) []m func GetPlainTextSecrets(key []byte, encryptedSecrets api.GetEncryptedSecretsV2Response) ([]models.SingleEnvironmentVariable, error) { plainTextSecrets := []models.SingleEnvironmentVariable{} - for _, secret := range encryptedSecrets { + for _, secret := range encryptedSecrets.Secrets { // Decrypt key key_iv, err := base64.StdEncoding.DecodeString(secret.SecretKeyIV) if err != nil {