feat(forum): rebuild plate, post and compose pages
Match the reference layouts for the remaining forum routes: plate pages get the blurred header card, moderator row and the affix tab bar with per-tab filtering, topping posts and moderator-only pending/trash tabs; post pages get the article shell with breadcrumbs, cover, meta row, vote box, tag row and footer actions; compose pages get the reference editor plus settings sidebar (submit/draft, status, access, plate, topic, tag, type, vote) with a cover picker. Saving now honours draft state and the featured image through the REST contract. Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
This commit is contained in:
1 parent
eceddb5f7d
commit
5d3358d844
13 files changed
+891
-199
No files matched your search
@@ -0,0 +1,63 @@
|
||||
const test = require('node:test')
|
||||
const assert = require('node:assert/strict')
|
||||
const fs = require('node:fs')
|
||||
const path = require('node:path')
|
||||
|
||||
const root = path.resolve(__dirname, '..', '..')
|
||||
const read = (file) => fs.readFileSync(path.join(root, file), 'utf8')
|
||||
|
||||
test('plate pages render the reference header card, tab bar and list', () => {
|
||||
const listing = read('src/Forum/ListingView.php')
|
||||
const cards = read('src/Forum/Cards.php')
|
||||
const view = read('src/Forum/View.php')
|
||||
assert.match(view, /public static function listing\(\): void \{\s*ListingView::plate\(\);/)
|
||||
for (const token of ['plate-tab', 'tab-nav-theme', 'affix-header-sm', 'data-forum-tab', 'data-forum-more', 'post_ajax_loader', 'content-wrap', 'content-layout', 'sidebar']) {
|
||||
assert.ok(listing.includes(token), `plate page missing ${token}`)
|
||||
}
|
||||
// Reference header: blurred cover + mask + stats + moderator avatars.
|
||||
for (const token of ['plate-header-wrap', 'forum-header blur-header', 'abs-blur-bg', 'forum-mask', 'moderator-btns', 'count-mates']) {
|
||||
assert.ok(cards.includes(token), `plate header missing ${token}`)
|
||||
}
|
||||
// Moderator-only tabs (pending / trash) appear on plate pages.
|
||||
assert.match(listing, /'pending'/)
|
||||
assert.match(listing, /'trash'/)
|
||||
// Topping posts are pulled out of the main loop on the first tab.
|
||||
assert.match(listing, /_jio_forum_pinned/)
|
||||
assert.match(listing, /post__not_in/)
|
||||
})
|
||||
|
||||
test('post detail pages use the reference article shell', () => {
|
||||
const post = read('src/Forum/PostView.php')
|
||||
const template = read('templates/pages/page-forum-post.php')
|
||||
assert.match(template, /PostView::render\(\)/)
|
||||
for (const token of ['fixed-wrap single-wrap', 'fixed-wrap-content', 'forum-single-cover', 'breadcrumb', 'id="article"', 'article zib-widget forum-article', 'article-header clearfix', 'forum-article-meta', 'wp-posts-content', 'article-tags', 'forum-article-footer', 'footer-actions', 'vote-box forum-vote', 'comments-card']) {
|
||||
assert.ok(post.includes(token), `post page missing ${token}`)
|
||||
}
|
||||
// Banners, permissions and actions stay server-side.
|
||||
assert.match(post, /Access::can_view\(/)
|
||||
assert.match(post, /Cards::title\(\$post, 'article-title'/)
|
||||
assert.match(post, /data-forum-action="score"/)
|
||||
assert.match(post, /jio_is_show_sidebar\(\)/)
|
||||
})
|
||||
|
||||
test('compose pages mirror the reference editor plus settings sidebar', () => {
|
||||
const edit = read('src/Forum/EditView.php')
|
||||
const template = read('templates/pages/page-forum-edit.php')
|
||||
assert.match(template, /EditView::render\(\)/)
|
||||
for (const token of ['editor-main-box', 'edit-posts-featured', 'edit-posts-title', 'line-form-input', 'jio_forum_content', 'bbs-posts-edit', 'but-average', 'bbs-posts-submit', 'data-forum-draft', 'drop-select', 'allow-view-drop', 'plate-drop', 'type-drop', 'forum-type-vote']) {
|
||||
assert.ok(edit.includes(token), `compose page missing ${token}`)
|
||||
}
|
||||
assert.match(edit, /class="sidebar show-sidebar"/)
|
||||
assert.match(edit, /wp_editor\(/)
|
||||
})
|
||||
|
||||
test('compose page saves draft state and the cover through the REST contract', () => {
|
||||
const rest = read('src/Forum/RestPosts.php')
|
||||
const runtime = read('assets/js/forum-runtime.js')
|
||||
assert.match(rest, /\$requested === 'draft'/)
|
||||
assert.match(rest, /featured_image_id/)
|
||||
assert.match(rest, /set_post_thumbnail\(/)
|
||||
for (const token of ['data-forum-type-set', 'data-forum-view', 'data-forum-plate', 'data-forum-status', 'data-forum-topics', 'data-forum-tags', 'data-forum-cover-file']) {
|
||||
assert.ok(runtime.includes(token), `compose runtime missing ${token}`)
|
||||
}
|
||||
})
|
||||
Reference in new issue
Block a user