diff --git a/index.html b/index.html index dcd6967..c8a360f 100644 --- a/index.html +++ b/index.html @@ -4,6 +4,7 @@ + Vite App diff --git a/src/api/common/index.js b/src/api/common/index.js index d9f60ae..343c228 100644 --- a/src/api/common/index.js +++ b/src/api/common/index.js @@ -1,10 +1,22 @@ import request from '@/utils/request.js'; // 校验token返回用户信息 -export function getUserInfo(params) { +export function getUserInfo(appToken) { return request({ - url: '/thirdPartyInterfaceInfoEx/test', - method: 'get', - params + url: `/open/digital_yili/${appToken}`, + method: 'get' + }); +} +/* +根据员工号查询用户信息 +header里传个digitalYiliToken +*/ +export function getByCodeInfo(userCode, digitalYiliToken) { + return request({ + url: `/open/digital_yili/user/${userCode}`, + headers: { + digitalYiliToken: digitalYiliToken || '' + }, + method: 'get' }); } diff --git a/src/api/publish/index.js b/src/api/publish/index.js new file mode 100644 index 0000000..7ac20a6 --- /dev/null +++ b/src/api/publish/index.js @@ -0,0 +1,45 @@ +import request from '@/utils/request'; + +// 投放问卷 +export function publishSurvey(data) { + return request({ + url: `/console/survey_publishes`, + method: 'post', + data + }); +} + +// 问卷详情 +export function getSurveyInfo(sn) { + return request({ + url: `/console/surveys/${sn}`, + method: 'get' + }); +} + +// 查看二维码 +export function getQrcode(sn) { + return request({ + url: `/console/survey_publishes/${sn}/qrcode`, + method: 'get' + }); +} + +// 获取问卷测试是否弹层 +export function getCheckSurvey(sn) { + return request({ + url: `/console/check_survey_test/${sn}`, + method: 'get' + }); +} + +/* 获取问题列表 */ +export function getQuestionList(params, code) { + return request({ + headers: { + 'survey-invite-code': code || '' + }, + url: `/console/surveys/${params}/questions`, + method: 'get' + }); +} diff --git a/src/assets/img/publish/not_pulish.png b/src/assets/img/publish/not_pulish.png new file mode 100644 index 0000000..482ced2 Binary files /dev/null and b/src/assets/img/publish/not_pulish.png differ diff --git a/src/layouts/utils.js b/src/layouts/utils.js new file mode 100644 index 0000000..d5f05c2 --- /dev/null +++ b/src/layouts/utils.js @@ -0,0 +1,471 @@ +// import { getQuesByPages } from '@/views/planetDesign/Design/js/util'; +// import { A_COMMON_SET_ACTIVEQUESTION } from '@store/constance/constance.common' +import { createVNode } from 'vue'; +import { showConfirmDialog, showDialog } from 'vant'; +import { getQuestionList, getCheckSurvey } from '@/api/publish'; +// import store from '@/store'; +// import Scroll from '@views/planetDesign/Design/js/scroll' +// /** +// * 统一的弹窗 +// * @param options +// */ +/** + * 统一的弹窗 + * @param options + */ +function showModal(options) { + const confirm = (...rest) => { + if (options.incompleteQuestionList?.length) { + if (options.onOk) { + options.onOk(...rest); + } + // const firstQuestion = options.incompleteQuestionList[0]; + // store.commit(`common/${A_COMMON_SET_ACTIVEQUESTION}`, JSON.stringify(firstQuestion)); + // const el = document.getElementById(firstQuestion.id); + + // new Scroll(el).animate(); + } + }; + + showConfirmDialog({ + class: 'custom-modal custom-modal-title-notice', + title: '提示', + icon: null, + ...options + }) + .then(() => { + confirm(); + }) + .catch(() => {}); +} + +/** + * PSM的判断 + * @param {*} data + * @returns + */ +const canPlanetPublishPSM = function(data) { + let isFb = true; + let content = ''; + let title = '题目设置未完成'; + const incompleteQuestionList = []; + data.questions + && data.questions.forEach((s) => { + if (s.question_type === 101 && s.config.price_gradient.length <= 0) { + isFb = false; + content = 'psm题目未完成设置,请设置价格区间后投放'; + title = '题目设置未完成'; + incompleteQuestionList.push(s); + } + }); + + if (isFb === true) { + return true; + } else { + const titleStr = incompleteQuestionList.map((item) => item.title).join('、') || ''; + showModal({ + title, + content: `${titleStr} ${content}`, + incompleteQuestionList + }); + } +}; +/** + * Mxd和热区的判断 + * @param {*} data + * @returns + */ +const canPlanetPublishMxdAndHotArea = function(data) { + let isFb = true; + let content = ''; + const qSteams = []; + const incompleteQuestionList = []; + let type = 0; + let title = '题目设置未完成'; + data.questions + && data.questions.forEach((s) => { + if (s.question_type === 105 && s.config.design_version <= 0) { + isFb = false; + content = 'maxdiff题目未完成设置,请生成设计后投放'; + title = '题目设置未完成'; + type = 1; + incompleteQuestionList.push(s); + } + if (s.question_type === 25 || s.question_type === 26) { + if ((s.options?.[0]?.length || 0) <= 0 && (s?.associate?.length || 0) <= 0) { + isFb = false; + qSteams.push(`(${s.title})`); + type = 2; + incompleteQuestionList.push(s); + } + } + }); + + if (isFb === true) { + return true; + } else { + if (type === 2) { + const titleStr = qSteams.join(','); + title = '添加选区'; + content = `${titleStr} 未添加选区,请添加选区后进行投放`; + } + showModal({ + title, + content, + incompleteQuestionList + }); + } +}; + +/** + * 3D相关的判断 + * @param {*} data + * @returns + */ +const canPlanetPublish3D = function(data) { + { + let canFB = true; + let content = ''; + const qSteams = []; + let title = ''; + data.questions + && data.questions.forEach((s) => { + if (QUESTION_TYPE.contains(s.question_type)) { + try { + if (s.config.is_three_dimensions && !s.config.scene) { + canFB = false; + qSteams.push(`(${s.title})`); + } + } catch (error) { + console.warn(error); + } + } + }); + + if (!canFB === true) { + const titleStr = qSteams.join(','); + title = '选择场景'; + content = `${titleStr} 未选择场景,请选择场景后进行投放`; + showModal({ + title, + content + }); + return; + } + } + + { + let canFB = true; + let content = ''; + const qSteams = []; + let title = ''; + data.questions + && data.questions.forEach((s) => { + if (QUESTION_TYPE.contains(s.question_type)) { + try { + if (s.config.is_three_dimensions && s.config.is_binding_goods) { + const wares = []; + const scene_information = s.config.scene_information; + const sceneInformation + = typeof scene_information === 'string' + ? JSON.parse(scene_information) + : scene_information; + sceneInformation.shelves.forEach((shelf) => { + shelf.wares.forEach((ware) => { + if (!ware.option_index) return; + wares.push(ware); + }); + }); + + const options = s.options.flat(); + s.associate.forEach((ass) => { + const question = data.questions.find((q) => q.question_index == ass.question_index); + if (!question) return; + options.push(...question.options.flat()); + }); + + // options = options.filter(option => !option.is_other); + + // 判定是否有选项未关联商品 + if (options.length > wares.length) { + canFB = false; + qSteams.push(`(${s.title})`); + } + } + } catch (error) { + console.warn(error); + } + } + }); + + if (!canFB === true) { + const titleStr = qSteams.join(','); + title = '商品关联选项'; + content = `${titleStr} 仍有选项未关联商品,无法进行投放`; + showModal({ + title, + content + }); + return; + } + } + + return true; +}; +/** + * 图片题的判断 + * @param {*} data + * @returns + */ +const canPlanetPublishImage = function(data) { + { + let canFB = true; + let content = ''; + const qSteams = []; + let title = ''; + data.questions + && data.questions.forEach((s) => { + if (s.question_type == 13) { + try { + if (s.options.length <= 0 || s.options.some((y) => y.length <= 0)) { + canFB = false; + qSteams.push(`(${s.title})`); + } + } catch (error) { + console.warn(error); + } + } + }); + if (!canFB === true) { + const titleStr = qSteams.join(','); + title = '题目设置未完成'; + // content = `${titleStr} 未上传图片,请上传图片后进行投放`; + content = `图片题 ${titleStr} 未上传图片,请设置后投放`; + showModal({ + title, + content + }); + return; + } + } + + return true; +}; + +/** + * 多项填空题 + * @param data + * @param publishType + */ +function canPublishMultiCompletion(data, publishType) { + const publishStr = ['', '预览', '投放'][publishType] || '投放'; + const questions = []; + + if (!data?.questions?.length) { + return true; + } + + data.questions.forEach((quiz) => { + if (quiz.question_type !== 27) { + return; + } + + if (!getDomText(quiz.config?.text_content)) { + questions.push(quiz.title); + } + }); + + if (questions.length) { + showModal({ + title: '题目设置未完成', + content: `多项填空题 (${questions.join('、')}) 未设置填空,请设置后${publishStr}` + }); + return false; + } + + return true; +} + +/** + * 校验 “逻辑 -> 随机列表” 是否满足投放条件 + * @param data + * @return {boolean} + */ +function canPublishRandom(data, publishType) { + const publishStr = ['', '预览', '投放'][publishType] || '投放'; + + const errors = []; + const randomList = data?.survey?.group_pages || []; + + randomList.forEach((random, randomIndex) => { + const list = random.list || []; + + // 每一个随机,至少要有两个随机题组 + if (list.length < 2) { + errors.push({ message: `“${random.title}”需至少配置2个“随机题组”` }); + return false; + } + + list.forEach((item, index) => { + // 这三个是必填的 + const fields = [ + { label: 'title', name: '题组名称', validator: (value) => !!value }, + { label: 'start', name: '题组起点', validator: (value) => !!value }, + { label: 'end', name: '题组终点', validator: (value) => !!value } + ]; + + fields.forEach((field) => { + const isValidated = field.validator(item[field.label]); + if (!isValidated) { + errors.push({ + message: + field.message + || `请填写“${random.title}”中第${index + 1}组“随机题组”的“${field.name}”` + }); + } + }); + }); + }); + + if (errors.length) { + showModal({ + title: '修改随机题组', + content: `随机题组设置不完全,请前往“逻辑设置-随机列表”修改后${publishStr}` + }); + return false; + } + + return true; +} + +/** + * 循环逻辑的判断 + * @param data + * @param publishType + */ +function isLoopingLogicValid(data, publishType) { + const publishStr = ['', '预览', '投放'][publishType] || '投放'; + + if ( + (data?.cycle_pages || []).every((i) => { + return ( + i.question_index + && i.relation_type !== undefined + && i.relation_type !== null + && i.first_page + && i.last_page + ); + }) + ) { + return loopingAvailable({ + cycles: data.cycle_pages || [], + questions: getQuesByPages(data.questions || [], data.survey.pages), + logics: data.logics || [], + isPerPage: data.survey?.is_one_page_one_question + }); + } + + showDialog({ + class: 'custom-modal custom-modal-title-notice show-icon', + title: '修改循环', + content: `循环题组不完全,请前往循环列表修改后${publishStr}` + }); + + return false; +} + +export const canPlanetPublish = async function(sn, publishType) { + const parsedPublishType = !publishType ? 2 : publishType; + + const num = window.location.href.indexOf('code='); + let code; + if (num > -1) { + code = window.location.href.slice(num + 5, window.location.href.length); + } else { + code = ''; + } + const { data } = await getQuestionList(sn, code); + if (!canPlanetPublishPSM(data)) return false; + if (!canPlanetPublishMxdAndHotArea(data)) return false; + if (!canPlanetPublish3D(data)) return false; + if (!canPlanetPublishImage(data)) return false; + if (!canPublishMultiCompletion(data, parsedPublishType)) return false; + if (!canPublishRandom(data, parsedPublishType)) return false; + // if (!isLoopingLogicValid(data, parsedPublishType)) return false; + + if (parsedPublishType === 2) { + const qrcodeRes = await getCheckSurvey(sn); + if (qrcodeRes?.data?.show_test_button) { + const res = await new Promise((resolve) => { + showConfirmDialog({ + class: 'custom-modal custom-modal-title-confirm-notice show-icon', + title: '确认要投放这个问卷吗?', + // content: () => + // createVNode('div', {}, [ + // createVNode( + // 'div', + // { + // style: { + // position: 'absolute', + // top: '0', + // right: '0', + // display: 'flex', + // justifyContent: 'center', + // alignItems: 'center', + // width: '56px', + // height: '56px', + // fontSize: '14px', + // cursor: 'pointer' + // }, + // onClick: () => { + // console.log('close'); + // modal.destroy(); + // resolve(false); + // } + // }, + // // 使用 HTML 实体 × 来替代 ant - design 的 CloseOutlined + // ['×'] + // ), + // createVNode( + // 'div', + // {}, + // '投放前测试能帮助您确认问卷设计逻辑及作答数据是否正确,避免因问卷设计问题造成重大损失。' + // ) + // ]), + contentStyle: { + position: 'absolute', + top: '0', + right: '0', + display: 'flex', + justifyContent: 'center', + alignItems: 'center', + width: '56px', + height: '56px', + fontSize: '14px', + cursor: 'pointer' + }, + message: + '投放前测试能帮助您确认问卷设计逻辑及作答数据是否正确,避免因问卷设计问题造成重大损失。', + confirmButtonText: '去测试', + onConfirm() { + resolve(false); + // window.open(`${location.origin}/#/answer?sn=${sn}&is_test=1`); + }, + width: '640px', + height: '364px', + cancelButtonText: '继续投放', + onCancel() { + resolve(true); + }, + dialogStyle: { + fontSize: '44px' + }, + zIndex: 9999999 + }); + }); + if (!res) return; + } + } + + return true; +}; diff --git a/src/views/Survey/views/Publish/Index.vue b/src/views/Survey/views/Publish/Index.vue index d68c60f..957f686 100644 --- a/src/views/Survey/views/Publish/Index.vue +++ b/src/views/Survey/views/Publish/Index.vue @@ -1,79 +1,84 @@