github.com/wallyworld/juju@v0.0.0-20161013125918-6cf1bc9d917a/apiserver/singular/singular_test.go (about)

     1  // Copyright 2015 Canonical Ltd.
     2  // Licensed under the AGPLv3, see LICENCE file for details.
     3  
     4  package singular_test
     5  
     6  import (
     7  	"time"
     8  
     9  	"github.com/juju/errors"
    10  	"github.com/juju/testing"
    11  	jc "github.com/juju/testing/checkers"
    12  	gc "gopkg.in/check.v1"
    13  
    14  	"github.com/juju/juju/apiserver/common"
    15  	"github.com/juju/juju/apiserver/params"
    16  	"github.com/juju/juju/apiserver/singular"
    17  	"github.com/juju/juju/core/lease"
    18  	coretesting "github.com/juju/juju/testing"
    19  )
    20  
    21  type SingularSuite struct {
    22  	testing.IsolationSuite
    23  }
    24  
    25  var _ = gc.Suite(&SingularSuite{})
    26  
    27  func (s *SingularSuite) TestRequiresEnvironManager(c *gc.C) {
    28  	auth := mockAuth{nonManager: true}
    29  	facade, err := singular.NewFacade(nil, auth)
    30  	c.Check(facade, gc.IsNil)
    31  	c.Check(err, gc.Equals, common.ErrPerm)
    32  }
    33  
    34  func (s *SingularSuite) TestAcceptsEnvironManager(c *gc.C) {
    35  	backend := &mockBackend{}
    36  	facade, err := singular.NewFacade(backend, mockAuth{})
    37  	c.Check(facade, gc.NotNil)
    38  	c.Check(err, jc.ErrorIsNil)
    39  
    40  	backend.stub.CheckCallNames(c)
    41  }
    42  
    43  func (s *SingularSuite) TestInvalidClaims(c *gc.C) {
    44  	breakers := []func(claim *params.SingularClaim){
    45  		func(claim *params.SingularClaim) { claim.ModelTag = "" },
    46  		func(claim *params.SingularClaim) { claim.ModelTag = "machine-123" },
    47  		func(claim *params.SingularClaim) { claim.ModelTag = "environ-blargle" },
    48  		func(claim *params.SingularClaim) { claim.ControllerTag = "" },
    49  		func(claim *params.SingularClaim) { claim.ControllerTag = "machine-456" },
    50  		func(claim *params.SingularClaim) { claim.ControllerTag = coretesting.ModelTag.String() },
    51  		func(claim *params.SingularClaim) { claim.Duration = time.Second - time.Millisecond },
    52  		func(claim *params.SingularClaim) { claim.Duration = time.Minute + time.Millisecond },
    53  	}
    54  	count := len(breakers)
    55  
    56  	var claims params.SingularClaims
    57  	claims.Claims = make([]params.SingularClaim, count)
    58  	for i, breaker := range breakers {
    59  		claim := params.SingularClaim{
    60  			ModelTag:      coretesting.ModelTag.String(),
    61  			ControllerTag: "machine-123",
    62  			Duration:      time.Minute,
    63  		}
    64  		breaker(&claim)
    65  		claims.Claims[i] = claim
    66  	}
    67  
    68  	backend := &mockBackend{}
    69  	facade, err := singular.NewFacade(backend, mockAuth{})
    70  	c.Assert(err, jc.ErrorIsNil)
    71  	result := facade.Claim(claims)
    72  	c.Assert(result.Results, gc.HasLen, count)
    73  
    74  	for i, result := range result.Results {
    75  		c.Logf("checking claim %d", i)
    76  		checkDenied(c, result)
    77  	}
    78  	backend.stub.CheckCallNames(c)
    79  }
    80  
    81  func (s *SingularSuite) TestValidClaims(c *gc.C) {
    82  	durations := []time.Duration{
    83  		time.Second,
    84  		10 * time.Second,
    85  		30 * time.Second,
    86  		time.Minute,
    87  	}
    88  	errors := []error{
    89  		nil,
    90  		errors.New("pow!"),
    91  		lease.ErrClaimDenied,
    92  		nil,
    93  	}
    94  	count := len(durations)
    95  	if len(errors) != count {
    96  		c.Fatalf("please fix your test data")
    97  	}
    98  
    99  	var claims params.SingularClaims
   100  	claims.Claims = make([]params.SingularClaim, count)
   101  	expectCalls := []testing.StubCall{}
   102  	for i, duration := range durations {
   103  		claims.Claims[i] = params.SingularClaim{
   104  			ModelTag:      coretesting.ModelTag.String(),
   105  			ControllerTag: "machine-123",
   106  			Duration:      duration,
   107  		}
   108  		expectCalls = append(expectCalls, testing.StubCall{
   109  			FuncName: "Claim",
   110  			Args: []interface{}{
   111  				coretesting.ModelTag.Id(),
   112  				"machine-123",
   113  				durations[i],
   114  			},
   115  		})
   116  	}
   117  
   118  	backend := &mockBackend{}
   119  	backend.stub.SetErrors(errors...)
   120  	facade, err := singular.NewFacade(backend, mockAuth{})
   121  	c.Assert(err, jc.ErrorIsNil)
   122  	result := facade.Claim(claims)
   123  	c.Assert(result.Results, gc.HasLen, count)
   124  
   125  	for i, err := range result.Results {
   126  		switch errors[i] {
   127  		case nil:
   128  			c.Check(err.Error, gc.IsNil)
   129  		case lease.ErrClaimDenied:
   130  			c.Check(err.Error, jc.Satisfies, params.IsCodeLeaseClaimDenied)
   131  		default:
   132  			c.Check(err.Error.Error(), gc.Equals, errors[i].Error())
   133  		}
   134  	}
   135  	backend.stub.CheckCalls(c, expectCalls)
   136  }
   137  
   138  func (s *SingularSuite) TestWait(c *gc.C) {
   139  	waits := params.Entities{
   140  		Entities: []params.Entity{{
   141  			"machine-123", // rejected
   142  		}, {
   143  			"grarble floop", // rejected
   144  		}, {
   145  			coretesting.ModelTag.String(), // stub-error
   146  		}, {
   147  			coretesting.ModelTag.String(), // success
   148  		}},
   149  	}
   150  	count := len(waits.Entities)
   151  
   152  	backend := &mockBackend{}
   153  	backend.stub.SetErrors(errors.New("zap!"), nil)
   154  	facade, err := singular.NewFacade(backend, mockAuth{})
   155  	c.Assert(err, jc.ErrorIsNil)
   156  	result := facade.Wait(waits)
   157  	c.Assert(result.Results, gc.HasLen, count)
   158  
   159  	checkDenied(c, result.Results[0])
   160  	checkDenied(c, result.Results[1])
   161  	c.Check(result.Results[2].Error, gc.ErrorMatches, "zap!")
   162  	c.Check(result.Results[3].Error, gc.IsNil)
   163  
   164  	backend.stub.CheckCalls(c, []testing.StubCall{{
   165  		FuncName: "WaitUntilExpired",
   166  		Args:     []interface{}{coretesting.ModelTag.Id()},
   167  	}, {
   168  		FuncName: "WaitUntilExpired",
   169  		Args:     []interface{}{coretesting.ModelTag.Id()},
   170  	}})
   171  }
   172  
   173  func checkDenied(c *gc.C, result params.ErrorResult) {
   174  	c.Check(result.Error, gc.ErrorMatches, "permission denied")
   175  	c.Check(result.Error, jc.Satisfies, params.IsCodeUnauthorized)
   176  }