/
version.go
284 lines (251 loc) · 9.94 KB
/
version.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
package readme
import (
"encoding/json"
"fmt"
)
// VersionEndpoint is the ReadMe API URL endpoint for Version metadata.
const VersionEndpoint = "/version"
// VersionService is an interface for using the version endpoints of the ReadMe.com API.
//
// See: https://docs.readme.com/main/reference/getproject
type VersionService interface {
// Create a new version within a project.
//
// API Reference: https://docs.readme.com/main/reference/createversion
Create(prams VersionParams) (Version, *APIResponse, error)
// Delete a version.
//
// The version may be provided using either the semver identifier for the project version
// ('1.0.0') or an API ID for the version prefixed with 'id' ('id:63ac899d11c4680047ec5970').
//
// When using the semantic version identifier, use the formatted VersionClean value listed in
// the response from the GetAll() function for best results.
//
// API Reference: https://docs.readme.com/main/reference/deleteversion
Delete(version string) (bool, *APIResponse, error)
// Get a single version.
//
// The version may be provided using either the semver identifier for the project version
// ('1.0.0') or an API ID for the version prefixed with 'id' ('id:63ac899d11c4680047ec5970').
//
// When using the semantic version identifier, use the formatted VersionClean value listed in
// the response from the GetAll() function for best results.
//
// API Reference: https://docs.readme.com/main/reference/getversion
Get(version string) (Version, *APIResponse, error)
// GetAll retrieves a list of versions associated with an API key.
//
// API Reference: https://docs.readme.com/main/reference/getversions
GetAll() ([]VersionSummary, *APIResponse, error)
// Update an existing version.
//
// The version may be provided using either the semver identifier for the project version
// ('1.0.0') or an API ID for the version prefixed with 'id' ('id:63ac899d11c4680047ec5970').
//
// When using the semantic version identifier, use the formatted VersionClean value listed in
// the response from the GetAll() function for best results.
//
// API Reference: https://docs.readme.com/main/reference/updateversion
Update(version string, params VersionParams) (Version, *APIResponse, error)
// GetVersion parses a provided string to determine if it it's a semantic version identifier (1.0.0)
// or an API version identifier (id:63ac899d11c4680047ec5970). If it's an API version identifier,
// the value is compared with the results from GetAll() to return the semantic version that's used
// for API requests. If the specified version is already a semantic version string, it will be
// returned as-is.
GetVersion(version string) (string, error)
}
// VersionClient handles communication with the Project related methods of the ReadMe.com API.
type VersionClient struct {
client *Client
}
// Version represents the details of a specific version.
type Version struct {
Categories []string `json:"categories"`
Codename string `json:"codename"`
CreatedAt string `json:"createdAt"`
ForkedFrom string `json:"forked_from"`
ID string `json:"_id"`
IsBeta bool `json:"is_beta"`
IsDeprecated bool `json:"is_deprecated"`
IsHidden bool `json:"is_hidden"`
IsStable bool `json:"is_stable"`
Project string `json:"project"`
ReleaseDate string `json:"releaseDate"`
Version string `json:"version"`
VersionClean string `json:"version_clean"`
}
// VersionSummary represents the response from the ReadMe API when retrieving a list of versions
// with GetAll().
type VersionSummary struct {
Codename string `json:"codename"`
CreatedAt string `json:"createdAt"`
ForkedFrom string `json:"forked_from"`
ID string `json:"_id"`
IsBeta bool `json:"is_beta"`
IsDeprecated bool `json:"is_deprecated"`
IsHidden bool `json:"is_hidden"`
IsStable bool `json:"is_stable"`
Version string `json:"version"`
VersionClean string `json:"version_clean"`
}
// VersionParams represents the request parameters used when creating or updating a version.
type VersionParams struct {
// Codename is the dubbed name of version.
Codename string `json:"codename,omitempty"`
// From is the semantic Version to use as the base fork.
// This is *required* when creating or updating a version.
From string `json:"from"`
// IsBeta toggles whether the version is a beta release.
// API default is `false`.
IsBeta *bool `json:"is_beta"`
// IsDeprecated toggles whether the version is deprecated. Only allowed when updating.
// API default is `false`.
IsDeprecated *bool `json:"is_deprecated"`
// IsHidden toggles public accessibility.
// API default is `false`.
IsHidden *bool `json:"is_hidden"`
// IsStable toggles whether the version should be the project's main version.
// API default is `false`.
IsStable *bool `json:"is_stable"`
// Version is the number.
// This is *required* when creating or updating a version.
Version string `json:"version"`
}
// Ensure the implementation satisfies the expected interfaces.
// This is a compile-time check.
// See: https://golang.org/doc/faq#guarantee_satisfies_interface
var _ VersionService = &VersionClient{}
// GetVersion parses a provided string to determine if it it's a semantic version identifier (1.0.0)
// or an API version identifier (id:63ac899d11c4680047ec5970). If it's an API version identifier,
// the value is compared with the results from GetAll() to return the semantic version that's used
// for API requests. If the specified version is already a semantic version string, it will be
// returned as-is.
func (c VersionClient) GetVersion(version string) (string, error) {
isID, reqID := ParseID(version)
if !isID {
return version, nil
}
all, _, err := c.client.Version.GetAll()
if err != nil {
return "", fmt.Errorf("unable to get list of versions: %w", err)
}
for _, vers := range all {
if vers.ID == reqID {
return vers.Version, nil
}
}
return "", fmt.Errorf("no match for version ID %s", reqID)
}
// GetAll retrieves a list of versions associated with an API key.
//
// API Reference: https://docs.readme.com/main/reference/getversions
func (c VersionClient) GetAll() ([]VersionSummary, *APIResponse, error) {
var versions []VersionSummary
apiResponse, err := c.client.APIRequest(&APIRequest{
Method: "GET",
Endpoint: VersionEndpoint,
UseAuth: true,
OkStatusCode: []int{200},
Response: &versions,
})
return versions, apiResponse, err
}
// Get a single version.
//
// The version may be provided using either the semver identifier for the project version ('1.0.0')
// or an API ID for the version prefixed with 'id' ('id:63ac899d11c4680047ec5970').
//
// When using the semantic version identifier, use the formatted VersionClean value listed in the
// response from the GetAll() function for best results.
//
// API Reference: https://docs.readme.com/main/reference/getversion
func (c VersionClient) Get(version string) (Version, *APIResponse, error) {
version, err := c.GetVersion(version)
if err != nil {
return Version{}, nil, err
}
versionResponse := Version{}
apiResponse, err := c.client.APIRequest(&APIRequest{
Method: "GET",
Endpoint: fmt.Sprintf("%s/%s", VersionEndpoint, version),
UseAuth: true,
OkStatusCode: []int{200},
Response: &versionResponse,
})
return versionResponse, apiResponse, err
}
// Create a new version within a project.
//
// API Reference: https://docs.readme.com/main/reference/createversion
func (c VersionClient) Create(params VersionParams) (Version, *APIResponse, error) {
payload, err := json.Marshal(params)
if err != nil {
return Version{}, nil, fmt.Errorf("unable to parse request: %w", err)
}
response := Version{}
apiResponse, err := c.client.APIRequest(&APIRequest{
Method: "POST",
Endpoint: VersionEndpoint,
UseAuth: true,
Payload: payload,
Headers: []RequestHeader{{"Content-Type": "application/json"}},
OkStatusCode: []int{200},
Response: &response,
})
return response, apiResponse, err
}
// Update an existing version.
//
// The version may be provided using either the semver identifier for the project version ('1.0.0')
// or an API ID for the version prefixed with 'id' ('id:63ac899d11c4680047ec5970').
//
// When using the semantic version identifier, use the formatted VersionClean value listed in the
// response from the GetAll() function for best results.
//
// API Reference: https://docs.readme.com/main/reference/updateversion
func (c VersionClient) Update(version string, params VersionParams) (Version, *APIResponse, error) {
version, err := c.GetVersion(version)
if err != nil {
return Version{}, nil, err
}
payload, err := json.Marshal(params)
if err != nil {
return Version{}, nil, fmt.Errorf("unable to parse request: %w", err)
}
response := Version{}
apiResponse, err := c.client.APIRequest(&APIRequest{
Method: "PUT",
Endpoint: fmt.Sprintf("%s/%s", VersionEndpoint, version),
UseAuth: true,
Payload: payload,
Headers: []RequestHeader{{"Content-Type": "application/json"}},
OkStatusCode: []int{200},
Response: &response,
})
return response, apiResponse, err
}
// Delete a version.
//
// The version may be provided using either the semver identifier for the project version ('1.0.0')
// or an API ID for the version prefixed with 'id' ('id:63ac899d11c4680047ec5970').
//
// When using the semantic version identifier, use the formatted VersionClean value listed in the
// response from the GetAll() function for best results.
//
// API Reference: https://docs.readme.com/main/reference/deleteversion
func (c VersionClient) Delete(version string) (bool, *APIResponse, error) {
version, err := c.GetVersion(version)
if err != nil {
return false, nil, err
}
apiResponse, err := c.client.APIRequest(&APIRequest{
Method: "DELETE",
Endpoint: fmt.Sprintf("%s/%s", VersionEndpoint, version),
UseAuth: true,
OkStatusCode: []int{200},
})
if err != nil {
return false, apiResponse, err
}
return true, apiResponse, nil
}