// Code generated by Speakeasy (https://speakeasy.com). DO NOT EDIT.

package shared

import (
	"encoding/json"
	"errors"
	"fmt"
	"github.com/airbytehq/terraform-provider-airbyte/internal/sdk/internal/utils"
)

type SourceSnowflakeSchemasCredentialsAuthType string

const (
	SourceSnowflakeSchemasCredentialsAuthTypeUsernamePassword SourceSnowflakeSchemasCredentialsAuthType = "username/password"
)

func (e SourceSnowflakeSchemasCredentialsAuthType) ToPointer() *SourceSnowflakeSchemasCredentialsAuthType {
	return &e
}
func (e *SourceSnowflakeSchemasCredentialsAuthType) UnmarshalJSON(data []byte) error {
	var v string
	if err := json.Unmarshal(data, &v); err != nil {
		return err
	}
	switch v {
	case "username/password":
		*e = SourceSnowflakeSchemasCredentialsAuthType(v)
		return nil
	default:
		return fmt.Errorf("invalid value for SourceSnowflakeSchemasCredentialsAuthType: %v", v)
	}
}

type UsernameAndPassword struct {
	authType SourceSnowflakeSchemasCredentialsAuthType `const:"username/password" json:"auth_type"`
	// The password associated with the username.
	Password string `json:"password"`
	// The username you created to allow Airbyte to access the database.
	Username string `json:"username"`
}

func (u UsernameAndPassword) MarshalJSON() ([]byte, error) {
	return utils.MarshalJSON(u, "", false)
}

func (u *UsernameAndPassword) UnmarshalJSON(data []byte) error {
	if err := utils.UnmarshalJSON(data, &u, "", false, true); err != nil {
		return err
	}
	return nil
}

func (o *UsernameAndPassword) GetAuthType() SourceSnowflakeSchemasCredentialsAuthType {
	return SourceSnowflakeSchemasCredentialsAuthTypeUsernamePassword
}

func (o *UsernameAndPassword) GetPassword() string {
	if o == nil {
		return ""
	}
	return o.Password
}

func (o *UsernameAndPassword) GetUsername() string {
	if o == nil {
		return ""
	}
	return o.Username
}

type SourceSnowflakeSchemasAuthType string

const (
	SourceSnowflakeSchemasAuthTypeKeyPairAuthentication SourceSnowflakeSchemasAuthType = "Key Pair Authentication"
)

func (e SourceSnowflakeSchemasAuthType) ToPointer() *SourceSnowflakeSchemasAuthType {
	return &e
}
func (e *SourceSnowflakeSchemasAuthType) UnmarshalJSON(data []byte) error {
	var v string
	if err := json.Unmarshal(data, &v); err != nil {
		return err
	}
	switch v {
	case "Key Pair Authentication":
		*e = SourceSnowflakeSchemasAuthType(v)
		return nil
	default:
		return fmt.Errorf("invalid value for SourceSnowflakeSchemasAuthType: %v", v)
	}
}

type KeyPairAuthentication struct {
	authType *SourceSnowflakeSchemasAuthType `const:"Key Pair Authentication" json:"auth_type,omitempty"`
	// RSA Private key to use for Snowflake connection. See the <a href="https://docs.airbyte.com/integrations/sources/snowflake#key-pair-authentication">docs</a> for more information on how to obtain this key.
	PrivateKey string `json:"private_key"`
	// Passphrase for private key
	PrivateKeyPassword *string `json:"private_key_password,omitempty"`
	// The username you created to allow Airbyte to access the database.
	Username string `json:"username"`
}

func (k KeyPairAuthentication) MarshalJSON() ([]byte, error) {
	return utils.MarshalJSON(k, "", false)
}

func (k *KeyPairAuthentication) UnmarshalJSON(data []byte) error {
	if err := utils.UnmarshalJSON(data, &k, "", false, true); err != nil {
		return err
	}
	return nil
}

func (o *KeyPairAuthentication) GetAuthType() *SourceSnowflakeSchemasAuthType {
	return SourceSnowflakeSchemasAuthTypeKeyPairAuthentication.ToPointer()
}

func (o *KeyPairAuthentication) GetPrivateKey() string {
	if o == nil {
		return ""
	}
	return o.PrivateKey
}

func (o *KeyPairAuthentication) GetPrivateKeyPassword() *string {
	if o == nil {
		return nil
	}
	return o.PrivateKeyPassword
}

func (o *KeyPairAuthentication) GetUsername() string {
	if o == nil {
		return ""
	}
	return o.Username
}

type SourceSnowflakeAuthType string

const (
	SourceSnowflakeAuthTypeOAuth SourceSnowflakeAuthType = "OAuth"
)

