Thanks to visit codestin.com
Credit goes to github.com

Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ chapter = true

**CheckoutApplication** is a builtin action, you can't modify it.

This action clones a repository into a directory.
This action clones a repository into a directory. If you want to clone a tag from your repository in this way, in your workflow payload you can add a key in your JSON like `"git.tag": "0.2"`.

This will run git clone with the following options:

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,10 +22,11 @@ Advanced parameters:

* depth - optional - 50 by default. You can remove --depth with the value 'false'
* submodules - true by default, you can set false to avoid this.
* tag - optional - empty by default, you can set to `{{.git.tag}}` to clone a tag from your repository. In this way, in your workflow payload you can add a key in your JSON like `"git.tag": "0.2"`.

Notes:

By defaut, depth is 50 and git clone with `--single-branch` automatically.
By default, depth is 50 and git clone with `--single-branch` automatically.
So, if you want to do in a step script `git diff anotherBranch`, you have to set depth to 'false'.

If there is no user && password && sshkey setted in action GitClone, CDS checks on Application VCS Strategy if some auth parameters can be used.
Expand Down
5 changes: 3 additions & 2 deletions docs/content/workflows/pipelines/variables.md
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ Here is the list of builtin variables, generated for every build:
- `{{.cds.application}}` The name of the current application
- `{{.cds.job}}` The name of the current job
- `{{.cds.manual}}` true if current pipeline is manually run, false otherwise
- `{{.cds.pipeline}}` The name of the current pipeline
- `{{.cds.pipeline}}` The name of the current pipeline
- `{{.cds.project}}` The name of the current project
- `{{.cds.run}}` Run Number of current workflow, example: 3.0
- `{{.cds.run.number}}` Number of current workflow, example: 3 if `{{.cds.run}} = 3.0`
Expand Down Expand Up @@ -97,6 +97,7 @@ Here is the list of git variables:
- `{{.git.url}}`
- `{{.git.http_url}}`
- `{{.git.branch}}`
- `{{.git.tag}}`
- `{{.git.author}}`
- `{{.git.message}}`
- `{{.git.server}}`
Expand Down Expand Up @@ -159,4 +160,4 @@ Helpers available and some examples:
- b64dec
- escape : replace '_', '/', '.' by '-'

