github.com/Heebron/moby@v0.0.0-20221111184709-6eab4f55faf7/image/v1/imagev1.go (about) 1 package v1 // import "github.com/docker/docker/image/v1" 2 3 import ( 4 "encoding/json" 5 "strings" 6 7 "github.com/docker/docker/api/types/versions" 8 "github.com/docker/docker/image" 9 "github.com/docker/docker/layer" 10 "github.com/docker/docker/pkg/stringid" 11 "github.com/opencontainers/go-digest" 12 "github.com/sirupsen/logrus" 13 ) 14 15 // noFallbackMinVersion is the minimum version for which v1compatibility 16 // information will not be marshaled through the Image struct to remove 17 // blank fields. 18 const noFallbackMinVersion = "1.8.3" 19 20 // HistoryFromConfig creates a History struct from v1 configuration JSON 21 func HistoryFromConfig(imageJSON []byte, emptyLayer bool) (image.History, error) { 22 h := image.History{} 23 var v1Image image.V1Image 24 if err := json.Unmarshal(imageJSON, &v1Image); err != nil { 25 return h, err 26 } 27 28 return image.History{ 29 Author: v1Image.Author, 30 Created: v1Image.Created, 31 CreatedBy: strings.Join(v1Image.ContainerConfig.Cmd, " "), 32 Comment: v1Image.Comment, 33 EmptyLayer: emptyLayer, 34 }, nil 35 } 36 37 // CreateID creates an ID from v1 image, layerID and parent ID. 38 // Used for backwards compatibility with old clients. 39 func CreateID(v1Image image.V1Image, layerID layer.ChainID, parent digest.Digest) (digest.Digest, error) { 40 v1Image.ID = "" 41 v1JSON, err := json.Marshal(v1Image) 42 if err != nil { 43 return "", err 44 } 45 46 var config map[string]*json.RawMessage 47 if err := json.Unmarshal(v1JSON, &config); err != nil { 48 return "", err 49 } 50 51 // FIXME: note that this is slightly incompatible with RootFS logic 52 config["layer_id"] = rawJSON(layerID) 53 if parent != "" { 54 config["parent"] = rawJSON(parent) 55 } 56 57 configJSON, err := json.Marshal(config) 58 if err != nil { 59 return "", err 60 } 61 logrus.Debugf("CreateV1ID %s", configJSON) 62 63 return digest.FromBytes(configJSON), nil 64 } 65 66 // MakeConfigFromV1Config creates an image config from the legacy V1 config format. 67 func MakeConfigFromV1Config(imageJSON []byte, rootfs *image.RootFS, history []image.History) ([]byte, error) { 68 var dver struct { 69 DockerVersion string `json:"docker_version"` 70 } 71 72 if err := json.Unmarshal(imageJSON, &dver); err != nil { 73 return nil, err 74 } 75 76 useFallback := versions.LessThan(dver.DockerVersion, noFallbackMinVersion) 77 78 if useFallback { 79 var v1Image image.V1Image 80 err := json.Unmarshal(imageJSON, &v1Image) 81 if err != nil { 82 return nil, err 83 } 84 imageJSON, err = json.Marshal(v1Image) 85 if err != nil { 86 return nil, err 87 } 88 } 89 90 var c map[string]*json.RawMessage 91 if err := json.Unmarshal(imageJSON, &c); err != nil { 92 return nil, err 93 } 94 95 delete(c, "id") 96 delete(c, "parent") 97 delete(c, "Size") // Size is calculated from data on disk and is inconsistent 98 delete(c, "parent_id") 99 delete(c, "layer_id") 100 delete(c, "throwaway") 101 102 c["rootfs"] = rawJSON(rootfs) 103 c["history"] = rawJSON(history) 104 105 return json.Marshal(c) 106 } 107 108 func rawJSON(value interface{}) *json.RawMessage { 109 jsonval, err := json.Marshal(value) 110 if err != nil { 111 return nil 112 } 113 return (*json.RawMessage)(&jsonval) 114 } 115 116 // ValidateID checks whether an ID string is a valid image ID. 117 func ValidateID(id string) error { 118 return stringid.ValidateID(id) 119 }