Skip to content

Commit

Permalink
Add "newGame" event to prevent game creation (#258)
Browse files Browse the repository at this point in the history
  • Loading branch information
utarwyn committed Jul 23, 2023
1 parent cac51bf commit 67f3fb8
Show file tree
Hide file tree
Showing 8 changed files with 29 additions and 14 deletions.
2 changes: 1 addition & 1 deletion src/__tests__/EventHandler.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ describe('EventHandler', () => {
});

test('should initialize supported events', () => {
expect(Array.from(eventHandler.listeners.keys())).toEqual(['win', 'tie']);
expect(Array.from(eventHandler.listeners.keys())).toEqual(['newGame', 'win', 'tie']);
});

test('should register a listener if event exists', () => {
Expand Down
7 changes: 7 additions & 0 deletions src/__tests__/GameCommand.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -193,5 +193,12 @@ describe('GameCommand', () => {
'game.in-progress'
);
});

test('should reject with the custom error if provided', async () => {
jest.spyOn(stateManager, 'createGame').mockRejectedValue(new Error('custom error'));
await expect(command['processInvitation'](tunnel, inviter)).rejects.toBe(
'custom error'
);
});
});
});
9 changes: 9 additions & 0 deletions src/__tests__/GameStateManager.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -93,6 +93,15 @@ describe('GameStateManager', () => {
expect(validator.isNewGamePossible).toHaveBeenCalledWith(tunnel, invited);
});

it('should reject if emitted event throws an error', async () => {
const error = new Error('cannot start the game');
jest.spyOn(bot.eventHandler, 'emitEvent').mockImplementation(() => {
throw error;
});
const invited = <GuildMember>{};
await expect(manager.createGame(tunnel, invited)).rejects.toEqual(error);
});

it('should create a game board and send it into the messaging tunnel', async () => {
const spyReplyWith = jest.spyOn(tunnel, 'replyWith');

Expand Down
17 changes: 6 additions & 11 deletions src/__tests__/I18nProvider.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -32,21 +32,16 @@ describe('I18nProvider', () => {
});

it.each`
data | key | replacements | warned | expected
${{ key: 'fake' }} | ${'key'} | ${null} | ${false} | ${'fake'}
${{ 'key.awo': '{p1}: {p2}' }} | ${'key.awo'} | ${{ p1: 'test1', p2: 'test2' }} | ${false} | ${'test1: test2'}
${{ key2: 'key2' }} | ${'key'} | ${null} | ${true} | ${'key'}
${undefined} | ${'my.key'} | ${null} | ${true} | ${'my.key'}
data | key | replacements | expected
${{ key: 'fake' }} | ${'key'} | ${null} | ${'fake'}
${{ 'key.awo': '{p1}: {p2}' }} | ${'key.awo'} | ${{ p1: 'test1', p2: 'test2' }} | ${'test1: test2'}
${{ key2: 'key2' }} | ${'key'} | ${null} | ${'key'}
${undefined} | ${'my.key'} | ${null} | ${'my.key'}
`(
'should translate $key with replacements $replacements',
({ data, key, replacements, warned, expected }) => {
const spyWarn = jest.spyOn(global.console, 'warn').mockImplementation();

({ data, key, replacements, expected }) => {
provider['localeData'] = data;

expect(provider.__(key, replacements)).toBe(expected);
expect(spyWarn).toHaveBeenCalledTimes(warned ? 1 : 0);
spyWarn.mockRestore();
}
);
});
2 changes: 2 additions & 0 deletions src/bot/EventHandler.ts
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import Entity from '@tictactoe/Entity';
* Supported type of events
*/
export type EventTypes = {
newGame: (data: { players: Entity[] }) => void;
win: (data: { winner: Entity; loser: Entity }) => void;
tie: (data: { players: Entity[] }) => void;
};
Expand All @@ -26,6 +27,7 @@ export default class EventHandler {
constructor() {
this.listeners = new Map();

this.supportEvent('newGame');
this.supportEvent('win');
this.supportEvent('tie');
}
Expand Down
2 changes: 1 addition & 1 deletion src/bot/command/GameCommand.ts
Original file line number Diff line number Diff line change
Expand Up @@ -127,6 +127,6 @@ export default class GameCommand {
} else {
handler = this.manager.createGame(tunnel);
}
return handler.catch(() => Promise.reject('game.in-progress'));
return handler.catch((err?: Error) => Promise.reject(err?.message ?? 'game.in-progress'));
}
}
3 changes: 3 additions & 0 deletions src/bot/state/GameStateManager.ts
Original file line number Diff line number Diff line change
Expand Up @@ -99,6 +99,9 @@ export default class GameStateManager {
this.bot.configuration
);

// Emit a custom event which can cancel the game creation if throws an error
this.bot.eventHandler.emitEvent('newGame', { players: gameboard.entities });

// Register the gameboard in the list
this.gameboards.push(gameboard);

Expand Down
1 change: 0 additions & 1 deletion src/i18n/I18nProvider.ts
Original file line number Diff line number Diff line change
Expand Up @@ -91,7 +91,6 @@ export class I18nProvider {

return message;
} else {
console.warn(`Cannot find language key ${key}. Using key instead.`);
return key;
}
}
Expand Down

0 comments on commit 67f3fb8

Please sign in to comment.