Skip to content
Toggle navigation
P
Projects
G
Groups
S
Snippets
Help
赵月辉
/
fastgpt-migrated
This project
Loading...
Sign in
Toggle navigation
Go to a project
Project
Repository
Issues
0
Merge Requests
0
Pipelines
Wiki
Snippets
Members
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Unverified
Commit
60a9dfb5
authored
Jul 17, 2023
by
archer
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
perf: bill
parent
f5460683
Hide whitespace changes
Inline
Side-by-side
Showing
10 changed files
with
129 additions
and
56 deletions
+129
-56
client/src/pages/api/openapi/modules/agent/recognizeIntention.ts
+2
-1
client/src/pages/api/openapi/modules/chat/gpt.ts
+12
-13
client/src/pages/api/openapi/modules/kb/search.ts
+2
-1
client/src/pages/api/user/update.ts
+2
-3
client/src/pages/number/components/BillDetail.tsx
+83
-0
client/src/pages/number/components/BillTable.tsx
+25
-2
client/src/pages/number/index.tsx
+0
-29
client/src/service/models/user.ts
+0
-4
client/src/types/user.d.ts
+1
-2
client/src/utils/adapt.ts
+2
-1
No files found.
client/src/pages/api/openapi/modules/agent/recognizeIntention.ts
View file @
60a9dfb5
...
...
@@ -8,6 +8,7 @@ import { ChatRoleEnum } from '@/constants/chat';
import
{
getOpenAIApi
,
axiosConfig
}
from
'@/service/ai/openai'
;
import
type
{
RecognizeIntentionAgentItemType
}
from
'@/types/app'
;
import
{
countModelPrice
,
pushTaskBillListItem
}
from
'@/service/events/pushBill'
;
import
{
getModel
}
from
'@/service/utils/data'
;
export
type
Props
=
{
systemPrompt
?:
string
;
...
...
@@ -115,7 +116,7 @@ export async function classifyQuestion({
billId
,
moduleName
:
'Recognize Intention'
,
amount
:
countModelPrice
({
model
:
agentModel
,
tokens
:
totalTokens
}),
model
:
agentModel
,
model
:
getModel
(
agentModel
)?.
name
,
tokenLen
:
totalTokens
});
...
...
client/src/pages/api/openapi/modules/chat/gpt.ts
View file @
60a9dfb5
...
...
@@ -31,21 +31,10 @@ export type Response = { [SpecificInputEnum.answerText]: string; totalTokens: nu
export
default
async
function
handler
(
req
:
NextApiRequest
,
res
:
NextApiResponse
)
{
let
{
model
,
temperature
=
0
,
stream
}
=
req
.
body
as
Props
;
try
{
// temperature adapt
const
modelConstantsData
=
getChatModel
(
model
);
if
(
!
modelConstantsData
)
{
throw
new
Error
(
'The chat model is undefined'
);
}
// FastGpt temperature range: 1~10
temperature
=
+
(
modelConstantsData
.
maxTemperature
*
(
temperature
/
10
)).
toFixed
(
2
);
const
response
=
await
chatCompletion
({
...
req
.
body
,
res
,
model
,
temperature
model
});
if
(
stream
)
{
...
...
@@ -88,6 +77,16 @@ export async function chatCompletion({
limitPrompt
=
''
,
billId
}:
Props
&
{
res
:
NextApiResponse
}):
Promise
<
Response
>
{
// temperature adapt
const
modelConstantsData
=
getChatModel
(
model
);
if
(
!
modelConstantsData
)
{
return
Promise
.
reject
(
'The chat model is undefined'
);
}
// FastGpt temperature range: 1~10
temperature
=
+
(
modelConstantsData
.
maxTemperature
*
(
temperature
/
10
)).
toFixed
(
2
);
const
messages
:
ChatItemType
[]
=
[
...(
quotePrompt
?
[
...
...
@@ -189,7 +188,7 @@ export async function chatCompletion({
billId
,
moduleName
:
'AI Chat'
,
amount
:
countModelPrice
({
model
,
tokens
:
totalTokens
}),
model
,
model
:
modelConstantsData
.
name
,
tokenLen
:
totalTokens
});
...
...
client/src/pages/api/openapi/modules/kb/search.ts
View file @
60a9dfb5
...
...
@@ -7,6 +7,7 @@ import { ChatRoleEnum } from '@/constants/chat';
import
{
modelToolMap
}
from
'@/utils/plugin'
;
import
{
getVector
}
from
'../../plugin/vector'
;
import
{
countModelPrice
,
pushTaskBillListItem
}
from
'@/service/events/pushBill'
;
import
{
getModel
}
from
'@/service/utils/data'
;
export
type
QuoteItemType
=
{
id
:
string
;
...
...
@@ -95,7 +96,7 @@ export async function kbSearch({
billId
,
moduleName
:
'Vector Generate'
,
amount
:
countModelPrice
({
model
:
vectorModel
,
tokens
:
tokenLen
}),
model
:
vectorModel
,
model
:
getModel
(
vectorModel
)?.
name
,
tokenLen
})
]);
...
...
client/src/pages/api/user/update.ts
View file @
60a9dfb5
...
...
@@ -9,7 +9,7 @@ import { UserUpdateParams } from '@/types/user';
/* 更新一些基本信息 */
export
default
async
function
handler
(
req
:
NextApiRequest
,
res
:
NextApiResponse
<
any
>
)
{
try
{
const
{
openaiKey
,
avatar
}
=
req
.
body
as
UserUpdateParams
;
const
{
avatar
}
=
req
.
body
as
UserUpdateParams
;
const
{
userId
}
=
await
authUser
({
req
,
authToken
:
true
});
...
...
@@ -20,8 +20,7 @@ export default async function handler(req: NextApiRequest, res: NextApiResponse<
_id
:
userId
},
{
...(
avatar
&&
{
avatar
}),
...(
openaiKey
!==
undefined
&&
{
openaiKey
})
...(
avatar
&&
{
avatar
})
}
);
...
...
client/src/pages/number/components/BillDetail.tsx
0 → 100644
View file @
60a9dfb5
import
React
from
'react'
;
import
{
Modal
,
ModalOverlay
,
ModalContent
,
ModalHeader
,
ModalBody
,
Flex
,
Box
,
Table
,
Thead
,
Tbody
,
Tr
,
Th
,
Td
,
TableContainer
}
from
'@chakra-ui/react'
;
import
{
UserBillType
}
from
'@/types/user'
;
import
dayjs
from
'dayjs'
;
import
{
BillSourceMap
}
from
'@/constants/user'
;
import
{
formatPrice
}
from
'@/utils/user'
;
const
BillDetail
=
({
bill
,
onClose
}:
{
bill
:
UserBillType
;
onClose
:
()
=>
void
})
=>
{
return
(
<
Modal
isOpen=
{
true
}
onClose=
{
onClose
}
isCentered
>
<
ModalOverlay
/>
<
ModalContent
minW=
{
'min(90vw,600px)'
}
>
<
ModalHeader
>
账单详情
</
ModalHeader
>
<
ModalBody
>
<
Flex
alignItems=
{
'center'
}
pb=
{
4
}
>
<
Box
flex=
{
'0 0 80px'
}
>
订单号:
</
Box
>
<
Box
>
{
bill
.
id
}
</
Box
>
</
Flex
>
<
Flex
alignItems=
{
'center'
}
pb=
{
4
}
>
<
Box
flex=
{
'0 0 80px'
}
>
生成时间:
</
Box
>
<
Box
>
{
dayjs
(
bill
.
time
).
format
(
'YYYY/MM/DD HH:mm:ss'
)
}
</
Box
>
</
Flex
>
<
Flex
alignItems=
{
'center'
}
pb=
{
4
}
>
<
Box
flex=
{
'0 0 80px'
}
>
应用名:
</
Box
>
<
Box
>
{
bill
.
appName
}
</
Box
>
</
Flex
>
<
Flex
alignItems=
{
'center'
}
pb=
{
4
}
>
<
Box
flex=
{
'0 0 80px'
}
>
来源:
</
Box
>
<
Box
>
{
BillSourceMap
[
bill
.
source
]
}
</
Box
>
</
Flex
>
<
Flex
alignItems=
{
'center'
}
pb=
{
4
}
>
<
Box
flex=
{
'0 0 80px'
}
>
总金额:
</
Box
>
<
Box
fontWeight=
{
'bold'
}
>
{
bill
.
total
}
元
</
Box
>
</
Flex
>
<
Box
pb=
{
4
}
>
<
Box
flex=
{
'0 0 80px'
}
mb=
{
1
}
>
扣费模块
</
Box
>
<
TableContainer
>
<
Table
>
<
Thead
>
<
Tr
>
<
Th
>
模块名
</
Th
>
<
Th
>
AI模型
</
Th
>
<
Th
>
Token长度
</
Th
>
<
Th
>
费用
</
Th
>
</
Tr
>
</
Thead
>
<
Tbody
>
{
bill
.
list
.
map
((
item
,
i
)
=>
(
<
Tr
key=
{
i
}
>
<
Td
>
{
item
.
moduleName
}
</
Td
>
<
Td
>
{
item
.
model
}
</
Td
>
<
Td
>
{
item
.
tokenLen
}
</
Td
>
<
Td
>
{
formatPrice
(
item
.
amount
)
}
</
Td
>
</
Tr
>
))
}
</
Tbody
>
</
Table
>
</
TableContainer
>
</
Box
>
</
ModalBody
>
</
ModalContent
>
</
Modal
>
);
};
export
default
BillDetail
;
client/src/pages/number/components/BillTable.tsx
View file @
60a9dfb5
import
React
,
{
useState
}
from
'react'
;
import
{
Table
,
Thead
,
Tbody
,
Tr
,
Th
,
Td
,
TableContainer
,
Flex
,
Box
}
from
'@chakra-ui/react'
;
import
{
Table
,
Thead
,
Tbody
,
Tr
,
Th
,
Td
,
TableContainer
,
Flex
,
Box
,
Button
}
from
'@chakra-ui/react'
;
import
{
BillSourceMap
}
from
'@/constants/user'
;
import
{
getUserBills
}
from
'@/api/user'
;
import
type
{
UserBillType
}
from
'@/types/user'
;
...
...
@@ -9,6 +20,9 @@ import dayjs from 'dayjs';
import
MyIcon
from
'@/components/Icon'
;
import
DateRangePicker
,
{
type
DateRangeType
}
from
'@/components/DateRangePicker'
;
import
{
addDays
}
from
'date-fns'
;
import
dynamic
from
'next/dynamic'
;
const
BillDetail
=
dynamic
(()
=>
import
(
'./BillDetail'
));
const
BillTable
=
()
=>
{
const
{
Loading
}
=
useLoading
();
...
...
@@ -30,6 +44,8 @@ const BillTable = () => {
}
});
const
[
billDetail
,
setBillDetail
]
=
useState
<
UserBillType
>
();
return
(
<>
<
TableContainer
position=
{
'relative'
}
minH=
{
'100px'
}
>
...
...
@@ -39,7 +55,8 @@ const BillTable = () => {
<
Th
>
时间
</
Th
>
<
Th
>
来源
</
Th
>
<
Th
>
应用名
</
Th
>
<
Th
>
金额
</
Th
>
<
Th
>
总金额
</
Th
>
<
Th
></
Th
>
</
Tr
>
</
Thead
>
<
Tbody
fontSize=
{
'sm'
}
>
...
...
@@ -49,6 +66,11 @@ const BillTable = () => {
<
Td
>
{
BillSourceMap
[
item
.
source
]
}
</
Td
>
<
Td
>
{
item
.
appName
||
'-'
}
</
Td
>
<
Td
>
{
item
.
total
}
元
</
Td
>
<
Td
>
<
Button
size=
{
'sm'
}
variant=
{
'base'
}
onClick=
{
()
=>
setBillDetail
(
item
)
}
>
详情
</
Button
>
</
Td
>
</
Tr
>
))
}
</
Tbody
>
...
...
@@ -75,6 +97,7 @@ const BillTable = () => {
</
Box
>
</
Flex
>
<
Loading
loading=
{
isLoading
}
fixed=
{
false
}
/>
{
!!
billDetail
&&
<
BillDetail
bill=
{
billDetail
}
onClose=
{
()
=>
setBillDetail
(
undefined
)
}
/>
}
</>
);
};
...
...
client/src/pages/number/index.tsx
View file @
60a9dfb5
...
...
@@ -83,20 +83,10 @@ const NumberSetting = ({ tableType }: { tableType: `${TableEnum}` }) => {
async
(
data
:
UserUpdateParams
)
=>
{
setLoading
(
true
);
try
{
if
(
data
.
openaiKey
)
{
const
text
=
await
authOpenAiKey
(
data
.
openaiKey
);
text
&&
toast
({
title
:
text
,
status
:
'warning'
});
}
await
putUserInfo
({
openaiKey
:
data
.
openaiKey
,
avatar
:
data
.
avatar
});
updateUserInfo
({
openaiKey
:
data
.
openaiKey
,
avatar
:
data
.
avatar
});
reset
(
data
);
...
...
@@ -193,25 +183,7 @@ const NumberSetting = ({ tableType }: { tableType: `${TableEnum}` }) => {
充值
</
Button
>
</
Flex
>
<
Box
fontSize=
{
'xs'
}
color=
{
'blackAlpha.500'
}
>
如果填写了自己的 openai 账号,网页上 openai 模型对话不会计费。
</
Box
>
</
Box
>
<
Flex
mt=
{
6
}
alignItems=
{
'center'
}
>
<
Box
flex=
{
'0 0 85px'
}
>
openaiKey:
</
Box
>
<
Input
{
...
register
(`
openaiKey
`)}
maxW=
{
'350px'
}
placeholder=
{
'openai账号。回车或失去焦点保存'
}
size=
{
'sm'
}
onBlur=
{
handleSubmit
(
onclickSave
)
}
onKeyDown=
{
(
e
)
=>
{
if
(
e
.
keyCode
===
13
)
{
handleSubmit
(
onclickSave
)();
}
}
}
></
Input
>
</
Flex
>
</
Card
>
<
Card
px=
{
6
}
py=
{
4
}
>
<
Box
fontSize=
{
'xl'
}
fontWeight=
{
'bold'
}
>
...
...
@@ -220,7 +192,6 @@ const NumberSetting = ({ tableType }: { tableType: `${TableEnum}` }) => {
{
[
{
label
:
'佣金比例'
,
value
:
`${userInfo?.promotion.rate || 15}%`
},
{
label
:
'已注册用户数'
,
value
:
`${invitedAmount}人`
},
{
label
:
'累计佣金'
,
value
:
`¥${historyAmount}`
},
{
label
:
'可用佣金'
,
value
:
`¥${residueAmount}`
}
].
map
((
item
)
=>
(
<
Flex
key=
{
item
.
label
}
alignItems=
{
'center'
}
mt=
{
4
}
justifyContent=
{
'space-between'
}
>
...
...
client/src/service/models/user.ts
View file @
60a9dfb5
...
...
@@ -42,10 +42,6 @@ const UserSchema = new Schema({
default
:
15
}
},
openaiKey
:
{
type
:
String
,
default
:
''
},
limit
:
{
exportKbTime
:
{
// Every half hour
...
...
client/src/types/user.d.ts
View file @
60a9dfb5
...
...
@@ -4,7 +4,6 @@ export interface UserType {
_id
:
string
;
username
:
string
;
avatar
:
string
;
openaiKey
:
string
;
balance
:
number
;
promotion
:
{
rate
:
number
;
...
...
@@ -14,7 +13,6 @@ export interface UserType {
export
interface
UserUpdateParams
{
balance
?:
number
;
avatar
?:
string
;
openaiKey
?:
string
;
}
export
interface
UserBillType
{
...
...
@@ -23,4 +21,5 @@ export interface UserBillType {
appName
:
string
;
source
:
BillSchema
[
'source'
];
total
:
number
;
list
:
BillSchema
[
'list'
];
}
client/src/utils/adapt.ts
View file @
60a9dfb5
...
...
@@ -18,7 +18,8 @@ export const adaptBill = (bill: BillSchema): UserBillType => {
source
:
bill
.
source
,
time
:
bill
.
time
,
total
:
formatPrice
(
bill
.
total
),
appName
:
bill
.
appName
appName
:
bill
.
appName
,
list
:
bill
.
list
};
};
...
...
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