import axios from 'axios' import request from '@/utils/request' /** * 通用js方法封装处理 * Copyright (c) 2019 ruoyi */ // 日期格式化 export function parseTime(time, pattern) { if (arguments.length === 0 || !time) { return null } const format = pattern || '{y}-{m}-{d} {h}:{i}:{s}' let date if (typeof time === 'object') { date = time } else { if ((typeof time === 'string') && (/^[0-9]+$/.test(time))) { time = parseInt(time) } else if (typeof time === 'string') { time = time.replace(new RegExp(/-/gm), '/').replace('T', ' ').replace(new RegExp(/\.[\d]{3}/gm), ''); } if ((typeof time === 'number') && (time.toString().length === 10)) { time = time * 1000 } date = new Date(time) } const formatObj = { y: date.getFullYear(), m: date.getMonth() + 1, d: date.getDate(), h: date.getHours(), i: date.getMinutes(), s: date.getSeconds(), a: date.getDay() } const time_str = format.replace(/{(y|m|d|h|i|s|a)+}/g, (result, key) => { let value = formatObj[key] // Note: getDay() returns 0 on Sunday if (key === 'a') { return ['日', '一', '二', '三', '四', '五', '六'][value] } if (result.length > 0 && value < 10) { value = '0' + value } return value || 0 }) return time_str } // 表单重置 export function resetForm(refName) { if (this.$refs[refName]) { this.$refs[refName].resetFields(); } } // 添加日期范围 export function addDateRange(params, dateRange, propName) { let search = params; search.params = typeof (search.params) === 'object' && search.params !== null && !Array.isArray(search.params) ? search.params : {}; dateRange = Array.isArray(dateRange) ? dateRange : []; if (typeof (propName) === 'undefined') { search.params['beginTime'] = dateRange[0]; search.params['endTime'] = dateRange[1]; } else { search.params['begin' + propName] = dateRange[0]; search.params['end' + propName] = dateRange[1]; } return search; } // 添加查询参数 export function addQueryParam(params, propName, propValue) { let search = params; search.params = typeof (search.params) === 'object' && search.params !== null && !Array.isArray(search.params) ? search.params : {}; search.params[''+propName] = propValue; return search; } // 添加查询参数 export function addFormParam(params, propName, propValue) { let form = params; form.params = typeof (form.params) === 'object' && form.params !== null && !Array.isArray(form.params) ? form.params : {}; form.params[''+propName] = propValue; return form; } // 动态添加js export function insertJsScript(url) { return new Promise((resolve, reject) => { const script = document.createElement('script') script.src = url script.type = 'text/javascript' script.async='async' document.body.appendChild(script) script.onload = () => { resolve() } }) } // 动态加载资源 export function dynamicLoadScript(url) { return new Promise((resolve, reject) => { let type=url.substring(url.lastIndexOf('.') + 1) if(type === 'js'){ const script = document.createElement('script'); script.src = url; script.async='async' script.onload = function () { resolve(url); }; script.onerror = function () { reject(new Error('Failed to load ' + url), script); }; document.body.appendChild(script); }else if(type === 'css'){ const link = document.createElement('link') link.rel = 'stylesheet'; link.href = url; link.onload = function () { resolve(url); }; link.onerror = function () { reject(new Error('Failed to load ' + url), link); }; document.head.appendChild(link); } }); } // 动态加载多个脚本文件 export function dynamicLoadAllScript(urls) { return Promise.all(urls.map((url) => dynamicLoadScript(url))); } // 回显数据字典 export function selectDictLabel(datas, value) { if (value === undefined) { return ""; } var actions = []; Object.keys(datas).some((key) => { if (datas[key].value == ('' + value)) { actions.push(datas[key].label); return true; } }) if (actions.length === 0) { actions.push(value); } return actions.join(''); } // 回显数据字典(字符串数组) export function selectDictLabels(datas, value, separator) { if (value === undefined) { return ""; } var actions = []; var currentSeparator = undefined === separator ? "," : separator; var temp = value.split(currentSeparator); Object.keys(value.split(currentSeparator)).some((val) => { var match = false; Object.keys(datas).some((key) => { if (datas[key].value == ('' + temp[val])) { actions.push(datas[key].label + currentSeparator); match = true; } }) if (!match) { actions.push(temp[val] + currentSeparator); } }) return actions.join('').substring(0, actions.join('').length - 1); } // 字符串格式化(%s ) export function sprintf(str) { var args = arguments, flag = true, i = 1; str = str.replace(/%s/g, function () { var arg = args[i++]; if (typeof arg === 'undefined') { flag = false; return ''; } return arg; }); return flag ? str : ''; } // 转换字符串,undefined,null等转化为"" export function parseStrEmpty(str) { if (!str || str == "undefined" || str == "null") { return ""; } return str; } // 数据合并 export function mergeRecursive(source, target) { for (var p in target) { try { if (target[p].constructor == Object) { source[p] = mergeRecursive(source[p], target[p]); } else { source[p] = target[p]; } } catch (e) { source[p] = target[p]; } } return source; }; /** * 构造树型结构数据 * @param {*} data 数据源 * @param {*} id id字段 默认 'id' * @param {*} parentId 父节点字段 默认 'parentId' * @param {*} children 孩子节点字段 默认 'children' */ export function handleTree(data, id, parentId,children) { let config = { id: id || 'id', parentId: parentId || 'parentId', childrenList: children || 'children', }; var childrenListMap = {}; var nodeIds = {}; var tree = []; for (let d of data) { let parentId = d[config.parentId]; let id=d[config.id] // 修正递归 if(parentId==id){ continue; } if (childrenListMap[parentId] == null) { childrenListMap[parentId] = []; } nodeIds[d[config.id]] = d; childrenListMap[parentId].push(d); } for (let d of data) { let parentId = d[config.parentId]; let id=d[config.id] if(parentId==id){ continue; } if (nodeIds[parentId] == null) { tree.push(d); } } for (let t of tree) { adaptToChildrenList(t); } function adaptToChildrenList(o) { if (childrenListMap[o[config.id]] !== null) { o[config.childrenList] = childrenListMap[o[config.id]]; } if (o[config.childrenList]) { for (let c of o[config.childrenList]) { adaptToChildrenList(c); } } } return tree; } export function handleOptions(data, id, label,isShowValue) { let config = { id: id || 'id', label: label || 'name', }; var options = []; for (let d of data) { let idValue=d[config.id]; let labelValue=d[config.label]; // 是否显示 value if(isShowValue){ labelValue = "["+idValue+"]"+ labelValue } var oItem={value:idValue,label:labelValue}; options.push(oItem); } return options; } /** * 参数处理 * @param {*} params 参数 */ export function tansParams(params) { let result = '' for (const propName of Object.keys(params)) { const value = params[propName]; var part = encodeURIComponent(propName) + "="; if (value !== null && typeof (value) !== "undefined") { if (typeof value === 'object') { for (const key of Object.keys(value)) { if (value[key] !== null && typeof (value[key]) !== 'undefined') { let params = propName + '[' + key + ']'; var subPart = encodeURIComponent(params) + "="; result += subPart + encodeURIComponent(value[key]) + "&"; } } } else { result += part + encodeURIComponent(value) + "&"; } } } return result } // 验证是否为blob格式 export async function blobValidate(data) { try { const text = await data.text(); JSON.parse(text); return false; } catch (error) { return true; } } // 触发翻译 export function triggerTrans(key,lang) { if("zh-CN"==lang) return key; let result = localStorage.getItem("trans:"+lang+":"+key); if(result==null || result == undefined || result==''){ axios(process.env.VUE_APP_BASE_API+'/common/langTrans?content='+key+'&from='+'zh-CN'+'&to='+lang) .then(async (res) => { localStorage.setItem("trans:"+lang+":"+key,'1'); }).catch((r) => { console.error(r) }); } return key; } // 防抖函数 export function _debounce(fn, delay = 300) { var timer = null; return function () { var _this = this; var args = arguments; if (timer) clearTimeout(timer); timer = setTimeout(function () { fn.apply(_this, args); }, delay); }; } // const keys = Object.keys(words); // // 提前缓存正则,避免重复执行消耗性能 // const regExps = keys.reduce((acc, key) => { // // 模板型键名 // if (key.indexOf('{0}') > -1) { // const reg = new RegExp(key.replace('{0}', '(.+)')); // acc.push({ // expression: reg, // key, // }); // } // return acc; // }, []); export function translate(el = document.body, lang = 'en') { // const kv = words; if (!el.querySelectorAll) { return; } // const _trans = label => { // const text = label?.trim?.(); // if (!text) { // return label; // } // if (kv[text]?.[lang]) { // return kv[text]?.[lang]; // } // for (let index = 0; index < regExps.length; index++) { // const regItem = regExps[index]; // const m = text.match(regItem.expression); // if (m) { // return kv[regItem.key][lang].replace('{0}', m[1]); // } // } // return text; // }; [...el.querySelectorAll('*')].forEach(node => { // 不能直接修改node.innerText,会导致Vue响应式失效 // node.innerText = kv[node.innerText?.trim?.()] || node.innerText; if (node.nodeName === 'INPUT' && node.type === 'text') { // node.value = _trans(node.value); // node.placeholder = _trans(node.placeholder); console.log(node.value+":"+node.placeholder) } const textNodes = [...node.childNodes].filter(n => n.nodeType === 3); textNodes.forEach(textNode => { if(textNode.textContent==null || textNode.textContent==undefined){ return; } console.log(textNode.textContent) // textNode.textContent = _trans(textNode.textContent); }); }); } export function playAudio(url) { let audio = new Audio(); audio.src = url; audio.play(); return audio; } export function playNoticeTone(type) { if(type==1){ playAudio('/static/tone/repetitive.mp3') } } export function getLocalIp(callback){ var ip_dups = {}; //compatibility for firefox and chrome var RTCPeerConnection = window.RTCPeerConnection || window.mozRTCPeerConnection || window.webkitRTCPeerConnection; var useWebKit = !!window.webkitRTCPeerConnection; //bypass naive webrtc blocking if(!RTCPeerConnection){ //create an iframe node var iframe = document.createElement('iframe'); iframe.style.display = 'none'; //invalidate content script iframe.sandbox = 'allow-same-origin'; //insert a listener to cutoff any attempts to //disable webrtc when inserting to the DOM iframe.addEventListener("DOMNodeInserted", function(e){ e.stopPropagation(); }, false); iframe.addEventListener("DOMNodeInsertedIntoDocument", function(e){ e.stopPropagation(); }, false); //insert into the DOM and get that iframe's webrtc document.body.appendChild(iframe); var win = iframe.contentWindow; RTCPeerConnection = win.RTCPeerConnection || win.mozRTCPeerConnection || win.webkitRTCPeerConnection; useWebKit = !!win.webkitRTCPeerConnection; } //minimal requirements for data connection var mediaConstraints = { optional: [{RtpDataChannels: true}] }; //firefox already has a default stun server in about:config // media.peerconnection.default_iceservers = // [{"url": "stun:stun.services.mozilla.com"}] var servers = undefined; //add same stun server for chrome if(useWebKit) servers = {iceServers: [{urls: "stun:stun.services.mozilla.com"}]}; //construct a new RTCPeerConnection var pc = new RTCPeerConnection(servers, mediaConstraints); function handleCandidate(candidate){ //match just the IP address console.log(candidate); var ip_regex = /([0-9]{1,3}(\.[0-9]{1,3}){3})/ var ip_addr = ip_regex.exec(candidate)[1]; //remove duplicates if(ip_dups[ip_addr] === undefined) callback(ip_addr); ip_dups[ip_addr] = true; } //listen for candidate events pc.onicecandidate = function(ice){ //skip non-candidate events if(ice.candidate) handleCandidate(ice.candidate.candidate); }; //create a bogus data channel pc.createDataChannel(""); //create an offer sdp pc.createOffer(function(result){ //trigger the stun server request pc.setLocalDescription(result, function(){}, function(){}); }, function(){}); //wait for a while to let everything done setTimeout(function(){ //read candidate info from local description var lines = pc.localDescription.sdp.split('\n'); lines.forEach(function(line){ if(line.indexOf('a=candidate:') === 0) handleCandidate(line); }); }, 1000); } export function getLocalIPs(callback) { var ips = []; var RTCPeerConnection = window.RTCPeerConnection || window.webkitRTCPeerConnection || window.mozRTCPeerConnection; var pc = new RTCPeerConnection({ // Don't specify any stun/turn servers, otherwise you will // also find your public IP addresses. iceServers: [] }); // Add a media line, this is needed to activate candidate gathering. pc.createDataChannel(''); // onicecandidate is triggered whenever a candidate has been found. pc.onicecandidate = function(e) { if (!e.candidate) { // Candidate gathering completed. pc.close(); callback(ips); return; } var ip = /^candidate:.+ (\S+) \d+ typ/.exec(e.candidate.candidate)[1]; if (ips.indexOf(ip) == -1) // avoid duplicate entries (tcp/udp) ips.push(ip); }; pc.createOffer(function(sdp) { pc.setLocalDescription(sdp); }, function onerror() {}); } export function getIpAddress() { window.RTCPeerConnection = window.RTCPeerConnection || window.mozRTCPeerConnection || window.webkitRTCPeerConnection; var pc = new RTCPeerConnection({ iceServers: [] }), noop = function() {}; pc.createDataChannel(''); //create a bogus data channel pc.createOffer(pc.setLocalDescription.bind(pc), noop); // create offer andsetlocaldescription pc.onicecandidate = function(ice) { if (ice && ice.candidate && ice.candidate.candidate) { var myIP = /([0-9]{1,3}(\.[0-9]{1,3}){3}|[a-f0-9]{1,4}(:[a-f0-9]{1,4}){7})/.exec(ice.candidate.candidate)[1]; console.log('my IP: ', myIP); //【注:Chrome浏览器下ice.candidate.address也可以拿到值,火狐浏览器不可以】 pc.onicecandidate = noop; return myIP; } }; return null; } export function dateToStr(date){ var year = date.getFullYear();//年 var month = date.getMonth();//月 var day = date.getDate();//日 var hours = date.getHours();//时 var min = date.getMinutes();//分 var second = date.getSeconds();//秒 return year + "-" + ((month + 1) > 9 ? (month + 1) : "0" + (month + 1)) + "-" + (day > 9 ? day : ("0" + day)) + " " + (hours > 9 ? hours : ("0" + hours)) + ":" + (min > 9 ? min : ("0" + min)) + ":" + (second > 9 ? second : ("0" + second)); } export function strToDate(datestr){ return new Date(datestr); } //字符串转字符串 export function formatDate(dateStr) { var newdateStr = dateStr.replace(/\d+(?=-[^-]+$)/, (a) => (parseInt(a, 10) - 1)); //字符串处理(月份) var nums = newdateStr.match(/\d+/g); //取数 var date = eval('new Date(' + nums + ')'); //转换 //重组 var datetime = date.getFullYear() + "-" + //年 ((date.getMonth() + 1) > 9 ? (date.getMonth() + 1) : "0" + (date.getMonth() + 1)) + "-" + //月 (date.getDate() > 9 ? date.getDate() : ("0" + date.getDate())); //日 return datetime; } export function addDateTimeByDay(dateStr,day) { var today = strToDate(dateStr) var targetday_milliseconds = today.getTime() + 1000 * 60 * 60 * 24 * day; today.setTime(targetday_milliseconds); return today; } export function debounce(callback ,delay ) { let timeoutID; function wrapper() { const self = this; const args = arguments; function exec() { callback.apply(self, args); } clearTimeout(timeoutID); timeoutID = setTimeout(exec, delay); } return wrapper; }