// Manifold returns a dependency manifold that runs a fan configurer
// worker, using the resource names defined in the supplied config.
196712
func Manifold(config ManifoldConfig) dependency.Manifold {
	return dependency.Manifold{
		Inputs: []string{
			config.APICallerName,
		},
		Output: func(in worker.Worker, out interface{}) error {
			inWorker, _ := in.(*FanConfigurer)
			if inWorker == nil {
				return errors.Errorf("in should be a %T; got %T", inWorker, in)
			}
			switch outPointer := out.(type) {
			case *bool:
				*outPointer = true
			default:
				return errors.Errorf("out should be *bool; got %T", out)
			}
			return nil
		},
		Start: func(context dependency.Context) (worker.Worker, error) {
			var apiCaller base.APICaller
			if err := context.Get(config.APICallerName, &apiCaller); err != nil {
				return nil, errors.Trace(err)
			}

			facade := apifanconfigurer.NewFacade(apiCaller)

			fanconfigurer, err := NewFanConfigurer(FanConfigurerConfig{
				Facade: facade,
			}, config.Clock)
			return fanconfigurer, errors.Annotate(err, "creating fanconfigurer orchestrator")
		},
	}
}
498091
func EnvironAPIManifold(config EnvironAPIConfig, start EnvironAPIStartFunc) dependency.Manifold {
	return dependency.Manifold{
		Inputs: []string{
			config.AgentName,
			config.APICallerName,
			config.EnvironName,
		},
		Start: func(context dependency.Context) (worker.Worker, error) {
			var agent agent.Agent
			if err := context.Get(config.AgentName, &agent); err != nil {
				return nil, errors.Trace(err)
			}
			var environ environs.Environ
			if err := context.Get(config.EnvironName, &environ); err != nil {
				return nil, errors.Trace(err)
			}
			var apiCaller base.APICaller
			if err := context.Get(config.APICallerName, &apiCaller); err != nil {
				return nil, errors.Trace(err)
			}
			return start(environ, apiCaller, agent)
		},
	}
}
488519
func (config ManifoldConfig) start(context dependency.Context) (worker.Worker, error) {
	if err := config.Validate(); err != nil {
		return nil, errors.Trace(err)
	}

	var agent agent.Agent
	if err := context.Get(config.AgentName, &agent); err != nil {
		return nil, errors.Trace(err)
	}
	var apiConn api.Connection
	if err := context.Get(config.APICallerName, &apiConn); err != nil {
		return nil, errors.Trace(err)
	}
	facade, err := config.NewRemoteRelationsFacade(apiConn)
	if err != nil {
		return nil, errors.Trace(err)
	}

	w, err := config.NewWorker(Config{
		ModelUUID:                agent.CurrentConfig().Model().Id(),
		RelationsFacade:          facade,
		NewRemoteModelFacadeFunc: remoteRelationsFacadeForModelFunc(config.NewControllerConnection),
		Clock:                    clock.WallClock,
	})
	if err != nil {
		return nil, errors.Trace(err)
	}
	return w, nil
}
611997
func (config ManifoldConfig) start(context dependency.Context) (worker.Worker, error) {
	if err := config.Validate(); err != nil {
		return nil, errors.Trace(err)
	}

	var stTracker workerstate.StateTracker
	if err := context.Get(config.StateName, &stTracker); err != nil {
		return nil, errors.Trace(err)
	}

	pool, err := stTracker.Use()
	if err != nil {
		return nil, errors.Trace(err)
	}

	w, err := config.NewWorker(Config{
		Logger:               config.Logger,
		WatcherFactory:       func() BackingWatcher { return pool.SystemState().WatchAllModels(pool) },
		PrometheusRegisterer: config.PrometheusRegisterer,
		Cleanup:              func() { _ = stTracker.Done() },
	})
	if err != nil {
		_ = stTracker.Done()
		return nil, errors.Trace(err)
	}
	return w, nil
}
355051
func Manifold(config ManifoldConfig) dependency.Manifold {
	return dependency.Manifold{
		Inputs: []string{
			config.AgentName,
			config.APICallerName,
			config.UpgradeStepsGateName,
		},
		Start: func(context dependency.Context) (worker.Worker, error) {
			// Sanity checks
			if config.OpenStateForUpgrade == nil {
				return nil, errors.New("missing OpenStateForUpgrade in config")
			}
			if config.PreUpgradeSteps == nil {
				return nil, errors.New("missing PreUpgradeSteps in config")
			}

			// Get machine agent.
			var agent agent.Agent
			if err := context.Get(config.AgentName, &agent); err != nil {
				return nil, errors.Trace(err)
			}

			// Get API connection.
			// TODO(fwereade): can we make the worker use an
			// APICaller instead? should be able to depend on
			// the Engine to abort us when conn is closed...
			var apiConn api.Connection
			if err := context.Get(config.APICallerName, &apiConn); err != nil {
				return nil, errors.Trace(err)
			}

			// Get upgradesteps completed lock.
			var upgradeStepsLock gate.Lock
			if err := context.Get(config.UpgradeStepsGateName, &upgradeStepsLock); err != nil {
				return nil, errors.Trace(err)
			}

			// Get a component capable of setting machine status
			// to indicate progress to the user.
			statusSetter, err := config.NewAgentStatusSetter(apiConn)
			if err != nil {
				return nil, errors.Trace(err)
			}
			// application tag for CAAS operator, machine or unit tag for agents.
			isOperator := agent.CurrentConfig().Tag().Kind() == names.ApplicationTagKind
			if isOperator {
				return NewWorker(
					upgradeStepsLock,
					agent,
					apiConn,
					nil,
					config.OpenStateForUpgrade,
					config.PreUpgradeSteps,
					statusSetter,
					isOperator,
				)
			}

			// Get the agent's jobs.
			// TODO(fwereade): use appropriate facade!
			agentFacade, err := apiagent.NewState(apiConn)
			if err != nil {
				return nil, errors.Trace(err)
			}
			entity, err := agentFacade.Entity(agent.CurrentConfig().Tag())
			if err != nil {
				return nil, errors.Trace(err)
			}
			return NewWorker(
				upgradeStepsLock,
				agent,
				apiConn,
				entity.Jobs(),
				config.OpenStateForUpgrade,
				config.PreUpgradeSteps,
				statusSetter,
				isOperator,
			)
		},
	}
}
820587
func Manifold(config ManifoldConfig) dependency.Manifold {
	return dependency.Manifold{
		Inputs: []string{
			config.AgentName,
			config.APICallerName,
			config.LeadershipTrackerName,
			config.CharmDirName,
			config.HookRetryStrategyName,
		},
		Start: func(context dependency.Context) (worker.Worker, error) {
			if config.Clock == nil {
				return nil, errors.NotValidf("missing Clock")
			}
			if config.MachineLock == nil {
				return nil, errors.NotValidf("missing MachineLock")
			}

			// Collect all required resources.
			var agent agent.Agent
			if err := context.Get(config.AgentName, &agent); err != nil {
				return nil, err
			}
			var apiConn api.Connection
			if err := context.Get(config.APICallerName, &apiConn); err != nil {
				// TODO(fwereade): absence of an APICaller shouldn't be the end of
				// the world -- we ought to return a type that can at least run the
				// leader-deposed hook -- but that's not done yet.
				return nil, err
			}
			var leadershipTracker leadership.TrackerWorker
			if err := context.Get(config.LeadershipTrackerName, &leadershipTracker); err != nil {
				return nil, err
			}
			var charmDirGuard fortress.Guard
			if err := context.Get(config.CharmDirName, &charmDirGuard); err != nil {
				return nil, err
			}

			var hookRetryStrategy params.RetryStrategy
			if err := context.Get(config.HookRetryStrategyName, &hookRetryStrategy); err != nil {
				return nil, err
			}

			downloader := api.NewCharmDownloader(apiConn)

			manifoldConfig := config
			// Configure and start the uniter.
			agentConfig := agent.CurrentConfig()
			tag := agentConfig.Tag()
			unitTag, ok := tag.(names.UnitTag)
			if !ok {
				return nil, errors.Errorf("expected a unit tag, got %v", tag)
			}
			uniterFacade := uniter.NewState(apiConn, unitTag)
			uniter, err := NewUniter(&UniterParams{
				UniterFacade:         uniterFacade,
				UnitTag:              unitTag,
				ModelType:            model.IAAS,
				LeadershipTracker:    leadershipTracker,
				DataDir:              agentConfig.DataDir(),
				Downloader:           downloader,
				MachineLock:          manifoldConfig.MachineLock,
				CharmDirGuard:        charmDirGuard,
				UpdateStatusSignal:   NewUpdateStatusTimer(),
				HookRetryStrategy:    hookRetryStrategy,
				NewOperationExecutor: operation.NewExecutor,
				TranslateResolverErr: config.TranslateResolverErr,
				Clock:                manifoldConfig.Clock,
			})
			if err != nil {
				return nil, errors.Trace(err)
			}
			return uniter, nil
		},
	}
}
1163644
func Manifold(config ManifoldConfig) dependency.Manifold {
	return dependency.Manifold{
		Inputs: []string{
			config.StateName,
		},
		Start: config.start,
		Filter: func(err error) error {
			if errors.Cause(err) == ErrRefresh {
				return dependency.ErrBounce
			}
			return err
		},
		Output: func(in worker.Worker, out interface{}) error {
			if w, ok := in.(*common.CleanupWorker); ok {
				in = w.Worker
			}
			return engine.FlagOutput(in, out)
		},
	}
}
664547
func APIManifold(config APIManifoldConfig, start APIStartFunc) dependency.Manifold {
	return dependency.Manifold{
		Inputs: []string{
			config.APICallerName,
		},
		Start: func(context dependency.Context) (worker.Worker, error) {
			var apiCaller base.APICaller
			if err := context.Get(config.APICallerName, &apiCaller); err != nil {
				return nil, err
			}
			return start(apiCaller)
		},
	}
}
1283135
func MachineManifold(config MachineManifoldConfig) dependency.Manifold {
	typedConfig := engine.AgentAPIManifoldConfig{
		AgentName:     config.AgentName,
		APICallerName: config.APICallerName,
	}
	return engine.AgentAPIManifold(typedConfig, config.newWorker)
}
389857
func (config ManifoldConfig) start(context dependency.Context) (worker.Worker, error) {
	if err := config.Validate(); err != nil {
		return nil, errors.Trace(err)
	}

	var stTracker workerstate.StateTracker
	if err := context.Get(config.StateName, &stTracker); err != nil {
		return nil, errors.Trace(err)
	}
	statePool, err := stTracker.Use()
	if err != nil {
		return nil, errors.Trace(err)
	}

	st := statePool.SystemState()
	w, err := config.NewWorker(Config{
		RestoreInfoWatcher: RestoreInfoWatcherShim{st},
	})
	if err != nil {
		stTracker.Done()
		return nil, errors.Trace(err)
	}
	return &cleanupWorker{
		RestoreStatusWorker: w,
		cleanup:             func() { stTracker.Done() },
	}, nil
}
979324
func Manifold(config ManifoldConfig) dependency.Manifold {
	manifold := dependency.Manifold{
		Inputs: []string{
			config.APICallerName,
		},
		Output: manifoldOutput,
		Start: func(context dependency.Context) (worker.Worker, error) {
			var apiCaller base.APICaller
			if err := context.Get(config.APICallerName, &apiCaller); err != nil {
				return nil, errors.Trace(err)
			}
			apiSt, err := agent.NewState(apiCaller)
			if err != nil {
				return nil, errors.Trace(err)
			}
			w, err := NewTracker(Config{
				Observer:       apiSt,
				NewEnvironFunc: config.NewEnvironFunc,
			})
			if err != nil {
				return nil, errors.Trace(err)
			}
			return w, nil
		},
	}
	return manifold
}
336338
func Manifold(config ManifoldConfig) dependency.Manifold {
	s := manifoldState{config: config}
	return dependency.Manifold{
		Inputs: []string{
			config.AgentName,
			config.ClockName,
			config.CentralHubName,
			config.StateName,
		},
		Start:  s.start,
		Output: s.output,
	}
}
637428
func (cfg ManifoldConfig) start(context dependency.Context) (worker.Worker, error) {
	if err := cfg.Validate(); err != nil {
		return nil, errors.Trace(err)
	}

	var agent agent.Agent
	if err := context.Get(cfg.AgentName, &agent); err != nil {
		return nil, errors.Trace(err)
	}
	var apiConn api.Connection
	if err := context.Get(cfg.APICallerName, &apiConn); err != nil {
		return nil, errors.Trace(err)
	}

	var environ environs.Environ
	if err := context.Get(cfg.EnvironName, &environ); err != nil {
		return nil, errors.Trace(err)
	}

	// Check if the env supports global firewalling.  If the
	// configured mode is instance, we can ignore fwEnv being a
	// nil value, as it won't be used.
	fwEnv, fwEnvOK := environ.(environs.Firewaller)

	mode := environ.Config().FirewallMode()
	if mode == config.FwNone {
		logger.Infof("stopping firewaller (not required)")
		return nil, dependency.ErrUninstall
	} else if mode == config.FwGlobal {
		if !fwEnvOK {
			logger.Infof("Firewall global mode set on provider with no support. stopping firewaller")
			return nil, dependency.ErrUninstall
		}
	}

	firewallerAPI, err := cfg.NewFirewallerFacade(apiConn)
	if err != nil {
		return nil, errors.Trace(err)
	}
	remoteRelationsAPI, err := cfg.NewRemoteRelationsFacade(apiConn)
	if err != nil {
		return nil, errors.Trace(err)
	}

	credentialAPI, err := cfg.NewCredentialValidatorFacade(apiConn)
	if err != nil {
		return nil, errors.Trace(err)
	}

	w, err := cfg.NewFirewallerWorker(Config{
		ModelUUID:               agent.CurrentConfig().Model().Id(),
		RemoteRelationsApi:      remoteRelationsAPI,
		FirewallerAPI:           firewallerAPI,
		EnvironFirewaller:       fwEnv,
		EnvironInstances:        environ,
		Mode:                    mode,
		NewCrossModelFacadeFunc: crossmodelFirewallerFacadeFunc(cfg.NewControllerConnection),
		CredentialAPI:           credentialAPI,
	})
	if err != nil {
		return nil, errors.Trace(err)
	}
	return w, nil
}
1169687
func Manifold(config ManifoldConfig) dependency.Manifold {
	return dependency.Manifold{
		Inputs: []string{
			config.ClockName,
			config.AgentName,
			config.AuthenticatorName,
			config.HubName,
			config.MuxName,
		},
		Start:  config.start,
		Output: transportOutput,
	}
}
842262
func manifoldStart(
	apiCaller base.APICaller,
	newExternalControllerWatcherClient NewExternalControllerWatcherClientFunc,
) (worker.Worker, error) {
	client := externalcontrollerupdater.New(apiCaller)
	worker, err := New(
		client,
		newExternalControllerWatcherClient,
		clock.WallClock,
	)
	if err != nil {
		return nil, errors.Trace(err)
	}
	return worker, nil
}
909991
func Manifold(config ManifoldConfig) dependency.Manifold {
	inputs := []string{
		config.AgentName,
		config.APICallerName,
	}

	// The machine agent uses these but the application agent doesn't.
	if config.UpgradeStepsGateName != "" {
		inputs = append(inputs, config.UpgradeStepsGateName)
	}
	if config.UpgradeCheckGateName != "" {
		inputs = append(inputs, config.UpgradeCheckGateName)
	}

	return dependency.Manifold{
		Inputs: inputs,
		Start: func(context dependency.Context) (worker.Worker, error) {
			if config.PreviousAgentVersion == version.Zero {
				return nil, errors.New("previous agent version not specified")
			}

			var agent agent.Agent
			if err := context.Get(config.AgentName, &agent); err != nil {
				return nil, err
			}
			currentConfig := agent.CurrentConfig()

			var apiCaller base.APICaller
			if err := context.Get(config.APICallerName, &apiCaller); err != nil {
				return nil, err
			}

			upgraderFacade := upgrader.NewState(apiCaller)
			operatorUpgraderFacade := caasoperatorupgrader.NewClient(apiCaller)

			var upgradeStepsWaiter gate.Waiter
			if config.UpgradeStepsGateName == "" {
				upgradeStepsWaiter = gate.NewLock()
			} else {
				if config.PreviousAgentVersion == version.Zero {
					return nil, errors.New("previous agent version not specified")
				}
				if err := context.Get(config.UpgradeStepsGateName, &upgradeStepsWaiter); err != nil {
					return nil, err
				}
			}

			var initialCheckUnlocker gate.Unlocker
			if config.UpgradeCheckGateName == "" {
				initialCheckUnlocker = gate.NewLock()
			} else {
				if err := context.Get(config.UpgradeCheckGateName, &initialCheckUnlocker); err != nil {
					return nil, err
				}
			}

			return NewUpgrader(Config{
				UpgraderClient:              upgraderFacade,
				CAASOperatorUpgrader:        operatorUpgraderFacade,
				AgentTag:                    currentConfig.Tag(),
				OrigAgentVersion:            config.PreviousAgentVersion,
				UpgradeStepsWaiter:          upgradeStepsWaiter,
				InitialUpgradeCheckComplete: initialCheckUnlocker,
			})
		},
	}
}
200705
func AgentManifold(config AgentManifoldConfig, start AgentStartFunc) dependency.Manifold {
	return dependency.Manifold{
		Inputs: []string{
			config.AgentName,
		},
		Start: func(context dependency.Context) (worker.Worker, error) {
			var agent agent.Agent
			if err := context.Get(config.AgentName, &agent); err != nil {
				return nil, err
			}
			return start(agent)
		},
	}
}