Skip to content

Commit

Permalink
Use gob encoding for manifest files.
Browse files Browse the repository at this point in the history
  • Loading branch information
wlynch authored and tekton-robot committed Oct 15, 2019
1 parent e4928a6 commit 9e10c01
Show file tree
Hide file tree
Showing 2 changed files with 59 additions and 78 deletions.
72 changes: 31 additions & 41 deletions cmd/pullrequest-init/disk.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,9 +17,8 @@ limitations under the License.
package main

import (
"bufio"
"encoding/gob"
"encoding/json"
"fmt"
"io/ioutil"
"net/url"
"os"
Expand Down Expand Up @@ -86,17 +85,7 @@ func ToDisk(pr *PullRequest, path string) error {
}

func commentsToDisk(path string, comments []*Comment) error {
// Create a manifest to keep track of the comments that existed when the
// resource was initialized. This is used to verify that a comment that
// doesn't exist on disk was actually deleted by the user and not newly
// created during upload.
f, err := os.Create(filepath.Join(path, manifestPath))
if err != nil {
return err
}
defer f.Close()
manifest := bufio.NewWriter(f)

manifest := Manifest{}
for _, c := range comments {
id := strconv.FormatInt(c.ID, 10)
commentPath := filepath.Join(path, id+".json")
Expand All @@ -107,33 +96,27 @@ func commentsToDisk(path string, comments []*Comment) error {
if err := ioutil.WriteFile(commentPath, b, 0600); err != nil {
return err
}
if _, err := manifest.WriteString(fmt.Sprintf("%s\n", id)); err != nil {
return err
}
manifest[id] = true
}
return manifest.Flush()

// Create a manifest to keep track of the comments that existed when the
// resource was initialized. This is used to verify that a comment that
// doesn't exist on disk was actually deleted by the user and not newly
// created during upload.
return manifestToDisk(manifest, filepath.Join(path, manifestPath))
}

func labelsToDisk(path string, labels []*Label) error {
f, err := os.Create(filepath.Join(path, manifestPath))
if err != nil {
return err
}
defer f.Close()
manifest := bufio.NewWriter(f)

manifest := Manifest{}
for _, l := range labels {
name := url.QueryEscape(l.Text)
labelPath := filepath.Join(path, name)
if err := ioutil.WriteFile(labelPath, []byte{}, 0600); err != nil {
return err
}
if _, err := manifest.WriteString(fmt.Sprintf("%s\n", l.Text)); err != nil {
return err
}

manifest[name] = true
}
return manifest.Flush()
return manifestToDisk(manifest, filepath.Join(path, manifestPath))
}

func statusToDisk(path string, statuses []*Status) error {
Expand All @@ -159,10 +142,6 @@ func refToDisk(name, path string, r *GitReference) error {
return ioutil.WriteFile(filepath.Join(path, name+".json"), b, 0700)
}

// Manifest is a list of sub-resources that exist within the PR resource to
// determine whether an item existed when the resource was initialized.
type Manifest map[string]bool

// FromDisk outputs a PullRequest object from an on-disk representation at the specified path.
func FromDisk(path string) (*PullRequest, map[string]Manifest, error) {
labelsPath := filepath.Join(path, "labels")
Expand Down Expand Up @@ -203,22 +182,33 @@ func FromDisk(path string) (*PullRequest, map[string]Manifest, error) {
return &pr, manifests, nil
}

func manifestFromDisk(path string) (map[string]bool, error) {
// Manifest is a list of sub-resources that exist within the PR resource to
// determine whether an item existed when the resource was initialized.
type Manifest map[string]bool

func manifestToDisk(manifest Manifest, path string) error {
f, err := os.Create(path)
if err != nil {
return err
}
defer f.Close()
enc := gob.NewEncoder(f)
return enc.Encode(manifest)
}

func manifestFromDisk(path string) (Manifest, error) {
f, err := os.Open(path)
if err != nil {
return nil, err
}
defer f.Close()

out := make(map[string]bool)
s := bufio.NewScanner(f)
for s.Scan() {
out[s.Text()] = true
}
if s.Err() != nil {
m := Manifest{}
dec := gob.NewDecoder(f)
if err := dec.Decode(&m); err != nil {
return nil, err
}
return out, nil
return m, nil
}

func commentsFromDisk(path string) ([]*Comment, Manifest, error) {
Expand Down
65 changes: 28 additions & 37 deletions cmd/pullrequest-init/disk_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@ limitations under the License.
package main

import (
"bufio"
"encoding/json"
"io/ioutil"
"net/url"
Expand All @@ -26,7 +25,6 @@ import (
"reflect"
"sort"
"strconv"
"strings"
"testing"

"github.com/google/go-cmp/cmp"
Expand Down Expand Up @@ -131,18 +129,21 @@ func TestToDisk(t *testing.T) {
t.Errorf("Error decoding label text: %s", fi.Name())
}
labels[text] = struct{}{}
labelManifest[text] = true
labelManifest[fi.Name()] = true
}

for _, l := range tektonPr.Labels {
if _, ok := labels[l.Text]; !ok {
t.Errorf("Expected label with text: %s, not found: %v", l.Text, labels)
}
}
gotManifest := readManifest(t, filepath.Join(d, "labels", manifestPath))
for _, m := range gotManifest {
if _, ok := labelManifest[m]; !ok {
t.Errorf("Label %s not found in manifest", m)
gotManifest, err := manifestFromDisk(filepath.Join(d, "labels", manifestPath))
if err != nil {
t.Fatalf("Error reading comment manifest: %v", err)
}
for m := range gotManifest {
if !labelManifest[m] {
t.Errorf("Label %s not found in manifest: %+v", m, labelManifest)
}
}
if len(labelManifest) != len(gotManifest) {
Expand Down Expand Up @@ -176,9 +177,12 @@ func TestToDisk(t *testing.T) {
t.Errorf("Get Comment: -want +got: %s", diff)
}
}
gotManifest = readManifest(t, filepath.Join(d, "comments", manifestPath))
for _, m := range gotManifest {
if _, ok := commentManifest[m]; !ok {
gotManifest, err = manifestFromDisk(filepath.Join(d, "comments", manifestPath))
if err != nil {
t.Fatalf("Error reading comment manifest: %v", err)
}
for m := range gotManifest {
if !commentManifest[m] {
t.Errorf("Comment %s not found in manifest", m)
}
}
Expand All @@ -187,24 +191,6 @@ func TestToDisk(t *testing.T) {
}
}

func readManifest(t *testing.T, path string) []string {
f, err := os.Open(path)
if err != nil {
t.Fatal(err)
}
defer f.Close()

var out []string
s := bufio.NewScanner(f)
for s.Scan() {
out = append(out, s.Text())
}
if s.Err() != nil {
t.Fatal(err)
}
return out
}

func TestFromDisk(t *testing.T) {
d, err := ioutil.TempDir("", "")
if err != nil {
Expand Down Expand Up @@ -266,9 +252,7 @@ func TestFromDisk(t *testing.T) {
t.Fatal(err)
}
}
if err := ioutil.WriteFile(filepath.Join(d, "labels", manifestPath), []byte(strings.Join(labels, "\n")), 0600); err != nil {
t.Errorf("Error creating label manifest: %s", err)
}
writeManifest(t, labels, filepath.Join(d, "labels", manifestPath))

// Write some comments
comments := []Comment{
Expand All @@ -293,9 +277,7 @@ func TestFromDisk(t *testing.T) {
writeFile(filepath.Join(d, "comments", id+".json"), &c)
manifest = append(manifest, id)
}
if err := ioutil.WriteFile(filepath.Join(d, "comments", manifestPath), []byte(strings.Join(manifest, "\n")), 0700); err != nil {
t.Errorf("Error creating comment manifest: %s", err)
}
writeManifest(t, manifest, filepath.Join(d, "comments", manifestPath))

// Comments can also be plain text.
if err := ioutil.WriteFile(filepath.Join(d, "comments", "plain"), []byte("plaincomment"), 0700); err != nil {
Expand Down Expand Up @@ -514,6 +496,17 @@ func Test_statusToDisk(t *testing.T) {
}
}

func writeManifest(t *testing.T, items []string, path string) {
t.Helper()
m := Manifest{}
for _, i := range items {
m[i] = true
}
if err := manifestToDisk(m, path); err != nil {
t.Fatal(err)
}
}

func Test_labelsFromDisk(t *testing.T) {
type args struct {
fileNames []string
Expand Down Expand Up @@ -566,9 +559,7 @@ func Test_labelsFromDisk(t *testing.T) {
t.Errorf("Error creating label: %s", err)
}
}
if err := ioutil.WriteFile(filepath.Join(d, manifestPath), []byte(strings.Join(tt.args.fileNames, "\n")), 0700); err != nil {
t.Errorf("Error creating label manifest: %s", err)
}
writeManifest(t, tt.args.fileNames, filepath.Join(d, manifestPath))
got, _, err := labelsFromDisk(d)
if err != nil {
t.Errorf("labelsFromDisk() error = %v", err)
Expand Down

0 comments on commit 9e10c01

Please sign in to comment.