-
Notifications
You must be signed in to change notification settings - Fork 0
/
Copy pathgetInvalidReason.js
224 lines (191 loc) · 60.7 KB
/
getInvalidReason.js
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
const { isProd } = require('./Utilities');
const timezonelessDateMatcher = /^2[0-1][0-9]{2}-[0-1][0-9]-[0-9]{2}$/;
const acceptableLists = ['normal', 'hard'];
const wordMatcher = /^[a-z]{2,15}$/;
const minNameLength = 2;
const maxNameLength = 128;
const maxNumberOfGuesses = 200;
const maxTime = 24 * 60 * 60 * 1000; // max time is 24 hours
const MAX_NUMBER_OF_LEADERS_FOR_DAYS_WORD_LIST = 20000;
const GRAND_FATHERED_SHORT_NAMES = new Set('RjDTZ'.split(''));
const reasons = {
badDate: "Date isn't the correct format, like '2019-04-30'",
dateOutOfRange: 'Date is too far in the future, greater than UTC+14, or the past',
badList: "wordlist isn't one of known lists",
noName: 'You must give a name.',
badTime: 'Time must be greater than 300 ms less than 24 hours',
invalidWord: 'Found an invalid word in the guesses',
unexpectedWord: "The last guess isn't the word I was expecting for this day and wordlist",
sameWordsAndTime: 'Having the exact same words and same completion time is *very* unlikely',
};
const NO_RESPONSE_INVALID_REASONS = new Set(Object.values(reasons));
function getInvalidReason(dateString, wordlist, name, time, guesses, leaders, fromBackup) {
leaders = leaders || {};
const numberOfLeaders = (leaders && Object.keys(leaders).length) || 0;
if (numberOfLeaders >= MAX_NUMBER_OF_LEADERS_FOR_DAYS_WORD_LIST) {
return `Sorry, we only accept ${MAX_NUMBER_OF_LEADERS_FOR_DAYS_WORD_LIST} entries for the board in a day.`;
}
const invalidDateReason = getInvalidDateReason(dateString, fromBackup);
if (invalidDateReason) {
return invalidDateReason;
}
if (!acceptableLists.includes(wordlist)) {
return `${reasons.badList}. badList: ${wordlist}`;
}
if (!name) {
return reasons.noName;
}
if (name.length > maxNameLength) {
return `Name can't be longer than ${maxNameLength}. Yours is ${name.length}`;
}
if (name.trim().length < minNameLength && !GRAND_FATHERED_SHORT_NAMES.has(name)) {
return `Your name, "${name}" is too short. Try a bit longer one.`;
}
const numberOfGuesses = guesses.length;
// allow guesses = 1 and time = 0 or 1, but if guesses are bigger than that the time must be reasonable
const guessedInOne = guesses.length === 1 && (time === 0 || time === 1)
if (!guessedInOne && !integerIsBetweenRange(time, 300, maxTime)) {
return `${reasons.badTime}. badTime: ${time}`;
}
if (numberOfGuesses >= maxNumberOfGuesses) {
return `Sorry, the completion board doesn't accept submissions with more than ${maxNumberOfGuesses} guesses`;
}
const firstInvalidWord = guesses.find(g => !wordMatcher.test(g));
if (firstInvalidWord) {
return `${reasons.invalidWord}. invalidWord: ${firstInvalidWord}`;
}
const word = guesses.slice(-1)[0];
const expectedWord = lookupWord(dateString, wordlist);
if (!expectedWord) {
return `Didn't find a word for the date (${dateString}) and wordlist (${wordlist}) you gave.`;
}
if (word !== expectedWord) {
return `${reasons.unexpectedWord}. unexpectedWord: ${word}, dateString: ${dateString}, wordlist: ${wordlist}, expectedWord: ${expectedWord}`;
}
if (isInappropriateName(name)) {
return 'inappropriate';
}
const joinedGuesses = guesses.join(',');
if (!fromBackup && Object.values(leaders).some(sameGuessesAndTime)) {
return `${reasons.sameWordsAndTime}. name: ${name}, time: ${time}`;
}
return '';
function isInappropriateName(input) {
const otherWord = lookupOtherWord(dateString, wordlist);
const lowerCaseNameWithNonSpaceCharsRemoved = input.toLowerCase().replace(/(_|-)/g, '');
const hasAnswersMatcher = new RegExp(`\\b(${expectedWord}|${otherWord})\\b`);
return hasBadWord(lowerCaseNameWithNonSpaceCharsRemoved)
|| hasAnswersMatcher.test(lowerCaseNameWithNonSpaceCharsRemoved);
}
function sameGuessesAndTime(savedLeader) {
return savedLeader.time === time
&& savedLeader.guesses.length > 1 // it is likely if both users happened to guess in 1
&& savedLeader.guesses.join(',') === joinedGuesses;
}
}
const simpleBadWordRegex = /\b(asses|twat)\b/;
const simpleNonBreakingBadWordRegex = /(fuck|dicks|asshole(s)?|shit|cock|penis|cunt|vagina|twats|boob|nigger|kike|puss(y|ies)|fag(s|got)?|whore|bitch|mick)/;
function hasBadWord(lowercaseString) {
return simpleNonBreakingBadWordRegex.test(lowercaseString)
|| simpleBadWordRegex.test(lowercaseString);
}
function getInvalidDateReason(dateString, fromBackup) {
if (!timezonelessDateMatcher.test(dateString)) {
return `${reasons.badDate}. badDate: ${dateString}`;
}
if (dateIsOutsideOfRange(dateString, fromBackup)) {
return `${reasons.dateOutOfRange}. dateOutOfRange: ${dateString}`;
}
return '';
}
// FIXME, this is currently just copy-pasted from frontend code, would be much better if we load this from the frontend on startup
/* eslint-disable */
const possibleWords = {
// normal words were from 1-1,000 common English words on TV and movies https://en.wiktionary.org/wiki/Wiktionary:Frequency_lists/TV/2006/1-1000
// later normal words were mined from existing guesses
normal: /* DON'T LOOK CLOSELY UNLESS YOU WANT TO BE SPOILED!!! */['', '', '', 'course', 'against', 'ready', 'daughter', 'work', 'friends', 'minute', 'though', 'supposed', 'honey', 'point', 'start', 'check', 'alone', 'matter', 'office', 'hospital', 'three', 'already', 'anyway', 'important', 'tomorrow', 'almost', 'later', 'found', 'trouble', 'excuse', 'hello', 'money', 'different', 'between', 'every', 'party', 'either', 'enough', 'year', 'house', 'story', 'crazy', 'mind', 'break', 'tonight', 'person', 'sister', 'pretty', 'trust', 'funny', 'gift', 'change', 'business', 'train', 'under', 'close', 'reason', 'today', 'beautiful', 'brother', 'since', 'bank', 'yourself', 'without', 'until', 'forget', 'anyone', 'promise', 'happy', 'bake', 'worry', 'school', 'afraid', 'cause', 'doctor', 'exactly', 'second', 'phone', 'look', 'feel', 'somebody', 'stuff', 'elephant', 'morning', 'heard', 'world', 'chance', 'call', 'watch', 'whatever', 'perfect', 'dinner', 'family', 'heart', 'least', 'answer', 'woman', 'bring', 'probably', 'question', 'stand', 'truth', 'problem', 'patch', 'pass', 'famous', 'true', 'power', 'cool', 'last', 'fish', 'remote', 'race', 'noon', 'wipe', 'grow', 'jumbo', 'learn', 'itself', 'chip', 'print', 'young', 'argue', 'clean', 'remove', 'flip', 'flew', 'replace', 'kangaroo', 'side', 'walk', 'gate', 'finger', 'target', 'judge', 'push', 'thought', 'wear', 'desert', 'relief', 'basic', 'bright', 'deal', 'father', 'machine', 'know', 'step', 'exercise', 'present', 'wing', 'lake', 'beach', 'ship', 'wait', 'fancy', 'eight', 'hall', 'rise', 'river', 'round', 'girl', 'winter', 'speed', 'long', 'oldest', 'lock', 'kiss', 'lava', 'garden', 'fight', 'hook', 'desk', 'test', 'serious', 'exit', 'branch', 'keyboard', 'naked', 'science', 'trade', 'quiet', 'home', 'prison', 'blue', 'window', 'whose', 'spot', 'hike', 'laptop', 'dark', 'create', 'quick', 'face', 'freeze', 'plug', 'menu', 'terrible', 'accept', 'door', 'touch', 'care', 'rescue', 'ignore', 'real', 'title', 'city', 'fast', 'season', 'town', 'picture', 'tower', 'zero', 'engine', 'lift', 'respect', 'time', 'mission', 'play', 'discover', 'nail', 'half', 'unusual', 'ball', 'tool', 'heavy', 'night', 'farm', 'firm', 'gone', 'help', 'easy', 'library', 'group', 'jungle', 'taste', 'large', 'imagine', 'normal', 'outside', 'paper', 'nose', 'long', 'queen', 'olive', 'doing', 'moon', 'hour', 'protect', 'hate', 'dead', 'double', 'nothing', 'restaurant', 'reach', 'note', 'tell', 'baby', 'future', 'tall', 'drop', 'speak', 'rule', 'pair', 'ride', 'ticket', 'game', 'hair', 'hurt', 'allow', 'oven', 'live', 'horse', 'bottle', 'rock', 'public', 'find', 'garage', 'green', 'heat', 'plan', 'mean', 'little', 'spend', 'nurse', 'practice', 'wish', 'uncle', 'core', 'stop', 'number', 'nest', 'magazine', 'pool', 'message', 'active', 'throw', 'pull', 'level', 'wrist', 'bubble', 'hold', 'movie', 'huge', 'ketchup', 'finish', 'pilot', 'teeth', 'flag', 'head', 'private', 'together', 'jewel', 'child', 'decide', 'listen', 'garbage', 'jealous', 'wide', 'straight', 'fall', 'joke', 'table', 'spread', 'laundry', 'deep', 'quit', 'save', 'worst', 'email', 'glass', 'scale', 'safe', 'path', 'camera', 'excellent', 'place', 'zone', 'luck', 'tank', 'sign', 'report', 'myself', 'knee', 'need', 'root', 'light', 'sure', 'page', 'life', 'space', 'magic', 'size', 'tape', 'food', 'wire', 'period', 'mistake', 'full', 'paid', 'horrible', 'special', 'hidden', 'rain', 'field', 'kick', 'ground', 'screen', 'risky', 'junk', 'juice', 'human', 'nobody', 'mall', 'bathroom', 'high', 'class', 'street', 'cold', 'metal', 'nervous', 'bike', 'internet', 'wind', 'lion', 'summer', 'president', 'empty', 'square', 'jersey', 'worm', 'popular', 'loud', 'online', 'something', 'photo', 'knot', 'mark', 'zebra', 'road', 'storm', 'grab', 'record', 'said', 'floor', 'theater', 'kitchen', 'action', 'equal', 'nice', 'dream', 'sound', 'fifth', 'comfy', 'talk', 'police', 'draw', 'bunch', 'idea', 'jerk', 'copy', 'success', 'team', 'favor', 'open', 'neat', 'whale', 'gold', 'free', 'mile', 'lying', 'meat', 'nine', 'wonderful', 'hero', 'quilt', 'info', 'radio', 'move', 'early', 'remember', 'understand', 'month', 'everyone', 'quarter', 'center', 'universe', 'name', 'zoom', 'inside', 'label', 'yell', 'jacket', 'nation', 'support', 'lunch', 'twice', 'hint', 'jiggle', 'boot', 'alive', 'build', 'date', 'room', 'fire', 'music', 'leader', 'rest', 'plant', 'connect', 'land', 'body', 'belong', 'trick', 'wild', 'quality', 'band', 'health', 'website', 'love', 'hand', 'okay', 'yeah', 'dozen', 'glove', 'give', 'thick', 'flow', 'project', 'tight', 'join', 'cost', 'trip', 'lower', 'magnet', 'parent', 'grade', 'angry', 'line', 'rich', 'owner', 'block', 'shut', 'neck', 'write', 'hotel', 'danger', 'impossible', 'illegal', 'show', 'come', 'want', 'truck', 'click', 'chocolate', 'none', 'done', 'bone', 'hope', 'share', 'cable', 'leaf', 'water', 'teacher', 'dust', 'orange', 'handle', 'unhappy', 'guess', 'past', 'frame', 'knob', 'winner', 'ugly', 'lesson', 'bear', 'gross', 'midnight', 'grass', 'middle', 'birthday', 'rose', 'useless', 'hole', 'drive', 'loop', 'color', 'sell', 'unfair', 'send', 'crash', 'knife', 'wrong', 'guest', 'strong', 'weather', 'kilometer', 'undo', 'catch', 'neighbor', 'stream', 'random', 'continue', 'return', 'begin', 'kitten', 'thin', 'pick', 'whole', 'useful', 'rush', 'mine', 'toilet', 'enter', 'wedding', 'wood', 'meet', 'stolen', 'hungry', 'card', 'fair', 'crowd', 'glow', 'ocean', 'peace', 'match', 'hill', 'welcome', 'across', 'drag', 'island', 'edge', 'great', 'unlock', 'feet', 'iron', 'wall', 'laser', 'fill', 'boat', 'weird', 'hard', 'happen', 'tiny', 'event', 'math', 'robot', 'recently', 'seven', 'tree', 'rough', 'secret', 'nature', 'short', 'mail', 'inch', 'raise', 'warm', 'gentle', 'gentle', 'glue', 'roll', 'search', 'regular', 'here', 'count', 'hunt', 'keep', 'week', 'soap', 'bread', 'lost', 'mountain', 'tent', 'pack', 'stupid', 'make', 'book', 'mess', 'letter', 'most', 'stay', 'what', 'before', 'more', 'bite', 'lime', 'best', 'rope', 'frog', 'crab', 'pile', 'read', 'sand', 'stuck', 'bottom', 'duck', 'take', 'hurry', 'tail', 'other', 'snake', 'word', 'kite', 'piano', 'hoop', 'mother', 'lazy', 'knock', 'please', 'over', 'igloo', 'bath', 'bean', 'lung', 'umbrella', 'bomb', 'spin', 'sorry', 'back', 'less', 'turn', 'bell', 'stick', 'song', 'energy', 'late', 'paint', 'near', 'crap', 'sour', 'hide', 'rabbit', 'never', 'store', 'jingle', 'jump', 'jelly', 'people', 'poop', 'turtle', 'melon', 'loose', 'sugar', 'spring', 'ring', 'poke', 'rice', 'sweet', 'star', 'friend', 'coat', 'clap', 'part', 'lemon', 'soon', 'lamp', 'like', 'spoon', 'milk', 'noise', 'giraffe', 'salt', 'tiger', 'sack', 'nope', 'left', 'sock', 'marble', 'mirror', 'lick', 'king', 'eagle', 'toast', 'straw', 'cone', 'hear', 'apple', 'fart', 'echo', 'good', 'doll', 'dumb', 'munch', 'mouse', 'hose', 'fence', 'sick', 'pole', 'goose', 'onion', 'super', 'some', 'lizard', 'deer', 'panda', 'mouth', 'monkey', 'soup', 'maybe', 'white', 'cake', 'seed', 'comb', 'sing', 'first', 'silly', 'miss', 'laugh', 'mask', 'after', 'wave', 'grape', 'fear', 'same', 'made', 'drip', 'quack', 'hundred', 'teach', 'koala', 'octopus', 'right', 'pizza', 'park', 'giant', 'next', 'monster', 'foot', 'plate', 'list', 'dance', 'goat', 'horn', 'banana', 'each', 'drink', 'potato', 'cheese', 'feather', 'voice', 'crack', 'smell', 'slam', 'hiccup', 'sunny', 'puke', 'cloud', 'stripe', 'dress', 'tummy', 'hang', 'meow', 'cook', 'there', 'front', 'fork', 'zipper', 'slow', 'juggle', 'wheel', 'butt', 'purse', 'burn', 'taco', 'candy', 'puddle', 'dragon', 'tomato', 'ladder', 'yawn', 'earth', 'wand', 'noodle', 'sink', 'corn', 'fresh', 'stack', 'drum', 'fifty', 'extra', 'because', 'rubber', 'cage', 'chicken', 'black', 'tooth', 'hippo', 'underwear', 'pencil', 'spill', 'sleep', 'cave', 'chair', 'carrot', 'score', 'dizzy', 'boom', 'roar', 'pipe', 'sweat', 'alphabet', 'steam', 'puppy', 'club', 'think', 'surprise', 'string', 'spit', 'plane', 'slip', 'snail', 'thing', 'unicorn', 'bunny', 'brush', 'pillow', 'balloon', 'animal', 'stir', 'tablet', 'twist', 'butter', 'scream', 'wizard', 'donut', 'buzz', 'swing', 'smart', 'boring', 'soft', 'kitty', 'smile', 'wash', 'shape', 'puzzle', 'tire', 'snack', 'below', 'soda', 'pancake', 'climb', 'pinch', 'favorite', 'weed', 'pants', 'yellow', 'roof', 'again', 'stare', 'clock', 'penguin', 'pocket', 'grumpy', 'swim', 'snow', 'dude', 'goop', 'shout', 'lucky', 'ceiling', 'circle', 'belt', 'better', 'bird', 'five', 'popcorn', 'four', 'sandwich', 'fuzzy', 'pasta', 'fridge', 'oops', 'fruit', 'salad', 'board', 'flower', 'blood', 'forest', 'couch', 'fixed', 'apology', 'bicycle', 'imagination', 'castle', 'brick', 'starve', 'squiggle', 'region', 'setting', 'squeak', 'biscuit', 'goldfish', 'launch', 'install', 'flavor', 'calendar', 'emergency', 'burp', 'invent', 'rubbish', 'measure', 'syrup', 'address', 'dish', 'honest', 'adorable', 'retry', 'cliff', 'steep', 'hammock', 'cheat', 'backward', 'tortilla', 'sled', 'bleach', 'scrap', 'gigantic', 'homework', 'barf', 'eject', 'bucket', 'beard', 'muddy', 'legend', 'queasy', 'accessory', 'burrito', 'cancel', 'trombone', 'karate', 'chain', 'whine', 'replay', 'teaspoon', 'accident', 'fireworks', 'weigh', 'sassy', 'correct', 'jackpot', 'squint', 'adventure', 'bobcat', 'sunlight', 'cellphone', 'visitor', 'above', 'bamboo', 'borrow', 'toolbox', 'multiply', 'sparrow', 'discovery', 'obstacle', 'headphones', 'officer', 'computer', 'recover', 'skateboard', 'proof', 'always', 'moss', 'macaroni', 'upset', 'scribble', 'trumpet', 'shadow', 'serve', 'howl', 'shirt', 'along', 'yuck', 'celebrate', 'statue', 'verb', 'crisp', 'goof', 'parade', 'celery', 'subway', 'waist', 'tropical', 'burger', 'gurgle', 'fizzy', 'steady', 'sheet', 'tackle', 'curve', 'shield', 'ding', 'extreme', 'sweep', 'octagon', 'dinosaur', 'gravy', 'slice', 'janitor', 'cement', 'cabbage', 'beetle', 'strawberry', 'angle', 'independent', 'vein', 'guts', 'pandemic', 'split', 'fairy', 'asleep', 'fries', 'hobby', 'broom', 'breakfast', 'ankle', 'sheep', 'scratch', 'breathe', 'insect', 'broke', 'control', 'recipe', 'marshmallow', 'gargle', 'alien', 'shock', 'tongue', 'pressure', 'firefighter', 'angel', 'curtain', 'contest', 'agree', 'shred', 'napkin', 'microphone', 'panic', 'tissue', 'wiggle', 'sprain', 'swamp', 'crunch', 'combine', 'chomp', 'wrestle', 'another', 'bruise', 'tofu', 'sausage', 'valley', 'putty', 'ooze', 'bush', 'alligator', 'grease', 'fierce', 'battery', 'swallow', 'cookie', 'buckle', 'blur', 'caught', 'ribbon', 'petal', 'slurp', 'alley', 'recess', 'helicopter', 'daisy', 'troll', 'behind', 'trophy', 'groove', 'plush', 'snug', 'doodle', 'succeed', 'swap', 'helmet', 'anger', 'busy', 'defend', 'daddy', 'sweater', 'fidget', 'closet', 'alert', 'shin', 'slug', 'yolk', 'planet', 'ahead', 'wrinkle', 'whistle', 'cabinet', 'muscle', 'fountain', 'pajamas', 'medal', 'wagon', 'pyramid', 'fault', 'focus', 'clump', 'taxi', 'choir', 'button', 'quesadilla', 'brunch', 'choke', 'fungus', 'package', 'baseball', 'flute', 'manatee', 'narrow', 'pretend', 'amazing', 'turkey', 'visit', 'rectangle', 'purr', 'skull', 'shark', 'shave', 'cheer', 'picnic', 'shower', 'shelf', 'local', 'velcro', 'upward', 'hamburger', 'spaghetti', 'gravity', 'thigh', 'beauty', 'kazoo', 'elbow', 'garlic', 'flamingo', 'organ', 'crayon', 'pumpkin', 'flour', 'floss', 'tweet', 'twig', 'should', 'smear', 'shovel', 'crud', 'challenge', 'sharp', 'bridge', 'spike', 'crawl', 'carpet', 'away', 'shoulder', 'skirt', 'glitter', 'carry', 'clown', 'dimple', 'sword', 'gallon', 'envelope', 'bribe', 'upstairs', 'vitamin', 'pantry', 'mattress', 'squirrel', 'rocket', 'circus', 'rainbow', 'sprint', 'bait', 'cheek', 'study', 'bacon', 'chunk', 'reef', 'berry', 'spine', 'skeleton', 'dolphin', 'sandal', 'mushroom', 'elevator', 'anchor', 'blink', 'fang', 'chase', 'squab', 'buddy', 'parachute', 'model', 'guitar', 'squeeze', 'bench', 'awesome', 'instant', 'triangle', 'drizzle', 'beep', 'sneeze', 'airplane', 'material', 'skip', 'blind', 'spark', 'burnt', 'tennis', 'waddle', 'skin', 'subtract', 'clack', 'sunset', 'crush', 'gutter', 'sneak', 'bagel', 'breeze', 'mommy', 'student', 'smash', 'balance', 'scoot', 'icky', 'crease', 'fantastic', 'allergy', 'shake', 'dough', 'cramp', 'blush', 'scissors', 'bulb', 'scoop', 'wham', 'coast', 'belly', 'growl', 'spider', 'cheap', 'couple', 'stale', 'diamond', 'gunk', 'blog', 'grump', 'snot', 'annoy', 'scroll', 'sewer', 'corner', 'truce', 'aunt', 'bang', 'coconut', 'furry', 'saddle', 'switch', 'squish', 'curb', 'cash', 'force', 'braid', 'costume', 'mumble', 'boost', 'shrug', 'lobster', 'whisper', 'instead', 'snip', 'treasure', 'cheddar', 'meteor', 'bass', 'raffle', 'poodle', 'dentist', 'snuggle', 'fossil', 'crater', 'cactus', 'chalk', 'giggle', 'cricket', 'squid', 'video', 'polite', 'stairs', 'yummy', 'referee', 'dodge', 'redo', 'shiny', 'journey', 'vaccine', 'bling', 'bingo', 'wasp', 'mosquito', 'warn', 'wheat', 'toes', 'flash', 'guacamole', 'arch', 'midway', 'shampoo', 'turd', 'hollow', 'news', 'century', 'waffle', 'globe', 'attack', 'author', 'cereal', 'shade', 'clothes', 'arrow', 'cemetery', 'stiff', 'sleeves', 'cinnamon', 'goober', 'skunk', 'cough', 'blast', 'chug', 'honk', 'tantrum', 'gulp', 'vampire', 'trash', 'candle', 'volcano', 'relax', 'sunrise', 'dollar', 'nifty', 'football', 'tangle', 'blank', 'sniff', 'brake', 'pouch', 'droop', 'vegetable', 'bully', 'mushy', 'faucet', 'comfortable', 'traffic', 'cucumber', 'orphan', 'basket', 'diary', 'rumble', 'pudding', 'mutter', 'lobby', 'cousin', 'satellite', 'lollipop', 'swoop', 'erase', 'tuba', 'shallow', 'chore', 'mould', 'critter', 'flick', 'buffalo', 'expert', 'headache', 'sparkle', 'creak', 'gobble', 'bobble', 'pearl', 'pounce', 'weekend', 'grumble', 'broccoli', 'thanks', 'toddler', 'scrub', 'chew', 'scooter', 'funnel', 'tornado', 'raspberry', 'crumble', 'attic', 'electricity', 'cherry', 'thumb', 'cotton', 'coach', 'safety', 'frown', 'around', 'receipt', 'tattle', 'ranch', 'palace', 'yogurt', 'airport', 'scary', 'station', 'spank', 'language', 'goggles', 'comet', 'yoga', 'blob', 'oatmeal', 'stomach', 'community', 'splash', 'snooze', 'hiss', 'shrink', 'bound', 'reply', 'wrench', 'devil', 'cushion', 'polish', 'chapter', 'ambulance', 'niece', 'drool', 'attitude', 'whoa', 'crouch', 'ruler', 'release', 'princess', 'unicycle', 'delicious', 'shuffle', 'catapult', 'apron', 'area', 'wallet', 'captain', 'shaggy', 'altogether', 'country', 'cupboard', 'original', 'avocado', 'fluff', 'cocoon', 'awake', 'tutu', 'reptile', 'drawer', 'improve', 'grocery', 'caterpillar', 'booth', 'disappear', 'pelican', 'turbo', 'setup', 'curious', 'blanket', 'dibs', 'pastry', 'chatter', 'nuclear', 'partner', 'scarf', 'valentine', 'barrel', 'blah', 'surface', 'chemical', 'bravo', 'stadium', 'expect', 'cartoon', 'capital', 'waggle', 'attention', 'similar', 'pedal', 'diaper', 'rattle', 'scatter', 'siren', 'crocodile', 'chimney', 'pollen', 'pavement', 'teapot', 'village', 'flex', 'attach', 'canoe', 'cavity', 'bonk', 'army', 'hawk', 'spinach', 'explain', 'channel', 'tractor', 'recycle', 'skinny', 'escape', 'spicy','jiggle','root','join','reach','write','internet','dream','live','horse','lying','success','cost','wild','whatever','pilot','active','luck','kiss','parent','judge','though','world','movie','team','record','knot','bottle','later','oldest','tool','bone','morning','comfy','sign','summer','famous','tape','page','hate','under','engine','build','look','friends','hall','print','hero','throw','excellent','trust','copy','daughter','answer','future','info','watch','street','argue','nervous','dinner','target','call','something','laptop','quiet','hope','paper','home','jewel','said','lava','bathroom','rest','flow','unusual','girl','teeth','stand','push','nest','finish','zone','desk','bubble','remove','magic','trade','click','love','jacket','body','keyboard','normal','allow','crazy','present','office','every','house','okay','knee','clean','honey','inside','night','practice','beach','lift','action','garbage','favor','phone','power','start','thick','plant','protect','game','joke','since','brother','fifth','large','second','pool','water','last','taste','hook','already','dead','quit','lunch','yell','cause','understand','different','nice','website','learn','door','line','radio','touch','mean','sister','feel','spread','date','year','nose','universe','whose','side','sound','support','walk','decide','sure','online','high','health','size','garden','child','patch','hint','tell','found','level','deep','probably','plan','anyway','ground','today','hurt','point','town','science','unhappy','pair','round','lion','trouble','land','hand','wire','alive','picture','firm','between','everyone','prison','truck','kitchen','paid','desert','half','terrible','whale','twice','machine','quality','beautiful','fight','grab','nothing','little','heart','matter','juice','play','plug','public','stop','mission','heat','room','band','open','three','equal','gold','mistake','naked','school','listen','accept','spot','come','guess','grow','problem','handle','owner','almost','give','spend','huge','finger','need','itself','dozen','road','help','place','farm','afraid','time','core','doing','tonight','ignore','change','tomorrow','nurse','head','fancy','gate','rise','freeze','report','tank','cool','exactly','neat','course','chip','nail','garage','question','mind','promise','outside','draw','care','talk','storm','restaurant','drop','flag','fire','serious','metal','ketchup','path','worm','gone','noon','glass','mile','city','neck','eight','risky','mall','remote','table','space','bike','lake','grade','race','bank','tight','wide','alone','cold','trip','leader','empty','connect','rain','president','past','dust','easy','life','music','center','email','father','impossible','test','face','jersey','teacher','step','loud','tower','screen','person','long','happy','jealous','special','forget','create','nation','theater','season','somebody','money','food','check','excuse','heard','branch','story','show','wish','junk','illegal','nobody','blue','wind','without','cable','olive','angry','supposed','private','pull','uncle','moon','orange','know','green','find','perfect','quilt','pretty','horrible','number','basic','label','until','chance','glove','photo','none','square','ticket','close','least','zebra','human','wipe','replace','bunch','stuff','discover','rich','idea','hold','share','yeah','full','lower','hidden','quarter','scale','rescue','winter','anyone','break','wing','hour','myself','work','imagine','bring','nine','speed','wear','magnet','period','ball','message','straight','pass','oven','kick','meat','hair','speak','wait','jungle','party','flew','heavy','note','queen','long','floor','real','camera','wonderful','exit','name','wrist','deal','truth','hotel','double','zoom','group','safe','block','hospital','worst','kangaroo','business','against','minute','quick','bake','family','funny','chocolate','light','menu','leaf','thought','ship','magazine','hike','shut','police','popular','mark','title','river','true','laundry','window','trick','zero','flip','baby','lock','save','done','respect','doctor','dark','ready','woman','train','early','belong','boot','together','fall','danger','gift','bright','reason','hello','library','ride','remember','fish','free','jumbo','relief','young','want','jerk','tall','month','enough','worry','either','move','rule','fast','rock','project','exercise','yourself','elephant','class','important','field','take','adventure','goof','deer','officer','wrong','warm','cone','near','grape','spit','part','pocket','trombone','monster','yellow','math','lost','cook','word','snake','foot','pinch','useful','balloon','syrup','spill','bleach','castle','rough','brick','drip','fill','pizza','sleep','wizard','puppy','never','celebrate','boat','dance','sink','read','potato','good','enter','neighbor','quack','retry','candy','sweat','spring','tortilla','ugly','voice','weird','stay','region','roof','corn','sour','salt','park','fruit','onion','sorry','sand','favorite','extra','bottom','borrow','purse','right','kitty','like','parade','echo','legend','snail','always','moss','seven','calendar','fresh','whine','knob','mess','computer','turtle','piano','meow','discovery','each','stupid','burp','mirror','cloud','bean','pack','multiply','stream','fair','sled','tooth','teaspoon','recover','lizard','spoon','hole','nature','launch','mail','over','wheel','tablet','flower','swim','thing','ladder','headphones','sparrow','birthday','bread','begin','useless','cancel','beard','feet','tent','burrito','jingle','knife','lemon','fifty','seed','toast','macaroni','poop','hill','igloo','lazy','snow','jackpot','donut','hiccup','crap','squeak','circle','pencil','frame','tackle','nope','sweep','random','buzz','grass','bear','ding','please','ocean','dress','wall','extreme','fuzzy','jelly','dumb','goop','secret','hang','sugar','tree','hose','cheese','popcorn','drum','guest','cheat','noise','squint','eagle','drink','karate','umbrella','four','smile','puddle','kite','fence','backward','mouse','stick','drag','toolbox','shape','dish','white','tiger','bite','pillow','short','cellphone','statue','inch','goat','tail','skateboard','rubbish','queasy','dinosaur','accident','adorable','emergency','regular','comb','laugh','barf','lesson','return','address','chicken','waist','correct','lick','black','ring','crash','along','grumpy','tomato','earth','boom','miss','fridge','catch','wood','install','steady','butter','hungry','measure','pipe','keep','alphabet','mouth','paint','same','frog','honest','stare','hundred','scribble','animal','strong','before','back','loop','replay','unicorn','raise','left','fear','rubber','duck','again','sing','giraffe','super','mountain','event','turn','munch','goose','cave','plane','steam','send','pants','sunlight','laser','clap','kitten','soda','letter','other','fizzy','king','apple','lime','feather','crack','muddy','silly','think','gentle','bamboo','rice','sell','scream','fixed','smell','some','less','forest','shirt','mine','glue','slam','horn','club','dude','flavor','gentle','fart','best','yuck','hide','late','soft','pile','curve','gigantic','rose','upset','book','accessory','crowd','burger','most','koala','monkey','friend','chain','teach','juggle','hard','stuck','climb','dragon','hunt','sheet','unlock','invent','bird','stripe','sassy','cage','puke','steep','howl','bucket','mask','list','smart','plate','melon','winner','roar','next','hear','star','spin','unfair','above','apology','underwear','because','here','peace','penguin','happen','poke','maybe','wave','tire','robot','straw','marble','rush','wedding','shout','there','octagon','hurry','butt','great','shadow','hoop','continue','edge','store','tummy','fork','dizzy','knock','made','cake','panda','iron','snack','ceiling','biscuit','sunny','rabbit','five','puzzle','stir','pick','count','tropical','after','stack','middle','mother','blood','surprise','burn','pancake','jump','clock','salad','celery','bobcat','gurgle','verb','search','sandwich','serve','loose','banana','lucky','score','island','visitor','bath','doll','chair','fireworks','proof','tiny','rope','sweet','sock','scrap','setting','people','oops','hippo','board','thin','front','homework','hammock','drive','subway','song','yawn','gross','week','taco','midnight','match','slow','roll','more','welcome','pasta','lung','wand','bomb','toilet','string','eject','better','swing','energy','crisp','slip','lamp','soup','soap','across','starve','below','trumpet','color','weed','bell','make','sick','undo','glow','whole','obstacle','crab','imagination','milk','recently','first','weather','carrot','soon','what','belt','meet','cliff','boring','sack','noodle','brush','weigh','wash','octopus','goldfish','bicycle','coat','stolen','kilometer','squiggle','shield','card','pole','twist','zipper','giant','bunny','couch',],
// hard words were gotten from a top 100 SAT word list https://education.yourdictionary.com/for-students-and-parents/100-most-common-sat-words.html
// later hard words were mined from existing guesses
hard: /* DON'T LOOK CLOSELY UNLESS YOU WANT TO BE SPOILED!!! */['abdicate', 'empathy', 'abate', 'venerable', 'exemplary', 'hackneyed', 'foster', 'aberration', 'clairvoyant', 'extenuating', 'mundane', 'forbearance', 'fortitude', 'prudent', 'hypothesis', 'ephemeral', 'scrutinize', 'capitulate', 'spurious', 'substantiate', 'intuitive', 'tenacious', 'digression', 'prosperity', 'compromise', 'vindicate', 'fraught', 'submissive', 'ostentatious', 'boisterous', 'bias', 'impetuous', 'wary', 'rancorous', 'deleterious', 'amicable', 'reclusive', 'canny', 'superficial', 'emulate', 'frugal', 'perfidious', 'jubilation', 'brusque', 'intrepid', 'sagacity', 'arid', 'inconsequential', 'nonchalant', 'reconciliation', 'brazen', 'prosaic', 'pretentious', 'benevolent', 'aesthetic', 'adversity', 'abhor', 'divergent', 'fortuitous', 'conditional', 'disdain', 'demagogue', 'asylum', 'compassion', 'hedonist', 'condescending', 'querulous', 'collaborate', 'inevitable', 'discredit', 'renovation', 'lobbyist', 'enervating', 'provocative', 'florid', 'convergence', 'subtle', 'diligent', 'surreptitious', 'orator', 'superfluous', 'opulent', 'capacious', 'tactful', 'longevity', 'restrained', 'conformist', 'abstain', 'pragmatic', 'reverence', 'spontaneous', 'anachronistic', 'haughty', 'procrastinate', 'parched', 'camaraderie', 'precocious', 'evanescent', 'impute', 'transient', 'predecessor', 'snorkel', 'confluence', 'pyromaniac', 'remedial', 'genetic', 'conventional', 'digitize', 'corroborate', 'ossify', 'compound', 'proxy', 'innovate', 'harassment', 'disparage', 'sufficient', 'negligence', 'attache', 'dubious', 'mandible', 'temporary', 'regret', 'words', 'convoluted', 'adequate', 'diminish', 'plausible', 'necessity', 'materialistic', 'abysmal', 'osteoporosis', 'diminutive', 'deficient', 'capture', 'nutrition', 'keen', 'delirious', 'laminate', 'lunatic', 'succulent', 'fraternity', 'loathe', 'entrenched', 'effigy', 'hazardous', 'foment', 'dilate', 'condone', 'osmosis', 'hypocrite', 'reconnaissance', 'anomaly', 'counteract', 'delegate', 'subsequent', 'underscore', 'eccentric', 'seethe', 'scallop', 'decree', 'asymmetrical', 'devise', 'enumerate', 'precedent', 'peevish', 'caricature', 'prohibit', 'ridiculous', 'redact', 'restitution', 'dispatch', 'erratic', 'juvenile', 'sacrilegious', 'saucer', 'flagrant', 'feasibility', 'filament', 'undermine', 'reclaim', 'unveil', 'maternity', 'superb', 'exhilarating', 'quirk', 'irreconcilable', 'chasm', 'suspicious', 'garment', 'typical', 'fructose', 'dopamine', 'coarse', 'resilient', 'burble', 'gorge', 'rhombus', 'ambiguous', 'facilitate', 'repudiate', 'adversarial', 'necromancer', 'mercenary', 'jaunt', 'atavistic', 'analogous', 'frock', 'bodacious', 'proletariat', 'sundry', 'theoretical', 'lament', 'contemplate', 'anticipate', 'culmination', 'complement', 'rebuttal', 'viper', 'confide', 'endow', 'galvanize', 'summation', 'constitution', 'prosecute', 'auspices', 'survival', 'gregarious', 'syndicate', 'quorum', 'ferocious', 'surreal', 'melodramatic', 'justify', 'controversial', 'reinforce', 'ubiquitous', 'rustic', 'virtuous', 'dilemma', 'provincial', 'establish', 'yearn', 'catamaran', 'onset', 'regurgitate', 'renounce', 'obsolete', 'nimbus', 'orthogonal', 'amendment', 'kleptomaniac', 'herring', 'marginal', 'conducive', 'invade', 'coincide', 'deference', 'scorn', 'dignity', 'complacent', 'sheath', 'austere', 'postulate', 'coddle', 'nuisance', 'jarring', 'amiable', 'desolate', 'worthwhile', 'condemn', 'indifferent', 'stupendous', 'widget', 'kinetic', 'clout', 'avid', 'theology', 'sporadic', 'cognition', 'confound', 'retention', 'provision', 'knight', 'callous', 'gorgeous', 'refute', 'agitate', 'inundate', 'qualitative', 'gargoyle', 'scandalous', 'restoration', 'chronic', 'dire', 'validate', 'quell', 'cuddle', 'affluent', 'momentous', 'synchronous', 'reconsider', 'objective', 'fraudulent', 'battlement', 'malleable', 'notable', 'impartial', 'gremlin', 'withstand', 'bevel', 'virile', 'petulant', 'preamble', 'squalor', 'fray', 'lavender', 'buccaneer', 'blather', 'calamity', 'excel', 'hypothetical', 'tedious', 'demonstrate', 'nominee', 'leukemia', 'supine', 'flourish', 'peculiar', 'fluctuate', 'easel', 'palliative', 'nuptials', 'asynchronous', 'undulate', 'brothel', 'egregious', 'hostile', 'dominion', 'congregate', 'vicious', 'malicious', 'logarithm', 'conformity', 'restructure', 'stark', 'dependency', 'jeopardize', 'perish', 'incite', 'limbic', 'brawl', 'diversify', 'intimate', 'hegemony', 'warranty', 'allegory', 'diligence', 'mercurial', 'tryst', 'zealot', 'righteous', 'reconcile', 'saber', 'dapper', 'inversion', 'placid', 'immolate', 'proffer', 'unilateral', 'universal', 'rambunctious', 'coordination', 'recompense', 'foreseeable', 'geriatric', 'candid', 'secrete', 'jaded', 'ramification', 'persecute', 'guarantee', 'devious', 'invoke', 'simian', 'astute', 'sparingly', 'concise', 'surly', 'bohemian', 'recite', 'solidarity', 'dearth', 'dilute', 'quench', 'iteration', 'lambaste', 'sociopath', 'timorous', 'valiant', 'apex', 'susceptible', 'comparable', 'fatigue', 'remnant', 'query', 'marauder', 'recreation', 'superlative', 'bogart', 'omnipotent', 'chalice', 'brevity', 'hitherto', 'empirical', 'brute', 'narrative', 'potent', 'advocate', 'intone', 'unprecedented', 'supercilious', 'nautical', 'heritage', 'cadence', 'kiosk', 'quid', 'novice', 'yacht', 'taut', 'quirky', 'delusion', 'grim', 'recoup', 'quizzical', 'unadorned', 'teeming', 'conduct', 'gadget', 'recumbent', 'tension', 'expend', 'tremendous', 'providence', 'navigate', 'robust', 'juncture', 'altercation', 'wallop', 'wreckage', 'intravenous', 'ambivalent', 'prow', 'spawn', 'demur', 'convey', 'demeanor', 'paramount', 'bubonic', 'brackish', 'ornate', 'calibrate', 'substantial', 'temperament', 'niche', 'sumptuous', 'gruesome', 'sustain', 'frankly', 'loiter', 'yield', 'nymph', 'swivel', 'oxymoron', 'emphatic', 'ostensible', 'bolus', 'evoke', 'capitalize', 'adhere', 'conceive', 'lemur', 'reform', 'diabolical', 'delicate', 'savvy', 'contradict', 'sinister', 'warrant', 'litigious', 'arsenal', 'bygones', 'vital', 'nuance', 'fragile', 'articulate', 'precarious', 'brunt', 'jolt', 'rapture', 'paddock', 'conviction', 'deliberate', 'adamant', 'exacerbate', 'surmount', 'acquisition', 'discord', 'jealous', 'vigor', 'allude', 'nascent', 'envy', 'provoke', 'synthesis', 'treacherous', 'oust', 'emit', 'ameliorate', 'paranormal', 'doctrine', 'cultivate', 'blemish', 'surveillance', 'abscond', 'tentative', 'commission', 'blithe', 'reluctant', 'braggart', 'bemuse', 'bumpkin', 'stature', 'khaki', 'eloquent', 'introvert', 'granular', 'cower', 'karma', 'ruminate', 'vintage', 'iota', 'insatiable', 'sublimate', 'fiscal', 'accumulate', 'solvent', 'hydrogen', 'competent', 'salacious', 'apprehensive', 'transparent', 'eminent', 'ostracize', 'consensus', 'horizontal', 'terse', 'infer', 'gauge', 'contender', 'prompt', 'hectare', 'endure', 'subordinate', 'entail', 'lucrative', 'exploit', 'assertion', 'gargantuan', 'hence', 'innate', 'hoist', 'juggernaut', 'concede', 'locomotion', 'exert', 'vestigial', 'quantitative', 'election', 'tabular', 'candor', 'astringent', 'nominal', 'indiscriminate', 'viable', 'reproach', 'kosher', 'civic', 'notorious', 'jubilant', 'triumvirate', 'telemetry', 'judgemental', 'billet', 'dismay', 'clamour', 'renovate', 'imposing', 'transaction', 'bolster', 'prescribe', 'stationary', 'irrational', 'yeti', 'foist', 'dreary', 'novel', 'quaint', 'recalcitrant', 'jovial', 'responsibility', 'deplete', 'pinnacle', 'fumigate', 'forage', 'indulge', 'zombie', 'sodium', 'sage', 'sage', 'annihilate', 'rigorous', 'zenith', 'harbinger', 'cumulative', 'sentiment', 'fundamental', 'principle', 'collate', 'joust', 'reticent', 'knack', 'deference', 'rancid', 'aura', 'imminent', 'concur', 'lye', 'defer', 'vain', 'cogent', 'catastrophe', 'auspicious', 'din', 'relish', 'contour', 'affable', 'concave', 'deluge', 'dastardly', 'ether', 'synthetic', 'commiserate', 'dell', 'amble', 'synergy', 'dominate', 'foist', 'azure', 'daft', 'destitute', 'fable', 'mandate', 'myriad', 'spore', 'estuary', 'gall', 'amenable', 'expel', 'inept', 'bucolic', 'eon', 'gaffe', 'macabre', 'dunce', 'cyst', 'cacophony', 'coherent', 'pallid', 'svelte', 'gander', 'surmise', 'uvula', 'ramble', 'nomenclature', 'pyre', 'enact', 'suss', 'conch', 'vie', 'quail', 'conduit', 'demure', 'frantic', 'recluse', 'ruse', 'crass', 'languish', 'alimony', 'garish', 'sullen', 'indigo', 'queue', 'ozone', 'spat', 'inane', 'intuit', 'mull', 'cede', 'vim', 'congeal', 'recede', 'culpable', 'culminate', 'byte', 'apt', 'median', 'fester', 'dilettante', 'tepid', 'iodine', 'prowess', 'noxious', 'lucrative', 'quibble', 'sully', 'ire', 'condense', 'vex', 'czar', 'emote', 'congress', 'adept', 'deity', 'destiny', 'synonym', 'mnemonic', 'conifer', 'ravenous', 'ghost', 'inverse', 'suture', 'cooperate', 'tyrant', 'contempt', 'gyrate', 'recant', 'vestibule', 'aorta', 'hubris', 'reed', 'sustenance', 'sublime', 'garrulous', 'frail', 'vacuum', 'fraud', 'vile', 'pernicious', 'quip', 'intuition', 'myopic', 'isthmus', 'avarice', 'jackal', 'maudlin', 'tabulate', 'irate', 'lucid', 'deter', 'omen', 'postulate', 'blight', 'conflate', 'jocular', 'salient', 'hiatus', 'raze', 'elegant', 'convex', 'surge', 'oblong', 'reign', 'comrade', 'bray', 'aghast', 'cunning', 'valor', 'suave', 'modicum', 'cogitate', 'conundrum', 'jeopardy', 'coincidence', 'wan', 'reckless', 'conical', 'invert', 'abrupt', 'aggravate', 'alkaline', 'allure', 'amateur', 'ambient', 'anvil', 'augment', 'axiom', 'bellicose', 'belligerent', 'buccaneer', 'byzantine', 'dogma', 'tangent', 'preen', 'lurid', 'querulous', 'conceit', 'irascible', 'synopsis', 'illicit', 'languid', 'matte', 'facetious', 'deciduous', 'tenacious', 'catatonic', 'rupture', 'dirigible', 'rhetoric', 'caustic', 'connive', 'indigenous', 'eulogy', 'despot', 'malice', 'surfeit', 'zany', 'entropy', 'frazzle', 'indignant', 'convivial', 'synapse', 'fallacy', 'maverick', 'iridescent', 'turgid', 'futile', 'lavish', 'cognizant', 'regale', 'maelstrom', 'quixotic', 'dystopia', 'flagrant', 'quintessential', 'vivacious', 'deign', 'knave', 'cipher', 'gallant', 'clandestine', 'concatenate', 'deranged', 'rudimentary', 'quaff', 'demented', 'lozenge', 'raucous', 'cistern', 'feral', 'prescient', 'fraternize', 'oscillate', 'surmount', 'immolate', 'syndicate', 'condescend', 'connotation', 'scandal', 'denigrate', 'tenuous', 'indolent', 'cabal', 'dichotomy', 'stymie', 'fatuous', 'furtive', 'susceptible', 'denizen', 'tumult', 'exonerate', 'effigy', 'sagacious', 'luminous', 'miasma', 'congruent', 'vilify', 'coalesce', 'putrid', 'manipulate', 'ludicrous', 'crustacean', 'rigor', 'jamboree', 'petulant', 'lambast', 'effervescent', 'tacit', 'detriment', 'wallow', 'derelict', 'craven', 'pernicious', 'quarantine', 'folly', 'obelisk', 'relegate', 'cohort', 'sycophant', 'ratify', 'vindicate', 'deride', 'malevolent', 'lithe', 'klaxon', 'caliber', 'degenerate', 'irradiate', 'paranoid', 'demigod', 'erudite', 'nautical', 'jugular', 'diatribe', 'copious', 'surrogate', 'voracious', 'umbrage', 'dexterity', 'pallor', 'remedy', 'repent', 'eavesdrop', 'rampant', 'ceviche', 'inanimate', 'archaic', 'evince', 'frivolous', 'filibuster', 'idiomatic', 'moult', 'satchel', 'angst', 'indict', 'supplement', 'eloquence', 'trivial', 'scoundrel', 'perigee', 'nautilus', 'paranoia', 'prism', 'decipher', 'proverbial', 'idol', 'cartilage', 'discontinuous', 'chauffeur', 'rappel', 'stalactite', 'semblance', 'guttural', 'savory', 'omniscient', 'mortify', 'excrement', 'filch', 'supplicant', 'hallucinate', 'bootleg', 'vacate', 'recuperate', 'sundries', 'schematic', 'tamarind', 'congenial', 'forensic', 'verdict', 'castigate', 'truncate', 'stagnant', 'maleficent', 'abalone', 'integrity', 'proactive', 'simile', 'banshee', 'fillet', 'arboreal', 'plagiarism', 'microbe', 'relapse', 'aspiration', 'fission', 'hellacious', 'filial', 'requiem', 'chauvinism', 'symposium', 'besmirch', 'quarrel', 'miscellaneous', 'onerous', 'swashbuckler', 'subservient', 'allele', 'entourage', 'fondue', 'neurotic', 'ardent', 'lilt', 'verdant', 'bode', 'cynic', 'contiguous', 'epaulet', 'rampage', 'wyvern', 'bluster', 'malady', 'longitude', 'mosaic', 'yurt', 'tyranny', 'laud', 'tangible', 'lateral', 'enzyme', 'usurp', 'conjecture', 'facade', 'pander', 'abscess', 'loquacious', 'demise', 'masticate', 'coefficient', 'quiescent', 'indicative', 'ambidextrous', 'grotto', 'oracle', 'dollop', 'cobalt', 'gaudy', 'anonymous', 'diurnal', 'despondent', 'collage', 'gyroscope', 'vanguard', 'tantamount', 'juxtaposition', 'syllabus', 'emancipate', 'roil', 'asinine', 'euphemism', 'wrath', 'elongate', 'vector', 'tincture', 'asymptomatic', 'pneumonia', 'sentient', 'buttress', 'exhume', 'conglomerate', 'sacrifice', 'eerie', 'subliminal', 'blunder', 'doff', 'vitriol', 'melancholy', 'forfeit', 'pertinent', 'alleviate', 'annotate', 'renege', 'denounce', 'igneous', 'fickle', 'delectable', 'perjury', 'delinquent', 'dissuade', 'mezzanine', 'euphoria', 'pristine', 'curtail', 'harangue', 'peril', 'rhizome', 'halitosis', 'agnostic', 'copse', 'pensive', 'trundle', 'spartan', 'annul', 'banal', 'fastidious', 'abut', 'suede', 'turbulent', 'avast', 'persevere', 'elide', 'luscious', 'placate', 'churlish', 'cauterize', 'reprobate', 'fugue', 'hibernate', 'verve', 'atrophy', 'adroit', 'catacomb', 'privy', 'concentric', 'saturate', 'addendum', 'ricochet', 'fallow', 'manifold', 'accrue', 'morose', 'bemoan', 'impasse', 'sylvan', 'aviary', 'exude', 'stipulate', 'sedentary', 'ogre', 'trellis', 'conscience', 'ingot', 'dendrite', 'torrent', 'cytoplasm', 'jargon', 'devolve', 'curmudgeon', 'tarnish', 'citadel', 'coup', 'wanton', 'itinerant', 'heretic', 'ineffable', 'mandatory', 'omnivore', 'vagabond', 'quash', 'flippant', 'diffident', 'vacillate', 'innocuous', 'heuristic', 'bombastic', 'parabola', 'ballast', 'cairn', 'rapt', 'haptic', 'cylinder', 'integral', 'reprise', 'auxiliary', 'derivative', 'fervent', 'dilapidated', 'axis', 'parapet', 'segue', 'torque', 'ambrosia', 'eligible', 'allegiance', 'isotope', 'ligament', 'peruse', 'abrasive', 'solstice', 'meticulous', 'coniferous', 'ingenious', 'litmus', 'blatant', 'paltry', 'salivate', 'cordial', 'derogatory', 'magnanimous', 'immaculate', 'concoct', 'trope', 'privilege', 'latitude', 'lathe', 'malign', 'vehement', 'swelter', 'bequeath', 'aperture', 'etymology', 'alacrity', 'rancor', 'dervish', 'obfuscate', 'placard', 'alabaster', 'miser', 'collateral', 'rotund', 'repugnant', 'renaissance', 'cranium', 'epoch', 'fracture', 'travesty', 'envoy', 'clamber', 'cadaver', 'cypher', 'mirth', 'dirge', 'morbid', 'culvert', 'supplant', 'pundit', 'grovel', 'truant', 'avert', 'soporific', 'mead', 'fallible', 'diode', 'levitate', 'elucidate', 'vociferous', 'arduous', 'stringent', 'rampart', 'cavalier', 'pterodactyl', 'truculent', 'foray', 'secular', 'neuron', 'squander', 'essence', 'cypress', 'vanquish', 'enigma', 'swindle', 'rummage', 'charisma', 'anagram', 'torrid', 'bespoke', 'depose', 'sovereign', 'abyss', 'ambiance', 'vindictive', 'asymptote', 'drivel', 'relent', 'arcane', 'fulcrum', 'nepotism', 'lymph', 'etiquette', 'assent', 'nougat', 'aptitude', 'conflagration', 'mage', 'density', 'revel', 'rapport', 'vertigo', 'ebullient', 'pacify', 'lattice', 'tempest', 'loam', 'sediment', 'fiend', 'nefarious', 'grief', 'livid', 'egress', 'fungible', 'punitive', 'palpable', 'maladroit', 'eviscerate', 'akimbo', 'cataclysm', 'ascertain', 'wrangle', 'opaque', 'olfactory', 'heft', 'averse', 'abolish', 'reprimand', 'arable', 'aggregate', 'strident', 'admonish', 'romp', 'sympathy', 'foliage', 'ardor', 'atrium', 'arachnid', 'intangible', 'duvet', 'morass', 'treason', 'lenient', 'moribund', 'vicarious', 'repute', 'veracity', 'aloof', 'bodice', 'talisman', 'rubric', 'confiscate', 'reminisce', 'rejuvenate', 'assail', 'cretin', 'moxie', 'pertain', 'gripe', 'misanthrope', 'assimilate', 'hectic', 'epiphany', 'exhort', 'fondant', 'lecherous', 'alibi', 'flack', 'effusive', 'gambit', 'sine', 'droll', 'chide', 'pontificate', 'exquisite', 'watt', 'paucity', 'tsunami', 'contrive', 'volt', 'flamboyant', 'epitome', 'tithe', 'heresy', 'fetid', 'trauma', 'parity', 'detritus', 'tactile', 'feign', 'brandish', 'nexus', 'clavicle', 'marsupial', 'validity', 'atone', 'saffron', 'demarcate', 'forlorn', 'symbiosis', 'cryptic', 'ellipse', 'inebriate', 'pungent', 'perennial', 'onus', 'luge', 'flux', 'imbibe', 'pedantic', 'ennui', 'derisive', 'placebo', 'swill', 'bereft', 'platitude', 'alliteration', 'arbitrary', 'vantage', 'grotesque', 'apprehend', 'allegation', 'bivouac', 'miscreant', 'insidious', 'plethora', 'malaise', 'arrogant', 'amnesty', 'ambulatory', 'manacle', 'enunciate', 'ambience', 'subdue', 'pummel', 'arboretum', 'tendril', 'gauche', 'cerulean', 'apathy', 'detract', 'bauble', 'prototype', 'requisite', 'autistic', 'panacea', 'dote', 'potable', 'latent', 'vigilant', 'flummox', 'magma', 'draconian', 'heist', 'luminary', 'viscous', 'vernacular', 'obscure', 'rivet', 'exuberant', 'mirage', 'concoction', 'tranquil', 'diaspora', 'cuneiform', 'attrition', 'nemesis', 'cyclops', 'inculcate', 'herald', 'hysterical', 'oblique', 'coalition', 'matriarch', 'finagle', 'zest', 'druid', 'plight', 'volatile', 'aspirate', 'edifice', 'collude', 'vogue', 'blasphemy', 'repose', 'savant', 'traipse', 'fetter', 'cadre', 'salve', 'cantankerous', 'percolate', 'posterior', 'asymmetric', 'ballistic', 'hone', 'nullify', 'immutable', 'assuage', 'doldrums', 'emasculate', 'heinous', 'ampersand', 'pantomime', 'pilfer', 'crescent', 'ambulate', 'provenance', 'valise', 'lascivious', 'feasible', 'venerate', 'convalesce', 'peddle', 'reprieve', 'alias', 'promenade', 'pittance', 'arbitrate', 'apprise', 'fluke', 'bizarre', 'abject', 'titillate', 'laudable', 'oblige', 'rescind', 'insipid', 'incandescent', 'subterfuge', 'barrage', 'bulbous', 'basal', 'puce', 'laconic', 'plinth', 'exodus', 'grimace', 'febrile', 'vigil', 'suppress', 'tuppence', 'treachery', 'perturb', 'burlesque', 'bawdy', 'amnesia', 'festoon', 'acclimate', 'adorn', 'succinct', 'nebula', 'abode', 'fiasco', 'poignant', 'fruition', 'colloquial', 'obstinate', 'crucible', 'verisimilitude', 'attenuate', 'viceroy', 'ventricle', 'rouge', 'lichen', 'frigate', 'obsequious', 'concomitant', 'visage', 'instigate', 'ascent', 'hellion', 'wraith', 'revamp', 'visceral', 'saga', 'tragedy', 'aplomb', 'imbue', 'attribute', 'exorbitant', 'firmament', 'crevice', 'volition', 'tenet', 'insolent', 'grommet','brazen','grim','condone','bohemian','deliberate','petulant','candid','dilate','syndicate','analogous','establish','provoke','ossify','survival','quizzical','boisterous','ridiculous','ramification','venerable','compound','oust','evanescent','recite','reconcile','rhombus','retention','saucer','scrutinize','gorgeous','fructose','condemn','demeanor','sinister','palliative','flagrant','justify','surveillance','iteration','chalice','culmination','articulate','convergence','intravenous','dearth','divergent','eccentric','yearn','nymph','dominion','rebuttal','recoup','filament','exacerbate','virile','foment','diminish','proletariat','coordination','capitulate','malicious','fortitude','warrant','obsolete','abysmal','swivel','regret','taut','impetuous','doctrine','herring','precedent','inconsequential','tenacious','affluent','recompense','melodramatic','stupendous','allegory','placid','gruesome','pretentious','conducive','buccaneer','battlement','diminutive','hitherto','ambivalent','resilient','pragmatic','restructure','dependency','jaunt','comparable','nutrition','redact','fragile','concise','proffer','perish','cultivate','nuisance','arsenal','vital','tedious','blather','nuptials','attache','gargoyle','caricature','warranty','nautical','complacent','sporadic','marginal','subsequent','evoke','notable','amiable','apex','compassion','quid','reconnaissance','ornate','condescending','surreal','reinforce','effigy','gadget','snorkel','coddle','amendment','sociopath','vicious','compromise','querulous','temporary','inevitable','saber','complement','auspices','lobbyist','facilitate','hostile','leukemia','deference','seethe','diversify','qualitative','sparingly','orthogonal','procrastinate','decree','dopamine','superlative','orator','peculiar','bubonic','susceptible','loiter','convoluted','anticipate','fraternity','scorn','abhor','momentous','invade','tremendous','timorous','digitize','rambunctious','intone','haughty','bodacious','sumptuous','calibrate','bygones','diligent','paranormal','asymmetrical','anomaly','empirical','commission','devious','unadorned','simian','delegate','peevish','foreseeable','conduct','necessity','ferocious','entrenched','innovate','quirk','pyromaniac','contemplate','brute','delusion','diabolical','potent','benevolent','provocative','cuddle','remnant','unveil','galvanize','juncture','exhilarating','inversion','jeopardize','inundate','intrepid','asynchronous','precarious','prosaic','substantial','acquisition','constitution','astute','prow','easel','nascent','nonchalant','capitalize','fluctuate','brawl','sagacity','virtuous','repudiate','hegemony','immolate','controversial','reconsider','conviction','niche','narrative','exemplary','recumbent','brackish','sheath','perfidious','blemish','proxy','allude','forbearance','kiosk','solidarity','dire','contradict','theology','providence','aberration','delirious','extenuating','erratic','fortuitous','braggart','jolt','canny','validate','confound','asylum','reform','materialistic','righteous','cognition','excel','jaded','irreconcilable','anachronistic','fraudulent','typical','longevity','mandible','coincide','juvenile','callous','provincial','restitution','loathe','collaborate','synthesis','surmount','tactful','conventional','rapture','ameliorate','congregate','hypocrite','impute','teeming','necromancer','viper','hazardous','florid','logarithm','adequate','hypothesis','frugal','omnipotent','capture','devise','avid','navigate','vindicate','malleable','hypothetical','zealot','foster','fray','bevel','renovation','chronic','brunt','savvy','universal','hedonist','emulate','heritage','spawn','withstand','conformity','gregarious','negligence','renounce','lavender','frock','bogart','underscore','objective','refute','squalor','sufficient','osteoporosis','discord','ostentatious','delicate','adversity','convey','remedial','maternity','spontaneous','plausible','novice','rancorous','tension','wary','confluence','lemur','harassment','quench','emphatic','mercenary','valiant','scandalous','limbic','robust','osmosis','tryst','dubious','dapper','fatigue','yield','prudent','onset','query','disparage','succulent','substantiate','intuitive','worthwhile','advocate','laminate','enervating','ostensible','dilute','yacht','conformist','sustain','atavistic','transient','spurious','sundry','demonstrate','surreptitious','intimate','nuance','corroborate','supercilious','quirky','digression','jealous','temperament','prosperity','dignity','gremlin','quell','ambiguous','restrained','genetic','wreckage','litigious','expend','indifferent','enumerate','brothel','prohibit','submissive','jubilation','marauder','demagogue','geriatric','lament','deleterious','counteract','deficient','scallop','bolus','desolate','clout','prosecute','endow','conditional','kinetic','catamaran','ephemeral','lambaste','provision','brevity','kleptomaniac','reverence','coarse','clairvoyant','parched','precocious','persecute','reluctant','sacrilegious','lunatic','gorge','vigor','incite','regurgitate','superfluous','discredit','reconciliation','paddock','disdain','hackneyed','guarantee','confide','synchronous','knight','postulate','suspicious','recreation','unprecedented','undermine','reclusive','treacherous','quorum','dilemma','tentative','abstain','dispatch','agitate','unilateral','summation','subtle','fraught','superb','secrete','demur','garment','mercurial','stark','oxymoron','chasm','conceive','nimbus','words','wallop','bias','brusque','adversarial','emit','altercation','diligence','arid','reclaim','opulent','adamant','calamity','impartial','restoration','nominee','paramount','rustic','jarring','capacious','undulate','frankly','austere','adhere','widget','camaraderie','blithe','superficial','predecessor','aesthetic','envy','ubiquitous','mundane','keen','feasibility','supine','abscond','amicable','egregious','theoretical','cadence','surly','preamble','invoke','burble','flourish','prescribe','annihilate','usurp','manipulate','indigenous','fondue','alkaline','lucrative','verdict','demure','pyre','ire','bluster','rigor','tyrant','supplement','furtive','spat','quarrel','telemetry','dreary','tamarind','putrid','quintessential','simile','surmount','isthmus','catastrophe','stalactite','surrogate','requiem','reticent','khaki','kosher','supplicant','frail','postulate','indignant','futile','pallid','chauvinism','gargantuan','vilify','relapse','harbinger','tenuous','garish','indigo','byte','dilettante','concede','malevolent','cipher','eavesdrop','iridescent','dunce','eulogy','enact','hiatus','paranoia','oracle','gauge','assertion','locomotion','bumpkin','frazzle','dichotomy','cower','longitude','ghost','noxious','ether','introvert','stagnant','tabular','rigorous','symposium','synthetic','cogent','filial','emote','bemuse','rappel','inanimate','indiscriminate','recluse','mosaic','quixotic','aorta','vex','degenerate','infer','pinnacle','insatiable','congeal','intuit','czar','foist','forensic','eminent','caustic','cede','grotto','synopsis','fraud','dystopia','affable','indolent','estuary','repent','zombie','modicum','besmirch','novel','maudlin','perigee','trivial','conflate','axiom','maelstrom','prowess','susceptible','quarantine','jamboree','indulge','aghast','fission','lurid','blight','fable','indict','lucrative','destitute','nautical','proverbial','cooperate','frivolous','foist','filibuster','contender','contiguous','vestigial','yeti','miasma','iodine','abscess','sully','quaff','election','triumvirate','fiscal','quibble','congruent','sentiment','prescient','lambast','languish','transparent','recede','recuperate','tyranny','tumult','commiserate','dexterity','preen','masticate','evince','facetious','ruminate','synergy','crass','cabal','solvent','cogitate','vain','moult','malice','sagacious','myriad','fraternize','hydrogen','coalesce','stymie','exert','detriment','cobalt','pander','reproach','lilt','coefficient','quip','dell','sodium','rancid','rampant','stationary','conjecture','mortify','vivacious','hectare','prompt','synonym','apt','innate','prism','byzantine','conduit','clamour','despot','surge','bootleg','mandate','copious','culminate','jocular','salient','effervescent','joust','contempt','entail','conical','feral','rampage','exploit','quail','filch','scoundrel','oblong','surmise','malady','castigate','vacuum','cartilage','lozenge','dollop','myopic','illicit','recant','civic','dastardly','connive','coincidence','daft','intuition','surfeit','tangible','excrement','jackal','tepid','svelte','abalone','contour','viable','gyrate','onerous','hellacious','cynic','languid','accumulate','juggernaut','karma','ozone','amateur','alimony','klaxon','pernicious','laud','omniscient','inverse','diatribe','principle','obelisk','craven','ludicrous','granular','ravenous','cistern','entourage','endure','erudite','chauffeur','stature','gander','eon','din','fester','reign','syndicate','congenial','nomenclature','immolate','fallacy','hence','demented','ardent','luminous','plagiarism','quantitative','quiescent','frantic','spore','competent','judgemental','discontinuous','congress','hubris','cohort','zany','mull','vindicate','fundamental','turgid','ambidextrous','miscellaneous','renovate','sage','rhetoric','imposing','demigod','cognizant','median','concave','pallor','lateral','destiny','forage','sycophant','wyvern','tenacious','astringent','fillet','deference','voracious','deplete','clandestine','indicative','quaint','loquacious','archaic','folly','bode','salacious','augment','neurotic','querulous','comrade','candor','vacate','flagrant','verdant','ruse','elegant','banshee','gaffe','horizontal','rupture','enzyme','raucous','arboreal','nautilus','maleficent','scandal','paranoid','schematic','amble','gaudy','deity','queue','idiomatic','fatuous','fumigate','consensus','valor','wan','buccaneer','allure','abrupt','jubilant','denigrate','conch','sublimate','reckless','irate','remedy','subordinate','aspiration','concatenate','sustenance','maverick','cacophony','oscillate','relegate','hoist','jovial','sublime','ramble','macabre','mnemonic','rudimentary','vie','zenith','belligerent','truncate','bellicose','dismay','recalcitrant','iota','responsibility','cumulative','conundrum','vintage','allele','collate','subservient','eloquence','ratify','umbrage','convex','lye','jeopardy','vile','deride','concur','coherent','auspicious','lavish','irradiate','aura','condense','sullen','deign','relish','uvula','raze','deciduous','vim','cunning','convivial','defer','catatonic','semblance','swashbuckler','irascible','crustacean','derelict','garrulous','idol','deter','bray','connotation','facade','guttural','reed','microbe','proactive','cyst','amenable','suave','inept','invert','lucid','ceviche','hallucinate','conifer','dogma','suss','ostracize','culpable','yurt','dominate','demise','gallant','eloquent','tangent','regale','inane','notorious','exonerate','imminent','synapse','matte','azure','sundries','denizen','aggravate','angst','knack','effigy','suture','integrity','entropy','sage','savory','vestibule','anvil','caliber','terse','decipher','condescend','dirigible','irrational','jugular','petulant','transaction','satchel','apprehensive','conceit','wallow','epaulet','ambient','gall','nominal','deluge','bucolic','pernicious','expel','bolster','knave','deranged','billet','avarice','tabulate','lithe','omen','adept','tacit',],
};
/* eslint-enable */
// on the frontend because of some counting error we had to duplicate the 618th index word, however, this wasn't a problem on the backend, so remove this from the list when copy-pasting the words from the frontend.
possibleWords.normal = possibleWords.normal.slice(0, 618).concat(possibleWords.normal.slice(619));
possibleWords.hard = possibleWords.hard.slice(0, 618).concat(possibleWords.hard.slice(619));
function lookupWord(dateString, difficulty) {
const date = getDate(dateString);
return getWord(date, difficulty);
}
function getDate(dateString) {
const [year, month, day] = dateString.split('-').map(str => parseInt(str, 10));
return new Date(year, month - 1, day);
}
function dateIsOutsideOfRange(dateString, fromBackup) {
const date = +getDate(dateString);
const now = new Date();
const minutesToUTC = now.getTimezoneOffset();
// UTC+14 is the earliest possible date https://en.wikipedia.org/wiki/UTC%2B14:00
const minutesToEarliestDate = minutesToUTC + (14 * 60);
const earliestEpochTime = +now + (minutesToEarliestDate * 60 * 1000);
// const minutesToLatestDate = minutesToUTC - (12 * 60); // latest is UTC-1200
// const latestEpochTime = +now + (minutesToLatestDate * 60 * 1000);
return date > earliestEpochTime;
// // don't check late submit in non prod so tests can work (probably would be better
// // to mock now or something)
// // FIXME something is really broken with this, but only in prod
// || (!fromBackup && isProd && && date < latestEpochTime);
}
function getWord(date, difficulty) {
const index = getWordIndex(date);
return possibleWords[difficulty][index];
}
function getWordIndex(date) {
const doy = getDOY(date);
const thisYear = date.getFullYear();
const yearsSince2019 = (date.getFullYear() - 2019);
let yearOffset = yearsSince2019 * 365;
// add in days for leap years
for (let y = 2022; y < thisYear; y++) { // FIXME better, this should be since 2019
if (isLeapYear(y)) {
yearOffset += 1;
}
}
return doy + yearOffset - 114;
}
function lookupOtherWord(dateString, wordlist) {
const otherWordList = { normal: 'hard', hard: 'normal' }[wordlist];
return lookupWord(dateString, otherWordList);
}
function integerIsBetweenRange(number, min, max) {
return integerIsGreaterThan(number, min)
&& number < max;
}
function integerIsGreaterThan(number, min) {
return Number.isInteger(number)
&& number > min;
}
// https://stackoverflow.com/questions/8619879/javascript-calculate-the-day-of-the-year-1-366
/* eslint-disable */
function isDuringLeapYear(date) {
var year = date.getFullYear();
return isLeapYear(year);
}
function isLeapYear(year) {
if ((year & 3) != 0) return false;
return ((year % 100) != 0 || (year % 400) == 0);
}
// Get Day of Year
function getDOY(date) {
var dayCount = [0, 31, 59, 90, 120, 151, 181, 212, 243, 273, 304, 334];
var mn = date.getMonth();
var dn = date.getDate();
var dayOfYear = dayCount[mn] + dn;
if (mn > 1 && isDuringLeapYear(date)) dayOfYear++;
return dayOfYear;
};
/* eslint-enable */
module.exports = {
getInvalidReason,
NO_RESPONSE_INVALID_REASONS,
hasBadWord,
};