From cfcf3464463ca2b40a05ec9ebffca0879f24b604 Mon Sep 17 00:00:00 2001 From: CanisMinor Date: Fri, 12 Apr 2024 03:09:42 +0000 Subject: [PATCH] =?UTF-8?q?=F0=9F=91=B7=20ci:=20Update=20ci?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .bunfig.toml | 3 + .changelogrc.js | 1 + .commitlintrc.js | 1 + .editorconfig | 16 ++++ .eslintignore | 2 +- .github/FUNDING.yml | 13 +++ .github/ISSUE_TEMPLATE/1_bug_report.yml | 45 +++++++++ .github/ISSUE_TEMPLATE/2_feature_request.yml | 21 +++++ .github/ISSUE_TEMPLATE/3_question.yml | 15 +++ .github/ISSUE_TEMPLATE/4_other.md | 7 ++ .github/PULL_REQUEST_TEMPLATE.md | 19 ++++ .github/workflows/issue-auto-comments.yml | 72 ++++++++++++++ .github/workflows/issue-check-inactive.yml | 23 +++++ .github/workflows/issue-close-require.yml | 52 +++++++++++ .github/workflows/release.yml | 36 +++++++ .github/workflows/test.yml | 27 ++++++ .gitignore | 70 +++++++++----- .husky/commit-msg | 4 + .husky/pre-commit | 5 + .npmrc | 12 ++- .prettierignore | 65 ++++++++++++- .prettierrc.js | 21 +---- .releaserc.js | 1 + .remarkrc.js | 1 + README.md | 32 +++---- next.config.mjs | 38 +++++++- package.json | 93 ++++++++++++++++--- renovate.json | 13 +++ .../api/chat/openai/createErrorResponse.ts | 3 +- src/app/api/chat/openai/route.ts | 6 +- src/app/api/voice/edge/voices/route.ts | 3 +- src/app/api/voice/microsoft/voices/route.ts | 11 ++- src/app/home/Background/index.tsx | 1 + src/app/home/Dialog/index.tsx | 1 + src/app/home/RoleSelect/index.tsx | 4 +- src/app/home/RoleSelect/style.ts | 61 +++++------- src/app/home/VirtualIdol/index.tsx | 1 + src/app/home/page.tsx | 1 + src/app/layout.tsx | 1 + src/app/page.tsx | 2 +- src/components/AgentInfo/index.tsx | 4 +- src/components/AgentMeta/index.tsx | 4 +- src/components/Application/index.tsx | 1 + src/components/DanceInfo/index.tsx | 4 +- .../HolographicCard/components/Container.tsx | 3 +- .../components/LaserShine/LaserShine.tsx | 1 + .../components/LaserShine/useLaserShine.ts | 1 + .../components/Orbit/index.tsx | 1 + src/components/HolographicCard/index.tsx | 1 + src/components/Panel/Container.tsx | 4 +- src/components/Panel/index.tsx | 4 +- src/constants/dance.ts | 20 ++-- src/features/AgentViewer/ToolBar/index.tsx | 3 +- src/features/AgentViewer/index.tsx | 4 +- src/features/ChatInput/Actions/History.tsx | 3 +- src/features/ChatInput/Actions/Record.tsx | 5 +- src/features/ChatInput/Actions/Token.tsx | 5 +- .../ChatInput/Actions/Voice/index.tsx | 6 +- src/features/ChatInput/Footer/index.tsx | 1 + src/features/ChatInput/MessageInput/index.tsx | 9 +- src/features/ChatInput/TextArea.tsx | 7 +- src/features/ChatItem/Actions/Assistant.tsx | 3 +- src/features/ChatItem/Actions/User.tsx | 3 +- src/features/ChatItem/Actions/index.tsx | 8 +- src/features/ChatItem/ActionsBar.tsx | 8 +- src/features/ChatItem/Error/ApiError.tsx | 4 +- src/features/ChatItem/Error/ApiKeyForm.tsx | 5 +- src/features/ChatItem/Error/OpenAPIKey.tsx | 1 + src/features/ChatItem/Error/index.tsx | 6 +- src/features/ChatItem/Messages/Default.tsx | 4 +- src/features/ChatItem/Messages/index.tsx | 4 +- src/features/ChatItem/index.tsx | 8 +- src/features/ChatItem/type.ts | 3 +- src/features/ImageViewer/index.tsx | 1 + src/features/Timer/index.tsx | 1 + src/features/emoteController/autoBlink.ts | 9 +- src/features/emoteController/autoLookAt.ts | 5 +- .../emoteController/emoteController.ts | 7 +- .../emoteController/expressionController.ts | 1 + src/features/messages/speakCharacter.ts | 1 + src/features/vrmViewer/model.ts | 8 +- src/features/vrmViewer/viewer.ts | 1 + src/hooks/useCalculateToken.ts | 3 +- src/hooks/useSendMessage.ts | 3 +- src/layout/index.tsx | 8 +- .../AgentPanel/Agent/AgentCard/index.tsx | 9 +- .../AgentPanel/Agent/AgentList/index.tsx | 9 +- src/panels/AgentPanel/Agent/index.tsx | 4 +- src/panels/AgentPanel/index.tsx | 4 +- src/panels/ChatPanel/ChatBot/ChatHeader.tsx | 1 + .../ChatPanel/ChatBot/ChatList/index.tsx | 6 +- src/panels/ChatPanel/ChatBot/index.tsx | 1 + src/panels/ChatPanel/ChatBot/type.ts | 3 +- src/panels/ChatPanel/SideBar/Header.tsx | 4 +- .../ChatPanel/SideBar/SessionList/List.tsx | 6 +- .../SessionList/SessionItem/Actions.tsx | 3 +- .../SideBar/SessionList/SessionItem/index.tsx | 3 +- src/panels/ChatPanel/SideBar/index.tsx | 1 + src/panels/ChatPanel/index.tsx | 4 +- src/panels/ConfigPanel/Config/common.tsx | 9 +- src/panels/ConfigPanel/Config/index.tsx | 1 + .../ConfigPanel/Config/model/openai.tsx | 7 +- src/panels/ConfigPanel/index.tsx | 4 +- .../DancePanel/Dance/DanceCard/index.tsx | 5 +- .../DancePanel/Dance/DanceList/index.tsx | 7 +- src/panels/DancePanel/Dance/index.tsx | 1 + src/panels/DancePanel/index.tsx | 4 +- .../Agent/AgentCard/SubscribeButton.tsx | 3 +- .../MarketPanel/Agent/AgentCard/index.tsx | 7 +- .../Agent/AgentIndex/AgentList.tsx | 5 +- .../MarketPanel/Agent/AgentIndex/Header.tsx | 3 +- .../MarketPanel/Agent/AgentIndex/index.tsx | 1 + src/panels/MarketPanel/Agent/index.tsx | 1 + .../Dance/DanceCard/SubscribeButton.tsx | 3 +- .../MarketPanel/Dance/DanceCard/index.tsx | 7 +- .../Dance/DanceIndex/DanceList.tsx | 5 +- .../MarketPanel/Dance/DanceIndex/Header.tsx | 3 +- .../MarketPanel/Dance/DanceIndex/index.tsx | 1 + src/panels/MarketPanel/Dance/index.tsx | 1 + src/panels/MarketPanel/SideNav/index.tsx | 3 +- src/panels/MarketPanel/index.tsx | 4 +- src/panels/PanelContainer.tsx | 3 +- src/panels/RolePanel/Info/index.tsx | 3 +- src/panels/RolePanel/Role/index.tsx | 3 +- .../RolePanel/Touch/ActionList/index.tsx | 9 +- .../RolePanel/Touch/SideBar/AreaList.tsx | 6 +- src/panels/RolePanel/Touch/index.tsx | 1 + src/panels/RolePanel/Voice/index.tsx | 7 +- src/panels/RolePanel/index.tsx | 4 +- src/panels/index.tsx | 21 ++--- src/services/dance.ts | 1 + src/store/agent/index.ts | 6 +- src/store/agent/selectors/agent.ts | 1 + src/store/config/index.ts | 9 +- src/store/dance/index.ts | 4 +- src/store/dance/selectors/dance.ts | 1 + src/store/dance/slices/dancelist.ts | 7 +- src/store/dance/slices/playlist.ts | 5 +- src/store/market/index.ts | 1 + src/store/market/slices/agent.ts | 5 +- src/store/market/slices/dance.ts | 30 +++--- src/store/market/slices/panel.ts | 3 +- src/store/session/hooks/useSessionStore.ts | 17 ++++ src/store/session/index.ts | 29 +++--- src/store/session/reducers/message.ts | 3 +- src/store/session/selectors.ts | 1 + src/store/touch.ts | 3 +- src/store/viewer.ts | 3 +- src/styles/index.tsx | 1 + src/types/api.ts | 2 +- src/types/chat.ts | 1 + global.d.ts => src/types/global.d.ts | 0 src/types/touch.ts | 3 +- src/utils/fetch.ts | 3 +- src/utils/keyboard.ts | 12 +-- tests/setup.ts | 35 +++++++ tests/utils.tsx | 11 +++ tsconfig.json | 14 ++- vercel.json | 3 + vitest.config.ts | 28 ++++++ 160 files changed, 1101 insertions(+), 340 deletions(-) create mode 100644 .bunfig.toml create mode 100644 .changelogrc.js create mode 100644 .commitlintrc.js create mode 100644 .editorconfig create mode 100644 .github/FUNDING.yml create mode 100644 .github/ISSUE_TEMPLATE/1_bug_report.yml create mode 100644 .github/ISSUE_TEMPLATE/2_feature_request.yml create mode 100644 .github/ISSUE_TEMPLATE/3_question.yml create mode 100644 .github/ISSUE_TEMPLATE/4_other.md create mode 100644 .github/PULL_REQUEST_TEMPLATE.md create mode 100644 .github/workflows/issue-auto-comments.yml create mode 100644 .github/workflows/issue-check-inactive.yml create mode 100644 .github/workflows/issue-close-require.yml create mode 100644 .github/workflows/release.yml create mode 100644 .github/workflows/test.yml create mode 100755 .husky/commit-msg create mode 100755 .husky/pre-commit create mode 100644 .releaserc.js create mode 100644 .remarkrc.js create mode 100644 renovate.json create mode 100644 src/store/session/hooks/useSessionStore.ts rename global.d.ts => src/types/global.d.ts (100%) create mode 100644 tests/setup.ts create mode 100644 tests/utils.tsx create mode 100644 vercel.json create mode 100644 vitest.config.ts diff --git a/.bunfig.toml b/.bunfig.toml new file mode 100644 index 00000000..d6bb75b0 --- /dev/null +++ b/.bunfig.toml @@ -0,0 +1,3 @@ +[install.lockfile] + +save = false diff --git a/.changelogrc.js b/.changelogrc.js new file mode 100644 index 00000000..9a2f5f98 --- /dev/null +++ b/.changelogrc.js @@ -0,0 +1 @@ +module.exports = require('@lobehub/lint').changelog; diff --git a/.commitlintrc.js b/.commitlintrc.js new file mode 100644 index 00000000..9b8c6ace --- /dev/null +++ b/.commitlintrc.js @@ -0,0 +1 @@ +module.exports = require('@lobehub/lint').commitlint; diff --git a/.editorconfig b/.editorconfig new file mode 100644 index 00000000..7e3649ac --- /dev/null +++ b/.editorconfig @@ -0,0 +1,16 @@ +# http://editorconfig.org +root = true + +[*] +indent_style = space +indent_size = 2 +end_of_line = lf +charset = utf-8 +trim_trailing_whitespace = true +insert_final_newline = true + +[*.md] +trim_trailing_whitespace = false + +[Makefile] +indent_style = tab diff --git a/.eslintignore b/.eslintignore index 6744fef1..b2452033 100644 --- a/.eslintignore +++ b/.eslintignore @@ -1,4 +1,4 @@ -# Eslintignore from LobeHub +# Eslintignore for LobeHub ################################################################ # dependencies diff --git a/.github/FUNDING.yml b/.github/FUNDING.yml new file mode 100644 index 00000000..c7b7d028 --- /dev/null +++ b/.github/FUNDING.yml @@ -0,0 +1,13 @@ +# These are supported funding model platforms + +github: # Replace with up to 4 GitHub Sponsors-enabled usernames e.g., [user1, user2] +patreon: # Replace with a single Patreon username +open_collective: lobehub +ko_fi: # Replace with a single Ko-fi username +tidelift: # Replace with a single Tidelift platform-name/package-name e.g., npm/babel +community_bridge: # Replace with a single Community Bridge project-name e.g., cloud-foundry +liberapay: # Replace with a single Liberapay username +issuehunt: # +otechie: # Replace with a single Otechie username +lfx_crowdfunding: # Replace with a single LFX Crowdfunding project-name e.g., cloud-foundry +custom: # Replace with up to 4 custom sponsorship URLs e.g., ['link1', 'link2'] diff --git a/.github/ISSUE_TEMPLATE/1_bug_report.yml b/.github/ISSUE_TEMPLATE/1_bug_report.yml new file mode 100644 index 00000000..d181c387 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/1_bug_report.yml @@ -0,0 +1,45 @@ +name: '🐛 反馈缺陷 Bug Report' +description: '反馈一个问题缺陷 | Report an bug' +title: '[Bug] ' +labels: '🐛 Bug' +body: + - type: dropdown + attributes: + label: '💻 系统环境 | Operating System' + options: + - Windows + - macOS + - Ubuntu + - Other Linux + - Other + validations: + required: true + - type: dropdown + attributes: + label: '🌐 浏览器 | Browser' + options: + - Chrome + - Edge + - Safari + - Firefox + - Other + validations: + required: true + - type: textarea + attributes: + label: '🐛 问题描述 | Bug Description' + description: A clear and concise description of the bug. + validations: + required: true + - type: textarea + attributes: + label: '🚦 期望结果 | Expected Behavior' + description: A clear and concise description of what you expected to happen. + - type: textarea + attributes: + label: '📷 复现步骤 | Recurrence Steps' + description: A clear and concise description of how to recurrence. + - type: textarea + attributes: + label: '📝 补充信息 | Additional Information' + description: If your problem needs further explanation, or if the issue you're seeing cannot be reproduced in a gist, please add more information here. diff --git a/.github/ISSUE_TEMPLATE/2_feature_request.yml b/.github/ISSUE_TEMPLATE/2_feature_request.yml new file mode 100644 index 00000000..edcf7d06 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/2_feature_request.yml @@ -0,0 +1,21 @@ +name: '🌠 功能需求 Feature Request' +description: '需求或建议 | Suggest an idea' +title: '[Request] ' +labels: '🌠 Feature Request' +body: + - type: textarea + attributes: + label: '🥰 需求描述 | Feature Description' + description: Please add a clear and concise description of the problem you are seeking to solve with this feature request. + validations: + required: true + - type: textarea + attributes: + label: '🧐 解决方案 | Proposed Solution' + description: Describe the solution you'd like in a clear and concise manner. + validations: + required: true + - type: textarea + attributes: + label: '📝 补充信息 | Additional Information' + description: Add any other context about the problem here. diff --git a/.github/ISSUE_TEMPLATE/3_question.yml b/.github/ISSUE_TEMPLATE/3_question.yml new file mode 100644 index 00000000..f989f7d1 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/3_question.yml @@ -0,0 +1,15 @@ +name: '😇 疑问或帮助 Help Wanted' +description: '疑问或需要帮助 | Need help' +title: '[Question] ' +labels: '😇 Help Wanted' +body: + - type: textarea + attributes: + label: '🧐 问题描述 | Proposed Solution' + description: A clear and concise description of the proplem. + validations: + required: true + - type: textarea + attributes: + label: '📝 补充信息 | Additional Information' + description: Add any other context about the problem here. diff --git a/.github/ISSUE_TEMPLATE/4_other.md b/.github/ISSUE_TEMPLATE/4_other.md new file mode 100644 index 00000000..215dd1f3 --- /dev/null +++ b/.github/ISSUE_TEMPLATE/4_other.md @@ -0,0 +1,7 @@ +--- +name: '📝 其他 Other' +about: '其他问题 | Other issues' +title: '' +labels: '' +assignees: '' +--- diff --git a/.github/PULL_REQUEST_TEMPLATE.md b/.github/PULL_REQUEST_TEMPLATE.md new file mode 100644 index 00000000..789d4bc1 --- /dev/null +++ b/.github/PULL_REQUEST_TEMPLATE.md @@ -0,0 +1,19 @@ +#### 💻 变更类型 | Change Type + + + +- [ ] ✨ feat +- [ ] 🐛 fix +- [ ] ♻️ refactor +- [ ] 💄 style +- [ ] 🔨 chore +- [ ] ⚡️ perf +- [ ] 📝 docs + +#### 🔀 变更说明 | Description of Change + + + +#### 📝 补充信息 | Additional Information + + diff --git a/.github/workflows/issue-auto-comments.yml b/.github/workflows/issue-auto-comments.yml new file mode 100644 index 00000000..65b3c989 --- /dev/null +++ b/.github/workflows/issue-auto-comments.yml @@ -0,0 +1,72 @@ +name: Issue Auto Comment +on: + issues: + types: + - opened + - closed + - assigned + pull_request_target: + types: + - opened + - closed + +permissions: + contents: read + +jobs: + run: + permissions: + issues: write # for actions-cool/issues-helper to update issues + pull-requests: write # for actions-cool/issues-helper to update PRs + runs-on: ubuntu-latest + steps: + - name: Auto Comment on Issues Opened + uses: wow-actions/auto-comment@v1 + with: + GITHUB_TOKEN: ${{ secrets.GH_TOKEN}} + issuesOpened: | + 👀 @{{ author }} + Thank you for raising an issue. We will investigate into the matter and get back to you as soon as possible. + Please make sure you have given us as much context as possible.\ + 非常感谢您提交 issue。我们会尽快调查此事,并尽快回复您。 请确保您已经提供了尽可能多的背景信息。 + - name: Auto Comment on Issues Closed + uses: wow-actions/auto-comment@v1 + with: + GITHUB_TOKEN: ${{ secrets.GH_TOKEN}} + issuesClosed: | + ✅ @{{ author }} +
+ This issue is closed, If you have any questions, you can comment and reply.\ + 此问题已经关闭。如果您有任何问题,可以留言并回复。 + - name: Auto Comment on Pull Request Opened + uses: wow-actions/auto-comment@v1 + with: + GITHUB_TOKEN: ${{ secrets.GH_TOKEN}} + pullRequestOpened: | + 👍 @{{ author }} +
+ Thank you for raising your pull request and contributing to our Community + Please make sure you have followed our contributing guidelines. We will review it as soon as possible. + If you encounter any problems, please feel free to connect with us.\ + 非常感谢您提出拉取请求并为我们的社区做出贡献,请确保您已经遵循了我们的贡献指南,我们会尽快审查它。 + 如果您遇到任何问题,请随时与我们联系。 + - name: Auto Comment on Pull Request Merged + uses: actions-cool/pr-welcome@main + if: github.event.pull_request.merged == true + with: + token: ${{ secrets.GH_TOKEN }} + comment: | + ❤️ Great PR @${{ github.event.pull_request.user.login }} ❤️ +
+ The growth of project is inseparable from user feedback and contribution, thanks for your contribution!\ + 项目的成长离不开用户反馈和贡献,感谢您的贡献! + emoji: 'hooray' + pr-emoji: '+1, heart' + - name: Remove inactive + if: github.event.issue.state == 'open' && github.actor == github.event.issue.user.login + uses: actions-cool/issues-helper@v3 + with: + actions: 'remove-labels' + token: ${{ secrets.GH_TOKEN }} + issue-number: ${{ github.event.issue.number }} + labels: 'Inactive' diff --git a/.github/workflows/issue-check-inactive.yml b/.github/workflows/issue-check-inactive.yml new file mode 100644 index 00000000..a5ae1fba --- /dev/null +++ b/.github/workflows/issue-check-inactive.yml @@ -0,0 +1,23 @@ +name: Issue Check Inactive + +on: + schedule: + - cron: '0 0 */15 * *' + +permissions: + contents: read + +jobs: + issue-check-inactive: + permissions: + issues: write # for actions-cool/issues-helper to update issues + pull-requests: write # for actions-cool/issues-helper to update PRs + runs-on: ubuntu-latest + steps: + - name: check-inactive + uses: actions-cool/issues-helper@v3 + with: + actions: 'check-inactive' + token: ${{ secrets.GH_TOKEN }} + inactive-label: 'Inactive' + inactive-day: 30 diff --git a/.github/workflows/issue-close-require.yml b/.github/workflows/issue-close-require.yml new file mode 100644 index 00000000..e64d0cd4 --- /dev/null +++ b/.github/workflows/issue-close-require.yml @@ -0,0 +1,52 @@ +name: Issue Close Require + +on: + schedule: + - cron: '0 0 * * *' + +permissions: + contents: read + +jobs: + issue-close-require: + permissions: + issues: write # for actions-cool/issues-helper to update issues + pull-requests: write # for actions-cool/issues-helper to update PRs + runs-on: ubuntu-latest + steps: + - name: need reproduce + uses: actions-cool/issues-helper@v3 + with: + actions: 'close-issues' + token: ${{ secrets.GH_TOKEN }} + labels: '✅ Fixed' + inactive-day: 3 + body: | + 👋 @{{ github.event.issue.user.login }} +
+ Since the issue was labeled with `✅ Fixed`, but no response in 3 days. This issue will be closed. If you have any questions, you can comment and reply.\ + 由于该 issue 被标记为已修复,同时 3 天未收到回应。现关闭 issue,若有任何问题,可评论回复。 + - name: need reproduce + uses: actions-cool/issues-helper@v3 + with: + actions: 'close-issues' + token: ${{ secrets.GH_TOKEN }} + labels: '🤔 Need Reproduce' + inactive-day: 3 + body: | + 👋 @{{ github.event.issue.user.login }} +
+ Since the issue was labeled with `🤔 Need Reproduce`, but no response in 3 days. This issue will be closed. If you have any questions, you can comment and reply.\ + 由于该 issue 被标记为需要更多信息,却 3 天未收到回应。现关闭 issue,若有任何问题,可评论回复。 + - name: need reproduce + uses: actions-cool/issues-helper@v3 + with: + actions: 'close-issues' + token: ${{ secrets.GH_TOKEN }} + labels: "🙅🏻‍♀️ WON'T DO" + inactive-day: 3 + body: | + 👋 @{{ github.event.issue.user.login }} +
+ Since the issue was labeled with `🙅🏻‍♀️ WON'T DO`, and no response in 3 days. This issue will be closed. If you have any questions, you can comment and reply.\ + 由于该 issue 被标记为暂不处理,同时 3 天未收到回应。现关闭 issue,若有任何问题,可评论回复。 diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml new file mode 100644 index 00000000..f7f1a4fe --- /dev/null +++ b/.github/workflows/release.yml @@ -0,0 +1,36 @@ +name: Release CI +on: + push: + branches: + - master + - alpha + - beta + - rc + +jobs: + release: + name: Release + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + + - name: Install bun + uses: oven-sh/setup-bun@v1 + + - name: Install deps + run: bun i + + - name: CI + run: bun run ci + + - name: Test + run: bun run test + + - name: Build + run: bun run build + + - name: Release + run: bun run release + env: + GITHUB_TOKEN: ${{ secrets.GH_TOKEN }} + NPM_TOKEN: ${{ secrets.NPM_TOKEN }} diff --git a/.github/workflows/test.yml b/.github/workflows/test.yml new file mode 100644 index 00000000..ceb56316 --- /dev/null +++ b/.github/workflows/test.yml @@ -0,0 +1,27 @@ +name: Test CI +on: + pull_request: + push: + branches: + - '!master' +jobs: + test: + runs-on: ubuntu-latest + + steps: + - uses: actions/checkout@v4 + + - name: Install bun + uses: oven-sh/setup-bun@v1 + + - name: Install deps + run: bun i + + - name: CI + run: bun run ci + + - name: Test and coverage + run: bun run test:coverage + + - name: Upload coverage to Codecov + uses: codecov/codecov-action@v4 diff --git a/.gitignore b/.gitignore index 685b1225..92ef2968 100644 --- a/.gitignore +++ b/.gitignore @@ -1,28 +1,47 @@ -# See https://help.github.com/articles/ignoring-files/ for more about ignoring files. +# Gitignore for LobeHub +################################################################ -# dependencies -/node_modules -/.pnp -.pnp.js +# general +.DS_Store +.idea +.vscode +.history +.temp +.env.local +venv +temp +tmp -# testing -/coverage +# dependencies +node_modules +*.log +*.lock +package-lock.json -# next.js -/.next/ -/out/ +# ci +coverage +.coverage +.eslintcache +.stylelintcache # production -/build +dist +es +lib +logs +test-output -# misc -.DS_Store -*.pem +# umi +.umi +.umi-production +.umi-test +.dumi/tmp* -# debug -npm-debug.log* -yarn-debug.log* -yarn-error.log* +# husky +.husky/prepare-commit-msg + +# misc +# add other ignore file below # local env files .env*.local @@ -30,11 +49,14 @@ yarn-error.log* # vercel .vercel -# +# typescript *.tsbuildinfo next-env.d.ts - -package-lock.json -.vscode - -.idea +.next +.env +public/*.js +bun.lockb +sitemap*.xml +robots.txt + +*.patch diff --git a/.husky/commit-msg b/.husky/commit-msg new file mode 100755 index 00000000..0abe7314 --- /dev/null +++ b/.husky/commit-msg @@ -0,0 +1,4 @@ +#!/usr/bin/env sh +. "$(dirname -- "$0")/_/husky.sh" + +# npx --no -- commitlint --edit ${1} diff --git a/.husky/pre-commit b/.husky/pre-commit new file mode 100755 index 00000000..8da041a2 --- /dev/null +++ b/.husky/pre-commit @@ -0,0 +1,5 @@ +#!/usr/bin/env sh +. "$(dirname -- "$0")/_/husky.sh" + +npm run type-check +npx --no-install lint-staged diff --git a/.npmrc b/.npmrc index 7a4ffc46..d9ed3d37 100644 --- a/.npmrc +++ b/.npmrc @@ -1 +1,11 @@ -lockfile=false \ No newline at end of file +lockfile=false +resolution-mode=highest +public-hoist-pattern[]=*@umijs/lint* +public-hoist-pattern[]=*changelog* +public-hoist-pattern[]=*commitlint* +public-hoist-pattern[]=*eslint* +public-hoist-pattern[]=*postcss* +public-hoist-pattern[]=*prettier* +public-hoist-pattern[]=*remark* +public-hoist-pattern[]=*semantic-release* +public-hoist-pattern[]=*stylelint* diff --git a/.prettierignore b/.prettierignore index 6a50e206..3e459cbe 100644 --- a/.prettierignore +++ b/.prettierignore @@ -1,2 +1,63 @@ -/dist -*.yaml +# Prettierignore for LobeHub +################################################################ + +# general +.DS_Store +.editorconfig +.idea +.vscode +.history +.temp +.env.local +.husky +.npmrc +.gitkeep +venv +temp +tmp +LICENSE + +# dependencies +node_modules +*.log +*.lock +package-lock.json + +# ci +coverage +.coverage +.eslintcache +.stylelintcache +test-output +__snapshots__ +*.snap + +# production +dist +es +lib +logs + +# umi +.umi +.umi-production +.umi-test +.dumi/tmp* + +# ignore files +.*ignore + +# docker +docker +Dockerfile* + +# image +*.webp +*.gif +*.png +*.jpg +*.svg + +# misc +# add other ignore file below +.next \ No newline at end of file diff --git a/.prettierrc.js b/.prettierrc.js index a24274f0..f0355a9c 100644 --- a/.prettierrc.js +++ b/.prettierrc.js @@ -1,20 +1 @@ -module.exports = { - pluginSearchDirs: false, - plugins: [ - require.resolve('prettier-plugin-organize-imports'), - require.resolve('prettier-plugin-packagejson'), - ], - printWidth: 100, - proseWrap: 'never', - singleQuote: true, - endOfLine: 'lf', - trailingComma: 'all', - overrides: [ - { - files: '*.md', - options: { - proseWrap: 'preserve', - }, - }, - ], -}; +module.exports = require('@lobehub/lint').prettier; diff --git a/.releaserc.js b/.releaserc.js new file mode 100644 index 00000000..37930011 --- /dev/null +++ b/.releaserc.js @@ -0,0 +1 @@ +module.exports = require('@lobehub/lint').semanticRelease; diff --git a/.remarkrc.js b/.remarkrc.js new file mode 100644 index 00000000..b673c10e --- /dev/null +++ b/.remarkrc.js @@ -0,0 +1 @@ +module.exports = require('@lobehub/lint').remarklint; diff --git a/README.md b/README.md index 3ec34685..cc49c696 100644 --- a/README.md +++ b/README.md @@ -96,27 +96,23 @@ Contributions of all types are more than welcome, if you are interested in contr Copyright © 2023 [lobehub][profile-link].
This project is [MIT](./LICENSE) licensed. -[profile-link]: https://github.com/lobehub -[back-to-top]: https://img.shields.io/badge/-BACK_TO_TOP-black?style=flat-square -[github-issues-link]: https://github.com/lobehub/lobe-vidol/issues -[pr-welcome-shield]: https://img.shields.io/badge/%F0%9F%A4%AF%20PR%20WELCOME-%E2%86%92-ffcb47?labelColor=black&style=for-the-badge -[pr-welcome-link]: https://github.com/lobehub/lobe-vidol/pulls -[github-contrib-shield]: https://contrib.rocks/image?repo=lobehub%2Fvidol.chat -[github-contrib-link]: https://github.com/lobehub/lobe-vidol/graphs/contributors [back-to-top]: https://img.shields.io/badge/-BACK_TO_TOP-black?style=flat-square -[github-codespace-shield]: https://github.com/codespaces/badge.svg -[github-codespace-link]: https://codespaces.new/lobehub/lobe-vidol -[bun-shield]: https://img.shields.io/badge/-speedup%20with%20bun-black?logo=bun&style=for-the-badge [bun-link]: https://bun.sh -[back-to-top]: https://img.shields.io/badge/-BACK_TO_TOP-black?style=flat-square -[back-to-top]: https://img.shields.io/badge/-BACK_TO_TOP-black?style=flat-square -[github-contributors-shield]: https://img.shields.io/github/contributors/lobehub/lobe-vidol?color=c4f042&labelColor=black&style=flat-square +[bun-shield]: https://img.shields.io/badge/-speedup%20with%20bun-black?logo=bun&style=for-the-badge +[github-codespace-link]: https://codespaces.new/lobehub/lobe-vidol +[github-codespace-shield]: https://github.com/codespaces/badge.svg +[github-contrib-link]: https://github.com/lobehub/lobe-vidol/graphs/contributors +[github-contrib-shield]: https://contrib.rocks/image?repo=lobehub%2Fvidol.chat [github-contributors-link]: https://github.com/lobehub/lobe-vidol/graphs/contributors -[github-forks-shield]: https://img.shields.io/github/forks/lobehub/lobe-vidol?color=8ae8ff&labelColor=black&style=flat-square +[github-contributors-shield]: https://img.shields.io/github/contributors/lobehub/lobe-vidol?color=c4f042&labelColor=black&style=flat-square [github-forks-link]: https://github.com/lobehub/lobe-vidol/network/members -[github-stars-shield]: https://img.shields.io/github/stars/lobehub/lobe-vidol?color=ffcb47&labelColor=black&style=flat-square -[github-stars-link]: https://github.com/lobehub/lobe-vidol/network/stargazers -[github-issues-shield]: https://img.shields.io/github/issues/lobehub/lobe-vidol?color=ff80eb&labelColor=black&style=flat-square +[github-forks-shield]: https://img.shields.io/github/forks/lobehub/lobe-vidol?color=8ae8ff&labelColor=black&style=flat-square [github-issues-link]: https://github.com/lobehub/lobe-vidol/issues -[github-license-shield]: https://img.shields.io/github/license/lobehub/lobe-vidol?color=white&labelColor=black&style=flat-square +[github-issues-shield]: https://img.shields.io/github/issues/lobehub/lobe-vidol?color=ff80eb&labelColor=black&style=flat-square [github-license-link]: https://github.com/lobehub/lobe-vidol/blob/main/LICENSE +[github-license-shield]: https://img.shields.io/github/license/lobehub/lobe-vidol?color=white&labelColor=black&style=flat-square +[github-stars-link]: https://github.com/lobehub/lobe-vidol/network/stargazers +[github-stars-shield]: https://img.shields.io/github/stars/lobehub/lobe-vidol?color=ffcb47&labelColor=black&style=flat-square +[pr-welcome-link]: https://github.com/lobehub/lobe-vidol/pulls +[pr-welcome-shield]: https://img.shields.io/badge/%F0%9F%A4%AF%20PR%20WELCOME-%E2%86%92-ffcb47?labelColor=black&style=for-the-badge +[profile-link]: https://github.com/lobehub diff --git a/next.config.mjs b/next.config.mjs index 56914aa9..c71e3572 100644 --- a/next.config.mjs +++ b/next.config.mjs @@ -1,16 +1,46 @@ -import nextPWA from 'next-pwa'; +import nextPWA from '@ducanh2912/next-pwa'; +import analyzer from '@next/bundle-analyzer'; + const isProd = process.env.NODE_ENV === 'production'; const withPWA = nextPWA({ dest: 'public', register: true, - skipWaiting: true, + workboxOptions: { + skipWaiting: true, + }, +}); + +const withBundleAnalyzer = analyzer({ + enabled: process.env.ANALYZE === 'true', }); /** @type {import('next').NextConfig} */ const nextConfig = { + compress: isProd, + pageExtensions: ['tsx', 'ts'], + experimental: { + optimizePackageImports: ['@lobehub/ui', '@lobehub/icons', 'chroma-js', 'shiki'], + webVitalsAttribution: ['CLS', 'LCP'], + }, reactStrictMode: true, - transpilePackages: ['@lobehub/ui'], + webpack(config) { + config.experiments = { + asyncWebAssembly: true, + layers: true, + }; + // to fix shikiji compile error + // refs: https://github.com/antfu/shikiji/issues/23 + config.module.rules.push({ + test: /\.m?js$/, + type: 'javascript/auto', + resolve: { + fullySpecified: false, + }, + }); + + return config; + }, }; -export default isProd ? withPWA(nextConfig) : nextConfig; +export default isProd ? withBundleAnalyzer(withPWA(nextConfig)) : nextConfig; diff --git a/package.json b/package.json index f0d62b34..2413c4a4 100644 --- a/package.json +++ b/package.json @@ -1,18 +1,67 @@ { "name": "@lobehub/vidol", - "homepage": "https://github.com/lobehub/lobe-vidol", - "description": "Make Virtual Idols Accessible To EveryOne!", "version": "0.0.1", "private": true, + "description": "Make Virtual Idols Accessible To EveryOne!", + "keywords": [ + "framework", + "virtual-odols", + "chatbot", + "chatgpt", + "nextjs", + "vercel-ai", + "openai", + "azure-openai", + "visual-model", + "tts" + ], + "homepage": "https://github.com/lobehub/lobe-vidol", + "bugs": { + "url": "https://github.com/lobehub/lobe-vidol/issues/new/choose" + }, + "repository": { + "type": "git", + "url": "https://github.com/lobehub/lobe-vidol.git" + }, + "license": "MIT", + "author": "LobeHub ", + "sideEffects": false, "scripts": { "build": "next build", "dev": "next dev", - "lint": "npm run lint:ts && npm run lint:style && npm run type-check", + "lint": "npm run lint:ts && npm run lint:style && npm run type-check && npm run lint:circular", + "lint:circular": "dpdm src/**/*.ts --warning false --tree false --exit-code circular:1 -T true --skip-dynamic-imports circular", + "lint:md": "remark . --quiet --frail --output", "lint:style": "stylelint \"{src,tests}/**/*.{js,jsx,ts,tsx}\" --fix", "lint:ts": "eslint \"{src,tests}/**/*.{js,jsx,ts,tsx}\" --fix", + "prepare": "husky", + "prettier": "prettier -c --write \"**/**\"", + "release": "semantic-release", "start": "next start", + "test": "vitest", + "test:coverage": "vitest run --coverage", + "test:update": "vitest -u", "type-check": "tsc --noEmit" }, + "lint-staged": { + "*.md": [ + "remark --quiet --output --", + "prettier --write --no-error-on-unmatched-pattern" + ], + "*.json": [ + "prettier --write --no-error-on-unmatched-pattern" + ], + "*.{js,jsx}": [ + "prettier --write", + "stylelint --fix", + "eslint --fix" + ], + "*.{ts,tsx}": [ + "prettier --parser=typescript --write", + "stylelint --fix", + "eslint --fix" + ] + }, "dependencies": { "@ant-design/icons": "^5.3.6", "@ant-design/pro-card": "^2.6.0", @@ -20,7 +69,7 @@ "@dnd-kit/utilities": "^3.2.2", "@gltf-transform/core": "^3.10.1", "@lobehub/tts": "^1.24.0", - "@lobehub/ui": "^1.137.7", + "@lobehub/ui": "^1.138.1", "@pixiv/three-vrm": "^2.1.1", "@pixiv/three-vrm-core": "^2.1.1", "@react-spring/web": "^9.7.3", @@ -46,12 +95,12 @@ "polished": "^4.3.1", "react": "^18.2.0", "react-dom": "^18.2.0", - "react-intersection-observer": "^9.8.1", + "react-intersection-observer": "^9.8.2", "react-layout-kit": "^1.9.0", "react-lazy-load": "^4.0.1", "react-virtuoso": "^4.7.8", + "swr": "^2.2.5", "three": "^0.162.0", - "typescript": "5.1.3", "ua-parser-js": "^1.0.37", "utility-types": "^3.11.0", "uuid": "^9.0.1", @@ -59,19 +108,37 @@ "zustand": "^4.5.2" }, "devDependencies": { - "@lobehub/lint": "^1.23.0", + "@commitlint/cli": "^19.2.1", + "@ducanh2912/next-pwa": "^10.2.6", + "@lobehub/lint": "^1.23.3", + "@next/bundle-analyzer": "^14.1.4", + "@peculiar/webcrypto": "^1.4.6", + "@testing-library/jest-dom": "^6.4.2", + "@testing-library/react": "^14.3.0", "@types/lodash-es": "^4.17.12", "@types/node": "20.3.1", - "@types/react": "^18.2.74", - "@types/react-dom": "^18.2.24", + "@types/react": "^18.2.77", + "@types/react-dom": "^18.2.25", "@types/three": "^0.162.0", "@types/ua-parser-js": "^0.7.39", + "@types/uuid": "^9.0.8", + "commitlint": "^19.2.1", + "dpdm": "^3.14.0", "eslint": "^8.57.0", "eslint-config-next": "13.4.7", - "eslint-plugin-unicorn": "^51.0.1", + "glob": "^10.3.12", + "husky": "^9.0.11", + "jsdom": "^24.0.0", + "lint-staged": "^15.2.2", "prettier": "^3.2.5", - "prettier-plugin-organize-imports": "^3.2.4", - "prettier-plugin-packagejson": "^2.4.14", - "stylelint": "^15.11.0" + "remark": "^14.0.3", + "remark-cli": "^11.0.0", + "semantic-release": "^21.1.2", + "stylelint": "^15.11.0", + "tsx": "^4.7.2", + "typescript": "^5.4.5", + "vite": "^5.2.8", + "vitest": "~1.2.2", + "vitest-canvas-mock": "^0.3.3" } } diff --git a/renovate.json b/renovate.json new file mode 100644 index 00000000..99c84e1f --- /dev/null +++ b/renovate.json @@ -0,0 +1,13 @@ +{ + "$schema": "https://docs.renovatebot.com/renovate-schema.json", + "automerge": false, + "dependencyDashboard": true, + "ignoreDeps": [], + "labels": ["dependencies"], + "postUpdateOptions": ["yarnDedupeHighest"], + "prConcurrentLimit": 30, + "prHourlyLimit": 0, + "rebaseWhen": "conflicted", + "schedule": "on sunday before 6:00am", + "timezone": "UTC" +} diff --git a/src/app/api/chat/openai/createErrorResponse.ts b/src/app/api/chat/openai/createErrorResponse.ts index fd43f7bf..90027969 100644 --- a/src/app/api/chat/openai/createErrorResponse.ts +++ b/src/app/api/chat/openai/createErrorResponse.ts @@ -1,6 +1,7 @@ -import { ErrorTypeEnum } from '@/types/api'; import { NextResponse } from 'next/server'; +import { ErrorTypeEnum } from '@/types/api'; + const getStatusCode = (errorType: ErrorTypeEnum) => { switch (errorType) { case ErrorTypeEnum.API_KEY_MISSING: { diff --git a/src/app/api/chat/openai/route.ts b/src/app/api/chat/openai/route.ts index 4e192fe3..ffbcdfad 100644 --- a/src/app/api/chat/openai/route.ts +++ b/src/app/api/chat/openai/route.ts @@ -1,7 +1,9 @@ -import { OPENAI_API_KEY, OPENAI_END_POINT } from '@/constants/openai'; -import { ErrorTypeEnum } from '@/types/api'; import { OpenAIStream, StreamingTextResponse } from 'ai'; import OpenAI, { ClientOptions } from 'openai'; + +import { OPENAI_API_KEY, OPENAI_END_POINT } from '@/constants/openai'; +import { ErrorTypeEnum } from '@/types/api'; + import { createErrorResponse } from './createErrorResponse'; export const POST = async (req: Request) => { diff --git a/src/app/api/voice/edge/voices/route.ts b/src/app/api/voice/edge/voices/route.ts index 7bdc7f91..bf65c861 100644 --- a/src/app/api/voice/edge/voices/route.ts +++ b/src/app/api/voice/edge/voices/route.ts @@ -1,6 +1,7 @@ -import { voiceMap } from '@/utils/voices'; import { NextResponse } from 'next/server'; +import { voiceMap } from '@/utils/voices'; + const axios = require('axios'); interface Voice { diff --git a/src/app/api/voice/microsoft/voices/route.ts b/src/app/api/voice/microsoft/voices/route.ts index 409a3ccf..1f9f4308 100644 --- a/src/app/api/voice/microsoft/voices/route.ts +++ b/src/app/api/voice/microsoft/voices/route.ts @@ -1,5 +1,6 @@ +import { NextResponse } from 'next/server'; + import { voiceMap } from '@/utils/voices'; -import {NextResponse } from 'next/server'; const { v4: uuidv4 } = require('uuid'); const axios = require('axios'); @@ -21004,12 +21005,12 @@ export const GET = async () => { const config = { data: data, headers: { - accept: 'application/json, text/plain, */*', + 'accept': 'application/json, text/plain, */*', 'accept-language': 'zh-CN,zh;q=0.9,en;q=0.8,en-GB;q=0.7,en-US;q=0.6', - authority: 'southeastasia.api.speech.microsoft.com', + 'authority': 'southeastasia.api.speech.microsoft.com', 'content-type': 'application/json', - customvoiceconnectionid: uuidv4(), - origin: 'https://speech.microsoft.com', + 'customvoiceconnectionid': uuidv4(), + 'origin': 'https://speech.microsoft.com', 'sec-ch-ua': '"Microsoft Edge";v="113", "Chromium";v="113", "Not-A.Brand";v="24"', 'sec-ch-ua-mobile': '?0', 'sec-ch-ua-platform': '"Windows"', diff --git a/src/app/home/Background/index.tsx b/src/app/home/Background/index.tsx index 9d2ac9a4..d9fe0dff 100644 --- a/src/app/home/Background/index.tsx +++ b/src/app/home/Background/index.tsx @@ -1,4 +1,5 @@ import { useConfigStore } from '@/store/config'; + import { useStyles } from './style'; const Background = () => { diff --git a/src/app/home/Dialog/index.tsx b/src/app/home/Dialog/index.tsx index c8ffd169..33b8ae41 100644 --- a/src/app/home/Dialog/index.tsx +++ b/src/app/home/Dialog/index.tsx @@ -1,5 +1,6 @@ import ChatItem from '@/features/ChatItem'; import { sessionSelectors, useSessionStore } from '@/store/session'; + import { useStyles } from './style'; const Dialog = () => { diff --git a/src/app/home/RoleSelect/index.tsx b/src/app/home/RoleSelect/index.tsx index 20e869b6..b7967a6e 100644 --- a/src/app/home/RoleSelect/index.tsx +++ b/src/app/home/RoleSelect/index.tsx @@ -1,7 +1,9 @@ 'use client'; -import { sessionSelectors, useSessionStore } from '@/store/session'; import { Avatar } from '@lobehub/ui'; + +import { sessionSelectors, useSessionStore } from '@/store/session'; + import { useStyles } from './style'; const AvatarSize = 64; diff --git a/src/app/home/RoleSelect/style.ts b/src/app/home/RoleSelect/style.ts index 2d504cda..9e173cc2 100644 --- a/src/app/home/RoleSelect/style.ts +++ b/src/app/home/RoleSelect/style.ts @@ -5,26 +5,26 @@ export const useStyles = createStyles(({ css, token }) => ({ transform-style: preserve-3d; `, // satellite: css` -// @keyframes orbit { -// 0% { -// transform: rotateZ(0deg); -// } -// 100% { -// transform: rotateZ(360deg); -// } -// } -// position: absolute; -// width: 6px; -// height: 6px; -// top: 50%; -// left: 50%; -// margin-top: calc(-36px - 3px); /* 轨道直径的一半,用于居中 */ -// border-radius: 50%; -// background-color: ${token.colorPrimary}; /* 小球颜色 */ -// transform-origin: 0 calc(36px + 2px); /* 小球绕头像中心旋转的轨道半径 */ -// animation: orbit 3s linear infinite; /* 应用动画 */ -// `, -orbit: css` + // @keyframes orbit { + // 0% { + // transform: rotateZ(0deg); + // } + // 100% { + // transform: rotateZ(360deg); + // } + // } + // position: absolute; + // width: 6px; + // height: 6px; + // top: 50%; + // left: 50%; + // margin-top: calc(-36px - 3px); /* 轨道直径的一半,用于居中 */ + // border-radius: 50%; + // background-color: ${token.colorPrimary}; /* 小球颜色 */ + // transform-origin: 0 calc(36px + 2px); /* 小球绕头像中心旋转的轨道半径 */ + // animation: orbit 3s linear infinite; /* 应用动画 */ + // `, + orbit: css` position: absolute; top: 50%; left: 50%; @@ -37,26 +37,7 @@ orbit: css` border: 3px solid ${token.colorPrimary}; /* 轨道颜色和透明度 */ border-radius: 50%; `, - - - - - - - - - - - - - - - - - - - - + roleSelect: css` position: fixed; top: 64px; diff --git a/src/app/home/VirtualIdol/index.tsx b/src/app/home/VirtualIdol/index.tsx index b921e7bd..c4273889 100644 --- a/src/app/home/VirtualIdol/index.tsx +++ b/src/app/home/VirtualIdol/index.tsx @@ -3,6 +3,7 @@ import AgentViewer from '@/features/AgentViewer'; import ImageViewer from '@/features/ImageViewer'; import { useSessionStore } from '@/store/session'; + import { useStyles } from './style'; const VirtualIdol = () => { diff --git a/src/app/home/page.tsx b/src/app/home/page.tsx index 1e7bf522..de8f2b8d 100644 --- a/src/app/home/page.tsx +++ b/src/app/home/page.tsx @@ -8,6 +8,7 @@ import VirtualIdol from '@/app/home/VirtualIdol'; import { apps } from '@/app/home/apps'; import { useConfigStore } from '@/store/config'; import { PanelKey } from '@/types/config'; + import Docker from './Docker'; const Desktop = () => { diff --git a/src/app/layout.tsx b/src/app/layout.tsx index bc2c48e5..05a3f707 100644 --- a/src/app/layout.tsx +++ b/src/app/layout.tsx @@ -4,6 +4,7 @@ import { PropsWithChildren } from 'react'; import { VIDOL_THEME_APPEARANCE } from '@/constants/common'; import Layout from '@/layout'; + import StyleRegistry from './StyleRegistry'; inject(); diff --git a/src/app/page.tsx b/src/app/page.tsx index ced01cfc..fd667706 100644 --- a/src/app/page.tsx +++ b/src/app/page.tsx @@ -1,5 +1,5 @@ -import PageLoading from '@/app/welcome/loading'; import Redirect from '@/app/welcome/Redirect'; +import PageLoading from '@/app/welcome/loading'; const Index = () => ( <> diff --git a/src/components/AgentInfo/index.tsx b/src/components/AgentInfo/index.tsx index 7c1fc8d1..c76ac091 100644 --- a/src/components/AgentInfo/index.tsx +++ b/src/components/AgentInfo/index.tsx @@ -1,8 +1,10 @@ -import { Agent } from '@/types/agent'; import { Avatar } from '@lobehub/ui'; import { Space, Tag } from 'antd'; import React, { memo } from 'react'; import { Center } from 'react-layout-kit'; + +import { Agent } from '@/types/agent'; + import { useStyles } from './style'; interface AgentInfoProps { diff --git a/src/components/AgentMeta/index.tsx b/src/components/AgentMeta/index.tsx index 85b11f3e..3ab23a89 100644 --- a/src/components/AgentMeta/index.tsx +++ b/src/components/AgentMeta/index.tsx @@ -1,6 +1,8 @@ -import { AgentMeta } from '@/types/agent'; import { Avatar } from '@lobehub/ui'; import { Typography } from 'antd'; + +import { AgentMeta } from '@/types/agent'; + import { useStyles } from './style'; interface AgentMetaProps { diff --git a/src/components/Application/index.tsx b/src/components/Application/index.tsx index 01dd11dc..f3960057 100644 --- a/src/components/Application/index.tsx +++ b/src/components/Application/index.tsx @@ -2,6 +2,7 @@ import { Avatar, Icon, Tooltip } from '@lobehub/ui'; import { cx } from 'antd-style'; import { LucideIcon } from 'lucide-react'; import { memo } from 'react'; + import { useStyles } from './style'; interface ApplicationProps { diff --git a/src/components/DanceInfo/index.tsx b/src/components/DanceInfo/index.tsx index ee6bf570..a105a3f3 100644 --- a/src/components/DanceInfo/index.tsx +++ b/src/components/DanceInfo/index.tsx @@ -1,8 +1,10 @@ -import { Dance } from '@/types/dance'; import { Avatar } from '@lobehub/ui'; import { Space } from 'antd'; import React, { memo } from 'react'; import { Center } from 'react-layout-kit'; + +import { Dance } from '@/types/dance'; + import { useStyles } from './style'; interface DanceInfoProps { diff --git a/src/components/HolographicCard/components/Container.tsx b/src/components/HolographicCard/components/Container.tsx index 5d730d48..452a0f21 100644 --- a/src/components/HolographicCard/components/Container.tsx +++ b/src/components/HolographicCard/components/Container.tsx @@ -1,4 +1,5 @@ import { CSSProperties, ReactNode, memo } from 'react'; + import { LaserShine, useLaserShine } from './LaserShine'; import Orbit from './Orbit'; import { useStyles } from './style'; @@ -28,7 +29,7 @@ const Container = memo(({ foil, mask, children, className, loadi ...shineStyle, '--foil': `url(${foil ?? ''})`, '--mask': `url(${mask ?? ''})`, - width: 320, + 'width': 320, } as CSSProperties, content: { display: 'grid', diff --git a/src/components/HolographicCard/components/LaserShine/LaserShine.tsx b/src/components/HolographicCard/components/LaserShine/LaserShine.tsx index b400abe1..87c6e2df 100644 --- a/src/components/HolographicCard/components/LaserShine/LaserShine.tsx +++ b/src/components/HolographicCard/components/LaserShine/LaserShine.tsx @@ -1,6 +1,7 @@ import { animated } from '@react-spring/web'; import { CSSProperties, memo } from 'react'; import { DivProps } from 'react-layout-kit'; + import { useStyles } from './style'; export interface LaserShineProps extends DivProps { diff --git a/src/components/HolographicCard/components/LaserShine/useLaserShine.ts b/src/components/HolographicCard/components/LaserShine/useLaserShine.ts index 5f2403ce..2835fd9a 100644 --- a/src/components/HolographicCard/components/LaserShine/useLaserShine.ts +++ b/src/components/HolographicCard/components/LaserShine/useLaserShine.ts @@ -1,5 +1,6 @@ import { useSpring } from '@react-spring/web'; import { CSSProperties } from 'react'; + import { adjust, clamp, round } from '../../utils/math'; const randomSeed = { diff --git a/src/components/HolographicCard/components/Orbit/index.tsx b/src/components/HolographicCard/components/Orbit/index.tsx index aaa74ec1..0eb64ca0 100644 --- a/src/components/HolographicCard/components/Orbit/index.tsx +++ b/src/components/HolographicCard/components/Orbit/index.tsx @@ -1,5 +1,6 @@ import { animated, useSpring } from '@react-spring/web'; import { CSSProperties, MouseEventHandler, ReactNode, forwardRef } from 'react'; + import { clamp, round } from '../../utils/math'; import { useStyles } from './styles'; diff --git a/src/components/HolographicCard/index.tsx b/src/components/HolographicCard/index.tsx index d494b368..8647c2eb 100644 --- a/src/components/HolographicCard/index.tsx +++ b/src/components/HolographicCard/index.tsx @@ -1,5 +1,6 @@ import { createStyles } from 'antd-style'; import { ReactNode, memo, useEffect, useState } from 'react'; + import Container from './components/Container'; const useStyles = createStyles(({ css }) => ({ diff --git a/src/components/Panel/Container.tsx b/src/components/Panel/Container.tsx index ecdc4123..b89347ac 100644 --- a/src/components/Panel/Container.tsx +++ b/src/components/Panel/Container.tsx @@ -1,10 +1,12 @@ -import { INITIAL_COORDINATES, INITIAL_Z_INDEX } from '@/constants/common'; import { useDraggable } from '@dnd-kit/core'; import { ActionIcon, Logo } from '@lobehub/ui'; import { Tooltip } from 'antd'; import classNames from 'classnames'; import { XIcon } from 'lucide-react'; import React, { PropsWithChildren, memo } from 'react'; + +import { INITIAL_COORDINATES, INITIAL_Z_INDEX } from '@/constants/common'; + import { useStyles } from './style'; interface ContainerProps { diff --git a/src/components/Panel/index.tsx b/src/components/Panel/index.tsx index 0b496bf7..59733591 100644 --- a/src/components/Panel/index.tsx +++ b/src/components/Panel/index.tsx @@ -1,4 +1,3 @@ -import { INITIAL_COORDINATES, INITIAL_Z_INDEX } from '@/constants/common'; import { DndContext, KeyboardSensor, @@ -9,6 +8,9 @@ import { } from '@dnd-kit/core'; import type { Coordinates } from '@dnd-kit/utilities'; import React, { PropsWithChildren, useEffect, useState } from 'react'; + +import { INITIAL_COORDINATES, INITIAL_Z_INDEX } from '@/constants/common'; + import Container from './Container'; interface ControlPanelProps { diff --git a/src/constants/dance.ts b/src/constants/dance.ts index 1b2aaf33..98b736a0 100644 --- a/src/constants/dance.ts +++ b/src/constants/dance.ts @@ -1,13 +1,15 @@ import { Dance } from '@/types/dance'; export const DEFAULT_DANCE: Dance = { - "danceId": "vidol-dance-gokuraku", - "name": "極楽浄土", - "createAt": "2023-10-31", - "src": "https://registry.npmmirror.com/@v-idol/vidol-dance-gokuraku/1.0.0/files/gokuraku.vmd", - "audio": "https://registry.npmmirror.com/@v-idol/vidol-dance-gokuraku/1.0.0/files/Gokuraku jodo.mp3", - "cover": "https://registry.npmmirror.com/@v-idol/vidol-dance-gokuraku/1.0.0/files/cover.jpg", - "thumb": "https://registry.npmmirror.com/@v-idol/vidol-dance-gokuraku/1.0.0/files/thumb.jpg", - "readme": "WHAT CHANGED?!\r\n-FIXED THE GOOGLY/SHAKY EYES\r\n-Added eye motions that were supposed to be there\r\n-Audio is slightly more in sync\r\n\r\nSong: 【GARNiDELiA】極楽浄土【とく×メイリア】\r\nhttps://www.nicovideo.jp/watch/sm28709142\r\n\r\nMotion by yurie\r\nhttps://www.nicovideo.jp/watch/sm29180863", - "schemaVersion": 1 + danceId: 'vidol-dance-gokuraku', + name: '極楽浄土', + createAt: '2023-10-31', + src: 'https://registry.npmmirror.com/@v-idol/vidol-dance-gokuraku/1.0.0/files/gokuraku.vmd', + audio: + 'https://registry.npmmirror.com/@v-idol/vidol-dance-gokuraku/1.0.0/files/Gokuraku jodo.mp3', + cover: 'https://registry.npmmirror.com/@v-idol/vidol-dance-gokuraku/1.0.0/files/cover.jpg', + thumb: 'https://registry.npmmirror.com/@v-idol/vidol-dance-gokuraku/1.0.0/files/thumb.jpg', + readme: + 'WHAT CHANGED?!\r\n-FIXED THE GOOGLY/SHAKY EYES\r\n-Added eye motions that were supposed to be there\r\n-Audio is slightly more in sync\r\n\r\nSong: 【GARNiDELiA】極楽浄土【とく×メイリア】\r\nhttps://www.nicovideo.jp/watch/sm28709142\r\n\r\nMotion by yurie\r\nhttps://www.nicovideo.jp/watch/sm29180863', + schemaVersion: 1, }; diff --git a/src/features/AgentViewer/ToolBar/index.tsx b/src/features/AgentViewer/ToolBar/index.tsx index 8d25c5db..44865997 100644 --- a/src/features/AgentViewer/ToolBar/index.tsx +++ b/src/features/AgentViewer/ToolBar/index.tsx @@ -1,8 +1,9 @@ -import { useViewerStore } from '@/store/viewer'; import { ActionIconGroup } from '@lobehub/ui'; import { Expand, Grid3x3, LandPlot, Orbit, RotateCw, SwitchCamera } from 'lucide-react'; import React from 'react'; +import { useViewerStore } from '@/store/viewer'; + interface ToolBarProps { className?: string; style?: React.CSSProperties; diff --git a/src/features/AgentViewer/index.tsx b/src/features/AgentViewer/index.tsx index 7c14f158..c3ea9e8f 100644 --- a/src/features/AgentViewer/index.tsx +++ b/src/features/AgentViewer/index.tsx @@ -1,8 +1,10 @@ +import { memo, useCallback, useEffect, useState } from 'react'; + import PageLoading from '@/components/PageLoading'; import ToolBar from '@/features/AgentViewer/ToolBar'; import { sessionSelectors, useSessionStore } from '@/store/session'; import { useViewerStore } from '@/store/viewer'; -import { memo, useCallback, useEffect, useState } from 'react'; + import { useStyles } from './style'; function AgentViewer() { diff --git a/src/features/ChatInput/Actions/History.tsx b/src/features/ChatInput/Actions/History.tsx index c04fef94..77f8e4a9 100644 --- a/src/features/ChatInput/Actions/History.tsx +++ b/src/features/ChatInput/Actions/History.tsx @@ -1,8 +1,9 @@ -import { useSessionStore } from '@/store/session'; import { ActionIcon } from '@lobehub/ui'; import { Popconfirm } from 'antd'; import { Eraser } from 'lucide-react'; +import { useSessionStore } from '@/store/session'; + const History = () => { const [clearHistory] = useSessionStore((s) => [s.clearHistory]); return ( diff --git a/src/features/ChatInput/Actions/Record.tsx b/src/features/ChatInput/Actions/Record.tsx index fc4c4d05..3d8cad12 100644 --- a/src/features/ChatInput/Actions/Record.tsx +++ b/src/features/ChatInput/Actions/Record.tsx @@ -1,9 +1,10 @@ -import { useSpeechRecognition } from '@/hooks/useSpeechRecognition'; -import { useSessionStore } from '@/store/session'; import { ActionIcon } from '@lobehub/ui'; import { Mic } from 'lucide-react'; import { useCallback } from 'react'; +import { useSpeechRecognition } from '@/hooks/useSpeechRecognition'; +import { useSessionStore } from '@/store/session'; + const Record = () => { const [sendMessage, setMessageInput] = useSessionStore((s) => [s.sendMessage, s.setMessageInput]); diff --git a/src/features/ChatInput/Actions/Token.tsx b/src/features/ChatInput/Actions/Token.tsx index 9fb8dee1..df73555c 100644 --- a/src/features/ChatInput/Actions/Token.tsx +++ b/src/features/ChatInput/Actions/Token.tsx @@ -1,8 +1,9 @@ +import { TokenTag } from '@lobehub/ui'; +import { isEqual } from 'lodash-es'; + import { OPENAI_MODEL_LIST } from '@/constants/openai'; import { useCalculateToken } from '@/hooks/useCalculateToken'; import { configSelectors, useConfigStore } from '@/store/config'; -import { TokenTag } from '@lobehub/ui'; -import { isEqual } from 'lodash-es'; const Token = () => { const config = useConfigStore((s) => configSelectors.currentOpenAIConfig(s), isEqual); diff --git a/src/features/ChatInput/Actions/Voice/index.tsx b/src/features/ChatInput/Actions/Voice/index.tsx index 5342ead8..0fe9dd1a 100644 --- a/src/features/ChatInput/Actions/Voice/index.tsx +++ b/src/features/ChatInput/Actions/Voice/index.tsx @@ -1,8 +1,10 @@ -import { toogleVoice } from '@/services/chat'; -import { useSessionStore } from '@/store/session'; import { ActionIcon } from '@lobehub/ui'; import classNames from 'classnames'; import { Volume2 } from 'lucide-react'; + +import { toogleVoice } from '@/services/chat'; +import { useSessionStore } from '@/store/session'; + import { useStyles } from './style'; const VoiceSwitch = () => { diff --git a/src/features/ChatInput/Footer/index.tsx b/src/features/ChatInput/Footer/index.tsx index 68ca57c1..467913cf 100644 --- a/src/features/ChatInput/Footer/index.tsx +++ b/src/features/ChatInput/Footer/index.tsx @@ -1,4 +1,5 @@ import { ChatSendButton } from '@lobehub/ui'; + import useChatInput from '../../../hooks/useSendMessage'; const Footer = () => { diff --git a/src/features/ChatInput/MessageInput/index.tsx b/src/features/ChatInput/MessageInput/index.tsx index 6c3c2dc3..61c59834 100644 --- a/src/features/ChatInput/MessageInput/index.tsx +++ b/src/features/ChatInput/MessageInput/index.tsx @@ -1,13 +1,14 @@ -import { DEFAULT_USER_AVATAR } from '@/constants/common'; -import useChatInput from '@/hooks/useSendMessage'; -import { useSessionStore } from '@/store/session'; -import { isCommandPressed } from '@/utils/keyboard'; import { Avatar, Input } from '@lobehub/ui'; import { Button, Space } from 'antd'; import { createStyles } from 'antd-style'; import { InputRef } from 'antd/es/input/Input'; import { memo, useRef } from 'react'; +import { DEFAULT_USER_AVATAR } from '@/constants/common'; +import useChatInput from '@/hooks/useSendMessage'; +import { useSessionStore } from '@/store/session'; +import { isCommandPressed } from '@/utils/keyboard'; + const useStyles = createStyles(({ css }) => { return { textarea: css` diff --git a/src/features/ChatInput/TextArea.tsx b/src/features/ChatInput/TextArea.tsx index 4dd432a2..fab79424 100644 --- a/src/features/ChatInput/TextArea.tsx +++ b/src/features/ChatInput/TextArea.tsx @@ -1,11 +1,12 @@ -import useChatInput from '@/hooks/useSendMessage'; -import { useSessionStore } from '@/store/session'; -import { isCommandPressed } from '@/utils/keyboard'; import { TextArea } from '@lobehub/ui'; import { createStyles } from 'antd-style'; import { TextAreaRef } from 'antd/es/input/TextArea'; import React, { memo, useRef } from 'react'; +import useChatInput from '@/hooks/useSendMessage'; +import { useSessionStore } from '@/store/session'; +import { isCommandPressed } from '@/utils/keyboard'; + const useStyles = createStyles(({ css }) => { return { textarea: css` diff --git a/src/features/ChatItem/Actions/Assistant.tsx b/src/features/ChatItem/Actions/Assistant.tsx index a8c7759c..e3b2f6b9 100644 --- a/src/features/ChatItem/Actions/Assistant.tsx +++ b/src/features/ChatItem/Actions/Assistant.tsx @@ -1,9 +1,10 @@ -import type { RenderAction } from '@/features/ChatItem/type'; import { ActionIconGroup, useChatListActionsBar } from '@lobehub/ui'; import { ActionIconGroupItems } from '@lobehub/ui/es/ActionIconGroup'; import { Play } from 'lucide-react'; import { memo } from 'react'; +import type { RenderAction } from '@/features/ChatItem/type'; + const AssistantActionsBar: RenderAction = ({ onActionClick }) => { const { copy, regenerate, divider, del, edit } = useChatListActionsBar({ copy: '复制', diff --git a/src/features/ChatItem/Actions/User.tsx b/src/features/ChatItem/Actions/User.tsx index 987e19f9..efcc632e 100644 --- a/src/features/ChatItem/Actions/User.tsx +++ b/src/features/ChatItem/Actions/User.tsx @@ -1,7 +1,8 @@ -import type { RenderAction } from '@/features/ChatItem/type'; import { ActionIconGroup, useChatListActionsBar } from '@lobehub/ui'; import { memo } from 'react'; +import type { RenderAction } from '@/features/ChatItem/type'; + const UserActionsBar: RenderAction = ({ onActionClick }) => { const { copy, divider, del, edit } = useChatListActionsBar({ copy: '复制', diff --git a/src/features/ChatItem/Actions/index.tsx b/src/features/ChatItem/Actions/index.tsx index 6e2174e0..4cdc11ed 100644 --- a/src/features/ChatItem/Actions/index.tsx +++ b/src/features/ChatItem/Actions/index.tsx @@ -1,10 +1,12 @@ +import { copyToClipboard } from '@lobehub/ui'; +import { App } from 'antd'; +import { useCallback } from 'react'; + import { OnActionsClick, RenderAction } from '@/features/ChatItem/type'; import { handleSpeakAi } from '@/services/chat'; import { useSessionStore } from '@/store/session'; import { LLMRoleType } from '@/types/llm'; -import { copyToClipboard } from '@lobehub/ui'; -import { App } from 'antd'; -import { useCallback } from 'react'; + import AssistantActionsBar from './Assistant'; import UserActionsBar from './User'; diff --git a/src/features/ChatItem/ActionsBar.tsx b/src/features/ChatItem/ActionsBar.tsx index 85233eb2..1a366330 100644 --- a/src/features/ChatItem/ActionsBar.tsx +++ b/src/features/ChatItem/ActionsBar.tsx @@ -1,9 +1,11 @@ -import { ActionsBarProps } from '@/features/ChatItem/type'; -import { useChatListActionsBar } from '@/hooks/useChatListActionsBar'; -import { sessionSelectors, useSessionStore } from '@/store/session'; import { ActionEvent, ActionIconGroup } from '@lobehub/ui'; import isEqual from 'fast-deep-equal'; import { memo, useCallback } from 'react'; + +import { ActionsBarProps } from '@/features/ChatItem/type'; +import { useChatListActionsBar } from '@/hooks/useChatListActionsBar'; +import { sessionSelectors, useSessionStore } from '@/store/session'; + import { renderActions, useActionsClick } from './Actions'; const ActionsBar = memo((props) => { diff --git a/src/features/ChatItem/Error/ApiError.tsx b/src/features/ChatItem/Error/ApiError.tsx index 2df7eb2f..801cf347 100644 --- a/src/features/ChatItem/Error/ApiError.tsx +++ b/src/features/ChatItem/Error/ApiError.tsx @@ -1,5 +1,7 @@ -import { ChatMessage } from '@/types/chat'; import { memo } from 'react'; + +import { ChatMessage } from '@/types/chat'; + import ErrorJsonViewer from './ErrorJsonViewer'; import OpenAPIKey from './OpenAPIKey'; diff --git a/src/features/ChatItem/Error/ApiKeyForm.tsx b/src/features/ChatItem/Error/ApiKeyForm.tsx index 9e5d5868..19bf7c2a 100644 --- a/src/features/ChatItem/Error/ApiKeyForm.tsx +++ b/src/features/ChatItem/Error/ApiKeyForm.tsx @@ -1,11 +1,12 @@ -import { configSelectors, useConfigStore } from '@/store/config'; -import { useSessionStore } from '@/store/session'; import { Icon } from '@lobehub/ui'; import { Button, Input } from 'antd'; import { Network } from 'lucide-react'; import { memo, useState } from 'react'; import { Center, Flexbox } from 'react-layout-kit'; +import { configSelectors, useConfigStore } from '@/store/config'; +import { useSessionStore } from '@/store/session'; + import { FormAction } from './style'; interface APIKeyFormProps { diff --git a/src/features/ChatItem/Error/OpenAPIKey.tsx b/src/features/ChatItem/Error/OpenAPIKey.tsx index 8c244443..dad94ca7 100644 --- a/src/features/ChatItem/Error/OpenAPIKey.tsx +++ b/src/features/ChatItem/Error/OpenAPIKey.tsx @@ -1,4 +1,5 @@ import { memo } from 'react'; + import APIKeyForm from './ApiKeyForm'; import { ErrorActionContainer } from './style'; diff --git a/src/features/ChatItem/Error/index.tsx b/src/features/ChatItem/Error/index.tsx index d19a9ad4..a5346bc7 100644 --- a/src/features/ChatItem/Error/index.tsx +++ b/src/features/ChatItem/Error/index.tsx @@ -1,7 +1,9 @@ -import { ErrorTypeEnum } from '@/types/api'; -import { ChatMessage, ChatMessageError } from '@/types/chat'; import type { AlertProps } from '@lobehub/ui'; import { memo } from 'react'; + +import { ErrorTypeEnum } from '@/types/api'; +import { ChatMessage, ChatMessageError } from '@/types/chat'; + import ApiError from './ApiError'; import ErrorJsonViewer from './ErrorJsonViewer'; import OpenAPIKey from './OpenAPIKey'; diff --git a/src/features/ChatItem/Messages/Default.tsx b/src/features/ChatItem/Messages/Default.tsx index 6533b690..09c1eaad 100644 --- a/src/features/ChatItem/Messages/Default.tsx +++ b/src/features/ChatItem/Messages/Default.tsx @@ -1,6 +1,8 @@ +import { ReactNode, memo } from 'react'; + import { LOADING_FLAG } from '@/constants/common'; import { ChatMessage } from '@/types/chat'; -import { ReactNode, memo } from 'react'; + import BubblesLoading from './Loading'; export const DefaultMessage = memo< diff --git a/src/features/ChatItem/Messages/index.tsx b/src/features/ChatItem/Messages/index.tsx index 3530c177..39a623a8 100644 --- a/src/features/ChatItem/Messages/index.tsx +++ b/src/features/ChatItem/Messages/index.tsx @@ -1,5 +1,7 @@ -import { ChatMessage } from '@/types/chat'; import React from 'react'; + +import { ChatMessage } from '@/types/chat'; + import { DefaultMessage } from './Default'; export type RenderMessage = React.FC; diff --git a/src/features/ChatItem/index.tsx b/src/features/ChatItem/index.tsx index 3b536c26..b6f6b6a7 100644 --- a/src/features/ChatItem/index.tsx +++ b/src/features/ChatItem/index.tsx @@ -1,10 +1,12 @@ -import { useSessionStore } from '@/store/session'; -import { sessionSelectors } from '@/store/session/selectors'; -import { ChatMessage } from '@/types/chat'; import { AlertProps, ChatItem, ChatItemProps } from '@lobehub/ui'; import { createStyles } from 'antd-style'; import isEqual from 'fast-deep-equal'; import { ReactNode, memo, useCallback, useMemo, useState } from 'react'; + +import { useSessionStore } from '@/store/session'; +import { sessionSelectors } from '@/store/session/selectors'; +import { ChatMessage } from '@/types/chat'; + import ActionsBar from './ActionsBar'; import ErrorMessageExtra, { getErrorAlertConfig } from './Error'; import { renderMessages } from './Messages'; diff --git a/src/features/ChatItem/type.ts b/src/features/ChatItem/type.ts index 4d1846d0..c77d0c3b 100644 --- a/src/features/ChatItem/type.ts +++ b/src/features/ChatItem/type.ts @@ -1,7 +1,8 @@ -import { ChatMessage } from '@/types/chat'; import { ActionEvent, ActionIconGroupProps } from '@lobehub/ui'; import { FC, ReactNode } from 'react'; +import { ChatMessage } from '@/types/chat'; + export type ActionsBarProps = ActionIconGroupProps; export type OnActionsClick = (action: ActionEvent, message: ChatMessage) => void; diff --git a/src/features/ImageViewer/index.tsx b/src/features/ImageViewer/index.tsx index 9a74f4eb..c9eaec32 100644 --- a/src/features/ImageViewer/index.tsx +++ b/src/features/ImageViewer/index.tsx @@ -1,5 +1,6 @@ import HolographicCard from '@/components/HolographicCard'; import { sessionSelectors, useSessionStore } from '@/store/session'; + import { useStyles } from './style'; const Docker = () => { diff --git a/src/features/Timer/index.tsx b/src/features/Timer/index.tsx index 2d47a815..a0419d67 100644 --- a/src/features/Timer/index.tsx +++ b/src/features/Timer/index.tsx @@ -2,6 +2,7 @@ import { useInterval } from 'ahooks'; import { useState } from 'react'; + import { useStyles } from './style'; const getTime = () => { diff --git a/src/features/emoteController/autoBlink.ts b/src/features/emoteController/autoBlink.ts index 94e4063a..e0795eb4 100644 --- a/src/features/emoteController/autoBlink.ts +++ b/src/features/emoteController/autoBlink.ts @@ -1,5 +1,6 @@ -import { VRMExpressionManager } from "@pixiv/three-vrm"; -import { BLINK_CLOSE_MAX, BLINK_OPEN_MAX } from "./emoteConstants"; +import { VRMExpressionManager } from '@pixiv/three-vrm'; + +import { BLINK_CLOSE_MAX, BLINK_OPEN_MAX } from './emoteConstants'; /** * 自動瞬きを制御するクラス @@ -53,12 +54,12 @@ export class AutoBlink { private close() { this._isOpen = false; this._remainingTime = BLINK_CLOSE_MAX; - this._expressionManager.setValue("blink", 1); + this._expressionManager.setValue('blink', 1); } private open() { this._isOpen = true; this._remainingTime = BLINK_OPEN_MAX; - this._expressionManager.setValue("blink", 0); + this._expressionManager.setValue('blink', 0); } } diff --git a/src/features/emoteController/autoLookAt.ts b/src/features/emoteController/autoLookAt.ts index 41236ff1..8710a5c2 100644 --- a/src/features/emoteController/autoLookAt.ts +++ b/src/features/emoteController/autoLookAt.ts @@ -1,5 +1,6 @@ -import * as THREE from "three"; -import { VRM } from "@pixiv/three-vrm"; +import { VRM } from '@pixiv/three-vrm'; +import * as THREE from 'three'; + /** * 目線を制御するクラス * diff --git a/src/features/emoteController/emoteController.ts b/src/features/emoteController/emoteController.ts index 9a67bf78..a677c82e 100644 --- a/src/features/emoteController/emoteController.ts +++ b/src/features/emoteController/emoteController.ts @@ -1,6 +1,7 @@ -import * as THREE from "three"; -import { VRM, VRMExpressionPresetName } from "@pixiv/three-vrm"; -import { ExpressionController } from "./expressionController"; +import { VRM, VRMExpressionPresetName } from '@pixiv/three-vrm'; +import * as THREE from 'three'; + +import { ExpressionController } from './expressionController'; /** * 感情表現としてExpressionとMotionを操作する為のクラス diff --git a/src/features/emoteController/expressionController.ts b/src/features/emoteController/expressionController.ts index df6debd6..7533ba5f 100644 --- a/src/features/emoteController/expressionController.ts +++ b/src/features/emoteController/expressionController.ts @@ -1,5 +1,6 @@ import { VRM, VRMExpressionManager, VRMExpressionPresetName } from '@pixiv/three-vrm'; import * as THREE from 'three'; + import { AutoBlink } from './autoBlink'; import { AutoLookAt } from './autoLookAt'; diff --git a/src/features/messages/speakCharacter.ts b/src/features/messages/speakCharacter.ts index 8cae1221..62bd9cc4 100644 --- a/src/features/messages/speakCharacter.ts +++ b/src/features/messages/speakCharacter.ts @@ -1,6 +1,7 @@ import { speechApi } from '@/services/tts'; import { Screenplay } from '@/types/touch'; import { wait } from '@/utils/wait'; + import { Viewer } from '../vrmViewer/viewer'; const createSpeakCharacter = () => { diff --git a/src/features/vrmViewer/model.ts b/src/features/vrmViewer/model.ts index e9184897..1e098eb9 100644 --- a/src/features/vrmViewer/model.ts +++ b/src/features/vrmViewer/model.ts @@ -1,3 +1,7 @@ +import { VRM, VRMLoaderPlugin, VRMUtils } from '@pixiv/three-vrm'; +import * as THREE from 'three'; +import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader'; + import { convert } from '@/lib/VMDAnimation/vmd2vrmanim'; import { bindToVRM, toOffset } from '@/lib/VMDAnimation/vmd2vrmanim.binding'; import IKHandler from '@/lib/VMDAnimation/vrm-ik-handler'; @@ -5,9 +9,7 @@ import { VRMAnimation } from '@/lib/VRMAnimation/VRMAnimation'; import { loadVRMAnimation } from '@/lib/VRMAnimation/loadVRMAnimation'; import { VRMLookAtSmootherLoaderPlugin } from '@/lib/VRMLookAtSmootherLoaderPlugin/VRMLookAtSmootherLoaderPlugin'; import { Screenplay } from '@/types/touch'; -import { VRM, VRMLoaderPlugin, VRMUtils } from '@pixiv/three-vrm'; -import * as THREE from 'three'; -import { GLTFLoader } from 'three/examples/jsm/loaders/GLTFLoader'; + import { EmoteController } from '../emoteController/emoteController'; import { LipSync } from '../lipSync/lipSync'; diff --git a/src/features/vrmViewer/viewer.ts b/src/features/vrmViewer/viewer.ts index a250e149..732312bc 100644 --- a/src/features/vrmViewer/viewer.ts +++ b/src/features/vrmViewer/viewer.ts @@ -2,6 +2,7 @@ import { Parser } from 'mmd-parser'; import * as THREE from 'three'; import { GridHelper, Mesh, MeshLambertMaterial, PlaneGeometry } from 'three'; import { OrbitControls } from 'three/examples/jsm/controls/OrbitControls'; + import { Model } from './model'; /** diff --git a/src/hooks/useCalculateToken.ts b/src/hooks/useCalculateToken.ts index d00bad33..4420ca84 100644 --- a/src/hooks/useCalculateToken.ts +++ b/src/hooks/useCalculateToken.ts @@ -1,7 +1,8 @@ -import { sessionSelectors, useSessionStore } from '@/store/session'; import { getEncoding } from 'js-tiktoken'; import { useMemo } from 'react'; +import { sessionSelectors, useSessionStore } from '@/store/session'; + const enc = getEncoding('cl100k_base'); export const useCalculateToken = () => { diff --git a/src/hooks/useSendMessage.ts b/src/hooks/useSendMessage.ts index 72a55e29..9de94dab 100644 --- a/src/hooks/useSendMessage.ts +++ b/src/hooks/useSendMessage.ts @@ -1,6 +1,7 @@ -import { useSessionStore } from '@/store/session'; import { useCallback } from 'react'; +import { useSessionStore } from '@/store/session'; + const useSendMessage = () => { const [sendMessage, setMessageInput] = useSessionStore((s) => [s.sendMessage, s.setMessageInput]); return useCallback(() => { diff --git a/src/layout/index.tsx b/src/layout/index.tsx index 0848e9a9..e8947d8f 100644 --- a/src/layout/index.tsx +++ b/src/layout/index.tsx @@ -1,13 +1,15 @@ 'use client'; +import { ThemeProvider } from '@lobehub/ui'; +import { ThemeAppearance, createStyles } from 'antd-style'; +import { ReactNode } from 'react'; + import { VIDOL_THEME_APPEARANCE } from '@/constants/common'; import { useConfigStore } from '@/store/config'; import { useThemeStore } from '@/store/theme'; import { GlobalStyle } from '@/styles'; import { setCookie } from '@/utils/cookie'; -import { ThemeProvider } from '@lobehub/ui'; -import { ThemeAppearance, createStyles } from 'antd-style'; -import { ReactNode } from 'react'; + import StoreHydration from './StoreHydration'; const useStyles = createStyles(({ css }) => ({ diff --git a/src/panels/AgentPanel/Agent/AgentCard/index.tsx b/src/panels/AgentPanel/Agent/AgentCard/index.tsx index f929b0c6..4adefd59 100644 --- a/src/panels/AgentPanel/Agent/AgentCard/index.tsx +++ b/src/panels/AgentPanel/Agent/AgentCard/index.tsx @@ -1,12 +1,13 @@ -import AgentInfo from '@/components/AgentInfo'; -import { agentListSelectors, useAgentStore } from '@/store/agent'; -import { useConfigStore } from '@/store/config'; -import { useSessionStore } from '@/store/session'; import { DraggablePanel } from '@lobehub/ui'; import { Button, Popconfirm } from 'antd'; import { createStyles } from 'antd-style'; import { memo, useState } from 'react'; +import AgentInfo from '@/components/AgentInfo'; +import { agentListSelectors, useAgentStore } from '@/store/agent'; +import { useConfigStore } from '@/store/config'; +import { useSessionStore } from '@/store/session'; + const useStyles = createStyles(({ css, token }) => ({ content: css` display: flex; diff --git a/src/panels/AgentPanel/Agent/AgentList/index.tsx b/src/panels/AgentPanel/Agent/AgentList/index.tsx index 9f266992..f84a5755 100644 --- a/src/panels/AgentPanel/Agent/AgentList/index.tsx +++ b/src/panels/AgentPanel/Agent/AgentList/index.tsx @@ -1,12 +1,13 @@ -import { agentListSelectors, useAgentStore } from '@/store/agent'; -import { useConfigStore } from '@/store/config'; -import { useMarketStore } from '@/store/market'; -import { Agent } from '@/types/agent'; import { GradientButton } from '@lobehub/ui'; import { Card, List, Typography } from 'antd'; import { memo } from 'react'; import { Flexbox } from 'react-layout-kit'; +import { agentListSelectors, useAgentStore } from '@/store/agent'; +import { useConfigStore } from '@/store/config'; +import { useMarketStore } from '@/store/market'; +import { Agent } from '@/types/agent'; + const { Text } = Typography; const { Meta } = Card; diff --git a/src/panels/AgentPanel/Agent/index.tsx b/src/panels/AgentPanel/Agent/index.tsx index 42abe12f..4bc4ac11 100644 --- a/src/panels/AgentPanel/Agent/index.tsx +++ b/src/panels/AgentPanel/Agent/index.tsx @@ -1,8 +1,10 @@ -import { useAgentStore } from '@/store/agent'; import { createStyles } from 'antd-style'; import classNames from 'classnames'; import dynamic from 'next/dynamic'; import React, { memo } from 'react'; + +import { useAgentStore } from '@/store/agent'; + import AgentCard from './AgentCard'; import AgentList from './AgentList'; diff --git a/src/panels/AgentPanel/index.tsx b/src/panels/AgentPanel/index.tsx index 6409de05..aa28ea3d 100644 --- a/src/panels/AgentPanel/index.tsx +++ b/src/panels/AgentPanel/index.tsx @@ -1,7 +1,9 @@ 'use client'; -import PanelContainer from '@/panels/PanelContainer'; import React from 'react'; + +import PanelContainer from '@/panels/PanelContainer'; + import Agent from './Agent'; import { useStyles } from './style'; diff --git a/src/panels/ChatPanel/ChatBot/ChatHeader.tsx b/src/panels/ChatPanel/ChatBot/ChatHeader.tsx index c0454c3b..1af281ed 100644 --- a/src/panels/ChatPanel/ChatBot/ChatHeader.tsx +++ b/src/panels/ChatPanel/ChatBot/ChatHeader.tsx @@ -1,5 +1,6 @@ import AgentMeta from '@/components/AgentMeta'; import { sessionSelectors, useSessionStore } from '@/store/session'; + import Voice from '../../../features/ChatInput/Actions/Voice'; import { useStyles } from './style'; diff --git a/src/panels/ChatPanel/ChatBot/ChatList/index.tsx b/src/panels/ChatPanel/ChatBot/ChatList/index.tsx index 71f3c656..5843af3f 100644 --- a/src/panels/ChatPanel/ChatBot/ChatList/index.tsx +++ b/src/panels/ChatPanel/ChatBot/ChatList/index.tsx @@ -1,9 +1,11 @@ -import Item from '@/features/ChatItem'; -import { sessionSelectors, useSessionStore } from '@/store/session'; import isEqual from 'fast-deep-equal'; import { memo, useEffect, useRef, useState } from 'react'; import { Flexbox } from 'react-layout-kit'; import { Virtuoso, VirtuosoHandle } from 'react-virtuoso'; + +import Item from '@/features/ChatItem'; +import { sessionSelectors, useSessionStore } from '@/store/session'; + import AutoScroll from './AutoScroll'; const itemContent = (index: number, id: string) => { diff --git a/src/panels/ChatPanel/ChatBot/index.tsx b/src/panels/ChatPanel/ChatBot/index.tsx index 7d78a19d..b97ffacc 100644 --- a/src/panels/ChatPanel/ChatBot/index.tsx +++ b/src/panels/ChatPanel/ChatBot/index.tsx @@ -1,5 +1,6 @@ import classNames from 'classnames'; import React, { memo } from 'react'; + import ChatInput from '../../../features/ChatInput'; import ChatHeader from './ChatHeader'; import ChatList from './ChatList'; diff --git a/src/panels/ChatPanel/ChatBot/type.ts b/src/panels/ChatPanel/ChatBot/type.ts index 4d1846d0..c77d0c3b 100644 --- a/src/panels/ChatPanel/ChatBot/type.ts +++ b/src/panels/ChatPanel/ChatBot/type.ts @@ -1,7 +1,8 @@ -import { ChatMessage } from '@/types/chat'; import { ActionEvent, ActionIconGroupProps } from '@lobehub/ui'; import { FC, ReactNode } from 'react'; +import { ChatMessage } from '@/types/chat'; + export type ActionsBarProps = ActionIconGroupProps; export type OnActionsClick = (action: ActionEvent, message: ChatMessage) => void; diff --git a/src/panels/ChatPanel/SideBar/Header.tsx b/src/panels/ChatPanel/SideBar/Header.tsx index 04505599..2876b0c2 100644 --- a/src/panels/ChatPanel/SideBar/Header.tsx +++ b/src/panels/ChatPanel/SideBar/Header.tsx @@ -1,8 +1,10 @@ -import { useConfigStore } from '@/store/config'; import { ActionIcon, SearchBar } from '@lobehub/ui'; import { Plus } from 'lucide-react'; import { memo } from 'react'; import { Flexbox } from 'react-layout-kit'; + +import { useConfigStore } from '@/store/config'; + import { useStyles } from './style'; interface HeaderProps { diff --git a/src/panels/ChatPanel/SideBar/SessionList/List.tsx b/src/panels/ChatPanel/SideBar/SessionList/List.tsx index 79bca08a..f03fb926 100644 --- a/src/panels/ChatPanel/SideBar/SessionList/List.tsx +++ b/src/panels/ChatPanel/SideBar/SessionList/List.tsx @@ -1,8 +1,10 @@ -import { useSessionStore } from '@/store/session'; -import { sessionSelectors } from '@/store/session/selectors'; import { createStyles } from 'antd-style'; import { memo } from 'react'; import LazyLoad from 'react-lazy-load'; + +import { useSessionStore } from '@/store/session'; +import { sessionSelectors } from '@/store/session/selectors'; + import SessionItem from './SessionItem'; const useStyles = createStyles( diff --git a/src/panels/ChatPanel/SideBar/SessionList/SessionItem/Actions.tsx b/src/panels/ChatPanel/SideBar/SessionList/SessionItem/Actions.tsx index ce66487d..03ace480 100644 --- a/src/panels/ChatPanel/SideBar/SessionList/SessionItem/Actions.tsx +++ b/src/panels/ChatPanel/SideBar/SessionList/SessionItem/Actions.tsx @@ -1,8 +1,9 @@ -import { useSessionStore } from '@/store/session'; import { ActionIcon } from '@lobehub/ui'; import { App, Dropdown, MenuProps } from 'antd'; import { MoreVertical, Trash2 } from 'lucide-react'; +import { useSessionStore } from '@/store/session'; + interface ActionsProps { id: string; setOpen: (open: boolean) => void; diff --git a/src/panels/ChatPanel/SideBar/SessionList/SessionItem/index.tsx b/src/panels/ChatPanel/SideBar/SessionList/SessionItem/index.tsx index 1381d6b0..181988b3 100644 --- a/src/panels/ChatPanel/SideBar/SessionList/SessionItem/index.tsx +++ b/src/panels/ChatPanel/SideBar/SessionList/SessionItem/index.tsx @@ -1,7 +1,8 @@ -import { sessionSelectors, useSessionStore } from '@/store/session'; import { memo, useMemo, useState } from 'react'; import { shallow } from 'zustand/shallow'; +import { sessionSelectors, useSessionStore } from '@/store/session'; + import Actions from './Actions'; import ListItem from './ListItem'; diff --git a/src/panels/ChatPanel/SideBar/index.tsx b/src/panels/ChatPanel/SideBar/index.tsx index 69df5ed9..306c215f 100644 --- a/src/panels/ChatPanel/SideBar/index.tsx +++ b/src/panels/ChatPanel/SideBar/index.tsx @@ -1,6 +1,7 @@ import { DraggablePanel } from '@lobehub/ui'; import { createStyles } from 'antd-style'; import { memo, useState } from 'react'; + import Header from './Header'; import SessionList from './SessionList/List'; diff --git a/src/panels/ChatPanel/index.tsx b/src/panels/ChatPanel/index.tsx index 1c95b8b8..7b05705f 100644 --- a/src/panels/ChatPanel/index.tsx +++ b/src/panels/ChatPanel/index.tsx @@ -1,8 +1,10 @@ 'use client'; -import PanelContainer from '@/panels/PanelContainer'; import classNames from 'classnames'; import React from 'react'; + +import PanelContainer from '@/panels/PanelContainer'; + import ChatBot from './ChatBot'; import SideBar from './SideBar'; import { useStyles } from './style'; diff --git a/src/panels/ConfigPanel/Config/common.tsx b/src/panels/ConfigPanel/Config/common.tsx index 1188c7ca..83c04989 100644 --- a/src/panels/ConfigPanel/Config/common.tsx +++ b/src/panels/ConfigPanel/Config/common.tsx @@ -1,7 +1,3 @@ -import { useConfigStore } from '@/store/config'; -import { useSessionStore } from '@/store/session'; -import { useThemeStore } from '@/store/theme'; -import { BackgroundEffect } from '@/types/config'; import { CheckCard } from '@ant-design/pro-card'; import { Form, @@ -17,6 +13,11 @@ import classNames from 'classnames'; import { Monitor, Settings2 } from 'lucide-react'; import React from 'react'; +import { useConfigStore } from '@/store/config'; +import { useSessionStore } from '@/store/session'; +import { useThemeStore } from '@/store/theme'; +import { BackgroundEffect } from '@/types/config'; + interface CommonConfigProps { className?: string; style?: React.CSSProperties; diff --git a/src/panels/ConfigPanel/Config/index.tsx b/src/panels/ConfigPanel/Config/index.tsx index 5399bbae..39fe5e35 100644 --- a/src/panels/ConfigPanel/Config/index.tsx +++ b/src/panels/ConfigPanel/Config/index.tsx @@ -1,6 +1,7 @@ import { TabsNav } from '@lobehub/ui'; import classNames from 'classnames'; import React, { memo, useState } from 'react'; + import CommonConfig from './common'; import OpenAIConfig from './model/openai'; import { useStyles } from './style'; diff --git a/src/panels/ConfigPanel/Config/model/openai.tsx b/src/panels/ConfigPanel/Config/model/openai.tsx index 16cd40d8..a774911a 100644 --- a/src/panels/ConfigPanel/Config/model/openai.tsx +++ b/src/panels/ConfigPanel/Config/model/openai.tsx @@ -1,6 +1,3 @@ -import { OPENAI_MODEL_LIST } from '@/constants/openai'; -import { chatCompletion } from '@/services/chat'; -import { configSelectors, useConfigStore } from '@/store/config'; import { Form, FormGroup, FormItem } from '@lobehub/ui'; import { useRequest } from 'ahooks'; import { Form as AForm, Button, Input, Select, Tag, message } from 'antd'; @@ -10,6 +7,10 @@ import { debounce, isEqual } from 'lodash-es'; import { BotIcon } from 'lucide-react'; import React, { useEffect } from 'react'; +import { OPENAI_MODEL_LIST } from '@/constants/openai'; +import { chatCompletion } from '@/services/chat'; +import { configSelectors, useConfigStore } from '@/store/config'; + interface ConfigProps { className?: string; style?: React.CSSProperties; diff --git a/src/panels/ConfigPanel/index.tsx b/src/panels/ConfigPanel/index.tsx index 915d299b..b8fcc39f 100644 --- a/src/panels/ConfigPanel/index.tsx +++ b/src/panels/ConfigPanel/index.tsx @@ -1,7 +1,9 @@ 'use client'; -import PanelContainer from '@/panels/PanelContainer'; import React from 'react'; + +import PanelContainer from '@/panels/PanelContainer'; + import Config from './Config'; import { useStyles } from './style'; diff --git a/src/panels/DancePanel/Dance/DanceCard/index.tsx b/src/panels/DancePanel/Dance/DanceCard/index.tsx index 41acd423..a2ff90df 100644 --- a/src/panels/DancePanel/Dance/DanceCard/index.tsx +++ b/src/panels/DancePanel/Dance/DanceCard/index.tsx @@ -1,10 +1,11 @@ -import DanceInfo from '@/components/DanceInfo'; -import { danceListSelectors, useDanceStore } from '@/store/dance'; import { DraggablePanel } from '@lobehub/ui'; import { Button, Popconfirm } from 'antd'; import { createStyles } from 'antd-style'; import { memo, useState } from 'react'; +import DanceInfo from '@/components/DanceInfo'; +import { danceListSelectors, useDanceStore } from '@/store/dance'; + const useStyles = createStyles(({ css, token }) => ({ content: css` display: flex; diff --git a/src/panels/DancePanel/Dance/DanceList/index.tsx b/src/panels/DancePanel/Dance/DanceList/index.tsx index d1b51bf4..dccd2346 100644 --- a/src/panels/DancePanel/Dance/DanceList/index.tsx +++ b/src/panels/DancePanel/Dance/DanceList/index.tsx @@ -1,10 +1,11 @@ -import { useConfigStore } from '@/store/config'; -import { useDanceStore } from '@/store/dance'; -import { useMarketStore } from '@/store/market'; import { GradientButton } from '@lobehub/ui'; import { Card, List } from 'antd'; import { Flexbox } from 'react-layout-kit'; +import { useConfigStore } from '@/store/config'; +import { useDanceStore } from '@/store/dance'; +import { useMarketStore } from '@/store/market'; + const { Meta } = Card; const DanceList = () => { diff --git a/src/panels/DancePanel/Dance/index.tsx b/src/panels/DancePanel/Dance/index.tsx index 30ebe889..8eb43b6d 100644 --- a/src/panels/DancePanel/Dance/index.tsx +++ b/src/panels/DancePanel/Dance/index.tsx @@ -3,6 +3,7 @@ import { createStyles } from 'antd-style'; import classNames from 'classnames'; import React, { memo } from 'react'; import { Center } from 'react-layout-kit'; + import DanceCard from './DanceCard'; import DanceList from './DanceList'; diff --git a/src/panels/DancePanel/index.tsx b/src/panels/DancePanel/index.tsx index 043d0d21..cf3c34ef 100644 --- a/src/panels/DancePanel/index.tsx +++ b/src/panels/DancePanel/index.tsx @@ -1,7 +1,9 @@ 'use client'; -import PanelContainer from '@/panels/PanelContainer'; import React from 'react'; + +import PanelContainer from '@/panels/PanelContainer'; + import Dance from './Dance'; import { useStyles } from './style'; diff --git a/src/panels/MarketPanel/Agent/AgentCard/SubscribeButton.tsx b/src/panels/MarketPanel/Agent/AgentCard/SubscribeButton.tsx index a3bb4f73..f3dfae30 100644 --- a/src/panels/MarketPanel/Agent/AgentCard/SubscribeButton.tsx +++ b/src/panels/MarketPanel/Agent/AgentCard/SubscribeButton.tsx @@ -1,6 +1,7 @@ +import { Button, message } from 'antd'; + import { agentListSelectors, useAgentStore } from '@/store/agent'; import { Agent } from '@/types/agent'; -import { Button, message } from 'antd'; interface SubscribeButtonProps { agent: Agent; diff --git a/src/panels/MarketPanel/Agent/AgentCard/index.tsx b/src/panels/MarketPanel/Agent/AgentCard/index.tsx index 1f6a0885..ece79c37 100644 --- a/src/panels/MarketPanel/Agent/AgentCard/index.tsx +++ b/src/panels/MarketPanel/Agent/AgentCard/index.tsx @@ -1,9 +1,10 @@ -import AgentInfo from '@/components/AgentInfo'; -import { marketStoreSelectors, useMarketStore } from '@/store/market'; - import { DraggablePanel } from '@lobehub/ui'; import { createStyles } from 'antd-style'; import { memo, useState } from 'react'; + +import AgentInfo from '@/components/AgentInfo'; +import { marketStoreSelectors, useMarketStore } from '@/store/market'; + import DownloadButton from './SubscribeButton'; const useStyles = createStyles(({ css, token }) => ({ diff --git a/src/panels/MarketPanel/Agent/AgentIndex/AgentList.tsx b/src/panels/MarketPanel/Agent/AgentIndex/AgentList.tsx index 1cb4dee1..b9f2c65f 100644 --- a/src/panels/MarketPanel/Agent/AgentIndex/AgentList.tsx +++ b/src/panels/MarketPanel/Agent/AgentIndex/AgentList.tsx @@ -1,9 +1,10 @@ -import { agentListSelectors, useAgentStore } from '@/store/agent'; -import { marketStoreSelectors, useMarketStore } from '@/store/market'; import { CheckCircleTwoTone } from '@ant-design/icons'; import { Card, List } from 'antd'; import { memo } from 'react'; +import { agentListSelectors, useAgentStore } from '@/store/agent'; +import { marketStoreSelectors, useMarketStore } from '@/store/market'; + const { Meta } = List.Item; const AgentList = () => { diff --git a/src/panels/MarketPanel/Agent/AgentIndex/Header.tsx b/src/panels/MarketPanel/Agent/AgentIndex/Header.tsx index b84cb49d..1edcb92e 100644 --- a/src/panels/MarketPanel/Agent/AgentIndex/Header.tsx +++ b/src/panels/MarketPanel/Agent/AgentIndex/Header.tsx @@ -1,9 +1,10 @@ -import { useMarketStore } from '@/store/market'; import { Button } from 'antd'; import { createStyles } from 'antd-style'; import classNames from 'classnames'; import React, { memo, useEffect } from 'react'; +import { useMarketStore } from '@/store/market'; + const useStyles = createStyles(({ css }) => ({ actions: css` display: flex; diff --git a/src/panels/MarketPanel/Agent/AgentIndex/index.tsx b/src/panels/MarketPanel/Agent/AgentIndex/index.tsx index d49acf77..a6997422 100644 --- a/src/panels/MarketPanel/Agent/AgentIndex/index.tsx +++ b/src/panels/MarketPanel/Agent/AgentIndex/index.tsx @@ -1,4 +1,5 @@ import { memo } from 'react'; + import AgentList from './AgentList'; import Header from './Header'; diff --git a/src/panels/MarketPanel/Agent/index.tsx b/src/panels/MarketPanel/Agent/index.tsx index 59c10945..46587ec9 100644 --- a/src/panels/MarketPanel/Agent/index.tsx +++ b/src/panels/MarketPanel/Agent/index.tsx @@ -3,6 +3,7 @@ import { createStyles } from 'antd-style'; import classNames from 'classnames'; import React, { memo } from 'react'; import { Center } from 'react-layout-kit'; + import AgentCard from './AgentCard'; import AgentIndex from './AgentIndex'; diff --git a/src/panels/MarketPanel/Dance/DanceCard/SubscribeButton.tsx b/src/panels/MarketPanel/Dance/DanceCard/SubscribeButton.tsx index a2150d7d..066d6fae 100644 --- a/src/panels/MarketPanel/Dance/DanceCard/SubscribeButton.tsx +++ b/src/panels/MarketPanel/Dance/DanceCard/SubscribeButton.tsx @@ -1,6 +1,7 @@ +import { Button, message } from 'antd'; + import { danceListSelectors, useDanceStore } from '@/store/dance'; import { Dance } from '@/types/dance'; -import { Button, message } from 'antd'; interface SubscribeButtonProps { dance: Dance; diff --git a/src/panels/MarketPanel/Dance/DanceCard/index.tsx b/src/panels/MarketPanel/Dance/DanceCard/index.tsx index 7c7f7e6d..dce7136c 100644 --- a/src/panels/MarketPanel/Dance/DanceCard/index.tsx +++ b/src/panels/MarketPanel/Dance/DanceCard/index.tsx @@ -1,9 +1,10 @@ -import DanceInfo from '@/components/DanceInfo'; -import { marketStoreSelectors, useMarketStore } from '@/store/market'; - import { DraggablePanel } from '@lobehub/ui'; import { createStyles } from 'antd-style'; import { memo, useState } from 'react'; + +import DanceInfo from '@/components/DanceInfo'; +import { marketStoreSelectors, useMarketStore } from '@/store/market'; + import SubscribeButton from './SubscribeButton'; const useStyles = createStyles(({ css, token }) => ({ diff --git a/src/panels/MarketPanel/Dance/DanceIndex/DanceList.tsx b/src/panels/MarketPanel/Dance/DanceIndex/DanceList.tsx index 5c7f7ac0..e45ecaa2 100644 --- a/src/panels/MarketPanel/Dance/DanceIndex/DanceList.tsx +++ b/src/panels/MarketPanel/Dance/DanceIndex/DanceList.tsx @@ -1,9 +1,10 @@ -import { danceListSelectors, useDanceStore } from '@/store/dance'; -import { marketStoreSelectors, useMarketStore } from '@/store/market'; import { CheckCircleTwoTone } from '@ant-design/icons'; import { Card, List } from 'antd'; import { memo } from 'react'; +import { danceListSelectors, useDanceStore } from '@/store/dance'; +import { marketStoreSelectors, useMarketStore } from '@/store/market'; + const { Meta } = List.Item; const DanceList = () => { diff --git a/src/panels/MarketPanel/Dance/DanceIndex/Header.tsx b/src/panels/MarketPanel/Dance/DanceIndex/Header.tsx index 377b4d35..85a07826 100644 --- a/src/panels/MarketPanel/Dance/DanceIndex/Header.tsx +++ b/src/panels/MarketPanel/Dance/DanceIndex/Header.tsx @@ -1,9 +1,10 @@ -import { useMarketStore } from '@/store/market'; import { Button } from 'antd'; import { createStyles } from 'antd-style'; import classNames from 'classnames'; import React, { memo, useEffect } from 'react'; +import { useMarketStore } from '@/store/market'; + const useStyles = createStyles(({ css }) => ({ actions: css` display: flex; diff --git a/src/panels/MarketPanel/Dance/DanceIndex/index.tsx b/src/panels/MarketPanel/Dance/DanceIndex/index.tsx index 8a36c6de..74a00b4f 100644 --- a/src/panels/MarketPanel/Dance/DanceIndex/index.tsx +++ b/src/panels/MarketPanel/Dance/DanceIndex/index.tsx @@ -1,4 +1,5 @@ import { memo } from 'react'; + import DanceList from './DanceList'; import Header from './Header'; diff --git a/src/panels/MarketPanel/Dance/index.tsx b/src/panels/MarketPanel/Dance/index.tsx index 0c120945..25f4a2ed 100644 --- a/src/panels/MarketPanel/Dance/index.tsx +++ b/src/panels/MarketPanel/Dance/index.tsx @@ -3,6 +3,7 @@ import { createStyles } from 'antd-style'; import classNames from 'classnames'; import React from 'react'; import { Center } from 'react-layout-kit'; + import DanceCard from './DanceCard'; import DanceIndex from './DanceIndex'; diff --git a/src/panels/MarketPanel/SideNav/index.tsx b/src/panels/MarketPanel/SideNav/index.tsx index 49de42c9..bcaa6160 100644 --- a/src/panels/MarketPanel/SideNav/index.tsx +++ b/src/panels/MarketPanel/SideNav/index.tsx @@ -1,7 +1,8 @@ -import { useMarketStore } from '@/store/market'; import { ActionIcon, SideNav as LobeSideNav } from '@lobehub/ui'; import { Music2, User } from 'lucide-react'; +import { useMarketStore } from '@/store/market'; + interface SideNavProps { className?: string; } diff --git a/src/panels/MarketPanel/index.tsx b/src/panels/MarketPanel/index.tsx index 17f9a76e..4bb45552 100644 --- a/src/panels/MarketPanel/index.tsx +++ b/src/panels/MarketPanel/index.tsx @@ -1,8 +1,10 @@ 'use client'; +import React from 'react'; + import PanelContainer from '@/panels/PanelContainer'; import { useMarketStore } from '@/store/market'; -import React from 'react'; + import Agent from './Agent'; import Dance from './Dance'; import SideNav from './SideNav'; diff --git a/src/panels/PanelContainer.tsx b/src/panels/PanelContainer.tsx index 24144f9e..8c7d6472 100644 --- a/src/panels/PanelContainer.tsx +++ b/src/panels/PanelContainer.tsx @@ -1,9 +1,10 @@ 'use client'; +import React, { PropsWithChildren } from 'react'; + import Panel from '@/components/Panel'; import { configSelectors, useConfigStore } from '@/store/config'; import { PanelKey } from '@/types/config'; -import React, { PropsWithChildren } from 'react'; interface PanelContainerProps { className?: string; diff --git a/src/panels/RolePanel/Info/index.tsx b/src/panels/RolePanel/Info/index.tsx index e551469f..08a0d80a 100644 --- a/src/panels/RolePanel/Info/index.tsx +++ b/src/panels/RolePanel/Info/index.tsx @@ -1,10 +1,11 @@ -import { sessionSelectors, useSessionStore } from '@/store/session'; import { Avatar, FormFooter } from '@lobehub/ui'; import { Button, Form, Input, message } from 'antd'; import { createStyles } from 'antd-style'; import classNames from 'classnames'; import React from 'react'; +import { sessionSelectors, useSessionStore } from '@/store/session'; + const FormItem = Form.Item; interface InfoProps { diff --git a/src/panels/RolePanel/Role/index.tsx b/src/panels/RolePanel/Role/index.tsx index a6b0ee61..2982588c 100644 --- a/src/panels/RolePanel/Role/index.tsx +++ b/src/panels/RolePanel/Role/index.tsx @@ -1,10 +1,11 @@ -import { sessionSelectors, useSessionStore } from '@/store/session'; import { FormFooter } from '@lobehub/ui'; import { Button, Form, Input, message } from 'antd'; import { createStyles } from 'antd-style'; import classNames from 'classnames'; import React from 'react'; +import { sessionSelectors, useSessionStore } from '@/store/session'; + const FormItem = Form.Item; interface InfoProps { diff --git a/src/panels/RolePanel/Touch/ActionList/index.tsx b/src/panels/RolePanel/Touch/ActionList/index.tsx index 2c014b8a..71152f5f 100644 --- a/src/panels/RolePanel/Touch/ActionList/index.tsx +++ b/src/panels/RolePanel/Touch/ActionList/index.tsx @@ -1,13 +1,14 @@ -import { speakCharacter } from '@/features/messages/speakCharacter'; -import { sessionSelectors, useSessionStore } from '@/store/session'; -import { useTouchStore } from '@/store/touch'; -import { useViewerStore } from '@/store/viewer'; import { ActionIcon } from '@lobehub/ui'; import { List } from 'antd'; import { createStyles } from 'antd-style'; import { isEqual } from 'lodash-es'; import { PlayIcon } from 'lucide-react'; +import { speakCharacter } from '@/features/messages/speakCharacter'; +import { sessionSelectors, useSessionStore } from '@/store/session'; +import { useTouchStore } from '@/store/touch'; +import { useViewerStore } from '@/store/viewer'; + const useStyles = createStyles(({ css, token }) => ({ active: css` background-color: ${token.controlItemBgActiveHover}; diff --git a/src/panels/RolePanel/Touch/SideBar/AreaList.tsx b/src/panels/RolePanel/Touch/SideBar/AreaList.tsx index 31c3ae6a..fab3a804 100644 --- a/src/panels/RolePanel/Touch/SideBar/AreaList.tsx +++ b/src/panels/RolePanel/Touch/SideBar/AreaList.tsx @@ -1,9 +1,9 @@ -import { useTouchStore } from '@/store/touch'; -import { TouchAreaEnum } from '@/types/touch'; import { List } from 'antd'; +import { createStyles } from 'antd-style'; import classNames from 'classnames'; -import { createStyles } from 'antd-style'; +import { useTouchStore } from '@/store/touch'; +import { TouchAreaEnum } from '@/types/touch'; const useStyles = createStyles(({ css, token }) => ({ active: css` diff --git a/src/panels/RolePanel/Touch/index.tsx b/src/panels/RolePanel/Touch/index.tsx index 9ed15254..e9896962 100644 --- a/src/panels/RolePanel/Touch/index.tsx +++ b/src/panels/RolePanel/Touch/index.tsx @@ -1,6 +1,7 @@ import { createStyles } from 'antd-style'; import classNames from 'classnames'; import React, { memo } from 'react'; + import ActionList from './ActionList'; import SideBar from './SideBar'; diff --git a/src/panels/RolePanel/Voice/index.tsx b/src/panels/RolePanel/Voice/index.tsx index b5c68131..fb7d7a79 100644 --- a/src/panels/RolePanel/Voice/index.tsx +++ b/src/panels/RolePanel/Voice/index.tsx @@ -1,6 +1,3 @@ -import { speechApi, voiceListApi } from '@/services/tts'; -import { sessionSelectors, useSessionStore } from '@/store/session'; -import { Voice } from '@/types/tts'; import { FormFooter } from '@lobehub/ui'; import { useRequest } from 'ahooks'; import { Button, Divider, Form, Input, Select, Slider, message } from 'antd'; @@ -8,6 +5,10 @@ import { createStyles } from 'antd-style'; import classNames from 'classnames'; import React, { useEffect, useRef, useState } from 'react'; +import { speechApi, voiceListApi } from '@/services/tts'; +import { sessionSelectors, useSessionStore } from '@/store/session'; +import { Voice } from '@/types/tts'; + const FormItem = Form.Item; interface ConfigProps { diff --git a/src/panels/RolePanel/index.tsx b/src/panels/RolePanel/index.tsx index dc3fc5d8..1853d83d 100644 --- a/src/panels/RolePanel/index.tsx +++ b/src/panels/RolePanel/index.tsx @@ -1,8 +1,10 @@ 'use client'; -import PanelContainer from '@/panels/PanelContainer'; import { TabsNav } from '@lobehub/ui'; import React, { useState } from 'react'; + +import PanelContainer from '@/panels/PanelContainer'; + import Info from './Info'; import Role from './Role'; import Touch from './Touch'; diff --git a/src/panels/index.tsx b/src/panels/index.tsx index f28856c8..12c751c2 100644 --- a/src/panels/index.tsx +++ b/src/panels/index.tsx @@ -1,17 +1,8 @@ 'use client'; - - - - - - - - - -export {default as AgentPanel} from './AgentPanel'; -export {default as ChatPanel} from './ChatPanel'; -export {default as ConfigPanel} from './ConfigPanel'; -export {default as DancePanel} from './DancePanel'; -export {default as MarketPanel} from './MarketPanel'; -export {default as RolePanel} from './RolePanel'; \ No newline at end of file +export { default as AgentPanel } from './AgentPanel'; +export { default as ChatPanel } from './ChatPanel'; +export { default as ConfigPanel } from './ConfigPanel'; +export { default as DancePanel } from './DancePanel'; +export { default as MarketPanel } from './MarketPanel'; +export { default as RolePanel } from './RolePanel'; diff --git a/src/services/dance.ts b/src/services/dance.ts index 108fdfe7..538bcc83 100644 --- a/src/services/dance.ts +++ b/src/services/dance.ts @@ -1,4 +1,5 @@ import { DANCE_INDEX_URL } from '@/constants/common'; + /** * 请求 Dance 列表 */ diff --git a/src/store/agent/index.ts b/src/store/agent/index.ts index df93f2fa..293977b1 100644 --- a/src/store/agent/index.ts +++ b/src/store/agent/index.ts @@ -1,9 +1,9 @@ -import { Agent } from '@/types/agent'; import { produce } from 'immer'; import { persist } from 'zustand/middleware'; import { shallow } from 'zustand/shallow'; import { createWithEqualityFn } from 'zustand/traditional'; +import { Agent } from '@/types/agent'; export interface AgentStore { activateAgent: (identifier: string) => void; @@ -65,6 +65,4 @@ export const useAgentStore = createWithEqualityFn()( shallow, ); - - -export {agentListSelectors} from './selectors/agent'; \ No newline at end of file +export { agentListSelectors } from './selectors/agent'; diff --git a/src/store/agent/selectors/agent.ts b/src/store/agent/selectors/agent.ts index b98e69e2..e92d6b95 100644 --- a/src/store/agent/selectors/agent.ts +++ b/src/store/agent/selectors/agent.ts @@ -1,4 +1,5 @@ import { Agent } from '@/types/agent'; + import { AgentStore } from '../index'; const showSideBar = (s: AgentStore) => !!s.currentIdentifier; diff --git a/src/store/config/index.ts b/src/store/config/index.ts index b5c052a1..b4193556 100644 --- a/src/store/config/index.ts +++ b/src/store/config/index.ts @@ -1,12 +1,13 @@ -import { Config, Panel, PanelKey } from '@/types/config'; import { produce } from 'immer'; import { isEqual, merge } from 'lodash-es'; import { devtools, persist } from 'zustand/middleware'; import { shallow } from 'zustand/shallow'; import { createWithEqualityFn } from 'zustand/traditional'; import { StateCreator } from 'zustand/vanilla'; -import { ConfigState, initialState } from './initialState'; +import { Config, Panel, PanelKey } from '@/types/config'; + +import { ConfigState, initialState } from './initialState'; const CONFIG_STORAGE_KEY = 'vidol-chat-config-storage'; @@ -114,6 +115,4 @@ export const useConfigStore = createWithEqualityFn()( shallow, ); - - -export {configSelectors} from './selectors/config'; \ No newline at end of file +export { configSelectors } from './selectors/config'; diff --git a/src/store/dance/index.ts b/src/store/dance/index.ts index 58475bb6..1f36098b 100644 --- a/src/store/dance/index.ts +++ b/src/store/dance/index.ts @@ -25,6 +25,4 @@ export const useDanceStore = createWithEqualityFn()( shallow, ); - - -export {danceListSelectors} from './selectors/dance'; \ No newline at end of file +export { danceListSelectors } from './selectors/dance'; diff --git a/src/store/dance/selectors/dance.ts b/src/store/dance/selectors/dance.ts index 2d41dff7..40ac54b7 100644 --- a/src/store/dance/selectors/dance.ts +++ b/src/store/dance/selectors/dance.ts @@ -1,4 +1,5 @@ import { Dance } from '@/types/dance'; + import { DanceStore } from '../index'; const showSideBar = (s: DanceStore) => !!s.currentIdentifier; diff --git a/src/store/dance/slices/dancelist.ts b/src/store/dance/slices/dancelist.ts index 4a8bfbeb..eec79f0c 100644 --- a/src/store/dance/slices/dancelist.ts +++ b/src/store/dance/slices/dancelist.ts @@ -1,10 +1,11 @@ +import { produce } from 'immer'; +import { isEqual } from 'lodash-es'; +import { StateCreator } from 'zustand/vanilla'; + import { DEFAULT_DANCE } from '@/constants/dance'; import { getDanceIndex } from '@/services/dance'; import { DanceStore } from '@/store/dance'; import { Dance } from '@/types/dance'; -import { produce } from 'immer'; -import { isEqual } from 'lodash-es'; -import { StateCreator } from 'zustand/vanilla'; export interface DanceListStore { activateDance: (identifier: string) => void; diff --git a/src/store/dance/slices/playlist.ts b/src/store/dance/slices/playlist.ts index b7305906..f6b5d635 100644 --- a/src/store/dance/slices/playlist.ts +++ b/src/store/dance/slices/playlist.ts @@ -1,8 +1,9 @@ +import { produce } from 'immer'; +import { StateCreator } from 'zustand/vanilla'; + import { DEFAULT_DANCE } from '@/constants/dance'; import { DanceStore } from '@/store/dance'; import { Dance } from '@/types/dance'; -import { produce } from 'immer'; -import { StateCreator } from 'zustand/vanilla'; export interface PlayListStore { addAndPlayItem: (dance: Dance) => void; diff --git a/src/store/market/index.ts b/src/store/market/index.ts index 86be0697..d116f787 100644 --- a/src/store/market/index.ts +++ b/src/store/market/index.ts @@ -2,6 +2,7 @@ import { devtools, persist } from 'zustand/middleware'; import { shallow } from 'zustand/shallow'; import { createWithEqualityFn } from 'zustand/traditional'; import { StateCreator } from 'zustand/vanilla'; + import { agentSelectors } from './selectors/agent'; import { danceSelectors } from './selectors/dance'; import { AgentStore, createAgentStore } from './slices/agent'; diff --git a/src/store/market/slices/agent.ts b/src/store/market/slices/agent.ts index 966df72e..c06a5b74 100644 --- a/src/store/market/slices/agent.ts +++ b/src/store/market/slices/agent.ts @@ -1,8 +1,9 @@ +import { isEqual } from 'lodash-es'; +import { StateCreator } from 'zustand/vanilla'; + import { getAgentIndex } from '@/services/agent'; import { MarketStore } from '@/store/market'; import { Agent } from '@/types/agent'; -import { isEqual } from 'lodash-es'; -import { StateCreator } from 'zustand/vanilla'; export interface AgentStore { activateAgent: (identifier: string) => void; diff --git a/src/store/market/slices/dance.ts b/src/store/market/slices/dance.ts index eb0699ff..b527008a 100644 --- a/src/store/market/slices/dance.ts +++ b/src/store/market/slices/dance.ts @@ -1,16 +1,18 @@ -import { getDanceIndex } from '@/services/dance'; -import { MarketStore } from '@/store/market'; -import { Dance } from '@/types/dance'; // 更改这里 +// 更改这里 import { isEqual } from 'lodash-es'; import { StateCreator } from 'zustand/vanilla'; +import { getDanceIndex } from '@/services/dance'; +import { MarketStore } from '@/store/market'; +import { Dance } from '@/types/dance'; + export interface DanceStore { // 更改这里 - activateDance: (identifier: string) => void; + activateDance: (identifier: string) => void; // 更改这里 - currentDanceId: string; + currentDanceId: string; // 更改这里 - danceList: Dance[]; + danceList: Dance[]; // 更改这里 danceLoading: boolean; // 更改这里 deactivateDance: () => void; // 更改这里 @@ -26,17 +28,17 @@ export const createDanceStore: StateCreator< > = (set, get) => { return { // 更改这里 -activateDance: (identifier) => { + activateDance: (identifier) => { // 更改这里 set({ currentDanceId: identifier }); // 更改这里 - }, - -currentDanceId: '', - -// 更改这里 -danceList: [], + }, + + currentDanceId: '', + + // 更改这里 + danceList: [], // 更改这里 -danceLoading: false, + danceLoading: false, deactivateDance: () => { // 更改这里 set({ currentDanceId: undefined }); // 更改这里 diff --git a/src/store/market/slices/panel.ts b/src/store/market/slices/panel.ts index 17794c1a..c9a54a23 100644 --- a/src/store/market/slices/panel.ts +++ b/src/store/market/slices/panel.ts @@ -1,6 +1,7 @@ -import { MarketStore } from '@/store/market'; import { StateCreator } from 'zustand/vanilla'; +import { MarketStore } from '@/store/market'; + export type tabType = 'agent' | 'dance'; export interface PanelStore { diff --git a/src/store/session/hooks/useSessionStore.ts b/src/store/session/hooks/useSessionStore.ts new file mode 100644 index 00000000..f37bad75 --- /dev/null +++ b/src/store/session/hooks/useSessionStore.ts @@ -0,0 +1,17 @@ +import { devtools, persist } from 'zustand/middleware'; +import { shallow } from 'zustand/shallow'; +import { createWithEqualityFn } from 'zustand/traditional'; + +import { SESSION_STORAGE_KEY, SessionStore, createSessonStore } from '@/store/session'; + +export const useSessionStore = createWithEqualityFn()( + persist( + devtools(createSessonStore, { + name: 'VIDOL_SESSION_STORE', + }), + { + name: SESSION_STORAGE_KEY, // name of the item in the storage (must be unique) + }, + ), + shallow, +); diff --git a/src/store/session/index.ts b/src/store/session/index.ts index 42a3f64a..1527bcbc 100644 --- a/src/store/session/index.ts +++ b/src/store/session/index.ts @@ -1,9 +1,3 @@ -import { LOADING_FLAG } from '@/constants/common'; -import { chatCompletion, handleSpeakAi } from '@/services/chat'; -import { Agent } from '@/types/agent'; -import { ChatMessage } from '@/types/chat'; -import { Session } from '@/types/session'; -import { fetchSEE } from '@/utils/fetch'; import { nanoid } from 'ai'; import { produce } from 'immer'; import { merge } from 'lodash-es'; @@ -12,15 +6,23 @@ import { devtools, persist } from 'zustand/middleware'; import { shallow } from 'zustand/shallow'; import { createWithEqualityFn } from 'zustand/traditional'; import { StateCreator } from 'zustand/vanilla'; + +import { LOADING_FLAG } from '@/constants/common'; +import { chatCompletion, handleSpeakAi } from '@/services/chat'; +import { Agent } from '@/types/agent'; +import { ChatMessage } from '@/types/chat'; +import { Session } from '@/types/session'; +import { fetchSEE } from '@/utils/fetch'; + import { initialState } from './initialState'; import { MessageActionType, messageReducer } from './reducers/message'; import { sessionSelectors } from './selectors'; -const SESSION_STORAGE_KEY = 'vidol-chat-session-storage'; +export const SESSION_STORAGE_KEY = 'vidol-chat-session-storage'; export enum ViewerModeEnum { Img = 'Img', - Normal = 'Normal' + Normal = 'Normal', } export interface SessionStore { @@ -131,7 +133,7 @@ export interface SessionStore { voiceOn: boolean; } -const createSessonStore: StateCreator = ( +export const createSessonStore: StateCreator = ( set, get, ) => ({ @@ -242,7 +244,10 @@ const createSessonStore: StateCreator()( shallow, ); - - -export {sessionSelectors} from './selectors'; \ No newline at end of file +export { sessionSelectors } from './selectors'; diff --git a/src/store/session/reducers/message.ts b/src/store/session/reducers/message.ts index 78279e40..dae2d462 100644 --- a/src/store/session/reducers/message.ts +++ b/src/store/session/reducers/message.ts @@ -1,6 +1,7 @@ +import { produce } from 'immer'; + import { ChatMessage } from '@/types/chat'; import { LLMRoleType } from '@/types/llm'; -import { produce } from 'immer'; export interface AddMessageAction { payload: { diff --git a/src/store/session/selectors.ts b/src/store/session/selectors.ts index 87aa9b72..353c1e6b 100644 --- a/src/store/session/selectors.ts +++ b/src/store/session/selectors.ts @@ -3,6 +3,7 @@ import { DEFAULT_USER_AVATAR } from '@/constants/common'; import { Agent } from '@/types/agent'; import { ChatMessage } from '@/types/chat'; import { Session } from '@/types/session'; + import { SessionStore } from './index'; const currentSession = (s: SessionStore): Session | undefined => { diff --git a/src/store/touch.ts b/src/store/touch.ts index d1052762..2f9e862c 100644 --- a/src/store/touch.ts +++ b/src/store/touch.ts @@ -1,8 +1,9 @@ -import { TouchAction, TouchActionConfig, TouchAreaEnum } from '@/types/touch'; import { create } from 'zustand'; import { devtools } from 'zustand/middleware'; import { StateCreator } from 'zustand/vanilla'; +import { TouchAction, TouchActionConfig, TouchAreaEnum } from '@/types/touch'; + const DEFAULT_TOUCH_ACTION_CONFIG: TouchActionConfig = { [TouchAreaEnum.Head]: [ { diff --git a/src/store/viewer.ts b/src/store/viewer.ts index 436f113c..a20a6176 100644 --- a/src/store/viewer.ts +++ b/src/store/viewer.ts @@ -1,7 +1,8 @@ -import { Viewer } from '@/features/vrmViewer/viewer'; import { shallow } from 'zustand/shallow'; import { createWithEqualityFn } from 'zustand/traditional'; +import { Viewer } from '@/features/vrmViewer/viewer'; + interface ViewerStore { viewer: Viewer; } diff --git a/src/styles/index.tsx b/src/styles/index.tsx index 416c13ed..8b549cfe 100644 --- a/src/styles/index.tsx +++ b/src/styles/index.tsx @@ -1,4 +1,5 @@ import { createGlobalStyle } from 'antd-style'; + import global from './global'; const prefixCls = 'ant'; diff --git a/src/types/api.ts b/src/types/api.ts index 21ae0a63..a7d1a8af 100644 --- a/src/types/api.ts +++ b/src/types/api.ts @@ -1,7 +1,7 @@ export enum ErrorTypeEnum { API_KEY_MISSING = 'API_KEY_MISSING', INTERNAL_SERVER_ERROR = 'INTERNAL_SERVER_ERROR', - OPENAI_API_ERROR = 'OPENAI_API_ERROR' + OPENAI_API_ERROR = 'OPENAI_API_ERROR', } export interface APIErrorResponse { diff --git a/src/types/chat.ts b/src/types/chat.ts index 65f6f8fa..759d317d 100644 --- a/src/types/chat.ts +++ b/src/types/chat.ts @@ -1,4 +1,5 @@ import { ErrorTypeEnum } from '@/types/api'; + import { LLMRoleType } from './llm'; /** diff --git a/global.d.ts b/src/types/global.d.ts similarity index 100% rename from global.d.ts rename to src/types/global.d.ts diff --git a/src/types/touch.ts b/src/types/touch.ts index 154a6d92..58f98c09 100644 --- a/src/types/touch.ts +++ b/src/types/touch.ts @@ -1,4 +1,5 @@ import { VRMExpressionPresetName } from '@pixiv/three-vrm'; + import { TTS } from './tts'; export const emotions = ['neutral', 'happy', 'angry', 'sad', 'relaxed'] as const; @@ -9,7 +10,7 @@ export enum TouchAreaEnum { Belly = 'belly', Chest = 'chest', Head = 'head', - Leg = 'leg' + Leg = 'leg', } export interface TouchAction { diff --git a/src/utils/fetch.ts b/src/utils/fetch.ts index 25e5fdb1..3b5e5ffb 100644 --- a/src/utils/fetch.ts +++ b/src/utils/fetch.ts @@ -1,6 +1,7 @@ +import { message } from 'antd'; + import { APIErrorResponse, ErrorTypeEnum } from '@/types/api'; import { ChatMessageError } from '@/types/chat'; -import { message } from 'antd'; const getMessageByErrorType = (errorType: ErrorTypeEnum) => { const errorMap = { diff --git a/src/utils/keyboard.ts b/src/utils/keyboard.ts index aa251600..9ef29f72 100644 --- a/src/utils/keyboard.ts +++ b/src/utils/keyboard.ts @@ -3,11 +3,11 @@ import { KeyboardEvent } from 'react'; import { isMacOS } from './platform'; export const isCommandPressed = (event: KeyboardEvent) => { - const isMac = isMacOS(); + const isMac = isMacOS(); - if (isMac) { - return event.metaKey; // Use metaKey (Command key) on macOS - } else { - return event.ctrlKey; // Use ctrlKey on Windows/Linux - } + if (isMac) { + return event.metaKey; // Use metaKey (Command key) on macOS + } else { + return event.ctrlKey; // Use ctrlKey on Windows/Linux + } }; diff --git a/tests/setup.ts b/tests/setup.ts new file mode 100644 index 00000000..d9be8c71 --- /dev/null +++ b/tests/setup.ts @@ -0,0 +1,35 @@ +/* eslint-disable import/newline-after-import,import/first */ +import '@testing-library/jest-dom'; +import { theme } from 'antd'; +// mock indexedDB to test with dexie +// refs: https://github.com/dumbmatter/fakeIndexedDB#dexie-and-other-indexeddb-api-wrappers +import 'fake-indexeddb/auto'; +import React from 'react'; + +// only inject in the dom environment +if ( + // not node runtime + typeof window !== 'undefined' && + // not edge runtime + typeof (globalThis as any).EdgeRuntime !== 'string' +) { + // test with canvas + await import('vitest-canvas-mock'); +} + +// node runtime +if (typeof window === 'undefined') { + // test with polyfill crypto + const { Crypto } = await import('@peculiar/webcrypto'); + + Object.defineProperty(global, 'crypto', { + value: new Crypto(), + writable: true, + }); +} + +// remove antd hash on test +theme.defaultConfig.hashed = false; + +// 将 React 设置为全局变量,这样就不需要在每个测试文件中导入它了 +(global as any).React = React; diff --git a/tests/utils.tsx b/tests/utils.tsx new file mode 100644 index 00000000..6b4e0947 --- /dev/null +++ b/tests/utils.tsx @@ -0,0 +1,11 @@ +import { PropsWithChildren } from 'react'; +import { SWRConfig } from 'swr'; + +// 全局的 SWR 配置 +const swrConfig = { + provider: () => new Map(), +}; + +export const withSWR = ({ children }: PropsWithChildren) => ( + {children} +); diff --git a/tsconfig.json b/tsconfig.json index 1b9685e9..58be0817 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -1,4 +1,5 @@ { + "$schema": "https://json.schemastore.org/tsconfig", "compilerOptions": { "target": "ESNext", "lib": ["dom", "dom.iterable", "esnext"], @@ -23,6 +24,15 @@ "@/*": ["./src/*"] } }, - "include": ["next-env.d.ts", "**/*.ts", "**/*.tsx", ".next/types/**/*.ts"], - "exclude": ["node_modules"] + "exclude": ["node_modules"], + "include": [ + "next-env.d.ts", + "vitest.config.ts", + "src", + "tests", + "**/*.ts", + "**/*.d.ts", + "**/*.tsx", + ".next/types/**/*.ts" + ] } diff --git a/vercel.json b/vercel.json new file mode 100644 index 00000000..78c7b379 --- /dev/null +++ b/vercel.json @@ -0,0 +1,3 @@ +{ + "installCommand": "bun install" +} diff --git a/vitest.config.ts b/vitest.config.ts new file mode 100644 index 00000000..ab26fbb8 --- /dev/null +++ b/vitest.config.ts @@ -0,0 +1,28 @@ +import { resolve } from 'node:path'; +import { defineConfig } from 'vitest/config'; + +export default defineConfig({ + optimizeDeps: { + exclude: ['crypto', 'util', 'tty'], + include: ['@lobehub/tts'], + }, + test: { + alias: { + '@': resolve(__dirname, './src'), + '~test-utils': resolve(__dirname, './tests/utils.tsx'), + }, + coverage: { + all: false, + exclude: ['__mocks__/**'], + provider: 'v8', + reporter: ['text', 'json', 'lcov', 'text-summary'], + }, + deps: { + inline: ['vitest-canvas-mock'], + }, + // threads: false, + environment: 'jsdom', + globals: true, + setupFiles: './tests/setup.ts', + }, +});