~juju-qa/ubuntu/xenial/juju/xenial-2.0-beta3

« back to all changes in this revision

Viewing changes to src/gopkg.in/juju/charmstore.v5-unstable/internal/v5/search_test.go

  • Committer: Martin Packman
  • Date: 2016-03-30 19:31:08 UTC
  • mfrom: (1.1.41)
  • Revision ID: martin.packman@canonical.com-20160330193108-h9iz3ak334uk0z5r
Merge new upstream source 2.0~beta3

Show diffs side-by-side

added added

removed removed

Lines of Context:
4
4
package v5_test // import "gopkg.in/juju/charmstore.v5-unstable/internal/v5"
5
5
 
6
6
import (
7
 
        "bytes"
8
7
        "encoding/json"
9
8
        "net/http"
10
9
        "net/url"
17
16
        gc "gopkg.in/check.v1"
18
17
        "gopkg.in/juju/charm.v6-unstable"
19
18
        "gopkg.in/juju/charmrepo.v2-unstable/csclient/params"
20
 
        "gopkg.in/macaroon-bakery.v1/bakery/checkers"
21
 
        "gopkg.in/macaroon-bakery.v1/httpbakery"
22
 
        "gopkg.in/macaroon.v1"
23
 
        "gopkg.in/mgo.v2/bson"
24
19
 
25
20
        "gopkg.in/juju/charmstore.v5-unstable/internal/charmstore"
26
 
        "gopkg.in/juju/charmstore.v5-unstable/internal/mongodoc"
27
21
        "gopkg.in/juju/charmstore.v5-unstable/internal/router"
28
22
        "gopkg.in/juju/charmstore.v5-unstable/internal/storetesting"
29
23
        "gopkg.in/juju/charmstore.v5-unstable/internal/v5"
55
49
func (s *SearchSuite) SetUpTest(c *gc.C) {
56
50
        s.commonSuite.SetUpTest(c)
57
51
        s.addCharmsToStore(c)
58
 
        // hide the riak charm
59
 
        err := s.store.DB.BaseEntities().UpdateId(
60
 
                charm.MustParseURL("cs:~charmers/riak"),
61
 
                bson.D{{"$set", map[string]mongodoc.ACL{
62
 
                        "acls": {
63
 
                                Read: []string{"charmers", "test-user"},
64
 
                        },
65
 
                }}},
66
 
        )
 
52
        err := s.store.SetPerms(charm.MustParseURL("cs:~charmers/riak"), "stable.read", "charmers", "test-user")
67
53
        c.Assert(err, gc.IsNil)
68
54
        err = s.store.UpdateSearch(newResolvedURL("~charmers/trusty/riak-0", 0))
69
55
        c.Assert(err, gc.IsNil)
73
59
 
74
60
func (s *SearchSuite) addCharmsToStore(c *gc.C) {
75
61
        for name, id := range exportTestCharms {
76
 
                err := s.store.AddCharmWithArchive(id, getCharm(name))
77
 
                c.Assert(err, gc.IsNil)
78
 
                err = s.store.SetPerms(&id.URL, "read", params.Everyone, id.URL.User)
79
 
                c.Assert(err, gc.IsNil)
80
 
                err = s.store.UpdateSearch(id)
81
 
                c.Assert(err, gc.IsNil)
 
62
                s.addPublicCharm(c, getSearchCharm(name), id)
82
63
        }
83
64
        for name, id := range exportTestBundles {
84
 
                err := s.store.AddBundleWithArchive(id, getBundle(name))
85
 
                c.Assert(err, gc.IsNil)
86
 
                err = s.store.SetPerms(&id.URL, "read", params.Everyone, id.URL.User)
87
 
                c.Assert(err, gc.IsNil)
88
 
                err = s.store.UpdateSearch(id)
89
 
                c.Assert(err, gc.IsNil)
 
65
                s.addPublicBundle(c, getSearchBundle(name), id, false)
90
66
        }
91
67
}
92
68
 
93
 
func getCharm(name string) *charm.CharmDir {
 
69
func getSearchCharm(name string) *storetesting.Charm {
94
70
        ca := storetesting.Charms.CharmDir(name)
95
 
        ca.Meta().Categories = append(strings.Split(name, "-"), "bar")
96
 
        return ca
 
71
        meta := ca.Meta()
 
72
        meta.Categories = append(strings.Split(name, "-"), "bar")
 
73
        return storetesting.NewCharm(meta)
97
74
}
98
75
 
99
 
func getBundle(name string) *charm.BundleDir {
 
76
func getSearchBundle(name string) *storetesting.Bundle {
100
77
        ba := storetesting.Charms.BundleDir(name)
101
 
        ba.Data().Tags = append(strings.Split(name, "-"), "baz")
102
 
        return ba
 
78
        data := ba.Data()
 
79
        data.Tags = append(strings.Split(name, "-"), "baz")
 
80
        return storetesting.NewBundle(data)
103
81
}
104
82
 
105
83
func (s *SearchSuite) TestParseSearchParams(c *gc.C) {
471
449
                about: "archive-size",
472
450
                query: "name=mysql&include=archive-size",
473
451
                meta: map[string]interface{}{
474
 
                        "archive-size": params.ArchiveSizeResponse{438},
 
452
                        "archive-size": params.ArchiveSizeResponse{getSearchCharm("mysql").Size()},
475
453
                },
476
454
        }, {
477
455
                about: "bundle-metadata",
478
456
                query: "name=wordpress-simple&type=bundle&include=bundle-metadata",
479
457
                meta: map[string]interface{}{
480
 
                        "bundle-metadata": getBundle("wordpress-simple").Data(),
 
458
                        "bundle-metadata": getSearchBundle("wordpress-simple").Data(),
481
459
                },
482
460
        }, {
483
461
                about: "bundle-machine-count",
495
473
                about: "charm-actions",
496
474
                query: "name=wordpress&type=charm&include=charm-actions",
497
475
                meta: map[string]interface{}{
498
 
                        "charm-actions": getCharm("wordpress").Actions(),
 
476
                        "charm-actions": getSearchCharm("wordpress").Actions(),
499
477
                },
500
478
        }, {
501
479
                about: "charm-config",
502
480
                query: "name=wordpress&type=charm&include=charm-config",
503
481
                meta: map[string]interface{}{
504
 
                        "charm-config": getCharm("wordpress").Config(),
 
482
                        "charm-config": getSearchCharm("wordpress").Config(),
505
483
                },
506
484
        }, {
507
485
                about: "charm-related",
508
486
                query: "name=wordpress&type=charm&include=charm-related",
509
487
                meta: map[string]interface{}{
510
488
                        "charm-related": params.RelatedResponse{
511
 
                                Provides: map[string][]params.MetaAnyResponse{
 
489
                                Provides: map[string][]params.EntityResult{
512
490
                                        "mysql": {
513
491
                                                {
514
492
                                                        Id: exportTestCharms["mysql"].PreferredURL(),
527
505
                query: "name=wordpress&type=charm&include=charm-related&include=charm-config",
528
506
                meta: map[string]interface{}{
529
507
                        "charm-related": params.RelatedResponse{
530
 
                                Provides: map[string][]params.MetaAnyResponse{
 
508
                                Provides: map[string][]params.EntityResult{
531
509
                                        "mysql": {
532
510
                                                {
533
511
                                                        Id: exportTestCharms["mysql"].PreferredURL(),
540
518
                                        },
541
519
                                },
542
520
                        },
543
 
                        "charm-config": getCharm("wordpress").Config(),
 
521
                        "charm-config": getSearchCharm("wordpress").Config(),
544
522
                },
545
523
        }}
546
524
        for i, test := range tests {
591
569
        // cs:riak will not be found because it is not visible to "everyone".
592
570
        c.Assert(resp.Results, gc.HasLen, len(exportTestCharms)-1)
593
571
 
594
 
        // Now remove one of the blobs. The search should still
 
572
        // Now remove one of the blobs. The list should still
595
573
        // work, but only return a single result.
596
 
        blobName, _, err := s.store.BlobNameAndHash(newResolvedURL("~charmers/precise/wordpress-23", 23))
 
574
        entity, err := s.store.FindEntity(newResolvedURL("~charmers/precise/wordpress-23", 23), nil)
 
575
 
597
576
        c.Assert(err, gc.IsNil)
598
 
        err = s.store.BlobStore.Remove(blobName)
 
577
        err = s.store.BlobStore.Remove(entity.BlobName)
599
578
        c.Assert(err, gc.IsNil)
600
579
 
601
580
        // Now search again - we should get one result less
723
702
        for n, cnt := range charmDownloads {
724
703
                url := newResolvedURL("cs:~downloads-test/trusty/x-1", -1)
725
704
                url.URL.Name = n
726
 
                err := s.store.AddCharmWithArchive(url, getCharm(n))
727
 
                c.Assert(err, gc.IsNil)
728
 
                err = s.store.SetPerms(&url.URL, "read", params.Everyone, url.URL.User)
729
 
                c.Assert(err, gc.IsNil)
730
 
                err = s.store.UpdateSearch(url)
731
 
                c.Assert(err, gc.IsNil)
 
705
                s.addPublicCharm(c, getSearchCharm(n), url)
732
706
                for i := 0; i < cnt; i++ {
733
707
                        err := s.store.IncrementDownloadCounts(url)
734
708
                        c.Assert(err, gc.IsNil)
755
729
        doc, err := s.store.ES.GetSearchDocument(charm.MustParseURL("~openstack-charmers/trusty/mysql-7"))
756
730
        c.Assert(err, gc.IsNil)
757
731
        c.Assert(doc.TotalDownloads, gc.Equals, int64(0))
758
 
        s.assertPut(c, "~openstack-charmers/trusty/mysql-7/meta/extra-info/"+params.LegacyDownloadStats, 57)
 
732
        s.assertPutAsAdmin(c, "~openstack-charmers/trusty/mysql-7/meta/extra-info/"+params.LegacyDownloadStats, 57)
759
733
        doc, err = s.store.ES.GetSearchDocument(charm.MustParseURL("~openstack-charmers/trusty/mysql-7"))
760
734
        c.Assert(err, gc.IsNil)
761
735
        c.Assert(doc.TotalDownloads, gc.Equals, int64(57))
762
736
}
763
737
 
764
 
func (s *SearchSuite) assertPut(c *gc.C, url string, val interface{}) {
765
 
        body, err := json.Marshal(val)
766
 
        c.Assert(err, gc.IsNil)
767
 
        rec := httptesting.DoRequest(c, httptesting.DoRequestParams{
768
 
                Handler: s.srv,
769
 
                URL:     storeURL(url),
770
 
                Method:  "PUT",
771
 
                Header: http.Header{
772
 
                        "Content-Type": {"application/json"},
773
 
                },
774
 
                Username: testUsername,
775
 
                Password: testPassword,
776
 
                Body:     bytes.NewReader(body),
777
 
        })
778
 
        c.Assert(rec.Code, gc.Equals, http.StatusOK, gc.Commentf("headers: %v, body: %s", rec.HeaderMap, rec.Body.String()))
779
 
        c.Assert(rec.Body.String(), gc.HasLen, 0)
780
 
}
781
 
 
782
738
func (s *SearchSuite) TestSearchWithAdminCredentials(c *gc.C) {
783
739
        rec := httptesting.DoRequest(c, httptesting.DoRequestParams{
784
740
                Handler:  s.srv,
801
757
}
802
758
 
803
759
func (s *SearchSuite) TestSearchWithUserMacaroon(c *gc.C) {
804
 
        m, err := s.store.Bakery.NewMacaroon("", nil, []checkers.Caveat{
805
 
                checkers.DeclaredCaveat("username", "test-user"),
806
 
        })
807
 
        c.Assert(err, gc.IsNil)
808
 
        macaroonCookie, err := httpbakery.NewCookie(macaroon.Slice{m})
809
 
        c.Assert(err, gc.IsNil)
810
760
        rec := httptesting.DoRequest(c, httptesting.DoRequestParams{
811
761
                Handler: s.srv,
812
762
                URL:     storeURL("search"),
813
 
                Cookies: []*http.Cookie{macaroonCookie},
 
763
                Do:      s.bakeryDoAsUser(c, "test-user"),
814
764
        })
815
765
        c.Assert(rec.Code, gc.Equals, http.StatusOK)
816
766
        expected := []*router.ResolvedURL{
821
771
                exportTestBundles["wordpress-simple"],
822
772
        }
823
773
        var sr params.SearchResponse
824
 
        err = json.Unmarshal(rec.Body.Bytes(), &sr)
 
774
        err := json.Unmarshal(rec.Body.Bytes(), &sr)
825
775
        c.Assert(err, gc.IsNil)
826
776
        assertResultSet(c, sr, expected)
827
777
}
828
778
 
829
779
func (s *SearchSuite) TestSearchWithUserInGroups(c *gc.C) {
830
 
        m, err := s.store.Bakery.NewMacaroon("", nil, []checkers.Caveat{
831
 
                checkers.DeclaredCaveat(v5.UsernameAttr, "bob"),
832
 
        })
833
 
        c.Assert(err, gc.IsNil)
834
 
        macaroonCookie, err := httpbakery.NewCookie(macaroon.Slice{m})
835
 
        c.Assert(err, gc.IsNil)
836
780
        s.idM.groups = map[string][]string{
837
781
                "bob": {"test-user", "test-user2"},
838
782
        }
839
783
        rec := httptesting.DoRequest(c, httptesting.DoRequestParams{
840
784
                Handler: s.srv,
841
785
                URL:     storeURL("search"),
842
 
                Cookies: []*http.Cookie{macaroonCookie},
 
786
                Do:      s.bakeryDoAsUser(c, "bob"),
843
787
        })
844
788
        c.Assert(rec.Code, gc.Equals, http.StatusOK)
845
789
        expected := []*router.ResolvedURL{
850
794
                exportTestBundles["wordpress-simple"],
851
795
        }
852
796
        var sr params.SearchResponse
853
 
        err = json.Unmarshal(rec.Body.Bytes(), &sr)
 
797
        err := json.Unmarshal(rec.Body.Bytes(), &sr)
854
798
        c.Assert(err, gc.IsNil)
855
799
        assertResultSet(c, sr, expected)
856
800
}
857
801
 
858
802
func (s *SearchSuite) TestSearchWithBadAdminCredentialsAndACookie(c *gc.C) {
859
 
        m, err := s.store.Bakery.NewMacaroon("", nil, []checkers.Caveat{
860
 
                checkers.DeclaredCaveat("username", "test-user"),
861
 
        })
862
 
        c.Assert(err, gc.IsNil)
863
 
        macaroonCookie, err := httpbakery.NewCookie(macaroon.Slice{m})
864
 
        c.Assert(err, gc.IsNil)
865
803
        rec := httptesting.DoRequest(c, httptesting.DoRequestParams{
866
804
                Handler:  s.srv,
 
805
                Do:       s.bakeryDoAsUser(c, "test-user"),
867
806
                URL:      storeURL("search"),
868
 
                Cookies:  []*http.Cookie{macaroonCookie},
869
807
                Username: testUsername,
870
808
                Password: "bad-password",
871
809
        })
877
815
                exportTestBundles["wordpress-simple"],
878
816
        }
879
817
        var sr params.SearchResponse
880
 
        err = json.Unmarshal(rec.Body.Bytes(), &sr)
 
818
        err := json.Unmarshal(rec.Body.Bytes(), &sr)
881
819
        c.Assert(err, gc.IsNil)
882
820
        assertResultSet(c, sr, expected)
883
821
}