Merge lp:~stevenwilkin/snapweb/add-remove-snaps-via-api into lp:~snappy-dev/snapweb/trunk
- add-remove-snaps-via-api
- Merge into trunk
Status: | Merged |
---|---|
Approved by: | Federico Gimenez |
Approved revision: | 180 |
Merged at revision: | 178 |
Proposed branch: | lp:~stevenwilkin/snapweb/add-remove-snaps-via-api |
Merge into: | lp:~snappy-dev/snapweb/trunk |
Diff against target: |
823 lines (+302/-310) 10 files modified
snappy/common_test.go (+8/-0) snappy/converge.go (+23/-56) snappy/converge_test.go (+11/-11) snappy/handlers.go (+3/-10) snappy/handlers_test.go (+0/-2) snappy/snapd_client.go (+2/-0) statustracker/statustracker.go (+134/-0) statustracker/statustracker_test.go (+121/-0) webprogress/meter.go (+0/-159) webprogress/progress.go (+0/-72) |
To merge this branch: | bzr merge lp:~stevenwilkin/snapweb/add-remove-snaps-via-api |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
Martin Albisetti (community) | Approve | ||
Review via email: mp+288437@code.launchpad.net |
Commit message
Add and remove snaps via the snapd API
Description of the change
Add and remove snaps via the snapd API.
Includes a workaround to keep track of which snaps are being added/removed which will be excised when progress of background operations can be communicated via the API.
Martin Albisetti (beuno) : | # |
Snappy Tarmac (snappydevtarmac) wrote : | # |
Steven Wilkin (stevenwilkin) wrote : | # |
retest this please
Snappy Tarmac (snappydevtarmac) wrote : | # |
The attempt to merge lp:~stevenwilkin/webdm/add-remove-snaps-via-api into lp:webdm failed. Below is the output from the failed tests.
Checking formatting
Installing godeps
Install golint
Obtaining dependencies
update golang.org/x/crypto failed; trying to fetch newer version
golang.org/x/crypto now at 60052bd85f2d912
update github.
github.
update gopkg.in/check.v1 failed; trying to fetch newer version
gopkg.in/check.v1 now at 64131543e7896d5
update gopkg.in/yaml.v2 failed; trying to fetch newer version
gopkg.in/yaml.v2 now at 49c95bdc2184325
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
Building
Running tests from /tmp/tmp.
=== RUN Test
OK: 4 passed
--- PASS: Test (0.01s)
PASS
coverage: 60.0% of statements
ok launchpad.
? launchpad.
=== RUN Test
WARNING: cannot create /tmp/check-
OK: 17 passed
--- PASS: Test (0.01s)
PASS
coverage: 46.8% of statements
ok launchpad.
=== RUN Test
-------
FAIL: statustracker_
statustracker_
c.Assert(
... obtained string = "installing"
... expected string = "uninstalled"
OOPS: 7 passed, 1 FAILED
--- FAIL: Test (0.51s)
FAIL
coverage: 100.0% of statements
FAIL launchpad.
# we always run in a fresh dir in tarmac
export GOPATH=$(mktemp -d)
trap 'rm -rf "$GOPATH"' EXIT
# this is a hack, but not sure tarmac is golang friendly
mkdir -p $GOPATH/
Snappy Tarmac (snappydevtarmac) wrote : | # |
The attempt to merge lp:~stevenwilkin/webdm/add-remove-snaps-via-api into lp:webdm failed. Below is the output from the failed tests.
Checking formatting
Installing godeps
Install golint
Obtaining dependencies
update gopkg.in/check.v1 failed; trying to fetch newer version
gopkg.in/check.v1 now at 64131543e7896d5
update github.
github.
update golang.org/x/crypto failed; trying to fetch newer version
golang.org/x/crypto now at 60052bd85f2d912
update gopkg.in/yaml.v2 failed; trying to fetch newer version
gopkg.in/yaml.v2 now at 49c95bdc2184325
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
Building
Running tests from /tmp/tmp.
=== RUN Test
OK: 4 passed
--- PASS: Test (0.01s)
PASS
coverage: 60.0% of statements
ok launchpad.
? launchpad.
=== RUN Test
WARNING: cannot create /tmp/check-
OK: 17 passed
--- PASS: Test (0.01s)
PASS
coverage: 46.8% of statements
ok launchpad.
=== RUN Test
-------
FAIL: statustracker_
statustracker_
c.Assert(
... obtained string = "installing"
... expected string = "uninstalled"
OOPS: 7 passed, 1 FAILED
--- FAIL: Test (0.51s)
FAIL
coverage: 100.0% of statements
FAIL launchpad.
# we always run in a fresh dir in tarmac
export GOPATH=$(mktemp -d)
trap 'rm -rf "$GOPATH"' EXIT
# this is a hack, but not sure tarmac is golang friendly
mkdir -p $GOPATH/
Snappy Tarmac (snappydevtarmac) wrote : | # |
The attempt to merge lp:~stevenwilkin/webdm/add-remove-snaps-via-api into lp:webdm failed. Below is the output from the failed tests.
Checking formatting
Installing godeps
Install golint
Obtaining dependencies
update github.
github.
update github.
update github.
update github.
update github.
update github.
update github.
update gopkg.in/check.v1 failed; trying to fetch newer version
update golang.org/x/crypto failed; trying to fetch newer version
update github.
update github.
update github.
update gopkg.in/yaml.v2 failed; trying to fetch newer version
1 repositories updated; 12 failed
# we always run in a fresh dir in tarmac
export GOPATH=$(mktemp -d)
trap 'rm -rf "$GOPATH"' EXIT
# this is a hack, but not sure tarmac is golang friendly
mkdir -p $GOPATH/
cp -a . $GOPATH/
cd $GOPATH/
./run-checks
godeps: cannot update "/tmp/tmp.
error: unable to create file interfaces/
error: unable to create file interfaces/
error: unable to create file interfaces/
error: unable to create file interfaces/
error: unable to create file interfaces/
error: unable to create file interfaces/
error: unable to create file interfaces/
error: unable to create file interfaces/
error: unable to create file interfaces/
error: unable to create file interfaces/core.go (No space left on device)
error: unable to create file interfaces/
fatal: cannot create directory at 'interfaces/dbus': No space left on device
warning: Clone succeeded, but checkout failed.
You can inspect what was checked out with 'git status'
and retry the checkout with 'git checkout -f HEAD'
godeps: cannot update "/tmp/tmp.
godeps: cannot update "/tmp/tmp.
Snappy Tarmac (snappydevtarmac) wrote : | # |
The attempt to merge lp:~stevenwilkin/webdm/add-remove-snaps-via-api into lp:webdm failed. Below is the output from the failed tests.
Checking formatting
Installing godeps
Install golint
Obtaining dependencies
update github.
github.
update github.
update github.
update github.
update github.
update golang.org/x/crypto failed; trying to fetch newer version
update gopkg.in/check.v1 failed; trying to fetch newer version
update github.
update github.
update github.
update github.
update gopkg.in/yaml.v2 failed; trying to fetch newer version
update github.
1 repositories updated; 12 failed
# we always run in a fresh dir in tarmac
export GOPATH=$(mktemp -d)
trap 'rm -rf "$GOPATH"' EXIT
# this is a hack, but not sure tarmac is golang friendly
mkdir -p $GOPATH/
cp -a . $GOPATH/
cd $GOPATH/
./run-checks
godeps: cannot update "/tmp/tmp.
error: unable to create file integration-
fatal: cannot create directory at 'integration-
warning: Clone succeeded, but checkout failed.
You can inspect what was checked out with 'git status'
and retry the checkout with 'git checkout -f HEAD'
godeps: cannot update "/tmp/tmp.
godeps: cannot update "/tmp/tmp.
godeps: cannot update "/tmp/tmp.
godeps: cannot update "/tmp/tmp.
godeps: cannot update "/tmp/tmp.
godeps: cannot update "/tmp/tmp.
godeps: cannot update "/tmp/tmp.
Snappy Tarmac (snappydevtarmac) wrote : | # |
The attempt to merge lp:~stevenwilkin/webdm/add-remove-snaps-via-api into lp:webdm failed. Below is the output from the failed tests.
Checking formatting
Installing godeps
Install golint
Obtaining dependencies
update golang.org/x/crypto failed; trying to fetch newer version
golang.org/x/crypto now at 60052bd85f2d912
update github.
github.
update gopkg.in/yaml.v2 failed; trying to fetch newer version
gopkg.in/yaml.v2 now at 49c95bdc2184325
update github.
github.
update github.
update github.
update github.
update github.
update github.
update gopkg.in/check.v1 failed; trying to fetch newer version
update github.
update github.
update github.
4 repositories updated; 9 failed
# we always run in a fresh dir in tarmac
export GOPATH=$(mktemp -d)
trap 'rm -rf "$GOPATH"' EXIT
# this is a hack, but not sure tarmac is golang friendly
mkdir -p $GOPATH/
cp -a . $GOPATH/
cd $GOPATH/
./run-checks
godeps: cannot update "/tmp/tmp.
/tmp/tmp.
godeps: cannot update "/tmp/tmp.
/tmp/tmp.
godeps: cannot update "/tmp/tmp.
error: could not lock config file /tmp/tmp.
error: could not lock config file /tmp/tmp.
error: could not lock config file /tmp/tmp.
fatal: Unable to create temporary file '/tmp/tmp.
godeps: cannot update "/tmp/tmp.
error: could not lock config file /tmp/tmp.
error: could not lock config file /tmp/tmp.
Snappy Tarmac (snappydevtarmac) wrote : | # |
The attempt to merge lp:~stevenwilkin/webdm/add-remove-snaps-via-api into lp:webdm failed. Below is the output from the failed tests.
Checking formatting
Installing godeps
Install golint
Obtaining dependencies
update gopkg.in/check.v1 failed; trying to fetch newer version
gopkg.in/check.v1 now at 64131543e7896d5
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
update github.
github.
update gopkg.in/yaml.v2 failed; trying to fetch newer version
gopkg.in/yaml.v2 now at 49c95bdc2184325
update github.
update github.
update github.
update github.
update golang.org/x/crypto failed; trying to fetch newer version
7 repositories updated; 6 failed
# we always run in a fresh dir in tarmac
export GOPATH=$(mktemp -d)
trap 'rm -rf "$GOPATH"' EXIT
# this is a hack, but not sure tarmac is golang friendly
mkdir -p $GOPATH/
cp -a . $GOPATH/
cd $GOPATH/
./run-checks
godeps: cannot update "/tmp/tmp.
error: unable to create temporary file: No space left on device
fatal: failed to write object
fatal: unpack-objects failed
godeps: cannot update "/tmp/tmp.
error: unable to create directory for /tmp/tmp.
fatal: Cannot update the ref 'HEAD'.
Unexpected end of command stream
godeps: cannot update "/tmp/tmp.
error: Unable to open /tmp/tmp.
fatal: Unable to create '/tmp/tmp.
Unexpected end of command stream
godeps: cannot update "/tmp/tmp.
error: Unable to append to /tmp/tmp.JIqQJ...
Snappy Tarmac (snappydevtarmac) wrote : | # |
The attempt to merge lp:~stevenwilkin/webdm/add-remove-snaps-via-api into lp:webdm failed. Below is the output from the failed tests.
Checking formatting
Installing godeps
Install golint
Obtaining dependencies
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
update gopkg.in/check.v1 failed; trying to fetch newer version
update github.
update github.
update github.
update golang.org/x/crypto failed; trying to fetch newer version
update github.
update gopkg.in/yaml.v2 failed; trying to fetch newer version
5 repositories updated; 8 failed
# we always run in a fresh dir in tarmac
export GOPATH=$(mktemp -d)
trap 'rm -rf "$GOPATH"' EXIT
# this is a hack, but not sure tarmac is golang friendly
mkdir -p $GOPATH/
cp -a . $GOPATH/
cd $GOPATH/
./run-checks
godeps: cannot update "/tmp/tmp.
error: unable to create file gen-coverage.sh (No space left on device)
error: unable to create file get-deps.sh (No space left on device)
fatal: cannot create directory at 'i18n': No space left on device
warning: Clone succeeded, but checkout failed.
You can inspect what was checked out with 'git status'
and retry the checkout with 'git checkout -f HEAD'
godeps: cannot update "/tmp/tmp.
godeps: cannot update "/tmp/tmp.
godeps: cannot update "/tmp/tmp.
godeps: cannot update "/tmp/tmp.
godeps: cannot update "/tmp/tmp.
Snappy Tarmac (snappydevtarmac) wrote : | # |
The attempt to merge lp:~stevenwilkin/webdm/add-remove-snaps-via-api into lp:webdm failed. Below is the output from the failed tests.
Checking formatting
Installing godeps
Install golint
Obtaining dependencies
update github.
github.
update gopkg.in/check.v1 failed; trying to fetch newer version
gopkg.in/check.v1 now at 64131543e7896d5
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update golang.org/x/crypto failed; trying to fetch newer version
golang.org/x/crypto now at 60052bd85f2d912
update github.
github.
update github.
update github.
github.
github.
update gopkg.in/yaml.v2 failed; trying to fetch newer version
gopkg.in/yaml.v2 now at 49c95bdc2184325
update github.
github.
update github.
github.
Building
# we always run in a fresh dir in tarmac
export GOPATH=$(mktemp -d)
# this is a hack, but not sure tarmac is golang friendly
mkdir -p $GOPATH/
cp -a . $GOPATH/
cd $GOPATH/
./run-checks
github.
github.
github.
github.
github.
github.
github.
golang.
golang.
golang.
golang.
golang.
github.
github.
launchpad.
github.
gopkg.in/yaml.v2
github.
github.
github.
github.
github.
github.
github.
github.
github.
github.
github.
Snappy Tarmac (snappydevtarmac) wrote : | # |
The `tree_dir` option for the target branch is not a lightweight checkout. Please ask a project administrator to resolve the issue, and try again.
Snappy Tarmac (snappydevtarmac) wrote : | # |
The attempt to merge lp:~stevenwilkin/webdm/add-remove-snaps-via-api into lp:webdm failed. Below is the output from the failed tests.
sed: -e expression #1, char 52: unknown option to `s'
Snappy Tarmac (snappydevtarmac) wrote : | # |
The attempt to merge lp:~stevenwilkin/webdm/add-remove-snaps-via-api into lp:webdm failed. Below is the output from the failed tests.
Checking formatting
Installing godeps
Install golint
Obtaining dependencies
update github.
github.
update github.
github.
update github.
github.
update golang.org/x/crypto failed; trying to fetch newer version
golang.org/x/crypto now at 60052bd85f2d912
update gopkg.in/yaml.v2 failed; trying to fetch newer version
gopkg.in/yaml.v2 now at 49c95bdc2184325
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update gopkg.in/check.v1 failed; trying to fetch newer version
gopkg.in/check.v1 now at 64131543e7896d5
update github.
github.
update github.
github.
Building
# we always run in a fresh dir in tarmac
export GOPATH=$(mktemp -d -p /mnt/tarmac/tmp)
trap 'rm -rf "$GOPATH"' EXIT
# this is a hack, but not sure tarmac is golang friendly
mkdir -p $GOPATH/
cp -a . $GOPATH/
cd $GOPATH/
./run-checks
github.
github.
github.
github.
github.
github.
github.
# github.
Assembler messages:
Fatal error: can't create $WORK/github.
golang.
go build golang.
golang.
go build golang.
golang.
go build golang.
gopkg.in/yaml.v2
go build gopkg....
Snappy Tarmac (snappydevtarmac) wrote : | # |
The attempt to merge lp:~stevenwilkin/webdm/add-remove-snaps-via-api into lp:webdm failed. Below is the output from the failed tests.
Checking formatting
Installing godeps
Install golint
Obtaining dependencies
update github.
github.
update golang.org/x/crypto failed; trying to fetch newer version
golang.org/x/crypto now at 60052bd85f2d912
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update gopkg.in/yaml.v2 failed; trying to fetch newer version
gopkg.in/yaml.v2 now at 49c95bdc2184325
update gopkg.in/check.v1 failed; trying to fetch newer version
gopkg.in/check.v1 now at 64131543e7896d5
update github.
github.
update github.
github.
update github.
github.
update github.
github.
Building
Running tests from /mnt/tarmac/
=== RUN Test
OK: 4 passed
--- PASS: Test (0.00s)
PASS
coverage: 60.0% of statements
ok launchpad.
? launchpad.
=== RUN Test
WARNING: cannot create /mnt/tarmac/
OK: 17 passed
--- PASS: Test (0.02s)
PASS
coverage: 46.8% of statements
ok launchpad.
=== RUN Test
OK: 8 passed
--- PASS: Test (0.41s)
PASS
coverage: 100.0% of statements
ok launchpad.
Running vet
Running lint
Obtaining npm dependencies
# we always run in a fresh dir in tarmac
export GOPATH=$(mktemp -d -p /mnt/tarmac/tmp); export TMPDIR=
trap 'rm -rf "$GOPATH"' EXIT
# this is a hack, but not sure tarmac is golang friendly
mkdir -p $GOPATH/
cp -a . $GOPATH/
cd $GOPATH/
./run-checks
github.
github.
github.
Preview Diff
1 | === modified file 'snappy/common_test.go' |
2 | --- snappy/common_test.go 2016-02-02 17:51:45 +0000 |
3 | +++ snappy/common_test.go 2016-04-21 06:04:15 +0000 |
4 | @@ -85,6 +85,14 @@ |
5 | return snaps, f.err |
6 | } |
7 | |
8 | +func (f *fakeSnapdClient) AddSnap(name string) (string, error) { |
9 | + return "", nil |
10 | +} |
11 | + |
12 | +func (f *fakeSnapdClient) RemoveSnap(name string) (string, error) { |
13 | + return "", nil |
14 | +} |
15 | + |
16 | var _ snapdClient = (*fakeSnapdClient)(nil) |
17 | |
18 | type fakeSnapdClientServicesNoExternalUI struct { |
19 | |
20 | === modified file 'snappy/converge.go' |
21 | --- snappy/converge.go 2016-02-02 17:51:45 +0000 |
22 | +++ snappy/converge.go 2016-04-21 06:04:15 +0000 |
23 | @@ -26,25 +26,22 @@ |
24 | |
25 | "github.com/ubuntu-core/snappy/client" |
26 | "github.com/ubuntu-core/snappy/snap" |
27 | - "github.com/ubuntu-core/snappy/snappy" |
28 | - "launchpad.net/webdm/webprogress" |
29 | ) |
30 | |
31 | type snapPkg struct { |
32 | - ID string `json:"id"` |
33 | - Name string `json:"name"` |
34 | - Origin string `json:"origin"` |
35 | - Version string `json:"version"` |
36 | - Description string `json:"description"` |
37 | - Icon string `json:"icon"` |
38 | - Status webprogress.Status `json:"status"` |
39 | - Message string `json:"message,omitempty"` |
40 | - IsError bool `json:"-"` |
41 | - Progress float64 `json:"progress,omitempty"` |
42 | - InstalledSize int64 `json:"installed_size,omitempty"` |
43 | - DownloadSize int64 `json:"download_size,omitempty"` |
44 | - Type snap.Type `json:"type,omitempty"` |
45 | - UIPort uint64 `json:"ui_port,omitempty"` |
46 | + ID string `json:"id"` |
47 | + Name string `json:"name"` |
48 | + Origin string `json:"origin"` |
49 | + Version string `json:"version"` |
50 | + Description string `json:"description"` |
51 | + Icon string `json:"icon"` |
52 | + Status string `json:"status"` |
53 | + Message string `json:"message,omitempty"` |
54 | + Progress float64 `json:"progress,omitempty"` |
55 | + InstalledSize int64 `json:"installed_size,omitempty"` |
56 | + DownloadSize int64 `json:"download_size,omitempty"` |
57 | + Type snap.Type `json:"type,omitempty"` |
58 | + UIPort uint64 `json:"ui_port,omitempty"` |
59 | } |
60 | |
61 | type response struct { |
62 | @@ -77,40 +74,28 @@ |
63 | return snapPkgs, nil |
64 | } |
65 | |
66 | -func (h *Handler) doRemovePackage(progress *webprogress.WebProgress, ID string) { |
67 | - pkgName := strings.Split(ID, ".")[0] |
68 | - |
69 | - err := snappy.Remove(pkgName, 0, progress) |
70 | - progress.ErrorChan <- err |
71 | - close(progress.ErrorChan) |
72 | -} |
73 | - |
74 | func (h *Handler) removePackage(ID string) error { |
75 | - progress, err := h.statusTracker.Add(ID, webprogress.OperationRemove) |
76 | + snap, err := h.snapdClient.Snap(ID) |
77 | if err != nil { |
78 | return err |
79 | } |
80 | |
81 | - go h.doRemovePackage(progress, ID) |
82 | - |
83 | - return nil |
84 | -} |
85 | - |
86 | -func (h *Handler) doInstallPackage(progress *webprogress.WebProgress, ID string) { |
87 | - _, err := snappy.Install(ID, 0, progress) |
88 | - progress.ErrorChan <- err |
89 | - close(progress.ErrorChan) |
90 | + h.statusTracker.TrackUninstall(snap) |
91 | + |
92 | + _, err = h.snapdClient.RemoveSnap(ID) |
93 | + return err |
94 | } |
95 | |
96 | func (h *Handler) installPackage(ID string) error { |
97 | - progress, err := h.statusTracker.Add(ID, webprogress.OperationInstall) |
98 | + snap, err := h.snapdClient.Snap(ID) |
99 | if err != nil { |
100 | return err |
101 | } |
102 | |
103 | - go h.doInstallPackage(progress, ID) |
104 | + h.statusTracker.TrackInstall(snap) |
105 | |
106 | - return nil |
107 | + _, err = h.snapdClient.AddSnap(ID) |
108 | + return err |
109 | } |
110 | |
111 | func hasPortInformation(snapQ *client.Snap) bool { |
112 | @@ -126,6 +111,7 @@ |
113 | Version: snapQ.Version, |
114 | Description: snapQ.Description, |
115 | Type: snap.Type(snapQ.Type), |
116 | + Status: h.statusTracker.Status(snapQ), |
117 | } |
118 | |
119 | if hasPortInformation(snapQ) { |
120 | @@ -150,25 +136,6 @@ |
121 | snap.DownloadSize = snapQ.DownloadSize |
122 | } |
123 | |
124 | - if stat, ok := h.statusTracker.Get(snap.ID); ok { |
125 | - snap.Status = stat.Status |
126 | - if stat.Done() { |
127 | - defer h.statusTracker.Remove(snap.ID) |
128 | - |
129 | - if stat.Error != nil { |
130 | - snap.Message = stat.Error.Error() |
131 | - snap.IsError = true |
132 | - } |
133 | - |
134 | - } else { |
135 | - snap.Progress = stat.Progress() |
136 | - } |
137 | - } else if isInstalled { |
138 | - snap.Status = webprogress.StatusInstalled |
139 | - } else { |
140 | - snap.Status = webprogress.StatusUninstalled |
141 | - } |
142 | - |
143 | return snap |
144 | } |
145 | |
146 | |
147 | === modified file 'snappy/converge_test.go' |
148 | --- snappy/converge_test.go 2016-02-02 17:51:45 +0000 |
149 | +++ snappy/converge_test.go 2016-04-21 06:04:15 +0000 |
150 | @@ -24,7 +24,7 @@ |
151 | "github.com/ubuntu-core/snappy/client" |
152 | "github.com/ubuntu-core/snappy/snap" |
153 | . "gopkg.in/check.v1" |
154 | - "launchpad.net/webdm/webprogress" |
155 | + "launchpad.net/webdm/statustracker" |
156 | ) |
157 | |
158 | type PackagePayloadSuite struct { |
159 | @@ -36,7 +36,7 @@ |
160 | |
161 | func (s *PackagePayloadSuite) SetUpTest(c *C) { |
162 | os.Setenv("SNAP_APP_DATA_PATH", c.MkDir()) |
163 | - s.h.statusTracker = webprogress.New() |
164 | + s.h.statusTracker = statustracker.New() |
165 | s.c = &fakeSnapdClient{} |
166 | s.h.setClient(s.c) |
167 | } |
168 | @@ -75,7 +75,7 @@ |
169 | |
170 | func (s *PayloadSuite) SetUpTest(c *C) { |
171 | os.Setenv("SNAP_APP_DATA_PATH", c.MkDir()) |
172 | - s.h.statusTracker = webprogress.New() |
173 | + s.h.statusTracker = statustracker.New() |
174 | s.h.setClient(&fakeSnapdClient{}) |
175 | } |
176 | |
177 | @@ -86,7 +86,7 @@ |
178 | |
179 | c.Check(q.Name, Equals, fakeSnap.Name) |
180 | c.Check(q.Version, Equals, fakeSnap.Version) |
181 | - c.Check(q.Status, Equals, webprogress.StatusInstalled) |
182 | + c.Check(q.Status, Equals, statustracker.StatusInstalled) |
183 | c.Check(q.Type, Equals, snap.Type(fakeSnap.Type)) |
184 | c.Check(q.UIPort, Equals, uint64(0)) |
185 | c.Check(q.Icon, Equals, "/icons/chatroom.ogra_icon.png") |
186 | @@ -101,7 +101,7 @@ |
187 | |
188 | c.Assert(q.Name, Equals, fakeSnap.Name) |
189 | c.Assert(q.Version, Equals, fakeSnap.Version) |
190 | - c.Assert(q.Status, Equals, webprogress.StatusInstalled) |
191 | + c.Assert(q.Status, Equals, statustracker.StatusInstalled) |
192 | c.Assert(q.Type, Equals, snap.Type(fakeSnap.Type)) |
193 | c.Assert(q.UIPort, Equals, uint64(0)) |
194 | } |
195 | @@ -114,7 +114,7 @@ |
196 | |
197 | c.Assert(q.Name, Equals, fakeSnap.Name) |
198 | c.Assert(q.Version, Equals, fakeSnap.Version) |
199 | - c.Assert(q.Status, Equals, webprogress.StatusInstalled) |
200 | + c.Assert(q.Status, Equals, statustracker.StatusInstalled) |
201 | c.Assert(q.Type, Equals, snap.Type(fakeSnap.Type)) |
202 | c.Assert(q.UIPort, Equals, uint64(1024)) |
203 | } |
204 | @@ -129,18 +129,18 @@ |
205 | |
206 | c.Assert(q.Name, Equals, fakeSnap.Name) |
207 | c.Assert(q.Version, Equals, fakeSnap.Version) |
208 | - c.Assert(q.Status, Equals, webprogress.StatusInstalled) |
209 | + c.Assert(q.Status, Equals, statustracker.StatusInstalled) |
210 | c.Assert(q.Type, Equals, snap.Type(fakeSnap.Type)) |
211 | c.Assert(q.UIPort, Equals, uint64(0)) |
212 | } |
213 | |
214 | func (s *PayloadSuite) TestPayloadSnapInstalling(c *C) { |
215 | fakeSnap := newDefaultSnap() |
216 | - fakeSnapID := fakeSnap.Name + "." + fakeSnap.Origin |
217 | - s.h.statusTracker.Add(fakeSnapID, webprogress.OperationInstall) |
218 | + fakeSnap.Status = client.StatusNotInstalled |
219 | + s.h.statusTracker.TrackInstall(fakeSnap) |
220 | |
221 | payload := s.h.snapToPayload(fakeSnap) |
222 | - c.Assert(payload.Status, Equals, webprogress.StatusInstalling) |
223 | + c.Assert(payload.Status, Equals, statustracker.StatusInstalling) |
224 | } |
225 | |
226 | type AllPackagesSuite struct { |
227 | @@ -152,7 +152,7 @@ |
228 | |
229 | func (s *AllPackagesSuite) SetUpTest(c *C) { |
230 | os.Setenv("SNAP_APP_DATA_PATH", c.MkDir()) |
231 | - s.h.statusTracker = webprogress.New() |
232 | + s.h.statusTracker = statustracker.New() |
233 | s.c = &fakeSnapdClient{} |
234 | s.h.setClient(s.c) |
235 | } |
236 | |
237 | === modified file 'snappy/handlers.go' |
238 | --- snappy/handlers.go 2016-02-23 16:00:47 +0000 |
239 | +++ snappy/handlers.go 2016-04-21 06:04:15 +0000 |
240 | @@ -26,21 +26,21 @@ |
241 | |
242 | "github.com/ubuntu-core/snappy/client" |
243 | "github.com/ubuntu-core/snappy/snappy" |
244 | - "launchpad.net/webdm/webprogress" |
245 | + "launchpad.net/webdm/statustracker" |
246 | |
247 | "github.com/gorilla/mux" |
248 | ) |
249 | |
250 | // Handler implements snappy's packages api. |
251 | type Handler struct { |
252 | - statusTracker *webprogress.StatusTracker |
253 | + statusTracker *statustracker.StatusTracker |
254 | snapdClient snapdClient |
255 | } |
256 | |
257 | // NewHandler creates an instance that implements snappy's packages api. |
258 | func NewHandler() *Handler { |
259 | return &Handler{ |
260 | - statusTracker: webprogress.New(), |
261 | + statusTracker: statustracker.New(), |
262 | snapdClient: client.New(nil), |
263 | } |
264 | } |
265 | @@ -92,10 +92,6 @@ |
266 | return |
267 | } |
268 | |
269 | - if payload.IsError { |
270 | - w.WriteHeader(http.StatusInternalServerError) |
271 | - } |
272 | - |
273 | if err := enc.Encode(payload); err != nil { |
274 | w.WriteHeader(http.StatusInternalServerError) |
275 | // give up on json |
276 | @@ -155,9 +151,6 @@ |
277 | case snappy.ErrAlreadyInstalled: |
278 | status = http.StatusOK |
279 | msg = "Installed" |
280 | - case webprogress.ErrPackageInstallInProgress: |
281 | - status = http.StatusBadRequest |
282 | - msg = "Operation in progress" |
283 | case snappy.ErrPackageNotFound: |
284 | status = http.StatusNotFound |
285 | msg = "Package not found" |
286 | |
287 | === modified file 'snappy/handlers_test.go' |
288 | --- snappy/handlers_test.go 2016-02-02 17:50:38 +0000 |
289 | +++ snappy/handlers_test.go 2016-04-21 06:04:15 +0000 |
290 | @@ -23,7 +23,6 @@ |
291 | "os" |
292 | |
293 | "github.com/ubuntu-core/snappy/client" |
294 | - "launchpad.net/webdm/webprogress" |
295 | |
296 | . "gopkg.in/check.v1" |
297 | ) |
298 | @@ -37,7 +36,6 @@ |
299 | |
300 | func (s *HandlersSuite) SetUpTest(c *C) { |
301 | os.Setenv("SNAP_APP_DATA_PATH", c.MkDir()) |
302 | - s.h.statusTracker = webprogress.New() |
303 | s.c = &fakeSnapdClient{} |
304 | s.h.setClient(s.c) |
305 | } |
306 | |
307 | === modified file 'snappy/snapd_client.go' |
308 | --- snappy/snapd_client.go 2016-02-02 17:50:37 +0000 |
309 | +++ snappy/snapd_client.go 2016-04-21 06:04:15 +0000 |
310 | @@ -26,4 +26,6 @@ |
311 | Services(pkg string) (map[string]*client.Service, error) |
312 | Snap(name string) (*client.Snap, error) |
313 | FilterSnaps(filter client.SnapFilter) (map[string]*client.Snap, error) |
314 | + AddSnap(name string) (string, error) |
315 | + RemoveSnap(name string) (string, error) |
316 | } |
317 | |
318 | === added directory 'statustracker' |
319 | === added file 'statustracker/statustracker.go' |
320 | --- statustracker/statustracker.go 1970-01-01 00:00:00 +0000 |
321 | +++ statustracker/statustracker.go 2016-04-21 06:04:15 +0000 |
322 | @@ -0,0 +1,134 @@ |
323 | +/* |
324 | + * Copyright (C) 2016 Canonical Ltd |
325 | + * |
326 | + * This program is free software: you can redistribute it and/or modify |
327 | + * it under the terms of the GNU General Public License version 3 as |
328 | + * published by the Free Software Foundation. |
329 | + * |
330 | + * This program is distributed in the hope that it will be useful, |
331 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
332 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
333 | + * GNU General Public License for more details. |
334 | + * |
335 | + * You should have received a copy of the GNU General Public License |
336 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
337 | + * |
338 | + */ |
339 | + |
340 | +// Package statustracker enables the tracking of snap installation and removal. |
341 | +// |
342 | +// Once a snap has been marked as "installing" it will remain in that |
343 | +// state until it's status as provided by snapd indicates that it is installed |
344 | +// on the system. Similarly for removing snaps. Status lifecycle is thus: |
345 | +// |
346 | +// "uninstalled" -> "installing" -> "installed" -> "uninstalling" and repeat |
347 | +package statustracker |
348 | + |
349 | +import ( |
350 | + "sync" |
351 | + "time" |
352 | + |
353 | + "github.com/ubuntu-core/snappy/client" |
354 | +) |
355 | + |
356 | +const ( |
357 | + // StatusInstalled indicates the package is in an installed state. |
358 | + StatusInstalled = "installed" |
359 | + // StatusUninstalled indicates the package is in an uninstalled state. |
360 | + StatusUninstalled = "uninstalled" |
361 | + // StatusInstalling indicates the package is in an installing state. |
362 | + StatusInstalling = "installing" |
363 | + // StatusUninstalling indicates the package is in an uninstalling state. |
364 | + StatusUninstalling = "uninstalling" |
365 | +) |
366 | + |
367 | +var trackerDuration = 1 * time.Minute |
368 | + |
369 | +// StatusTracker tracks statuses |
370 | +type StatusTracker struct { |
371 | + sync.Mutex |
372 | + statuses map[string]string |
373 | +} |
374 | + |
375 | +// New returns a new status tracker |
376 | +func New() *StatusTracker { |
377 | + return &StatusTracker{ |
378 | + statuses: make(map[string]string), |
379 | + } |
380 | +} |
381 | + |
382 | +// Status returns the status of the given snap |
383 | +func (s *StatusTracker) Status(snap *client.Snap) string { |
384 | + s.Lock() |
385 | + defer s.Unlock() |
386 | + |
387 | + status, ok := s.statuses[snapID(snap)] |
388 | + if !ok { |
389 | + return translateStatus(snap) |
390 | + } |
391 | + |
392 | + if hasCompleted(status, snap) { |
393 | + delete(s.statuses, snapID(snap)) |
394 | + return translateStatus(snap) |
395 | + } |
396 | + |
397 | + return status |
398 | +} |
399 | + |
400 | +// TrackInstall tracks the installation of the given snap |
401 | +func (s *StatusTracker) TrackInstall(snap *client.Snap) { |
402 | + if isInstalled(snap) { |
403 | + return |
404 | + } |
405 | + |
406 | + s.trackOperation(snapID(snap), StatusInstalling) |
407 | +} |
408 | + |
409 | +func (s *StatusTracker) trackOperation(id, operation string) { |
410 | + s.Lock() |
411 | + defer s.Unlock() |
412 | + |
413 | + s.statuses[id] = operation |
414 | + |
415 | + go func() { |
416 | + <-time.After(trackerDuration) |
417 | + s.Lock() |
418 | + delete(s.statuses, id) |
419 | + s.Unlock() |
420 | + }() |
421 | +} |
422 | + |
423 | +// TrackUninstall tracks the removal of the given snap |
424 | +func (s *StatusTracker) TrackUninstall(snap *client.Snap) { |
425 | + if !isInstalled(snap) { |
426 | + return |
427 | + } |
428 | + |
429 | + s.trackOperation(snapID(snap), StatusUninstalling) |
430 | +} |
431 | + |
432 | +func snapID(s *client.Snap) string { |
433 | + return s.Name + "." + s.Origin |
434 | +} |
435 | + |
436 | +func isInstalled(s *client.Snap) bool { |
437 | + return s.Status == client.StatusInstalled || s.Status == client.StatusActive |
438 | +} |
439 | + |
440 | +// translate a status from the snappy world into one webdm understands |
441 | +func translateStatus(s *client.Snap) string { |
442 | + if isInstalled(s) { |
443 | + return StatusInstalled |
444 | + } |
445 | + |
446 | + return StatusUninstalled |
447 | +} |
448 | + |
449 | +// has the tracked process denoted by status completed? |
450 | +func hasCompleted(status string, snap *client.Snap) bool { |
451 | + if status == StatusInstalling { |
452 | + return isInstalled(snap) |
453 | + } |
454 | + |
455 | + return !isInstalled(snap) |
456 | +} |
457 | |
458 | === added file 'statustracker/statustracker_test.go' |
459 | --- statustracker/statustracker_test.go 1970-01-01 00:00:00 +0000 |
460 | +++ statustracker/statustracker_test.go 2016-04-21 06:04:15 +0000 |
461 | @@ -0,0 +1,121 @@ |
462 | +/* |
463 | + * Copyright (C) 2016 Canonical Ltd |
464 | + * |
465 | + * This program is free software: you can redistribute it and/or modify |
466 | + * it under the terms of the GNU General Public License version 3 as |
467 | + * published by the Free Software Foundation. |
468 | + * |
469 | + * This program is distributed in the hope that it will be useful, |
470 | + * but WITHOUT ANY WARRANTY; without even the implied warranty of |
471 | + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
472 | + * GNU General Public License for more details. |
473 | + * |
474 | + * You should have received a copy of the GNU General Public License |
475 | + * along with this program. If not, see <http://www.gnu.org/licenses/>. |
476 | + * |
477 | + */ |
478 | + |
479 | +package statustracker |
480 | + |
481 | +import ( |
482 | + "testing" |
483 | + "time" |
484 | + |
485 | + "github.com/ubuntu-core/snappy/client" |
486 | + |
487 | + . "gopkg.in/check.v1" |
488 | +) |
489 | + |
490 | +func Test(t *testing.T) { TestingT(t) } |
491 | + |
492 | +type StatusTrackerSuite struct { |
493 | + t *StatusTracker |
494 | +} |
495 | + |
496 | +var _ = Suite(&StatusTrackerSuite{}) |
497 | + |
498 | +func (s *StatusTrackerSuite) SetUpTest(c *C) { |
499 | + s.t = New() |
500 | +} |
501 | + |
502 | +func (s *StatusTrackerSuite) TestTranslateStatus(c *C) { |
503 | + tests := []struct { |
504 | + snapStatus string |
505 | + status string |
506 | + }{ |
507 | + {client.StatusInstalled, StatusInstalled}, |
508 | + {client.StatusActive, StatusInstalled}, |
509 | + {client.StatusNotInstalled, StatusUninstalled}, |
510 | + {client.StatusRemoved, StatusUninstalled}, |
511 | + } |
512 | + |
513 | + for _, tt := range tests { |
514 | + snap := &client.Snap{Status: tt.snapStatus} |
515 | + c.Assert(translateStatus(snap), Equals, tt.status) |
516 | + } |
517 | +} |
518 | + |
519 | +func (s *StatusTrackerSuite) TestHasCompleted(c *C) { |
520 | + tests := []struct { |
521 | + status string |
522 | + snapStatus string |
523 | + completed bool |
524 | + }{ |
525 | + {StatusInstalling, client.StatusInstalled, true}, |
526 | + {StatusInstalling, client.StatusRemoved, false}, |
527 | + {StatusUninstalling, client.StatusRemoved, true}, |
528 | + {StatusUninstalling, client.StatusActive, false}, |
529 | + } |
530 | + |
531 | + for _, tt := range tests { |
532 | + snap := &client.Snap{Status: tt.snapStatus} |
533 | + c.Assert(hasCompleted(tt.status, snap), Equals, tt.completed) |
534 | + } |
535 | +} |
536 | + |
537 | +func (s *StatusTrackerSuite) TestUntrackedSnap(c *C) { |
538 | + snap := &client.Snap{Status: client.StatusInstalled} |
539 | + c.Assert(s.t.Status(snap), Equals, StatusInstalled) |
540 | +} |
541 | + |
542 | +func (s *StatusTrackerSuite) TestTrackInstallAlreadyInstalled(c *C) { |
543 | + snap := &client.Snap{Status: client.StatusInstalled} |
544 | + s.t.TrackInstall(snap) |
545 | + c.Assert(s.t.Status(snap), Equals, StatusInstalled) |
546 | +} |
547 | + |
548 | +func (s *StatusTrackerSuite) TestTrackInstall(c *C) { |
549 | + snap := &client.Snap{Status: client.StatusNotInstalled} |
550 | + s.t.TrackInstall(snap) |
551 | + c.Assert(s.t.Status(snap), Equals, StatusInstalling) |
552 | + // installation completes |
553 | + snap.Status = client.StatusActive |
554 | + c.Assert(s.t.Status(snap), Equals, StatusInstalled) |
555 | +} |
556 | + |
557 | +func (s *StatusTrackerSuite) TestTrackInstallExpiry(c *C) { |
558 | + trackerDuration = 200 * time.Millisecond |
559 | + |
560 | + snap := &client.Snap{Status: client.StatusNotInstalled} |
561 | + s.t.TrackInstall(snap) |
562 | + c.Assert(s.t.Status(snap), Equals, StatusInstalling) |
563 | + |
564 | + // don't track indefinitely if operation fails |
565 | + time.Sleep(trackerDuration * 2) |
566 | + c.Assert(s.t.Status(snap), Equals, StatusUninstalled) |
567 | +} |
568 | + |
569 | +func (s *StatusTrackerSuite) TestTrackUninstallNotInstalled(c *C) { |
570 | + snap := &client.Snap{Status: client.StatusNotInstalled} |
571 | + s.t.TrackUninstall(snap) |
572 | + c.Assert(s.t.Status(snap), Equals, StatusUninstalled) |
573 | +} |
574 | + |
575 | +func (s *StatusTrackerSuite) TestTrackUninstall(c *C) { |
576 | + snap := &client.Snap{Status: client.StatusInstalled} |
577 | + s.t.TrackUninstall(snap) |
578 | + c.Assert(s.t.Status(snap), Equals, StatusUninstalling) |
579 | + // uninstallation completes |
580 | + snap.Status = client.StatusRemoved |
581 | + c.Assert(s.t.Status(snap), Equals, StatusUninstalled) |
582 | +} |
583 | |
584 | === removed file 'webprogress/meter.go' |
585 | --- webprogress/meter.go 2015-12-11 15:07:16 +0000 |
586 | +++ webprogress/meter.go 1970-01-01 00:00:00 +0000 |
587 | @@ -1,159 +0,0 @@ |
588 | -/* |
589 | - * Copyright (C) 2014-2015 Canonical Ltd |
590 | - * |
591 | - * This program is free software: you can redistribute it and/or modify |
592 | - * it under the terms of the GNU General Public License version 3 as |
593 | - * published by the Free Software Foundation. |
594 | - * |
595 | - * This program is distributed in the hope that it will be useful, |
596 | - * but WITHOUT ANY WARRANTY; without even the implied warranty of |
597 | - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
598 | - * GNU General Public License for more details. |
599 | - * |
600 | - * You should have received a copy of the GNU General Public License |
601 | - * along with this program. If not, see <http://www.gnu.org/licenses/>. |
602 | - * |
603 | - */ |
604 | - |
605 | -package webprogress |
606 | - |
607 | -import "github.com/ubuntu-core/snappy/progress" |
608 | - |
609 | -// Operation indicates the desired operation to perform |
610 | -type Operation uint |
611 | - |
612 | -const ( |
613 | - // OperationInstall indicates that a package needs installing |
614 | - OperationInstall Operation = iota |
615 | - // OperationRemove indicates that a package needs uninstalling |
616 | - OperationRemove |
617 | -) |
618 | - |
619 | -// Status indicates the status a package is in. |
620 | -type Status string |
621 | - |
622 | -const ( |
623 | - // StatusInstalled indicates the package is in an installed state. |
624 | - StatusInstalled Status = "installed" |
625 | - // StatusUninstalled indicates the package is in an uninstalled state. |
626 | - StatusUninstalled Status = "uninstalled" |
627 | - // StatusInstalling indicates the package is in an installing state. |
628 | - StatusInstalling Status = "installing" |
629 | - // StatusUninstalling indicates the package is in an uninstalling state. |
630 | - StatusUninstalling Status = "uninstalling" |
631 | -) |
632 | - |
633 | -// WebProgress show progress on the terminal |
634 | -type WebProgress struct { |
635 | - progress.Meter |
636 | - total float64 |
637 | - current float64 |
638 | - Status Status |
639 | - statusMessage string |
640 | - notificationMessage string |
641 | - Error error |
642 | - ErrorChan chan error |
643 | - operation Operation |
644 | -} |
645 | - |
646 | -// NewWebProgress returns a new WebProgress type |
647 | -func NewWebProgress(op Operation) *WebProgress { |
648 | - var status Status |
649 | - switch op { |
650 | - case OperationInstall: |
651 | - status = StatusInstalling |
652 | - case OperationRemove: |
653 | - status = StatusUninstalling |
654 | - default: |
655 | - panic("Not a valid Operation") |
656 | - } |
657 | - |
658 | - t := &WebProgress{ |
659 | - ErrorChan: make(chan error), |
660 | - Status: status, |
661 | - operation: op, |
662 | - } |
663 | - |
664 | - go func() { |
665 | - err := <-t.ErrorChan |
666 | - |
667 | - if err != nil { |
668 | - t.Status = StatusUninstalled |
669 | - t.Error = err |
670 | - } else { |
671 | - var status Status |
672 | - switch op { |
673 | - case OperationInstall: |
674 | - status = StatusInstalled |
675 | - case OperationRemove: |
676 | - status = StatusUninstalled |
677 | - default: |
678 | - panic("Not a valid Operation") |
679 | - } |
680 | - t.Status = status |
681 | - } |
682 | - }() |
683 | - |
684 | - return t |
685 | -} |
686 | - |
687 | -// Start starts showing progress |
688 | -func (t *WebProgress) Start(pkgName string, total float64) { |
689 | - t.total = total |
690 | -} |
691 | - |
692 | -// Set sets the progress to the current value |
693 | -func (t *WebProgress) Set(current float64) { |
694 | - t.current = current |
695 | -} |
696 | - |
697 | -// SetTotal set the total steps needed |
698 | -func (t *WebProgress) SetTotal(total float64) { |
699 | - t.total = total |
700 | -} |
701 | - |
702 | -// Finished stops displaying the progress |
703 | -func (t *WebProgress) Finished() { |
704 | -} |
705 | - |
706 | -// Done returns a boolean value indicating that the progress report |
707 | -// has finished with no concerns if it was succesfull or not. |
708 | -func (t *WebProgress) Done() bool { |
709 | - return t.Status == StatusInstalled || t.Status == StatusUninstalled |
710 | -} |
711 | - |
712 | -// Write is there so that progress can implement a Writer and can be |
713 | -// used to display progress of io operations |
714 | -// |
715 | -// This is not needed for web progress. |
716 | -func (t *WebProgress) Write(p []byte) (n int, err error) { |
717 | - t.current += float64(len(p)) |
718 | - return len(p), nil |
719 | -} |
720 | - |
721 | -// Spin advances a spinner, i.e. can be used to show progress for operations |
722 | -// that have a unknown duration |
723 | -func (t *WebProgress) Spin(msg string) { |
724 | - t.statusMessage = msg |
725 | -} |
726 | - |
727 | -// Agreed asks the user whether they agree to the given license text |
728 | -func (t *WebProgress) Agreed(intro, license string) bool { |
729 | - // TODO needs implementation |
730 | - return true |
731 | -} |
732 | - |
733 | -// Notify the user of miscelaneous events |
734 | -func (t *WebProgress) Notify(msg string) { |
735 | - // TODO needs implementation producer/consumer |
736 | - t.notificationMessage = msg |
737 | -} |
738 | - |
739 | -// Progress returns the current progress |
740 | -func (t *WebProgress) Progress() float64 { |
741 | - if t.total == 0 { |
742 | - return 0 |
743 | - } |
744 | - |
745 | - return t.current * 100 / t.total |
746 | -} |
747 | |
748 | === removed file 'webprogress/progress.go' |
749 | --- webprogress/progress.go 2015-05-06 14:41:13 +0000 |
750 | +++ webprogress/progress.go 1970-01-01 00:00:00 +0000 |
751 | @@ -1,72 +0,0 @@ |
752 | -/* |
753 | - * Copyright (C) 2014-2015 Canonical Ltd |
754 | - * |
755 | - * This program is free software: you can redistribute it and/or modify |
756 | - * it under the terms of the GNU General Public License version 3 as |
757 | - * published by the Free Software Foundation. |
758 | - * |
759 | - * This program is distributed in the hope that it will be useful, |
760 | - * but WITHOUT ANY WARRANTY; without even the implied warranty of |
761 | - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
762 | - * GNU General Public License for more details. |
763 | - * |
764 | - * You should have received a copy of the GNU General Public License |
765 | - * along with this program. If not, see <http://www.gnu.org/licenses/>. |
766 | - * |
767 | - */ |
768 | - |
769 | -package webprogress |
770 | - |
771 | -import ( |
772 | - "errors" |
773 | - "sync" |
774 | -) |
775 | - |
776 | -var ( |
777 | - // ErrPackageInstallInProgress indicates that installation of the package is |
778 | - // already in progress. |
779 | - ErrPackageInstallInProgress = errors.New("package installion in progress") |
780 | -) |
781 | - |
782 | -// StatusTracker holds the state of all operations that require progress information. |
783 | -type StatusTracker struct { |
784 | - status map[string]*WebProgress |
785 | - l sync.Mutex |
786 | -} |
787 | - |
788 | -// New creates a new Status. |
789 | -func New() *StatusTracker { |
790 | - return &StatusTracker{status: make(map[string]*WebProgress)} |
791 | -} |
792 | - |
793 | -// Add add pkg to the list of progresses to track, it is idempotent |
794 | -func (i *StatusTracker) Add(pkg string, op Operation) (*WebProgress, error) { |
795 | - i.l.Lock() |
796 | - defer i.l.Unlock() |
797 | - |
798 | - if _, ok := i.status[pkg]; ok { |
799 | - return nil, ErrPackageInstallInProgress |
800 | - } |
801 | - |
802 | - i.status[pkg] = NewWebProgress(op) |
803 | - |
804 | - return i.status[pkg], nil |
805 | -} |
806 | - |
807 | -// Remove removes pkg to the list of progresses to track, it is a no op |
808 | -// to remove multiple times. |
809 | -func (i *StatusTracker) Remove(pkg string) { |
810 | - i.l.Lock() |
811 | - defer i.l.Unlock() |
812 | - |
813 | - delete(i.status, pkg) |
814 | -} |
815 | - |
816 | -// Get returns a *WebProgress corresponding to pkg or nil if not tracked. |
817 | -func (i *StatusTracker) Get(pkg string) (*WebProgress, bool) { |
818 | - i.l.Lock() |
819 | - defer i.l.Unlock() |
820 | - |
821 | - w, ok := i.status[pkg] |
822 | - return w, ok |
823 | -} |
The attempt to merge lp:~stevenwilkin/webdm/add-remove-snaps-via-api into lp:webdm failed. Below is the output from the failed tests.
Checking formatting com/davecheney/ mdns failed; trying to fetch newer version com/davecheney/ mdns now at de174d86a3d3e87 bfad9cb66cedd04 33380b67b0 com/mvo5/ uboot-go failed; trying to fetch newer version com/mvo5/ uboot-go now at 69978a3e4b05cca 9d7cfee489b3453 dfed45e72c com/gosexy/ gettext failed; trying to fetch newer version com/gosexy/ gettext now at 98b7b91596d20b9 6909e6b60d57411 547dd9959c com/ubuntu- core/snappy failed; trying to fetch newer version com/ubuntu- core/snappy now at 5bcb20229bb884b 85144eab0fe5db7 aa05a27ebf 93457e8811b0cf2 6b773de469 bcc6bd5a76287eb 75ea96c673 com/davecheney/ gmx failed; trying to fetch newer version com/davecheney/ gmx now at d765420e7fbacce cb2a38cf2a02701 fe3e0888a3 com/gorilla/ context failed; trying to fetch newer version com/gorilla/ context now at 50c25fb3b2b3b3c c724e9b6ac75fb4 4b3bccd0da com/gorilla/ mux failed; trying to fetch newer version com/gorilla/ mux now at e444e69cbd2e2e3 e0749a2f3c717ce c491552bbf com/miekg/ dns failed; trying to fetch newer version com/miekg/ dns now at 5a357a6fc5e8526 8b929350aa6423e 2d56dcc4ff com/mvo5/ goconfigparser failed; trying to fetch newer version com/mvo5/ goconfigparser now at 26426272dda20cc 76aa1fa44286dc7 43d2972fe8 6fb6c4e0d370a05 f24a0bf213 com/cheggaaa/ pb failed; trying to fetch newer version com/cheggaaa/ pb now at e8c7cc515bfde3e 267957a3b110080 ceed51354e
Installing godeps
Install golint
Obtaining dependencies
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update golang.org/x/crypto failed; trying to fetch newer version
golang.org/x/crypto now at 60052bd85f2d912
update gopkg.in/check.v1 failed; trying to fetch newer version
gopkg.in/check.v1 now at 64131543e7896d5
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update github.
github.
update gopkg.in/yaml.v2 failed; trying to fetch newer version
gopkg.in/yaml.v2 now at 49c95bdc2184325
update github.
github.
Building
# we always run in a fresh dir in tarmac
export GOPATH=$(mktemp -d)
trap 'rm -rf "$GOPATH"' EXIT
# this is a hack, but not sure tarmac is golang friendly src/launchpad. net/webdm src/launchpad. net/webdm/ src/launchpad. net/webdm
mkdir -p $GOPATH/
cp -a . $GOPATH/
cd $GOPATH/
./run-checks com/davecheney/ gmx com/miekg/ dns com/gorilla/ context com/gorilla/ mux com/ubuntu- core/snappy/ dirs com/ubuntu- core/snappy/ logger com/ubuntu- core/snappy/ helpers com/davecheney/ mdns net/webdm/ avahi org/x/crypto/ cast5 org/x/crypto/ openpgp/ elgamal org/x/crypto/ openpgp/ errors org/x/crypto/ openpgp/ s2k org/x/crypto/ openpgp/ packet com/ubuntu- core/snappy/ asserts com/ubuntu- core/snappy/ snap com/ubuntu- core/snappy/ arch com/ubuntu- core/snappy/ systemd com/ubuntu- core/snappy/ client com/ubuntu- core/snappy/ coreconfig com/gosexy/ gettext com/ubuntu- core/snappy/ oauth com/mvo5/ goconfigparser com/mvo5/ uboot-go/ uenv com/ubuntu- core/snappy/ partition com/ubuntu- core/snap. ..
github.
github.
github.
github.
github.
github.
github.
github.
launchpad.
golang.
golang.
golang.
golang.
gopkg.in/yaml.v2
golang.
github.
github.
github.
github.
github.
github.
github.
github.
github.
github.
github.
github.