github.com/axw/juju@v0.0.0-20161005053422-4bd6544d08d4/api/migrationflag/facade.go (about)

     1  // Copyright 2016 Canonical Ltd.
     2  // Licensed under the LGPLv3, see LICENCE file for details.
     3  
     4  package migrationflag
     5  
     6  import (
     7  	"github.com/juju/errors"
     8  	"gopkg.in/juju/names.v2"
     9  
    10  	"github.com/juju/juju/api/base"
    11  	"github.com/juju/juju/apiserver/params"
    12  	"github.com/juju/juju/core/migration"
    13  	"github.com/juju/juju/watcher"
    14  )
    15  
    16  // NewWatcherFunc exists to let us unit test Facade without patching.
    17  type NewWatcherFunc func(base.APICaller, params.NotifyWatchResult) watcher.NotifyWatcher
    18  
    19  // NewFacade returns a Facade backed by the supplied api caller.
    20  func NewFacade(apiCaller base.APICaller, newWatcher NewWatcherFunc) *Facade {
    21  	facadeCaller := base.NewFacadeCaller(apiCaller, "MigrationFlag")
    22  	return &Facade{
    23  		caller:     facadeCaller,
    24  		newWatcher: newWatcher,
    25  	}
    26  }
    27  
    28  // Facade lets a client watch and query a model's migration phase.
    29  type Facade struct {
    30  	caller     base.FacadeCaller
    31  	newWatcher NewWatcherFunc
    32  }
    33  
    34  // Phase returns the current migration.Phase for the supplied model UUID.
    35  func (facade *Facade) Phase(uuid string) (migration.Phase, error) {
    36  	results := params.PhaseResults{}
    37  	err := facade.call("Phase", uuid, &results)
    38  	if err != nil {
    39  		return migration.UNKNOWN, errors.Trace(err)
    40  	}
    41  	if count := len(results.Results); count != 1 {
    42  		return migration.UNKNOWN, countError(count)
    43  	}
    44  	result := results.Results[0]
    45  	if result.Error != nil {
    46  		return migration.UNKNOWN, errors.Trace(result.Error)
    47  	}
    48  	phase, ok := migration.ParsePhase(result.Phase)
    49  	if !ok {
    50  		err := errors.Errorf("unknown phase %q", result.Phase)
    51  		return migration.UNKNOWN, err
    52  	}
    53  	return phase, nil
    54  }
    55  
    56  // Watch returns a NotifyWatcher that will inform of potential changes
    57  // to the result of Phase for the supplied model UUID.
    58  func (facade *Facade) Watch(uuid string) (watcher.NotifyWatcher, error) {
    59  	results := params.NotifyWatchResults{}
    60  	err := facade.call("Watch", uuid, &results)
    61  	if err != nil {
    62  		return nil, errors.Trace(err)
    63  	}
    64  	if count := len(results.Results); count != 1 {
    65  		return nil, countError(count)
    66  	}
    67  	result := results.Results[0]
    68  	if result.Error != nil {
    69  		return nil, errors.Trace(result.Error)
    70  	}
    71  	apiCaller := facade.caller.RawAPICaller()
    72  	watcher := facade.newWatcher(apiCaller, result)
    73  	return watcher, nil
    74  }
    75  
    76  // call converts the supplied model uuid into a params.Entities and
    77  // invokes the facade caller.
    78  func (facade *Facade) call(name, uuid string, results interface{}) error {
    79  	model := names.NewModelTag(uuid).String()
    80  	args := params.Entities{[]params.Entity{{model}}}
    81  	err := facade.caller.FacadeCall(name, args, results)
    82  	return errors.Trace(err)
    83  }
    84  
    85  // countError complains about malformed results.
    86  func countError(count int) error {
    87  	return errors.Errorf("expected 1 result, got %d", count)
    88  }