func (e SourceSnowflakeAuthType) ToPointer() *SourceSnowflakeAuthType {
	return &e
}
func (e *SourceSnowflakeAuthType) UnmarshalJSON(data []byte) error {
	var v string
	if err := json.Unmarshal(data, &v); err != nil {
		return err
	}
	switch v {
	case "OAuth":
		*e = SourceSnowflakeAuthType(v)
		return nil
	default:
		return fmt.Errorf("invalid value for SourceSnowflakeAuthType: %v", v)
	}
}

type SourceSnowflakeOAuth20 struct {
	// Access Token for making authenticated requests.
	AccessToken *string                 `json:"access_token,omitempty"`
	authType    SourceSnowflakeAuthType `const:"OAuth" json:"auth_type"`
	// The Client ID of your Snowflake developer application.
	ClientID string `json:"client_id"`
	// The Client Secret of your Snowflake developer application.
	ClientSecret string `json:"client_secret"`
	// Refresh Token for making authenticated requests.
	RefreshToken *string `json:"refresh_token,omitempty"`
}

func (s SourceSnowflakeOAuth20) MarshalJSON() ([]byte, error) {
	return utils.MarshalJSON(s, "", false)
}

func (s *SourceSnowflakeOAuth20) UnmarshalJSON(data []byte) error {
	if err := utils.UnmarshalJSON(data, &s, "", false, true); err != nil {
		return err
	}
	return nil
}

func (o *SourceSnowflakeOAuth20) GetAccessToken() *string {
	if o == nil {
		return nil
	}
	return o.AccessToken
}

func (o *SourceSnowflakeOAuth20) GetAuthType() SourceSnowflakeAuthType {
	return SourceSnowflakeAuthTypeOAuth
}

func (o *SourceSnowflakeOAuth20) GetClientID() string {
	if o == nil {
		return ""
	}
	return o.ClientID
}

func (o *SourceSnowflakeOAuth20) GetClientSecret() string {
	if o == nil {
		return ""
	}
	return o.ClientSecret
}

func (o *SourceSnowflakeOAuth20) GetRefreshToken() *string {
	if o == nil {
		return nil
	}
	return o.RefreshToken
}

type SourceSnowflakeAuthorizationMethodType string

const (
	SourceSnowflakeAuthorizationMethodTypeSourceSnowflakeOAuth20 SourceSnowflakeAuthorizationMethodType = "source-snowflake_OAuth2.0"
	SourceSnowflakeAuthorizationMethodTypeKeyPairAuthentication  SourceSnowflakeAuthorizationMethodType = "Key Pair Authentication"
	SourceSnowflakeAuthorizationMethodTypeUsernameAndPassword    SourceSnowflakeAuthorizationMethodType = "Username and Password"
)

type SourceSnowflakeAuthorizationMethod struct {
	SourceSnowflakeOAuth20 *SourceSnowflakeOAuth20 `queryParam:"inline"`
	KeyPairAuthentication  *KeyPairAuthentication  `queryParam:"inline"`
	UsernameAndPassword    *UsernameAndPassword    `queryParam:"inline"`

	Type SourceSnowflakeAuthorizationMethodType
}

func CreateSourceSnowflakeAuthorizationMethodSourceSnowflakeOAuth20(sourceSnowflakeOAuth20 SourceSnowflakeOAuth20) SourceSnowflakeAuthorizationMethod {
	typ := SourceSnowflakeAuthorizationMethodTypeSourceSnowflakeOAuth20

	return SourceSnowflakeAuthorizationMethod{
		SourceSnowflakeOAuth20: &sourceSnowflakeOAuth20,
		Type:                   typ,
	}
}

func CreateSourceSnowflakeAuthorizationMethodKeyPairAuthentication(keyPairAuthentication KeyPairAuthentication) SourceSnowflakeAuthorizationMethod {
	typ := SourceSnowflakeAuthorizationMethodTypeKeyPairAuthentication

	return SourceSnowflakeAuthorizationMethod{
		KeyPairAuthentication: &keyPairAuthentication,
		Type:                  typ,
	}
}

func CreateSourceSnowflakeAuthorizationMethodUsernameAndPassword(usernameAndPassword UsernameAndPassword) SourceSnowflakeAuthorizationMethod {
	typ := SourceSnowflakeAuthorizationMethodTypeUsernameAndPassword

	return SourceSnowflakeAuthorizationMethod{
		UsernameAndPassword: &usernameAndPassword,
		Type:                typ,
	}
}

