chore: playground mutilmodel input
This commit is contained in:
@@ -143,7 +143,7 @@ export async function queryHuggingfaceModels(
|
||||
additionalFields: ['sha'],
|
||||
fetch(url: string, config: any) {
|
||||
try {
|
||||
return fetch(`${url}`, {
|
||||
return fetch(url, {
|
||||
...config,
|
||||
signal: options.signal
|
||||
});
|
||||
|
||||
@@ -308,16 +308,22 @@ const AddModal: React.FC<AddModalProps> = (props) => {
|
||||
borderRadius: '8px 0 0 8px'
|
||||
}
|
||||
}}
|
||||
width="90%"
|
||||
width={
|
||||
modelSource === modelSourceMap.huggingface_value
|
||||
? 'calc(100vw - 220px)'
|
||||
: 600
|
||||
}
|
||||
footer={false}
|
||||
>
|
||||
<div style={{ display: 'flex' }}>
|
||||
<ColumnWrapper>
|
||||
<SearchModel
|
||||
modelSource={modelSource}
|
||||
onSelectModel={handleOnSelectModel}
|
||||
></SearchModel>
|
||||
</ColumnWrapper>
|
||||
{modelSource === modelSourceMap.huggingface_value && (
|
||||
<ColumnWrapper>
|
||||
<SearchModel
|
||||
modelSource={modelSource}
|
||||
onSelectModel={handleOnSelectModel}
|
||||
></SearchModel>
|
||||
</ColumnWrapper>
|
||||
)}
|
||||
{modelSource === modelSourceMap.huggingface_value && (
|
||||
<ColumnWrapper>
|
||||
<ModelCard repo={huggingfaceRepoId}></ModelCard>
|
||||
|
||||
@@ -1,6 +1,7 @@
|
||||
import { convertFileSize } from '@/utils';
|
||||
import { SearchOutlined } from '@ant-design/icons';
|
||||
import { Button, Col, Empty, Row, Space, Spin } from 'antd';
|
||||
import { useIntl } from '@umijs/max';
|
||||
import { Col, Empty, Row, Space, Spin } from 'antd';
|
||||
import classNames from 'classnames';
|
||||
import _ from 'lodash';
|
||||
import { useEffect, useState } from 'react';
|
||||
@@ -14,6 +15,7 @@ interface HFModelFileProps {
|
||||
onSelectFile?: (file: any) => void;
|
||||
}
|
||||
const HFModelFile: React.FC<HFModelFileProps> = (props) => {
|
||||
const intl = useIntl();
|
||||
const [dataSource, setDataSource] = useState<any>({
|
||||
fileList: [],
|
||||
loading: false
|
||||
@@ -61,6 +63,13 @@ const HFModelFile: React.FC<HFModelFileProps> = (props) => {
|
||||
return null;
|
||||
};
|
||||
|
||||
const handleOnEnter = (e: any, item: any) => {
|
||||
e.stopPropagation();
|
||||
if (e.key === 'Enter') {
|
||||
handleSelectModelFile(item);
|
||||
}
|
||||
};
|
||||
|
||||
useEffect(() => {
|
||||
handleFetchModelFiles();
|
||||
}, [props.repo]);
|
||||
@@ -72,16 +81,17 @@ const HFModelFile: React.FC<HFModelFileProps> = (props) => {
|
||||
<div style={{ padding: '16px 20px' }}>
|
||||
<Spin spinning={dataSource.loading} style={{ minHeight: 100 }}>
|
||||
{dataSource.fileList.length ? (
|
||||
<Row gutter={[16, 16]}>
|
||||
<Row gutter={[16, 24]}>
|
||||
{_.map(dataSource.fileList, (item: any) => {
|
||||
return (
|
||||
<Col span={24} key={item.path}>
|
||||
<div
|
||||
tabIndex={0}
|
||||
className={classNames('hf-model-file', {
|
||||
active: item.path === current
|
||||
})}
|
||||
tabIndex={0}
|
||||
onClick={() => handleSelectModelFile(item)}
|
||||
onKeyDown={(e) => handleOnEnter(e, item)}
|
||||
>
|
||||
<div className="title">{item.path}</div>
|
||||
<Space className="tags">
|
||||
@@ -91,9 +101,15 @@ const HFModelFile: React.FC<HFModelFileProps> = (props) => {
|
||||
{getModelQuantizationType(item)}
|
||||
</Space>
|
||||
<div className="btn">
|
||||
<Button size="middle">
|
||||
{item.path === current ? 'Selected' : 'Select'}
|
||||
</Button>
|
||||
{/* <Button size="middle">
|
||||
{item.path === current
|
||||
? intl.formatMessage({
|
||||
id: 'common.button.selected'
|
||||
})
|
||||
: intl.formatMessage({
|
||||
id: 'common.button.select'
|
||||
})}
|
||||
</Button> */}
|
||||
</div>
|
||||
</div>
|
||||
</Col>
|
||||
|
||||
@@ -4,7 +4,7 @@ import {
|
||||
FolderOutlined,
|
||||
HeartOutlined
|
||||
} from '@ant-design/icons';
|
||||
import { Button, Space, Tag } from 'antd';
|
||||
import { Space, Tag } from 'antd';
|
||||
import classNames from 'classnames';
|
||||
import dayjs from 'dayjs';
|
||||
import _ from 'lodash';
|
||||
@@ -42,14 +42,12 @@ const HFModelItem: React.FC<HFModelItemProps> = (props) => {
|
||||
<Space size={16}>
|
||||
{props.task && (
|
||||
<Tag
|
||||
color="geekblue"
|
||||
style={{
|
||||
backgroundColor: 'var(--color-white-1)',
|
||||
marginRight: 0
|
||||
}}
|
||||
>
|
||||
<span style={{ color: 'var(--ant-color-text-tertiary)' }}>
|
||||
{props.task}
|
||||
</span>
|
||||
<span style={{ opacity: 0.65 }}>{props.task}</span>
|
||||
</Tag>
|
||||
)}
|
||||
<span>
|
||||
@@ -86,9 +84,9 @@ const HFModelItem: React.FC<HFModelItemProps> = (props) => {
|
||||
})}
|
||||
</Space>
|
||||
<div className="btn">
|
||||
<Button size="middle">
|
||||
{/* <Button size="middle">
|
||||
{props.active ? 'Selected' : 'Select'}
|
||||
</Button>
|
||||
</Button> */}
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import IconFont from '@/components/icon-font';
|
||||
import { downloadFile } from '@huggingface/hub';
|
||||
import { Button, Empty, Tag } from 'antd';
|
||||
import React, { useEffect, useState } from 'react';
|
||||
import { queryHuggingfaceModelDetail } from '../apis';
|
||||
@@ -9,6 +10,13 @@ const ModelCard: React.FC<{ repo: string }> = (props) => {
|
||||
const { repo } = props;
|
||||
const [modelData, setModelData] = useState<any>({});
|
||||
|
||||
const loadFile = async (repo: string, sha: string) => {
|
||||
const res = await (
|
||||
await downloadFile({ repo, revision: sha, path: 'README.md' })
|
||||
)?.text();
|
||||
return res;
|
||||
};
|
||||
|
||||
const getModelCardData = async () => {
|
||||
if (!repo) {
|
||||
setModelData(null);
|
||||
@@ -16,6 +24,12 @@ const ModelCard: React.FC<{ repo: string }> = (props) => {
|
||||
}
|
||||
try {
|
||||
const res = await queryHuggingfaceModelDetail({ repo });
|
||||
const modelConfig = await loadFile(repo, res.sha);
|
||||
console.log('modelcard=======', {
|
||||
res,
|
||||
repo,
|
||||
modelConfig
|
||||
});
|
||||
setModelData(res);
|
||||
} catch (error) {
|
||||
setModelData({});
|
||||
|
||||
@@ -1,4 +1,5 @@
|
||||
import IconFont from '@/components/icon-font';
|
||||
import { BulbOutlined } from '@ant-design/icons';
|
||||
import { useIntl } from '@umijs/max';
|
||||
import { Button, Input, Select } from 'antd';
|
||||
import _ from 'lodash';
|
||||
@@ -243,6 +244,7 @@ const SearchModel: React.FC<SearchInputProps> = (props) => {
|
||||
renderHFSearch()
|
||||
) : (
|
||||
<div style={{ lineHeight: '18px' }}>
|
||||
<BulbOutlined className="font-size-14 m-r-5" />
|
||||
{intl.formatMessage(
|
||||
{ id: 'model.form.ollamatips' },
|
||||
{ name: intl.formatMessage({ id: 'model.form.ollama.model' }) }
|
||||
|
||||
@@ -21,6 +21,12 @@ const SearchResult: React.FC<SearchResultProps> = (props) => {
|
||||
e.stopPropagation();
|
||||
onSelect?.(item);
|
||||
};
|
||||
const handleOnEnter = (e: any, item: any) => {
|
||||
e.stopPropagation();
|
||||
if (e.key === 'Enter') {
|
||||
onSelect?.(item);
|
||||
}
|
||||
};
|
||||
return (
|
||||
<div style={{ ...props.style }} className="search-result-wrap">
|
||||
<Spin spinning={props.loading}>
|
||||
@@ -29,7 +35,10 @@ const SearchResult: React.FC<SearchResultProps> = (props) => {
|
||||
<Row gutter={[16, 16]}>
|
||||
{resultList.map((item, index) => (
|
||||
<Col span={24} key={item.name}>
|
||||
<div onClick={(e) => handleSelect(e, item)}>
|
||||
<div
|
||||
onClick={(e) => handleSelect(e, item)}
|
||||
onKeyDown={(e) => handleOnEnter(e, item)}
|
||||
>
|
||||
<HFModelItem
|
||||
source={source}
|
||||
tags={item.tags}
|
||||
|
||||
@@ -4,6 +4,19 @@
|
||||
overflow-y: auto;
|
||||
overflow-x: hidden;
|
||||
border-left: 1px solid var(--ant-color-split);
|
||||
// custom scrollbar
|
||||
&::-webkit-scrollbar {
|
||||
width: 8px;
|
||||
}
|
||||
|
||||
&::-webkit-scrollbar-thumb {
|
||||
background-color: var(--ant-color-fill);
|
||||
border-radius: 4px;
|
||||
}
|
||||
|
||||
&::-webkit-scrollbar-track {
|
||||
background-color: var(--color-white-1);
|
||||
}
|
||||
}
|
||||
|
||||
.column-wrapper-footer {
|
||||
|
||||
@@ -3,18 +3,28 @@
|
||||
padding: 16px 20px;
|
||||
border-radius: 0 0 var(--border-radius-base) var(--border-radius-base);
|
||||
overflow-y: auto;
|
||||
height: calc(100vh - 194px);
|
||||
// custom scrollbar
|
||||
&::-webkit-scrollbar {
|
||||
width: 8px;
|
||||
}
|
||||
|
||||
&::-webkit-scrollbar-thumb {
|
||||
background-color: var(--ant-color-fill);
|
||||
border-radius: 4px;
|
||||
}
|
||||
|
||||
&::-webkit-scrollbar-track {
|
||||
background-color: var(--color-white-1);
|
||||
}
|
||||
}
|
||||
|
||||
.search-bar {
|
||||
position: sticky;
|
||||
top: 0;
|
||||
z-index: 100;
|
||||
left: 0;
|
||||
right: 0;
|
||||
padding-inline: 20px;
|
||||
background: var(--color-white-1);
|
||||
border-bottom: 1px solid var(--ant-color-split);
|
||||
// box-shadow: 0 1px 2px rgba(5, 5, 5, 5%);
|
||||
padding-bottom: 16px;
|
||||
|
||||
.filter {
|
||||
|
||||
Reference in New Issue
Block a user