|
|
@@ -4,323 +4,355 @@
|
|
|
</el-affix>
|
|
|
<el-affix :offset="44">
|
|
|
<div class="application-overview">
|
|
|
- <!-- 右侧主内容区 -->
|
|
|
- <div class="main-content">
|
|
|
- <div style="display: flex; justify-content: space-between; padding-right: 30px">
|
|
|
- <!-- 搜索栏 -->
|
|
|
- <div class="search-bar">
|
|
|
- <el-input placeholder="输入搜索关键词" v-model="searchStr" class="search-input">
|
|
|
- </el-input>
|
|
|
- <el-button type="primary" class="search-btn" @click="searchServerList">搜索</el-button>
|
|
|
- <!-- <span>搜索到{{total}}条微功能服务</span> -->
|
|
|
- </div>
|
|
|
+ <div class="wgn-body">
|
|
|
+ <aside class="wgn-side-nav" aria-label="微功能锚点导航">
|
|
|
+ <button
|
|
|
+ v-for="block in groupedWgnSections"
|
|
|
+ :key="block.cat.value"
|
|
|
+ type="button"
|
|
|
+ class="wgn-anchor"
|
|
|
+ :class="{ active: activeAnchorId === block.cat.value }"
|
|
|
+ @click="scrollToAnchor(block.cat.value)"
|
|
|
+ >
|
|
|
+ {{ block.cat.label }}
|
|
|
+ </button>
|
|
|
+ </aside>
|
|
|
+ <!-- 右侧主内容区 -->
|
|
|
+ <div class="main-content">
|
|
|
+ <div style="display: flex; justify-content: space-between; padding-right: 30px">
|
|
|
+ <!-- 搜索栏 -->
|
|
|
+ <div class="search-bar">
|
|
|
+ <el-input
|
|
|
+ placeholder="输入搜索关键词"
|
|
|
+ v-model="searchStr"
|
|
|
+ class="search-input"
|
|
|
+ clearable
|
|
|
+ @clear="searchServerList"
|
|
|
+ @keyup.enter="searchServerList"
|
|
|
+ >
|
|
|
+ </el-input>
|
|
|
+ <el-button type="primary" class="search-btn" @click="searchServerList"
|
|
|
+ >搜索</el-button
|
|
|
+ >
|
|
|
+ <!-- <span>搜索到{{total}}条微功能服务</span> -->
|
|
|
+ </div>
|
|
|
|
|
|
- <div>
|
|
|
- <el-button
|
|
|
- v-if="$getUserType() != 1"
|
|
|
- type="primary"
|
|
|
- class="search-btn"
|
|
|
- @click="createTask"
|
|
|
- >大批量数据处理任务</el-button
|
|
|
- >
|
|
|
+ <div>
|
|
|
+ <el-button
|
|
|
+ v-if="$getUserType() != 1"
|
|
|
+ type="primary"
|
|
|
+ class="search-btn"
|
|
|
+ @click="createTask"
|
|
|
+ >大批量数据处理任务</el-button
|
|
|
+ >
|
|
|
+ </div>
|
|
|
</div>
|
|
|
- </div>
|
|
|
|
|
|
- <!-- 应用卡片网格 -->
|
|
|
- <div class="wgn-content">
|
|
|
- <div class="applications-grid">
|
|
|
- <div class="application-card" v-for="(item, index) in dmsServerList" :key="index">
|
|
|
- <div class="card-image">
|
|
|
- <img :src="curUrl + item.c_picture" :alt="item.title" />
|
|
|
- </div>
|
|
|
- <div class="card-content">
|
|
|
- <div class="wgn-header">
|
|
|
- <h3 class="wgn-name">{{ item.title }}</h3>
|
|
|
- <!-- <span class="wgn-version">{{ item.version }}</span> -->
|
|
|
- </div>
|
|
|
- <!-- <div class="wgn-tags">
|
|
|
- <el-tag size="small" type="success">{{ item.buffName }}</el-tag>
|
|
|
- <el-tag size="small" v-for="tag in item.tags" :key="tag">{{ tag }}</el-tag>
|
|
|
- </div> -->
|
|
|
- <el-tooltip placement="top" effect="dark">
|
|
|
- <template #content>
|
|
|
- <div style="max-width: 500px">{{ item.content }}</div>
|
|
|
- </template>
|
|
|
- <p class="wgn-description">{{ item.content }}</p>
|
|
|
- </el-tooltip>
|
|
|
- <div class="wgn-footer">
|
|
|
- <!-- <span class="wgn-date">{{ item.createTime }}</span> -->
|
|
|
- <el-button
|
|
|
- type="primary"
|
|
|
- size="small"
|
|
|
- class="visit-button"
|
|
|
- @click="handleOnlineDemo(item)"
|
|
|
- >在线体验</el-button
|
|
|
- >
|
|
|
- <el-button
|
|
|
- type="primary"
|
|
|
- size="small"
|
|
|
- class="visit-button"
|
|
|
- @click="handleApply(item)"
|
|
|
- >申请使用</el-button
|
|
|
+ <!-- 应用卡片:按一级场景分组,锚点滚动 -->
|
|
|
+ <div class="wgn-content" ref="wgnScrollRoot">
|
|
|
+ <template v-if="groupedWgnSections.length">
|
|
|
+ <section
|
|
|
+ v-for="block in groupedWgnSections"
|
|
|
+ :key="block.cat.value"
|
|
|
+ :id="sectionDomId(block.cat.value)"
|
|
|
+ class="wgn-anchor-section"
|
|
|
+ >
|
|
|
+ <h2 class="wgn-anchor-section-title">{{ block.cat.label }}</h2>
|
|
|
+ <div class="applications-grid">
|
|
|
+ <div
|
|
|
+ class="application-card"
|
|
|
+ v-for="(item, index) in block.items"
|
|
|
+ :key="(item.c_scene_name || '') + '-' + index"
|
|
|
>
|
|
|
+ <div class="card-image">
|
|
|
+ <img :src="curUrl + item.c_picture" :alt="item.title" />
|
|
|
+ </div>
|
|
|
+ <div class="card-content">
|
|
|
+ <div class="wgn-header">
|
|
|
+ <h3 class="wgn-name">{{ item.title }}</h3>
|
|
|
+ </div>
|
|
|
+ <el-tooltip placement="top" effect="dark">
|
|
|
+ <template #content>
|
|
|
+ <div style="max-width: 500px">{{ item.content }}</div>
|
|
|
+ </template>
|
|
|
+ <p class="wgn-description">{{ item.content }}</p>
|
|
|
+ </el-tooltip>
|
|
|
+ <div class="wgn-footer">
|
|
|
+ <el-button
|
|
|
+ type="primary"
|
|
|
+ size="small"
|
|
|
+ class="visit-button"
|
|
|
+ @click="handleOnlineDemo(item)"
|
|
|
+ >在线体验</el-button
|
|
|
+ >
|
|
|
+ <el-button
|
|
|
+ type="primary"
|
|
|
+ size="small"
|
|
|
+ class="visit-button"
|
|
|
+ @click="handleApply(item)"
|
|
|
+ >申请使用</el-button
|
|
|
+ >
|
|
|
+ </div>
|
|
|
+ </div>
|
|
|
+ </div>
|
|
|
</div>
|
|
|
- </div>
|
|
|
- </div>
|
|
|
+ </section>
|
|
|
+ </template>
|
|
|
+ <el-empty v-else description="暂无数据" />
|
|
|
</div>
|
|
|
- </div>
|
|
|
|
|
|
- <!-- 申请使用微功能服务的表单弹窗 -->
|
|
|
- <el-dialog
|
|
|
- title="申请使用微功能服务"
|
|
|
- v-model="showFrom"
|
|
|
- width="60%"
|
|
|
- :close-on-click-modal="false"
|
|
|
- :close-on-press-escape="false"
|
|
|
- :show-close="true"
|
|
|
- >
|
|
|
- <el-form :model="column.from" :rules="rules" ref="formRef" label-width="120px">
|
|
|
- <el-form-item label="应用名称" prop="c_application_name">
|
|
|
- <el-input v-model="column.from.c_application_name" placeholder="请输入应用名称" />
|
|
|
- </el-form-item>
|
|
|
- <el-form-item label="接口路径" prop="c_interface_path">
|
|
|
- <el-input
|
|
|
- v-model="column.from.c_interface_path"
|
|
|
- disabled
|
|
|
- placeholder="请输入接口路径"
|
|
|
- />
|
|
|
- </el-form-item>
|
|
|
- <el-form-item label="联系电话" prop="c_phone">
|
|
|
- <el-input v-model="column.from.c_phone" placeholder="请输入联系电话" />
|
|
|
- </el-form-item>
|
|
|
- <el-form-item label="单位名称" prop="c_unit_name">
|
|
|
- <el-input v-model="column.from.c_unit_name" placeholder="请输入单位名称" />
|
|
|
- </el-form-item>
|
|
|
- <el-form-item label="部门名称" prop="c_department">
|
|
|
- <el-input v-model="column.from.c_department" placeholder="请输入部门名称" />
|
|
|
- </el-form-item>
|
|
|
- <!-- 项目负责人 -->
|
|
|
- <el-form-item label="项目负责人" prop="c_business_leader">
|
|
|
- <el-input v-model="column.from.c_business_leader" placeholder="请输入项目负责人" />
|
|
|
- </el-form-item>
|
|
|
- <!-- 申请使用微功能服务的详细信息 -->
|
|
|
- <el-form-item label="申请使用微功能服务的详细信息" prop="content">
|
|
|
- <el-input
|
|
|
- type="textarea"
|
|
|
- v-model="column.from.content"
|
|
|
- placeholder="请输入申请使用微功能服务的详细信息"
|
|
|
- />
|
|
|
- </el-form-item>
|
|
|
- </el-form>
|
|
|
- <template #footer>
|
|
|
- <div class="dialog-footer">
|
|
|
- <el-button @click="showFrom = false">取消</el-button>
|
|
|
- <el-button type="primary" @click="handleApplySubmit">确定</el-button>
|
|
|
- </div>
|
|
|
- </template>
|
|
|
- </el-dialog>
|
|
|
- <!-- 创建任务的表单弹窗 -->
|
|
|
- <el-dialog
|
|
|
- title="创建任务"
|
|
|
- v-model="showTaskFrom"
|
|
|
- width="60%"
|
|
|
- :close-on-click-modal="false"
|
|
|
- :close-on-press-escape="false"
|
|
|
- :show-close="true"
|
|
|
- >
|
|
|
- <el-form
|
|
|
- :model="taskColumn.from"
|
|
|
- :rules="taskColumn.rules"
|
|
|
- ref="taskFormRef"
|
|
|
- label-width="120px"
|
|
|
+ <!-- 申请使用微功能服务的表单弹窗 -->
|
|
|
+ <el-dialog
|
|
|
+ title="申请使用微功能服务"
|
|
|
+ v-model="showFrom"
|
|
|
+ width="60%"
|
|
|
+ :close-on-click-modal="false"
|
|
|
+ :close-on-press-escape="false"
|
|
|
+ :show-close="true"
|
|
|
>
|
|
|
- <el-form-item label="任务名称" prop="c_name">
|
|
|
- <el-input v-model="taskColumn.from.c_name" placeholder="请输入任务名称" clearable>
|
|
|
- <template #prepend>{{
|
|
|
- $moment(new Date()).format("YYMMDD_HHmm") +
|
|
|
- "_" +
|
|
|
- (taskColumn.from.c_type
|
|
|
- ? $getDmsTypes("yzt_task_type", taskColumn.from.c_type) + "_"
|
|
|
- : "")
|
|
|
- }}</template>
|
|
|
- </el-input>
|
|
|
- </el-form-item>
|
|
|
- <el-form-item label="任务备注" prop="c_comment">
|
|
|
- <el-input
|
|
|
- type="textarea"
|
|
|
- clearable
|
|
|
- v-model="taskColumn.from.c_comment"
|
|
|
- placeholder="请输入任务备注"
|
|
|
- />
|
|
|
- </el-form-item>
|
|
|
- <!-- 下拉框选择任务类型 -->
|
|
|
- <el-form-item label="任务类型" prop="c_type">
|
|
|
- <el-select
|
|
|
- v-model="taskColumn.from.c_type"
|
|
|
- @change="changeTaskType"
|
|
|
- placeholder="请选择任务类型"
|
|
|
- >
|
|
|
- <el-option
|
|
|
- v-for="(name, index) in $store.state.DmsTypesMap['yzt_task_type']"
|
|
|
- :key="index"
|
|
|
- :label="name"
|
|
|
- :value="index"
|
|
|
+ <el-form :model="column.from" :rules="rules" ref="formRef" label-width="120px">
|
|
|
+ <el-form-item label="应用名称" prop="c_application_name">
|
|
|
+ <el-input v-model="column.from.c_application_name" placeholder="请输入应用名称" />
|
|
|
+ </el-form-item>
|
|
|
+ <el-form-item label="接口路径" prop="c_interface_path">
|
|
|
+ <el-input
|
|
|
+ v-model="column.from.c_interface_path"
|
|
|
+ disabled
|
|
|
+ placeholder="请输入接口路径"
|
|
|
/>
|
|
|
- </el-select>
|
|
|
- </el-form-item>
|
|
|
- <!-- 渲染任务描述:仅查看 -->
|
|
|
- <el-form-item
|
|
|
- label="任务描述"
|
|
|
- prop="apiDescription"
|
|
|
- v-if="taskColumn.apiFrom.apiDescription"
|
|
|
- >
|
|
|
- <el-input type="textarea" disabled v-model="taskColumn.apiFrom.apiDescription" />
|
|
|
- </el-form-item>
|
|
|
- <!-- 任务文件是必须的 -->
|
|
|
- <el-form-item label="任务文件" prop="c_source_file">
|
|
|
- <el-input disabled v-model="taskColumn.from.c_source_file" v-show="false" />
|
|
|
- <el-upload class="avatar-uploader" :http-request="handleTCUpload" :limit="1">
|
|
|
- <el-button size="small" type="primary">点击上传</el-button>
|
|
|
- </el-upload>
|
|
|
- </el-form-item>
|
|
|
- <el-divider />
|
|
|
- <!-- 其他参数数据 -->
|
|
|
- <el-form-item label="其他参数数据" prop="c_source_data" v-show="false">
|
|
|
- <el-input
|
|
|
- type="textarea"
|
|
|
- clearable
|
|
|
- v-model="taskColumn.from.c_source_data"
|
|
|
- placeholder="请输入其他参数数据"
|
|
|
- />
|
|
|
- </el-form-item>
|
|
|
- <div
|
|
|
- v-if="
|
|
|
- taskColumn.apiFrom.apiParameterRules &&
|
|
|
- includesKey([
|
|
|
- 'lonKey',
|
|
|
- 'latKey',
|
|
|
- 'outFileType',
|
|
|
- 'inPrj',
|
|
|
- 'outPrj',
|
|
|
- 'compressionRatio',
|
|
|
- 'keyType',
|
|
|
- 'geocodeColumnKeyword',
|
|
|
- ])
|
|
|
- "
|
|
|
+ </el-form-item>
|
|
|
+ <el-form-item label="联系电话" prop="c_phone">
|
|
|
+ <el-input v-model="column.from.c_phone" placeholder="请输入联系电话" />
|
|
|
+ </el-form-item>
|
|
|
+ <el-form-item label="单位名称" prop="c_unit_name">
|
|
|
+ <el-input v-model="column.from.c_unit_name" placeholder="请输入单位名称" />
|
|
|
+ </el-form-item>
|
|
|
+ <el-form-item label="部门名称" prop="c_department">
|
|
|
+ <el-input v-model="column.from.c_department" placeholder="请输入部门名称" />
|
|
|
+ </el-form-item>
|
|
|
+ <!-- 项目负责人 -->
|
|
|
+ <el-form-item label="项目负责人" prop="c_business_leader">
|
|
|
+ <el-input v-model="column.from.c_business_leader" placeholder="请输入项目负责人" />
|
|
|
+ </el-form-item>
|
|
|
+ <!-- 申请使用微功能服务的详细信息 -->
|
|
|
+ <el-form-item label="申请使用微功能服务的详细信息" prop="content">
|
|
|
+ <el-input
|
|
|
+ type="textarea"
|
|
|
+ v-model="column.from.content"
|
|
|
+ placeholder="请输入申请使用微功能服务的详细信息"
|
|
|
+ />
|
|
|
+ </el-form-item>
|
|
|
+ </el-form>
|
|
|
+ <template #footer>
|
|
|
+ <div class="dialog-footer">
|
|
|
+ <el-button @click="showFrom = false">取消</el-button>
|
|
|
+ <el-button type="primary" @click="handleApplySubmit">确定</el-button>
|
|
|
+ </div>
|
|
|
+ </template>
|
|
|
+ </el-dialog>
|
|
|
+ <!-- 创建任务的表单弹窗 -->
|
|
|
+ <el-dialog
|
|
|
+ title="创建任务"
|
|
|
+ v-model="showTaskFrom"
|
|
|
+ width="60%"
|
|
|
+ :close-on-click-modal="false"
|
|
|
+ :close-on-press-escape="false"
|
|
|
+ :show-close="true"
|
|
|
+ >
|
|
|
+ <el-form
|
|
|
+ :model="taskColumn.from"
|
|
|
+ :rules="taskColumn.rules"
|
|
|
+ ref="taskFormRef"
|
|
|
+ label-width="120px"
|
|
|
>
|
|
|
- <template
|
|
|
- v-for="(rulesItem, index) in taskColumn.apiFrom.apiParameterRules"
|
|
|
- :key="index"
|
|
|
- >
|
|
|
- <el-form-item
|
|
|
- v-if="
|
|
|
- [
|
|
|
- 'lonKey',
|
|
|
- 'latKey',
|
|
|
- 'outFileType',
|
|
|
- 'inPrj',
|
|
|
- 'outPrj',
|
|
|
- 'compressionRatio',
|
|
|
- 'keyType',
|
|
|
- 'geocodeColumnKeyword',
|
|
|
- ].includes(rulesItem)
|
|
|
- "
|
|
|
- :label="
|
|
|
- rulesItem === 'keyType'
|
|
|
- ? '类型字段'
|
|
|
- : rulesItem === 'geocodeColumnKeyword'
|
|
|
- ? '数据列名'
|
|
|
- : rulesItem
|
|
|
- "
|
|
|
+ <el-form-item label="任务名称" prop="c_name">
|
|
|
+ <el-input v-model="taskColumn.from.c_name" placeholder="请输入任务名称" clearable>
|
|
|
+ <template #prepend>{{
|
|
|
+ $moment(new Date()).format("YYMMDD_HHmm") +
|
|
|
+ "_" +
|
|
|
+ (taskColumn.from.c_type
|
|
|
+ ? $getDmsTypes("yzt_task_type", taskColumn.from.c_type) + "_"
|
|
|
+ : "")
|
|
|
+ }}</template>
|
|
|
+ </el-input>
|
|
|
+ </el-form-item>
|
|
|
+ <el-form-item label="任务备注" prop="c_comment">
|
|
|
+ <el-input
|
|
|
+ type="textarea"
|
|
|
+ clearable
|
|
|
+ v-model="taskColumn.from.c_comment"
|
|
|
+ placeholder="请输入任务备注"
|
|
|
+ />
|
|
|
+ </el-form-item>
|
|
|
+ <!-- 下拉框选择任务类型 -->
|
|
|
+ <el-form-item label="任务类型" prop="c_type">
|
|
|
+ <el-select
|
|
|
+ v-model="taskColumn.from.c_type"
|
|
|
+ @change="changeTaskType"
|
|
|
+ placeholder="请选择任务类型"
|
|
|
>
|
|
|
- <el-input
|
|
|
- v-if="['lonKey', 'latKey'].includes(rulesItem)"
|
|
|
- v-model="taskColumn.from.c_source_data[rulesItem]"
|
|
|
- placeholder="当文件为xlsx时必填"
|
|
|
+ <el-option
|
|
|
+ v-for="(name, index) in $store.state.DmsTypesMap['yzt_task_type']"
|
|
|
+ :key="index"
|
|
|
+ :label="name"
|
|
|
+ :value="index"
|
|
|
/>
|
|
|
- <el-select
|
|
|
+ </el-select>
|
|
|
+ </el-form-item>
|
|
|
+ <!-- 渲染任务描述:仅查看 -->
|
|
|
+ <el-form-item
|
|
|
+ label="任务描述"
|
|
|
+ prop="apiDescription"
|
|
|
+ v-if="taskColumn.apiFrom.apiDescription"
|
|
|
+ >
|
|
|
+ <el-input type="textarea" disabled v-model="taskColumn.apiFrom.apiDescription" />
|
|
|
+ </el-form-item>
|
|
|
+ <!-- 任务文件是必须的 -->
|
|
|
+ <el-form-item label="任务文件" prop="c_source_file">
|
|
|
+ <el-input disabled v-model="taskColumn.from.c_source_file" v-show="false" />
|
|
|
+ <el-upload class="avatar-uploader" :http-request="handleTCUpload" :limit="1">
|
|
|
+ <el-button size="small" type="primary">点击上传</el-button>
|
|
|
+ </el-upload>
|
|
|
+ </el-form-item>
|
|
|
+ <el-divider />
|
|
|
+ <!-- 其他参数数据 -->
|
|
|
+ <el-form-item label="其他参数数据" prop="c_source_data" v-show="false">
|
|
|
+ <el-input
|
|
|
+ type="textarea"
|
|
|
+ clearable
|
|
|
+ v-model="taskColumn.from.c_source_data"
|
|
|
+ placeholder="请输入其他参数数据"
|
|
|
+ />
|
|
|
+ </el-form-item>
|
|
|
+ <div
|
|
|
+ v-if="
|
|
|
+ taskColumn.apiFrom.apiParameterRules &&
|
|
|
+ includesKey([
|
|
|
+ 'lonKey',
|
|
|
+ 'latKey',
|
|
|
+ 'outFileType',
|
|
|
+ 'inPrj',
|
|
|
+ 'outPrj',
|
|
|
+ 'compressionRatio',
|
|
|
+ 'keyType',
|
|
|
+ 'geocodeColumnKeyword',
|
|
|
+ ])
|
|
|
+ "
|
|
|
+ >
|
|
|
+ <template
|
|
|
+ v-for="(rulesItem, index) in taskColumn.apiFrom.apiParameterRules"
|
|
|
+ :key="index"
|
|
|
+ >
|
|
|
+ <el-form-item
|
|
|
v-if="
|
|
|
- ['outFileType', 'inPrj', 'outPrj', 'compressionRatio'].includes(rulesItem)
|
|
|
+ [
|
|
|
+ 'lonKey',
|
|
|
+ 'latKey',
|
|
|
+ 'outFileType',
|
|
|
+ 'inPrj',
|
|
|
+ 'outPrj',
|
|
|
+ 'compressionRatio',
|
|
|
+ 'keyType',
|
|
|
+ 'geocodeColumnKeyword',
|
|
|
+ ].includes(rulesItem)
|
|
|
+ "
|
|
|
+ :label="
|
|
|
+ rulesItem === 'keyType'
|
|
|
+ ? '类型字段'
|
|
|
+ : rulesItem === 'geocodeColumnKeyword'
|
|
|
+ ? '数据列名'
|
|
|
+ : rulesItem
|
|
|
"
|
|
|
- v-model="taskColumn.from.c_source_data[rulesItem]"
|
|
|
- :placeholder="'请选择' + rulesItem"
|
|
|
>
|
|
|
- <el-option
|
|
|
- v-for="item in taskColumn.selectOptions[rulesItem]"
|
|
|
- :key="'wgn-task-selectOptions-form-' + item.label"
|
|
|
- :label="item.label"
|
|
|
- :value="item.value"
|
|
|
+ <el-input
|
|
|
+ v-if="['lonKey', 'latKey'].includes(rulesItem)"
|
|
|
+ v-model="taskColumn.from.c_source_data[rulesItem]"
|
|
|
+ placeholder="当文件为xlsx时必填"
|
|
|
/>
|
|
|
- </el-select>
|
|
|
- <el-select
|
|
|
- v-if="rulesItem === 'keyType'"
|
|
|
- v-model="taskColumn.from.c_source_data.keyType"
|
|
|
- placeholder="非空转空时选择地物类型"
|
|
|
- :clearable="!isGeocodingTaskKeyTypeReadonly()"
|
|
|
- filterable
|
|
|
- :disabled="isGeocodingTaskKeyTypeReadonly()"
|
|
|
- >
|
|
|
- <el-option
|
|
|
- v-for="item in taskColumn.selectOptions.keyType"
|
|
|
- :key="'wgn-task-keyType-' + item.value"
|
|
|
- :label="item.label"
|
|
|
- :value="item.value"
|
|
|
+ <el-select
|
|
|
+ v-if="
|
|
|
+ ['outFileType', 'inPrj', 'outPrj', 'compressionRatio'].includes(rulesItem)
|
|
|
+ "
|
|
|
+ v-model="taskColumn.from.c_source_data[rulesItem]"
|
|
|
+ :placeholder="'请选择' + rulesItem"
|
|
|
+ >
|
|
|
+ <el-option
|
|
|
+ v-for="item in taskColumn.selectOptions[rulesItem]"
|
|
|
+ :key="'wgn-task-selectOptions-form-' + item.label"
|
|
|
+ :label="item.label"
|
|
|
+ :value="item.value"
|
|
|
+ />
|
|
|
+ </el-select>
|
|
|
+ <el-select
|
|
|
+ v-if="rulesItem === 'keyType'"
|
|
|
+ v-model="taskColumn.from.c_source_data.keyType"
|
|
|
+ placeholder="非空转空时选择地物类型"
|
|
|
+ :clearable="!isGeocodingTaskKeyTypeReadonly()"
|
|
|
+ filterable
|
|
|
+ :disabled="isGeocodingTaskKeyTypeReadonly()"
|
|
|
+ >
|
|
|
+ <el-option
|
|
|
+ v-for="item in taskColumn.selectOptions.keyType"
|
|
|
+ :key="'wgn-task-keyType-' + item.value"
|
|
|
+ :label="item.label"
|
|
|
+ :value="item.value"
|
|
|
+ />
|
|
|
+ </el-select>
|
|
|
+ <el-input
|
|
|
+ v-if="rulesItem === 'geocodeColumnKeyword' && isTaskGeocodeZipForColumnInput"
|
|
|
+ v-model="taskColumn.from.c_source_data.geocodeColumnKeyword"
|
|
|
+ placeholder="zip 内含多个表格时请手动输入列名(与各表表头一致)"
|
|
|
+ clearable
|
|
|
/>
|
|
|
- </el-select>
|
|
|
- <el-input
|
|
|
- v-if="rulesItem === 'geocodeColumnKeyword' && isTaskGeocodeZipForColumnInput"
|
|
|
- v-model="taskColumn.from.c_source_data.geocodeColumnKeyword"
|
|
|
- placeholder="zip 内含多个表格时请手动输入列名(与各表表头一致)"
|
|
|
- clearable
|
|
|
+ <el-select
|
|
|
+ v-if="rulesItem === 'geocodeColumnKeyword' && !isTaskGeocodeZipForColumnInput"
|
|
|
+ v-model="taskColumn.from.c_source_data.geocodeColumnKeyword"
|
|
|
+ placeholder="请先上传 CSV / XLSX,将自动读取表头"
|
|
|
+ clearable
|
|
|
+ filterable
|
|
|
+ :disabled="
|
|
|
+ !taskColumn.selectOptions.geocodeColumnKeyword ||
|
|
|
+ !taskColumn.selectOptions.geocodeColumnKeyword.length
|
|
|
+ "
|
|
|
+ >
|
|
|
+ <el-option
|
|
|
+ v-for="item in taskColumn.selectOptions.geocodeColumnKeyword"
|
|
|
+ :key="'wgn-task-geocol-' + item.value"
|
|
|
+ :label="item.label"
|
|
|
+ :value="item.value"
|
|
|
+ />
|
|
|
+ </el-select>
|
|
|
+ </el-form-item>
|
|
|
+ </template>
|
|
|
+ </div>
|
|
|
+ <!-- 任务状态默认为初始化 -->
|
|
|
+ <el-form-item label="任务状态" prop="c_state" v-show="false">
|
|
|
+ <el-select disabled v-model="taskColumn.from.c_state" placeholder="请选择任务状态">
|
|
|
+ <el-option
|
|
|
+ v-for="(name, index) in $store.state.DmsTypesMap['task_status']"
|
|
|
+ :key="'wgn-task-form-' + index"
|
|
|
+ :label="name"
|
|
|
+ :value="index"
|
|
|
/>
|
|
|
- <el-select
|
|
|
- v-if="rulesItem === 'geocodeColumnKeyword' && !isTaskGeocodeZipForColumnInput"
|
|
|
- v-model="taskColumn.from.c_source_data.geocodeColumnKeyword"
|
|
|
- placeholder="请先上传 CSV / XLSX,将自动读取表头"
|
|
|
- clearable
|
|
|
- filterable
|
|
|
- :disabled="
|
|
|
- !taskColumn.selectOptions.geocodeColumnKeyword ||
|
|
|
- !taskColumn.selectOptions.geocodeColumnKeyword.length
|
|
|
- "
|
|
|
- >
|
|
|
- <el-option
|
|
|
- v-for="item in taskColumn.selectOptions.geocodeColumnKeyword"
|
|
|
- :key="'wgn-task-geocol-' + item.value"
|
|
|
- :label="item.label"
|
|
|
- :value="item.value"
|
|
|
- />
|
|
|
- </el-select>
|
|
|
- </el-form-item>
|
|
|
- </template>
|
|
|
- </div>
|
|
|
- <!-- 任务状态默认为初始化 -->
|
|
|
- <el-form-item label="任务状态" prop="c_state" v-show="false">
|
|
|
- <el-select disabled v-model="taskColumn.from.c_state" placeholder="请选择任务状态">
|
|
|
- <el-option
|
|
|
- v-for="(name, index) in $store.state.DmsTypesMap['task_status']"
|
|
|
- :key="'wgn-task-form-' + index"
|
|
|
- :label="name"
|
|
|
- :value="index"
|
|
|
- />
|
|
|
- </el-select>
|
|
|
- </el-form-item>
|
|
|
- <!-- 任务负责人默认为当前登录用户 -->
|
|
|
- <el-form-item label="用户id" prop="c_user_id" v-show="false">
|
|
|
- <el-input disabled v-model="taskColumn.from.c_user_id" />
|
|
|
- </el-form-item>
|
|
|
- <!-- 任务负责人默认为当前登录用户 -->
|
|
|
- <el-form-item label="用户名" prop="c_user_name" v-show="false">
|
|
|
- <el-input disabled v-model="taskColumn.from.c_user_name" />
|
|
|
- </el-form-item>
|
|
|
- </el-form>
|
|
|
- <template #footer>
|
|
|
- <div class="dialog-footer">
|
|
|
- <el-button @click="showTaskFrom = false">取消</el-button>
|
|
|
- <el-button type="primary" @click="handleTaskSubmit">确定</el-button>
|
|
|
- </div>
|
|
|
- </template>
|
|
|
- </el-dialog>
|
|
|
+ </el-select>
|
|
|
+ </el-form-item>
|
|
|
+ <!-- 任务负责人默认为当前登录用户 -->
|
|
|
+ <el-form-item label="用户id" prop="c_user_id" v-show="false">
|
|
|
+ <el-input disabled v-model="taskColumn.from.c_user_id" />
|
|
|
+ </el-form-item>
|
|
|
+ <!-- 任务负责人默认为当前登录用户 -->
|
|
|
+ <el-form-item label="用户名" prop="c_user_name" v-show="false">
|
|
|
+ <el-input disabled v-model="taskColumn.from.c_user_name" />
|
|
|
+ </el-form-item>
|
|
|
+ </el-form>
|
|
|
+ <template #footer>
|
|
|
+ <div class="dialog-footer">
|
|
|
+ <el-button @click="showTaskFrom = false">取消</el-button>
|
|
|
+ <el-button type="primary" @click="handleTaskSubmit">确定</el-button>
|
|
|
+ </div>
|
|
|
+ </template>
|
|
|
+ </el-dialog>
|
|
|
+ </div>
|
|
|
</div>
|
|
|
</div>
|
|
|
</el-affix>
|
|
|
@@ -331,6 +363,7 @@ import { ElNotification } from "element-plus";
|
|
|
import moment from "moment";
|
|
|
import * as XLSX from "xlsx";
|
|
|
import api from "@/api/content";
|
|
|
+import { WGN_SCENE_LIST } from "@/data/wgnSceneList";
|
|
|
export default {
|
|
|
name: "ApplicationOverview",
|
|
|
data() {
|
|
|
@@ -341,6 +374,9 @@ export default {
|
|
|
searchStr: "",
|
|
|
// 微功能服务列表
|
|
|
dmsServerList: [],
|
|
|
+ sceneMenuTree: WGN_SCENE_LIST,
|
|
|
+ activeAnchorId: null,
|
|
|
+ anchorScrollLock: false,
|
|
|
// 是否显示申请使用微功能服务的表单弹窗
|
|
|
showFrom: false,
|
|
|
// 是否显示创建任务的表单弹窗
|
|
|
@@ -532,6 +568,17 @@ export default {
|
|
|
};
|
|
|
},
|
|
|
computed: {
|
|
|
+ /** 按一级场景分组,仅保留当前搜索结果下仍有卡片的分类 */
|
|
|
+ groupedWgnSections() {
|
|
|
+ const list = this.dmsServerList || [];
|
|
|
+ return this.sceneMenuTree
|
|
|
+ .map((cat) => {
|
|
|
+ const codes = new Set((cat.children || []).map((ch) => ch.value));
|
|
|
+ const items = list.filter((i) => codes.has(i.c_scene_name));
|
|
|
+ return { cat, items };
|
|
|
+ })
|
|
|
+ .filter((g) => g.items.length > 0);
|
|
|
+ },
|
|
|
isTaskGeocodeZipForColumnInput() {
|
|
|
const n =
|
|
|
(this.taskUploadRawFile && this.taskUploadRawFile.name) ||
|
|
|
@@ -540,6 +587,22 @@ export default {
|
|
|
return String(n).toLowerCase().endsWith(".zip");
|
|
|
},
|
|
|
},
|
|
|
+ watch: {
|
|
|
+ groupedWgnSections: {
|
|
|
+ handler(blocks) {
|
|
|
+ this.$nextTick(() => {
|
|
|
+ if (blocks.length) {
|
|
|
+ if (!blocks.some((b) => b.cat.value === this.activeAnchorId)) {
|
|
|
+ this.activeAnchorId = blocks[0].cat.value;
|
|
|
+ }
|
|
|
+ } else {
|
|
|
+ this.activeAnchorId = null;
|
|
|
+ }
|
|
|
+ this.bindAnchorSpy();
|
|
|
+ });
|
|
|
+ },
|
|
|
+ },
|
|
|
+ },
|
|
|
mounted() {
|
|
|
// 任务负责人默认为当前登录用户
|
|
|
this.taskColumn.from.c_user_id = this.$store.state.userInfo.id;
|
|
|
@@ -547,7 +610,61 @@ export default {
|
|
|
this.taskColumn.from.c_user_name = this.$store.state.userInfo.username;
|
|
|
this.searchServerList();
|
|
|
},
|
|
|
+ beforeUnmount() {
|
|
|
+ this.unbindAnchorSpy();
|
|
|
+ },
|
|
|
methods: {
|
|
|
+ sectionDomId(catValue) {
|
|
|
+ return "wgn-section-" + String(catValue).replace(/\./g, "-");
|
|
|
+ },
|
|
|
+ scrollToAnchor(catValue) {
|
|
|
+ const root = this.$refs.wgnScrollRoot;
|
|
|
+ const el = document.getElementById(this.sectionDomId(catValue));
|
|
|
+ if (!root || !el) return;
|
|
|
+ this.anchorScrollLock = true;
|
|
|
+ this.activeAnchorId = catValue;
|
|
|
+ const rootRect = root.getBoundingClientRect();
|
|
|
+ const elRect = el.getBoundingClientRect();
|
|
|
+ const nextTop = elRect.top - rootRect.top + root.scrollTop - 8;
|
|
|
+ root.scrollTo({ top: Math.max(0, nextTop), behavior: "smooth" });
|
|
|
+ window.setTimeout(() => {
|
|
|
+ this.anchorScrollLock = false;
|
|
|
+ this.updateActiveAnchorFromScroll();
|
|
|
+ }, 480);
|
|
|
+ },
|
|
|
+ unbindAnchorSpy() {
|
|
|
+ const root = this.$refs.wgnScrollRoot;
|
|
|
+ if (root && this._wgnOnScroll) {
|
|
|
+ root.removeEventListener("scroll", this._wgnOnScroll);
|
|
|
+ }
|
|
|
+ this._wgnOnScroll = null;
|
|
|
+ },
|
|
|
+ bindAnchorSpy() {
|
|
|
+ this.unbindAnchorSpy();
|
|
|
+ const root = this.$refs.wgnScrollRoot;
|
|
|
+ if (!root) return;
|
|
|
+ this._wgnOnScroll = () => this.updateActiveAnchorFromScroll();
|
|
|
+ root.addEventListener("scroll", this._wgnOnScroll, { passive: true });
|
|
|
+ this.updateActiveAnchorFromScroll();
|
|
|
+ },
|
|
|
+ updateActiveAnchorFromScroll() {
|
|
|
+ if (this.anchorScrollLock) return;
|
|
|
+ const root = this.$refs.wgnScrollRoot;
|
|
|
+ const blocks = this.groupedWgnSections;
|
|
|
+ if (!root || !blocks.length) return;
|
|
|
+ const rootRect = root.getBoundingClientRect();
|
|
|
+ const threshold = 28;
|
|
|
+ let current = blocks[0].cat.value;
|
|
|
+ for (const { cat } of blocks) {
|
|
|
+ const el = document.getElementById(this.sectionDomId(cat.value));
|
|
|
+ if (!el) continue;
|
|
|
+ const top = el.getBoundingClientRect().top - rootRect.top;
|
|
|
+ if (top <= threshold) {
|
|
|
+ current = cat.value;
|
|
|
+ }
|
|
|
+ }
|
|
|
+ this.activeAnchorId = current;
|
|
|
+ },
|
|
|
isGeocodingTaskKeyTypeReadonly() {
|
|
|
const label = this.$getDmsTypes("yzt_task_type", this.taskColumn.from.c_type);
|
|
|
return label === "文件地名地址查询";
|
|
|
@@ -644,11 +761,7 @@ export default {
|
|
|
// 接口路径
|
|
|
this.taskColumn.apiFrom.apiUrl = apiInfo.c_url;
|
|
|
const pr = this.taskColumn.apiFrom.apiParameterRules;
|
|
|
- if (
|
|
|
- pr &&
|
|
|
- pr.includes("geocodeColumnKeyword") &&
|
|
|
- this.taskUploadRawFile
|
|
|
- ) {
|
|
|
+ if (pr && pr.includes("geocodeColumnKeyword") && this.taskUploadRawFile) {
|
|
|
this.refreshTaskGeocodeColumns(this.taskUploadRawFile);
|
|
|
}
|
|
|
this.syncKeyTypeForGeocodingTask();
|
|
|
@@ -783,7 +896,7 @@ export default {
|
|
|
routerPath = {
|
|
|
// path: item.c_url,
|
|
|
path: "sksj",
|
|
|
- }
|
|
|
+ };
|
|
|
// this.$router.push(routerPath);
|
|
|
window.open(routerPath.path, "_blank");
|
|
|
} else {
|
|
|
@@ -824,22 +937,33 @@ export default {
|
|
|
.then((res) => {
|
|
|
if (res.code === 200) {
|
|
|
// 过滤掉自定义工具微功能服务1.5.8.1
|
|
|
- this.dmsServerList = res.content.data.filter(
|
|
|
- (item) => item.c_scene_name != "1.5.8.1"
|
|
|
- );
|
|
|
+ // this.dmsServerList = res.content.data.filter(
|
|
|
+ // (item) => item.c_scene_name != "1.5.8.1"
|
|
|
+ // );
|
|
|
// 转换时间格式
|
|
|
- this.dmsServerList = this.dmsServerList.map((item) => ({
|
|
|
+ this.dmsServerList = res.content.data.map((item) => ({
|
|
|
...item,
|
|
|
createTime: moment(item.create_time).format("YYYY-MM-DD HH:mm:ss"),
|
|
|
}));
|
|
|
this.total = this.dmsServerList.length;
|
|
|
+ if (this.total === 0) {
|
|
|
+ this.$message({
|
|
|
+ message: "暂无数据",
|
|
|
+ type: "info",
|
|
|
+ });
|
|
|
+ }
|
|
|
// ElNotification.success({
|
|
|
// title: "成功",
|
|
|
// message: "搜索到" + this.dmsServerList.length + "条微功能服务",
|
|
|
// offset: 80,
|
|
|
// });
|
|
|
} else {
|
|
|
+ this.dmsServerList = [];
|
|
|
this.total = 0;
|
|
|
+ this.$message({
|
|
|
+ message: "暂无数据",
|
|
|
+ type: "info",
|
|
|
+ });
|
|
|
// ElNotification.error({
|
|
|
// title: "失败",
|
|
|
// message: "搜索到0条微功能服务",
|
|
|
@@ -969,10 +1093,70 @@ export default {
|
|
|
color: #ffffff;
|
|
|
}
|
|
|
|
|
|
+.wgn-body {
|
|
|
+ display: flex;
|
|
|
+ align-items: flex-start;
|
|
|
+ width: 100%;
|
|
|
+ box-sizing: border-box;
|
|
|
+ min-height: calc(100vh - 44px);
|
|
|
+}
|
|
|
+
|
|
|
+.wgn-side-nav {
|
|
|
+ flex: 0 0 200px;
|
|
|
+ padding: 12px 12px 24px 24px;
|
|
|
+ background: transparent;
|
|
|
+ border: none;
|
|
|
+ position: sticky;
|
|
|
+ top: 52px;
|
|
|
+ align-self: flex-start;
|
|
|
+ max-height: calc(100vh - 56px);
|
|
|
+ overflow-y: auto;
|
|
|
+}
|
|
|
+
|
|
|
+.wgn-anchor {
|
|
|
+ display: block;
|
|
|
+ width: 100%;
|
|
|
+ padding: 10px 4px 10px 0;
|
|
|
+ margin: 0 0 2px;
|
|
|
+ border: none;
|
|
|
+ background: transparent;
|
|
|
+ color: rgba(255, 255, 255, 0.85);
|
|
|
+ font-size: 16px;
|
|
|
+ text-align: left;
|
|
|
+ cursor: pointer;
|
|
|
+ border-radius: 4px;
|
|
|
+}
|
|
|
+
|
|
|
+.wgn-anchor:hover {
|
|
|
+ color: #ffffff;
|
|
|
+}
|
|
|
+
|
|
|
+.wgn-anchor.active {
|
|
|
+ color: #69b1ff;
|
|
|
+ font-weight: 600;
|
|
|
+}
|
|
|
+
|
|
|
+.wgn-anchor-section {
|
|
|
+ scroll-margin-top: 12px;
|
|
|
+}
|
|
|
+
|
|
|
+.wgn-anchor-section + .wgn-anchor-section {
|
|
|
+ margin-top: 36px;
|
|
|
+}
|
|
|
+
|
|
|
+.wgn-anchor-section-title {
|
|
|
+ margin: 0 0 18px;
|
|
|
+ font-size: 20px;
|
|
|
+ font-weight: 600;
|
|
|
+ color: #ffffff;
|
|
|
+ letter-spacing: 0.02em;
|
|
|
+}
|
|
|
+
|
|
|
/* 右侧主内容区 */
|
|
|
.main-content {
|
|
|
flex: 1;
|
|
|
- padding: 20px 100px;
|
|
|
+ min-width: 0;
|
|
|
+ padding: 20px 40px 20px 8px;
|
|
|
overflow-y: auto;
|
|
|
}
|
|
|
|