本文整理汇总了Golang中github.com/juju/juju/environs.BootstrapContext类的典型用法代码示例。如果您正苦于以下问题:Golang BootstrapContext类的具体用法?Golang BootstrapContext怎么用?Golang BootstrapContext使用的例子?那么恭喜您, 这里精选的类代码示例或许可以为您提供帮助。
在下文中一共展示了BootstrapContext类的15个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的Golang代码示例。
示例1: ConfigureMachine
func ConfigureMachine(ctx environs.BootstrapContext, client ssh.Client, host string, machineConfig *cloudinit.MachineConfig) error {
// Bootstrap is synchronous, and will spawn a subprocess
// to complete the procedure. If the user hits Ctrl-C,
// SIGINT is sent to the foreground process attached to
// the terminal, which will be the ssh subprocess at this
// point. For that reason, we do not call StopInterruptNotify
// until this function completes.
cloudcfg := coreCloudinit.New()
cloudcfg.SetAptUpdate(machineConfig.EnableOSRefreshUpdate)
cloudcfg.SetAptUpgrade(machineConfig.EnableOSUpgrade)
udata, err := cloudinit.NewUserdataConfig(machineConfig, cloudcfg)
if err != nil {
return err
}
if err := udata.ConfigureJuju(); err != nil {
return err
}
configScript, err := sshinit.ConfigureScript(cloudcfg)
if err != nil {
return err
}
script := shell.DumpFileOnErrorScript(machineConfig.CloudInitOutputLog) + configScript
return sshinit.RunConfigureScript(script, sshinit.ConfigureParams{
Host: "[email protected]" + host,
Client: client,
Config: cloudcfg,
ProgressWriter: ctx.GetStderr(),
})
}
示例2: PrepareForBootstrap
// PrepareForBootstrap is specified in the EnvironProvider interface.
func (prov *azureEnvironProvider) PrepareForBootstrap(ctx environs.BootstrapContext, cfg *config.Config) (environs.Environ, error) {
// Ensure that internal configuration is not specified, and then set
// what we can now. We only need to do this during bootstrap. Validate
// will check for changes later.
unknownAttrs := cfg.UnknownAttrs()
for _, key := range internalConfigAttributes {
if _, ok := unknownAttrs[key]; ok {
return nil, errors.Errorf(`internal config %q must not be specified`, key)
}
}
// Record the UUID that will be used for the controller environment.
cfg, err := cfg.Apply(map[string]interface{}{
configAttrControllerResourceGroup: resourceGroupName(cfg),
})
if err != nil {
return nil, errors.Annotate(err, "recording controller-resource-group")
}
env, err := prov.Open(cfg)
if err != nil {
return nil, errors.Trace(err)
}
if ctx.ShouldVerifyCredentials() {
if err := verifyCredentials(env.(*azureEnviron)); err != nil {
return nil, errors.Trace(err)
}
}
return env, nil
}
示例3: Bootstrap
// Bootstrap is a common implementation of the Bootstrap method defined on
// environs.Environ; we strongly recommend that this implementation be used
// when writing a new provider.
func Bootstrap(ctx environs.BootstrapContext, env environs.Environ, args environs.BootstrapParams) (arch, series string, _ environs.BootstrapFinalizer, err error) {
// TODO make safe in the case of racing Bootstraps
// If two Bootstraps are called concurrently, there's
// no way to make sure that only one succeeds.
var inst instance.Instance
defer func() { handleBootstrapError(err, ctx, inst, env) }()
// First thing, ensure we have tools otherwise there's no point.
series = config.PreferredSeries(env.Config())
availableTools, err := args.AvailableTools.Match(coretools.Filter{Series: series})
if err != nil {
return "", "", nil, err
}
// Get the bootstrap SSH client. Do this early, so we know
// not to bother with any of the below if we can't finish the job.
client := ssh.DefaultClient
if client == nil {
// This should never happen: if we don't have OpenSSH, then
// go.crypto/ssh should be used with an auto-generated key.
return "", "", nil, fmt.Errorf("no SSH client available")
}
machineConfig, err := environs.NewBootstrapMachineConfig(args.Constraints, series)
if err != nil {
return "", "", nil, err
}
machineConfig.EnableOSRefreshUpdate = env.Config().EnableOSRefreshUpdate()
machineConfig.EnableOSUpgrade = env.Config().EnableOSUpgrade()
fmt.Fprintln(ctx.GetStderr(), "Launching instance")
inst, hw, _, err := env.StartInstance(environs.StartInstanceParams{
Constraints: args.Constraints,
Tools: availableTools,
MachineConfig: machineConfig,
Placement: args.Placement,
})
if err != nil {
return "", "", nil, fmt.Errorf("cannot start bootstrap instance: %v", err)
}
fmt.Fprintf(ctx.GetStderr(), " - %s\n", inst.Id())
err = SaveState(env.Storage(), &BootstrapState{
StateInstances: []instance.Id{inst.Id()},
})
if err != nil {
return "", "", nil, fmt.Errorf("cannot save state: %v", err)
}
finalize := func(ctx environs.BootstrapContext, mcfg *cloudinit.MachineConfig) error {
mcfg.InstanceId = inst.Id()
mcfg.HardwareCharacteristics = hw
if err := environs.FinishMachineConfig(mcfg, env.Config()); err != nil {
return err
}
return FinishBootstrap(ctx, client, inst, mcfg)
}
return *hw.Arch, series, finalize, nil
}
示例4: PrepareForBootstrap
// PrepareForBootstrap implements environs.Environ.
func (env *environ) PrepareForBootstrap(ctx environs.BootstrapContext) error {
if ctx.ShouldVerifyCredentials() {
if err := env.gce.VerifyCredentials(); err != nil {
return errors.Trace(err)
}
}
return nil
}
示例5: Bootstrap
// Bootstrap is a common implementation of the Bootstrap method defined on
// environs.Environ; we strongly recommend that this implementation be used
// when writing a new provider.
func Bootstrap(ctx environs.BootstrapContext, env environs.Environ, args environs.BootstrapParams) (err error) {
// TODO make safe in the case of racing Bootstraps
// If two Bootstraps are called concurrently, there's
// no way to make sure that only one succeeds.
var inst instance.Instance
defer func() { handleBootstrapError(err, ctx, inst, env) }()
network.InitializeFromConfig(env.Config())
// First thing, ensure we have tools otherwise there's no point.
selectedTools, err := EnsureBootstrapTools(ctx, env, config.PreferredSeries(env.Config()), args.Constraints.Arch)
if err != nil {
return err
}
// Get the bootstrap SSH client. Do this early, so we know
// not to bother with any of the below if we can't finish the job.
client := ssh.DefaultClient
if client == nil {
// This should never happen: if we don't have OpenSSH, then
// go.crypto/ssh should be used with an auto-generated key.
return fmt.Errorf("no SSH client available")
}
privateKey, err := GenerateSystemSSHKey(env)
if err != nil {
return err
}
machineConfig := environs.NewBootstrapMachineConfig(privateKey)
fmt.Fprintln(ctx.GetStderr(), "Launching instance")
inst, hw, _, err := env.StartInstance(environs.StartInstanceParams{
Constraints: args.Constraints,
Tools: selectedTools,
MachineConfig: machineConfig,
Placement: args.Placement,
})
if err != nil {
return fmt.Errorf("cannot start bootstrap instance: %v", err)
}
fmt.Fprintf(ctx.GetStderr(), " - %s\n", inst.Id())
machineConfig.InstanceId = inst.Id()
machineConfig.HardwareCharacteristics = hw
err = bootstrap.SaveState(
env.Storage(),
&bootstrap.BootstrapState{
StateInstances: []instance.Id{inst.Id()},
})
if err != nil {
return fmt.Errorf("cannot save state: %v", err)
}
return FinishBootstrap(ctx, client, inst, machineConfig)
}
示例6: PrepareForBootstrap
// PrepareForBootstrap is specified in the EnvironProvider interface.
func (p maasEnvironProvider) PrepareForBootstrap(ctx environs.BootstrapContext, cfg *config.Config) (environs.Environ, error) {
env, err := p.Open(cfg)
if err != nil {
return nil, err
}
if ctx.ShouldVerifyCredentials() {
if err := verifyCredentials(env.(*maasEnviron)); err != nil {
return nil, err
}
}
return env, nil
}
示例7: PrepareForBootstrap
// PrepareForBootstrap is specified in the EnvironProvider interface.
func (p joyentProvider) PrepareForBootstrap(ctx environs.BootstrapContext, cfg *config.Config) (environs.Environ, error) {
e, err := p.Open(cfg)
if err != nil {
return nil, errors.Trace(err)
}
if ctx.ShouldVerifyCredentials() {
if err := verifyCredentials(e.(*joyentEnviron)); err != nil {
return nil, errors.Trace(err)
}
}
return e, nil
}
示例8: PrepareForBootstrap
func (p environProvider) PrepareForBootstrap(ctx environs.BootstrapContext, cfg *config.Config) (environs.Environ, error) {
cfg, err := p.PrepareForCreateEnvironment(cfg)
if err != nil {
return nil, err
}
e, err := p.Open(cfg)
if err != nil {
return nil, err
}
if ctx.ShouldVerifyCredentials() {
if err := verifyCredentials(e.(*environ)); err != nil {
return nil, err
}
}
return e, nil
}
示例9: PrepareForBootstrap
// PrepareForBootstrap is specified in the EnvironProvider interface.
func (prov azureEnvironProvider) PrepareForBootstrap(ctx environs.BootstrapContext, cfg *config.Config) (environs.Environ, error) {
cfg, err := prov.PrepareForCreateEnvironment(cfg)
if err != nil {
return nil, errors.Trace(err)
}
env, err := prov.Open(cfg)
if err != nil {
return nil, errors.Trace(err)
}
if ctx.ShouldVerifyCredentials() {
if err := verifyCredentials(env.(*azureEnviron)); err != nil {
return nil, errors.Trace(err)
}
}
return env, nil
}
示例10: validateBootstrapVPC
func validateBootstrapVPC(apiClient vpcAPIClient, region, vpcID string, forceVPCID bool, ctx environs.BootstrapContext) error {
if vpcID == vpcIDNone {
ctx.Infof("Using EC2-classic features or default VPC in region %q", region)
}
if !isVPCIDSet(vpcID) {
return nil
}
err := validateVPC(apiClient, vpcID)
switch {
case isVPCNotUsableError(err):
// VPC missing or has no subnets at all.
return errors.Annotate(err, vpcNotUsableForBootstrapErrorPrefix)
case isVPCNotRecommendedError(err):
// VPC does not meet minumum validation criteria.
if !forceVPCID {
return errors.Annotatef(err, vpcNotRecommendedErrorPrefix, vpcID)
}
ctx.Infof(vpcNotRecommendedButForcedWarning)
case err != nil:
// Anything else unexpected while validating the VPC.
return errors.Annotate(err, cannotValidateVPCErrorPrefix)
}
ctx.Infof("Using VPC %q in region %q", vpcID, region)
return nil
}
示例11: UploadTools
// UploadTools uploads tools for the specified series and any other relevant series to
// the environment storage, after which it sets the agent-version. If forceVersion is true,
// we allow uploading even when the agent-version is already set in the environment.
func UploadTools(ctx environs.BootstrapContext, env environs.Environ, toolsArch *string, forceVersion bool, bootstrapSeries ...string) error {
logger.Infof("checking that upload is possible")
// Check the series are valid.
for _, series := range bootstrapSeries {
if _, err := ubuntu.SeriesVersion(series); err != nil {
return err
}
}
// See that we are allowed to upload the tools.
if err := validateUploadAllowed(env, toolsArch, forceVersion); err != nil {
return err
}
// Make storage interruptible.
interrupted := make(chan os.Signal, 1)
interruptStorage := make(chan struct{})
ctx.InterruptNotify(interrupted)
defer ctx.StopInterruptNotify(interrupted)
defer close(interrupted)
go func() {
defer close(interruptStorage) // closing interrupts all uploads
if _, ok := <-interrupted; ok {
ctx.Infof("cancelling tools upload")
}
}()
stor := newInterruptibleStorage(env.Storage(), interruptStorage)
cfg := env.Config()
explicitVersion := uploadVersion(version.Current.Number, nil)
uploadSeries := SeriesToUpload(cfg, bootstrapSeries)
ctx.Infof("uploading tools for series %s", uploadSeries)
tools, err := sync.Upload(stor, &explicitVersion, uploadSeries...)
if err != nil {
return err
}
cfg, err = cfg.Apply(map[string]interface{}{
"agent-version": tools.Version.Number.String(),
})
if err == nil {
err = env.SetConfig(cfg)
}
if err != nil {
return fmt.Errorf("failed to update environment configuration: %v", err)
}
return nil
}
示例12: Bootstrap
// Bootstrap bootstraps the given environment. The supplied constraints are
// used to provision the instance, and are also set within the bootstrapped
// environment.
func Bootstrap(ctx environs.BootstrapContext, environ environs.Environ, args BootstrapParams) error {
cfg := environ.Config()
network.InitializeFromConfig(cfg)
if secret := cfg.AdminSecret(); secret == "" {
return errors.Errorf("environment configuration has no admin-secret")
}
if authKeys := ssh.SplitAuthorisedKeys(cfg.AuthorizedKeys()); len(authKeys) == 0 {
// Apparently this can never happen, so it's not tested. But, one day,
// Config will act differently (it's pretty crazy that, AFAICT, the
// authorized-keys are optional config settings... but it's impossible
// to actually *create* a config without them)... and when it does,
// we'll be here to catch this problem early.
return errors.Errorf("environment configuration has no authorized-keys")
}
if _, hasCACert := cfg.CACert(); !hasCACert {
return errors.Errorf("environment configuration has no ca-cert")
}
if _, hasCAKey := cfg.CAPrivateKey(); !hasCAKey {
return errors.Errorf("environment configuration has no ca-private-key")
}
// Set default tools metadata source, add image metadata source,
// then verify constraints. Providers may rely on image metadata
// for constraint validation.
var imageMetadata []*imagemetadata.ImageMetadata
if args.MetadataDir != "" {
var err error
imageMetadata, err = setPrivateMetadataSources(environ, args.MetadataDir)
if err != nil {
return err
}
}
if err := validateConstraints(environ, args.Constraints); err != nil {
return err
}
_, supportsNetworking := environs.SupportsNetworking(environ)
ctx.Infof("Bootstrapping environment %q", cfg.Name())
logger.Debugf("environment %q supports service/machine networks: %v", cfg.Name(), supportsNetworking)
disableNetworkManagement, _ := cfg.DisableNetworkManagement()
logger.Debugf("network management by juju enabled: %v", !disableNetworkManagement)
availableTools, err := findAvailableTools(environ, args.AgentVersion, args.Constraints.Arch, args.UploadTools)
if errors.IsNotFound(err) {
return errors.New(noToolsMessage)
} else if err != nil {
return err
}
if lxcMTU, ok := cfg.LXCDefaultMTU(); ok {
logger.Debugf("using MTU %v for all created LXC containers' network interfaces", lxcMTU)
}
// If we're uploading, we must override agent-version;
// if we're not uploading, we want to ensure we have an
// agent-version set anyway, to appease FinishInstanceConfig.
// In the latter case, setBootstrapTools will later set
// agent-version to the correct thing.
agentVersion := version.Current
if args.AgentVersion != nil {
agentVersion = *args.AgentVersion
}
if cfg, err = cfg.Apply(map[string]interface{}{
"agent-version": agentVersion.String(),
}); err != nil {
return err
}
if err = environ.SetConfig(cfg); err != nil {
return err
}
ctx.Infof("Starting new instance for initial state server")
arch, series, finalizer, err := environ.Bootstrap(ctx, environs.BootstrapParams{
Constraints: args.Constraints,
Placement: args.Placement,
AvailableTools: availableTools,
})
if err != nil {
return err
}
matchingTools, err := availableTools.Match(coretools.Filter{
Arch: arch,
Series: series,
})
if err != nil {
return err
}
selectedTools, err := setBootstrapTools(environ, matchingTools)
if err != nil {
return err
}
if selectedTools.URL == "" {
if !args.UploadTools {
logger.Warningf("no prepackaged tools available")
}
ctx.Infof("Building tools to upload (%s)", selectedTools.Version)
builtTools, err := sync.BuildToolsTarball(&selectedTools.Version.Number, cfg.AgentStream())
//.........这里部分代码省略.........
示例13: BootstrapInstance
// BootstrapInstance creates a new instance with the series of its choice,
// constrained to those of the available tools, and
// returns the instance result, series, and a function that
// must be called to finalize the bootstrap process by transferring
// the tools and installing the initial Juju controller.
// This method is called by Bootstrap above, which implements environs.Bootstrap, but
// is also exported so that providers can manipulate the started instance.
func BootstrapInstance(ctx environs.BootstrapContext, env environs.Environ, args environs.BootstrapParams,
) (_ *environs.StartInstanceResult, selectedSeries string, _ environs.BootstrapFinalizer, err error) {
// TODO make safe in the case of racing Bootstraps
// If two Bootstraps are called concurrently, there's
// no way to make sure that only one succeeds.
// First thing, ensure we have tools otherwise there's no point.
if args.BootstrapSeries != "" {
selectedSeries = args.BootstrapSeries
} else {
selectedSeries = config.PreferredSeries(env.Config())
}
availableTools, err := args.AvailableTools.Match(coretools.Filter{
Series: selectedSeries,
})
if err != nil {
return nil, "", nil, err
}
// Filter image metadata to the selected series.
var imageMetadata []*imagemetadata.ImageMetadata
seriesVersion, err := series.SeriesVersion(selectedSeries)
if err != nil {
return nil, "", nil, errors.Trace(err)
}
for _, m := range args.ImageMetadata {
if m.Version != seriesVersion {
continue
}
imageMetadata = append(imageMetadata, m)
}
// Get the bootstrap SSH client. Do this early, so we know
// not to bother with any of the below if we can't finish the job.
client := ssh.DefaultClient
if client == nil {
// This should never happen: if we don't have OpenSSH, then
// go.crypto/ssh should be used with an auto-generated key.
return nil, "", nil, fmt.Errorf("no SSH client available")
}
publicKey, err := simplestreams.UserPublicSigningKey()
if err != nil {
return nil, "", nil, err
}
envCfg := env.Config()
instanceConfig, err := instancecfg.NewBootstrapInstanceConfig(
args.ControllerConfig, args.BootstrapConstraints, args.ModelConstraints, selectedSeries, publicKey,
)
if err != nil {
return nil, "", nil, err
}
instanceConfig.EnableOSRefreshUpdate = env.Config().EnableOSRefreshUpdate()
instanceConfig.EnableOSUpgrade = env.Config().EnableOSUpgrade()
instanceConfig.Tags = instancecfg.InstanceTags(envCfg.UUID(), args.ControllerConfig.ControllerUUID(), envCfg, instanceConfig.Jobs)
maybeSetBridge := func(icfg *instancecfg.InstanceConfig) {
// If we need to override the default bridge name, do it now. When
// args.ContainerBridgeName is empty, the default names for LXC
// (lxcbr0) and KVM (virbr0) will be used.
if args.ContainerBridgeName != "" {
logger.Debugf("using %q as network bridge for all container types", args.ContainerBridgeName)
if icfg.AgentEnvironment == nil {
icfg.AgentEnvironment = make(map[string]string)
}
icfg.AgentEnvironment[agent.LxcBridge] = args.ContainerBridgeName
}
}
maybeSetBridge(instanceConfig)
cloudRegion := args.CloudName
if args.CloudRegion != "" {
cloudRegion += "/" + args.CloudRegion
}
fmt.Fprintf(ctx.GetStderr(), "Launching controller instance(s) on %s...\n", cloudRegion)
// Print instance status reports status changes during provisioning.
// Note the carriage returns, meaning subsequent prints are to the same
// line of stderr, not a new line.
instanceStatus := func(settableStatus status.Status, info string, data map[string]interface{}) error {
// The data arg is not expected to be used in this case, but
// print it, rather than ignore it, if we get something.
dataString := ""
if len(data) > 0 {
dataString = fmt.Sprintf(" %v", data)
}
fmt.Fprintf(ctx.GetStderr(), " - %s%s\r", info, dataString)
return nil
}
// Likely used after the final instanceStatus call to white-out the
// current stderr line before the next use, removing any residual status
// reporting output.
statusCleanup := func(info string) error {
// The leading spaces account for the leading characters
//.........这里部分代码省略.........
示例14: Bootstrap
// Bootstrap bootstraps the given environment. The supplied constraints are
// used to provision the instance, and are also set within the bootstrapped
// environment.
func Bootstrap(ctx environs.BootstrapContext, environ environs.Environ, args BootstrapParams) error {
if err := args.Validate(); err != nil {
return errors.Annotate(err, "validating bootstrap parameters")
}
cfg := environ.Config()
if authKeys := ssh.SplitAuthorisedKeys(cfg.AuthorizedKeys()); len(authKeys) == 0 {
// Apparently this can never happen, so it's not tested. But, one day,
// Config will act differently (it's pretty crazy that, AFAICT, the
// authorized-keys are optional config settings... but it's impossible
// to actually *create* a config without them)... and when it does,
// we'll be here to catch this problem early.
return errors.Errorf("model configuration has no authorized-keys")
}
_, supportsNetworking := environs.SupportsNetworking(environ)
logger.Debugf("model %q supports service/machine networks: %v", cfg.Name(), supportsNetworking)
disableNetworkManagement, _ := cfg.DisableNetworkManagement()
logger.Debugf("network management by juju enabled: %v", !disableNetworkManagement)
// Set default tools metadata source, add image metadata source,
// then verify constraints. Providers may rely on image metadata
// for constraint validation.
var customImageMetadata []*imagemetadata.ImageMetadata
if args.MetadataDir != "" {
var err error
customImageMetadata, err = setPrivateMetadataSources(args.MetadataDir)
if err != nil {
return err
}
}
var bootstrapSeries *string
if args.BootstrapSeries != "" {
bootstrapSeries = &args.BootstrapSeries
}
var bootstrapArchForImageSearch string
if args.BootstrapConstraints.Arch != nil {
bootstrapArchForImageSearch = *args.BootstrapConstraints.Arch
} else if args.ModelConstraints.Arch != nil {
bootstrapArchForImageSearch = *args.ModelConstraints.Arch
} else {
bootstrapArchForImageSearch = arch.HostArch()
// We no longer support i386.
if bootstrapArchForImageSearch == arch.I386 {
bootstrapArchForImageSearch = arch.AMD64
}
}
ctx.Verbosef("Loading image metadata")
imageMetadata, err := bootstrapImageMetadata(environ,
bootstrapSeries,
bootstrapArchForImageSearch,
args.BootstrapImage,
&customImageMetadata,
)
if err != nil {
return errors.Trace(err)
}
// We want to determine a list of valid architectures for which to pick tools and images.
// This includes architectures from custom and other available image metadata.
architectures := set.NewStrings()
if len(customImageMetadata) > 0 {
for _, customMetadata := range customImageMetadata {
architectures.Add(customMetadata.Arch)
}
}
if len(imageMetadata) > 0 {
for _, iMetadata := range imageMetadata {
architectures.Add(iMetadata.Arch)
}
}
constraintsValidator, err := environ.ConstraintsValidator()
if err != nil {
return err
}
constraintsValidator.UpdateVocabulary(constraints.Arch, architectures.SortedValues())
bootstrapConstraints, err := constraintsValidator.Merge(
args.ModelConstraints, args.BootstrapConstraints,
)
if err != nil {
return errors.Trace(err)
}
// The arch we use to find tools isn't the boostrapConstraints arch.
// We copy the constraints arch to a separate variable and
// update it from the host arch if not specified.
// (axw) This is still not quite right:
// For e.g. if there is a MAAS with only ARM64 machines,
// on an AMD64 client, we're going to look for only AMD64 tools,
// limiting what the provider can bootstrap anyway.
var bootstrapArch string
if bootstrapConstraints.Arch != nil {
//.........这里部分代码省略.........
示例15: finalizeInstanceBootstrapConfig
func finalizeInstanceBootstrapConfig(
ctx environs.BootstrapContext,
icfg *instancecfg.InstanceConfig,
args BootstrapParams,
cfg *config.Config,
customImageMetadata []*imagemetadata.ImageMetadata,
) error {
if icfg.APIInfo != nil || icfg.Controller.MongoInfo != nil {
return errors.New("machine configuration already has api/state info")
}
controllerCfg := icfg.Controller.Config
caCert, hasCACert := controllerCfg.CACert()
if !hasCACert {
return errors.New("controller configuration has no ca-cert")
}
icfg.APIInfo = &api.Info{
Password: args.AdminSecret,
CACert: caCert,
ModelTag: names.NewModelTag(cfg.UUID()),
}
icfg.Controller.MongoInfo = &mongo.MongoInfo{
Password: args.AdminSecret,
Info: mongo.Info{CACert: caCert},
}
// These really are directly relevant to running a controller.
// Initially, generate a controller certificate with no host IP
// addresses in the SAN field. Once the controller is up and the
// NIC addresses become known, the certificate can be regenerated.
cert, key, err := controller.GenerateControllerCertAndKey(caCert, args.CAPrivateKey, nil)
if err != nil {
return errors.Annotate(err, "cannot generate controller certificate")
}
icfg.Bootstrap.StateServingInfo = params.StateServingInfo{
StatePort: controllerCfg.StatePort(),
APIPort: controllerCfg.APIPort(),
Cert: string(cert),
PrivateKey: string(key),
CAPrivateKey: args.CAPrivateKey,
}
if _, ok := cfg.AgentVersion(); !ok {
return errors.New("controller model configuration has no agent-version")
}
icfg.Bootstrap.ControllerModelConfig = cfg
icfg.Bootstrap.CustomImageMetadata = customImageMetadata
icfg.Bootstrap.ControllerCloudName = args.CloudName
icfg.Bootstrap.ControllerCloud = args.Cloud
icfg.Bootstrap.ControllerCloudRegion = args.CloudRegion
icfg.Bootstrap.ControllerCloudCredential = args.CloudCredential
icfg.Bootstrap.ControllerCloudCredentialName = args.CloudCredentialName
icfg.Bootstrap.ControllerConfig = args.ControllerConfig
icfg.Bootstrap.ControllerInheritedConfig = args.ControllerInheritedConfig
icfg.Bootstrap.RegionInheritedConfig = args.Cloud.RegionConfig
icfg.Bootstrap.HostedModelConfig = args.HostedModelConfig
icfg.Bootstrap.Timeout = args.DialOpts.Timeout
icfg.Bootstrap.GUI = guiArchive(args.GUIDataSourceBaseURL, func(msg string) {
ctx.Infof(msg)
})
return nil
}