github.com/mattyw/juju@v0.0.0-20140610034352-732aecd63861/state/apiserver/root_test.go (about)

     1  // Copyright 2012, 2013 Canonical Ltd.
     2  // Licensed under the AGPLv3, see LICENCE file for details.
     3  
     4  package apiserver_test
     5  
     6  import (
     7  	"fmt"
     8  	"reflect"
     9  	"time"
    10  
    11  	jc "github.com/juju/testing/checkers"
    12  	gc "launchpad.net/gocheck"
    13  
    14  	"github.com/juju/juju/rpc/rpcreflect"
    15  	"github.com/juju/juju/state/apiserver"
    16  	"github.com/juju/juju/testing"
    17  )
    18  
    19  type rootSuite struct{}
    20  
    21  var _ = gc.Suite(&rootSuite{})
    22  
    23  var allowedDiscardedMethods = []string{
    24  	"AuthClient",
    25  	"AuthEnvironManager",
    26  	"AuthMachineAgent",
    27  	"AuthOwner",
    28  	"AuthUnitAgent",
    29  	"GetAuthEntity",
    30  	"GetAuthTag",
    31  }
    32  
    33  func (*rootSuite) TestDiscardedAPIMethods(c *gc.C) {
    34  	t := rpcreflect.TypeOf(apiserver.RootType)
    35  	// We must have some root-level methods.
    36  	c.Assert(t.MethodNames(), gc.Not(gc.HasLen), 0)
    37  	c.Assert(t.DiscardedMethods(), gc.DeepEquals, allowedDiscardedMethods)
    38  
    39  	for _, name := range t.MethodNames() {
    40  		m, err := t.Method(name)
    41  		c.Assert(err, gc.IsNil)
    42  		// We must have some methods on every object returned
    43  		// by a root-level method.
    44  		c.Assert(m.ObjType.MethodNames(), gc.Not(gc.HasLen), 0)
    45  		// We don't allow any methods that don't implement
    46  		// an RPC entry point.
    47  		c.Assert(m.ObjType.DiscardedMethods(), gc.HasLen, 0)
    48  	}
    49  }
    50  
    51  func (r *rootSuite) TestPingTimeout(c *gc.C) {
    52  	closedc := make(chan time.Time, 1)
    53  	action := func() {
    54  		closedc <- time.Now()
    55  	}
    56  	timeout := apiserver.NewPingTimeout(action, 50*time.Millisecond)
    57  	for i := 0; i < 2; i++ {
    58  		time.Sleep(10 * time.Millisecond)
    59  		timeout.Ping()
    60  	}
    61  	// Expect action to be executed about 50ms after last ping.
    62  	broken := time.Now()
    63  	var closed time.Time
    64  	select {
    65  	case closed = <-closedc:
    66  	case <-time.After(testing.LongWait):
    67  		c.Fatalf("action never executed")
    68  	}
    69  	closeDiff := closed.Sub(broken) / time.Millisecond
    70  	c.Assert(50 <= closeDiff && closeDiff <= 100, gc.Equals, true)
    71  }
    72  
    73  func (r *rootSuite) TestPingTimeoutStopped(c *gc.C) {
    74  	closedc := make(chan time.Time, 1)
    75  	action := func() {
    76  		closedc <- time.Now()
    77  	}
    78  	timeout := apiserver.NewPingTimeout(action, 20*time.Millisecond)
    79  	timeout.Ping()
    80  	timeout.Stop()
    81  	// The action should never trigger
    82  	select {
    83  	case <-closedc:
    84  		c.Fatalf("action triggered after Stop()")
    85  	case <-time.After(testing.ShortWait):
    86  	}
    87  }
    88  
    89  type errRootSuite struct {
    90  	testing.BaseSuite
    91  }
    92  
    93  var _ = gc.Suite(&errRootSuite{})
    94  
    95  func (s *errRootSuite) TestErrorRoot(c *gc.C) {
    96  	origErr := fmt.Errorf("my custom error")
    97  	errRoot := apiserver.NewErrRoot(origErr)
    98  	st, err := errRoot.Admin("")
    99  	c.Check(st, gc.IsNil)
   100  	c.Check(err, gc.Equals, origErr)
   101  }
   102  
   103  func (s *errRootSuite) TestErrorRootViaRPC(c *gc.C) {
   104  	origErr := fmt.Errorf("my custom error")
   105  	errRoot := apiserver.NewErrRoot(origErr)
   106  	val := rpcreflect.ValueOf(reflect.ValueOf(errRoot))
   107  	caller, err := val.MethodCaller("Admin", "Login")
   108  	c.Assert(err, gc.IsNil)
   109  	resp, err := caller.Call("", reflect.Value{})
   110  	c.Check(err, gc.Equals, origErr)
   111  	c.Check(resp.IsValid(), jc.IsFalse)
   112  }