package tfdiags

// This "Extra" idea is something we've inherited from HCL's diagnostic model,
// and so it's primarily to expose that functionality from wrapped HCL
// diagnostics but other diagnostic types could potentially implement this
// protocol too, if needed.

// ExtraInfo tries to retrieve extra information of interface type T from
// the given diagnostic.
//
// "Extra information" is situation-specific additional contextual data which
// might allow for some special tailored reporting of particular
// diagnostics in the UI. Conventionally the extra information is provided
// as a hidden type that implements one or more interfaces which a caller
// can pass as type parameter T to retrieve a value of that type when the
// diagnostic has such an implementation.
//
// If the given diagnostic's extra value has an implementation of interface T
// then ExtraInfo returns a non-nil interface value. If there is no such
// implementation, ExtraInfo returns a nil T.
//
// Although the signature of this function does not constrain T to be an
// interface type, our convention is to only use interface types to access
// extra info in order to allow for alternative or wrapping implementations
// of the interface.
func ExtraInfo[T any](diag Diagnostic) T {
	extra := diag.ExtraInfo()
	if ret, ok := extra.(T); ok {
		return ret
	}

	// If "extra" doesn't implement T directly then we'll delegate to
	// our ExtraInfoNext helper to try iteratively unwrapping it.
	return ExtraInfoNext[T](extra)
}

// ExtraInfoNext takes a value previously returned by ExtraInfo and attempts
// to find an implementation of interface T wrapped inside of it. The return
// value meaning is the same as for ExtraInfo.
//
// This is to help with the less common situation where a particular "extra"
// value might be wrapping another value implementing the same interface,
// and so callers can peel away one layer at a time until there are no more
// nested layers.
//
// Because this function is intended for searching for _nested_ implementations
// of T, ExtraInfoNext does not consider whether value "previous" directly
// implements interface T, on the assumption that the previous call to ExtraInfo
// with the same T caused "previous" to already be that result.
func ExtraInfoNext[T any](previous interface{}) T {
	// As long as T is an interface type as documented, zero will always be
	// a nil interface value for us to return in the non-matching case.
	var zero T

	unwrapper, ok := previous.(DiagnosticExtraUnwrapper)
	// If the given value isn't unwrappable then it can't possibly have
	// any other info nested inside of it.
	if !ok {
		return zero
	}

	extra := unwrapper.UnwrapDiagnosticExtra()

	// We'll keep unwrapping until we either find the interface we're
	// looking for or we run out of layers of unwrapper.
	for {
		if ret, ok := extra.(T); ok {
			return ret
		}

		if unwrapper, ok := extra.(DiagnosticExtraUnwrapper); ok {
			extra = unwrapper.UnwrapDiagnosticExtra()
		} else {
			return zero
		}
	}
}

// DiagnosticExtraUnwrapper is an interface implemented by values in the
// Extra field of Diagnostic when they are wrapping another "Extra" value that
// was generated downstream.
//
// Diagnostic recipients which want to examine "Extra" values to sniff for
// particular types of extra data can either type-assert this interface
// directly and repeatedly unwrap until they recieve nil, or can use the
// helper function DiagnosticExtra.
//
// This interface intentionally matches hcl.DiagnosticExtraUnwrapper, so that
// wrapping extra values implemented using HCL's API will also work with the
// tfdiags API, but that non-HCL uses of this will not need to implement HCL
// just to get this interface.
type DiagnosticExtraUnwrapper interface {
	// If the reciever is wrapping another "diagnostic extra" value, returns
	// that value. Otherwise returns nil to indicate dynamically that nothing
	// is wrapped.
	//
	// The "nothing is wrapped" condition can be signalled either by this
	// method returning nil or by a type not implementing this interface at all.
	//
	// Implementers should never create unwrap "cycles" where a nested extra
	// value returns a value that was also wrapping it.
	UnwrapDiagnosticExtra() interface{}
}

// DiagnosticExtraBecauseUnknown is an interface implemented by values in
// the Extra field of Diagnostic when the diagnostic is potentially caused by
// the presence of unknown values in an expression evaluation.
//
// Just implementing this interface is not sufficient signal, though. Callers
// must also call the DiagnosticCausedByUnknown method in order to confirm
// the result, or use the package-level function DiagnosticCausedByUnknown
// as a convenient wrapper.
type DiagnosticExtraBecauseUnknown interface {
	// DiagnosticCausedByUnknown returns true if the associated diagnostic
	// was caused by the presence of unknown values during an expression
	// evaluation, or false otherwise.
	//
	// Callers might use this to tailor what contextual information they show
	// alongside an error report in the UI, to avoid potential confusion
	// caused by talking about the presence of unknown values if that was
	// immaterial to the error.
	DiagnosticCausedByUnknown() bool
}

// DiagnosticCausedByUnknown returns true if the given diagnostic has an
// indication that it was caused by the presence of unknown values during
// an expression evaluation.
//
// This is a wrapper around checking if the diagnostic's extra info implements
// interface DiagnosticExtraBecauseUnknown and then calling its method if so.
func DiagnosticCausedByUnknown(diag Diagnostic) bool {
	maybe := ExtraInfo[DiagnosticExtraBecauseUnknown](diag)
	if maybe == nil {
		return false
	}
	return maybe.DiagnosticCausedByUnknown()
}

// DiagnosticExtraBecauseSensitive is an interface implemented by values in
// the Extra field of Diagnostic when the diagnostic is potentially caused by
// the presence of sensitive values in an expression evaluation.
//
// Just implementing this interface is not sufficient signal, though. Callers
// must also call the DiagnosticCausedBySensitive method in order to confirm
// the result, or use the package-level function DiagnosticCausedBySensitive
// as a convenient wrapper.
type DiagnosticExtraBecauseSensitive interface {
	// DiagnosticCausedBySensitive returns true if the associated diagnostic
	// was caused by the presence of sensitive values during an expression
	// evaluation, or false otherwise.
	//
	// Callers might use this to tailor what contextual information they show
	// alongside an error report in the UI, to avoid potential confusion
	// caused by talking about the presence of sensitive values if that was
	// immaterial to the error.
	DiagnosticCausedBySensitive() bool
}

// DiagnosticCausedBySensitive returns true if the given diagnostic has an
// indication that it was caused by the presence of sensitive values during
// an expression evaluation.
//
// This is a wrapper around checking if the diagnostic's extra info implements
// interface DiagnosticExtraBecauseSensitive and then calling its method if so.
func DiagnosticCausedBySensitive(diag Diagnostic) bool {
	maybe := ExtraInfo[DiagnosticExtraBecauseSensitive](diag)
	if maybe == nil {
		return false
	}
	return maybe.DiagnosticCausedBySensitive()
}
