github.com/makyo/juju@v0.0.0-20160425123129-2608902037e9/api/leadership/client.go (about)

     1  // Copyright 2014 Canonical Ltd.
     2  // Licensed under the AGPLv3, see LICENCE file for details.
     3  
     4  /*
     5  Package leadership implements the client to the analog leadership
     6  service.
     7  */
     8  package leadership
     9  
    10  import (
    11  	"time"
    12  
    13  	"github.com/juju/errors"
    14  	"github.com/juju/names"
    15  
    16  	"github.com/juju/juju/api/base"
    17  	"github.com/juju/juju/apiserver/params"
    18  	"github.com/juju/juju/core/leadership"
    19  )
    20  
    21  type client struct {
    22  	base.FacadeCaller
    23  }
    24  
    25  // NewClient returns a new leadership.Claimer backed by the supplied api caller.
    26  func NewClient(caller base.APICaller) leadership.Claimer {
    27  	return &client{base.NewFacadeCaller(caller, "LeadershipService")}
    28  }
    29  
    30  // ClaimLeadership is part of the leadership.Claimer interface.
    31  func (c *client) ClaimLeadership(serviceId, unitId string, duration time.Duration) error {
    32  
    33  	results, err := c.bulkClaimLeadership(c.prepareClaimLeadership(serviceId, unitId, duration))
    34  	if err != nil {
    35  		return err
    36  	}
    37  
    38  	// TODO(fwereade): this is not a rightful panic; we don't know who'll be using
    39  	// this client, and/or whether or not we're running critical code in the same
    40  	// process.
    41  	if err := results.Results[0].Error; err != nil {
    42  		if params.IsCodeLeadershipClaimDenied(err) {
    43  			return leadership.ErrClaimDenied
    44  		}
    45  		return err
    46  	}
    47  	return nil
    48  }
    49  
    50  // BlockUntilLeadershipReleased is part of the leadership.Claimer interface.
    51  func (c *client) BlockUntilLeadershipReleased(serviceId string) error {
    52  	const friendlyErrMsg = "error blocking on leadership release"
    53  	var result params.ErrorResult
    54  	err := c.FacadeCall("BlockUntilLeadershipReleased", names.NewServiceTag(serviceId), &result)
    55  	if err != nil {
    56  		return errors.Annotate(err, friendlyErrMsg)
    57  	} else if result.Error != nil {
    58  		return errors.Annotate(result.Error, friendlyErrMsg)
    59  	}
    60  	return nil
    61  }
    62  
    63  //
    64  // Prepare functions for building bulk-calls.
    65  //
    66  
    67  // prepareClaimLeadership creates a single set of params in
    68  // preperation for making a bulk call.
    69  func (c *client) prepareClaimLeadership(serviceId, unitId string, duration time.Duration) params.ClaimLeadershipParams {
    70  	return params.ClaimLeadershipParams{
    71  		names.NewServiceTag(serviceId).String(),
    72  		names.NewUnitTag(unitId).String(),
    73  		duration.Seconds(),
    74  	}
    75  }
    76  
    77  //
    78  // Bulk calls.
    79  //
    80  
    81  func (c *client) bulkClaimLeadership(args ...params.ClaimLeadershipParams) (*params.ClaimLeadershipBulkResults, error) {
    82  	// Don't make the jump over the network if we don't have to.
    83  	if len(args) <= 0 {
    84  		return &params.ClaimLeadershipBulkResults{}, nil
    85  	}
    86  
    87  	bulkParams := params.ClaimLeadershipBulkParams{args}
    88  	var results params.ClaimLeadershipBulkResults
    89  	if err := c.FacadeCall("ClaimLeadership", bulkParams, &results); err != nil {
    90  		return nil, errors.Annotate(err, "error making a leadership claim")
    91  	}
    92  	return &results, nil
    93  }