// BuildManifest creates the manifest for the given context
557087
func BuildManifest(ctx Context) (*Manifest, error) {
	resourcesByPath := map[string]Resource{}
	hardlinks := newHardlinkManager()

	if err := ctx.Walk(func(p string, fi os.FileInfo, err error) error {
		if err != nil {
			return fmt.Errorf("error walking %s: %v", p, err)
		}

		if p == string(os.PathSeparator) {
			// skip root
			return nil
		}

		resource, err := ctx.Resource(p, fi)
		if err != nil {
			if err == ErrNotFound {
				return nil
			}
			log.Printf("error getting resource %q: %v", p, err)
			return err
		}

		// add to the hardlink manager
		if err := hardlinks.Add(fi, resource); err == nil {
			// Resource has been accepted by hardlink manager so we don't add
			// it to the resourcesByPath until we merge at the end.
			return nil
		} else if err != errNotAHardLink {
			// handle any other case where we have a proper error.
			return fmt.Errorf("adding hardlink %s: %v", p, err)
		}

		resourcesByPath[p] = resource

		return nil
	}); err != nil {
		return nil, err
	}

	// merge and post-process the hardlinks.
	hardlinked, err := hardlinks.Merge()
	if err != nil {
		return nil, err
	}

	for _, resource := range hardlinked {
		resourcesByPath[resource.Path()] = resource
	}

	var resources []Resource
	for _, resource := range resourcesByPath {
		resources = append(resources, resource)
	}

	sort.Stable(ByPath(resources))

	return &Manifest{
		Resources: resources,
	}, nil
}
263883
func ExportManifest(m interface{}) *Manifest {
	v := reflect.ValueOf(m)
	return (*Manifest)(unsafe.Pointer(v.Pointer()))
}
583198
func GenerateManifest(layerData types.DockerImageData, manhash string, dockerURL *common.ParsedDockerURL, debug log.Logger) (*schema.ImageManifest, error) {
	dockerConfig := layerData.Config
	genManifest := &schema.ImageManifest{}

	appURL := ""
	appURL = dockerURL.IndexURL + "/"
	appURL += dockerURL.ImageName + "-" + layerData.ID
	appURL, err := appctypes.SanitizeACIdentifier(appURL)
	if err != nil {
		return nil, err
	}
	name := appctypes.MustACIdentifier(appURL)
	genManifest.Name = *name

	acVersion, err := appctypes.NewSemVer(schema.AppContainerVersion.String())
	if err != nil {
		panic("invalid appc spec version")
	}
	genManifest.ACVersion = *acVersion

	genManifest.ACKind = appctypes.ACKind(schema.ImageManifestKind)

	var annotations appctypes.Annotations

	labels := make(map[appctypes.ACIdentifier]string)
	parentLabels := make(map[appctypes.ACIdentifier]string)

	setLabel(labels, "layer", layerData.ID)
	setLabel(labels, "version", dockerURL.Tag)

	setOSArch(labels, layerData.OS, layerData.Architecture)
	setOSArch(parentLabels, layerData.OS, layerData.Architecture)

	setAnnotation(&annotations, "authors", layerData.Author)
	epoch := time.Unix(0, 0)
	if !layerData.Created.Equal(epoch) {
		setAnnotation(&annotations, "created", layerData.Created.Format(time.RFC3339))
	}
	setAnnotation(&annotations, "docker-comment", layerData.Comment)
	setAnnotation(&annotations, common.AppcDockerOriginalName, dockerURL.OriginalName)
	setAnnotation(&annotations, common.AppcDockerRegistryURL, dockerURL.IndexURL)
	setAnnotation(&annotations, common.AppcDockerRepository, dockerURL.ImageName)
	setAnnotation(&annotations, common.AppcDockerImageID, layerData.ID)
	setAnnotation(&annotations, common.AppcDockerParentImageID, layerData.Parent)
	setAnnotation(&annotations, common.AppcDockerManifestHash, manhash)

	if dockerConfig != nil {
		exec := getExecCommand(dockerConfig.Entrypoint, dockerConfig.Cmd)
		user, group := parseDockerUser(dockerConfig.User)
		var env appctypes.Environment
		for _, v := range dockerConfig.Env {
			parts := strings.SplitN(v, "=", 2)
                        if len(parts) == 2 {
				env.Set(parts[0], parts[1])
                        }
		}
		app := &appctypes.App{
			Exec:             exec,
			User:             user,
			Group:            group,
			Environment:      env,
			WorkingDirectory: dockerConfig.WorkingDir,
		}

		app.UserLabels = dockerConfig.Labels

		app.MountPoints, err = convertVolumesToMPs(dockerConfig.Volumes)
		if err != nil {
			return nil, err
		}

		app.Ports, err = convertPorts(dockerConfig.ExposedPorts, dockerConfig.PortSpecs, debug)
		if err != nil {
			return nil, err
		}

		ep, cmd, err := generateEPCmdAnnotation(dockerConfig.Entrypoint, dockerConfig.Cmd)
		if err != nil {
			return nil, err
		}
		if len(ep) > 0 {
			setAnnotation(&annotations, common.AppcDockerEntrypoint, ep)
		}
		if len(cmd) > 0 {
			setAnnotation(&annotations, common.AppcDockerCmd, cmd)
		}

		genManifest.App = app
	}

	if layerData.Parent != "" {
		indexPrefix := ""
		// omit docker hub index URL in app name
		indexPrefix = dockerURL.IndexURL + "/"
		parentImageNameString := indexPrefix + dockerURL.ImageName + "-" + layerData.Parent
		parentImageNameString, err := appctypes.SanitizeACIdentifier(parentImageNameString)
		if err != nil {
			return nil, err
		}
		parentImageName := appctypes.MustACIdentifier(parentImageNameString)

		plbl, err := appctypes.LabelsFromMap(labels)
		if err != nil {
			return nil, err
		}

		genManifest.Dependencies = append(genManifest.Dependencies, appctypes.Dependency{ImageName: *parentImageName, Labels: plbl})

		setAnnotation(&annotations, common.AppcDockerTag, dockerURL.Tag)
	}

	genManifest.Labels, err = appctypes.LabelsFromMap(labels)
	if err != nil {
		return nil, err
	}
	genManifest.Annotations = annotations

	return genManifest, nil
}
1085248
func (s Storage) loadManifest() (moduleManifest, error) {
	manifest := moduleManifest{}

	manifestPath := filepath.Join(s.StorageDir, manifestName)
	data, err := ioutil.ReadFile(manifestPath)
	if err != nil && !os.IsNotExist(err) {
		return manifest, err
	}

	if len(data) == 0 {
		return manifest, nil
	}

	if err := json.Unmarshal(data, &manifest); err != nil {
		return manifest, err
	}
	return manifest, nil
}
473318
func makeManifestFile(opts Options) (fs.File, error) {
	if opts.VersionFile != "" && !fs.IsCleanSlashPath(opts.VersionFile) {
		return nil, fmt.Errorf("version file path should be a clean path relative to a package root: %s", opts.VersionFile)
	}
	if err := pkg.ValidateInstallMode(opts.InstallMode); err != nil {
		return nil, err
	}
	formatVer := pkg.ManifestFormatVersion
	if opts.OverrideFormatVersion != "" {
		formatVer = opts.OverrideFormatVersion
	}
	buf := &bytes.Buffer{}
	err := pkg.WriteManifest(&pkg.Manifest{
		FormatVersion: formatVer,
		PackageName:   opts.PackageName,
		VersionFile:   opts.VersionFile,
		InstallMode:   opts.InstallMode,
	}, buf)
	if err != nil {
		return nil, err
	}
	out := manifestFile(buf.Bytes())
	return &out, nil
}
1287574
func ReadManifest(r io.Reader) (manifest Manifest, err error) {
	blob, err := ioutil.ReadAll(r)
	if err == nil {
		err = json.Unmarshal(blob, &manifest)
	}
	return
}
371935
func UpdateManifest(m Manifests, root string, paths []string, id flux.ResourceID, f func(manifest []byte) ([]byte, error)) error {
	resources, err := m.LoadManifests(root, paths)
	if err != nil {
		return err
	}

	resource, ok := resources[id.String()]
	if !ok {
		return ErrResourceNotFound(id.String())
	}

	path := filepath.Join(root, resource.Source())
	def, err := ioutil.ReadFile(path)
	if err != nil {
		return err
	}

	newDef, err := f(def)
	if err != nil {
		return err
	}

	fi, err := os.Stat(path)
	if err != nil {
		return err
	}
	return ioutil.WriteFile(path, newDef, fi.Mode())
}
1065518
func (d *deployerImpl) readManifest(ctx context.Context, instanceDir string) (pkg.Manifest, error) {
	manifestPath := filepath.Join(instanceDir, filepath.FromSlash(pkg.ManifestName))
	r, err := os.Open(manifestPath)
	if err != nil {
		return pkg.Manifest{}, err
	}
	defer r.Close()
	manifest, err := pkg.ReadManifest(r)
	if err != nil {
		return pkg.Manifest{}, err
	}
	// Older packages do not have Files section in the manifest, so reconstruct it
	// from actual files on disk.
	if len(manifest.Files) == 0 {
		if manifest.Files, err = scanPackageDir(ctx, instanceDir); err != nil {
			return pkg.Manifest{}, err
		}
	}
	return manifest, nil
}
738849
func (r *Registry) PutManifest(ctx context.Context, repository, ref string, manifest distribution.Manifest) error {
	url := r.url("/v2/%s/manifests/%s", repository, ref)
	r.Logf("registry.manifest.put url=%s repository=%s reference=%s", url, repository, ref)

	b, err := json.Marshal(manifest)
	if err != nil {
		return err
	}

	req, err := http.NewRequest("PUT", url, bytes.NewBuffer(b))
	if err != nil {
		return err
	}

	req.Header.Set("Content-Type", schema2.MediaTypeManifest)
	resp, err := r.Client.Do(req.WithContext(ctx))
	if resp != nil {
		defer resp.Body.Close()
	}
	return err
}
703354
func buildPutManifestRequest(imageManifest types.ImageManifest, targetRef reference.Named) (mountRequest, error) {
	refWithoutTag, err := reference.WithName(targetRef.Name())
	if err != nil {
		return mountRequest{}, err
	}
	mountRef, err := reference.WithDigest(refWithoutTag, imageManifest.Descriptor.Digest)
	if err != nil {
		return mountRequest{}, err
	}

	// This indentation has to be added to ensure sha parity with the registry
	v2ManifestBytes, err := json.MarshalIndent(imageManifest.SchemaV2Manifest, "", "   ")
	if err != nil {
		return mountRequest{}, err
	}
	// indent only the DeserializedManifest portion of this, in order to maintain parity with the registry
	// and not alter the sha
	var v2Manifest schema2.DeserializedManifest
	if err = v2Manifest.UnmarshalJSON(v2ManifestBytes); err != nil {
		return mountRequest{}, err
	}
	imageManifest.SchemaV2Manifest = &v2Manifest

	return mountRequest{ref: mountRef, manifest: imageManifest}, err
}
935955
func VerifyManifest(ctx Context, manifest *Manifest) error {
	for _, resource := range manifest.Resources {
		if err := ctx.Verify(resource); err != nil {
			return err
		}
	}

	return nil
}
888505
func (ttles *TTLExpirationScheduler) AddManifest(manifestRef reference.Canonical, ttl time.Duration) error {
	ttles.Lock()
	defer ttles.Unlock()

	if ttles.stopped {
		return fmt.Errorf("scheduler not started")
	}

	ttles.add(manifestRef, ttl, entryTypeManifest)
	return nil
}
927146
func (p *Pod) UpdateManifest(m *schema.PodManifest, path string) error {
	if !p.mutable {
		return ErrImmutable
	}

	mpath := common.PodManifestPath(path)
	mstat, err := os.Stat(mpath)
	if err != nil {
		return err
	}

	tmpf, err := ioutil.TempFile(path, "")
	if err != nil {
		return err
	}

	defer func() {
		tmpf.Close()
		os.Remove(tmpf.Name())
	}()

	if err := tmpf.Chmod(mstat.Mode().Perm()); err != nil {
		return err
	}

	if err := json.NewEncoder(tmpf).Encode(m); err != nil {
		return err
	}

	if err := os.Rename(tmpf.Name(), mpath); err != nil {
		return err
	}

	return nil
}
1135115
func AppImageManifestPath(root string, appName types.ACName) string {
	return filepath.Join(AppInfoPath(root, appName), aci.ManifestFile)
}
165789
func getManifest(manifestName, manifestType, manifestFormat string, images ...string) (io.Reader, error) {
	podContainers := []goyaml.MapSlice{}

	for _, imageName := range images {
		host, namespace, repo, tag := splitDockerImageName(imageName)

		container := goyaml.MapSlice{
			{Key: "name", Value: repo},
			{Key: "image", Value: imageName},
		}

		img, err := getImageMetadata(host, namespace, repo, tag)

		if err != nil {
			return nil, fmt.Errorf("failed to get image metadata %q: %v", imageName, err)
		}
		portSlice := []goyaml.MapSlice{}
		for p := range img.ContainerConfig.ExposedPorts {
			port, err := strconv.Atoi(p.port())
			if err != nil {
				return nil, fmt.Errorf("failed to parse port %q: %v", p.port(), err)
			}
			portEntry := goyaml.MapSlice{{
				Key:   "name",
				Value: strings.Join([]string{p.proto(), p.port()}, "-"),
			}, {
				Key:   "containerPort",
				Value: port,
			}}
			portSlice = append(portSlice, portEntry)
			if p.proto() != "tcp" {
				portEntry = append(portEntry, goyaml.MapItem{Key: "protocol", Value: strings.ToUpper(p.proto())})
			}
		}
		if len(img.ContainerConfig.ExposedPorts) > 0 {
			container = append(container, goyaml.MapItem{Key: "ports", Value: portSlice})
		}
		podContainers = append(podContainers, container)
	}

	containerManifest := goyaml.MapSlice{
		{Key: "containers", Value: podContainers},
	}

	var data interface{}

	// TODO(proppy): add flag to handle multiple version
	apiVersion := goyaml.MapItem{Key: "apiVersion", Value: "v1"}

	switch manifestType {
	case "container":
		data = append(goyaml.MapSlice{apiVersion,
			{Key: "kind", Value: "ContainerList"},
			{Key: "metadata", Value: goyaml.MapSlice{}},
		}, containerManifest...)
	case "pod":
		data = goyaml.MapSlice{apiVersion,
			{Key: "kind", Value: "Pod"},
			{Key: "metadata", Value: goyaml.MapSlice{
				{Key: "name", Value: manifestName},
			}},
			{Key: "spec", Value: containerManifest},
		}
	default:
		return nil, fmt.Errorf("unsupported manifest type %q", manifestFormat)
	}

	yamlBytes, err := goyaml.Marshal(data)
	if err != nil {
		return nil, fmt.Errorf("failed to marshal container manifest: %v", err)
	}

	switch manifestFormat {
	case "yaml":
		return bytes.NewBuffer(yamlBytes), nil
	case "json":
		jsonBytes, err := yaml.YAMLToJSON(yamlBytes)
		if err != nil {
			return nil, fmt.Errorf("failed to marshal container manifest into JSON: %v", err)
		}
		var jsonPretty bytes.Buffer
		if err := json.Indent(&jsonPretty, jsonBytes, "", "  "); err != nil {
			return nil, fmt.Errorf("failed to indent json %q: %v", string(jsonBytes), err)
		}
		return &jsonPretty, nil
	default:
		return nil, fmt.Errorf("unsupported manifest format %q", manifestFormat)
	}

}
1319700
func LoadPodManifest(root string) (*schema.PodManifest, error) {
	buf, err := ioutil.ReadFile(common.PodManifestPath(root))
	if err != nil {
		return nil, errwrap.Wrap(errors.New("failed reading pod manifest"), err)
	}

	pm := &schema.PodManifest{}
	if err := json.Unmarshal(buf, pm); err != nil {
		return nil, errwrap.Wrap(errors.New("failed unmarshalling pod manifest"), err)
	}
	return pm, nil
}
172870
func (s *JobDescriptor) SetManifest(v *JobManifest) *JobDescriptor {
	s.Manifest = v
	return s
}