Skip to content

Commit 9cefdd3

Browse files
authored
Fix multi card same pack (#976)
1 parent 85b66c1 commit 9cefdd3

13 files changed

+461
-304
lines changed

.babelrc

+2-1
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@
2727
"@babel/plugin-proposal-function-sent",
2828
"@babel/plugin-proposal-export-namespace-from",
2929
"@babel/plugin-proposal-numeric-separator",
30-
"@babel/plugin-proposal-throw-expressions"
30+
"@babel/plugin-proposal-throw-expressions",
31+
"@babel/plugin-proposal-private-methods"
3132
]
3233
}

backend/human.js

+1-1
Original file line numberDiff line numberDiff line change
@@ -121,7 +121,7 @@ module.exports = class extends Player {
121121

122122
this.pool.push(card);
123123
this.picks.push(pickcard);
124-
this.send("add", card.name);
124+
this.send("add", card);
125125

126126
let [next] = this.packs;
127127
if (!next)

backend/pool.js

+21-6
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,19 @@
11
const {sample, shuffle, random, range, times, constant, pull} = require("lodash");
22
const boosterGenerator = require("./boosterGenerator");
33
const { getCardByUuid, getCardByName, getRandomSet, getExpansionOrCoreModernSets: getModernList, getExansionOrCoreSets: getSetsList } = require("./data");
4+
const draftId = require("uuid").v1;
5+
6+
/**
7+
* @desc add a unique id to a card
8+
* @param card
9+
* @returns {{...card, cardId: string}}
10+
*/
11+
const addCardId = (card) => ({
12+
...card,
13+
cardId: draftId()
14+
});
15+
16+
const addCardIdsToBoosterCards = (pack) => pack.map(addCardId);
417

518
const SealedCube = ({ cubeList, playersLength, playerPoolSize = 90 }) => {
619
return DraftCube({
@@ -11,14 +24,12 @@ const SealedCube = ({ cubeList, playersLength, playerPoolSize = 90 }) => {
1124
});
1225
};
1326

14-
//TODO: filter cards that are from set EXP etc.
1527
const DraftCube = ({ cubeList, playersLength, packsNumber = 3, playerPackSize = 15 }) => {
1628
let list = shuffle(cubeList); // copy the list to work on it
1729

1830
return range(playersLength * packsNumber)
19-
.map(() => {
20-
return list.splice(0, playerPackSize).map(getCardByName);
21-
});
31+
.map(() => list.splice(0, playerPackSize).map(getCardByName))
32+
.map(addCardIdsToBoosterCards);
2233
};
2334

2435
// Replace RNG set with real set
@@ -29,12 +40,14 @@ const replaceRNGSet = (sets) => (
2940
const SealedNormal = ({ playersLength, sets }) => (
3041
times(playersLength , constant(replaceRNGSet(sets)))
3142
.map(sets => sets.flatMap(boosterGenerator))
43+
.map(addCardIdsToBoosterCards)
3244
);
3345

3446
const DraftNormal = ({ playersLength, sets }) => (
3547
replaceRNGSet(sets)
3648
.flatMap(set => times(playersLength, constant(set)))
3749
.map(boosterGenerator)
50+
.map(addCardIdsToBoosterCards)
3851
);
3952

4053
// Get a random set and transform it to pack
@@ -79,13 +92,15 @@ const DraftChaos = ({ playersLength, packsNumber = 3, modernOnly, totalChaos })
7992
const setList = modernOnly ? getModernList() : getSetsList();
8093

8194
return range(playersLength * packsNumber)
82-
.map(() => totalChaos ? getTotalChaosPack(setList) : getRandomPack(setList));
95+
.map(() => totalChaos ? getTotalChaosPack(setList) : getRandomPack(setList))
96+
.map(addCardIdsToBoosterCards);
8397
};
8498

8599
const SealedChaos = ({ playersLength, packsNumber = 6, modernOnly, totalChaos }) => {
86100
const pool = DraftChaos({playersLength, packsNumber, modernOnly, totalChaos});
87101
return range(playersLength)
88-
.map(() => pool.splice(0, packsNumber).flat());
102+
.map(() => pool.splice(0, packsNumber).flat())
103+
.map(addCardIdsToBoosterCards);
89104
};
90105

91106
module.exports = {

backend/pool.spec.js

+40-25
Original file line numberDiff line numberDiff line change
@@ -3,67 +3,84 @@
33
const assert = require("assert");
44
const Pool = require("./pool");
55
const {range, times, constant} = require("lodash");
6-
const { getPlayableSets } = require("./data");
6+
const {getPlayableSets} = require("./data");
7+
8+
const assertPackIsCorrect = (got) => {
9+
const cardIds = new Set();
10+
let expectedCardsSize = 0;
11+
got.forEach(pool => pool.forEach(card => {
12+
assert(card.name !== undefined);
13+
assert(card.cardId !== undefined);
14+
cardIds.add(card.cardId);
15+
expectedCardsSize++;
16+
}));
17+
assert.equal(cardIds.size, expectedCardsSize, "cards should all have a unique ID");
18+
};
719

820
describe("Acceptance tests for Pool class", () => {
921
describe("can make a cube pool", () => {
1022
it("should return a sealed cube pool with length equal to player length", () => {
1123
const cubeList = times(720, constant("island"));
1224
const playersLength = 8;
13-
const got = Pool.SealedCube({ cubeList, playersLength });
14-
assert.equal(playersLength, got.length);
15-
got.forEach(pool => pool.forEach(card => assert(card.name != undefined)));
25+
const playerPoolSize = 90;
26+
const got = Pool.SealedCube({cubeList, playersLength, playerPoolSize});
27+
assert.equal(got.length, playersLength);
28+
assertPackIsCorrect(got);
1629
});
1730

1831
it("should return a draft cube pool with length equal to player length per playersPack", () => {
1932
const cubeList = times(720, constant("island"));
2033
const playersLength = 8;
2134
const packsNumber = 3;
22-
const got = Pool.DraftCube({ cubeList, playersLength, packsNumber });
23-
assert.equal(playersLength*packsNumber, got.length);
24-
got.forEach(pool => pool.forEach(card => assert(card.name != undefined)));
35+
const playerPackSize = 15;
36+
const got = Pool.DraftCube({cubeList, playersLength, packsNumber, playerPackSize});
37+
assert.equal(got.length, playersLength * packsNumber);
38+
assertPackIsCorrect(got);
2539
});
2640
});
2741

2842
describe("can make a normal pool", () => {
2943
it("should return a sealed pool with length equal to player length", () => {
30-
const sets = times(6, constant("M19"));
44+
const packsNumber = 6;
45+
const sets = times(packsNumber, constant("M19"));
3146
const playersLength = 8;
32-
const got = Pool.SealedNormal({ sets, playersLength });
33-
assert.equal(playersLength, got.length);
34-
got.forEach(pool => pool.forEach(card => assert(card.name != undefined)));
47+
const got = Pool.SealedNormal({sets, playersLength});
48+
assert.equal(got.length, playersLength);
49+
assertPackIsCorrect(got);
3550
});
3651

3752
it("should return a draft pool with length equal to player length per playersPack", () => {
38-
const sets = times(3, constant("M19"));
53+
const packsNumber = 3;
54+
const sets = times(packsNumber, constant("M19"));
3955
const playersLength = 8;
40-
const got = Pool.DraftNormal({ sets, playersLength });
41-
assert.equal(playersLength * 3, got.length);
42-
got.forEach(pool => pool.forEach(card => assert(card.name != undefined)));
56+
const got = Pool.DraftNormal({sets, playersLength});
57+
assert.equal(got.length, playersLength * packsNumber);
58+
assertPackIsCorrect(got);
4359
});
4460
});
4561

4662
describe("can make a chaos pool", () => {
4763
it("should return a sealed chaos pool with length equal to player length", () => {
4864
const playersLength = 8;
4965
const got = Pool.SealedChaos({ modernOnly: true, totalChaos: true, playersLength });
50-
assert.equal(playersLength, got.length);
51-
got.forEach(pool => pool.forEach(card => assert(card.name != undefined)));
66+
assert.equal(got.length, playersLength);
67+
assertPackIsCorrect(got);
5268
});
5369

5470
it("should return a draft chaos pool with length equal to player length per playersPack", () => {
5571
const playersLength = 8;
56-
const got = Pool.DraftChaos({ modernOnly: true, totalChaos: true, playersLength });
57-
assert.equal(playersLength * 3, got.length);
58-
got.forEach(pool => pool.forEach(card => assert(card.name != undefined)));
72+
const packsNumber = 3;
73+
const got = Pool.DraftChaos({packsNumber, modernOnly: true, totalChaos: true, playersLength});
74+
assert.equal(got.length, playersLength * packsNumber);
75+
assertPackIsCorrect(got);
5976
});
6077
});
6178

6279
describe("can make a TimeSpiral pool", () => {
6380
it("should return a timespiral pool", () => {
6481
const [got] = Pool.DraftNormal({playersLength: 1, sets: ["TSP"]});
6582
assert.equal(got.length, 15);
66-
got.forEach(card => assert(card.name != undefined));
83+
assertPackIsCorrect([got]);
6784
});
6885
});
6986

@@ -75,10 +92,8 @@ describe("Acceptance tests for Pool class", () => {
7592
if (code === "random" || Date.parse(releaseDate) > new Date() || code === "UST") {
7693
return;
7794
}
78-
const [got] = Pool.DraftNormal({playersLength: 1, sets: [code]});
79-
got.forEach(card => {
80-
assert(card.name != undefined, `${code} has an error: ${card}`);
81-
});
95+
const got = Pool.DraftNormal({playersLength: 1, sets: [code]});
96+
assertPackIsCorrect(got);
8297
});
8398
});
8499
});

frontend/src/app.js

+17
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ import EventEmitter from "events";
33
import {STRINGS} from "./config";
44
import eio from "engine.io-client";
55
import {times, constant} from "lodash";
6+
import GameState from "./gamestate";
67

78
function message(msg) {
89
let args = JSON.parse(msg);
@@ -68,6 +69,8 @@ let App = {
6869
pickNumber: 0,
6970
packSize: 15,
7071
gameSeats: 8, // seats of the game being played
72+
gameState: null, // records the current state of cards is a GameState
73+
gameStates: {}, // Object representation of the gameState
7174

7275
get didGameStart() {
7376
// both round === 0 and round is undefined
@@ -133,6 +136,20 @@ let App = {
133136
let msg = JSON.stringify(args);
134137
this.ws.send(msg);
135138
},
139+
initGameState(id) {
140+
const { gameStates } = App.state;
141+
if (!gameStates[id]) {
142+
App.state.gameState = new GameState();
143+
} else {
144+
App.state.gameState = new GameState(gameStates[id]);
145+
}
146+
App.state.gameState.on("updateGameState", (gameState) => {
147+
App.save("gameStates", {
148+
// ...App.state.gameStates,
149+
[id]: gameState
150+
});
151+
});
152+
},
136153
error(err) {
137154
App.err = err;
138155
App.route("");

0 commit comments

Comments
 (0)