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

[Security Solution] Fix Policy-License-Watcher payload #86185

Merged
merged 2 commits into from
Dec 18, 2020

Conversation

pzl
Copy link
Member

@pzl pzl commented Dec 16, 2020

Summary

License-watcher, Policy-changer service didn't adhere to the update package policy payload, which lacks an id. This strips that out. Critical bugfix for 7.11

@pzl pzl added v8.0.0 release_note:skip Skip the PR/issue when compiling release notes Feature:Endpoint Elastic Endpoint feature v7.11.0 Team:Defend Workflows “EDR Workflows” sub-team of Security Solution labels Dec 16, 2020
@pzl pzl requested review from a team as code owners December 16, 2020 20:42
@elasticmachine
Copy link
Contributor

Pinging @elastic/endpoint-app-team (Feature:Endpoint)

@@ -91,21 +91,22 @@ export class PolicyWatcher {
return;
}
response.items.forEach(async (policy) => {
const policyConfig = policy.inputs[0].config?.policy.value;
const { id, ...updatePolicy } = policy;
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think this is going to do it. The type for UpdatePackagePolicy (Fleet) does not have several of the properties defined in the PackagePolicy which we get from the list API (I'm surprised its taking in the revision - wondering if that is doing anything at all when the update occurs)

My suggestion would be to do something similar to what we do in

const { id, revision, created_by, created_at, updated_by, updated_at, ...newPolicy } = policy;

Perhaps the above method I reference should be elevated to security_solution/common/ and then re-used in both frontend and server?

_(ps. I realize now that even the method I referenced can still "leak" properties)

Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

so, yes, you're right in that there are extra properties not being stripped in order to match UpdatePackagePolicy perfectly. I don't know why typescript isn't complaining more about this.

that being said, only id is getting rejected during save. The rest are ignored.

as for destructuring further, we'd be starting a sisyphus task. Any time a field might be added to PackagePolicy, and not explicitly added to UpdatePackagePolicy, it would need to be destructured here too.

We can aid ourselves a little by combining the two places it may happen as you mention.

But I would say no, no need here. My reasoning being:

  1. This does fix the bug behavior. Everything succeeds here
  2. So doing more destructuring and cleanup would be a refactor / improvement. But not a very clean or future-proof one. This can be cleaned up, but that doesn't seem any more robust. We should actually do that robustly (perhaps explicitly creating a new UpdatePolicyPackage object, and assigning the properties explicitly. So the default is to drop extra props))

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

😄
Ok. Maybe you can get a 👍 from Fleet then? Maybe @jfsiii or @neptunian or @nchaulet ?

(a bit more - some of which I mentioned in our slack conversation)

The problem I see (and I will likely suggest changes to Fleet services if possible) is that for fleet, this is not an issue because they use the service from the API and have Schema’s in place to validate the input - so no extra properties are going to make it in. We however are using it via their service which means we have to ensure the data is valid. We're fortunate in this case in that the update service overrides the extra properties we're passing in.

Typescript types by default are not "exact" but rather if an object with x amount of properties has enough of them to full-fill the targe Type, then typescript is happy, which is the case here. Really (IMO) the types for the input arguments to the service need to be defined as Exact<> (note: this is not supported in Typescript today, but a proposal). There are ways to do this in Typescript today until the utility type lands (see here)

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think @pzl has a good point in that we'd have to maintain destructuring - however the one part that scares me is that it doesn't look like created_at or created_by are overridden, so we'd presumably be overwriting that.

the code I'm looking at:

{
...restOfPackagePolicy,
inputs,
revision: oldPackagePolicy.revision + 1,
updated_at: new Date().toISOString(),
updated_by: options?.user?.username ?? 'system',
},

Agreed with Dan's point that the types should be stricter and we should just create a new UpdatePackagePolicy object that enforces that we're only passing the expected fields

@kevinlog
Copy link
Contributor

kevinlog commented Dec 16, 2020

I verified this locally and the update will now occur:

image

The bug looks like it's fixed!

@kevinlog
Copy link
Contributor

@pzl
I'm OK with this as long as you're confident that there isn't any surface area to update fields that we don't want to (created_*). Destructuring seems like a quick way to go about this, although you have valid points that it doesn't scale well.

Could we make the change @paul-tavares suggests and then open another ticket to make the improvements on type checking, etc?

Copy link
Member

@nchaulet nchaulet left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

we should probably add the Exact<UpdatePackagePolicy> on the fleet side in a follow up PR.

@kibanamachine
Copy link
Contributor

💚 Build Succeeded

Metrics [docs]

Distributable file count

id before after diff
default 47283 48043 +760

History

To update your PR or re-run it, just comment with:
@elasticmachine merge upstream

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Feature:Endpoint Elastic Endpoint feature release_note:skip Skip the PR/issue when compiling release notes Team:Defend Workflows “EDR Workflows” sub-team of Security Solution v7.11.0 v8.0.0
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants