From 5f69ba49d6930e77daa80b388bc3604364af919d Mon Sep 17 00:00:00 2001 From: Greg Slepak Date: Fri, 26 Jul 2024 19:19:15 -0700 Subject: [PATCH] log registrations + add ip to backend errors (#2261) * log registrations + add ip to backend errors * bump to 1.0.2 * attempt to diagnose #2256 --- backend/routes.js | 26 +++++++++++++-------- package.json | 2 +- test/cypress/integration/group-chat.spec.js | 5 ++-- test/cypress/support/commands.js | 2 ++ 4 files changed, 21 insertions(+), 14 deletions(-) diff --git a/backend/routes.js b/backend/routes.js index 17cbebc46c..c19afd1e76 100644 --- a/backend/routes.js +++ b/backend/routes.js @@ -42,6 +42,9 @@ const route = new Proxy({}, { // RESTful API routes +// TODO: Update this regex once `chel` uses prefixed manifests +const manifestRegex = /^z9brRu3V[123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz]{44}$/ + // NOTE: We could get rid of this RESTful API and just rely on pubsub.js to do this // —BUT HTTP2 might be better than websockets and so we keep this around. // See related TODO in pubsub.js and the reddit discussion link. @@ -52,8 +55,7 @@ route.POST('/event', { }, validate: { payload: Joi.string().required() } }, async function (request, h) { - // TODO: Update this regex once `chel` uses prefixed manifests - const manifestRegex = /^z9brRu3V[123456789ABCDEFGHJKLMNPQRSTUVWXYZabcdefghijkmnopqrstuvwxyz]{44}$/ + const ip = request.headers['x-real-ip'] || request.info.remoteAddress try { const deserializedHEAD = GIMessage.deserializeHEAD(request.payload) try { @@ -89,6 +91,7 @@ route.POST('/event', { if (Boom.isBoom(r)) { return r } + console.info(`new user: ${name}=${deserializedHEAD.contractID} (${ip})`) } } } @@ -113,6 +116,7 @@ route.POST('/event', { } return deserializedHEAD.hash } catch (err) { + err.ip = ip logger.error(err, 'POST /event', err.message) return err } @@ -120,6 +124,7 @@ route.POST('/event', { route.GET('/eventsAfter/{contractID}/{since}/{limit?}', {}, async function (request, h) { const { contractID, since, limit } = request.params + const ip = request.headers['x-real-ip'] || request.info.remoteAddress try { if (contractID.startsWith('_private') || since.startsWith('_private')) { return Boom.notFound() @@ -138,6 +143,7 @@ route.GET('/eventsAfter/{contractID}/{since}/{limit?}', {}, async function (requ request.events.once('disconnect', stream.destroy.bind(stream)) return stream } catch (err) { + err.ip = ip logger.error(err, `GET /eventsAfter/${contractID}/${since}`, err.message) return err } @@ -722,8 +728,8 @@ route.POST('/zkpp/register/{name}', { } } } catch (e) { - const ip = req.headers['x-real-ip'] || req.info.remoteAddress - console.error(e, 'Error at POST /zkpp/{name}: ' + e.message, { ip }) + e.ip = req.headers['x-real-ip'] || req.info.remoteAddress + console.error(e, 'Error at POST /zkpp/{name}: ' + e.message) } return Boom.internal('internal error') @@ -740,8 +746,8 @@ route.GET('/zkpp/{name}/auth_hash', { return challenge || Boom.notFound() } catch (e) { - const ip = req.headers['x-real-ip'] || req.info.remoteAddress - console.error(e, 'Error at GET /zkpp/{name}/auth_hash: ' + e.message, { ip }) + e.ip = req.headers['x-real-ip'] || req.info.remoteAddress + console.error(e, 'Error at GET /zkpp/{name}/auth_hash: ' + e.message) } return Boom.internal('internal error') @@ -765,8 +771,8 @@ route.GET('/zkpp/{name}/contract_hash', { return salt } } catch (e) { - const ip = req.headers['x-real-ip'] || req.info.remoteAddress - console.error(e, 'Error at GET /zkpp/{name}/contract_hash: ' + e.message, { ip }) + e.ip = req.headers['x-real-ip'] || req.info.remoteAddress + console.error(e, 'Error at GET /zkpp/{name}/contract_hash: ' + e.message) } return Boom.internal('internal error') @@ -791,8 +797,8 @@ route.POST('/zkpp/updatePasswordHash/{name}', { return result } } catch (e) { - const ip = req.headers['x-real-ip'] || req.info.remoteAddress - console.error(e, 'Error at POST /zkpp/updatePasswordHash/{name}: ' + e.message, { ip }) + e.ip = req.headers['x-real-ip'] || req.info.remoteAddress + console.error(e, 'Error at POST /zkpp/updatePasswordHash/{name}: ' + e.message) } return Boom.internal('internal error') diff --git a/package.json b/package.json index a4ab15aaa9..72e0a92854 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "group-income", - "version": "1.0.1", + "version": "1.0.2", "contractsVersion": "1.0.0", "private": true, "description": "Group Income is a decentralized and private (end-to-end encrypted) financial safety net for you and your friends.", diff --git a/test/cypress/integration/group-chat.spec.js b/test/cypress/integration/group-chat.spec.js index 8518360bae..01c1d5a159 100644 --- a/test/cypress/integration/group-chat.spec.js +++ b/test/cypress/integration/group-chat.spec.js @@ -504,8 +504,7 @@ describe('Group Chat Basic Features (Create & Join & Leave & Close)', () => { cy.giRedirectToGroupChat() - // TODO: uncomment this and fix this heisenbug: https://github.com/okTurtles/group-income/issues/2256 - // cy.giCheckIfJoinedChatroom(CHATROOM_GENERAL_NAME, me) + // cy.giCheckIfJoinedChatroom(CHATROOM_GENERAL_NAME, me) // giAcceptGroupInvite already checks this cy.getByDT('channelMembers').should('contain', '2 members') cy.giLogout() }) @@ -527,7 +526,7 @@ describe('Group Chat Basic Features (Create & Join & Leave & Close)', () => { cy.giRedirectToGroupChat() - cy.giCheckIfJoinedChatroom(CHATROOM_GENERAL_NAME, me) + // cy.giCheckIfJoinedChatroom(CHATROOM_GENERAL_NAME, me) // giAcceptGroupInvite already checks this cy.getByDT('channelMembers').should('contain', '3 members') cy.giLogout() }) diff --git a/test/cypress/support/commands.js b/test/cypress/support/commands.js index 05fd050934..4af8996128 100644 --- a/test/cypress/support/commands.js +++ b/test/cypress/support/commands.js @@ -739,6 +739,8 @@ Cypress.Commands.add('giCheckIfJoinedChatroom', ( cy.getByDT('conversationWrapper').within(($el) => { if (inviter) { + // TODO: fix this heisenbug here: https://github.com/okTurtles/group-income/issues/2256 + cy.get('.c-message:last-child .c-who > span:first-child').scrollIntoView() cy.get('.c-message:last-child .c-who > span:first-child').should('contain', inviter) } const message = selfJoin ? `Joined ${channelName}` : `Added a member to ${channelName}: ${invitee}`