index.vue 31 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917918919920921922923924925926927928929930931932933934935936937938939940941942943944945946947948949950951952953954955956957958959960961962963
  1. <template>
  2. <div class="app-container">
  3. <el-form :model="queryParams" ref="queryForm" :inline="true" v-show="showSearch" label-width="68px">
  4. <el-form-item label="名称" prop="name">
  5. <el-input
  6. v-model="queryParams.name"
  7. placeholder="请输入名称"
  8. clearable
  9. size="small"
  10. @keyup.enter.native="handleQuery"
  11. />
  12. </el-form-item>
  13. <el-form-item label="所属公司" prop="companyId">
  14. <el-select
  15. v-model="queryParams.companyId"
  16. filterable
  17. remote
  18. reserve-keyword
  19. placeholder="请输入公司名称搜索"
  20. :remote-method="searchCompanies"
  21. :loading="companySearchLoading"
  22. style="width: 220px"
  23. clearable
  24. size="small"
  25. >
  26. <el-option
  27. v-for="item in companyOptions"
  28. :key="item.dictValue"
  29. :label="item.dictLabel"
  30. :value="item.dictValue"
  31. />
  32. </el-select>
  33. </el-form-item>
  34. <el-form-item label="appid" prop="appid">
  35. <el-input
  36. v-model="queryParams.appid"
  37. placeholder="请输入appid"
  38. clearable
  39. size="small"
  40. @keyup.enter.native="handleQuery"
  41. />
  42. </el-form-item>
  43. <el-form-item label="所属部门" prop="deptName">
  44. <el-input
  45. v-model="queryParams.deptName"
  46. placeholder="请输入部门信息"
  47. clearable
  48. size="small"
  49. @keyup.enter.native="handleQuery"
  50. />
  51. </el-form-item>
  52. <el-form-item label="状态" prop="status">
  53. <el-select
  54. v-model="queryParams.status"
  55. placeholder="请选择状态"
  56. clearable
  57. size="small"
  58. >
  59. <el-option
  60. v-for="item in statusOptions"
  61. :key="item.value"
  62. :label="item.label"
  63. :value="item.value"
  64. />
  65. </el-select>
  66. </el-form-item>
  67. <el-form-item>
  68. <el-button type="primary" icon="el-icon-search" size="mini" @click="handleQuery">搜索</el-button>
  69. <el-button icon="el-icon-refresh" size="mini" @click="resetQuery">重置</el-button>
  70. </el-form-item>
  71. </el-form>
  72. <el-row :gutter="10" class="mb8">
  73. <el-col :span="1.5">
  74. <el-button
  75. type="primary"
  76. plain
  77. icon="el-icon-plus"
  78. size="mini"
  79. @click="handleAdd"
  80. v-hasPermi="['course:playSourceConfig:add']"
  81. >新增</el-button>
  82. </el-col>
  83. <el-col :span="1.5">
  84. <el-button
  85. type="success"
  86. plain
  87. icon="el-icon-edit"
  88. size="mini"
  89. :disabled="single"
  90. @click="handleUpdate"
  91. v-hasPermi="['course:playSourceConfig:edit']"
  92. >修改</el-button>
  93. </el-col>
  94. <el-col :span="1.5">
  95. <el-button
  96. type="danger"
  97. plain
  98. icon="el-icon-delete"
  99. size="mini"
  100. :disabled="multiple"
  101. @click="handleDelete"
  102. v-hasPermi="['course:playSourceConfig:remove']"
  103. >删除</el-button>
  104. </el-col>
  105. <right-toolbar :showSearch.sync="showSearch" @queryTable="getList"></right-toolbar>
  106. </el-row>
  107. <!-- 开关配置对话框 -->
  108. <el-dialog title="开关配置" :visible.sync="switchDialogVisible" width="500px" class="switch-dialog">
  109. <el-form :model="switchForm" label-width="100px">
  110. <el-form-item label="AppId">
  111. <el-input v-model="switchForm.appId" :disabled="true"></el-input>
  112. </el-form-item>
  113. <el-form-item label="开关状态">
  114. <el-switch
  115. v-model="switchForm.switchStatus"
  116. active-text="开启"
  117. inactive-text="关闭"
  118. active-value="001"
  119. inactive-value="002">
  120. </el-switch>
  121. </el-form-item>
  122. <el-form-item label="配置信息" v-if="switchForm.configInfo">
  123. <el-input
  124. type="textarea"
  125. :rows="4"
  126. v-model="switchForm.configInfo"
  127. :disabled="true">
  128. </el-input>
  129. </el-form-item>
  130. </el-form>
  131. <span slot="footer" class="dialog-footer">
  132. <el-button @click="switchDialogVisible = false">取 消</el-button>
  133. <el-button type="primary" @click="submitSwitchConfig">确 定</el-button>
  134. </span>
  135. </el-dialog>
  136. <el-table v-loading="loading" :data="list" @selection-change="handleSelectionChange" border>
  137. <el-table-column type="selection" width="55" align="center" />
  138. <el-table-column label="ID" align="center" prop="id" />
  139. <el-table-column label="名称" align="center" prop="name" />
  140. <el-table-column label="所属公司" align="center" prop="companyId" :formatter="companyNameFormatter"/>
  141. <el-table-column label="所属部门" align="center" width="120px">
  142. <template v-slot="scope">
  143. <span style="font-size: 20px">{{scope.row.deptName}}</span>
  144. </template>
  145. </el-table-column>
  146. <el-table-column label="图标" align="center" prop="img">
  147. <template slot-scope="scope">
  148. <el-image
  149. style="width: 80px; height: 80px"
  150. :src="scope.row.img"
  151. :preview-src-list="[scope.row.img]">
  152. </el-image>
  153. </template>
  154. </el-table-column>
  155. <el-table-column label="原始ID" align="center" prop="originalId" />
  156. <el-table-column label="appId" align="center" prop="appid" />
  157. <el-table-column label="secret" align="center" prop="secret" />
  158. <el-table-column label="token" align="center" prop="token" />
  159. <el-table-column label="aesKey" align="center" prop="aesKey" />
  160. <el-table-column label="msgDataFormat" align="center" prop="msgDataFormat" />
  161. <el-table-column label="类型" align="center" prop="type">
  162. <template slot-scope="scope">
  163. <dict-tag :options="typesOptions" :value="scope.row.type"/>
  164. </template>
  165. </el-table-column>
  166. <el-table-column label="互医/商城小程序" align="center" prop="isMall" width="80px">
  167. <template slot-scope="scope">
  168. <el-tag prop="isMall" v-for="(item, index) in isMallOptions" v-if="scope.row.isMall==item.dictValue">{{item.dictLabel}}</el-tag>
  169. </template>
  170. </el-table-column>
  171. <el-table-column
  172. v-hasPermi="['course:playSourceConfig:courseMini']"
  173. label="是否看课小程序"
  174. align="center"
  175. prop="isCourseMini"
  176. width="120px"
  177. >
  178. <template slot-scope="scope">
  179. <el-tag>{{ getIsCourseMiniLabel(scope.row.isCourseMini) }}</el-tag>
  180. </template>
  181. </el-table-column>
  182. <el-table-column label="状态" align="center" prop="status" width="100px">
  183. <template slot-scope="scope">
  184. <el-tag
  185. :type="scope.row.status === -1 ? 'info' : scope.row.status === 0 ? 'success' : scope.row.status === 1 ? 'warning' : 'danger'"
  186. >
  187. {{ getStatusLabel(scope.row.status) }}
  188. </el-tag>
  189. </template>
  190. </el-table-column>
  191. <el-table-column label="协议状态" align="center" prop="settingsProtocolType" width="100">
  192. <template v-slot="scope">
  193. <el-tag
  194. :type="scope.row.settingsProtocolType === 2 ? 'success' : scope.row.settingsProtocolType === 1 ? 'warning' : 'info'"
  195. >
  196. {{ getProtocolStatusLabel(scope.row.settingsProtocolType) }}
  197. </el-tag>
  198. </template>
  199. </el-table-column>
  200. <el-table-column label="创建时间" align="center" prop="createTime" />
  201. <el-table-column label="修改时间" align="center" prop="updateTime" />
  202. <el-table-column label="操作" align="center" fixed="right" width="120px">
  203. <template slot-scope="scope">
  204. <el-button
  205. size="mini"
  206. type="text"
  207. icon="el-icon-edit"
  208. @click="handleUpdate(scope.row)"
  209. v-hasPermi="['course:playSourceConfig:edit']"
  210. >修改</el-button>
  211. <el-button
  212. size="mini"
  213. type="text"
  214. icon="el-icon-delete"
  215. @click="handleDelete(scope.row)"
  216. v-hasPermi="['course:playSourceConfig:remove']"
  217. >删除</el-button>
  218. <el-button
  219. size="mini"
  220. type="text"
  221. icon="el-icon-setting"
  222. @click="handleSwitchConfig(scope.row)"
  223. >是否展示销售</el-button>
  224. <el-button
  225. size="mini"
  226. type="text"
  227. icon="el-icon-document"
  228. @click="handlePrivacyConfig(scope.row)"
  229. >隐私协议</el-button>
  230. </template>
  231. </el-table-column>
  232. </el-table>
  233. <pagination
  234. v-show="total>0"
  235. :total="total"
  236. :page.sync="queryParams.pageNum"
  237. :limit.sync="queryParams.pageSize"
  238. @pagination="getList"
  239. />
  240. <!-- 添加或修改点播配置对话框 -->
  241. <el-dialog :title="title" :visible.sync="open" width="800px" append-to-body :before-close="resetOption">
  242. <el-form ref="form" :model="form" :rules="rules" label-width="130px">
  243. <el-form-item label="名称" prop="name">
  244. <el-input v-model="form.name" placeholder="请输入名称" />
  245. </el-form-item>
  246. <el-form-item label="所属公司" prop="companyId">
  247. <el-select
  248. v-model="form.companyId"
  249. filterable
  250. remote
  251. reserve-keyword
  252. placeholder="请输入公司名称搜索"
  253. :remote-method="searchCompanies"
  254. :loading="companySearchLoading"
  255. style="width: 220px"
  256. clearable
  257. size="small"
  258. >
  259. <el-option
  260. v-for="item in companyOptions"
  261. :key="item.dictValue"
  262. :label="item.dictLabel"
  263. :value="item.dictValue"
  264. />
  265. </el-select>
  266. </el-form-item>
  267. <el-form-item label="所属部门" prop="createDeptId">
  268. <treeselect v-model="form.createDeptId" :options="deptOptions" :normalizer="normalizer" placeholder="选择上级部门" :disabled="(username !== 'admin' && title === '修改小程序配置')" />
  269. </el-form-item>
  270. <el-form-item label="是否是互医/商城小程序" prop="isMall">
  271. <el-select
  272. v-model="form.isMall"
  273. style="width: 220px"
  274. clearable
  275. size="small"
  276. >
  277. <el-option
  278. v-for="item in isMallOptions"
  279. :key="item.dictValue"
  280. :label="item.dictLabel"
  281. :value="item.dictValue"
  282. />
  283. </el-select>
  284. </el-form-item>
  285. <el-form-item
  286. v-hasPermi="['course:playSourceConfig:courseMini']"
  287. label="是否看课小程序"
  288. prop="isCourseMini"
  289. >
  290. <el-select
  291. v-model="form.isCourseMini"
  292. placeholder="请选择是否看课小程序"
  293. style="width: 220px"
  294. size="small"
  295. >
  296. <el-option
  297. v-for="item in isCourseMiniOptions"
  298. :key="item.dictValue"
  299. :label="item.dictLabel"
  300. :value="item.dictValue"
  301. />
  302. </el-select>
  303. <div class="form-tip-text">
  304. 请认真选择:该标识主要用于区分 APP 用户与小程序用户,影响用户归属与业务统计。
  305. </div>
  306. </el-form-item>
  307. <el-form-item label="状态" prop="status">
  308. <el-select
  309. v-model="form.status"
  310. placeholder="请选择状态"
  311. style="width: 220px"
  312. clearable
  313. size="small"
  314. >
  315. <el-option
  316. v-for="item in statusOptions"
  317. :key="item.value"
  318. :label="item.label"
  319. :value="item.value"
  320. />
  321. </el-select>
  322. </el-form-item>
  323. <el-form-item label="图标" prop="img">
  324. <image-upload v-model="form.img" :file-type='["png", "jpg", "jpeg"]' :limit="1"/>
  325. </el-form-item>
  326. <el-form-item label="类型" prop="type">
  327. <el-select
  328. v-model="form.type"
  329. placeholder="请选择类型">
  330. <el-option
  331. v-for="item in typesOptions"
  332. :key="item.dictValue"
  333. :label="item.dictLabel"
  334. :value="item.dictValue"/>
  335. </el-select>
  336. </el-form-item>
  337. <el-form-item label="原始id" prop="originalId">
  338. <el-input v-model="form.originalId" placeholder="请输入原始id" />
  339. </el-form-item>
  340. <el-form-item label="appid" prop="appid">
  341. <el-input v-model="form.appid" placeholder="请输入appid" />
  342. </el-form-item>
  343. <el-form-item label="secret" prop="secret">
  344. <el-input v-model="form.secret" placeholder="请输入secret" />
  345. </el-form-item>
  346. <el-form-item label="token" prop="token">
  347. <el-input v-model="form.token" placeholder="请输入token" />
  348. </el-form-item>
  349. <el-form-item label="aesKey" prop="aesKey">
  350. <el-input v-model="form.aesKey" placeholder="请输入aesKey" />
  351. </el-form-item>
  352. <el-form-item label="msgDataFormat" prop="msgDataFormat">
  353. <el-input v-model="form.msgDataFormat" placeholder="请输入msgDataFormat" />
  354. </el-form-item>
  355. </el-form>
  356. <div slot="footer" class="dialog-footer">
  357. <el-button type="primary" @click="submitForm">确 定</el-button>
  358. <el-button @click="cancel">取 消</el-button>
  359. </div>
  360. </el-dialog>
  361. <!-- 隐私协议配置对话框 -->
  362. <el-dialog
  363. :title="privacyTitle"
  364. :visible.sync="privacyDialogVisible"
  365. width="60%"
  366. class="privacy-dialog"
  367. :close-on-click-modal="false"
  368. >
  369. <el-form
  370. ref="privacyFormRef"
  371. :model="privacyForm"
  372. :rules="privacyRules"
  373. label-width="100px"
  374. >
  375. <el-form-item label="医生注册协议" prop="doctorRegister">
  376. <editor v-model="privacyForm.doctorRegister" :min-height="292"/>
  377. </el-form-item>
  378. <el-form-item label="医生多机构备案协议" prop="doctorFiling">
  379. <editor v-model="privacyForm.doctorFiling" :min-height="292"/>
  380. </el-form-item>
  381. <el-form-item label="药师注册协议" prop="pharmacistRegister">
  382. <editor v-model="privacyForm.pharmacistRegister" :min-height="292"/>
  383. </el-form-item>
  384. <el-form-item label="药师多机构备案协议" prop="pharmacistFiling">
  385. <editor v-model="privacyForm.pharmacistFiling" :min-height="292"/>
  386. </el-form-item>
  387. <el-form-item label="用户协议" prop="userRegister">
  388. <editor v-model="privacyForm.userRegister" :min-height="292"/>
  389. </el-form-item>
  390. <el-form-item label="隐私协议" prop="userPrivacy">
  391. <editor v-model="privacyForm.userPrivacy" :min-height="292"/>
  392. </el-form-item>
  393. <el-form-item label="健康客服协议" prop="userHealth">
  394. <editor v-model="privacyForm.userHealth" :min-height="292"/>
  395. </el-form-item>
  396. <el-form-item label="会员服务协议" prop="vipService">
  397. <editor v-model="privacyForm.vipService" :min-height="292"/>
  398. </el-form-item>
  399. <el-form-item label="会员自动续费协议" prop="vipAutomaticService">
  400. <editor v-model="privacyForm.vipAutomaticService" :min-height="292"/>
  401. </el-form-item>
  402. <el-form-item label="用户注销协议" prop="userRemoveService">
  403. <editor v-model="privacyForm.userRemoveService" :min-height="292"/>
  404. </el-form-item>
  405. <el-form-item label="商家规则" prop="storeRules">
  406. <editor v-model="privacyForm.storeRules" :min-height="292"/>
  407. </el-form-item>
  408. <el-form-item label="入驻协议" prop="residencyAgreement">
  409. <editor v-model="privacyForm.residencyAgreement" :min-height="292"/>
  410. </el-form-item>
  411. </el-form>
  412. <span slot="footer" class="dialog-footer">
  413. <el-button @click="privacyDialogVisible = false">取消</el-button>
  414. <el-button type="primary" @click="submitPrivacyConfig">保存</el-button>
  415. </span>
  416. </el-dialog>
  417. </div>
  418. </template>
  419. <script>
  420. import {list, get, update, add, del,getProtocolConfig,updateProtocolConfig} from '@/api/course/coursePlaySourceConfig'
  421. import {updateIsTownOn} from "@/api/system/config";
  422. import { allList } from '@/api/company/company'
  423. import { resetForm } from '@/utils/common'
  424. import { checkPermi } from '@/utils/permission'
  425. import Treeselect from "@riophae/vue-treeselect";
  426. import {listDept} from "@/api/system/dept";
  427. import "@riophae/vue-treeselect/dist/vue-treeselect.css";
  428. import { getUserProfile } from "@/api/system/user";
  429. import Template from '@/views/his/complaint/template.vue'
  430. export default {
  431. name: 'CoursePlaySourceConfig',
  432. components: { Template, Treeselect},
  433. data() {
  434. return {
  435. privacyTitle:null,
  436. privacyDialogVisible: false,
  437. privacyForm: {
  438. appId: '',
  439. doctorRegister:null,
  440. doctorFiling:null,
  441. pharmacistRegister:null,
  442. pharmacistFilinga:null,
  443. userRegister:null,
  444. userPrivacy:null,
  445. userHealth:null,
  446. vipService:null,
  447. vipAutomaticService:null,
  448. userRemoveService:null,
  449. storeRules:null,
  450. residencyAgreement:null,
  451. },
  452. authOptions:[
  453. {
  454. dictLabel: "食品",
  455. dictValue: 0
  456. },
  457. {
  458. dictLabel: "药品",
  459. dictValue: 1
  460. }
  461. ],
  462. username:null,
  463. // 部门树选项
  464. deptOptions: [],
  465. switchDialogVisible: false,
  466. // 公司搜索相关
  467. companySearchLoading: false,
  468. companyOptions: [],
  469. formatterCompanyOptions: [],
  470. switchForm: {
  471. appId: '',
  472. switchStatus: '001',
  473. },
  474. queryParams: {
  475. pageNum: 1,
  476. pageSize: 10,
  477. name: null,
  478. appid: null,
  479. status: null,
  480. deptName:null
  481. },
  482. showSearch: true,
  483. single: true,
  484. multiple: true,
  485. ids: [],
  486. loading: false,
  487. list: [],
  488. total: 0,
  489. typesOptions: [],
  490. statusOptions: [
  491. {
  492. label: "待审核",
  493. value: -1
  494. },
  495. {
  496. label: "正常",
  497. value: 0
  498. },
  499. {
  500. label: "半封禁",
  501. value: 1
  502. },
  503. {
  504. label: "封禁",
  505. value: 2
  506. }
  507. ],
  508. isMallOptions:[
  509. {
  510. dictLabel: "是",
  511. dictValue: 1
  512. },
  513. {
  514. dictLabel: "否",
  515. dictValue: 0
  516. }
  517. ],
  518. isCourseMiniOptions:[
  519. {
  520. dictLabel: "是",
  521. dictValue: 1
  522. },
  523. {
  524. dictLabel: "否",
  525. dictValue: 0
  526. }
  527. ],
  528. title: null,
  529. open: false,
  530. form: {isMall:0, isCourseMini: 1},
  531. rules: {
  532. name: [
  533. { required: true, message: "名称不能为空", trigger: "blur" }
  534. ],
  535. // companyId: [
  536. // { required: true, message: "所属公司不能为空", trigger: "blur" }
  537. // ],
  538. appid: [
  539. { required: true, message: "appid不能为空", trigger: "blur" }
  540. ],
  541. img: [
  542. { required: true, message: "图标不能为空", trigger: "blur" }
  543. ],
  544. type: [
  545. { required: true, message: "类型不能为空", trigger: "blur" }
  546. ],
  547. originalId: [
  548. { required: true, message: "原始id不能为空", trigger: "blur" }
  549. ],
  550. secret: [
  551. { required: true, message: "secret不能为空", trigger: "blur" }
  552. ],
  553. token: [
  554. { required: true, message: "token不能为空", trigger: "blur" }
  555. ],
  556. aesKey: [
  557. { required: true, message: "aesKey不能为空", trigger: "blur" }
  558. ],
  559. msgDataFormat: [
  560. { required: true, message: "msgDataFormat不能为空", trigger: "blur" }
  561. ]
  562. }
  563. }
  564. },
  565. created() {
  566. this.getDicts("play_source_type").then(response => {
  567. this.typesOptions = response.data.map(item => {
  568. return {
  569. ...item,
  570. listClass: 'primary'}
  571. })
  572. });
  573. //初始化formatterCompanyOptions
  574. allList().then(e => {
  575. this.formatterCompanyOptions = e.rows;
  576. });
  577. this.getList();
  578. listDept().then(response => {
  579. this.deptOptions = this.handleTree(response.data, "deptId");
  580. });
  581. getUserProfile().then(response => {
  582. const data = response.data;
  583. this.username = data.userName;
  584. });
  585. },
  586. methods: {
  587. resetForm,
  588. resetOption(){
  589. console.log(1)
  590. this.companyOptions = [];
  591. this.open = false;
  592. },
  593. /** 转换部门数据结构 */
  594. normalizer(node) {
  595. if (node.hasOwnProperty('id') && !node.hasOwnProperty('deptId')) {
  596. return {
  597. id: node.id,
  598. label: this.getDeptNameById(node.id) || '未知部门',
  599. children: node.children || []
  600. };
  601. }
  602. if (node.children && !node.children.length) {
  603. delete node.children;
  604. }
  605. return {
  606. id: node.deptId,
  607. label: node.deptName,
  608. children: node.children
  609. };
  610. },
  611. getDeptNameById(targetId) {
  612. const deptOptions =this.deptOptions
  613. console.log("text:"+JSON.stringify(deptOptions))
  614. for (let i = 0; i < deptOptions.length; i++) {
  615. const dept = deptOptions[i];
  616. if (dept.deptId === targetId) {
  617. return dept.deptName;
  618. }
  619. }
  620. return '未知部门';
  621. },
  622. // 处理开关配置
  623. handleSwitchConfig(row) {
  624. this.switchForm.appId = row.appid;
  625. this.switchForm.switchStatus = "001"; // 默认关闭状态
  626. // 调用接口获取开关状态
  627. this.getSwitchConfig(row.appid);
  628. this.switchDialogVisible = true;
  629. },
  630. /** 搜索公司 */
  631. searchCompanies(query) {
  632. this.companySearchLoading = true;
  633. allList().then(response => {
  634. this.companyOptions = response.rows;
  635. if (query) {
  636. this.companyOptions = this.companyOptions.filter(item =>
  637. item.dictLabel.includes(query)
  638. );
  639. }
  640. this.companySearchLoading = false;
  641. }).catch(()=>{
  642. this.companySearchLoading = false;
  643. });
  644. },
  645. companyNameFormatter(row){
  646. let company = this.formatterCompanyOptions.filter(item => item.dictValue === row.companyId)[0];
  647. return company ? company.dictLabel : '';
  648. },
  649. departmentNameFormatter(row) {
  650. // 容错处理:检查必要参数
  651. if (!this.deptOptions || !this.deptOptions.length || !row.deptId) {
  652. return '';
  653. }
  654. // 使用 deptId 匹配(与表格 prop 保持一致)
  655. const targetId = String(row.deptId);
  656. // 递归查找树形结构中的部门
  657. const findDept = (depts) => {
  658. for (const dept of depts) {
  659. // 先检查当前节点
  660. if (String(dept.deptId) === targetId) {
  661. return dept;
  662. }
  663. // 如果有子节点,递归查找
  664. if (dept.children && dept.children.length > 0) {
  665. const found = findDept(dept.children);
  666. if (found) return found;
  667. }
  668. }
  669. return null;
  670. };
  671. const dept = findDept(this.deptOptions);
  672. return dept?.deptName || '';
  673. },
  674. // 获取开关配置
  675. getSwitchConfig(appId) {
  676. const params = {
  677. appId: this.switchForm.appId
  678. };
  679. updateIsTownOn(params).then(response=>{
  680. if (response.code === 200) {
  681. if ( response.date){
  682. this.switchForm.switchStatus = response.date;
  683. }
  684. } else {
  685. this.$message.error('获取配置失败: ' + response.msg);
  686. }
  687. }).catch(error => {
  688. this.$message.error('请求失败: ' + error.message);
  689. });
  690. },
  691. // 提交开关配置
  692. submitSwitchConfig() {
  693. const params = {
  694. appId: this.switchForm.appId,
  695. bock: this.switchForm.switchStatus
  696. };
  697. updateIsTownOn(params).then(response=>{
  698. if (response.code === 200) {
  699. this.$message.success('配置更新成功');
  700. this.switchDialogVisible = false;
  701. } else {
  702. this.$message.error('更新失败: ' + response.msg);
  703. }
  704. })
  705. },
  706. getList() {
  707. this.loading = true;
  708. list(this.queryParams).then(response => {
  709. this.list = response.rows;
  710. this.total = response.total;
  711. this.loading = false;
  712. });
  713. },
  714. handleQuery() {
  715. this.queryParams.pageNum = 1;
  716. this.getList();
  717. },
  718. resetQuery() {
  719. this.resetForm("queryForm");
  720. this.getList();
  721. },
  722. handleAdd() {
  723. this.reset()
  724. this.open = true
  725. this.form.isMall = 0;
  726. this.form.isCourseMini = 1;
  727. this.title = "添加小程序配置"
  728. },
  729. handleUpdate(row) {
  730. this.reset()
  731. const id = row.id || this.ids
  732. get(id).then(response => {
  733. this.form = {
  734. ...response.data,
  735. type: response.data.type.toString(),
  736. isCourseMini: response.data.isCourseMini == null ? 1 : response.data.isCourseMini
  737. }
  738. this.searchCompanies("");
  739. this.open = true
  740. this.title = "修改小程序配置"
  741. })
  742. },
  743. handleDelete(row) {
  744. const id = row.id || this.ids
  745. this.$confirm('是否确认删除小程序配置编号为"' + id + '"的数据项?', "警告", {
  746. confirmButtonText: "确定",
  747. cancelButtonText: "取消",
  748. type: "warning"
  749. }).then(function() {
  750. return del(id);
  751. }).then(() => {
  752. this.getList();
  753. this.msgSuccess("删除成功");
  754. }).catch(() => {});
  755. },
  756. handleSelectionChange(selection) {
  757. this.ids = selection.map(item => item.id)
  758. this.single = selection.length!==1
  759. this.multiple = !selection.length
  760. },
  761. submitForm() {
  762. if (checkPermi(['course:playSourceConfig:courseMini'])) {
  763. if (this.form.isCourseMini === null || this.form.isCourseMini === undefined || this.form.isCourseMini === '') {
  764. this.msgError('请选择是否看课小程序')
  765. return
  766. }
  767. }
  768. this.$refs["form"].validate(valid => {
  769. if (valid) {
  770. const submitData = { ...this.form }
  771. if (!checkPermi(['course:playSourceConfig:courseMini'])) {
  772. delete submitData.isCourseMini
  773. }
  774. if (this.form.id != null) {
  775. update(submitData).then(response => {
  776. const {code, msg} = response
  777. if (code !== 200) {
  778. this.msgError(msg)
  779. return
  780. }
  781. this.msgSuccess("修改成功");
  782. this.open = false;
  783. this.getList();
  784. });
  785. } else {
  786. add(submitData).then(response => {
  787. const {code, msg} = response
  788. if (code !== 200) {
  789. this.msgError(msg)
  790. return
  791. }
  792. this.msgSuccess("新增成功");
  793. this.open = false;
  794. this.getList();
  795. });
  796. }
  797. }
  798. });
  799. },
  800. cancel() {
  801. this.open = false;
  802. this.reset();
  803. },
  804. reset() {
  805. this.form = {
  806. id: null,
  807. name: null,
  808. appid: null,
  809. secret: null,
  810. img: null,
  811. originalId: null,
  812. token: 'Ncbnd7lJvkripVOpyTFAna6NAWCxCrvC',
  813. aesKey: 'HlEiBB55eaWUaeBVAQO3cWKWPYv1vOVQSq7nFNICw4E',
  814. msgDataFormat: 'JSON',
  815. type: '1',
  816. isMall: 0,
  817. isCourseMini: 1,
  818. status: 0
  819. }
  820. this.resetForm("form");
  821. },
  822. getStatusLabel(status) {
  823. const statusMap = {
  824. '-1': '待审核',
  825. '0': '正常',
  826. '1': '半封禁',
  827. '2': '封禁'
  828. };
  829. return statusMap[status] || '未知';
  830. },
  831. getIsCourseMiniLabel(value) {
  832. if (value == null || value === 1) {
  833. return '是'
  834. }
  835. return '否'
  836. },
  837. // 处理隐私协议配置
  838. async handlePrivacyConfig(row) {
  839. try {
  840. this.privacyTitle = '《' + row.name + '》' + '隐私协议配置';
  841. this.privacyForm.id = row.id;
  842. this.privacyForm.appid = row.appid;
  843. this.privacyForm.name = row.name;
  844. // 显示加载
  845. this.$loading({
  846. lock: true,
  847. text: '正在加载协议配置...',
  848. spinner: 'el-icon-loading',
  849. background: 'rgba(0, 0, 0, 0.7)'
  850. });
  851. // 调用接口获取协议配置
  852. const response = await getProtocolConfig(row.id);
  853. if (response.code === 200 && response.data) {
  854. const data = response.data;
  855. // 将接口返回的数据映射到表单
  856. this.privacyForm.doctorRegister = data.doctorRegister || null;
  857. this.privacyForm.doctorFiling = data.doctorFiling || null;
  858. this.privacyForm.pharmacistRegister = data.pharmacistRegister || null;
  859. this.privacyForm.pharmacistFiling = data.pharmacistFiling || null;
  860. this.privacyForm.userRegister = data.userRegister || null;
  861. this.privacyForm.userPrivacy = data.userPrivacy || null;
  862. this.privacyForm.userHealth = data.userHealth || null;
  863. this.privacyForm.vipService = data.vipService || null;
  864. this.privacyForm.vipAutomaticService = data.vipAutomaticService || null;
  865. this.privacyForm.userRemoveService = data.userRemoveService || null;
  866. this.privacyForm.storeRules = data.storeRules || null;
  867. this.privacyForm.residencyAgreement = data.residencyAgreement || null;
  868. this.privacyForm.settingsProtocolType = data.settingsProtocolType || 0;
  869. this.$message.success('协议配置加载成功');
  870. } else {
  871. this.$message.warning('未找到协议配置,将创建新的配置');
  872. // 清空表单
  873. Object.keys(this.privacyForm).forEach(key => {
  874. if (key !== 'id' && key !== 'appid' && key !== 'name') {
  875. this.privacyForm[key] = null;
  876. }
  877. });
  878. }
  879. this.privacyDialogVisible = true;
  880. } catch (error) {
  881. this.$message.error('加载协议配置失败: ' + (error.message || error));
  882. } finally {
  883. this.$loading().close();
  884. }
  885. },
  886. // 提交隐私协议配置
  887. async submitPrivacyConfig() {
  888. try {
  889. // 验证必要字段
  890. if (!this.privacyForm.id) {
  891. this.$message.error('配置ID不能为空');
  892. return;
  893. }
  894. // 显示加载
  895. const loadingInstance = this.$loading({
  896. lock: true,
  897. text: '正在保存协议配置...',
  898. spinner: 'el-icon-loading',
  899. background: 'rgba(0, 0, 0, 0.7)'
  900. });
  901. // 调用更新接口
  902. const response = await updateProtocolConfig(this.privacyForm);
  903. if (response.code === 200) {
  904. this.$message.success(response.msg || '保存成功');
  905. this.privacyDialogVisible = false;
  906. // 刷新列表
  907. this.getList();
  908. } else {
  909. this.$message.error(response.msg || '保存失败');
  910. }
  911. } catch (error) {
  912. this.$message.error('保存失败: ' + (error.message || error));
  913. } finally {
  914. this.$loading().close();
  915. }
  916. },
  917. // 获取协议状态标签
  918. getProtocolStatusLabel(type) {
  919. const statusMap = {
  920. '0': '未设置',
  921. '1': '部分设置',
  922. '2': '已设置'
  923. };
  924. return statusMap[type] || '未知';
  925. }
  926. },
  927. }
  928. </script>
  929. <style scoped>
  930. .form-tip-text {
  931. margin-top: 6px;
  932. line-height: 1.5;
  933. font-size: 12px;
  934. color: #909399;
  935. }
  936. </style>