Skip to content

Commit

Permalink
Merge pull request #1356 from vasilzhigilei/vasil/add-per-hostname-tl…
Browse files Browse the repository at this point in the history
…s-settings

add per-hostname tls settings api and tests
  • Loading branch information
jacobbednarz authored Aug 10, 2023
2 parents dba5957 + fb3ee89 commit dc111b0
Show file tree
Hide file tree
Showing 3 changed files with 526 additions and 0 deletions.
3 changes: 3 additions & 0 deletions .changelog/1356.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
```release-note:enhancement
per_hostname_tls_settings: add support for managing hostname level TLS settings
```
250 changes: 250 additions & 0 deletions per_hostname_tls_settings.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,250 @@
package cloudflare

import (
"context"
"encoding/json"
"errors"
"fmt"
"net/http"
"time"
)

// HostnameTLSSetting represents the metadata for a user-created tls setting.
type HostnameTLSSetting struct {
Hostname string `json:"hostname"`
Value string `json:"value"`
Status string `json:"status"`
CreatedAt *time.Time `json:"created_at"`
UpdatedAt *time.Time `json:"updated_at"`
}

// HostnameTLSSettingResponse represents the response from the PUT and DELETE endpoints for per-hostname tls settings.
type HostnameTLSSettingResponse struct {
Response
Result HostnameTLSSetting `json:"result"`
}

// HostnameTLSSettingsResponse represents the response from the retrieval endpoint for per-hostname tls settings.
type HostnameTLSSettingsResponse struct {
Response
Result []HostnameTLSSetting `json:"result"`
ResultInfo `json:"result_info"`
}

// ListHostnameTLSSettingsParams represents the data related to per-hostname tls settings being retrieved.
type ListHostnameTLSSettingsParams struct {
Setting string
PaginationOptions
Limit int `url:"limit,omitempty"`
Offset int `url:"offset,omitempty"`
Hostname []string `url:"hostname,omitempty"`
}

// UpdateHostnameTLSSettingParams represents the data related to the per-hostname tls setting being updated.
type UpdateHostnameTLSSettingParams struct {
Setting string
Hostname string
Value string `json:"value"`
}

// DeleteHostnameTLSSettingParams represents the data related to the per-hostname tls setting being deleted.
type DeleteHostnameTLSSettingParams struct {
Setting string
Hostname string
}

var (
ErrMissingHostnameTLSSettingName = errors.New("tls setting name required but missing")
)

// ListHostnameTLSSettings returns a list of all user-created tls setting values for the specified setting and hostnames.
//
// API reference: https://developers.cloudflare.com/api/operations/per-hostname-tls-settings-list
func (api *API) ListHostnameTLSSettings(ctx context.Context, rc *ResourceContainer, params ListHostnameTLSSettingsParams) ([]HostnameTLSSetting, ResultInfo, error) {
if rc.Identifier == "" {
return []HostnameTLSSetting{}, ResultInfo{}, ErrMissingZoneID
}
if params.Setting == "" {
return []HostnameTLSSetting{}, ResultInfo{}, ErrMissingHostnameTLSSettingName
}

uri := fmt.Sprintf("/zones/%s/hostnames/settings/%s", rc.Identifier, params.Setting)
res, err := api.makeRequestContext(ctx, http.MethodGet, uri, params)
if err != nil {
return []HostnameTLSSetting{}, ResultInfo{}, err
}
var r HostnameTLSSettingsResponse
if err := json.Unmarshal(res, &r); err != nil {
return []HostnameTLSSetting{}, ResultInfo{}, fmt.Errorf("%s: %w", errUnmarshalError, err)
}
return r.Result, r.ResultInfo, err
}