You're a go developper? See all helpers on https://github.com/ovh/cds/blob/master/sdk/interpolate/interpolate_helper.go#L23
You're a go developper? See all helpers on https://github.com/ovh/cds/blob/master/sdk/interpolate/interpolate_helper.go#L23
7 changes: 7 additions & 0 deletions engine/api/action/builtin.go
Original file line number Diff line number Diff line change
Expand Up @@ -123,6 +123,13 @@ The public key have to be granted on your repository`,
Type: sdk.BooleanParameter,
Advanced: true,
})
gitclone.Parameter(sdk.Parameter{
Name: "tag",
Description: "Useful when you want to git clone a specific tag",
Value: "",
Type: sdk.StringParameter,
Advanced: true,
})
gitclone.Requirement("git", sdk.BinaryRequirement, "git")

if err := checkBuiltinAction(db, gitclone); err != nil {
Expand Down
11 changes: 11 additions & 0 deletions engine/api/repositoriesmanager/repositories_manager.go
Original file line number Diff line number Diff line change
Expand Up @@ -297,6 +297,17 @@ func (c *vcsClient) Commits(ctx context.Context, fullname, branch, since, until
return commits, nil
}

func (c *vcsClient) CommitsBetweenRefs(ctx context.Context, fullname, base, head string) ([]sdk.VCSCommit, error) {
var commits []sdk.VCSCommit
path := fmt.Sprintf("/vcs/%s/repos/%s/commits?base=%s&head=%s", c.name, fullname, url.QueryEscape(base), url.QueryEscape(head))
if code, err := c.doJSONRequest(ctx, "GET", path, nil, &commits); err != nil {
if code != http.StatusNotFound {
return nil, err
}
}
return commits, nil
}

func (c *vcsClient) Commit(ctx context.Context, fullname, hash string) (sdk.VCSCommit, error) {
commit := sdk.VCSCommit{}
path := fmt.Sprintf("/vcs/%s/repos/%s/commits/%s", c.name, fullname, hash)
Expand Down
1 change: 1 addition & 0 deletions engine/api/suggest.go
Original file line number Diff line number Diff line change
Expand Up @@ -138,6 +138,7 @@ func (api *API) getVariablesHandler() service.Handler {
gitVar := []string{
"{{.git.hash}}",
"{{.git.branch}}",
"{{.git.tag}}",
"{{.git.author}}",
"{{.git.project}}",
"{{.git.repository}}",
Expand Down
63 changes: 47 additions & 16 deletions engine/api/workflow/dao_node_run.go
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ workflow_node_run.triggers_run,
workflow_node_run.vcs_repository,
workflow_node_run.vcs_hash,
workflow_node_run.vcs_branch,
workflow_node_run.vcs_tag,
workflow_node_run.vcs_server,
workflow_node_run.workflow_node_name,
workflow_node_run.header
Expand Down Expand Up @@ -247,6 +248,9 @@ func fromDBNodeRun(rr NodeRun, opts LoadRunOptions) (*sdk.WorkflowNodeRun, error
if rr.VCSBranch.Valid {
r.VCSBranch = rr.VCSBranch.String
}
if rr.VCSTag.Valid {
r.VCSTag = rr.VCSTag.String
}
if rr.VCSServer.Valid {
r.VCSServer = rr.VCSServer.String
}
Expand Down Expand Up @@ -339,6 +343,8 @@ func makeDBNodeRun(n sdk.WorkflowNodeRun) (*NodeRun, error) {
nodeRunDB.VCSHash.String = n.VCSHash
nodeRunDB.VCSBranch.Valid = true
nodeRunDB.VCSBranch.String = n.VCSBranch
nodeRunDB.VCSTag.Valid = true
nodeRunDB.VCSTag.String = n.VCSTag
nodeRunDB.VCSRepository.Valid = true
nodeRunDB.VCSRepository.String = n.VCSRepository

Expand Down Expand Up @@ -476,16 +482,16 @@ func GetNodeRunBuildCommits(ctx context.Context, db gorp.SqlExecutor, store cach
if errclient != nil {
return nil, cur, sdk.WrapError(errclient, "GetNodeRunBuildCommits> Cannot get client")
}

cur.Remote = nodeRun.VCSRepository
cur.Branch = nodeRun.VCSBranch
cur.Hash = nodeRun.VCSHash
cur.Tag = nodeRun.VCSTag

if cur.Remote == "" {
cur.Remote = app.RepositoryFullname
}

if cur.Branch == "" {
if cur.Branch == "" && cur.Tag == "" {
branches, errBr := client.Branches(ctx, cur.Remote)
if errBr != nil {
return nil, cur, sdk.WrapError(errBr, "GetNodeRunBuildCommits> Cannot load branches from vcs api remote %s", cur.Remote)
Expand Down Expand Up @@ -514,7 +520,7 @@ func GetNodeRunBuildCommits(ctx context.Context, db gorp.SqlExecutor, store cach
}

var lastCommit sdk.VCSCommit
if cur.Hash == "" {
if cur.Hash == "" && cur.Tag == "" && cur.Branch != "" {
//If we only have the current branch, search for the branch
br, err := client.Branch(ctx, repo, cur.Branch)
if err != nil {
Expand Down Expand Up @@ -548,24 +554,46 @@ func GetNodeRunBuildCommits(ctx context.Context, db gorp.SqlExecutor, store cach
if prev.Hash != "" && cur.Hash == prev.Hash {
log.Debug("GetNodeRunBuildCommits> there is not difference between the previous build and the current build for node %s", nodeRun.WorkflowNodeName)
} else if prev.Hash != "" {
if cur.Hash == "" {
switch {
case cur.Hash == "" && cur.Tag == "":
br, err := client.Branch(ctx, repo, cur.Branch)
if err != nil {
return nil, cur, sdk.WrapError(err, "GetNodeRunBuildCommits> Cannot get branch %s", cur.Branch)
}
cur.Hash = br.LatestCommit
}
//If we are lucky, return a true diff
commits, err := client.Commits(ctx, repo, cur.Branch, prev.Hash, cur.Hash)
if err != nil {
return nil, cur, sdk.WrapError(err, "GetNodeRunBuildCommits> Cannot get commits")
}
if commits != nil {
res = commits
//If we are lucky, return a true diff
commits, err := client.Commits(ctx, repo, cur.Branch, prev.Hash, cur.Hash)
if err != nil {
return nil, cur, sdk.WrapError(err, "GetNodeRunBuildCommits> Cannot get commits")
}
if commits != nil {
res = commits
}

case cur.Hash == "" && cur.Tag != "":
c, err := client.CommitsBetweenRefs(ctx, repo, prev.Hash, cur.Tag)
if err != nil {
return nil, cur, sdk.WrapError(err, "GetNodeRunBuildCommits> Cannot get commits")
}
if c != nil {
res = c
}
}
} else if prev.Hash == "" {
if lastCommit.Hash != "" {
res = []sdk.VCSCommit{lastCommit}
} else if cur.Tag != "" {
base := prev.Tag
if base == "" {
base = prev.Hash
}
c, err := client.CommitsBetweenRefs(ctx, repo, base, cur.Tag)
if err != nil {
return nil, cur, sdk.WrapError(err, "GetNodeRunBuildCommits> Cannot get commits")
}
if c != nil {
res = c
}
}
} else {
//If we only get current node run hash
Expand Down Expand Up @@ -593,7 +621,7 @@ func PreviousNodeRun(db gorp.SqlExecutor, nr sdk.WorkflowNodeRun, n sdk.Workflow
`, nodeRunFields)
var nodeRun sdk.WorkflowNodeRun
var rr = NodeRun{}
if err := db.SelectOne(&rr, query, n.Name, workflowID, nr.VCSBranch, nr.Number, nr.WorkflowNodeID, nr.ID); err != nil {
if err := db.SelectOne(&rr, query, n.Name, workflowID, nr.VCSBranch, nr.VCSTag, nr.Number, nr.WorkflowNodeID, nr.ID); err != nil {
return nodeRun, sdk.WrapError(err, "PreviousNodeRun> Cannot load previous run on workflow %d node %s", workflowID, n.Name)
}
pNodeRun, errF := fromDBNodeRun(rr, LoadRunOptions{})
Expand All @@ -610,11 +638,11 @@ func PreviousNodeRun(db gorp.SqlExecutor, nr sdk.WorkflowNodeRun, n sdk.Workflow
//If you don't have environment linked set envID to 0 or -1
func PreviousNodeRunVCSInfos(db gorp.SqlExecutor, projectKey string, wf *sdk.Workflow, nodeName string, current sdk.BuildNumberAndHash, appID int64, envID int64) (sdk.BuildNumberAndHash, error) {
var previous sdk.BuildNumberAndHash
var prevHash, prevBranch, prevRepository sql.NullString
var prevHash, prevBranch, prevTag, prevRepository sql.NullString
var previousBuildNumber sql.NullInt64

queryPrevious := `
SELECT workflow_node_run.vcs_branch, workflow_node_run.vcs_hash, workflow_node_run.vcs_repository, workflow_node_run.num
SELECT workflow_node_run.vcs_branch, workflow_node_run.vcs_tag, workflow_node_run.vcs_hash, workflow_node_run.vcs_repository, workflow_node_run.num
FROM workflow_node_run
JOIN workflow_node ON workflow_node.name = workflow_node_run.workflow_node_name AND workflow_node.name = $1 AND workflow_node.workflow_id = $2
JOIN workflow_node_context ON workflow_node_context.workflow_node_id = workflow_node.id
Expand All @@ -630,7 +658,7 @@ func PreviousNodeRunVCSInfos(db gorp.SqlExecutor, projectKey string, wf *sdk.Wor
}
queryPrevious += fmt.Sprintf(" ORDER BY workflow_node_run.num DESC LIMIT 1")

errPrev := db.QueryRow(queryPrevious, argPrevious...).Scan(&prevBranch, &prevHash, &prevRepository, &previousBuildNumber)
errPrev := db.QueryRow(queryPrevious, argPrevious...).Scan(&prevBranch, &prevTag, &prevHash, &prevRepository, &previousBuildNumber)
if errPrev == sql.ErrNoRows {
log.Warning("PreviousNodeRunVCSInfos> no result with previous %d %s , arguments %v", current.BuildNumber, nodeName, argPrevious)
return previous, nil
Expand All @@ -642,6 +670,9 @@ func PreviousNodeRunVCSInfos(db gorp.SqlExecutor, projectKey string, wf *sdk.Wor
if prevBranch.Valid {
previous.Branch = prevBranch.String
}
if prevTag.Valid {
previous.Tag = prevTag.String
}
if prevHash.Valid {
previous.Hash = prevHash.String
}
Expand Down
6 changes: 6 additions & 0 deletions engine/api/workflow/execute_node_run.go
Original file line number Diff line number Diff line change
Expand Up @@ -766,6 +766,7 @@ func SyncNodeRunRunJob(ctx context.Context, db gorp.SqlExecutor, nodeRun *sdk.Wo

type vcsInfos struct {
Repository string
Tag string
Branch string
Hash string
Author string
Expand All @@ -783,6 +784,7 @@ func getVCSInfos(ctx context.Context, db gorp.SqlExecutor, store cache.Store, vc
var vcsInfos vcsInfos
vcsInfos.Repository = gitValues[tagGitRepository]
vcsInfos.Branch = gitValues[tagGitBranch]
vcsInfos.Tag = gitValues[tagGitTag]
vcsInfos.Hash = gitValues[tagGitHash]
vcsInfos.Author = gitValues[tagGitAuthor]
vcsInfos.Message = gitValues[tagGitMessage]
Expand Down Expand Up @@ -848,6 +850,7 @@ func getVCSInfos(ctx context.Context, db gorp.SqlExecutor, store cache.Store, vc
return vcsInfos, sdk.NewError(sdk.ErrNotFound, fmt.Errorf("repository %s not found", vcsInfos.Repository))
}
vcsInfos.Repository = applicationRepositoryFullname
vcsInfos.Tag = ""
}
}

Expand All @@ -868,6 +871,9 @@ func getVCSInfos(ctx context.Context, db gorp.SqlExecutor, store cache.Store, vc
vcsInfos.HTTPUrl = repo.HTTPCloneURL

if vcsInfos.Branch == "" && !isChildNode {
if vcsInfos.Tag != "" {
return vcsInfos, nil
}
return vcsInfos, sdk.WrapError(sdk.ErrBranchNameNotProvided, "computeVCSInfos> should not have an empty branch")
}

Expand Down
1 change: 1 addition & 0 deletions engine/api/workflow/gorp_model.go
Original file line number Diff line number Diff line change
Expand Up @@ -66,6 +66,7 @@ type NodeRun struct {
TriggersRun sql.NullString `db:"triggers_run"`
VCSRepository sql.NullString `db:"vcs_repository"`
VCSBranch sql.NullString `db:"vcs_branch"`
VCSTag sql.NullString `db:"vcs_tag"`
VCSHash sql.NullString `db:"vcs_hash"`
VCSServer sql.NullString `db:"vcs_server"`
Header sql.NullString `db:"header"`
Expand Down
9 changes: 8 additions & 1 deletion engine/api/workflow/process.go
Original file line number Diff line number Diff line change
Expand Up @@ -620,7 +620,12 @@ func processWorkflowNodeRun(ctx context.Context, db gorp.SqlExecutor, store cach
// Tag VCS infos : add in tag only if it does not exist
if !w.TagExists(tagGitRepository) {
w.Tag(tagGitRepository, run.VCSRepository)
w.Tag(tagGitBranch, run.VCSBranch)
if run.VCSBranch != "" {
w.Tag(tagGitBranch, run.VCSBranch)
}
if run.VCSTag != "" {
w.Tag(tagGitTag, run.VCSTag)
}
if len(run.VCSHash) >= 7 {
w.Tag(tagGitHash, run.VCSHash[:7])
} else {
Expand Down Expand Up @@ -720,11 +725,13 @@ func processWorkflowNodeRun(ctx context.Context, db gorp.SqlExecutor, store cach
func setValuesGitInBuildParameters(run *sdk.WorkflowNodeRun, vcsInfos vcsInfos) {
run.VCSRepository = vcsInfos.Repository
run.VCSBranch = vcsInfos.Branch
run.VCSTag = vcsInfos.Tag
run.VCSHash = vcsInfos.Hash
run.VCSServer = vcsInfos.Server

sdk.ParameterAddOrSetValue(&run.BuildParameters, tagGitRepository, sdk.StringParameter, run.VCSRepository)
sdk.ParameterAddOrSetValue(&run.BuildParameters, tagGitBranch, sdk.StringParameter, run.VCSBranch)
sdk.ParameterAddOrSetValue(&run.BuildParameters, tagGitTag, sdk.StringParameter, run.VCSTag)
sdk.ParameterAddOrSetValue(&run.BuildParameters, tagGitHash, sdk.StringParameter, run.VCSHash)
sdk.ParameterAddOrSetValue(&run.BuildParameters, tagGitAuthor, sdk.StringParameter, vcsInfos.Author)
sdk.ParameterAddOrSetValue(&run.BuildParameters, tagGitMessage, sdk.StringParameter, vcsInfos.Message)
Expand Down
6 changes: 5 additions & 1 deletion engine/api/workflow/resync_workflow.go
Original file line number Diff line number Diff line change
Expand Up @@ -120,7 +120,8 @@ func ResyncNodeRunsWithCommits(ctx context.Context, db gorp.SqlExecutor, store c
return
}

commits, curVCSInfos, err := GetNodeRunBuildCommits(ctx, db, store, proj, &wr.Workflow, n.Name, wr.Number, &nr, n.Context.Application, n.Context.Environment)
//New context because we are in goroutine
commits, curVCSInfos, err := GetNodeRunBuildCommits(context.Background(), db, store, proj, &wr.Workflow, n.Name, wr.Number, &nr, n.Context.Application, n.Context.Environment)
if err != nil {
log.Error("ResyncNodeRuns> cannot get build commits on a node run %v", err)
} else if commits != nil {
Expand All @@ -143,6 +144,9 @@ func ResyncNodeRunsWithCommits(ctx context.Context, db gorp.SqlExecutor, store c
if curVCSInfos.Remote != "" {
tagsUpdated = wr.Tag(tagGitRepository, curVCSInfos.Remote)
}
if curVCSInfos.Tag != "" {
tagsUpdated = wr.Tag(tagGitTag, curVCSInfos.Tag)
}

if tagsUpdated {
if err := UpdateWorkflowRunTags(db, wr); err != nil {
Expand Down
7 changes: 6 additions & 1 deletion engine/api/workflow/workflow_run_event.go
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,11 @@ func ResyncCommitStatus(ctx context.Context, db gorp.SqlExecutor, store cache.St
return sdk.WrapError(errClient, "resyncCommitStatus> Cannot get client")
}

statuses, errStatuses := client.ListStatuses(ctx, node.Context.Application.RepositoryFullname, nodeRun.VCSHash)
ref := nodeRun.VCSHash
if nodeRun.VCSTag != "" {
ref = nodeRun.VCSTag
}
statuses, errStatuses := client.ListStatuses(ctx, node.Context.Application.RepositoryFullname, ref)
if errStatuses != nil {
return sdk.WrapError(errStatuses, "resyncCommitStatus> Cannot get statuses")
}
Expand Down Expand Up @@ -191,6 +195,7 @@ func sendVCSEventStatus(ctx context.Context, db gorp.SqlExecutor, store cache.St
Payload: nodeRun.Payload,
SourceNodeRuns: nodeRun.SourceNodeRuns,
Hash: nodeRun.VCSHash,
Tag: nodeRun.VCSTag,
BranchName: nodeRun.VCSBranch,
NodeID: nodeRun.WorkflowNodeID,
RunID: nodeRun.WorkflowRunID,
Expand Down
Loading