Support programming excluded patterns in gitrepository spec

-- More coming in this commit message soon

Signed-off-by: Erik Hollensbe <github@hollensbe.org>
This commit is contained in:
Erik Hollensbe 2020-07-07 14:55:23 +00:00
parent 9a92164f17
commit b1b1dbcec5
6 changed files with 86 additions and 19 deletions

View File

@ -54,6 +54,13 @@ type GitRepositorySpec struct {
// Verify OpenPGP signature for the commit that HEAD points to.
// +optional
Verification *GitRepositoryVerification `json:"verify,omitempty"`
// SourceIgnore overrides the set of excluded patterns in the .sourceignore
// format (which is the same as .gitignore). If not provided, a default will
// be used, consult the documentation for your version to find out what those
// are.
// +optional
SourceIgnore *string `json:"sourceIgnore,omitempty"`
}
// GitRepositoryRef defines the git ref used for pull and checkout operations.

View File

@ -140,6 +140,11 @@ func (in *GitRepositorySpec) DeepCopyInto(out *GitRepositorySpec) {
*out = new(GitRepositoryVerification)
**out = **in
}
if in.SourceIgnore != nil {
in, out := &in.SourceIgnore, &out.SourceIgnore
*out = new(string)
**out = **in
}
}
// DeepCopy is an autogenerated deepcopy function, copying the receiver, creating a new GitRepositorySpec.

View File

@ -82,6 +82,12 @@ spec:
TODO: Add other useful fields. apiVersion, kind, uid?'
type: string
type: object
sourceIgnore:
description: SourceIgnore overrides the set of excluded patterns in
the .sourceignore format (which is the same as .gitignore). If not
provided, a default will be used, consult the documentation for your
version to find out what those are.
type: string
timeout:
description: The timeout for remote git operations like cloning, default
to 20s.

View File

@ -198,8 +198,7 @@ func (r *GitRepositoryReconciler) sync(ctx context.Context, repository sourcev1.
defer unlock()
// archive artifact and check integrity
err = r.Storage.Archive(artifact, tmpGit)
if err != nil {
if err := r.Storage.Archive(artifact, tmpGit, repository.Spec); err != nil {
err = fmt.Errorf("storage archive error: %w", err)
return sourcev1.GitRepositoryNotReady(repository, sourcev1.StorageOperationFailedReason, err.Error()), err
}

View File

@ -19,6 +19,7 @@ package controllers
import (
"archive/tar"
"bufio"
"bytes"
"compress/gzip"
"crypto/sha1"
"fmt"
@ -108,7 +109,7 @@ func (s *Storage) RemoveAllButCurrent(artifact sourcev1.Artifact) error {
})
if len(errors) > 0 {
return fmt.Errorf("faild to remove files: %s", strings.Join(errors, " "))
return fmt.Errorf("failed to remove files: %s", strings.Join(errors, " "))
}
return nil
}
@ -123,15 +124,17 @@ func (s *Storage) ArtifactExist(artifact sourcev1.Artifact) bool {
// Archive creates a tar.gz to the artifact path from the given dir excluding any VCS specific
// files and directories, or any of the excludes defined in the excludeFiles.
func (s *Storage) Archive(artifact sourcev1.Artifact, dir string) error {
// Returns a modified sourcev1.Artifact and any error.
func (s *Storage) Archive(artifact sourcev1.Artifact, dir string, spec sourcev1.GitRepositorySpec) error {
if _, err := os.Stat(dir); err != nil {
return err
}
ps, err := loadExcludePatterns(dir)
ps, err := loadExcludePatterns(dir, spec)
if err != nil {
return err
}
matcher := gitignore.NewMatcher(ps)
gzFile, err := os.Create(artifact.Path)
@ -241,27 +244,44 @@ func (s *Storage) Lock(artifact sourcev1.Artifact) (unlock func(), err error) {
return mutex.Lock()
}
func loadExcludePatterns(dir string) ([]gitignore.Pattern, error) {
func getPatterns(reader io.Reader, path []string) []gitignore.Pattern {
ps := []gitignore.Pattern{}
scanner := bufio.NewScanner(reader)
for scanner.Scan() {
s := scanner.Text()
if !strings.HasPrefix(s, "#") && len(strings.TrimSpace(s)) > 0 {
ps = append(ps, gitignore.ParsePattern(s, path))
}
}
return ps
}
// loadExcludePatterns loads the excluded patterns from sourceignore or other
// sources.
func loadExcludePatterns(dir string, spec sourcev1.GitRepositorySpec) ([]gitignore.Pattern, error) {
path := strings.Split(dir, "/")
var ps []gitignore.Pattern
for _, p := range strings.Split(excludeVCS, ",") {
ps = append(ps, gitignore.ParsePattern(p, path))
}
for _, p := range strings.Split(excludeExt, ",") {
ps = append(ps, gitignore.ParsePattern(p, path))
}
if f, err := os.Open(filepath.Join(dir, excludeFile)); err == nil {
defer f.Close()
scanner := bufio.NewScanner(f)
for scanner.Scan() {
s := scanner.Text()
if !strings.HasPrefix(s, "#") && len(strings.TrimSpace(s)) > 0 {
ps = append(ps, gitignore.ParsePattern(s, path))
}
if spec.SourceIgnore == nil {
for _, p := range strings.Split(excludeExt, ",") {
ps = append(ps, gitignore.ParsePattern(p, path))
}
} else if !os.IsNotExist(err) {
return nil, err
if f, err := os.Open(filepath.Join(dir, excludeFile)); err == nil {
defer f.Close()
ps = append(ps, getPatterns(f, path)...)
} else if !os.IsNotExist(err) {
return nil, err
}
} else {
ps = append(ps, getPatterns(bytes.NewBufferString(*spec.SourceIgnore), path)...)
}
return ps, nil
}

View File

@ -157,6 +157,21 @@ GitRepositoryVerification
<p>Verify OpenPGP signature for the commit that HEAD points to.</p>
</td>
</tr>
<tr>
<td>
<code>sourceIgnore</code><br>
<em>
string
</em>
</td>
<td>
<em>(Optional)</em>
<p>SourceIgnore overrides the set of excluded patterns in the .sourceignore
format (which is the same as .gitignore). If not provided, a default will
be used, consult the documentation for your version to find out what those
are.</p>
</td>
</tr>
</table>
</td>
</tr>
@ -666,6 +681,21 @@ GitRepositoryVerification
<p>Verify OpenPGP signature for the commit that HEAD points to.</p>
</td>
</tr>
<tr>
<td>
<code>sourceIgnore</code><br>
<em>
string
</em>
</td>
<td>
<em>(Optional)</em>
<p>SourceIgnore overrides the set of excluded patterns in the .sourceignore
format (which is the same as .gitignore). If not provided, a default will
be used, consult the documentation for your version to find out what those
are.</p>
</td>
</tr>
</tbody>
</table>
</div>