github.com/mhilton/juju-juju@v0.0.0-20150901100907-a94dd2c73455/apiserver/uniter/uniter_v2_test.go (about)

     1  // Copyright 2015 Canonical Ltd.
     2  // Licensed under the AGPLv3, see LICENCE file for details.
     3  
     4  package uniter_test
     5  
     6  import (
     7  	"time"
     8  
     9  	"github.com/juju/errors"
    10  	"github.com/juju/names"
    11  	jc "github.com/juju/testing/checkers"
    12  	"github.com/juju/utils"
    13  	gc "gopkg.in/check.v1"
    14  
    15  	"github.com/juju/juju/apiserver/params"
    16  	apiservertesting "github.com/juju/juju/apiserver/testing"
    17  	"github.com/juju/juju/apiserver/uniter"
    18  	"github.com/juju/juju/state"
    19  	"github.com/juju/juju/testing/factory"
    20  )
    21  
    22  //TODO run all common V0 and V1 tests.
    23  type uniterV2Suite struct {
    24  	uniterBaseSuite
    25  	uniter *uniter.UniterAPIV2
    26  }
    27  
    28  var _ = gc.Suite(&uniterV2Suite{})
    29  
    30  func (s *uniterV2Suite) SetUpTest(c *gc.C) {
    31  	s.uniterBaseSuite.setUpTest(c)
    32  
    33  	uniterAPIV2, err := uniter.NewUniterAPIV2(
    34  		s.State,
    35  		s.resources,
    36  		s.authorizer,
    37  	)
    38  	c.Assert(err, jc.ErrorIsNil)
    39  	s.uniter = uniterAPIV2
    40  }
    41  
    42  func (s *uniterV2Suite) TestStorageAttachments(c *gc.C) {
    43  	// We need to set up a unit that has storage metadata defined.
    44  	ch := s.AddTestingCharm(c, "storage-block")
    45  	sCons := map[string]state.StorageConstraints{
    46  		"data": {Pool: "", Size: 1024, Count: 1},
    47  	}
    48  	service := s.AddTestingServiceWithStorage(c, "storage-block", ch, sCons)
    49  	unit, err := service.AddUnit()
    50  	c.Assert(err, jc.ErrorIsNil)
    51  	err = s.State.AssignUnit(unit, state.AssignCleanEmpty)
    52  	c.Assert(err, jc.ErrorIsNil)
    53  	assignedMachineId, err := unit.AssignedMachineId()
    54  	c.Assert(err, jc.ErrorIsNil)
    55  	machine, err := s.State.Machine(assignedMachineId)
    56  	c.Assert(err, jc.ErrorIsNil)
    57  
    58  	volumeAttachments, err := machine.VolumeAttachments()
    59  	c.Assert(err, jc.ErrorIsNil)
    60  	c.Assert(volumeAttachments, gc.HasLen, 1)
    61  
    62  	err = machine.SetProvisioned("inst-id", "fake_nonce", nil)
    63  	c.Assert(err, jc.ErrorIsNil)
    64  
    65  	err = s.State.SetVolumeInfo(
    66  		volumeAttachments[0].Volume(),
    67  		state.VolumeInfo{VolumeId: "vol-123", Size: 456},
    68  	)
    69  	c.Assert(err, jc.ErrorIsNil)
    70  
    71  	err = s.State.SetVolumeAttachmentInfo(
    72  		machine.MachineTag(),
    73  		volumeAttachments[0].Volume(),
    74  		state.VolumeAttachmentInfo{DeviceName: "xvdf1"},
    75  	)
    76  	c.Assert(err, jc.ErrorIsNil)
    77  
    78  	password, err := utils.RandomPassword()
    79  	err = unit.SetPassword(password)
    80  	c.Assert(err, jc.ErrorIsNil)
    81  	st := s.OpenAPIAs(c, unit.Tag(), password)
    82  	uniter, err := st.Uniter()
    83  	c.Assert(err, jc.ErrorIsNil)
    84  
    85  	attachments, err := uniter.UnitStorageAttachments(unit.UnitTag())
    86  	c.Assert(err, jc.ErrorIsNil)
    87  	c.Assert(attachments, gc.DeepEquals, []params.StorageAttachmentId{{
    88  		StorageTag: "storage-data-0",
    89  		UnitTag:    unit.Tag().String(),
    90  	}})
    91  }
    92  
    93  // TestSetStatus tests backwards compatibility for
    94  // set status has been properly implemented.
    95  func (s *uniterV2Suite) TestSetStatus(c *gc.C) {
    96  	s.testSetStatus(c, s.uniter)
    97  }
    98  
    99  // TestSetAgentStatus tests agent part of set status
   100  // implemented for this version.
   101  func (s *uniterV2Suite) TestSetAgentStatus(c *gc.C) {
   102  	s.testSetAgentStatus(c, s.uniter)
   103  }
   104  
   105  // TestSetUnitStatus tests unit part of set status
   106  // implemented for this version.
   107  func (s *uniterV2Suite) TestSetUnitStatus(c *gc.C) {
   108  	s.testSetUnitStatus(c, s.uniter)
   109  }
   110  
   111  func (s *uniterV2Suite) TestUnitStatus(c *gc.C) {
   112  	err := s.wordpressUnit.SetStatus(state.StatusMaintenance, "blah", nil)
   113  	c.Assert(err, jc.ErrorIsNil)
   114  	err = s.mysqlUnit.SetStatus(state.StatusTerminated, "foo", nil)
   115  	c.Assert(err, jc.ErrorIsNil)
   116  
   117  	args := params.Entities{
   118  		Entities: []params.Entity{
   119  			{Tag: "unit-mysql-0"},
   120  			{Tag: "unit-wordpress-0"},
   121  			{Tag: "unit-foo-42"},
   122  			{Tag: "machine-1"},
   123  			{Tag: "invalid"},
   124  		}}
   125  	result, err := s.uniter.UnitStatus(args)
   126  	c.Assert(err, jc.ErrorIsNil)
   127  	// Zero out the updated timestamps so we can easily check the results.
   128  	for i, statusResult := range result.Results {
   129  		r := statusResult
   130  		if r.Status != "" {
   131  			c.Assert(r.Since, gc.NotNil)
   132  		}
   133  		r.Since = nil
   134  		result.Results[i] = r
   135  	}
   136  	c.Assert(result, gc.DeepEquals, params.StatusResults{
   137  		Results: []params.StatusResult{
   138  			{Error: apiservertesting.ErrUnauthorized},
   139  			{Status: params.StatusMaintenance, Info: "blah", Data: map[string]interface{}{}},
   140  			{Error: apiservertesting.ErrUnauthorized},
   141  			{Error: apiservertesting.ErrUnauthorized},
   142  			{Error: apiservertesting.ServerError(`"invalid" is not a valid tag`)},
   143  		},
   144  	})
   145  }
   146  
   147  type unitMetricBatchesSuite struct {
   148  	uniterBaseSuite
   149  	uniter *uniter.UniterAPIV2
   150  }
   151  
   152  var _ = gc.Suite(&unitMetricBatchesSuite{})
   153  
   154  func (s *unitMetricBatchesSuite) SetUpTest(c *gc.C) {
   155  	s.uniterBaseSuite.setUpTest(c)
   156  
   157  	meteredAuthorizer := apiservertesting.FakeAuthorizer{
   158  		Tag: s.meteredUnit.Tag(),
   159  	}
   160  	var err error
   161  	s.uniter, err = uniter.NewUniterAPIV2(
   162  		s.State,
   163  		s.resources,
   164  		meteredAuthorizer,
   165  	)
   166  	c.Assert(err, jc.ErrorIsNil)
   167  }
   168  
   169  func (s *unitMetricBatchesSuite) TestAddMetricsBatch(c *gc.C) {
   170  	metrics := []params.Metric{{Key: "pings", Value: "5", Time: time.Now().UTC()}}
   171  	uuid := utils.MustNewUUID().String()
   172  
   173  	result, err := s.uniter.AddMetricBatches(params.MetricBatchParams{
   174  		Batches: []params.MetricBatchParam{{
   175  			Tag: s.meteredUnit.Tag().String(),
   176  			Batch: params.MetricBatch{
   177  				UUID:     uuid,
   178  				CharmURL: s.meteredCharm.URL().String(),
   179  				Created:  time.Now(),
   180  				Metrics:  metrics,
   181  			}}}},
   182  	)
   183  
   184  	c.Assert(result, gc.DeepEquals, params.ErrorResults{
   185  		Results: []params.ErrorResult{{nil}},
   186  	})
   187  	c.Assert(err, jc.ErrorIsNil)
   188  
   189  	batch, err := s.State.MetricBatch(uuid)
   190  	c.Assert(err, jc.ErrorIsNil)
   191  	c.Assert(batch.UUID(), gc.Equals, uuid)
   192  	c.Assert(batch.CharmURL(), gc.Equals, s.meteredCharm.URL().String())
   193  	c.Assert(batch.Unit(), gc.Equals, s.meteredUnit.Name())
   194  	storedMetrics := batch.Metrics()
   195  	c.Assert(storedMetrics, gc.HasLen, 1)
   196  	c.Assert(storedMetrics[0].Key, gc.Equals, metrics[0].Key)
   197  	c.Assert(storedMetrics[0].Value, gc.Equals, metrics[0].Value)
   198  }
   199  
   200  func (s *unitMetricBatchesSuite) TestAddMetricsBatchNoCharmURL(c *gc.C) {
   201  	metrics := []params.Metric{{Key: "pings", Value: "5", Time: time.Now().UTC()}}
   202  	uuid := utils.MustNewUUID().String()
   203  
   204  	result, err := s.uniter.AddMetricBatches(params.MetricBatchParams{
   205  		Batches: []params.MetricBatchParam{{
   206  			Tag: s.meteredUnit.Tag().String(),
   207  			Batch: params.MetricBatch{
   208  				UUID:     uuid,
   209  				CharmURL: s.meteredCharm.URL().String(),
   210  				Created:  time.Now(),
   211  				Metrics:  metrics,
   212  			}}}})
   213  
   214  	c.Assert(result, gc.DeepEquals, params.ErrorResults{
   215  		Results: []params.ErrorResult{{nil}},
   216  	})
   217  	c.Assert(err, jc.ErrorIsNil)
   218  
   219  	batch, err := s.State.MetricBatch(uuid)
   220  	c.Assert(err, jc.ErrorIsNil)
   221  	c.Assert(batch.UUID(), gc.Equals, uuid)
   222  	c.Assert(batch.CharmURL(), gc.Equals, s.meteredCharm.URL().String())
   223  	c.Assert(batch.Unit(), gc.Equals, s.meteredUnit.Name())
   224  	storedMetrics := batch.Metrics()
   225  	c.Assert(storedMetrics, gc.HasLen, 1)
   226  	c.Assert(storedMetrics[0].Key, gc.Equals, metrics[0].Key)
   227  	c.Assert(storedMetrics[0].Value, gc.Equals, metrics[0].Value)
   228  }
   229  
   230  func (s *unitMetricBatchesSuite) TestAddMetricsBatchDiffTag(c *gc.C) {
   231  	unit2 := s.Factory.MakeUnit(c, &factory.UnitParams{Service: s.meteredService, SetCharmURL: true})
   232  
   233  	metrics := []params.Metric{{Key: "pings", Value: "5", Time: time.Now().UTC()}}
   234  	uuid := utils.MustNewUUID().String()
   235  
   236  	tests := []struct {
   237  		about  string
   238  		tag    string
   239  		expect string
   240  	}{{
   241  		about:  "different unit",
   242  		tag:    unit2.Tag().String(),
   243  		expect: "permission denied",
   244  	}, {
   245  		about:  "user tag",
   246  		tag:    names.NewLocalUserTag("admin").String(),
   247  		expect: `"user-admin@local" is not a valid unit tag`,
   248  	}, {
   249  		about:  "machine tag",
   250  		tag:    names.NewMachineTag("0").String(),
   251  		expect: `"machine-0" is not a valid unit tag`,
   252  	}}
   253  
   254  	for i, test := range tests {
   255  		c.Logf("test %d: %s", i, test.about)
   256  		result, err := s.uniter.AddMetricBatches(params.MetricBatchParams{
   257  			Batches: []params.MetricBatchParam{{
   258  				Tag: test.tag,
   259  				Batch: params.MetricBatch{
   260  					UUID:     uuid,
   261  					CharmURL: "",
   262  					Created:  time.Now(),
   263  					Metrics:  metrics,
   264  				}}}})
   265  
   266  		if test.expect == "" {
   267  			c.Assert(result.OneError(), jc.ErrorIsNil)
   268  		} else {
   269  			c.Assert(result.OneError(), gc.ErrorMatches, test.expect)
   270  		}
   271  		c.Assert(err, jc.ErrorIsNil)
   272  
   273  		_, err = s.State.MetricBatch(uuid)
   274  		c.Assert(err, jc.Satisfies, errors.IsNotFound)
   275  	}
   276  }