Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Sign in / Register
Toggle navigation
N
Neos
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Locked Files
Issues
1
Issues
1
List
Boards
Labels
Service Desk
Milestones
Merge Requests
2
Merge Requests
2
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Security & Compliance
Security & Compliance
Dependency List
License Compliance
Packages
Packages
List
Container Registry
Analytics
Analytics
CI / CD
Code Review
Insights
Issues
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
MyCard
Neos
Commits
c53d5c21
Commit
c53d5c21
authored
Aug 09, 2023
by
timel
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
optimize: init
parent
21b2db98
Pipeline
#23006
passed with stages
in 14 minutes and 10 seconds
Changes
9
Pipelines
1
Hide whitespace changes
Inline
Side-by-side
Showing
9 changed files
with
135 additions
and
52 deletions
+135
-52
src/infra/eventbus.ts
src/infra/eventbus.ts
+2
-2
src/infra/index.ts
src/infra/index.ts
+2
-2
src/infra/pfetch.ts
src/infra/pfetch.ts
+35
-0
src/middleware/sqlite.ts
src/middleware/sqlite.ts
+5
-1
src/stores/initStore.ts
src/stores/initStore.ts
+1
-0
src/ui/Layout/index.module.scss
src/ui/Layout/index.module.scss
+11
-1
src/ui/Layout/index.tsx
src/ui/Layout/index.tsx
+19
-18
src/ui/Layout/utils.ts
src/ui/Layout/utils.ts
+58
-9
src/ui/Match/index.tsx
src/ui/Match/index.tsx
+2
-19
No files found.
src/infra/eventbus.ts
View file @
c53d5c21
import
{
EventEmitter
}
from
"
eventemitter3
"
;
import
{
v4
as
v4uuid
}
from
"
uuid
"
;
export
const
eventEmitter
=
new
EventEmitter
();
const
eventEmitter
=
new
EventEmitter
();
export
enum
Task
{
Move
=
"
move
"
,
// 卡片移动
...
...
@@ -13,7 +13,7 @@ export enum Task {
const
getEnd
=
(
task
:
Task
)
=>
`
${
task
}
-end`
;
/** 在组件之中注册方法 */
/** 在组件之中注册方法
,注意注册的方法一旦执行成功,必须返回一个true
*/
const
register
=
<
T
extends
unknown
[]
>
(
task
:
Task
,
fn
:
(...
args
:
T
)
=>
Promise
<
boolean
>
...
...
src/infra/index.ts
View file @
c53d5c21
// Some implementation of infrastructure
/* eslint import/export: 0 */
export
*
from
"
./console
"
;
import
"
./console
"
;
export
*
from
"
./eventbus
"
;
export
*
from
"
./pfetch
"
;
export
*
from
"
./sleep
"
;
export
*
from
"
./stream
"
;
src/infra/pfetch.ts
0 → 100644
View file @
c53d5c21
/** 在fetch的基础上,封装一个pfetch。增加一个可选的新参数,这个参数是一个回调函数,从而让外界可以感知fetch的进度(0->1),比如下载进度。 */
export
async
function
pfetch
(
input
:
RequestInfo
,
options
?:
{
init
?:
RequestInit
;
progressCallback
?:
(
progress
:
number
)
=>
void
;
}
):
Promise
<
Response
>
{
const
response
=
await
fetch
(
input
,
options
?.
init
);
const
clonedResponse
=
response
.
clone
();
// Clone the response to create a new body stream
if
(
typeof
options
?.
progressCallback
===
"
function
"
)
{
const
contentLength
=
parseInt
(
response
.
headers
.
get
(
"
content-length
"
)
||
"
0
"
,
10
);
let
bytesRead
=
0
;
const
reader
=
clonedResponse
.
body
!
.
getReader
();
while
(
true
)
{
const
{
done
,
value
}
=
await
reader
.
read
();
if
(
done
)
{
break
;
}
bytesRead
+=
value
.
length
;
const
progress
=
(
bytesRead
/
contentLength
)
*
100
;
options
?.
progressCallback
(
progress
);
}
}
return
response
;
}
src/middleware/sqlite.ts
View file @
c53d5c21
...
...
@@ -9,6 +9,7 @@ import initSqlJs, { Database } from "sql.js";
import
{
CardData
,
CardMeta
,
CardText
}
from
"
@/api/cards
"
;
import
{
useConfig
}
from
"
@/config
"
;
import
{
pfetch
}
from
"
@/infra
"
;
const
NeosConfig
=
useConfig
();
...
...
@@ -26,6 +27,7 @@ export interface sqliteAction {
// 初始化DB需要业务方传入的数据
initInfo
?:
{
dbUrl
:
string
;
progressCallback
?:
(
progress
:
number
)
=>
void
;
// 用于获取读取进度
};
// 需要读取卡牌数据的ID
payload
?:
{
...
...
@@ -51,7 +53,9 @@ export default async function (action: sqliteAction): Promise<sqliteResult> {
case
sqliteCmd
.
INIT
:
{
const
info
=
action
.
initInfo
;
if
(
info
)
{
const
dataPromise
=
fetch
(
info
.
dbUrl
).
then
((
res
)
=>
res
.
arrayBuffer
());
// TODO: i18n
const
dataPromise
=
pfetch
(
info
.
dbUrl
,
{
progressCallback
:
action
.
initInfo
?.
progressCallback
,
}).
then
((
res
)
=>
res
.
arrayBuffer
());
// TODO: i18n
const
[
SQL
,
buffer
]
=
await
Promise
.
all
([
sqlPromise
,
dataPromise
]);
YGODB
=
new
SQL
.
Database
(
new
Uint8Array
(
buffer
));
...
...
src/stores/initStore.ts
View file @
c53d5c21
...
...
@@ -8,6 +8,7 @@ export const initStore = proxy({
},
decks
:
false
,
i18n
:
false
,
wasm
:
false
,
// ...
reset
()
{},
}
satisfies
NeosStore
);
src/ui/Layout/index.module.scss
View file @
c53d5c21
...
...
@@ -10,10 +10,20 @@
.logo-container
{
align-items
:
center
;
height
:
min-content
;
padding
:
5px
10px
;
background-color
:
hsl
(
0
,
0%
,
100%
,
0
);
transition
:
0
.2s
;
border-radius
:
20px
;
.logo
{
width
:
60px
;
filter
:
brightness
(
1
.5
);
transform
:
translateY
(
1px
);
transition
:
0
.2s
;
}
&
:hover
{
background-color
:
hsl
(
0
,
0%
,
100%
,
0
.9
);
.logo
{
filter
:
invert
(
1
);
}
}
}
...
...
src/ui/Layout/index.tsx
View file @
c53d5c21
import
{
Avatar
}
from
"
antd
"
;
import
{
useEffect
}
from
"
react
"
;
import
{
type
LoaderFunction
,
NavLink
,
...
...
@@ -7,30 +8,35 @@ import {
}
from
"
react-router-dom
"
;
import
{
useSnapshot
}
from
"
valtio
"
;
import
{
CookieKeys
,
getCookie
}
from
"
@/api
"
;
import
{
useConfig
}
from
"
@/config
"
;
import
{
accountStore
,
deckStore
,
initStore
,
type
User
}
from
"
@/stores
"
;
import
{
accountStore
}
from
"
@/stores
"
;
import
styles
from
"
./index.module.scss
"
;
import
{
initSqlite
}
from
"
./utils
"
;
import
{
getLoginStatus
,
handleSSOLogin
,
initDeck
,
initSqlite
,
initWASM
,
}
from
"
./utils
"
;
const
NeosConfig
=
useConfig
();
export
const
loader
:
LoaderFunction
=
async
()
=>
{
const
user
=
getCookie
<
User
>
(
CookieKeys
.
USER
);
if
(
user
)
accountStore
.
login
(
user
);
// 加载卡组
if
(
!
initStore
.
decks
)
deckStore
.
initialize
().
then
(()
=>
(
initStore
.
decks
=
true
));
// 加载ygodb
if
(
!
initStore
.
sqlite
.
progress
)
{
initSqlite
().
then
(()
=>
(
initStore
.
sqlite
.
progress
=
1
));
initStore
.
sqlite
.
progress
=
0.01
;
}
getLoginStatus
();
initDeck
();
initSqlite
();
initWASM
();
return
null
;
};
export
const
Component
=
()
=>
{
// 捕获SSO登录
const
location
=
useLocation
();
useEffect
(()
=>
{
location
.
search
&&
handleSSOLogin
(
location
.
search
);
},
[
location
.
search
]);
// TODO 根据是否登录,显示内容
const
{
pathname
}
=
useLocation
();
const
pathnamesHideHeader
=
[
"
/waitroom
"
];
...
...
@@ -45,11 +51,6 @@ export const Component = () => {
alt=
"NEOS"
/>
</
div
>
{
/* <img
className={styles.logo}
src={`${NeosConfig.assetsPath}/neos-logo.svg`}
alt="NEOS"
/> */
}
<
NavLink
to=
"/"
>
主页
</
NavLink
>
<
NavLink
to=
"/match"
>
匹配
</
NavLink
>
<
NavLink
to=
"/build"
>
组卡
</
NavLink
>
...
...
src/ui/Layout/utils.ts
View file @
c53d5c21
import
rustInit
from
"
rust-src
"
;
import
{
CookieKeys
,
getCookie
,
setCookie
}
from
"
@/api
"
;
import
{
useConfig
}
from
"
@/config
"
;
import
{
useEnv
}
from
"
@/hook
"
;
import
sqliteMiddleWare
,
{
sqliteCmd
}
from
"
@/middleware/sqlite
"
;
import
{
initStore
}
from
"
@/stores
"
;
import
{
accountStore
,
deckStore
,
initStore
,
type
User
}
from
"
@/stores
"
;
const
{
cardsDbUrl
}
=
useConfig
();
const
{
BASE_URL
}
=
useEnv
();
/** 加载ygodb */
export
const
initSqlite
=
async
()
=>
{
const
{
sqlite
}
=
initStore
;
sqlite
.
progress
=
0.01
;
await
sqliteMiddleWare
({
cmd
:
sqliteCmd
.
INIT
,
initInfo
:
{
dbUrl
:
cardsDbUrl
},
});
sqlite
.
progress
=
1
;
if
(
!
initStore
.
sqlite
.
progress
)
{
const
{
sqlite
}
=
initStore
;
const
progressCallback
=
(
progress
:
number
)
=>
(
sqlite
.
progress
=
progress
*
0.9
);
sqlite
.
progress
=
0.01
;
await
sqliteMiddleWare
({
cmd
:
sqliteCmd
.
INIT
,
initInfo
:
{
dbUrl
:
cardsDbUrl
,
progressCallback
},
});
sqlite
.
progress
=
1
;
}
};
/** 加载卡组 */
export
const
initDeck
=
async
()
=>
{
if
(
!
initStore
.
decks
)
{
await
deckStore
.
initialize
();
initStore
.
decks
=
true
;
}
};
/** 加载WASM */
export
const
initWASM
=
async
()
=>
{
const
url
=
BASE_URL
===
"
/
"
?
undefined
:
new
URL
(
"
rust_src_bg.wasm
"
,
`
${
BASE_URL
}
assets/`
);
await
rustInit
(
url
);
initStore
.
wasm
=
true
;
};
/** sso登录跳转回来 */
export
const
handleSSOLogin
=
async
(
search
:
string
)
=>
{
/** 从SSO跳转回的URL之中,解析用户信息 */
function
getSSOUser
(
searchParams
:
URLSearchParams
):
User
{
return
Object
.
fromEntries
(
searchParams
)
as
unknown
as
User
;
}
const
sso
=
new
URLSearchParams
(
search
).
get
(
"
sso
"
);
const
user
=
sso
?
getSSOUser
(
new
URLSearchParams
(
atob
(
sso
)))
:
undefined
;
if
(
user
)
{
accountStore
.
login
(
user
);
setCookie
(
CookieKeys
.
USER
,
JSON
.
stringify
(
user
));
// TODO: toast显示登录成功
}
};
/** 从cookie获取登录态 */
export
const
getLoginStatus
=
async
()
=>
{
const
user
=
getCookie
<
User
>
(
CookieKeys
.
USER
);
if
(
user
)
accountStore
.
login
(
user
);
};
src/ui/Match/index.tsx
View file @
c53d5c21
import
{
EditFilled
,
SettingFilled
}
from
"
@ant-design/icons
"
;
import
{
Space
}
from
"
antd
"
;
import
{
useEffect
,
useState
}
from
"
react
"
;
import
{
type
LoaderFunction
,
useNavigate
}
from
"
react-router-dom
"
;
import
{
useNavigate
}
from
"
react-router-dom
"
;
import
{
useSnapshot
}
from
"
valtio
"
;
import
{
CookieKeys
,
setCookie
}
from
"
@/api
"
;
import
{
useConfig
}
from
"
@/config
"
;
import
{
accountStore
,
deckStore
,
IDeck
,
roomStore
,
type
User
}
from
"
@/stores
"
;
import
{
accountStore
,
deckStore
,
IDeck
,
roomStore
}
from
"
@/stores
"
;
import
{
Background
,
IconFont
,
Select
}
from
"
@/ui/Shared
"
;
import
styles
from
"
./index.module.scss
"
;
...
...
@@ -14,17 +13,6 @@ import { MatchModal, matchStore } from "./MatchModal";
import
{
ReplayModal
,
replayOpen
}
from
"
./ReplayModal
"
;
import
{
init
}
from
"
./util
"
;
export
const
loader
:
LoaderFunction
=
()
=>
{
const
sso
=
new
URLSearchParams
(
location
.
search
).
get
(
"
sso
"
);
const
user
=
sso
?
getSSOUser
(
new
URLSearchParams
(
atob
(
sso
)))
:
undefined
;
if
(
user
)
{
accountStore
.
login
(
user
);
setCookie
(
CookieKeys
.
USER
,
JSON
.
stringify
(
user
));
// TODO: toast显示登录成功
}
return
null
;
};
const
NeosConfig
=
useConfig
();
export
const
Component
:
React
.
FC
=
()
=>
{
...
...
@@ -150,8 +138,3 @@ const Mode: React.FC<{
<
div
className=
{
styles
.
desc
}
>
{
desc
}
</
div
>
</
div
>
);
/** 从SSO跳转回的URL之中,解析用户信息 */
function
getSSOUser
(
searchParams
:
URLSearchParams
):
User
{
return
Object
.
fromEntries
(
searchParams
)
as
unknown
as
User
;
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment