// Copyright The Monogon Project Authors.
// SPDX-License-Identifier: Apache-2.0

// Package main implements 'stampgo', a tool to convert build status data into a
// version.spec.Version proto, which is then embedded into a Go source file.
package main

import (
	"bufio"
	"flag"
	"fmt"
	"log"
	"os"
	"regexp"
	"strconv"
	"strings"

	"github.com/coreos/go-semver/semver"
	"google.golang.org/protobuf/proto"

	"source.monogon.dev/version/spec"
)

var (
	flagStatusFile string
	flagOutFile    string
	flagImportpath string
	flagProduct    string
)

var (
	rePrereleaseCommitOffset = regexp.MustCompile(`^dev([0-9]+)$`)
	rePrereleaseDirty        = regexp.MustCompile(`^dirty$`)
	rePrereleaseGitHash      = regexp.MustCompile(`^g[0-9a-f]+$`)
)

func init() {
	flag.StringVar(&flagStatusFile, "status_file", "", "path to bazel workspace status file")
	flag.StringVar(&flagOutFile, "out_file", "version.go", "path to os-release output file")
	flag.StringVar(&flagImportpath, "importpath", "", "importpath of generated source")
	flag.StringVar(&flagProduct, "product", "", "product name within the monogon source tree")
}

// parseStatusFile reads and parses a Bazel build status file and returns
// a string -> string map based on its contents.
func parseStatusFile(path string) (map[string]string, error) {
	f, err := os.Open(path)
	if err != nil {
		return nil, fmt.Errorf("open failed: %w", err)
	}
	defer f.Close()

	res := make(map[string]string)
	scanner := bufio.NewScanner(f)
	for scanner.Scan() {
		line := scanner.Text()
		parts := strings.Split(line, " ")
		if len(parts) != 2 {
			return nil, fmt.Errorf("invalid line: %q", line)
		}
		k, v := parts[0], parts[1]
		if k == "" {
			return nil, fmt.Errorf("invalid line: %q", line)
		}
		if _, ok := res[k]; ok {
			return nil, fmt.Errorf("repeated key %q", k)
		}
		res[k] = v
	}
	return res, nil
}

func main() {
	flag.Parse()
	if flagImportpath == "" {
		log.Fatalf("Importpath must be set")
	}
	importpathParts := strings.Split(flagImportpath, "/")
	packageName := importpathParts[len(importpathParts)-1]

	values, err := parseStatusFile(flagStatusFile)
	if err != nil {
		log.Fatalf("Failed to read workspace status file: %v", err)
	}

	commitHash := values["STABLE_MONOGON_gitCommit"]
	if commitHash == "" {
		log.Fatalf("No git commit in workspace status")
	}
	if len(commitHash) < 8 {
		log.Fatalf("Git commit hash too short")
	}
	buildTreeState := spec.Version_GitInformation_BUILD_TREE_STATE_INVALID
	switch values["STABLE_MONOGON_gitTreeState"] {
	case "clean":
		buildTreeState = spec.Version_GitInformation_BUILD_TREE_STATE_CLEAN
	case "dirty":
		buildTreeState = spec.Version_GitInformation_BUILD_TREE_STATE_DIRTY
	default:
		log.Fatalf("Invalid git tree state %q", values["STABLE_MONOGON_gitTreeState"])
	}

	version := &spec.Version{
		GitInformation: &spec.Version_GitInformation{
			CommitHash:     commitHash[:8],
			BuildTreeState: buildTreeState,
		},
	}

	productVersion := values["STABLE_MONOGON_"+flagProduct+"_version"]
	if productVersion != "" {
		if productVersion[0] != 'v' {
			log.Fatalf("Invalid %s version %q: does not start with v", flagProduct, productVersion)
		}
		productVersion = productVersion[1:]
		v, err := semver.NewVersion(productVersion)
		if err != nil {
			log.Fatalf("Invalid %s version %q: %v", flagProduct, productVersion, err)
		}
		// Parse prerelease strings (v1.2.3-foo-bar -> [foo, bar])
		for _, el := range v.PreRelease.Slice() {
			// Skip empty slices which happens when there's a semver string with no
			// prerelease data.
			if el == "" {
				continue
			}
			preCommitOffset := rePrereleaseCommitOffset.FindStringSubmatch(el)
			preDirty := rePrereleaseDirty.FindStringSubmatch(el)
			preGitHash := rePrereleaseGitHash.FindStringSubmatch(el)
			switch {
			case preCommitOffset != nil:
				offset, err := strconv.ParseUint(preCommitOffset[1], 10, 64)
				if err != nil {
					log.Fatalf("Invalid commit offset value: %v", err)
				}
				version.GitInformation.CommitsSinceRelease = offset
			case preDirty != nil:
				// Ignore field, we have it from the global monorepo state.
			case preGitHash != nil:
				// Ignore field, we have it from the global monorepo state.
			default:
				log.Fatalf("Invalid prerelease string %q (in %q)", el, productVersion)
			}
		}
		version.Release = &spec.Version_Release{
			Major: v.Major,
			Minor: v.Minor,
			Patch: v.Patch,
		}
	}

	versionBytes, err := proto.Marshal(version)
	if err != nil {
		log.Fatalf("failed to marshal version: %v", err)
	}
	literalBytes := make([]string, len(versionBytes))
	for i, by := range versionBytes {
		literalBytes[i] = fmt.Sprintf("0x%02x", by)
	}

	content := []string{
		`// Generated by //version/stampgo`,
		`package ` + packageName,
		``,
		`import (`,
		`	"fmt"`,
		`	"os"`,
		``,
		`	"google.golang.org/protobuf/proto"`,
		``,
		`	"source.monogon.dev/version/spec"`,
		`)`,
		``,
		`var raw = []byte{`,
		`	` + strings.Join(literalBytes, ", ") + `,`,
		`}`,
		``,
		`var Version *spec.Version`,
		``,
		`func init() {`,
		`	var version spec.Version`,
		`	if err := proto.Unmarshal(raw, &version); err != nil {`,
		`		fmt.Fprintf(os.Stderr, "Invalid stamped version: %v\n", err)`,
		`	}`,
		`	Version = &version`,
		`}`,
		``,
	}

	if err := os.WriteFile(flagOutFile, []byte(strings.Join(content, "\n")), 0644); err != nil {
		log.Fatalf("Failed to write output file: %v", err)
	}
}
