Skip to content

Commit 28c40be

Browse files
#665 - [Feature Request] Get PGP keys in user API
1 parent 750213b commit 28c40be

File tree

3 files changed

+214
-5
lines changed

3 files changed

+214
-5
lines changed

src/main/java/org/gitlab4j/api/UserApi.java

Lines changed: 83 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -14,6 +14,7 @@
1414
import org.gitlab4j.api.GitLabApi.ApiVersion;
1515
import org.gitlab4j.api.models.CustomAttribute;
1616
import org.gitlab4j.api.models.Email;
17+
import org.gitlab4j.api.models.GpgKey;
1718
import org.gitlab4j.api.models.ImpersonationToken;
1819
import org.gitlab4j.api.models.ImpersonationToken.Scope;
1920
import org.gitlab4j.api.models.SshKey;
@@ -522,7 +523,7 @@ public User createUser(User user, CharSequence password, Integer projectsLimit)
522523
* Either password or resetPassword should be specified (resetPassword takes priority).</p>
523524
*
524525
* <pre><code>GitLab Endpoint: POST /users</code></pre>
525-
*
526+
*
526527
* <p>The following properties of the provided User instance can be set during creation:<pre><code> email (required) - Email
527528
* username (required) - Username
528529
* name (required) - Name
@@ -1211,4 +1212,85 @@ public void deleteEmail(final Long emailId) throws GitLabApiException {
12111212
public void deleteEmail(final Object userIdOrUsername, final Long emailId) throws GitLabApiException {
12121213
delete(Response.Status.NO_CONTENT, null, "users", getUserIdOrUsername(userIdOrUsername), "emails", emailId);
12131214
}
1215+
1216+
/**
1217+
* Get all GPG keys for the current user.
1218+
*
1219+
* <pre><code>GitLab Endpoint: GET /user/gpg_keys</code></pre>
1220+
*
1221+
* @throws GitLabApiException if any exception occurs
1222+
*/
1223+
public List<GpgKey> listGpgKeys() throws GitLabApiException {
1224+
Response response = get(Response.Status.OK, null, "user", "gpg_keys");
1225+
return (response.readEntity(new GenericType<List<GpgKey>>() {}));
1226+
}
1227+
1228+
/**
1229+
* Add a GPG key for the current user
1230+
*
1231+
* <pre><code>GitLab Endpoint: POST /user/gpg_keys</code></pre>
1232+
*
1233+
* @param key the ASCII-armored exported public GPG key to add
1234+
* @throws GitLabApiException if any exception occurs
1235+
*/
1236+
public GpgKey addGpgKey(final String key) throws GitLabApiException {
1237+
GitLabApiForm formData = new GitLabApiForm()
1238+
.withParam("key", key, true);
1239+
Response response = post(Response.Status.CREATED, formData, "user", "gpg_keys");
1240+
return (response.readEntity(GpgKey.class));
1241+
}
1242+
1243+
/**
1244+
* Remove a specific GPG key for the current user
1245+
*
1246+
* <pre><code>GitLab Endpoint: DELETE /user/gpg_keys/:keyId</code></pre>
1247+
*
1248+
* @param keyId the key ID in the form if an Integer(ID)
1249+
* @throws GitLabApiException if any exception occurs
1250+
*/
1251+
public void deleteGpgKey(final Integer keyId) throws GitLabApiException {
1252+
delete(Response.Status.NO_CONTENT, null, "user", "gpg_keys", keyId);
1253+
}
1254+
1255+
/**
1256+
* Get all GPG keys for a given user.
1257+
*
1258+
* <pre><code>GitLab Endpoint: GET /users/:id/gpg_keys</code></pre>
1259+
*
1260+
* @param userId the user in the form of an Integer(ID)
1261+
* @throws GitLabApiException if any exception occurs
1262+
*/
1263+
public List<GpgKey> listGpgKeys(final Integer userId) throws GitLabApiException {
1264+
Response response = get(Response.Status.OK, null, "users", userId, "gpg_keys");
1265+
return (response.readEntity(new GenericType<List<GpgKey>>() {}));
1266+
}
1267+
1268+
/**
1269+
* Add a GPG key for a specific user
1270+
*
1271+
* <pre><code>GitLab Endpoint: POST /users/:id/gpg_keys</code></pre>
1272+
*
1273+
* @param userId the user in the form of an Integer(ID)
1274+
* @param key the ASCII-armored exported public GPG key to add
1275+
* @throws GitLabApiException if any exception occurs
1276+
*/
1277+
public GpgKey addGpgKey(final Integer userId, final String key) throws GitLabApiException {
1278+
GitLabApiForm formData = new GitLabApiForm()
1279+
.withParam("key", key, true);
1280+
Response response = post(Response.Status.CREATED, formData, "users", userId, "gpg_keys");
1281+
return (response.readEntity(GpgKey.class));
1282+
}
1283+
1284+
/**
1285+
* Remove a specific GPG key for a specific user
1286+
*
1287+
* <pre><code>GitLab Endpoint: DELETE /users/:id/gpg_keys/:keyId</code></pre>
1288+
*
1289+
* @param userId the user in the form of an Integer(ID)
1290+
* @param keyId the key ID in the form if an Integer(ID)
1291+
* @throws GitLabApiException if any exception occurs
1292+
*/
1293+
public void deleteGpgKey(final Integer userId, final Integer keyId) throws GitLabApiException {
1294+
delete(Response.Status.NO_CONTENT, null, "users", userId, "gpg_keys", keyId);
1295+
}
12141296
}
Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
package org.gitlab4j.api.models;
2+
3+
import java.util.Date;
4+
5+
public class GpgKey {
6+
7+
private Integer id;
8+
private String key;
9+
private Date created_at;
10+
11+
public Integer getId() {
12+
return id;
13+
}
14+
15+
public void setId(Integer id) {
16+
this.id = id;
17+
}
18+
19+
public String getKey() {
20+
return key;
21+
}
22+
23+
public void setKey(String key) {
24+
this.key = key;
25+
}
26+
27+
public Date getCreated_at() {
28+
return created_at;
29+
}
30+
31+
public void setCreated_at(Date created_at) {
32+
this.created_at = created_at;
33+
}
34+
}

