This commit is contained in:
2025-07-06 19:57:20 +09:00
parent da31fe93c4
commit 191e5d3a76
22 changed files with 344 additions and 231 deletions
+26 -37
View File
@@ -21,7 +21,7 @@
"markdown-it": "^14.1.0", "markdown-it": "^14.1.0",
"react": "^19.1.0", "react": "^19.1.0",
"react-dom": "^19.1.0", "react-dom": "^19.1.0",
"react-helmet": "^6.1.0", "react-helmet-async": "^2.0.5",
"react-markdown": "^10.1.0", "react-markdown": "^10.1.0",
"react-markdown-editor-lite": "^1.3.4", "react-markdown-editor-lite": "^1.3.4",
"react-router-dom": "^6.30.0", "react-router-dom": "^6.30.0",
@@ -3841,6 +3841,15 @@
"integrity": "sha512-0aO8FkhNZlj/ZIbNi7Lxxr12obT7cL1moPfE4tg1LkX7LlLfC6DeX4l2ZEud1ukP9jNQyNnfzQVqwbwmAATY4Q==", "integrity": "sha512-0aO8FkhNZlj/ZIbNi7Lxxr12obT7cL1moPfE4tg1LkX7LlLfC6DeX4l2ZEud1ukP9jNQyNnfzQVqwbwmAATY4Q==",
"license": "MIT" "license": "MIT"
}, },
"node_modules/invariant": {
"version": "2.2.4",
"resolved": "https://registry.npmjs.org/invariant/-/invariant-2.2.4.tgz",
"integrity": "sha512-phJfQVBuaJM5raOpJjSfkiD6BpbCE4Ns//LaXl6wGYtUBY83nWS6Rf9tXm2e8VaK60JEjYldbPif/A2B1C2gNA==",
"license": "MIT",
"dependencies": {
"loose-envify": "^1.0.0"
}
},
"node_modules/is-alphabetical": { "node_modules/is-alphabetical": {
"version": "2.0.1", "version": "2.0.1",
"resolved": "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-2.0.1.tgz", "resolved": "https://registry.npmjs.org/is-alphabetical/-/is-alphabetical-2.0.1.tgz",
@@ -4964,6 +4973,7 @@
"version": "4.1.1", "version": "4.1.1",
"resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz", "resolved": "https://registry.npmjs.org/object-assign/-/object-assign-4.1.1.tgz",
"integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==", "integrity": "sha512-rJgTQnkUnH1sFw8yT6VSU3zD3sWmu6sZhIseY8VX+GRu3P6F7Fu+JNDoXfklElbLJSnc3FUQHVe4cU5hj+BcUg==",
"dev": true,
"license": "MIT", "license": "MIT",
"engines": { "engines": {
"node": ">=0.10.0" "node": ">=0.10.0"
@@ -5338,17 +5348,6 @@
"node": ">= 0.8.0" "node": ">= 0.8.0"
} }
}, },
"node_modules/prop-types": {
"version": "15.8.1",
"resolved": "https://registry.npmjs.org/prop-types/-/prop-types-15.8.1.tgz",
"integrity": "sha512-oj87CgZICdulUohogVAR7AjlC0327U4el4L6eAvOqCeudMDVU0NThNaV+b9Df4dXgSP1gXMTnPdhfe/2qDH5cg==",
"license": "MIT",
"dependencies": {
"loose-envify": "^1.4.0",
"object-assign": "^4.1.1",
"react-is": "^16.13.1"
}
},
"node_modules/property-information": { "node_modules/property-information": {
"version": "7.1.0", "version": "7.1.0",
"resolved": "https://registry.npmjs.org/property-information/-/property-information-7.1.0.tgz", "resolved": "https://registry.npmjs.org/property-information/-/property-information-7.1.0.tgz",
@@ -5444,27 +5443,20 @@
"integrity": "sha512-nsO+KSNgo1SbJqJEYRE9ERzo7YtYbou/OqjSQKxV7jcKox7+usiUVZOAC+XnDOABXggQTno0Y1CpVnuWEc1boQ==", "integrity": "sha512-nsO+KSNgo1SbJqJEYRE9ERzo7YtYbou/OqjSQKxV7jcKox7+usiUVZOAC+XnDOABXggQTno0Y1CpVnuWEc1boQ==",
"license": "MIT" "license": "MIT"
}, },
"node_modules/react-helmet": { "node_modules/react-helmet-async": {
"version": "6.1.0", "version": "2.0.5",
"resolved": "https://registry.npmjs.org/react-helmet/-/react-helmet-6.1.0.tgz", "resolved": "https://registry.npmjs.org/react-helmet-async/-/react-helmet-async-2.0.5.tgz",
"integrity": "sha512-4uMzEY9nlDlgxr61NL3XbKRy1hEkXmKNXhjbAIOVw5vcFrsdYbH2FEwcNyWvWinl103nXgzYNlns9ca+8kFiWw==", "integrity": "sha512-rYUYHeus+i27MvFE+Jaa4WsyBKGkL6qVgbJvSBoX8mbsWoABJXdEO0bZyi0F6i+4f0NuIb8AvqPMj3iXFHkMwg==",
"license": "MIT", "license": "Apache-2.0",
"dependencies": { "dependencies": {
"object-assign": "^4.1.1", "invariant": "^2.2.4",
"prop-types": "^15.7.2", "react-fast-compare": "^3.2.2",
"react-fast-compare": "^3.1.1", "shallowequal": "^1.1.0"
"react-side-effect": "^2.1.0"
}, },
"peerDependencies": { "peerDependencies": {
"react": ">=16.3.0" "react": "^16.6.0 || ^17.0.0 || ^18.0.0"
} }
}, },
"node_modules/react-is": {
"version": "16.13.1",
"resolved": "https://registry.npmjs.org/react-is/-/react-is-16.13.1.tgz",
"integrity": "sha512-24e6ynE2H+OKt4kqsOvNd8kBpV65zoxbA4BVsEOB3ARVWQki/DHzaUoC5KuON/BiccDaCCTZBuOcfZs70kR8bQ==",
"license": "MIT"
},
"node_modules/react-markdown": { "node_modules/react-markdown": {
"version": "10.1.0", "version": "10.1.0",
"resolved": "https://registry.npmjs.org/react-markdown/-/react-markdown-10.1.0.tgz", "resolved": "https://registry.npmjs.org/react-markdown/-/react-markdown-10.1.0.tgz",
@@ -5596,15 +5588,6 @@
"react-dom": ">=16.8" "react-dom": ">=16.8"
} }
}, },
"node_modules/react-side-effect": {
"version": "2.1.2",
"resolved": "https://registry.npmjs.org/react-side-effect/-/react-side-effect-2.1.2.tgz",
"integrity": "sha512-PVjOcvVOyIILrYoyGEpDN3vmYNLdy1CajSFNt4TDsVQC5KpTijDvWVoR+/7Rz2xT978D8/ZtFceXxzsPwZEDvw==",
"license": "MIT",
"peerDependencies": {
"react": "^16.3.0 || ^17.0.0 || ^18.0.0"
}
},
"node_modules/react-style-singleton": { "node_modules/react-style-singleton": {
"version": "2.2.3", "version": "2.2.3",
"resolved": "https://registry.npmjs.org/react-style-singleton/-/react-style-singleton-2.2.3.tgz", "resolved": "https://registry.npmjs.org/react-style-singleton/-/react-style-singleton-2.2.3.tgz",
@@ -5805,6 +5788,12 @@
"semver": "bin/semver.js" "semver": "bin/semver.js"
} }
}, },
"node_modules/shallowequal": {
"version": "1.1.0",
"resolved": "https://registry.npmjs.org/shallowequal/-/shallowequal-1.1.0.tgz",
"integrity": "sha512-y0m1JoUZSlPAjXVtPPW70aZWfIL/dSP7AFkRnniLCrK/8MDKog3TySTBmckD+RObVxH0v4Tox67+F14PdED2oQ==",
"license": "MIT"
},
"node_modules/shebang-command": { "node_modules/shebang-command": {
"version": "2.0.0", "version": "2.0.0",
"resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz", "resolved": "https://registry.npmjs.org/shebang-command/-/shebang-command-2.0.0.tgz",
+1 -1
View File
@@ -22,7 +22,7 @@
"markdown-it": "^14.1.0", "markdown-it": "^14.1.0",
"react": "^19.1.0", "react": "^19.1.0",
"react-dom": "^19.1.0", "react-dom": "^19.1.0",
"react-helmet": "^6.1.0", "react-helmet-async": "^2.0.5",
"react-markdown": "^10.1.0", "react-markdown": "^10.1.0",
"react-markdown-editor-lite": "^1.3.4", "react-markdown-editor-lite": "^1.3.4",
"react-router-dom": "^6.30.0", "react-router-dom": "^6.30.0",
+11 -14
View File
@@ -27,31 +27,28 @@ export default () => {
const [user, setUser] = useState<User | null> (null) const [user, setUser] = useState<User | null> (null)
useEffect (() => { useEffect (() => {
const createUser = () => ( const createUser = async () => {
axios.post (`${ API_BASE_URL }/users`) const { data } = await axios.post (`${ API_BASE_URL }/users`)
.then (res => { if (data.code)
if (res.data.code)
{ {
localStorage.setItem ('user_code', res.data.code) localStorage.setItem ('user_code', data.code)
setUser (toCamel (res.data.user, { deep: true })) setUser (toCamel (data.user, { deep: true }))
}
} }
}))
const code = localStorage.getItem ('user_code') const code = localStorage.getItem ('user_code')
if (code) if (code)
{ {
void (axios.post (`${ API_BASE_URL }/users/verify`, { code }) void (async () => {
.then (res => { const { data } = await axios.post (`${ API_BASE_URL }/users/verify`, { code })
if (res.data.valid) if (data.valid)
setUser (toCamel (res.data.user, { deep: true })) setUser (toCamel (data.user, { deep: true }))
else else
createUser () createUser ()
})) }) ()
} }
else else
createUser () createUser ()
alert ('このサイトはまだ作りかけです!!!!\n出てけ!!!!!!!!!!!!!!!!!!!!')
}, []) }, [])
return ( return (
+1 -1
View File
@@ -47,7 +47,7 @@ export default ({ post }: Props) => {
<SidebarComponent> <SidebarComponent>
<TagSearch /> <TagSearch />
{CATEGORIES.map ((cat: Category) => cat in tags && ( {CATEGORIES.map ((cat: Category) => cat in tags && (
<div className="my-3"> <div className="my-3" key={cat}>
<SubsectionTitle>{categoryNames[cat]}</SubsectionTitle> <SubsectionTitle>{categoryNames[cat]}</SubsectionTitle>
<ul> <ul>
{tags[cat].map (tag => ( {tags[cat].map (tag => (
+3 -5
View File
@@ -55,16 +55,14 @@ export default ({ posts }: Props) => {
<TagSearch /> <TagSearch />
<SectionTitle></SectionTitle> <SectionTitle></SectionTitle>
<ul> <ul>
{CATEGORIES.map (cat => cat in tags && ( {CATEGORIES.flatMap (cat => cat in tags ? (
<> tags[cat].map (tag => (
{tags[cat].map (tag => (
<li key={tag.id} className="mb-1"> <li key={tag.id} className="mb-1">
<Link to={`/posts?${ (new URLSearchParams ({ tags: tag.name })).toString () }`}> <Link to={`/posts?${ (new URLSearchParams ({ tags: tag.name })).toString () }`}>
{tag.name} {tag.name}
</Link> </Link>
<span className="ml-1">{tag.postCount}</span> <span className="ml-1">{tag.postCount}</span>
</li>))} </li>))) : [])}
</>))}
</ul> </ul>
<SectionTitle></SectionTitle> <SectionTitle></SectionTitle>
{posts.length && ( {posts.length && (
@@ -0,0 +1,21 @@
import { Button } from '@/components/ui/button'
import { Dialog,
DialogContent,
DialogDescription,
DialogTitle,
DialogTrigger } from '@/components/ui/dialog'
type Props = { visible: boolean
onVisibleChange: (visible: boolean) => void
user: User | null,
setUser: (user: User) => void }
export default ({ visible, onVisibleChange, user, setUser }: Props) => {
return (
<Dialog open={visible} onOpenChange={onVisibleChange}>
<DialogContent className="space-y-6">
<DialogTitle></DialogTitle>
</DialogContent>
</Dialog>)
}
@@ -0,0 +1,32 @@
import { Button } from '@/components/ui/button'
import { Dialog,
DialogContent,
DialogDescription,
DialogTitle,
DialogTrigger } from '@/components/ui/dialog'
type Props = { visible: boolean
onVisibleChange: (visible: boolean) => void
user: User | null }
export default ({ visible, onVisibleChange, user }: Props) => {
return (
<Dialog open={visible} onOpenChange={onVisibleChange}>
<DialogContent className="space-y-6">
<DialogTitle></DialogTitle>
<div>
<p></p>
<div className="m-2">{user?.inheritanceCode}</div>
<p className="mt-1 text-sm text-red-500">
!
</p>
<div className="my-4">
<Button className="px-4 py-2 bg-red-600 text-white rounded disabled:bg-gray-400">
</Button>
</div>
</div>
</DialogContent>
</Dialog>)
}
+4
View File
@@ -7,3 +7,7 @@ export const CATEGORIES = ['general',
'meta'] as const 'meta'] as const
export const USER_ROLES = ['admin', 'member', 'guest'] as const export const USER_ROLES = ['admin', 'member', 'guest'] as const
export const enum ViewFlagBehavior { OnShowedDetail = 1,
OnClickedLink = 2,
NotAuto = 3 }
+9 -4
View File
@@ -1,10 +1,15 @@
import { StrictMode } from 'react' import { StrictMode } from 'react'
import { createRoot } from 'react-dom/client' import { createRoot } from 'react-dom/client'
import './index.css' import { HelmetProvider } from 'react-helmet-async'
import App from './App.tsx'
import '@/index.css'
import App from '@/App'
const helmetContext = { }
createRoot (document.getElementById ('root')!).render ( createRoot (document.getElementById ('root')!).render (
<StrictMode> <StrictMode>
<HelmetProvider context={helmetContext}>
<App /> <App />
</StrictMode>, </HelmetProvider>
) </StrictMode>)
+1 -1
View File
@@ -1,4 +1,4 @@
import { Helmet } from 'react-helmet' import { Helmet } from 'react-helmet-async'
import MainArea from '@/components/layout/MainArea' import MainArea from '@/components/layout/MainArea'
import { SITE_TITLE } from '@/config' import { SITE_TITLE } from '@/config'
+1 -1
View File
@@ -1,7 +1,7 @@
import axios from 'axios' import axios from 'axios'
import toCamel from 'camelcase-keys' import toCamel from 'camelcase-keys'
import React, { useEffect, useState } from 'react' import React, { useEffect, useState } from 'react'
import { Helmet } from 'react-helmet' import { Helmet } from 'react-helmet-async'
import { Link, useLocation, useParams } from 'react-router-dom' import { Link, useLocation, useParams } from 'react-router-dom'
import TagDetailSidebar from '@/components/TagDetailSidebar' import TagDetailSidebar from '@/components/TagDetailSidebar'
+22 -15
View File
@@ -1,7 +1,7 @@
import axios from 'axios' import axios from 'axios'
import toCamel from 'camelcase-keys' import toCamel from 'camelcase-keys'
import React, { useEffect, useRef, useState } from 'react' import React, { useEffect, useRef, useState } from 'react'
import { Helmet } from 'react-helmet' import { Helmet } from 'react-helmet-async'
import { Link, useLocation } from 'react-router-dom' import { Link, useLocation } from 'react-router-dom'
import TagSidebar from '@/components/TagSidebar' import TagSidebar from '@/components/TagSidebar'
@@ -14,7 +14,7 @@ import type { Post, Tag, WikiPage } from '@/types'
export default () => { export default () => {
const [posts, setPosts] = useState<Post[] | null> (null) const [posts, setPosts] = useState<Post[]> ([])
const [wikiPage, setWikiPage] = useState<WikiPage | null> (null) const [wikiPage, setWikiPage] = useState<WikiPage | null> (null)
const [cursor, setCursor] = useState ('') const [cursor, setCursor] = useState ('')
const [loading, setLoading] = useState (false) const [loading, setLoading] = useState (false)
@@ -28,7 +28,7 @@ export default () => {
match: (anyFlg ? 'any' : 'all'), match: (anyFlg ? 'any' : 'all'),
...(withCursor ? { cursor } : { }) } }) ...(withCursor ? { cursor } : { }) } })
const data = toCamel (res.data, { deep: true }) const data = toCamel (res.data, { deep: true })
setPosts (posts => [...(posts || []), ...data.posts]) setPosts (posts => [...(withCursor ? posts : []), ...data.posts])
setCursor (data.nextCursor) setCursor (data.nextCursor)
setLoading (false) setLoading (false)
} }
@@ -52,18 +52,24 @@ export default () => {
}, [loaderRef, loading]) }, [loaderRef, loading])
useEffect (() => { useEffect (() => {
setPosts (null) setPosts ([])
setCursor ('')
loadMore (false) loadMore (false)
setWikiPage (null) setWikiPage (null)
if (tags.length === 1) if (tags.length === 1)
{ {
void (axios.get (`${ API_BASE_URL }/wiki/title/${ encodeURIComponent (tags[0]) }`) void (async () => {
.then (res => setWikiPage (toCamel (res.data, { deep: true }))) try
.catch (() => { {
const tagName = tags[0]
const { data } = await axios.get (`${ API_BASE_URL }/wiki/title/${ tagName }`)
setWikiPage (toCamel (data, { deep: true }))
}
catch
{
; ;
})) }
}) ()
} }
}, [location.search]) }, [location.search])
@@ -76,28 +82,29 @@ export default () => {
: `${ SITE_TITLE } 〜 ぼざクリ関聯綜合リンク集サイト`} : `${ SITE_TITLE } 〜 ぼざクリ関聯綜合リンク集サイト`}
</title> </title>
</Helmet> </Helmet>
<TagSidebar posts={posts?.slice (0, 20) || []} /> <TagSidebar posts={posts.slice (0, 20)} />
<MainArea> <MainArea>
<TabGroup key={wikiPage}> <TabGroup key={wikiPage}>
<Tab name="広場"> <Tab name="広場">
{posts == null ? 'Loading...' : ( {posts.length
posts.length
? ( ? (
<div className="flex flex-wrap gap-4 p-4"> <div className="flex flex-wrap gap-4 p-4">
{posts.map (post => ( {posts.map (post => (
<Link to={`/posts/${ post.id }`} <Link to={`/posts/${ post.id }`}
key={post.id} key={post.id}
className="w-40 h-40 overflow-hidden rounded-lg shadow-md hover:shadow-lg"> className="w-40 h-40 overflow-hidden rounded-lg shadow-md hover:shadow-lg">
<img src={post.thumbnail ?? post.thumbnailBase} <img src={post.thumbnail || post.thumbnailBase || null}
alt={post.title || post.url} alt={post.title || post.url}
title={post.title || post.url || null}
className="object-none w-full h-full" /> className="object-none w-full h-full" />
</Link>))} </Link>))}
</div>) </div>)
: '広場には何もありませんよ.')} : !(loading) && '広場には何もありませんよ.'}
{loading && 'Loading...'}
<div ref={loaderRef} className="h-12"></div> <div ref={loaderRef} className="h-12"></div>
</Tab> </Tab>
{(wikiPage && wikiPage.body) && ( {(wikiPage && wikiPage.body) && (
<Tab name="Wiki" init={posts && !(posts.length)}> <Tab name="Wiki" init={!(posts.length)}>
<WikiBody body={wikiPage.body} /> <WikiBody body={wikiPage.body} />
<div className="my-2"> <div className="my-2">
<Link to={`/wiki/${ wikiPage.title }`}>Wiki </Link> <Link to={`/wiki/${ wikiPage.title }`}>Wiki </Link>
+2 -2
View File
@@ -1,6 +1,6 @@
import axios from 'axios' import axios from 'axios'
import React, { useEffect, useState, useRef } from 'react' import React, { useEffect, useState, useRef } from 'react'
import { Helmet } from 'react-helmet' import { Helmet } from 'react-helmet-async'
import { Link, useLocation, useParams, useNavigate } from 'react-router-dom' import { Link, useLocation, useParams, useNavigate } from 'react-router-dom'
import NicoViewer from '@/components/NicoViewer' import NicoViewer from '@/components/NicoViewer'
@@ -49,7 +49,7 @@ export default () => {
toast ({ title: '投稿成功!' }) toast ({ title: '投稿成功!' })
navigate ('/posts') navigate ('/posts')
}) })
.catch (e => toast ({ title: '投稿失敗', .catch (() => toast ({ title: '投稿失敗',
description: '入力を確認してください。' }))) description: '入力を確認してください。' })))
} }
+58 -5
View File
@@ -1,26 +1,48 @@
import { useEffect, useState } from 'react' import { useEffect, useState } from 'react'
import { Helmet } from 'react-helmet' import { Helmet } from 'react-helmet-async'
import Form from '@/components/common/Form' import Form from '@/components/common/Form'
import Label from '@/components/common/Label' import Label from '@/components/common/Label'
import PageTitle from '@/components/common/PageTitle' import PageTitle from '@/components/common/PageTitle'
import MainArea from '@/components/layout/MainArea' import MainArea from '@/components/layout/MainArea'
import { SITE_TITLE } from '@/config' import InheritDialogue from '@/components/users/InheritDialogue'
import UserCodeDialogue from '@/components/users/UserCodeDialogue'
import { API_BASE_URL, SITE_TITLE } from '@/config'
import { Button } from '@/components/ui/button'
import type { User } from '@/types' import type { User } from '@/types'
type Props = { user: User type Props = { user: User | null
setUser: (user: User) => void } setUser: (user: User) => void }
export default ({ user, setUser }: Props) => { export default ({ user, setUser }: Props) => {
const [name, setName] = useState ('') const [name, setName] = useState ('')
const [userCodeVsbl, setUserCodeVsbl] = useState (false)
const [inheritVsbl, setInheritVsbl] = useState (false)
const handleSubmit = async () => {
const formData = new FormData ()
formData.append ('name', name)
try
{
await axios.post (`${ API_BASE_URL }/users`, formData, { headers: {
'Content-Type': 'multipart/form-data',
'X-Transfer-Code': localStorage.getItem ('user_code') || '' } })
toast ({ title: '設定を更新しました.' })
}
catch
{
toast ({ title: 'しっぱい……' })
}
}
useEffect (() => { useEffect (() => {
if (!user) if (!user)
return return
setName (user?.name) setName (user.name)
}, [user]) }, [user])
return ( return (
@@ -29,6 +51,7 @@ export default ({ user, setUser }: Props) => {
<meta name="robots" content="noindex" /> <meta name="robots" content="noindex" />
<title> | {SITE_TITLE}</title> <title> | {SITE_TITLE}</title>
</Helmet> </Helmet>
<Form> <Form>
<PageTitle></PageTitle> <PageTitle></PageTitle>
@@ -41,10 +64,40 @@ export default ({ user, setUser }: Props) => {
placeholder="名もなきニジラー" placeholder="名もなきニジラー"
onChange={ev => setName (ev.target.value)} /> onChange={ev => setName (ev.target.value)} />
{(user && !(user.name)) && ( {(user && !(user.name)) && (
<p class="mt-1 text-sm text-red-500"> <p className="mt-1 text-sm text-red-500">
30 !!!! 30 !!!!
</p>)} </p>)}
</div> </div>
{/* 送信 */}
<Button onClick={handleSubmit}
className="px-4 py-2 bg-blue-600 text-white rounded disabled:bg-gray-400">
</Button>
{/* 引継ぎ */}
<div>
<Label></Label>
<Button onClick={() => setUserCodeVsbl (true)}
className="px-4 py-2 bg-gray-600 text-white rounded disabled:bg-gray-400"
disabled={!(user)}>
</Button>
<Button onClick={() => setInheritVsbl (true)}
className="ml-2 px-4 py-2 bg-red-600 text-white rounded disabled:bg-gray-400"
disabled={!(user)}>
</Button>
</div>
</Form> </Form>
<UserCodeDialogue visible={userCodeVsbl}
onVisibleChange={setUserCodeVsbl}
user={user} />
<InheritDialogue visible={inheritVsbl}
onVisibleChange={setInheritVsbl}
user={user}
setUser={setUser} />
</MainArea>) </MainArea>)
} }
+1 -1
View File
@@ -1,7 +1,7 @@
import axios from 'axios' import axios from 'axios'
import toCamel from 'camelcase-keys' import toCamel from 'camelcase-keys'
import { useEffect, useState } from 'react' import { useEffect, useState } from 'react'
import { Helmet } from 'react-helmet' import { Helmet } from 'react-helmet-async'
import { Link, useLocation, useNavigate, useParams } from 'react-router-dom' import { Link, useLocation, useNavigate, useParams } from 'react-router-dom'
import WikiBody from '@/components/WikiBody' import WikiBody from '@/components/WikiBody'
+1 -1
View File
@@ -1,7 +1,7 @@
import axios from 'axios' import axios from 'axios'
import toCamel from 'camelcase-keys' import toCamel from 'camelcase-keys'
import { useEffect, useState } from 'react' import { useEffect, useState } from 'react'
import { Helmet } from 'react-helmet' import { Helmet } from 'react-helmet-async'
import { Link, useLocation, useParams } from 'react-router-dom' import { Link, useLocation, useParams } from 'react-router-dom'
import PageTitle from '@/components/common/PageTitle' import PageTitle from '@/components/common/PageTitle'
+1 -1
View File
@@ -1,7 +1,7 @@
import axios from 'axios' import axios from 'axios'
import MarkdownIt from 'markdown-it' import MarkdownIt from 'markdown-it'
import React, { useEffect, useState, useRef } from 'react' import React, { useEffect, useState, useRef } from 'react'
import { Helmet } from 'react-helmet' import { Helmet } from 'react-helmet-async'
import MdEditor from 'react-markdown-editor-lite' import MdEditor from 'react-markdown-editor-lite'
import { Link, useLocation, useParams, useNavigate } from 'react-router-dom' import { Link, useLocation, useParams, useNavigate } from 'react-router-dom'
+1 -1
View File
@@ -1,7 +1,7 @@
import axios from 'axios' import axios from 'axios'
import toCamel from 'camelcase-keys' import toCamel from 'camelcase-keys'
import { useEffect, useState } from 'react' import { useEffect, useState } from 'react'
import { Helmet } from 'react-helmet' import { Helmet } from 'react-helmet-async'
import { Link, useLocation, useParams } from 'react-router-dom' import { Link, useLocation, useParams } from 'react-router-dom'
import MainArea from '@/components/layout/MainArea' import MainArea from '@/components/layout/MainArea'
+1 -1
View File
@@ -1,7 +1,7 @@
import axios from 'axios' import axios from 'axios'
import MarkdownIt from 'markdown-it' import MarkdownIt from 'markdown-it'
import React, { useEffect, useState, useRef } from 'react' import React, { useEffect, useState, useRef } from 'react'
import { Helmet } from 'react-helmet' import { Helmet } from 'react-helmet-async'
import MdEditor from 'react-markdown-editor-lite' import MdEditor from 'react-markdown-editor-lite'
import { Link, useLocation, useParams, useNavigate } from 'react-router-dom' import { Link, useLocation, useParams, useNavigate } from 'react-router-dom'
+1 -1
View File
@@ -1,7 +1,7 @@
import axios from 'axios' import axios from 'axios'
import toCamel from 'camelcase-keys' import toCamel from 'camelcase-keys'
import React, { useEffect, useState } from 'react' import React, { useEffect, useState } from 'react'
import { Helmet } from 'react-helmet' import { Helmet } from 'react-helmet-async'
import { Link } from 'react-router-dom' import { Link } from 'react-router-dom'
import SectionTitle from '@/components/common/SectionTitle' import SectionTitle from '@/components/common/SectionTitle'
import MainArea from '@/components/layout/MainArea' import MainArea from '@/components/layout/MainArea'
+5
View File
@@ -0,0 +1,5 @@
import { Route,
createBrowserRouter,
createRoutesFromElements } from 'react-router-dom'
import App from '@/App'
+4 -2
View File
@@ -2,6 +2,7 @@ import { defineConfig } from 'vite'
import react from '@vitejs/plugin-react' import react from '@vitejs/plugin-react'
import path from 'path' import path from 'path'
// https://vite.dev/config/ // https://vite.dev/config/
export default defineConfig ({ export default defineConfig ({
plugins: [react()], plugins: [react()],
@@ -12,5 +13,6 @@ export default defineConfig({
allowedHosts: ['hub.nizika.monster', 'localhost'], allowedHosts: ['hub.nizika.monster', 'localhost'],
proxy: { '/api': { target: 'http://localhost:3002', proxy: { '/api': { target: 'http://localhost:3002',
changeOrigin: true, changeOrigin: true,
secure: false } } } secure: false } },
}) watch: { usePolling: true,
interval: 100 } } })