From 32c1a10a07b10f13ca68be73a72ae643fb69ab51 Mon Sep 17 00:00:00 2001 From: Deeksha Sharma Date: Thu, 4 Jul 2024 10:00:54 +0530 Subject: [PATCH 1/9] remove hardcoded values for private and direct cos config endpoint. Use defaults values when no env variables are set --- ibm/conns/config.go | 27 ++++++++++++++++--- ibm/service/cos/data_source_ibm_cos_bucket.go | 16 +++++++---- ibm/service/cos/resource_ibm_cos_bucket.go | 17 ++++++++---- 3 files changed, 46 insertions(+), 14 deletions(-) diff --git a/ibm/conns/config.go b/ibm/conns/config.go index d79da32fb5b..3aa6e55a1c9 100644 --- a/ibm/conns/config.go +++ b/ibm/conns/config.go @@ -2015,13 +2015,31 @@ func (c *Config) ClientSession() (interface{}, error) { } // OBJECT STORAGE Service - cosconfigurl := "https://config.cloud-object-storage.cloud.ibm.com/v1" - if fileMap != nil && c.Visibility != "public-and-private" { - cosconfigurl = fileFallBack(fileMap, c.Visibility, "IBMCLOUD_COS_CONFIG_ENDPOINT", c.Region, cosconfigurl) + + // default urls + configUrls := map[string]string{ + "public": "https://config.cloud-object-storage.cloud.ibm.com/v1", + "private": "https://config.private.cloud-object-storage.cloud.ibm.com/v1", + "direct": "https://config.direct.cloud-object-storage.cloud.ibm.com/v1", + } + // set urls present in fileMap + if fileMap != nil && (c.Visibility != "public-and-private") { + for visibility, url := range configUrls { + configUrls[visibility] = fileFallBack(fileMap, c.Visibility, "IBMCLOUD_COS_CONFIG_ENDPOINT", c.Region, url) + } + } + // set urls to environment variable + for visibility, url := range configUrls { + configUrls[visibility] = EnvFallBack([]string{"IBMCLOUD_COS_CONFIG_ENDPOINT"}, url) + } + + cosConfigURLsJson, err := json.Marshal(configUrls) + if err != nil { + return nil, err } cosconfigoptions := &cosconfig.ResourceConfigurationV1Options{ Authenticator: authenticator, - URL: EnvFallBack([]string{"IBMCLOUD_COS_CONFIG_ENDPOINT"}, cosconfigurl), + URL: string(cosConfigURLsJson), } cosconfigclient, err := cosconfig.NewResourceConfigurationV1(cosconfigoptions) if err != nil { @@ -3479,6 +3497,7 @@ func newSession(c *Config) (*Session, error) { if err != nil { return nil, err } + ibmSession.BluemixSession = sess } diff --git a/ibm/service/cos/data_source_ibm_cos_bucket.go b/ibm/service/cos/data_source_ibm_cos_bucket.go index 83f519a3940..34e3662c5eb 100644 --- a/ibm/service/cos/data_source_ibm_cos_bucket.go +++ b/ibm/service/cos/data_source_ibm_cos_bucket.go @@ -4,6 +4,7 @@ package cos import ( + "encoding/json" "fmt" "strings" "time" @@ -62,7 +63,7 @@ func DataSourceIBMCosBucket() *schema.Resource { Optional: true, // ValidateFunc: validate.ValidateAllowedStringValues([]string{"public", "private", "direct"}), ValidateFunc: validate.InvokeDataSourceValidator("ibm_cos_bucket", "endpoint_type"), - Description: "public or private", + Description: "COS endpoint type: public, private, direct", ConflictsWith: []string{"satellite_location_id"}, Default: "public", }, @@ -711,12 +712,17 @@ func dataSourceIBMCosBucketRead(d *schema.ResourceData, meta interface{}) error if err != nil { return err } - if endpointType == "private" { - sess.SetServiceURL("https://config.private.cloud-object-storage.cloud.ibm.com/v1") + cosConfigURLsJson := sess.GetServiceURL() + cosConfigURLs := new(map[string]string) + if err := json.Unmarshal([]byte(cosConfigURLsJson), cosConfigURLs); err != nil { + return err } - if endpointType == "direct" { - sess.SetServiceURL("https://config.direct.cloud-object-storage.cloud.ibm.com/v1") + + cosConfigURL, exists := (*cosConfigURLs)[endpointType] + if !exists { + return fmt.Errorf("failed to get %s cos config endpoint for COS bucket: %s endpoint not set", endpointType, endpointType) } + sess.SetServiceURL(cosConfigURL) if bucketType == "sl" { satconfig := fmt.Sprintf("https://config.%s.%s.cloud-object-storage.appdomain.cloud/v1", serviceID, satlc_id) diff --git a/ibm/service/cos/resource_ibm_cos_bucket.go b/ibm/service/cos/resource_ibm_cos_bucket.go index 299dfb77ad8..146502cd601 100644 --- a/ibm/service/cos/resource_ibm_cos_bucket.go +++ b/ibm/service/cos/resource_ibm_cos_bucket.go @@ -5,6 +5,7 @@ package cos import ( "context" + "encoding/json" "fmt" "log" "regexp" @@ -152,7 +153,7 @@ func ResourceIBMCOSBucket() *schema.Resource { "endpoint_type": { Type: schema.TypeString, Optional: true, - Description: "public or private", + Description: "COS endpoint type: public, private, direct", ConflictsWith: []string{"satellite_location_id"}, DiffSuppressFunc: flex.ApplyOnce, Default: "public", @@ -923,12 +924,18 @@ func resourceIBMCOSBucketUpdate(d *schema.ResourceData, meta interface{}) error if err != nil { return err } - if endpointType == "private" { - sess.SetServiceURL("https://config.private.cloud-object-storage.cloud.ibm.com/v1") + + cosConfigURLsJson := sess.GetServiceURL() + cosConfigURLs := new(map[string]string) + if err := json.Unmarshal([]byte(cosConfigURLsJson), cosConfigURLs); err != nil { + return err } - if endpointType == "direct" { - sess.SetServiceURL("https://config.direct.cloud-object-storage.cloud.ibm.com/v1") + + cosConfigURL, exists := (*cosConfigURLs)[endpointType] + if !exists { + return fmt.Errorf("failed to get %s cos config endpoint for COS bucket: %s endpoint not set", endpointType, endpointType) } + sess.SetServiceURL(cosConfigURL) if apiType == "sl" { satconfig := fmt.Sprintf("https://config.%s.%s.cloud-object-storage.appdomain.cloud/v1", serviceID, bLocation) From 8a7a56e92dea7ae73b91feda01f1728d6da0ca90 Mon Sep 17 00:00:00 2001 From: Deeksha Sharma Date: Thu, 4 Jul 2024 10:07:30 +0530 Subject: [PATCH 2/9] update code --- ibm/service/cos/resource_ibm_cos_bucket.go | 13 +++++++++---- 1 file changed, 9 insertions(+), 4 deletions(-) diff --git a/ibm/service/cos/resource_ibm_cos_bucket.go b/ibm/service/cos/resource_ibm_cos_bucket.go index 146502cd601..793adadb9b9 100644 --- a/ibm/service/cos/resource_ibm_cos_bucket.go +++ b/ibm/service/cos/resource_ibm_cos_bucket.go @@ -1165,12 +1165,17 @@ func resourceIBMCOSBucketRead(d *schema.ResourceData, meta interface{}) error { if err != nil { return err } - if endpointType == "private" { - sess.SetServiceURL("https://config.private.cloud-object-storage.cloud.ibm.com/v1") + cosConfigURLsJson := sess.GetServiceURL() + cosConfigURLs := new(map[string]string) + if err := json.Unmarshal([]byte(cosConfigURLsJson), cosConfigURLs); err != nil { + return err } - if endpointType == "direct" { - sess.SetServiceURL("https://config.direct.cloud-object-storage.cloud.ibm.com/v1") + + cosConfigURL, exists := (*cosConfigURLs)[endpointType] + if !exists { + return fmt.Errorf("failed to get %s cos config endpoint for COS bucket: %s endpoint not set", endpointType, endpointType) } + sess.SetServiceURL(cosConfigURL) if apiType == "sl" { From 56e9d753247621366d569cdbbea56dcf7113ea9d Mon Sep 17 00:00:00 2001 From: Deeksha Sharma Date: Thu, 4 Jul 2024 16:38:38 +0530 Subject: [PATCH 3/9] update code --- ibm/conns/config.go | 26 +++------------- ibm/service/cos/data_source_ibm_cos_bucket.go | 21 +++++++------ ibm/service/cos/resource_ibm_cos_bucket.go | 31 +++++++------------ 3 files changed, 27 insertions(+), 51 deletions(-) diff --git a/ibm/conns/config.go b/ibm/conns/config.go index 3aa6e55a1c9..6e1564acced 100644 --- a/ibm/conns/config.go +++ b/ibm/conns/config.go @@ -2015,31 +2015,13 @@ func (c *Config) ClientSession() (interface{}, error) { } // OBJECT STORAGE Service - - // default urls - configUrls := map[string]string{ - "public": "https://config.cloud-object-storage.cloud.ibm.com/v1", - "private": "https://config.private.cloud-object-storage.cloud.ibm.com/v1", - "direct": "https://config.direct.cloud-object-storage.cloud.ibm.com/v1", - } - // set urls present in fileMap - if fileMap != nil && (c.Visibility != "public-and-private") { - for visibility, url := range configUrls { - configUrls[visibility] = fileFallBack(fileMap, c.Visibility, "IBMCLOUD_COS_CONFIG_ENDPOINT", c.Region, url) - } - } - // set urls to environment variable - for visibility, url := range configUrls { - configUrls[visibility] = EnvFallBack([]string{"IBMCLOUD_COS_CONFIG_ENDPOINT"}, url) - } - - cosConfigURLsJson, err := json.Marshal(configUrls) - if err != nil { - return nil, err + cosconfigurl := "https://config.cloud-object-storage.cloud.ibm.com/v1" + if fileMap != nil && c.Visibility != "public-and-private" { + cosconfigurl = fileFallBack(fileMap, c.Visibility, "IBMCLOUD_COS_CONFIG_ENDPOINT", c.Region, cosconfigurl) } cosconfigoptions := &cosconfig.ResourceConfigurationV1Options{ Authenticator: authenticator, - URL: string(cosConfigURLsJson), + URL: EnvFallBack([]string{"IBMCLOUD_COS_CONFIG_ENDPOINT"}, cosconfigurl), } cosconfigclient, err := cosconfig.NewResourceConfigurationV1(cosconfigoptions) if err != nil { diff --git a/ibm/service/cos/data_source_ibm_cos_bucket.go b/ibm/service/cos/data_source_ibm_cos_bucket.go index 34e3662c5eb..803c424c945 100644 --- a/ibm/service/cos/data_source_ibm_cos_bucket.go +++ b/ibm/service/cos/data_source_ibm_cos_bucket.go @@ -4,7 +4,6 @@ package cos import ( - "encoding/json" "fmt" "strings" "time" @@ -24,6 +23,11 @@ import ( var bucketTypes = []string{"single_site_location", "region_location", "cross_region_location"} +var cosConfigUrls = map[string]string{ + "private": "https://config.private.cloud-object-storage.cloud.ibm.com/v1", + "direct": "https://config.direct.cloud-object-storage.cloud.ibm.com/v1", +} + func DataSourceIBMCosBucket() *schema.Resource { return &schema.Resource{ Read: dataSourceIBMCosBucketRead, @@ -712,17 +716,14 @@ func dataSourceIBMCosBucketRead(d *schema.ResourceData, meta interface{}) error if err != nil { return err } - cosConfigURLsJson := sess.GetServiceURL() - cosConfigURLs := new(map[string]string) - if err := json.Unmarshal([]byte(cosConfigURLsJson), cosConfigURLs); err != nil { - return err - } + if endpointType != "public" { + // uses default url in case url is not defined for the corresponding visibility + // cosConfigURL := conns.FileFallBack(rsConClient.Config.EndpointsFile, endpointType, "IBMCLOUD_COS_CONFIG_ENDPOINT", bucketRegion, cosConfigUrls[endpointType]) - cosConfigURL, exists := (*cosConfigURLs)[endpointType] - if !exists { - return fmt.Errorf("failed to get %s cos config endpoint for COS bucket: %s endpoint not set", endpointType, endpointType) + // uses default url when IBMCLOUD_COS_CONFIG_ENDPOINT is not set. + cosConfigURL := conns.EnvFallBack([]string{"IBMCLOUD_COS_CONFIG_ENDPOINT"}, cosConfigUrls[endpointType]) + sess.SetServiceURL(cosConfigURL) } - sess.SetServiceURL(cosConfigURL) if bucketType == "sl" { satconfig := fmt.Sprintf("https://config.%s.%s.cloud-object-storage.appdomain.cloud/v1", serviceID, satlc_id) diff --git a/ibm/service/cos/resource_ibm_cos_bucket.go b/ibm/service/cos/resource_ibm_cos_bucket.go index 793adadb9b9..0cc6c5f3f26 100644 --- a/ibm/service/cos/resource_ibm_cos_bucket.go +++ b/ibm/service/cos/resource_ibm_cos_bucket.go @@ -5,7 +5,6 @@ package cos import ( "context" - "encoding/json" "fmt" "log" "regexp" @@ -925,17 +924,14 @@ func resourceIBMCOSBucketUpdate(d *schema.ResourceData, meta interface{}) error return err } - cosConfigURLsJson := sess.GetServiceURL() - cosConfigURLs := new(map[string]string) - if err := json.Unmarshal([]byte(cosConfigURLsJson), cosConfigURLs); err != nil { - return err - } + if endpointType != "public" { + // uses default url in case url is not defined for the corresponding visibility + // cosConfigURL := conns.FileFallBack(rsConClient.Config.EndpointsFile, endpointType, "IBMCLOUD_COS_CONFIG_ENDPOINT", bucketRegion, cosConfigUrls[endpointType]) - cosConfigURL, exists := (*cosConfigURLs)[endpointType] - if !exists { - return fmt.Errorf("failed to get %s cos config endpoint for COS bucket: %s endpoint not set", endpointType, endpointType) + // uses default url when IBMCLOUD_COS_CONFIG_ENDPOINT is not set. + cosConfigURL := conns.EnvFallBack([]string{"IBMCLOUD_COS_CONFIG_ENDPOINT"}, cosConfigUrls[endpointType]) + sess.SetServiceURL(cosConfigURL) } - sess.SetServiceURL(cosConfigURL) if apiType == "sl" { satconfig := fmt.Sprintf("https://config.%s.%s.cloud-object-storage.appdomain.cloud/v1", serviceID, bLocation) @@ -1165,17 +1161,14 @@ func resourceIBMCOSBucketRead(d *schema.ResourceData, meta interface{}) error { if err != nil { return err } - cosConfigURLsJson := sess.GetServiceURL() - cosConfigURLs := new(map[string]string) - if err := json.Unmarshal([]byte(cosConfigURLsJson), cosConfigURLs); err != nil { - return err - } + if endpointType != "public" { + // uses default url in case url is not defined for the corresponding visibility + // cosConfigURL := conns.FileFallBack(rsConClient.Config.EndpointsFile, endpointType, "IBMCLOUD_COS_CONFIG_ENDPOINT", bucketRegion, cosConfigUrls[endpointType]) - cosConfigURL, exists := (*cosConfigURLs)[endpointType] - if !exists { - return fmt.Errorf("failed to get %s cos config endpoint for COS bucket: %s endpoint not set", endpointType, endpointType) + // uses default url when IBMCLOUD_COS_CONFIG_ENDPOINT is not set. + cosConfigURL := conns.EnvFallBack([]string{"IBMCLOUD_COS_CONFIG_ENDPOINT"}, cosConfigUrls[endpointType]) + sess.SetServiceURL(cosConfigURL) } - sess.SetServiceURL(cosConfigURL) if apiType == "sl" { From 4baac1d2c9d8eee47fcee0719ffbb95731b5b5fb Mon Sep 17 00:00:00 2001 From: Deeksha Sharma Date: Thu, 4 Jul 2024 16:45:11 +0530 Subject: [PATCH 4/9] remove extra space --- ibm/conns/config.go | 1 - 1 file changed, 1 deletion(-) diff --git a/ibm/conns/config.go b/ibm/conns/config.go index 6e1564acced..d79da32fb5b 100644 --- a/ibm/conns/config.go +++ b/ibm/conns/config.go @@ -3479,7 +3479,6 @@ func newSession(c *Config) (*Session, error) { if err != nil { return nil, err } - ibmSession.BluemixSession = sess } From e3b6809808488c2635c82a7353993fbf923fcf9d Mon Sep 17 00:00:00 2001 From: Deeksha Sharma Date: Mon, 8 Jul 2024 17:59:32 +0530 Subject: [PATCH 5/9] update code --- ibm/conns/config.go | 22 ++++++++++ ibm/service/cos/data_source_ibm_cos_bucket.go | 14 ++++--- ibm/service/cos/resource_ibm_cos_bucket.go | 41 +++++++++++-------- website/docs/d/cos_bucket.html.markdown | 2 + .../guides/custom-service-endpoints.html.md | 20 +++++++++ 5 files changed, 77 insertions(+), 22 deletions(-) diff --git a/ibm/conns/config.go b/ibm/conns/config.go index d79da32fb5b..9cc46efbdd5 100644 --- a/ibm/conns/config.go +++ b/ibm/conns/config.go @@ -8,6 +8,7 @@ import ( "encoding/json" "errors" "fmt" + "io" "io/ioutil" "log" "net" @@ -3567,6 +3568,27 @@ func EnvFallBack(envs []string, defaultValue string) string { return defaultValue } +func FileFallBack(endpointsFile, visibility, key, region, defaultValue string) string { + var fileMap map[string]interface{} + if f := EnvFallBack([]string{"IBMCLOUD_ENDPOINTS_FILE_PATH", "IC_ENDPOINTS_FILE_PATH"}, endpointsFile); f != "" { + jsonFile, err := os.Open(f) + if err != nil { + log.Fatalf("Unable to open Endpoints File %s", err) + } + defer jsonFile.Close() + bytes, err := io.ReadAll(jsonFile) + if err != nil { + log.Fatalf("Unable to read Endpoints File %s", err) + } + err = json.Unmarshal([]byte(bytes), &fileMap) + if err != nil { + log.Fatalf("Unable to unmarshal Endpoints File %s", err) + } + } + + return fileFallBack(fileMap, visibility, key, region, defaultValue) +} + func fileFallBack(fileMap map[string]interface{}, visibility, key, region, defaultValue string) string { if val, ok := fileMap[key]; ok { if v, ok := val.(map[string]interface{})[visibility]; ok { diff --git a/ibm/service/cos/data_source_ibm_cos_bucket.go b/ibm/service/cos/data_source_ibm_cos_bucket.go index 803c424c945..5a368faecd6 100644 --- a/ibm/service/cos/data_source_ibm_cos_bucket.go +++ b/ibm/service/cos/data_source_ibm_cos_bucket.go @@ -602,7 +602,7 @@ func dataSourceIBMCosBucketRead(d *schema.ResourceData, meta interface{}) error keyProtectFlag = true } - var satlc_id, apiEndpoint, apiEndpointPrivate, directApiEndpoint string + var satlc_id, apiEndpoint, apiEndpointPrivate, directApiEndpoint, visibility string if satlc, ok := d.GetOk("satellite_location_id"); ok { satlc_id = satlc.(string) @@ -617,15 +617,19 @@ func dataSourceIBMCosBucketRead(d *schema.ResourceData, meta interface{}) error } else { apiEndpoint, apiEndpointPrivate, directApiEndpoint = SelectCosApi(bucketLocationConvert(bucketType), bucketRegion) + visibility = endpointType if endpointType == "private" { apiEndpoint = apiEndpointPrivate } if endpointType == "direct" { + // visibility type "direct" is not supported in endpoints file. + visibility = "private" apiEndpoint = directApiEndpoint } } + apiEndpoint = conns.FileFallBack(rsConClient.Config.EndpointsFile, visibility, "IBMCLOUD_COS_ENDPOINT", bucketRegion, apiEndpoint) apiEndpoint = conns.EnvFallBack([]string{"IBMCLOUD_COS_ENDPOINT"}, apiEndpoint) if apiEndpoint == "" { return fmt.Errorf("[ERROR] The endpoint doesn't exists for given location %s and endpoint type %s", bucketRegion, endpointType) @@ -717,11 +721,9 @@ func dataSourceIBMCosBucketRead(d *schema.ResourceData, meta interface{}) error return err } if endpointType != "public" { - // uses default url in case url is not defined for the corresponding visibility - // cosConfigURL := conns.FileFallBack(rsConClient.Config.EndpointsFile, endpointType, "IBMCLOUD_COS_CONFIG_ENDPOINT", bucketRegion, cosConfigUrls[endpointType]) - - // uses default url when IBMCLOUD_COS_CONFIG_ENDPOINT is not set. - cosConfigURL := conns.EnvFallBack([]string{"IBMCLOUD_COS_CONFIG_ENDPOINT"}, cosConfigUrls[endpointType]) + // User is expected to define both private and direct url type under "private" in endpoints file since visibility type "direct" is not supported. + cosConfigURL := conns.FileFallBack(rsConClient.Config.EndpointsFile, "private", "IBMCLOUD_COS_CONFIG_ENDPOINT", bucketRegion, cosConfigUrls[endpointType]) + cosConfigURL = conns.EnvFallBack([]string{"IBMCLOUD_COS_CONFIG_ENDPOINT"}, cosConfigURL) sess.SetServiceURL(cosConfigURL) } diff --git a/ibm/service/cos/resource_ibm_cos_bucket.go b/ibm/service/cos/resource_ibm_cos_bucket.go index 0cc6c5f3f26..cf32331d4c4 100644 --- a/ibm/service/cos/resource_ibm_cos_bucket.go +++ b/ibm/service/cos/resource_ibm_cos_bucket.go @@ -746,21 +746,27 @@ func resourceIBMCOSBucketUpdate(d *schema.ResourceData, meta interface{}) error serviceID = bucketsatcrn } - var apiEndpoint, apiEndpointPrivate, directApiEndpoint string + var apiEndpoint, apiEndpointPrivate, directApiEndpoint, visibility string if apiType == "sl" { apiEndpoint = SelectSatlocCosApi(apiType, serviceID, bLocation) } else { apiEndpoint, apiEndpointPrivate, directApiEndpoint = SelectCosApi(apiType, bLocation) + visibility = endpointType if endpointType == "private" { apiEndpoint = apiEndpointPrivate } if endpointType == "direct" { + // visibility type "direct" is not supported in endpoints file. + visibility = "private" apiEndpoint = directApiEndpoint } } + apiEndpoint = conns.FileFallBack(rsConClient.Config.EndpointsFile, visibility, "IBMCLOUD_COS_ENDPOINT", bLocation, apiEndpoint) + apiEndpoint = conns.EnvFallBack([]string{"IBMCLOUD_COS_ENDPOINT"}, apiEndpoint) + authEndpoint, err := rsConClient.Config.EndpointLocator.IAMEndpoint() if err != nil { @@ -769,7 +775,7 @@ func resourceIBMCOSBucketUpdate(d *schema.ResourceData, meta interface{}) error authEndpointPath := fmt.Sprintf("%s%s", authEndpoint, "/identity/token") apiKey := rsConClient.Config.BluemixAPIKey if apiKey != "" { - s3Conf = aws.NewConfig().WithEndpoint(conns.EnvFallBack([]string{"IBMCLOUD_COS_ENDPOINT"}, apiEndpoint)).WithCredentials(ibmiam.NewStaticCredentials(aws.NewConfig(), authEndpointPath, apiKey, serviceID)).WithS3ForcePathStyle(true) + s3Conf = aws.NewConfig().WithEndpoint(apiEndpoint).WithCredentials(ibmiam.NewStaticCredentials(aws.NewConfig(), authEndpointPath, apiKey, serviceID)).WithS3ForcePathStyle(true) } iamAccessToken := rsConClient.Config.IAMAccessToken if iamAccessToken != "" { @@ -782,7 +788,7 @@ func resourceIBMCOSBucketUpdate(d *schema.ResourceData, meta interface{}) error Expiration: time.Now().Add(-1 * time.Hour).Unix(), }, nil } - s3Conf = aws.NewConfig().WithEndpoint(conns.EnvFallBack([]string{"IBMCLOUD_COS_ENDPOINT"}, apiEndpoint)).WithCredentials(ibmiam.NewCustomInitFuncCredentials(aws.NewConfig(), initFunc, authEndpointPath, serviceID)).WithS3ForcePathStyle(true) + s3Conf = aws.NewConfig().WithEndpoint(apiEndpoint).WithCredentials(ibmiam.NewCustomInitFuncCredentials(aws.NewConfig(), initFunc, authEndpointPath, serviceID)).WithS3ForcePathStyle(true) } s3Sess := session.Must(session.NewSession()) s3Client := s3.New(s3Sess, s3Conf) @@ -925,11 +931,9 @@ func resourceIBMCOSBucketUpdate(d *schema.ResourceData, meta interface{}) error } if endpointType != "public" { - // uses default url in case url is not defined for the corresponding visibility - // cosConfigURL := conns.FileFallBack(rsConClient.Config.EndpointsFile, endpointType, "IBMCLOUD_COS_CONFIG_ENDPOINT", bucketRegion, cosConfigUrls[endpointType]) - - // uses default url when IBMCLOUD_COS_CONFIG_ENDPOINT is not set. - cosConfigURL := conns.EnvFallBack([]string{"IBMCLOUD_COS_CONFIG_ENDPOINT"}, cosConfigUrls[endpointType]) + // User is expected to define both private and direct url type under "private" in endpoints file since visibility type "direct" is not supported. + cosConfigURL := conns.FileFallBack(rsConClient.Config.EndpointsFile, "private", "IBMCLOUD_COS_CONFIG_ENDPOINT", bLocation, cosConfigUrls[endpointType]) + cosConfigURL = conns.EnvFallBack([]string{"IBMCLOUD_COS_CONFIG_ENDPOINT"}, cosConfigURL) sess.SetServiceURL(cosConfigURL) } @@ -1162,11 +1166,9 @@ func resourceIBMCOSBucketRead(d *schema.ResourceData, meta interface{}) error { return err } if endpointType != "public" { - // uses default url in case url is not defined for the corresponding visibility - // cosConfigURL := conns.FileFallBack(rsConClient.Config.EndpointsFile, endpointType, "IBMCLOUD_COS_CONFIG_ENDPOINT", bucketRegion, cosConfigUrls[endpointType]) - - // uses default url when IBMCLOUD_COS_CONFIG_ENDPOINT is not set. - cosConfigURL := conns.EnvFallBack([]string{"IBMCLOUD_COS_CONFIG_ENDPOINT"}, cosConfigUrls[endpointType]) + // User is expected to define both private and direct url type under "private" in endpoints file since visibility type "direct" is not supported. + cosConfigURL := conns.FileFallBack(rsConClient.Config.EndpointsFile, "private", "IBMCLOUD_COS_CONFIG_ENDPOINT", bLocation, cosConfigUrls[endpointType]) + cosConfigURL = conns.EnvFallBack([]string{"IBMCLOUD_COS_CONFIG_ENDPOINT"}, cosConfigURL) sess.SetServiceURL(cosConfigURL) } @@ -1351,22 +1353,25 @@ func resourceIBMCOSBucketCreate(d *schema.ResourceData, meta interface{}) error var endpointType = d.Get("endpoint_type").(string) - var apiEndpoint, privateApiEndpoint, directApiEndpoint string + var apiEndpoint, privateApiEndpoint, directApiEndpoint, visibility string if apiType == "sl" { - apiEndpoint = SelectSatlocCosApi(apiType, serviceID, bLocation) } else { apiEndpoint, privateApiEndpoint, directApiEndpoint = SelectCosApi(apiType, bLocation) + visibility = endpointType if endpointType == "private" { apiEndpoint = privateApiEndpoint } if endpointType == "direct" { + // visibility type "direct" is not supported in endpoints file. + visibility = "private" apiEndpoint = directApiEndpoint } } + apiEndpoint = conns.FileFallBack(rsConClient.Config.EndpointsFile, visibility, "IBMCLOUD_COS_ENDPOINT", bLocation, apiEndpoint) apiEndpoint = conns.EnvFallBack([]string{"IBMCLOUD_COS_ENDPOINT"}, apiEndpoint) if apiEndpoint == "" { @@ -1467,7 +1472,7 @@ func resourceIBMCOSBucketDelete(d *schema.ResourceData, meta interface{}) error endpointType := parseBucketId(d.Id(), "endpointType") - var apiEndpoint, apiEndpointPrivate, directApiEndpoint string + var apiEndpoint, apiEndpointPrivate, directApiEndpoint, visibility string if apiType == "sl" { @@ -1475,15 +1480,19 @@ func resourceIBMCOSBucketDelete(d *schema.ResourceData, meta interface{}) error } else { apiEndpoint, apiEndpointPrivate, directApiEndpoint = SelectCosApi(apiType, bLocation) + visibility = endpointType if endpointType == "private" { apiEndpoint = apiEndpointPrivate } if endpointType == "direct" { + // visibility type "direct" is not supported in endpoints file. + visibility = "private" apiEndpoint = directApiEndpoint } } + apiEndpoint = conns.FileFallBack(rsConClient.Config.EndpointsFile, visibility, "IBMCLOUD_COS_ENDPOINT", bLocation, apiEndpoint) apiEndpoint = conns.EnvFallBack([]string{"IBMCLOUD_COS_ENDPOINT"}, apiEndpoint) if apiEndpoint == "" { diff --git a/website/docs/d/cos_bucket.html.markdown b/website/docs/d/cos_bucket.html.markdown index 73a9727d2fa..5b14083b880 100644 --- a/website/docs/d/cos_bucket.html.markdown +++ b/website/docs/d/cos_bucket.html.markdown @@ -232,3 +232,5 @@ In addition to all argument reference list, you can access the following attribu - `s3_endpoint_public` - (String) Public endpoint for cos bucket. - `s3_endpoint_private` - (String) Private endpoint for cos bucket. - `s3_endpoint_direct` - (String) Direct endpoint for cos bucket. +**Note:** +Since the current endpoints file schema does not support "direct" as visibility type, the user must define url for the same under exisiting visibility type "private" for "IBMCLOUD_COS_CONFIG_ENDPOINT" and "IBMCLOUD_COS_ENDPOINT". \ No newline at end of file diff --git a/website/docs/guides/custom-service-endpoints.html.md b/website/docs/guides/custom-service-endpoints.html.md index b03eedc00b4..a254c1740e6 100644 --- a/website/docs/guides/custom-service-endpoints.html.md +++ b/website/docs/guides/custom-service-endpoints.html.md @@ -134,6 +134,26 @@ To use public and private regional endpoints for a service, you must add these e } } ``` +**Note:** + +The endpoints file accepts "public", "private" and "public-and-private" as visibility while COS resources support "public", "private" and "direct as endpoint-types. +Since endpoints file does not accomodate type "direct", users must define the url for "direct" endpoint-type under exisiting visibility type "private" for "IBMCLOUD_COS_CONFIG_ENDPOINT" and "IBMCLOUD_COS_ENDPOINT". + +**Example**: + +```json +{ + "IBMCLOUD_COS_CONFIG_ENDPOINT":{ + "public":{ + "us-south":"https://config.cloud-object-storage.cloud.ibm.com/v1" + }, + "private":{ + "us-south":"https://config.direct.cloud-object-storage.cloud.ibm.com/v1" + } + } +} +``` + ## Prioritisation of endpoints From 8bb42f82170589544e746d295390182604a98127 Mon Sep 17 00:00:00 2001 From: Deeksha Sharma Date: Wed, 10 Jul 2024 11:35:32 +0530 Subject: [PATCH 6/9] update comment --- .../guides/custom-service-endpoints.html.md | 18 +++++++++++++++++- 1 file changed, 17 insertions(+), 1 deletion(-) diff --git a/website/docs/guides/custom-service-endpoints.html.md b/website/docs/guides/custom-service-endpoints.html.md index a254c1740e6..ae3dd6af785 100644 --- a/website/docs/guides/custom-service-endpoints.html.md +++ b/website/docs/guides/custom-service-endpoints.html.md @@ -137,7 +137,8 @@ To use public and private regional endpoints for a service, you must add these e **Note:** The endpoints file accepts "public", "private" and "public-and-private" as visibility while COS resources support "public", "private" and "direct as endpoint-types. -Since endpoints file does not accomodate type "direct", users must define the url for "direct" endpoint-type under exisiting visibility type "private" for "IBMCLOUD_COS_CONFIG_ENDPOINT" and "IBMCLOUD_COS_ENDPOINT". +Since endpoints file schema does not supprt "direct", users must define the url for "direct" endpoint-type under exisiting visibility type "private" for "IBMCLOUD_COS_CONFIG_ENDPOINT" and "IBMCLOUD_COS_ENDPOINT". +The user cannot define urls for both private and direct endpoint-type simultaneously in the endpoints file under "private" field. **Example**: @@ -154,6 +155,21 @@ Since endpoints file does not accomodate type "direct", users must define the ur } ``` +OR + +```json +{ + "IBMCLOUD_COS_CONFIG_ENDPOINT":{ + "public":{ + "us-south":"https://config.cloud-object-storage.cloud.ibm.com/v1" + }, + "private":{ + "us-south":"https://config.private.cloud-object-storage.cloud.ibm.com/v1" + } + } +} +``` + ## Prioritisation of endpoints From 80b8aff505b3ddf9e2522ece873562adbff397d1 Mon Sep 17 00:00:00 2001 From: Deeksha Sharma Date: Mon, 15 Jul 2024 10:49:27 +0530 Subject: [PATCH 7/9] udpate documentation --- website/docs/d/cos_bucket.html.markdown | 34 ++++++++++++++++++++++++- website/docs/r/cos_bucket.html.markdown | 34 +++++++++++++++++++++++++ 2 files changed, 67 insertions(+), 1 deletion(-) diff --git a/website/docs/d/cos_bucket.html.markdown b/website/docs/d/cos_bucket.html.markdown index 5b14083b880..7256b1a5ef0 100644 --- a/website/docs/d/cos_bucket.html.markdown +++ b/website/docs/d/cos_bucket.html.markdown @@ -233,4 +233,36 @@ In addition to all argument reference list, you can access the following attribu - `s3_endpoint_private` - (String) Private endpoint for cos bucket. - `s3_endpoint_direct` - (String) Direct endpoint for cos bucket. **Note:** -Since the current endpoints file schema does not support "direct" as visibility type, the user must define url for the same under exisiting visibility type "private" for "IBMCLOUD_COS_CONFIG_ENDPOINT" and "IBMCLOUD_COS_ENDPOINT". \ No newline at end of file + +Since the current endpoints file schema does not support "direct", the user must define direct url under "private" for "IBMCLOUD_COS_CONFIG_ENDPOINT" and "IBMCLOUD_COS_ENDPOINT". + + +**Example**: + +```json +{ + "IBMCLOUD_COS_CONFIG_ENDPOINT":{ + "public":{ + "us-south":"https://config.cloud-object-storage.cloud.ibm.com/v1" + }, + "private":{ + "us-south":"https://config.direct.cloud-object-storage.cloud.ibm.com/v1" + } + } +} +``` + +OR + +```json +{ + "IBMCLOUD_COS_CONFIG_ENDPOINT":{ + "public":{ + "us-south":"https://config.cloud-object-storage.cloud.ibm.com/v1" + }, + "private":{ + "us-south":"https://config.private.cloud-object-storage.cloud.ibm.com/v1" + } + } +} +``` \ No newline at end of file diff --git a/website/docs/r/cos_bucket.html.markdown b/website/docs/r/cos_bucket.html.markdown index 0b0d7cf0697..41700d444ad 100644 --- a/website/docs/r/cos_bucket.html.markdown +++ b/website/docs/r/cos_bucket.html.markdown @@ -597,4 +597,38 @@ id = `$CRN:meta:$buckettype:$bucketlocation` $ terraform import ibm_cos_bucket.cos_bucket crn:v1:staging:public:cloud-object-storage:satloc_dal_c8fctn320qtrspbisg80:a/81ee25188545f05150650a0a4ee015bb:a2deec95-0836-4720-bfc7-ca41c28a8c66:bucket:tf-listbuckettest:meta:sl:c8fctn320qtrspbisg80:public +``` + +**Note:** + +Since the current endpoints file schema does not support "direct", the user must define direct url under "private" for "IBMCLOUD_COS_CONFIG_ENDPOINT" and "IBMCLOUD_COS_ENDPOINT". + +**Example**: + +```json +{ + "IBMCLOUD_COS_CONFIG_ENDPOINT":{ + "public":{ + "us-south":"https://config.cloud-object-storage.cloud.ibm.com/v1" + }, + "private":{ + "us-south":"https://config.direct.cloud-object-storage.cloud.ibm.com/v1" + } + } +} +``` + +OR + +```json +{ + "IBMCLOUD_COS_CONFIG_ENDPOINT":{ + "public":{ + "us-south":"https://config.cloud-object-storage.cloud.ibm.com/v1" + }, + "private":{ + "us-south":"https://config.private.cloud-object-storage.cloud.ibm.com/v1" + } + } +} ``` \ No newline at end of file From 92299df563f2acec18fd27f04f2dd1db56c381d5 Mon Sep 17 00:00:00 2001 From: Deeksha Sharma Date: Wed, 17 Jul 2024 13:17:14 +0530 Subject: [PATCH 8/9] documentation update for issue #4819 --- examples/ibm-cos-bucket/README.md | 5 +++++ website/docs/r/cos_bucket.html.markdown | 4 ++++ 2 files changed, 9 insertions(+) diff --git a/examples/ibm-cos-bucket/README.md b/examples/ibm-cos-bucket/README.md index 6f4e5f63601..91d220a059d 100644 --- a/examples/ibm-cos-bucket/README.md +++ b/examples/ibm-cos-bucket/README.md @@ -22,6 +22,11 @@ Run `terraform destroy` when you don't need these resources. Create an IBM Cloud Object Storage bucket. The bucket is used to store your data: + **Note:** + +A bucket name can be reused as soon as 15 minutes after the contents of the bucket have been deleted and the bucket has been deleted. Then, the objects and bucket are irrevocably deleted and can not be restored. +For more information, please refer to [this link](https://cloud.ibm.com/docs/cloud-object-storage?topic=cloud-object-storage-faq-bucket#faq-reuse-name) + ```terraform data "ibm_resource_group" "cos_group" { diff --git a/website/docs/r/cos_bucket.html.markdown b/website/docs/r/cos_bucket.html.markdown index 4110d8e1163..51157ca623d 100644 --- a/website/docs/r/cos_bucket.html.markdown +++ b/website/docs/r/cos_bucket.html.markdown @@ -11,6 +11,10 @@ description: Create or delete an IBM Cloud Object Storage bucket. The bucket is used to store your data. For more information, about configuration options, see [Create some buckets to store your data](https://cloud.ibm.com/docs/cloud-object-storage?topic=cloud-object-storage-getting-started-cloud-object-storage#gs-create-buckets). To create a bucket, you must provision an IBM Cloud Object Storage instance first by using the [`ibm_resource_instance`](https://registry.terraform.io/providers/IBM-Cloud/ibm/latest/docs/resources/resource_instance) resource. + **Note:** + +A bucket name can be reused as soon as 15 minutes after the contents of the bucket have been deleted and the bucket has been deleted. Then, the objects and bucket are irrevocably deleted and can not be restored. +For more information, please refer to [this link](https://cloud.ibm.com/docs/cloud-object-storage?topic=cloud-object-storage-faq-bucket#faq-reuse-name) ## Example usage The following example creates an instance of IBM Cloud Object Storage, IBM Cloud Activity Tracker, and IBM Cloud Monitoring. Then, multiple buckets are created and configured to send audit events and metrics to your service instances. From 07c284bf4f85d1bd1c586784c74d2e062efb3754 Mon Sep 17 00:00:00 2001 From: Deeksha Sharma Date: Wed, 17 Jul 2024 13:23:08 +0530 Subject: [PATCH 9/9] update doc --- website/docs/r/cos_bucket.html.markdown | 2 ++ 1 file changed, 2 insertions(+) diff --git a/website/docs/r/cos_bucket.html.markdown b/website/docs/r/cos_bucket.html.markdown index 51157ca623d..812d8e93c89 100644 --- a/website/docs/r/cos_bucket.html.markdown +++ b/website/docs/r/cos_bucket.html.markdown @@ -11,6 +11,8 @@ description: Create or delete an IBM Cloud Object Storage bucket. The bucket is used to store your data. For more information, about configuration options, see [Create some buckets to store your data](https://cloud.ibm.com/docs/cloud-object-storage?topic=cloud-object-storage-getting-started-cloud-object-storage#gs-create-buckets). To create a bucket, you must provision an IBM Cloud Object Storage instance first by using the [`ibm_resource_instance`](https://registry.terraform.io/providers/IBM-Cloud/ibm/latest/docs/resources/resource_instance) resource. + + **Note:** A bucket name can be reused as soon as 15 minutes after the contents of the bucket have been deleted and the bucket has been deleted. Then, the objects and bucket are irrevocably deleted and can not be restored.