| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340 |
- <template>
- <div class="model-container">
- <!-- 模型选择下拉菜单 -->
- <el-dropdown
- @command="handleModelTypeChange"
- trigger="click"
- :hide-on-click="true"
- style="margin-bottom: 5px"
- >
- <span class="el-dropdown-link">
- {{ selectedModelTypeLabel
- }}<el-icon class="el-icon--right"><ArrowDown /></el-icon>
- </span>
- <template #dropdown>
- <el-dropdown-menu>
- <el-dropdown-item
- v-for="type in modelTypes"
- :key="type.value"
- :command="type.value"
- :disabled="selectedModelType === type.value"
- >
- {{ type.label }}
- </el-dropdown-item>
- </el-dropdown-menu>
- </template>
- </el-dropdown>
- <!-- 加载失败提示 -->
- <el-alert
- v-if="errorOccurred"
- :title="`加载数据失败: ${errorMessage}`"
- type="error"
- show-icon
- style="margin-bottom: 5px"
- />
- <!-- 动态加载的模型信息按表格显示 -->
- <el-table
- v-if="selectedModelType && filteredModels.length > 0 && !loading"
- :data="pagedFilteredModels"
- style="width: 100%"
- border
- height="calc(100vh - 300px)"
- >
- <el-table-column prop="ModelID" label="序号" min-width="80" />
- <el-table-column prop="Model_name" label="模型名称" min-width="180" />
- <el-table-column prop="Data_type" label="数据类型" min-width="120" />
- <el-table-column
- prop="Performance_score"
- label="性能评分"
- min-width="120"
- />
- <el-table-column prop="Created_at" label="创建时间" min-width="180" />
- <el-table-column label="操作" min-width="100">
- <template #default="scope">
- <el-button size="small" @click="selectModel(scope.row)"
- >选择</el-button
- >
- </template>
- </el-table-column>
- </el-table>
- <!-- 分页控制 -->
- <div
- class="demo-pagination-block"
- v-if="selectedModelType && filteredModels.length > 0"
- style="text-align: center; margin-top: 20px"
- >
- <el-pagination
- v-model:current-page="currentPage"
- v-model:page-size="pageSize"
- :page-sizes="[10, 20, 30, 40]"
- layout="total, sizes, prev, pager, next, jumper"
- :total="filteredModels.length"
- @size-change="handleSizeChange"
- @current-change="handleCurrentChange"
- />
- </div>
- <!-- 当没有选择任何模型类型时显示提示信息 -->
- <div
- v-if="!selectedModelType && !loading && !errorOccurred"
- style="text-align: center; padding-top: 5px"
- >
- 请选择一个模型类型以查看详细信息。
- </div>
- <!-- 当筛选结果为空时显示提示信息 -->
- <div
- v-if="
- selectedModelType &&
- filteredModels.length === 0 &&
- !loading &&
- !errorOccurred
- "
- style="text-align: center; padding-top: 5px"
- >
- 没有找到与所选模型类型匹配的数据。
- </div>
- </div>
- </template>
- <script lang="ts" setup>
- import { ref, onMounted, computed } from "vue";
- import axios from "axios";
- import { ElMessage, ElMessageBox } from "element-plus";
- import { ArrowDown } from "@element-plus/icons-vue";
- import { table } from "@/API/menus";
- interface ModelData {
- ModelID: number;
- Model_name: string;
- Model_type: string;
- Created_at: string;
- Description: string;
- DatasetID: string;
- ModelFilePath: string;
- Data_type: string;
- Performance_score: number;
- MAE: number;
- RMSE: number;
- CV_score: string;
- }
- interface Dataset {
- id: any;
- name: string;
- description: string;
- type: string;
- count: number;
- status: string;
- uploadTime: string;
- selected: boolean;
- }
- const loading = ref(true);
- const allModels = ref<ModelData[]>([]);
- const rows = ref<Dataset[]>([]);
- const selectedModelType = ref<string>("");
- const selectedModelTypeLabel = ref<string>("请选择模型类型");
- const selectedModel = ref<ModelData | null>(null);
- const errorOccurred = ref(false);
- const errorMessage = ref("");
- const modelTypes = [
- { value: "reduce", label: "降酸模型(Reduce Model)" },
- { value: "reflux", label: "反酸模型(Reflux Model)" },
- ];
- // 分页相关
- const currentPage = ref(1);
- const pageSize = ref(10);
- // 获取所有模型
- const fetchAllModels = async () => {
- try {
- const requestBody = { table: "Models" };
- const response = await table(requestBody);
- allModels.value = response.data.rows.map((row: any) => ({
- ...row,
- selected: false,
- }));
- } catch (error) {
- let msg = "未知错误";
- if (error && typeof error === "object" && "message" in error)
- msg = (error as any).message || msg;
- console.error("Error fetching models:", msg);
- ElMessage.error("数据加载失败:" + msg);
- errorOccurred.value = true;
- errorMessage.value = msg;
- } finally {
- loading.value = false;
- }
- };
- // 获取所有数据集
- const fetchData = async () => {
- try {
- const response = await table({ table: "Datasets" });
- return response.data.rows;
- } catch (error) {
- let msg = "未知错误";
- if (error && typeof error === "object" && "message" in error)
- msg = (error as any).message || msg;
- console.error("Error fetching datasets:", msg);
- throw new Error(msg);
- }
- };
- // 加载数据集
- const LoadData = async () => {
- try {
- rows.value = (await fetchData()).map((row: any) => ({
- id: row.Dataset_ID,
- name: row.Dataset_name,
- description: row.Dataset_description,
- type: row.Dataset_type,
- count: row.Row_count,
- status: row.Status,
- uploadTime: row.Uploaded_at,
- selected: false,
- }));
- } catch (error) {
- let msg = "未知错误";
- if (error && typeof error === "object" && "message" in error)
- msg = (error as any).message || msg;
- console.error("Error loading datasets:", msg);
- ElMessage.error("数据加载失败:" + msg);
- errorOccurred.value = true;
- errorMessage.value = msg;
- } finally {
- loading.value = false;
- }
- };
- // 过滤模型
- const filteredModels = computed(() => {
- if (!selectedModelType.value) return [];
- return allModels.value.filter((m) => m.Data_type === selectedModelType.value);
- });
- // 分页后的模型
- const pagedFilteredModels = computed(() => {
- const start = (currentPage.value - 1) * pageSize.value;
- return filteredModels.value.slice(start, start + pageSize.value);
- });
- // 切换模型类型
- const handleModelTypeChange = async (value: string) => {
- selectedModelType.value = value;
- const selectedType = modelTypes.find((t) => t.value === value);
- if (selectedType) selectedModelTypeLabel.value = selectedType.label;
- selectedModel.value = null;
- currentPage.value = 1;
- // 尝试恢复上次保存的模型
- try {
- const resp = await axios.get(
- `https://www.soilgd.com:5000/model-selection?model_type=${value}`
- ); //https://www.soilgd.com:5000
- if (resp.data && resp.data.data && resp.data.data.model_id) {
- const found = allModels.value.find(
- (m) => m.ModelID === resp.data.data.model_id
- );
- if (found) {
- selectedModel.value = found;
- ElMessage.info(`已恢复上次选择的模型:${found.Model_name}`);
- }
- }
- } catch (e) {
- console.warn("恢复上次模型失败", e);
- }
- };
- // 选择并保存模型(弹框确认)
- const selectModel = async (model: ModelData) => {
- try {
- await ElMessageBox.confirm(
- `确认选择模型:${model.ModelID} 吗?`,
- "确认操作",
- { confirmButtonText: "确定", cancelButtonText: "取消", type: "warning" }
- );
- selectedModel.value = model;
- //https://www.soilgd.com:5000
- await axios.post("https://www.soilgd.com:5000/model-selection", {
- model_type: selectedModelType.value,
- model_id: model.ModelID,
- model_name: model.Model_name,
- });
- ElMessage.success(`已保存选中模型:${model.Model_name}`);
- } catch (error) {
- if (error !== "cancel" && error !== "close") {
- let msg = "未知错误";
- if (error && typeof error === "object" && "message" in error)
- msg = (error as any).message || msg;
- console.error("保存模型失败:", msg);
- ElMessage.error("保存失败:" + msg);
- }
- }
- };
- // 分页事件
- const handleSizeChange = (val: number) => (pageSize.value = val);
- const handleCurrentChange = (val: number) => (currentPage.value = val);
- onMounted(() => {
- fetchAllModels();
- LoadData();
- });
- </script>
- <style scoped>
- .model-container {
- display: grid;
- gap: 10px;
- padding: 10px;
- background-color: #f9fafb;
- border-radius: 8px;
- box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
- height: 100%;
- }
- .example-showcase .el-dropdown-link {
- cursor: pointer;
- color: var(--el-color-primary);
- display: flex;
- align-items: center;
- }
- .el-popper.is-light {
- border: none !important;
- box-shadow: 0 2px 12px 0 rgba(0, 0, 0, 0.1);
- }
- .el-table {
- width: 100%;
- margin-top: 10px;
- border-radius: 8px;
- }
- :deep(.el-table th) {
- background-color: #61e054 !important;
- color: #fff;
- }
- :deep(.el-table td),
- :deep(.el-table th) {
- padding: 8px 0;
- }
- :deep(.el-table__row:nth-child(odd)) {
- background-color: #e4fbe5 !important;
- }
- :deep(.el-dropdown-menu__item.is-disabled) {
- color: #c0c4cc !important;
- cursor: not-allowed !important;
- }
- </style>
|