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

     1  // Copyright 2013 Canonical Ltd.
     2  // Licensed under the AGPLv3, see LICENCE file for details.
     3  
     4  package provisioner
     5  
     6  import (
     7  	"fmt"
     8  
     9  	"github.com/juju/names"
    10  
    11  	"github.com/juju/juju/state/api/base"
    12  	"github.com/juju/juju/state/api/common"
    13  	"github.com/juju/juju/state/api/params"
    14  	"github.com/juju/juju/state/api/watcher"
    15  	"github.com/juju/juju/tools"
    16  )
    17  
    18  // State provides access to the Machiner API facade.
    19  type State struct {
    20  	*common.EnvironWatcher
    21  	*common.APIAddresser
    22  
    23  	caller base.Caller
    24  }
    25  
    26  const provisionerFacade = "Provisioner"
    27  
    28  // NewState creates a new client-side Machiner facade.
    29  func NewState(caller base.Caller) *State {
    30  	return &State{
    31  		EnvironWatcher: common.NewEnvironWatcher(provisionerFacade, caller),
    32  		APIAddresser:   common.NewAPIAddresser(provisionerFacade, caller),
    33  		caller:         caller}
    34  }
    35  
    36  func (st *State) call(method string, params, result interface{}) error {
    37  	return st.caller.Call(provisionerFacade, "", method, params, result)
    38  }
    39  
    40  // machineLife requests the lifecycle of the given machine from the server.
    41  func (st *State) machineLife(tag string) (params.Life, error) {
    42  	return common.Life(st.caller, provisionerFacade, tag)
    43  }
    44  
    45  // Machine provides access to methods of a state.Machine through the facade.
    46  func (st *State) Machine(tag string) (*Machine, error) {
    47  	life, err := st.machineLife(tag)
    48  	if err != nil {
    49  		return nil, err
    50  	}
    51  	return &Machine{
    52  		tag:  tag,
    53  		life: life,
    54  		st:   st,
    55  	}, nil
    56  }
    57  
    58  // WatchEnvironMachines returns a StringsWatcher that notifies of
    59  // changes to the lifecycles of the machines (but not containers) in
    60  // the current environment.
    61  func (st *State) WatchEnvironMachines() (watcher.StringsWatcher, error) {
    62  	var result params.StringsWatchResult
    63  	err := st.call("WatchEnvironMachines", nil, &result)
    64  	if err != nil {
    65  		return nil, err
    66  	}
    67  	if err := result.Error; err != nil {
    68  		return nil, result.Error
    69  	}
    70  	w := watcher.NewStringsWatcher(st.caller, result)
    71  	return w, nil
    72  }
    73  
    74  func (st *State) WatchMachineErrorRetry() (watcher.NotifyWatcher, error) {
    75  	var result params.NotifyWatchResult
    76  	err := st.call("WatchMachineErrorRetry", nil, &result)
    77  	if err != nil {
    78  		return nil, err
    79  	}
    80  	if err := result.Error; err != nil {
    81  		return nil, result.Error
    82  	}
    83  	w := watcher.NewNotifyWatcher(st.caller, result)
    84  	return w, nil
    85  }
    86  
    87  // StateAddresses returns the list of addresses used to connect to the state.
    88  func (st *State) StateAddresses() ([]string, error) {
    89  	var result params.StringsResult
    90  	err := st.call("StateAddresses", nil, &result)
    91  	if err != nil {
    92  		return nil, err
    93  	}
    94  	return result.Result, nil
    95  }
    96  
    97  // Tools returns the agent tools for the given entity.
    98  func (st *State) Tools(tag string) (*tools.Tools, error) {
    99  	var results params.ToolsResults
   100  	args := params.Entities{
   101  		Entities: []params.Entity{{Tag: tag}},
   102  	}
   103  	err := st.call("Tools", args, &results)
   104  	if err != nil {
   105  		// TODO: Not directly tested
   106  		return nil, err
   107  	}
   108  	if len(results.Results) != 1 {
   109  		// TODO: Not directly tested
   110  		return nil, fmt.Errorf("expected 1 result, got %d", len(results.Results))
   111  	}
   112  	result := results.Results[0]
   113  	if err := result.Error; err != nil {
   114  		return nil, err
   115  	}
   116  	return result.Tools, nil
   117  }
   118  
   119  // ContainerManagerConfig returns information from the environment config that is
   120  // needed for configuring the container manager.
   121  func (st *State) ContainerManagerConfig(args params.ContainerManagerConfigParams) (result params.ContainerManagerConfig, err error) {
   122  	err = st.call("ContainerManagerConfig", args, &result)
   123  	return result, err
   124  }
   125  
   126  // ContainerConfig returns information from the environment config that is
   127  // needed for container cloud-init.
   128  func (st *State) ContainerConfig() (result params.ContainerConfig, err error) {
   129  	err = st.call("ContainerConfig", nil, &result)
   130  	return result, err
   131  }
   132  
   133  // MachinesWithTransientErrors returns a slice of machines and corresponding status information
   134  // for those machines which have transient provisioning errors.
   135  func (st *State) MachinesWithTransientErrors() ([]*Machine, []params.StatusResult, error) {
   136  	var results params.StatusResults
   137  	err := st.call("MachinesWithTransientErrors", nil, &results)
   138  	if err != nil {
   139  		return nil, nil, err
   140  	}
   141  	machines := make([]*Machine, len(results.Results))
   142  	for i, status := range results.Results {
   143  		if status.Error != nil {
   144  			continue
   145  		}
   146  		machines[i] = &Machine{
   147  			tag:  names.MachineTag(status.Id),
   148  			life: status.Life,
   149  			st:   st,
   150  		}
   151  	}
   152  	return machines, results.Results, nil
   153  }