mirror of
https://github.com/HabitRPG/habitica.git
synced 2025-12-17 14:47:53 +01:00
Update tests to assert against translation strings
This commit is contained in:
@@ -32,5 +32,24 @@
|
|||||||
|
|
||||||
"armoireEquipment": "<%= image %> You found a piece of rare Equipment in the Armoire: <%= dropText %>! Awesome!",
|
"armoireEquipment": "<%= image %> You found a piece of rare Equipment in the Armoire: <%= dropText %>! Awesome!",
|
||||||
"armoireFood": "<%= image %> You rummage in the Armoire and find <%= dropArticle %><%= dropText %>. What's that doing in here?",
|
"armoireFood": "<%= image %> You rummage in the Armoire and find <%= dropArticle %><%= dropText %>. What's that doing in here?",
|
||||||
"armoireExp": "You wrestle with the Armoire and gain Experience. Take that!"
|
"armoireExp": "You wrestle with the Armoire and gain Experience. Take that!",
|
||||||
|
|
||||||
|
"messageInsufficientGems": "Not enough gems!",
|
||||||
|
|
||||||
|
"messageAuthPasswordMustMatch": ":password and :confirmPassword don't match",
|
||||||
|
"messageAuthCredentialsRequired": ":username, :email, :password, :confirmPassword required",
|
||||||
|
"messageAuthUsernameTaken": "Username already taken",
|
||||||
|
"messageAuthEmailTaken": "Email already taken",
|
||||||
|
"messageAuthNoUserFound": "No user found.",
|
||||||
|
"messageAuthMustBeLoggedIn": "You must be logged in.",
|
||||||
|
"messageAuthMustIncludeTokens": "You must include a token and uid (user id) in your request",
|
||||||
|
|
||||||
|
"messageGroupNotFound": "Group not found or you don't have access.",
|
||||||
|
"messageGroupAlreadyInParty": "Already in a party, try refreshing.",
|
||||||
|
"messageGroupOnlyLeaderCanUpdate": "Only the group leader can update the group!",
|
||||||
|
"messageGroupRequiresInvite": "Can't join a group you're not invited to.",
|
||||||
|
"messageGroupCannotRemoveSelf": "You cannot remove yourself!",
|
||||||
|
|
||||||
|
"messageUserOperationProtected": "path `<%= operation %>` was not saved, as it's a protected path.",
|
||||||
|
"messageUserOperationNotFound": "<%= operation %> operation not found"
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ import {
|
|||||||
createAndPopulateGroup,
|
createAndPopulateGroup,
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../helpers/api.helper';
|
} from '../../helpers/api.helper';
|
||||||
import {
|
import {
|
||||||
find,
|
find,
|
||||||
@@ -148,7 +149,7 @@ describe('GET /groups/:id', () => {
|
|||||||
return expect(api.get(`/groups/${createdGroup._id}`))
|
return expect(api.get(`/groups/${createdGroup._id}`))
|
||||||
.to.eventually.be.rejected.and.eql({
|
.to.eventually.be.rejected.and.eql({
|
||||||
code: 404,
|
code: 404,
|
||||||
text: 'Group not found or you don\'t have access.',
|
text: t('messageGroupNotFound'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
@@ -178,7 +179,7 @@ describe('GET /groups/:id', () => {
|
|||||||
return expect(api.get(`/groups/${createdGroup._id}`))
|
return expect(api.get(`/groups/${createdGroup._id}`))
|
||||||
.to.eventually.be.rejected.and.eql({
|
.to.eventually.be.rejected.and.eql({
|
||||||
code: 404,
|
code: 404,
|
||||||
text: 'Group not found or you don\'t have access.',
|
text: t('messageGroupNotFound'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
@@ -227,7 +228,7 @@ describe('GET /groups/:id', () => {
|
|||||||
return expect(api.get('/groups/group-that-does-not-exist'))
|
return expect(api.get('/groups/group-that-does-not-exist'))
|
||||||
.to.eventually.be.rejected.and.eql({
|
.to.eventually.be.rejected.and.eql({
|
||||||
code: 404,
|
code: 404,
|
||||||
text: 'Group not found or you don\'t have access.',
|
text: t('messageGroupNotFound'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ import {
|
|||||||
generateGroup,
|
generateGroup,
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../helpers/api.helper';
|
} from '../../helpers/api.helper';
|
||||||
|
|
||||||
describe('POST /groups', () => {
|
describe('POST /groups', () => {
|
||||||
@@ -82,7 +83,7 @@ describe('POST /groups', () => {
|
|||||||
});
|
});
|
||||||
})).to.eventually.be.rejected.and.eql({
|
})).to.eventually.be.rejected.and.eql({
|
||||||
code: 400,
|
code: 400,
|
||||||
text: 'Already in a party, try refreshing.',
|
text: t('messageGroupAlreadyInParty'),
|
||||||
});
|
});
|
||||||
})
|
})
|
||||||
|
|
||||||
@@ -119,11 +120,10 @@ describe('POST /groups', () => {
|
|||||||
});
|
});
|
||||||
})).to.eventually.be.rejected.and.eql({
|
})).to.eventually.be.rejected.and.eql({
|
||||||
code: 401,
|
code: 401,
|
||||||
text: 'Not enough gems!',
|
text: t('messageInsufficientGems'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
it('can create a public guild', () => {
|
it('can create a public guild', () => {
|
||||||
return expect(api.post('/groups', {
|
return expect(api.post('/groups', {
|
||||||
type: 'guild',
|
type: 'guild',
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ import {
|
|||||||
generateGroup,
|
generateGroup,
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../helpers/api.helper';
|
} from '../../helpers/api.helper';
|
||||||
|
|
||||||
describe('POST /groups/:id', () => {
|
describe('POST /groups/:id', () => {
|
||||||
@@ -34,7 +35,7 @@ describe('POST /groups/:id', () => {
|
|||||||
name: 'Change'
|
name: 'Change'
|
||||||
})).to.eventually.be.rejected.and.eql({
|
})).to.eventually.be.rejected.and.eql({
|
||||||
code: 401,
|
code: 401,
|
||||||
text: 'Only the group leader can update the group!',
|
text: t('messageGroupOnlyLeaderCanUpdate'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ import {
|
|||||||
createAndPopulateGroup,
|
createAndPopulateGroup,
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../helpers/api.helper';
|
} from '../../helpers/api.helper';
|
||||||
import { each, find } from 'lodash';
|
import { each, find } from 'lodash';
|
||||||
|
|
||||||
@@ -75,7 +76,7 @@ describe('POST /groups/:id/join', () => {
|
|||||||
return api.get(`/groups/${group._id}`);
|
return api.get(`/groups/${group._id}`);
|
||||||
})).to.eventually.be.rejected.and.eql({
|
})).to.eventually.be.rejected.and.eql({
|
||||||
code: 401,
|
code: 401,
|
||||||
text: 'Can\'t join a group you\'re not invited to.',
|
text: t('messageGroupRequiresInvite'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ import {
|
|||||||
generateGroup,
|
generateGroup,
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../helpers/api.helper';
|
} from '../../helpers/api.helper';
|
||||||
import { find } from 'lodash';
|
import { find } from 'lodash';
|
||||||
|
|
||||||
@@ -88,7 +89,7 @@ describe('POST /groups/:id/leave', () => {
|
|||||||
return api.get(`/groups/${group._id}`);
|
return api.get(`/groups/${group._id}`);
|
||||||
})).to.eventually.be.rejected.and.eql({
|
})).to.eventually.be.rejected.and.eql({
|
||||||
code: 404,
|
code: 404,
|
||||||
text: 'Group not found or you don\'t have access.',
|
text: t('messageGroupNotFound'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -3,6 +3,7 @@ import {
|
|||||||
generateGroup,
|
generateGroup,
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../helpers/api.helper';
|
} from '../../helpers/api.helper';
|
||||||
|
|
||||||
describe('POST /groups/:id/removeMember', () => {
|
describe('POST /groups/:id/removeMember', () => {
|
||||||
@@ -40,7 +41,7 @@ describe('POST /groups/:id/removeMember', () => {
|
|||||||
uuid: leader._id,
|
uuid: leader._id,
|
||||||
})).to.eventually.be.rejected.and.eql({
|
})).to.eventually.be.rejected.and.eql({
|
||||||
code: 401,
|
code: 401,
|
||||||
text: 'You cannot remove yourself!',
|
text: t('messageGroupCannotRemoveSelf'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
import {
|
import {
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../helpers/api.helper';
|
} from '../../helpers/api.helper';
|
||||||
import {v4 as generateRandomUserName} from 'uuid';
|
import {v4 as generateRandomUserName} from 'uuid';
|
||||||
|
|
||||||
@@ -39,7 +40,55 @@ describe('POST /register', () => {
|
|||||||
confirmPassword: confirmPassword,
|
confirmPassword: confirmPassword,
|
||||||
})).to.eventually.be.rejected.and.eql({
|
})).to.eventually.be.rejected.and.eql({
|
||||||
code: 401,
|
code: 401,
|
||||||
text: ':password and :confirmPassword don\'t match',
|
text: t('messageAuthPasswordMustMatch'),
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('requires a username', () => {
|
||||||
|
let api = requester();
|
||||||
|
let email = `${generateRandomUserName()}@example.com`;
|
||||||
|
let password = 'password';
|
||||||
|
let confirmPassword = 'password';
|
||||||
|
|
||||||
|
return expect(api.post('/register', {
|
||||||
|
email: email,
|
||||||
|
password: password,
|
||||||
|
confirmPassword: confirmPassword,
|
||||||
|
})).to.eventually.be.rejected.and.eql({
|
||||||
|
code: 401,
|
||||||
|
text: t('messageAuthCredentialsRequired'),
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('requires an email', () => {
|
||||||
|
let api = requester();
|
||||||
|
let username = generateRandomUserName();
|
||||||
|
let password = 'password';
|
||||||
|
let confirmPassword = 'password';
|
||||||
|
|
||||||
|
return expect(api.post('/register', {
|
||||||
|
username: username,
|
||||||
|
password: password,
|
||||||
|
confirmPassword: confirmPassword,
|
||||||
|
})).to.eventually.be.rejected.and.eql({
|
||||||
|
code: 401,
|
||||||
|
text: t('messageAuthCredentialsRequired'),
|
||||||
|
});
|
||||||
|
});
|
||||||
|
|
||||||
|
it('requires a password', () => {
|
||||||
|
let api = requester();
|
||||||
|
let username = generateRandomUserName();
|
||||||
|
let email = `${username}@example.com`;
|
||||||
|
let confirmPassword = 'password';
|
||||||
|
|
||||||
|
return expect(api.post('/register', {
|
||||||
|
username: username,
|
||||||
|
email: email,
|
||||||
|
confirmPassword: confirmPassword,
|
||||||
|
})).to.eventually.be.rejected.and.eql({
|
||||||
|
code: 401,
|
||||||
|
text: t('messageAuthCredentialsRequired'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
@@ -68,7 +117,7 @@ describe('POST /register', () => {
|
|||||||
confirmPassword: password,
|
confirmPassword: password,
|
||||||
})).to.eventually.be.rejected.and.eql({
|
})).to.eventually.be.rejected.and.eql({
|
||||||
code: 401,
|
code: 401,
|
||||||
text: 'Username already taken',
|
text: t('messageAuthUsernameTaken'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -84,7 +133,7 @@ describe('POST /register', () => {
|
|||||||
confirmPassword: password,
|
confirmPassword: password,
|
||||||
})).to.eventually.be.rejected.and.eql({
|
})).to.eventually.be.rejected.and.eql({
|
||||||
code: 401,
|
code: 401,
|
||||||
text: 'Email already taken',
|
text: t('messageAuthEmailTaken'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
import {
|
import {
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../helpers/api.helper';
|
} from '../../helpers/api.helper';
|
||||||
|
|
||||||
describe('DELETE /user', () => {
|
describe('DELETE /user', () => {
|
||||||
@@ -17,10 +18,14 @@ describe('DELETE /user', () => {
|
|||||||
return api.get('/user');
|
return api.get('/user');
|
||||||
})).to.eventually.be.rejected.and.eql({
|
})).to.eventually.be.rejected.and.eql({
|
||||||
code: 401,
|
code: 401,
|
||||||
text: 'No user found.',
|
text: t('messageAuthNoUserFound'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
context('user has active subscription', () => {
|
||||||
|
it('does not delete account');
|
||||||
|
});
|
||||||
|
|
||||||
context('user in solo group', () => {
|
context('user in solo group', () => {
|
||||||
|
|
||||||
it('deletes party when user is the only member');
|
it('deletes party when user is the only member');
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
import {
|
import {
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../helpers/api.helper';
|
} from '../../helpers/api.helper';
|
||||||
|
|
||||||
describe('GET /user/tags/id', () => {
|
describe('GET /user/tags/id', () => {
|
||||||
@@ -22,7 +23,7 @@ describe('GET /user/tags/id', () => {
|
|||||||
return expect(api.get('/user/tags/not-an-id'))
|
return expect(api.get('/user/tags/not-an-id'))
|
||||||
.to.eventually.be.rejected.and.eql({
|
.to.eventually.be.rejected.and.eql({
|
||||||
code: 404,
|
code: 404,
|
||||||
text: 'Tag not found.'
|
text: t('messageTagNotFound'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
import {
|
import {
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../helpers/api.helper';
|
} from '../../helpers/api.helper';
|
||||||
|
|
||||||
import { each } from 'lodash';
|
import { each } from 'lodash';
|
||||||
@@ -15,7 +16,7 @@ describe('PUT /user', () => {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
context('allowed paths', () => {
|
context('allowed operations', () => {
|
||||||
it('updates the user', () => {
|
it('updates the user', () => {
|
||||||
return api.put('/user', {
|
return api.put('/user', {
|
||||||
'profile.name' : 'Frodo',
|
'profile.name' : 'Frodo',
|
||||||
@@ -29,8 +30,8 @@ describe('PUT /user', () => {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
context('top level protected paths', () => {
|
context('top level protected operations', () => {
|
||||||
let protectedPaths = {
|
let protectedOperations = {
|
||||||
'gem balance': {balance: 100},
|
'gem balance': {balance: 100},
|
||||||
'auth': {'auth.blocked': true, 'auth.timestamps.created': new Date()},
|
'auth': {'auth.blocked': true, 'auth.timestamps.created': new Date()},
|
||||||
'contributor': {'contributor.level': 9, 'contributor.admin': true, 'contributor.text': 'some text'},
|
'contributor': {'contributor.level': 9, 'contributor.admin': true, 'contributor.text': 'some text'},
|
||||||
@@ -40,11 +41,11 @@ describe('PUT /user', () => {
|
|||||||
'tasks': {todos: [], habits: [], dailys: [], rewards: []},
|
'tasks': {todos: [], habits: [], dailys: [], rewards: []},
|
||||||
};
|
};
|
||||||
|
|
||||||
each(protectedPaths, (data, testName) => {
|
each(protectedOperations, (data, testName) => {
|
||||||
it(`does not allow updating ${testName}`, () => {
|
it(`does not allow updating ${testName}`, () => {
|
||||||
let errorText = [];
|
let errorText = [];
|
||||||
each(data, (value, path) => {
|
each(data, (value, operation) => {
|
||||||
errorText.push(`path \`${path}\` was not saved, as it's a protected path.`);
|
errorText.push(t('messageUserOperationProtected', { operation: operation }));
|
||||||
});
|
});
|
||||||
return expect(api.put('/user', data)).to.eventually.be.rejected.and.eql({
|
return expect(api.put('/user', data)).to.eventually.be.rejected.and.eql({
|
||||||
code: 401,
|
code: 401,
|
||||||
@@ -54,16 +55,16 @@ describe('PUT /user', () => {
|
|||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
context('sub-level protected paths', () => {
|
context('sub-level protected operations', () => {
|
||||||
let protectedPaths = {
|
let protectedOperations = {
|
||||||
'class stat': {'stats.class': 'wizard'},
|
'class stat': {'stats.class': 'wizard'},
|
||||||
};
|
};
|
||||||
|
|
||||||
each(protectedPaths, (data, testName) => {
|
each(protectedOperations, (data, testName) => {
|
||||||
it(`does not allow updating ${testName}`, () => {
|
it(`does not allow updating ${testName}`, () => {
|
||||||
let errorText = [];
|
let errorText = [];
|
||||||
each(data, (value, path) => {
|
each(data, (value, operation) => {
|
||||||
errorText.push(`path \`${path}\` was not saved, as it's a protected path.`);
|
errorText.push(t('messageUserOperationProtected', { operation: operation }));
|
||||||
});
|
});
|
||||||
return expect(api.put('/user', data)).to.eventually.be.rejected.and.eql({
|
return expect(api.put('/user', data)).to.eventually.be.rejected.and.eql({
|
||||||
code: 401,
|
code: 401,
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
import {
|
import {
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../../helpers/api.helper';
|
} from '../../../helpers/api.helper';
|
||||||
|
|
||||||
import { each } from 'lodash';
|
import { each } from 'lodash';
|
||||||
@@ -49,7 +50,7 @@ describe('POST /user/batch-update', () => {
|
|||||||
{op: operation},
|
{op: operation},
|
||||||
])).to.eventually.be.rejected.and.eql({
|
])).to.eventually.be.rejected.and.eql({
|
||||||
code: 500,
|
code: 500,
|
||||||
text: `${operation} operation not found`,
|
text: t('messageUserOperationNotFound', { operation: operation}),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
@@ -61,7 +62,7 @@ describe('POST /user/batch-update', () => {
|
|||||||
{op: 'aNotRealOperation'},
|
{op: 'aNotRealOperation'},
|
||||||
])).to.eventually.be.rejected.and.eql({
|
])).to.eventually.be.rejected.and.eql({
|
||||||
code: 500,
|
code: 500,
|
||||||
text: 'aNotRealOperation operation not found',
|
text: t('messageUserOperationNotFound', { operation: 'aNotRealOperation' }),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
import {
|
import {
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../../helpers/api.helper';
|
} from '../../../helpers/api.helper';
|
||||||
|
|
||||||
describe('DELETE /user/tasks/:id', () => {
|
describe('DELETE /user/tasks/:id', () => {
|
||||||
@@ -20,7 +21,7 @@ describe('DELETE /user/tasks/:id', () => {
|
|||||||
return api.get(`/user/tasks/${task.id}`);
|
return api.get(`/user/tasks/${task.id}`);
|
||||||
})).to.eventually.be.rejected.and.eql({
|
})).to.eventually.be.rejected.and.eql({
|
||||||
code: 404,
|
code: 404,
|
||||||
text: 'No task found.',
|
text: t('messageTaskNotFound'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -28,7 +29,7 @@ describe('DELETE /user/tasks/:id', () => {
|
|||||||
return expect(api.del('/user/tasks/task-that-does-not-exist'))
|
return expect(api.del('/user/tasks/task-that-does-not-exist'))
|
||||||
.to.eventually.be.rejected.and.eql({
|
.to.eventually.be.rejected.and.eql({
|
||||||
code: 404,
|
code: 404,
|
||||||
text: 'Task not found.',
|
text: t('messageTaskNotFound'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
import {
|
import {
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../../helpers/api.helper';
|
} from '../../../helpers/api.helper';
|
||||||
|
|
||||||
describe('GET /user/tasks/', () => {
|
describe('GET /user/tasks/', () => {
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
import {
|
import {
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../../helpers/api.helper';
|
} from '../../../helpers/api.helper';
|
||||||
|
|
||||||
describe('GET /user/tasks/:id', () => {
|
describe('GET /user/tasks/:id', () => {
|
||||||
@@ -28,7 +29,7 @@ describe('GET /user/tasks/:id', () => {
|
|||||||
return expect(api.get('/user/tasks/task-that-does-not-exist'))
|
return expect(api.get('/user/tasks/task-that-does-not-exist'))
|
||||||
.to.eventually.be.rejected.and.eql({
|
.to.eventually.be.rejected.and.eql({
|
||||||
code: 404,
|
code: 404,
|
||||||
text: 'No task found.',
|
text: t('messageTaskNotFound'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -38,7 +39,7 @@ describe('GET /user/tasks/:id', () => {
|
|||||||
return api.get(`/user/tasks/${otherUsersTask.id}`);
|
return api.get(`/user/tasks/${otherUsersTask.id}`);
|
||||||
})).to.eventually.be.rejected.and.eql({
|
})).to.eventually.be.rejected.and.eql({
|
||||||
code: 404,
|
code: 404,
|
||||||
text: 'No task found.',
|
text: t('messageTaskNotFound'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
import {
|
import {
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../../helpers/api.helper';
|
} from '../../../helpers/api.helper';
|
||||||
|
|
||||||
describe('POST /user/tasks', () => {
|
describe('POST /user/tasks', () => {
|
||||||
@@ -46,7 +47,7 @@ describe('POST /user/tasks', () => {
|
|||||||
id: todo.id,
|
id: todo.id,
|
||||||
})).to.eventually.be.rejected.and.eql({
|
})).to.eventually.be.rejected.and.eql({
|
||||||
code: 409,
|
code: 409,
|
||||||
text: 'A task with that ID already exists.',
|
text: t('messageDuplicateTaskID'),
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,7 @@
|
|||||||
import {
|
import {
|
||||||
generateUser,
|
generateUser,
|
||||||
requester,
|
requester,
|
||||||
|
translate as t,
|
||||||
} from '../../../helpers/api.helper';
|
} from '../../../helpers/api.helper';
|
||||||
|
|
||||||
describe('PUT /user/tasks/:id', () => {
|
describe('PUT /user/tasks/:id', () => {
|
||||||
|
|||||||
@@ -7,6 +7,9 @@ import {
|
|||||||
import {MongoClient as mongo} from 'mongodb';
|
import {MongoClient as mongo} from 'mongodb';
|
||||||
import {v4 as generateUUID} from 'uuid';
|
import {v4 as generateUUID} from 'uuid';
|
||||||
import superagent from 'superagent';
|
import superagent from 'superagent';
|
||||||
|
import i18n from '../../common/script/src/i18n';
|
||||||
|
require('coffee-script');
|
||||||
|
i18n.translations = require('../../website/src/i18n.js').translations;
|
||||||
|
|
||||||
const API_TEST_SERVER_PORT = 3003;
|
const API_TEST_SERVER_PORT = 3003;
|
||||||
|
|
||||||
@@ -22,6 +25,22 @@ export function requester(user={}) {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// Use this to verify error messages returned by the server
|
||||||
|
// That way, if the translated string changes, the test
|
||||||
|
// will not break. NOTE: it checks agains errors with string as well.
|
||||||
|
export function translate(key, variables) {
|
||||||
|
const STRING_ERROR_MSG = 'Error processing the string. Please see Help > Report a Bug.';
|
||||||
|
const STRING_DOES_NOT_EXIST_MSG = /^String '.*' not found.$/;
|
||||||
|
|
||||||
|
let translatedString = i18n.t(key, variables);
|
||||||
|
|
||||||
|
expect(translatedString).to.not.be.empty;
|
||||||
|
expect(translatedString).to.not.eql(STRING_ERROR_MSG);
|
||||||
|
expect(translatedString).to.not.match(STRING_DOES_NOT_EXIST_MSG);
|
||||||
|
|
||||||
|
return translatedString;
|
||||||
|
};
|
||||||
|
|
||||||
// Creates a new user and returns it
|
// Creates a new user and returns it
|
||||||
// If you need the user to have specific requirements,
|
// If you need the user to have specific requirements,
|
||||||
// such as a balance > 0, just pass in the adjustment
|
// such as a balance > 0, just pass in the adjustment
|
||||||
|
|||||||
@@ -16,9 +16,9 @@ var isProd = nconf.get('NODE_ENV') === 'production';
|
|||||||
|
|
||||||
var api = module.exports;
|
var api = module.exports;
|
||||||
|
|
||||||
var NO_TOKEN_OR_UID = { err: "You must include a token and uid (user id) in your request"};
|
var NO_TOKEN_OR_UID = { err: shared.i18n.t('messageAuthMustIncludeTokens') };
|
||||||
var NO_USER_FOUND = {err: "No user found."};
|
var NO_USER_FOUND = {err: shared.i18n.t('messageAuthNoUserFound') };
|
||||||
var NO_SESSION_FOUND = { err: "You must be logged in." };
|
var NO_SESSION_FOUND = { err: shared.i18n.t('messageAuthMustBeLoggedIn') };
|
||||||
var accountSuspended = function(uuid){
|
var accountSuspended = function(uuid){
|
||||||
return {
|
return {
|
||||||
err: 'Account has been suspended, please contact leslie@habitica.com with your UUID ('+uuid+') for assistance.',
|
err: 'Account has been suspended, please contact leslie@habitica.com with your UUID ('+uuid+') for assistance.',
|
||||||
@@ -72,9 +72,9 @@ api.registerUser = function(req, res, next) {
|
|||||||
async.auto({
|
async.auto({
|
||||||
validate: function(cb) {
|
validate: function(cb) {
|
||||||
if (!(username && req.body.password && email))
|
if (!(username && req.body.password && email))
|
||||||
return cb({code:401, err: ":username, :email, :password, :confirmPassword required"});
|
return cb({code:401, err: shared.i18n.t('messageAuthCredentialsRequired')});
|
||||||
if (req.body.password !== req.body.confirmPassword)
|
if (req.body.password !== req.body.confirmPassword)
|
||||||
return cb({code:401, err: ":password and :confirmPassword don't match"});
|
return cb({code:401, err: shared.i18n.t('messageAuthPasswordMustMatch')});
|
||||||
if (!validator.isEmail(email))
|
if (!validator.isEmail(email))
|
||||||
return cb({code:401, err: ":email invalid"});
|
return cb({code:401, err: ":email invalid"});
|
||||||
cb();
|
cb();
|
||||||
@@ -90,7 +90,7 @@ api.registerUser = function(req, res, next) {
|
|||||||
if (data.findReg) {
|
if (data.findReg) {
|
||||||
if (email === data.findReg.auth.local.email) return cb({code:401, err:"Email already taken"});
|
if (email === data.findReg.auth.local.email) return cb({code:401, err:"Email already taken"});
|
||||||
// Check that the lowercase username isn't already used
|
// Check that the lowercase username isn't already used
|
||||||
if (lowerCaseUsername === data.findReg.auth.local.lowerCaseUsername) return cb({code:401, err:"Username already taken"});
|
if (lowerCaseUsername === data.findReg.auth.local.lowerCaseUsername) return cb({code:401, err: shared.i18n.t('messageAuthUsernameTaken')});
|
||||||
}
|
}
|
||||||
var salt = utils.makeSalt();
|
var salt = utils.makeSalt();
|
||||||
var newUser = {
|
var newUser = {
|
||||||
@@ -309,7 +309,7 @@ api.changeEmail = function(req, res, next){
|
|||||||
User.findOne({'auth.local.email': email}, {auth:1}, cb);
|
User.findOne({'auth.local.email': email}, {auth:1}, cb);
|
||||||
},
|
},
|
||||||
function(found, cb){
|
function(found, cb){
|
||||||
if(found) return cb({code:401, err: "Email already taken"});
|
if(found) return cb({code:401, err: shared.i18n.t('messageAuthEmailTaken')});
|
||||||
if (invalidPassword(res.locals.user, req.body.password)) return cb(invalidPassword(res.locals.user, req.body.password));
|
if (invalidPassword(res.locals.user, req.body.password)) return cb(invalidPassword(res.locals.user, req.body.password));
|
||||||
res.locals.user.auth.local.email = email;
|
res.locals.user.auth.local.email = email;
|
||||||
res.locals.user.save(cb);
|
res.locals.user.save(cb);
|
||||||
|
|||||||
@@ -143,7 +143,7 @@ api.get = function(req, res, next) {
|
|||||||
q.exec(function(err, group){
|
q.exec(function(err, group){
|
||||||
if (err) return next(err);
|
if (err) return next(err);
|
||||||
if(!group){
|
if(!group){
|
||||||
if(gid !== 'party') return res.json(404,{err: "Group not found or you don't have access."});
|
if(gid !== 'party') return res.json(404,{err: shared.i18n.t('messageGroupNotFound')});
|
||||||
|
|
||||||
// Don't send a 404 when querying for a party even if it doesn't exist
|
// Don't send a 404 when querying for a party even if it doesn't exist
|
||||||
// so that users with no party don't get a 404 on every access to the site
|
// so that users with no party don't get a 404 on every access to the site
|
||||||
@@ -184,7 +184,7 @@ api.create = function(req, res, next) {
|
|||||||
group.leader = user._id;
|
group.leader = user._id;
|
||||||
|
|
||||||
if(group.type === 'guild'){
|
if(group.type === 'guild'){
|
||||||
if(user.balance < 1) return res.json(401, {err: 'Not enough gems!'});
|
if(user.balance < 1) return res.json(401, {err: shared.i18n.t('messageInsufficientGems')});
|
||||||
|
|
||||||
group.balance = 1;
|
group.balance = 1;
|
||||||
user.balance--;
|
user.balance--;
|
||||||
@@ -209,7 +209,7 @@ api.create = function(req, res, next) {
|
|||||||
Group.findOne({type:'party',members:{$in:[user._id]}},cb);
|
Group.findOne({type:'party',members:{$in:[user._id]}},cb);
|
||||||
},
|
},
|
||||||
function(found, cb){
|
function(found, cb){
|
||||||
if (found) return cb('Already in a party, try refreshing.');
|
if (found) return cb(shared.i18n.t('messageGroupAlreadyInParty'));
|
||||||
group.save(cb);
|
group.save(cb);
|
||||||
},
|
},
|
||||||
function(saved, count, cb){
|
function(saved, count, cb){
|
||||||
@@ -218,7 +218,7 @@ api.create = function(req, res, next) {
|
|||||||
saved.populate('members', nameFields, cb);
|
saved.populate('members', nameFields, cb);
|
||||||
}
|
}
|
||||||
], function(err, populated){
|
], function(err, populated){
|
||||||
if (err == 'Already in a party, try refreshing.') return res.json(400,{err:err});
|
if (err === shared.i18n.t('messageGroupAlreadyInParty')) return res.json(400,{err:err});
|
||||||
if (err) return next(err);
|
if (err) return next(err);
|
||||||
group = user = null;
|
group = user = null;
|
||||||
return res.json(populated);
|
return res.json(populated);
|
||||||
@@ -231,7 +231,7 @@ api.update = function(req, res, next) {
|
|||||||
var user = res.locals.user;
|
var user = res.locals.user;
|
||||||
|
|
||||||
if(group.leader !== user._id)
|
if(group.leader !== user._id)
|
||||||
return res.json(401, {err: "Only the group leader can update the group!"});
|
return res.json(401, {err: shared.i18n.t('messageGroupOnlyLeaderCanUpdate')});
|
||||||
|
|
||||||
'name description logo logo leaderMessage leader leaderOnly'.split(' ').forEach(function(attr){
|
'name description logo logo leaderMessage leader leaderOnly'.split(' ').forEach(function(attr){
|
||||||
group[attr] = req.body[attr];
|
group[attr] = req.body[attr];
|
||||||
@@ -251,7 +251,7 @@ api.attachGroup = function(req, res, next) {
|
|||||||
var q = (gid == 'party') ? Group.findOne({type: 'party', members: {'$in': [res.locals.user._id]}}) : Group.findById(gid);
|
var q = (gid == 'party') ? Group.findOne({type: 'party', members: {'$in': [res.locals.user._id]}}) : Group.findById(gid);
|
||||||
q.exec(function(err, group){
|
q.exec(function(err, group){
|
||||||
if(err) return next(err);
|
if(err) return next(err);
|
||||||
if(!group) return res.json(404, {err: "Group not found"});
|
if(!group) return res.json(404, {err: shared.i18n.t('messageGroupNotFound')});
|
||||||
res.locals.group = group;
|
res.locals.group = group;
|
||||||
next();
|
next();
|
||||||
});
|
});
|
||||||
@@ -270,7 +270,7 @@ api.getChat = function(req, res, next) {
|
|||||||
populateQuery(gid, q);
|
populateQuery(gid, q);
|
||||||
q.exec(function(err, group){
|
q.exec(function(err, group){
|
||||||
if (err) return next(err);
|
if (err) return next(err);
|
||||||
if (!group && gid!=='party') return res.json(404,{err: "Group not found or you don't have access."});
|
if (!group && gid!=='party') return res.json(404,{err: shared.i18n.t('messageGroupNotFound')});
|
||||||
res.json(res.locals.group.chat);
|
res.json(res.locals.group.chat);
|
||||||
gid = null;
|
gid = null;
|
||||||
});
|
});
|
||||||
@@ -470,7 +470,7 @@ api.join = function(req, res, next) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(!isUserInvited) return res.json(401, {err: "Can't join a group you're not invited to."});
|
if(!isUserInvited) return res.json(401, {err: shared.i18n.t('messageGroupRequiresInvite')});
|
||||||
|
|
||||||
if (!_.contains(group.members, user._id)){
|
if (!_.contains(group.members, user._id)){
|
||||||
if (group.members.length === 0) {
|
if (group.members.length === 0) {
|
||||||
|
|||||||
@@ -164,7 +164,7 @@ api.getTasks = function(req, res, next) {
|
|||||||
*/
|
*/
|
||||||
api.getTask = function(req, res, next) {
|
api.getTask = function(req, res, next) {
|
||||||
var task = findTask(req,res);
|
var task = findTask(req,res);
|
||||||
if (!task) return res.json(404, {err: "No task found."});
|
if (!task) return res.json(404, {err: shared.i18n.t('messageTaskNotFound')});
|
||||||
return res.json(200, task);
|
return res.json(200, task);
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -317,7 +317,7 @@ api.update = function(req, res, next) {
|
|||||||
if (acceptablePUTPaths[k])
|
if (acceptablePUTPaths[k])
|
||||||
user.fns.dotSet(k, v);
|
user.fns.dotSet(k, v);
|
||||||
else
|
else
|
||||||
errors.push("path `" + k + "` was not saved, as it's a protected path.");
|
errors.push(shared.i18n.t('messageUserOperationProtected', { operation: k }));
|
||||||
return true;
|
return true;
|
||||||
});
|
});
|
||||||
user.save(function(err) {
|
user.save(function(err) {
|
||||||
@@ -600,7 +600,7 @@ api.batchUpdate = function(req, res, next) {
|
|||||||
return cb(code+": "+ (data.message ? data.message : data.err ? data.err : JSON.stringify(data)));
|
return cb(code+": "+ (data.message ? data.message : data.err ? data.err : JSON.stringify(data)));
|
||||||
return cb();
|
return cb();
|
||||||
};
|
};
|
||||||
if(!api[_req.op]) { return cb(_req.op + ' operation not found'); }
|
if(!api[_req.op]) { return cb(shared.i18n.t('messageUserOperationNotFound', { operation: _req.op })); }
|
||||||
api[_req.op](_req, res, cb);
|
api[_req.op](_req, res, cb);
|
||||||
});
|
});
|
||||||
})
|
})
|
||||||
|
|||||||
Reference in New Issue
Block a user