Team policy endpoint now accepts null to unset a script or software installer (#24658)

https://github.com/fleetdm/fleet/issues/23490

# Checklist for submitter

- [x] Changes file added for user-visible changes in `changes/`,
`orbit/changes/` or `ee/fleetd-chrome/changes`.
See [Changes
files](https://github.com/fleetdm/fleet/blob/main/docs/Contributing/Committing-Changes.md#changes-files)
for more information.
- [x] Added/updated tests
- [x] Manual QA for all new/changed functionality

---------

Co-authored-by: Ian Littman <iansltx@gmail.com>
This commit is contained in:
Konstantin Sykulev
2024-12-12 13:33:19 -06:00
committed by GitHub
co-authored by Ian Littman
parent d45403f1ca
commit 669e944f50
6 changed files with 118 additions and 69 deletions
@@ -0,0 +1 @@
* Allowed team policy endpoint (`PATCH /api/latest/fleet/teams/{team_id}/policies/{policy_id}`) to receive explicit `null` as a value for `script_id` or `software_title_id` to unset a script or software installer respectively.
@@ -560,9 +560,9 @@ const ManagePolicyPage = ({
responses.concat(
changedPolicies.map((changedPolicy) => {
return teamPoliciesAPI.update(changedPolicy.id, {
// "software_title_id": 0 will unset software install for the policy
// "software_title_id": null will unset software install for the policy
// "software_title_id": X will set the value to the given integer (except 0).
software_title_id: changedPolicy.swIdToInstall || 0,
software_title_id: changedPolicy.swIdToInstall || null,
team_id: teamIdForApi,
});
})
@@ -613,9 +613,9 @@ const ManagePolicyPage = ({
responses.concat(
changedPolicies.map((changedPolicy) => {
return teamPoliciesAPI.update(changedPolicy.id, {
// "script_id": 0 will unset running a script for the policy (a script never has ID 0)
// "script_id": null will unset running a script for the policy
// "script_id": X will sets script X to run when the policy fails
script_id: changedPolicy.scriptIdToRun || 0,
script_id: changedPolicy.scriptIdToRun || null,
team_id: teamIdForApi,
});
})
+4 -2
View File
@@ -4,6 +4,8 @@ import (
"errors"
"strings"
"time"
"github.com/fleetdm/fleet/v4/pkg/optjson"
)
// PolicyPayload holds data for policy creation.
@@ -162,12 +164,12 @@ type ModifyPolicyPayload struct {
// Value 0 will unset the current installer from the policy.
//
// Only applies to team policies.
SoftwareTitleID *uint `json:"software_title_id" premium:"true"`
SoftwareTitleID optjson.Any[uint] `json:"software_title_id" premium:"true"`
// ScriptID is the ID of the script that will be executed if the policy fails.
// Value 0 will unset the current script from the policy.
//
// Only applies to team policies.
ScriptID *uint `json:"script_id" premium:"true"`
ScriptID optjson.Any[uint] `json:"script_id" premium:"true"`
}
// Verify verifies the policy payload is valid.
+41 -35
View File
@@ -2404,16 +2404,18 @@ func (s *integrationTestSuite) TestGlobalPoliciesProprietary() {
assert.Equal(t, "admin1@example.com", gpResp.Policy.AuthorEmail)
assert.Equal(t, "darwin", gpResp.Policy.Platform)
mgpParams := modifyGlobalPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
Name: ptr.String("TestQuery4"),
Query: ptr.String("select * from osquery_info;"),
Description: ptr.String("Some description updated"),
Resolution: ptr.String("some global resolution updated"),
},
}
mgpResp := modifyGlobalPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/policies/%d", gpResp.Policy.ID), mgpParams, http.StatusOK, &mgpResp)
response := s.DoRaw("PATCH", fmt.Sprintf("/api/latest/fleet/policies/%d", gpResp.Policy.ID), []byte(`{
"name": "TestQuery4",
"query": "select * from osquery_info;",
"description": "Some description updated",
"resolution": "some global resolution updated"
}`), http.StatusOK)
var mgpResp modifyGlobalPolicyResponse
responseBody, err := io.ReadAll(response.Body)
require.NoError(t, err)
err = json.Unmarshal(responseBody, &mgpResp)
require.NoError(t, err)
require.NotNil(t, gpResp.Policy)
assert.Equal(t, "TestQuery4", mgpResp.Policy.Name)
assert.Equal(t, "select * from osquery_info;", mgpResp.Policy.Query)
@@ -2473,13 +2475,14 @@ func (s *integrationTestSuite) TestGlobalPoliciesProprietary() {
s.DoJSON("GET", listHostsURL, nil, http.StatusOK, &listHostsResp)
require.Len(t, listHostsResp.Hosts, 1)
mgpParams = modifyGlobalPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
Query: ptr.String("select * from users;"),
},
}
mgpResp = modifyGlobalPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/policies/%d", gpResp.Policy.ID), mgpParams, http.StatusOK, &mgpResp)
response = s.DoRaw("PATCH", fmt.Sprintf("/api/latest/fleet/policies/%d", gpResp.Policy.ID), []byte(`{
"query": "select * from users;"
}`), http.StatusOK)
responseBody, err = io.ReadAll(response.Body)
require.NoError(t, err)
err = json.Unmarshal(responseBody, &mgpResp)
require.NoError(t, err)
require.NotNil(t, gpResp.Policy)
assert.Equal(t, "TestQuery4", mgpResp.Policy.Name)
assert.Equal(t, "select * from users;", mgpResp.Policy.Query)
@@ -2538,13 +2541,14 @@ func (s *integrationTestSuite) TestGlobalPoliciesProprietary() {
require.Len(t, listHostsResp.Hosts, 1)
// Modify the platform for the policy, which should clear the policy stats
mgpParams = modifyGlobalPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
Platform: ptr.String("linux"),
},
}
mgpResp = modifyGlobalPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/policies/%d", gpResp.Policy.ID), mgpParams, http.StatusOK, &mgpResp)
response = s.DoRaw("PATCH", fmt.Sprintf("/api/latest/fleet/policies/%d", gpResp.Policy.ID), []byte(`{
"platform": "linux"
}`), http.StatusOK)
responseBody, err = io.ReadAll(response.Body)
require.NoError(t, err)
err = json.Unmarshal(responseBody, &mgpResp)
require.NoError(t, err)
require.NotNil(t, gpResp.Policy)
assert.Equal(t, "TestQuery4", mgpResp.Policy.Name)
assert.Equal(t, "select * from users;", mgpResp.Policy.Query)
@@ -2630,16 +2634,19 @@ func (s *integrationTestSuite) TestTeamPoliciesProprietary() {
assert.Equal(t, "admin1@example.com", tpResp.Policy.AuthorEmail)
tpNameNew := "TestPolicy4"
mtpParams := modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
Name: ptr.String(tpNameNew),
Query: ptr.String("select * from osquery_info;"),
Description: ptr.String("Some description updated"),
Resolution: ptr.String("some team resolution updated"),
},
}
mtpResp := modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, tpResp.Policy.ID), mtpParams, http.StatusOK, &mtpResp)
response := s.DoRaw("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, tpResp.Policy.ID), []byte(fmt.Sprintf(`{
"name": "%s",
"query": "select * from osquery_info;",
"description": "Some description updated",
"resolution": "some team resolution updated"
}`, tpNameNew)), http.StatusOK)
var mtpResp modifyGlobalPolicyResponse
responseBody, err := io.ReadAll(response.Body)
require.NoError(t, err)
err = json.Unmarshal(responseBody, &mtpResp)
require.NoError(t, err)
require.NotNil(t, mtpResp.Policy)
assert.Equal(t, tpNameNew, mtpResp.Policy.Name)
assert.Equal(t, "select * from osquery_info;", mtpResp.Policy.Query)
@@ -12663,5 +12670,4 @@ func (s *integrationTestSuite) TestSecretVariables() {
require.NoError(t, err)
require.Len(t, secrets, 1)
assert.Equal(t, "value", secrets[0].Value)
}
+62 -22
View File
@@ -11696,14 +11696,14 @@ func (s *integrationEnterpriseTestSuite) TestBatchSetSoftwareInstallersWithPolic
mtplr := modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: &rubyDebTitleID,
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: rubyDebTitleID},
},
}, http.StatusOK, &mtplr)
// Associate ruby.deb in team2 to policy2Team2.
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team2.ID, policy2Team2.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: &rubyDebTitleID,
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: rubyDebTitleID},
},
}, http.StatusOK, &mtplr)
@@ -14211,28 +14211,28 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsSoftwareInstallers
mtplr := modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: ptr.Uint(999_999),
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: 999_999},
},
}, http.StatusBadRequest, &mtplr)
// Attempt to associate to a software title without associated installer.
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: ptr.Uint(foobarAppTitleID),
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: foobarAppTitleID},
},
}, http.StatusBadRequest, &mtplr)
// Attempt to associate vppApp to policy1Team1 which should fail because we only allow associating software installers.
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: &vppAppTitleID,
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: vppAppTitleID},
},
}, http.StatusBadRequest, &mtplr)
// Associate dummy_installer.pkg to policy1Team1.
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: &dummyInstallerPkgTitleID,
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: dummyInstallerPkgTitleID},
},
}, http.StatusOK, &mtplr)
// Change name only (to test not setting a software_title_id).
@@ -14249,13 +14249,33 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsSoftwareInstallers
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: ptr.Uint(0),
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: 0},
},
}, http.StatusOK, &mtplr)
policy1Team1, err = s.ds.Policy(ctx, policy1Team1.ID)
require.NoError(t, err)
require.Nil(t, policy1Team1.SoftwareInstallerID)
// re-add software installer to policy1Team1
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: dummyInstallerPkgTitleID},
},
}, http.StatusOK, &mtplr)
policy1Team1, err = s.ds.Policy(ctx, policy1Team1.ID)
require.NoError(t, err)
require.NotNil(t, policy1Team1.SoftwareInstallerID)
require.Equal(t, dummyInstallerPkgInstallerID, *policy1Team1.SoftwareInstallerID)
// Set to null to disable
mtplr = modifyTeamPolicyResponse{}
s.DoRaw("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), []byte(`{
"software_title_id": null
}`), http.StatusOK)
policy1Team1, err = s.ds.Policy(ctx, policy1Team1.ID)
require.NoError(t, err)
require.Nil(t, policy1Team1.SoftwareInstallerID)
host1LastInstall, err := s.ds.GetHostLastInstallData(ctx, host1Team1.ID, dummyInstallerPkgInstallerID)
require.NoError(t, err)
require.Nil(t, host1LastInstall)
@@ -14288,7 +14308,7 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsSoftwareInstallers
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: &dummyInstallerPkgTitleID,
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: dummyInstallerPkgTitleID},
},
}, http.StatusOK, &mtplr)
policy1Team1, err = s.ds.Policy(ctx, policy1Team1.ID)
@@ -14337,7 +14357,7 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsSoftwareInstallers
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: &rubyDebTitleID,
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: rubyDebTitleID},
},
}, http.StatusOK, &mtplr)
@@ -14363,7 +14383,7 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsSoftwareInstallers
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: &dummyInstallerPkgTitleID,
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: dummyInstallerPkgTitleID},
},
}, http.StatusOK, &mtplr)
@@ -14371,7 +14391,7 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsSoftwareInstallers
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy2Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: &rubyDebTitleID,
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: rubyDebTitleID},
},
}, http.StatusOK, &mtplr)
@@ -14473,7 +14493,7 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsSoftwareInstallers
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team2.ID, policy4Team2.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: &fleetOsqueryMSITitleID,
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: fleetOsqueryMSITitleID},
},
}, http.StatusOK, &mtplr)
@@ -14533,7 +14553,7 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsSoftwareInstallers
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team2.ID, policy4Team2.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
SoftwareTitleID: ptr.Uint(0),
SoftwareTitleID: optjson.Any[uint]{Set: true, Valid: true, Value: 0},
},
}, http.StatusOK, &mtplr)
@@ -14774,14 +14794,14 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsScripts() {
mtplr := modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
ScriptID: ptr.Uint(999_999),
ScriptID: optjson.Any[uint]{Set: true, Valid: true, Value: 999_999},
},
}, http.StatusBadRequest, &mtplr)
// Associate first script to policy1Team1.
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
ScriptID: &script.ID,
ScriptID: optjson.Any[uint]{Set: true, Valid: true, Value: script.ID},
},
}, http.StatusOK, &mtplr)
// Change name only (to test not setting a script_id).
@@ -14798,13 +14818,33 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsScripts() {
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
ScriptID: ptr.Uint(0),
ScriptID: optjson.Any[uint]{Set: true, Valid: true, Value: 0},
},
}, http.StatusOK, &mtplr)
policy1Team1, err = s.ds.Policy(ctx, policy1Team1.ID)
require.NoError(t, err)
require.Nil(t, policy1Team1.ScriptID)
// re-add script to policy1Team1.
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
ScriptID: optjson.Any[uint]{Set: true, Valid: true, Value: script.ID},
},
}, http.StatusOK, &mtplr)
policy1Team1, err = s.ds.Policy(ctx, policy1Team1.ID)
require.NoError(t, err)
require.NotNil(t, policy1Team1.ScriptID)
require.Equal(t, script.ID, *policy1Team1.ScriptID)
// set to null to disable
mtplr = modifyTeamPolicyResponse{}
s.DoRaw("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), []byte(`{
"script_id": null
}`), http.StatusOK)
policy1Team1, err = s.ds.Policy(ctx, policy1Team1.ID)
require.NoError(t, err)
require.Nil(t, policy1Team1.ScriptID)
// Add some results and stats that should be cleared after updating the script
distributedResp := submitDistributedQueryResultsResponse{}
s.DoJSONWithoutAuth("POST", "/api/osquery/distributed/write", genDistributedReqWithPolicyResults(
@@ -14833,7 +14873,7 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsScripts() {
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
ScriptID: &script.ID,
ScriptID: optjson.Any[uint]{Set: true, Valid: true, Value: script.ID},
},
}, http.StatusOK, &mtplr)
policy1Team1, err = s.ds.Policy(ctx, policy1Team1.ID)
@@ -14881,7 +14921,7 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsScripts() {
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
ScriptID: &winScript.ID,
ScriptID: optjson.Any[uint]{Set: true, Valid: true, Value: winScript.ID},
},
}, http.StatusOK, &mtplr)
@@ -14907,7 +14947,7 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsScripts() {
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy1Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
ScriptID: &script.ID,
ScriptID: optjson.Any[uint]{Set: true, Valid: true, Value: script.ID},
},
}, http.StatusOK, &mtplr)
@@ -14915,7 +14955,7 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsScripts() {
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team1.ID, policy2Team1.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
ScriptID: &winScript.ID,
ScriptID: optjson.Any[uint]{Set: true, Valid: true, Value: winScript.ID},
},
}, http.StatusOK, &mtplr)
@@ -15002,7 +15042,7 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsScripts() {
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team2.ID, policy4Team2.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
ScriptID: &psScript.ID,
ScriptID: optjson.Any[uint]{Set: true, Valid: true, Value: psScript.ID},
},
}, http.StatusOK, &mtplr)
@@ -15024,7 +15064,7 @@ func (s *integrationEnterpriseTestSuite) TestPolicyAutomationsScripts() {
mtplr = modifyTeamPolicyResponse{}
s.DoJSON("PATCH", fmt.Sprintf("/api/latest/fleet/teams/%d/policies/%d", team2.ID, policy4Team2.ID), modifyTeamPolicyRequest{
ModifyPolicyPayload: fleet.ModifyPolicyPayload{
ScriptID: ptr.Uint(0),
ScriptID: optjson.Any[uint]{Set: true, Valid: true, Value: 0},
},
}, http.StatusOK, &mtplr)
+6 -6
View File
@@ -515,8 +515,8 @@ func (svc *Service) modifyPolicy(ctx context.Context, teamID *uint, id uint, p f
policy.FailingHostCount = 0
policy.PassingHostCount = 0
}
if p.SoftwareTitleID != nil {
softwareInstallerID, err := svc.deduceSoftwareInstallerIDFromTitleID(ctx, teamID, p.SoftwareTitleID)
if p.SoftwareTitleID.Set {
softwareInstallerID, err := svc.deduceSoftwareInstallerIDFromTitleID(ctx, teamID, &p.SoftwareTitleID.Value)
if err != nil {
return nil, err
}
@@ -529,19 +529,19 @@ func (svc *Service) modifyPolicy(ctx context.Context, teamID *uint, id uint, p f
}
policy.SoftwareInstallerID = softwareInstallerID
}
if p.ScriptID != nil { // indicates that script ID is changing, but might be to 0 to remove
if p.ScriptID.Set { // indicates that script ID is changing, but might be to 0 to remove
// If the associated script is changed (or it's set and the policy didn't have an associated script)
// then we clear the results of the policy so that automation can be triggered upon failure
// (automation is currently triggered on the first failure or when it goes from passing to failure).
if *p.ScriptID != 0 && (policy.ScriptID == nil || *policy.ScriptID != *p.ScriptID) {
if p.ScriptID.Value != 0 && (policy.ScriptID == nil || *policy.ScriptID != p.ScriptID.Value) {
removeAllMemberships = true
removeStats = true
}
if *p.ScriptID == 0 {
if p.ScriptID.Value == 0 {
policy.ScriptID = nil
} else {
policy.ScriptID = p.ScriptID
policy.ScriptID = &p.ScriptID.Value
}
}