Skip to content

Commit e06d384

Browse files
committedOct 22, 2023
Add Munki script check
1 parent d9ccce9 commit e06d384

File tree

3 files changed

+543
-1
lines changed

3 files changed

+543
-1
lines changed
 

‎goztl.go

+3-1
Original file line numberDiff line numberDiff line change
@@ -15,7 +15,7 @@ import (
1515
)
1616

1717
const (
18-
libraryVersion = "0.1.41"
18+
libraryVersion = "0.1.42"
1919
userAgent = "goztl/" + libraryVersion
2020
mediaType = "application/json"
2121
)
@@ -57,6 +57,7 @@ type Client struct {
5757
// Munki
5858
MunkiConfigurations MunkiConfigurationsService
5959
MunkiEnrollments MunkiEnrollmentsService
60+
MunkiScriptChecks MunkiScriptChecksService
6061
// Osquery
6162
OsqueryATC OsqueryATCService
6263
OsqueryConfigurations OsqueryConfigurationsService
@@ -176,6 +177,7 @@ func NewClient(httpClient *http.Client, bu string, token string, opts ...ClientO
176177
// Munki
177178
c.MunkiConfigurations = &MunkiConfigurationsServiceOp{client: c}
178179
c.MunkiEnrollments = &MunkiEnrollmentsServiceOp{client: c}
180+
c.MunkiScriptChecks = &MunkiScriptChecksServiceOp{client: c}
179181
// Osquery
180182
c.OsqueryATC = &OsqueryATCServiceOp{client: c}
181183
c.OsqueryConfigurations = &OsqueryConfigurationsServiceOp{client: c}

‎munki_script_checks.go

+205
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,205 @@
1+
package goztl
2+
3+
import (
4+
"context"
5+
"fmt"
6+
"net/http"
7+
)
8+
9+
const mscBasePath = "munki/script_checks/"
10+
11+
// MunkiScriptChecksService is an interface for interfacing with the Munki script checks
12+
// endpoints of the Zentral API.
13+
type MunkiScriptChecksService interface {
14+
List(context.Context, *ListOptions) ([]MunkiScriptCheck, *Response, error)
15+
GetByID(context.Context, int) (*MunkiScriptCheck, *Response, error)
16+
GetByName(context.Context, string) (*MunkiScriptCheck, *Response, error)
17+
Create(context.Context, *MunkiScriptCheckRequest) (*MunkiScriptCheck, *Response, error)
18+
Update(context.Context, int, *MunkiScriptCheckRequest) (*MunkiScriptCheck, *Response, error)
19+
Delete(context.Context, int) (*Response, error)
20+
}
21+
22+
// MunkiScriptChecksServiceOp handles communication with the Munki script checks related
23+
// methods of the Zentral API.
24+
type MunkiScriptChecksServiceOp struct {
25+
client *Client
26+
}
27+
28+
var _ MunkiScriptChecksService = &MunkiScriptChecksServiceOp{}
29+
30+
// MunkiScriptCheck represents a Zentral Munki script check.
31+
type MunkiScriptCheck struct {
32+
ID int `json:"id"`
33+
Name string `json:"name"`
34+
Description string `json:"description"`
35+
Type string `json:"type"`
36+
Source string `json:"source"`
37+
ExpectedResult string `json:"expected_result"`
38+
ArchAMD64 bool `json:"arch_amd64"`
39+
ArchARM64 bool `json:"arch_arm64"`
40+
MinOSVersion string `json:"min_os_version"`
41+
MaxOSVersion string `json:"max_os_version"`
42+
TagIDs []int `json:"tags"`
43+
Version int `json:"version"`
44+
Created Timestamp `json:"created_at"`
45+
Updated Timestamp `json:"updated_at"`
46+
}
47+
48+
// MunkiScriptCheckRequest represents a request to create or update a Munki script check.
49+
type MunkiScriptCheckRequest struct {
50+
Name string `json:"name"`
51+
Description string `json:"description"`
52+
Type string `json:"type"`
53+
Source string `json:"source"`
54+
ExpectedResult string `json:"expected_result"`
55+
ArchAMD64 bool `json:"arch_amd64"`
56+
ArchARM64 bool `json:"arch_arm64"`
57+
MinOSVersion string `json:"min_os_version"`
58+
MaxOSVersion string `json:"max_os_version"`
59+
TagIDs []int `json:"tags"`
60+
}
61+
62+
func (msc MunkiScriptCheck) String() string {
63+
return Stringify(msc)
64+
}
65+
66+
type listMunkiScriptCheckOptions struct {
67+
Name string `url:"name,omitempty"`
68+
}
69+
70+
// List lists all the Munki script checks.
71+
func (s *MunkiScriptChecksServiceOp) List(ctx context.Context, opt *ListOptions) ([]MunkiScriptCheck, *Response, error) {
72+
return s.list(ctx, opt, nil)
73+
}
74+
75+
// GetByID retrieves a Munki script check by id.
76+
func (s *MunkiScriptChecksServiceOp) GetByID(ctx context.Context, mscID int) (*MunkiScriptCheck, *Response, error) {
77+
if mscID < 1 {
78+
return nil, nil, NewArgError("mscID", "cannot be less than 1")
79+
}
80+
81+
path := fmt.Sprintf("%s%d/", mscBasePath, mscID)
82+
83+
req, err := s.client.NewRequest(ctx, http.MethodGet, path, nil)
84+
if err != nil {
85+
return nil, nil, err
86+
}
87+
88+
msc := new(MunkiScriptCheck)
89+
90+
resp, err := s.client.Do(ctx, req, msc)
91+
if err != nil {
92+
return nil, resp, err
93+
}
94+
95+
return msc, resp, err
96+
}
97+
98+
// GetByName retrieves a Munki script check by name.
99+
func (s *MunkiScriptChecksServiceOp) GetByName(ctx context.Context, name string) (*MunkiScriptCheck, *Response, error) {
100+
if len(name) < 1 {
101+
return nil, nil, NewArgError("name", "cannot be blank")
102+
}
103+
104+
listMunkiScriptCheckOpt := &listMunkiScriptCheckOptions{Name: name}
105+
106+
mscs, resp, err := s.list(ctx, nil, listMunkiScriptCheckOpt)
107+
if err != nil {
108+
return nil, resp, err
109+
}
110+
if len(mscs) < 1 {
111+
return nil, resp, nil
112+
}
113+
114+
return &mscs[0], resp, err
115+
}
116+
117+
// Create a new Munki script check.
118+
func (s *MunkiScriptChecksServiceOp) Create(ctx context.Context, createRequest *MunkiScriptCheckRequest) (*MunkiScriptCheck, *Response, error) {
119+
if createRequest == nil {
120+
return nil, nil, NewArgError("createRequest", "cannot be nil")
121+
}
122+
123+
req, err := s.client.NewRequest(ctx, http.MethodPost, mscBasePath, createRequest)
124+
if err != nil {
125+
return nil, nil, err
126+
}
127+
128+
msc := new(MunkiScriptCheck)
129+
resp, err := s.client.Do(ctx, req, msc)
130+
if err != nil {
131+
return nil, resp, err
132+
}
133+
134+
return msc, resp, err
135+
}
136+
137+
// Update a Munki script check.
138+
func (s *MunkiScriptChecksServiceOp) Update(ctx context.Context, mscID int, updateRequest *MunkiScriptCheckRequest) (*MunkiScriptCheck, *Response, error) {
139+
if mscID < 1 {
140+
return nil, nil, NewArgError("mscID", "cannot be less than 1")
141+
}
142+
143+
if updateRequest == nil {
144+
return nil, nil, NewArgError("updateRequest", "cannot be nil")
145+
}
146+
147+
path := fmt.Sprintf("%s%d/", mscBasePath, mscID)
148+
149+
req, err := s.client.NewRequest(ctx, http.MethodPut, path, updateRequest)
150+
if err != nil {
151+
return nil, nil, err
152+
}
153+
154+
msc := new(MunkiScriptCheck)
155+
resp, err := s.client.Do(ctx, req, msc)
156+
if err != nil {
157+
return nil, resp, err
158+
}
159+
160+
return msc, resp, err
161+
}
162+
163+
// Delete a Munki script check.
164+
func (s *MunkiScriptChecksServiceOp) Delete(ctx context.Context, mscID int) (*Response, error) {
165+
if mscID < 1 {
166+
return nil, NewArgError("mscID", "cannot be less than 1")
167+
}
168+
169+
path := fmt.Sprintf("%s%d/", mscBasePath, mscID)
170+
171+
req, err := s.client.NewRequest(ctx, http.MethodDelete, path, nil)
172+
if err != nil {
173+
return nil, err
174+
}
175+
176+
resp, err := s.client.Do(ctx, req, nil)
177+
178+
return resp, err
179+
}
180+
181+
// Helper method for listing Munki script checks.
182+
func (s *MunkiScriptChecksServiceOp) list(ctx context.Context, opt *ListOptions, mscOpt *listMunkiScriptCheckOptions) ([]MunkiScriptCheck, *Response, error) {
183+
path := mscBasePath
184+
path, err := addOptions(path, opt)
185+
if err != nil {
186+
return nil, nil, err
187+
}
188+
path, err = addOptions(path, mscOpt)
189+
if err != nil {
190+
return nil, nil, err
191+
}
192+
193+
req, err := s.client.NewRequest(ctx, http.MethodGet, path, nil)
194+
if err != nil {
195+
return nil, nil, err
196+
}
197+
198+
var mscs []MunkiScriptCheck
199+
resp, err := s.client.Do(ctx, req, &mscs)
200+
if err != nil {
201+
return nil, resp, err
202+
}
203+
204+
return mscs, resp, err
205+
}

‎munki_script_checks_test.go

+335
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,335 @@
1+
package goztl
2+
3+
import (
4+
"context"
5+
"encoding/json"
6+
"fmt"
7+
"net/http"
8+
"testing"
9+
10+
"github.com/google/go-cmp/cmp"
11+
"github.com/stretchr/testify/assert"
12+
)
13+
14+
var mscListJSONResponse = `
15+
[
16+
{
17+
"id": 1,
18+
"name": "Default",
19+
"description": "Description",
20+
"type": "ZTL_INT",
21+
"source": "echo 10",
22+
"expected_result": "10",
23+
"arch_amd64": false,
24+
"arch_arm64": true,
25+
"min_os_version": "14",
26+
"max_os_version": "15",
27+
"tags": [2, 3, 4],
28+
"version": 5,
29+
"created_at": "2022-07-22T01:02:03.444444",
30+
"updated_at": "2022-07-22T01:02:03.444444"
31+
}
32+
]
33+
`
34+
35+
var mscGetJSONResponse = `
36+
{
37+
"id": 1,
38+
"name": "Default",
39+
"description": "Description",
40+
"type": "ZTL_INT",
41+
"source": "echo 10",
42+
"expected_result": "10",
43+
"arch_amd64": false,
44+
"arch_arm64": true,
45+
"min_os_version": "14",
46+
"max_os_version": "15",
47+
"tags": [2, 3, 4],
48+
"version": 5,
49+
"created_at": "2022-07-22T01:02:03.444444",
50+
"updated_at": "2022-07-22T01:02:03.444444"
51+
}
52+
`
53+
54+
var mscCreateJSONResponse = `
55+
{
56+
"id": 1,
57+
"name": "Default",
58+
"description": "Description",
59+
"type": "ZTL_INT",
60+
"source": "echo 10",
61+
"expected_result": "10",
62+
"arch_amd64": false,
63+
"arch_arm64": true,
64+
"min_os_version": "14",
65+
"max_os_version": "15",
66+
"tags": [2, 3, 4],
67+
"version": 5,
68+
"created_at": "2022-07-22T01:02:03.444444",
69+
"updated_at": "2022-07-22T01:02:03.444444"
70+
}
71+
`
72+
73+
var mscUpdateJSONResponse = `
74+
{
75+
"id": 1,
76+
"name": "Default",
77+
"description": "Description",
78+
"type": "ZTL_INT",
79+
"source": "echo 10",
80+
"expected_result": "10",
81+
"arch_amd64": false,
82+
"arch_arm64": true,
83+
"min_os_version": "14",
84+
"max_os_version": "15",
85+
"tags": [2, 3, 4],
86+
"version": 5,
87+
"created_at": "2022-07-22T01:02:03.444444",
88+
"updated_at": "2022-07-22T01:02:03.444444"
89+
}
90+
`
91+
92+
func TestMunkiScriptChecksService_List(t *testing.T) {
93+
client, mux, teardown := setup()
94+
defer teardown()
95+
96+
mux.HandleFunc("/munki/script_checks/", func(w http.ResponseWriter, r *http.Request) {
97+
testMethod(t, r, "GET")
98+
testHeader(t, r, "Accept", "application/json")
99+
fmt.Fprint(w, mscListJSONResponse)
100+
})
101+
102+
ctx := context.Background()
103+
got, _, err := client.MunkiScriptChecks.List(ctx, nil)
104+
if err != nil {
105+
t.Errorf("MunkiScriptChecks.List returned error: %v", err)
106+
}
107+
108+
want := []MunkiScriptCheck{
109+
{
110+
ID: 1,
111+
Name: "Default",
112+
Description: "Description",
113+
Type: "ZTL_INT",
114+
Source: "echo 10",
115+
ExpectedResult: "10",
116+
ArchAMD64: false,
117+
ArchARM64: true,
118+
MinOSVersion: "14",
119+
MaxOSVersion: "15",
120+
TagIDs: []int{2, 3, 4},
121+
Version: 5,
122+
Created: Timestamp{referenceTime},
123+
Updated: Timestamp{referenceTime},
124+
},
125+
}
126+
if !cmp.Equal(got, want) {
127+
t.Errorf("MunkiScriptChecks.List returned %+v, want %+v", got, want)
128+
}
129+
}
130+
131+
func TestMunkiScriptChecksService_GetByID(t *testing.T) {
132+
client, mux, teardown := setup()
133+
defer teardown()
134+
135+
mux.HandleFunc("/munki/script_checks/1/", func(w http.ResponseWriter, r *http.Request) {
136+
testMethod(t, r, "GET")
137+
testHeader(t, r, "Accept", "application/json")
138+
fmt.Fprint(w, mscGetJSONResponse)
139+
})
140+
141+
ctx := context.Background()
142+
got, _, err := client.MunkiScriptChecks.GetByID(ctx, 1)
143+
if err != nil {
144+
t.Errorf("MunkiScriptChecks.GetByID returned error: %v", err)
145+
}
146+
147+
want := &MunkiScriptCheck{
148+
ID: 1,
149+
Name: "Default",
150+
Description: "Description",
151+
Type: "ZTL_INT",
152+
Source: "echo 10",
153+
ExpectedResult: "10",
154+
ArchAMD64: false,
155+
ArchARM64: true,
156+
MinOSVersion: "14",
157+
MaxOSVersion: "15",
158+
TagIDs: []int{2, 3, 4},
159+
Version: 5,
160+
Created: Timestamp{referenceTime},
161+
Updated: Timestamp{referenceTime},
162+
}
163+
if !cmp.Equal(got, want) {
164+
t.Errorf("MunkiScriptChecks.GetByID returned %+v, want %+v", got, want)
165+
}
166+
}
167+
168+
func TestMunkiScriptChecksService_GetByName(t *testing.T) {
169+
client, mux, teardown := setup()
170+
defer teardown()
171+
172+
mux.HandleFunc("/munki/script_checks/", func(w http.ResponseWriter, r *http.Request) {
173+
testMethod(t, r, "GET")
174+
testHeader(t, r, "Accept", "application/json")
175+
testQueryArg(t, r, "name", "Default")
176+
fmt.Fprint(w, mscListJSONResponse)
177+
})
178+
179+
ctx := context.Background()
180+
got, _, err := client.MunkiScriptChecks.GetByName(ctx, "Default")
181+
if err != nil {
182+
t.Errorf("MunkiScriptChecks.GetByName returned error: %v", err)
183+
}
184+
185+
want := &MunkiScriptCheck{
186+
ID: 1,
187+
Name: "Default",
188+
Description: "Description",
189+
Type: "ZTL_INT",
190+
Source: "echo 10",
191+
ExpectedResult: "10",
192+
ArchAMD64: false,
193+
ArchARM64: true,
194+
MinOSVersion: "14",
195+
MaxOSVersion: "15",
196+
TagIDs: []int{2, 3, 4},
197+
Version: 5,
198+
Created: Timestamp{referenceTime},
199+
Updated: Timestamp{referenceTime},
200+
}
201+
if !cmp.Equal(got, want) {
202+
t.Errorf("MunkiScriptChecks.GetByName returned %+v, want %+v", got, want)
203+
}
204+
}
205+
206+
func TestMunkiScriptChecksService_Create(t *testing.T) {
207+
client, mux, teardown := setup()
208+
defer teardown()
209+
210+
createRequest := &MunkiScriptCheckRequest{
211+
Name: "Default",
212+
Description: "Description",
213+
Type: "ZTL_INT",
214+
Source: "echo 10",
215+
ExpectedResult: "10",
216+
ArchAMD64: false,
217+
ArchARM64: true,
218+
MinOSVersion: "14",
219+
MaxOSVersion: "15",
220+
TagIDs: []int{2, 3, 4},
221+
}
222+
223+
mux.HandleFunc("/munki/script_checks/", func(w http.ResponseWriter, r *http.Request) {
224+
v := new(MunkiScriptCheckRequest)
225+
err := json.NewDecoder(r.Body).Decode(v)
226+
if err != nil {
227+
t.Fatal(err)
228+
}
229+
testMethod(t, r, "POST")
230+
testHeader(t, r, "Accept", "application/json")
231+
testHeader(t, r, "Content-Type", "application/json")
232+
assert.Equal(t, createRequest, v)
233+
234+
fmt.Fprint(w, mscCreateJSONResponse)
235+
})
236+
237+
ctx := context.Background()
238+
got, _, err := client.MunkiScriptChecks.Create(ctx, createRequest)
239+
if err != nil {
240+
t.Errorf("MunkiScriptChecks.Create returned error: %v", err)
241+
}
242+
243+
want := &MunkiScriptCheck{
244+
ID: 1,
245+
Name: "Default",
246+
Description: "Description",
247+
Type: "ZTL_INT",
248+
Source: "echo 10",
249+
ExpectedResult: "10",
250+
ArchAMD64: false,
251+
ArchARM64: true,
252+
MinOSVersion: "14",
253+
MaxOSVersion: "15",
254+
TagIDs: []int{2, 3, 4},
255+
Version: 5,
256+
Created: Timestamp{referenceTime},
257+
Updated: Timestamp{referenceTime},
258+
}
259+
if !cmp.Equal(got, want) {
260+
t.Errorf("MunkiScriptChecks.Create returned %+v, want %+v", got, want)
261+
}
262+
}
263+
264+
func TestMunkiScriptChecksService_Update(t *testing.T) {
265+
client, mux, teardown := setup()
266+
defer teardown()
267+
268+
updateRequest := &MunkiScriptCheckRequest{
269+
Name: "Default",
270+
Description: "Description",
271+
Type: "ZTL_INT",
272+
Source: "echo 10",
273+
ExpectedResult: "10",
274+
ArchAMD64: false,
275+
ArchARM64: true,
276+
MinOSVersion: "14",
277+
MaxOSVersion: "15",
278+
TagIDs: []int{2, 3, 4},
279+
}
280+
281+
mux.HandleFunc("/munki/script_checks/1/", func(w http.ResponseWriter, r *http.Request) {
282+
v := new(MunkiScriptCheckRequest)
283+
err := json.NewDecoder(r.Body).Decode(v)
284+
if err != nil {
285+
t.Fatal(err)
286+
}
287+
testMethod(t, r, "PUT")
288+
testHeader(t, r, "Accept", "application/json")
289+
testHeader(t, r, "Content-Type", "application/json")
290+
assert.Equal(t, updateRequest, v)
291+
fmt.Fprint(w, mscUpdateJSONResponse)
292+
})
293+
294+
ctx := context.Background()
295+
got, _, err := client.MunkiScriptChecks.Update(ctx, 1, updateRequest)
296+
if err != nil {
297+
t.Errorf("MunkiScriptChecks.Update returned error: %v", err)
298+
}
299+
300+
want := &MunkiScriptCheck{
301+
ID: 1,
302+
Name: "Default",
303+
Description: "Description",
304+
Type: "ZTL_INT",
305+
Source: "echo 10",
306+
ExpectedResult: "10",
307+
ArchAMD64: false,
308+
ArchARM64: true,
309+
MinOSVersion: "14",
310+
MaxOSVersion: "15",
311+
TagIDs: []int{2, 3, 4},
312+
Version: 5,
313+
Created: Timestamp{referenceTime},
314+
Updated: Timestamp{referenceTime},
315+
}
316+
if !cmp.Equal(got, want) {
317+
t.Errorf("MunkiScriptChecks.Update returned %+v, want %+v", got, want)
318+
}
319+
}
320+
321+
func TestMunkiScriptChecksService_Delete(t *testing.T) {
322+
client, mux, teardown := setup()
323+
defer teardown()
324+
325+
mux.HandleFunc("/munki/script_checks/1/", func(w http.ResponseWriter, r *http.Request) {
326+
testMethod(t, r, "DELETE")
327+
w.WriteHeader(http.StatusNoContent)
328+
})
329+
330+
ctx := context.Background()
331+
_, err := client.MunkiScriptChecks.Delete(ctx, 1)
332+
if err != nil {
333+
t.Errorf("MunkiScriptChecks.Delete returned error: %v", err)
334+
}
335+
}

0 commit comments

Comments
 (0)
Please sign in to comment.