// UpdateHostnameTLSSetting will update the per-hostname tls setting for the specified hostname.
//
// API reference: https://developers.cloudflare.com/api/operations/per-hostname-tls-settings-put
func (api *API) UpdateHostnameTLSSetting(ctx context.Context, rc *ResourceContainer, params UpdateHostnameTLSSettingParams) (HostnameTLSSetting, error) {
if rc.Identifier == "" {
return HostnameTLSSetting{}, ErrMissingZoneID
}
if params.Setting == "" {
return HostnameTLSSetting{}, ErrMissingHostnameTLSSettingName
}
if params.Hostname == "" {
return HostnameTLSSetting{}, ErrMissingHostname
}

uri := fmt.Sprintf("/zones/%s/hostnames/settings/%s/%s", rc.Identifier, params.Setting, params.Hostname)
res, err := api.makeRequestContext(ctx, http.MethodPut, uri, params)
if err != nil {
return HostnameTLSSetting{}, err
}
var r HostnameTLSSettingResponse
if err := json.Unmarshal(res, &r); err != nil {
return HostnameTLSSetting{}, fmt.Errorf("%s: %w", errUnmarshalError, err)
}
return r.Result, nil
}

// DeleteHostnameTLSSetting will delete the specified per-hostname tls setting.
//
// API reference: https://developers.cloudflare.com/api/operations/per-hostname-tls-settings-delete
func (api *API) DeleteHostnameTLSSetting(ctx context.Context, rc *ResourceContainer, params DeleteHostnameTLSSettingParams) (HostnameTLSSetting, error) {
if rc.Identifier == "" {
return HostnameTLSSetting{}, ErrMissingZoneID
}
if params.Setting == "" {
return HostnameTLSSetting{}, ErrMissingHostnameTLSSettingName
}
if params.Hostname == "" {
return HostnameTLSSetting{}, ErrMissingHostname
}

uri := fmt.Sprintf("/zones/%s/hostnames/settings/%s/%s", rc.Identifier, params.Setting, params.Hostname)
res, err := api.makeRequestContext(ctx, http.MethodDelete, uri, nil)
if err != nil {
return HostnameTLSSetting{}, err
}
var r HostnameTLSSettingResponse
if err := json.Unmarshal(res, &r); err != nil {
return HostnameTLSSetting{}, fmt.Errorf("%s: %w", errUnmarshalError, err)
}
return r.Result, nil
}

// HostnameTLSSettingCiphers represents the metadata for a user-created ciphers tls setting.
type HostnameTLSSettingCiphers struct {
Hostname string `json:"hostname"`
Value []string `json:"value"`
Status string `json:"status"`
CreatedAt *time.Time `json:"created_at"`
UpdatedAt *time.Time `json:"updated_at"`
}

// HostnameTLSSettingCiphersResponse represents the response from the PUT and DELETE endpoints for per-hostname ciphers tls settings.
type HostnameTLSSettingCiphersResponse struct {
Response
Result HostnameTLSSettingCiphers `json:"result"`
}

// HostnameTLSSettingsCiphersResponse represents the response from the retrieval endpoint for per-hostname ciphers tls settings.
type HostnameTLSSettingsCiphersResponse struct {
Response
Result []HostnameTLSSettingCiphers `json:"result"`
ResultInfo `json:"result_info"`
}

// ListHostnameTLSSettingsCiphersParams represents the data related to per-hostname ciphers tls settings being retrieved.
type ListHostnameTLSSettingsCiphersParams struct {
PaginationOptions
Limit int `url:"limit,omitempty"`
Offset int `url:"offset,omitempty"`
Hostname []string `url:"hostname,omitempty"`
}

// UpdateHostnameTLSSettingCiphersParams represents the data related to the per-hostname ciphers tls setting being updated.
type UpdateHostnameTLSSettingCiphersParams struct {
Hostname string
Value []string `json:"value"`
}

// DeleteHostnameTLSSettingCiphersParams represents the data related to the per-hostname ciphers tls setting being deleted.
type DeleteHostnameTLSSettingCiphersParams struct {
Hostname string
}

