Exemplo n.º 1
0
// UpdateLatestRevisions retrieves the latest revision information from the charm store for all deployed charms
// and records this information in state.
func (api *CharmRevisionUpdaterAPI) UpdateLatestRevisions() (params.ErrorResult, error) {
	// First get the uuid for the environment to use when querying the charm store.
	env, err := api.state.Environment()
	if err != nil {
		return params.ErrorResult{Error: common.ServerError(err)}, nil
	}
	uuid := env.UUID()

	deployedCharms, err := fetchAllDeployedCharms(api.state)
	if err != nil {
		return params.ErrorResult{Error: common.ServerError(err)}, nil
	}
	// Look up the revision information for all the deployed charms.
	curls, err := retrieveLatestCharmInfo(deployedCharms, uuid)
	if err != nil {
		return params.ErrorResult{Error: common.ServerError(err)}, nil
	}
	// Add the charms and latest revision info to state as charm placeholders.
	for _, curl := range curls {
		if err = api.state.AddStoreCharmPlaceholder(curl); err != nil {
			return params.ErrorResult{Error: common.ServerError(err)}, nil
		}
	}
	return params.ErrorResult{}, nil
}
Exemplo n.º 2
0
func (api *UserManagerAPI) RemoveUser(args params.Entities) (params.ErrorResults, error) {
	result := params.ErrorResults{
		Results: make([]params.ErrorResult, len(args.Entities)),
	}
	if len(args.Entities) == 0 {
		return result, nil
	}
	canWrite, err := api.getCanWrite()
	if err != nil {
		return result, err
	}
	for i, arg := range args.Entities {
		if !canWrite(arg.Tag) {
			result.Results[i].Error = common.ServerError(common.ErrPerm)
			continue
		}
		user, err := api.state.User(arg.Tag)
		if err != nil {
			result.Results[i].Error = common.ServerError(common.ErrPerm)
			continue
		}
		err = user.Deactivate()
		if err != nil {
			result.Results[i].Error = common.ServerError(fmt.Errorf("Failed to remove user: %s", err))
			continue
		}
	}
	return result, nil
}
Exemplo n.º 3
0
// SetSupportedContainers updates the list of containers supported by the machines passed in args.
func (p *ProvisionerAPI) SetSupportedContainers(
	args params.MachineContainersParams) (params.ErrorResults, error) {

	result := params.ErrorResults{
		Results: make([]params.ErrorResult, len(args.Params)),
	}
	for i, arg := range args.Params {
		canAccess, err := p.getAuthFunc()
		if err != nil {
			return result, err
		}
		machine, err := p.getMachine(canAccess, arg.MachineTag)
		if err != nil {
			result.Results[i].Error = common.ServerError(err)
			continue
		}
		if len(arg.ContainerTypes) == 0 {
			err = machine.SupportsNoContainers()
		} else {
			err = machine.SetSupportedContainers(arg.ContainerTypes)
		}
		if err != nil {
			result.Results[i].Error = common.ServerError(err)
		}
	}
	return result, nil
}
Exemplo n.º 4
0
// WatchAuthorisedKeys starts a watcher to track changes to the authorised ssh keys
// for the specified machines.
// The current implementation relies on global authorised keys being stored in the environment config.
// This will change as new user management and authorisation functionality is added.
func (api *KeyUpdaterAPI) WatchAuthorisedKeys(arg params.Entities) (params.NotifyWatchResults, error) {
	results := make([]params.NotifyWatchResult, len(arg.Entities))

	canRead, err := api.getCanRead()
	if err != nil {
		return params.NotifyWatchResults{}, err
	}
	for i, entity := range arg.Entities {
		// 1. Check permissions
		if !canRead(entity.Tag) {
			results[i].Error = common.ServerError(common.ErrPerm)
			continue
		}
		// 2. Check entity exists
		if _, err := api.state.FindEntity(entity.Tag); err != nil {
			if errors.IsNotFound(err) {
				results[i].Error = common.ServerError(common.ErrPerm)
			} else {
				results[i].Error = common.ServerError(err)
			}
			continue
		}
		// 3. Watch fr changes
		var err error
		watch := api.state.WatchForEnvironConfigChanges()
		// Consume the initial event.
		if _, ok := <-watch.Changes(); ok {
			results[i].NotifyWatcherId = api.resources.Register(watch)
		} else {
			err = watcher.MustErr(watch)
		}
		results[i].Error = common.ServerError(err)
	}
	return params.NotifyWatchResults{Results: results}, nil
}
Exemplo n.º 5
0
func (api *UserManagerAPI) AddUser(args params.EntityPasswords) (params.ErrorResults, error) {
	result := params.ErrorResults{
		Results: make([]params.ErrorResult, len(args.Changes)),
	}
	if len(args.Changes) == 0 {
		return result, nil
	}
	canWrite, err := api.getCanWrite()
	if err != nil {
		result.Results[0].Error = common.ServerError(err)
		return result, err
	}
	for i, arg := range args.Changes {
		if !canWrite(arg.Tag) {
			result.Results[0].Error = common.ServerError(common.ErrPerm)
			continue
		}
		_, err := api.state.AddUser(arg.Tag, arg.Password)
		if err != nil {
			err = fmt.Errorf("Failed to create user: %v", err)
			result.Results[i].Error = common.ServerError(err)
			continue
		}
	}
	return result, nil
}
Exemplo n.º 6
0
// DesiredVersion reports the Agent Version that we want that agent to be running
func (u *UpgraderAPI) DesiredVersion(args params.Entities) (params.VersionResults, error) {
	results := make([]params.VersionResult, len(args.Entities))
	if len(args.Entities) == 0 {
		return params.VersionResults{}, nil
	}
	agentVersion, _, err := u.getGlobalAgentVersion()
	if err != nil {
		return params.VersionResults{}, common.ServerError(err)
	}
	// Is the desired version greater than the current API server version?
	isNewerVersion := agentVersion.Compare(version.Current.Number) > 0
	for i, entity := range args.Entities {
		err := common.ErrPerm
		if u.authorizer.AuthOwner(entity.Tag) {
			if !isNewerVersion || u.entityIsManager(entity.Tag) {
				results[i].Version = &agentVersion
			} else {
				logger.Debugf("desired version is %s, but current version is %s and agent is not a manager node", agentVersion, version.Current.Number)
				results[i].Version = &version.Current.Number
			}
			err = nil
		}
		results[i].Error = common.ServerError(err)
	}
	return params.VersionResults{Results: results}, nil
}
Exemplo n.º 7
0
// SetInstanceInfo sets the provider specific machine id, nonce,
// metadata and network info for each given machine. Once set, the
// instance id cannot be changed.
func (p *ProvisionerAPI) SetInstanceInfo(args params.InstancesInfo) (params.ErrorResults, error) {
	result := params.ErrorResults{
		Results: make([]params.ErrorResult, len(args.Machines)),
	}
	canAccess, err := p.getAuthFunc()
	if err != nil {
		return result, err
	}
	for i, arg := range args.Machines {
		machine, err := p.getMachine(canAccess, arg.Tag)
		if err == nil {
			var networks []state.NetworkInfo
			var interfaces []state.NetworkInterfaceInfo
			networks, interfaces, err = networkParamsToStateParams(arg.Networks, arg.Interfaces)
			if err == nil {
				err = machine.SetInstanceInfo(
					arg.InstanceId, arg.Nonce, arg.Characteristics,
					networks, interfaces)
			}
			if err != nil {
				// Give the user more context about the error.
				err = fmt.Errorf("aborted instance %q: %v", arg.InstanceId, err)
			}
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 8
0
// RequestedNetworks returns the requested networks for each given
// machine entity. Each entry in both lists is returned with its
// provider specific id.
func (p *ProvisionerAPI) RequestedNetworks(args params.Entities) (params.RequestedNetworksResults, error) {
	result := params.RequestedNetworksResults{
		Results: make([]params.RequestedNetworkResult, len(args.Entities)),
	}
	canAccess, err := p.getAuthFunc()
	if err != nil {
		return result, err
	}
	for i, entity := range args.Entities {
		machine, err := p.getMachine(canAccess, entity.Tag)
		if err == nil {
			var includeNetworks []string
			var excludeNetworks []string
			includeNetworks, excludeNetworks, err = machine.RequestedNetworks()
			if err == nil {
				// TODO(dimitern) For now, since network names and
				// provider ids are the same, we return what we got
				// from state. In the future, when networks can be
				// added before provisioning, we should convert both
				// slices from juju network names to provider-specific
				// ids before returning them.
				result.Results[i].IncludeNetworks = includeNetworks
				result.Results[i].ExcludeNetworks = excludeNetworks
			}
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 9
0
// DistributionGroup returns, for each given machine entity,
// a slice of instance.Ids that belong to the same distribution
// group as that machine. This information may be used to
// distribute instances for high availability.
func (p *ProvisionerAPI) DistributionGroup(args params.Entities) (params.DistributionGroupResults, error) {
	result := params.DistributionGroupResults{
		Results: make([]params.DistributionGroupResult, len(args.Entities)),
	}
	canAccess, err := p.getAuthFunc()
	if err != nil {
		return result, err
	}
	for i, entity := range args.Entities {
		machine, err := p.getMachine(canAccess, entity.Tag)
		if err == nil {
			// If the machine is an environment manager, return
			// environment manager instances. Otherwise, return
			// instances with services in common with the machine
			// being provisioned.
			if machine.IsManager() {
				result.Results[i].Result, err = environManagerInstances(p.st)
			} else {
				result.Results[i].Result, err = commonServiceInstances(p.st, machine)
			}
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 10
0
func (api *RsyslogAPI) SetRsyslogCert(args params.SetRsyslogCertParams) (params.ErrorResult, error) {
	var result params.ErrorResult
	if !api.canModify {
		result.Error = common.ServerError(common.ErrBadCreds)
		return result, nil
	}
	if _, err := cert.ParseCert(string(args.CACert)); err != nil {
		result.Error = common.ServerError(err)
		return result, nil
	}
	attrs := map[string]interface{}{"rsyslog-ca-cert": string(args.CACert)}
	if err := api.st.UpdateEnvironConfig(attrs, nil, nil); err != nil {
		result.Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 11
0
// CharmURL returns the charm URL for all given units or services.
func (u *UniterAPI) CharmURL(args params.Entities) (params.StringBoolResults, error) {
	result := params.StringBoolResults{
		Results: make([]params.StringBoolResult, len(args.Entities)),
	}
	accessUnitOrService := common.AuthEither(u.accessUnit, u.accessService)
	canAccess, err := accessUnitOrService()
	if err != nil {
		return params.StringBoolResults{}, err
	}
	for i, entity := range args.Entities {
		err := common.ErrPerm
		if canAccess(entity.Tag) {
			var unitOrService state.Entity
			unitOrService, err = u.st.FindEntity(entity.Tag)
			if err == nil {
				charmURLer := unitOrService.(interface {
					CharmURL() (*charm.URL, bool)
				})
				curl, ok := charmURLer.CharmURL()
				if curl != nil {
					result.Results[i].Result = curl.String()
					result.Results[i].Ok = ok
				}
			}
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 12
0
// ReadRemoteSettings returns the remote settings of each given set of
// relation/local unit/remote unit.
func (u *UniterAPI) ReadRemoteSettings(args params.RelationUnitPairs) (params.RelationSettingsResults, error) {
	result := params.RelationSettingsResults{
		Results: make([]params.RelationSettingsResult, len(args.RelationUnitPairs)),
	}
	canAccess, err := u.accessUnit()
	if err != nil {
		return params.RelationSettingsResults{}, err
	}
	for i, arg := range args.RelationUnitPairs {
		relUnit, err := u.getRelationUnit(canAccess, arg.Relation, arg.LocalUnit)
		if err == nil {
			remoteUnit := ""
			remoteUnit, err = u.checkRemoteUnit(relUnit, arg.RemoteUnit)
			if err == nil {
				var settings map[string]interface{}
				settings, err = relUnit.ReadSettings(remoteUnit)
				if err == nil {
					result.Results[i].Settings, err = convertRelationSettings(settings)
				}
			}
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 13
0
// GetPrincipal returns the result of calling PrincipalName() and
// converting it to a tag, on each given unit.
func (u *UniterAPI) GetPrincipal(args params.Entities) (params.StringBoolResults, error) {
	result := params.StringBoolResults{
		Results: make([]params.StringBoolResult, len(args.Entities)),
	}
	canAccess, err := u.accessUnit()
	if err != nil {
		return params.StringBoolResults{}, err
	}
	for i, entity := range args.Entities {
		err := common.ErrPerm
		if canAccess(entity.Tag) {
			var unit *state.Unit
			unit, err = u.getUnit(entity.Tag)
			if err == nil {
				principal, ok := unit.PrincipalName()
				if principal != "" {
					result.Results[i].Result = names.UnitTag(principal)
				}
				result.Results[i].Ok = ok
			}
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 14
0
// CharmArchiveURL returns the URL, corresponding to the charm archive
// (bundle) in the provider storage for each given charm URL, along
// with the DisableSSLHostnameVerification flag.
func (u *UniterAPI) CharmArchiveURL(args params.CharmURLs) (params.CharmArchiveURLResults, error) {
	result := params.CharmArchiveURLResults{
		Results: make([]params.CharmArchiveURLResult, len(args.URLs)),
	}
	// Get the SSL hostname verification environment setting.
	envConfig, err := u.st.EnvironConfig()
	if err != nil {
		return result, err
	}
	// SSLHostnameVerification defaults to true, so we need to
	// invert that, for backwards-compatibility (older versions
	// will have DisableSSLHostnameVerification: false by default).
	disableSSLHostnameVerification := !envConfig.SSLHostnameVerification()
	for i, arg := range args.URLs {
		curl, err := charm.ParseURL(arg.URL)
		if err != nil {
			err = common.ErrPerm
		} else {
			var sch *state.Charm
			sch, err = u.st.Charm(curl)
			if errors.IsNotFound(err) {
				err = common.ErrPerm
			}
			if err == nil {
				result.Results[i].Result = sch.BundleURL().String()
				result.Results[i].DisableSSLHostnameVerification = disableSSLHostnameVerification
			}
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 15
0
// PublicAddress returns the public address for each given unit, if set.
func (u *UniterAPI) PublicAddress(args params.Entities) (params.StringResults, error) {
	result := params.StringResults{
		Results: make([]params.StringResult, len(args.Entities)),
	}
	canAccess, err := u.accessUnit()
	if err != nil {
		return params.StringResults{}, err
	}
	for i, entity := range args.Entities {
		err := common.ErrPerm
		if canAccess(entity.Tag) {
			var unit *state.Unit
			unit, err = u.getUnit(entity.Tag)
			if err == nil {
				address, ok := unit.PublicAddress()
				if ok {
					result.Results[i].Result = address
				} else {
					err = common.NoAddressSetError(entity.Tag, "public")
				}
			}
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 16
0
// UpdateSettings persists all changes made to the local settings of
// all given pairs of relation and unit. Keys with empty values are
// considered a signal to delete these values.
func (u *UniterAPI) UpdateSettings(args params.RelationUnitsSettings) (params.ErrorResults, error) {
	result := params.ErrorResults{
		Results: make([]params.ErrorResult, len(args.RelationUnits)),
	}
	canAccess, err := u.accessUnit()
	if err != nil {
		return params.ErrorResults{}, err
	}
	for i, arg := range args.RelationUnits {
		relUnit, err := u.getRelationUnit(canAccess, arg.Relation, arg.Unit)
		if err == nil {
			var settings *state.Settings
			settings, err = relUnit.Settings()
			if err == nil {
				for k, v := range arg.Settings {
					if v == "" {
						settings.Delete(k)
					} else {
						settings.Set(k, v)
					}
				}
				_, err = settings.Write()
			}
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 17
0
// ConfigSettings returns the complete set of service charm config
// settings available to each given unit.
func (u *UniterAPI) ConfigSettings(args params.Entities) (params.ConfigSettingsResults, error) {
	result := params.ConfigSettingsResults{
		Results: make([]params.ConfigSettingsResult, len(args.Entities)),
	}
	canAccess, err := u.accessUnit()
	if err != nil {
		return params.ConfigSettingsResults{}, err
	}
	for i, entity := range args.Entities {
		err := common.ErrPerm
		if canAccess(entity.Tag) {
			var unit *state.Unit
			unit, err = u.getUnit(entity.Tag)
			if err == nil {
				var settings charm.Settings
				settings, err = unit.ConfigSettings()
				if err == nil {
					result.Results[i].Settings = params.ConfigSettings(settings)
				}
			}
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 18
0
// SetCharmURL sets the charm URL for each given unit. An error will
// be returned if a unit is dead, or the charm URL is not know.
func (u *UniterAPI) SetCharmURL(args params.EntitiesCharmURL) (params.ErrorResults, error) {
	result := params.ErrorResults{
		Results: make([]params.ErrorResult, len(args.Entities)),
	}
	canAccess, err := u.accessUnit()
	if err != nil {
		return params.ErrorResults{}, err
	}
	for i, entity := range args.Entities {
		err := common.ErrPerm
		if canAccess(entity.Tag) {
			var unit *state.Unit
			unit, err = u.getUnit(entity.Tag)
			if err == nil {
				var curl *charm.URL
				curl, err = charm.ParseURL(entity.CharmURL)
				if err == nil {
					err = unit.SetCharmURL(curl)
				}
			}
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 19
0
// AuthorisedKeys reports the authorised ssh keys for the specified machines.
// The current implementation relies on global authorised keys being stored in the environment config.
// This will change as new user management and authorisation functionality is added.
func (api *KeyUpdaterAPI) AuthorisedKeys(arg params.Entities) (params.StringsResults, error) {
	if len(arg.Entities) == 0 {
		return params.StringsResults{}, nil
	}
	results := make([]params.StringsResult, len(arg.Entities))

	// For now, authorised keys are global, common to all machines.
	var keys []string
	config, configErr := api.state.EnvironConfig()
	if configErr == nil {
		keys = ssh.SplitAuthorisedKeys(config.AuthorizedKeys())
	}

	canRead, err := api.getCanRead()
	if err != nil {
		return params.StringsResults{}, err
	}
	for i, entity := range arg.Entities {
		// 1. Check permissions
		if !canRead(entity.Tag) {
			results[i].Error = common.ServerError(common.ErrPerm)
			continue
		}
		// 2. Check entity exists
		if _, err := api.state.FindEntity(entity.Tag); err != nil {
			if errors.IsNotFound(err) {
				results[i].Error = common.ServerError(common.ErrPerm)
			} else {
				results[i].Error = common.ServerError(err)
			}
			continue
		}
		// 3. Get keys
		var err error
		if configErr == nil {
			results[i].Result = keys
		} else {
			err = configErr
		}
		results[i].Error = common.ServerError(err)
	}
	return params.StringsResults{Results: results}, nil
}
Exemplo n.º 20
0
// WatchContainers starts a StringsWatcher to watch containers deployed to
// any machine passed in args.
func (p *ProvisionerAPI) WatchContainers(args params.WatchContainers) (params.StringsWatchResults, error) {
	result := params.StringsWatchResults{
		Results: make([]params.StringsWatchResult, len(args.Params)),
	}
	for i, arg := range args.Params {
		watcherResult, err := p.watchOneMachineContainers(arg)
		result.Results[i] = watcherResult
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 21
0
func (api *API) GetEntities(args params.Entities) params.AgentGetEntitiesResults {
	results := params.AgentGetEntitiesResults{
		Entities: make([]params.AgentGetEntitiesResult, len(args.Entities)),
	}
	for i, entity := range args.Entities {
		result, err := api.getEntity(entity.Tag)
		result.Error = common.ServerError(err)
		results.Entities[i] = result
	}
	return results
}
Exemplo n.º 22
0
// ListKeys returns the authorised ssh keys for the specified users.
func (api *KeyManagerAPI) ListKeys(arg params.ListSSHKeys) (params.StringsResults, error) {
	if len(arg.Entities.Entities) == 0 {
		return params.StringsResults{}, nil
	}
	results := make([]params.StringsResult, len(arg.Entities.Entities))

	// For now, authorised keys are global, common to all users.
	var keyInfo []string
	cfg, configErr := api.state.EnvironConfig()
	if configErr == nil {
		keys := ssh.SplitAuthorisedKeys(cfg.AuthorizedKeys())
		keyInfo = parseKeys(keys, arg.Mode)
	}

	canRead, err := api.getCanRead()
	if err != nil {
		return params.StringsResults{}, err
	}
	for i, entity := range arg.Entities.Entities {
		if !canRead(entity.Tag) {
			results[i].Error = common.ServerError(common.ErrPerm)
			continue
		}
		if _, err := api.state.User(entity.Tag); err != nil {
			if errors.IsNotFound(err) {
				results[i].Error = common.ServerError(common.ErrPerm)
			} else {
				results[i].Error = common.ServerError(err)
			}
			continue
		}
		var err error
		if configErr == nil {
			results[i].Result = keyInfo
		} else {
			err = configErr
		}
		results[i].Error = common.ServerError(err)
	}
	return params.StringsResults{Results: results}, nil
}
Exemplo n.º 23
0
// Tools finds the tools necessary for the given agents.
func (u *UnitUpgraderAPI) Tools(args params.Entities) (params.ToolsResults, error) {
	result := params.ToolsResults{
		Results: make([]params.ToolsResult, len(args.Entities)),
	}
	for i, entity := range args.Entities {
		result.Results[i].Error = common.ServerError(common.ErrPerm)
		if u.authorizer.AuthOwner(entity.Tag) {
			result.Results[i] = u.getMachineTools(entity.Tag)
		}
	}
	return result, nil
}
Exemplo n.º 24
0
func (u *UnitUpgraderAPI) getMachineTools(tag string) params.ToolsResult {
	var result params.ToolsResult
	machine, err := u.getAssignedMachine(tag)
	if err != nil {
		result.Error = common.ServerError(err)
		return result
	}
	machineTools, err := machine.AgentTools()
	if err != nil {
		result.Error = common.ServerError(err)
		return result
	}
	// For older 1.16 upgrader workers, we need to supply a tools URL since the worker will attempt to
	// download the tools even though they already have been fetched by the machine agent. Newer upgrader
	// workers do not have this problem. So to be compatible across all versions, we return the full
	// tools metadata.
	// TODO (wallyworld) - remove in 1.20, just return machineTools
	cfg, err := u.st.EnvironConfig()
	if err != nil {
		result.Error = common.ServerError(err)
		return result
	}
	// SSLHostnameVerification defaults to true, so we need to
	// invert that, for backwards-compatibility (older versions
	// will have DisableSSLHostnameVerification: false by default).
	result.DisableSSLHostnameVerification = !cfg.SSLHostnameVerification()
	env, err := environs.New(cfg)
	if err != nil {
		result.Error = common.ServerError(err)
		return result
	}
	agentTools, err := envtools.FindExactTools(
		env, machineTools.Version.Number, machineTools.Version.Series, machineTools.Version.Arch)
	if err != nil {
		result.Error = common.ServerError(err)
		return result
	}
	result.Tools = agentTools
	return result
}
Exemplo n.º 25
0
// AddMachinesV2 adds new machines with the supplied parameters.
func (c *Client) AddMachinesV2(args params.AddMachines) (params.AddMachinesResults, error) {
	results := params.AddMachinesResults{
		Machines: make([]params.AddMachinesResult, len(args.MachineParams)),
	}
	for i, p := range args.MachineParams {
		m, err := c.addOneMachine(p)
		results.Machines[i].Error = common.ServerError(err)
		if err == nil {
			results.Machines[i].Machine = m.Id()
		}
	}
	return results, nil
}
Exemplo n.º 26
0
// RelationById returns information about all given relations,
// specified by their ids, including their key and the local
// endpoint.
func (u *UniterAPI) RelationById(args params.RelationIds) (params.RelationResults, error) {
	result := params.RelationResults{
		Results: make([]params.RelationResult, len(args.RelationIds)),
	}
	for i, relId := range args.RelationIds {
		relParams, err := u.getOneRelationById(relId)
		if err == nil {
			result.Results[i] = relParams
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 27
0
// DesiredVersion reports the Agent Version that we want that unit to be running.
// The desired version is what the unit's assigned machine is running.
func (u *UnitUpgraderAPI) DesiredVersion(args params.Entities) (params.VersionResults, error) {
	result := make([]params.VersionResult, len(args.Entities))
	if len(args.Entities) == 0 {
		return params.VersionResults{}, nil
	}
	for i, entity := range args.Entities {
		err := common.ErrPerm
		if u.authorizer.AuthOwner(entity.Tag) {
			result[i].Version, err = u.getMachineToolsVersion(entity.Tag)
		}
		result[i].Error = common.ServerError(err)
	}
	return params.VersionResults{Results: result}, nil
}
Exemplo n.º 28
0
func (s *errorsSuite) TestErrorTransform(c *gc.C) {
	for _, t := range errorTransformTests {
		err1 := common.ServerError(t.err)
		if t.err == nil {
			c.Assert(err1, gc.IsNil)
		} else {
			c.Assert(err1.Message, gc.Equals, t.err.Error())
			c.Assert(err1.Code, gc.Equals, t.code)
			if t.helperFunc != nil {
				c.Assert(err1, jc.Satisfies, t.helperFunc)
			}
		}
	}
}
Exemplo n.º 29
0
// WatchRelationUnits returns a RelationUnitsWatcher for observing
// changes to every unit in the supplied relation that is visible to
// the supplied unit. See also state/watcher.go:RelationUnit.Watch().
func (u *UniterAPI) WatchRelationUnits(args params.RelationUnits) (params.RelationUnitsWatchResults, error) {
	result := params.RelationUnitsWatchResults{
		Results: make([]params.RelationUnitsWatchResult, len(args.RelationUnits)),
	}
	canAccess, err := u.accessUnit()
	if err != nil {
		return params.RelationUnitsWatchResults{}, err
	}
	for i, arg := range args.RelationUnits {
		relUnit, err := u.getRelationUnit(canAccess, arg.Relation, arg.Unit)
		if err == nil {
			result.Results[i], err = u.watchOneRelationUnit(relUnit)
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}
Exemplo n.º 30
0
// Relation returns information about all given relation/unit pairs,
// including their id, key and the local endpoint.
func (u *UniterAPI) Relation(args params.RelationUnits) (params.RelationResults, error) {
	result := params.RelationResults{
		Results: make([]params.RelationResult, len(args.RelationUnits)),
	}
	canAccess, err := u.accessUnit()
	if err != nil {
		return params.RelationResults{}, err
	}
	for i, rel := range args.RelationUnits {
		relParams, err := u.getOneRelation(canAccess, rel.Relation, rel.Unit)
		if err == nil {
			result.Results[i] = relParams
		}
		result.Results[i].Error = common.ServerError(err)
	}
	return result, nil
}