feat: read the profile's topics from Studio, and add working-copy deletion
Two things an author could not control from Studio. The profile's "주요 관심 주제" was four strings in the JSX. Creating or removing a topic in Studio changed nothing, and correcting the list meant a rebuild and a redeploy. It now renders the published topic list. The old literal opened with "Backend Architecture", which no record in the catalogue actually carries — the profile was advertising a topic that did not exist, and nothing could have caught that while the list lived in the markup. The working-copy list gained a delete control. It routes by kind because the contract and the storage both do: Case and Reference share one table split by type, Question is its own. Decision has no delete — its lifecycle is accept, reject, supersede, which records what happened rather than erasing it — so the control does not appear for it. The list summary carries no version, so deletion reads the working copy first and uses the version it finds. A stale version from a list left open should fail as a conflict, not delete whatever is there now.
This commit is contained in:
@@ -23,8 +23,6 @@ const principles = [
|
||||
},
|
||||
] as const;
|
||||
|
||||
const topics = ["Backend Architecture", "JPA", "Authentication", "Redis"] as const;
|
||||
|
||||
export function ProfilePage() {
|
||||
// The two project slugs this named were the static fixture's, and they exist
|
||||
// in no real deployment — the page asked the backend for them, took two 404s,
|
||||
@@ -34,10 +32,14 @@ export function ProfilePage() {
|
||||
const entries = (await queries.searchPublicContent("")).filter(
|
||||
(item) => item.contentType === "PROJECT",
|
||||
);
|
||||
const resolved = await Promise.all(
|
||||
entries.map((item) => queries.getProject(item.path.replace("/projects/", ""))),
|
||||
);
|
||||
return { currentProjects: resolved.filter((project) => project !== undefined) };
|
||||
const [resolved, topics] = await Promise.all([
|
||||
Promise.all(entries.map((item) => queries.getProject(item.path.replace("/projects/", "")))),
|
||||
queries.listTopics(),
|
||||
]);
|
||||
return {
|
||||
currentProjects: resolved.filter((project) => project !== undefined),
|
||||
topics,
|
||||
};
|
||||
});
|
||||
|
||||
// Only the project list comes from the network. Returning the page-wide
|
||||
@@ -96,14 +98,24 @@ export function ProfilePage() {
|
||||
</ul>
|
||||
)}
|
||||
</section>
|
||||
{/*
|
||||
이 목록은 코드에 네 개가 박혀 있었다 — Studio 에서 주제를 만들거나 지워도 프로필은
|
||||
그대로였고, 고치려면 배포를 다시 해야 했다. 이제 공개 주제 목록을 그대로 그린다.
|
||||
*/}
|
||||
<section className="profile-topics" aria-labelledby="profile-topics-title">
|
||||
<p className="section-kicker">Topics</p>
|
||||
<h2 id="profile-topics-title">주요 관심 주제</h2>
|
||||
<ul>
|
||||
{topics.map((topic) => (
|
||||
<li key={topic}>{topic}</li>
|
||||
))}
|
||||
</ul>
|
||||
{!view.ready ? (
|
||||
view.fallback
|
||||
) : view.data.topics.length === 0 ? (
|
||||
<p className="public-empty-note">아직 등록한 주제가 없습니다.</p>
|
||||
) : (
|
||||
<ul>
|
||||
{view.data.topics.map((topic) => (
|
||||
<li key={topic.slug}>{topic.name}</li>
|
||||
))}
|
||||
</ul>
|
||||
)}
|
||||
</section>
|
||||
</main>
|
||||
);
|
||||
|
||||
Reference in New Issue
Block a user