// ListHostnameTLSSettingsCiphers returns a list of all user-created tls setting ciphers values for the specified setting and hostnames.
// Ciphers functions are separate due to the API returning a list of strings as the value, rather than a string (as is the case for the other tls settings).
//
// API reference: https://developers.cloudflare.com/api/operations/per-hostname-tls-settings-list
func (api *API) ListHostnameTLSSettingsCiphers(ctx context.Context, rc *ResourceContainer, params ListHostnameTLSSettingsCiphersParams) ([]HostnameTLSSettingCiphers, ResultInfo, error) {
if rc.Identifier == "" {
return []HostnameTLSSettingCiphers{}, ResultInfo{}, ErrMissingZoneID
}

uri := fmt.Sprintf("/zones/%s/hostnames/settings/ciphers", rc.Identifier)
res, err := api.makeRequestContext(ctx, http.MethodGet, uri, params)
if err != nil {
return []HostnameTLSSettingCiphers{}, ResultInfo{}, err
}
var r HostnameTLSSettingsCiphersResponse
if err := json.Unmarshal(res, &r); err != nil {
return []HostnameTLSSettingCiphers{}, ResultInfo{}, fmt.Errorf("%s: %w", errUnmarshalError, err)
}
return r.Result, r.ResultInfo, err
}

// UpdateHostnameTLSSettingCiphers will update the per-hostname ciphers tls setting for the specified hostname.
// Ciphers functions are separate due to the API returning a list of strings as the value, rather than a string (as is the case for the other tls settings).
//
// API reference: https://developers.cloudflare.com/api/operations/per-hostname-tls-settings-put
func (api *API) UpdateHostnameTLSSettingCiphers(ctx context.Context, rc *ResourceContainer, params UpdateHostnameTLSSettingCiphersParams) (HostnameTLSSettingCiphers, error) {
if rc.Identifier == "" {
return HostnameTLSSettingCiphers{}, ErrMissingZoneID
}
if params.Hostname == "" {
return HostnameTLSSettingCiphers{}, ErrMissingHostname
}

uri := fmt.Sprintf("/zones/%s/hostnames/settings/ciphers/%s", rc.Identifier, params.Hostname)
res, err := api.makeRequestContext(ctx, http.MethodPut, uri, params)
if err != nil {
return HostnameTLSSettingCiphers{}, err
}
var r HostnameTLSSettingCiphersResponse
if err := json.Unmarshal(res, &r); err != nil {
return HostnameTLSSettingCiphers{}, fmt.Errorf("%s: %w", errUnmarshalError, err)
}
return r.Result, nil
}

// DeleteHostnameTLSSettingCiphers will delete the specified per-hostname ciphers tls setting value.
// Ciphers functions are separate due to the API returning a list of strings as the value, rather than a string (as is the case for the other tls settings).
//
// API reference: https://developers.cloudflare.com/api/operations/per-hostname-tls-settings-delete
func (api *API) DeleteHostnameTLSSettingCiphers(ctx context.Context, rc *ResourceContainer, params DeleteHostnameTLSSettingCiphersParams) (HostnameTLSSettingCiphers, error) {
if rc.Identifier == "" {
return HostnameTLSSettingCiphers{}, ErrMissingZoneID
}
if params.Hostname == "" {
return HostnameTLSSettingCiphers{}, ErrMissingHostname
}

uri := fmt.Sprintf("/zones/%s/hostnames/settings/ciphers/%s", rc.Identifier, params.Hostname)
res, err := api.makeRequestContext(ctx, http.MethodDelete, uri, nil)
if err != nil {
return HostnameTLSSettingCiphers{}, err
}
// Unmarshal into HostnameTLSSettingResponse first because the API returns an empty string
var r HostnameTLSSettingResponse
if err := json.Unmarshal(res, &r); err != nil {
return HostnameTLSSettingCiphers{}, fmt.Errorf("%s: %w", errUnmarshalError, err)
}
return HostnameTLSSettingCiphers{
Hostname: r.Result.Hostname,
Value: []string{},
Status: r.Result.Status,
CreatedAt: r.Result.CreatedAt,
UpdatedAt: r.Result.UpdatedAt,
}, nil
}
Loading

0 comments on commit dc111b0

Please sign in to comment.