Skip to content

Commit 0cb5c80

Browse files
mauromeddaColstuwjx
authored andcommitted
Projects CRUD API (#23)
Implements the Projects API Create, Read, Update and Delete functions with related tests and usage examples.
1 parent 1a9b65f commit 0cb5c80

File tree

6 files changed

+296
-4
lines changed

6 files changed

+296
-4
lines changed

ROADMAP.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,8 +12,8 @@
1212
- [ ] Support Dashboard endpoints;
1313
- [ ] Support Orgnizations endpoints;
1414
- [ ] Support Users endpoints;
15-
- [ ] Support Projects endpoints;
16-
- [ ] Support ProjectUpdates endpoints;
15+
- [x] Support Projects endpoints;
16+
- [x] Support ProjectUpdates endpoints;
1717
- [ ] Support Teams endpoints;
1818
- [ ] Support Credentials endpoints;
1919
- [ ] Support CredentialTypes endpoints;

awxtesting/mockserver/mockdata/projects.go

Lines changed: 81 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -163,4 +163,85 @@ var (
163163
"scm_update_cache_timeout": 0,
164164
"last_update_failed": false
165165
}`)
166+
// MockedUpdateProjectResponse mocked `UpdateProject` endpoint response
167+
MockedUpdateProjectResponse = []byte(`
168+
{
169+
"id": 4,
170+
"type": "project",
171+
"url": "/api/v2/projects/4/",
172+
"related": {
173+
"created_by": "/api/v2/users/1/",
174+
"modified_by": "/api/v2/users/1/",
175+
"object_roles": "/api/v2/projects/4/object_roles/",
176+
"copy": "/api/v2/projects/4/copy/",
177+
"access_list": "/api/v2/projects/4/access_list/",
178+
"schedules": "/api/v2/projects/4/schedules/",
179+
"organization": "/api/v2/organizations/1/"
180+
},
181+
"summary_fields": {
182+
"organization": {
183+
"id": 1,
184+
"name": "Default",
185+
"description": ""
186+
},
187+
"created_by": {
188+
"id": 1,
189+
"username": "admin",
190+
"first_name": "admin",
191+
"last_name": "admin"
192+
},
193+
"modified_by": {
194+
"id": 1,
195+
"username": "admin",
196+
"first_name": "admin",
197+
"last_name": "admin"
198+
},
199+
"object_roles": {
200+
"admin_role": {
201+
"id": 14,
202+
"description": "Can manage all aspects of the project",
203+
"name": "Admin"
204+
},
205+
"use_role": {
206+
"id": 16,
207+
"description": "Can manage all aspects of the project",
208+
"name": "Use"
209+
},
210+
"update_role": {
211+
"id": 17,
212+
"description": "May update project or inventory or group using the configured source update system",
213+
"name": "Update"
214+
},
215+
"read_role": {
216+
"id": 15,
217+
"description": "May view settings for the project",
218+
"name": "Read"
219+
}
220+
},
221+
"user_capabilities": {
222+
"edit": true,
223+
"start": true,
224+
"copy": true,
225+
"schedule": true,
226+
"delete": true
227+
}
228+
},
229+
"created": "2018-06-28T16:31:15.809617Z",
230+
"modified": "2018-06-28T16:31:15.923732Z",
231+
"name": "Demo Project",
232+
"description": "Test Update",
233+
"local_path": "",
234+
"scm_type": "git",
235+
"scm_url": "https://github.com/ansible/ansible-tower-samples",
236+
"scm_clean": false,
237+
"scm_delete_on_update": false,
238+
"status": "never updated",
239+
"scm_delete_on_next_update": false,
240+
"scm_update_on_launch": true,
241+
"scm_update_cache_timeout": 0,
242+
"last_update_failed": false
243+
}`)
244+
245+
// MockedDeleteProjectResponse mocked `DeleteProject` endpoint response
246+
MockedDeleteProjectResponse = []byte(`{}`)
166247
)

awxtesting/mockserver/mockserver.go

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -121,6 +121,14 @@ func (s *mockServer) ProjectsHandler(rw http.ResponseWriter, req *http.Request)
121121
result := mockdata.MockedCreateProjectResponse
122122
rw.Write(result)
123123
return
124+
case req.Method == "PATCH":
125+
result := mockdata.MockedUpdateProjectResponse
126+
rw.Write(result)
127+
return
128+
case req.Method == "DELETE":
129+
result := mockdata.MockedDeleteProjectResponse
130+
rw.Write(result)
131+
return
124132
default:
125133
result := mockdata.MockedListProjectsResponse
126134
rw.Write(result)

examples/project.md

Lines changed: 49 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@
55
> List Projects
66
77
```go
8+
package main
89
import (
910
"log"
1011
awxGo "github.com/Colstuwjx/awx-go"
@@ -23,15 +24,17 @@ func main() {
2324
}
2425
```
2526

27+
2628
> Create Project
2729
2830
```go
31+
package main
2932
import (
3033
"log"
3134
awxGo "github.com/Colstuwjx/awx-go"
3235
)
3336

34-
fun main() {
37+
func main() {
3538
awx := awxGo.NewAWX("http://awx.your_server_host.com", "your_awx_username", "your_awx_passwd", nil)
3639
result, err := awx.ProjectService.CreateProject(map[string]interface{}{
3740
"name": "TestProject",
@@ -48,4 +51,48 @@ fun main() {
4851

4952
log.Printf("Project created. Project ID: %d", result.Project.ID)
5053
}
51-
```
54+
```
55+
56+
> Update Project
57+
58+
```go
59+
package main
60+
import (
61+
"log"
62+
awxGo "github.com/Colstuwjx/awx-go"
63+
)
64+
65+
func main() {
66+
awx := awxGo.NewAWX("http://awx.your_server_host.com", "your_awx_username", "your_awx_passwd", nil)
67+
result, err := awx.ProjectService.UpdateProject(4, map[string]interface{}{
68+
"description": "Update Example",
69+
}, map[string]string{})
70+
71+
if err != nil {
72+
log.Fatalf("Update Projects err: %s", err)
73+
}
74+
75+
log.Printf("Project Updated. Project ID: %d", result.ID)
76+
}
77+
```
78+
79+
> Delete Project
80+
81+
```go
82+
package main
83+
import (
84+
"log"
85+
awxGo "github.com/Colstuwjx/awx-go"
86+
)
87+
88+
func main() {
89+
awx := awxGo.NewAWX("http://awx.your_server_host.com", "your_awx_username", "your_awx_passwd", nil)
90+
result, err := awx.ProjectService.DeleteProject(4)
91+
92+
if err != nil {
93+
log.Fatalf("Delete Projects err: %s", err)
94+
}
95+
96+
log.Printf("Project Deleted. Project ID: %d", result.ID)
97+
}
98+
```

projects.go

Lines changed: 37 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -63,3 +63,40 @@ func (p *ProjectService) CreateProject(data map[string]interface{}, params map[s
6363

6464
return result, nil
6565
}
66+
67+
// UpdateProject update an awx Project.
68+
func (p *ProjectService) UpdateProject(id int, data map[string]interface{}, params map[string]string) (*Project, error) {
69+
result := new(Project)
70+
endpoint := fmt.Sprintf("/api/v2/projects/%d", id)
71+
payload, err := json.Marshal(data)
72+
if err != nil {
73+
return nil, err
74+
}
75+
resp, err := p.client.Requester.PatchJSON(endpoint, bytes.NewReader(payload), result, nil)
76+
if err != nil {
77+
return nil, err
78+
}
79+
80+
if err := CheckResponse(resp); err != nil {
81+
return nil, err
82+
}
83+
84+
return result, nil
85+
}
86+
87+
// DeleteProject delete an awx Project.
88+
func (p *ProjectService) DeleteProject(id int) (*Project, error) {
89+
result := new(Project)
90+
endpoint := fmt.Sprintf("/api/v2/projects/%d", id)
91+
92+
resp, err := p.client.Requester.Delete(endpoint, result, nil)
93+
if err != nil {
94+
return nil, err
95+
}
96+
97+
if err := CheckResponse(resp); err != nil {
98+
return nil, err
99+
}
100+
101+
return result, nil
102+
}

projects_test.go

Lines changed: 119 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -217,3 +217,122 @@ func TestCreateProject(t *testing.T) {
217217
t.Log("CreateProject passed!")
218218
}
219219
}
220+
221+
func TestUpdateProject(t *testing.T) {
222+
var (
223+
expectUpdateProjectResponse = &Project{
224+
ID: 4,
225+
Type: "project",
226+
URL: "/api/v2/projects/4/",
227+
Related: &Related{
228+
CreatedBy: "/api/v2/users/1/",
229+
ModifiedBy: "/api/v2/users/1/",
230+
ObjectRoles: "/api/v2/projects/4/object_roles/",
231+
Copy: "/api/v2/projects/4/copy/",
232+
AccessList: "/api/v2/projects/4/access_list/",
233+
Schedules: "/api/v2/projects/4/schedules/",
234+
Organization: "/api/v2/organizations/1/",
235+
},
236+
SummaryFields: &Summary{
237+
Organization: &OrgnizationSummary{
238+
ID: 1,
239+
Name: "Default",
240+
Description: "",
241+
},
242+
CreatedBy: &ByUserSummary{
243+
ID: 1,
244+
Username: "admin",
245+
FirstName: "admin",
246+
LastName: "admin",
247+
},
248+
ModifiedBy: &ByUserSummary{
249+
ID: 1,
250+
Username: "admin",
251+
FirstName: "admin",
252+
LastName: "admin",
253+
},
254+
ObjectRoles: &ObjectRoles{
255+
AdminRole: &ApplyRole{
256+
ID: 14,
257+
Description: "Can manage all aspects of the project",
258+
Name: "Admin",
259+
},
260+
261+
UseRole: &ApplyRole{
262+
ID: 16,
263+
Description: "Can manage all aspects of the project",
264+
Name: "Use",
265+
},
266+
267+
UpdateRole: &ApplyRole{
268+
ID: 17,
269+
Description: "May update project or inventory or group using the configured source update system",
270+
Name: "Update",
271+
},
272+
273+
ReadRole: &ApplyRole{
274+
ID: 15,
275+
Description: "May view settings for the project",
276+
Name: "Read",
277+
},
278+
},
279+
280+
UserCapabilities: &UserCapabilities{
281+
Edit: true,
282+
Start: true,
283+
Copy: true,
284+
Schedule: true,
285+
Delete: true,
286+
},
287+
},
288+
Created: func() time.Time {
289+
t, _ := time.Parse(time.RFC3339, "2018-06-28T16:31:15.809617Z")
290+
return t
291+
}(),
292+
293+
Modified: func() time.Time {
294+
t, _ := time.Parse(time.RFC3339, "2018-06-28T16:31:15.923732Z")
295+
return t
296+
}(),
297+
Name: "Demo Project",
298+
Description: "Test Update",
299+
LocalPath: "",
300+
ScmType: "git",
301+
ScmURL: "https://github.com/ansible/ansible-tower-samples",
302+
ScmClean: false,
303+
ScmDeleteOnUpdate: false,
304+
Status: "never updated",
305+
ScmDeleteOnNextUpdate: false,
306+
ScmUpdateOnLaunch: true,
307+
ScmUpdateCacheTimeout: 0,
308+
LastUpdateFailed: false,
309+
}
310+
)
311+
312+
awx := NewAWX(testAwxHost, testAwxUserName, testAwxPasswd, nil)
313+
result, err := awx.ProjectService.UpdateProject(4, map[string]interface{}{
314+
"description": "Test Update",
315+
}, map[string]string{})
316+
317+
if err != nil {
318+
t.Fatalf("UpdateProject err: %s", err)
319+
} else {
320+
checkAPICallResult(t, expectUpdateProjectResponse, result)
321+
t.Log("UpdateProject passed!")
322+
}
323+
}
324+
325+
func TestDeleteProject(t *testing.T) {
326+
var (
327+
expectDeleteProjectResponse = &Project{}
328+
)
329+
awx := NewAWX(testAwxHost, testAwxUserName, testAwxPasswd, nil)
330+
result, err := awx.ProjectService.DeleteProject(4)
331+
332+
if err != nil {
333+
t.Fatalf("DeleteProject err: %s", err)
334+
} else {
335+
checkAPICallResult(t, expectDeleteProjectResponse, result)
336+
t.Log("DeleteProject passed!")
337+
}
338+
}

0 commit comments

Comments
 (0)