-
Notifications
You must be signed in to change notification settings - Fork 145
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
add OCIError to differentiate 'MUST/SHOULD' and add reference support #354
Conversation
cmd/runtimetest/main.go
Outdated
@@ -642,6 +644,12 @@ func validate(context *cli.Context) error { | |||
err := v.test(spec) | |||
t.Ok(err == nil, v.description) | |||
if err != nil { | |||
if logLevel >= logrus.ErrorLevel { | |||
// Skip 'SHOULD', 'MAY' ... |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I don't like overloading logrus.ErrorLevel
to control this, since “SHOULD violations are fatal” is not the same as “I want to see debug logging”. Can we add a setting to the Validator
structure to control this for config validation, and a command-line parameter to runtimetest
to control this for runtime validation?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, overloading logrus is a little bit tricky.
I'll use another flag like 'rfc-level'.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Maybe compliance-level
would be better than rfc-level
? There are many RFCs, and what we're interested in here is how well the tested-thing complies with the specification.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'll update with all your good suggestions tomorrow. It is a little bit late here.
validate/error.go
Outdated
Err error | ||
} | ||
|
||
const ReferencePrefix = "https://github.com/opencontainers/runtime-spec/blob/master/" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Instead of floating this with master
, we should be using the ociVersion
of the config we're checking against. This is another reason that we should only be supporting tagged spec releases.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The current version is: '-rc5-dev' and we don't have a matched release.
We can change it after v.1.0.0 release, for example: https://github.com/opencontainers/runtime-spec/blob/v1.0.0/config-linux.md
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The current version is: '-rc5-dev'…
The current runtime-spec version supported by runtime-tools' master is -rc1-dev
. If we make the adjustment I'm asking for in the in-flight #349, we can target -rc5
. I see no purpose to targeting -rc5-dev
.
The OCIError structure looks reasonable to me. I think we should use
it for MUST-level violations as well.
|
All the 'MUST-level' errors need to be filled. We can add all ErrorCode. It also helps to track #66. |
Updated: The tagged release and other 'MUST' error will be added in the following commits. PTAL @wking @mrunalp @hqhq @Mashimiao |
@@ -0,0 +1,69 @@ | |||
package validate |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How would you feel about pulling this out into its own package? I think image-spec and image-tools would also benefit from this approach to handling compliance levels?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think image-tool could use the same OCIError struct. But OCIErrorCode can not be shared between runtime-tool and image-tool. I think we can keep it here.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
But OCIErrorCode can not be shared between runtime-tool and image-tool. I think we can keep it here.
Yeah. A stand-alone module with all the tooling and a public code-> string map, and then the validating consumer populates that map (and spec URL) for whatever it's testing.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The runtime-tool and image-tool are separated, where should we have such a 'stand-alone module', "opencontainers/certification"?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The runtime-tool and image-tool are separated, where should we have such a 'stand-alone module', ...
I was thinking a separate sub-package in this repo. Or maybe in runtime-spec, since both image repos currently have some runtime-spec connections. It seems too tiny for its own repo, and opencontainers/certification seems more focused on policy than implementation.
validate/error.go
Outdated
Err error | ||
} | ||
|
||
//FIXME: change to tagged spec releases |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In order to support this future change, we probably want to include a SpecVersion
field in the OCIError
structure.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
How about add a field (not in this PR) like this :
SpecVersions []string
So each OCI Error will be associate with one or more spec versions.
In runtimetest, we can add another option:
spec-version.
So if an OCI Error does not have the wanted spec-version, we can ignore it.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So each OCI Error will be associate with one or more spec versions.
I think it's better to only test against the spec for the target version. But if we're passing around that target version so we can decide what conditions to test, there's probably no need to stash it on Error
. I'll withdraw my suggestion, and we can leave the struct fields alone.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
With #349 landed we can fix this FIXME.
validate/error.go
Outdated
) | ||
|
||
// OCIError represents an error with compliance level and OCI reference | ||
type OCIError struct { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This type is already OCI-namespaced via the package path (github.com/opencontainers/runtime-tools/validate
). I think we can just go with Error
as the struct name.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
OK
validate/error.go
Outdated
case "SHOULD": | ||
return ComplianceShould | ||
case "MUST": | ||
return ComplianceMust |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This doesn't seem quite right. RFC 2119 has the following levels:
- MUST-level (MUST, MUST NOT, REQUIRED, SHALL, SHALL NOT).
- SHOULD-level (SHOULD, SHOULD NOT, RECOMMENDED, NOT RECOMMENDED).
- MAY-level (MAY, OPTIONAL).
You've listed yours in the inverse order from the RFC (and left off NOT RECOMMENDED?), and that means that your ComplianceMustNot
is less than your ComplianceMust
, even though both should be in the MUST-level. I recommend either:
a. Reorder your constants to put ComplianceShould
at the bottom of the SHOULD-level constants and ComplianceMust
at the bottom of the MUST-level constants.
b. Add a function that maps the constants to their level (e.g. ComplianceLevel(ComplianceShallNot) → ComplianceMust
) and use that when deciding whether errors are fatal.
c. Adjust this case here to select whatever the lowest constant is for that level (e.g. "MUST" → ComplianceShall
).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
updated with solution C.
completions/bash/oci-runtime-tool
Outdated
__oci-runtime-tool_complete_compliance_level() { | ||
COMPREPLY=( $( compgen -W " | ||
must | ||
should |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Missing may
(which is documented here). Although I'm not sure what MAY-level validation looks like, and would be fine dropping it from --compliance-level
.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Lost 'may' in previous PR. We have 'MAY' in spec. In this case, we 'may' print 'MAY' information when platform.os is linux
but the linux
item is not set.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In this case, we 'may' print 'MAY' information when
platform.os
islinux
but thelinux
item is not set.
So would this be all unset OPTIONAL child properties? Or more case-by case at the runtime-tools maintainers descretion? Either was, a fatal level seems odd. If something deserves occasional fatal warnings, it should probably be SHOULD in the spec.
validate/error.go
Outdated
Err error | ||
} | ||
|
||
//FIXME: change to tagged spec releases |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
With #349 landed we can fix this FIXME.
cmd/runtimetest/main.go
Outdated
|
||
for fs, fstype := range defaultFS { | ||
if !(mountsMap[fs] == fstype) { | ||
return ociErr.NewError(ociErr.DefaultFilesystems, fmt.Sprintf("%v must exist and expected type is %v", fs, fstype)) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
“must” → “SHOULD”.
var validationErrors error | ||
for _, v := range defaultValidations { | ||
err := v.test(spec) | ||
t.Ok(err == nil, v.description) | ||
if err != nil { | ||
if e, ok := err.(*ociErr.Error); ok && e.Level < complianceLevel { | ||
continue |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We may want to print these as warnings even if they are non-fatal. With TAP, I'd recommend using diagnostics. I'm not sure what the best approach is with Go's testing framework, but we should probably figure that out ;).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I opened #362 to keep track of this.
validate/error.go
Outdated
case "REQUIRED": | ||
return ComplianceMust | ||
default: | ||
return ComplianceMust |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think the default should be to raise an “unrecognized level” error. Silently defaulting to MUST seems confusing.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
you are right. I should raise error here.
// NewError creates an Error by ErrorCode and message | ||
func NewError(code ErrorCode, msg string) error { | ||
err := ociErrors[code] | ||
err.Err = errors.New(msg) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Is this making a new Error
? It looks like it's attaching a new error
to a pre-existing Error
(possibly clobbering a previous error
). Or maybe we will only ever report one error
for a given ErrorCode
and we want that clobbering? Or maybe I'm misreading this and we are creating a new Error
;).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm creating a new Error :) So the OCIError could be used as a normal Error.
Updated by
PTAL @wking @Mashimiao @mrunalp @hqhq |
Signed-off-by: liangchenye <[email protected]>
Signed-off-by: liangchenye <[email protected]>
Signed-off-by: liangchenye <[email protected]>
63a13b3
to
ccf57b5
Compare
Signed-off-by: liangchenye <[email protected]>
rebased and fixed the glint error. PTAL @Mashimiao @hqhq @mrunalp |
@q384566678 PTAL |
@@ -30,6 +32,13 @@ const PrGetNoNewPrivs = 39 | |||
const specConfig = "config.json" | |||
|
|||
var ( | |||
defaultFS = map[string]string{ | |||
"/proc": "proc", |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
proc -> procfs
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
proc here is right, there is no procfs such type in Linux
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
https://github.com/opencontainers/runtime-spec/blame/master/config-linux.md#L15
In the spec
is defined.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
we call it procfs but the real type in Linux is proc. I will submit a PR to fix it in runtime-spec
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
fine.
1 similar comment
As discussed in [1]. This makes it easier for other projects (e.g. image-tools) to use the same tooling if they want. Some components of the old validate/error.go were runtime-spec-specific (e.g. the reference template and ociErrors), so they've stayed in the validate package. I've also expanded NewError to take an explicit version (as requested in [2]). That allows us to link to the proper spec even if we're capable of validating several spec versions (e.g. 1.0 and 1.1 configurations or runtimes). [1]: opencontainers#354 (comment) [2]: opencontainers#354 (comment) Signed-off-by: W. Trevor King <[email protected]>
As discussed in [1]. This makes it easier for other projects (e.g. image-tools) to use the same tooling if they want. Some components of the old validate/error.go were runtime-spec-specific (e.g. the reference template and ociErrors), so they've stayed in the validate package. I've also expanded NewError to take an explicit version (as requested in [2]). That allows us to link to the proper spec even if we're capable of validating several spec versions (e.g. 1.0 and 1.1 configurations or runtimes). [1]: opencontainers#354 (comment) [2]: opencontainers#354 (comment) Signed-off-by: W. Trevor King <[email protected]>
The man-page entry and Bash completions for this option were added in 4029999 (oci error: add error level and reference, 2017-03-31, opencontainers#354), but the option was left unimplemented. The implementation in this commit is very similar to the existing runtimetest implementation from 4029999, except we warn instead of silently skipping non-fatal spec violations. The warning (vs. error) on invalid level arguments follows the runtimetest implementation from 6316a4e (use released version as reference; improve Parse error, 2017-04-12, opencontainers#354). I'd personally prefer hard errors on invalid level arguments, but didn't want to break runtime-tools consistency over that. Signed-off-by: W. Trevor King <[email protected]>
this is an implementation of #353 .
PTAL
@wking @Mashimiao @mrunalp