示例#1
0
// getContainerArtifacts returns type-specific interfaces for
// managing containers.
//
// The ToolsFinder passed in may be replaced or wrapped to
// enforce container-specific constraints.
func (cs *ContainerSetup) getContainerArtifacts(
	containerType instance.ContainerType, toolsFinder ToolsFinder,
) (
	container.Initialiser,
	environs.InstanceBroker,
	ToolsFinder,
	error,
) {
	var initialiser container.Initialiser
	var broker environs.InstanceBroker

	managerConfig, err := containerManagerConfig(containerType, cs.provisioner, cs.config)
	if err != nil {
		return nil, nil, nil, err
	}

	switch containerType {
	case instance.KVM:
		initialiser = kvm.NewContainerInitialiser()
		broker, err = NewKvmBroker(
			cs.provisioner,
			cs.config,
			managerConfig,
		)
		if err != nil {
			logger.Errorf("failed to create new kvm broker")
			return nil, nil, nil, err
		}
	case instance.LXD:
		series, err := cs.machine.Series()
		if err != nil {
			return nil, nil, nil, err
		}

		initialiser = lxd.NewContainerInitialiser(series)
		manager, err := lxd.NewContainerManager(managerConfig)
		if err != nil {
			return nil, nil, nil, err
		}
		broker, err = NewLxdBroker(
			cs.provisioner,
			manager,
			cs.config,
		)
		if err != nil {
			logger.Errorf("failed to create new lxd broker")
			return nil, nil, nil, err
		}
	default:
		return nil, nil, nil, fmt.Errorf("unknown container type: %v", containerType)
	}

	return initialiser, broker, toolsFinder, nil
}
// getContainerArtifacts returns type-specific interfaces for
// managing containers.
//
// The ToolsFinder passed in may be replaced or wrapped to
// enforce container-specific constraints.
func (cs *ContainerSetup) getContainerArtifacts(
	containerType instance.ContainerType, toolsFinder ToolsFinder,
) (
	container.Initialiser,
	environs.InstanceBroker,
	ToolsFinder,
	error,
) {
	var initialiser container.Initialiser
	var broker environs.InstanceBroker

	managerConfig, err := containerManagerConfig(containerType, cs.provisioner, cs.config)
	if err != nil {
		return nil, nil, nil, err
	}

	// Override default MTU for LXC NICs, if needed.
	if mtu := managerConfig.PopValue(container.ConfigLXCDefaultMTU); mtu != "" {
		value, err := strconv.Atoi(mtu)
		if err != nil {
			return nil, nil, nil, errors.Trace(err)
		}
		logger.Infof("setting MTU to %v for all LXC containers' interfaces", value)
		cs.lxcDefaultMTU = value
	}

	// Enable IP forwarding and ARP proxying if needed.
	if ipfwd := managerConfig.PopValue(container.ConfigIPForwarding); ipfwd != "" {
		if err := setIPAndARPForwarding(true); err != nil {
			return nil, nil, nil, errors.Trace(err)
		}
		cs.addressableContainers = true
		logger.Infof("enabled IP forwarding and ARP proxying for containers")
	}

	// Enable NAT if needed.
	if nat := managerConfig.PopValue(container.ConfigEnableNAT); nat != "" {
		cs.enableNAT = true
		logger.Infof("enabling NAT for containers")
	}

	switch containerType {
	case instance.LXC:
		series, err := cs.machine.Series()
		if err != nil {
			return nil, nil, nil, err
		}

		initialiser = lxc.NewContainerInitialiser(series)
		broker, err = NewLxcBroker(
			cs.provisioner,
			cs.config,
			managerConfig,
			cs.imageURLGetter,
			cs.enableNAT,
			cs.lxcDefaultMTU,
		)
		if err != nil {
			return nil, nil, nil, err
		}

		// LXC containers must have the same architecture as the host.
		// We should call through to the finder since the version of
		// tools running on the host may not match, but we want to
		// override the arch constraint with the arch of the host.
		toolsFinder = hostArchToolsFinder{toolsFinder}

	case instance.KVM:
		initialiser = kvm.NewContainerInitialiser()
		broker, err = NewKvmBroker(
			cs.provisioner,
			cs.config,
			managerConfig,
			cs.enableNAT,
		)
		if err != nil {
			logger.Errorf("failed to create new kvm broker")
			return nil, nil, nil, err
		}
	case instance.LXD:
		series, err := cs.machine.Series()
		if err != nil {
			return nil, nil, nil, err
		}

		initialiser = lxd.NewContainerInitialiser(series)
		broker, err = NewLxdBroker(
			cs.provisioner,
			cs.config,
			managerConfig,
			cs.enableNAT,
		)
		if err != nil {
			logger.Errorf("failed to create new lxd broker")
			return nil, nil, nil, err
		}
	default:
		return nil, nil, nil, fmt.Errorf("unknown container type: %v", containerType)
	}

	return initialiser, broker, toolsFinder, nil
}