feat: Use party's quest key in cron

This commit is contained in:
Blade Barringer
2016-05-31 22:35:07 -05:00
parent 3113e1a1e8
commit c04bac44e7
3 changed files with 429 additions and 65 deletions

View File

@@ -5,49 +5,53 @@ import { quests as questScrolls } from '../../../../../common/script/content';
import * as email from '../../../../../website/server/libs/api-v3/email';
describe('Group Model', () => {
let party, questLeader, participatingMember, nonParticipatingMember, undecidedMember;
beforeEach(async () => {
sandbox.stub(email, 'sendTxn');
party = new Group({
name: 'test party',
type: 'party',
privacy: 'private',
});
questLeader = new User({
party: { _id: party._id },
profile: { name: 'Quest Leader' },
items: {
quests: {
whale: 1,
},
},
});
party.leader = questLeader._id;
participatingMember = new User({
party: { _id: party._id },
profile: { name: 'Participating Member' },
});
nonParticipatingMember = new User({
party: { _id: party._id },
profile: { name: 'Non-Participating Member' },
});
undecidedMember = new User({
party: { _id: party._id },
profile: { name: 'Undecided Member' },
});
await Promise.all([
party.save(),
questLeader.save(),
participatingMember.save(),
nonParticipatingMember.save(),
undecidedMember.save(),
]);
});
context('Instance Methods', () => {
describe('#startQuest', () => {
let party, questLeader, participatingMember, nonParticipatingMember, undecidedMember;
beforeEach(async () => {
sandbox.stub(email, 'sendTxn');
party = new Group({
name: 'test party',
type: 'party',
privacy: 'private',
});
questLeader = new User({
party: { _id: party._id },
items: {
quests: {
whale: 1,
},
},
});
party.leader = questLeader._id;
participatingMember = new User({
party: { _id: party._id },
});
nonParticipatingMember = new User({
party: { _id: party._id },
});
undecidedMember = new User({
party: { _id: party._id },
});
await Promise.all([
party.save(),
questLeader.save(),
participatingMember.save(),
nonParticipatingMember.save(),
undecidedMember.save(),
]);
});
context('Failure Conditions', () => {
it('throws an error if group is not a party', async () => {
let guild = new Group({
@@ -74,11 +78,12 @@ describe('Group Model', () => {
party.quest.key = 'whale';
party.quest.active = false;
party.quest.leader = questLeader._id;
party.quest.members = { };
party.quest.members[questLeader._id] = true;
party.quest.members[participatingMember._id] = true;
party.quest.members[nonParticipatingMember._id] = false;
party.quest.members[undecidedMember._id] = null;
party.quest.members = {
[questLeader._id]: true,
[participatingMember._id]: true,
[nonParticipatingMember._id]: false,
[undecidedMember._id]: null,
};
});
it('activates quest', () => {
@@ -296,5 +301,344 @@ describe('Group Model', () => {
});
});
});
describe('processQuestProgress', () => {
let progress;
beforeEach(async () => {
progress = {
up: 5,
down: -5,
};
party.quest.active = true;
party.quest.members = {
[questLeader._id]: true,
[participatingMember._id]: true,
[nonParticipatingMember._id]: false,
[undecidedMember._id]: null,
};
await party.save();
sandbox.stub(Group, 'processBossQuest').returns(Promise.resolve());
sandbox.stub(Group, 'processCollectionQuest').returns(Promise.resolve());
});
it('returns early if user is not in a party', async () => {
let userWithoutParty = new User();
await userWithoutParty.save();
await Group.processQuestProgress(userWithoutParty, progress);
expect(Group.processBossQuest).to.not.be.called;
expect(Group.processCollectionQuest).to.not.be.called;
});
it('returns early if party is not on quest', async () => {
party.quest.active = false;
await party.save();
await Group.processQuestProgress(participatingMember, progress);
expect(Group.processBossQuest).to.not.be.called;
expect(Group.processCollectionQuest).to.not.be.called;
});
it('returns early if user is not on quest', async () => {
await Group.processQuestProgress(nonParticipatingMember, progress);
expect(Group.processBossQuest).to.not.be.called;
expect(Group.processCollectionQuest).to.not.be.called;
});
it('returns early if user has made no progress', async () => {
await Group.processQuestProgress(participatingMember, null);
expect(Group.processBossQuest).to.not.be.called;
expect(Group.processCollectionQuest).to.not.be.called;
});
it('returns early if quest does not exist', async () => {
party.quest.key = 'foobar';
await party.save();
await Group.processQuestProgress(participatingMember, progress);
expect(Group.processBossQuest).to.not.be.called;
expect(Group.processCollectionQuest).to.not.be.called;
});
it('calls processBossQuest if quest is a boss quest', async () => {
party.quest.key = 'whale';
await party.save();
await Group.processQuestProgress(participatingMember, progress);
expect(Group.processBossQuest).to.be.calledOnce;
expect(Group.processCollectionQuest).to.not.be.called;
});
it('calls processCollectionQuest if quest is a boss quest', async () => {
party.quest.key = 'evilsanta2';
await party.save();
await Group.processQuestProgress(participatingMember, progress);
expect(Group.processBossQuest).to.not.be.called;
expect(Group.processCollectionQuest).to.be.calledOnce;
});
});
describe('processBossQuest', () => {
let progress, quest;
beforeEach(async () => {
progress = {
up: 5,
down: -5,
};
quest = questScrolls.whale;
party.quest.members = {
[questLeader._id]: true,
[participatingMember._id]: true,
[nonParticipatingMember._id]: false,
[undecidedMember._id]: null,
};
party.quest.key = 'whale';
await party.save();
await party.startQuest(questLeader);
sandbox.stub(party, 'sendChat');
});
it('applies user\'s progress to quest boss hp', async () => {
await Group.processBossQuest({
user: participatingMember,
progress,
quest,
group: party,
});
expect(party.quest.progress.hp).to.eql(495);
});
it('sends a chat message about progress', async () => {
await Group.processBossQuest({
user: participatingMember,
progress,
quest,
group: party,
});
expect(party.sendChat).to.be.calledOnce;
expect(party.sendChat).to.be.calledWith('`Participating Member attacks Wailing Whale for 5.0 damage.` `Wailing Whale attacks party for 7.5 damage.`');
});
it('applies damage only to participating members of party', async () => {
await Group.processBossQuest({
user: participatingMember,
progress,
quest,
group: party,
});
let [
updatedLeader,
updatedParticipatingMember,
updatedNonParticipatingMember,
updatedUndecidedMember,
] = await Promise.all([
User.findById(questLeader._id),
User.findById(participatingMember._id),
User.findById(nonParticipatingMember._id),
User.findById(undecidedMember._id),
]);
expect(updatedLeader.stats.hp).to.eql(42.5);
expect(updatedParticipatingMember.stats.hp).to.eql(42.5);
expect(updatedNonParticipatingMember.stats.hp).to.eql(50);
expect(updatedUndecidedMember.stats.hp).to.eql(50);
});
it('sends message about victory', async () => {
progress.up = 999;
await Group.processBossQuest({
user: participatingMember,
progress,
quest,
group: party,
});
expect(party.sendChat).to.be.calledTwice;
expect(party.sendChat).to.be.calledWith('`You defeated Wailing Whale! Questing party members receive the rewards of victory.`');
});
it('calls finishQuest when boss has <= 0 hp', async () => {
progress.up = 999;
sandbox.spy(party, 'finishQuest');
await Group.processBossQuest({
user: participatingMember,
progress,
quest,
group: party,
});
expect(party.finishQuest).to.be.calledOnce;
expect(party.finishQuest).to.be.calledWith(quest);
});
context('rage quests', () => {
beforeEach(async () => {
party.quest.active = false;
party.quest.key = 'trex_undead';
quest = questScrolls[party.quest.key];
await party.save();
await party.startQuest(questLeader);
});
it('applies down progress to boss rage', async () => {
await Group.processBossQuest({
user: participatingMember,
progress,
quest,
group: party,
});
expect(party.quest.progress.rage).to.eql(10);
});
it('activates rage when progress.down triggers rage bar', async () => {
progress.down = -999;
party.quest.progress.hp = 300;
await Group.processBossQuest({
user: participatingMember,
progress,
quest,
group: party,
});
expect(party.sendChat).to.be.calledWith(quest.boss.rage.effect('en'));
expect(party.quest.progress.hp).to.eql(383.5);
expect(party.quest.progress.rage).to.eql(0);
});
it('rage sets boss hp to max hp if raging would have caused hp to be higher than the max', async () => {
progress.down = -999;
party.quest.progress.hp = 490;
await Group.processBossQuest({
user: participatingMember,
progress,
quest,
group: party,
});
expect(party.quest.progress.hp).to.eql(500);
});
});
});
describe('processCollectionQuest', () => {
let progress, quest;
beforeEach(async () => {
progress = {
collect: {
soapBars: 5,
},
};
quest = questScrolls.atom1;
party.quest.members = {
[questLeader._id]: true,
[participatingMember._id]: true,
[nonParticipatingMember._id]: false,
[undecidedMember._id]: null,
};
party.quest.key = 'atom1';
await party.save();
await party.startQuest(questLeader);
sandbox.stub(party, 'sendChat');
});
it('applies user\'s progress to found quest items', async () => {
await Group.processCollectionQuest({
user: participatingMember,
progress,
quest,
group: party,
});
expect(party.quest.progress.collect.soapBars).to.eq(5)
});
it('sends a chat message about progress', async () => {
await Group.processCollectionQuest({
user: participatingMember,
progress,
quest,
group: party,
});
expect(party.sendChat).to.be.calledOnce;
expect(party.sendChat).to.be.calledWith('`Participating Member found 5 Bars of Soap.`');
});
it('sends a chat message if no progress is made', async () => {
delete progress.collect.soapBars;
await Group.processCollectionQuest({
user: participatingMember,
progress,
quest,
group: party,
});
expect(party.sendChat).to.be.calledOnce;
expect(party.sendChat).to.be.calledWith('`Participating Member found nothing.`');
});
it('sends message about victory', async () => {
progress.collect.soapBars = 500;
await Group.processCollectionQuest({
user: participatingMember,
progress,
quest,
group: party,
});
expect(party.sendChat).to.be.calledTwice;
expect(party.sendChat).to.be.calledWith('`All items found! Party has received their rewards.`');
});
it('calls finishQuest when all items are found', async () => {
progress.collect.soapBars = 999;
sandbox.spy(party, 'finishQuest');
await Group.processCollectionQuest({
user: participatingMember,
progress,
quest,
group: party,
});
expect(party.finishQuest).to.be.calledOnce;
expect(party.finishQuest).to.be.calledWith(quest);
});
});
});
});