From 2a750625146a51ce5608b00ae71fc861167139ae Mon Sep 17 00:00:00 2001 From: Yisroel Baum Date: Sun, 3 May 2026 17:11:12 +0300 Subject: [PATCH 1/6] add logout tests for all authed pages --- cypress/e2e/auth.cy.js | 54 ++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 54 insertions(+) diff --git a/cypress/e2e/auth.cy.js b/cypress/e2e/auth.cy.js index ae22d22..bc44396 100644 --- a/cypress/e2e/auth.cy.js +++ b/cypress/e2e/auth.cy.js @@ -69,6 +69,60 @@ describe('Authentication flows', () => { cy.url().should('include', '/login') }) + it('logout button on today page works', () => { + cy.loginAsUser() + cy.visit('/today') + cy.get('#logout').click() + cy.url().should('include', '/login') + cy.visit('/today') + cy.url().should('include', '/login') + }) + + it('logout button on user texts list page works', () => { + cy.loginAsUser() + cy.visit('/texts') + cy.get('#logout').click() + cy.url().should('include', '/login') + cy.visit('/texts') + cy.url().should('include', '/login') + }) + + it('logout button on user specific text page works', () => { + cy.loginAsUser() + cy.visit('/texts/0') + cy.get('#logout').click() + cy.url().should('include', '/login') + cy.visit('/texts/0') + cy.url().should('include', '/login') + }) + + it('logout button on admin page works', () => { + cy.loginAsAdmin() + cy.visit('/admin') + cy.get('#logout').click() + cy.url().should('include', '/login') + cy.visit('/admin') + cy.url().should('include', '/login') + }) + + it('logout button on admin texts list page works', () => { + cy.loginAsAdmin() + cy.visit('/admin/texts') + cy.get('#logout').click() + cy.url().should('include', '/login') + cy.visit('/admin/texts') + cy.url().should('include', '/login') + }) + + it('logout button on admin specific text page works', () => { + cy.loginAsAdmin() + cy.visit('/admin/texts/0') + cy.get('#logout').click() + cy.url().should('include', '/login') + cy.visit('/admin/texts/0') + cy.url().should('include', '/login') + }) + it('non-admin user hitting /admin gets 403', () => { cy.loginAsUser() cy.request({ From e83f098280980b7831c348d9501a3edde48f9e48 Mon Sep 17 00:00:00 2001 From: Yisroel Baum Date: Sun, 3 May 2026 17:25:08 +0300 Subject: [PATCH 2/6] add seeding for manual testing --- data/seedMore.php | 127 ++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 127 insertions(+) create mode 100644 data/seedMore.php diff --git a/data/seedMore.php b/data/seedMore.php new file mode 100644 index 0000000..abea97f --- /dev/null +++ b/data/seedMore.php @@ -0,0 +1,127 @@ + 0, + 'name' => 'Tanach', + 'userId' => 1, + ], +]; + +$nodes = [ + [ + 'id' => 0, + 'title' => 'Tanach', + 'textId' => 0, + 'parentNodeId' => null, + ], + [ + 'id' => 1, + 'title' => 'Torah', + 'textId' => 0, + 'parentNodeId' => 0, + ], + [ + 'id' => 2, + 'title' => 'Neviim', + 'textId' => 0, + 'parentNodeId' => 0, + ], + [ + 'id' => 3, + 'title' => 'Kesuvim', + 'textId' => 0, + 'parentNodeId' => 0, + ], + [ + 'id' => 4, + 'title' => 'Bereishis', + 'textId' => 0, + 'parentNodeId' => 1, + ], + [ + 'id' => 5, + 'title' => 'Shmos', + 'textId' => 0, + 'parentNodeId' => 1, + ], + [ + 'id' => 6, + 'title' => 'Vayikra', + 'textId' => 0, + 'parentNodeId' => 1, + ], + [ + 'id' => 7, + 'title' => 'Bamidbar', + 'textId' => 0, + 'parentNodeId' => 1, + ], + [ + 'id' => 8, + 'title' => 'Devarim', + 'textId' => 0, + 'parentNodeId' => 1, + ], + [ + 'id' => 9, + 'title' => 'Bereishis', + 'textId' => 0, + 'parentNodeId' => 4, + ], + [ + 'id' => 10, + 'title' => 'Noach', + 'textId' => 0, + 'parentNodeId' => 4, + ], + [ + 'id' => 11, + 'title' => 'Lech Lecha', + 'textId' => 0, + 'parentNodeId' => 4, + ], +]; + +// Default credentials: +// admin@example.com / admin1234 (admin) +// user@example.com / password1 (regular user) +// user2@example.com / password2 (second regular user, no texts seeded) +$users = [ + [ + 'id' => 0, + 'email' => 'admin@example.com', + 'passwordHash' => password_hash('admin1234', PASSWORD_DEFAULT), + 'isAdmin' => true, + ], + [ + 'id' => 1, + 'email' => 'user@example.com', + 'passwordHash' => password_hash('password1', PASSWORD_DEFAULT), + 'isAdmin' => false, + ], + [ + 'id' => 2, + 'email' => 'user2@example.com', + 'passwordHash' => password_hash('password2', PASSWORD_DEFAULT), + 'isAdmin' => false, + ], +]; + +$plans = []; +$scheduledNodes = []; +$sessions = []; + +$fileDataMap = [ + 'texts.json' => $texts, + 'nodes.json' => $nodes, + 'users.json' => $users, + 'plans.json' => $plans, + 'scheduledNodes.json' => $scheduledNodes, + 'sessions.json' => $sessions, +]; + +foreach ($fileDataMap as $file => $data) { + $path = __DIR__ . "/$file"; + file_put_contents($path, json_encode($data, JSON_PRETTY_PRINT)); +} From 33668e29303b0dc4f11d89b8299c7d87419f32d6 Mon Sep 17 00:00:00 2001 From: Yisroel Baum Date: Sun, 3 May 2026 17:25:31 +0300 Subject: [PATCH 3/6] add logout button to today and userText --- views/templates/today.php | 1 + views/templates/userText.php | 11 ++++++++--- 2 files changed, 9 insertions(+), 3 deletions(-) diff --git a/views/templates/today.php b/views/templates/today.php index 4a5ed8a..46e85b4 100644 --- a/views/templates/today.php +++ b/views/templates/today.php @@ -12,6 +12,7 @@

Today

Home +
diff --git a/views/templates/userText.php b/views/templates/userText.php index c9b568a..5b2626d 100644 --- a/views/templates/userText.php +++ b/views/templates/userText.php @@ -9,14 +9,19 @@
+ From 17ab181adb4d37e8a684cd930a7d36f90d1d8736 Mon Sep 17 00:00:00 2001 From: Yisroel Baum Date: Sun, 3 May 2026 17:32:48 +0300 Subject: [PATCH 4/6] guard text.js node fetch on non-ok response --- public/js/text.js | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-) diff --git a/public/js/text.js b/public/js/text.js index 2b021d0..7566869 100644 --- a/public/js/text.js +++ b/public/js/text.js @@ -32,8 +32,15 @@ document.addEventListener('DOMContentLoaded', () => { function fetchAndRenderNodes(textId) { return fetch('/api/nodes/' + textId, { credentials: 'same-origin' }) - .then(res => res.json()) + .then(function (response) { + if (!response.ok) { + return null; + } + return response.json(); + }) .then(nodes => { + if (!Array.isArray(nodes)) return; + const existing = document.querySelector('#text-detail > ul'); if (existing) existing.remove(); From 9c062c4f0e056db30fdb4c3b602f79e011a83ac1 Mon Sep 17 00:00:00 2001 From: Yisroel Baum Date: Sun, 3 May 2026 17:33:01 +0300 Subject: [PATCH 5/6] add logout button to admin texts page --- views/templates/texts.php | 2 ++ 1 file changed, 2 insertions(+) diff --git a/views/templates/texts.php b/views/templates/texts.php index a37bd1e..2da7733 100644 --- a/views/templates/texts.php +++ b/views/templates/texts.php @@ -14,6 +14,7 @@ Back to Admin + @@ -31,6 +32,7 @@ + From e2b1371452c846c3c6bd8bc83ca743d1d67873be Mon Sep 17 00:00:00 2001 From: Yisroel Baum Date: Sun, 3 May 2026 17:33:11 +0300 Subject: [PATCH 6/6] add logout button to admin text page --- views/templates/text.php | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/views/templates/text.php b/views/templates/text.php index 6d41421..6c62559 100644 --- a/views/templates/text.php +++ b/views/templates/text.php @@ -9,14 +9,18 @@
+