[ARVADOS] updated: d5142a69848df7fa506b8cb16a76cb621598769a
git at public.curoverse.com
git at public.curoverse.com
Mon May 18 23:12:53 EDT 2015
Summary of changes:
.../app/assets/javascripts/infinite_scroll.js | 8 +--
apps/workbench/app/assets/javascripts/tab_panes.js | 18 ++++-
docker/arvdock | 55 +++++++++-----
docker/sso/database.yml.in | 22 ++++++
sdk/go/keepclient/keepclient.go | 23 +++---
sdk/go/keepclient/keepclient_test.go | 84 ++++++++++------------
sdk/go/keepclient/support.go | 8 +--
sdk/python/arvados/keep.py | 7 +-
.../20150512193020_read_only_on_keep_services.rb | 6 +-
services/keepproxy/keepproxy_test.go | 4 +-
services/keepstore/pull_worker.go | 2 +-
11 files changed, 141 insertions(+), 96 deletions(-)
create mode 100644 docker/sso/database.yml.in
via d5142a69848df7fa506b8cb16a76cb621598769a (commit)
via b085f051e459981a385c95c4ae147546312c08d9 (commit)
via f1827e2044aff826e63826880b296a59c4a17e2a (commit)
via 6702cdabbecef52d342c6f8c67c22cd15377165c (commit)
via e41260f6a5b14753fcad27fbd0e0515a051a4671 (commit)
via d39be4ad92ae92f72367d633f92208f8487ba1b2 (commit)
via 47b10ff0fa5416a5c9fadfd73bb69b1817aac1be (commit)
via 37fe7a30a22b669818a185df137c34da09022af3 (commit)
via 77f11805c9daf93356ad083f03841b546aab9c7d (commit)
via 60460bc7b4a04c04aec915221f808c3577343460 (commit)
via 311dc34b42e16f26b82bdf168dc11b39557dac19 (commit)
via d14dd75b263d8f999603b66d23f74667d36a2412 (commit)
via 17fb6bca5786bad5cff83a187e70adbca9c1d14a (commit)
via 7e78bad94194f9ce7a39888cbac30eaf4fbf4af7 (commit)
via acf8433929b812913208e0868599d3a507c7cf34 (commit)
via bfee777f81cbdb447a107f47d6077994e93e4b8c (commit)
via 7538d084fa8778289053f62a6fb8d3ea04868258 (commit)
via e5f039f2e451790ff3838c5810a22a0749d18f6d (commit)
via 37ab170974e6b15c961605b8ed51678ed58a3a52 (commit)
from 1f2a1c4d4e12109291578a70e1a1316960343eeb (commit)
Those revisions listed above that are new to this repository have
not appeared on any other notification email; so we list those
revisions in full, below.
commit d5142a69848df7fa506b8cb16a76cb621598769a
Author: Radhika Chippada <radhika at curoverse.com>
Date: Mon May 18 23:11:59 2015 -0400
4717: rename writableRoots as writableLocalRoots.
diff --git a/sdk/go/keepclient/keepclient.go b/sdk/go/keepclient/keepclient.go
index 5ebdf0a..f82e5c7 100644
--- a/sdk/go/keepclient/keepclient.go
+++ b/sdk/go/keepclient/keepclient.go
@@ -38,8 +38,8 @@ type KeepClient struct {
Want_replicas int
Using_proxy bool
localRoots *map[string]string
+ writableLocalRoots *map[string]string
gatewayRoots *map[string]string
- writableRoots *map[string]string
lock sync.RWMutex
Client *http.Client
}
@@ -195,12 +195,12 @@ func (kc *KeepClient) GatewayRoots() map[string]string {
return *kc.gatewayRoots
}
-// WritableRoots() returns the map of writable Keep services:
+// WritableLocalRoots() returns the map of writable local Keep services:
// uuid -> baseURI.
-func (kc *KeepClient) WritableRoots() map[string]string {
+func (kc *KeepClient) WritableLocalRoots() map[string]string {
kc.lock.RLock()
defer kc.lock.RUnlock()
- return *kc.writableRoots
+ return *kc.writableLocalRoots
}
// SetServiceRoots updates the localRoots and gatewayRoots maps,
@@ -210,24 +210,27 @@ func (kc *KeepClient) WritableRoots() map[string]string {
// caller can reuse/modify them after SetServiceRoots returns, but
// they should not be modified by any other goroutine while
// SetServiceRoots is running.
-func (kc *KeepClient) SetServiceRoots(newLocals, newGateways map[string]string, writableRoots map[string]string) {
+func (kc *KeepClient) SetServiceRoots(newLocals, newWritableLocals map[string]string, newGateways map[string]string) {
locals := make(map[string]string)
for uuid, root := range newLocals {
locals[uuid] = root
}
+
+ writables := make(map[string]string)
+ for uuid, root := range newWritableLocals {
+ writables[uuid] = root
+ }
+
gateways := make(map[string]string)
for uuid, root := range newGateways {
gateways[uuid] = root
}
- writables := make(map[string]string)
- for uuid, root := range writableRoots {
- writables[uuid] = root
- }
+
kc.lock.Lock()
defer kc.lock.Unlock()
kc.localRoots = &locals
+ kc.writableLocalRoots = &writables
kc.gatewayRoots = &gateways
- kc.writableRoots = &writables
}
// getSortedRoots returns a list of base URIs of Keep services, in the
diff --git a/sdk/go/keepclient/keepclient_test.go b/sdk/go/keepclient/keepclient_test.go
index e22ffe0..c1f6a3e 100644
--- a/sdk/go/keepclient/keepclient_test.go
+++ b/sdk/go/keepclient/keepclient_test.go
@@ -243,17 +243,17 @@ func (s *StandaloneSuite) TestPutB(c *C) {
kc.Want_replicas = 2
arv.ApiToken = "abc123"
localRoots := make(map[string]string)
- writableRoots := make(map[string]string)
+ writableLocalRoots := make(map[string]string)
ks := RunSomeFakeKeepServers(st, 5)
for i, k := range ks {
localRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
- writableRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
+ writableLocalRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
defer k.listener.Close()
}
- kc.SetServiceRoots(localRoots, nil, writableRoots)
+ kc.SetServiceRoots(localRoots, writableLocalRoots, nil)
kc.PutB([]byte("foo"))
@@ -288,17 +288,17 @@ func (s *StandaloneSuite) TestPutHR(c *C) {
kc.Want_replicas = 2
arv.ApiToken = "abc123"
localRoots := make(map[string]string)
- writableRoots := make(map[string]string)
+ writableLocalRoots := make(map[string]string)
ks := RunSomeFakeKeepServers(st, 5)
for i, k := range ks {
localRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
- writableRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
+ writableLocalRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
defer k.listener.Close()
}
- kc.SetServiceRoots(localRoots, nil, writableRoots)
+ kc.SetServiceRoots(localRoots, writableLocalRoots, nil)
reader, writer := io.Pipe()
@@ -344,23 +344,23 @@ func (s *StandaloneSuite) TestPutWithFail(c *C) {
kc.Want_replicas = 2
arv.ApiToken = "abc123"
localRoots := make(map[string]string)
- writableRoots := make(map[string]string)
+ writableLocalRoots := make(map[string]string)
ks1 := RunSomeFakeKeepServers(st, 4)
ks2 := RunSomeFakeKeepServers(fh, 1)
for i, k := range ks1 {
localRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
- writableRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
+ writableLocalRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
defer k.listener.Close()
}
for i, k := range ks2 {
localRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i+len(ks1))] = k.url
- writableRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i+len(ks1))] = k.url
+ writableLocalRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i+len(ks1))] = k.url
defer k.listener.Close()
}
- kc.SetServiceRoots(localRoots, nil, writableRoots)
+ kc.SetServiceRoots(localRoots, writableLocalRoots, nil)
shuff := NewRootSorter(
kc.LocalRoots(), Md5String("foo")).GetSortedRoots()
@@ -403,23 +403,23 @@ func (s *StandaloneSuite) TestPutWithTooManyFail(c *C) {
kc.Want_replicas = 2
arv.ApiToken = "abc123"
localRoots := make(map[string]string)
- writableRoots := make(map[string]string)
+ writableLocalRoots := make(map[string]string)
ks1 := RunSomeFakeKeepServers(st, 1)
ks2 := RunSomeFakeKeepServers(fh, 4)
for i, k := range ks1 {
localRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
- writableRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
+ writableLocalRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
defer k.listener.Close()
}
for i, k := range ks2 {
localRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i+len(ks1))] = k.url
- writableRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i+len(ks1))] = k.url
+ writableLocalRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i+len(ks1))] = k.url
defer k.listener.Close()
}
- kc.SetServiceRoots(localRoots, nil, writableRoots)
+ kc.SetServiceRoots(localRoots, writableLocalRoots, nil)
_, replicas, err := kc.PutB([]byte("foo"))
@@ -464,7 +464,7 @@ func (s *StandaloneSuite) TestGet(c *C) {
arv, err := arvadosclient.MakeArvadosClient()
kc, _ := MakeKeepClient(&arv)
arv.ApiToken = "abc123"
- kc.SetServiceRoots(map[string]string{"x": ks.url}, nil, map[string]string{ks.url: ""})
+ kc.SetServiceRoots(map[string]string{"x": ks.url}, map[string]string{ks.url: ""}, nil)
r, n, url2, err := kc.Get(hash)
defer r.Close()
@@ -490,7 +490,7 @@ func (s *StandaloneSuite) TestGetFail(c *C) {
arv, err := arvadosclient.MakeArvadosClient()
kc, _ := MakeKeepClient(&arv)
arv.ApiToken = "abc123"
- kc.SetServiceRoots(map[string]string{"x": ks.url}, nil, map[string]string{ks.url: ""})
+ kc.SetServiceRoots(map[string]string{"x": ks.url}, map[string]string{ks.url: ""}, nil)
r, n, url2, err := kc.Get(hash)
c.Check(err, Equals, BlockNotFound)
@@ -525,8 +525,8 @@ func (s *StandaloneSuite) TestGetWithServiceHint(c *C) {
arv.ApiToken = "abc123"
kc.SetServiceRoots(
map[string]string{"x": ks0.url},
- map[string]string{uuid: ks.url},
- map[string]string{ks0.url: "", ks.url: ""})
+ map[string]string{"x": ks0.url},
+ map[string]string{uuid: ks.url})
r, n, uri, err := kc.Get(hash + "+K@" + uuid)
defer r.Close()
@@ -619,8 +619,8 @@ func (s *StandaloneSuite) TestGetWithServiceHintFailoverToLocals(c *C) {
arv.ApiToken = "abc123"
kc.SetServiceRoots(
map[string]string{"zzzzz-bi6l4-keepdisk0000000": ksLocal.url},
- map[string]string{uuid: ksGateway.url},
- map[string]string{"zzzzz-bi6l4-keepdisk0000000": ksLocal.url})
+ map[string]string{"zzzzz-bi6l4-keepdisk0000000": ksLocal.url},
+ map[string]string{uuid: ksGateway.url})
r, n, uri, err := kc.Get(hash + "+K@" + uuid)
c.Assert(err, Equals, nil)
@@ -654,7 +654,7 @@ func (s *StandaloneSuite) TestChecksum(c *C) {
arv, err := arvadosclient.MakeArvadosClient()
kc, _ := MakeKeepClient(&arv)
arv.ApiToken = "abc123"
- kc.SetServiceRoots(map[string]string{"x": ks.url}, nil, map[string]string{ks.url: ""})
+ kc.SetServiceRoots(map[string]string{"x": ks.url}, map[string]string{ks.url: ""}, nil)
r, n, _, err := kc.Get(barhash)
_, err = ioutil.ReadAll(r)
@@ -689,23 +689,23 @@ func (s *StandaloneSuite) TestGetWithFailures(c *C) {
kc, _ := MakeKeepClient(&arv)
arv.ApiToken = "abc123"
localRoots := make(map[string]string)
- writableRoots := make(map[string]string)
+ writableLocalRoots := make(map[string]string)
ks1 := RunSomeFakeKeepServers(st, 1)
ks2 := RunSomeFakeKeepServers(fh, 4)
for i, k := range ks1 {
localRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
- writableRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
+ writableLocalRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
defer k.listener.Close()
}
for i, k := range ks2 {
localRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i+len(ks1))] = k.url
- writableRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i+len(ks1))] = k.url
+ writableLocalRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i+len(ks1))] = k.url
defer k.listener.Close()
}
- kc.SetServiceRoots(localRoots, nil, writableRoots)
+ kc.SetServiceRoots(localRoots, writableLocalRoots, nil)
// This test works only if one of the failing services is
// attempted before the succeeding service. Otherwise,
@@ -786,17 +786,17 @@ func (s *StandaloneSuite) TestPutProxy(c *C) {
kc.Using_proxy = true
arv.ApiToken = "abc123"
localRoots := make(map[string]string)
- writableRoots := make(map[string]string)
+ writableLocalRoots := make(map[string]string)
ks1 := RunSomeFakeKeepServers(st, 1)
for i, k := range ks1 {
localRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
- writableRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
+ writableLocalRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
defer k.listener.Close()
}
- kc.SetServiceRoots(localRoots, nil, writableRoots)
+ kc.SetServiceRoots(localRoots, writableLocalRoots, nil)
_, replicas, err := kc.PutB([]byte("foo"))
<-st.handled
@@ -819,16 +819,16 @@ func (s *StandaloneSuite) TestPutProxyInsufficientReplicas(c *C) {
kc.Using_proxy = true
arv.ApiToken = "abc123"
localRoots := make(map[string]string)
- writableRoots := make(map[string]string)
+ writableLocalRoots := make(map[string]string)
ks1 := RunSomeFakeKeepServers(st, 1)
for i, k := range ks1 {
localRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
- writableRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
+ writableLocalRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
defer k.listener.Close()
}
- kc.SetServiceRoots(localRoots, nil, writableRoots)
+ kc.SetServiceRoots(localRoots, writableLocalRoots, nil)
_, replicas, err := kc.PutB([]byte("foo"))
<-st.handled
@@ -878,9 +878,7 @@ func (s *StandaloneSuite) TestMakeLocatorInvalidInput(c *C) {
c.Check(err, Equals, InvalidLocatorError)
}
-func (s *StandaloneSuite) TestPutBWant2ReplicasWithOnlyOneWritableRoots(c *C) {
- log.Printf("TestPutWant2ReplicasWithOnlyOneWritableRoots")
-
+func (s *StandaloneSuite) TestPutBWant2ReplicasWithOnlyOneWritableLocalRoot(c *C) {
hash := Md5String("foo")
st := StubPutHandler{
@@ -896,19 +894,19 @@ func (s *StandaloneSuite) TestPutBWant2ReplicasWithOnlyOneWritableRoots(c *C) {
kc.Want_replicas = 2
arv.ApiToken = "abc123"
localRoots := make(map[string]string)
- writableRoots := make(map[string]string)
+ writableLocalRoots := make(map[string]string)
ks := RunSomeFakeKeepServers(st, 5)
for i, k := range ks {
localRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
if i == 0 {
- writableRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
+ writableLocalRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", i)] = k.url
}
defer k.listener.Close()
}
- kc.SetServiceRoots(localRoots, nil, writableRoots)
+ kc.SetServiceRoots(localRoots, writableLocalRoots, nil)
_, replicas, err := kc.PutB([]byte("foo"))
@@ -916,13 +914,9 @@ func (s *StandaloneSuite) TestPutBWant2ReplicasWithOnlyOneWritableRoots(c *C) {
c.Check(replicas, Equals, 1)
c.Check(<-st.handled, Equals, localRoots[fmt.Sprintf("zzzzz-bi6l4-fakefakefake%03d", 0)])
-
- log.Printf("TestPutWant2ReplicasWithOnlyOneWritableRoots done")
}
-func (s *StandaloneSuite) TestPutBWithNoWritableRoots(c *C) {
- log.Printf("TestPutBWithNoWritableRoots")
-
+func (s *StandaloneSuite) TestPutBWithNoWritableLocalRoots(c *C) {
hash := Md5String("foo")
st := StubPutHandler{
@@ -938,7 +932,7 @@ func (s *StandaloneSuite) TestPutBWithNoWritableRoots(c *C) {
kc.Want_replicas = 2
arv.ApiToken = "abc123"
localRoots := make(map[string]string)
- writableRoots := make(map[string]string)
+ writableLocalRoots := make(map[string]string)
ks := RunSomeFakeKeepServers(st, 5)
@@ -947,12 +941,10 @@ func (s *StandaloneSuite) TestPutBWithNoWritableRoots(c *C) {
defer k.listener.Close()
}
- kc.SetServiceRoots(localRoots, nil, writableRoots)
+ kc.SetServiceRoots(localRoots, writableLocalRoots, nil)
_, replicas, err := kc.PutB([]byte("foo"))
c.Check(err, Equals, InsufficientReplicasError)
c.Check(replicas, Equals, 0)
-
- log.Printf("TestPutBWithNoWritableRoots done")
}
diff --git a/sdk/go/keepclient/support.go b/sdk/go/keepclient/support.go
index b989c5d..7b96341 100644
--- a/sdk/go/keepclient/support.go
+++ b/sdk/go/keepclient/support.go
@@ -94,7 +94,7 @@ func (this *KeepClient) DiscoverKeepServers() error {
listed := make(map[string]bool)
localRoots := make(map[string]string)
gatewayRoots := make(map[string]string)
- writableRoots := make(map[string]string)
+ writableLocalRoots := make(map[string]string)
for _, service := range m.Items {
scheme := "http"
@@ -118,7 +118,7 @@ func (this *KeepClient) DiscoverKeepServers() error {
}
if service.ReadOnly == false {
- writableRoots[service.Uuid] = url
+ writableLocalRoots[service.Uuid] = url
}
// Gateway services are only used when specified by
@@ -135,7 +135,7 @@ func (this *KeepClient) DiscoverKeepServers() error {
this.setClientSettingsStore()
}
- this.SetServiceRoots(localRoots, gatewayRoots, writableRoots)
+ this.SetServiceRoots(localRoots, writableLocalRoots, gatewayRoots)
return nil
}
@@ -219,7 +219,7 @@ func (this KeepClient) putReplicas(
requestId := fmt.Sprintf("%x", md5.Sum([]byte(locator+time.Now().String())))[0:8]
// Calculate the ordering for uploading to servers
- sv := NewRootSorter(this.WritableRoots(), hash).GetSortedRoots()
+ sv := NewRootSorter(this.WritableLocalRoots(), hash).GetSortedRoots()
// The next server to try contacting
next_server := 0
diff --git a/sdk/python/arvados/keep.py b/sdk/python/arvados/keep.py
index 2846630..1e09172 100644
--- a/sdk/python/arvados/keep.py
+++ b/sdk/python/arvados/keep.py
@@ -648,10 +648,7 @@ class KeepClient(object):
'uuid': 'proxy',
'_service_root': proxy,
}]
- self._writable_services = [{
- 'uuid': 'proxy',
- '_service_root': proxy,
- }]
+ self._writable_services = self._keep_services
self.using_proxy = True
self._static_services_list = True
else:
@@ -759,7 +756,7 @@ class KeepClient(object):
# for this locator, and return their service_roots (base URIs)
# in that order.
use_services = self._keep_services
- if (need_writable == True):
+ if need_writable:
use_services = self._writable_services
sorted_roots.extend([
svc['_service_root'] for svc in sorted(
diff --git a/services/api/db/migrate/20150512193020_read_only_on_keep_services.rb b/services/api/db/migrate/20150512193020_read_only_on_keep_services.rb
index 1778b07..f86e471 100644
--- a/services/api/db/migrate/20150512193020_read_only_on_keep_services.rb
+++ b/services/api/db/migrate/20150512193020_read_only_on_keep_services.rb
@@ -1,9 +1,5 @@
class ReadOnlyOnKeepServices < ActiveRecord::Migration
- def up
+ def change
add_column :keep_services, :read_only, :boolean, null: false, default: false
end
-
- def down
- remove_column :keep_services, :read_only
- end
end
diff --git a/services/keepproxy/keepproxy_test.go b/services/keepproxy/keepproxy_test.go
index b70b933..5bd832b 100644
--- a/services/keepproxy/keepproxy_test.go
+++ b/services/keepproxy/keepproxy_test.go
@@ -118,10 +118,10 @@ func runProxy(c *C, args []string, port int, bogusClientToken bool) keepclient.K
locals := map[string]string{
"proxy": fmt.Sprintf("http://localhost:%v", port),
}
- writables := map[string]string{
+ writableLocals := map[string]string{
"proxy": fmt.Sprintf("http://localhost:%v", port),
}
- kc.SetServiceRoots(locals, nil, writables)
+ kc.SetServiceRoots(locals, writableLocals, nil)
c.Check(kc.Using_proxy, Equals, true)
c.Check(len(kc.LocalRoots()), Equals, 1)
for _, root := range kc.LocalRoots() {
diff --git a/services/keepstore/pull_worker.go b/services/keepstore/pull_worker.go
index 2707b98..3d67cf2 100644
--- a/services/keepstore/pull_worker.go
+++ b/services/keepstore/pull_worker.go
@@ -46,7 +46,7 @@ func PullItemAndProcess(pullRequest PullRequest, token string, keepClient *keepc
for _, addr := range pullRequest.Servers {
service_roots[addr] = addr
}
- keepClient.SetServiceRoots(service_roots, nil, keepClient.WritableRoots())
+ keepClient.SetServiceRoots(service_roots, nil, nil)
// Generate signature with a random token
expires_at := time.Now().Add(60 * time.Second)
commit b085f051e459981a385c95c4ae147546312c08d9
Merge: 1f2a1c4 f1827e2
Author: Radhika Chippada <radhika at curoverse.com>
Date: Mon May 18 22:22:18 2015 -0400
Merge branch 'master' into 4717-read-only-keep-services-flag
-----------------------------------------------------------------------
hooks/post-receive
--
More information about the arvados-commits
mailing list