claim codes are working

This commit is contained in:
2023-07-11 17:36:37 -04:00
parent c45852438f
commit 5c79291130
7 changed files with 172 additions and 119 deletions

View File

@@ -14,18 +14,18 @@ console.log('SERVERID:', serverID);
export const rooms: RoomGroupI[] = [
{
name: 'Discreetly',
name: 'Discreetly Test',
id: genId(serverID, 'Discreetly'),
rooms: [
{
id: genId(serverID, 'General'),
name: 'General',
name: 'General 1 Second',
membership: { identityCommitments: [] },
rateLimit: 1000 // in ms
},
{
id: genId(serverID, 'Test'),
name: 'Test',
id: genId(serverID, '10sec'),
name: '10 Second Room',
membership: {
identityCommitments: []
},
@@ -34,14 +34,16 @@ export const rooms: RoomGroupI[] = [
]
},
{
name: 'Events',
id: genId(serverID, 'Events'),
name: 'SERVER TEST',
id: genId(serverID, 'Test'),
rooms: [
{
id: genId(serverID, 'Devconnect 2023'),
name: 'Devconnect 2023',
membership: { identityCommitments: [] },
rateLimit: 1000 // in ms
id: genId(serverID, 'Test'),
name: 'Test',
membership: {
identityCommitments: []
},
rateLimit: 10000 // in ms
}
]
}

22
dist/config/rooms.js vendored
View File

@@ -15,18 +15,18 @@ catch (error) {
console.log('SERVERID:', serverID);
exports.rooms = [
{
name: 'Discreetly',
name: 'Discreetly Test',
id: (0, discreetly_interfaces_1.genId)(serverID, 'Discreetly'),
rooms: [
{
id: (0, discreetly_interfaces_1.genId)(serverID, 'General'),
name: 'General',
name: 'General 1 Second',
membership: { identityCommitments: [] },
rateLimit: 1000 // in ms
},
{
id: (0, discreetly_interfaces_1.genId)(serverID, 'Test'),
name: 'Test',
id: (0, discreetly_interfaces_1.genId)(serverID, '10sec'),
name: '10 Second Room',
membership: {
identityCommitments: []
},
@@ -35,14 +35,16 @@ exports.rooms = [
]
},
{
name: 'Events',
id: (0, discreetly_interfaces_1.genId)(serverID, 'Events'),
name: 'SERVER TEST',
id: (0, discreetly_interfaces_1.genId)(serverID, 'Test'),
rooms: [
{
id: (0, discreetly_interfaces_1.genId)(serverID, 'Devconnect 2023'),
name: 'Devconnect 2023',
membership: { identityCommitments: [] },
rateLimit: 1000 // in ms
id: (0, discreetly_interfaces_1.genId)(serverID, 'Test'),
name: 'Test',
membership: {
identityCommitments: []
},
rateLimit: 10000 // in ms
}
]
}

80
dist/src/server.js vendored
View File

@@ -1,4 +1,13 @@
"use strict";
var __spreadArray = (this && this.__spreadArray) || function (to, from, pack) {
if (pack || arguments.length === 2) for (var i = 0, l = from.length, ar; i < l; i++) {
if (ar || !(i in from)) {
if (!ar) ar = Array.prototype.slice.call(from, 0, i);
ar[i] = from[i];
}
}
return to.concat(ar || Array.prototype.slice.call(from));
};
Object.defineProperty(exports, "__esModule", { value: true });
var express = require("express");
var http_1 = require("http");
@@ -30,27 +39,11 @@ var io = new socket_io_1.Server(socket_server, {
});
var userCount = {};
var loadedRooms;
var TESTGROUPID;
// TODO get the claim code manager working with redis to store the state of the rooms and claim codes in a redis database that persists across server restarts
// Redis
var redisClient = (0, redis_1.createClient)();
redisClient.connect().then(function () { return (0, utils_1.pp)('Redis Connected'); });
var ccm;
redisClient.get('ccm').then(function (cc) {
if (!cc) {
ccm = new discreetly_claimcodes_1.default();
ccm.generateClaimCodeSet(10, 999, 'TEST');
var ccs = ccm.getClaimCodeSets();
redisClient.set('ccm', JSON.stringify(ccs));
}
else {
ccm = new discreetly_claimcodes_1.default(JSON.parse(cc));
if (ccm.getUsedCount(999).unusedCount < 5) {
ccm.generateClaimCodeSet(10, 999, 'TEST');
var ccs = ccm.getClaimCodeSets();
redisClient.set('ccm', JSON.stringify(ccs));
}
}
});
redisClient.get('rooms').then(function (rooms) {
rooms = JSON.parse(rooms);
if (rooms) {
@@ -62,6 +55,25 @@ redisClient.get('rooms').then(function (rooms) {
}
(0, utils_1.pp)({ 'Loaded Rooms': loadedRooms });
});
var ccm;
redisClient.get('ccm').then(function (cc) {
TESTGROUPID = BigInt(loadedRooms[0].id);
if (!cc) {
ccm = new discreetly_claimcodes_1.default();
ccm.generateClaimCodeSet(10, TESTGROUPID, 'TEST');
var ccs_1 = ccm.getClaimCodeSets();
redisClient.set('ccm', JSON.stringify(ccs_1));
}
else {
ccm = new discreetly_claimcodes_1.default(JSON.parse(cc));
if (ccm.getUsedCount(TESTGROUPID).unusedCount < 5) {
ccm.generateClaimCodeSet(10, TESTGROUPID, 'TEST');
var ccs_2 = ccm.getClaimCodeSets();
redisClient.set('ccm', JSON.stringify(ccs_2));
}
}
var ccs = ccm.getClaimCodeSets();
});
redisClient.on('error', function (err) { return (0, utils_1.pp)('Redis Client Error: ' + err, 'error'); });
io.on('connection', function (socket) {
(0, utils_1.pp)('SocketIO: a user connected', 'debug');
@@ -107,8 +119,6 @@ app.get('/api/rooms/:id', function (req, res) {
res.json(room);
});
// TODO api endpoint that creates new rooms and generates invite codes for them
var testGroupId0 = '917472730658974787195329824193375792646499428986660190540754124137738350241';
var testGroupId1 = '355756154407663058879850750536398206548026044600409795496806929599466182253';
app.post('/join', function (req, res) {
var data = req.body;
var code = data.code, idc = data.idc;
@@ -116,10 +126,33 @@ app.post('/join', function (req, res) {
var result = ccm.claimCode(code);
var groupID = result.groupID;
if (result.status === 'CLAIMED') {
var claimedRooms_1 = [];
var alreadyAddedRooms_1 = [];
loadedRooms.forEach(function (group) {
if (group.id == groupID) {
group.rooms.forEach(function (room) {
var added = (0, utils_1.addIdentityToRoom)(BigInt(room.id), BigInt(idc));
if (added) {
claimedRooms_1.push(room);
}
else {
alreadyAddedRooms_1.push(room);
}
});
}
});
var r = __spreadArray(__spreadArray([], claimedRooms_1, true), alreadyAddedRooms_1, true);
if (claimedRooms_1.length > 0) {
res.status(200).json({ status: 'valid', rooms: r });
}
else if (alreadyAddedRooms_1.length > 0) {
res.status(200).json({ status: 'already-added', rooms: r });
}
else {
res.status(451).json({ status: 'invalid' });
}
// the DB should be updated after we successfully send a response
redisClient.set('ccm', JSON.stringify(ccm.getClaimCodeSets()));
(0, utils_1.addIdentityToRoom)(testGroupId1, idc);
(0, utils_1.pp)('Express[/join]Code claimed: ' + code);
res.status(200).json({ groupID: groupID });
}
else {
res.status(451).json({ status: 'invalid' });
@@ -135,8 +168,9 @@ app.post('/group/add', function (req, res) {
});
app.get('/logclaimcodes', function (req, res) {
(0, utils_1.pp)('-----CLAIMCODES-----', 'debug');
(0, utils_1.pp)(ccm.getClaimCodeSets());
(0, utils_1.pp)(ccm.getClaimCodeSet(TESTGROUPID));
(0, utils_1.pp)('-----ENDOFCODES-----', 'debug');
res.status(200).json({ status: 'ok' });
});
app.listen(HTTP_PORT, function () {
(0, utils_1.pp)("Express Http Server is running at http://localhost:".concat(HTTP_PORT));

14
package-lock.json generated
View File

@@ -12,7 +12,7 @@
"atob": "^2.1.2",
"body-parser": "^1.20.2",
"cors": "^2.8.5",
"discreetly-claimcodes": "^1.0.2",
"discreetly-claimcodes": "^1.0.5",
"discreetly-interfaces": "^0.1.3",
"dotenv": "^16.3.1",
"express": "^4.18.2",
@@ -933,9 +933,9 @@
}
},
"node_modules/discreetly-claimcodes": {
"version": "1.0.2",
"resolved": "https://registry.npmjs.org/discreetly-claimcodes/-/discreetly-claimcodes-1.0.2.tgz",
"integrity": "sha512-qAJoG1PZZEsPNtlnK1sxZYl2tyojA6kQQcFNZFf9mRpJHgl1bfx9+x2UfhC0PKF4214sYtGAw7WgTDH8iJ3LKA=="
"version": "1.0.5",
"resolved": "https://registry.npmjs.org/discreetly-claimcodes/-/discreetly-claimcodes-1.0.5.tgz",
"integrity": "sha512-ygx8rKtiweDg/Qj5qbHVy31osFV+CcGrNNtxDpeqqRnkO9tkqH9CvtdPJuR3R0R8vzT7kyBTwmN0LGQe3/aXhQ=="
},
"node_modules/discreetly-interfaces": {
"version": "0.1.3",
@@ -3111,9 +3111,9 @@
"integrity": "sha512-2sJGJTaXIIaR1w4iJSNoN0hnMY7Gpc/n8D4qSCJw8QqFWXf7cuAgnEHxBpweaVcPevC2l3KpjYCx3NypQQgaJg=="
},
"discreetly-claimcodes": {
"version": "1.0.2",
"resolved": "https://registry.npmjs.org/discreetly-claimcodes/-/discreetly-claimcodes-1.0.2.tgz",
"integrity": "sha512-qAJoG1PZZEsPNtlnK1sxZYl2tyojA6kQQcFNZFf9mRpJHgl1bfx9+x2UfhC0PKF4214sYtGAw7WgTDH8iJ3LKA=="
"version": "1.0.5",
"resolved": "https://registry.npmjs.org/discreetly-claimcodes/-/discreetly-claimcodes-1.0.5.tgz",
"integrity": "sha512-ygx8rKtiweDg/Qj5qbHVy31osFV+CcGrNNtxDpeqqRnkO9tkqH9CvtdPJuR3R0R8vzT7kyBTwmN0LGQe3/aXhQ=="
},
"discreetly-interfaces": {
"version": "0.1.3",

View File

@@ -17,7 +17,7 @@
"atob": "^2.1.2",
"body-parser": "^1.20.2",
"cors": "^2.8.5",
"discreetly-claimcodes": "^1.0.2",
"discreetly-claimcodes": "^1.0.5",
"discreetly-interfaces": "^0.1.3",
"dotenv": "^16.3.1",
"express": "^4.18.2",
@@ -34,4 +34,4 @@
"nodemon": "^2.0.22",
"typescript": "^5.1.6"
}
}
}

View File

@@ -4,14 +4,13 @@ import { Server as SocketIOServer, Socket } from 'socket.io';
import * as cors from 'cors';
import { createClient } from 'redis';
import { serverConfig, rooms as defaultRooms, rooms } from '../config/rooms';
import { MessageI, RoomGroupI } from 'discreetly-interfaces';
import type { MessageI, RoomI, RoomGroupI } from 'discreetly-interfaces';
import verifyProof from './verifier';
import ClaimCodeManager from 'discreetly-claimcodes';
import type { ClaimCodeStatus } from 'discreetly-claimcodes';
import { pp, addIdentityToRoom, createGroup } from './utils';
import { faker } from '@faker-js/faker';
// HTTP is to get info from the server about configuration, rooms, etc
const HTTP_PORT = 3001;
// Socket is to communicate chat room messages back and forth
@@ -29,7 +28,6 @@ const app = express();
const socket_server = new Server(app);
app.use(express.json());
const io = new SocketIOServer(socket_server, {
cors: {
origin: '*'
@@ -42,32 +40,13 @@ interface userCountI {
let userCount: userCountI = {};
let loadedRooms: RoomGroupI[];
let TESTGROUPID: BigInt;
// TODO get the claim code manager working with redis to store the state of the rooms and claim codes in a redis database that persists across server restarts
// Redis
const redisClient = createClient();
redisClient.connect().then(() => pp('Redis Connected'));
let ccm: ClaimCodeManager;
redisClient.get('ccm').then((cc) => {
if (!cc) {
ccm = new ClaimCodeManager();
ccm.generateClaimCodeSet(10, 999, 'TEST');
const ccs = ccm.getClaimCodeSets();
redisClient.set('ccm', JSON.stringify(ccs));
} else {
ccm = new ClaimCodeManager(JSON.parse(cc));
if (ccm.getUsedCount(999).unusedCount < 5) {
ccm.generateClaimCodeSet(10, 999, 'TEST');
const ccs = ccm.getClaimCodeSets();
redisClient.set('ccm', JSON.stringify(ccs));
}
}
});
redisClient.get('rooms').then((rooms) => {
rooms = JSON.parse(rooms);
if (rooms) {
@@ -79,6 +58,28 @@ redisClient.get('rooms').then((rooms) => {
pp({ 'Loaded Rooms': loadedRooms });
});
let ccm: ClaimCodeManager;
redisClient.get('ccm').then((cc) => {
TESTGROUPID = BigInt(loadedRooms[0].id);
if (!cc) {
ccm = new ClaimCodeManager();
ccm.generateClaimCodeSet(10, TESTGROUPID, 'TEST');
const ccs = ccm.getClaimCodeSets();
redisClient.set('ccm', JSON.stringify(ccs));
} else {
ccm = new ClaimCodeManager(JSON.parse(cc));
if (ccm.getUsedCount(TESTGROUPID).unusedCount < 5) {
ccm.generateClaimCodeSet(10, TESTGROUPID, 'TEST');
const ccs = ccm.getClaimCodeSets();
redisClient.set('ccm', JSON.stringify(ccs));
}
}
const ccs = ccm.getClaimCodeSets();
});
redisClient.on('error', (err) => pp('Redis Client Error: ' + err, 'error'));
io.on('connection', (socket: Socket) => {
@@ -136,8 +137,6 @@ app.get('/api/rooms/:id', (req, res) => {
});
// TODO api endpoint that creates new rooms and generates invite codes for them
const testGroupId0 = '917472730658974787195329824193375792646499428986660190540754124137738350241';
const testGroupId1 = '355756154407663058879850750536398206548026044600409795496806929599466182253';
app.post('/join', (req, res) => {
const data = req.body;
const { code, idc } = data;
@@ -145,10 +144,32 @@ app.post('/join', (req, res) => {
const result: ClaimCodeStatus = ccm.claimCode(code);
const groupID = result.groupID;
if (result.status === 'CLAIMED') {
let claimedRooms = [];
let alreadyAddedRooms = [];
loadedRooms.forEach((group) => {
if (group.id == groupID) {
group.rooms.forEach((room: RoomI) => {
let added = addIdentityToRoom(BigInt(room.id), BigInt(idc));
if (added) {
claimedRooms.push(room);
} else {
alreadyAddedRooms.push(room);
}
});
}
});
let r = [...claimedRooms, ...alreadyAddedRooms];
if (claimedRooms.length > 0) {
res.status(200).json({ status: 'valid', rooms: r });
} else if (alreadyAddedRooms.length > 0) {
res.status(200).json({ status: 'already-added', rooms: r });
} else {
res.status(451).json({ status: 'invalid' });
}
// the DB should be updated after we successfully send a response
redisClient.set('ccm', JSON.stringify(ccm.getClaimCodeSets()));
addIdentityToRoom(testGroupId1, idc);
pp('Express[/join]Code claimed: ' + code);
res.status(200).json({ groupID });
} else {
res.status(451).json({ status: 'invalid' });
}
@@ -159,14 +180,15 @@ app.post('/group/add', (req, res) => {
const data = req.body;
const { password, groupName, rooms, codes } = data;
if (password === process.env.PASSWORD) {
createGroup(groupName, rooms)
createGroup(groupName, rooms);
}
})
});
app.get('/logclaimcodes', (req, res) => {
pp('-----CLAIMCODES-----', 'debug');
pp(ccm.getClaimCodeSets());
pp(ccm.getClaimCodeSet(TESTGROUPID));
pp('-----ENDOFCODES-----', 'debug');
res.status(200).json({ status: 'ok' });
});
app.listen(HTTP_PORT, () => {
@@ -183,8 +205,6 @@ process.on('SIGINT', () => {
redisClient.disconnect().then(process.exit());
});
if (TESTING) {
class randomMessagePicker {
values: any;

View File

@@ -1,6 +1,6 @@
import { createClient } from 'redis';
import { RoomGroupI, ServerI, genId } from 'discreetly-interfaces';
import type { RoomI, RoomGroupI, ServerI } from 'discreetly-interfaces';
import { genId } from 'discreetly-interfaces';
const redisClient = createClient();
redisClient.connect();
@@ -19,37 +19,32 @@ export const findRoomById = (rooms, id) => {
}
};
export const findGroupById = (rooms, groupId) => {
for (let i = 0; i < rooms.length; i++) {
if (rooms[i].id === groupId) {
const group = rooms[i];
return group;
}
export const findGroupById = (roomGroups: RoomGroupI[], groupId: BigInt): RoomGroupI => {
const group = roomGroups.find((group) => group.id === groupId);
if (!group) {
console.error('Group not found');
} else {
return group;
}
};
export const addIdentityToRoom = (groupId, identityCommitment) => {
redisClient.get('rooms').then((res) => {
const data = JSON.parse(res);
const group = findGroupById(data, groupId);
if (group) {
const groupIndex = data.findIndex((gIdx) => gIdx.name === group.name);
if (groupIndex === -1) {
console.error('Group not found');
} else {
data[groupIndex].rooms.forEach((room) => {
if (!room.membership.identityCommitments.find((id) => id === identityCommitment)) {
room.membership.identityCommitments.push(identityCommitment);
console.log(`Identity set in room ${room.name}`);
redisClient.set('rooms', JSON.stringify(data));
} else {
console.error(`Identity already exists in room ${room.name}`);
export const addIdentityToRoom = (roomID: BigInt, identityCommitment: BigInt): Boolean => {
return redisClient.get('rooms').then((res) => {
const roomGroups = JSON.parse(res) as RoomGroupI[];
roomGroups.forEach((group) => {
group.rooms.forEach((room) => {
if (BigInt(room.id) == roomID) {
if (room.membership.identityCommitments.includes(identityCommitment)) {
console.log('Identity already in room');
return false;
}
});
}
} else {
console.error('Group not found');
}
room.membership.identityCommitments.push(identityCommitment);
redisClient.set('rooms', JSON.stringify(roomGroups));
console.debug(`IdentityCommitment ${identityCommitment} added to room ${roomID}`);
return true;
}
});
});
});
};
@@ -57,22 +52,22 @@ export const createGroup = (groupName, roomNames) => {
const newGroup: RoomGroupI = {
id: genId(BigInt(999), groupName),
name: groupName,
rooms: roomNames.map(roomName => {
rooms: roomNames.map((roomName) => {
return {
id: genId(BigInt(999), roomName),
name: roomName,
membership: { identityCommitments: [] },
rateLimit: 1000
}
};
})
}
redisClient.get('rooms').then(groups => {
};
redisClient.get('rooms').then((groups) => {
const data = JSON.parse(groups);
data.push(newGroup);
redisClient.set('rooms', JSON.stringify(data));
pp(`Group ${groupName} created`);
});
}
};
// Pretty Print to console
export const pp = (str: any, level = 'log') => {