Skip to content

Commit 5eaece8

Browse files
committed
EXTRA-user-update-and-tests
1 parent 9dbfb30 commit 5eaece8

File tree

4 files changed

+295
-10
lines changed

4 files changed

+295
-10
lines changed

server/src/resolvers/user.js

Lines changed: 9 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import jwt from 'jsonwebtoken';
22
import { combineResolvers } from 'graphql-resolvers';
33
import { AuthenticationError, UserInputError } from 'apollo-server';
44

5-
import { isAdmin } from './authorization';
5+
import { isAdmin, isAuthenticated } from './authorization';
66

77
const createToken = async (user, secret, expiresIn) => {
88
const { id, email, username, role } = user;
@@ -65,6 +65,14 @@ export default {
6565
return { token: createToken(user, secret, '30m') };
6666
},
6767

68+
updateUser: combineResolvers(
69+
isAuthenticated,
70+
async (parent, { username }, { models, me }) => {
71+
const user = await models.User.findById(me.id);
72+
return await user.update({ username });
73+
},
74+
),
75+
6876
deleteUser: combineResolvers(
6977
isAdmin,
7078
async (parent, { id }, { models }) => {

server/src/schema/user.js

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ export default gql`
1515
): Token!
1616
1717
signIn(login: String!, password: String!): Token!
18+
updateUser(username: String!): User!
1819
deleteUser(id: ID!): Boolean!
1920
}
2021

server/src/tests/api.js

Lines changed: 90 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,41 @@ import axios from 'axios';
22

33
const API_URL = 'http://localhost:8000/graphql';
44

5+
export const signIn = async variables =>
6+
await axios.post(API_URL, {
7+
query: `
8+
mutation ($login: String!, $password: String!) {
9+
signIn(login: $login, password: $password) {
10+
token
11+
}
12+
}
13+
`,
14+
variables,
15+
});
16+
17+
export const me = async token =>
18+
await axios.post(
19+
API_URL,
20+
{
21+
query: `
22+
{
23+
me {
24+
id
25+
email
26+
username
27+
}
28+
}
29+
`,
30+
},
31+
token
32+
? {
33+
headers: {
34+
'x-token': token,
35+
},
36+
}
37+
: null,
38+
);
39+
540
export const user = async variables =>
641
axios.post(API_URL, {
742
query: `
@@ -17,18 +52,62 @@ export const user = async variables =>
1752
variables,
1853
});
1954

20-
export const signIn = async variables =>
21-
await axios.post(API_URL, {
55+
export const users = async () =>
56+
axios.post(API_URL, {
2257
query: `
23-
mutation ($login: String!, $password: String!) {
24-
signIn(login: $login, password: $password) {
58+
{
59+
users {
60+
id
61+
username
62+
email
63+
role
64+
}
65+
}
66+
`,
67+
});
68+
69+
export const signUp = async variables =>
70+
axios.post(API_URL, {
71+
query: `
72+
mutation(
73+
$username: String!,
74+
$email: String!,
75+
$password: String!
76+
) {
77+
signUp(
78+
username: $username,
79+
email: $email,
80+
password: $password
81+
) {
2582
token
2683
}
2784
}
2885
`,
2986
variables,
3087
});
3188

89+
export const updateUser = async (variables, token) =>
90+
axios.post(
91+
API_URL,
92+
{
93+
query: `
94+
mutation ($username: String!) {
95+
updateUser(username: $username) {
96+
username
97+
}
98+
}
99+
`,
100+
variables,
101+
},
102+
token
103+
? {
104+
headers: {
105+
'x-token': token,
106+
},
107+
}
108+
: null,
109+
);
110+
32111
export const deleteUser = async (variables, token) =>
33112
axios.post(
34113
API_URL,
@@ -40,9 +119,11 @@ export const deleteUser = async (variables, token) =>
40119
`,
41120
variables,
42121
},
43-
{
44-
headers: {
45-
'x-token': token,
46-
},
47-
},
122+
token
123+
? {
124+
headers: {
125+
'x-token': token,
126+
},
127+
}
128+
: null,
48129
);

server/src/tests/user.spec.js

Lines changed: 195 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -34,6 +34,135 @@ describe('users', () => {
3434
});
3535
});
3636

37+
describe('users: [User!]', () => {
38+
it('returns a list of users', async () => {
39+
const expectedResult = {
40+
data: {
41+
users: [
42+
{
43+
id: '1',
44+
username: 'rwieruch',
45+
email: 'hello@robin.com',
46+
role: 'ADMIN',
47+
},
48+
{
49+
id: '2',
50+
username: 'ddavids',
51+
email: 'hello@david.com',
52+
role: null,
53+
},
54+
],
55+
},
56+
};
57+
58+
const result = await userApi.users();
59+
60+
expect(result.data).to.eql(expectedResult);
61+
});
62+
});
63+
64+
describe('me: User', () => {
65+
it('returns null when no user is signed in', async () => {
66+
const expectedResult = {
67+
data: {
68+
me: null,
69+
},
70+
};
71+
72+
const { data } = await userApi.me();
73+
74+
expect(data).to.eql(expectedResult);
75+
});
76+
77+
it('returns me when me is signed in', async () => {
78+
const expectedResult = {
79+
data: {
80+
me: {
81+
id: '1',
82+
username: 'rwieruch',
83+
email: 'hello@robin.com',
84+
},
85+
},
86+
};
87+
88+
const {
89+
data: {
90+
data: {
91+
signIn: { token },
92+
},
93+
},
94+
} = await userApi.signIn({
95+
login: 'rwieruch',
96+
password: 'rwieruch',
97+
});
98+
99+
const { data } = await userApi.me(token);
100+
101+
expect(data).to.eql(expectedResult);
102+
});
103+
});
104+
105+
describe('signUp, updateUser, deleteUser', () => {
106+
it('signs up a user, updates a user and deletes the user as admin', async () => {
107+
// sign up
108+
109+
let {
110+
data: {
111+
data: {
112+
signUp: { token },
113+
},
114+
},
115+
} = await userApi.signUp({
116+
username: 'Mark',
117+
email: 'mark@gmule.com',
118+
password: 'asdasdasd',
119+
});
120+
121+
const {
122+
data: {
123+
data: { me },
124+
},
125+
} = await userApi.me(token);
126+
127+
expect(me).to.eql({
128+
id: '3',
129+
username: 'Mark',
130+
email: 'mark@gmule.com',
131+
});
132+
133+
// update as user
134+
135+
const {
136+
data: {
137+
data: { updateUser },
138+
},
139+
} = await userApi.updateUser({ username: 'Mark' }, token);
140+
141+
expect(updateUser.username).to.eql('Mark');
142+
143+
// delete as admin
144+
145+
const {
146+
data: {
147+
data: {
148+
signIn: { token: adminToken },
149+
},
150+
},
151+
} = await userApi.signIn({
152+
login: 'rwieruch',
153+
password: 'rwieruch',
154+
});
155+
156+
const {
157+
data: {
158+
data: { deleteUser },
159+
},
160+
} = await userApi.deleteUser({ id: me.id }, adminToken);
161+
162+
expect(deleteUser).to.eql(true);
163+
});
164+
});
165+
37166
describe('deleteUser(id: String!): Boolean!', () => {
38167
it('returns an error because only admins can delete a user', async () => {
39168
const {
@@ -54,4 +183,70 @@ describe('users', () => {
54183
expect(errors[0].message).to.eql('Not authorized as admin.');
55184
});
56185
});
186+
187+
describe('updateUser(username: String!): User!', () => {
188+
it('returns an error because only authenticated users can update a user', async () => {
189+
const {
190+
data: { errors },
191+
} = await userApi.updateUser({ username: 'Mark' });
192+
193+
expect(errors[0].message).to.eql('Not authenticated as user.');
194+
});
195+
});
196+
197+
describe('signIn(login: String!, password: String!): Token!', () => {
198+
it('returns a token when a user signs in with username', async () => {
199+
const {
200+
data: {
201+
data: {
202+
signIn: { token },
203+
},
204+
},
205+
} = await userApi.signIn({
206+
login: 'ddavids',
207+
password: 'ddavids',
208+
});
209+
210+
expect(token).to.be.a('string');
211+
});
212+
213+
it('returns a token when a user signs in with email', async () => {
214+
const {
215+
data: {
216+
data: {
217+
signIn: { token },
218+
},
219+
},
220+
} = await userApi.signIn({
221+
login: 'hello@david.com',
222+
password: 'ddavids',
223+
});
224+
225+
expect(token).to.be.a('string');
226+
});
227+
228+
it('returns an error when a user provides a wrong password', async () => {
229+
const {
230+
data: { errors },
231+
} = await userApi.signIn({
232+
login: 'ddavids',
233+
password: 'dontknow',
234+
});
235+
236+
expect(errors[0].message).to.eql('Invalid password.');
237+
});
238+
});
239+
240+
it('returns an error when a user is not found', async () => {
241+
const {
242+
data: { errors },
243+
} = await userApi.signIn({
244+
login: 'dontknow',
245+
password: 'ddavids',
246+
});
247+
248+
expect(errors[0].message).to.eql(
249+
'No user found with this login credentials.',
250+
);
251+
});
57252
});

0 commit comments

Comments
 (0)