Repository: moby/moby
File: client/container_create.go (Go)

Code before:
	if containerName != "" {
		query.Set("name", containerName)
	}

	body := container.CreateRequest{
		Config:           config,
		HostConfig:       hostConfig,
		NetworkingConfig: networkingConfig,
	}

	resp, err := cli.post(ctx, "/containers/create", query, body, nil)
	defer ensureReaderClosed(resp)
	if err != nil {
		return response, err
	}

	err = json.NewDecoder(resp.Body).Decode(&response)
	return response, err
}

// formatPlatform returns a formatted string representing platform (e.g. linux/arm/v7).
//
// Similar to containerd's platforms.Format(), but does allow components to be
// omitted (e.g. pass "architecture" only, without "os":
// https://github.com/containerd/containerd/blob/v1.5.2/platforms/platforms.go#L243-L263
func formatPlatform(platform *ocispec.Platform) string {
	if platform == nil {
		return ""
	}
	return path.Join(platform.OS, platform.Architecture, platform.Variant)
}

// hasEndpointSpecificMacAddress checks whether one of the endpoint in networkingConfig has a MacAddress defined.
func hasEndpointSpecificMacAddress(networkingConfig *network.NetworkingConfig) bool {
	if networkingConfig == nil {
		return false
	}
	for _, endpoint := range networkingConfig.EndpointsConfig {
		if endpoint.MacAddress != "" {
			return true
		}
	}
	return false
}

// allCapabilities is a magic value for "all capabilities"
const allCapabilities = "ALL"

// normalizeCapabilities normalizes capabilities to their canonical form,
// removes duplicates, and sorts the results.
//

Review comment (suggestion):
I'll be opening a ticket for this; the TL;DR is that `docker container create` does not currently support passing `os.version`, which gets silently discarded, but the daemon _would_ be able to handle it.


I'm considering that perhaps we should move away from using the `?platform=` query-arg (which uses the string format, not JSON), and adding information in the body (HostConfig?) that can hold information that was passed to resolve the image (name of image, requested platform?)

Code after:
	}

	if containerName != "" {
		query.Set("name", containerName)
	}

	body := container.CreateRequest{
		Config:           config,
		HostConfig:       hostConfig,
		NetworkingConfig: networkingConfig,
	}

	resp, err := cli.post(ctx, "/containers/create", query, body, nil)
	defer ensureReaderClosed(resp)
	if err != nil {
		return response, err
	}

	err = json.NewDecoder(resp.Body).Decode(&response)
	return response, err
}

// formatPlatform returns a formatted string representing platform (e.g., "linux/arm/v7").
//
// It is a fork of [platforms.Format], and does not yet support "os.version",
// as [[platforms.FormatAll] does.
//
// [platforms.Format]: https://github.com/containerd/platforms/blob/v1.0.0-rc.1/platforms.go#L309-L316
// [platforms.FormatAll]: https://github.com/containerd/platforms/blob/v1.0.0-rc.1/platforms.go#L318-L330
func formatPlatform(platform ocispec.Platform) string {
	if platform.OS == "" {
		return "unknown"
	}
	return path.Join(platform.OS, platform.Architecture, platform.Variant)
}

// hasEndpointSpecificMacAddress checks whether one of the endpoint in networkingConfig has a MacAddress defined.
func hasEndpointSpecificMacAddress(networkingConfig *network.NetworkingConfig) bool {
	if networkingConfig == nil {
		return false
	}
	for _, endpoint := range networkingConfig.EndpointsConfig {
		if endpoint.MacAddress != "" {
			return true
		}
	}
	return false
}

// allCapabilities is a magic value for "all capabilities"
const allCapabilities = "ALL"