src/test/java/org/gitlab4j/api/TestUserApi.java

Lines changed: 97 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@
1919
import javax.ws.rs.core.Response;
2020

2121
import org.gitlab4j.api.models.Email;
22+
import org.gitlab4j.api.models.GpgKey;
2223
import org.gitlab4j.api.models.ImpersonationToken;
2324
import org.gitlab4j.api.models.ImpersonationToken.Scope;
2425
import org.gitlab4j.api.models.SshKey;
@@ -57,14 +58,66 @@ public class TestUserApi extends AbstractIntegrationTest {
5758
private static final String TEST_SUDO_AS_USERNAME = HelperUtils.getProperty(SUDO_AS_USERNAME_KEY);
5859

5960
private static final String TEST_IMPERSONATION_TOKEN_NAME = "token1";
60-
private static final String TEST_SSH_KEY =
61+
private static final String TEST_SSH_KEY =
6162
"ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAABAQC3rWzl/oPAD+Em2iGTmR81HcYZsopvnKp7jelI4XS91fT1NjCRrGsxf5Mw/" +
6263
"KnmtBjhk+kQjkhIrnsBDcs6DZWtNcHJtyWJZrYsfxMTqWCaQv+OTRwVboqS2pmPcbK3gizUd5GCLFTKbg4OMpdywTwi6NAPwQ" +
6364
"rtn3xwiVnGGCfBSyRFppcYP81otALctrlAW57V5+bQwFIJteJ+NWe1UmPxrqQ0N/a+dEEoJHzwX8RtVSkULafrRw8avn6Zp2x" +
6465
"1OlD2aIEMQWvepNTRW6UDMSmWFc61ycy1pF5sCT5rij+b/fN4qCEvQs6R7GmCzaaZzbWuAqaxLRdITm/WUxdG6rjh";
6566

6667
private static final String TEST_USER_EMAIL = "[email protected]";
6768

69+
// Key for [email protected] - set to never expire
70+
private static final String TEST_GPG_KEY = "-----BEGIN PGP PUBLIC KEY BLOCK-----\n\n" +
71+
"mQINBGBHltIBEADW8zSGAs/XEkwWI36xOusuOqSINhTDVuqq3n50Oazb+a9Ai/MM\n" +
72+
"8GTm900ZZghGBVUXGm8PkWuSmabcpbDbjYmJx8aIY71UipXxXrfBzr8S2yOx7IjU\n" +
73+
"m6AEw0HwNUF6ayBwsklUFFWMyCeCVSCeZNldFwKRQApP6YOlTlwmZFESv32J6AHz\n" +
74+
"goeEsIcoea484nVJKOl7unneb8TyuF6kmViyZtiDkjeiH5vNy8XjSWH9xl5tcBxy\n" +
75+
"70NxkZt9EKnMq8izy51OBdzA+oWByGIGRjRPrW+5niMCGltV0w12M0uMDa2pJU2B\n" +
76+
"Z0U7uL/Lj3srMnD54OjbjK++wtYbshhGKXhAzshk9RgZq5fEN7Jjn1CTvue5EcHz\n" +
77+
"D27RD4yy35MledJ0hrvcTVVxvFmTg3TfDFdQBVLHjRATdXo7xT1Wg35M3z3aVSRt\n" +
78+
"PoynOxGNSotKUGfW5bhCB9XjUNpNY7+IphLS4LuQ3vZdEs9MTTWagoOoDx5w2PRS\n" +
79+
"7VNccRsqgIbNkpPjy78wN9m1QV97ytFs57eE+FfNDkKYeeCQDeHbeBlOmoEP/vSc\n" +
80+
"plOb6K3mdJgs0d5klXTOrFRVCYHHQ84p1YyQDKZO2Qd6JtHo5FNeqvgj5JwnBdfH\n" +
81+
"NGUdnaSn6hQTd8UB0AfwB+CC7cJq/fhbgcNvfK0ErHd24tsCif8vP9AG4QARAQAB\n" +
82+
"tBtGYWtlIFBlcnNvbiA8ZmFrZUBmYWtlLmNvbT6JAk4EEwEIADgWIQSE5/Jy7XYO\n" +
83+
"8riBcF/RhpwhMYJMpwUCYEeW0gIbAwULCQgHAgYVCgkICwIEFgIDAQIeAQIXgAAK\n" +
84+
"CRDRhpwhMYJMp+ESD/99LNCF1bqg/jhQOC4UIdwzCCVkUP8imrL6NnBUso+FAwH6\n" +
85+
"AT+Pbg8JLpM0lfcjzD5PV+ekLtWTZZVsyObfdRo7GrtBt/wcLKfJU5uQmrJfRClN\n" +
86+
"mdiHbh8LyVwfhLp20JRqV6NiEWSdWwNBq8zMZGgZ6HONC7JPGokak0MKpU2Woyc3\n" +
87+
"BlAU+998mdoDPKWT8XEr8cnHFFuUpZb4oWhqNV36mFrkdBZovEbnfefA+JvcxwEs\n" +
88+
"khAeaNLmpZWZ95YSimJuL4sKUjPCXlkHs9nayTFeDdNcZPAuZwfBCLpdCSj4ErYV\n" +
89+
"MyMHs/8J7CibulJB/o8qpp07oa3Qlcd62XNpqDOEIxiWHefnaYgkyIHtmzhXH4Fa\n" +
90+
"O7Ir3zGcwARXpQfobRUmtFdzeJT3zVVdUWjkKr5rgwYZZraADXGvOo8xJ5cvdrzq\n" +
91+
"4/yvOaNNoIA4KkuZcXbnqsh31pT77PxsqK60+TpLzw/jyzTqmVTEG+6SUobW7o6D\n" +
92+
"qrpqR2RPH0GtyzKHuGKSCJClDmiLF+XSyjScGUAlQ9hcFquI6F1Vddy88yURaESK\n" +
93+
"qy2agvhSkgpRxeuglytl6ZbWp/AIXrkh3F6qJozMNMFzEokapRYsQe+QdXCDSGDQ\n" +
94+
"DNvXXfIvxrFv+vQLy4jjM+DwJfrw0eN2XZ+U3E9sP0uloiVgU1zg1wc2tyPv77kC\n" +
95+
"DQRgR5bSARAAwumSlVvzb3JORu2ezPsCh8C+VJe2nPo8m+vR1Dni58UB3xnixZnF\n" +
96+
"lPaEprnIO5TSDwELJJN3oNM+AVAPjUJYHotKny5iBSFPIbHYYHs/mGRqo4jHa4b6\n" +
97+
"riNRWJ1xoYdvzH7PKAcV36tl27Y4SuQVMYmnaSXbDkGOqd9cenqVHikhj9+SJxNr\n" +
98+
"yIHrw/SNbNbRl3cMVfke2vgRp9Eso5Ivpl6tjNoohAwDp3L6MGbHliEYQgk8pjzq\n" +
99+
"bIR4lakKNVdRQoW/ZaQM2GkDlbCIEuY/7Rr4ZA1L0tsALY+bnv+9SMtA1OnMvNQ7\n" +
100+
"7Pn2uTSHeIbSVxsRk9aWmK63l20OEcB/YPmTSeNvq0JVzJ2fLG2ZL6NUHBBF2DB4\n" +
101+
"x66FA8mu9cK3Y9Jnc/3KWdzGA74R4HSIcuDPGkZmPtDMXSgXArRuD0s71QgH5E3U\n" +
102+
"9/QJ8g4s9Mjb/8aBhbg+7lm8HzN3XANmbR+y/s71Askw/ewlbhfmwxK+/XI3xDr0\n" +
103+
"1jkf42cmoLq4/Y292mQjFkcq6cCFIxDOXM89Qopbtm6PnaQsKyz0GoiyHsP846yS\n" +
104+
"RdiHTVHrUdiLl+6TIK90cm8CzNoiF+UGvdD4HObWbySh8O8n1nno+lX9EwSoq20o\n" +
105+
"0WobXesDjNIrzJHow0WGGbx5gTxlZq0WwmgXgwYM0PbqlfjxFjct+98AEQEAAYkC\n" +
106+
"NgQYAQgAIBYhBITn8nLtdg7yuIFwX9GGnCExgkynBQJgR5bSAhsMAAoJENGGnCEx\n" +
107+
"gkynbOkQAI+N/wFxOTbewuTiy0P11saqqYr7Jwc7NLhqOVZ1tHKaTB6ZDbIrlWjN\n" +
108+
"u2tFk7PqsA4/zI6KO9JoKiQYbopZ+xjd1nCJUjkUKI/wi4rl0t7ELQKhlSlUC11f\n" +
109+
"Nz0C6Q+9cwRQCCT4sX/ZkzVQbGWx9fkAYVHzezDqh43xorXJ2ix5y63pr1NGuUgx\n" +
110+
"EujMlUbXFzXpUrCmdUVWujlp4gSEfd6tLW0WMw0tYJe6UY7xx4EmWsT+kAGj7QLH\n" +
111+
"L06yFigDQ0eUkGQ1T7Z0AjG4EXGETbX6lSLwzIBnmaZXQxdx4LiRy9TcaNtcowH4\n" +
112+
"U2yxCoG0o0kS7sS/rI77TV6WZ46DPCJmlNJ+MP8lt0j/nsDA3AECB1AA+8SNepbA\n" +
113+
"LSZY7MJmh4nsqJ+iy/XMosipluZx2u6ZwlXAHxAzHhs7FBsvdMtq/gLNAlZzVyeH\n" +
114+
"UqzRaMJps7xIbap5d5jZT5jaZwFeGi+63YVRx3Jm6dkiBCPFffLyWdrzkFTZdWqZ\n" +
115+
"PkiRbJ64wYPIWQgAN/RhmCcRBhxJE8f7kgo/nBkZ5dwmfXgnXpheEaaCSzvJ4nMh\n" +
116+
"TUdg6ZLna12QndjI5gy5aenrr5H/HmDKKSNkuWZv0+NS4GhwnL8NFs+MRk6znpLN\n" +
117+
"aEjPdfYxINCMz+uotKJV9NieDWIbEJLlfZUf2hJwuwwjQGAyVf7b\n" +
118+
"=ryCD\n" +
119+
"-----END PGP PUBLIC KEY BLOCK-----";
120+
68121
private static final String TEST_EXTERNAL_USERNAME = HelperUtils.getProperty(EXTERNAL_USERNAME_KEY);
69122
private static final String TEST_EXTERNAL_PROVIDER = HelperUtils.getProperty(EXTERNAL_PROVIDER_KEY);
70123
private static final String TEST_EXTERNAL_UID = HelperUtils.getProperty(EXTERNAL_UID_KEY);
@@ -150,7 +203,7 @@ public void testGetVersion() throws GitLabApiException {
150203
assertNotNull(version.getVersion());
151204
assertNotNull(version.getRevision());
152205
}
153-
206+
154207
@Test
155208
public void testGetCurrentUser() throws GitLabApiException {
156209
User currentUser = gitLabApi.getUserApi().getCurrentUser();
@@ -268,7 +321,7 @@ public void testCreateImpersonationToken() throws GitLabApiException, ParseExcep
268321

269322
User user = gitLabApi.getUserApi().getCurrentUser();
270323

271-
// NOTE: READ_REGISTRY scope is left out because the GitLab server docker instance does not have the
324+
// NOTE: READ_REGISTRY scope is left out because the GitLab server docker instance does not have the
272325
// registry configured and the test would thus fail.
273326
Scope[] scopes = {Scope.API, Scope.READ_USER, Scope.READ_REPOSITORY, Scope.WRITE_REPOSITORY, Scope.SUDO};
274327
Date expiresAt = ISO8601.toDate("2018-01-01T00:00:00Z");
@@ -440,11 +493,51 @@ public void testEmails() throws GitLabApiException {
440493
assertTrue(emails.size() == currentSize + 1);
441494
Email found = emails.stream().filter(e -> e.getEmail().equals(TEST_USER_EMAIL)).findAny().orElse(null);
442495
assertNotNull(found);
443-
496+
444497
gitLabApi.getUserApi().deleteEmail(currentUser, email.getId());
445498
emails = gitLabApi.getUserApi().getEmails(currentUser);
446499
assertEquals(currentSize, emails.size());
447500
found = emails.stream().filter(e -> e.getEmail().equals(TEST_USER_EMAIL)).findAny().orElse(null);
448501
assertNull(found);
449502
}
503+
504+
@Test
505+
public void testGpgKeys() throws GitLabApiException {
506+
User currentUser = gitLabApi.getUserApi().getCurrentUser();
507+
assertNotNull(currentUser);
508+
List<GpgKey> keys = gitLabApi.getUserApi().listGpgKeys(currentUser.getId());
509+
assertNotNull(keys);
510+
int currentSize = keys.size();
511+
512+
GpgKey key = gitLabApi.getUserApi().addGpgKey(currentUser.getId(), TEST_GPG_KEY);
513+
keys = gitLabApi.getUserApi().listGpgKeys(currentUser.getId());
514+
assertTrue(keys.size() == currentSize + 1);
515+
GpgKey found = keys.stream().filter(e -> e.getKey().equals(TEST_GPG_KEY)).findAny().orElse(null);
516+
assertNotNull(found);
517+
518+
gitLabApi.getUserApi().deleteGpgKey(currentUser.getId(), key.getId());
519+
keys = gitLabApi.getUserApi().listGpgKeys(currentUser.getId());
520+
assertEquals(currentSize, keys.size());
521+
found = keys.stream().filter(e -> e.getKey().equals(TEST_GPG_KEY)).findAny().orElse(null);
522+
assertNull(found);
523+
}
524+
525+
@Test
526+
public void testGpgKeysCurrentUser() throws GitLabApiException {
527+
List<GpgKey> keys = gitLabApi.getUserApi().listGpgKeys();
528+
assertNotNull(keys);
529+
int currentSize = keys.size();
530+
531+
GpgKey key = gitLabApi.getUserApi().addGpgKey(TEST_GPG_KEY);
532+
keys = gitLabApi.getUserApi().listGpgKeys();
533+
assertTrue(keys.size() == currentSize + 1);
534+
GpgKey found = keys.stream().filter(e -> e.getKey().equals(TEST_GPG_KEY)).findAny().orElse(null);
535+
assertNotNull(found);
536+
537+
gitLabApi.getUserApi().deleteGpgKey(key.getId());
538+
keys = gitLabApi.getUserApi().listGpgKeys();
539+
assertEquals(currentSize, keys.size());
540+
found = keys.stream().filter(e -> e.getKey().equals(TEST_GPG_KEY)).findAny().orElse(null);
541+
assertNull(found);
542+
}
450543
}

0 commit comments

Comments
 (0)