// Copyright 2021 The Android Open Source Project
//
// Licensed under the Apache License, Version 2.0 (the "License");
// you may not use this file except in compliance with the License.
// You may obtain a copy of the License at
//
//      http://www.apache.org/licenses/LICENSE-2.0
//
// Unless required by applicable law or agreed to in writing, software
// distributed under the License is distributed on an "AS IS" BASIS,
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
// See the License for the specific language governing permissions and
// limitations under the License.

package snapshot

import (
	"encoding/json"
	"fmt"
	"path/filepath"
	"sort"
	"strings"

	"github.com/google/blueprint"
	"github.com/google/blueprint/proptools"

	"android/soong/android"
)

//
// The host_snapshot module creates a snapshot of the modules defined in
// the deps property.  The modules within the deps property (host tools)
// are ones that return a valid path via HostToolPath() of the
// HostToolProvider.  The created snapshot contains the binaries and any
// transitive PackagingSpecs of the included host tools, along with a JSON
// meta file.
//
// The snapshot is installed into a source tree via
// development/vendor_snapshot/update.py, the included modules are
// provided as preferred prebuilts.
//
// To determine which tools to include in the host snapshot see
// host_fake_snapshot.go.

func init() {
	registerHostBuildComponents(android.InitRegistrationContext)
}

func registerHostBuildComponents(ctx android.RegistrationContext) {
	ctx.RegisterModuleType("host_snapshot", hostSnapshotFactory)
}

// Relative installation path
type RelativeInstallPath interface {
	RelativeInstallPath() string
}

type hostSnapshot struct {
	android.ModuleBase
	android.PackagingBase

	outputFile android.OutputPath
	installDir android.InstallPath
}

type ProcMacro interface {
	ProcMacro() bool
	CrateName() string
}

func hostSnapshotFactory() android.Module {
	module := &hostSnapshot{}
	initHostToolsModule(module)
	return module
}
func initHostToolsModule(module *hostSnapshot) {
	android.InitPackageModule(module)
	android.InitAndroidMultiTargetsArchModule(module, android.HostSupported, android.MultilibCommon)
}

var dependencyTag = struct {
	blueprint.BaseDependencyTag
	android.InstallAlwaysNeededDependencyTag
	android.PackagingItemAlwaysDepTag
}{}

func (f *hostSnapshot) DepsMutator(ctx android.BottomUpMutatorContext) {
	f.AddDeps(ctx, dependencyTag)
}
func (f *hostSnapshot) installFileName() string {
	return f.Name() + ".zip"
}

// Create zipfile with JSON description, notice files... for dependent modules
func (f *hostSnapshot) CreateMetaData(ctx android.ModuleContext, fileName string) android.OutputPath {
	var jsonData []SnapshotJsonFlags
	var metaPaths android.Paths

	installedNotices := make(map[string]bool)
	metaZipFile := android.PathForModuleOut(ctx, fileName).OutputPath

	// Create JSON file based on the direct dependencies
	ctx.VisitDirectDeps(func(dep android.Module) {
		desc := hostJsonDesc(dep)
		if desc != nil {
			jsonData = append(jsonData, *desc)
		}
		for _, notice := range dep.EffectiveLicenseFiles() {
			if _, ok := installedNotices[notice.String()]; !ok {
				installedNotices[notice.String()] = true
				noticeOut := android.PathForModuleOut(ctx, "NOTICE_FILES", notice.String()).OutputPath
				CopyFileToOutputPathRule(pctx, ctx, notice, noticeOut)
				metaPaths = append(metaPaths, noticeOut)
			}
		}
	})
	// Sort notice paths and json data for repeatble build
	sort.Slice(jsonData, func(i, j int) bool {
		return (jsonData[i].ModuleName < jsonData[j].ModuleName)
	})
	sort.Slice(metaPaths, func(i, j int) bool {
		return (metaPaths[i].String() < metaPaths[j].String())
	})

	marsh, err := json.Marshal(jsonData)
	if err != nil {
		ctx.ModuleErrorf("host snapshot json marshal failure: %#v", err)
		return android.OutputPath{}
	}

	jsonZipFile := android.PathForModuleOut(ctx, "host_snapshot.json").OutputPath
	metaPaths = append(metaPaths, jsonZipFile)
	rspFile := android.PathForModuleOut(ctx, "host_snapshot.rsp").OutputPath
	android.WriteFileRule(ctx, jsonZipFile, string(marsh))

	builder := android.NewRuleBuilder(pctx, ctx)

	builder.Command().
		BuiltTool("soong_zip").
		FlagWithArg("-C ", android.PathForModuleOut(ctx).OutputPath.String()).
		FlagWithOutput("-o ", metaZipFile).
		FlagWithRspFileInputList("-r ", rspFile, metaPaths)
	builder.Build("zip_meta", fmt.Sprintf("zipping meta data for %s", ctx.ModuleName()))

	return metaZipFile
}

