Merge branch 'develop' into release
1
.babelrc
@@ -1,6 +1,7 @@
|
|||||||
{
|
{
|
||||||
"presets": ["es2015"],
|
"presets": ["es2015"],
|
||||||
"plugins": [
|
"plugins": [
|
||||||
|
"transform-object-rest-spread",
|
||||||
["transform-async-to-module-method", {
|
["transform-async-to-module-method", {
|
||||||
"module": "bluebird",
|
"module": "bluebird",
|
||||||
"method": "coroutine"
|
"method": "coroutine"
|
||||||
|
|||||||
@@ -7,6 +7,7 @@ RUN npm install -g gulp grunt-cli bower mocha
|
|||||||
RUN mkdir -p /usr/src/habitrpg
|
RUN mkdir -p /usr/src/habitrpg
|
||||||
WORKDIR /usr/src/habitrpg
|
WORKDIR /usr/src/habitrpg
|
||||||
RUN git clone https://github.com/HabitRPG/habitica.git /usr/src/habitrpg
|
RUN git clone https://github.com/HabitRPG/habitica.git /usr/src/habitrpg
|
||||||
|
RUN cp config.json.example config.json
|
||||||
RUN npm install
|
RUN npm install
|
||||||
RUN bower install --allow-root
|
RUN bower install --allow-root
|
||||||
|
|
||||||
|
|||||||
@@ -1,3 +1,3 @@
|
|||||||
web:
|
web:
|
||||||
volumes:
|
volumes:
|
||||||
- '.:/habitrpg'
|
- '.:/usr/src/habitrpg'
|
||||||
|
|||||||
16467
npm-shrinkwrap.json
generated
@@ -31,7 +31,7 @@
|
|||||||
"bluebird": "^3.3.5",
|
"bluebird": "^3.3.5",
|
||||||
"body-parser": "^1.15.0",
|
"body-parser": "^1.15.0",
|
||||||
"bootstrap": "^4.0.0-alpha.6",
|
"bootstrap": "^4.0.0-alpha.6",
|
||||||
"bootstrap-vue": "^0.16.1",
|
"bootstrap-vue": "^0.18.0",
|
||||||
"bower": "~1.3.12",
|
"bower": "~1.3.12",
|
||||||
"browserify": "~12.0.1",
|
"browserify": "~12.0.1",
|
||||||
"compression": "^1.6.1",
|
"compression": "^1.6.1",
|
||||||
@@ -40,7 +40,7 @@
|
|||||||
"coupon-code": "^0.4.5",
|
"coupon-code": "^0.4.5",
|
||||||
"css-loader": "^0.28.0",
|
"css-loader": "^0.28.0",
|
||||||
"csv-stringify": "^1.0.2",
|
"csv-stringify": "^1.0.2",
|
||||||
"cwait": "^1.0.0",
|
"cwait": "~1.0.1",
|
||||||
"domain-middleware": "~0.1.0",
|
"domain-middleware": "~0.1.0",
|
||||||
"estraverse": "^4.1.1",
|
"estraverse": "^4.1.1",
|
||||||
"express": "~4.14.0",
|
"express": "~4.14.0",
|
||||||
@@ -73,6 +73,7 @@
|
|||||||
"html-webpack-plugin": "^2.8.1",
|
"html-webpack-plugin": "^2.8.1",
|
||||||
"image-size": "~0.3.2",
|
"image-size": "~0.3.2",
|
||||||
"in-app-purchase": "^1.1.6",
|
"in-app-purchase": "^1.1.6",
|
||||||
|
"intro.js": "^2.6.0",
|
||||||
"jade": "~1.11.0",
|
"jade": "~1.11.0",
|
||||||
"jquery": "^3.1.1",
|
"jquery": "^3.1.1",
|
||||||
"js2xmlparser": "~1.0.0",
|
"js2xmlparser": "~1.0.0",
|
||||||
@@ -81,7 +82,7 @@
|
|||||||
"method-override": "^2.3.5",
|
"method-override": "^2.3.5",
|
||||||
"moment": "^2.13.0",
|
"moment": "^2.13.0",
|
||||||
"moment-recur": "habitrpg/moment-recur#v1.0.6",
|
"moment-recur": "habitrpg/moment-recur#v1.0.6",
|
||||||
"mongoose": "^4.8.6",
|
"mongoose": "~4.8.6",
|
||||||
"mongoose-id-autoinc": "~2013.7.14-4",
|
"mongoose-id-autoinc": "~2013.7.14-4",
|
||||||
"morgan": "^1.7.0",
|
"morgan": "^1.7.0",
|
||||||
"nconf": "~0.8.2",
|
"nconf": "~0.8.2",
|
||||||
@@ -125,9 +126,11 @@
|
|||||||
"vue": "^2.1.0",
|
"vue": "^2.1.0",
|
||||||
"vue-loader": "^11.0.0",
|
"vue-loader": "^11.0.0",
|
||||||
"vue-mugen-scroll": "^0.2.1",
|
"vue-mugen-scroll": "^0.2.1",
|
||||||
|
"vue-notification": "^1.3.2",
|
||||||
"vue-router": "^2.0.0-rc.5",
|
"vue-router": "^2.0.0-rc.5",
|
||||||
"vue-style-loader": "^3.0.0",
|
"vue-style-loader": "^3.0.0",
|
||||||
"vue-template-compiler": "^2.1.10",
|
"vue-template-compiler": "^2.1.10",
|
||||||
|
"vuejs-datepicker": "^0.9.4",
|
||||||
"webpack": "^2.2.1",
|
"webpack": "^2.2.1",
|
||||||
"webpack-merge": "^4.0.0",
|
"webpack-merge": "^4.0.0",
|
||||||
"winston": "^2.1.0",
|
"winston": "^2.1.0",
|
||||||
|
|||||||
@@ -10,6 +10,8 @@ import {
|
|||||||
TAVERN_ID,
|
TAVERN_ID,
|
||||||
} from '../../../../../website/server/models/group';
|
} from '../../../../../website/server/models/group';
|
||||||
import { v4 as generateUUID } from 'uuid';
|
import { v4 as generateUUID } from 'uuid';
|
||||||
|
import { getMatchesByWordArray, removePunctuationFromString } from '../../../../../website/server/libs/stringUtils';
|
||||||
|
import bannedWords from '../../../../../website/server/libs/bannedWords';
|
||||||
import * as email from '../../../../../website/server/libs/email';
|
import * as email from '../../../../../website/server/libs/email';
|
||||||
import { IncomingWebhook } from '@slack/client';
|
import { IncomingWebhook } from '@slack/client';
|
||||||
import nconf from 'nconf';
|
import nconf from 'nconf';
|
||||||
@@ -21,6 +23,9 @@ describe('POST /chat', () => {
|
|||||||
let testMessage = 'Test Message';
|
let testMessage = 'Test Message';
|
||||||
let testBannedWordMessage = 'TEST_PLACEHOLDER_SWEAR_WORD_HERE';
|
let testBannedWordMessage = 'TEST_PLACEHOLDER_SWEAR_WORD_HERE';
|
||||||
let testSlurMessage = 'message with TEST_PLACEHOLDER_SLUR_WORD_HERE';
|
let testSlurMessage = 'message with TEST_PLACEHOLDER_SLUR_WORD_HERE';
|
||||||
|
let bannedWordErrorMessage = t('bannedWordUsed').split('.');
|
||||||
|
bannedWordErrorMessage[0] += ` (${removePunctuationFromString(testBannedWordMessage.toLowerCase())})`;
|
||||||
|
bannedWordErrorMessage = bannedWordErrorMessage.join('.');
|
||||||
|
|
||||||
before(async () => {
|
before(async () => {
|
||||||
let { group, groupLeader, members } = await createAndPopulateGroup({
|
let { group, groupLeader, members } = await createAndPopulateGroup({
|
||||||
@@ -31,7 +36,6 @@ describe('POST /chat', () => {
|
|||||||
},
|
},
|
||||||
members: 2,
|
members: 2,
|
||||||
});
|
});
|
||||||
|
|
||||||
user = groupLeader;
|
user = groupLeader;
|
||||||
groupWithChat = group;
|
groupWithChat = group;
|
||||||
member = members[0];
|
member = members[0];
|
||||||
@@ -88,7 +92,7 @@ describe('POST /chat', () => {
|
|||||||
.to.eventually.be.rejected.and.eql({
|
.to.eventually.be.rejected.and.eql({
|
||||||
code: 400,
|
code: 400,
|
||||||
error: 'BadRequest',
|
error: 'BadRequest',
|
||||||
message: t('bannedWordUsed'),
|
message: bannedWordErrorMessage,
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -98,7 +102,7 @@ describe('POST /chat', () => {
|
|||||||
.to.eventually.be.rejected.and.eql({
|
.to.eventually.be.rejected.and.eql({
|
||||||
code: 400,
|
code: 400,
|
||||||
error: 'BadRequest',
|
error: 'BadRequest',
|
||||||
message: t('bannedWordUsed'),
|
message: bannedWordErrorMessage,
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -108,10 +112,26 @@ describe('POST /chat', () => {
|
|||||||
.to.eventually.be.rejected.and.eql({
|
.to.eventually.be.rejected.and.eql({
|
||||||
code: 400,
|
code: 400,
|
||||||
error: 'BadRequest',
|
error: 'BadRequest',
|
||||||
message: t('bannedWordUsed'),
|
message: bannedWordErrorMessage,
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('checks error message has the banned words used', async () => {
|
||||||
|
let randIndex = Math.floor(Math.random() * (bannedWords.length + 1));
|
||||||
|
let testBannedWords = bannedWords.slice(randIndex, randIndex + 2).map((w) => w.replace(/\\/g, ''));
|
||||||
|
let chatMessage = `Mixing ${testBannedWords[0]} and ${testBannedWords[1]} is bad for you.`;
|
||||||
|
await expect(user.post('/groups/habitrpg/chat', { message: chatMessage}))
|
||||||
|
.to.eventually.be.rejected
|
||||||
|
.and.have.property('message')
|
||||||
|
.that.includes(testBannedWords.join(', '));
|
||||||
|
});
|
||||||
|
|
||||||
|
it('check all banned words are matched', async () => {
|
||||||
|
let message = bannedWords.join(',').replace(/\\/g, '');
|
||||||
|
let matches = getMatchesByWordArray(message, bannedWords);
|
||||||
|
expect(matches.length).to.equal(bannedWords.length);
|
||||||
|
});
|
||||||
|
|
||||||
it('does not error when bad word is suffix of a word', async () => {
|
it('does not error when bad word is suffix of a word', async () => {
|
||||||
let wordAsSuffix = `prefix${testBannedWordMessage}`;
|
let wordAsSuffix = `prefix${testBannedWordMessage}`;
|
||||||
let message = await user.post('/groups/habitrpg/chat', { message: wordAsSuffix});
|
let message = await user.post('/groups/habitrpg/chat', { message: wordAsSuffix});
|
||||||
|
|||||||
@@ -152,7 +152,7 @@ describe('GET /tasks/user', () => {
|
|||||||
expect(dailys2[0].isDue).to.be.true;
|
expect(dailys2[0].isDue).to.be.true;
|
||||||
});
|
});
|
||||||
|
|
||||||
it('returns dailies with isDue for the date specified and will add CDS offset if time is not supplied and assumes timezones', async () => {
|
xit('returns dailies with isDue for the date specified and will add CDS offset if time is not supplied and assumes timezones', async () => {
|
||||||
let timezone = 420;
|
let timezone = 420;
|
||||||
await user.update({
|
await user.update({
|
||||||
'preferences.dayStart': 0,
|
'preferences.dayStart': 0,
|
||||||
@@ -179,7 +179,7 @@ describe('GET /tasks/user', () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
|
|
||||||
it('returns dailies with isDue for the date specified and will add CDS offset if time is not supplied and assumes timezones', async () => {
|
xit('returns dailies with isDue for the date specified and will add CDS offset if time is not supplied and assumes timezones', async () => {
|
||||||
let timezone = 240;
|
let timezone = 240;
|
||||||
await user.update({
|
await user.update({
|
||||||
'preferences.dayStart': 0,
|
'preferences.dayStart': 0,
|
||||||
@@ -205,7 +205,7 @@ describe('GET /tasks/user', () => {
|
|||||||
expect(dailys2[0].isDue).to.be.false;
|
expect(dailys2[0].isDue).to.be.false;
|
||||||
});
|
});
|
||||||
|
|
||||||
it('returns dailies with isDue for the date specified and will add CDS offset if time is not supplied and assumes timezones', async () => {
|
xit('returns dailies with isDue for the date specified and will add CDS offset if time is not supplied and assumes timezones', async () => {
|
||||||
let timezone = 540;
|
let timezone = 540;
|
||||||
await user.update({
|
await user.update({
|
||||||
'preferences.dayStart': 0,
|
'preferences.dayStart': 0,
|
||||||
|
|||||||
@@ -566,6 +566,17 @@ describe('cron', () => {
|
|||||||
expect(tasksByType.habits[0].counterDown).to.equal(0);
|
expect(tasksByType.habits[0].counterDown).to.equal(0);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should reset habit counters even if user is resting in the Inn', () => {
|
||||||
|
user.preferences.sleep = true;
|
||||||
|
tasksByType.habits[0].counterUp = 1;
|
||||||
|
tasksByType.habits[0].counterDown = 1;
|
||||||
|
|
||||||
|
cron({user, tasksByType, daysMissed, analytics});
|
||||||
|
|
||||||
|
expect(tasksByType.habits[0].counterUp).to.equal(0);
|
||||||
|
expect(tasksByType.habits[0].counterDown).to.equal(0);
|
||||||
|
});
|
||||||
|
|
||||||
it('should reset a weekly habit counter each Monday', () => {
|
it('should reset a weekly habit counter each Monday', () => {
|
||||||
tasksByType.habits[0].frequency = 'weekly';
|
tasksByType.habits[0].frequency = 'weekly';
|
||||||
tasksByType.habits[0].counterUp = 1;
|
tasksByType.habits[0].counterUp = 1;
|
||||||
|
|||||||
604
website/assets/sprites/dist/spritesmith-main-0.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-0.png
vendored
|
Before Width: | Height: | Size: 524 KiB After Width: | Height: | Size: 566 KiB |
7522
website/assets/sprites/dist/spritesmith-main-1.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-1.png
vendored
|
Before Width: | Height: | Size: 72 KiB After Width: | Height: | Size: 248 KiB |
2362
website/assets/sprites/dist/spritesmith-main-10.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-10.png
vendored
|
Before Width: | Height: | Size: 159 KiB After Width: | Height: | Size: 155 KiB |
1156
website/assets/sprites/dist/spritesmith-main-11.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-11.png
vendored
|
Before Width: | Height: | Size: 136 KiB After Width: | Height: | Size: 152 KiB |
1176
website/assets/sprites/dist/spritesmith-main-12.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-12.png
vendored
|
Before Width: | Height: | Size: 157 KiB After Width: | Height: | Size: 142 KiB |
1216
website/assets/sprites/dist/spritesmith-main-13.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-13.png
vendored
|
Before Width: | Height: | Size: 135 KiB After Width: | Height: | Size: 148 KiB |
2436
website/assets/sprites/dist/spritesmith-main-14.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-14.png
vendored
|
Before Width: | Height: | Size: 145 KiB After Width: | Height: | Size: 144 KiB |
1636
website/assets/sprites/dist/spritesmith-main-15.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-15.png
vendored
|
Before Width: | Height: | Size: 153 KiB After Width: | Height: | Size: 156 KiB |
1084
website/assets/sprites/dist/spritesmith-main-16.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-16.png
vendored
|
Before Width: | Height: | Size: 177 KiB After Width: | Height: | Size: 174 KiB |
694
website/assets/sprites/dist/spritesmith-main-17.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-17.png
vendored
|
Before Width: | Height: | Size: 162 KiB After Width: | Height: | Size: 160 KiB |
2542
website/assets/sprites/dist/spritesmith-main-18.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-18.png
vendored
|
Before Width: | Height: | Size: 99 KiB After Width: | Height: | Size: 147 KiB |
5572
website/assets/sprites/dist/spritesmith-main-2.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-2.png
vendored
|
Before Width: | Height: | Size: 63 KiB After Width: | Height: | Size: 54 KiB |
5746
website/assets/sprites/dist/spritesmith-main-3.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-3.png
vendored
|
Before Width: | Height: | Size: 61 KiB After Width: | Height: | Size: 77 KiB |
4882
website/assets/sprites/dist/spritesmith-main-4.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-4.png
vendored
|
Before Width: | Height: | Size: 105 KiB After Width: | Height: | Size: 74 KiB |
2092
website/assets/sprites/dist/spritesmith-main-5.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-5.png
vendored
|
Before Width: | Height: | Size: 154 KiB After Width: | Height: | Size: 165 KiB |
2488
website/assets/sprites/dist/spritesmith-main-6.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-6.png
vendored
|
Before Width: | Height: | Size: 150 KiB After Width: | Height: | Size: 162 KiB |
2570
website/assets/sprites/dist/spritesmith-main-7.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-7.png
vendored
|
Before Width: | Height: | Size: 147 KiB After Width: | Height: | Size: 140 KiB |
1284
website/assets/sprites/dist/spritesmith-main-8.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-8.png
vendored
|
Before Width: | Height: | Size: 426 KiB After Width: | Height: | Size: 345 KiB |
1306
website/assets/sprites/dist/spritesmith-main-9.css
vendored
BIN
website/assets/sprites/dist/spritesmith-main-9.png
vendored
|
Before Width: | Height: | Size: 234 KiB After Width: | Height: | Size: 315 KiB |
|
After Width: | Height: | Size: 1.4 KiB |
|
After Width: | Height: | Size: 2.6 KiB |
|
After Width: | Height: | Size: 2.9 KiB |
|
After Width: | Height: | Size: 3.4 KiB |
|
After Width: | Height: | Size: 1.0 KiB |
|
After Width: | Height: | Size: 2.9 KiB |
|
After Width: | Height: | Size: 3.4 KiB |
|
After Width: | Height: | Size: 3.2 KiB |
|
After Width: | Height: | Size: 1.4 KiB |
|
After Width: | Height: | Size: 3.7 KiB |
|
After Width: | Height: | Size: 335 B |
|
After Width: | Height: | Size: 2.8 KiB |
|
After Width: | Height: | Size: 3.0 KiB |
|
After Width: | Height: | Size: 1013 B |
|
After Width: | Height: | Size: 1.0 KiB |
|
After Width: | Height: | Size: 818 B |
|
After Width: | Height: | Size: 3.4 KiB |
|
After Width: | Height: | Size: 2.8 KiB |
|
After Width: | Height: | Size: 3.4 KiB |
|
After Width: | Height: | Size: 1.1 KiB |
|
After Width: | Height: | Size: 676 B |
|
After Width: | Height: | Size: 1.1 KiB |
|
After Width: | Height: | Size: 1.8 KiB |
|
After Width: | Height: | Size: 3.3 KiB |
|
After Width: | Height: | Size: 1.8 KiB |
|
After Width: | Height: | Size: 2.3 KiB |
|
After Width: | Height: | Size: 657 B |
|
After Width: | Height: | Size: 3.7 KiB |
|
After Width: | Height: | Size: 3.2 KiB |
|
After Width: | Height: | Size: 2.9 KiB |
|
After Width: | Height: | Size: 980 B |
|
After Width: | Height: | Size: 2.9 KiB |
|
After Width: | Height: | Size: 2.2 KiB |
|
After Width: | Height: | Size: 1.3 KiB |
|
After Width: | Height: | Size: 3.1 KiB |
|
After Width: | Height: | Size: 3.6 KiB |
|
After Width: | Height: | Size: 9.1 KiB |
|
After Width: | Height: | Size: 997 B |
|
After Width: | Height: | Size: 1.7 KiB |
|
After Width: | Height: | Size: 335 B |
|
After Width: | Height: | Size: 871 B |
|
After Width: | Height: | Size: 3.3 KiB |
|
After Width: | Height: | Size: 3.1 KiB |
|
After Width: | Height: | Size: 1.2 KiB |
|
After Width: | Height: | Size: 2.6 KiB |
|
After Width: | Height: | Size: 700 B |
|
After Width: | Height: | Size: 1.4 KiB |
|
After Width: | Height: | Size: 3.1 KiB |
|
After Width: | Height: | Size: 2.7 KiB |
|
After Width: | Height: | Size: 1.0 KiB |
|
After Width: | Height: | Size: 3.6 KiB |
|
After Width: | Height: | Size: 806 B |
|
After Width: | Height: | Size: 3.2 KiB |
|
After Width: | Height: | Size: 3.5 KiB |