// Package parsers defines parsers for the paths of "import" statements found in TypeScript and Sass
// files.
//
// The ad-hoc parsers in this package utilize regular expressions to extract out import paths,
// filter out comments, etc. While these parsers do not capture every aspect of the TypeScript and
// Sass grammars, they are sufficient for the purpose of parsing the import statements in the
// TypeScript and Sass files found in our codebase.
//
// The following alternatives were ruled out because of their high implementation and maintenance
// cost:
//
//  - Using third-party parsers written in Go (none exist at this time).
//  - Generate real parsers using e.g. Goyacc (https://pkg.go.dev/golang.org/x/tools/cmd/goyacc).
//  - Use the TypeScript compiler API to inspect the AST of a TypeScript file (requires calling
//    Node.js code from Gazelle).
package parsers

import (
	"regexp"
	"sort"
	"strings"

	"go.skia.org/infra/bazel/gazelle/parsers"
)

////////////////////////////////
// TypeScript imports parser. //
////////////////////////////////

// tsImportRegexps contains all the regular expressions necessary to extract imports from a
// TypeScript source file.
var tsImportRegexps = []*regexp.Regexp{
	// Matches the following styles of imports:
	//     import * from 'foo';
	//     export * from 'foo';
	//     import * as bar from 'foo';
	//     import { bar, baz } from 'foo';
	//     import { bar, baz as qux } from 'foo';
	regexp.MustCompile(`^\s*(import|export)\s*(\*|[[:alnum:]]|_|\$|,|\{|\}|\s)*\s*from\s*'(?P<path>.*)'`), // Single quotes.
	regexp.MustCompile(`^\s*(import|export)\s*(\*|[[:alnum:]]|_|\$|,|\{|\}|\s)*\s*from\s*"(?P<path>.*)"`), // Double quotes.

	// Matches multiline imports, e.g.:
	//     import {
	//       bar,
	//       baz as qux,
	//     } from 'foo';
	regexp.MustCompile(`^\s*}?\s*from\s*'(?P<path>.*)'`), // Single quotes.
	regexp.MustCompile(`^\s*}?\s*from\s*"(?P<path>.*)"`), // Double quotes.

	// Matches imports for side-effects only, e.g.:
	//     import 'foo';
	regexp.MustCompile(`^\s*import\s*'(?P<path>.*)'`), // Single quotes.
	regexp.MustCompile(`^\s*import\s*"(?P<path>.*)"`), // Double quotes.
}

// ignoredTsImportsRegexp matches import paths that should be ignored, namely CSS and Sass imports.
// Importing CSS and Sass files from TypeScript files is a Webpack idiom that both the TypeScript
// compiler and our front-end BUILD rules ignore, in favor of other mechanisms such as the
// sass_deps and sk_element_deps in various rules, and "ghost" Sass imports.
//
// See the sk_element macro definition for more, or go/skia-infra-bazel-frontend for the design.
var ignoredTsImportsRegexp = regexp.MustCompile(`\.s?css$`)

// ParseTSImports takes the contents of a TypeScript source file and extracts the verbatim paths of
// any imported modules.
func ParseTSImports(source string) []string {
	// Remove comments from the source file.
	lines := parsers.SplitLinesAndRemoveComments(source)

	// Extract all imports.
	importsSet := map[string]bool{}
	for _, line := range lines {
		for _, re := range tsImportRegexps {
			match := re.FindStringSubmatch(line)
			if len(match) != 0 {
				importPath := match[len(match)-1] // The path is the last capture group on all regexps.
				importsSet[importPath] = true
			}
		}
	}

	// Filter out ignored imports, and sort imports lexicographically.
	var imports []string
	for path := range importsSet {
		if !ignoredTsImportsRegexp.MatchString(path) {
			imports = append(imports, path)
		}
	}
	sort.Strings(imports)

	return imports
}

//////////////////////////
// Sass imports parser. //
//////////////////////////

// sassImportRegexps match the following kinds of Sass imports:
//
//     @import 'foo';
//     @use 'foo';
//     @use 'foo' as bar;
//     @use 'foo' with (
//       $bar: 1px
//     );
//     @forward 'foo';
//     @forward 'foo' as foo-*;
//     @forward 'foo' hide $bar, $baz;
//     @forward 'foo' with (
//       $bar: $1px
//     );
//
// See https://sass-lang.com/documentation/at-rules.
var sassImportRegexps = []*regexp.Regexp{
	regexp.MustCompile(`^\s*@(import|use|forward)\s*'(?P<path>[\w~_/\.\-]+)'`), // Single quotes.
	regexp.MustCompile(`^\s*@(import|use|forward)\s*"(?P<path>[\w~_/\.\-]+)"`), // Double quotes.
}

// ParseSassImports takes the contents of a Sass source file and extracts the verbatim paths of any
// imported modules.
func ParseSassImports(source string) []string {
	// Remove comments from the source file.
	lines := parsers.SplitLinesAndRemoveComments(source)

	// Extract all imports.
	importsSet := map[string]bool{}
	for _, line := range lines {
		for _, re := range sassImportRegexps {
			match := re.FindStringSubmatch(line)
			if len(match) != 0 {
				importPath := match[len(match)-1] // The path is the last capture group on all regexps.
				// Filter out plain CSS imports. See
				// https://sass-lang.com/documentation/at-rules/import#plain-css-imports.
				if strings.HasSuffix(importPath, ".css") {
					continue
				}
				importsSet[importPath] = true
			}
		}
	}

	// Sort imports lexicographically.
	var imports []string
	for path := range importsSet {
		imports = append(imports, path)
	}
	sort.Strings(imports)

	return imports
}
