github.com/wallyworld/juju@v0.0.0-20161013125918-6cf1bc9d917a/core/description/unit_test.go (about) 1 // Copyright 2016 Canonical Ltd. 2 // Licensed under the AGPLv3, see LICENCE file for details. 3 4 package description 5 6 import ( 7 jc "github.com/juju/testing/checkers" 8 gc "gopkg.in/check.v1" 9 "gopkg.in/juju/names.v2" 10 "gopkg.in/yaml.v2" 11 ) 12 13 type UnitSerializationSuite struct { 14 SliceSerializationSuite 15 } 16 17 var _ = gc.Suite(&UnitSerializationSuite{}) 18 19 func (s *UnitSerializationSuite) SetUpTest(c *gc.C) { 20 s.SliceSerializationSuite.SetUpTest(c) 21 s.importName = "units" 22 s.sliceName = "units" 23 s.importFunc = func(m map[string]interface{}) (interface{}, error) { 24 return importUnits(m) 25 } 26 s.testFields = func(m map[string]interface{}) { 27 m["units"] = []interface{}{} 28 } 29 } 30 31 func minimalUnitMap() map[interface{}]interface{} { 32 return map[interface{}]interface{}{ 33 "name": "ubuntu/0", 34 "machine": "0", 35 "agent-status": minimalStatusMap(), 36 "agent-status-history": emptyStatusHistoryMap(), 37 "workload-status": minimalStatusMap(), 38 "workload-status-history": emptyStatusHistoryMap(), 39 "workload-version-history": emptyStatusHistoryMap(), 40 "password-hash": "secure-hash", 41 "tools": minimalAgentToolsMap(), 42 "payloads": map[interface{}]interface{}{ 43 "version": 1, 44 "payloads": []interface{}{}, 45 }, 46 } 47 } 48 49 func minimalUnit() *unit { 50 u := newUnit(minimalUnitArgs()) 51 u.SetAgentStatus(minimalStatusArgs()) 52 u.SetWorkloadStatus(minimalStatusArgs()) 53 u.SetTools(minimalAgentToolsArgs()) 54 return u 55 } 56 57 func minimalUnitArgs() UnitArgs { 58 return UnitArgs{ 59 Tag: names.NewUnitTag("ubuntu/0"), 60 Machine: names.NewMachineTag("0"), 61 PasswordHash: "secure-hash", 62 } 63 } 64 65 func (s *UnitSerializationSuite) completeUnit() *unit { 66 // This unit is about completeness, not reasonableness. That is why the 67 // unit has a principal (normally only for subordinates), and also a list 68 // of subordinates. 69 args := UnitArgs{ 70 Tag: names.NewUnitTag("ubuntu/0"), 71 Machine: names.NewMachineTag("0"), 72 PasswordHash: "secure-hash", 73 Principal: names.NewUnitTag("principal/0"), 74 Subordinates: []names.UnitTag{ 75 names.NewUnitTag("sub1/0"), 76 names.NewUnitTag("sub2/0"), 77 }, 78 WorkloadVersion: "malachite", 79 MeterStatusCode: "meter code", 80 MeterStatusInfo: "meter info", 81 } 82 unit := newUnit(args) 83 unit.SetAgentStatus(minimalStatusArgs()) 84 unit.SetWorkloadStatus(minimalStatusArgs()) 85 unit.SetTools(minimalAgentToolsArgs()) 86 return unit 87 } 88 89 func (s *UnitSerializationSuite) TestNewUnit(c *gc.C) { 90 unit := s.completeUnit() 91 92 c.Assert(unit.Tag(), gc.Equals, names.NewUnitTag("ubuntu/0")) 93 c.Assert(unit.Name(), gc.Equals, "ubuntu/0") 94 c.Assert(unit.Machine(), gc.Equals, names.NewMachineTag("0")) 95 c.Assert(unit.PasswordHash(), gc.Equals, "secure-hash") 96 c.Assert(unit.Principal(), gc.Equals, names.NewUnitTag("principal/0")) 97 c.Assert(unit.Subordinates(), jc.DeepEquals, []names.UnitTag{ 98 names.NewUnitTag("sub1/0"), 99 names.NewUnitTag("sub2/0"), 100 }) 101 c.Assert(unit.WorkloadVersion(), gc.Equals, "malachite") 102 c.Assert(unit.MeterStatusCode(), gc.Equals, "meter code") 103 c.Assert(unit.MeterStatusInfo(), gc.Equals, "meter info") 104 c.Assert(unit.Tools(), gc.NotNil) 105 c.Assert(unit.WorkloadStatus(), gc.NotNil) 106 c.Assert(unit.AgentStatus(), gc.NotNil) 107 } 108 109 func (s *UnitSerializationSuite) TestMinimalUnitValid(c *gc.C) { 110 unit := minimalUnit() 111 c.Assert(unit.Validate(), jc.ErrorIsNil) 112 } 113 114 func (s *UnitSerializationSuite) TestMinimalMatches(c *gc.C) { 115 bytes, err := yaml.Marshal(minimalUnit()) 116 c.Assert(err, jc.ErrorIsNil) 117 118 var source map[interface{}]interface{} 119 err = yaml.Unmarshal(bytes, &source) 120 c.Assert(err, jc.ErrorIsNil) 121 c.Assert(source, jc.DeepEquals, minimalUnitMap()) 122 } 123 124 func (s *UnitSerializationSuite) exportImport(c *gc.C, unit_ *unit) *unit { 125 initial := units{ 126 Version: 1, 127 Units_: []*unit{unit_}, 128 } 129 130 bytes, err := yaml.Marshal(initial) 131 c.Assert(err, jc.ErrorIsNil) 132 133 var source map[string]interface{} 134 err = yaml.Unmarshal(bytes, &source) 135 c.Assert(err, jc.ErrorIsNil) 136 137 units, err := importUnits(source) 138 c.Assert(err, jc.ErrorIsNil) 139 c.Assert(units, gc.HasLen, 1) 140 return units[0] 141 } 142 143 func (s *UnitSerializationSuite) TestParsingSerializedData(c *gc.C) { 144 initial := s.completeUnit() 145 unit := s.exportImport(c, initial) 146 c.Assert(unit, jc.DeepEquals, initial) 147 } 148 149 func (s *UnitSerializationSuite) TestAnnotations(c *gc.C) { 150 initial := minimalUnit() 151 annotations := map[string]string{ 152 "string": "value", 153 "another": "one", 154 } 155 initial.SetAnnotations(annotations) 156 157 unit := s.exportImport(c, initial) 158 c.Assert(unit.Annotations(), jc.DeepEquals, annotations) 159 } 160 161 func (s *UnitSerializationSuite) TestConstraints(c *gc.C) { 162 initial := minimalUnit() 163 args := ConstraintsArgs{ 164 Architecture: "amd64", 165 Memory: 8 * gig, 166 RootDisk: 40 * gig, 167 } 168 initial.SetConstraints(args) 169 170 unit := s.exportImport(c, initial) 171 c.Assert(unit.Constraints(), jc.DeepEquals, newConstraints(args)) 172 } 173 174 func (s *UnitSerializationSuite) TestAgentStatusHistory(c *gc.C) { 175 initial := minimalUnit() 176 args := testStatusHistoryArgs() 177 initial.SetAgentStatusHistory(args) 178 179 unit := s.exportImport(c, initial) 180 for i, point := range unit.AgentStatusHistory() { 181 c.Check(point.Value(), gc.Equals, args[i].Value) 182 c.Check(point.Message(), gc.Equals, args[i].Message) 183 c.Check(point.Data(), jc.DeepEquals, args[i].Data) 184 c.Check(point.Updated(), gc.Equals, args[i].Updated) 185 } 186 } 187 188 func (s *UnitSerializationSuite) TestWorkloadStatusHistory(c *gc.C) { 189 initial := minimalUnit() 190 args := testStatusHistoryArgs() 191 initial.SetWorkloadStatusHistory(args) 192 193 unit := s.exportImport(c, initial) 194 for i, point := range unit.WorkloadStatusHistory() { 195 c.Check(point.Value(), gc.Equals, args[i].Value) 196 c.Check(point.Message(), gc.Equals, args[i].Message) 197 c.Check(point.Data(), jc.DeepEquals, args[i].Data) 198 c.Check(point.Updated(), gc.Equals, args[i].Updated) 199 } 200 } 201 202 func (s *UnitSerializationSuite) TestPayloads(c *gc.C) { 203 initial := minimalUnit() 204 expected := initial.AddPayload(allPayloadArgs()) 205 c.Check(expected.Name(), gc.Equals, "bob") 206 c.Check(expected.Type(), gc.Equals, "docker") 207 c.Check(expected.RawID(), gc.Equals, "d06f00d") 208 c.Check(expected.State(), gc.Equals, "running") 209 c.Check(expected.Labels(), jc.DeepEquals, []string{"auto", "foo"}) 210 211 unit := s.exportImport(c, initial) 212 213 payloads := unit.Payloads() 214 c.Assert(payloads, gc.HasLen, 1) 215 c.Assert(payloads[0], jc.DeepEquals, expected) 216 }