// Create the host tool zip file
func (f *hostSnapshot) GenerateAndroidBuildActions(ctx android.ModuleContext) {
	// Create a zip file for the binaries, and a zip of the meta data, then merge zips
	depsZipFile := android.PathForModuleOut(ctx, f.Name()+"_deps.zip").OutputPath
	modsZipFile := android.PathForModuleOut(ctx, f.Name()+"_mods.zip").OutputPath
	f.outputFile = android.PathForModuleOut(ctx, f.installFileName()).OutputPath

	f.installDir = android.PathForModuleInstall(ctx)

	f.CopyDepsToZip(ctx, f.GatherPackagingSpecs(ctx), depsZipFile)

	builder := android.NewRuleBuilder(pctx, ctx)
	builder.Command().
		BuiltTool("zip2zip").
		FlagWithInput("-i ", depsZipFile).
		FlagWithOutput("-o ", modsZipFile).
		Text("**/*:" + proptools.ShellEscape(f.installDir.String()))

	metaZipFile := f.CreateMetaData(ctx, f.Name()+"_meta.zip")

	builder.Command().
		BuiltTool("merge_zips").
		Output(f.outputFile).
		Input(metaZipFile).
		Input(modsZipFile)

	builder.Build("manifest", fmt.Sprintf("Adding manifest %s", f.installFileName()))
	ctx.InstallFile(f.installDir, f.installFileName(), f.outputFile)

}

// Implements android.AndroidMkEntriesProvider
func (f *hostSnapshot) AndroidMkEntries() []android.AndroidMkEntries {
	return []android.AndroidMkEntries{android.AndroidMkEntries{
		Class:      "ETC",
		OutputFile: android.OptionalPathForPath(f.outputFile),
		DistFiles:  android.MakeDefaultDistFiles(f.outputFile),
		ExtraEntries: []android.AndroidMkExtraEntriesFunc{
			func(ctx android.AndroidMkExtraEntriesContext, entries *android.AndroidMkEntries) {
				entries.SetString("LOCAL_MODULE_PATH", f.installDir.String())
				entries.SetString("LOCAL_INSTALLED_MODULE_STEM", f.installFileName())
			},
		},
	}}
}

// Get host tools path and relative install string helpers
func hostToolPath(m android.Module) android.OptionalPath {
	if provider, ok := m.(android.HostToolProvider); ok {
		return provider.HostToolPath()
	}
	return android.OptionalPath{}

}
func hostRelativePathString(m android.Module) string {
	var outString string
	if rel, ok := m.(RelativeInstallPath); ok {
		outString = rel.RelativeInstallPath()
	}
	return outString
}

// Create JSON description for given module, only create descriptions for binary modules
// and rust_proc_macro modules which provide a valid HostToolPath
func hostJsonDesc(m android.Module) *SnapshotJsonFlags {
	path := hostToolPath(m)
	relPath := hostRelativePathString(m)
	procMacro := false
	moduleStem := filepath.Base(path.String())
	crateName := ""

	if pm, ok := m.(ProcMacro); ok && pm.ProcMacro() {
		procMacro = pm.ProcMacro()
		moduleStem = strings.TrimSuffix(moduleStem, filepath.Ext(moduleStem))
		crateName = pm.CrateName()
	}

	if path.Valid() && path.String() != "" {
		props := &SnapshotJsonFlags{
			ModuleStemName:      moduleStem,
			Filename:            path.String(),
			Required:            append(m.HostRequiredModuleNames(), m.RequiredModuleNames()...),
			RelativeInstallPath: relPath,
			RustProcMacro:       procMacro,
			CrateName:           crateName,
		}
		props.InitBaseSnapshotProps(m)
		return props
	}
	return nil
}
