package nextcloud

import "strings"

const ultidocSidecarSuffix = ".ultidoc.json"

// IsUltidocSidecarName reports whether name is a TipTap sidecar file.
func IsUltidocSidecarName(name string) bool {
	return strings.HasSuffix(strings.ToLower(strings.TrimSpace(name)), ultidocSidecarSuffix)
}

func documentBaseName(name string) string {
	name = strings.TrimSpace(name)
	if name == "" {
		return ""
	}
	lower := strings.ToLower(name)
	if strings.HasSuffix(lower, ultidocSidecarSuffix) {
		return name[:len(name)-len(ultidocSidecarSuffix)]
	}
	if i := strings.LastIndex(name, "."); i > 0 {
		return name[:i]
	}
	return name
}

func sidecarSourceKey(filePath string) string {
	dir := parentDirPath(filePath)
	base := strings.ToLower(documentBaseName(fileNameFromPath(filePath)))
	return dir + "\x00" + base
}

func parentDirPath(filePath string) string {
	filePath = NormalizeClientPath(filePath)
	if filePath == "/" {
		return "/"
	}
	i := strings.LastIndex(filePath, "/")
	if i <= 0 {
		return "/"
	}
	return filePath[:i]
}

func fileNameFromPath(p string) string {
	p = NormalizeClientPath(p)
	if i := strings.LastIndex(p, "/"); i >= 0 {
		return p[i+1:]
	}
	return p
}

// FilterHiddenUltidocSidecars removes .ultidoc.json sidecars when the source document
// is present in the same listing (sidecar storage mode). Orphan sidecars (overwrite mode)
// remain visible.
func FilterHiddenUltidocSidecars(files []FileInfo) []FileInfo {
	if len(files) == 0 {
		return files
	}

	sources := make(map[string]struct{}, len(files))
	for _, f := range files {
		if f.Type == "directory" || IsUltidocSidecarName(f.Name) {
			continue
		}
		sources[sidecarSourceKey(f.Path)] = struct{}{}
	}

	out := make([]FileInfo, 0, len(files))
	for _, f := range files {
		if f.Type != "directory" && IsUltidocSidecarName(f.Name) {
			if _, ok := sources[sidecarSourceKey(f.Path)]; ok {
				continue
			}
		}
		out = append(out, f)
	}
	return out
}
