From f8762b074e74a0f1f42e7badcae3fcf00e991f4c Mon Sep 17 00:00:00 2001 From: Evelynn Chen Date: Mon, 7 Oct 2024 13:37:50 -0400 Subject: [PATCH 01/11] still getting errors on checking for user perms --- src/posts/endorsements.js | 7 ++++ src/privileges/posts.js | 12 ++++++ test/posts.js | 81 +++++++++++++++++++++++++++++---------- 3 files changed, 79 insertions(+), 21 deletions(-) diff --git a/src/posts/endorsements.js b/src/posts/endorsements.js index d6e5498ece..bcd83450f6 100644 --- a/src/posts/endorsements.js +++ b/src/posts/endorsements.js @@ -2,6 +2,7 @@ const db = require('../database'); const plugins = require('../plugins'); +const privileges = require('../privileges'); module.exports = function (Posts) { Posts.endorse = async function (pid, uid) { @@ -17,6 +18,12 @@ module.exports = function (Posts) { throw new Error('[[error:not-logged-in]]'); } + const isAllowed = await privileges.posts.canEndorse(uid); + + if (!isAllowed) { + throw new Error('[[error:permission-denied]]'); + } + const isEndorsing = type === 'endorse'; const [postData, hasEndorsed] = await Promise.all([ diff --git a/src/privileges/posts.js b/src/privileges/posts.js index fbd6858282..b126e19b68 100644 --- a/src/privileges/posts.js +++ b/src/privileges/posts.js @@ -225,6 +225,18 @@ privsPosts.canPurge = async function (pid, uid) { return (results.purge && (results.owner || results.isModerator)) || results.isAdmin; }; +privsPosts.canEndorse = async function (uid) { + if (parseInt(uid, 10) <= 0) { + return false; + } + const isAdmin = await user.isAdministrator(uid); + if (isAdmin) { + return true; + } + const isGlobalMod = await user.isGlobalModerator(uid); + return isGlobalMod; +}; + async function isAdminOrMod(pid, uid) { if (parseInt(uid, 10) <= 0) { return false; diff --git a/test/posts.js b/test/posts.js index f797522bb5..de7f18f7f5 100644 --- a/test/posts.js +++ b/test/posts.js @@ -133,33 +133,72 @@ describe('Post\'s', () => { }); describe('endorsing and unendorsing', function () { - let testPid; - let testUid; + let adminUid; + let globalModUid; + let regularUserUid; + let postResult; before(async () => { - testUid = await user.create({ username: 'endorser' }); - const postResult = await topics.post({ - uid: testUid, - cid: cid, - title: 'test topic for endorsement feature', - content: 'endorsement topic content', - }); - testPid = postResult.postData.pid; + // adminUid = await user.create({ username: 'admin' }); + // await groups.join('administrators', adminUid); + + adminUid = await user.create({ username: 'admin', password: '123456' }); + await groups.join('administrators', adminUid); + + globalModUid = await user.create({ username: 'global mod' }); + await groups.join('Global Moderators', globalModUid); + + regularUserUid = await user.create({ username: 'regular user' }); + + ({ cid } = await categories.create({ + name: 'test endorsement category', + description: 'category for testing endorsements', + })); + + postResult = await topics.post({ + uid: regularUserUid, + cid: cid, + title: 'test topic for endorsement feature', + content: 'endorsement topic content', + }); + }); + + it('should allow an admin to endorse a post', async function () { + const result = await apiPosts.endorse(postResult.postData.pid, adminUid); + assert.strictEqual(result.isEndorsed, true); }); - it('should mark post as endorsed', async function () { - const caller = { uid: testUid }; - const data = { pid: testPid }; - const result = await apiPosts.endorse(caller, data); - assert.strictEqual(result.isEndorsed, true); + it('should allow a global mod to endorse a post', async function () { + const result = await apiPosts.endorse(postResult.postData.pid, globalModUid); + assert.strictEqual(result.isEndorsed, true); }); - it('should change post to unendorsed', async function () { - await apiPosts.endorse({ uid: testUid }, { pid: testPid }); - const caller = { uid: testUid }; - const data = { pid: testPid }; - const result = await apiPosts.unendorse(caller, data); - assert.strictEqual(result.isEndorsed, false); + it('should not allow a regular user to endorse a post', async () => { + try { + await apiPosts.endorse(postResult.postData.pid, regularUserUid); + assert.fail('Regular user should not be able to endorse a post'); + } catch (err) { + assert.strictEqual(err.message, '[[error:permission-denied]]'); + } + }); + + it('should allow an admin to unendorse a post', async () => { + const result = await apiPosts.unendorse(postResult.postData.pid, adminUid); + assert.strictEqual(result.isEndorsed, false); + }); + + it('should allow a global mod to unendorse a post', async () => { + const result = await apiPosts.unendorse(postResult.postData.pid, globalModUid); + assert.strictEqual(result.isEndorsed, false); + }); + + it('should not allow a regular user to unendorse a post', async function () { + try { + await apiPosts.unendorse(postResult.postData.pid, regularUserUid); + assert.fail('Regular user should not be able to unendorse a post'); + } catch (err) { + assert.strictEqual(err.message, '[[error:permission-denied]]'); + } }); }); From 197d51568d9d2905524d76f461b75b7604b6df85 Mon Sep 17 00:00:00 2001 From: Vicky Chen Date: Wed, 9 Oct 2024 20:05:08 -0400 Subject: [PATCH 02/11] initial debugging, added print statements to privileges/posts.js file but not printing - suspect cause of error here --- src/privileges/posts.js | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/src/privileges/posts.js b/src/privileges/posts.js index b126e19b68..f66e2ca959 100644 --- a/src/privileges/posts.js +++ b/src/privileges/posts.js @@ -227,13 +227,19 @@ privsPosts.canPurge = async function (pid, uid) { privsPosts.canEndorse = async function (uid) { if (parseInt(uid, 10) <= 0) { + console.log("VICKY CHEN HERE"); + console.log("Invalid UID", uid); return false; } + console.log("Checking if UID", uid, "is admin..."); const isAdmin = await user.isAdministrator(uid); + console.log("isAdmin result for UID", uid, ":", isAdmin); if (isAdmin) { return true; } + console.log("Checking if UID", uid, "is global moderator..."); const isGlobalMod = await user.isGlobalModerator(uid); + console.log("isGlobalMod result for UID", uid, ":", isGlobalMod); return isGlobalMod; }; From 7044854e30f2429987327ecc473789da6d72de4f Mon Sep 17 00:00:00 2001 From: Vicky Chen Date: Wed, 9 Oct 2024 20:16:56 -0400 Subject: [PATCH 03/11] found potential test case fail issue, noticed the uid is undefined value --- src/privileges/posts.js | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/src/privileges/posts.js b/src/privileges/posts.js index f66e2ca959..4e4a62c7a7 100644 --- a/src/privileges/posts.js +++ b/src/privileges/posts.js @@ -226,20 +226,21 @@ privsPosts.canPurge = async function (pid, uid) { }; privsPosts.canEndorse = async function (uid) { + console.log("CAN ENDORSE FUNCTION IS BEING CALLED"); if (parseInt(uid, 10) <= 0) { - console.log("VICKY CHEN HERE"); - console.log("Invalid UID", uid); + console.error("VICKY CHEN HERE"); + console.error("Invalid UID", uid); return false; } - console.log("Checking if UID", uid, "is admin..."); + console.error("Checking if UID", uid, "is admin..."); const isAdmin = await user.isAdministrator(uid); - console.log("isAdmin result for UID", uid, ":", isAdmin); + console.error("isAdmin result for UID", uid, ":", isAdmin); if (isAdmin) { return true; } - console.log("Checking if UID", uid, "is global moderator..."); + console.error("Checking if UID", uid, "is global moderator..."); const isGlobalMod = await user.isGlobalModerator(uid); - console.log("isGlobalMod result for UID", uid, ":", isGlobalMod); + console.error("isGlobalMod result for UID", uid, ":", isGlobalMod); return isGlobalMod; }; From 37eace1ecbfa1dbfcf7c3465ee2cf97f41f40277 Mon Sep 17 00:00:00 2001 From: Vicky Chen Date: Wed, 9 Oct 2024 20:25:58 -0400 Subject: [PATCH 04/11] confirmed that uid is also undefined in endorsements.js --- src/posts/endorsements.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/posts/endorsements.js b/src/posts/endorsements.js index bcd83450f6..399ef0fc40 100644 --- a/src/posts/endorsements.js +++ b/src/posts/endorsements.js @@ -17,7 +17,7 @@ module.exports = function (Posts) { if (parseInt(uid, 10) <= 0) { throw new Error('[[error:not-logged-in]]'); } - + console.log("USER ID BEFORE CALLING CAN ENDORSE VICKY: ", uid); const isAllowed = await privileges.posts.canEndorse(uid); if (!isAllowed) { From c47cd1c1918071e709001fd11e18be0f24139f6d Mon Sep 17 00:00:00 2001 From: Vicky Chen Date: Wed, 9 Oct 2024 20:31:43 -0400 Subject: [PATCH 05/11] confirmed uid issue lies outside of endorsements.js file (already undefined at line 8) --- src/posts/endorsements.js | 1 + 1 file changed, 1 insertion(+) diff --git a/src/posts/endorsements.js b/src/posts/endorsements.js index 399ef0fc40..87cde6f93e 100644 --- a/src/posts/endorsements.js +++ b/src/posts/endorsements.js @@ -6,6 +6,7 @@ const privileges = require('../privileges'); module.exports = function (Posts) { Posts.endorse = async function (pid, uid) { + console.log("Calling toggleEndorse with UID VICKY2:", uid); return await toggleEndorse('endorse', pid, uid); }; From 98483346eb5f932bc8dedb54833b5dc72d0abd11 Mon Sep 17 00:00:00 2001 From: Vicky Chen Date: Wed, 9 Oct 2024 20:42:38 -0400 Subject: [PATCH 06/11] confirmed that caller.uid and pid are all undefined in posts.js --- src/api/posts.js | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/api/posts.js b/src/api/posts.js index add4fd82a4..fe53439625 100644 --- a/src/api/posts.js +++ b/src/api/posts.js @@ -514,9 +514,11 @@ postsAPI.getReplies = async (caller, { pid }) => { }; postsAPI.endorse = async (caller, { pid }) => { + console.log("VICKYC3", pid, caller.uid); return await posts.endorse(pid, caller.uid); }; postsAPI.unendorse = async (caller, { pid }) => { + console.log("VICKYC4", pid, caller.uid); return await posts.unendorse(pid, caller.uid); }; From 5af2d371a48f03f3c07418bf7221b5ad0f203b58 Mon Sep 17 00:00:00 2001 From: Vicky Chen Date: Wed, 9 Oct 2024 21:05:38 -0400 Subject: [PATCH 07/11] attempted to add uid param in tools.js, socket.io.js, and index.js --- src/socket.io/posts/tools.js | 16 ++++++++++++---- test/helpers/index.js | 4 +++- test/socket.io.js | 3 ++- 3 files changed, 17 insertions(+), 6 deletions(-) diff --git a/src/socket.io/posts/tools.js b/src/socket.io/posts/tools.js index 5c1f97845d..7b50878234 100644 --- a/src/socket.io/posts/tools.js +++ b/src/socket.io/posts/tools.js @@ -94,12 +94,20 @@ module.exports = function (SocketPosts) { await Promise.all(logs); }; + // SocketPosts.endorse = async function (socket, data) { + // if (!data || !data.pid) { + // throw new Error('[[error:invalid-data]]'); + // } + // return await apiPosts.endorse(socket, { pid: data.pid }); + // }; + SocketPosts.endorse = async function (socket, data) { - if (!data || !data.pid) { - throw new Error('[[error:invalid-data]]'); + const uid = socket.handshake.query.uid; + if (!uid || !data || !data.pid ) { + throw new Error('[error:invalid-data'); } - return await apiPosts.endorse(socket, { pid: data.pid }); - }; + return await apiPosts.endorse({ uid }, { pid: data.pid }); + } SocketPosts.unendorse = async function (socket, data) { if (!data || !data.pid) { diff --git a/test/helpers/index.js b/test/helpers/index.js index e71a05edaa..37873e4fe6 100644 --- a/test/helpers/index.js +++ b/test/helpers/index.js @@ -59,9 +59,10 @@ helpers.logoutUser = async function (jar) { return { response, body }; }; -helpers.connectSocketIO = function (res, csrf_token) { +helpers.connectSocketIO = function (res, csrf_token, uid) { const io = require('socket.io-client'); const cookie = res.headers['set-cookie']; + const socket = io(nconf.get('base_url'), { path: `${nconf.get('relative_path')}/socket.io`, extraHeaders: { @@ -70,6 +71,7 @@ helpers.connectSocketIO = function (res, csrf_token) { }, query: { _csrf: csrf_token, + uid: uid }, }); return new Promise((resolve, reject) => { diff --git a/test/socket.io.js b/test/socket.io.js index 6c0a5a2367..15563fabb8 100644 --- a/test/socket.io.js +++ b/test/socket.io.js @@ -50,7 +50,8 @@ describe('socket.io', () => { it('should connect and auth properly', async () => { const { response, csrf_token } = await helpers.loginUser('admin', 'adminpwd'); - io = await helpers.connectSocketIO(response, csrf_token); + const uid = response.user.uid; + io = await helpers.connectSocketIO(response, csrf_token, uid); assert(io); assert(io.emit); }); From f04a1a517e8693a27a4f940fe22aabf1b82d3c54 Mon Sep 17 00:00:00 2001 From: Vicky Chen Date: Wed, 9 Oct 2024 21:24:53 -0400 Subject: [PATCH 08/11] attempted more print statement to debug uid --- src/socket.io/posts/tools.js | 1 + test/helpers/index.js | 2 ++ test/socket.io.js | 6 +++++- 3 files changed, 8 insertions(+), 1 deletion(-) diff --git a/src/socket.io/posts/tools.js b/src/socket.io/posts/tools.js index 7b50878234..893cd2c86f 100644 --- a/src/socket.io/posts/tools.js +++ b/src/socket.io/posts/tools.js @@ -102,6 +102,7 @@ module.exports = function (SocketPosts) { // }; SocketPosts.endorse = async function (socket, data) { + console.log("VICKY8 Socket handshake query: ", socket.handshake.query); const uid = socket.handshake.query.uid; if (!uid || !data || !data.pid ) { throw new Error('[error:invalid-data'); diff --git a/test/helpers/index.js b/test/helpers/index.js index 37873e4fe6..dc87ec0fe0 100644 --- a/test/helpers/index.js +++ b/test/helpers/index.js @@ -60,6 +60,8 @@ helpers.logoutUser = async function (jar) { }; helpers.connectSocketIO = function (res, csrf_token, uid) { + console.log("VICKY7 UID passed to connectSocketIO", uid); + const io = require('socket.io-client'); const cookie = res.headers['set-cookie']; diff --git a/test/socket.io.js b/test/socket.io.js index 15563fabb8..c6a5d1d774 100644 --- a/test/socket.io.js +++ b/test/socket.io.js @@ -50,7 +50,11 @@ describe('socket.io', () => { it('should connect and auth properly', async () => { const { response, csrf_token } = await helpers.loginUser('admin', 'adminpwd'); - const uid = response.user.uid; + console.log("VICKY5 Login response object: ", response); + + const uid = response.user?.uid || 'No UID'; + console.log("VICKY6 Retrieved UID: ", uid); + io = await helpers.connectSocketIO(response, csrf_token, uid); assert(io); assert(io.emit); From a202f2d67aa1bb636873e04e754ff9e80f3c54e5 Mon Sep 17 00:00:00 2001 From: Vicky Chen Date: Wed, 9 Oct 2024 21:50:52 -0400 Subject: [PATCH 09/11] noticed that admin and pid are valid --- test/posts.js | 3 +++ 1 file changed, 3 insertions(+) diff --git a/test/posts.js b/test/posts.js index de7f18f7f5..e8d6028ffe 100644 --- a/test/posts.js +++ b/test/posts.js @@ -143,6 +143,7 @@ describe('Post\'s', () => { // await groups.join('administrators', adminUid); adminUid = await user.create({ username: 'admin', password: '123456' }); + console.log("Admin UID VICKY9:", adminUid); await groups.join('administrators', adminUid); globalModUid = await user.create({ username: 'global mod' }); @@ -164,7 +165,9 @@ describe('Post\'s', () => { }); it('should allow an admin to endorse a post', async function () { + console.log("VICKY10", postResult.postData.pid, adminUid) const result = await apiPosts.endorse(postResult.postData.pid, adminUid); + console.log("VICKYC11 Endorsement result:", result); assert.strictEqual(result.isEndorsed, true); }); From adbb2794c1ac63a48c8fd62e567f1f8557cd9e27 Mon Sep 17 00:00:00 2001 From: Vicky Chen Date: Wed, 9 Oct 2024 21:55:16 -0400 Subject: [PATCH 10/11] tried error case in posts.js --- test/posts.js | 23 +++++++++++++++++------ 1 file changed, 17 insertions(+), 6 deletions(-) diff --git a/test/posts.js b/test/posts.js index e8d6028ffe..d2854db51a 100644 --- a/test/posts.js +++ b/test/posts.js @@ -164,12 +164,23 @@ describe('Post\'s', () => { }); }); - it('should allow an admin to endorse a post', async function () { - console.log("VICKY10", postResult.postData.pid, adminUid) - const result = await apiPosts.endorse(postResult.postData.pid, adminUid); - console.log("VICKYC11 Endorsement result:", result); - assert.strictEqual(result.isEndorsed, true); - }); + // it('should allow an admin to endorse a post', async function () { + // console.log("VICKY10", postResult.postData.pid, adminUid) + // const result = await apiPosts.endorse(postResult.postData.pid, adminUid); + // console.log("VICKYC11 Endorsement result:", result); + // assert.strictEqual(result.isEndorsed, true); + // }); + + it('should allow an admin to endorse a post', async function () { + try { + console.log("VICKY10", postResult.postData.pid, adminUid); + const result = await apiPosts.endorse(postResult.postData.pid, adminUid); + console.log("Endorsement result:", result); // This will log the result if it works + assert.strictEqual(result.isEndorsed, true); + } catch (err) { + console.error("Endorsement failed with error:", err); // This will log the actual error + } + }); it('should allow a global mod to endorse a post', async function () { const result = await apiPosts.endorse(postResult.postData.pid, globalModUid); From a51706c1ce93cfb05ea2c859abc03cb4f0da5748 Mon Sep 17 00:00:00 2001 From: Vicky Chen Date: Thu, 10 Oct 2024 20:35:22 -0400 Subject: [PATCH 11/11] edited to privileges/posts.js file --- src/privileges/posts.js | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/privileges/posts.js b/src/privileges/posts.js index 4e4a62c7a7..bc5a64c88a 100644 --- a/src/privileges/posts.js +++ b/src/privileges/posts.js @@ -234,8 +234,9 @@ privsPosts.canEndorse = async function (uid) { } console.error("Checking if UID", uid, "is admin..."); const isAdmin = await user.isAdministrator(uid); - console.error("isAdmin result for UID", uid, ":", isAdmin); + console.error("isAdmin result for UID VICKY13", uid, ":", isAdmin); if (isAdmin) { + console.log("True VICKY14"); return true; } console.error("Checking if UID", uid, "is global moderator...");