mirror of https://github.com/docker/cli.git
Merge pull request #286 from thaJeztah/bump-moby
Bump moby to 87df0e533b619c088091fd1e2310e92bb9a24822
This commit is contained in:
commit
30933b516b
|
@ -21,6 +21,9 @@
|
||||||
},
|
},
|
||||||
"RootFS": {
|
"RootFS": {
|
||||||
"Type": ""
|
"Type": ""
|
||||||
|
},
|
||||||
|
"Metadata": {
|
||||||
|
"LastTagTime": "0001-01-01T00:00:00Z"
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
|
@ -45,6 +48,9 @@
|
||||||
},
|
},
|
||||||
"RootFS": {
|
"RootFS": {
|
||||||
"Type": ""
|
"Type": ""
|
||||||
|
},
|
||||||
|
"Metadata": {
|
||||||
|
"LastTagTime": "0001-01-01T00:00:00Z"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
|
|
|
@ -21,6 +21,9 @@
|
||||||
},
|
},
|
||||||
"RootFS": {
|
"RootFS": {
|
||||||
"Type": ""
|
"Type": ""
|
||||||
|
},
|
||||||
|
"Metadata": {
|
||||||
|
"LastTagTime": "0001-01-01T00:00:00Z"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
|
|
|
@ -7,7 +7,7 @@ github.com/coreos/etcd 824277cb3a577a0e8c829ca9ec557b973fe06d20
|
||||||
github.com/cpuguy83/go-md2man a65d4d2de4d5f7c74868dfa9b202a3c8be315aaa
|
github.com/cpuguy83/go-md2man a65d4d2de4d5f7c74868dfa9b202a3c8be315aaa
|
||||||
github.com/davecgh/go-spew 346938d642f2ec3594ed81d874461961cd0faa76
|
github.com/davecgh/go-spew 346938d642f2ec3594ed81d874461961cd0faa76
|
||||||
github.com/docker/distribution b38e5838b7b2f2ad48e06ec4b500011976080621
|
github.com/docker/distribution b38e5838b7b2f2ad48e06ec4b500011976080621
|
||||||
github.com/docker/docker 050c1bb17bd033e909cb653f5449b683608293d6
|
github.com/docker/docker 87df0e533b619c088091fd1e2310e92bb9a24822
|
||||||
github.com/docker/docker-credential-helpers v0.5.1
|
github.com/docker/docker-credential-helpers v0.5.1
|
||||||
|
|
||||||
# the docker/go package contains a customized version of canonical/json
|
# the docker/go package contains a customized version of canonical/json
|
||||||
|
|
|
@ -4,15 +4,9 @@ import (
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
"encoding/pem"
|
"encoding/pem"
|
||||||
"fmt"
|
"fmt"
|
||||||
"mime"
|
|
||||||
"os"
|
"os"
|
||||||
"path/filepath"
|
"path/filepath"
|
||||||
"sort"
|
|
||||||
"strconv"
|
|
||||||
"strings"
|
|
||||||
|
|
||||||
"github.com/Sirupsen/logrus"
|
|
||||||
"github.com/docker/docker/api/types"
|
|
||||||
"github.com/docker/docker/pkg/ioutils"
|
"github.com/docker/docker/pkg/ioutils"
|
||||||
"github.com/docker/docker/pkg/system"
|
"github.com/docker/docker/pkg/system"
|
||||||
"github.com/docker/libtrust"
|
"github.com/docker/libtrust"
|
||||||
|
@ -28,101 +22,6 @@ const (
|
||||||
NoBaseImageSpecifier string = "scratch"
|
NoBaseImageSpecifier string = "scratch"
|
||||||
)
|
)
|
||||||
|
|
||||||
// byPortInfo is a temporary type used to sort types.Port by its fields
|
|
||||||
type byPortInfo []types.Port
|
|
||||||
|
|
||||||
func (r byPortInfo) Len() int { return len(r) }
|
|
||||||
func (r byPortInfo) Swap(i, j int) { r[i], r[j] = r[j], r[i] }
|
|
||||||
func (r byPortInfo) Less(i, j int) bool {
|
|
||||||
if r[i].PrivatePort != r[j].PrivatePort {
|
|
||||||
return r[i].PrivatePort < r[j].PrivatePort
|
|
||||||
}
|
|
||||||
|
|
||||||
if r[i].IP != r[j].IP {
|
|
||||||
return r[i].IP < r[j].IP
|
|
||||||
}
|
|
||||||
|
|
||||||
if r[i].PublicPort != r[j].PublicPort {
|
|
||||||
return r[i].PublicPort < r[j].PublicPort
|
|
||||||
}
|
|
||||||
|
|
||||||
return r[i].Type < r[j].Type
|
|
||||||
}
|
|
||||||
|
|
||||||
// DisplayablePorts returns formatted string representing open ports of container
|
|
||||||
// e.g. "0.0.0.0:80->9090/tcp, 9988/tcp"
|
|
||||||
// it's used by command 'docker ps'
|
|
||||||
func DisplayablePorts(ports []types.Port) string {
|
|
||||||
type portGroup struct {
|
|
||||||
first uint16
|
|
||||||
last uint16
|
|
||||||
}
|
|
||||||
groupMap := make(map[string]*portGroup)
|
|
||||||
var result []string
|
|
||||||
var hostMappings []string
|
|
||||||
var groupMapKeys []string
|
|
||||||
sort.Sort(byPortInfo(ports))
|
|
||||||
for _, port := range ports {
|
|
||||||
current := port.PrivatePort
|
|
||||||
portKey := port.Type
|
|
||||||
if port.IP != "" {
|
|
||||||
if port.PublicPort != current {
|
|
||||||
hostMappings = append(hostMappings, fmt.Sprintf("%s:%d->%d/%s", port.IP, port.PublicPort, port.PrivatePort, port.Type))
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
portKey = fmt.Sprintf("%s/%s", port.IP, port.Type)
|
|
||||||
}
|
|
||||||
group := groupMap[portKey]
|
|
||||||
|
|
||||||
if group == nil {
|
|
||||||
groupMap[portKey] = &portGroup{first: current, last: current}
|
|
||||||
// record order that groupMap keys are created
|
|
||||||
groupMapKeys = append(groupMapKeys, portKey)
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
if current == (group.last + 1) {
|
|
||||||
group.last = current
|
|
||||||
continue
|
|
||||||
}
|
|
||||||
|
|
||||||
result = append(result, formGroup(portKey, group.first, group.last))
|
|
||||||
groupMap[portKey] = &portGroup{first: current, last: current}
|
|
||||||
}
|
|
||||||
for _, portKey := range groupMapKeys {
|
|
||||||
g := groupMap[portKey]
|
|
||||||
result = append(result, formGroup(portKey, g.first, g.last))
|
|
||||||
}
|
|
||||||
result = append(result, hostMappings...)
|
|
||||||
return strings.Join(result, ", ")
|
|
||||||
}
|
|
||||||
|
|
||||||
func formGroup(key string, start, last uint16) string {
|
|
||||||
parts := strings.Split(key, "/")
|
|
||||||
groupType := parts[0]
|
|
||||||
var ip string
|
|
||||||
if len(parts) > 1 {
|
|
||||||
ip = parts[0]
|
|
||||||
groupType = parts[1]
|
|
||||||
}
|
|
||||||
group := strconv.Itoa(int(start))
|
|
||||||
if start != last {
|
|
||||||
group = fmt.Sprintf("%s-%d", group, last)
|
|
||||||
}
|
|
||||||
if ip != "" {
|
|
||||||
group = fmt.Sprintf("%s:%s->%s", ip, group, group)
|
|
||||||
}
|
|
||||||
return fmt.Sprintf("%s/%s", group, groupType)
|
|
||||||
}
|
|
||||||
|
|
||||||
// MatchesContentType validates the content type against the expected one
|
|
||||||
func MatchesContentType(contentType, expectedType string) bool {
|
|
||||||
mimetype, _, err := mime.ParseMediaType(contentType)
|
|
||||||
if err != nil {
|
|
||||||
logrus.Errorf("Error parsing media type: %s error: %v", contentType, err)
|
|
||||||
}
|
|
||||||
return err == nil && mimetype == expectedType
|
|
||||||
}
|
|
||||||
|
|
||||||
// LoadOrCreateTrustKey attempts to load the libtrust key at the given path,
|
// LoadOrCreateTrustKey attempts to load the libtrust key at the given path,
|
||||||
// otherwise generates a new one
|
// otherwise generates a new one
|
||||||
func LoadOrCreateTrustKey(trustKeyPath string) (libtrust.PrivateKey, error) {
|
func LoadOrCreateTrustKey(trustKeyPath string) (libtrust.PrivateKey, error) {
|
||||||
|
|
|
@ -45,6 +45,12 @@ type ImageInspect struct {
|
||||||
VirtualSize int64
|
VirtualSize int64
|
||||||
GraphDriver GraphDriverData
|
GraphDriver GraphDriverData
|
||||||
RootFS RootFS
|
RootFS RootFS
|
||||||
|
Metadata ImageMetadata
|
||||||
|
}
|
||||||
|
|
||||||
|
// ImageMetadata contains engine-local data about the image
|
||||||
|
type ImageMetadata struct {
|
||||||
|
LastTagTime time.Time `json:",omitempty"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// Container contains response of Engine API:
|
// Container contains response of Engine API:
|
||||||
|
|
|
@ -15,18 +15,24 @@ import (
|
||||||
"github.com/pkg/errors"
|
"github.com/pkg/errors"
|
||||||
)
|
)
|
||||||
|
|
||||||
|
type gitRepo struct {
|
||||||
|
remote string
|
||||||
|
ref string
|
||||||
|
subdir string
|
||||||
|
}
|
||||||
|
|
||||||
// Clone clones a repository into a newly created directory which
|
// Clone clones a repository into a newly created directory which
|
||||||
// will be under "docker-build-git"
|
// will be under "docker-build-git"
|
||||||
func Clone(remoteURL string) (string, error) {
|
func Clone(remoteURL string) (string, error) {
|
||||||
if !urlutil.IsGitTransport(remoteURL) {
|
repo, err := parseRemoteURL(remoteURL)
|
||||||
remoteURL = "https://" + remoteURL
|
|
||||||
}
|
|
||||||
root, err := ioutil.TempDir("", "docker-build-git")
|
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
|
|
||||||
u, err := url.Parse(remoteURL)
|
fetch := fetchArgs(repo.remote, repo.ref)
|
||||||
|
|
||||||
|
root, err := ioutil.TempDir("", "docker-build-git")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return "", err
|
return "", err
|
||||||
}
|
}
|
||||||
|
@ -35,22 +41,47 @@ func Clone(remoteURL string) (string, error) {
|
||||||
return "", errors.Wrapf(err, "failed to init repo at %s: %s", root, out)
|
return "", errors.Wrapf(err, "failed to init repo at %s: %s", root, out)
|
||||||
}
|
}
|
||||||
|
|
||||||
ref, subdir := getRefAndSubdir(u.Fragment)
|
|
||||||
fetch := fetchArgs(u, ref)
|
|
||||||
|
|
||||||
u.Fragment = ""
|
|
||||||
|
|
||||||
// Add origin remote for compatibility with previous implementation that
|
// Add origin remote for compatibility with previous implementation that
|
||||||
// used "git clone" and also to make sure local refs are created for branches
|
// used "git clone" and also to make sure local refs are created for branches
|
||||||
if out, err := gitWithinDir(root, "remote", "add", "origin", u.String()); err != nil {
|
if out, err := gitWithinDir(root, "remote", "add", "origin", repo.remote); err != nil {
|
||||||
return "", errors.Wrapf(err, "failed add origin repo at %s: %s", u.String(), out)
|
return "", errors.Wrapf(err, "failed add origin repo at %s: %s", repo.remote, out)
|
||||||
}
|
}
|
||||||
|
|
||||||
if output, err := gitWithinDir(root, fetch...); err != nil {
|
if output, err := gitWithinDir(root, fetch...); err != nil {
|
||||||
return "", errors.Wrapf(err, "error fetching: %s", output)
|
return "", errors.Wrapf(err, "error fetching: %s", output)
|
||||||
}
|
}
|
||||||
|
|
||||||
return checkoutGit(root, ref, subdir)
|
return checkoutGit(root, repo.ref, repo.subdir)
|
||||||
|
}
|
||||||
|
|
||||||
|
func parseRemoteURL(remoteURL string) (gitRepo, error) {
|
||||||
|
repo := gitRepo{}
|
||||||
|
|
||||||
|
if !isGitTransport(remoteURL) {
|
||||||
|
remoteURL = "https://" + remoteURL
|
||||||
|
}
|
||||||
|
|
||||||
|
var fragment string
|
||||||
|
if strings.HasPrefix(remoteURL, "git@") {
|
||||||
|
// git@.. is not an URL, so cannot be parsed as URL
|
||||||
|
parts := strings.SplitN(remoteURL, "#", 2)
|
||||||
|
|
||||||
|
repo.remote = parts[0]
|
||||||
|
if len(parts) == 2 {
|
||||||
|
fragment = parts[1]
|
||||||
|
}
|
||||||
|
repo.ref, repo.subdir = getRefAndSubdir(fragment)
|
||||||
|
} else {
|
||||||
|
u, err := url.Parse(remoteURL)
|
||||||
|
if err != nil {
|
||||||
|
return repo, err
|
||||||
|
}
|
||||||
|
|
||||||
|
repo.ref, repo.subdir = getRefAndSubdir(u.Fragment)
|
||||||
|
u.Fragment = ""
|
||||||
|
repo.remote = u.String()
|
||||||
|
}
|
||||||
|
return repo, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func getRefAndSubdir(fragment string) (ref string, subdir string) {
|
func getRefAndSubdir(fragment string) (ref string, subdir string) {
|
||||||
|
@ -65,11 +96,11 @@ func getRefAndSubdir(fragment string) (ref string, subdir string) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
func fetchArgs(remoteURL *url.URL, ref string) []string {
|
func fetchArgs(remoteURL string, ref string) []string {
|
||||||
args := []string{"fetch", "--recurse-submodules=yes"}
|
args := []string{"fetch", "--recurse-submodules=yes"}
|
||||||
shallow := true
|
shallow := true
|
||||||
|
|
||||||
if strings.HasPrefix(remoteURL.Scheme, "http") {
|
if urlutil.IsURL(remoteURL) {
|
||||||
res, err := http.Head(fmt.Sprintf("%s/info/refs?service=git-upload-pack", remoteURL))
|
res, err := http.Head(fmt.Sprintf("%s/info/refs?service=git-upload-pack", remoteURL))
|
||||||
if err != nil || res.Header.Get("Content-Type") != "application/x-git-upload-pack-advertisement" {
|
if err != nil || res.Header.Get("Content-Type") != "application/x-git-upload-pack-advertisement" {
|
||||||
shallow = false
|
shallow = false
|
||||||
|
@ -120,3 +151,9 @@ func gitWithinDir(dir string, args ...string) ([]byte, error) {
|
||||||
func git(args ...string) ([]byte, error) {
|
func git(args ...string) ([]byte, error) {
|
||||||
return exec.Command("git", args...).CombinedOutput()
|
return exec.Command("git", args...).CombinedOutput()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// isGitTransport returns true if the provided str is a git transport by inspecting
|
||||||
|
// the prefix of the string for known protocols used in git.
|
||||||
|
func isGitTransport(str string) bool {
|
||||||
|
return urlutil.IsURL(str) || strings.HasPrefix(str, "git://") || strings.HasPrefix(str, "git@")
|
||||||
|
}
|
||||||
|
|
|
@ -30,6 +30,7 @@ func (cli *Client) ContainerStatPath(ctx context.Context, containerID, path stri
|
||||||
}
|
}
|
||||||
|
|
||||||
// CopyToContainer copies content into the container filesystem.
|
// CopyToContainer copies content into the container filesystem.
|
||||||
|
// Note that `content` must be a Reader for a TAR
|
||||||
func (cli *Client) CopyToContainer(ctx context.Context, container, path string, content io.Reader, options types.CopyToContainerOptions) error {
|
func (cli *Client) CopyToContainer(ctx context.Context, container, path string, content io.Reader, options types.CopyToContainerOptions) error {
|
||||||
query := url.Values{}
|
query := url.Values{}
|
||||||
query.Set("path", filepath.ToSlash(path)) // Normalize the paths used in the API.
|
query.Set("path", filepath.ToSlash(path)) // Normalize the paths used in the API.
|
||||||
|
|
|
@ -18,13 +18,15 @@ func (cli *Client) Ping(ctx context.Context) (types.Ping, error) {
|
||||||
}
|
}
|
||||||
defer ensureReaderClosed(serverResp)
|
defer ensureReaderClosed(serverResp)
|
||||||
|
|
||||||
ping.APIVersion = serverResp.header.Get("API-Version")
|
if serverResp.header != nil {
|
||||||
|
ping.APIVersion = serverResp.header.Get("API-Version")
|
||||||
|
|
||||||
if serverResp.header.Get("Docker-Experimental") == "true" {
|
if serverResp.header.Get("Docker-Experimental") == "true" {
|
||||||
ping.Experimental = true
|
ping.Experimental = true
|
||||||
|
}
|
||||||
|
ping.OSType = serverResp.header.Get("OSType")
|
||||||
}
|
}
|
||||||
|
|
||||||
ping.OSType = serverResp.header.Get("OSType")
|
err = cli.checkResponseErr(serverResp)
|
||||||
|
return ping, err
|
||||||
return ping, nil
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -24,6 +24,7 @@ type serverResponse struct {
|
||||||
body io.ReadCloser
|
body io.ReadCloser
|
||||||
header http.Header
|
header http.Header
|
||||||
statusCode int
|
statusCode int
|
||||||
|
reqURL *url.URL
|
||||||
}
|
}
|
||||||
|
|
||||||
// head sends an http request to the docker API using the method HEAD.
|
// head sends an http request to the docker API using the method HEAD.
|
||||||
|
@ -118,11 +119,18 @@ func (cli *Client) sendRequest(ctx context.Context, method, path string, query u
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return serverResponse{}, err
|
return serverResponse{}, err
|
||||||
}
|
}
|
||||||
return cli.doRequest(ctx, req)
|
resp, err := cli.doRequest(ctx, req)
|
||||||
|
if err != nil {
|
||||||
|
return resp, err
|
||||||
|
}
|
||||||
|
if err := cli.checkResponseErr(resp); err != nil {
|
||||||
|
return resp, err
|
||||||
|
}
|
||||||
|
return resp, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (cli *Client) doRequest(ctx context.Context, req *http.Request) (serverResponse, error) {
|
func (cli *Client) doRequest(ctx context.Context, req *http.Request) (serverResponse, error) {
|
||||||
serverResp := serverResponse{statusCode: -1}
|
serverResp := serverResponse{statusCode: -1, reqURL: req.URL}
|
||||||
|
|
||||||
resp, err := ctxhttp.Do(ctx, cli.client, req)
|
resp, err := ctxhttp.Do(ctx, cli.client, req)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
@ -179,37 +187,44 @@ func (cli *Client) doRequest(ctx context.Context, req *http.Request) (serverResp
|
||||||
|
|
||||||
if resp != nil {
|
if resp != nil {
|
||||||
serverResp.statusCode = resp.StatusCode
|
serverResp.statusCode = resp.StatusCode
|
||||||
|
serverResp.body = resp.Body
|
||||||
|
serverResp.header = resp.Header
|
||||||
}
|
}
|
||||||
|
|
||||||
if serverResp.statusCode < 200 || serverResp.statusCode >= 400 {
|
|
||||||
body, err := ioutil.ReadAll(resp.Body)
|
|
||||||
if err != nil {
|
|
||||||
return serverResp, err
|
|
||||||
}
|
|
||||||
if len(body) == 0 {
|
|
||||||
return serverResp, fmt.Errorf("Error: request returned %s for API route and version %s, check if the server supports the requested API version", http.StatusText(serverResp.statusCode), req.URL)
|
|
||||||
}
|
|
||||||
|
|
||||||
var errorMessage string
|
|
||||||
if (cli.version == "" || versions.GreaterThan(cli.version, "1.23")) &&
|
|
||||||
resp.Header.Get("Content-Type") == "application/json" {
|
|
||||||
var errorResponse types.ErrorResponse
|
|
||||||
if err := json.Unmarshal(body, &errorResponse); err != nil {
|
|
||||||
return serverResp, fmt.Errorf("Error reading JSON: %v", err)
|
|
||||||
}
|
|
||||||
errorMessage = errorResponse.Message
|
|
||||||
} else {
|
|
||||||
errorMessage = string(body)
|
|
||||||
}
|
|
||||||
|
|
||||||
return serverResp, fmt.Errorf("Error response from daemon: %s", strings.TrimSpace(errorMessage))
|
|
||||||
}
|
|
||||||
|
|
||||||
serverResp.body = resp.Body
|
|
||||||
serverResp.header = resp.Header
|
|
||||||
return serverResp, nil
|
return serverResp, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (cli *Client) checkResponseErr(serverResp serverResponse) error {
|
||||||
|
if serverResp.statusCode >= 200 && serverResp.statusCode < 400 {
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
|
||||||
|
body, err := ioutil.ReadAll(serverResp.body)
|
||||||
|
if err != nil {
|
||||||
|
return err
|
||||||
|
}
|
||||||
|
if len(body) == 0 {
|
||||||
|
return fmt.Errorf("Error: request returned %s for API route and version %s, check if the server supports the requested API version", http.StatusText(serverResp.statusCode), serverResp.reqURL)
|
||||||
|
}
|
||||||
|
|
||||||
|
var ct string
|
||||||
|
if serverResp.header != nil {
|
||||||
|
ct = serverResp.header.Get("Content-Type")
|
||||||
|
}
|
||||||
|
|
||||||
|
var errorMessage string
|
||||||
|
if (cli.version == "" || versions.GreaterThan(cli.version, "1.23")) && ct == "application/json" {
|
||||||
|
var errorResponse types.ErrorResponse
|
||||||
|
if err := json.Unmarshal(body, &errorResponse); err != nil {
|
||||||
|
return fmt.Errorf("Error reading JSON: %v", err)
|
||||||
|
}
|
||||||
|
errorMessage = errorResponse.Message
|
||||||
|
} else {
|
||||||
|
errorMessage = string(body)
|
||||||
|
}
|
||||||
|
|
||||||
|
return fmt.Errorf("Error response from daemon: %s", strings.TrimSpace(errorMessage))
|
||||||
|
}
|
||||||
|
|
||||||
func (cli *Client) addHeaders(req *http.Request, headers headers) *http.Request {
|
func (cli *Client) addHeaders(req *http.Request, headers headers) *http.Request {
|
||||||
// Add CLI Config's HTTP Headers BEFORE we set the Docker headers
|
// Add CLI Config's HTTP Headers BEFORE we set the Docker headers
|
||||||
// then the user can't change OUR headers
|
// then the user can't change OUR headers
|
||||||
|
@ -239,9 +254,9 @@ func encodeData(data interface{}) (*bytes.Buffer, error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func ensureReaderClosed(response serverResponse) {
|
func ensureReaderClosed(response serverResponse) {
|
||||||
if body := response.body; body != nil {
|
if response.body != nil {
|
||||||
// Drain up to 512 bytes and close the body to let the Transport reuse the connection
|
// Drain up to 512 bytes and close the body to let the Transport reuse the connection
|
||||||
io.CopyN(ioutil.Discard, body, 512)
|
io.CopyN(ioutil.Discard, response.body, 512)
|
||||||
response.body.Close()
|
response.body.Close()
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -39,7 +39,7 @@ func (cli *Client) ServiceCreate(ctx context.Context, service swarm.ServiceSpec,
|
||||||
service.TaskTemplate.ContainerSpec.Image = img
|
service.TaskTemplate.ContainerSpec.Image = img
|
||||||
}
|
}
|
||||||
// add platforms that are compatible with the service
|
// add platforms that are compatible with the service
|
||||||
service.TaskTemplate.Placement = updateServicePlatforms(service.TaskTemplate.Placement, distributionInspect)
|
service.TaskTemplate.Placement = setServicePlatforms(service.TaskTemplate.Placement, distributionInspect)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
var response types.ServiceCreateResponse
|
var response types.ServiceCreateResponse
|
||||||
|
@ -86,13 +86,15 @@ func imageWithTagString(image string) string {
|
||||||
return ""
|
return ""
|
||||||
}
|
}
|
||||||
|
|
||||||
// updateServicePlatforms updates the Platforms in swarm.Placement to list
|
// setServicePlatforms sets Platforms in swarm.Placement to list all
|
||||||
// all compatible platforms for the service, as found in distributionInspect
|
// compatible platforms for the service, as found in distributionInspect
|
||||||
// and returns a pointer to the new or updated swarm.Placement struct
|
// and returns a pointer to the new or updated swarm.Placement struct.
|
||||||
func updateServicePlatforms(placement *swarm.Placement, distributionInspect registrytypes.DistributionInspect) *swarm.Placement {
|
func setServicePlatforms(placement *swarm.Placement, distributionInspect registrytypes.DistributionInspect) *swarm.Placement {
|
||||||
if placement == nil {
|
if placement == nil {
|
||||||
placement = &swarm.Placement{}
|
placement = &swarm.Placement{}
|
||||||
}
|
}
|
||||||
|
// reset any existing listed platforms
|
||||||
|
placement.Platforms = []swarm.Platform{}
|
||||||
for _, p := range distributionInspect.Platforms {
|
for _, p := range distributionInspect.Platforms {
|
||||||
placement.Platforms = append(placement.Platforms, swarm.Platform{
|
placement.Platforms = append(placement.Platforms, swarm.Platform{
|
||||||
Architecture: p.Architecture,
|
Architecture: p.Architecture,
|
||||||
|
|
|
@ -51,7 +51,7 @@ func (cli *Client) ServiceUpdate(ctx context.Context, serviceID string, version
|
||||||
service.TaskTemplate.ContainerSpec.Image = img
|
service.TaskTemplate.ContainerSpec.Image = img
|
||||||
}
|
}
|
||||||
// add platforms that are compatible with the service
|
// add platforms that are compatible with the service
|
||||||
service.TaskTemplate.Placement = updateServicePlatforms(service.TaskTemplate.Placement, distributionInspect)
|
service.TaskTemplate.Placement = setServicePlatforms(service.TaskTemplate.Placement, distributionInspect)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -29,12 +29,6 @@ func IsGitURL(str string) bool {
|
||||||
return checkURL(str, "git")
|
return checkURL(str, "git")
|
||||||
}
|
}
|
||||||
|
|
||||||
// IsGitTransport returns true if the provided str is a git transport by inspecting
|
|
||||||
// the prefix of the string for known protocols used in git.
|
|
||||||
func IsGitTransport(str string) bool {
|
|
||||||
return IsURL(str) || strings.HasPrefix(str, "git://") || strings.HasPrefix(str, "git@")
|
|
||||||
}
|
|
||||||
|
|
||||||
// IsTransportURL returns true if the provided str is a transport (tcp, tcp+tls, udp, unix) URL.
|
// IsTransportURL returns true if the provided str is a transport (tcp, tcp+tls, udp, unix) URL.
|
||||||
func IsTransportURL(str string) bool {
|
func IsTransportURL(str string) bool {
|
||||||
return checkURL(str, "transport")
|
return checkURL(str, "transport")
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
# the following lines are in sorted order, FYI
|
# the following lines are in sorted order, FYI
|
||||||
github.com/Azure/go-ansiterm 388960b655244e76e24c75f48631564eaefade62
|
github.com/Azure/go-ansiterm 388960b655244e76e24c75f48631564eaefade62
|
||||||
github.com/Microsoft/hcsshim v0.5.23
|
github.com/Microsoft/hcsshim v0.5.25
|
||||||
github.com/Microsoft/go-winio v0.4.2
|
github.com/Microsoft/go-winio v0.4.2
|
||||||
github.com/Sirupsen/logrus v0.11.0
|
github.com/Sirupsen/logrus v0.11.0
|
||||||
github.com/davecgh/go-spew 346938d642f2ec3594ed81d874461961cd0faa76
|
github.com/davecgh/go-spew 346938d642f2ec3594ed81d874461961cd0faa76
|
||||||
|
@ -8,7 +8,7 @@ github.com/docker/libtrust 9cbd2a1374f46905c68a4eb3694a130610adc62a
|
||||||
github.com/go-check/check 4ed411733c5785b40214c70bce814c3a3a689609 https://github.com/cpuguy83/check.git
|
github.com/go-check/check 4ed411733c5785b40214c70bce814c3a3a689609 https://github.com/cpuguy83/check.git
|
||||||
github.com/gorilla/context v1.1
|
github.com/gorilla/context v1.1
|
||||||
github.com/gorilla/mux v1.1
|
github.com/gorilla/mux v1.1
|
||||||
github.com/jhowardmsft/opengcs v0.0.3
|
github.com/jhowardmsft/opengcs v0.0.7
|
||||||
github.com/kr/pty 5cf931ef8f
|
github.com/kr/pty 5cf931ef8f
|
||||||
github.com/mattn/go-shellwords v1.0.3
|
github.com/mattn/go-shellwords v1.0.3
|
||||||
github.com/tchap/go-patricia v2.2.6
|
github.com/tchap/go-patricia v2.2.6
|
||||||
|
@ -17,7 +17,7 @@ github.com/vdemeester/shakers 24d7f1d6a71aa5d9cbe7390e4afb66b7eef9e1b3
|
||||||
golang.org/x/net 7dcfb8076726a3fdd9353b6b8a1f1b6be6811bd6
|
golang.org/x/net 7dcfb8076726a3fdd9353b6b8a1f1b6be6811bd6
|
||||||
golang.org/x/sys 8f0908ab3b2457e2e15403d3697c9ef5cb4b57a9
|
golang.org/x/sys 8f0908ab3b2457e2e15403d3697c9ef5cb4b57a9
|
||||||
github.com/docker/go-units 9e638d38cf6977a37a8ea0078f3ee75a7cdb2dd1
|
github.com/docker/go-units 9e638d38cf6977a37a8ea0078f3ee75a7cdb2dd1
|
||||||
github.com/docker/go-connections e15c02316c12de00874640cd76311849de2aeed5
|
github.com/docker/go-connections 3ede32e2033de7505e6500d6c868c2b9ed9f169d
|
||||||
golang.org/x/text f72d8390a633d5dfb0cc84043294db9f6c935756
|
golang.org/x/text f72d8390a633d5dfb0cc84043294db9f6c935756
|
||||||
github.com/stretchr/testify 4d4bfba8f1d1027c4fdbe371823030df51419987
|
github.com/stretchr/testify 4d4bfba8f1d1027c4fdbe371823030df51419987
|
||||||
github.com/pmezard/go-difflib v1.0.0
|
github.com/pmezard/go-difflib v1.0.0
|
||||||
|
@ -27,7 +27,7 @@ github.com/imdario/mergo 0.2.1
|
||||||
golang.org/x/sync de49d9dcd27d4f764488181bea099dfe6179bcf0
|
golang.org/x/sync de49d9dcd27d4f764488181bea099dfe6179bcf0
|
||||||
|
|
||||||
#get libnetwork packages
|
#get libnetwork packages
|
||||||
github.com/docker/libnetwork f4a15a0890383619ad797b3bd2481cc6f46a978d
|
github.com/docker/libnetwork 6426d1e66f33c0b0c8bb135b7ee547447f54d043
|
||||||
github.com/docker/go-events 18b43f1bc85d9cdd42c05a6cd2d444c7a200a894
|
github.com/docker/go-events 18b43f1bc85d9cdd42c05a6cd2d444c7a200a894
|
||||||
github.com/armon/go-radix e39d623f12e8e41c7b5529e9a9dd67a1e2261f80
|
github.com/armon/go-radix e39d623f12e8e41c7b5529e9a9dd67a1e2261f80
|
||||||
github.com/armon/go-metrics eb0af217e5e9747e41dd5303755356b62d28e3ec
|
github.com/armon/go-metrics eb0af217e5e9747e41dd5303755356b62d28e3ec
|
||||||
|
@ -106,7 +106,7 @@ github.com/stevvooe/continuity cd7a8e21e2b6f84799f5dd4b65faf49c8d3ee02d
|
||||||
github.com/tonistiigi/fsutil 0ac4c11b053b9c5c7c47558f81f96c7100ce50fb
|
github.com/tonistiigi/fsutil 0ac4c11b053b9c5c7c47558f81f96c7100ce50fb
|
||||||
|
|
||||||
# cluster
|
# cluster
|
||||||
github.com/docker/swarmkit a4bf0135f63fb60f0e76ae81579cde87f580db6e
|
github.com/docker/swarmkit 79381d0840be27f8b3f5c667b348a4467d866eeb
|
||||||
github.com/gogo/protobuf v0.4
|
github.com/gogo/protobuf v0.4
|
||||||
github.com/cloudflare/cfssl 7fb22c8cba7ecaf98e4082d22d65800cf45e042a
|
github.com/cloudflare/cfssl 7fb22c8cba7ecaf98e4082d22d65800cf45e042a
|
||||||
github.com/google/certificate-transparency d90e65c3a07988180c5b1ece71791c0b6506826e
|
github.com/google/certificate-transparency d90e65c3a07988180c5b1ece71791c0b6506826e
|
||||||
|
|
|
@ -153,16 +153,18 @@ func (m *MountPoint) Cleanup() error {
|
||||||
// before creating the source directory on the host.
|
// before creating the source directory on the host.
|
||||||
func (m *MountPoint) Setup(mountLabel string, rootIDs idtools.IDPair, checkFun func(m *MountPoint) error) (path string, err error) {
|
func (m *MountPoint) Setup(mountLabel string, rootIDs idtools.IDPair, checkFun func(m *MountPoint) error) (path string, err error) {
|
||||||
defer func() {
|
defer func() {
|
||||||
if err == nil {
|
if err != nil || !label.RelabelNeeded(m.Mode) {
|
||||||
if label.RelabelNeeded(m.Mode) {
|
return
|
||||||
if err = label.Relabel(m.Source, mountLabel, label.IsShared(m.Mode)); err != nil {
|
}
|
||||||
path = ""
|
|
||||||
err = errors.Wrapf(err, "error setting label on mount source '%s'", m.Source)
|
err = label.Relabel(m.Source, mountLabel, label.IsShared(m.Mode))
|
||||||
return
|
if err == syscall.ENOTSUP {
|
||||||
}
|
err = nil
|
||||||
}
|
}
|
||||||
|
if err != nil {
|
||||||
|
path = ""
|
||||||
|
err = errors.Wrapf(err, "error setting label on mount source '%s'", m.Source)
|
||||||
}
|
}
|
||||||
return
|
|
||||||
}()
|
}()
|
||||||
|
|
||||||
if m.Volume != nil {
|
if m.Volume != nil {
|
||||||
|
|
Loading…
Reference in New Issue