func (u *SourceSnowflakeAuthorizationMethod) UnmarshalJSON(data []byte) error {

	var usernameAndPassword UsernameAndPassword = UsernameAndPassword{}
	if err := utils.UnmarshalJSON(data, &usernameAndPassword, "", true, true); err == nil {
		u.UsernameAndPassword = &usernameAndPassword
		u.Type = SourceSnowflakeAuthorizationMethodTypeUsernameAndPassword
		return nil
	}

	var keyPairAuthentication KeyPairAuthentication = KeyPairAuthentication{}
	if err := utils.UnmarshalJSON(data, &keyPairAuthentication, "", true, true); err == nil {
		u.KeyPairAuthentication = &keyPairAuthentication
		u.Type = SourceSnowflakeAuthorizationMethodTypeKeyPairAuthentication
		return nil
	}

	var sourceSnowflakeOAuth20 SourceSnowflakeOAuth20 = SourceSnowflakeOAuth20{}
	if err := utils.UnmarshalJSON(data, &sourceSnowflakeOAuth20, "", true, true); err == nil {
		u.SourceSnowflakeOAuth20 = &sourceSnowflakeOAuth20
		u.Type = SourceSnowflakeAuthorizationMethodTypeSourceSnowflakeOAuth20
		return nil
	}

	return fmt.Errorf("could not unmarshal `%s` into any supported union types for SourceSnowflakeAuthorizationMethod", string(data))
}

func (u SourceSnowflakeAuthorizationMethod) MarshalJSON() ([]byte, error) {
	if u.SourceSnowflakeOAuth20 != nil {
		return utils.MarshalJSON(u.SourceSnowflakeOAuth20, "", true)
	}

	if u.KeyPairAuthentication != nil {
		return utils.MarshalJSON(u.KeyPairAuthentication, "", true)
	}

	if u.UsernameAndPassword != nil {
		return utils.MarshalJSON(u.UsernameAndPassword, "", true)
	}

	return nil, errors.New("could not marshal union type SourceSnowflakeAuthorizationMethod: all fields are null")
}

type Snowflake string

const (
	SnowflakeSnowflake Snowflake = "snowflake"
)

func (e Snowflake) ToPointer() *Snowflake {
	return &e
}
func (e *Snowflake) UnmarshalJSON(data []byte) error {
	var v string
	if err := json.Unmarshal(data, &v); err != nil {
		return err
	}
	switch v {
	case "snowflake":
		*e = Snowflake(v)
		return nil
	default:
		return fmt.Errorf("invalid value for Snowflake: %v", v)
	}
}

type SourceSnowflake struct {
	Credentials *SourceSnowflakeAuthorizationMethod `json:"credentials,omitempty"`
	// The database you created for Airbyte to access data.
	Database string `json:"database"`
	// The host domain of the snowflake instance (must include the account, region, cloud environment, and end with snowflakecomputing.com).
	Host string `json:"host"`
	// Additional properties to pass to the JDBC URL string when connecting to the database formatted as 'key=value' pairs separated by the symbol '&'. (example: key1=value1&key2=value2&key3=value3).
	JdbcURLParams *string `json:"jdbc_url_params,omitempty"`
	// The role you created for Airbyte to access Snowflake.
	Role string `json:"role"`
	// The source Snowflake schema tables. Leave empty to access tables from multiple schemas.
	Schema *string `json:"schema,omitempty"`
	// The warehouse you created for Airbyte to access data.
	Warehouse  string    `json:"warehouse"`
	sourceType Snowflake `const:"snowflake" json:"sourceType"`
}

func (s SourceSnowflake) MarshalJSON() ([]byte, error) {
	return utils.MarshalJSON(s, "", false)
}

func (s *SourceSnowflake) UnmarshalJSON(data []byte) error {
	if err := utils.UnmarshalJSON(data, &s, "", false, false); err != nil {
		return err
	}
	return nil
}

func (o *SourceSnowflake) GetCredentials() *SourceSnowflakeAuthorizationMethod {
	if o == nil {
		return nil
	}
	return o.Credentials
}

func (o *SourceSnowflake) GetDatabase() string {
	if o == nil {
		return ""
	}
	return o.Database
}

func (o *SourceSnowflake) GetHost() string {
	if o == nil {
		return ""
	}
	return o.Host
}

func (o *SourceSnowflake) GetJdbcURLParams() *string {
	if o == nil {
		return nil
	}
	return o.JdbcURLParams
}

func (o *SourceSnowflake) GetRole() string {
	if o == nil {
		return ""
	}
	return o.Role
}

func (o *SourceSnowflake) GetSchema() *string {
	if o == nil {
		return nil
	}
	return o.Schema
}

func (o *SourceSnowflake) GetWarehouse() string {
	if o == nil {
		return ""
	}
	return o.Warehouse
}

func (o *SourceSnowflake) GetSourceType() Snowflake {
	return SnowflakeSnowflake
}
