Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

apis.errs.Also does not propagate error level #2514

Open
lbernick opened this issue May 4, 2022 · 8 comments
Open

apis.errs.Also does not propagate error level #2514

lbernick opened this issue May 4, 2022 · 8 comments
Assignees
Labels
area/API kind/bug Categorizes issue or PR as related to a bug. lifecycle/frozen Indicates that an issue or PR should not be auto-closed due to staleness.

Comments

@lbernick
Copy link

lbernick commented May 4, 2022

/area API
/kind bug

Steps to Reproduce the Problem

Using "warning" level error introduced in #2498:

func TestFoo(t *testing.T) {
	var errs *apis.FieldError
	errs = errs.Also(apis.FieldError("foo").At(apis.WarningLevel))
	if errs.Level != apis.WarningLevel {
		t.Errorf("Expected an error at warning level but got level %s", errs.Level)
	}
}

Expected Behavior

The aggregated error has the level that is the highest level of any errors combined with Also.
In the example above, I would expect errs.Level to be Warning, and errs.Filter(apis.WarningLevel).Level to also be Warning.

Actual Behavior

In the example above, errs.Level and errs.Filter(apis.WarningLevel).Level are both Error. (i.e. an error at level "warning" aggregated with no error turns into an error at level "error")

@mattmoor

@knative-prow knative-prow bot added area/API kind/bug Categorizes issue or PR as related to a bug. labels May 4, 2022
@mattmoor
Copy link
Member

mattmoor commented May 5, 2022

Thanks for opening this 🙏

cc @dprotaso @evankanderson @vaikas @n3wscott

To reiterate some of the thread in Tekton, this is sort of a reflection of the awkward conflation of apis.FieldError as both an error and an aggregation of errors (via .Also())

In your example, errs.Message won't match the single error it contains either, so I think the breakdown here is more general than the new Level field. I wonder if for aggregated errors we should set Level to reflect the constituents and perhaps add a Mixed level when multiple levels are present? This would at least make the cases @lbernick describes a bit more intuitive. I'd guess it would avoid back-compat problems since nothing is really using anything but error yet, so nothing should get a mixed level with .Also.

What do folks think?

@vaikas
Copy link
Contributor

vaikas commented May 5, 2022

@mattmoor you have a link to Tekton thread handy since it seems to have more context?

@mattmoor
Copy link
Member

mattmoor commented May 5, 2022

@evankanderson
Copy link
Member

I'd expect the "lowest" level when aggregating via Also (since ErrorLevel is 0 and counts upward), but otherwise I agree with the diagnosis.

Given that this code is unlikely to be in a tight loop, I wonder if looping over the set of contained errors to determine the correct collection-level would be correct. You could early-exit the loop if ErrorLevel is encountered, since that's the lowest level. If we imagine a Suggestion level that's less severe than Warning:

Err1 Err2 Alsoed (symmetrical)
error error error
error warning error
error suggestion error
warning warning warning
warning suggestion warning
suggestion suggestion suggestion

The worst case performance would be constructing a long chain of Warning level errors, where you'd end up scanning O(n^2) errors as you add one to the head of the chain, but this is probably acceptable (and maybe we'd cache things so it's actually O(n), I haven't thought too deeply).

@github-actions
Copy link
Contributor

github-actions bot commented Aug 4, 2022

This issue is stale because it has been open for 90 days with no
activity. It will automatically close after 30 more days of
inactivity. Reopen the issue with /reopen. Mark the issue as
fresh by adding the comment /remove-lifecycle stale.

@github-actions github-actions bot added the lifecycle/stale Denotes an issue or PR has remained open with no activity and has become stale. label Aug 4, 2022
@dprotaso
Copy link
Member

dprotaso commented Aug 5, 2022

/lifecycle frozen

@knative-prow knative-prow bot added lifecycle/frozen Indicates that an issue or PR should not be auto-closed due to staleness. and removed lifecycle/stale Denotes an issue or PR has remained open with no activity and has become stale. labels Aug 5, 2022
@JeromeJu
Copy link

Thanks @evankanderson for the table of the combinations of errs incurred.

I would like to confirm my understanding on the O(n) solution, would that need to introduce a hash-table in a (possible cyclic?) graph?

@evankanderson
Copy link
Member

You shouldn't need a hash table for caching, as you only need to track the "head" of the chain as long as the cache is correct. Using .Also() in any sort of correct issue should produce a tree, not an arbitrary graph.

If you want, you could use the go benchmark library to compare approaches if you want to learn that...

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
area/API kind/bug Categorizes issue or PR as related to a bug. lifecycle/frozen Indicates that an issue or PR should not be auto-closed due to staleness.
Projects
None yet
Development

No branches or pull requests

6 participants