diff --git a/cmd/gitness/wire_gen.go b/cmd/gitness/wire_gen.go index 5ab076ada..70f0e0692 100644 --- a/cmd/gitness/wire_gen.go +++ b/cmd/gitness/wire_gen.go @@ -88,6 +88,7 @@ func initSystem(ctx context.Context, config *types.Config) (*server.System, erro } pathUID := check.ProvidePathUIDCheck() repoStore := database.ProvideRepoStore(db, pathCache) + pipelineStore := database.ProvidePipelineStore(db) gitrpcConfig, err := server.ProvideGitRPCClientConfig() if err != nil { return nil, err @@ -96,27 +97,26 @@ func initSystem(ctx context.Context, config *types.Config) (*server.System, erro if err != nil { return nil, err } - repoController := repo.ProvideController(config, db, provider, pathUID, authorizer, pathStore, repoStore, spaceStore, principalStore, gitrpcInterface) + repoController := repo.ProvideController(config, db, provider, pathUID, authorizer, pathStore, repoStore, spaceStore, pipelineStore, principalStore, gitrpcInterface) executionStore := database.ProvideExecutionStore(db) stageStore := database.ProvideStageStore(db) - pipelineStore := database.ProvidePipelineStore(db) - executionController := execution.ProvideController(db, authorizer, executionStore, stageStore, pipelineStore, spaceStore) + executionController := execution.ProvideController(db, authorizer, executionStore, repoStore, stageStore, pipelineStore) stepStore := database.ProvideStepStore(db) logStore := logs.ProvideLogStore(db, config) logStream := livelog.ProvideLogStream(config) - logsController := logs2.ProvideController(db, authorizer, executionStore, pipelineStore, stageStore, stepStore, logStore, logStream, spaceStore) + logsController := logs2.ProvideController(db, authorizer, executionStore, repoStore, pipelineStore, stageStore, stepStore, logStore, logStream) secretStore := database.ProvideSecretStore(db) connectorStore := database.ProvideConnectorStore(db) templateStore := database.ProvideTemplateStore(db) spaceController := space.ProvideController(db, provider, pathUID, authorizer, pathStore, pipelineStore, secretStore, connectorStore, templateStore, spaceStore, repoStore, principalStore, repoController, membershipStore) - pipelineController := pipeline.ProvideController(db, pathUID, pathStore, repoStore, authorizer, pipelineStore, spaceStore) + pipelineController := pipeline.ProvideController(db, pathUID, pathStore, repoStore, authorizer, pipelineStore) encrypter, err := encrypt.ProvideEncrypter(config) if err != nil { return nil, err } secretController := secret.ProvideController(db, pathUID, pathStore, encrypter, secretStore, authorizer, spaceStore) triggerStore := database.ProvideTriggerStore(db) - triggerController := trigger.ProvideController(db, authorizer, triggerStore, pipelineStore, spaceStore) + triggerController := trigger.ProvideController(db, authorizer, triggerStore, pipelineStore, repoStore) connectorController := connector.ProvideController(db, pathUID, connectorStore, authorizer, spaceStore) templateController := template.ProvideController(db, pathUID, templateStore, authorizer, spaceStore) pluginStore := database.ProvidePluginStore(db) diff --git a/internal/api/auth/pipeline.go b/internal/api/auth/pipeline.go index 8c5c199a6..8d012b8ca 100644 --- a/internal/api/auth/pipeline.go +++ b/internal/api/auth/pipeline.go @@ -9,21 +9,26 @@ import ( "github.com/harness/gitness/internal/auth" "github.com/harness/gitness/internal/auth/authz" + "github.com/harness/gitness/internal/paths" "github.com/harness/gitness/types" "github.com/harness/gitness/types/enum" + "github.com/pkg/errors" ) -// CheckPipeline checks if a repo specific permission is granted for the current auth session -// in the scope of its parent. +// CheckPipeline checks if a pipeline specific permission is granted for the current auth session +// in the scope of the parent. // Returns nil if the permission is granted, otherwise returns an error. // NotAuthenticated, NotAuthorized, or any underlying error. func CheckPipeline(ctx context.Context, authorizer authz.Authorizer, session *auth.Session, - parentPath, uid string, permission enum.Permission) error { - scope := &types.Scope{SpacePath: parentPath} + repoPath string, pipelineUID string, permission enum.Permission) error { + spacePath, repoName, err := paths.DisectLeaf(repoPath) + if err != nil { + return errors.Wrapf(err, "Failed to disect path '%s'", repoPath) + } + scope := &types.Scope{SpacePath: spacePath, Repo: repoName} resource := &types.Resource{ Type: enum.ResourceTypePipeline, - Name: uid, + Name: pipelineUID, } - return Check(ctx, authorizer, session, scope, resource, permission) } diff --git a/internal/api/controller/execution/controller.go b/internal/api/controller/execution/controller.go index a6801f361..00753c52a 100644 --- a/internal/api/controller/execution/controller.go +++ b/internal/api/controller/execution/controller.go @@ -15,25 +15,25 @@ type Controller struct { db *sqlx.DB authorizer authz.Authorizer executionStore store.ExecutionStore + repoStore store.RepoStore stageStore store.StageStore pipelineStore store.PipelineStore - spaceStore store.SpaceStore } func NewController( db *sqlx.DB, authorizer authz.Authorizer, executionStore store.ExecutionStore, + repoStore store.RepoStore, stageStore store.StageStore, pipelineStore store.PipelineStore, - spaceStore store.SpaceStore, ) *Controller { return &Controller{ db: db, authorizer: authorizer, executionStore: executionStore, + repoStore: repoStore, stageStore: stageStore, pipelineStore: pipelineStore, - spaceStore: spaceStore, } } diff --git a/internal/api/controller/execution/create.go b/internal/api/controller/execution/create.go index a32a738f7..662105c87 100644 --- a/internal/api/controller/execution/create.go +++ b/internal/api/controller/execution/create.go @@ -23,25 +23,25 @@ type CreateInput struct { func (c *Controller) Create( ctx context.Context, session *auth.Session, - spaceRef string, - uid string, + repoRef string, + pipelineUID string, in *CreateInput, ) (*types.Execution, error) { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, fmt.Errorf("failed to find space: %w", err) + return nil, fmt.Errorf("failed to find repo by ref: %w", err) } - - pipeline, err := c.pipelineStore.FindByUID(ctx, space.ID, uid) - if err != nil { - return nil, fmt.Errorf("failed to find pipeline: %w", err) - } - - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, pipeline.UID, enum.PermissionPipelineExecute) + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, + pipelineUID, enum.PermissionPipelineExecute) if err != nil { return nil, fmt.Errorf("failed to authorize: %w", err) } + pipeline, err := c.pipelineStore.FindByUID(ctx, repo.ID, pipelineUID) + if err != nil { + return nil, fmt.Errorf("failed to find pipeline: %w", err) + } + pipeline, err = c.pipelineStore.IncrementSeqNum(ctx, pipeline) if err != nil { return nil, fmt.Errorf("failed to increment sequence number: %w", err) diff --git a/internal/api/controller/execution/delete.go b/internal/api/controller/execution/delete.go index 2b4c808dd..a12916db4 100644 --- a/internal/api/controller/execution/delete.go +++ b/internal/api/controller/execution/delete.go @@ -16,23 +16,23 @@ import ( func (c *Controller) Delete( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, pipelineUID string, executionNum int64, ) error { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return fmt.Errorf("failed to find parent space: %w", err) + return fmt.Errorf("failed to find repo by ref: %w", err) + } + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, pipelineUID, enum.PermissionPipelineDelete) + if err != nil { + return fmt.Errorf("failed to authorize: %w", err) } - pipeline, err := c.pipelineStore.FindByUID(ctx, space.ID, pipelineUID) + pipeline, err := c.pipelineStore.FindByUID(ctx, repo.ID, pipelineUID) if err != nil { return fmt.Errorf("failed to find pipeline: %w", err) } - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, pipeline.UID, enum.PermissionPipelineDelete) - if err != nil { - return fmt.Errorf("could not authorize: %w", err) - } err = c.executionStore.Delete(ctx, pipeline.ID, executionNum) if err != nil { return fmt.Errorf("could not delete execution: %w", err) diff --git a/internal/api/controller/execution/find.go b/internal/api/controller/execution/find.go index cdd464f48..686c2c1f9 100644 --- a/internal/api/controller/execution/find.go +++ b/internal/api/controller/execution/find.go @@ -17,25 +17,23 @@ import ( func (c *Controller) Find( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, pipelineUID string, executionNum int64, ) (*types.Execution, error) { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, fmt.Errorf("failed to find parent space: %w", err) + return nil, fmt.Errorf("failed to find repo by ref: %w", err) + } + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, pipelineUID, enum.PermissionPipelineView) + if err != nil { + return nil, fmt.Errorf("failed to authorize: %w", err) } - pipeline, err := c.pipelineStore.FindByUID(ctx, space.ID, pipelineUID) + pipeline, err := c.pipelineStore.FindByUID(ctx, repo.ID, pipelineUID) if err != nil { return nil, fmt.Errorf("failed to find pipeline: %w", err) } - - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, pipeline.UID, enum.PermissionPipelineView) - if err != nil { - return nil, fmt.Errorf("could not authorize: %w", err) - } - execution, err := c.executionStore.Find(ctx, pipeline.ID, executionNum) if err != nil { return nil, fmt.Errorf("failed to find execution %d: %w", executionNum, err) diff --git a/internal/api/controller/execution/list.go b/internal/api/controller/execution/list.go index a5ba72f6b..47f1e7b0d 100644 --- a/internal/api/controller/execution/list.go +++ b/internal/api/controller/execution/list.go @@ -17,24 +17,25 @@ import ( func (c *Controller) List( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, pipelineUID string, pagination types.Pagination, ) ([]*types.Execution, int64, error) { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, 0, fmt.Errorf("failed to find parent space: %w", err) - } - pipeline, err := c.pipelineStore.FindByUID(ctx, space.ID, pipelineUID) - if err != nil { - return nil, 0, fmt.Errorf("failed to find pipeline: %w", err) + return nil, 0, fmt.Errorf("failed to find repo by ref: %w", err) } - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, pipeline.UID, enum.PermissionPipelineView) + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, pipelineUID, enum.PermissionPipelineView) if err != nil { return nil, 0, fmt.Errorf("failed to authorize: %w", err) } + pipeline, err := c.pipelineStore.FindByUID(ctx, repo.ID, pipelineUID) + if err != nil { + return nil, 0, fmt.Errorf("failed to find pipeline: %w", err) + } + var count int64 var executions []*types.Execution diff --git a/internal/api/controller/execution/update.go b/internal/api/controller/execution/update.go index 7e2e6b6e8..7c2184b0a 100644 --- a/internal/api/controller/execution/update.go +++ b/internal/api/controller/execution/update.go @@ -21,21 +21,21 @@ type UpdateInput struct { func (c *Controller) Update( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, pipelineUID string, executionNum int64, in *UpdateInput) (*types.Execution, error) { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, fmt.Errorf("failed to find space: %w", err) + return nil, fmt.Errorf("failed to find repo by ref: %w", err) } - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, pipelineUID, enum.PermissionPipelineEdit) + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, pipelineUID, enum.PermissionPipelineEdit) if err != nil { - return nil, fmt.Errorf("failed to check auth: %w", err) + return nil, fmt.Errorf("failed to authorize: %w", err) } - pipeline, err := c.pipelineStore.FindByUID(ctx, space.ID, pipelineUID) + pipeline, err := c.pipelineStore.FindByUID(ctx, repo.ID, pipelineUID) if err != nil { return nil, fmt.Errorf("failed to find pipeline: %w", err) } diff --git a/internal/api/controller/execution/wire.go b/internal/api/controller/execution/wire.go index c85fd0ee2..29d6449ea 100644 --- a/internal/api/controller/execution/wire.go +++ b/internal/api/controller/execution/wire.go @@ -20,10 +20,10 @@ var WireSet = wire.NewSet( func ProvideController(db *sqlx.DB, authorizer authz.Authorizer, executionStore store.ExecutionStore, + repoStore store.RepoStore, stageStore store.StageStore, pipelineStore store.PipelineStore, - spaceStore store.SpaceStore, ) *Controller { - return NewController(db, authorizer, executionStore, stageStore, - pipelineStore, spaceStore) + return NewController(db, authorizer, executionStore, repoStore, stageStore, + pipelineStore) } diff --git a/internal/api/controller/logs/controller.go b/internal/api/controller/logs/controller.go index 273909c73..6a6d8f3b4 100644 --- a/internal/api/controller/logs/controller.go +++ b/internal/api/controller/logs/controller.go @@ -16,34 +16,34 @@ type Controller struct { db *sqlx.DB authorizer authz.Authorizer executionStore store.ExecutionStore + repoStore store.RepoStore pipelineStore store.PipelineStore stageStore store.StageStore stepStore store.StepStore logStore store.LogStore logStream livelog.LogStream - spaceStore store.SpaceStore } func NewController( db *sqlx.DB, authorizer authz.Authorizer, executionStore store.ExecutionStore, + repoStore store.RepoStore, pipelineStore store.PipelineStore, stageStore store.StageStore, stepStore store.StepStore, logStore store.LogStore, logStream livelog.LogStream, - spaceStore store.SpaceStore, ) *Controller { return &Controller{ db: db, authorizer: authorizer, executionStore: executionStore, + repoStore: repoStore, pipelineStore: pipelineStore, stageStore: stageStore, stepStore: stepStore, logStore: logStore, logStream: logStream, - spaceStore: spaceStore, } } diff --git a/internal/api/controller/logs/find.go b/internal/api/controller/logs/find.go index 06d92dfe9..3ff681bf3 100644 --- a/internal/api/controller/logs/find.go +++ b/internal/api/controller/logs/find.go @@ -17,27 +17,26 @@ import ( func (c *Controller) Find( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, pipelineUID string, executionNum int64, stageNum int, stepNum int, ) (io.ReadCloser, error) { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, fmt.Errorf("failed to find parent space: %w", err) + return nil, fmt.Errorf("failed to find repo by ref: %w", err) + } + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, pipelineUID, enum.PermissionPipelineView) + if err != nil { + return nil, fmt.Errorf("failed to authorize pipeline: %w", err) } - pipeline, err := c.pipelineStore.FindByUID(ctx, space.ID, pipelineUID) + pipeline, err := c.pipelineStore.FindByUID(ctx, repo.ID, pipelineUID) if err != nil { return nil, fmt.Errorf("failed to find pipeline: %w", err) } - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, pipeline.UID, enum.PermissionPipelineView) - if err != nil { - return nil, fmt.Errorf("could not authorize: %w", err) - } - execution, err := c.executionStore.Find(ctx, pipeline.ID, executionNum) if err != nil { return nil, fmt.Errorf("failed to find execution: %w", err) diff --git a/internal/api/controller/logs/tail.go b/internal/api/controller/logs/tail.go index 1cbcf45e0..2e2a37467 100644 --- a/internal/api/controller/logs/tail.go +++ b/internal/api/controller/logs/tail.go @@ -17,27 +17,25 @@ import ( func (c *Controller) Tail( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, pipelineUID string, executionNum int64, stageNum int, stepNum int, ) (<-chan *livelog.Line, <-chan error, error) { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, nil, fmt.Errorf("failed to find parent space: %w", err) + return nil, nil, fmt.Errorf("failed to find repo by ref: %w", err) } - - pipeline, err := c.pipelineStore.FindByUID(ctx, space.ID, pipelineUID) + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, pipelineUID, enum.PermissionPipelineView) + if err != nil { + return nil, nil, fmt.Errorf("failed to authorize pipeline: %w", err) + } + pipeline, err := c.pipelineStore.FindByUID(ctx, repo.ID, pipelineUID) if err != nil { return nil, nil, fmt.Errorf("failed to find pipeline: %w", err) } - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, pipeline.UID, enum.PermissionPipelineView) - if err != nil { - return nil, nil, fmt.Errorf("could not authorize: %w", err) - } - execution, err := c.executionStore.Find(ctx, pipeline.ID, executionNum) if err != nil { return nil, nil, fmt.Errorf("failed to find execution: %w", err) diff --git a/internal/api/controller/logs/wire.go b/internal/api/controller/logs/wire.go index 3217dd1e3..21ec30db1 100644 --- a/internal/api/controller/logs/wire.go +++ b/internal/api/controller/logs/wire.go @@ -21,13 +21,13 @@ var WireSet = wire.NewSet( func ProvideController(db *sqlx.DB, authorizer authz.Authorizer, executionStore store.ExecutionStore, + repoStore store.RepoStore, pipelineStore store.PipelineStore, stageStore store.StageStore, stepStore store.StepStore, logStore store.LogStore, logStream livelog.LogStream, - spaceStore store.SpaceStore, ) *Controller { - return NewController(db, authorizer, executionStore, - pipelineStore, stageStore, stepStore, logStore, logStream, spaceStore) + return NewController(db, authorizer, executionStore, repoStore, + pipelineStore, stageStore, stepStore, logStore, logStream) } diff --git a/internal/api/controller/pipeline/controller.go b/internal/api/controller/pipeline/controller.go index 61020c78a..5168d28d3 100644 --- a/internal/api/controller/pipeline/controller.go +++ b/internal/api/controller/pipeline/controller.go @@ -20,7 +20,6 @@ type Controller struct { repoStore store.RepoStore authorizer authz.Authorizer pipelineStore store.PipelineStore - spaceStore store.SpaceStore } func NewController( @@ -30,7 +29,6 @@ func NewController( pathStore store.PathStore, repoStore store.RepoStore, pipelineStore store.PipelineStore, - spaceStore store.SpaceStore, ) *Controller { return &Controller{ db: db, @@ -39,6 +37,5 @@ func NewController( repoStore: repoStore, authorizer: authorizer, pipelineStore: pipelineStore, - spaceStore: spaceStore, } } diff --git a/internal/api/controller/pipeline/create.go b/internal/api/controller/pipeline/create.go index 2de13b205..4405b0037 100644 --- a/internal/api/controller/pipeline/create.go +++ b/internal/api/controller/pipeline/create.go @@ -7,7 +7,6 @@ package pipeline import ( "context" "fmt" - "strconv" "strings" "time" @@ -26,34 +25,26 @@ var ( ) type CreateInput struct { - Description string `json:"description"` - SpaceRef string `json:"space_ref"` - UID string `json:"uid"` - RepoRef string `json:"repo_ref"` // empty if repo_type != gitness - RepoType enum.ScmType `json:"repo_type"` - DefaultBranch string `json:"default_branch"` - ConfigPath string `json:"config_path"` + Description string `json:"description"` + UID string `json:"uid"` + DefaultBranch string `json:"default_branch"` + ConfigPath string `json:"config_path"` } -func (c *Controller) Create(ctx context.Context, session *auth.Session, in *CreateInput) (*types.Pipeline, error) { - parentSpace, err := c.spaceStore.FindByRef(ctx, in.SpaceRef) +func (c *Controller) Create( + ctx context.Context, + session *auth.Session, + repoRef string, + in *CreateInput, +) (*types.Pipeline, error) { + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, fmt.Errorf("failed to find parent by ref: %w", err) + return nil, fmt.Errorf("failed to find repo by ref: %w", err) } - err = apiauth.CheckPipeline(ctx, c.authorizer, session, parentSpace.Path, in.UID, enum.PermissionPipelineEdit) + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, "", enum.PermissionPipelineEdit) if err != nil { - return nil, err - } - - var repoID int64 - - if in.RepoType == enum.ScmTypeGitness { - repo, err := c.repoStore.FindByRef(ctx, in.RepoRef) - if err != nil { - return nil, fmt.Errorf("failed to find repo by ref: %w", err) - } - repoID = repo.ID + return nil, fmt.Errorf("failed to authorize pipeline: %w", err) } if err := c.sanitizeCreateInput(in); err != nil { @@ -64,11 +55,9 @@ func (c *Controller) Create(ctx context.Context, session *auth.Session, in *Crea now := time.Now().UnixMilli() pipeline = &types.Pipeline{ Description: in.Description, - SpaceID: parentSpace.ID, + RepoID: repo.ID, UID: in.UID, Seq: 0, - RepoID: repoID, - RepoType: in.RepoType, DefaultBranch: in.DefaultBranch, ConfigPath: in.ConfigPath, Created: now, @@ -84,11 +73,6 @@ func (c *Controller) Create(ctx context.Context, session *auth.Session, in *Crea } func (c *Controller) sanitizeCreateInput(in *CreateInput) error { - parentRefAsID, err := strconv.ParseInt(in.SpaceRef, 10, 64) - if (err == nil && parentRefAsID <= 0) || (len(strings.TrimSpace(in.SpaceRef)) == 0) { - return errPipelineRequiresParent - } - if err := c.uidCheck(in.UID, false); err != nil { return err } diff --git a/internal/api/controller/pipeline/delete.go b/internal/api/controller/pipeline/delete.go index 92eba72ac..5831ce296 100644 --- a/internal/api/controller/pipeline/delete.go +++ b/internal/api/controller/pipeline/delete.go @@ -13,17 +13,18 @@ import ( "github.com/harness/gitness/types/enum" ) -func (c *Controller) Delete(ctx context.Context, session *auth.Session, spaceRef string, uid string) error { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) +func (c *Controller) Delete(ctx context.Context, session *auth.Session, repoRef string, uid string) error { + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return fmt.Errorf("failed to find parent space: %w", err) + return fmt.Errorf("failed to find repo by ref: %w", err) } - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, uid, enum.PermissionPipelineDelete) + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, uid, enum.PermissionPipelineDelete) if err != nil { - return fmt.Errorf("could not authorize: %w", err) + return fmt.Errorf("failed to authorize pipeline: %w", err) } - err = c.pipelineStore.DeleteByUID(ctx, space.ID, uid) + + err = c.pipelineStore.DeleteByUID(ctx, repo.ID, uid) if err != nil { return fmt.Errorf("could not delete pipeline: %w", err) } diff --git a/internal/api/controller/pipeline/find.go b/internal/api/controller/pipeline/find.go index f132227b9..70d74defe 100644 --- a/internal/api/controller/pipeline/find.go +++ b/internal/api/controller/pipeline/find.go @@ -17,16 +17,16 @@ import ( func (c *Controller) Find( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, uid string, ) (*types.Pipeline, error) { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, fmt.Errorf("failed to find parent space: %w", err) + return nil, fmt.Errorf("failed to find repo by ref: %w", err) } - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, uid, enum.PermissionPipelineView) + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, uid, enum.PermissionPipelineView) if err != nil { - return nil, fmt.Errorf("could not authorize: %w", err) + return nil, fmt.Errorf("failed to authorize pipeline: %w", err) } - return c.pipelineStore.FindByUID(ctx, space.ID, uid) + return c.pipelineStore.FindByUID(ctx, repo.ID, uid) } diff --git a/internal/api/controller/pipeline/update.go b/internal/api/controller/pipeline/update.go index ef77518b3..cc9182346 100644 --- a/internal/api/controller/pipeline/update.go +++ b/internal/api/controller/pipeline/update.go @@ -23,21 +23,20 @@ type UpdateInput struct { func (c *Controller) Update( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, uid string, in *UpdateInput, ) (*types.Pipeline, error) { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, fmt.Errorf("failed to find parent space: %w", err) + return nil, fmt.Errorf("failed to find repo by ref: %w", err) + } + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, uid, enum.PermissionPipelineEdit) + if err != nil { + return nil, fmt.Errorf("failed to authorize pipeline: %w", err) } - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, uid, enum.PermissionPipelineEdit) - if err != nil { - return nil, fmt.Errorf("could not authorize: %w", err) - } - - pipeline, err := c.pipelineStore.FindByUID(ctx, space.ID, uid) + pipeline, err := c.pipelineStore.FindByUID(ctx, repo.ID, uid) if err != nil { return nil, fmt.Errorf("failed to find pipeline: %w", err) } diff --git a/internal/api/controller/pipeline/wire.go b/internal/api/controller/pipeline/wire.go index d665a8ee6..6dfcd0fc0 100644 --- a/internal/api/controller/pipeline/wire.go +++ b/internal/api/controller/pipeline/wire.go @@ -24,7 +24,6 @@ func ProvideController(db *sqlx.DB, repoStore store.RepoStore, authorizer authz.Authorizer, pipelineStore store.PipelineStore, - spaceStore store.SpaceStore, ) *Controller { - return NewController(db, uidCheck, authorizer, pathStore, repoStore, pipelineStore, spaceStore) + return NewController(db, uidCheck, authorizer, pathStore, repoStore, pipelineStore) } diff --git a/internal/api/controller/repo/controller.go b/internal/api/controller/repo/controller.go index 1c0357de5..6bae1d018 100644 --- a/internal/api/controller/repo/controller.go +++ b/internal/api/controller/repo/controller.go @@ -29,6 +29,7 @@ type Controller struct { pathStore store.PathStore repoStore store.RepoStore spaceStore store.SpaceStore + pipelineStore store.PipelineStore principalStore store.PrincipalStore gitRPCClient gitrpc.Interface } @@ -42,6 +43,7 @@ func NewController( pathStore store.PathStore, repoStore store.RepoStore, spaceStore store.SpaceStore, + pipelineStore store.PipelineStore, principalStore store.PrincipalStore, gitRPCClient gitrpc.Interface, ) *Controller { @@ -54,6 +56,7 @@ func NewController( pathStore: pathStore, repoStore: repoStore, spaceStore: spaceStore, + pipelineStore: pipelineStore, principalStore: principalStore, gitRPCClient: gitRPCClient, } diff --git a/internal/api/controller/space/list_pipelines.go b/internal/api/controller/repo/list_pipelines.go similarity index 69% rename from internal/api/controller/space/list_pipelines.go rename to internal/api/controller/repo/list_pipelines.go index 87d999bb4..6f8feff73 100644 --- a/internal/api/controller/space/list_pipelines.go +++ b/internal/api/controller/repo/list_pipelines.go @@ -1,7 +1,7 @@ // Copyright 2022 Harness Inc. All rights reserved. // Use of this source code is governed by the Polyform Free Trial License // that can be found in the LICENSE.md file for this repository. -package space +package repo import ( "context" @@ -14,33 +14,33 @@ import ( "github.com/harness/gitness/types/enum" ) -// ListPipelines lists the pipelines in a space. +// ListPipelines lists the pipelines under a repository. func (c *Controller) ListPipelines( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, filter types.ListQueryFilter, ) ([]*types.Pipeline, int64, error) { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, 0, fmt.Errorf("failed to find parent space: %w", err) + return nil, 0, fmt.Errorf("failed to find repo: %w", err) } - err = apiauth.CheckSpace(ctx, c.authorizer, session, space, enum.PermissionPipelineView, false) + err = apiauth.CheckRepo(ctx, c.authorizer, session, repo, enum.PermissionPipelineView, false) if err != nil { - return nil, 0, fmt.Errorf("could not authorize: %w", err) + return nil, 0, fmt.Errorf("failed to authorize: %w", err) } var count int64 var pipelines []*types.Pipeline err = dbtx.New(c.db).WithTx(ctx, func(ctx context.Context) (err error) { - count, err = c.pipelineStore.Count(ctx, space.ID, filter) + count, err = c.pipelineStore.Count(ctx, repo.ID, filter) if err != nil { return fmt.Errorf("failed to count child executions: %w", err) } - pipelines, err = c.pipelineStore.List(ctx, space.ID, filter) + pipelines, err = c.pipelineStore.List(ctx, repo.ID, filter) if err != nil { return fmt.Errorf("failed to count child executions: %w", err) } diff --git a/internal/api/controller/repo/wire.go b/internal/api/controller/repo/wire.go index c642348e3..fba02dba7 100644 --- a/internal/api/controller/repo/wire.go +++ b/internal/api/controller/repo/wire.go @@ -23,7 +23,8 @@ var WireSet = wire.NewSet( func ProvideController(config *types.Config, db *sqlx.DB, urlProvider *url.Provider, uidCheck check.PathUID, authorizer authz.Authorizer, pathStore store.PathStore, repoStore store.RepoStore, - spaceStore store.SpaceStore, principalStore store.PrincipalStore, rpcClient gitrpc.Interface) *Controller { + spaceStore store.SpaceStore, pipelineStore store.PipelineStore, + principalStore store.PrincipalStore, rpcClient gitrpc.Interface) *Controller { return NewController(config.Git.DefaultBranch, db, urlProvider, uidCheck, - authorizer, pathStore, repoStore, spaceStore, principalStore, rpcClient) + authorizer, pathStore, repoStore, spaceStore, pipelineStore, principalStore, rpcClient) } diff --git a/internal/api/controller/trigger/controller.go b/internal/api/controller/trigger/controller.go index 3e0076037..304974bbc 100644 --- a/internal/api/controller/trigger/controller.go +++ b/internal/api/controller/trigger/controller.go @@ -16,7 +16,7 @@ type Controller struct { authorizer authz.Authorizer triggerStore store.TriggerStore pipelineStore store.PipelineStore - spaceStore store.SpaceStore + repoStore store.RepoStore } func NewController( @@ -24,13 +24,13 @@ func NewController( authorizer authz.Authorizer, triggerStore store.TriggerStore, pipelineStore store.PipelineStore, - spaceStore store.SpaceStore, + repoStore store.RepoStore, ) *Controller { return &Controller{ db: db, authorizer: authorizer, triggerStore: triggerStore, pipelineStore: pipelineStore, - spaceStore: spaceStore, + repoStore: repoStore, } } diff --git a/internal/api/controller/trigger/create.go b/internal/api/controller/trigger/create.go index 2bb847e01..8d95174a5 100644 --- a/internal/api/controller/trigger/create.go +++ b/internal/api/controller/trigger/create.go @@ -24,25 +24,24 @@ type CreateInput struct { func (c *Controller) Create( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, pipelineUID string, in *CreateInput, ) (*types.Trigger, error) { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, fmt.Errorf("failed to find space: %w", err) + return nil, fmt.Errorf("failed to find repo by ref: %w", err) } - - pipeline, err := c.pipelineStore.FindByUID(ctx, space.ID, pipelineUID) - if err != nil { - return nil, fmt.Errorf("failed to find pipeline: %w", err) - } - // Trigger permissions are associated with pipeline permissions. If a user has permissions // to edit the pipeline, they will have permissions to create a trigger as well. - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, pipeline.UID, enum.PermissionPipelineEdit) + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, pipelineUID, enum.PermissionPipelineEdit) if err != nil { - return nil, fmt.Errorf("failed to authorize: %w", err) + return nil, fmt.Errorf("failed to authorize pipeline: %w", err) + } + + pipeline, err := c.pipelineStore.FindByUID(ctx, repo.ID, pipelineUID) + if err != nil { + return nil, fmt.Errorf("failed to find pipeline: %w", err) } now := time.Now().UnixMilli() diff --git a/internal/api/controller/trigger/delete.go b/internal/api/controller/trigger/delete.go index 18e1ce147..d0355d5c1 100644 --- a/internal/api/controller/trigger/delete.go +++ b/internal/api/controller/trigger/delete.go @@ -16,26 +16,26 @@ import ( func (c *Controller) Delete( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, pipelineUID string, triggerUID string, ) error { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return fmt.Errorf("failed to find parent space: %w", err) + return fmt.Errorf("failed to find repo by ref: %w", err) + } + // Trigger permissions are associated with pipeline permissions. If a user has permissions + // to edit the pipeline, they will have permissions to remove a trigger as well. + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, pipelineUID, enum.PermissionPipelineEdit) + if err != nil { + return fmt.Errorf("failed to authorize pipeline: %w", err) } - pipeline, err := c.pipelineStore.FindByUID(ctx, space.ID, pipelineUID) + pipeline, err := c.pipelineStore.FindByUID(ctx, repo.ID, pipelineUID) if err != nil { return fmt.Errorf("failed to find pipeline: %w", err) } - // Trigger permissions are associated with pipeline permissions. If a user has permissions - // to delete the pipeline, they will have permissions to remove a trigger as well. - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, pipeline.UID, enum.PermissionPipelineEdit) - if err != nil { - return fmt.Errorf("could not authorize: %w", err) - } err = c.triggerStore.DeleteByUID(ctx, pipeline.ID, triggerUID) if err != nil { return fmt.Errorf("could not delete trigger: %w", err) diff --git a/internal/api/controller/trigger/find.go b/internal/api/controller/trigger/find.go index 908793bcd..3c805e35f 100644 --- a/internal/api/controller/trigger/find.go +++ b/internal/api/controller/trigger/find.go @@ -17,25 +17,24 @@ import ( func (c *Controller) Find( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, pipelineUID string, triggerUID string, ) (*types.Trigger, error) { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, fmt.Errorf("failed to find parent space: %w", err) + return nil, fmt.Errorf("failed to find repo by ref: %w", err) + } + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, pipelineUID, enum.PermissionPipelineView) + if err != nil { + return nil, fmt.Errorf("failed to authorize pipeline: %w", err) } - pipeline, err := c.pipelineStore.FindByUID(ctx, space.ID, pipelineUID) + pipeline, err := c.pipelineStore.FindByUID(ctx, repo.ID, pipelineUID) if err != nil { return nil, fmt.Errorf("failed to find pipeline: %w", err) } - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, pipeline.UID, enum.PermissionPipelineView) - if err != nil { - return nil, fmt.Errorf("could not authorize: %w", err) - } - trigger, err := c.triggerStore.FindByUID(ctx, pipeline.ID, triggerUID) if err != nil { return nil, fmt.Errorf("failed to find trigger %s: %w", triggerUID, err) diff --git a/internal/api/controller/trigger/list.go b/internal/api/controller/trigger/list.go index 753421221..868198b2b 100644 --- a/internal/api/controller/trigger/list.go +++ b/internal/api/controller/trigger/list.go @@ -16,22 +16,24 @@ import ( func (c *Controller) List( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, pipelineUID string, filter types.ListQueryFilter, ) ([]*types.Trigger, int64, error) { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, 0, fmt.Errorf("failed to find parent space: %w", err) + return nil, 0, fmt.Errorf("failed to find repo by ref: %w", err) } - pipeline, err := c.pipelineStore.FindByUID(ctx, space.ID, pipelineUID) + // Trigger permissions are associated with pipeline permissions. If a user has permissions + // to view the pipeline, they will have permissions to list triggers as well. + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, pipelineUID, enum.PermissionPipelineView) if err != nil { - return nil, 0, fmt.Errorf("failed to find pipeline: %w", err) + return nil, 0, fmt.Errorf("failed to authorize pipeline: %w", err) } - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, pipeline.UID, enum.PermissionPipelineView) + pipeline, err := c.pipelineStore.FindByUID(ctx, repo.ID, pipelineUID) if err != nil { - return nil, 0, fmt.Errorf("failed to authorize: %w", err) + return nil, 0, fmt.Errorf("failed to find pipeline: %w", err) } count, err := c.triggerStore.Count(ctx, pipeline.ID, filter) diff --git a/internal/api/controller/trigger/update.go b/internal/api/controller/trigger/update.go index d6aa64776..adef2f668 100644 --- a/internal/api/controller/trigger/update.go +++ b/internal/api/controller/trigger/update.go @@ -23,21 +23,22 @@ type UpdateInput struct { func (c *Controller) Update( ctx context.Context, session *auth.Session, - spaceRef string, + repoRef string, pipelineUID string, triggerUID string, in *UpdateInput) (*types.Trigger, error) { - space, err := c.spaceStore.FindByRef(ctx, spaceRef) + repo, err := c.repoStore.FindByRef(ctx, repoRef) if err != nil { - return nil, fmt.Errorf("failed to find space: %w", err) + return nil, fmt.Errorf("failed to find repo by ref: %w", err) + } + // Trigger permissions are associated with pipeline permissions. If a user has permissions + // to edit the pipeline, they will have permissions to edit the trigger as well. + err = apiauth.CheckPipeline(ctx, c.authorizer, session, repo.Path, pipelineUID, enum.PermissionPipelineEdit) + if err != nil { + return nil, fmt.Errorf("failed to authorize pipeline: %w", err) } - err = apiauth.CheckPipeline(ctx, c.authorizer, session, space.Path, pipelineUID, enum.PermissionPipelineEdit) - if err != nil { - return nil, fmt.Errorf("failed to check auth: %w", err) - } - - pipeline, err := c.pipelineStore.FindByUID(ctx, space.ID, pipelineUID) + pipeline, err := c.pipelineStore.FindByUID(ctx, repo.ID, pipelineUID) if err != nil { return nil, fmt.Errorf("failed to find pipeline: %w", err) } diff --git a/internal/api/controller/trigger/wire.go b/internal/api/controller/trigger/wire.go index 0d69575f1..8fb3ab6f7 100644 --- a/internal/api/controller/trigger/wire.go +++ b/internal/api/controller/trigger/wire.go @@ -21,7 +21,7 @@ func ProvideController(db *sqlx.DB, authorizer authz.Authorizer, triggerStore store.TriggerStore, pipelineStore store.PipelineStore, - spaceStore store.SpaceStore, + repoStore store.RepoStore, ) *Controller { - return NewController(db, authorizer, triggerStore, pipelineStore, spaceStore) + return NewController(db, authorizer, triggerStore, pipelineStore, repoStore) } diff --git a/internal/api/handler/execution/create.go b/internal/api/handler/execution/create.go index 97366148e..348972237 100644 --- a/internal/api/handler/execution/create.go +++ b/internal/api/handler/execution/create.go @@ -11,19 +11,18 @@ import ( "github.com/harness/gitness/internal/api/controller/execution" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleCreate(executionCtrl *execution.Controller) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return @@ -36,7 +35,7 @@ func HandleCreate(executionCtrl *execution.Controller) http.HandlerFunc { return } - execution, err := executionCtrl.Create(ctx, session, spaceRef, pipelineUID, in) + execution, err := executionCtrl.Create(ctx, session, repoRef, pipelineUID, in) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/execution/delete.go b/internal/api/handler/execution/delete.go index 77ee63e2f..164c24110 100644 --- a/internal/api/handler/execution/delete.go +++ b/internal/api/handler/execution/delete.go @@ -10,19 +10,18 @@ import ( "github.com/harness/gitness/internal/api/controller/execution" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleDelete(executionCtrl *execution.Controller) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return @@ -33,7 +32,7 @@ func HandleDelete(executionCtrl *execution.Controller) http.HandlerFunc { return } - err = executionCtrl.Delete(ctx, session, spaceRef, pipelineUID, n) + err = executionCtrl.Delete(ctx, session, repoRef, pipelineUID, n) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/execution/find.go b/internal/api/handler/execution/find.go index 9a4bc4c49..124da3ccc 100644 --- a/internal/api/handler/execution/find.go +++ b/internal/api/handler/execution/find.go @@ -10,14 +10,13 @@ import ( "github.com/harness/gitness/internal/api/controller/execution" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleFind(executionCtrl *execution.Controller) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return @@ -27,13 +26,13 @@ func HandleFind(executionCtrl *execution.Controller) http.HandlerFunc { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - execution, err := executionCtrl.Find(ctx, session, spaceRef, pipelineUID, n) + execution, err := executionCtrl.Find(ctx, session, repoRef, pipelineUID, n) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/execution/list.go b/internal/api/handler/execution/list.go index eb590f239..b69c9886a 100644 --- a/internal/api/handler/execution/list.go +++ b/internal/api/handler/execution/list.go @@ -10,19 +10,18 @@ import ( "github.com/harness/gitness/internal/api/controller/execution" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleList(executionCtrl *execution.Controller) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return @@ -30,7 +29,7 @@ func HandleList(executionCtrl *execution.Controller) http.HandlerFunc { pagination := request.ParsePaginationFromRequest(r) - repos, totalCount, err := executionCtrl.List(ctx, session, spaceRef, pipelineUID, pagination) + repos, totalCount, err := executionCtrl.List(ctx, session, repoRef, pipelineUID, pagination) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/execution/update.go b/internal/api/handler/execution/update.go index 14fdf18f9..5709bf21d 100644 --- a/internal/api/handler/execution/update.go +++ b/internal/api/handler/execution/update.go @@ -11,7 +11,6 @@ import ( "github.com/harness/gitness/internal/api/controller/execution" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleUpdate(executionCtrl *execution.Controller) http.HandlerFunc { @@ -26,12 +25,12 @@ func HandleUpdate(executionCtrl *execution.Controller) http.HandlerFunc { return } - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return @@ -42,7 +41,7 @@ func HandleUpdate(executionCtrl *execution.Controller) http.HandlerFunc { return } - pipeline, err := executionCtrl.Update(ctx, session, spaceRef, pipelineUID, n, in) + pipeline, err := executionCtrl.Update(ctx, session, repoRef, pipelineUID, n, in) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/logs/find.go b/internal/api/handler/logs/find.go index fb0832a84..b1e7b469c 100644 --- a/internal/api/handler/logs/find.go +++ b/internal/api/handler/logs/find.go @@ -11,14 +11,18 @@ import ( "github.com/harness/gitness/internal/api/controller/logs" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleFind(logCtrl *logs.Controller) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) - pipelineRef, err := request.GetPipelineRefFromPath(r) + repoRef, err := request.GetRepoRefFromPath(r) + if err != nil { + render.TranslatedUserError(w, err) + return + } + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return @@ -38,14 +42,8 @@ func HandleFind(logCtrl *logs.Controller) http.HandlerFunc { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) - if err != nil { - render.TranslatedUserError(w, err) - return - } - rc, err := logCtrl.Find( - ctx, session, spaceRef, pipelineUID, + ctx, session, repoRef, pipelineUID, executionNum, int(stageNum), int(stepNum)) if err != nil { render.TranslatedUserError(w, err) diff --git a/internal/api/handler/logs/tail.go b/internal/api/handler/logs/tail.go index 122eb2379..b611d0ad4 100644 --- a/internal/api/handler/logs/tail.go +++ b/internal/api/handler/logs/tail.go @@ -14,7 +14,6 @@ import ( "github.com/harness/gitness/internal/api/controller/logs" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" "github.com/rs/zerolog/log" ) @@ -28,7 +27,7 @@ func HandleTail(logCtrl *logs.Controller) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return @@ -48,7 +47,7 @@ func HandleTail(logCtrl *logs.Controller) http.HandlerFunc { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return @@ -65,7 +64,7 @@ func HandleTail(logCtrl *logs.Controller) http.HandlerFunc { f.Flush() linec, errc, err := logCtrl.Tail( - ctx, session, spaceRef, pipelineUID, + ctx, session, repoRef, pipelineUID, executionNum, int(stageNum), int(stepNum)) if err != nil { render.TranslatedUserError(w, err) diff --git a/internal/api/handler/pipeline/create.go b/internal/api/handler/pipeline/create.go index df1f49a9c..9018512cd 100644 --- a/internal/api/handler/pipeline/create.go +++ b/internal/api/handler/pipeline/create.go @@ -18,14 +18,20 @@ func HandleCreate(pipelineCtrl *pipeline.Controller) http.HandlerFunc { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) + repoRef, err := request.GetRepoRefFromPath(r) + if err != nil { + render.TranslatedUserError(w, err) + return + } + in := new(pipeline.CreateInput) - err := json.NewDecoder(r.Body).Decode(in) + err = json.NewDecoder(r.Body).Decode(in) if err != nil { render.BadRequestf(w, "Invalid Request Body: %s.", err) return } - pipeline, err := pipelineCtrl.Create(ctx, session, in) + pipeline, err := pipelineCtrl.Create(ctx, session, repoRef, in) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/pipeline/delete.go b/internal/api/handler/pipeline/delete.go index 1679df7a1..656e6f566 100644 --- a/internal/api/handler/pipeline/delete.go +++ b/internal/api/handler/pipeline/delete.go @@ -10,25 +10,24 @@ import ( "github.com/harness/gitness/internal/api/controller/pipeline" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleDelete(pipelineCtrl *pipeline.Controller) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - err = pipelineCtrl.Delete(ctx, session, spaceRef, pipelineUID) + err = pipelineCtrl.Delete(ctx, session, repoRef, pipelineUID) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/pipeline/find.go b/internal/api/handler/pipeline/find.go index 74ee6c77d..f2b70948a 100644 --- a/internal/api/handler/pipeline/find.go +++ b/internal/api/handler/pipeline/find.go @@ -10,25 +10,24 @@ import ( "github.com/harness/gitness/internal/api/controller/pipeline" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleFind(pipelineCtrl *pipeline.Controller) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - pipeline, err := pipelineCtrl.Find(ctx, session, spaceRef, pipelineUID) + pipeline, err := pipelineCtrl.Find(ctx, session, repoRef, pipelineUID) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/pipeline/update.go b/internal/api/handler/pipeline/update.go index 631ea4a77..05ed6ed61 100644 --- a/internal/api/handler/pipeline/update.go +++ b/internal/api/handler/pipeline/update.go @@ -11,7 +11,6 @@ import ( "github.com/harness/gitness/internal/api/controller/pipeline" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleUpdate(pipelineCtrl *pipeline.Controller) http.HandlerFunc { @@ -26,18 +25,18 @@ func HandleUpdate(pipelineCtrl *pipeline.Controller) http.HandlerFunc { return } - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - pipeline, err := pipelineCtrl.Update(ctx, session, spaceRef, pipelineUID, in) + pipeline, err := pipelineCtrl.Update(ctx, session, repoRef, pipelineUID, in) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/space/list_pipelines.go b/internal/api/handler/repo/list_pipelines.go similarity index 72% rename from internal/api/handler/space/list_pipelines.go rename to internal/api/handler/repo/list_pipelines.go index 30aba9b4b..2c81367c3 100644 --- a/internal/api/handler/space/list_pipelines.go +++ b/internal/api/handler/repo/list_pipelines.go @@ -2,28 +2,28 @@ // Use of this source code is governed by the Polyform Free Trial License // that can be found in the LICENSE.md file for this repository. -package space +package repo import ( "net/http" - "github.com/harness/gitness/internal/api/controller/space" + "github.com/harness/gitness/internal/api/controller/repo" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" ) -func HandleListPipelines(spaceCtrl *space.Controller) http.HandlerFunc { +func HandleListPipelines(repoCtrl *repo.Controller) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) - spaceRef, err := request.GetSpaceRefFromPath(r) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } filter := request.ParseListQueryFilterFromRequest(r) - repos, totalCount, err := spaceCtrl.ListPipelines(ctx, session, spaceRef, filter) + repos, totalCount, err := repoCtrl.ListPipelines(ctx, session, repoRef, filter) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/trigger/create.go b/internal/api/handler/trigger/create.go index 52d36c166..2caa51fbc 100644 --- a/internal/api/handler/trigger/create.go +++ b/internal/api/handler/trigger/create.go @@ -11,19 +11,18 @@ import ( "github.com/harness/gitness/internal/api/controller/trigger" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleCreate(triggerCtrl *trigger.Controller) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return @@ -36,7 +35,7 @@ func HandleCreate(triggerCtrl *trigger.Controller) http.HandlerFunc { return } - trigger, err := triggerCtrl.Create(ctx, session, spaceRef, pipelineUID, in) + trigger, err := triggerCtrl.Create(ctx, session, repoRef, pipelineUID, in) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/trigger/delete.go b/internal/api/handler/trigger/delete.go index 492624bbf..a83fba7bd 100644 --- a/internal/api/handler/trigger/delete.go +++ b/internal/api/handler/trigger/delete.go @@ -10,19 +10,18 @@ import ( "github.com/harness/gitness/internal/api/controller/trigger" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleDelete(triggerCtrl *trigger.Controller) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return @@ -33,7 +32,7 @@ func HandleDelete(triggerCtrl *trigger.Controller) http.HandlerFunc { return } - err = triggerCtrl.Delete(ctx, session, spaceRef, pipelineUID, triggerUID) + err = triggerCtrl.Delete(ctx, session, repoRef, pipelineUID, triggerUID) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/trigger/find.go b/internal/api/handler/trigger/find.go index f60714a78..6d1ae53c4 100644 --- a/internal/api/handler/trigger/find.go +++ b/internal/api/handler/trigger/find.go @@ -10,14 +10,13 @@ import ( "github.com/harness/gitness/internal/api/controller/trigger" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleFind(triggerCtrl *trigger.Controller) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return @@ -27,13 +26,13 @@ func HandleFind(triggerCtrl *trigger.Controller) http.HandlerFunc { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - trigger, err := triggerCtrl.Find(ctx, session, spaceRef, pipelineUID, triggerUID) + trigger, err := triggerCtrl.Find(ctx, session, repoRef, pipelineUID, triggerUID) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/trigger/list.go b/internal/api/handler/trigger/list.go index 615f83f25..268cb7037 100644 --- a/internal/api/handler/trigger/list.go +++ b/internal/api/handler/trigger/list.go @@ -10,19 +10,18 @@ import ( "github.com/harness/gitness/internal/api/controller/trigger" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleList(triggerCtrl *trigger.Controller) http.HandlerFunc { return func(w http.ResponseWriter, r *http.Request) { ctx := r.Context() session, _ := request.AuthSessionFrom(ctx) - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return @@ -30,7 +29,7 @@ func HandleList(triggerCtrl *trigger.Controller) http.HandlerFunc { filter := request.ParseListQueryFilterFromRequest(r) - repos, totalCount, err := triggerCtrl.List(ctx, session, spaceRef, pipelineUID, filter) + repos, totalCount, err := triggerCtrl.List(ctx, session, repoRef, pipelineUID, filter) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/handler/trigger/update.go b/internal/api/handler/trigger/update.go index 04d87c3d4..be63b6f63 100644 --- a/internal/api/handler/trigger/update.go +++ b/internal/api/handler/trigger/update.go @@ -11,7 +11,6 @@ import ( "github.com/harness/gitness/internal/api/controller/trigger" "github.com/harness/gitness/internal/api/render" "github.com/harness/gitness/internal/api/request" - "github.com/harness/gitness/internal/paths" ) func HandleUpdate(triggerCtrl *trigger.Controller) http.HandlerFunc { @@ -26,12 +25,12 @@ func HandleUpdate(triggerCtrl *trigger.Controller) http.HandlerFunc { return } - pipelineRef, err := request.GetPipelineRefFromPath(r) + pipelineUID, err := request.GetPipelineUIDFromPath(r) if err != nil { render.TranslatedUserError(w, err) return } - spaceRef, pipelineUID, err := paths.DisectLeaf(pipelineRef) + repoRef, err := request.GetRepoRefFromPath(r) if err != nil { render.TranslatedUserError(w, err) return @@ -42,7 +41,7 @@ func HandleUpdate(triggerCtrl *trigger.Controller) http.HandlerFunc { return } - pipeline, err := triggerCtrl.Update(ctx, session, spaceRef, pipelineUID, triggerUID, in) + pipeline, err := triggerCtrl.Update(ctx, session, repoRef, pipelineUID, triggerUID, in) if err != nil { render.TranslatedUserError(w, err) return diff --git a/internal/api/openapi/pipeline.go b/internal/api/openapi/pipeline.go index c618200f8..61d3b5af9 100644 --- a/internal/api/openapi/pipeline.go +++ b/internal/api/openapi/pipeline.go @@ -17,7 +17,8 @@ import ( ) type pipelineRequest struct { - Ref string `path:"pipeline_ref"` + repoRequest + Ref string `path:"pipeline_uid"` } type executionRequest struct { @@ -47,6 +48,7 @@ type createTriggerRequest struct { } type createPipelineRequest struct { + repoRequest pipeline.CreateInput } @@ -87,7 +89,19 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&opCreate, new(usererror.Error), http.StatusInternalServerError) _ = reflector.SetJSONResponse(&opCreate, new(usererror.Error), http.StatusUnauthorized) _ = reflector.SetJSONResponse(&opCreate, new(usererror.Error), http.StatusForbidden) - _ = reflector.Spec.AddOperation(http.MethodPost, "/pipelines", opCreate) + _ = reflector.Spec.AddOperation(http.MethodPost, "/repos/{repo_ref}/pipelines", opCreate) + + opPipelines := openapi3.Operation{} + opPipelines.WithTags("repos") + opPipelines.WithMapOfAnything(map[string]interface{}{"operationId": "listPipelines"}) + opPipelines.WithParameters(queryParameterQueryRepo, queryParameterPage, queryParameterLimit) + _ = reflector.SetRequest(&opPipelines, new(repoRequest), http.MethodGet) + _ = reflector.SetJSONResponse(&opPipelines, []types.Pipeline{}, http.StatusOK) + _ = reflector.SetJSONResponse(&opPipelines, new(usererror.Error), http.StatusInternalServerError) + _ = reflector.SetJSONResponse(&opPipelines, new(usererror.Error), http.StatusUnauthorized) + _ = reflector.SetJSONResponse(&opPipelines, new(usererror.Error), http.StatusForbidden) + _ = reflector.SetJSONResponse(&opPipelines, new(usererror.Error), http.StatusNotFound) + _ = reflector.Spec.AddOperation(http.MethodGet, "/repos/{repo_ref}/pipelines", opPipelines) opFind := openapi3.Operation{} opFind.WithTags("pipeline") @@ -98,7 +112,7 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&opFind, new(usererror.Error), http.StatusUnauthorized) _ = reflector.SetJSONResponse(&opFind, new(usererror.Error), http.StatusForbidden) _ = reflector.SetJSONResponse(&opFind, new(usererror.Error), http.StatusNotFound) - _ = reflector.Spec.AddOperation(http.MethodGet, "/pipelines/{pipeline_ref}", opFind) + _ = reflector.Spec.AddOperation(http.MethodGet, "/repos/{repo_ref}/pipelines/{pipeline_uid}", opFind) opDelete := openapi3.Operation{} opDelete.WithTags("pipeline") @@ -109,7 +123,7 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&opDelete, new(usererror.Error), http.StatusUnauthorized) _ = reflector.SetJSONResponse(&opDelete, new(usererror.Error), http.StatusForbidden) _ = reflector.SetJSONResponse(&opDelete, new(usererror.Error), http.StatusNotFound) - _ = reflector.Spec.AddOperation(http.MethodDelete, "/pipelines/{pipeline_ref}", opDelete) + _ = reflector.Spec.AddOperation(http.MethodDelete, "/repos/{repo_ref}/pipelines/{pipeline_uid}", opDelete) opUpdate := openapi3.Operation{} opUpdate.WithTags("pipeline") @@ -122,7 +136,7 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&opUpdate, new(usererror.Error), http.StatusForbidden) _ = reflector.SetJSONResponse(&opUpdate, new(usererror.Error), http.StatusNotFound) _ = reflector.Spec.AddOperation(http.MethodPatch, - "/pipelines/{pipeline_ref}", opUpdate) + "/repos/{repo_ref}/pipelines/{pipeline_uid}", opUpdate) executionCreate := openapi3.Operation{} executionCreate.WithTags("pipeline") @@ -134,7 +148,7 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&executionCreate, new(usererror.Error), http.StatusUnauthorized) _ = reflector.SetJSONResponse(&executionCreate, new(usererror.Error), http.StatusForbidden) _ = reflector.Spec.AddOperation(http.MethodPost, - "/pipelines/{pipeline_ref}/executions", executionCreate) + "/repos/{repo_ref}/pipelines/{pipeline_uid}/executions", executionCreate) executionFind := openapi3.Operation{} executionFind.WithTags("pipeline") @@ -146,7 +160,7 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&executionFind, new(usererror.Error), http.StatusForbidden) _ = reflector.SetJSONResponse(&executionFind, new(usererror.Error), http.StatusNotFound) _ = reflector.Spec.AddOperation(http.MethodGet, - "/pipelines/{pipeline_ref}/executions/{execution_number}", executionFind) + "/repos/{repo_ref}/pipelines/{pipeline_uid}/executions/{execution_number}", executionFind) executionDelete := openapi3.Operation{} executionDelete.WithTags("pipeline") @@ -158,7 +172,7 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&executionDelete, new(usererror.Error), http.StatusForbidden) _ = reflector.SetJSONResponse(&executionDelete, new(usererror.Error), http.StatusNotFound) _ = reflector.Spec.AddOperation(http.MethodDelete, - "/pipelines/{pipeline_ref}/executions/{execution_number}", executionDelete) + "/repos/{repo_ref}/pipelines/{pipeline_uid}/executions/{execution_number}", executionDelete) executionUpdate := openapi3.Operation{} executionUpdate.WithTags("pipeline") @@ -171,7 +185,7 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&executionUpdate, new(usererror.Error), http.StatusForbidden) _ = reflector.SetJSONResponse(&executionUpdate, new(usererror.Error), http.StatusNotFound) _ = reflector.Spec.AddOperation(http.MethodPatch, - "/pipelines/{pipeline_ref}/executions/{execution_number}", executionUpdate) + "/repos/{repo_ref}/pipelines/{pipeline_uid}/executions/{execution_number}", executionUpdate) executionList := openapi3.Operation{} executionList.WithTags("pipeline") @@ -184,7 +198,7 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&executionList, new(usererror.Error), http.StatusForbidden) _ = reflector.SetJSONResponse(&executionList, new(usererror.Error), http.StatusNotFound) _ = reflector.Spec.AddOperation(http.MethodGet, - "/pipelines/{pipeline_ref}/executions", executionList) + "/repos/{repo_ref}/pipelines/{pipeline_uid}/executions", executionList) triggerCreate := openapi3.Operation{} triggerCreate.WithTags("pipeline") @@ -196,7 +210,7 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&triggerCreate, new(usererror.Error), http.StatusUnauthorized) _ = reflector.SetJSONResponse(&triggerCreate, new(usererror.Error), http.StatusForbidden) _ = reflector.Spec.AddOperation(http.MethodPost, - "/pipelines/{pipeline_ref}/triggers", triggerCreate) + "/repos/{repo_ref}/pipelines/{pipeline_uid}/triggers", triggerCreate) triggerFind := openapi3.Operation{} triggerFind.WithTags("pipeline") @@ -208,7 +222,7 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&triggerFind, new(usererror.Error), http.StatusForbidden) _ = reflector.SetJSONResponse(&triggerFind, new(usererror.Error), http.StatusNotFound) _ = reflector.Spec.AddOperation(http.MethodGet, - "/pipelines/{pipeline_ref}/triggers/{trigger_uid}", triggerFind) + "/repos/{repo_ref}/pipelines/{pipeline_uid}/triggers/{trigger_uid}", triggerFind) triggerDelete := openapi3.Operation{} triggerDelete.WithTags("pipeline") @@ -220,7 +234,7 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&triggerDelete, new(usererror.Error), http.StatusForbidden) _ = reflector.SetJSONResponse(&triggerDelete, new(usererror.Error), http.StatusNotFound) _ = reflector.Spec.AddOperation(http.MethodDelete, - "/pipelines/{pipeline_ref}/triggers/{trigger_uid}", triggerDelete) + "/repos/{repo_ref}/pipelines/{pipeline_uid}/triggers/{trigger_uid}", triggerDelete) triggerUpdate := openapi3.Operation{} triggerUpdate.WithTags("pipeline") @@ -233,7 +247,7 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&triggerUpdate, new(usererror.Error), http.StatusForbidden) _ = reflector.SetJSONResponse(&triggerUpdate, new(usererror.Error), http.StatusNotFound) _ = reflector.Spec.AddOperation(http.MethodPatch, - "/pipelines/{pipeline_ref}/triggers/{trigger_uid}", triggerUpdate) + "/repos/{repo_ref}/pipelines/{pipeline_uid}/triggers/{trigger_uid}", triggerUpdate) triggerList := openapi3.Operation{} triggerList.WithTags("pipeline") @@ -246,7 +260,7 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&triggerList, new(usererror.Error), http.StatusForbidden) _ = reflector.SetJSONResponse(&triggerList, new(usererror.Error), http.StatusNotFound) _ = reflector.Spec.AddOperation(http.MethodGet, - "/pipelines/{pipeline_ref}/triggers", triggerList) + "/repos/{repo_ref}/pipelines/{pipeline_uid}/triggers", triggerList) logView := openapi3.Operation{} logView.WithTags("pipeline") @@ -258,5 +272,5 @@ func pipelineOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&logView, new(usererror.Error), http.StatusForbidden) _ = reflector.SetJSONResponse(&logView, new(usererror.Error), http.StatusNotFound) _ = reflector.Spec.AddOperation(http.MethodGet, - "/pipelines/{pipeline_ref}/executions/{execution_number}/logs/{stage_number}/{step_number}", logView) + "/repos/{repo_ref}/pipelines/{pipeline_uid}/executions/{execution_number}/logs/{stage_number}/{step_number}", logView) } diff --git a/internal/api/openapi/plugin.go b/internal/api/openapi/plugin.go index 71432f548..fcca4bdbf 100644 --- a/internal/api/openapi/plugin.go +++ b/internal/api/openapi/plugin.go @@ -7,11 +7,11 @@ package openapi import ( "net/http" - "github.com/gotidy/ptr" "github.com/harness/gitness/internal/api/request" "github.com/harness/gitness/internal/api/usererror" "github.com/harness/gitness/types" + "github.com/gotidy/ptr" "github.com/swaggest/openapi-go/openapi3" ) diff --git a/internal/api/openapi/space.go b/internal/api/openapi/space.go index cf63a9980..1a2117938 100644 --- a/internal/api/openapi/space.go +++ b/internal/api/openapi/space.go @@ -230,18 +230,6 @@ func spaceOperations(reflector *openapi3.Reflector) { _ = reflector.SetJSONResponse(&opRepos, new(usererror.Error), http.StatusNotFound) _ = reflector.Spec.AddOperation(http.MethodGet, "/spaces/{space_ref}/repos", opRepos) - opPipelines := openapi3.Operation{} - opPipelines.WithTags("space") - opPipelines.WithMapOfAnything(map[string]interface{}{"operationId": "listPipelines"}) - opPipelines.WithParameters(queryParameterQueryRepo, queryParameterPage, queryParameterLimit) - _ = reflector.SetRequest(&opPipelines, new(spaceRequest), http.MethodGet) - _ = reflector.SetJSONResponse(&opPipelines, []types.Pipeline{}, http.StatusOK) - _ = reflector.SetJSONResponse(&opPipelines, new(usererror.Error), http.StatusInternalServerError) - _ = reflector.SetJSONResponse(&opPipelines, new(usererror.Error), http.StatusUnauthorized) - _ = reflector.SetJSONResponse(&opPipelines, new(usererror.Error), http.StatusForbidden) - _ = reflector.SetJSONResponse(&opPipelines, new(usererror.Error), http.StatusNotFound) - _ = reflector.Spec.AddOperation(http.MethodGet, "/spaces/{space_ref}/pipelines", opPipelines) - opTemplates := openapi3.Operation{} opTemplates.WithTags("space") opTemplates.WithMapOfAnything(map[string]interface{}{"operationId": "listTemplates"}) diff --git a/internal/api/request/pipeline.go b/internal/api/request/pipeline.go index e7aa62189..d25c1a888 100644 --- a/internal/api/request/pipeline.go +++ b/internal/api/request/pipeline.go @@ -10,14 +10,14 @@ import ( ) const ( - PathParamPipelineRef = "pipeline_ref" + PathParamPipelineRef = "pipeline_uid" PathParamExecutionNumber = "execution_number" PathParamStageNumber = "stage_number" PathParamStepNumber = "step_number" PathParamTriggerUID = "trigger_uid" ) -func GetPipelineRefFromPath(r *http.Request) (string, error) { +func GetPipelineUIDFromPath(r *http.Request) (string, error) { rawRef, err := PathParamOrError(r, PathParamPipelineRef) if err != nil { return "", err diff --git a/internal/router/api.go b/internal/router/api.go index d71aaacfa..87f20dd62 100644 --- a/internal/router/api.go +++ b/internal/router/api.go @@ -71,7 +71,7 @@ type APIHandler interface { var ( // terminatedPathPrefixesAPI is the list of prefixes that will require resolving terminated paths. - terminatedPathPrefixesAPI = []string{"/v1/spaces/", "/v1/repos/", "/v1/pipelines/", + terminatedPathPrefixesAPI = []string{"/v1/spaces/", "/v1/repos/", "/v1/secrets/", "/v1/connectors", "/v1/templates"} ) @@ -162,8 +162,7 @@ func setupRoutesV1(r chi.Router, sysCtrl *system.Controller, ) { setupSpaces(r, spaceCtrl) - setupRepos(r, repoCtrl, pullreqCtrl, webhookCtrl, checkCtrl) - setupPipelines(r, pipelineCtrl, executionCtrl, triggerCtrl, logCtrl) + setupRepos(r, repoCtrl, pipelineCtrl, executionCtrl, triggerCtrl, logCtrl, pullreqCtrl, webhookCtrl, checkCtrl) setupConnectors(r, connectorCtrl) setupTemplates(r, templateCtrl) setupSecrets(r, secretCtrl) @@ -193,7 +192,6 @@ func setupSpaces(r chi.Router, spaceCtrl *space.Controller) { r.Get("/spaces", handlerspace.HandleListSpaces(spaceCtrl)) r.Get("/repos", handlerspace.HandleListRepos(spaceCtrl)) r.Get("/service-accounts", handlerspace.HandleListServiceAccounts(spaceCtrl)) - r.Get("/pipelines", handlerspace.HandleListPipelines(spaceCtrl)) r.Get("/secrets", handlerspace.HandleListSecrets(spaceCtrl)) r.Get("/connectors", handlerspace.HandleListConnectors(spaceCtrl)) r.Get("/templates", handlerspace.HandleListTemplates(spaceCtrl)) @@ -223,6 +221,10 @@ func setupSpaces(r chi.Router, spaceCtrl *space.Controller) { func setupRepos(r chi.Router, repoCtrl *repo.Controller, + pipelineCtrl *pipeline.Controller, + executionCtrl *execution.Controller, + triggerCtrl *trigger.Controller, + logCtrl *logs.Controller, pullreqCtrl *pullreq.Controller, webhookCtrl *webhook.Controller, checkCtrl *check.Controller, @@ -312,6 +314,8 @@ func setupRepos(r chi.Router, setupWebhook(r, webhookCtrl) + setupPipelines(r, repoCtrl, pipelineCtrl, executionCtrl, triggerCtrl, logCtrl) + SetupChecks(r, checkCtrl) }) }) @@ -319,11 +323,13 @@ func setupRepos(r chi.Router, func setupPipelines( r chi.Router, + repoCtrl *repo.Controller, pipelineCtrl *pipeline.Controller, executionCtrl *execution.Controller, triggerCtrl *trigger.Controller, logCtrl *logs.Controller) { r.Route("/pipelines", func(r chi.Router) { + r.Get("/", handlerrepo.HandleListPipelines(repoCtrl)) // Create takes path and parentId via body, not uri r.Post("/", handlerpipeline.HandleCreate(pipelineCtrl)) r.Route(fmt.Sprintf("/{%s}", request.PathParamPipelineRef), func(r chi.Router) { diff --git a/internal/store/database/migrate/ci/ci_migrations.sql b/internal/store/database/migrate/ci/ci_migrations.sql index d69497388..d6a93f39f 100644 --- a/internal/store/database/migrate/ci/ci_migrations.sql +++ b/internal/store/database/migrate/ci/ci_migrations.sql @@ -1,6 +1,7 @@ DROP TABLE IF exists pipelines; DROP TABLE IF exists executions; DROP TABLE IF exists stages; +DROP TABLE IF exists secrets; DROP TABLE IF exists steps; DROP TABLE IF exists logs; DROP TABLE IF exists plugins; @@ -10,26 +11,17 @@ DROP TABLE IF exists triggers; CREATE TABLE pipelines ( pipeline_id INTEGER PRIMARY KEY AUTOINCREMENT ,pipeline_description TEXT NOT NULL - ,pipeline_space_id INTEGER NOT NULL ,pipeline_uid TEXT NOT NULL ,pipeline_seq INTEGER NOT NULL DEFAULT 0 ,pipeline_repo_id INTEGER NOT NULL - ,pipeline_repo_type TEXT NOT NULL - ,pipeline_repo_name TEXT NOT NULL ,pipeline_default_branch TEXT NOT NULL ,pipeline_config_path TEXT NOT NULL ,pipeline_created INTEGER NOT NULL ,pipeline_updated INTEGER NOT NULL ,pipeline_version INTEGER NOT NULL - -- Ensure unique combination of UID and ParentID - ,UNIQUE (pipeline_space_id, pipeline_uid) - - -- Foreign key to spaces table - ,CONSTRAINT fk_pipeline_space_id FOREIGN KEY (pipeline_space_id) - REFERENCES spaces (space_id) MATCH SIMPLE - ON UPDATE NO ACTION - ON DELETE CASCADE + -- Ensure unique combination of UID and repo ID + ,UNIQUE (pipeline_repo_id, pipeline_uid) -- Foreign key to repositories table ,CONSTRAINT fk_pipelines_repo_id FOREIGN KEY (pipeline_repo_id) @@ -198,20 +190,20 @@ CREATE TABLE logs ( -- Insert some pipelines INSERT INTO pipelines ( - pipeline_id, pipeline_description, pipeline_space_id, pipeline_uid, pipeline_seq, - pipeline_repo_id, pipeline_repo_type, pipeline_repo_name, pipeline_default_branch, + pipeline_id, pipeline_description, pipeline_uid, pipeline_seq, + pipeline_repo_id, pipeline_default_branch, pipeline_config_path, pipeline_created, pipeline_updated, pipeline_version ) VALUES ( - 1, 'Sample Pipeline 1', 1, 'pipeline_uid_1', 2, 1, 'git', 'sample_repo_1', + 1, 'Sample Pipeline 1', 'pipeline_uid_1', 2, 1, 'main', 'config_path_1', 1678932000, 1678932100, 1 ); INSERT INTO pipelines ( - pipeline_id, pipeline_description, pipeline_space_id, pipeline_uid, pipeline_seq, - pipeline_repo_id, pipeline_repo_type, pipeline_repo_name, pipeline_default_branch, + pipeline_id, pipeline_description, pipeline_uid, pipeline_seq, + pipeline_repo_id, pipeline_default_branch, pipeline_config_path, pipeline_created, pipeline_updated, pipeline_version ) VALUES ( - 2, 'Sample Pipeline 2', 1, 'pipeline_uid_2', 0, 1, 'git', 'sample_repo_2', + 2, 'Sample Pipeline 2', 'pipeline_uid_2', 0, 1, 'develop', 'config_path_2', 1678932200, 1678932300, 1 ); diff --git a/internal/store/database/pipeline.go b/internal/store/database/pipeline.go index 0aa333ead..eb4a3129a 100644 --- a/internal/store/database/pipeline.go +++ b/internal/store/database/pipeline.go @@ -31,12 +31,9 @@ const ( pipelineColumns = ` pipeline_id ,pipeline_description - ,pipeline_space_id ,pipeline_uid ,pipeline_seq ,pipeline_repo_id - ,pipeline_repo_type - ,pipeline_repo_name ,pipeline_default_branch ,pipeline_config_path ,pipeline_created @@ -69,14 +66,14 @@ func (s *pipelineStore) Find(ctx context.Context, id int64) (*types.Pipeline, er return dst, nil } -// FindByUID returns a pipeline in a given space with a given UID. -func (s *pipelineStore) FindByUID(ctx context.Context, spaceID int64, uid string) (*types.Pipeline, error) { +// FindByUID returns a pipeline for a given repo with a given UID. +func (s *pipelineStore) FindByUID(ctx context.Context, repoID int64, uid string) (*types.Pipeline, error) { const findQueryStmt = pipelineQueryBase + ` - WHERE pipeline_space_id = $1 AND pipeline_uid = $2` + WHERE pipeline_repo_id = $1 AND pipeline_uid = $2` db := dbtx.GetAccessor(ctx, s.db) dst := new(types.Pipeline) - if err := db.GetContext(ctx, dst, findQueryStmt, spaceID, uid); err != nil { + if err := db.GetContext(ctx, dst, findQueryStmt, repoID, uid); err != nil { return nil, database.ProcessSQLErrorf(err, "Failed to find pipeline") } return dst, nil @@ -87,12 +84,9 @@ func (s *pipelineStore) Create(ctx context.Context, pipeline *types.Pipeline) er const pipelineInsertStmt = ` INSERT INTO pipelines ( pipeline_description - ,pipeline_space_id ,pipeline_uid ,pipeline_seq ,pipeline_repo_id - ,pipeline_repo_type - ,pipeline_repo_name ,pipeline_default_branch ,pipeline_config_path ,pipeline_created @@ -100,12 +94,9 @@ func (s *pipelineStore) Create(ctx context.Context, pipeline *types.Pipeline) er ,pipeline_version ) VALUES ( :pipeline_description, - :pipeline_space_id, :pipeline_uid, :pipeline_seq, :pipeline_repo_id, - :pipeline_repo_type, - :pipeline_repo_name, :pipeline_default_branch, :pipeline_config_path, :pipeline_created, @@ -171,16 +162,16 @@ func (s *pipelineStore) Update(ctx context.Context, p *types.Pipeline) error { return nil } -// List lists all the pipelines present in a space. +// List lists all the pipelines for a repository. func (s *pipelineStore) List( ctx context.Context, - parentID int64, + repoID int64, filter types.ListQueryFilter, ) ([]*types.Pipeline, error) { stmt := database.Builder. Select(pipelineColumns). From("pipelines"). - Where("pipeline_space_id = ?", fmt.Sprint(parentID)) + Where("pipeline_repo_id = ?", fmt.Sprint(repoID)) if filter.Query != "" { stmt = stmt.Where("LOWER(pipeline_uid) LIKE ?", fmt.Sprintf("%%%s%%", strings.ToLower(filter.Query))) @@ -231,12 +222,12 @@ func (s *pipelineStore) UpdateOptLock(ctx context.Context, } } -// Count of pipelines in a space. -func (s *pipelineStore) Count(ctx context.Context, parentID int64, filter types.ListQueryFilter) (int64, error) { +// Count of pipelines under a repo. +func (s *pipelineStore) Count(ctx context.Context, repoID int64, filter types.ListQueryFilter) (int64, error) { stmt := database.Builder. Select("count(*)"). From("pipelines"). - Where("pipeline_space_id = ?", parentID) + Where("pipeline_repo_id = ?", repoID) if filter.Query != "" { stmt = stmt.Where("LOWER(pipeline_uid) LIKE ?", fmt.Sprintf("%%%s%%", strings.ToLower(filter.Query))) @@ -272,15 +263,15 @@ func (s *pipelineStore) Delete(ctx context.Context, id int64) error { return nil } -// DeleteByUID deletes a pipeline with a given UID in a space. -func (s *pipelineStore) DeleteByUID(ctx context.Context, spaceID int64, uid string) error { +// DeleteByUID deletes a pipeline with a given UID under a given repo. +func (s *pipelineStore) DeleteByUID(ctx context.Context, repoID int64, uid string) error { const pipelineDeleteStmt = ` DELETE FROM pipelines - WHERE pipeline_space_id = $1 AND pipeline_uid = $2` + WHERE pipeline_repo_id = $1 AND pipeline_uid = $2` db := dbtx.GetAccessor(ctx, s.db) - if _, err := db.ExecContext(ctx, pipelineDeleteStmt, spaceID, uid); err != nil { + if _, err := db.ExecContext(ctx, pipelineDeleteStmt, repoID, uid); err != nil { return database.ProcessSQLErrorf(err, "Could not delete pipeline") } diff --git a/mocks/mock_client.go b/mocks/mock_client.go index 3cb746055..b16a6490e 100644 --- a/mocks/mock_client.go +++ b/mocks/mock_client.go @@ -8,10 +8,9 @@ import ( context "context" reflect "reflect" + gomock "github.com/golang/mock/gomock" user "github.com/harness/gitness/internal/api/controller/user" types "github.com/harness/gitness/types" - - gomock "github.com/golang/mock/gomock" ) // MockClient is a mock of Client interface. diff --git a/mocks/mock_store.go b/mocks/mock_store.go index 9310f3729..0af0bbc34 100644 --- a/mocks/mock_store.go +++ b/mocks/mock_store.go @@ -8,10 +8,9 @@ import ( context "context" reflect "reflect" + gomock "github.com/golang/mock/gomock" types "github.com/harness/gitness/types" enum "github.com/harness/gitness/types/enum" - - gomock "github.com/golang/mock/gomock" ) // MockPrincipalStore is a mock of PrincipalStore interface. diff --git a/types/pipeline.go b/types/pipeline.go index 019bf99a1..5c1e7eb51 100644 --- a/types/pipeline.go +++ b/types/pipeline.go @@ -4,20 +4,15 @@ package types -import "github.com/harness/gitness/types/enum" - type Pipeline struct { - ID int64 `db:"pipeline_id" json:"id"` - Description string `db:"pipeline_description" json:"description"` - SpaceID int64 `db:"pipeline_space_id" json:"space_id"` - UID string `db:"pipeline_uid" json:"uid"` - Seq int64 `db:"pipeline_seq" json:"seq"` // last execution number for this pipeline - RepoID int64 `db:"pipeline_repo_id" json:"repo_id"` // null if repo_type != gitness - RepoType enum.ScmType `db:"pipeline_repo_type" json:"repo_type"` - RepoName string `db:"pipeline_repo_name" json:"repo_name"` - DefaultBranch string `db:"pipeline_default_branch" json:"default_branch"` - ConfigPath string `db:"pipeline_config_path" json:"config_path"` - Created int64 `db:"pipeline_created" json:"created"` - Updated int64 `db:"pipeline_updated" json:"updated"` - Version int64 `db:"pipeline_version" json:"version"` + ID int64 `db:"pipeline_id" json:"id"` + Description string `db:"pipeline_description" json:"description"` + UID string `db:"pipeline_uid" json:"uid"` + Seq int64 `db:"pipeline_seq" json:"seq"` // last execution number for this pipeline + RepoID int64 `db:"pipeline_repo_id" json:"repo_id"` + DefaultBranch string `db:"pipeline_default_branch" json:"default_branch"` + ConfigPath string `db:"pipeline_config_path" json:"config_path"` + Created int64 `db:"pipeline_created" json:"created"` + Updated int64 `db:"pipeline_updated" json:"updated"` + Version int64 `db:"pipeline_version" json:"version"` }