// Copyright (c) 2024-2026 Celestino Amoroso (celestino.amoroso@gmail.com).
// All rights reserved.

// context-helpers.go
package kern

func CloneContext(sourceCtx ExprContext) (clonedCtx ExprContext) {
	if sourceCtx != nil {
		clonedCtx = sourceCtx.Clone()
	}
	return
}

func exportVar(ctx ExprContext, name string, value any) {
	if name[0] == '@' {
		name = name[1:]
	}
	ctx.UnsafeSetVar(name, value)
}

func exportFunc(ctx ExprContext, name string, info ExprFunc) {
	if name[0] == '@' {
		name = name[1:]
	}
	ctx.RegisterFunc(name, info.Functor(), info.ReturnType(), info.Params())
}

func ExportObjects(destCtx, sourceCtx ExprContext) {
	exportAll := CtrlIsEnabled(sourceCtx, ControlExportAll)
	// fmt.Printf("Exporting from sourceCtx [%p] to destCtx [%p] -- exportAll=%t\n", sourceCtx, destCtx, exportAll)
	// Export variables
	for _, refName := range sourceCtx.EnumVars(func(name string) bool { return (exportAll || name[0] == '@') && !(name[0] == '_') }) {
		// fmt.Printf("\tExporting %q\n", refName)
		refValue, _ := sourceCtx.GetVar(refName)
		exportVar(destCtx, refName, refValue)
	}
	// Export functions
	for _, refName := range sourceCtx.EnumFuncs(func(name string) bool { return exportAll || name[0] == '@' }) {
		if info, _ := sourceCtx.GetFuncInfo(refName); info != nil {
			exportFunc(destCtx, refName, info)
		}
	}
}

func exportObjectsToParent(sourceCtx ExprContext) {
	if parentCtx := sourceCtx.GetParent(); parentCtx != nil {
		ExportObjects(parentCtx, sourceCtx)
	}
}
