source: pages/api/postgre/index.js@ 87614a5

main
Last change on this file since 87614a5 was 87614a5, checked in by anastasovv <simon@…>, 2 years ago

Blackjack prototype

  • Property mode set to 100644
File size: 13.3 KB
Line 
1import { v4 as uuidv4 } from 'uuid';
2
3import axios from 'axios';
4
5require('dotenv').config();
6
7const crypto = require('crypto');
8
9const Pool = require('pg').Pool
10const pool = new Pool({
11 connectionString: 'postgres://postgres:postgres@db/postgres'
12});
13
14const sessions = []
15// example session
16// const session = {
17// id,
18// displayName,
19// username,
20// credits,
21// lastActivity,
22// }
23
24// update credits in database
25// setInterval(() => {
26// sessions.filter(session => Date.now() - session.lastActivity > 5*60*1000).forEach(session => {
27// pool.query('UPDATE players SET credits = $1 WHERE username = $2', [session.credits, session.username], (error, results) => {
28// if (error) throw error;
29// });
30// });
31// }, 5*60*1000)
32
33export default function handler(req, res) {
34 /**
35 * GET method
36 */
37 if (req.method === 'GET') {
38 /**
39 * /---------------------- GET ----------------------/
40 * @action give_credits
41 * @param session_id
42 * @param credits
43 */
44 if (req.query?.action === 'add_credits' && req.query?.session_id && req.query?.credits) {
45 const session_id = req.query.session_id
46 const session = sessions.find(session => session.id === session_id)
47
48 if (session) {
49 session.lastActivity = Date.now();
50
51 if (parseInt(req.query.credits) > 0) {
52 session.credits = session.credits + parseInt(req.query.credits)
53
54 pool.query('UPDATE players SET credits = $1 WHERE username = $2', [session.credits, session.username], (error, results) => {
55 if (error) throw error;
56 });
57 }
58
59 if (req.query?.dont_update_stats) {
60 // continue
61 } else {
62 pool.query('SELECT * FROM stats WHERE username = $1', [session.username], (error, results) => {
63 if (error) throw error;
64
65 if (results.rows.length > 0) {
66 const stats = results.rows[0]
67
68 if (parseInt(req.query.credits) > 0) {
69 pool.query('UPDATE stats SET money_earned = $1 WHERE username = $2', [parseInt(stats.money_earned) + parseInt(req.query.credits), session.username], (error, results) => {
70 if (error) throw error;
71 });
72 }
73
74 if (req.query?.game === 'blackjack') {
75 if (req.query?.outcome === 'player_busted' || req.query?.outcome === 'player_lost') {
76 pool.query('UPDATE stats SET blackjack_games = $1 WHERE username = $2', [parseInt(stats.blackjack_games) + 1, session.username], (error, results) => {
77 if (error) throw error;
78 });
79 }
80 else if (req.query?.outcome === 'dealer_busted' || req.query?.outcome === 'player_won') {
81 pool.query('UPDATE stats SET blackjack_games = $1, blackjack_won_games = $2 WHERE username = $3', [parseInt(stats.blackjack_games) + 1, parseInt(stats.blackjack_won_games) + 1, session.username], (error, results) => {
82 if (error) throw error;
83 });
84 }
85 }
86 }
87 });
88 }
89
90 res.json({
91 success: true,
92 credits: session.credits,
93 })
94
95 return ;
96 }
97
98 res.json({
99 success: false,
100 })
101 }
102
103 /**
104 * /---------------------- GET ----------------------/
105 * @action take_credits
106 * @param session_id
107 * @param credits
108 */
109 if (req.query?.action === 'take_credits' && req.query?.session_id && req.query?.credits) {
110 const session_id = req.query.session_id
111 const session = sessions.find(session => session.id === session_id)
112
113 if (session) {
114 session.lastActivity = Date.now();
115
116 session.credits = session.credits - parseInt(req.query.credits)
117
118 pool.query('UPDATE players SET credits = $1 WHERE username = $2', [session.credits, session.username], (error, results) => {
119 if (error) throw error;
120 });
121
122 pool.query('SELECT * FROM stats WHERE username = $1', [session.username], (error, results) => {
123 if (error) throw error;
124
125 if (results.rows.length > 0) {
126 const stats = results.rows[0]
127
128 pool.query('UPDATE stats SET money_bet = $1 WHERE username = $2', [parseInt(stats.money_bet) + parseInt(req.query.credits), session.username], (error, results) => {
129 if (error) throw error;
130 });
131 }
132 });
133
134 res.json({
135 success: true,
136 credits: session.credits,
137 })
138 return ;
139 }
140
141 res.json({
142 success: false,
143 })
144 }
145
146 /**
147 * /---------------------- GET ----------------------/
148 * @action get_stats
149 * @param session_id
150 */
151 if (req.query?.action === 'get_stats' && req.query?.session_id) {
152 const session_id = req.query.session_id
153 const session = sessions.find(session => session.id === session_id)
154
155 if (session) {
156 session.lastActivity = Date.now();
157
158 pool.query('SELECT * FROM stats WHERE username = $1', [session.username], (error, results) => {
159 if (error) throw error;
160
161 if (results.rows.length > 0) {
162 res.json({
163 success: true,
164 stats: results.rows[0],
165 })
166 }
167 else {
168 res.json({
169 success: false,
170 })
171 }
172 });
173
174 return ;
175 }
176
177 res.json({
178 success: false,
179 })
180 }
181
182 /**
183 * /---------------------- GET ----------------------/
184 * @action get_player_info_on_enter
185 * @param session_id
186 */
187 if (req.query?.action === 'get_player_info_on_enter' && req.query?.session_id) {
188 const session_id = req.query.session_id
189 const session = sessions.find(session => session.id === session_id)
190
191 if (session) {
192 res.json({
193 success: true,
194 displayName: session.displayName,
195 session_id: session.id,
196 credits: session.credits,
197 })
198 return ;
199 }
200
201 res.json({
202 success: false,
203 })
204 }
205
206 /**
207 * /---------------------- GET ----------------------/
208 * @action check_if_logged_in
209 * @param session_id
210 */
211 if (req.query?.action === 'check_if_logged_in' && req.query?.session_id) {
212 const session_id = req.query.session_id
213 const session = sessions.find(session => session.id === session_id)
214
215 if (session) {
216 res.json({
217 success: true,
218 displayName: session.displayName,
219 session_id: session.id,
220 credits: session.credits,
221 })
222 return ;
223 }
224
225 res.json({
226 success: false,
227 })
228 }
229
230 /**
231 * /---------------------- GET ----------------------/
232 * @action logout
233 * @param session_id
234 */
235 if (req.query?.action === 'logout' && req.query?.session_id) {
236 const session_id = req.query.session_id
237 const session = sessions.find(session => session.id === session_id)
238
239 if (session) {
240 pool.query('UPDATE players SET credits = $1 WHERE username = $2', [session.credits, session.username], (error, results) => {
241 if (error) throw error;
242 });
243
244 sessions.splice(sessions.indexOf(session), 1);
245
246 axios.get(`${process.env.HOME_URL}/api/blackjack/?action=remove_room&session_id=${session_id}`);
247 }
248
249 res.json({
250 success: true,
251 message: 'Successfully logged out',
252 })
253 }
254 }
255
256 /**
257 * POST method
258 */
259 if (req.method === 'POST') {
260 const { body } = req;
261
262 /**
263 * /---------------------- POST ----------------------/
264 * @action register
265 * @param username
266 * @param displayName
267 * @param password
268 */
269 if (body?.action === 'register') {
270 // checks
271 if (body?.username == "undefined" || body?.username == "null" || body?.username == "") {
272 res.json({
273 success: false,
274 message: 'Username is required',
275 });
276 return ;
277 }
278 if (/[^a-zA-Z]/g.test(body?.username)) {
279 res.json({
280 success: false,
281 message: 'Username must contain only letters',
282 })
283 return ;
284 }
285 if (body?.displayName == "undefined" || body?.displayName == "null" || body?.displayName == "") {
286 res.json({
287 success: false,
288 message: 'Display name is required',
289 });
290 return ;
291 }
292 if (body?.displayName?.toLowerCase() === "guest") {
293 res.json({
294 success: false,
295 message: 'Display name cannot be guest',
296 });
297 return ;
298 }
299 if (body?.password == "undefined" || body?.password == "null" || body?.password == "") {
300 res.json({
301 success: false,
302 message: 'Password is required',
303 });
304 return ;
305 }
306
307 // everything's okay
308 body.username = body.username.toLowerCase()
309
310 // hash password
311 const salt = crypto.randomBytes(16).toString('hex');
312 const hashedPassword = crypto.pbkdf2Sync(body.password, salt, 1000, 64, 'sha512').toString('hex');
313
314 // check if user already exists
315 pool.query('SELECT * FROM users WHERE username = $1', [body.username], (error, results) => {
316 if (error) throw error;
317
318 if (results.rows.length > 0) {
319 res.json({
320 success: false,
321 message: 'Username already exists',
322 });
323 return ;
324 }
325
326 // store user in database
327 pool.query('INSERT INTO users (username, password, salt) VALUES ($1, $2, $3)', [body.username, hashedPassword, salt], (error, usersResults) => {
328 if (error) throw error;
329
330 pool.query('INSERT INTO players (username, display_name, credits) VALUES ($1, $2, $3)', [body.username, body.displayName, 1000], (error, playersResults) => {
331 if (error) throw error;
332
333 pool.query('INSERT INTO stats (username, blackjack_games, roulette_games, poker_games, blackjack_won_games, roulette_won_games, poker_won_games, money_bet, money_earned) VALUES ($1, $2, $3, $4, $5, $6, $7, $8, $9)', [body.username, 0, 0, 0, 0, 0, 0, 0, 0], (error, statsResults) => {
334 if (error) throw error;
335
336 res.json({
337 success: true,
338 message: 'Registration successful',
339 });
340 return ;
341 });
342 });
343 });
344 });
345 }
346
347 /**
348 * /---------------------- POST ----------------------/
349 * @action login
350 * @param username
351 * @param password
352 */
353 if (body?.action === 'login') {
354 // checks
355 if (body?.username == "undefined" || body?.username == "null" || body?.username == "") {
356 res.json({
357 success: false,
358 message: 'Username is required',
359 });
360 return ;
361 }
362 if (/[^a-zA-Z]/g.test(body?.username)) {
363 res.json({
364 success: false,
365 message: 'Username must contain only letters',
366 })
367 return ;
368 }
369 if (body?.password == "undefined" || body?.password == "null" || body?.password == "") {
370 res.json({
371 success: false,
372 message: 'Password is required',
373 });
374 return ;
375 }
376
377 // everything's okay
378 body.username = body.username.toLowerCase();
379
380 // check if user exists
381 pool.query('SELECT * FROM users WHERE username = $1', [body.username], (error, usersResults) => {
382 if (error) throw error;
383
384 if (usersResults.rows.length === 0) {
385 res.json({
386 success: false,
387 message: 'User does not exist. Try Registering instead.',
388 });
389 return ;
390 }
391 else {
392 if (usersResults.rows.length > 0) {
393 const user = usersResults.rows[0];
394 const salt = user.salt;
395 const hashedPassword = crypto.pbkdf2Sync(body.password, salt, 1000, 64, 'sha512').toString('hex');
396
397 if (hashedPassword === user.password) {
398 pool.query('SELECT * FROM players WHERE username = $1', [body.username], (error, playersResults) => {
399 if (playersResults.rows.length > 0) {
400 let session = sessions.find(session => session.username === playersResults.rows[0].username)
401
402 if (session) {
403 // Already logged in
404 res.json({
405 success: false,
406 message: 'You are already logged in',
407 })
408 }
409 else {
410 // create a session
411 session = {
412 id: uuidv4(),
413 displayName: playersResults.rows[0].display_name,
414 username: playersResults.rows[0].username,
415 credits: playersResults.rows[0].credits,
416 lastActivity: Date.now(),
417 }
418
419 sessions.push(session);
420
421 res.json({
422 success: true,
423 message: 'Login successful',
424 session: session,
425 })
426 }
427
428 return ;
429 }
430 });
431 }
432 else {
433 res.json({
434 success: false,
435 message: 'Username and password do not match.',
436 });
437 }
438 }
439 }
440 });
441 }
442 }
443
444 /**
445 * PUT method
446 */
447 if (req.method === 'PUT') {
448
449 }
450}
Note: See TracBrowser for help on using the repository browser.