Files
Victor Farazdagi 61754a0eec feat(studio): add Snowflake replication destination (#46767)
## Details of change

Adds Snowflake to the Studio replication destination flow:
- destination selection and display
- create/edit form fields
- validate/create/update payload serialization
- generated Platform API types

Snowflake remains gated behind `etlEnableSnowflakePrivateAlpha`.

**Note:** I have configured `etlEnableSnowflakePrivateAlpha` in
ConfigCat ("all" in staging and tied to my own org id in prod).

## Details of Verification Process

- Studio focused Vitest coverage for form serialization and diagram
mapping
- Studio typecheck
- ESLint on changed Studio replication files
- Local `mise fullstack:dev` smoke test to confirm the Snowflake form
renders ok.

<img width="937" height="569" alt="image"
src="https://github.com/user-attachments/assets/8d6b3a87-1f9d-4a59-91da-be719714ea49"
/>


Full create/validate E2E depends on the Platform PR and ETL runtime
rollout.


## Review Requests

Please check the Snowflake wire payload matches the Platform/ETL
contract and that gating/edit/display behavior follows the existing ETL
destination patterns.

<!-- This is an auto-generated comment: release notes by coderabbit.ai
-->
## Summary by CodeRabbit

* **New Features**
* Snowflake added as a supported replication destination (private-alpha
gated), including UI for selecting and configuring connection and auth
(account, user, database, schema, role, private key, optional
passphrase).
* **Validation**
* Form validation and submission now handle Snowflake-specific
required/optional fields.
* **Tests**
* Unit tests added for Snowflake form behavior and replication-type
detection.
* **API**
* Destination create/update/validate flows extended to accept Snowflake
payloads.
<!-- end of auto-generated comment: release notes by coderabbit.ai -->
2026-06-11 10:25:57 +03:00

55 lines
1.9 KiB
TypeScript

import { useFlag } from 'common'
import { useSelectedOrganizationQuery } from '@/hooks/misc/useSelectedOrganization'
/**
* Organization level opt in for ETL private alpha, there's 2 flags we're using which controls
* the individual destination types. Access to the ETL UI (`useIsETLPrivateAlpha`) will just
* check if the org has access to at least one of the destination types
*/
const useIsCurrentOrgInFlagList = (flag: string) => {
const flagValue = useFlag(flag)
const { data: organization } = useSelectedOrganizationQuery()
const allowedOrgSlugs =
typeof flagValue === 'string'
? (flagValue as string).split(',').map((x: string) => x.trim())
: []
// [Joshen] Override for to enable for all organizations by setting the flag value as `all`
if (allowedOrgSlugs.includes('all')) return true
// [Joshen] Otherwise fallback to checking against org slug
return allowedOrgSlugs.includes(organization?.slug ?? '')
}
export const useIsETLBigQueryPrivateAlpha = () => {
return useIsCurrentOrgInFlagList('etlEnableBigQueryPrivateAlpha')
}
export const useIsETLIcebergPrivateAlpha = () => {
return useIsCurrentOrgInFlagList('etlEnableIcebergPrivateAlpha')
}
export const useIsETLDucklakePrivateAlpha = () => {
return useIsCurrentOrgInFlagList('etlEnableDucklakePrivateAlpha')
}
export const useIsETLSnowflakePrivateAlpha = () => {
return useIsCurrentOrgInFlagList('etlEnableSnowflakePrivateAlpha')
}
export const useIsETLPrivateAlpha = () => {
const hasAccessToETLBigQuery = useIsCurrentOrgInFlagList('etlEnableBigQueryPrivateAlpha')
const hasAccessToETLIceberg = useIsCurrentOrgInFlagList('etlEnableIcebergPrivateAlpha')
const hasAccessToETLDucklake = useIsCurrentOrgInFlagList('etlEnableDucklakePrivateAlpha')
const hasAccessToETLSnowflake = useIsCurrentOrgInFlagList('etlEnableSnowflakePrivateAlpha')
return (
hasAccessToETLBigQuery ||
hasAccessToETLIceberg ||
hasAccessToETLDucklake ||
hasAccessToETLSnowflake
)
}