From 5cfd41ae1a494a245d19e8e03947f649e3b64dec Mon Sep 17 00:00:00 2001 From: Ansuman Satapathy Date: Tue, 3 Sep 2024 09:59:29 +0000 Subject: [PATCH] feat: [CDE-202]: infra provider resource cache (#2637) * feat: [CDE-202]: infra provider resource cache * feat: [CDE-202]: infra provider resource cache * feat: [CDE-202]: infra provider resource cache * feat: [CDE-202]: infra provider resource cache * feat: [CDE-202]: infra provider resource cache * feat: [CDE-202]: infra provider resource cache * feat: [CDE-202]: infra provider resource cache * feat: [CDE-202]: infra provider resource cache * feat: [CDE-202]: infra provider resource cache * feat: [CDE-202]: infra provider resource cache --- app/api/controller/gitspace/create.go | 27 ++++--- app/api/controller/gitspace/find.go | 2 +- .../infraprovider/create_resources.go | 2 +- .../orchestrator/orchestrator_impl.go | 52 ++++--------- app/services/gitspace/find.go | 7 -- app/services/gitspaceinfraevent/handler.go | 5 +- app/services/infraprovider/create.go | 2 +- app/services/infraprovider/update.go | 2 +- app/store/cache.go | 3 + app/store/cache/wire.go | 6 ++ app/store/database.go | 7 ++ app/store/database/gitspace_config.go | 38 ++++++---- app/store/database/infra_provider_resource.go | 73 ++++++++++++++++--- app/store/database/wire.go | 14 +++- cmd/gitness/wire_gen.go | 4 +- types/gitspace.go | 27 ++++--- types/infra_provider.go | 6 +- 17 files changed, 168 insertions(+), 109 deletions(-) diff --git a/app/api/controller/gitspace/create.go b/app/api/controller/gitspace/create.go index ef00884fd..b12f64e93 100644 --- a/app/api/controller/gitspace/create.go +++ b/app/api/controller/gitspace/create.go @@ -149,20 +149,19 @@ func (c *Controller) Create( DisplayName: principal.DisplayName, ID: &principalID} gitspaceConfig = &types.GitspaceConfig{ - Identifier: identifier, - Name: in.Name, - IDE: in.IDE, - InfraProviderResourceID: infraProviderResource.ID, - InfraProviderResourceIdentifier: infraProviderResource.Identifier, - State: enum.GitspaceStateUninitialized, - SpaceID: space.ID, - SpacePath: space.Path, - Created: now, - Updated: now, - SSHTokenIdentifier: in.SSHTokenIdentifier, - CodeRepo: codeRepo, - GitspaceUser: user, + Identifier: identifier, + Name: in.Name, + IDE: in.IDE, + State: enum.GitspaceStateUninitialized, + SpaceID: space.ID, + SpacePath: space.Path, + Created: now, + Updated: now, + SSHTokenIdentifier: in.SSHTokenIdentifier, + CodeRepo: codeRepo, + GitspaceUser: user, } + gitspaceConfig.InfraProviderResource = *infraProviderResource err = c.gitspaceConfigStore.Create(ctx, gitspaceConfig) if err != nil { return fmt.Errorf("failed to create gitspace config for : %q %w", identifier, err) @@ -209,7 +208,7 @@ func (c *Controller) autoCreateDefaultResource(ctx context.Context, parentSpace Updated: now, } defaultResource := types.InfraProviderResource{ - Identifier: defaultResourceIdentifier, + UID: defaultResourceIdentifier, Name: "Standard Docker Resource", InfraProviderConfigIdentifier: defaultDockerConfig.Identifier, InfraProviderType: enum.InfraProviderTypeDocker, diff --git a/app/api/controller/gitspace/find.go b/app/api/controller/gitspace/find.go index c46459bcf..114251c37 100644 --- a/app/api/controller/gitspace/find.go +++ b/app/api/controller/gitspace/find.go @@ -40,7 +40,7 @@ func (c *Controller) Find( return nil, fmt.Errorf("failed to authorize: %w", err) } - res, err := c.gitspaceSvc.Find(ctx, space.ID, space.Path, identifier) + res, err := c.gitspaceSvc.Find(ctx, space.ID, identifier) if err != nil { return nil, fmt.Errorf("failed to find gitspace: %w", err) } diff --git a/app/api/controller/infraprovider/create_resources.go b/app/api/controller/infraprovider/create_resources.go index c059572a2..0201e4b8d 100644 --- a/app/api/controller/infraprovider/create_resources.go +++ b/app/api/controller/infraprovider/create_resources.go @@ -112,7 +112,7 @@ func mapToResourceEntity(in []ResourceInput, parentSpace types.Space, now int64) var resources []types.InfraProviderResource for _, res := range in { infraProviderResource := types.InfraProviderResource{ - Identifier: res.Identifier, + UID: res.Identifier, InfraProviderType: res.InfraProviderType, Name: res.Name, SpaceID: parentSpace.ID, diff --git a/app/gitspace/orchestrator/orchestrator_impl.go b/app/gitspace/orchestrator/orchestrator_impl.go index aaad90f79..2145df9b3 100644 --- a/app/gitspace/orchestrator/orchestrator_impl.go +++ b/app/gitspace/orchestrator/orchestrator_impl.go @@ -86,12 +86,6 @@ func (o orchestrator) TriggerStartGitspace( ctx context.Context, gitspaceConfig types.GitspaceConfig, ) error { - infraProviderResource, err := o.infraProviderResourceStore.Find(ctx, gitspaceConfig.InfraProviderResourceID) - if err != nil { - return fmt.Errorf("cannot get the infraprovider resource for ID %d: %w", - gitspaceConfig.InfraProviderResourceID, err) - } - requiredGitspacePorts, err := o.getPortsRequiredForGitspace(gitspaceConfig) if err != nil { return fmt.Errorf("cannot get the ports required for gitspace during start: %w", err) @@ -99,12 +93,13 @@ func (o orchestrator) TriggerStartGitspace( o.emitGitspaceEvent(ctx, gitspaceConfig, enum.GitspaceEventTypeInfraProvisioningStart) - err = o.infraProvisioner.TriggerProvision(ctx, *infraProviderResource, gitspaceConfig, requiredGitspacePorts) + err = o.infraProvisioner.TriggerProvision(ctx, gitspaceConfig.InfraProviderResource, + gitspaceConfig, requiredGitspacePorts) if err != nil { o.emitGitspaceEvent(ctx, gitspaceConfig, enum.GitspaceEventTypeInfraProvisioningFailed) return fmt.Errorf( - "cannot trigger provision infrastructure for ID %d: %w", gitspaceConfig.InfraProviderResourceID, err) + "cannot trigger provision infrastructure for ID %s: %w", gitspaceConfig.InfraProviderResource.UID, err) } return nil @@ -114,13 +109,7 @@ func (o orchestrator) TriggerStopGitspace( ctx context.Context, gitspaceConfig types.GitspaceConfig, ) error { - infraProviderResource, err := o.infraProviderResourceStore.Find(ctx, gitspaceConfig.InfraProviderResourceID) - if err != nil { - return fmt.Errorf( - "cannot get the infraProviderResource with ID %d: %w", gitspaceConfig.InfraProviderResourceID, err) - } - - infra, err := o.getProvisionedInfra(ctx, infraProviderResource, gitspaceConfig) + infra, err := o.getProvisionedInfra(ctx, &gitspaceConfig.InfraProviderResource, gitspaceConfig) if err != nil { return fmt.Errorf( "unable to find provisioned infra while triggering stop for gitspace instance %s: %w", @@ -134,12 +123,12 @@ func (o orchestrator) TriggerStopGitspace( o.emitGitspaceEvent(ctx, gitspaceConfig, enum.GitspaceEventTypeInfraStopStart) - err = o.infraProvisioner.TriggerStop(ctx, *infraProviderResource, *infra) + err = o.infraProvisioner.TriggerStop(ctx, gitspaceConfig.InfraProviderResource, *infra) if err != nil { o.emitGitspaceEvent(ctx, gitspaceConfig, enum.GitspaceEventTypeInfraStopFailed) return fmt.Errorf( - "cannot trigger stop infrastructure with ID %d: %w", gitspaceConfig.InfraProviderResourceID, err) + "cannot trigger stop infrastructure with ID %s: %w", gitspaceConfig.InfraProviderResource.UID, err) } return nil @@ -213,13 +202,7 @@ func (o orchestrator) TriggerDeleteGitspace( ctx context.Context, gitspaceConfig types.GitspaceConfig, ) error { - infraProviderResource, err := o.infraProviderResourceStore.Find(ctx, gitspaceConfig.InfraProviderResourceID) - if err != nil { - return fmt.Errorf( - "cannot get the infraProviderResource with ID %d: %w", gitspaceConfig.InfraProviderResourceID, err) - } - - infra, err := o.getProvisionedInfra(ctx, infraProviderResource, gitspaceConfig) + infra, err := o.getProvisionedInfra(ctx, &gitspaceConfig.InfraProviderResource, gitspaceConfig) if err != nil { return fmt.Errorf( "unable to find provisioned infra while triggering delete for gitspace instance %s: %w", @@ -233,12 +216,12 @@ func (o orchestrator) TriggerDeleteGitspace( o.emitGitspaceEvent(ctx, gitspaceConfig, enum.GitspaceEventTypeInfraDeprovisioningStart) - err = o.infraProvisioner.TriggerDeprovision(ctx, *infraProviderResource, gitspaceConfig, *infra) + err = o.infraProvisioner.TriggerDeprovision(ctx, gitspaceConfig.InfraProviderResource, gitspaceConfig, *infra) if err != nil { o.emitGitspaceEvent(ctx, gitspaceConfig, enum.GitspaceEventTypeInfraDeprovisioningFailed) return fmt.Errorf( - "cannot trigger deprovision infrastructure with ID %d: %w", gitspaceConfig.InfraProviderResourceID, err) + "cannot trigger deprovision infrastructure with ID %s: %w", gitspaceConfig.InfraProviderResource.UID, err) } return nil @@ -319,7 +302,7 @@ func (o orchestrator) ResumeStartGitspace( o.emitGitspaceEvent(ctx, gitspaceConfig, enum.GitspaceEventTypeInfraProvisioningFailed) return *gitspaceInstance, fmt.Errorf( - "cannot provision infrastructure for ID %d: %w", gitspaceConfig.InfraProviderResourceID, err) + "cannot provision infrastructure for ID %s: %w", gitspaceConfig.InfraProviderResource.UID, err) } if provisionedInfra.Status != enum.InfraStatusProvisioned { @@ -451,7 +434,7 @@ func (o orchestrator) ResumeStopGitspace( o.emitGitspaceEvent(ctx, gitspaceConfig, enum.GitspaceEventTypeInfraStopFailed) return instanceState, fmt.Errorf( - "cannot stop provisioned infrastructure with ID %d: %w", gitspaceConfig.InfraProviderResourceID, err) + "cannot stop provisioned infrastructure with ID %s: %w", gitspaceConfig.InfraProviderResource.UID, err) } if stoppedInfra.Status != enum.InfraStatusDestroyed && @@ -485,7 +468,7 @@ func (o orchestrator) ResumeDeleteGitspace( if err != nil { o.emitGitspaceEvent(ctx, gitspaceConfig, enum.GitspaceEventTypeInfraDeprovisioningFailed) return instanceState, fmt.Errorf( - "cannot deprovision infrastructure with ID %d: %w", gitspaceConfig.InfraProviderResourceID, err) + "cannot deprovision infrastructure with ID %s: %w", gitspaceConfig.InfraProviderResource.UID, err) } if deprovisionedInfra.Status != enum.InfraStatusDestroyed { @@ -542,15 +525,6 @@ func (o orchestrator) getProvisionedInfra( infraProviderResource *types.InfraProviderResource, gitspaceConfig types.GitspaceConfig, ) (*types.Infrastructure, error) { - if infraProviderResource == nil { - var err error - infraProviderResource, err = o.infraProviderResourceStore.Find(ctx, gitspaceConfig.InfraProviderResourceID) - if err != nil { - return nil, fmt.Errorf( - "cannot get the infraProviderResource with ID %d: %w", gitspaceConfig.InfraProviderResourceID, err) - } - } - requiredGitspacePorts, err := o.getPortsRequiredForGitspace(gitspaceConfig) if err != nil { return nil, fmt.Errorf("cannot get the ports required for gitspace: %w", err) @@ -566,7 +540,7 @@ func (o orchestrator) getProvisionedInfra( } if infra.Storage == "" { - log.Warn().Msgf("couldn't find the storage for resource ID %d", gitspaceConfig.InfraProviderResourceID) + log.Warn().Msgf("couldn't find the storage for resource ID %s", gitspaceConfig.InfraProviderResource.UID) } return infra, nil diff --git a/app/services/gitspace/find.go b/app/services/gitspace/find.go index caf144d6b..8b284d754 100644 --- a/app/services/gitspace/find.go +++ b/app/services/gitspace/find.go @@ -28,7 +28,6 @@ import ( func (c *Service) Find( ctx context.Context, spaceID int64, - spacePath string, identifier string, ) (*types.GitspaceConfig, error) { var gitspaceConfigResult *types.GitspaceConfig @@ -37,12 +36,6 @@ func (c *Service) Find( if err != nil { return fmt.Errorf("failed to find gitspace config: %w", err) } - infraProviderResource, err := c.infraProviderSvc.FindResource(ctx, gitspaceConfig.InfraProviderResourceID) - if err != nil { - return fmt.Errorf("failed to find infra provider resource for gitspace config: %w", err) - } - gitspaceConfig.SpacePath = spacePath - gitspaceConfig.InfraProviderResourceIdentifier = infraProviderResource.Identifier instance, err := c.gitspaceInstanceStore.FindLatestByGitspaceConfigID(ctx, gitspaceConfig.ID, gitspaceConfig.SpaceID) if err != nil && !errors.Is(err, store.ErrResourceNotFound) { return err diff --git a/app/services/gitspaceinfraevent/handler.go b/app/services/gitspaceinfraevent/handler.go index 16e00fc2a..55635f732 100644 --- a/app/services/gitspaceinfraevent/handler.go +++ b/app/services/gitspaceinfraevent/handler.go @@ -35,7 +35,7 @@ func (s *Service) handleGitspaceInfraEvent( payload := event.Payload config, fetchErr := s.getConfig( - ctx, payload.Infra.SpaceID, payload.Infra.SpacePath, payload.Infra.GitspaceConfigIdentifier) + ctx, payload.Infra.SpaceID, payload.Infra.GitspaceConfigIdentifier) if fetchErr != nil { return fetchErr } @@ -96,10 +96,9 @@ func (s *Service) handleGitspaceInfraEvent( func (s *Service) getConfig( ctx context.Context, spaceID int64, - spacePath string, identifier string, ) (*types.GitspaceConfig, error) { - config, err := s.gitspaceSvc.Find(ctx, spaceID, spacePath, identifier) + config, err := s.gitspaceSvc.Find(ctx, spaceID, identifier) if err != nil { return nil, fmt.Errorf( "failed to find gitspace config during infra event handling, identifier %s: %w", identifier, err) diff --git a/app/services/infraprovider/create.go b/app/services/infraprovider/create.go index 51328ba34..121d69565 100644 --- a/app/services/infraprovider/create.go +++ b/app/services/infraprovider/create.go @@ -86,7 +86,7 @@ func (c *Service) createResources(ctx context.Context, resources []types.InfraPr } err = c.infraProviderResourceStore.Create(ctx, resource) if err != nil { - return fmt.Errorf("failed to create infraprovider resource for : %q %w", resource.Identifier, err) + return fmt.Errorf("failed to create infraprovider resource for : %q %w", resource.UID, err) } } return nil diff --git a/app/services/infraprovider/update.go b/app/services/infraprovider/update.go index 57f2fcefd..e3b9ac7fd 100644 --- a/app/services/infraprovider/update.go +++ b/app/services/infraprovider/update.go @@ -59,7 +59,7 @@ func (c *Service) UpdateResource(ctx context.Context, resource types.InfraProvid if err != nil { return err } - infraProviderResource, err := c.FindResourceByIdentifier(ctx, space.ID, resource.Identifier) + infraProviderResource, err := c.FindResourceByIdentifier(ctx, space.ID, resource.UID) if err != nil { return err } diff --git a/app/store/cache.go b/app/store/cache.go index 25eb074c8..333158ea8 100644 --- a/app/store/cache.go +++ b/app/store/cache.go @@ -28,4 +28,7 @@ type ( // RepoGitInfoCache caches repository IDs to values GitUID. RepoGitInfoCache cache.Cache[int64, *types.RepositoryGitInfo] + + // InfraProviderResourceCache caches infraprovider resourceIDs to infraprovider resource. + InfraProviderResourceCache cache.ExtendedCache[int64, *types.InfraProviderResource] ) diff --git a/app/store/cache/wire.go b/app/store/cache/wire.go index 78a9e1eb8..4c30a7291 100644 --- a/app/store/cache/wire.go +++ b/app/store/cache/wire.go @@ -29,6 +29,7 @@ var WireSet = wire.NewSet( ProvidePrincipalInfoCache, ProvidePathCache, ProvideRepoGitInfoCache, + ProvideInfraProviderResourceCache, ) // ProvidePrincipalInfoCache provides a cache for storing types.PrincipalInfo objects. @@ -48,3 +49,8 @@ func ProvidePathCache( func ProvideRepoGitInfoCache(getter store.RepoGitInfoView) store.RepoGitInfoCache { return cache.New[int64, *types.RepositoryGitInfo](getter, 15*time.Minute) } + +// ProvideInfraProviderResourceCache provides a cache for storing types.InfraProviderResource objects. +func ProvideInfraProviderResourceCache(getter store.InfraProviderResourceView) store.InfraProviderResourceCache { + return cache.NewExtended[int64, *types.InfraProviderResource](getter, 5*time.Minute) +} diff --git a/app/store/database.go b/app/store/database.go index ac808a5a9..f02758100 100644 --- a/app/store/database.go +++ b/app/store/database.go @@ -134,6 +134,13 @@ type ( FindMany(ctx context.Context, ids []int64) ([]*types.PrincipalInfo, error) } + // InfraProviderResourceView defines helper utility for fetching types.InfraProviderResource objects. + // It uses the same underlying data storage as InfraProviderResourceStore. + InfraProviderResourceView interface { + Find(ctx context.Context, id int64) (*types.InfraProviderResource, error) + FindMany(ctx context.Context, ids []int64) ([]*types.InfraProviderResource, error) + } + // SpacePathStore defines the path data storage for spaces. SpacePathStore interface { // InsertSegment inserts a space path segment to the table. diff --git a/app/store/database/gitspace_config.go b/app/store/database/gitspace_config.go index 3d08c3f21..34b88aafb 100644 --- a/app/store/database/gitspace_config.go +++ b/app/store/database/gitspace_config.go @@ -16,6 +16,7 @@ package database import ( "context" + "fmt" "strings" "github.com/harness/gitness/app/store" @@ -84,16 +85,22 @@ type gitspaceConfig struct { var _ store.GitspaceConfigStore = (*gitspaceConfigStore)(nil) // NewGitspaceConfigStore returns a new GitspaceConfigStore. -func NewGitspaceConfigStore(db *sqlx.DB, pCache store.PrincipalInfoCache) store.GitspaceConfigStore { +func NewGitspaceConfigStore( + db *sqlx.DB, + pCache store.PrincipalInfoCache, + rCache store.InfraProviderResourceCache, +) store.GitspaceConfigStore { return &gitspaceConfigStore{ db: db, pCache: pCache, + rCache: rCache, } } type gitspaceConfigStore struct { db *sqlx.DB pCache store.PrincipalInfoCache + rCache store.InfraProviderResourceCache } func (s gitspaceConfigStore) Count(ctx context.Context, filter *types.GitspaceFilter) (int64, error) { @@ -174,7 +181,7 @@ func (s gitspaceConfigStore) Create(ctx context.Context, gitspaceConfig *types.G gitspaceConfig.Identifier, gitspaceConfig.Name, gitspaceConfig.IDE, - gitspaceConfig.InfraProviderResourceID, + gitspaceConfig.InfraProviderResource.ID, gitspaceConfig.CodeRepo.AuthType, gitspaceConfig.CodeRepo.AuthID, gitspaceConfig.CodeRepo.Type, @@ -233,7 +240,7 @@ func mapToInternalGitspaceConfig(config *types.GitspaceConfig) *gitspaceConfig { Identifier: config.Identifier, Name: config.Name, IDE: config.IDE, - InfraProviderResourceID: config.InfraProviderResourceID, + InfraProviderResourceID: config.InfraProviderResource.ID, CodeAuthType: config.CodeRepo.AuthType, CodeAuthID: config.CodeRepo.AuthID, CodeRepoIsPrivate: config.CodeRepo.IsPrivate, @@ -313,16 +320,15 @@ func (s *gitspaceConfigStore) mapToGitspaceConfig( AuthID: in.CodeAuthID, } var res = &types.GitspaceConfig{ - ID: in.ID, - Identifier: in.Identifier, - Name: in.Name, - InfraProviderResourceID: in.InfraProviderResourceID, - IDE: in.IDE, - SpaceID: in.SpaceID, - Created: in.Created, - Updated: in.Updated, - SSHTokenIdentifier: in.SSHTokenIdentifier, - CodeRepo: codeRepo, + ID: in.ID, + Identifier: in.Identifier, + Name: in.Name, + IDE: in.IDE, + SpaceID: in.SpaceID, + Created: in.Created, + Updated: in.Updated, + SSHTokenIdentifier: in.SSHTokenIdentifier, + CodeRepo: codeRepo, GitspaceUser: types.GitspaceUser{ ID: in.CreatedBy.Ptr(), Identifier: in.UserUID}, @@ -334,6 +340,12 @@ func (s *gitspaceConfigStore) mapToGitspaceConfig( res.GitspaceUser.Email = author.Email } } + + if resource, err := s.rCache.Get(ctx, in.InfraProviderResourceID); err == nil { + res.InfraProviderResource = *resource + } else { + return nil, fmt.Errorf("couldn't set resource to the config in DB: %s", in.Identifier) + } return res, nil } diff --git a/app/store/database/infra_provider_resource.go b/app/store/database/infra_provider_resource.go index cbf47a840..cb9951510 100644 --- a/app/store/database/infra_provider_resource.go +++ b/app/store/database/infra_provider_resource.go @@ -25,6 +25,7 @@ import ( "github.com/harness/gitness/types" "github.com/harness/gitness/types/enum" + "github.com/Masterminds/squirrel" "github.com/guregu/null" "github.com/jmoiron/sqlx" "github.com/pkg/errors" @@ -103,7 +104,7 @@ func (s infraProviderResourceStore) List(ctx context.Context, infraProviderConfi if err := db.SelectContext(ctx, dst, sql, args...); err != nil { return nil, database.ProcessSQLErrorf(ctx, err, "Failed to list infraprovider resources") } - return s.mapToInfraProviderResources(ctx, *dst) + return mapToInfraProviderResources(ctx, *dst) } func (s infraProviderResourceStore) Find(ctx context.Context, id int64) (*types.InfraProviderResource, error) { @@ -121,7 +122,7 @@ func (s infraProviderResourceStore) Find(ctx context.Context, id int64) (*types. if err := db.GetContext(ctx, dst, sql, args...); err != nil { return nil, database.ProcessSQLErrorf(ctx, err, "Failed to find infraprovider resource %d", id) } - return s.mapToInfraProviderResource(ctx, dst) + return mapToInfraProviderResource(ctx, dst) } func (s infraProviderResourceStore) FindByIdentifier( @@ -143,7 +144,7 @@ func (s infraProviderResourceStore) FindByIdentifier( if err := db.GetContext(ctx, dst, sql, args...); err != nil { return nil, database.ProcessSQLErrorf(ctx, err, "Failed to find infraprovider resource %s", identifier) } - return s.mapToInfraProviderResource(ctx, dst) + return mapToInfraProviderResource(ctx, dst) } func (s infraProviderResourceStore) Create( @@ -183,7 +184,7 @@ func (s infraProviderResourceStore) Create( db := dbtx.GetAccessor(ctx, s.db) if err = db.QueryRowContext(ctx, sql, args...).Scan(&infraProviderResource.ID); err != nil { return database.ProcessSQLErrorf( - ctx, err, "infra provider resource create failed %s", infraProviderResource.Identifier) + ctx, err, "infra provider resource create failed %s", infraProviderResource.UID) } return nil } @@ -195,7 +196,7 @@ func (s infraProviderResourceStore) Update( dbinfraProviderResource, err := s.mapToInternalInfraProviderResource(ctx, infraProviderResource) if err != nil { return fmt.Errorf( - "failed to map to DB Obj for infraprovider resource %s", infraProviderResource.Identifier) + "failed to map to DB Obj for infraprovider resource %s", infraProviderResource.UID) } stmt := database.Builder. Update(infraProviderResourceTable). @@ -214,7 +215,7 @@ func (s infraProviderResourceStore) Update( db := dbtx.GetAccessor(ctx, s.db) if _, err := db.ExecContext(ctx, sql, args...); err != nil { return database.ProcessSQLErrorf( - ctx, err, "Failed to update infraprovider resource %s", infraProviderResource.Identifier) + ctx, err, "Failed to update infraprovider resource %s", infraProviderResource.UID) } return nil } @@ -236,7 +237,7 @@ func (s infraProviderResourceStore) DeleteByIdentifier(ctx context.Context, spac return nil } -func (s infraProviderResourceStore) mapToInfraProviderResource(_ context.Context, +func mapToInfraProviderResource(_ context.Context, in *infraProviderResource) (*types.InfraProviderResource, error) { openTofuParamsMap := make(map[string]string) marshalErr := json.Unmarshal(in.OpenTofuParams, &openTofuParamsMap) @@ -244,7 +245,7 @@ func (s infraProviderResourceStore) mapToInfraProviderResource(_ context.Context return nil, marshalErr } return &types.InfraProviderResource{ - Identifier: in.Identifier, + UID: in.Identifier, InfraProviderConfigID: in.InfraProviderConfigID, ID: in.ID, InfraProviderType: in.InfraProviderType, @@ -271,7 +272,7 @@ func (s infraProviderResourceStore) mapToInternalInfraProviderResource(_ context return nil, marshalErr } return &infraProviderResource{ - Identifier: in.Identifier, + Identifier: in.UID, InfraProviderConfigID: in.InfraProviderConfigID, InfraProviderType: in.InfraProviderType, Name: in.Name, @@ -290,15 +291,65 @@ func (s infraProviderResourceStore) mapToInternalInfraProviderResource(_ context }, nil } -func (s infraProviderResourceStore) mapToInfraProviderResources(ctx context.Context, +func mapToInfraProviderResources(ctx context.Context, resources []infraProviderResource) ([]*types.InfraProviderResource, error) { var err error res := make([]*types.InfraProviderResource, len(resources)) for i := range resources { - res[i], err = s.mapToInfraProviderResource(ctx, &resources[i]) + res[i], err = mapToInfraProviderResource(ctx, &resources[i]) if err != nil { return nil, err } } return res, nil } + +var _ store.InfraProviderResourceView = (*InfraProviderResourceView)(nil) + +// NewInfraProviderResourceView returns a new InfraProviderResourceView. +// It's used by the infraprovider resource cache. +func NewInfraProviderResourceView(db *sqlx.DB) *InfraProviderResourceView { + return &InfraProviderResourceView{ + db: db, + } +} + +type InfraProviderResourceView struct { + db *sqlx.DB +} + +func (i InfraProviderResourceView) Find(ctx context.Context, id int64) (*types.InfraProviderResource, error) { + stmt := database.Builder. + Select(infraProviderResourceSelectColumns). + From(infraProviderResourceTable). + Where(infraProviderResourceIDColumn+" = $1", id) + + sql, args, err := stmt.ToSql() + if err != nil { + return nil, errors.Wrap(err, "Failed to convert squirrel builder to sql") + } + dst := new(infraProviderResource) + db := dbtx.GetAccessor(ctx, i.db) + if err := db.GetContext(ctx, dst, sql, args...); err != nil { + return nil, database.ProcessSQLErrorf(ctx, err, "Failed to find infraprovider resource %d", id) + } + return mapToInfraProviderResource(ctx, dst) +} + +func (i InfraProviderResourceView) FindMany(ctx context.Context, ids []int64) ([]*types.InfraProviderResource, error) { + stmt := database.Builder. + Select(infraProviderResourceSelectColumns). + From(infraProviderResourceTable). + Where(squirrel.Eq{infraProviderTemplateIDColumn: ids}) + + sql, args, err := stmt.ToSql() + if err != nil { + return nil, errors.Wrap(err, "Failed to convert squirrel builder to sql") + } + dst := new([]infraProviderResource) + db := dbtx.GetAccessor(ctx, i.db) + if err := db.GetContext(ctx, dst, sql, args...); err != nil { + return nil, database.ProcessSQLErrorf(ctx, err, "Failed to find infraprovider resources") + } + return mapToInfraProviderResources(ctx, *dst) +} diff --git a/app/store/database/wire.go b/app/store/database/wire.go index 98bc2b0e5..8d843005d 100644 --- a/app/store/database/wire.go +++ b/app/store/database/wire.go @@ -33,6 +33,7 @@ var WireSet = wire.NewSet( ProvideUserGroupStore, ProvideUserGroupReviewerStore, ProvidePrincipalInfoView, + ProvideInfraProviderResourceView, ProvideSpacePathStore, ProvideSpaceStore, ProvideRepoStore, @@ -114,6 +115,11 @@ func ProvidePrincipalInfoView(db *sqlx.DB) store.PrincipalInfoView { return NewPrincipalInfoView(db) } +// ProvideInfraProviderResourceView provides a principal info store. +func ProvideInfraProviderResourceView(db *sqlx.DB) store.InfraProviderResourceView { + return NewInfraProviderResourceView(db) +} + // ProvideSpacePathStore provides a space path store. func ProvideSpacePathStore( db *sqlx.DB, @@ -170,8 +176,12 @@ func ProvideInfraProviderResourceStore(db *sqlx.DB) store.InfraProviderResourceS } // ProvideGitspaceConfigStore provides a gitspace config store. -func ProvideGitspaceConfigStore(db *sqlx.DB, pCache store.PrincipalInfoCache) store.GitspaceConfigStore { - return NewGitspaceConfigStore(db, pCache) +func ProvideGitspaceConfigStore( + db *sqlx.DB, + pCache store.PrincipalInfoCache, + rCache store.InfraProviderResourceCache, +) store.GitspaceConfigStore { + return NewGitspaceConfigStore(db, pCache, rCache) } // ProvideGitspaceInstanceStore provides a gitspace instance store. diff --git a/cmd/gitness/wire_gen.go b/cmd/gitness/wire_gen.go index d3d3df09b..ffc7e6458 100644 --- a/cmd/gitness/wire_gen.go +++ b/cmd/gitness/wire_gen.go @@ -275,7 +275,9 @@ func initSystem(ctx context.Context, config *types.Config) (*server.System, erro if err != nil { return nil, err } - gitspaceConfigStore := database.ProvideGitspaceConfigStore(db, principalInfoCache) + infraProviderResourceView := database.ProvideInfraProviderResourceView(db) + infraProviderResourceCache := cache.ProvideInfraProviderResourceCache(infraProviderResourceView) + gitspaceConfigStore := database.ProvideGitspaceConfigStore(db, principalInfoCache, infraProviderResourceCache) gitspaceInstanceStore := database.ProvideGitspaceInstanceStore(db) infraProviderResourceStore := database.ProvideInfraProviderResourceStore(db) infraProviderConfigStore := database.ProvideInfraProviderConfigStore(db) diff --git a/types/gitspace.go b/types/gitspace.go index bf3e52ae6..dc1d6a42a 100644 --- a/types/gitspace.go +++ b/types/gitspace.go @@ -19,20 +19,19 @@ import ( ) type GitspaceConfig struct { - ID int64 `json:"-"` - Identifier string `json:"identifier"` - Name string `json:"name"` - IDE enum.IDEType `json:"ide"` - State enum.GitspaceStateType `json:"state"` - InfraProviderResourceID int64 `json:"-"` - InfraProviderResourceIdentifier string `json:"resource_identifier"` - SpaceID int64 `json:"-"` - IsDeleted bool `json:"-"` - GitspaceInstance *GitspaceInstance `json:"instance"` - SpacePath string `json:"space_path"` - Created int64 `json:"created"` - Updated int64 `json:"updated"` - SSHTokenIdentifier string `json:"ssh_token_identifier"` + ID int64 `json:"-"` + Identifier string `json:"identifier"` + Name string `json:"name"` + IDE enum.IDEType `json:"ide"` + State enum.GitspaceStateType `json:"state"` + SpaceID int64 `json:"-"` + IsDeleted bool `json:"-"` + GitspaceInstance *GitspaceInstance `json:"instance"` + SpacePath string `json:"space_path"` + Created int64 `json:"created"` + Updated int64 `json:"updated"` + SSHTokenIdentifier string `json:"ssh_token_identifier"` + InfraProviderResource InfraProviderResource `json:"resource"` CodeRepo GitspaceUser } diff --git a/types/infra_provider.go b/types/infra_provider.go index 51fa937cc..44167155f 100644 --- a/types/infra_provider.go +++ b/types/infra_provider.go @@ -33,7 +33,7 @@ type InfraProviderConfig struct { type InfraProviderResource struct { ID int64 `json:"-"` - Identifier string `json:"identifier"` + UID string `json:"identifier"` Name string `json:"name"` InfraProviderConfigID int64 `json:"-"` InfraProviderConfigIdentifier string `json:"config_identifier"` @@ -56,6 +56,10 @@ type InfraProviderResource struct { Updated int64 `json:"updated"` } +func (i *InfraProviderResource) Identifier() int64 { + return i.ID +} + type InfraProviderTemplate struct { ID int64 `json:"-"` Identifier string `json:"identifier"`