| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182 |
- package models
- import (
- "fmt"
- "gorm.io/gorm"
- "github.com/launchdarkly/go-sdk-common/v3/ldcontext"
- "github.com/porter-dev/porter/api/types"
- "github.com/porter-dev/porter/internal/features"
- ints "github.com/porter-dev/porter/internal/models/integrations"
- )
- // ProjectFeatureFlags keeps track of all project-related feature flags
- var ProjectFeatureFlags = map[string]bool{
- "api_tokens_enabled": false,
- "azure_enabled": false,
- "capi_provisioner_enabled": true,
- "enable_reprovision": false,
- "full_add_ons": false,
- "helm_values_enabled": false,
- "managed_infra_enabled": false,
- "multi_cluster": false,
- "preview_envs_enabled": false,
- "rds_databases_enabled": false,
- "simplified_view_enabled": true,
- "stacks_enabled": false,
- "validate_apply_v2": false,
- }
- type ProjectPlan string
- const (
- ProjectPlanBasic ProjectPlan = "basic"
- ProjectPlanTeam ProjectPlan = "team"
- ProjectPlanGrowth ProjectPlan = "growth"
- ProjectPlanEnterprise ProjectPlan = "enterprise"
- )
- // Project type that extends gorm.Model
- type Project struct {
- gorm.Model `gorm:"embedded"`
- Name string `json:"name"`
- Roles []Role `json:"roles"`
- ProjectUsageID uint
- ProjectUsageCacheID uint
- // linked repos
- GitRepos []GitRepo `json:"git_repos,omitempty"`
- // linked registries
- Registries []Registry `json:"registries,omitempty"`
- // linked clusters
- Clusters []Cluster `json:"clusters"`
- ClusterCandidates []ClusterCandidate `json:"cluster_candidates"`
- // linked databases
- Databases []Database `json:"databases"`
- // linked helm repos
- HelmRepos []HelmRepo `json:"helm_repos"`
- // invitations to the project
- Invites []Invite `json:"invites"`
- // provisioned aws infra
- Infras []Infra `json:"infras"`
- // auth mechanisms
- KubeIntegrations []ints.KubeIntegration `json:"kube_integrations"`
- BasicIntegrations []ints.BasicIntegration `json:"basic_integrations"`
- OIDCIntegrations []ints.OIDCIntegration `json:"oidc_integrations"`
- OAuthIntegrations []ints.OAuthIntegration `json:"oauth_integrations"`
- AWSIntegrations []ints.AWSIntegration `json:"aws_integrations"`
- GCPIntegrations []ints.GCPIntegration `json:"gcp_integrations"`
- AzureIntegrations []ints.AzureIntegration `json:"azure_integrations"`
- GitlabIntegrations []ints.GitlabIntegration `json:"gitlab_integrations"`
- PreviewEnvsEnabled bool
- RDSDatabasesEnabled bool
- ManagedInfraEnabled bool
- StacksEnabled bool
- APITokensEnabled bool
- CapiProvisionerEnabled bool
- SimplifiedViewEnabled bool
- AzureEnabled bool
- HelmValuesEnabled bool
- MultiCluster bool `gorm:"default:false"`
- FullAddOns bool `gorm:"default:false"`
- ValidateApplyV2 bool `gorm:"default:false"`
- EnableReprovision bool `gorm:"default:false"`
- }
- // GetFeatureFlag calls launchdarkly for the specified flag
- // and returns the configured value
- func (p *Project) GetFeatureFlag(flagName string, launchDarklyClient *features.Client) bool {
- projectID := p.ID
- projectName := p.Name
- ldContext := getProjectContext(projectID, projectName)
- defaultValue := ProjectFeatureFlags[flagName]
- value, _ := launchDarklyClient.BoolVariation(flagName, ldContext, defaultValue)
- return value
- }
- // ToProjectType generates an external types.Project to be shared over REST
- func (p *Project) ToProjectType(launchDarklyClient *features.Client) types.Project {
- roles := make([]*types.Role, 0)
- for _, role := range p.Roles {
- roles = append(roles, role.ToRoleType())
- }
- projectID := p.ID
- projectName := p.Name
- return types.Project{
- ID: projectID,
- Name: projectName,
- Roles: roles,
- PreviewEnvsEnabled: p.GetFeatureFlag("preview_envs_enabled", launchDarklyClient),
- RDSDatabasesEnabled: p.GetFeatureFlag("rds_databases_enabled", launchDarklyClient),
- ManagedInfraEnabled: p.GetFeatureFlag("managed_infra_enabled", launchDarklyClient),
- StacksEnabled: p.GetFeatureFlag("stacks_enabled", launchDarklyClient),
- APITokensEnabled: p.GetFeatureFlag("api_tokens_enabled", launchDarklyClient),
- CapiProvisionerEnabled: p.GetFeatureFlag("capi_provisioner_enabled", launchDarklyClient),
- SimplifiedViewEnabled: p.GetFeatureFlag("simplified_view_enabled", launchDarklyClient),
- AzureEnabled: p.GetFeatureFlag("azure_enabled", launchDarklyClient),
- HelmValuesEnabled: p.GetFeatureFlag("helm_values_enabled", launchDarklyClient),
- MultiCluster: p.GetFeatureFlag("multi_cluster", launchDarklyClient),
- EnableReprovision: p.GetFeatureFlag("enable_reprovision", launchDarklyClient),
- ValidateApplyV2: p.GetFeatureFlag("validate_apply_v2", launchDarklyClient),
- FullAddOns: p.GetFeatureFlag("full_add_ons", launchDarklyClient),
- }
- }
- // ToProjectListType returns a "minified" version of a Project
- // suitable for api responses to GET /projects
- // TODO: update this in the future to use default values for all
- // the feature flags instead of trying to retrieve them from the database
- func (p *Project) ToProjectListType() *types.ProjectList {
- var roles []types.Role
- for _, role := range p.Roles {
- roles = append(roles, *role.ToRoleType())
- }
- return &types.ProjectList{
- ID: p.ID,
- Name: p.Name,
- // note: all of these fields should be considered deprecated
- // in an api response
- Roles: roles,
- PreviewEnvsEnabled: p.PreviewEnvsEnabled,
- RDSDatabasesEnabled: p.RDSDatabasesEnabled,
- ManagedInfraEnabled: p.ManagedInfraEnabled,
- StacksEnabled: p.StacksEnabled,
- APITokensEnabled: p.APITokensEnabled,
- CapiProvisionerEnabled: p.CapiProvisionerEnabled,
- SimplifiedViewEnabled: p.SimplifiedViewEnabled,
- AzureEnabled: p.AzureEnabled,
- HelmValuesEnabled: p.HelmValuesEnabled,
- MultiCluster: p.MultiCluster,
- EnableReprovision: p.EnableReprovision,
- ValidateApplyV2: p.ValidateApplyV2,
- FullAddOns: p.FullAddOns,
- }
- }
- func getProjectContext(projectID uint, projectName string) ldcontext.Context {
- projectIdentifier := fmt.Sprintf("project-%d", projectID)
- launchDarklyName := fmt.Sprintf("%s: %s", projectIdentifier, projectName)
- return ldcontext.NewBuilder(projectIdentifier).
- Kind("project").
- Name(launchDarklyName).
- SetInt("project_id", int(projectID)).
- Build()
- }
|