commit 0740c3f34979e1db3b4e8531af23336a00c27411 Author: GaoHao <1210693421@qq.com> Date: Fri Feb 7 14:49:20 2025 +0800 同步代码 diff --git a/.gitignore b/.gitignore new file mode 100644 index 0000000..063d141 --- /dev/null +++ b/.gitignore @@ -0,0 +1,6 @@ +unpackage/cache +unpackage/dist +unpackage/res +unpackage/resources +node_modules/ +/node_modules/ diff --git a/App.vue b/App.vue new file mode 100644 index 0000000..79a1e7a --- /dev/null +++ b/App.vue @@ -0,0 +1,179 @@ + + + + \ No newline at end of file diff --git a/androidPrivacy.json b/androidPrivacy.json new file mode 100644 index 0000000..b58f517 --- /dev/null +++ b/androidPrivacy.json @@ -0,0 +1,27 @@ +{ + "version" : "1", + "prompt" : "template", + "title" : "服务协议和隐私政策", + "message" : "  请你务必审慎阅读、充分理解“服务协议”和“隐私政策”各条款,包括但不限于:为了更好的向你提供服务,我们需要收集你的设备标识、操作日志等信息用于分析、优化应用性能。
  你可阅读《服务协议》《隐私政策》了解详细信息。如果你同意,请点击下面按钮开始接受我们的服务。", + "buttonAccept" : "同意并接受", + "buttonRefuse" : "暂不同意", + "second" : { + "title" : "确认提示", + "message" : "  进入应用前,你需先同意《服务协议》《隐私政策》,否则将退出应用。", + "buttonAccept" : "同意并继续", + "buttonRefuse" : "退出应用" + }, + "styles" : { + "backgroundColor" : "#FFFFFF", + "borderRadius" : "5px", + "title" : { + "color" : "#262626" + }, + "buttonAccept" : { + "color" : "#3981FF" + }, + "buttonRefuse" : { + "color" : "#A6A6A6" + } + } +} diff --git a/commons/JSON/mccAli.json b/commons/JSON/mccAli.json new file mode 100644 index 0000000..3b4fed6 --- /dev/null +++ b/commons/JSON/mccAli.json @@ -0,0 +1 @@ +[{"children":[{"msg":"","text":"火锅","value":"B0199"},{"msg":"","text":"中式正餐","value":"B0001"},{"msg":"","text":"西式正餐","value":"B0002"},{"msg":"","text":"日韩/东南亚菜","value":"B0003"},{"msg":"","text":"中式快餐","value":"B0004"},{"msg":"","text":"西式快餐","value":"B0005"},{"msg":"","text":"小吃/熟食","value":"B0006"},{"msg":"申请成为该行业商家,请提交:1. 商户与企业团餐合作协议或者2. 合作资质证明扫描件","text":"校园团餐","value":"B0007"},{"msg":"申请成为该行业商家,请提交:1. 商户与企业团餐合作协议或者2. 合作资质证明扫描件","text":"综合团餐","value":"B0008"},{"msg":"","text":"饮品/甜品","value":"B0009"},{"msg":"","text":"烘焙糕点","value":"B0010"},{"msg":"","text":"酒吧/清吧","value":"B0011"},{"msg":"","text":"咖啡馆/茶馆","value":"B0012"},{"msg":"","text":"宴会提供商","value":"B0200"},{"msg":"","text":"订餐服务平台","value":"B0117"}],"text":"餐饮","value":"A0001"},{"children":[{"msg":"","text":"小型商店","value":"B0013"},{"msg":"","text":"连锁便利店","value":"B0014"},{"msg":"","text":"大型超市","value":"B0015"},{"msg":"","text":"大卖场","value":"B0016"},{"msg":"","text":"百货商场","value":"B0017"},{"msg":"","text":"购物中心","value":"B0018"},{"msg":"","text":"奥特莱斯","value":"B0019"},{"msg":"","text":"商业街","value":"B0020"},{"msg":"","text":"水果店","value":"B0021"},{"msg":"","text":"食品零售","value":"B0201"},{"msg":"","text":"蔬菜/肉蛋/水产","value":"B0202"},{"msg":"","text":"茶叶","value":"B0022"},{"msg":"申请成为该行业商家,请提交:1. 《酒类经营许可证》或者2. 《酒类销售许可证》","text":"酒类","value":"B0023"},{"msg":"申请成为该行业商家,请提交:1. 《烟草专卖零售许可证》或者2. 《烟草专卖批发企业许可证》或者3. 《烟草专卖生产企业许可证》","text":"烟草/雪茄","value":"B0024"},{"msg":"","text":"营养品/保健品","value":"B0025"},{"msg":"","text":"服饰鞋包","value":"B0026"},{"msg":"","text":"美妆个护","value":"B0027"},{"msg":"","text":"黄金珠宝/钟表饰品","value":"B0028"},{"msg":"","text":"眼镜店","value":"B0029"},{"msg":"","text":"3C数码/家用电器","value":"B0030"},{"msg":"","text":"办公用品","value":"B0203"},{"msg":"","text":"图文音像/工美乐器","value":"B0031"},{"msg":"申请成为该行业商家,请提交:1. 《营业执照》","text":"母婴用品/儿童玩具","value":"B0032"},{"msg":"","text":"宠物/宠物用品","value":"B0033"},{"msg":"","text":"户外运动器材","value":"B0034"},{"msg":"","text":"五金建材","value":"B0035"},{"msg":"","text":"家居家纺","value":"B0216"},{"msg":"","text":"鲜花/绿植","value":"B0036"},{"msg":"申请成为该行业商家,请提交:1. 《文物复制品销售许可证》或者2. 《文物复制许可证》或者3. 《文物经营许可证》","text":"文物经营/文物复制品","value":"B0037"},{"msg":"","text":"计生用品","value":"B0038"},{"msg":"申请成为该行业商家,请提交:1. 《烟花爆竹安全生产许可证》或者2. 《烟花爆竹经营(零售)许可证》或者3. 《烟花爆竹经营(批发)许可证》或者4. 《烟花爆竹经营批发(含进出口)许可证》","text":"烟花爆竹","value":"B0039"},{"msg":"申请成为该行业商家,请提交:1. 《危险化学品经营许可证》","text":"危险化工产品","value":"B0040"},{"msg":"申请成为该行业商家,请提交:1. 《成品油零售经营批准证书》或者2. 营业执照经营范围包含销售/批发汽油、煤油、柴油、天然气、成品油、加油卡、加油服务","text":"石油及石油产品","value":"B0041"},{"msg":"","text":"工业产品","value":"B0042"},{"msg":"","text":"其他专业零售店","value":"B0043"},{"msg":"","text":"互联网综合电商平台","value":"B0114"},{"msg":"","text":"互联网垂直电商平台","value":"B0115"},{"msg":"","text":"社区团购服务平台","value":"B0118"}],"text":"零售批发","value":"A0002"},{"children":[{"msg":"","text":"美发/美容/美甲服务","value":"B0044"},{"msg":"","text":"洗浴/保健养生服务","value":"B0045"},{"msg":"","text":"家政/清洁服务","value":"B0046"},{"msg":"","text":"电器/家具/其他维修","value":"B0047"},{"msg":"","text":"建筑装饰/装修服务","value":"B0048"},{"msg":"","text":"地产/房屋中介代理","value":"B0049"},{"msg":"","text":"宠物医院/其他宠物服务","value":"B0050"},{"msg":"","text":"数码/娱乐设备租赁","value":"B0051"},{"msg":"","text":"无人值守自助服务","value":"B0052"},{"msg":"","text":"共享充电宝及其他共享租赁","value":"B0212"},{"msg":"","text":"无人值守自助零售","value":"B0213"},{"msg":"","text":"无人值守自助娱乐","value":"B0214"},{"msg":"","text":"婚介/婚庆/摄影服务","value":"B0053"},{"msg":"","text":"广告/会展/图文印刷","value":"B0054"},{"msg":"申请成为该行业商家,请提交:1. 《律师事务所执业许可证》","text":"法律咨询/律师事务所","value":"B0055"},{"msg":"","text":"会计/金融咨询服务","value":"B0056"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含企业征信业务和人民银行官网关于公司获取企业征信相关资质公示截图","text":"征信和信用报告咨询服务","value":"B0057"},{"msg":"","text":"人才招聘服务","value":"B0058"},{"msg":"申请成为该行业商家,请提交:1. 《殡葬服务经营许可证》","text":"丧葬服务","value":"B0059"},{"msg":"申请成为该行业商家,请提交:1. 《拍卖经营批准证书》或者2. 营业执照经营范围包含销售/批发汽油、煤油、柴油、天然气、成品油、加油卡、加油服务","text":"拍卖/收藏","value":"B0060"},{"msg":"","text":"其他商业及生活服务","value":"B0061"},{"msg":"","text":"默认行业","value":"B0223"},{"msg":"","text":"生活服务平台","value":"B0116"},{"msg":"","text":"在线工具","value":"B0112"},{"msg":"","text":"物业管理","value":"B0165"}],"text":"商业生活服务","value":"A0003"},{"children":[{"msg":"","text":"歌舞厅/休闲会所/KTV","value":"B0062"},{"msg":"","text":"棋牌桌游/电玩网吧","value":"B0063"},{"msg":"","text":"健身房/瑜伽/舞蹈","value":"B0064"},{"msg":"","text":"院线影城/演出赛事","value":"B0065"},{"msg":"","text":"游乐园/嘉年华","value":"B0066"},{"msg":"","text":"文化场馆","value":"B0067"},{"msg":"","text":"体育场馆","value":"B0068"},{"msg":"申请成为该行业商家,请提交:1. 《彩票销售许可证》","text":"彩票","value":"B0069"},{"msg":"","text":"其他文体娱乐","value":"B0070"},{"msg":"","text":"网络社交","value":"B0108"},{"msg":"申请成为该行业商家,请提交:1. 《网络文化经营许可证》且 营业执照经营范围明确包含相关内容或者2. 《互联网出版许可证》且 营业执照经营范围明确包含相关内容","text":"网络图书/视频/音乐","value":"B0109"},{"msg":"申请成为该行业商家,请提交:1. 《网络文化经营许可证》或者2. 营业执照经营范围包含网络游戏制作、经营、销售、系统服务、技术、计算机、通讯设备、电子产品、互联网、网络技术、网络工程等任意一项业务","text":"游戏","value":"B0110"},{"msg":"申请成为该行业商家,请提交:1. 《网络文化经营许可证》","text":"游戏周边服务/交易平台","value":"B0205"},{"msg":"申请成为该行业商家,请提交:1. 《网络文化经营许可证》且 营业执照经营范围明确包含相关内容","text":"网络直播","value":"B0111"}],"text":"休闲娱乐","value":"A0004"},{"children":[{"msg":"","text":"车辆零配件/用品精品","value":"B0071"},{"msg":"","text":"汽车洗美/维修养护","value":"B0072"},{"msg":"","text":"车辆销售","value":"B0073"},{"msg":"","text":"二手车销售","value":"B0074"},{"msg":"","text":"停车服务","value":"B0075"},{"msg":"","text":"代驾服务","value":"B0076"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含:电瓶车充电,电动车充电相关关键字","text":"电动汽车充换电","value":"B0077"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含:电瓶车充电,电动车充电相关关键字","text":"两轮电瓶车充换电","value":"B0078"},{"msg":"","text":"汽车租赁","value":"B0079"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含公路的投资、建设、收费、养护、管理、高速公路开发经营及服务","text":"ETC不停车自动缴费","value":"B0080"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含公路的投资、建设、收费、养护、管理、高速公路开发经营及服务","text":"MTC半自动车道收费","value":"B0081"},{"msg":"","text":"高速服务区","value":"B0082"},{"msg":"","text":"道路救援","value":"B0083"}],"text":"车主生活","value":"A0005"},{"children":[{"msg":"","text":"公路客运","value":"B0084"},{"msg":"申请成为该行业商家,请提交:1. 《道路运输经营许可证》或者2. 《出租车营运证》","text":"出租车客运","value":"B0085"},{"msg":"","text":"网约车客运","value":"B0086"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含地铁、轻轨、轨道交通服务 ","text":"地铁","value":"B0087"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含公共汽车、客运、公交服务","text":"公共交通","value":"B0088"},{"msg":"","text":"共享两轮车服务","value":"B0089"},{"msg":"申请成为该行业商家,请提交:1. 《成品油零售经营批准证书》或者2. 《燃气经营许可证》或者3. 营业执照经营范围包含销售/批发汽油、煤油、柴油、天然气、成品油、加油卡、加油服务","text":"加油卡、加油服务","value":"B0090"},{"msg":"申请成为该行业商家,请提交:1. 《成品油零售经营批准证书》或者2. 《燃气经营许可证》","text":"加油站、加气站","value":"B0091"},{"msg":"申请成为该行业商家,请提交:1. 《公共航空运输企业经营许可证》","text":"航空公司","value":"B0097"},{"msg":"","text":"机场","value":"B0098"},{"msg":"申请成为该行业商家,请提交:1. 《中国民用航空运输销售代理业务资格认可证书》或2、经营范围包含代售机票业务","text":"机票代理人","value":"B0099"},{"msg":"","text":"航空系统商","value":"B0100"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含铁路运输服务","text":"铁路旅客运输","value":"B0101"},{"msg":"","text":"游轮及巡游航线服务","value":"B0102"}],"text":"交通出行","value":"A0006"},{"children":[{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含物流、货运、仓储、集装箱等相关业务或者2. 《道路运输经营许可证》或者3. 《IATA航空货代资质》或者4. 《无船承运业务经营资格登记证》","text":"物流/快递","value":"B0092"},{"msg":"","text":"快递服务(个人商户)","value":"B0093"},{"msg":"","text":"物流平台","value":"B0217"},{"msg":"","text":"同城即时配送","value":"B0218"},{"msg":"申请成为该行业商家,请提交:1. 关键字匹配,商户名称包含:***邮政管理局(非快递公司,中国邮政不属于国家邮政) ","text":"邮政基本服务","value":"B0094"},{"msg":"","text":"驿站/自提柜","value":"B0095"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含物流、货运、仓储、集装箱等相关业务","text":"仓储","value":"B0096"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含铁路运输服务","text":"铁路货物运输","value":"B0103"},{"msg":"申请成为该行业商家,请提交:1. 《水路运输许可证》或者2. 营业执照内包含水运、船舶、海运的经营范围或客运船票的相关资质","text":"船舶、海运服务提供商","value":"B0104"},{"msg":"","text":"货品停放交易(国际专用)","value":"B0105"},{"msg":"","text":"国际货运代理和报关行","value":"B0106"},{"msg":"","text":"其他运输代理业","value":"B0107"}],"text":"物流运输","value":"A0015"},{"children":[{"msg":"","text":"信息检索服务/网络论坛","value":"B0113"},{"msg":"","text":"互联网数据服务","value":"B0120"},{"msg":"","text":"软件开发服务","value":"B0121"},{"msg":"","text":"数字类产品-游戏(国际专用)","value":"B0122"},{"msg":"","text":"数字类产品-软件提供商(国际专用)","value":"B0123"},{"msg":"","text":"数字类产品-其他(国际专用)","value":"B0124"},{"msg":"","text":"其他在线应用或综合类服务","value":"B0125"},{"msg":"","text":"网络推广/网络广告","value":"B0126"},{"msg":"申请成为该行业商家,请提交:1. 《电信业务经营许可证》或者2. 与运营商的合作协议","text":"电信运营商","value":"B0127"},{"msg":"申请成为该行业商家,请提交:1. 《信息网络传播视听节目许可证》","text":"付费电视","value":"B0128"},{"msg":"","text":"网络电话、传真服务","value":"B0129"}],"text":"网络通讯","value":"A0007"},{"children":[{"msg":"申请成为该行业商家,请提交:1. 教育行政部门出具的审批设立证明或者2. 《事业单位法人证书》","text":"儿童保育服务(公立,含学前教育)","value":"B0130"},{"msg":"申请成为该行业商家,请提交:1. 《民办学校办学许可证》","text":"儿童保育服务(民办,含学前教育)","value":"B0131"},{"msg":"申请成为该行业商家,请提交:1. 教育行政部门出具的审批设立证明或者2. 《事业单位法人证书》","text":"中小学校(公立)","value":"B0132"},{"msg":"申请成为该行业商家,请提交:1. 《民办学校办学许可证》","text":"中小学校(民办)","value":"B0133"},{"msg":"申请成为该行业商家,请提交:1. 教育行政部门出具的审批设立证明或者2. 《事业单位法人证书》","text":"大学与学院(公立)","value":"B0134"},{"msg":"申请成为该行业商家,请提交:1. 《民办学校办学许可证》","text":"大学与学院(民办)","value":"B0135"},{"msg":"申请成为该行业商家,请提交:1. 《事业单位法人证书》或者2. 《民办学校办学许可证》","text":"其他学校/公立培训机构","value":"B0136"},{"msg":"","text":"教育管理机构","value":"B0215"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含:培训、辅导、教育、咨询、活动策划、体育赛事组织策划、健康管理等业务","text":"教育培训机构","value":"B0137"},{"msg":"申请成为该行业商家,请提交:1. 《事业单位法人证书》或者2. 《民办非企业单位登记证书》","text":"少年宫及青少年发展中心","value":"B0138"},{"msg":"","text":"其他教育/培训","value":"B0139"}],"text":"教育培训","value":"A0008"},{"children":[{"msg":"申请成为该行业商家,请提交:1. 《药品经营许可证》或者2. 《互联网药品交易服务证》","text":"医药销售","value":"B0140"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含一类医疗器械或者2. 《第二类医疗器械经营备案凭证》或者3. 《医疗器械经营企业许可证》","text":"医疗器械销售","value":"B0141"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含一类医疗器械或者2. 《第二类医疗器械经营备案凭证》或者3. 《医疗器械经营企业许可证》或者4. 《互联网药品交易服务证》","text":"保健辅助治疗器材","value":"B0142"},{"msg":"申请成为该行业商家,请提交:1. 《医疗机构执业许可证》和《事业单位法人证书》","text":"公立医院","value":"B0143"},{"msg":"申请成为该行业商家,请提交:1. 《医疗机构执业许可证》","text":"社区卫生服务中心","value":"B0144"},{"msg":"申请成为该行业商家,请提交:1. 《医疗机构执业许可证》或者2. 《事业单位法人证书》中业务范围包含公共卫生","text":"专业公共卫生机构","value":"B0145"},{"msg":"申请成为该行业商家,请提交:1. 《医疗机构执业许可证》","text":"民营医院","value":"B0146"},{"msg":"申请成为该行业商家,请提交:1. 《医疗机构执业许可证》或者2. 《中医诊所备案证》","text":"诊所","value":"B0147"},{"msg":"申请成为该行业商家,请提交:1. 《执业医师资格证》","text":"个体医生","value":"B0148"},{"msg":"申请成为该行业商家,请提交:1. 《医疗机构执业许可证》","text":"医疗美容","value":"B0149"},{"msg":"申请成为该行业商家,请提交:1. 《医疗机构执业许可证》","text":"眼科医疗服务","value":"B0150"},{"msg":"申请成为该行业商家,请提交:1. 《医疗机构执业许可证》","text":"口腔医疗服务","value":"B0151"},{"msg":"申请成为该行业商家,请提交:1. 《医疗机构执业许可证》","text":"医学实验室及诊断中心","value":"B0152"},{"msg":"申请成为该行业商家,请提交:1. 银监会关于同意开展消费金融业务的批复或者2. 该协议医院的《医疗机构执业许可证》","text":"线上医疗服务","value":"B0153"},{"msg":"","text":"护理机构服务","value":"B0154"},{"msg":"申请成为该行业商家,请提交:1. 《医疗机构执业许可证》或者2. 营业执照经营范围包含“健康咨询”","text":"体检/健康咨询","value":"B0155"},{"msg":"申请成为该行业商家,请提交:1. 《医疗机构执业许可证》","text":"其他医疗保健服务","value":"B0156"}],"text":"医疗卫生","value":"A0009"},{"children":[{"msg":"","text":"酒店/旅馆/民宿","value":"B0157"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含:旅游","text":"景区","value":"B0158"},{"msg":"申请成为该行业商家,请提交:1. 《旅行社业务经营许可证》或者2. 《旅行社分社备案登记证明》或者3. 《旅行社业务经营许可证》经营范围中须包含出境旅游业务","text":"旅行社和旅游服务","value":"B0159"},{"msg":"申请成为该行业商家,请提交:1. 旅游相关:直销商户授权书、直销员资质或业务代理资质","text":"旅游相关服务直销","value":"B0160"},{"msg":"","text":"风景区系统商","value":"B0219"},{"msg":"","text":"观光车","value":"B0220"},{"msg":"","text":"游船码头","value":"B0221"},{"msg":"","text":"旅游服务平台(OTA)","value":"B0119"}],"text":"酒旅景区","value":"A0010"},{"children":[{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含公共事业的水、电、煤(燃)气等经营和收费相关业务或者2. 非实际水、电、煤等机构来签约,则需要提供水电煤服务提供商授权资质","text":"公共事业(电、气、水)","value":"B0161"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含公共事业的电力经营和收费相关业务或者2. 非实际电力机构来签约,则需要提供电力服务提供商授权资质","text":"公共事业-电力缴费","value":"B0204"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含公共事业的煤(燃)气经营和收费相关业务或者2. 非实际煤(燃)气经营机构来签约,则需要提供煤(燃)气服务提供商授权资质","text":"公共事业-煤气缴费","value":"B0211"},{"msg":"申请成为该行业商家,请提交:1. 营业执照经营范围包含公共事业的自来水经营和收费相关业务或者2. 非实际自来水经营机构来签约,则需要提供自来水服务提供商授权资质","text":"公共事业-自来水缴费","value":"B0206"},{"msg":"申请成为该行业商家,请提交:1. 营业执照范围包含广播电视节目策划、制作、经营、有线电视相关业务","text":"公共事业-有线电视缴费","value":"B0162"},{"msg":"","text":"公共事业-清洁服务缴费","value":"B0207"},{"msg":"","text":"公共事业-其他缴费","value":"B0163"},{"msg":"","text":"话费充值与缴费","value":"B0164"}],"text":"生活缴费","value":"A0011"},{"children":[{"msg":"申请成为该行业商家,请提交:1. 《金融许可证》或者2. 银监会关于同意开展个人贷款业务的批复或者3. 银监会关于同意开展信用卡业务的批复或者4. 银监会关于同意贵司的开业批复","text":"金融机构","value":"B0166"},{"msg":"申请成为该行业商家,请提交:1. 《金融许可证》或者2. 银监会关于同意开展对应业务的批复或开业批复或者3. 金融办关于同意开展对应业务的批复或开业批复或者4. 银行资质存管协议或与持牌金融机构的合作协议","text":"金融机构-其他服务","value":"B0167"},{"msg":"申请成为该行业商家,请提交:1. 《金融许可证》或者2. 《经营保险业务许可证》或者3. 《经营外汇业务许可证》或者4. 《个人本外币兑换特许业务经营许可证》","text":"外币汇兑","value":"B0168"},{"msg":"申请成为该行业商家,请提交:1. 《经营证券期货业务许可证》或者2. 证监会关于同意开展证券经营业务的批复、证监会及其派出机构颁布的基金类业务相关资格证书","text":"股票基金服务","value":"B0169"},{"msg":"申请成为该行业商家,请提交:1. 《小额贷款公司经营许可证》或者2. 金融办关于同意该公司(名称中带“小额贷款”字样)开业的批复","text":"小贷公司","value":"B0170"},{"msg":"申请成为该行业商家,请提交:1. 与持牌的消费金融公司、小贷公司、银行等持牌机构的业务合作协议,且协议内容需要体现平台用户的放款由对应合作机构发放。注:若最终资金端未体现直接合作,则需补充提交与合作方最终资金端的合作协议。","text":"借贷消费平台","value":"B0171"},{"msg":"申请成为该行业商家,请提交:1. 《金融许可证》或者2. 银监会关于同意开展融资租赁业务的批复","text":"融资租赁公司","value":"B0172"},{"msg":"申请成为该行业商家,请提交:1. 《金融许可证》或者2. 银监会关于同意开展金融租赁业务的批复","text":"金融租赁公司","value":"B0173"},{"msg":"申请成为该行业商家,请提交:1. 《金融许可证》或者2. 银监会关于同意开展汽车金融业务的批复","text":"汽车金融公司","value":"B0174"},{"msg":"申请成为该行业商家,请提交:1. 《金融许可证》或者2. 银监会关于同意开展消费金融业务的批复","text":"消费金融公司","value":"B0175"},{"msg":"申请成为该行业商家,请提交:1. 《金融许可证》或者2. 银监会关于同意开展信托业务的批复","text":"信托公司","value":"B0176"},{"msg":"申请成为该行业商家,请提交:1. 《支付业务许可证》(中国人民银行颁发)","text":"支付机构","value":"B0177"},{"msg":"申请成为该行业商家,请提交:1. 《融资性担保机构经营许可证》或者2. 金融办关于同意该公司(名称含有“融资担保”字样)开业的批复","text":"融资担保公司","value":"B0178"},{"msg":"","text":"其他金融服务","value":"B0179"},{"msg":"申请成为该行业商家,请提交:1. 《保险公司法人许可证》或者2. 《经营保险业务许可证》或者3. 《保险营销服务许可证》或者4. 《经营保险代理业务许可证》或者5. 《经营保险经纪业务许可证》或者6. 《经营保险公估业务许可证》或者7. 《保险兼业代理业务许可证》或者8. 保险资产管理:直销商户授权书、直销员资质或业务代理资质","text":"保险业务/保险代理","value":"B0180"},{"msg":"申请成为该行业商家,请提交:1. 《典当经营许可证》","text":"典当","value":"B0181"}],"text":"金融理财","value":"A0012"},{"children":[{"msg":"申请成为该行业商家,请提交:1. 关键字匹配,商户名称包含:***财政局(厅)/公安局(厅)/行政执法队/警察总队/人民政府(办公厅、室)/***人力资源和社会保障****中心(局、办公室)/***公积金管理中心/***医保局/**医疗保障局","text":"政府机构","value":"B0182"},{"msg":"申请成为该行业商家,请提交:1. 关键字匹配,商户名称包含:***财政局(厅)/公安局(厅)/行政执法队/警察总队","text":"行政费用和罚款(非税)","value":"B0183"},{"msg":"申请成为该行业商家,请提交:1. 关键字匹配,商户名称包含:***财政局(厅)/公安局(厅)/行政执法队/警察总队/人民政府(办公厅、室)/***人力资源和社会保障****中心(局、办公室)/***公积金管理中心","text":"公积金","value":"B0184"},{"msg":"申请成为该行业商家,请提交:1. 关键字匹配,商户名称包含:公安局(厅)/行政执法队/警察总队","text":"公安交管","value":"B0185"},{"msg":"申请成为该行业商家,请提交:1. 关键字匹配,商户名称包含:***医保局/**医疗保障局","text":"医保","value":"B0186"},{"msg":"申请成为该行业商家,请提交:1. 关键字匹配,商户名称包含:社会保障,常见名称为:***人力资源和社会保障****中心/局/办公室","text":"社会保障服务","value":"B0187"},{"msg":"申请成为该行业商家,请提交:1. 关键字匹配,商户名称包含:***财政局(厅)/公安局(厅)/行政执法队/警察总队/人民政府(办公厅、室)/***人力资源和社会保障****中心(局、办公室)/***公积金管理中心","text":"政府采购","value":"B0188"},{"msg":"","text":"文体机构","value":"B0222"},{"msg":"","text":"政府贷款","value":"B0189"},{"msg":"申请成为该行业商家,请提交:1. 关键字匹配,商户名称包含:***法院","text":"法庭费用","value":"B0190"},{"msg":"申请成为该行业商家,请提交:1. 关键字匹配,商户名称包含:***公安局(厅)","text":"保释金","value":"B0191"},{"msg":"申请成为该行业商家,请提交:1. 关键字匹配,商户名称包含:***税务局","text":"税务","value":"B0192"},{"msg":"申请成为该行业商家,请提交:1. 《社会团体法人证书》或者2. 《民办非企业单位登记证书》且业务范围包含公益/慈善/捐赠/捐款/志愿服务/扶贫/社会工作","text":"慈善和社会公益服务","value":"B0193"},{"msg":"申请成为该行业商家,请提交:1. 关键字匹配,商户名称包含:*****驻华大使馆","text":"使领馆","value":"B0194"},{"msg":"申请成为该行业商家,请提交:1. 《社会团体法人证书》","text":"行业协会和专业社团","value":"B0195"},{"msg":"","text":"汽车协会","value":"B0196"},{"msg":"申请成为该行业商家,请提交:1. 《宗教活动场所登记证》","text":"宗教组织","value":"B0197"},{"msg":"","text":"其他会员组织","value":"B0198"},{"msg":"","text":"中国共产党机关","value":"B0208"}],"text":"公共管理和社会组织","value":"A0013"},{"children":[{"msg":"","text":"集团行业","value":"B0209"}],"text":"集团类目","value":"A0014"}] \ No newline at end of file diff --git a/commons/class/list.js b/commons/class/list.js new file mode 100644 index 0000000..ee1e210 --- /dev/null +++ b/commons/class/list.js @@ -0,0 +1,48 @@ +import { + reactive, ref +} from 'vue'; +function isSameType(a, b) { + return a instanceof b === true || b instanceof a === true; +} +class LIST{ + constructor(data) { + this.data=reactive({ + page:0, + totalPage:0, + total:0, + list:[], + hasAjax:false, + status:'',//loading fail success + query:{ + + } + }) + Object.assign(this.data, data) + } + add(item){ + this.data.list.push(item) + } + del(index){ + this.data.list.splice(index,1) + } + update(index,item){ + this.data.list[index]=item + } + get(index){ + return this.data.list[index] + } + getVal(key){ + return this.data[key] + } + setQuery(key,val){ + this.data.query[key]=val + } + setVal(key,val){ + this.data[key]=val + if(key=='page'){ + this.data['page']=val + } + } +} + +export default LIST \ No newline at end of file diff --git a/commons/color.js b/commons/color.js new file mode 100644 index 0000000..5987b9e --- /dev/null +++ b/commons/color.js @@ -0,0 +1,7 @@ +export const ColorMain= '#318AFE'; +export const ColorRed= '#F02C45'; + + +export default{ + ColorMain,ColorRed +} diff --git a/commons/goodsData.js b/commons/goodsData.js new file mode 100644 index 0000000..3fa480a --- /dev/null +++ b/commons/goodsData.js @@ -0,0 +1,74 @@ +import dayjs from "dayjs"; +export const $types = [{ + title: "计量商品", + desc: '单价购买', + value: 'normal' + }, + { + title: "多规格", + desc: '多种不同规格', + value: 'sku' + }, + { + title: "套餐组合", + desc: '选择多种组合', + value: 'group' + }, + { + title: "称重商品", + desc: '按重量售卖', + value: 'weight' + }, + { + title: "时价商品", + desc: '收银端可更改价格', + value: 'currentPrice' + } +] + +// 商品默认sku +export const $defaultSku = { + salePrice: '', + memberPrice: '', + costPrice: '', + originPrice: '', + // stockNumber: '', + firstShared: '', + suit: 1, + barCode: `${uni.getStorageSync("shopId")}${dayjs().valueOf()}`, +} + + +// 库存记录筛选类型 +export const $invoicingType = [{ + text: '全部', + value: '' + }, + { + text: '供应商入库', + value: 'purveyor' + }, + { + text: '供应商退货', + value: 'reject' + }, + { + text: '其他入库', + value: 'purchase' + }, + { + text: '其他出库', + value: 'other-out' + } +] + +// 页面常用数据 +export const $pageData = { + query: { + page: 0, + size: 10 + }, + totalElements: 0, + list: [], + hasAjax: false, +} \ No newline at end of file diff --git a/commons/orderEnum.js b/commons/orderEnum.js new file mode 100644 index 0000000..c472261 --- /dev/null +++ b/commons/orderEnum.js @@ -0,0 +1,84 @@ +export default { + status: [ + { + key: 'unpaid', + label: '待支付' + }, + { + key: 'unsend', + label: '待发货' + }, + { + key: 'closed', + label: '订单完成' + }, + { + key: 'send', + label: '已发' + }, + { + key: 'refunding', + label: '申请退单' + }, + { + key: 'refund', + label: '退单' + }, + { + key: 'cancelled', + label: '取消订单' + }, + { + key: 'merge', + label: '合台' + }, + { + key: 'pending', + label: '挂单' + }, + { + key: 'activate', + label: '激活' + }, + { + key: 'paying', + label: '支付中' + } + ], + sendType: [ + { + key: 'post', + label: '快递' + }, + { + key: 'takeaway', + label: '外卖' + }, + { + key: 'takeself', + label: '自提' + }, + { + key: 'table', + label: '堂食' + } + ], + orderType: [ + { + key: 'cash', + label: '收银' + }, + { + key: 'miniapp', + label: '小程序' + }, + { + key: 'offline', + label: '线下' + }, + { + key: 'return', + label: '退单' + } + ] +} \ No newline at end of file diff --git a/commons/readme.txt b/commons/readme.txt new file mode 100644 index 0000000..592624a --- /dev/null +++ b/commons/readme.txt @@ -0,0 +1,14 @@ +该文件夹内放置: 项目自建资源, 比如 公共样式文件, 和 工具包等文件。 + + +目录结构: +commons + style + utils + +知识点: 样式文件不应该放置到 static文件夹内(css、less/scss 等资源不要放在 static 目录下,建议这些公用的资源放在自建的 common 目录下。), 详见: +https://uniapp.dcloud.net.cn/tutorial/project.html + + + + diff --git a/commons/style/common.scss b/commons/style/common.scss new file mode 100644 index 0000000..b6b3ec8 --- /dev/null +++ b/commons/style/common.scss @@ -0,0 +1,406 @@ +.u-relative, +.u-rela { + position: relative; +} + +.u-absolute, +.u-abso { + position: absolute; +} +.u-fixed,.u-fix{ + position: fixed; +} +.left-top{ + left: 0; + top: 0; +} +.u-overflow-hide{ + overflow: hidden; +} + +// nvue不能用标签命名样式,不能放在微信组件中,否则微信开发工具会报警告,无法使用标签名当做选择器 +/* #ifndef APP-NVUE */ +image { + display: inline-block; +} + +// 在weex,也即nvue中,所有元素默认为border-box +view, +text { + box-sizing: border-box; +} +/* #endif */ + +.u-font-xs { + font-size: 22rpx; +} + +.u-font-sm { + font-size: 26rpx; +} + +.u-font-md { + font-size: 28rpx; +} + +.u-font-lg { + font-size: 30rpx; +} + +.u-font-xl { + font-size: 34rpx; +} + +.u-flex { + /* #ifndef APP-NVUE */ + display: flex; + /* #endif */ + flex-direction: row; + align-items: center; +} + +.u-flex-wrap { + flex-wrap: wrap; +} + +.u-flex-nowrap { + flex-wrap: nowrap; +} + +.u-col-center { + align-items: center; +} + +.u-col-top { + align-items: flex-start; +} + +.u-col-bottom { + align-items: flex-end; +} + +.u-row-center { + justify-content: center; +} + +.u-row-left { + justify-content: flex-start; +} + +.u-row-right { + justify-content: flex-end; +} + +.u-row-between { + justify-content: space-between; +} + +.u-row-around { + justify-content: space-around; +} + +.u-text-left { + text-align: left; +} + +.u-text-center { + text-align: center; +} + +.u-text-right { + text-align: right; +} + +.u-flex-col { + /* #ifndef APP-NVUE */ + display: flex!important; + /* #endif */ + flex-direction: column!important; +} + +// 定义flex等分 +@for $i from 0 through 12 { + .u-flex-#{$i} { + flex: $i; + } +} + +// 定义字体(px)单位,小于20都为px单位字体 +@for $i from 9 to 20 { + .u-font-#{$i} { + font-size: $i + px; + } +} + +// 定义字体(rpx)单位,大于或等于20的都为rpx单位字体 +@for $i from 20 through 40 { + .u-font-#{$i} { + font-size: $i + rpx; + } +} + +// 定义内外边距,历遍1-80 +@for $i from 0 through 80 { + // 只要双数和能被5除尽的数 + @if $i % 2 == 0 or $i % 5 == 0 { + // 得出:u-margin-30或者u-m-30 + .u-margin-#{$i}, .u-m-#{$i} { + margin: $i + rpx!important; + } + + // 得出:u-padding-30或者u-p-30 + .u-padding-#{$i}, .u-p-#{$i} { + padding: $i + rpx!important; + } + + @each $short, $long in l left, t top, r right, b bottom { + // 缩写版,结果如: u-m-l-30 + // 定义外边距 + .u-m-#{$short}-#{$i} { + margin-#{$long}: $i + rpx!important; + } + + // 定义内边距 + .u-p-#{$short}-#{$i} { + padding-#{$long}: $i + rpx!important; + } + + // 完整版,结果如:u-margin-left-30 + // 定义外边距 + .u-margin-#{$long}-#{$i} { + margin-#{$long}: $i + rpx!important; + } + + // 定义内边距 + .u-padding-#{$long}-#{$i} { + padding-#{$long}: $i + rpx!important; + } + } + } +} + +// 重置nvue的默认关于flex的样式 +.u-reset-nvue { + flex-direction: row; + align-items: center; +} + +/* start--文本行数限制--start */ +.u-line-1 { + overflow: hidden; + white-space: nowrap; + text-overflow: ellipsis; +} + +.u-line-2 { + -webkit-line-clamp: 2; +} + +.u-line-3 { + -webkit-line-clamp: 3; +} + +.u-line-4 { + -webkit-line-clamp: 4; +} + +.u-line-5 { + -webkit-line-clamp: 5; +} + +.u-line-2, .u-line-3, .u-line-4, .u-line-5 { + overflow: hidden; + word-break: break-all; + text-overflow: ellipsis; + display: -webkit-box; // 弹性伸缩盒 + -webkit-box-orient: vertical; // 设置伸缩盒子元素排列方式 +} + +/* end--文本行数限制--end */ + + +/* start--不同颜色文字--start */ +.color-333{ + color: #333; +} +.color-666{ + color: #666; +} +.color-999{ + color: #999; +} +.color-red{ + color: $my-red-color; +} +.color-main{ + color:$my-main-color +} + +/* end--不同颜色文字--end */ + + +.tranistion{ + transition: all .3s ease-in-out; +} +.tranistion-1{ + transition: all .1s ease-in-out; +} +.tranistion-2{ + transition: all .2s ease-in-out; +} +.font-bold{ + font-weight: 700; +} + + +/* start--不同颜色背景--start */ +.my-bg-main{ + background-color:$my-main-color +} + +/* end--不同颜色背景--end */ + +.safe-page{ + padding-bottom: 60rpx!important; +} +::v-deep .uni-switch-input.uni-switch-input-checked{ + border-color: $my-main-color; + background-color: $my-main-color; +} +.min-page{ + /* #ifdef H5 */ + min-height: calc(100vh - 44px); + /* #endif */ + /* #ifndef H5 */ + min-height: 100vh; + /* #endif */ +} +.w-full{ + width: 100%; +} +.gap-20{ + gap: 20rpx; +} +.color-000{ + color: #000; +} +.color-fff{ + color: #fff; +} +.bg-fff{ + background-color: #fff; +} +.bg-gray{ + background-color: #F9F9F9; +} +.overflow-hide{ + /* #ifdef H5 */ + height: calc(100vh - 44px); + /* #endif */ + /* #ifndef H5 */ + height: 100vh; + /* #endif */ + overflow: hidden; +} +.no-wrap{ + white-space: nowrap; +} +.border-r-12{ + border-radius: 12rpx; +} +.border-r-18{ + border-radius: 18rpx; +} +.border-top{ + border-top: 1px solid #E5E5E5; +} +.border-bottom{ + border-bottom: 1px solid #E5E5E5; +} +.scale7{ + transform: scale(0.7); +} +.page-gray { + min-height: calc(100vh); + /* #ifdef H5 */ + min-height: calc(100vh - var(--window-top)); + /* #endif */ + display: flex; + flex-direction: column; + background: #F9F9F9; +} +.box-shadow{ + box-shadow: 0 0 5px #eee; +} +.safe-bottom{ + padding-bottom: env(safe-area-inset-bottom); + /* #ifdef H5 */ + padding-bottom: 28rpx; + /* #endif */ +} +.position-all{ + left: 0; + right: 0; + top: 0; + bottom: 0; +} +.fixed-top{ + position: fixed; + /* #ifdef H5 */ + top: 44px; + /* #endif */ + /* #ifndef H5 */ + top: 0; + /* #endif */ + left: 0; + right: 0; +} +.lh30 { + line-height: 30px; +} +.default-box-padding{ + padding: 32rpx 28rpx; +} +.icon-arrow-down-fill { + width: 16rpx; + height: 10rpx; +} +.zIndex-999{ + z-index: 999; +} +.icon-default-size{ + width: 28rpx; + height: 28rpx; +} +::v-deep.uni-easyinput__placeholder-class{ + font-size: 28rpx!important; +} +.filter-gray{ + filter: grayscale(1); +} +// .u-font-20{ +// font-size: 10px; +// } +// .u-font-24{ +// font-size: 12px; +// } +// .u-font-28{ +// font-size: 14px; +// } +// .u-font-32{ +// font-size: 16px; +// } +.line-th{ + text-decoration: line-through; +} +//覆盖u-view-plus 颜色 +.u-primary-light { + color: $my-main-color; +} +::v-deep .u-border{ + border-width: 1px!important; +} + +::v-deep .u-m-t-16 .u-textarea{ + border-width: 1px!important; +} \ No newline at end of file diff --git a/commons/style/global.scss b/commons/style/global.scss new file mode 100644 index 0000000..a3e94e8 --- /dev/null +++ b/commons/style/global.scss @@ -0,0 +1,230 @@ +/** + * 系统级别: 全局样式 + * + * @site https://www.jeequan.com + * @date 2022/11/22 07:29 + */ + +/** 已整理 **/ + + +// 通用 列表页样式 +.page-wrapper { + min-height: calc(100vh - 70rpx); /** 最小高度 **/ + padding-bottom: 70rpx; /** 安全距离(防止home条遮挡文字) **/ + background-color: $v-color-bgrey; /** 全局背景灰 **/ +} + +// 底部 固定的按钮, 比如: 创建门店, 创建员工等按钮。 +.list-footer{ + height: 100rpx; + background: transparent; + .button-wrapper { + border-top: 1rpx solid rgba(0,0,0, 0.07); + background-color: rgba(252, 252, 252, 0.85); + backdrop-filter: blur(20rpx); + position: fixed; + left: 0; + right: 0; + bottom: 0; + padding: 30rpx; + } +} + + +/** 详情页 覆写:list-item */ +.list-item-by-detail { + padding: 60rpx 60rpx 10rpx 60rpx !important; + background-color: transparent !important; /** 背景透明 **/ + .list-title{ + color: #fff !important; + } + .list-subtitle{ + color: rgba(251,252,253,0.7) !important; + } + .list-info { + image { + margin-right: 0 !important; + } + } +} + +/**列表条目渲染, 比如: 头像、 主标题, **/ +.list-item { + display: flex; + align-items: center; + padding: 0 40rpx; + height: 170rpx; + background-color: #FFF; /** 背景 白色 **/ + image { + flex-shrink: 0; + flex-grow: 0; + width: 100rpx; + height: 100rpx; + margin-right: 30rpx; + } + .list-info { + flex: 1; + .list-title { + display: flex; + justify-content: space-between; + align-items: center; + height: 40rpx; + color: rgba(77,77,77,1); + .list-name { + width: auto; + flex: 1; + display: flex; + align-items: center; + font-size: 30rpx; + font-weight: 400; + } + } + .list-subtitle { + color: rgba(153, 153, 153, 1); + margin-top: 25rpx; + font-size: 26rpx; + font-weight: 400; + width: 430rpx; + } + } +} + + +/** 状态小圆点 **/ +.state-dot { + display: flex; + align-items: center; + font-size: 30rpx; + font-weight: 400; + &::after { + content: ''; + display: block; + margin-left: 20rpx; + width: 20rpx; + height: 20rpx; + border-radius: 50%; + } +} + +/** 状态小圆点 **/ +.state-dot-enable { + &::after { + background-color: #168FFF; + } + +} + +/** 状态小圆点 **/ +.state-dot-disable { + &::after { + background-color: #D9D9D9; + } +} + +/** 状态小圆点 **/ +.state-dot-error { + &::after { + background-color: red; + } +} + + +/** + * 描述预览图, 参考: app详情 + * 第一个最后一个距离上下 40rpx, 中间间距20rpx + */ +.desc-view { + .desc-view-item { + display: flex; + justify-content: space-between; + padding: 20rpx 40rpx; + font-size: 30rpx; + font-weight: 400; + + .title { + color: #808080; + } + .desc { + color: #000; + } + + &:first-child { + margin-top: 20rpx; + } + &:last-child { + margin-bottom: 20rpx; + } + } +} + +/** 已整理 **/ + + + + +//容器内部元素上下左右居中 +.flex-center { + display: flex; + justify-content: center; + align-items: center; +} +// 触摸反馈样式 +.touch-hover { + background-color: #f7f8fa !important ; +} +.touch-button { + opacity: 0.5; +} +/* 单行文本超出省略号 */ +.single-text-beyond { + overflow: hidden; /*超出部分隐藏*/ + white-space: nowrap; /*禁止换行*/ + text-overflow: ellipsis; /*省略号*/ +} +// 按钮背景样式 +.footer-button-style { + border-top: 1rpx solid #fcfcfc; + background-color: rgba(252, 252, 252, 0.85); + backdrop-filter: blur(20rpx); +} +// 搜素框 提示语样式 +.input-placeholder { + font-size: 32rpx; + color: rgba(0, 0, 0, 0.35); +} + + +// 表单分割线 +.line { + height: 20rpx; + background-color: $v-color-bgrey; +} + + + +/** + * jeepay-btn 通用btn样式。 + * 用法: + */ +.jeepay-btn { + display: flex; + justify-content: center; + align-items: center; + height: 110rpx; + font-size: 33rpx; + font-weight: 500; + color: $J-color-tff; + border-radius: 20rpx; + background: linear-gradient(270deg, rgba(35,143,252,1) 0%, rgba(26,102,255,1) 100%); + box-shadow: 0 20rpx 60rpx -20rpx rgba(0,84,210,0.5); + &.hover-button { + opacity: 0.5; + } +} + +/** 输入框icon **/ +.input-icon{ + width: 36rpx; + height: 36rpx; +} diff --git a/commons/style/reset-uni-form.scss b/commons/style/reset-uni-form.scss new file mode 100644 index 0000000..a78d604 --- /dev/null +++ b/commons/style/reset-uni-form.scss @@ -0,0 +1,6 @@ +::v-deep .uni-easyinput__content-input{ +height: initial; +} +::v-deep .uni-forms-item{ + min-height: initial; +} diff --git a/commons/style/uni-overwrite.scss b/commons/style/uni-overwrite.scss new file mode 100644 index 0000000..94b7fb7 --- /dev/null +++ b/commons/style/uni-overwrite.scss @@ -0,0 +1,181 @@ +/** + * 系统级别:覆写 uni样式 + * + * @site https://www.jeequan.com + * @date 2022/11/22 07:29 + */ + + + + +/* 去除开关右侧边距 */ +.uni-switch-input { + margin-right: 0 !important; +} + +/* .uni-navbar { + position: relative; + z-index: 10; +} */ +.uni-popup{ + z-index: 998 !important; +} +// 表单组件样式 覆写 +.uni-forms-item { + display: flex; + align-items: center; + min-height: 120rpx; + background-color: $J-bg-ff; + font-size: 32rpx; + font-weight: 400; +} +.uni-forms-item ::v-deep .uni-forms-item__label { + font-size: 32rpx !important; + font-weight: 400; + text-indent: 40rpx; + color: #4d4d4d; + height: auto !important; +} + +// uni-form-item 表单校验, 如果校验不通过, 显示的文字占位, 并且添加下边距。 +.uni-forms-item__error.msg--active{ + position: relative !important; + margin-bottom: 30rpx; +} + + +.is-input-error-border .uni-easyinput__placeholder-class{ + color: #f56c6c !important +} + + +// 去掉按钮边框 +button:after { + border: none !important; +} + +// 去点导航栏组件center&right +::v-deep.uni-navbar__header { + .uni-navbar__header-container, + .uni-navbar__header-btns-right { + display: none !important; + } +} + +// 修改 uuni-easyinput +// form 外层必须包裹一个 view class="jeepay-form" +.jeepay-form { + .uni-easyinput { + .uni-easyinput__content { + border: 2px solid transparent !important; + height: 110rpx; + padding: 0 30rpx; + margin-bottom: 50rpx; + box-sizing: border-box !important; + border-radius: 20rpx !important; + background-color: rgba(247, 247, 247, 1) !important; + } + + .uni-easyinput__content-input { + color: rgba(0, 0, 0, 1); + font-size: 32rpx !important; + font-weight: 400; + } + + .is-foucs { + border: 2px solid #1d79fd !important; + background-color: white !important; + } + + .uni-input-placeholder + /* #ifdef MP-WEIXIN */ + ,.uni-easyinput__placeholder-class + /* #endif */ { + font-size: 32rpx !important; + color: #B3B3B3 !important; + } + } +} + +.jeepay-edit-form .uni-easyinput__content-input { + padding-left: 0 !important; + .uni-input-placeholder { + font-size: 32rpx !important; + } +} + +// 设置新密码覆盖form默认样式 +.new-password { + .uni-forms-item.is-direction-left { + padding: 0 40rpx; + .uni-forms-item__label { + width: 190rpx !important; + font-size: 32rpx !important; + font-weight: 400; + white-space: nowrap; + color: rgba(102, 102, 102, 1); + text-indent: 0 !important; + } + .uni-easyinput__placeholder-class { + font-size: 32rpx !important; + font-weight: 400 !important; + } + } +} + +// 搜索栏覆盖默认样式 +/* #ifdef MP-WEIXIN */ +.input-main { + button { + font-size: 32rpx; + color: rgba(29,121,253,1); + background: rgba(255,255,255,1); + } + .uni-easyinput { + .uni-easyinput__content { + background-color: $J-bg-f5 !important; + border-radius: $J-b-r12; + .uni-easyinput__content-input { + padding-left: 0 !important; + .uni-input-input { + border-radius: $J-b-r12 !important; + overflow: hidden !important; + } + } + .uni-input-placeholder { + font-size: 27rpx; + } + .uni-icons { + color: rgba(230,230,230,1) !important; + } + } + } +} +/* #endif */ + +// 搜索栏覆盖默认样式 +/* #ifdef MP-WEIXIN */ +button[is="components/Button/Button"] { + padding: 0; + background-color: transparent !important; +} +/* #endif */ + +// 修改时间选择器按钮颜色 +.xp-button--confirm { + background: $jeepay-bg-primary; +} +.xp-button--cancel { + color: rgba(0, 0, 0, 0.5) !important; +} +// label 样式 +.f-label{ + width: 280rpx; + align-self: start; + padding-top: 40rpx; + font-size: 32rpx ; + font-weight: 400; + text-indent: 40rpx; + color: #4d4d4d; +} + diff --git a/commons/style/vars.scss b/commons/style/vars.scss new file mode 100644 index 0000000..65ad362 --- /dev/null +++ b/commons/style/vars.scss @@ -0,0 +1,77 @@ +/** + * 系统级别: 自定义变量 + * + * @site https://www.jeequan.com + * @date 2022/11/22 07:29 + */ + +// $v : 表示: variables简写。 uni的默认都有特殊开头, 一般不会重复。 +$v-color-t21: #217dfe; + +// 全局通用: 背景灰 background grey +$v-color-bgrey: #F7F7F7; + +// 背景色 +$J-bg-f7: #f7f7f7; //页面背景色 +$J-bg-ff: #fff; +$J-bg-f5: #f5f5f5; //输入框背景色 + +// 文字颜色 +$J-color-t80: #808080; //常用于 未选中文字颜色 +$J-color-t21: #217dfe; //卡片文字选中 统计报表 +$J-color-tff: #fff; +$J-color-tSff: rgba(255, 255, 255, 0.7); +$J-color-t29: #2980fd; //选中 文字颜色 搜索 +$J-color-ta6: #a6a6a6; +$J-color-t4d: #4d4d4d; //标题颜色 +$J-color-t99: #999; +$J-color-t8c: #8c8c8c; // 卡片列表 标题文字颜色 +//圆角相关变量 +$J-b-r32: 32rpx; +$J-b-r12: 12rpx; +$J-b-r10: 10rpx; +$v-b-r20: 20rpx; + +// 文字大小 +$J-f-size30: 30rpx; + +// 常用边框颜色 +$v-b-color-ed: #ededed; + +//common.scss 分包页面以及组件里所用的颜色 +$my-main-color:#318AFE; +$my-red-color:#F02C45; + +//my-components +$u-main-color: #303133; +$u-content-color: #606266; +$u-tips-color: #909193; +$u-light-color: #c0c4cc; +$u-border-color: #dadbde; +$u-bg-color: #f3f4f6; +$u-disabled-color: #c8c9cc; + +$u-primary: #3c9cff; +$u-primary-dark: #398ade; +$u-primary-disabled: #9acafc; +$u-primary-light: #ecf5ff; + +$u-warning: #f9ae3d; +$u-warning-dark: #f1a532; +$u-warning-disabled: #f9d39b; +$u-warning-light: #fdf6ec; + +$u-success: #5ac725; +$u-success-dark: #53c21d; +$u-success-disabled: #a9e08f; +$u-success-light: #f5fff0; + +$u-error: #f56c6c; +$u-error-dark: #e45656; +$u-error-disabled: #f7b2b2; +$u-error-light: #fef0f0; + +$u-info: #909399; +$u-info-dark: #767a82; +$u-info-disabled: #c4c6c9; +$u-info-light: #f4f4f5; \ No newline at end of file diff --git a/commons/table-status.js b/commons/table-status.js new file mode 100644 index 0000000..4d53960 --- /dev/null +++ b/commons/table-status.js @@ -0,0 +1,38 @@ +export const $status = { + pending: { + label: "挂单中", + type: "#E6A23C", + }, + using: { + label: "开台中", + type: "#fa5555", + }, + paying: { + label: "结算中", + type: "#E6A23C", + }, + idle: { + label: "空闲", + type: "#3F9EFF", + }, + subscribe: { + label: "预定", + type: "rgb(34, 191, 100)", + }, + closed: { + label: "关台", + type: "rgb(221,221,221)", + }, + // opening: { + // label: "开台中", + // type: "#67C23A", + // }, + cleaning: { + label: "待清台", + type: "#FAAD14", + }, + unbind: { + label: "未绑定", + type: "rgb(221,221,221)", + } +} \ No newline at end of file diff --git a/commons/utils/.keep b/commons/utils/.keep new file mode 100644 index 0000000..e69de29 diff --git a/commons/utils/ak.js b/commons/utils/ak.js new file mode 100644 index 0000000..5a0a244 --- /dev/null +++ b/commons/utils/ak.js @@ -0,0 +1,28 @@ +/** + * 统一工具类 (all utils x ) aux ( 谐音 ) [ window 无法创建此命名的文件 放弃。 = = ] + * 统一使用: all Kit 简称 ak. + * + * @author terrfly + * @site https://www.jeepay.vip + * @date 2022/12/12 18:38 + */ + +import go from './go.js' +import emit from './emit.js' +import ent from './ent.js' +import cal from './cal.js' +import dataKit from './dataKit.js' +import timer from './timer.js' +import infoBox from './infoBox.js' + +const ak = { + go: go, + emit: emit, + ent: ent, + cal: cal, + timer: timer, + infoBox: infoBox, +} + +export default ak + diff --git a/commons/utils/cal.js b/commons/utils/cal.js new file mode 100644 index 0000000..b160920 --- /dev/null +++ b/commons/utils/cal.js @@ -0,0 +1,37 @@ +/** + * 数字, 计算相关函数 + * + * @author terrfly + * @site https://www.jeepay.vip + * @date 2022/11/22 10:38 + */ + +/** + * 保留小数n位,不进行四舍五入 + * num你传递过来的数字, + * decimal你保留的几位,默认保留小数后两位 + */ +const formatDecimal = function(num, decimal = 2) { + num = num.toString() + const index = num.indexOf('.') + if (index !== -1) { + num = num.substring(0, decimal + index + 1) + } else { + num = num.substring(0) + } + //截取后保留两位小数 + return parseFloat(num).toFixed(decimal) +} + +const model = { + // 分转元 + // amount - 金额 parseFloat - 是否转换为数字格式, 默认String + cert2Dollar(amount, needParseFloat = false) { + if (needParseFloat) { // parseFlot + return formatDecimal(amount / 100) + } + return formatDecimal(amount / 100) + } +} + +export default model \ No newline at end of file diff --git a/commons/utils/dataKit.js b/commons/utils/dataKit.js new file mode 100644 index 0000000..8dd0691 --- /dev/null +++ b/commons/utils/dataKit.js @@ -0,0 +1,38 @@ +/** + * 数据 工具类 + * + * @author terrfly + * @site https://www.jeepay.vip + * @date 2022/11/30 14:18 + */ + +const model = { + + // 递归遍历树状结构数据 matchFunc 匹配结果, true表示匹配成功, 否则继续匹配。 + // pnode 可不传入 + // 返回结构: [当前数据, 上级数据 ] + recursionTreeData: (treeData, matchFunc, childrenName = 'children', pnode = null ) => { + + for (let i = 0; i < treeData.length; i++) { + + const item = treeData[i] + + // 匹配成功 + if(matchFunc(item)){ + return [item, pnode] + } + + if (item[childrenName] && item[childrenName].length > 0) { + let res = model.recursionTreeData(item[childrenName], matchFunc, childrenName, item) + if(res){ + return res + } + } + } + + } + +} + +export default model + diff --git a/commons/utils/datamap.js b/commons/utils/datamap.js new file mode 100644 index 0000000..a48d464 --- /dev/null +++ b/commons/utils/datamap.js @@ -0,0 +1,164 @@ +/** + * datamap , 数据字典, 存放常用的配置常量信息。 如订单类型的判断, 用户类型的判断。 + * + * + * @author terrfly + * @site https://www.jeepay.vip + * @date 2022/11/28 16:16 + */ + +const payOrderStateMap = { + 0: { + text: '订单生成', + color: '#2980FD' + }, + 1: { + text: '支付中', + color: '#FFAA33' + }, + 2: { + text: '支付成功', + color: '#09BB07' + }, + 3: { + text: '支付失败', + color: '#CB2972' + }, + 4: { + text: '已撤销', + color: '#808080' + }, + 5: { + text: '已退款', + color: '#FF5B4C' + }, + 6: { + text: '订单关闭', + color: '#D9D9D9' + }, +} +// 订单 图片 和背景颜色 +const payOrderImageMap = { + WECHAT: { + title: '微信', + imgUrl: '/static/orderImg/wechat.svg', //微信支付 + bgColor: '#09BB07', + }, + ALIPAY: { + title: '支付宝', + imgUrl: '/static/orderImg/zfb.svg', //支付宝支付 + bgColor: '#458FFF', + }, + YSFPAY: { + title: '云闪付', + imgUrl: '/static/orderImg/ysf.svg', // 云闪付支付 + bgColor: '#FF5B4C', + }, + UNIONPAY: { + title: '银联', + imgUrl: '/static/orderImg/union-pay.svg', //银联支付 + bgColor: '#0D131A', + }, + OTHER: { + title: '其他', + imgUrl: '/static/orderImg/default-pay.svg', //其他支付 + bgColor: '#5F36C4', + }, +} + +// 1-超级管理员 2-普通用户 3-拓展员, 11-店长, 12-店员 +const userTypeMap = { + 1: { + text: '超管', + bgColor: 'linear-gradient(270deg, rgba(35,161,252,1) 0%, rgba(26,102,255,1) 100%)', + type: 'blue' + }, + 2: { + text: '普通用户', + bgColor: 'linear-gradient(270deg, rgba(35,161,252,1) 0%, rgba(26,102,255,1) 100%)' + }, + 3: { + text: '拓展员', + bgColor: 'linear-gradient(270deg, rgba(35,161,252,1) 0%, rgba(26,102,255,1) 100%)' + }, + 11: { + text: '店长', + bgColor: 'linear-gradient(270deg, rgba(220,61,138,1) 0%, rgba(187,23,92,1) 100%)', + type: 'purple' + }, + 12: { + text: '店员', + bgColor: ' linear-gradient(270deg, rgba(61,220,68,1) 0%, rgba(23,187,118,1) 100%)', + type: 'green' + }, +} +// 设备厂商 +const devProvider = { + zgwl: '智谷物联', + bsj: '博实结', + fe: '飞鹅', + ps: '品生', + clj: '财来聚', + wsy: '微收银', + xjl: '小精灵', + lmspay: '立码收', + lkls: '拉卡拉', + zw: '智网' +} + +const rechargeStateMap = { + 0: { + text: '初始化', + color: '#2980FD' + }, + 1: { + text: '充值中', + color: '#FFAA33' + }, + 2: { + text: '充值成功', + color: '#09BB07' + }, + 3: { + text: '充值失败', + color: '#CB2972' + } +} + +const model = { + // 订单状态文本和color + payOrderState: (state) => { + // 避免循环判断,影响性能。 + if (payOrderStateMap[state]) { + return payOrderStateMap[state] + } + + return { + text: '未知', + color: '#D9D9D9' + } + }, + + // 订单图片 和图片背景颜色 + payOrderImage: (state) => { + // 取值 找到 返回当前值 未找到返回空对象 + return payOrderImageMap[state] || {} + }, + + // 用户类型的判断 + userType: (userTypeVal) => { + return userTypeMap[userTypeVal] || {} + }, + // 查找设备厂商 找到就返回 找不到据返回空 + provider: (state) => { + return devProvider[state] || '未知' + }, + + // 会员充值订单图片 和图片背景颜色 + rechargeRecordImage: (state) => { + // 取值 找到 返回当前值 未找到返回空对象 + return rechargeStateMap[state] || {} + }, +} + +export default model \ No newline at end of file diff --git a/commons/utils/dayjs-time.js b/commons/utils/dayjs-time.js new file mode 100644 index 0000000..cd8a29d --- /dev/null +++ b/commons/utils/dayjs-time.js @@ -0,0 +1,30 @@ +import dayjs from 'dayjs'; + +// 获取今天的开始和结束时间 +export function getTodayTimestamps() { + const start = dayjs().startOf('day').format('YYYY-MM-DD HH:mm:ss'); + const end = dayjs().endOf('day').format('YYYY-MM-DD HH:mm:ss'); + return { start, end ,label:'今日'}; +} + +// 获取昨天的开始和结束时间 +export function getYesterdayTimestamps() { + const start = dayjs().subtract(1, 'day').startOf('day').format('YYYY-MM-DD HH:mm:ss'); + const end = dayjs().subtract(1, 'day').endOf('day').format('YYYY-MM-DD HH:mm:ss'); + return { start, end ,label:'昨日'}; +} + +// 获取本周的开始和结束时间 +export function getThisWeekTimestamps() { + const start = dayjs().startOf('week').format('YYYY-MM-DD HH:mm:ss'); + const end = dayjs().endOf('week').format('YYYY-MM-DD HH:mm:ss'); + return { start, end,label:'本周' }; +} + +// 获取本月的开始和结束时间 +export function getThisMonthTimestamps() { + const start = dayjs().startOf('month').format('YYYY-MM-DD HH:mm:ss'); + const end = dayjs().endOf('month').format('YYYY-MM-DD HH:mm:ss'); + return { start, end ,label:'本月'}; +} + \ No newline at end of file diff --git a/commons/utils/debounce.js b/commons/utils/debounce.js new file mode 100644 index 0000000..85551b0 --- /dev/null +++ b/commons/utils/debounce.js @@ -0,0 +1,25 @@ +/** + * @desc 函数防抖 + * @param func 目标函数 + * @param wait 延迟执行毫秒数 + * @param immediate true - 立即执行, false - 延迟执行 + */ +export const debounce = function(func, wait = 1000, immediate = true) { + let timer; + return function() { + let context = this, + args = arguments; + if (timer) clearTimeout(timer); + if (immediate) { + let callNow = !timer; + timer = setTimeout(() => { + timer = null; + }, wait); + if (callNow) func.apply(context, args); + } else { + timer = setTimeout(() => { + func.apply(context, args); + }, wait) + } + } +} \ No newline at end of file diff --git a/commons/utils/emit.js b/commons/utils/emit.js new file mode 100644 index 0000000..293c63d --- /dev/null +++ b/commons/utils/emit.js @@ -0,0 +1,138 @@ +/** + * 页面通讯工具类(uni.emit)的封装 + * + * @author terrfly + * @site https://www.jeequan.com + * @date 2022/11/24 15:54 + */ + +const model = { + + // 定义监听器的名字, 应该是一个页面一个, 不可两个页面公共一个, 否则会导致: 一个页面onUnload 移除时影响另一个页面的正常接收。 + // 业务页面 监听, onUnload应该移除掉。 + + // 通用搜索页 + ENAME_REF_SEARCH_PAGE : 'ENAME_REF_SEARCH_PAGE', + + // 应用列表页的刷新 + ENAME_REF_TABLE_MCH_APP : 'ENAME_REF_TABLE_MCH_APP', + // 应用详情 + ENAME_REF_TABLE_MCH_APP_DETAILS : 'ENAME_REF_TABLE_MCH_APP_DETAILS', + + // 调起扫一扫 + ENAME_E_PAY_SCAN : 'ENAME_E_PAY_SCAN', + // 重置 金额 + ENAME_RESET_PAY_AMOUNT: 'ENAME_RESET_PAY_AMOUNT', + // 更新支付订单信息 + ENAME_REF_PAY_ORDER : 'ENAME_REF_PAY_ORDER', + + // 更新 门店列表 + ENAME_REF_STORE_LIST : 'ENAME_REF_STORE_LIST', + + // 更新 门店详情 + ENAME_REF_STORE_DETAIL : 'ENAME_REF_STORE_DETAIL', + + // 更新 员工列表 + ENAME_REF_SYS_USER_LIST : 'ENAME_REF_SYS_USER_LIST', + + // 更新 员工详情 + ENAME_REF_SYS_USER_DETAIL : 'ENAME_REF_SYS_USER_DETAIL', + + // 更新 通道列表 + ENAME_REF_PAY_PASSAGE_LIST : 'ENAME_REF_PAY_PASSAGE_LIST', + + // 更新 辅助终端信息 + ENAME_REF_TERMINAL_LIST : 'ENAME_REF_TERMINAL_LIST', + + // 更新 辅助终端 详情页 + ENAME_REF_TERMINAL_DETAIL : 'ENAME_REF_TERMINAL_DETAIL', + + // 更新 智能pos 信息 + ENAME_REF_AUTOPOS_LIST : 'ENAME_REF_AUTOPOS_LIST', + + // 更新 智能pos 详情页 + ENAME_REF_AUTOPOS_DETAIL : 'ENAME_REF_AUTOPOS_DETAIL', + + // 更新 扫码pos 信息 + ENAME_REF_SCANPOS_LIST : 'ENAME_REF_SCANPOS_LIST', + + // 更新 扫码pos 详情页 + ENAME_REF_SCANPOS_DETAIL : 'ENAME_REF_SCANPOS_DETAIL', + // 码牌列表 + ENAME_REF_QRC_LIST : 'ENAME_REF_QRC_LIST', + + // 码牌详情 + ENAME_REF_QRC_DETAIL : 'ENAME_REF_QRC_DETAIL', + // 更新 打印机 信息 + ENAME_REF_PRINTER_LIST : 'ENAME_REF_PRINTER_LIST', + + // 更新 打印机 详情页 + ENAME_REF_PRINTER_DETAIL : 'ENAME_REF_PRINTER_DETAIL', + + // 云喇叭列表 + ENAME_REF_SPEAKER_LIST : 'ENAME_REF_SPEAKER_LIST', + + // 云喇叭详情 + ENAME_REF_SPEAKER_DETAIL : 'ENAME_REF_SPEAKER_DETAIL', + + + // 进件列表 + ENAME_REF_APPLYMENT_LIST : 'ENAME_REF_APPLYMENT_LIST', + + // 刷脸设备列表 + ENAME_REF_FACE_LIST : 'ENAME_REF_FACE_LIST', + // 刷脸设备详情 + ENAME_REF_FACE_DETAIL : 'ENAME_REF_FACE_DETAIL', + + // 刷脸广告列表 + ENAME_REF_AD_LIST : 'ENAME_REF_AD_LIST', + + // 刷脸广告 详情 + ENAME_REF_AD_DETAILS : 'ENAME_REF_AD_DETAILS', + + // 更新 会员列表 + ENAME_REF_MEMBER_LIST : 'ENAME_REF_MEMBER_LIST', + + // 更新 会员详情 + ENAME_REF_MEMBER_DETAIL : 'ENAME_REF_MEMBER_DETAIL', + + // 更新 会员账户流水列表 + ENAME_REF_MEMBER_ACCOUNT_HISTORY_LIST : 'ENAME_REF_MEMBER_ACCOUNT_HISTORY_LIST', + + // 更新 会员账户流水详情 + ENAME_REF_MEMBER_ACCOUNT_HISTORY_DETAIL : 'ENAME_REF_MEMBER_ACCOUNT_HISTORY_DETAIL', + + // 更新 会员充值记录列表 + ENAME_REF_MEMBER_RECHARGE_RECORD_LIST : 'ENAME_REF_MEMBER_RECHARGE_RECORD_LIST', + + // 更新 会员充值记录详情 + ENAME_REF_MEMBER_RECHARGE_RECORD_DETAIL : 'ENAME_REF_MEMBER_RECHARGE_RECORD_DETAIL', + + // 更新 充值规则列表 + ENAME_REF_RECHARGE_RULE_LIST : 'ENAME_REF_RECHARGE_RULE_LIST', + + // 刷新页面的 发射事件 , 更新页面 && 更新搜索页面 + refPageAndSearchEmit: (refEmitEventName, data = {} ) => { + model.pageEmit(refEmitEventName, data) + model.pageEmit(model.ENAME_REF_SEARCH_PAGE, data) + }, + + // 自定义 + pageEmit: (refEmitEventName, data) => { + uni.$emit(refEmitEventName, data ) + }, + + + + // 废弃该函数。 ( 因为: 页面只监听一次, 使用该函数则无法再次监听, 需要再每个页面写入: uni.$on 保证正常接收。 ) + // 监听页面刷新函数 + on: (refEmitEventName) => { + return new Promise( (resolve) => { + uni.$on(refEmitEventName, function(data){ + resolve( data ) + }) + }) + } +} + +export default model \ No newline at end of file diff --git a/commons/utils/encryptUtil.js b/commons/utils/encryptUtil.js new file mode 100644 index 0000000..95881ce --- /dev/null +++ b/commons/utils/encryptUtil.js @@ -0,0 +1,72 @@ +/** + * 加解密工具包 + * + * @author terrfly + * @site https://www.jeepay.vip + * @date 2021/5/16 17:35 + */ +import { SM4 } from 'gm-crypto' +import appConfig from '@/config/appConfig.js' + +let HEX_KEY = null + +// 字符串转16进制 +function str2hex(str) { + var val = '' + for (var i = 0; i < str.length; i++) { + if (val == '') + val = str.charCodeAt(i).toString(16) + else + val += str.charCodeAt(i).toString(16) + } + val += '' + return val +} + +// 获取hex秘钥 +function getHexKey(){ + + if(!HEX_KEY){ + + HEX_KEY = str2hex(appConfig.encryptKey) + + } + return HEX_KEY +} + + +// 解密 (http响应数据, 做通用处理) +export function sm4DecryptByResData(data){ + + if(!data){ + return data + } + + let res = SM4.decrypt(data, getHexKey(), { + inputEncoding: 'base64', + outputEncoding: 'utf8' + }) + + if(!res){ + return res + } + + return JSON.parse(res)['originData'] +} + +// 加密 (http响应数据, 做通用处理) +export function sm4EncryptByReqData(data){ + + if(!data){ + return data + } + + // 加密处理 + let encryptData = SM4.encrypt(JSON.stringify(data), getHexKey(), { + inputEncoding: 'utf8', + outputEncoding: 'base64' + }) + + return {encryptData : encryptData} +} + diff --git a/commons/utils/ent.js b/commons/utils/ent.js new file mode 100644 index 0000000..6b2bcf5 --- /dev/null +++ b/commons/utils/ent.js @@ -0,0 +1,21 @@ +/** + * 权限判断 + * + * @author terrfly + * @site https://www.jeequan.com + * @date 2022/11/22 14:29 + */ +import storageManage from '@/commons/utils/storageManage.js' +const model = { + + // 判断是否包含该权限 + has(entId){ + let userInfo = storageManage.userInfo() + if(userInfo && userInfo.entIdList && userInfo.entIdList.indexOf(entId) >= 0){ + return true; + } + return false; + } +} + +export default model \ No newline at end of file diff --git a/commons/utils/formUtil.js b/commons/utils/formUtil.js new file mode 100644 index 0000000..8d51bf8 --- /dev/null +++ b/commons/utils/formUtil.js @@ -0,0 +1,101 @@ +/** + * form 验证 工具类 + * + * @author terrfly + * @site https://www.jeepay.vip + * @date 2022/11/25 10:58 + */ + +import infoBox from '@/commons/utils/infoBox.js' + +const model = { + + + // 正则表达式 + regexp: { + + // 手机号验证规则 + mobile: /^1\d{10}$/, + + // 登录用户名: 字母开头 6 -18位。 + loginUsername: /^[a-zA-Z][a-zA-Z0-9]{5,17}$/, + + }, + + + // 验证规则: + rules: { + + // showText 为空, 说明是 input的placeHoloder 直接飘红, + // showText 有值: 在文本框下方提示。 + // 只有input 才有这种特殊判断。 + requiredInput: (showText, type = 'string') => { + return {format: type, required: true, errorMessage: showText ? ('请输入' + showText) : ' ' } + }, + + requiredSelect: (showText, type = 'string') => { + return {format: type, required: true, errorMessage: '请选择' + showText } + }, + + requiredUpload: (showText, type = 'string') => { + return {format: type, required: true, errorMessage: '请上传' + showText } + }, + + // 正则验证 , 请注意: 该规则需要在required后面, 此处不可包含required + patternRule: (showText, p) => { + return {pattern: p, errorMessage: '请输入正确的' + showText } + }, + + requiredInputShowToast: (showText, type = 'string') => { + return {format: type, required: true, errorMessage:' ', toastErrorMessage: '请输入' + showText } + }, + + requiredSelectShowToast: (showText, type = 'string') => { + return {format: type, required: true, errorMessage:' ', toastErrorMessage: '请选择' + showText } + }, + + requiredUploadShowToast: (showText, type = 'string') => { + return {format: type, required: true, errorMessage:' ', toastErrorMessage: '请上传' + showText } + }, + + patternRuleShowToast: (showText, p) => { + return {pattern: p, errorMessage:' ', toastErrorMessage: '请输入正确的' + showText } + }, + + }, + + + // 支持 提示信息 + // 类型如下: + // { + // required: true, + // toastErrorMessage: "请输入去去去去群", + // errorMessage: ' ', // 不会显示在下部, 需要空格占位 + // } + validate: (form) => { + + return form.validate().catch(e => { + + if(!e || e.length <= 0){ + return Promise.reject() + } + + for(let i = 0; i < e.length; i++){ + let k = e[i].key + let rules = form.rules[k].rules + for(let j = 0; j < rules.length; j++){ + if(rules[j].toastErrorMessage && rules[j].required){ + infoBox.showToast(rules[j].toastErrorMessage) // 仅提示一次即可 + return Promise.reject(e) + } + } + } + return Promise.reject(e) + }) + + }, + +} + +export default model + diff --git a/commons/utils/format.js b/commons/utils/format.js new file mode 100644 index 0000000..f3d5d0a --- /dev/null +++ b/commons/utils/format.js @@ -0,0 +1,55 @@ +/** + * 格式化价格函数,将价格限定在指定的最小值和最大值范围内,并保留两位小数。 + * + * @param {number} price - 需要格式化的价格。 + * @param {number} min - 价格的最小值。 + * @param {number} max - 价格的最大值,默认为100000000。 + * @param {Boolean} returnIsArea - 是否返回值符合范围区间,默认为false。 + * @returns {number} - 返回格式化后的价格,如果超出范围则返回最小值或最大值。 + */ +export const formatPrice = (price,min=-Infinity, max = 100000000,returnIsArea=false,isRerturnNullString=false) => { + + if(price === undefined || price === null||price===''){ + return isRerturnNullString?'':0 + } + // 将价格转换为浮点数并保留两位小数 + const newval = parseFloat((Math.floor(price * 100) / 100).toFixed(2)) + // 如果价格大于最大值,返回最大值 + if (newval > max) { + return returnIsArea?{value:max,error:true}:max + } + // 如果价格小于最小值,返回最小值 + if (newval < min) { + return returnIsArea?{value:min,error:true}:min + } + // 如果价格小于最小值,返回最小值 + if (newval < min) { + return min + } + // 返回格式化后的价格 + return newval +} +export function returnReverseVal(val, isReturnString = true) { + const isBol = typeof val === "boolean"; + const isString = typeof val === "string"; + let reverseNewval = ""; + if (isBol) { + reverseNewval = !val; + } + if (isString) { + reverseNewval = val === "true" ? "false" : "true"; + } + return reverseNewval; +} +export function returnBoolean(val) { + const isBol = typeof val === "boolean"; + const isString = typeof val === "string"; + let newval = ""; + if (isBol) { + newval = val; + } + if (isString) { + newval = val === "true" ? true : false; + } + return newval; +} \ No newline at end of file diff --git a/commons/utils/getDateArea.js b/commons/utils/getDateArea.js new file mode 100644 index 0000000..50583c6 --- /dev/null +++ b/commons/utils/getDateArea.js @@ -0,0 +1,32 @@ +function getDayArea(date = new Date(), type) { + const now = date + if (type === 'start') { + const startOfDay = new Date(now.getFullYear(), now.getMonth(), now.getDate()); + return startOfDay + } + if (type === 'end') { + const endOfDay = new Date(now.getFullYear(), now.getMonth(), now.getDate(), 23, 59, 59, 999); + return endOfDay; + } + return `${startOfDay}-${endOfDay}` +} +function getMonthArea(date = new Date(), type) { + let now = date + let currentMonthStart = new Date(now.getFullYear(), now.getMonth(), 1); + let currentMonthEnd = new Date(now.getFullYear(), now.getMonth() + 1, 0 , 23, 59, 59, 999); + if (type === 'start') { + return currentMonthStart + } + if (type === 'end') { + return currentMonthEnd; + } + return { + start: currentMonthStart, + end: currentMonthEnd + }; +} + + +export default { + getDayArea, getMonthArea +} \ No newline at end of file diff --git a/commons/utils/getQueryString.js b/commons/utils/getQueryString.js new file mode 100644 index 0000000..ed310c7 --- /dev/null +++ b/commons/utils/getQueryString.js @@ -0,0 +1,13 @@ +/** + * 获取url链接参数 + * @param {Object} url + * @param {Object} name + */ +export function getQueryString(url, name) { + var reg = new RegExp('(^|&|/?)' + name + '=([^&|/?]*)(&|/?|$)', 'i') + var r = url.substr(1).match(reg) + if (r != null) { + return r[2] + } + return null; +} \ No newline at end of file diff --git a/commons/utils/go.js b/commons/utils/go.js new file mode 100644 index 0000000..c044e60 --- /dev/null +++ b/commons/utils/go.js @@ -0,0 +1,109 @@ +/** + * 页面跳转工具类 + * + * @author terrfly + * @site https://www.jeequan.com + * @date 2022/11/14 17:12 + */ + +// 引入 pages用于解析 pageId 变量 , 注意 需要在 pages.json 定义pageId 参数。 +// 使用方法: go.to(""), 优点: 扩展分包可任意路径,业务调用不再传入固定URL, 传入的是pageId变量。 +import pagesJSON from '@/pages.json' +import emit from './emit.js' + +// 获取到全部的页面路径 和 ID +const ALL_PAGES = { } + +// 添加到 ALL_PAGES +function addPages(pagesRoot){ + let rootUrl = pagesRoot.root ? `/${pagesRoot.root}/` : '/' + pagesRoot.pages.forEach(r => { + if(r.pageId){ + ALL_PAGES[r.pageId] = rootUrl + r.path + } + }) +} + +// 1. 添加 主目录 +addPages(pagesJSON) + +// 2. 添加分包文件 目录 +if(pagesJSON.subPackages){ + pagesJSON.subPackages.forEach(r => addPages(r)) +} + +const model = { + + // 跳转类型 + GO_TYPE_TO: 'navigateTo', + GO_TYPE_REDIRECT: 'redirect', + GO_TYPE_RELAUNCH: 'reLaunch', + GO_TYPE_SWITCHTAB: 'switchTab', + + + // 对象转换url参数 + object2param: (obj) => { + + if(!obj || Object.keys(obj).length <= 0){ + return "" + } + + let result = "?" + Object.keys(obj).forEach(k => { + + let val = obj[k] + // H5需要转码, 其他平台不需要 + // #ifdef H5 + val = encodeURIComponent(val) + // #endif + + result += `${k}=${val}&` + }) + return result.substr(0, (result.length - 1)); + }, + + + // uni.navigateTo函数的封装: 保留当前页面,跳转到应用内的某个页面,使用uni.navigateBack可以返回到原页面。 + // 参数: pagesIdOrUrl(路径或者pageId), 页面参数, 扩展参数 + to: (pagesIdOrUrl, params = {}, type = model.GO_TYPE_TO, extObject = {}) => { + + // 使用ID作为标识 + if(pagesIdOrUrl.indexOf('PAGES_') == 0){ + pagesIdOrUrl = ALL_PAGES[pagesIdOrUrl] + } + pagesIdOrUrl += model.object2param(params) + if(type == model.GO_TYPE_TO){ + uni.navigateTo(Object.assign({ url: pagesIdOrUrl }, extObject)) + } + + if(type == model.GO_TYPE_REDIRECT){ + uni.redirectTo(Object.assign({ url: pagesIdOrUrl }, extObject)) + } + + if(type == model.GO_TYPE_RELAUNCH){ + uni.reLaunch(Object.assign({ url: pagesIdOrUrl }, extObject)) + } + + if(type == model.GO_TYPE_SWITCHTAB){ + uni.switchTab(Object.assign({ url: pagesIdOrUrl }, extObject)) + } + }, + + // 跳转到通用搜索页面 + toSearchPage: (pageType, extObject = {}) => { + model.to("PAGES_LIST_SEARCH", Object.assign({type: pageType}, extObject)) + }, + + // delta 返回到第几页, refEmitEventName: 触发全局更新函数 (更新 list and search ) + back: (delta = 1, refEmitEventName) => { + + if(refEmitEventName){ + emit.refPageAndSearchEmit(refEmitEventName) + } + uni.navigateBack(delta) + } + + +} + +export default model \ No newline at end of file diff --git a/commons/utils/goodsUtil.js b/commons/utils/goodsUtil.js new file mode 100644 index 0000000..9ff70de --- /dev/null +++ b/commons/utils/goodsUtil.js @@ -0,0 +1,37 @@ +export function canComputedPackFee(v) { + return v.pack && v.status != 'return' && v.status != 'refund' && v.status != 'refunding' +} +export function returnCanComputedGoodsArr(arr) { + return arr.filter(v => canComputedPackFee(v)) +} +export function returnPackFee(arr) { + return arr.reduce((prve, cur) => { + return prve + cur.packAmount + }, 0).toFixed(2) +} + +export function canTuicai(orderInfo, item) { + if (orderInfo.status == 'unpaid' && orderInfo.isPostpaid !== null && orderInfo.isPostpaid == 0) { + return false + } + return orderInfo.status == 'unpaid' && orderInfo.useType != 'dine-in-before' && item.status != 'return' +} +export function canTuiKuan(orderInfo, item) { + return orderInfo.status == 'closed' && item.status != 'return' && item.status != 'refund' && item.status != + 'refunding' +} +export function isTuiCai(item) { + return item.status == 'return' +} +export function isTui(item) { + return item.status == 'return' || item.status == 'refund' || item.status == 'refunding' +} +export function isGift(item) { + return !isTui(item) && item.gift +} +export function numSum(arr) { + const sum = arr.reduce((a, b) => { + return a + b * 100 + }, 0) + return (sum / 100).toFixed(2) +} \ No newline at end of file diff --git a/commons/utils/hasPermission.js b/commons/utils/hasPermission.js new file mode 100644 index 0000000..960feaa --- /dev/null +++ b/commons/utils/hasPermission.js @@ -0,0 +1,163 @@ +import { + $hasPermission +} from '@/http/yskApi/shop.js' +import infoBox from '@/commons/utils/infoBox.js' + +const $PermissionObj = { + data: [{ + key: 'yun_xu_cha_kan_jing_ying_shu_ju', + text: '允许查看经营数据' + }, + { + key: 'yun_xu_cha_kan_suo_you_jiao_ban_ji_lu', + text: '允许查看所有交班记录' + } + ], + default: [{ + key: 'yun_xu_xia_dan', + text: '允许下单' + }, + { + key: 'yun_xu_shou_kuan', + text: '允许收款' + }, + { + key: 'yun_xu_tui_kuan', + text: '允许退款' + }, + { + key: 'yun_xu_jiao_ban', + text: '允许交班' + } + ], + goods: [{ + key: 'yun_xu_xiu_gai_shang_pin', + text: '允许修改商品' + }, + { + key: 'yun_xu_shang_xia_jia_shang_pin', + text: '允许上下架商品' + }, + { + key: 'yun_xu_xiu_gai_fen_lei', + text: '允许修改分类' + }, + { + key: 'yun_xu_xiu_gai_fen_zu', + text: '允许修改分组' + } + ], + discount:[ + { + key: 'yun_xu_da_zhe', + text: '允许打折' + } + ], + vip:[ + { + text: '允许管理会员信息', + key: 'yun_xu_guan_li_hui_yuan_xin_xi' + }, + { + key: 'yun_xu_xiu_gai_hui_yuan_yu_e', + text: '允许修改会员余额' + } + ], + stock:[ + { + text: '允许提交报损', + key: 'yun_xu_ti_jiao_bao_sun' + }, + { + text: '允许沽清', + key: 'yun_xu_gu_qing' + }, + { + text: '允许售罄商品', + key: 'yun_xu_shou_qing_shang_pin' + }, + { + text:'允许修改商品库存', + key:'yun_xu_xiu_gai_shang_pin_ku_cun' + }, + { + text: '允许耗材入库', + key: 'yun_xu_hao_cai_ru_ku' + }, + { + text: '允许耗材出库', + key: 'yun_xu_hao_cai_chu_ku' + }, + { + text: '允许耗材盘点', + key: 'yun_xu_hao_cai_pan_dian' + } + ] +} + +function isChinese(str) { + for (var i = 0; i < str.length; i++) { + if (str.charCodeAt(i) >= 0x4E00 && str.charCodeAt(i) <= 0x9FFF) { + return true; // 是中文 + } + } + return false; // 不是中文,全是英文或其他 +} + +function isObjectButNotArray(value) { + return typeof value === 'object' && Array.isArray(value) === false; +} + +function findPermissionObj(str) { + for (let i in $PermissionObj) { + const obj = $PermissionObj[i].find(v => v.key == str || v.text == str) + if (obj) { + return obj + break + } + } + console.error('未找到相关权限配置,请检查权限配置文件commons/utils/hasPermission.js文件进行修改或增加') + return false +} + +function returnFormatParams(params) { + if (typeof params === 'string') { + return findPermissionObj(params) + } else { + if (isObjectButNotArray(params)) { + const obj=findPermissionObj(params.key || params.text) + return {...params,...obj} + } else { + console.error('参数只能是字符串或者对象,不能是数组') + } + } +} + +/** + * 判断是否有某权限 + * @param {Object|String} params + */ +export async function hasPermission(params) { + //如果是商户默认拥有全部权限 + const loginType=uni.getStorageSync('loginType') + if(loginType=='merchant'){ + return true + } + params = returnFormatParams(params) + if (!params) { + return infoBox.showToast('未找到相关权限,请检查代码或在权限配置文件commons/utils/hasPermission.js文件进行修改或增加') + } + const option = Object.assign({ + tips: true, + key: '', + text: '' + }, params) + const res = await $hasPermission({ + code: params.key + }) + if (!res && option.tips) { + infoBox.showToast('您没有' + params.text + '权限!') + } + return res +} + diff --git a/commons/utils/infoBox.js b/commons/utils/infoBox.js new file mode 100644 index 0000000..6b57f3f --- /dev/null +++ b/commons/utils/infoBox.js @@ -0,0 +1,62 @@ +/** + * 提示信息公共文件 + * + * @author terrfly + * @site https://www.jeequan.com + * @date 2022/11/14 15:29 + */ + +const model = { + + // uni.showToast的封装 + // 参数: 标题、 显示时长(单位: 秒), 扩展参数 + // 返回: promise对象, 当提示消失后调用 resolve() + showToast: (title, duration = 1.5, extObject) => { + return new Promise((resolve, reject) => { + uni.showToast(Object.assign({ title: title, icon: 'none', mask: false, duration: (duration * 1000) }, extObject)) + setTimeout(resolve, (duration * 1000)); + }) + }, + + // success类型的提示 + showSuccessToast: (title, duration) => { + return model.showToast(title, duration, {icon: 'success'}) + }, + + // error类型的提示 + showErrorToast: (title, duration) => { + return model.showToast(title, duration, {icon: 'error'}) + }, + + showLoading: (title = '请稍后' ) => { + return uni.showLoading({ title: title, mask: true }) + }, + + hideLoading: () => { + return uni.hideLoading() + }, + + // 返回 Promise 点击确定和取消 + // APP安卓原生提示(比较丑), APP 不推荐使用该函数 。 + showModal: (title, confirmText = '确定', cancalText = '取消', extObject) => { + return new Promise((resolve, reject) => { + uni.showModal( Object.assign({ + title: title, + confirmText: confirmText, + showCancel: cancalText ? true : false, + cancelText: cancalText, + success: function(r) { + if (r.confirm) { + resolve() + }else if (r.cancel) { + reject() + } + } + }, extObject )); + }); + }, + + +} + +export default model \ No newline at end of file diff --git a/commons/utils/pushmsg/QS-baiduyy.js b/commons/utils/pushmsg/QS-baiduyy.js new file mode 100644 index 0000000..9341b2d --- /dev/null +++ b/commons/utils/pushmsg/QS-baiduyy.js @@ -0,0 +1,143 @@ +import { $getBaiduToken } from '@/http/apiManager.js'; +const audioTeam = []; +let audioStartSwitch = false; +const getAudioUrl = 'https://tsn.baidu.com/text2audio'; + +export default function openVoice(objs) { // 传入需转为语音的文本内容 + let lineUp = false; + let returnAudio = false; + if (typeof(objs) !== 'string') { + if (objs && objs.lineUp === true) { + lineUp = true; + } + if (objs && objs.returnAudio === true) { + returnAudio = true; + } + } + if(returnAudio) { + return new Promise((resolve, reject)=>{ + openVoiceFc(objs, returnAudio).then(res=>{ + resolve(res); + }).catch(err=>{ + reject(err) + }); + }) + } + + if (!audioStartSwitch || lineUp) { + audioStartSwitch = true; + openVoiceFc(objs); + } else { + audioTeam.push(objs); + } +} + +function openVoiceFc(objs, returnAudio) { + if(returnAudio) { + return new Promise((resolve, reject)=>{ + $getBaiduToken().then(({bizData}) => { + if (bizData) { + resolve(tts(objs, bizData, returnAudio)); + } else { + reject('获取语音tok接口为空'); + } + }) + }) + }else{ + $getBaiduToken().then(({bizData}) => { + if (bizData) { + tts(objs, bizData); + } else { + } + }) + } +} + +function tts(objs, tok, returnAudio) { + if(typeof(objs)=='string') + objs = {voiceSet: {tex: objs}}; + const data = { + tok, + cuid: tok, + ctp: 1, + lan: 'zh', + ...objs.voiceSet + } + if(returnAudio) + return btts( data, objs.audioSet, objs.audioCallback, objs.lineUp, returnAudio); + btts( data, objs.audioSet, objs.audioCallback, objs.lineUp, returnAudio); +} + +function setAudioSet(options, audio) { + if (options) { + audio.volume = options.volume || 1; + audio.startTime = options.startTime || 0; + audio.loop = options.loop || false; + audio.obeyMuteSwitch = options.obeyMuteSwitch && typeof(options.obeyMuteSwitch) == 'boolean' ? options.obeyMuteSwitch : + true; //支持微信小程序、百度小程序、头条小程序 + } +} + +function btts(param, options, audioCallback, lineUp, returnAudio) { + let audio = uni.createInnerAudioContext(); + setAudioSet(options, audio); + // 序列化参数列表 + let fd = []; + for (let k in param) { + fd.push(k + '=' + encodeURIComponent(encodeURIComponent(param[k]))); + } + audio.src = `${getAudioUrl}?${fd.join('&')}`; + + if(returnAudio) { + audio.onEnded(() => { + audio.destroy(); //销毁音频实例 + audio = null; + }) + audio.onError((e)=>{ + if (audioCallback && audioCallback.onError && typeof(audioCallback.onError) == 'function') audioCallback.onError(e); + audio.destroy(); //销毁音频实例 + audio = null; + }) + return audio; + } + audio.onPlay(() => { + if (audioCallback && audioCallback.onPlay && typeof(audioCallback.onPlay) == 'function') audioCallback.onPlay(); + }) + audio.onPause(()=>{ + if (audioCallback && audioCallback.onPause && typeof(audioCallback.onPause) == 'function') audioCallback.onPause(); + }) + audio.onWaiting(()=>{ + if (audioCallback && audioCallback.onWaiting && typeof(audioCallback.onWaiting) == 'function') audioCallback.onWaiting(); + }) + audio.onStop(()=>{ + if (audioCallback && audioCallback.onStop && typeof(audioCallback.onStop) == 'function') audioCallback.onStop(); + }) + audio.onTimeUpdate(()=>{ + if (audioCallback && audioCallback.onTimeUpdate && typeof(audioCallback.onTimeUpdate) == 'function') audioCallback.onTimeUpdate(); + }) + audio.onSeeking(()=>{ + if (audioCallback && audioCallback.onSeeking && typeof(audioCallback.onSeeking) == 'function') audioCallback.onSeeking(); + }) + audio.onSeeked(()=>{ + if (audioCallback && audioCallback.onSeeked && typeof(audioCallback.onSeeked) == 'function') audioCallback.onSeeked(); + }) + audio.onEnded(() => { + audio.destroy(); //销毁音频实例 + audio = null; + if (audioCallback && audioCallback.onEnded && typeof(audioCallback.onEnded) == 'function') audioCallback.onEnded(); + if (lineUp !== false) { + if (audioTeam.length > 0) { + openVoiceFc(audioTeam[0]); + audioTeam.splice(0, 1); + } else { + audioStartSwitch = false; + } + } + }) + audio.onError((e)=>{ + if (audioCallback && audioCallback.onError && typeof(audioCallback.onError) == 'function') audioCallback.onError(e); + audio.destroy(); //销毁音频实例 + audio = null; + }) + audio.play(); +} diff --git a/commons/utils/pushmsg/pushMsgManage.js b/commons/utils/pushmsg/pushMsgManage.js new file mode 100644 index 0000000..10385dc --- /dev/null +++ b/commons/utils/pushmsg/pushMsgManage.js @@ -0,0 +1,71 @@ +import storageManage from '@/commons/utils/storageManage.js' +import dayjs from 'dayjs' +import baiduyy from './QS-baiduyy.js'; // 百度语音合成 + +// #ifdef MP-WEIXIN +import wxTextToSpeach from './wxTextToSpeach.js'; // 微信小程序插件语音合成 +// #endif + + +const model = { + // 监听推送通知 + addPushMsgEventListener: function(){ + + console.log("监听推送") + + // #ifdef APP-PLUS + // unipush1.0监听消息 + if(plus && plus.push) { + plus.push.addEventListener('receive', model.handlePush) + } + // #endif + // unipush2.0监听消息 + model.uniPushListener2() + }, + + + // uniPush2.0 接收推送消息 + uniPushListener2: function() { + uni.onPushMessage((res) => { + console.log("uniPush2.0 收到推送消息:", res.data) //监听推送消息 + model.handlePush(res.data) + }) + }, + + // 语音播报 + handlePush: function(message) { + + // 没有token信息 + if(!storageManage.token()){ + return false; + } + + // 信息不存在 + if(!message || !message.content) { + return false; + } + + const content = JSON.parse(message.content) + console.log("消息内容:", content) + + // 支付成功 + if (content && content.type == 'paySuccess') { + // 在过期时间之内, 则调起语音播报。 + if( dayjs(content.expiredTime).isAfter(dayjs()) ){ + console.log('执行消息播报'); + // #ifdef MP-WEIXIN + wxTextToSpeach(content.msg) + // #endif + + // #ifndef MP-WEIXIN + baiduyy(content.msg) + // #endif + uni.vibrateLong({}); + } + } + } + +} + + +export default model \ No newline at end of file diff --git a/commons/utils/pushmsg/registerPush.js b/commons/utils/pushmsg/registerPush.js new file mode 100644 index 0000000..1d8c813 --- /dev/null +++ b/commons/utils/pushmsg/registerPush.js @@ -0,0 +1,50 @@ +import { + $pushInfoRegister +} from '@/http/apiManager.js' +import storageManage from '@/commons/utils/storageManage.js' +// 默认导出 方法 注册 push连接 +export default async function() { + let cid1 = undefined // unipush1.0 客户端CID + let cid2 = undefined // unipush2.0 客户端CID + let orgCid = undefined // 原始cid如果获取的cid和新的cid不相同赋值原始cid后端会根据原始cid更新 + let cidType = undefined //传递类型 是 app 还是 微信 + // #ifdef APP-PLUS + cidType = 'app_plus' + // #endif + + // #ifdef MP-WEIXIN + cidType = 'mp_weixin' + // #endif + + // #ifdef APP-PLUS + if (!plus) { + cid1 = plus.push.getClientInfo().clientid + } + // #endif + const data = await uni.getPushClientId() + console.log('客户端推送标识:', data.cid) + cid2 = data.cid + // 如果不存 cid 本地存储 写入 cid + if (!storageManage.uniPush2Cid()) { + storageManage.uniPush2Cid(data.cid) + } else if (cid2 !== storageManage.uniPush2Cid()) { // 否则进行 cid 对比 判断 是否相等 不相等 赋值 orgCid + orgCid = storageManage.uniPush2Cid() //赋值原始cid + storageManage.uniPush2Cid(data.cid) //重新写入 cid + } + if (cid1) { + pushInfoRegister(cid1) + } else { + pushInfoRegister(cid1, cid2, orgCid, cidType) + } + + function pushInfoRegister(cid1 = '', cid2 = '', org = '', cidType = '') { + $pushInfoRegister({ + cid1, + cid2, + orgCid: org, + cidType + }).then(res => { + orgCid = '' //重置 数据 + }) + } +} diff --git a/commons/utils/pushmsg/wxTextToSpeach.js b/commons/utils/pushmsg/wxTextToSpeach.js new file mode 100644 index 0000000..bfd523d --- /dev/null +++ b/commons/utils/pushmsg/wxTextToSpeach.js @@ -0,0 +1,87 @@ +import { $mchConfig } from "@/http/apiManager" +import storageManage from '@/commons/utils/storageManage.js' +let num = 0 //计算错误此时 超过5次错误 不在出触发 +const plugin = requirePlugin("WechatSI") +const pushMsgArr = [] //维护一个消息队列 +let backgroundAudioManager = undefined //获取背景音频实例 +let audioMp3 = '' +console.log('执行创建 语音播报逻辑'); +// 获取配置项 判断是否 开启 小程序 语音推送 +export function getPushStatus () { + if (!storageManage.token()) return //未登录 不播放 + $mchConfig('orderConfig').then(({ bizData = [] }) => { + const weChat = bizData.find(v => v.configKey == "weChatVoice") + if (weChat && weChat?.configVal == 1) { + createBgMusice() + } + }) +} +// getPushStatus() +// 创建 背景音乐 +function createBgMusice (file) { + backgroundAudioManager = wx.getBackgroundAudioManager() + backgroundAudioManager.title = '订单通知' + if (!audioMp3) { + createFile() + } else { + backgroundAudioManager.src = audioMp3 + } + + // 监听 音频播放失败事件 + backgroundAudioManager.onError(function (res) { + console.log('音频播放失败', res, num); + if (num >= 5) return + createFile() + num++ + }) + // 监听 音频播放结束事件 + onBgMusiceEnd() +} +// 监听bei背景音乐播放状态 +export function onBgMusiceEnd () { + backgroundAudioManager.onEnded(() => { + if (pushMsgArr.length > 0) return broadcast(pushMsgArr.pop()) //如果有消息 则继续播放 + backgroundAudioManager.src = audioMp3 //否则播放默认背景音乐 + }) +} +export function startOrEndMusice (flag) { + if (!flag && !!backgroundAudioManager) return backgroundAudioManager.stop() //关闭背景音乐 地址指向空即可 + if (!backgroundAudioManager) return createBgMusice() // 如果一开始是关闭状态 则创建背景音乐实例 + backgroundAudioManager.src = audioMp3 // 否则重新赋值背景音地址即可 +} +export default function (message) { + if (!backgroundAudioManager) return + pushMsgArr.unshift(message) //将消息添加到消息队列头部 背景音乐播放结束后 会对消息队列 进行校验 如果消息队列有消息 会进行播放 否则继续循环背景音乐 +} +// 播放订单 +function broadcast (msg) { + plugin.textToSpeech({ + lang: "zh_CN", + tts: true, + content: msg, + success: function (res) { + backgroundAudioManager.src = res.filename; + onBgMusiceEnd() + }, + fail: function (res) { + console.log("fail tts", res) + } + }) +} + +// 创建文件 +export function createFile (file) { + const fs = wx.getFileSystemManager() + fs.copyFile({ + srcPath: `static/noiseless.mp3`, + destPath: `${wx.env.USER_DATA_PATH}/noiseless.mp3`, + success (res) { + console.log(res, `${wx.env.USER_DATA_PATH}/noiseless.mp3`) + audioMp3 = `${wx.env.USER_DATA_PATH}/noiseless.mp3` + backgroundAudioManager.src = audioMp3 + }, + fail (res) { + console.error(res) + } + }) +} \ No newline at end of file diff --git a/commons/utils/pushmsg/推送和播报相关.txt b/commons/utils/pushmsg/推送和播报相关.txt new file mode 100644 index 0000000..11b6a55 --- /dev/null +++ b/commons/utils/pushmsg/推送和播报相关.txt @@ -0,0 +1,10 @@ +创建 云空间 上传云函数 云函数 url化 运营平台 配置云函数地址 + +打包时 勾选云push 2.0 push1.0 仅支持 app 推送 + +注意配置 百度语音相关参数 + +使用push2.0 请将 static\noiseless.mp3 文件 配置到运营平台 系统 配置 通知配置 push2.0 uniPush语音播报音频文件(小程序播报必填) 下 + +注意:扩展库依赖3张opendb表:opendb-tempdata,opendb-device,uni-id-device。公测版uniCloud,执行扩展库会自动创建。如果你使用的是uniCloud正式版需要自己创建这3张表。 + \ No newline at end of file diff --git a/commons/utils/qrCode.js b/commons/utils/qrCode.js new file mode 100644 index 0000000..41c1be4 --- /dev/null +++ b/commons/utils/qrCode.js @@ -0,0 +1,1625 @@ +//--------------------------------------------------------------------- +// +// QR Code Generator for JavaScript +// +// Copyright (c) 2009 Kazuhiko Arase +// +// URL: http://www.d-project.com/ +// +// Licensed under the MIT license: +// http://www.opensource.org/licenses/mit-license.php +// +// The word 'QR Code' is registered trademark of +// DENSO WAVE INCORPORATED +// http://www.denso-wave.com/qrcode/faqpatent-e.html +// +//--------------------------------------------------------------------- + +//---------------微信小程序基于base64生成二维码插件修改------------------- +/* + * @Modified: Pudon + * @demoURL: https://github.com/Pudon/weapp-qrcode + * @Date: 2018-09-11 14:00:05 + * @Last Modified by: Pudon + * @Last Modified time: 2018-09-12 16:33:19 + */ +//--------------------------------------------------------------------- + +/** + * qrcode + * @param typeNumber 1 to 40 + * @param errorCorrectLevel 'L','M','Q','H' + */ +var qrcode = function(typeNumber, errorCorrectLevel) { + + var PAD0 = 0xEC; + var PAD1 = 0x11; + + var _typeNumber = typeNumber; + var _errorCorrectLevel = QRErrorCorrectLevel[errorCorrectLevel]; + var _modules = null; + var _moduleCount = 0; + var _dataCache = null; + var _dataList = new Array(); + + var _this = {}; + + var makeImpl = function(test, maskPattern) { + + _moduleCount = _typeNumber * 4 + 17; + _modules = function(moduleCount) { + var modules = new Array(moduleCount); + for (var row = 0; row < moduleCount; row += 1) { + modules[row] = new Array(moduleCount); + for (var col = 0; col < moduleCount; col += 1) { + modules[row][col] = null; + } + } + return modules; + }(_moduleCount); + + setupPositionProbePattern(0, 0); + setupPositionProbePattern(_moduleCount - 7, 0); + setupPositionProbePattern(0, _moduleCount - 7); + setupPositionAdjustPattern(); + setupTimingPattern(); + setupTypeInfo(test, maskPattern); + + if (_typeNumber >= 7) { + setupTypeNumber(test); + } + + if (_dataCache == null) { + _dataCache = createData(_typeNumber, _errorCorrectLevel, _dataList); + } + + mapData(_dataCache, maskPattern); + }; + + var setupPositionProbePattern = function(row, col) { + + for (var r = -1; r <= 7; r += 1) { + + if (row + r <= -1 || _moduleCount <= row + r) continue; + + for (var c = -1; c <= 7; c += 1) { + + if (col + c <= -1 || _moduleCount <= col + c) continue; + + if ( (0 <= r && r <= 6 && (c == 0 || c == 6) ) + || (0 <= c && c <= 6 && (r == 0 || r == 6) ) + || (2 <= r && r <= 4 && 2 <= c && c <= 4) ) { + _modules[row + r][col + c] = true; + } else { + _modules[row + r][col + c] = false; + } + } + } + }; + + var getBestMaskPattern = function() { + + var minLostPoint = 0; + var pattern = 0; + + for (var i = 0; i < 8; i += 1) { + + makeImpl(true, i); + + var lostPoint = QRUtil.getLostPoint(_this); + + if (i == 0 || minLostPoint > lostPoint) { + minLostPoint = lostPoint; + pattern = i; + } + } + + return pattern; + }; + + var setupTimingPattern = function() { + + for (var r = 8; r < _moduleCount - 8; r += 1) { + if (_modules[r][6] != null) { + continue; + } + _modules[r][6] = (r % 2 == 0); + } + + for (var c = 8; c < _moduleCount - 8; c += 1) { + if (_modules[6][c] != null) { + continue; + } + _modules[6][c] = (c % 2 == 0); + } + }; + + var setupPositionAdjustPattern = function() { + + var pos = QRUtil.getPatternPosition(_typeNumber); + + for (var i = 0; i < pos.length; i += 1) { + + for (var j = 0; j < pos.length; j += 1) { + + var row = pos[i]; + var col = pos[j]; + + if (_modules[row][col] != null) { + continue; + } + + for (var r = -2; r <= 2; r += 1) { + + for (var c = -2; c <= 2; c += 1) { + + if (r == -2 || r == 2 || c == -2 || c == 2 + || (r == 0 && c == 0) ) { + _modules[row + r][col + c] = true; + } else { + _modules[row + r][col + c] = false; + } + } + } + } + } + }; + + var setupTypeNumber = function(test) { + + var bits = QRUtil.getBCHTypeNumber(_typeNumber); + + for (var i = 0; i < 18; i += 1) { + var mod = (!test && ( (bits >> i) & 1) == 1); + _modules[Math.floor(i / 3)][i % 3 + _moduleCount - 8 - 3] = mod; + } + + for (var i = 0; i < 18; i += 1) { + var mod = (!test && ( (bits >> i) & 1) == 1); + _modules[i % 3 + _moduleCount - 8 - 3][Math.floor(i / 3)] = mod; + } + }; + + var setupTypeInfo = function(test, maskPattern) { + + var data = (_errorCorrectLevel << 3) | maskPattern; + var bits = QRUtil.getBCHTypeInfo(data); + + // vertical + for (var i = 0; i < 15; i += 1) { + + var mod = (!test && ( (bits >> i) & 1) == 1); + + if (i < 6) { + _modules[i][8] = mod; + } else if (i < 8) { + _modules[i + 1][8] = mod; + } else { + _modules[_moduleCount - 15 + i][8] = mod; + } + } + + // horizontal + for (var i = 0; i < 15; i += 1) { + + var mod = (!test && ( (bits >> i) & 1) == 1); + + if (i < 8) { + _modules[8][_moduleCount - i - 1] = mod; + } else if (i < 9) { + _modules[8][15 - i - 1 + 1] = mod; + } else { + _modules[8][15 - i - 1] = mod; + } + } + + // fixed module + _modules[_moduleCount - 8][8] = (!test); + }; + + var mapData = function(data, maskPattern) { + + var inc = -1; + var row = _moduleCount - 1; + var bitIndex = 7; + var byteIndex = 0; + var maskFunc = QRUtil.getMaskFunction(maskPattern); + + for (var col = _moduleCount - 1; col > 0; col -= 2) { + + if (col == 6) col -= 1; + + while (true) { + + for (var c = 0; c < 2; c += 1) { + + if (_modules[row][col - c] == null) { + + var dark = false; + + if (byteIndex < data.length) { + dark = ( ( (data[byteIndex] >>> bitIndex) & 1) == 1); + } + + var mask = maskFunc(row, col - c); + + if (mask) { + dark = !dark; + } + + _modules[row][col - c] = dark; + bitIndex -= 1; + + if (bitIndex == -1) { + byteIndex += 1; + bitIndex = 7; + } + } + } + + row += inc; + + if (row < 0 || _moduleCount <= row) { + row -= inc; + inc = -inc; + break; + } + } + } + }; + + var createBytes = function(buffer, rsBlocks) { + + var offset = 0; + + var maxDcCount = 0; + var maxEcCount = 0; + + var dcdata = new Array(rsBlocks.length); + var ecdata = new Array(rsBlocks.length); + + for (var r = 0; r < rsBlocks.length; r += 1) { + + var dcCount = rsBlocks[r].dataCount; + var ecCount = rsBlocks[r].totalCount - dcCount; + + maxDcCount = Math.max(maxDcCount, dcCount); + maxEcCount = Math.max(maxEcCount, ecCount); + + dcdata[r] = new Array(dcCount); + + for (var i = 0; i < dcdata[r].length; i += 1) { + dcdata[r][i] = 0xff & buffer.getBuffer()[i + offset]; + } + offset += dcCount; + + var rsPoly = QRUtil.getErrorCorrectPolynomial(ecCount); + var rawPoly = qrPolynomial(dcdata[r], rsPoly.getLength() - 1); + + var modPoly = rawPoly.mod(rsPoly); + ecdata[r] = new Array(rsPoly.getLength() - 1); + for (var i = 0; i < ecdata[r].length; i += 1) { + var modIndex = i + modPoly.getLength() - ecdata[r].length; + ecdata[r][i] = (modIndex >= 0)? modPoly.getAt(modIndex) : 0; + } + } + + var totalCodeCount = 0; + for (var i = 0; i < rsBlocks.length; i += 1) { + totalCodeCount += rsBlocks[i].totalCount; + } + + var data = new Array(totalCodeCount); + var index = 0; + + for (var i = 0; i < maxDcCount; i += 1) { + for (var r = 0; r < rsBlocks.length; r += 1) { + if (i < dcdata[r].length) { + data[index] = dcdata[r][i]; + index += 1; + } + } + } + + for (var i = 0; i < maxEcCount; i += 1) { + for (var r = 0; r < rsBlocks.length; r += 1) { + if (i < ecdata[r].length) { + data[index] = ecdata[r][i]; + index += 1; + } + } + } + + return data; + }; + + var createData = function(typeNumber, errorCorrectLevel, dataList) { + + var rsBlocks = QRRSBlock.getRSBlocks(typeNumber, errorCorrectLevel); + + var buffer = qrBitBuffer(); + + for (var i = 0; i < dataList.length; i += 1) { + var data = dataList[i]; + buffer.put(data.getMode(), 4); + buffer.put(data.getLength(), QRUtil.getLengthInBits(data.getMode(), typeNumber) ); + data.write(buffer); + } + + // calc num max data. + var totalDataCount = 0; + for (var i = 0; i < rsBlocks.length; i += 1) { + totalDataCount += rsBlocks[i].dataCount; + } + + if (buffer.getLengthInBits() > totalDataCount * 8) { + throw new Error('code length overflow. (' + + buffer.getLengthInBits() + + '>' + + totalDataCount * 8 + + ')'); + } + + // end code + if (buffer.getLengthInBits() + 4 <= totalDataCount * 8) { + buffer.put(0, 4); + } + + // padding + while (buffer.getLengthInBits() % 8 != 0) { + buffer.putBit(false); + } + + // padding + while (true) { + + if (buffer.getLengthInBits() >= totalDataCount * 8) { + break; + } + buffer.put(PAD0, 8); + + if (buffer.getLengthInBits() >= totalDataCount * 8) { + break; + } + buffer.put(PAD1, 8); + } + + return createBytes(buffer, rsBlocks); + }; + + _this.addData = function(data) { + var newData = qr8BitByte(data); + _dataList.push(newData); + _dataCache = null; + }; + + _this.isDark = function(row, col) { + if (row < 0 || _moduleCount <= row || col < 0 || _moduleCount <= col) { + throw new Error(row + ',' + col); + } + return _modules[row][col]; + }; + + _this.getModuleCount = function() { + return _moduleCount; + }; + + _this.make = function() { + makeImpl(false, getBestMaskPattern() ); + }; + + _this.createTableTag = function(cellSize, margin) { + + cellSize = cellSize || 2; + margin = (typeof margin == 'undefined')? cellSize * 4 : margin; + + var qrHtml = ''; + + qrHtml += ''; + qrHtml += ''; + + for (var r = 0; r < _this.getModuleCount(); r += 1) { + + qrHtml += ''; + + for (var c = 0; c < _this.getModuleCount(); c += 1) { + qrHtml += ''; + } + + qrHtml += ''; + qrHtml += '
'; + } + + qrHtml += '
'; + + return qrHtml; + }; + + _this.createImgTag = function(cellSize, margin, size) { + + cellSize = cellSize || 2; + margin = (typeof margin == 'undefined')? cellSize * 4 : margin; + + var min = margin; + var max = _this.getModuleCount() * cellSize + margin; + + return createImgTag(size, size, function(x, y) { + if (min <= x && x < max && min <= y && y < max) { + var c = Math.floor( (x - min) / cellSize); + var r = Math.floor( (y - min) / cellSize); + return _this.isDark(r, c)? 0 : 1; + } else { + return 1; + } + } ); + }; + + return _this; +}; + +//--------------------------------------------------------------------- +// qrcode.stringToBytes +//--------------------------------------------------------------------- + +qrcode.stringToBytes = function(s) { + var bytes = new Array(); + for (var i = 0; i < s.length; i += 1) { + var c = s.charCodeAt(i); + bytes.push(c & 0xff); + } + return bytes; +}; + +//--------------------------------------------------------------------- +// qrcode.createStringToBytes +//--------------------------------------------------------------------- + +/** + * @param unicodeData base64 string of byte array. + * [16bit Unicode],[16bit Bytes], ... + * @param numChars + */ +qrcode.createStringToBytes = function(unicodeData, numChars) { + + // create conversion map. + + var unicodeMap = function() { + + var bin = base64DecodeInputStream(unicodeData); + var read = function() { + var b = bin.read(); + if (b == -1) throw new Error(); + return b; + }; + + var count = 0; + var unicodeMap = {}; + while (true) { + var b0 = bin.read(); + if (b0 == -1) break; + var b1 = read(); + var b2 = read(); + var b3 = read(); + var k = String.fromCharCode( (b0 << 8) | b1); + var v = (b2 << 8) | b3; + unicodeMap[k] = v; + count += 1; + } + if (count != numChars) { + throw new Error(count + ' != ' + numChars); + } + + return unicodeMap; + }(); + + var unknownChar = '?'.charCodeAt(0); + + return function(s) { + var bytes = new Array(); + for (var i = 0; i < s.length; i += 1) { + var c = s.charCodeAt(i); + if (c < 128) { + bytes.push(c); + } else { + var b = unicodeMap[s.charAt(i)]; + if (typeof b == 'number') { + if ( (b & 0xff) == b) { + // 1byte + bytes.push(b); + } else { + // 2bytes + bytes.push(b >>> 8); + bytes.push(b & 0xff); + } + } else { + bytes.push(unknownChar); + } + } + } + return bytes; + }; +}; + +//--------------------------------------------------------------------- +// QRMode +//--------------------------------------------------------------------- + +var QRMode = { + MODE_NUMBER : 1 << 0, + MODE_ALPHA_NUM : 1 << 1, + MODE_8BIT_BYTE : 1 << 2, + MODE_KANJI : 1 << 3 +}; + +//--------------------------------------------------------------------- +// QRErrorCorrectLevel +//--------------------------------------------------------------------- + +var QRErrorCorrectLevel = { + L : 1, + M : 0, + Q : 3, + H : 2 +}; + +//--------------------------------------------------------------------- +// QRMaskPattern +//--------------------------------------------------------------------- + +var QRMaskPattern = { + PATTERN000 : 0, + PATTERN001 : 1, + PATTERN010 : 2, + PATTERN011 : 3, + PATTERN100 : 4, + PATTERN101 : 5, + PATTERN110 : 6, + PATTERN111 : 7 +}; + +//--------------------------------------------------------------------- +// QRUtil +//--------------------------------------------------------------------- + +var QRUtil = function() { + + var PATTERN_POSITION_TABLE = [ + [], + [6, 18], + [6, 22], + [6, 26], + [6, 30], + [6, 34], + [6, 22, 38], + [6, 24, 42], + [6, 26, 46], + [6, 28, 50], + [6, 30, 54], + [6, 32, 58], + [6, 34, 62], + [6, 26, 46, 66], + [6, 26, 48, 70], + [6, 26, 50, 74], + [6, 30, 54, 78], + [6, 30, 56, 82], + [6, 30, 58, 86], + [6, 34, 62, 90], + [6, 28, 50, 72, 94], + [6, 26, 50, 74, 98], + [6, 30, 54, 78, 102], + [6, 28, 54, 80, 106], + [6, 32, 58, 84, 110], + [6, 30, 58, 86, 114], + [6, 34, 62, 90, 118], + [6, 26, 50, 74, 98, 122], + [6, 30, 54, 78, 102, 126], + [6, 26, 52, 78, 104, 130], + [6, 30, 56, 82, 108, 134], + [6, 34, 60, 86, 112, 138], + [6, 30, 58, 86, 114, 142], + [6, 34, 62, 90, 118, 146], + [6, 30, 54, 78, 102, 126, 150], + [6, 24, 50, 76, 102, 128, 154], + [6, 28, 54, 80, 106, 132, 158], + [6, 32, 58, 84, 110, 136, 162], + [6, 26, 54, 82, 110, 138, 166], + [6, 30, 58, 86, 114, 142, 170] + ]; + var G15 = (1 << 10) | (1 << 8) | (1 << 5) | (1 << 4) | (1 << 2) | (1 << 1) | (1 << 0); + var G18 = (1 << 12) | (1 << 11) | (1 << 10) | (1 << 9) | (1 << 8) | (1 << 5) | (1 << 2) | (1 << 0); + var G15_MASK = (1 << 14) | (1 << 12) | (1 << 10) | (1 << 4) | (1 << 1); + + var _this = {}; + + var getBCHDigit = function(data) { + var digit = 0; + while (data != 0) { + digit += 1; + data >>>= 1; + } + return digit; + }; + + _this.getBCHTypeInfo = function(data) { + var d = data << 10; + while (getBCHDigit(d) - getBCHDigit(G15) >= 0) { + d ^= (G15 << (getBCHDigit(d) - getBCHDigit(G15) ) ); + } + return ( (data << 10) | d) ^ G15_MASK; + }; + + _this.getBCHTypeNumber = function(data) { + var d = data << 12; + while (getBCHDigit(d) - getBCHDigit(G18) >= 0) { + d ^= (G18 << (getBCHDigit(d) - getBCHDigit(G18) ) ); + } + return (data << 12) | d; + }; + + _this.getPatternPosition = function(typeNumber) { + return PATTERN_POSITION_TABLE[typeNumber - 1]; + }; + + _this.getMaskFunction = function(maskPattern) { + + switch (maskPattern) { + + case QRMaskPattern.PATTERN000 : + return function(i, j) { return (i + j) % 2 == 0; }; + case QRMaskPattern.PATTERN001 : + return function(i, j) { return i % 2 == 0; }; + case QRMaskPattern.PATTERN010 : + return function(i, j) { return j % 3 == 0; }; + case QRMaskPattern.PATTERN011 : + return function(i, j) { return (i + j) % 3 == 0; }; + case QRMaskPattern.PATTERN100 : + return function(i, j) { return (Math.floor(i / 2) + Math.floor(j / 3) ) % 2 == 0; }; + case QRMaskPattern.PATTERN101 : + return function(i, j) { return (i * j) % 2 + (i * j) % 3 == 0; }; + case QRMaskPattern.PATTERN110 : + return function(i, j) { return ( (i * j) % 2 + (i * j) % 3) % 2 == 0; }; + case QRMaskPattern.PATTERN111 : + return function(i, j) { return ( (i * j) % 3 + (i + j) % 2) % 2 == 0; }; + + default : + throw new Error('bad maskPattern:' + maskPattern); + } + }; + + _this.getErrorCorrectPolynomial = function(errorCorrectLength) { + var a = qrPolynomial([1], 0); + for (var i = 0; i < errorCorrectLength; i += 1) { + a = a.multiply(qrPolynomial([1, QRMath.gexp(i)], 0) ); + } + return a; + }; + + _this.getLengthInBits = function(mode, type) { + + if (1 <= type && type < 10) { + + // 1 - 9 + + switch(mode) { + case QRMode.MODE_NUMBER : return 10; + case QRMode.MODE_ALPHA_NUM : return 9; + case QRMode.MODE_8BIT_BYTE : return 8; + case QRMode.MODE_KANJI : return 8; + default : + throw new Error('mode:' + mode); + } + + } else if (type < 27) { + + // 10 - 26 + + switch(mode) { + case QRMode.MODE_NUMBER : return 12; + case QRMode.MODE_ALPHA_NUM : return 11; + case QRMode.MODE_8BIT_BYTE : return 16; + case QRMode.MODE_KANJI : return 10; + default : + throw new Error('mode:' + mode); + } + + } else if (type < 41) { + + // 27 - 40 + + switch(mode) { + case QRMode.MODE_NUMBER : return 14; + case QRMode.MODE_ALPHA_NUM : return 13; + case QRMode.MODE_8BIT_BYTE : return 16; + case QRMode.MODE_KANJI : return 12; + default : + throw new Error('mode:' + mode); + } + + } else { + throw new Error('type:' + type); + } + }; + + _this.getLostPoint = function(qrcode) { + + var moduleCount = qrcode.getModuleCount(); + + var lostPoint = 0; + + // LEVEL1 + + for (var row = 0; row < moduleCount; row += 1) { + for (var col = 0; col < moduleCount; col += 1) { + + var sameCount = 0; + var dark = qrcode.isDark(row, col); + + for (var r = -1; r <= 1; r += 1) { + + if (row + r < 0 || moduleCount <= row + r) { + continue; + } + + for (var c = -1; c <= 1; c += 1) { + + if (col + c < 0 || moduleCount <= col + c) { + continue; + } + + if (r == 0 && c == 0) { + continue; + } + + if (dark == qrcode.isDark(row + r, col + c) ) { + sameCount += 1; + } + } + } + + if (sameCount > 5) { + lostPoint += (3 + sameCount - 5); + } + } + }; + + // LEVEL2 + + for (var row = 0; row < moduleCount - 1; row += 1) { + for (var col = 0; col < moduleCount - 1; col += 1) { + var count = 0; + if (qrcode.isDark(row, col) ) count += 1; + if (qrcode.isDark(row + 1, col) ) count += 1; + if (qrcode.isDark(row, col + 1) ) count += 1; + if (qrcode.isDark(row + 1, col + 1) ) count += 1; + if (count == 0 || count == 4) { + lostPoint += 3; + } + } + } + + // LEVEL3 + + for (var row = 0; row < moduleCount; row += 1) { + for (var col = 0; col < moduleCount - 6; col += 1) { + if (qrcode.isDark(row, col) + && !qrcode.isDark(row, col + 1) + && qrcode.isDark(row, col + 2) + && qrcode.isDark(row, col + 3) + && qrcode.isDark(row, col + 4) + && !qrcode.isDark(row, col + 5) + && qrcode.isDark(row, col + 6) ) { + lostPoint += 40; + } + } + } + + for (var col = 0; col < moduleCount; col += 1) { + for (var row = 0; row < moduleCount - 6; row += 1) { + if (qrcode.isDark(row, col) + && !qrcode.isDark(row + 1, col) + && qrcode.isDark(row + 2, col) + && qrcode.isDark(row + 3, col) + && qrcode.isDark(row + 4, col) + && !qrcode.isDark(row + 5, col) + && qrcode.isDark(row + 6, col) ) { + lostPoint += 40; + } + } + } + + // LEVEL4 + + var darkCount = 0; + + for (var col = 0; col < moduleCount; col += 1) { + for (var row = 0; row < moduleCount; row += 1) { + if (qrcode.isDark(row, col) ) { + darkCount += 1; + } + } + } + + var ratio = Math.abs(100 * darkCount / moduleCount / moduleCount - 50) / 5; + lostPoint += ratio * 10; + + return lostPoint; + }; + + return _this; +}(); + +//--------------------------------------------------------------------- +// QRMath +//--------------------------------------------------------------------- + +var QRMath = function() { + + var EXP_TABLE = new Array(256); + var LOG_TABLE = new Array(256); + + // initialize tables + for (var i = 0; i < 8; i += 1) { + EXP_TABLE[i] = 1 << i; + } + for (var i = 8; i < 256; i += 1) { + EXP_TABLE[i] = EXP_TABLE[i - 4] + ^ EXP_TABLE[i - 5] + ^ EXP_TABLE[i - 6] + ^ EXP_TABLE[i - 8]; + } + for (var i = 0; i < 255; i += 1) { + LOG_TABLE[EXP_TABLE[i] ] = i; + } + + var _this = {}; + + _this.glog = function(n) { + + if (n < 1) { + throw new Error('glog(' + n + ')'); + } + + return LOG_TABLE[n]; + }; + + _this.gexp = function(n) { + + while (n < 0) { + n += 255; + } + + while (n >= 256) { + n -= 255; + } + + return EXP_TABLE[n]; + }; + + return _this; +}(); + +//--------------------------------------------------------------------- +// qrPolynomial +//--------------------------------------------------------------------- + +function qrPolynomial(num, shift) { + + if (typeof num.length == 'undefined') { + throw new Error(num.length + '/' + shift); + } + + var _num = function() { + var offset = 0; + while (offset < num.length && num[offset] == 0) { + offset += 1; + } + var _num = new Array(num.length - offset + shift); + for (var i = 0; i < num.length - offset; i += 1) { + _num[i] = num[i + offset]; + } + return _num; + }(); + + var _this = {}; + + _this.getAt = function(index) { + return _num[index]; + }; + + _this.getLength = function() { + return _num.length; + }; + + _this.multiply = function(e) { + + var num = new Array(_this.getLength() + e.getLength() - 1); + + for (var i = 0; i < _this.getLength(); i += 1) { + for (var j = 0; j < e.getLength(); j += 1) { + num[i + j] ^= QRMath.gexp(QRMath.glog(_this.getAt(i) ) + QRMath.glog(e.getAt(j) ) ); + } + } + + return qrPolynomial(num, 0); + }; + + _this.mod = function(e) { + + if (_this.getLength() - e.getLength() < 0) { + return _this; + } + + var ratio = QRMath.glog(_this.getAt(0) ) - QRMath.glog(e.getAt(0) ); + + var num = new Array(_this.getLength() ); + for (var i = 0; i < _this.getLength(); i += 1) { + num[i] = _this.getAt(i); + } + + for (var i = 0; i < e.getLength(); i += 1) { + num[i] ^= QRMath.gexp(QRMath.glog(e.getAt(i) ) + ratio); + } + + // recursive call + return qrPolynomial(num, 0).mod(e); + }; + + return _this; +}; + +//--------------------------------------------------------------------- +// QRRSBlock +//--------------------------------------------------------------------- + +var QRRSBlock = function() { + + + // [1: [L, M, Q, H], ..] + var RS_BLOCK_TABLE=[[1,26,19],[1,26,16],[1,26,13],[1,26,9],[1,44,34],[1,44,28],[1,44,22],[1,44,16],[1,70,55],[1,70,44],[2,35,17],[2,35,13],[1,100,80],[2,50,32],[2,50,24],[4,25,9],[1,134,108],[2,67,43],[2,33,15,2,34,16],[2,33,11,2,34,12],[2,86,68],[4,43,27],[4,43,19],[4,43,15],[2,98,78],[4,49,31],[2,32,14,4,33,15],[4,39,13,1,40,14],[2,121,97],[2,60,38,2,61,39],[4,40,18,2,41,19],[4,40,14,2,41,15],[2,146,116],[3,58,36,2,59,37],[4,36,16,4,37,17],[4,36,12,4,37,13],[2,86,68,2,87,69],[4,69,43,1,70,44],[6,43,19,2,44,20],[6,43,15,2,44,16],[4,101,81],[1,80,50,4,81,51],[4,50,22,4,51,23],[3,36,12,8,37,13],[2,116,92,2,117,93],[6,58,36,2,59,37],[4,46,20,6,47,21],[7,42,14,4,43,15],[4,133,107],[8,59,37,1,60,38],[8,44,20,4,45,21],[12,33,11,4,34,12],[3,145,115,1,146,116],[4,64,40,5,65,41],[11,36,16,5,37,17],[11,36,12,5,37,13],[5,109,87,1,110,88],[5,65,41,5,66,42],[5,54,24,7,55,25],[11,36,12],[5,122,98,1,123,99],[7,73,45,3,74,46],[15,43,19,2,44,20],[3,45,15,13,46,16],[1,135,107,5,136,108],[10,74,46,1,75,47],[1,50,22,15,51,23],[2,42,14,17,43,15],[5,150,120,1,151,121],[9,69,43,4,70,44],[17,50,22,1,51,23],[2,42,14,19,43,15],[3,141,113,4,142,114],[3,70,44,11,71,45],[17,47,21,4,48,22],[9,39,13,16,40,14],[3,135,107,5,136,108],[3,67,41,13,68,42],[15,54,24,5,55,25],[15,43,15,10,44,16],[4,144,116,4,145,117],[17,68,42],[17,50,22,6,51,23],[19,46,16,6,47,17],[2,139,111,7,140,112],[17,74,46],[7,54,24,16,55,25],[34,37,13],[4,151,121,5,152,122],[4,75,47,14,76,48],[11,54,24,14,55,25],[16,45,15,14,46,16],[6,147,117,4,148,118],[6,73,45,14,74,46],[11,54,24,16,55,25],[30,46,16,2,47,17],[8,132,106,4,133,107],[8,75,47,13,76,48],[7,54,24,22,55,25],[22,45,15,13,46,16],[10,142,114,2,143,115],[19,74,46,4,75,47],[28,50,22,6,51,23],[33,46,16,4,47,17],[8,152,122,4,153,123],[22,73,45,3,74,46],[8,53,23,26,54,24],[12,45,15,28,46,16],[3,147,117,10,148,118],[3,73,45,23,74,46],[4,54,24,31,55,25],[11,45,15,31,46,16],[7,146,116,7,147,117],[21,73,45,7,74,46],[1,53,23,37,54,24],[19,45,15,26,46,16],[5,145,115,10,146,116],[19,75,47,10,76,48],[15,54,24,25,55,25],[23,45,15,25,46,16],[13,145,115,3,146,116],[2,74,46,29,75,47],[42,54,24,1,55,25],[23,45,15,28,46,16],[17,145,115],[10,74,46,23,75,47],[10,54,24,35,55,25],[19,45,15,35,46,16],[17,145,115,1,146,116],[14,74,46,21,75,47],[29,54,24,19,55,25],[11,45,15,46,46,16],[13,145,115,6,146,116],[14,74,46,23,75,47],[44,54,24,7,55,25],[59,46,16,1,47,17],[12,151,121,7,152,122],[12,75,47,26,76,48],[39,54,24,14,55,25],[22,45,15,41,46,16],[6,151,121,14,152,122],[6,75,47,34,76,48],[46,54,24,10,55,25],[2,45,15,64,46,16],[17,152,122,4,153,123],[29,74,46,14,75,47],[49,54,24,10,55,25],[24,45,15,46,46,16],[4,152,122,18,153,123],[13,74,46,32,75,47],[48,54,24,14,55,25],[42,45,15,32,46,16],[20,147,117,4,148,118],[40,75,47,7,76,48],[43,54,24,22,55,25],[10,45,15,67,46,16],[19,148,118,6,149,119],[18,75,47,31,76,48],[34,54,24,34,55,25],[20,45,15,61,46,16]]; + + var qrRSBlock = function(totalCount, dataCount) { + var _this = {}; + _this.totalCount = totalCount; + _this.dataCount = dataCount; + return _this; + }; + + var _this = {}; + + var getRsBlockTable = function(typeNumber, errorCorrectLevel) { + + switch(errorCorrectLevel) { + case QRErrorCorrectLevel.L : + return RS_BLOCK_TABLE[(typeNumber - 1) * 4 + 0]; + case QRErrorCorrectLevel.M : + return RS_BLOCK_TABLE[(typeNumber - 1) * 4 + 1]; + case QRErrorCorrectLevel.Q : + return RS_BLOCK_TABLE[(typeNumber - 1) * 4 + 2]; + case QRErrorCorrectLevel.H : + return RS_BLOCK_TABLE[(typeNumber - 1) * 4 + 3]; + default : + return undefined; + } + }; + + _this.getRSBlocks = function(typeNumber, errorCorrectLevel) { + + var rsBlock = getRsBlockTable(typeNumber, errorCorrectLevel); + + if (typeof rsBlock == 'undefined') { + throw new Error('bad rs block @ typeNumber:' + typeNumber + + '/errorCorrectLevel:' + errorCorrectLevel); + } + + var length = rsBlock.length / 3; + + var list = new Array(); + + for (var i = 0; i < length; i += 1) { + + var count = rsBlock[i * 3 + 0]; + var totalCount = rsBlock[i * 3 + 1]; + var dataCount = rsBlock[i * 3 + 2]; + + for (var j = 0; j < count; j += 1) { + list.push(qrRSBlock(totalCount, dataCount) ); + } + } + + return list; + }; + + return _this; +}(); + +//--------------------------------------------------------------------- +// qrBitBuffer +//--------------------------------------------------------------------- + +var qrBitBuffer = function() { + + var _buffer = new Array(); + var _length = 0; + + var _this = {}; + + _this.getBuffer = function() { + return _buffer; + }; + + _this.getAt = function(index) { + var bufIndex = Math.floor(index / 8); + return ( (_buffer[bufIndex] >>> (7 - index % 8) ) & 1) == 1; + }; + + _this.put = function(num, length) { + for (var i = 0; i < length; i += 1) { + _this.putBit( ( (num >>> (length - i - 1) ) & 1) == 1); + } + }; + + _this.getLengthInBits = function() { + return _length; + }; + + _this.putBit = function(bit) { + + var bufIndex = Math.floor(_length / 8); + if (_buffer.length <= bufIndex) { + _buffer.push(0); + } + + if (bit) { + _buffer[bufIndex] |= (0x80 >>> (_length % 8) ); + } + + _length += 1; + }; + + return _this; +}; + +//--------------------------------------------------------------------- +// qr8BitByte +//--------------------------------------------------------------------- + +var qr8BitByte = function(data) { + + var _mode = QRMode.MODE_8BIT_BYTE; + var _data = data; + var _parsedData = []; + + var _this = {}; + + + // Added to support UTF-8 Characters + for (var i = 0, l = _data.length; i < l; i++) { + var byteArray = []; + var code = _data.charCodeAt(i); + + if (code > 0x10000) { + byteArray[0] = 0xF0 | ((code & 0x1C0000) >>> 18); + byteArray[1] = 0x80 | ((code & 0x3F000) >>> 12); + byteArray[2] = 0x80 | ((code & 0xFC0) >>> 6); + byteArray[3] = 0x80 | (code & 0x3F); + } else if (code > 0x800) { + byteArray[0] = 0xE0 | ((code & 0xF000) >>> 12); + byteArray[1] = 0x80 | ((code & 0xFC0) >>> 6); + byteArray[2] = 0x80 | (code & 0x3F); + } else if (code > 0x80) { + byteArray[0] = 0xC0 | ((code & 0x7C0) >>> 6); + byteArray[1] = 0x80 | (code & 0x3F); + } else { + byteArray[0] = code; + } + + // Fix Unicode corruption bug + _parsedData.push(byteArray); + } + + _parsedData = Array.prototype.concat.apply([], _parsedData); + + if (_parsedData.length != _data.length) { + _parsedData.unshift(191); + _parsedData.unshift(187); + _parsedData.unshift(239); + } + + var _bytes = _parsedData; + + _this.getMode = function() { + return _mode; + }; + + _this.getLength = function(buffer) { + return _bytes.length; + }; + + _this.write = function(buffer) { + for (var i = 0; i < _bytes.length; i += 1) { + buffer.put(_bytes[i], 8); + } + }; + + return _this; +}; + +//===================================================================== +// GIF Support etc. +// + +//--------------------------------------------------------------------- +// byteArrayOutputStream +//--------------------------------------------------------------------- + +var byteArrayOutputStream = function() { + + var _bytes = new Array(); + + var _this = {}; + + _this.writeByte = function(b) { + _bytes.push(b & 0xff); + }; + + _this.writeShort = function(i) { + _this.writeByte(i); + _this.writeByte(i >>> 8); + }; + + _this.writeBytes = function(b, off, len) { + off = off || 0; + len = len || b.length; + for (var i = 0; i < len; i += 1) { + _this.writeByte(b[i + off]); + } + }; + + _this.writeString = function(s) { + for (var i = 0; i < s.length; i += 1) { + _this.writeByte(s.charCodeAt(i) ); + } + }; + + _this.toByteArray = function() { + return _bytes; + }; + + _this.toString = function() { + var s = ''; + s += '['; + for (var i = 0; i < _bytes.length; i += 1) { + if (i > 0) { + s += ','; + } + s += _bytes[i]; + } + s += ']'; + return s; + }; + + return _this; +}; + +//--------------------------------------------------------------------- +// base64EncodeOutputStream +//--------------------------------------------------------------------- + +var base64EncodeOutputStream = function() { + + var _buffer = 0; + var _buflen = 0; + var _length = 0; + var _base64 = ''; + + var _this = {}; + + var writeEncoded = function(b) { + _base64 += String.fromCharCode(encode(b & 0x3f) ); + }; + + var encode = function(n) { + if (n < 0) { + // error. + } else if (n < 26) { + return 0x41 + n; + } else if (n < 52) { + return 0x61 + (n - 26); + } else if (n < 62) { + return 0x30 + (n - 52); + } else if (n == 62) { + return 0x2b; + } else if (n == 63) { + return 0x2f; + } + throw new Error('n:' + n); + }; + + _this.writeByte = function(n) { + + _buffer = (_buffer << 8) | (n & 0xff); + _buflen += 8; + _length += 1; + + while (_buflen >= 6) { + writeEncoded(_buffer >>> (_buflen - 6) ); + _buflen -= 6; + } + }; + + _this.flush = function() { + + if (_buflen > 0) { + writeEncoded(_buffer << (6 - _buflen) ); + _buffer = 0; + _buflen = 0; + } + + if (_length % 3 != 0) { + // padding + var padlen = 3 - _length % 3; + for (var i = 0; i < padlen; i += 1) { + _base64 += '='; + } + } + }; + + _this.toString = function() { + return _base64; + }; + + return _this; +}; + +//--------------------------------------------------------------------- +// base64DecodeInputStream +//--------------------------------------------------------------------- + +var base64DecodeInputStream = function(str) { + + var _str = str; + var _pos = 0; + var _buffer = 0; + var _buflen = 0; + + var _this = {}; + + _this.read = function() { + + while (_buflen < 8) { + + if (_pos >= _str.length) { + if (_buflen == 0) { + return -1; + } + throw new Error('unexpected end of file./' + _buflen); + } + + var c = _str.charAt(_pos); + _pos += 1; + + if (c == '=') { + _buflen = 0; + return -1; + } else if (c.match(/^\s$/) ) { + // ignore if whitespace. + continue; + } + + _buffer = (_buffer << 6) | decode(c.charCodeAt(0) ); + _buflen += 6; + } + + var n = (_buffer >>> (_buflen - 8) ) & 0xff; + _buflen -= 8; + return n; + }; + + var decode = function(c) { + if (0x41 <= c && c <= 0x5a) { + return c - 0x41; + } else if (0x61 <= c && c <= 0x7a) { + return c - 0x61 + 26; + } else if (0x30 <= c && c <= 0x39) { + return c - 0x30 + 52; + } else if (c == 0x2b) { + return 62; + } else if (c == 0x2f) { + return 63; + } else { + throw new Error('c:' + c); + } + }; + + return _this; +}; + +//--------------------------------------------------------------------- +// gifImage (B/W) +//--------------------------------------------------------------------- + +var gifImage = function(width, height) { + + var _width = width; + var _height = height; + var _data = new Array(width * height); + + var _this = {}; + + _this.setPixel = function(x, y, pixel) { + _data[y * _width + x] = pixel; + }; + + _this.write = function(out) { + + //--------------------------------- + // GIF Signature + + out.writeString('GIF87a'); + + //--------------------------------- + // Screen Descriptor + + out.writeShort(_width); + out.writeShort(_height); + + out.writeByte(0x80); // 2bit + out.writeByte(0); + out.writeByte(0); + + //--------------------------------- + // Global Color Map + + // black + out.writeByte(0x00); + out.writeByte(0x00); + out.writeByte(0x00); + + // white + out.writeByte(0xff); + out.writeByte(0xff); + out.writeByte(0xff); + + //--------------------------------- + // Image Descriptor + + out.writeString(','); + out.writeShort(0); + out.writeShort(0); + out.writeShort(_width); + out.writeShort(_height); + out.writeByte(0); + + //--------------------------------- + // Local Color Map + + //--------------------------------- + // Raster Data + + var lzwMinCodeSize = 2; + var raster = getLZWRaster(lzwMinCodeSize); + + out.writeByte(lzwMinCodeSize); + + var offset = 0; + + while (raster.length - offset > 255) { + out.writeByte(255); + out.writeBytes(raster, offset, 255); + offset += 255; + } + + out.writeByte(raster.length - offset); + out.writeBytes(raster, offset, raster.length - offset); + out.writeByte(0x00); + + //--------------------------------- + // GIF Terminator + out.writeString(';'); + }; + + var bitOutputStream = function(out) { + + var _out = out; + var _bitLength = 0; + var _bitBuffer = 0; + + var _this = {}; + + _this.write = function(data, length) { + + if ( (data >>> length) != 0) { + throw new Error('length over'); + } + + while (_bitLength + length >= 8) { + _out.writeByte(0xff & ( (data << _bitLength) | _bitBuffer) ); + length -= (8 - _bitLength); + data >>>= (8 - _bitLength); + _bitBuffer = 0; + _bitLength = 0; + } + + _bitBuffer = (data << _bitLength) | _bitBuffer; + _bitLength = _bitLength + length; + }; + + _this.flush = function() { + if (_bitLength > 0) { + _out.writeByte(_bitBuffer); + } + }; + + return _this; + }; + + var getLZWRaster = function(lzwMinCodeSize) { + + var clearCode = 1 << lzwMinCodeSize; + var endCode = (1 << lzwMinCodeSize) + 1; + var bitLength = lzwMinCodeSize + 1; + + // Setup LZWTable + var table = lzwTable(); + + for (var i = 0; i < clearCode; i += 1) { + table.add(String.fromCharCode(i) ); + } + table.add(String.fromCharCode(clearCode) ); + table.add(String.fromCharCode(endCode) ); + + var byteOut = byteArrayOutputStream(); + var bitOut = bitOutputStream(byteOut); + + // clear code + bitOut.write(clearCode, bitLength); + + var dataIndex = 0; + + var s = String.fromCharCode(_data[dataIndex]); + dataIndex += 1; + + while (dataIndex < _data.length) { + + var c = String.fromCharCode(_data[dataIndex]); + dataIndex += 1; + + if (table.contains(s + c) ) { + + s = s + c; + + } else { + + bitOut.write(table.indexOf(s), bitLength); + + if (table.size() < 0xfff) { + + if (table.size() == (1 << bitLength) ) { + bitLength += 1; + } + + table.add(s + c); + } + + s = c; + } + } + + bitOut.write(table.indexOf(s), bitLength); + + // end code + bitOut.write(endCode, bitLength); + + bitOut.flush(); + + return byteOut.toByteArray(); + }; + + var lzwTable = function() { + + var _map = {}; + var _size = 0; + + var _this = {}; + + _this.add = function(key) { + if (_this.contains(key) ) { + throw new Error('dup key:' + key); + } + _map[key] = _size; + _size += 1; + }; + + _this.size = function() { + return _size; + }; + + _this.indexOf = function(key) { + return _map[key]; + }; + + _this.contains = function(key) { + return typeof _map[key] != 'undefined'; + }; + + return _this; + }; + + return _this; +}; + +var createImgTag = function(width, height, getPixel, alt) { + + var gif = gifImage(width, height); + for (var y = 0; y < height; y += 1) { + for (var x = 0; x < width; x += 1) { + gif.setPixel(x, y, getPixel(x, y) ); + } + } + + var b = byteArrayOutputStream(); + gif.write(b); + + var base64 = base64EncodeOutputStream(); + var bytes = b.toByteArray(); + for (var i = 0; i < bytes.length; i += 1) { + base64.writeByte(bytes[i]); + } + base64.flush(); + + var img = ''; + img += 'data:image/gif;base64,'; + img += base64; + + return img; +}; + +//--------------------------------------------------------------------- +// returns qrcode function. + +var drawImg = function(text, options) { + options = options || {}; + var typeNumber = options.typeNumber || 4; + var errorCorrectLevel = options.errorCorrectLevel || 'M'; + var size = options.size || 500; + + var qr; + + try { + qr = qrcode(typeNumber, errorCorrectLevel || 'M'); + qr.addData(text); + qr.make(); + } catch (e) { + if(typeNumber >= 40) { + throw new Error('Text too long to encode'); + } else { + return drawImg(text, { + size: size, + errorCorrectLevel: errorCorrectLevel, + typeNumber: typeNumber + 1 + }); + } + } + + // calc cellsize and margin + var cellsize = parseInt(size / qr.getModuleCount()); + var margin = parseInt((size - qr.getModuleCount() * cellsize) / 2); + + return qr.createImgTag(cellsize, margin, size); +}; +export default { + drawImg: drawImg +}; \ No newline at end of file diff --git a/commons/utils/returrn-data.js b/commons/utils/returrn-data.js new file mode 100644 index 0000000..3619e8e --- /dev/null +++ b/commons/utils/returrn-data.js @@ -0,0 +1,7 @@ +export const objToArrary = (obj,keyNewName) => { + return Object.entries(obj).map(([key, value]) => ({ + key, + [keyNewName]:key, + ...value, + })) +} \ No newline at end of file diff --git a/commons/utils/rsaEncrypt.js b/commons/utils/rsaEncrypt.js new file mode 100644 index 0000000..1948ddd --- /dev/null +++ b/commons/utils/rsaEncrypt.js @@ -0,0 +1,14 @@ +import JSEncrypt from 'jsencrypt/bin/jsencrypt.min' + +// 密钥对生成 http://web.chacuo.net/netrsakeypair + +const publicKey = 'MFwwDQYJKoZIhvcNAQEBBQADSwAwSAJBANL378k3RiZHWx5AfJqdH9xRNBmD9wGD\n' + + '2iRe41HdTNF8RUhNnHit5NpMNtGL0NPTSSpPjjI1kJfVorRvaQerUgkCAwEAAQ==' + +// 加密 +export function encrypt(txt) { + const encryptor = new JSEncrypt() + encryptor.setPublicKey(publicKey) // 设置公钥 + return encryptor.encrypt(txt) // 对需要加密的数据进行加密 +} + diff --git a/commons/utils/safe-bottom.js b/commons/utils/safe-bottom.js new file mode 100644 index 0000000..9cfddc1 --- /dev/null +++ b/commons/utils/safe-bottom.js @@ -0,0 +1,35 @@ +import { + getCurrentInstance, +} from 'vue'; +export async function getElRect(elClass, instance,option) { + instance = instance ? instance : getCurrentInstance(); + const query = uni.createSelectorQuery().in(instance.proxy); + try{ + const res= await getEle(query,elClass,option) + return res + }catch(e){ + console.log(e); + } +} +async function getEle(query,elClass,option){ + return new Promise((resolve, reject)=>{ + query.select('.' + elClass).fields({ + size: true, + ...option + }, res => { + // 如果节点尚未生成,res值为null,循环调用执行 + if (!res) { + return setTimeout(() => { + getEle(query,elClass,option); + }, 10); + } + resolve(res); + }).exec(); + }) + +} + +export async function getSafeBottomHeight(className, height = 16) { + const bottomEle = await getElRect(className) + return bottomEle.height + height +} \ No newline at end of file diff --git a/commons/utils/saveImg.js b/commons/utils/saveImg.js new file mode 100644 index 0000000..98533ad --- /dev/null +++ b/commons/utils/saveImg.js @@ -0,0 +1,38 @@ +// 保存图片 +export function saveHeadImgFile(base64, quality) { + const bitmap = new plus.nativeObj.Bitmap("test"); + return new Promise((resolve, reject) => { + // 从本地加载Bitmap图片 + bitmap.loadBase64Data(base64, function() { + const url = "_doc/" + getTimeStamps() + ".png"; // url为时间戳命名方式 + + bitmap.save(url, { + overwrite: true, // 是否覆盖 + quality: quality // 图片清晰度 + }, (i) => { + console.log(url) + uni.saveImageToPhotosAlbum({ + filePath: url, + success: function() { + resolve({ + code: 0, + msg: '保存成功', + filePath: url + }); + }, + fail:function(){ + msg:'保存失败' + } + }); + }, (e) => { + reject('保存图片失败:' + JSON.stringify(e)); + }); + }, (e) => { + reject('加载图片失败:' + JSON.stringify(e)); + }); + }) +} + +function getTimeStamps (){ + return (new Date()).valueOf() +} \ No newline at end of file diff --git a/commons/utils/storageManage.js b/commons/utils/storageManage.js new file mode 100644 index 0000000..27c5fdd --- /dev/null +++ b/commons/utils/storageManage.js @@ -0,0 +1,290 @@ +/** + * 存储管理对象 + * 目标:将现有系统的所有需要存储的数据,统一管理 + * + * @author terrfly + * @site https://www.jeequan.com + * @date 2022/04/13 07:18 + */ + +import appConfig from "@/config/appConfig.js" + +// 应用级(vue级别)缓存, 当存在时则读取此值, 否则读取storage中的值。( vue线程内的缓存,不必要每次读取应用数据,影响性能) +const appCache = { + tokenVal: null, // token取值 + currentUser: null, // 当前商户信息 +} + +const model = { + + setLogin(res){ + const user=res.user.user + uni.setStorageSync('logoutHandle',false) + uni.setStorageSync('shopId', res.shopId) + uni.setStorageSync('shopName',res.shopName) + uni.setStorageSync('logo',res.logo) + uni.setStorageSync('loginType',res.loginType) + uni.setStorageSync('shopUserId',user.id) + if(res.loginType=='staff'){ + uni.setStorageSync('merchantName',user.createBy||user.updateBy) + } + }, + // 退出清空所有的缓存数据。 (不包含 环境相关) + cleanByLogout: () => { + // 1. 清空app级别缓存。 + Object.keys(appCache).forEach(k => appCache[k] = null) + const merchantName=uni.getStorageSync('merchantName') + const MerchantId=uni.getStorageSync('MerchantId') + let envName = model.env() // 获取到当前的环境变量 + uni.clearStorageSync() // 清除所有的缓存信息 + uni.setStorageSync('merchantName',merchantName) + uni.setStorageSync('MerchantId',MerchantId) + model.env(envName) // 重置env + }, + + // 获取和放置token + token: (val, isDelete = false) => { + if (isDelete) { + appCache.tokenVal = "" + return uni.removeStorageSync(appConfig.tokenKey) + } + + if (val) { + // 有值,为放置 + appCache.tokenVal = val + uni.setStorageSync(appConfig.tokenKey, val) + } else { + // 否则为获取 + + if (!appCache.tokenVal) { + //缓存取不到,获取应用本地信息 + appCache.tokenVal = uni.getStorageSync(appConfig.tokenKey) + } + return appCache.tokenVal + } + }, + // 获取和放置shopId + shopId: (val, isDelete = false) => { + if (isDelete) { + appCache.shopId = "" + return uni.removeStorageSync('shopId') + } + + if (val) { + // 有值,为放置 + appCache.shopId = val + uni.setStorageSync('shopId', val) + } else { + // 否则为获取 + + if (!appCache.shopId) { + //缓存取不到,获取应用本地信息 + appCache.shopId = uni.getStorageSync('shopId') + } + return appCache.shopId + } + }, + // 获取和放置店铺员工id + shopUserId: (val, isDelete = false) => { + if (isDelete) { + appCache.shopUserId = "" + return uni.removeStorageSync('shopUserId') + } + + if (val) { + // 有值,为放置 + appCache.shopUserId = val + uni.setStorageSync('shopUserId', val) + } else { + // 否则为获取 + + if (!appCache.shopUserId) { + //缓存取不到,获取应用本地信息 + appCache.shopUserId = uni.getStorageSync('shopUserId') + } + return appCache.shopUserId + } + }, + // 获取和放置useType就餐类型 + useType: (val, isDelete = false) => { + if (isDelete) { + appCache.useType = "" + return uni.removeStorageSync('useType') + } + + if (val) { + // 有值,为放置 + appCache.useType = val + uni.setStorageSync('useType', val) + } else { + // 否则为获取 + + if (!appCache.useType) { + //缓存取不到,获取应用本地信息 + appCache.useType = uni.getStorageSync('useType') + } + return appCache.useType + } + }, + // 缓存代客下单商品 + cacheGoods: (val, isDelete = false) => { + if (isDelete) { + appCache.cacheGoods = "" + return uni.removeStorageSync('cacheGoods') + } + + if (val) { + // 有值,为放置 + appCache.cacheGoods = val + uni.setStorageSync('cacheGoods', val) + } else { + // 否则为获取 + + if (!appCache.cacheGoods) { + //缓存取不到,获取应用本地信息 + appCache.cacheGoods = uni.getStorageSync('cacheGoods') + } + return appCache.cacheGoods + } + }, + // 缓存代客下单商品节点信息缓存 + cacheGoodsNode: (val, isDelete = false) => { + if (isDelete) { + appCache.cacheGoodsNode = "" + return uni.removeStorageSync('cacheGoodsNode') + } + + if (val) { + // 有值,为放置 + appCache.cacheGoodsNode = val + uni.setStorageSync('cacheGoodsNode', val) + } else { + // 否则为获取 + + if (!appCache.cacheGoodsNode) { + //缓存取不到,获取应用本地信息 + appCache.cacheGoodsNode = uni.getStorageSync('cacheGoodsNode') + } + return appCache.cacheGoodsNode + } + }, + // 已经登录的用户记录 + loggedInUser: (addUserName = null, removeUserName = null) => { + let key = "loggedInUserList" + + // 删除 + if (removeUserName) { + let nameList = uni.getStorageSync(key) || [] + if (nameList.length <= 0) { + //不存在数据 + return false + } + + let hasUserIndex = nameList.indexOf(removeUserName) + if (hasUserIndex >= 0) { + nameList.splice(hasUserIndex, 1) //删除 + uni.setStorageSync(key, nameList) + } + + return false + } + + // 有新插入的记录 + if (addUserName) { + let nameList = uni.getStorageSync(key) || [] + + let hasUser = false + for (let i = 0; i < nameList.length; i++) { + if (nameList[i] == addUserName) { + hasUser = true + } + } + + // 包含记录 + if (hasUser) { + return false + } + + // 最多存储 5 个 + if (nameList.length >= 5) { + nameList.splice(0, 1) //删除第一个 + } + nameList.push(addUserName) + uni.setStorageSync(key, nameList) + + //获取 + } else { + return uni.getStorageSync(key) || [] //默认空数组 + } + }, + + // 用户信息 + userInfo: (currentUserInfo) => { + if (currentUserInfo) { + // 仅保存基础数据 + let saveUser = { + + sysUserId: currentUserInfo.sysUserId, // 用户ID + realname: currentUserInfo.realname, // 用户姓名 + avatarUrl: currentUserInfo.avatarUrl, // 头像 + telphone: currentUserInfo.telphone, // 手机号 + userType: currentUserInfo.userType, // 用户类型 + + mchNo: currentUserInfo.userNo, // 商户No + mchShortName: currentUserInfo.shortName, // 商户简称 + mchType: currentUserInfo.mchType, // 商户类型 + mchLevel: currentUserInfo.mchLevel, // 商户级别 + isHasMemberEnt:currentUserInfo.isHasMemberEnt,// 是否购买会员模块 + entIdList: currentUserInfo.entIdList, // 权限集合List + + } + uni.setStorageSync("currentUserInfo", saveUser) // 改变存储 + appCache.currentUser = null + } + + if(!appCache.currentUser){ // 获取缓存数据 + appCache.currentUser = uni.getStorageSync("currentUserInfo") + } + + return appCache.currentUser + }, + + // 项目环境变量:(测试、 生产的切换) + env: (envMode) => { + if (envMode) { + uni.setStorageSync(appConfig.storeEnvEnumKey, envMode) // 改变存储 + } + return uni.getStorageSync(appConfig.storeEnvEnumKey) + }, + + // push 状态是否开启 + pushIsOpen: (pushFlag) => { + if (pushFlag) { + uni.setStorageSync('pushFlag', pushFlag) // 改变存储 + } + return uni.getStorageSync('pushFlag') + }, + // 网站信息 + siteInfos: (siteInfos) => { + if (siteInfos) { + uni.setStorageSync("siteInfos", siteInfos) // 改变存储 + } + return uni.getStorageSync("siteInfos") + }, + + // unipush2 cid + uniPush2Cid: (uniPush2Cid) => { + if (uniPush2Cid) { + uni.setStorageSync("uniPush2Cid", uniPush2Cid) // 改变存储 + } + return uni.getStorageSync("uniPush2Cid") + }, + uploadImgSize: (uploadImgSize) => { + if (uploadImgSize) { + uni.setStorageSync("uploadImgSize", uploadImgSize) // 存储 上传 图片大小限制 + } + return uni.getStorageSync("uploadImgSize") + }, +} + +export default model diff --git a/commons/utils/throttle.js b/commons/utils/throttle.js new file mode 100644 index 0000000..c78d59c --- /dev/null +++ b/commons/utils/throttle.js @@ -0,0 +1,29 @@ +/** + * @desc 函数节流 + * @param func 函数 + * @param wait 延迟执行毫秒数 + * @param type 1 使用表时间戳,在时间段开始的时候触发 2 使用表定时器,在时间段结束的时候触发 + */ +export const throttle = (func, wait = 1000, type = 1) => { + let previous = 0; + let timeout; + return function() { + let context = this; + let args = arguments; + if (type === 1) { + let now = Date.now(); + + if (now - previous > wait) { + func.apply(context, args); + previous = now; + } + } else if (type === 2) { + if (!timeout) { + timeout = setTimeout(() => { + timeout = null; + func.apply(context, args) + }, wait) + } + } + } +} diff --git a/commons/utils/timeInspect.js b/commons/utils/timeInspect.js new file mode 100644 index 0000000..5097766 --- /dev/null +++ b/commons/utils/timeInspect.js @@ -0,0 +1,14 @@ +import dayjs from 'dayjs' //时间格式库 +import infoBox from '@/commons/utils/infoBox.js' +// 时间校验 用于筛选 开始 时间不能大于结束 开始结束时间必选 时间 返回值 true 和 false +export const startAndEndTime = (start, end) => { + if (!start || !end) { + infoBox.showToast('请选择开始或结束时间') + return false + } + if (dayjs(start).isAfter(end)) { + infoBox.showToast('开始时间不能大于结束时间') + return false + } + return true +} diff --git a/commons/utils/timer.js b/commons/utils/timer.js new file mode 100644 index 0000000..546fa94 --- /dev/null +++ b/commons/utils/timer.js @@ -0,0 +1,54 @@ +/** + * 任务执行器 + * + * @author terrfly + * @site https://www.jeepay.vip + * @date 2022/11/15 16:30 + */ +const model = { + + + // 任务启动工具, 每 xxs调用一次, 知道多次x次为止。 + // 注意: 启动后将立马调用一次, 而不是1s后再调用。 + + // 参数: + // allCount: 全部的次数 (支持promise 并不一定是 秒) + // stepSecond : 步伐(单位: 秒) + // callbackFunc 回调函数, 支持返回 boolean 或者 promise , + // 注意: boolean类型: true 进入下一次循环, false: 停止任务。 + // promise类型: then 进入下一次循环, catch: 停止任务。 + startTimeoutTask: (stepSecond, allCount, callbackFunc) => { + + // 不存在回调函数 + if(!callbackFunc){ + return false; + } + + let callbackResult = callbackFunc(allCount) + + // 明确返回false, 说明不再循环 + if(callbackResult === false){ + return false + } + + // 不包含剩余次数了。 + if(allCount <= 0){ + return false + } + + // promise + if(typeof callbackResult == 'object'){ + + callbackResult.then(() => { + setTimeout(() => model.startTimeoutTask(stepSecond, --allCount, callbackFunc), (stepSecond * 1000) ) + }) + + }else{ // 其他boolean类型, 或返回不明确, 继续下一次任务。 + + setTimeout(() => model.startTimeoutTask(stepSecond, --allCount, callbackFunc), (stepSecond * 1000) ) + } + } +} + +export default model + diff --git a/commons/utils/unionScan.js b/commons/utils/unionScan.js new file mode 100644 index 0000000..cf04a1e --- /dev/null +++ b/commons/utils/unionScan.js @@ -0,0 +1,62 @@ +/** + * 统一扫码, 支持登录、 码牌绑定、 打印机、 等 + * + * @author terrfly + * @site https://www.jeepay.vip + * @date 2022/11/22 10:38 + */ + +import { $parseQrCodeUrl } from '@/http/apiManager.js' + +const model = { + + // 扫码结果类型 + QR_TYPE_LOGIN: 'QR_TYPE_LOGIN', // 登录 + QR_TYPE_QRC: 'QR_TYPE_QRC', // 码牌 + QR_TYPE_PRINTER: 'QR_TYPE_PRINTER', // 打印机 + QR_TYPE_OTHER: 'QR_TYPE_OTHER', // 其他 + + + returnFunc: (type, bizValue, originQrVal) => { + return { type: type, bizValue: bizValue, originQrVal: originQrVal} + }, + + // 解析 码牌 + parseQrc: (originQrVal) => { + return $parseQrCodeUrl(originQrVal).then( ({bizData}) => { + return model.returnFunc(model.QR_TYPE_QRC, bizData, originQrVal) + }) + }, + + + // 返回 类型 和 扫码的值 + // 参数: 是否解析qrc , 默认不解析 + scan: (isParseQRC = false) => { + + return uni.scanCode().then(({ result }) => { + + // 登录类型 + if(result.startsWith("JEEPAY_LOGIN_QR_")){ + return model.returnFunc(model.QR_TYPE_LOGIN, result.substring(16), result) + } + + + if(isParseQRC){ + return model.parseQrc(result).then( (res) => { + return res; + }).catch(() => { + return model.returnFunc(model.QR_TYPE_OTHER, result, result) + }) + }else{ + + return model.returnFunc(model.QR_TYPE_OTHER, result, result) + + } + + }) + } + +} + +export default model + diff --git a/commons/utils/useStroage.js b/commons/utils/useStroage.js new file mode 100644 index 0000000..da32ab5 --- /dev/null +++ b/commons/utils/useStroage.js @@ -0,0 +1,14 @@ +export default { + get(key) { + return uni.getStorageSync(key) + }, + set(key, value) { + uni.setStorageSync(key, value) + }, + del(key) { + uni.removeStorageSync(key) + }, + clear() { + uni.clearStorageSync() + } +} \ No newline at end of file diff --git a/commons/utils/versionManage.js b/commons/utils/versionManage.js new file mode 100644 index 0000000..0f98233 --- /dev/null +++ b/commons/utils/versionManage.js @@ -0,0 +1,121 @@ +import { $versionDetection } from '@/http/apiManager.js'; +import appConfig from '@/config/appConfig.js' + +// app更新 +function appPlusUpdate(sign){ + + // 获取版本号 + plus.runtime.getProperty(plus.runtime.appid, function(inf) { + + // 调起接口查询 + $versionDetection({versionNumber: inf.versionCode}) + .then(({ bizData }) => { + + //返回data为空或者版本号一致 + if (!bizData || Object.keys(bizData).length == 0 || !bizData.versionSerialNumber || bizData.versionSerialNumber == inf.versionCode) { + if(sign === 'checked') { + uni.showToast({ + title: '已是最新版本' + }) + } + return false; + } + // 是否强制更新 + let isForceUpdate = bizData.forceUpdate == 1 + uni.showModal({ + title: '发现新版本:' + bizData.versionName, + showCancel: !isForceUpdate , + content: bizData.versionDesc, + confirmText: '立即更新', + confirmColor: '#108EE9', + success: function(r) { + if (r.confirm) { + downLoad(bizData.downloadUrl); + }else{ + // 强制更新也需要更新 + if(isForceUpdate){ + downLoad(bizData.downloadUrl); + } + } + } + }); + }); + }); +} + +//下载更新包 +function downLoad(url) { + + if (!url) { + uni.showToast({icon: 'none',title: '下载地址错误'}); + return false; + } + // 下载文件 + uni.showLoading({title: '更新中'}); + uni.downloadFile({ + url: url, + success: res => { + uni.hideLoading(); + if (res.statusCode === 200) { + uni.showToast({title: '下载成功'}); + plus.runtime.install(res.tempFilePath); + } + }, + fail: res => { + uni.hideLoading(); + } + }); +} + + +// 获取当前版本 & 检查 +export function getCurrentVersionPromise() { + let isApp = false + +// #ifdef APP-PLUS + isApp = true +// #endif + + if(!isApp){ + return Promise.reject() + } + +// 获取版本号 + return new Promise((resolve, reject) => { + plus.runtime.getProperty(plus.runtime.appid, function(inf) { + resolve(inf) + }) + }) + +} + +// 获取当前版本 & 检查 +export function checkCurrVersion(sign) { +// #ifdef APP-PLUS + switch(uni.getSystemInfoSync().platform){ + case 'android': + appPlusUpdate(sign) //仅安卓更新 + break; + case 'ios': + break; + default: + break; + } +// #endif +} + + +//同步取出ext.json对象 +export function getExtStoreId(){ + try{ + const extConfig = uni.getExtConfigSync() + if(extConfig.domain){ + appConfig.env.JEEPAY_BASE_URL = extConfig.domain + } + // uni.showToast({title: JSON.stringify(extConfig),icon:"none",duration:3000}); + console.log(extConfig,'extJson对象'); + return extConfig; + }catch(err){ + console.log(err,'getExtStoreId__error') + } +} \ No newline at end of file diff --git a/commons/week.js b/commons/week.js new file mode 100644 index 0000000..b7b85da --- /dev/null +++ b/commons/week.js @@ -0,0 +1 @@ +export const $weeks=['周一','周二','周三','周四','周五','周六','周日']; \ No newline at end of file diff --git a/components/Button/Button.vue b/components/Button/Button.vue new file mode 100644 index 0000000..3bed10f --- /dev/null +++ b/components/Button/Button.vue @@ -0,0 +1,37 @@ + + + + + + + \ No newline at end of file diff --git a/components/JAgree/JAgree.vue b/components/JAgree/JAgree.vue new file mode 100644 index 0000000..72c1f08 --- /dev/null +++ b/components/JAgree/JAgree.vue @@ -0,0 +1,133 @@ + + + + + + \ No newline at end of file diff --git a/components/JAppPopup/JAppPopup.vue b/components/JAppPopup/JAppPopup.vue new file mode 100644 index 0000000..3cbf4af --- /dev/null +++ b/components/JAppPopup/JAppPopup.vue @@ -0,0 +1,185 @@ + + + + + diff --git a/components/JCell/JCell.vue b/components/JCell/JCell.vue new file mode 100644 index 0000000..29fdb4f --- /dev/null +++ b/components/JCell/JCell.vue @@ -0,0 +1,57 @@ + + + + + diff --git a/components/JDetailsCell/JDetailsCell.vue b/components/JDetailsCell/JDetailsCell.vue new file mode 100644 index 0000000..7c92a3f --- /dev/null +++ b/components/JDetailsCell/JDetailsCell.vue @@ -0,0 +1,65 @@ + + + + + diff --git a/components/JDetailsSwitch/JDetailsSwitch.vue b/components/JDetailsSwitch/JDetailsSwitch.vue new file mode 100644 index 0000000..ee80024 --- /dev/null +++ b/components/JDetailsSwitch/JDetailsSwitch.vue @@ -0,0 +1,36 @@ + + + + + diff --git a/components/JKeyboard/JKeyboard.vue b/components/JKeyboard/JKeyboard.vue new file mode 100644 index 0000000..867f190 --- /dev/null +++ b/components/JKeyboard/JKeyboard.vue @@ -0,0 +1,164 @@ + + + + + diff --git a/components/JPasswordInput/JPasswordInput.vue b/components/JPasswordInput/JPasswordInput.vue new file mode 100644 index 0000000..dc29ee9 --- /dev/null +++ b/components/JPasswordInput/JPasswordInput.vue @@ -0,0 +1,97 @@ + + + + + diff --git a/components/JSearchTitle/JSearchTitle.vue b/components/JSearchTitle/JSearchTitle.vue new file mode 100644 index 0000000..205ae87 --- /dev/null +++ b/components/JSearchTitle/JSearchTitle.vue @@ -0,0 +1,53 @@ + + + + diff --git a/components/JSinglePopup/JSinglePopup.vue b/components/JSinglePopup/JSinglePopup.vue new file mode 100644 index 0000000..63ae48a --- /dev/null +++ b/components/JSinglePopup/JSinglePopup.vue @@ -0,0 +1,116 @@ + + + + + diff --git a/components/JSwitch/JSwitch.vue b/components/JSwitch/JSwitch.vue new file mode 100644 index 0000000..bd48685 --- /dev/null +++ b/components/JSwitch/JSwitch.vue @@ -0,0 +1,45 @@ + + + + + diff --git a/components/JSwitchCard/JSwitchCard.vue b/components/JSwitchCard/JSwitchCard.vue new file mode 100644 index 0000000..ad678ff --- /dev/null +++ b/components/JSwitchCard/JSwitchCard.vue @@ -0,0 +1,55 @@ + + + + diff --git a/components/JTableList/JTableList.vue b/components/JTableList/JTableList.vue new file mode 100644 index 0000000..b97500d --- /dev/null +++ b/components/JTableList/JTableList.vue @@ -0,0 +1,117 @@ + + + + + diff --git a/components/JTipsPopupContent/JTipsPopupContent.vue b/components/JTipsPopupContent/JTipsPopupContent.vue new file mode 100644 index 0000000..c892448 --- /dev/null +++ b/components/JTipsPopupContent/JTipsPopupContent.vue @@ -0,0 +1,58 @@ + + + + + diff --git a/components/JeepayAdCard/JeepayAdCard.vue b/components/JeepayAdCard/JeepayAdCard.vue new file mode 100644 index 0000000..fb264a3 --- /dev/null +++ b/components/JeepayAdCard/JeepayAdCard.vue @@ -0,0 +1,53 @@ + + + + + diff --git a/components/JeepayAdStart/JeepayAdStart.vue b/components/JeepayAdStart/JeepayAdStart.vue new file mode 100644 index 0000000..17c1a5f --- /dev/null +++ b/components/JeepayAdStart/JeepayAdStart.vue @@ -0,0 +1,237 @@ + + + + + diff --git a/components/JeepayBackground/JeepayBackground.vue b/components/JeepayBackground/JeepayBackground.vue new file mode 100644 index 0000000..b822b59 --- /dev/null +++ b/components/JeepayBackground/JeepayBackground.vue @@ -0,0 +1,118 @@ + + + + + diff --git a/components/JeepayBanner/JeepayBanner.vue b/components/JeepayBanner/JeepayBanner.vue new file mode 100644 index 0000000..41041e0 --- /dev/null +++ b/components/JeepayBanner/JeepayBanner.vue @@ -0,0 +1,55 @@ + + + + + diff --git a/components/JeepayBizinfoSelect/JeepayBizinfoSelect.vue b/components/JeepayBizinfoSelect/JeepayBizinfoSelect.vue new file mode 100644 index 0000000..9775183 --- /dev/null +++ b/components/JeepayBizinfoSelect/JeepayBizinfoSelect.vue @@ -0,0 +1,143 @@ + + + + + + diff --git a/components/JeepayBizsPopupView/JeepayBizsPopupView.vue b/components/JeepayBizsPopupView/JeepayBizsPopupView.vue new file mode 100644 index 0000000..d6fa2d4 --- /dev/null +++ b/components/JeepayBizsPopupView/JeepayBizsPopupView.vue @@ -0,0 +1,144 @@ + + + + + + diff --git a/components/JeepayCard/JeepayCard.vue b/components/JeepayCard/JeepayCard.vue new file mode 100644 index 0000000..8774063 --- /dev/null +++ b/components/JeepayCard/JeepayCard.vue @@ -0,0 +1,90 @@ + + + + + + diff --git a/components/JeepayCheckbox/JeepayCheckbox.vue b/components/JeepayCheckbox/JeepayCheckbox.vue new file mode 100644 index 0000000..2c0cb4f --- /dev/null +++ b/components/JeepayCheckbox/JeepayCheckbox.vue @@ -0,0 +1,80 @@ + + + + + \ No newline at end of file diff --git a/components/JeepayCustomNavbar/JeepayCustomNavbar.vue b/components/JeepayCustomNavbar/JeepayCustomNavbar.vue new file mode 100644 index 0000000..e88c4d4 --- /dev/null +++ b/components/JeepayCustomNavbar/JeepayCustomNavbar.vue @@ -0,0 +1,159 @@ + + + + + \ No newline at end of file diff --git a/components/JeepayDescview/JeepayDescview.vue b/components/JeepayDescview/JeepayDescview.vue new file mode 100644 index 0000000..c97c487 --- /dev/null +++ b/components/JeepayDescview/JeepayDescview.vue @@ -0,0 +1,32 @@ + + + + + + diff --git a/components/JeepayDescviewItem/JeepayDescviewItem.vue b/components/JeepayDescviewItem/JeepayDescviewItem.vue new file mode 100644 index 0000000..570db41 --- /dev/null +++ b/components/JeepayDescviewItem/JeepayDescviewItem.vue @@ -0,0 +1,77 @@ + + + + + + diff --git a/components/JeepayForm/JeepayForm.vue b/components/JeepayForm/JeepayForm.vue new file mode 100644 index 0000000..7338763 --- /dev/null +++ b/components/JeepayForm/JeepayForm.vue @@ -0,0 +1,151 @@ + + + + + + \ No newline at end of file diff --git a/components/JeepayFormItem/JeepayFormItem.vue b/components/JeepayFormItem/JeepayFormItem.vue new file mode 100644 index 0000000..7f5a135 --- /dev/null +++ b/components/JeepayFormItem/JeepayFormItem.vue @@ -0,0 +1,71 @@ + + + + + \ No newline at end of file diff --git a/components/JeepayFormItemInput/JeepayFormItemInput.vue b/components/JeepayFormItemInput/JeepayFormItemInput.vue new file mode 100644 index 0000000..ee4d73a --- /dev/null +++ b/components/JeepayFormItemInput/JeepayFormItemInput.vue @@ -0,0 +1,42 @@ + + + + + \ No newline at end of file diff --git a/components/JeepayListview/JeepayListview.vue b/components/JeepayListview/JeepayListview.vue new file mode 100644 index 0000000..13a8604 --- /dev/null +++ b/components/JeepayListview/JeepayListview.vue @@ -0,0 +1,91 @@ + + + + + + diff --git a/components/JeepayLogin/LoginTextUp.vue b/components/JeepayLogin/LoginTextUp.vue new file mode 100644 index 0000000..01f0e3d --- /dev/null +++ b/components/JeepayLogin/LoginTextUp.vue @@ -0,0 +1,131 @@ + + + + + + diff --git a/components/JeepayNavigation/JeepayNavigation.vue b/components/JeepayNavigation/JeepayNavigation.vue new file mode 100644 index 0000000..1b3647a --- /dev/null +++ b/components/JeepayNavigation/JeepayNavigation.vue @@ -0,0 +1,165 @@ + + + + + + diff --git a/components/JeepayPopupConfirm/JeepayPopupConfirm.vue b/components/JeepayPopupConfirm/JeepayPopupConfirm.vue new file mode 100644 index 0000000..0ac692b --- /dev/null +++ b/components/JeepayPopupConfirm/JeepayPopupConfirm.vue @@ -0,0 +1,110 @@ + + + + + + + diff --git a/components/JeepayPopupInput/JeepayPopupInput.vue b/components/JeepayPopupInput/JeepayPopupInput.vue new file mode 100644 index 0000000..86fb7b9 --- /dev/null +++ b/components/JeepayPopupInput/JeepayPopupInput.vue @@ -0,0 +1,91 @@ + + + + + + + diff --git a/components/JeepayPopupListSelect/JeepayIncomingPopupListSelect.vue b/components/JeepayPopupListSelect/JeepayIncomingPopupListSelect.vue new file mode 100644 index 0000000..fac2af4 --- /dev/null +++ b/components/JeepayPopupListSelect/JeepayIncomingPopupListSelect.vue @@ -0,0 +1,361 @@ + + + + + + diff --git a/components/JeepayPopupListSelect/JeepayPopupListSelect.vue b/components/JeepayPopupListSelect/JeepayPopupListSelect.vue new file mode 100644 index 0000000..954f9a7 --- /dev/null +++ b/components/JeepayPopupListSelect/JeepayPopupListSelect.vue @@ -0,0 +1,387 @@ + + + + + + diff --git a/components/JeepayRadioPopupView/JeepayRadioPopupView.vue b/components/JeepayRadioPopupView/JeepayRadioPopupView.vue new file mode 100644 index 0000000..c08cc03 --- /dev/null +++ b/components/JeepayRadioPopupView/JeepayRadioPopupView.vue @@ -0,0 +1,116 @@ + + + + + + diff --git a/components/JeepayRed/JeepayRedBizinfoSelect.vue b/components/JeepayRed/JeepayRedBizinfoSelect.vue new file mode 100644 index 0000000..95ecb47 --- /dev/null +++ b/components/JeepayRed/JeepayRedBizinfoSelect.vue @@ -0,0 +1,134 @@ + + + + + + \ No newline at end of file diff --git a/components/JeepayRed/JeepayRedPopupListSelect.vue b/components/JeepayRed/JeepayRedPopupListSelect.vue new file mode 100644 index 0000000..edcd6dd --- /dev/null +++ b/components/JeepayRed/JeepayRedPopupListSelect.vue @@ -0,0 +1,355 @@ + + + + + + diff --git a/components/JeepaySearchSelect/JeepaySearchSelect.vue b/components/JeepaySearchSelect/JeepaySearchSelect.vue new file mode 100644 index 0000000..8e4e4da --- /dev/null +++ b/components/JeepaySearchSelect/JeepaySearchSelect.vue @@ -0,0 +1,74 @@ + + + + + + + \ No newline at end of file diff --git a/components/JeepayStateSelect/JeepayStateSelect.vue b/components/JeepayStateSelect/JeepayStateSelect.vue new file mode 100644 index 0000000..8f06507 --- /dev/null +++ b/components/JeepayStateSelect/JeepayStateSelect.vue @@ -0,0 +1,79 @@ + + + + + + + \ No newline at end of file diff --git a/components/JeepayStateSwitch/JeepayStateSwitch.vue b/components/JeepayStateSwitch/JeepayStateSwitch.vue new file mode 100644 index 0000000..ef933a6 --- /dev/null +++ b/components/JeepayStateSwitch/JeepayStateSwitch.vue @@ -0,0 +1,119 @@ + + + + + + diff --git a/components/JeepayTableList/JeepayTableList.vue b/components/JeepayTableList/JeepayTableList.vue new file mode 100644 index 0000000..8360ad3 --- /dev/null +++ b/components/JeepayTableList/JeepayTableList.vue @@ -0,0 +1,119 @@ + + + + + + diff --git a/components/JeepayTableListItem/JeepayTableListItem.vue b/components/JeepayTableListItem/JeepayTableListItem.vue new file mode 100644 index 0000000..09cdfd1 --- /dev/null +++ b/components/JeepayTableListItem/JeepayTableListItem.vue @@ -0,0 +1,90 @@ + + + + + + \ No newline at end of file diff --git a/components/JeepayTag/JeepayTag.vue b/components/JeepayTag/JeepayTag.vue new file mode 100644 index 0000000..a21a07b --- /dev/null +++ b/components/JeepayTag/JeepayTag.vue @@ -0,0 +1,56 @@ + + + + + diff --git a/components/JeepayUploadImg/JeepayUploadImg.vue b/components/JeepayUploadImg/JeepayUploadImg.vue new file mode 100644 index 0000000..e905a4b --- /dev/null +++ b/components/JeepayUploadImg/JeepayUploadImg.vue @@ -0,0 +1,167 @@ + + + + + + diff --git a/components/JeepayUploadImg/enlarge.vue b/components/JeepayUploadImg/enlarge.vue new file mode 100644 index 0000000..f463183 --- /dev/null +++ b/components/JeepayUploadImg/enlarge.vue @@ -0,0 +1,143 @@ + + + + + + diff --git a/components/helang-pickerColor/helang-pickerColor.vue b/components/helang-pickerColor/helang-pickerColor.vue new file mode 100644 index 0000000..bc2017b --- /dev/null +++ b/components/helang-pickerColor/helang-pickerColor.vue @@ -0,0 +1,135 @@ + + + + + diff --git a/components/my-components/edit-discount.vue b/components/my-components/edit-discount.vue new file mode 100644 index 0000000..2e2c5ac --- /dev/null +++ b/components/my-components/edit-discount.vue @@ -0,0 +1,212 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-action-sheet.vue b/components/my-components/my-action-sheet.vue new file mode 100644 index 0000000..dd9e208 --- /dev/null +++ b/components/my-components/my-action-sheet.vue @@ -0,0 +1,107 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-button.vue b/components/my-components/my-button.vue new file mode 100644 index 0000000..95364a3 --- /dev/null +++ b/components/my-components/my-button.vue @@ -0,0 +1,158 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-date-pickerview.vue b/components/my-components/my-date-pickerview.vue new file mode 100644 index 0000000..0ea73ad --- /dev/null +++ b/components/my-components/my-date-pickerview.vue @@ -0,0 +1,605 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-empty.vue b/components/my-components/my-empty.vue new file mode 100644 index 0000000..9fbf231 --- /dev/null +++ b/components/my-components/my-empty.vue @@ -0,0 +1,38 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-icons.vue b/components/my-components/my-icons.vue new file mode 100644 index 0000000..1a5872e --- /dev/null +++ b/components/my-components/my-icons.vue @@ -0,0 +1,71 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-img-empty.vue b/components/my-components/my-img-empty.vue new file mode 100644 index 0000000..938aa44 --- /dev/null +++ b/components/my-components/my-img-empty.vue @@ -0,0 +1,32 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-mask.vue b/components/my-components/my-mask.vue new file mode 100644 index 0000000..ec036d4 --- /dev/null +++ b/components/my-components/my-mask.vue @@ -0,0 +1,79 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-model.vue b/components/my-components/my-model.vue new file mode 100644 index 0000000..29e5c24 --- /dev/null +++ b/components/my-components/my-model.vue @@ -0,0 +1,225 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-pagination.vue b/components/my-components/my-pagination.vue new file mode 100644 index 0000000..0dbf76c --- /dev/null +++ b/components/my-components/my-pagination.vue @@ -0,0 +1,150 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-pickerview.vue b/components/my-components/my-pickerview.vue new file mode 100644 index 0000000..8dab2bc --- /dev/null +++ b/components/my-components/my-pickerview.vue @@ -0,0 +1,344 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-popup-table.vue b/components/my-components/my-popup-table.vue new file mode 100644 index 0000000..bcd3b0e --- /dev/null +++ b/components/my-components/my-popup-table.vue @@ -0,0 +1,268 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-radio.vue b/components/my-components/my-radio.vue new file mode 100644 index 0000000..e6a6836 --- /dev/null +++ b/components/my-components/my-radio.vue @@ -0,0 +1,96 @@ + + + + \ No newline at end of file diff --git a/components/my-components/my-reportDamage.vue b/components/my-components/my-reportDamage.vue new file mode 100644 index 0000000..c2cbd4f --- /dev/null +++ b/components/my-components/my-reportDamage.vue @@ -0,0 +1,345 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-search.vue b/components/my-components/my-search.vue new file mode 100644 index 0000000..ee4fe43 --- /dev/null +++ b/components/my-components/my-search.vue @@ -0,0 +1,59 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-step.vue b/components/my-components/my-step.vue new file mode 100644 index 0000000..9474c6b --- /dev/null +++ b/components/my-components/my-step.vue @@ -0,0 +1,95 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-switch.vue b/components/my-components/my-switch.vue new file mode 100644 index 0000000..1184b4d --- /dev/null +++ b/components/my-components/my-switch.vue @@ -0,0 +1,163 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-table-col.vue b/components/my-components/my-table-col.vue new file mode 100644 index 0000000..02409e3 --- /dev/null +++ b/components/my-components/my-table-col.vue @@ -0,0 +1,8 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-table.vue b/components/my-components/my-table.vue new file mode 100644 index 0000000..77cb15b --- /dev/null +++ b/components/my-components/my-table.vue @@ -0,0 +1,76 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-tabs.vue b/components/my-components/my-tabs.vue new file mode 100644 index 0000000..b17befe --- /dev/null +++ b/components/my-components/my-tabs.vue @@ -0,0 +1,144 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-tag.vue b/components/my-components/my-tag.vue new file mode 100644 index 0000000..40b174c --- /dev/null +++ b/components/my-components/my-tag.vue @@ -0,0 +1,9 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-time-area-pickerview.vue b/components/my-components/my-time-area-pickerview.vue new file mode 100644 index 0000000..9686372 --- /dev/null +++ b/components/my-components/my-time-area-pickerview.vue @@ -0,0 +1,49 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-up-upload.vue b/components/my-components/my-up-upload.vue new file mode 100644 index 0000000..bfbba13 --- /dev/null +++ b/components/my-components/my-up-upload.vue @@ -0,0 +1,118 @@ + + + + + \ No newline at end of file diff --git a/components/my-components/my-upload-file.vue b/components/my-components/my-upload-file.vue new file mode 100644 index 0000000..5d187ca --- /dev/null +++ b/components/my-components/my-upload-file.vue @@ -0,0 +1,116 @@ + + + + + \ No newline at end of file diff --git a/components/t-color-picker/t-color-picker.vue b/components/t-color-picker/t-color-picker.vue new file mode 100644 index 0000000..10486a5 --- /dev/null +++ b/components/t-color-picker/t-color-picker.vue @@ -0,0 +1,784 @@ + + + + + diff --git a/components/yhdsl-cropper/yhdsl-cropper.vue b/components/yhdsl-cropper/yhdsl-cropper.vue new file mode 100644 index 0000000..d5bdbc2 --- /dev/null +++ b/components/yhdsl-cropper/yhdsl-cropper.vue @@ -0,0 +1,977 @@ + + + + + \ No newline at end of file diff --git a/config/appConfig.js b/config/appConfig.js new file mode 100644 index 0000000..8e2a36a --- /dev/null +++ b/config/appConfig.js @@ -0,0 +1,27 @@ +const appConfig = { + + // 项目名称 + appName: '银收客', + + // token取值key + tokenKey: 'iToken', + // tokenKey: 'satoken', + + // 环境变量相关 + env: {}, + + // 环境变量常量 + ENV_ENUM: { + DEVELOPMENT: 'development', // 本地调试地址 + TEST: 'test', // 测试地址 + DEMO: 'demo', // 演示环境 + PRODUCTION: 'production' // 生产环境 + }, + + storeEnvEnumKey: 'currentEnvEnum', // 本地存储的envkey的值 + + encryptKey: '1234567890123456' // http数据加解密的key + +} + +export default appConfig; \ No newline at end of file diff --git a/env/config.js b/env/config.js new file mode 100644 index 0000000..55856a5 --- /dev/null +++ b/env/config.js @@ -0,0 +1,45 @@ +/** + * ENV 的封装 + * 由于uniapp 无法设置.env等打包属性,实现线上,线下多版本配置属性的无缝切换。 + * process.env.NODE_ENV 将在打包环境通过编译器进行替换, 线上打包后无法获取到 process对象。 所以将配置属性统一封装到appConfig中。 + * + * 环境地址环境枚举详见: appConfig.js + * + * @author terrfly + * @site https://www.jeequan.com + * @date 2021/12/16 17:57 + */ +import appConfig from '@/config/appConfig.js'; + +// uni-app 暂时不支持动态import(导包app报错), 需要将所有的env全部导入 = = 、 +import development from './env.development.js'; +import test from './env.test.js'; +import demo from './env.demo.js'; +import production from './env.production.js'; + +const allEnvMap = { + development: development, + test: test, + demo: demo, + production: production +} + +// 获取当前环境变量 +const processEnv = process.env.NODE_ENV + +// 改变env环境 +function changeEnv(envMode){ + + appConfig.env = allEnvMap[envMode || processEnv] + + // // 动态导包的方式:设置全局env配置项目 : 当参数不存在, 那么获取node环境 + // import(`./env.${envMode || processEnv}.js`).then(module => { + // appConfig.env = module.default + // }).catch(() => { + // appConfig.env = production //当出现错误, 比如本地没有复制dev文件时, 默认使用生产环境 + // }) +} + +export default { changeEnv: changeEnv } + + diff --git a/env/env.demo.js b/env/env.demo.js new file mode 100644 index 0000000..ebfe46d --- /dev/null +++ b/env/env.demo.js @@ -0,0 +1,6 @@ +export default { + 'JEEPAY_BASE_URL': 'https://b.rscygroup.com', // 请求URL(生产环境) + 'JEEPAY_BASE_URL_H5': 'https://b.rscygroup.com' + // 'JEEPAY_BASE_URL': 'http://192.168.1.8:9218' // 请求URL(测试环境) + // 'JEEPAY_BASE_URL': 'https://b.qilinshuzi.com' //支付网关URL +} \ No newline at end of file diff --git a/env/env.development.js b/env/env.development.js new file mode 100644 index 0000000..ebfe46d --- /dev/null +++ b/env/env.development.js @@ -0,0 +1,6 @@ +export default { + 'JEEPAY_BASE_URL': 'https://b.rscygroup.com', // 请求URL(生产环境) + 'JEEPAY_BASE_URL_H5': 'https://b.rscygroup.com' + // 'JEEPAY_BASE_URL': 'http://192.168.1.8:9218' // 请求URL(测试环境) + // 'JEEPAY_BASE_URL': 'https://b.qilinshuzi.com' //支付网关URL +} \ No newline at end of file diff --git a/env/env.production.js b/env/env.production.js new file mode 100644 index 0000000..ebfe46d --- /dev/null +++ b/env/env.production.js @@ -0,0 +1,6 @@ +export default { + 'JEEPAY_BASE_URL': 'https://b.rscygroup.com', // 请求URL(生产环境) + 'JEEPAY_BASE_URL_H5': 'https://b.rscygroup.com' + // 'JEEPAY_BASE_URL': 'http://192.168.1.8:9218' // 请求URL(测试环境) + // 'JEEPAY_BASE_URL': 'https://b.qilinshuzi.com' //支付网关URL +} \ No newline at end of file diff --git a/env/env.test.js b/env/env.test.js new file mode 100644 index 0000000..5ba49d6 --- /dev/null +++ b/env/env.test.js @@ -0,0 +1,5 @@ +export default { + // 'JEEPAY_BASE_URL': 'https://b.shouyinbei.com' // 请求URL(测试地址) + 'JEEPAY_BASE_URL_H5': 'https://b.rscygroup.com', + 'JEEPAY_BASE_URL': 'https://b.rscygroup.com' //支付网关URL +} \ No newline at end of file diff --git a/ext.json b/ext.json new file mode 100644 index 0000000..7a8f6b6 --- /dev/null +++ b/ext.json @@ -0,0 +1,8 @@ +{ + "extEnable": true, + "extAppid":"wx9b4f8ff05754599f", + "directCommit": false, + "ext": { + "name": "wechat" + } +} \ No newline at end of file diff --git a/http/apiManager.js b/http/apiManager.js new file mode 100644 index 0000000..c5e8c7a --- /dev/null +++ b/http/apiManager.js @@ -0,0 +1,624 @@ +/** + * api接口管理, 全部以$开头 + * @author terrfly + * @site https://www.jeequan.com + * @date 2021/12/17 09:57 + */ + +import http from './http.js' +import appConfig from '@/config/appConfig.js' +import { + Base64 +} from 'js-base64' +import infoBox from '@/commons/utils/infoBox.js' + +export const req = { + list: (uri, params) => { + return http.req(uri, params, 'GET', false) + }, + + add: (uri, data) => { + return http.req(uri, data, 'POST', false) + }, + + getById: (uri, bizId) => { + return http.req(`${uri}/${bizId}`, {}, 'GET', false) + }, + + updateById: (uri, bizId, data) => { + return http.req(`${uri}/${bizId}`, data, 'PUT', false) + }, + + delById: (uri, bizId) => { + return http.req(`${uri}/${bizId}`, {}, 'DELETE', false) + }, +} + +export const reqLoad = { + list: (uri, params) => { + return http.req(uri, params, 'GET') + }, + + add: (uri, data) => { + return http.req(uri, data, 'POST') + }, + + getById: (uri, bizId) => { + return http.req(`${uri}/${bizId}`, {}, 'GET') + }, + + updateById: (uri, bizId, data) => { + return http.req(`${uri}/${bizId}`, data, 'PUT') + }, + + delById: (uri, bizId) => { + return http.req(`${uri}/${bizId}`, {}, 'DELETE') + }, + + // 通用 新增 or 更新 + addOrUpdate: (bizId, url, data, showMessage = true) => { + //包含bizId 请求的是修改接口 + if (bizId) { + return reqLoad.updateById(url, bizId, data).then((res) => { + if (showMessage) { + return infoBox.showSuccessToast('更新成功').then(() => res) + } + return Promise.resolve(res) + }) + } else { + return reqLoad.add(url, data).then((res) => { + if (showMessage) { + return infoBox.showSuccessToast('新增成功').then(() => res) + } + return Promise.resolve(res) + }) + } + } +} + +/** 上传文件 url **/ +export const API_URL_SINGLE_FILE_UPLOAD = '/api/ossFiles/singleFile' + +/** 公告 **/ +export const API_URL_SYS_ARTICLES = '/api/sysArticles' + +/** 支付订单列表 */ +export const API_URL_PAY_ORDER_LIST = '/api/payOrder' + +/** 退款订单列表 */ +export const API_URL_REFUND_LIST = '/api/refundOrder' + +/** 商户应用 */ +export const API_URL_MCH_APP_LIST = '/api/mchApps' + +/** 门店列表 */ +export const API_URL_MCH_STORE_LIST = '/api/mchStore' + +/** 通知接收人列表 */ +export const API_URL_WXMP_USER_LIST = '/api/wxmp' + +/** 进件管理 */ +export const API_URL_MCH_APPLYMENT_LIST = '/api/mchApplyments' + +/** 员工管理 */ +export const API_URL_SYS_USER_LIST = '/api/sysUsers' + +/** 码牌管理 */ +export const API_URL_SYS_CODE_LIST = '/api/mchQrCodes' + +/** 通用设备管理 deviceType 1-喇叭 2-打印机 3-扫码POS 4-智能POS 6-刷脸设备*/ +export const API_URL_SYS_DEVICE_LIST = '/api/store/device' + +/** 辅助终端管理*/ +export const API_URL_SYS_TERMINALS = '/api/mchTerminals' + +/** 用户绑定门店列表 */ +export const API_URL_USER_BIND_STORE_LIST = '/api/mchStore/userStoreRelas' + +/** 商户支付通道列表 */ +export const API_URL_PAY_PASSAGE_LIST = '/api/mch/payPassages' +/** 广告列表 */ +export const API_URI_PAY_AD_LIST = '/api/advert' +/** 如意门店操作 */ +export const API_URI_DEV_RUYI = '/api/alipayShop' + +/** 会员管理 */ +export const API_URL_MEMBERS = '/api/member' + +/** 会员充值记录 */ +export const API_URL_MEMBER_RECHARGE_RECORDS = '/api/member/rechargeRecord' + +/** 会员充值规则管理 */ +export const API_URL_MEMBER_RECHARGE_RULES = '/api/member/rechargeRule' + +/** 会员账户流水 */ +export const API_URL_MEMBER_ACCOUNT_HISTORY = '/api/member/accountHistory' + +//营销红包开始 + +//红包规则 +export const API_URL_MCH_REF_PACKET_RULE_LIST = '/api/redPacketRule' +//新增红包规则 +export const API_URL_MCH_REF_PACKET_RULE_ADD = '/api/redPacketRule' + +//顾客统计 +export const API_URL_MCH_REF_PACKET_RULE_COUNT = '/api/redPacketUser/count' +//顾客列表 +export const API_URL_MCH_REF_PACKET_USER_LIST = '/api/redPacketUser' +//顾客红包 +export const API_URL_MCH_REF_PACKET_INFO_LIST = '/api/redPacketInfo' +//红包查询规则详情 +export const API_URL_MCH_REF_PACKET_RULE_QUERY = '/api/redPacketRule' +//红包修改规则 +export const API_URL_MCH_REF_PACKET_RULE_EDIT = '/api/redPacketRule/edit' +//红包余额变动明细列表 +export const API_URL_MCH_REF_PACKET_CHANGE = '/api/redPacketChange' +//渠道列表 +export const API_URL_MCH_ISV_LIST = '/api/isvInfo/isvInfoList' + + + +/* 密码登录 */ +export function $loginByPwd(username, pwd, safetyCode) { + // 登录类型 + let lt = '' + // #ifdef APP-PLUS + lt = Base64.encode('APP') + // #endif + // #ifdef H5 || MP-WEIXIN + lt = Base64.encode('LITE') + // #endif + + let data = { + ia: Base64.encode(username), + ip: Base64.encode(pwd), + mc: safetyCode ? Base64.encode(safetyCode) : null, + lt: lt, + } + return http.req('/api/anon/auth/validate', data, 'POST') +} + +/* 验证码登录 */ +export function $phoneCodeLogin(phone, code) { + // 登录类型 + let lt = '' + // #ifdef APP-PLUS + lt = Base64.encode('APP') + // #endif + // #ifdef H5 || MP-WEIXIN + lt = Base64.encode('LITE') + // #endif + + let data = { + phone: Base64.encode(phone), + code: Base64.encode(code), + lt: lt, + } + + return http.req('/api/anon/auth/phoneCode', data, 'POST') +} + +// 找回密码 +export function $retrieve({ + phone, + code, + newPwd +}) { + let data = { + phone: Base64.encode(phone), + code: Base64.encode(code), + newPwd: newPwd ? Base64.encode(newPwd) : '' + } + return http.req('/api/anon/cipher/retrieve', data, 'POST') +} + +/* 修改密码 */ +export function $modifyPwd({ + originalPwd, + confirmPwd +}) { + let data = { + originalPwd: Base64.encode(originalPwd), + confirmPwd: Base64.encode(confirmPwd) + } + return http.req("/api/current/modifyPwd", data, "PUT") +} + +/* 注册新商户 */ +export function $mchRegister({ + mchName, + confirmPwd, + inviteCode, + phone, + code +}) { + let data = { + mchName: mchName, // 用户名称 + confirmPwd: Base64.encode(confirmPwd), // 确认密码 + inviteCode, // 邀请码 + phone: Base64.encode(phone), // 手机号 + code: Base64.encode(code), // 短信验证码 + } + return http.req('/api/anon/register/mchRegister', data, 'POST') +} + +/* 发送短信验证码 */ +export function $sendSms(data, smsType) { + return http.req('/api/anon/sms/code', { + phone: data.phone, + vercode: data.vercode, + vercodeToken: data.vercodeToken, + smsType: smsType + }, 'POST') +} + +/* 获取个人信息 */ +export function $userInfo(cid1, cid2) { + return http.req('/api/current/user', { + cid1, + cid2 + }, 'GET') +} + +/* 获取公司信息 */ +export function $getSiteInfos() { + return http.req('/api/anon/siteInfos', {}, 'GET') +} + +// 隐私政策与服务协议 +export function $getTreaty() { + return http.req('/api/anon/treaty', {}, 'GET') +} + +/* 快捷收银 */ +export function $appPay(storeId, amount, sellerRemark, wayCode, authCode) { + let data = { + storeId, + amount, + sellerRemark, + wayCode, + authCode + } + + // 二维码, 返回结果为 图片地址 + if (wayCode == 'QR_CASHIER') { + data.payDataType = 'codeImgUrl' + } + + return http.req('/api/pay/app', data, 'POST') +} + +/* 当前商户信息 */ +export function $getMchInfo() { + return http.req('/api/mainChart', {}, 'GET') +} + +/* 订单打印 */ +export function $payOrderPrint(orderId) { + return http.req('/api/payOrder/print/' + orderId, {}, 'GET') +} + +/* 订单退款 */ +export function $payOrderRefund(orderId, refundAmount, refundReason, refundPassword) { + return http.req( + '/api/payOrder/refunds/' + orderId, { + refundAmount: refundAmount, + refundReason: refundReason, + refundPassword: Base64.encode(refundPassword), + refundModel: 1 + }, + 'POST' + ) +} +// // 首页统计信息 +// export function $indexStatistics (queryDateRange) { +// return http.req('/api/mainChart/payDayCount', { queryDateRange }, 'GET') +// } + +// 首页统计信息 +export function $indexStatistics(queryDateRange) { + return http.req('/api/payOrder/count?queryDateRange', { + queryDateRange + }, 'GET') +} + +// 统计报表 +export function $getStatInfo(data) { + return http.req('/api/statistic/total', data, 'GET', false) +} +// 统计报表设备 门店 支付方式统计 +export function $getStatistic(data) { + return http.req('/api/statistic', data, 'GET') +} + +/* 经纬度转换为areacode */ +export function $location2areacode(location) { + return http.req('/api/mchStore/location2areacode/', { + location: location + }, 'GET') +} + + +/* 获取上传form信息 */ +export function $ossFilesForm(bizType, file) { + let postData = { + bizType: bizType, + sourceFileName: file.name || file.path, // 如果没有name 则使用pach替换 + sourceFileSize: file.size, + } + + return http.req('/api/ossFiles/form', postData, 'POST') +} + +/* 系统设置 */ +// 获取语音播报开关信息 +export function $mchConfig(groupKey) { + return http.req('/api/mchConfig', { + groupKey: groupKey + }, 'GET') +} +// 修改语音播报开关信息 +export function $orderConfig(configData, mchNo) { + console.log('mchNo', mchNo); + return http.req('/api/mchConfig/orderConfig', { + configData: configData, + mchNo: mchNo + }, 'PUT') +} + +/* 修改个人信息 */ +export function $modifyUser({ + realname, + avatarUrl +}) { + return http.req("/api/current/user", { + realname, + avatarUrl + }, "PUT") +} + +/* 获取密码规则 */ +export function $getPasswordRules() { + return http.req("/api/anon/cipher/pwdRulesRegexp", "GET") +} + +// 验证是否有密码 +export function $isSipw() { + return http.req("/api/mchConfig/hasSipwValidate", "GET") +} + +// 验证原支付密码是否正确 +export function $isMchSipw(originalPwd) { + return http.req("/api/mchConfig/mchSipwValidate", { + originalPwd: Base64.encode(originalPwd) + }, "POST") +} + +/* 更新支付密码 */ +export function $updateMchSipw({ + originalPwd, + confirmPwd +}) { + let data = { + originalPwd: Base64.encode(originalPwd), + confirmPwd: Base64.encode(confirmPwd) + } + return http.req("/api/mchConfig/mchSipw", data, "PUT") +} + +/* 版本检测 */ +export function $versionDetection({ + versionNumber +}) { + return http.req("/api/anon/clientVersion/versionInfo", { + versionNumber: versionNumber + }, "GET") +} + +/* 查询用户权限 */ +export function $getUserEntRoles(sysUserId) { + return http.req("/api/sysUsers/userEntRoles/" + sysUserId, {}, "GET") +} + +/* 更新用户权限 */ +export function $updateUserEntRoles(sysUserId, ruleName, state) { + return http.req("/api/sysUsers/userEntRoles/" + sysUserId, { + ruleName, + state + }, "PUT") +} + + +/* 根据支付方式查询可配置的支付接口 */ +export function $getAvailablePayInterface(appId, wayCode) { + return http.req(`/api/mch/payPassages/availablePayInterface/${appId}/${wayCode}`, "GET") +} + +/* 支付方式配置支付接口 */ +export function $wayCodeConfigIfCode(appId, wayCode, ifCode) { + + let reqData = { + appId: appId, + wayCode: wayCode, + ifCode: ifCode, + state: 1 + } + return http.req(`/api/mch/payPassages/mchPassage`, reqData, "POST") +} +/*码牌扫码 二维码解析*/ +export function $parseQrCodeUrl(qrUrl) { + return http.req('/api/mchQrCodes/parseQrCodeUrl', { + qrUrl + }, 'GET') +} +/*码牌绑定*/ +export function $bindEmptyQR(qrcInfo) { + return http.req('/api/mchQrCodes/bindEmptyQR', qrcInfo, 'POST') +} +/*解绑码牌*/ +export function $unBindQrc(qrcId) { + return http.req('/api/mchQrCodes/unbind/' + qrcId, {}, 'POST') +} +/*码牌查询受支持的云喇叭设备*/ +export function $getHornList(qrcId) { + return http.req('/api/mchQrCodes/bindDevice/' + qrcId, 'GET') +} +/* 更新默认 */ +export function $updateTrmDefault(trmId, defaultFlag) { + return http.req('/api/mchTerminals/trmDefaults', { + trmId, + defaultFlag + }, 'PUT') +} + +/* 设备解绑 */ +export function $deviceUnbind(deviceId) { + return http.req('/api/store/device/unbind/' + deviceId, {}, 'POST') +} + + +/* 渠道报备列表 */ +export function $terminalChannelBindList(trmId) { + return http.req('/api/mchTerminals/channelBindInfos/' + trmId, {}, 'GET') +} + +/* 渠道报备 */ +export function $terminalChannelBindSend(trmId, ifCode) { + return http.req('/api/mchTerminals/channelSendup/' + trmId, { + ifCode: ifCode, + state: 1 + }, 'POST') +} + + +// 扫码登录 +export function $scanCodeLogin(qrcodeNo, qrcodeStatus) { + return http.req("/api/current/qrcode/login", { + qrcodeNo, + qrcodeStatus + }, "POST") +} + +// 云喇叭 播报测试 +export function $speakTest(devId, amount) { + return http.req("/api/store/device/speak/" + devId, amount, "POST") +} + +// 云打印 打印测试 +export function $printTest(devId, amount) { + return http.req(`/api/store/device/print/${devId}`, { + amount + }, "POST") +} + +/* 获取百度语音播报token */ +export function $getBaiduToken() { + return http.req("/api/pushinfo/getBaiduToken", {}, "GET") +} +// 获取通知接收人二维码图片 +export function $getWxMpInfo() { + return http.req("/api/wxmp/getWxmpInfo", {}, "GET") +} + +/* 获取进件通道列表 */ +export function $getAllAllowApplymentIfCodeList() { + return http.req("/api/payConfig/ifCodes", { + infoId: 'CURRENT', + configMode: 'mchApplyment' + }, "GET") +} +/* 查询店长可以绑定的门店 */ +export function $getBindStoreList(params) { + return http.req('/api/mchStore/bindStoreList', params, "GET") +} + +/* 提交unipush cid */ +export function $pushInfoRegister(data) { + console.log('push cid', data); + return http.req("/api/pushinfo/register", data, "POST") +} +/* 获取广告接口*/ +export function $adList(params) { + return http.req('/api/advert/appAdvert', params, 'GET') +} +/** 如意Lite 绑定解绑接口 */ +export function $BindLite(data) { + return http.req('/api/alipayIot/bind/' + data.deviceId, data, "POST") +} + +// 获取支付宝扫码授权 +export function $aliPayQrCodeOrApply(account = '', type = 'queryResult') { + return http.req(`/api/alipaySpOperation/${type}`, { + alipayAccount: account + }, type == 'apply' ? 'POST' : 'GET') +} +// 获取支付宝授权信息 +export function $aliAccountInfo() { + return http.req('/api/alipaySpOperation/authInfo', {}, 'GET') +} + +// 查询蚂蚁店铺状态 +export function $queryAliStore(storeId) { + return req.getById('/api/alipayShop/createResult', storeId) +} + + +// 获取上传图片 大小 +export function $getUploadImgSize() { + return http.req('/api/defaultConfig', {}, "GET") +} + +// 会员调账 +export function $memberManual(params) { + return http.req('/api/member/manual/' + params.memberId, params, "POST") +} + +//查询或修改会员配置信息 +export function $findOrEditMemberConfig(data, mode = 'GET', uri = '') { + return http.req('/api/mchConfig' + uri, data, mode) +} +/* 会员数据统计 */ +export function $memberInfoCount(params) { + return http.req('/api/member/count', params, 'GET') +} + +/* 查询商户支付应用 费率参数是否配置 */ +export function $getMchPayPassage(appId, ifCode) { + return http.req(`/api/payConfig/existPayParams/${appId}/${ifCode}`, {}, 'GET') +} + +/* 获取进件渠道列表 */ +export function $getAllIsvInfoList(ifCode, range = 0) { + return http.req("/api/isvInfo/isvInfoList", { + pageNumber: "-1", + range: range, + ifCode: ifCode + }, "GET") +} + + +// 请求验证码 +export function $isCode() { + return http.req("/api/anon/auth/vercode", "GET") +} + +export function $pmdfb(data) { + return http.req("/api/store/device/setMarqueeInfo", data, "POST") +} + +export function $getImgWH(params) { + return http.req(`/api/store/device/getMarketPoint/${params}`, "GET") +} + +export function $initializeImg(params) { + return http.req(`/api/store/device/getMarketPic/${params}`, "GET") +} + +export function $uploadImg(data) { + return http.req(`/api/store/device/setMarketPic`, data, "POST") +} + +/* 获取上传form信息 */ +export function $NewOssFilesForm(data) { + return http.req("/api/ossFiles/form", data, "POST") +} diff --git a/http/businessApiManger.js b/http/businessApiManger.js new file mode 100644 index 0000000..0503c48 --- /dev/null +++ b/http/businessApiManger.js @@ -0,0 +1,47 @@ +import request from './businessHttp.js' +import useStorage from '@/commons/utils/useStroage.js' + +/** + * 登录 + * @param {Object} data + */ +export function login(data) { + return request('/login/wx/merchant/login', data, 'post') +} + +/** + * 桌台列表 + * @param {Object} areaId + */ +export function tableList(areaId) { + return request('/table/list', { + shopId: useStorage.get('userInfo').shopId, + areaId: areaId + }, 'post') +} + +/** + * 区域列表 + * @param {Object} data + */ +export function areaList(data) { + return request('/table/area', { + shopId: useStorage.get('userInfo').shopId + }) +} + +/** + * 绑定桌码 + * @param {Object} data + */ +export function tableBinding(data) { + return request('/table/binding', data, 'post') +} + +/** + * 登录获取openid + * @param {Object} data + */ +export function wxlogin(data) { + return request('/login/wx/business/login', data) +} \ No newline at end of file diff --git a/http/businessHttp.js b/http/businessHttp.js new file mode 100644 index 0000000..2938964 --- /dev/null +++ b/http/businessHttp.js @@ -0,0 +1,52 @@ +/** + * 因为两个小程序接口不一致,餐饮商超商家端的接口使用该http + */ +import useStorage from '@/commons/utils/useStroage.js' +import go from '@/commons/utils/go.js'; +// const baseURL = 'http://192.168.2.128:9000/cashierService' +// const baseURL = 'http://192.168.2.41:9888/cashierService' +let baseURL = 'https://wxcashiertest.sxczgkj.cn/cashierService' +// #ifdef H5 +baseURL = '/ysk' +// #endif +// const baseURL = 'https://cashier.sxczgkj.cn/cashierService' +export default function(api = '', data = {}, method = 'GET') { + return new Promise((resolve, reject) => { + uni.request({ + url: `${baseURL}${api}`, + method: method, + data: data, + header: { + 'environment': 'wx', + 'type': 'ios', + 'version': '1.0.0', + 'token': useStorage.get('iToken'), + 'Authorization': useStorage.get('iToken'), + 'Content-Type': 'application/json' + }, + success: res => { + if (res.data.code == 0) { + resolve(res.data) + } else { + uni.showToast({ + icon: 'none', + "title": res.data.msg + }) + if(res.data.code==-4){ + setTimeout(()=>{ + go.to('PAGES_LOGIN', {}, 'redirect') + },2000) + } + reject(res.data.msg) + } + }, + fail: err => { + uni.showToast({ + icon: 'none', + "title": err.errMsg + }) + reject(err) + } + }) + }) +} \ No newline at end of file diff --git a/http/classApi.js b/http/classApi.js new file mode 100644 index 0000000..6ed1954 --- /dev/null +++ b/http/classApi.js @@ -0,0 +1,22 @@ + class API { + constructor(url,req) { + const map={ + add:'POST', + del:'DELETE', + update:'PUT', + get:'GET' + } + this.url=url + for(let key in map){ + this[key]=function(data){ + data=Array.isArray(data)?data:{...data,shopId:uni.getStorageSync('shopId')} + if(key==='del'){ + delete data.shopId + } + return req(url, data,map[key]) + } + } + } +} + +export default API \ No newline at end of file diff --git a/http/http.js b/http/http.js new file mode 100644 index 0000000..14122b6 --- /dev/null +++ b/http/http.js @@ -0,0 +1,161 @@ +/** + * HTTP的封装, 基于uni.request + * 包括: 通用响应结果的处理 和 业务的增删改查函数 + * + * @author terrfly + * @site https://www.jeequan.com + * @date 2021/12/16 18:35 + */ + +// 导入全局属性 +import appConfig from '@/config/appConfig.js' +import storageManage from '@/commons/utils/storageManage.js' +import { sm4DecryptByResData } from '@/commons/utils/encryptUtil.js' +import infoBox from "@/commons/utils/infoBox.js" +import go from '@/commons/utils/go.js'; +let baseUrl = 'http://101.37.12.135:8080' +// #ifdef H5 +baseUrl = '/server3/mch' +// #endif +// #ifndef H5 +baseUrl = 'http://101.37.12.135:8080/mch' +// #endif + +// 多少 ms 以内, 不提示loading +const loadingShowTime = 200 + +// 通用处理逻辑 +function commonsProcess(showLoading, httpReqCallback){ + + // 判断是否请求完成(用作 是否loading ) + // 包括: 'ing', 'ingLoading', 'finish' + let reqState = 'ing' + + // 是否已经提示的错误信息 + let isShowErrorToast = false + + + // 请求完成, 需要处理的动作 + let reqFinishFunc = () => { + + if(reqState == 'ingLoading'){ // 关闭loading弹层 + infoBox.hideLoading() + } + reqState = 'finish' // 请求完毕 + } + + // 明确显示loading + if(showLoading){ + // xx ms内响应完成,不提示loading + setTimeout(() => { + if(reqState == 'ing'){ + reqState = 'ingLoading' + infoBox.showLoading() + } + }, loadingShowTime) + } + + return httpReqCallback().then((httpData) => { + + reqFinishFunc(); // 请求完毕的动作 + + // 从http响应数据中解构响应数据 [ 响应码、 bodyData ] + let { statusCode, data } = httpData + // 避免混淆重新命名 + let bodyData = data + if(statusCode == 401){ + + // 清楚 token + storageManage.token(null, true) + + // 提示信息 + isShowErrorToast = true + // infoBox.showErrorToast('请登录').then(() => { + // go.to("PAGES_LOGIN", {}, go.GO_TYPE_RELAUNCH) + // }) + return Promise.reject(bodyData) // 跳转到catch函数 + } + // http响应码不正确 + if(statusCode != 200){ + isShowErrorToast = true + infoBox.showToast('服务器异常') + return Promise.reject(bodyData) // 跳转到catch函数 + } + + // 业务响应异常 + if(bodyData.code != 0){ + isShowErrorToast = true + infoBox.showToast(bodyData.msg) + if(bodyData.code == 5005){ // 密码已过期, 直接跳转到更改密码页面 + uni.reLaunch({url: '/pageUser/setting/updatePwd'}) + } + if(bodyData.code == 500){ // 密码已过期, 直接跳转到更改密码页面 + uni.redirectTo({url: '/pages/login/index'}) + } + return Promise.reject(bodyData) + } + + // 加密数据 + if(!bodyData.data && bodyData.encryptData){ + + return Promise.resolve({ bizData: sm4DecryptByResData(bodyData.encryptData), code: bodyData.code }) + } + + // 构造请求成功的响应数据 + return Promise.resolve({ bizData: bodyData.data, code: bodyData.code }) + + }).catch( res => { + reqFinishFunc(); // 请求完毕的动作 + // 如果没有提示错误, 那么此处提示 异常。 + if(!isShowErrorToast){ + infoBox.showToast(`请求网络异常`) + } + return Promise.reject(res) + + }).finally(() => { // finally 是 then结束后再执行, 此处不适用。 需要在请求完成后立马调用: reqFinishFunc() + + }); + +} + + +// 默认 显示loading(控制 xxs 内 不提示loading ) +function req(uri, data, method = "GET", showLoading = true, extParams = {}){ + + // 放置token + let headerObject = {} + headerObject[appConfig.tokenKey] = storageManage.token() + headerObject["satoken"] = storageManage.token() + + return commonsProcess(showLoading, () => { + return uni.request( + Object.assign({url: baseUrl + uri, data: data, method: method, header: headerObject}, extParams ) + ) + } + ) +} + + +// 上传 +function upload(uri, data, file, showLoading = true, extParams = {}){ + + // 放置token + let headerObject = {} + headerObject[appConfig.tokenKey] = storageManage.token() + + return commonsProcess(showLoading, () => { + return uni.uploadFile( + Object.assign({url: baseUrl + uri, formData: data, name: "file", filePath: file.path, header: headerObject}, extParams ) + ).then((httpData) => { + // uni.upload 返回bodyData 的是 string类型。 需要解析。 + httpData.data = JSON.parse(httpData.data) + return Promise.resolve(httpData) + }) + } + ) +} + +export default { + req : req, + upload : upload +} diff --git a/http/newApi/http.js b/http/newApi/http.js new file mode 100644 index 0000000..da81844 --- /dev/null +++ b/http/newApi/http.js @@ -0,0 +1,182 @@ +/** + * HTTP的封装, 基于uni.request + * 包括: 通用响应结果的处理 和 业务的增删改查函数 + * + * @author terrfly + * @site https://www.jeequan.com + * @date 2021/12/16 18:35 + */ + +// 导入全局属性 +import appConfig from '@/config/appConfig.js' +import storageManage from '@/commons/utils/storageManage.js' +import { + sm4DecryptByResData +} from '@/commons/utils/encryptUtil.js' +import infoBox from "@/commons/utils/infoBox.js" +import go from '@/commons/utils/go.js'; +let baseUrl = 'http://101.37.12.135:8080' +// #ifdef H5 +baseUrl = '/server3' +// #endif +// 多少 ms 以内, 不提示loading +const loadingShowTime = 200 + +// 通用处理逻辑 +function commonsProcess(showLoading, httpReqCallback) { + + // 判断是否请求完成(用作 是否loading ) + // 包括: 'ing', 'ingLoading', 'finish' + let reqState = 'ing' + + // 是否已经提示的错误信息 + let isShowErrorToast = false + + + // 请求完成, 需要处理的动作 + let reqFinishFunc = () => { + + if (reqState == 'ingLoading') { // 关闭loading弹层 + infoBox.hideLoading() + } + reqState = 'finish' // 请求完毕 + } + + // 明确显示loading + if (showLoading) { + // xx ms内响应完成,不提示loading + setTimeout(() => { + if (reqState == 'ing') { + reqState = 'ingLoading' + infoBox.showLoading() + } + }, loadingShowTime) + } + + return httpReqCallback().then((httpData) => { + console.log(httpData); + reqFinishFunc(); // 请求完毕的动作 + + // 从http响应数据中解构响应数据 [ 响应码、 bodyData ] + let { + statusCode, + data + } = httpData + + // 避免混淆重新命名 + let bodyData = data + if (statusCode == 401) { + + // 清楚 token + storageManage.token(null, true) + + // 提示信息 + isShowErrorToast = true + infoBox.showErrorToast('请登录').then(() => { + go.to("PAGES_LOGIN", {}, go.GO_TYPE_RELAUNCH) + }) + return Promise.reject(bodyData) // 跳转到catch函数 + } + // http响应码不正确 + if (statusCode != 200) { + isShowErrorToast = true + infoBox.showErrorToast('服务器异常') + return Promise.reject(bodyData) // 跳转到catch函数 + } + + // 业务响应异常 + if (bodyData.code != 200) { + isShowErrorToast = true + infoBox.showToast(bodyData.msg) + if (bodyData.code == 5005) { // 密码已过期, 直接跳转到更改密码页面 + uni.reLaunch({ + url: '/pageUser/setting/updatePwd' + }) + } + if(bodyData.code == 500){ // 密码已过期, 直接跳转到更改密码页面 + uni.redirectTo({url: '/pages/login/index'}) + } + return Promise.reject(bodyData) + } + + // 加密数据 + if (!bodyData.data && bodyData.encryptData) { + + return Promise.resolve({ + bizData: sm4DecryptByResData(bodyData.encryptData), + code: bodyData.code + }) + } + + // 构造请求成功的响应数据 + return Promise.resolve({ + bizData: bodyData.data, + code: bodyData.code + }) + + }).catch(res => { + reqFinishFunc(); // 请求完毕的动作 + + // 如果没有提示错误, 那么此处提示 异常。 + if (!isShowErrorToast) { + infoBox.showErrorToast(`请求网络异常`) + } + + return Promise.reject(res) + + }).finally(() => { // finally 是 then结束后再执行, 此处不适用。 需要在请求完成后立马调用: reqFinishFunc() + + }); + +} + + +// 默认 显示loading(控制 xxs 内 不提示loading ) +function req(uri, data, method = "GET", showLoading = true, extParams = {}) { + let headerObject = {} + // headerObject[appConfig.tokenKey] = storageManage.token() + headerObject["satoken"] = storageManage.token() + headerObject["content-type"] = 'application/json' + + return commonsProcess(showLoading, () => { + return uni.request( + Object.assign({ + url: baseUrl + uri, + data: data, + method: method, + header: headerObject + }, extParams) + ) + }) +} + + +// 上传 +function upload(uri, data, file, showLoading = true, extParams = {}) { + + // 放置token + let headerObject = {} + // headerObject[appConfig.tokenKey] = storageManage.token() + headerObject["satoken"] = storageManage.token() + + return commonsProcess(showLoading, () => { + return uni.uploadFile( + Object.assign({ + url: appConfig.env.JEEPAY_BASE_URL + uri, + formData: data, + name: "file", + filePath: file.path, + header: headerObject + }, extParams) + ).then((httpData) => { + // uni.upload 返回bodyData 的是 string类型。 需要解析。 + httpData.data = JSON.parse(httpData.data) + return Promise.resolve(httpData) + }) + }) +} + +export default { + req: req, + upload: upload +} \ No newline at end of file diff --git a/http/newApi/login.js b/http/newApi/login.js new file mode 100644 index 0000000..5674ba3 --- /dev/null +++ b/http/newApi/login.js @@ -0,0 +1,11 @@ +import http from './http.js' +import appConfig from '@/config/appConfig.js' +import { + Base64 +} from 'js-base64' +import infoBox from '@/commons/utils/infoBox.js' +/* 登录 */ +export function $login(postData) { + // return http.req('/login', params, 'GET') + return http.req('/login', postData, 'POST') +} diff --git a/http/php/api.ts b/http/php/api.ts new file mode 100644 index 0000000..b42ecd9 --- /dev/null +++ b/http/php/api.ts @@ -0,0 +1,33 @@ +import { request } from './request' +// 会员签入 登录 +export const douyincheckIn = (data : object | any) => { + return request('douyin/checkIn', 'POST', data, true) +} +// 登出 +export const userlogout = () => { + return request('user/logout', 'POST', '', true) +} +// 查询绑定状态 +export const searchstorestatus = (data : object) => { + return request('meituan/searchstorestatus', 'POST', data, true) +} +// 团购核销准备 +export const fulfilmentcertificateprepare = (data : object) => { + return request('douyin/fulfilmentcertificateprepare', 'POST', data, true) +} +// 获取uisdk 绑定 链接 +export const getuisdk = (data : object) => { + return request('douyin/getuisdk', 'POST', data, true) +} +// 团购核销 +export const certificateprepares = (data : object) => { + return request('douyin/certificateprepare', 'POST', data, true) +} +// 团购核销记录 +export const orderlist = (data : object) => { + return request('douyin/orderlist', 'POST', data, true) +} +// 团购核销撤销 +export const fulfilmentcertificatecanceles = (data : object) => { + return request('douyin/fulfilmentcertificatecancel', 'POST', data, true) +} diff --git a/http/php/request.ts b/http/php/request.ts new file mode 100644 index 0000000..f0ae0a2 --- /dev/null +++ b/http/php/request.ts @@ -0,0 +1,80 @@ +//服务器接口地址 +const baseURL : string = 'https://czgdoumei.sxczgkj.com/index.php/api/' +// 封装公共请求方法 +function request(url : string, method : "GET" | "POST" | undefined, data : object | any, toast : boolean) { + let networkType = '' + uni.getNetworkType({ + success: (res) => { + networkType = res.networkType + } + }); + if (networkType == 'none') { + uni.showToast({ + title: '网络异常,请检查网络', + icon: 'none' + }) + return false; + } + if (toast) { + uni.showLoading({ + title: '加载中', + mask: true + }) + } + return new Promise(async (resolve, reject) => { + let header : any + header = { + 'content-type': 'application/json', + 'clinttype':uni.getStorageSync('clint_type'), + 'bausertoken': uni.getStorageSync('phpuserinfo').token + }; + uni.request({ + url: baseURL + url, + method: method, + data: data, + header: header, + success(res : any) { + if (res.data.code != 1) { + //是否提示错误 + if (toast) { + uni.showToast({ + title: res.data.msg || res.data.message, + icon: 'none' + }) + setTimeout(() => { + uni.hideLoading() + }, 1000) + } + if (res.data.code == 401) { + uni.showToast({ + title: res.message || res.msg, + icon: "none", + success: () => { + // uni.removeStorageSync('logintoken'); + // uni.removeStorageSync('token'); + uni.reLaunch({ + url: '/pages/index/index' + }) + } + }) + } + uni.hideLoading() + reject(res.message | res.msg); + } else { + uni.hideLoading() + resolve(res.data.data); + } + }, + fail(err) { + uni.hideLoading() + //请求失败 + uni.showToast({ + title: '无法连接到服务器', + icon: 'none' + }) + reject(err) + } + }) + }) +} +export { request, baseURL } \ No newline at end of file diff --git a/http/yskApi/Instead.js b/http/yskApi/Instead.js new file mode 100644 index 0000000..9839f3b --- /dev/null +++ b/http/yskApi/Instead.js @@ -0,0 +1,415 @@ +// 代课下单 +import http from './http.js' +import $API from '@/http/classApi.js' +import appConfig from '@/config/appConfig.js' +import { + Base64 +} from 'js-base64' +import infoBox from '@/commons/utils/infoBox.js' + +const request = http.request + + +//就餐形式,默认堂食后付费 +const useType = 'dine-in-after' + +function getUseType() { + const type = uni.getStorageSync("useType") + return type ? type : useType +} + + +/** + * 获取当前台桌订单信息 + * @returns + */ +export function getCart(params) { + return request({ + url: `/api/place/cart`, + method: "get", + params:{ + shopId: uni.getStorageSync("shopId"), + useType: getUseType(), + ...params + } + }); +} +/** + * 已上架商品列表 + * @returns + */ +export function getGoodsLists(params,showLoading=true) { + return request({ + url: `/api/place/activate`, + method: "get", + params:{ + shopId: uni.getStorageSync("shopId"), + ...params + }, + showLoading + }); +} + +/** + * 点单 + * @returns + */ +export function addCart(data) { + return request({ + url: `/api/place/addCart`, + method: "post", + data:{ + shopId: uni.getStorageSync("shopId"), + useType: getUseType(), + ...data + } + }); +} + +/** + * 清空购物车/支付订单 + * @returns + */ +export function $clearCart(data) { + return request({ + url: `/api/place/clearCart`, + method: "delete", + data:{ + shopId: uni.getStorageSync("shopId"), + useType: getUseType(), + ...data + } + }); +} + +/** + * 删除购物车某个商品 + * @returns + */ +export function $removeCart(data) { + return request({ + url: `/api/place/removeCart`, + method: "delete", + data:{ + shopId: uni.getStorageSync("shopId"), + useType: getUseType(), + ...data + } + }); +} +/** + * 更新规格 + * @returns + */ +export function $updateCart(data) { + return request({ + url: `/api/place/updateCart`, + method: "put", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} +/** + * 批量打包 + * @returns + */ +export function $allPack(data) { + return request({ + url: `/api/place/pack`, + method: "put", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} +/** + * 获取取餐号 + * @returns + */ +export function $getMasterId(data) { + return request({ + url: `/api/place/masterId`, + method: "get", + params:{ + shopId: uni.getStorageSync("shopId"), + useType: getUseType(), + ...data + } + }); +} +/** + * 支付方式获取 + * @returns + */ +export function $getPayType(data) { + return request({ + url: `/api/place/payType`, + method: "get", + params:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} +/** + * 创建订单 + * @returns + */ +export function $createOrder(data) { + return request({ + url: `/api/place/order`, + method: "post", + data:{ + shopId: uni.getStorageSync("shopId"), + useType: getUseType(), + ...data + } + }); +} + + +/** + * 挂起订单 + * @returns + */ +export function $cacheOrder(data) { + return request({ + url: `/api/place/pending`, + method: "post", + data:{ + shopId: uni.getStorageSync("shopId"), + useType: getUseType(), + ...data + } + }); +} + +/** + * 获取已挂起订单 + * @returns + */ +export function $getCacheOrder(data) { + return request({ + url: `/api/place/pending/cart`, + method: "get", + params:{ + shopId: uni.getStorageSync("shopId"), + useType: getUseType(), + ...data + } + }); +} + +// 会员点单/取消会员点单 +export function $setUser(data) { + return request({ + url: `/api/place/updateVip`, + method: "put", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} +// 删除订单 +export function $delOrder(data) { + return request({ + url: `/api/place/order`, + method: "delete", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} +// 支付订单 +export function $payOrder(data) { + return request({ + url: '/api/place/pay', + method: "put", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} +//退单 + +export function $returnCart(data) { + return request({ + url: '/api/place/returnCart', + method: "put", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} +// 选择台桌 +export function $choseTable(data) { + return request({ + url: '/api/place/choseTable', + method: "put", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} +// 用餐人数 + +export function $choseCount(data) { + return request({ + url: '/api/place/choseCount', + method: "put", + data:{ + shopId: uni.getStorageSync("shopId"), + useType: getUseType(), + ...data + } + }); +} + +// 批量生成台桌 +export function $fastCreateTable(data) { + return request({ + url: '/api/tbShopTable/generate', + method: "post", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} + +//打印当前台桌订单 +export function $printOrder(data) { + return request({ + url: '/api/place/printOrder', + method: "post", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} +//打印当前台桌菜品 + +export function $printDishes(data) { + return request({ + url: '/api/place/printDishes', + method: "post", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} + +// 就餐模式切换 +export function $changeUseType(data) { + return request({ + url: '/api/place/choseModel', + method: "put", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} + +// 退款 +export function $returnOrder(data) { + return request({ + url: '/api/place/returnOrder', + method: "post", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} + +//获取订单可用优惠券 +export function $activateByOrderId(data) { + return request({ + url: '/api/tbShopCoupon/activateByOrderId', + method: "get", + params:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} + +//会员积分列表 +export function $returnMemberPointsList(data) { + return request({ + url: '/api/points/member-points/page', + method: "get", + params:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} + +// 会员积分账户信息 +export function $returnMemberPoints(memberId) { + return request({ + url: '/api/points/member-points/'+memberId, + method: "get", + params:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} +//002-获取订单可用积分及抵扣金额(支付页面使用) +export function $calcUsablePoints(data) { + return request({ + url: '/api/points/member-points/calc-usable-points', + method: "get", + params:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} +// 003-根据积分计算可抵扣金额 +export function $calcDeDuctionPoints(data) { + return request({ + url: '/api/points/member-points/calc-deduction-amount', + method: "get", + params:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} + +//购物车-临时菜添加 +export function $temporaryDishes(data) { + return request({ + url: '/api/place/temporaryDishes', + method: "post", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} +//单品改价 +export function $updatePrice(data) { + return request({ + url: '/api/place/updatePrice', + method: "put", + data:{ + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} diff --git a/http/yskApi/breakage.js b/http/yskApi/breakage.js new file mode 100644 index 0000000..a3c6f2e --- /dev/null +++ b/http/yskApi/breakage.js @@ -0,0 +1,33 @@ +import http from './http.js' +const request=http.request + + +/** + * 商品报损 + * @returns + */ +export function productBreakage(data) { + return request({ + url: `/api/tbProductStockDetail/frmLoss`, + method: 'post', + data:{ + shopId: uni.getStorageSync('shopId'), + ...data + } + }) +} + +/** + * 耗材报损 + * @returns + */ +export function consumableBreakage(data) { + return request({ + url: `/api/tbConsInfoFlow/frmLoss`, + method: 'post', + data:{ + shopId: uni.getStorageSync('shopId'), + ...data + } + }) +} diff --git a/http/yskApi/bwc.js b/http/yskApi/bwc.js new file mode 100644 index 0000000..6899f16 --- /dev/null +++ b/http/yskApi/bwc.js @@ -0,0 +1,33 @@ +import http from './http.js' +const request = http.request + + +/** + * 商品报损 + * @returns + */ +export function get(params) { + return request({ + url: `/freeDine`, + method: 'get', + params: { + shopId: uni.getStorageSync('shopId'), + ...params + } + }) +} + +/** + * 耗材报损 + * @returns + */ +export function edit(data) { + return request({ + url: `/freeDine`, + method: 'put', + params: { + shopId: uni.getStorageSync('shopId'), + ...data + } + }) +} \ No newline at end of file diff --git a/http/yskApi/consumable.js b/http/yskApi/consumable.js new file mode 100644 index 0000000..ac31a33 --- /dev/null +++ b/http/yskApi/consumable.js @@ -0,0 +1,232 @@ +import http from './http.js' +const request = http.request + + +/** + * 查询耗材类型 + * @returns + */ +export function gettbConsType(params) { + return request({ + url: '/api/tbConsType', + method: "get", + params + }); +} + +/** + * 新增耗材类型 + * @returns + */ +export function posttbConsType(data) { + return request({ + url: '/api/tbConsType', + method: "post", + data + }); +} +/** + * 修改耗材类型 + * @returns + */ +export function puttbConsType(data) { + return request({ + url: '/api/tbConsType', + method: "put", + data + }); +} +/** + * 查询耗材信息 + * @returns + */ +export function gettbConsInfo(params) { + // return request({ + // url: '/api/tbConsInfo', + // method: "get", + // params + // }); + return request({ + url: "/api/tbConsInfo", + method: "get", + params: { + ...params, + shopId: uni.getStorageSync("shopId"), + } + }); +} + + +/** + * 耗材入库 + * @returns + */ +export function posttbConsInfostockIn(data) { + return request({ + url: '/api/tbConsInfo/stockIn', + method: "post", + data + }); +} +/** + * 修改单位耗材值耗材 + * @returns + */ +export function postapitbConsInfo(data) { + return request({ + url: '/api/tbConsInfo', + method: "put", + data + }); +} +/** + * 新增耗材信息 + * @returns + */ +export function posttbConsInfo(data) { + return request({ + url: '/api/tbConsInfo', + method: "post", + data + }); +} + +/** + * 查询查询耗材规格信息 + * @returns + */ +export function getviewConSku(params) { + return request({ + url: '/api/viewConSku', + method: "get", + params + }); +} +/** + * 查询查询商品规格 + * @returns + */ +export function gettbProductSpec(params) { + return request({ + url: '/api/viewProductSkuShop', + method: "get", + params + }); +} +/** + * 新增商品规格耗材信息 + * @returns + */ +export function posttbProskuCon(data) { + return request({ + url: '/api/tbProskuCon', + method: "post", + data + }); +} +/** + * 新增商品规格耗材信息-修改后 + * @returns + */ +export function posttbProskuCons(data) { + return request({ + url: '/api/tbProskuCon', + method: "post", + data + }); +} +/** + * 修改商品规格耗材信息状态 + * @returns + */ +export function puttbProskuCon(data) { + return request({ + url: '/api/tbProskuCon', + method: "put", + data + }); +} +// 编辑单位耗材值 +// export function puttbProskuCon(data) { +// return request({ +// url: '/api/tbProskuCon', +// method: "put", +// data +// }); +// } +/** + * 删除商品规格耗材信息状态 + * @returns + */ +export function deletetbProskuCon(data) { + return request({ + url: '/api/tbProskuCon', + method: "delete", + data + }); +} +/** + * 查询耗材流水信息 + * @returns + */ +export function gettbConsInfoFlow(params) { + return request({ + url: '/api/tbConsInfoFlow', + method: "get", + params + }); +} +/** + * 分组查询获取耗材流水信息 + */ +// export function viewConInfoFlow(data) { +// return request({ +// url: "/api/viewConInfoFlow", +// method: "get", +// params: { +// shopId: uni.getStorageSync("shopId"), +// ...data +// } +// }); +// } + +/** + * 查询耗材单位列表 + */ +export function queryTbConUnitInfo(data) { + return request({ + url: "/api/tbConUnit/queryTbConUnitInfo", + method: "get", + params: { + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} + +/** + * 新增耗材单位 + */ +export function addtbConUnit(data) { + return request({ + url: '/api/tbConUnit', + method: "post", + data: { + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} +/** + * 修改耗材单位 + */ +export function edittbConUnit(data) { + return request({ + url: '/api/tbConUnit', + method: "put", + data: { + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} \ No newline at end of file diff --git a/http/yskApi/coupon.js b/http/yskApi/coupon.js new file mode 100644 index 0000000..ae4d4fc --- /dev/null +++ b/http/yskApi/coupon.js @@ -0,0 +1,58 @@ +import http from './http.js' +const request=http.request + + +/** + * 获取优惠券列表 + * @returns + */ +export function getTbShopCoupon(data) { + return request({ + url: `/api/tbShopCoupon`, + method: 'get', + params: { + shopId: uni.getStorageSync('shopId'), + ...data + } + }) +} + +/** + * 获取优惠券详情 + * @returns + */ +export function getTbShopCouponInfo(id) { + return request({ + url: `/api/tbShopCoupon/${id}`, + method: 'get', + params: { + } + }) +} + +/** + * 增加优惠券 + * @returns + */ +export function addTbShopCoupon(data) { + return request({ + url: `/api/tbShopCoupon`, + method: 'post', + params: { + shopId: uni.getStorageSync('shopId'), + ...data + } + }) +} + +/** + * 删除优惠券 + * @returns + */ +export function delTbShopCoupon(data) { + return request({ + url: `/api/tbShopCoupon`, + method: 'delete', + params: data + }) +} diff --git a/http/yskApi/couponCategory.js b/http/yskApi/couponCategory.js new file mode 100644 index 0000000..8f6c451 --- /dev/null +++ b/http/yskApi/couponCategory.js @@ -0,0 +1,30 @@ +import http from './http.js' +import appConfig from '@/config/appConfig.js' +import { + Base64 +} from 'js-base64' +import infoBox from '@/commons/utils/infoBox.js' + +/* 查询团购卷分类 */ +export function $tbCouponCategory(data, mehtod = 'GET') { + return http.req('/api/tbCouponCategory', { + ...data, + shopId: uni.getStorageSync('shopId') + }, 'GET') +} + + +export default { + add: function(data) { + return $tbCouponCategory(data, 'POST') + }, + del: function(data) { + return $tbCouponCategory(data, 'DELETE') + }, + update: function(data) { + return $tbCouponCategory(data, 'PUT') + }, + get: function(data) { + return $tbCouponCategory(data) + } +} \ No newline at end of file diff --git a/http/yskApi/credit.js b/http/yskApi/credit.js new file mode 100644 index 0000000..17c79d3 --- /dev/null +++ b/http/yskApi/credit.js @@ -0,0 +1,113 @@ +import http from './http.js' +const request=http.request + + +/** + * 获取挂账人列表 + * @returns + */ +export function getCreditBuyerList(data) { + return request({ + url: `/api/credit/buyer/page`, + method: 'get', + data + }) +} + +/** + * 增加挂账人 + * @returns + */ +export function addCreditBuyer(data) { + return request({ + url: '/api/credit/buyer', + method: 'post', + params: { + shopId: uni.getStorageSync('shopId'), + ...data + } + }) +} + +/** + * 编辑挂账人 + * @returns + */ +export function editCreditBuyer(data) { + return request({ + url: '/api/credit/buyer', + method: 'put', + data + }) +} + +/** + * 删除挂账人 + * @returns + */ +export function delCreditBuyer(id) { + return request({ + url: `/api/credit/buyer/${id}`, + method: 'delete' + }) +} + +/** + * 还款 + * @returns + */ +export function creditRePayment(data) { + return request({ + url: '/api/credit/buyer/repayment', + method: 'post', + data + }) +} + +/** + * 获取还款记录 + * @returns + */ +export function creditRePaymentRecord(params) { + return request({ + url: '/api/credit/payment-record/page', + method: 'get', + params + }) +} + +/** + * 挂账人-查看明细 + * @returns + */ +export function creditBuyerOrderList(params) { + return request({ + url: '/api/credit/buyer-order/page', + method: 'get', + params + }) +} + +/** + * 挂账人-查看明细-统计 + * @returns + */ +export function creditBuyerOrderSummary(params) { + return request({ + url: '/api/credit/buyer-order/summary', + method: 'get', + params + }) +} + +/** + * 挂账人-查看明细-付款 + * @returns + */ +export function creditPayment(data) { + return request({ + url: '/api/credit/buyer-order/pay', + method: 'post', + data + }) +} diff --git a/http/yskApi/devices.js b/http/yskApi/devices.js new file mode 100644 index 0000000..82b1c57 --- /dev/null +++ b/http/yskApi/devices.js @@ -0,0 +1,66 @@ +import http from './http.js' +const request = http.request + +/** + * 增加打印机 + * @returns + */ +export function tbPrintMachine(data, method = 'post') { + return request({ + url: '/api/shop-config/printer', + method: method, + data: { + shopId: uni.getStorageSync('shopId'), + ...data + } + }) +} + +/** + * 打印机列表 + * @returns + */ +export function tbPrintMachineGet(params) { + return request({ + url: '/api/shop-config/printer/list', + method: 'get', + params: { + shopId: uni.getStorageSync('shopId'), + sort: '', + ...params + } + }) +} + +// 打印机部分 +export function tbShopCategoryget(params) { + return request({ + url: '/api/tbShopCategory', + method: 'get', + params + }) +} +// 修改打印机状态 +export function shopConfigprinter(data) { + return request({ + url: '/api/shop-config/printer/update-status', + method: 'post', + data + }) +} + +// * 打印机详情 +export function printerd(id) { + return request({ + url: '/api/shop-config/printer/' + id, + method: 'get', + + }) +} +// 删除 +export function delTableHandle(id) { + return request({ + url: '/api/shop-config/printer/' + id, + method: 'DELETE', + }) +} \ No newline at end of file diff --git a/http/yskApi/file.js b/http/yskApi/file.js new file mode 100644 index 0000000..8065fcc --- /dev/null +++ b/http/yskApi/file.js @@ -0,0 +1,11 @@ +import http from './http.js' +import appConfig from '@/config/appConfig.js' +import { + Base64 +} from 'js-base64' +import infoBox from '@/commons/utils/infoBox.js' + +/* 上传图片 */ +export function $uploadFile(file,data) { + return http.upload('/api/qiNiuContent', data,file) +} diff --git a/http/yskApi/goods.js b/http/yskApi/goods.js new file mode 100644 index 0000000..9c369bf --- /dev/null +++ b/http/yskApi/goods.js @@ -0,0 +1,143 @@ +import http from './http.js' +import $API from '@/http/classApi.js' +import appConfig from '@/config/appConfig.js' +import { + Base64 +} from 'js-base64' +import infoBox from '@/commons/utils/infoBox.js' +function objectToUrlParams(obj) { + let params = []; + for (let key in obj) { + if (obj.hasOwnProperty(key)) { + let value = obj[key]; + let param = encodeURIComponent(key) + '=' + encodeURIComponent(value); + params.push(param); + } + } + return params.join('&'); +} +/* 商品列表 */ +export function $tbProduct(data) { + return http.req('/api/tbProduct', {...data,shopId:uni.getStorageSync('shopId')}, 'GET') +} + +/* 添加商品 */ +export function $addProduct(data) { + return http.req('/api/tbProduct', {...data,shopId:uni.getStorageSync('shopId')}, 'POST') +} + +/* 删除商品 */ +export function $delProduct(ids) { + return http.req('/api/tbProduct', ids, 'DELETE') +} + + +/* 更新商品相关 */ +export function $updateProduct(data) { + return http.req('/api/tbProduct', {...data,shopId:uni.getStorageSync('shopId')}, 'PUT') +} +/* 修改商品排序 */ +export function $upProSort(data) { + return http.req('/api/tbProduct/upProSort', {...data,shopId:uni.getStorageSync('shopId')}, 'POST') +} +/* 商品详情(单个商品) */ +export function $getProductDetail(product,showLoading=true) { + return http.req('/api/tbProduct/'+product, {shopId:uni.getStorageSync('shopId')}, 'GET',showLoading) +} + +/* 设置热销商品 */ +export function $goodsIsHot(data) { + return http.req('/api/tbProduct/isHot', {...data,shopId:uni.getStorageSync('shopId')}, 'GET') +} + + + +/** + * 商品分类列表 + */ +export function $tbShopCategory(data) { + return http.req('/api/tbShopCategory', {...data,shopId:uni.getStorageSync('shopId')}, 'GET') +} +/** + * 商品分类 + */ +export const $productCategory=new $API('/api/tbShopCategory',http.req) + + +/** + * 更新商品库存状态 + */ +export function $updateProductStatus(data){ + return http.req('/api/stock/productStatus', {...data,shopId:uni.getStorageSync('shopId')}, 'PUT') +} + +/** + * 库存记录列表 + */ +export function $getProductStockDetail(data){ + return http.req('/api/tbProductStockDetail/stock', {...data,shopId:uni.getStorageSync('shopId')}, 'POST') +} + +/** + * 库存记录变动数量 + */ +export function $getProductStockDetailSum(data){ + return http.req('/api/tbProductStockDetail/sum', {...data,shopId:uni.getStorageSync('shopId')}, 'GET') +} +/** + * 新增盘点 + */ +export function $addStocktakin(data){ + return http.req('/api/tbProductStocktakin', {...data,shopId:uni.getStorageSync('shopId')}, 'POST') +} +/** + * 盘点记录查询 + */ +export function $getStocktakin(data){ + return http.req('/api/tbProductStocktakin', {...data,shopId:uni.getStorageSync('shopId')}, 'GET') +} + + +/** + * 上下架商品 + */ +export function $updateGrounding(data){ + const ajaxData={...data,shopId:uni.getStorageSync('shopId')} + return http.req('/api/stock/grounding'+`?${objectToUrlParams(ajaxData)}`, ajaxData, 'PUT') +} + + + +/* 商品单位列表 */ +export function $tbShopUnit(data) { + return http.req('/api/tbShopUnit', {...data,shopId:uni.getStorageSync('shopId')}, 'GET') +} + +/* 商品规格 */ +export const $productSpec=new $API('/api/tbProductSpec',http.req) + + + +// v2 api start +// 商品列表 后台查询 +export function $tbProductList(data) { + return http.req('/api/tbProduct/list', {...data,shopId:uni.getStorageSync('shopId')}, 'GET') +} +/* 商品列表 V2 */ +export function $tbProductV2(data) { + return http.req('/api/tbProduct/list/v2', {...data,shopId:uni.getStorageSync('shopId')}, 'post') +} +/* 耗材与商品绑定关系 */ +export function $tbProskuConV2(data) { + return http.req('/api/tbProskuCon/V2', data, 'POST') +} + +/* 修改商品相关(快捷接口) */ +export function $updateProductData(data) { + return http.req('/api/stock/updateProductData', data, 'POST') +} +/* 商品报损 */ +export function $frmLoss(data) { + return http.req('/api/tbProductStockDetail/frmLoss', {...data,shopId:uni.getStorageSync('shopId')}, 'POST') +} +// v2 api end \ No newline at end of file diff --git a/http/yskApi/http.js b/http/yskApi/http.js new file mode 100644 index 0000000..bf3c162 --- /dev/null +++ b/http/yskApi/http.js @@ -0,0 +1,242 @@ +/** + * HTTP的封装, 基于uni.request + * 包括: 通用响应结果的处理 和 业务的增删改查函数 + * + * @author terrfly + * @site https://www.jeequan.com + * @date 2021/12/16 18:35 + */ + +// 导入全局属性 +import appConfig from '@/config/appConfig.js' +import storageManage from '@/commons/utils/storageManage.js' +import { + sm4DecryptByResData +} from '@/commons/utils/encryptUtil.js' +import infoBox from "@/commons/utils/infoBox.js" +import go from '@/commons/utils/go.js'; +import { reject } from 'lodash'; +// 测试服 +let baseUrl = 'https://admintestpapi.sxczgkj.cn' + +//预发布 +// let baseUrl = 'https://pre-cashieradmin.sxczgkj.cn' + +//正式 +// let baseUrl = 'https://cashieradmin.sxczgkj.cn' + +// 王伟本地测 +// let baseUrl = '/ww' +// let baseUrl = 'http://192.168.1.15:8000' + // 巩 + // let baseUrl = 'http://192.168.1.9:8000' +// 多少 ms 以内, 不提示loading +const loadingShowTime = 200 + + +function getHeader(){ + const headerObject={} + headerObject["Authorization"] = storageManage.token() + return headerObject +} + +// 通用处理逻辑 +function commonsProcess(showLoading, httpReqCallback) { + + // 判断是否请求完成(用作 是否loading ) + // 包括: 'ing', 'ingLoading', 'finish' + let reqState = 'ing' + + // 是否已经提示的错误信息 + let isShowErrorToast = false + + + // 请求完成, 需要处理的动作 + let reqFinishFunc = () => { + + if (reqState == 'ingLoading') { // 关闭loading弹层 + infoBox.hideLoading() + } + reqState = 'finish' // 请求完毕 + } + + // 明确显示loading + if (showLoading) { + // xx ms内响应完成,不提示loading + setTimeout(() => { + if (reqState == 'ing') { + reqState = 'ingLoading' + infoBox.showLoading() + } + }, loadingShowTime) + } + + return httpReqCallback().then((httpData) => { + reqFinishFunc(); // 请求完毕的动作 + // 从http响应数据中解构响应数据 [ 响应码、 bodyData ] + let { + statusCode, + data + } = httpData + // 避免混淆重新命名 + let bodyData = data + if (statusCode == 500) { + isShowErrorToast = true + return Promise.reject(bodyData) // 跳转到catch函数 + } + if (statusCode == 401) { + // storageManage.token(null, true) + // 提示信息 + isShowErrorToast = true + // infoBox.showErrorToast('请登录').then(() => { + // go.to("PAGES_LOGIN", {}, go.GO_TYPE_RELAUNCH) + // }) + return Promise.reject(bodyData) // 跳转到catch函数 + } + // http响应码不正确 + if (statusCode != 200 && statusCode != 204 && statusCode != 201) { + isShowErrorToast = true + data.message=data.message=='Bad credentials'?'用户名或密码错误':data.message + infoBox.showToast(data.message || '服务器异常') + return Promise.reject(bodyData) // 跳转到catch函数 + } + + // // 业务响应异常 + // if (bodyData.hasOwnProperty('code') && bodyData.code != 200) { + // isShowErrorToast = true + // infoBox.showToast(bodyData.msg) + // if (bodyData.code == 5005) { // 密码已过期, 直接跳转到更改密码页面 + // uni.reLaunch({ + // url: '/pageUser/setting/updatePwd' + // }) + // } + // // if(bodyData.code == 500){ // 密码已过期, 直接跳转到更改密码页面 + // // uni.redirectTo({url: '/pages/login/index'}) + // // } + // return bodyData + // // return Promise.reject(bodyData) + // } + + // 加密数据 + if (!bodyData.data && bodyData.encryptData) { + + return Promise.resolve({ + bizData: sm4DecryptByResData(bodyData.encryptData), + code: bodyData.code + }) + } + + // 构造请求成功的响应数据 + return Promise.resolve(bodyData) + + }).catch(res => { + if(res.status==401){ + storageManage.token(null, true) + infoBox.showErrorToast(res.message||'请登录').then(() => { + uni.redirectTo({url: '/pages/login/index'}) + reject() + }) + } + // if(res.status==400){ + // storageManage.token(null, true) + // infoBox.showErrorToast('').then(() => { + // go.to("PAGES_LOGIN", {}, go.GO_TYPE_RELAUNCH) + // }) + // } + if(res.status==500){ + infoBox.showErrorToast(res.message||'服务器异常').then(() => { + }) + } + // if(res&&res.msg){ + // infoBox.showErrorToast(res.msg) + // } + reqFinishFunc(); // 请求完毕的动作 + + // 如果没有提示错误, 那么此处提示 异常。 + if (!isShowErrorToast) { + infoBox.showErrorToast(`请求网络异常`) + } + + return Promise.reject(res) + + }).finally(() => { // finally 是 then结束后再执行, 此处不适用。 需要在请求完成后立马调用: reqFinishFunc() + + }); + +} + + +// 默认 显示loading(控制 xxs 内 不提示loading ) +function req(uri, data, method = "GET", showLoading = true, extParams = {}) { + // headerObject[appConfig.tokenKey] = storageManage.token() + return commonsProcess(showLoading, () => { + return uni.request( + Object.assign({ + url: baseUrl + uri, + data: data, + method: method, + header: getHeader() + }, extParams) + ) + }) +} + + +// 默认 显示loading(控制 xxs 内 不提示loading ) +function request(args) { + const { + url, + data, + params, + method = "GET", + showLoading = true, + extParams = {} + } = args + let headerObject = {} + // headerObject[appConfig.tokenKey] = storageManage.token() + return commonsProcess(showLoading, () => { + return uni.request( + Object.assign({ + url: baseUrl + url, + data: params||data, + method: method, + header: getHeader() + }, extParams) + + ) + }) +} + + + +// 上传 +function upload(uri, data, file, showLoading = true, extParams = {}) { + // 放置token + let headerObject = {} + // headerObject[appConfig.tokenKey] = storageManage.token() + + return commonsProcess(showLoading, () => { + return uni.uploadFile( + Object.assign({ + url: baseUrl + uri, + formData: data, + name: "file", + filePath: file.path||file.url, + header: getHeader() + }, extParams) + ).then((httpData) => { + // uni.upload 返回bodyData 的是 string类型。 需要解析。 + httpData.data = JSON.parse(httpData.data) + return Promise.resolve(httpData) + }).catch(err=>{ + uni.hideLoading() + infoBox.showErrorToast(`上传失败`) + }) + }) +} + +export default { + req: req, + request, + upload: upload +} \ No newline at end of file diff --git a/http/yskApi/invoicing.js b/http/yskApi/invoicing.js new file mode 100644 index 0000000..314a3a4 --- /dev/null +++ b/http/yskApi/invoicing.js @@ -0,0 +1,13 @@ +import http from './http.js' +import $API from '@/http/classApi.js' +import appConfig from '@/config/appConfig.js' +import { + Base64 +} from 'js-base64' +import infoBox from '@/commons/utils/infoBox.js' + +/* 操作记录 */ +export function $getStockOperate(data) { + return http.req('/api/tbProductStockOperate/list', {...data,shopId:uni.getStorageSync('shopId')}, 'POST') +} + diff --git a/http/yskApi/login.js b/http/yskApi/login.js new file mode 100644 index 0000000..0791b7a --- /dev/null +++ b/http/yskApi/login.js @@ -0,0 +1,44 @@ +import http from './http.js' +const request=http.request + +export function login(data) { + return request({ + url: "/auth/login", + method: "post", + data + }); +} + +export function getInfo() { + return request({ + url: "/auth/info", + method: "get" + }); +} + +export function getCodeImg(header) { + return request({ + url: "/auth/code", + method: "get" + }); +} + +export function logout() { + return request({ + url: "/auth/logout", + method: "delete" + }); +} + +/** + * 个人中心 修改密码 + * @param {*} data + * @returns + */ +export function updatePass(data) { + return request({ + url: "/api/users/updatePass", + method: "post", + data + }); +} diff --git a/http/yskApi/order.js b/http/yskApi/order.js new file mode 100644 index 0000000..764344e --- /dev/null +++ b/http/yskApi/order.js @@ -0,0 +1,108 @@ +import http from './http.js' +const request = http.request + +/** + * 查询订单 + * @param {*} data + * @returns + */ +export function tbOrderInfoData(data) { + return request({ + url: "/api/tbOrderInfo/date", + method: "post", + data: { + shopId: uni.getStorageSync('shopId'), + ...data + } + }); +} + +/** + * 导出数据 + * @param {*} data + * @returns + */ +export function tbOrderInfoDownload(data) { + return request({ + url: "/api/tbOrderInfo/download", + method: "post", + data: { + shopId: uni.getStorageSync('shopId'), + ...data + }, + responseType: "blob" + }); +} + +/** + * 通过Id查询订单 + * @param {*} id + * @returns + */ +export function tbOrderInfoDetail(id) { + return request({ + url: `/api/tbOrderInfo/${id}`, + method: "get" + }); +} + +/** + * 通过Id查询订单 + * @param {*} createdAt + * @returns + */ +export function payCount(createdAt) { + console.log(createdAt); + return request({ + url: `/api/tbOrderInfo/payCount`, + method: "post", + data: { + shopId: uni.getStorageSync('shopId'), + createdAt: createdAt + } + }); +} + +/** + * 订单列表 + * @param {*} createdAt + * @returns + */ +export function tbGroupOrderInfo(params) { + return request({ + url: `/api/tbGroupOrderInfo`, + method: "post", + data: { + shopId: uni.getStorageSync('shopId'), + ...params + } + }); +} + +/** + * 退单 + * @param {*} data + * @returns + */ +export function returnGpOrder(data) { + return request({ + url: `/api/tbGroupOrderInfo/returnGpOrder`, + method: "post", + data + }); +} + + +/** + * 店铺订单支付获取链接 + */ +export function $getOrderPayUrl(data) { + return request({ + url: `/api/shopPayApi/getOrderPayUrl`, + method: "get", + data: { + shopId: uni.getStorageSync('shopId'), + ...data + } + }); +} \ No newline at end of file diff --git a/http/yskApi/pageNotification.js b/http/yskApi/pageNotification.js new file mode 100644 index 0000000..9597344 --- /dev/null +++ b/http/yskApi/pageNotification.js @@ -0,0 +1,17 @@ +import http from './http.js' +const request=http.request + + +/** + * 获取订阅二维码 + * @returns + */ +export function getSubQrCode(params) { + return request({ + url: `/api/msg/subQrCode`, + method: 'get', + params: { + shopId: uni.getStorageSync('shopId'), + } + }) +} diff --git a/http/yskApi/pageWorkControl.js b/http/yskApi/pageWorkControl.js new file mode 100644 index 0000000..6f4d115 --- /dev/null +++ b/http/yskApi/pageWorkControl.js @@ -0,0 +1,29 @@ +import http from './http.js' +const request = http.request + +/** + * 查询交班记录 + * @returns + */ +export function tbHandover(data) { + return request({ + url: '/api/tbHandover?' + data, + method: 'get' + }) +} + + +/** + * 提交交班 + * @returns + */ +export function handoverData(data) { + return request({ + url: '/api/tbHandover/handoverData', + method: 'post', + data: { + shopId: uni.getStorageSync('shopId'), + ...data + } + }) +} \ No newline at end of file diff --git a/http/yskApi/requestAll.js b/http/yskApi/requestAll.js new file mode 100644 index 0000000..61487b2 --- /dev/null +++ b/http/yskApi/requestAll.js @@ -0,0 +1,315 @@ +import http from './http.js' +const request = http.request +// 销售总会list +export function summaryTrade(data) { + return request({ + url: '/api/summary/trade', + method: 'post', + data: { + ...data + } + }) +} +export function tbConsInfoFlowcount(data) { + return request({ + url: '/api/tbConsInfoFlow/count', + method: 'post', + data + }) +} +// 供应商列表 +export function tbShopPurveyorTransact(params) { + return request({ + url: '/api/tbShopPurveyorTransact', + method: 'get', + params + }) +} +// 添加供应商 +export function tbShopPurveyorpost(data) { + return request({ + url: `/api/tbShopPurveyor`, + method: "post", + data + }); +} +// 编辑供应商 +export function tbShopPurveyorput(data) { + return request({ + url: `/api/tbShopPurveyor`, + method: "put", + data + }); +} +// 结款记录列表 +export function tbShopPurveyorTransactinfo(data) { + return request({ + url: '/api/tbShopPurveyorTransact/info', + method: "post", + data + }) +} +// 付款 +export function tbShopPurveyorpayTransact(data) { + return request({ + url: '/api/tbShopPurveyorTransact/payTransact', + method: "post", + data + }) +} +// 账单付款记录 +export function tbShopPurveyorTransacttransactPayInfos(params) { + return request({ + url: '/api/tbShopPurveyorTransact/transactPayInfos', + method: 'get', + params + }) +} +// 删除供应商列表 +export function tbShopPurveyordelete(data) { + return request({ + url: `/api/tbShopPurveyor`, + method: "delete", + data + }); +} +// 耗材报损 +export function tbConsInfoFlowfrmLoss(data) { + return request({ + url: '/api/tbConsInfoFlow/frmLoss', + method: 'post', + data + }) +} +// 销售排行榜 +export function dateProduct(params) { + return request({ + url: '/api/summary/productSaleDate', + method: 'get', + params + }) +} +// 是否开启 +export function updateStatus(data) { + return request({ + url: `/api/tbPlussShopStaff/updateStatus`, + method: "put", + data + }); +} +// 编辑 +export function tbPlussShopStaffDetail(id) { + return request({ + url: `/api/tbPlussShopStaff/` + id, + method: "get" + }); +} +// 新增耗材类型 +export function tbConsType(data) { + return request({ + url: '/api/tbConsType ', + method: 'post', + data + }) +} +// 编辑耗材类型 +export function tbConsTypeput(data) { + return request({ + url: '/api/tbConsInfo ', + method: "put", + data + }); +} + +// 获取耗材类型列表 +export function tbConsTypeList(params) { + return request({ + url: '/api/tbConsType', + method: 'get', + params + }) +} +// 修改耗材类型 +export function edittbConsTypeput(data) { + return request({ + url: '/api/tbConsType ', + method: "put", + data + }); +} +// 添加耗材列表 +export function tbConsInfoAddlist(data) { + return request({ + url: '/api/tbConsInfo ', + method: 'post', + data + }) +} +// 操作耗材入库 +export function tbConsInfostockInOut(data) { + return request({ + url: '/api/tbConsInfo/stockInOut ', + method: 'post', + data + }) +} +// 获取耗材列表 +export function tbConsInfoList(params) { + return request({ + url: '/api/tbConsInfo', + method: 'get', + params + }) +} +// 耗材盘点 +export function tbConsInfotbConCheck(data) { + return request({ + url: '/api/tbConCheck ', + method: 'post', + data + }) +} +// 获取供应商列表 +export function tbShopPurveyor(params) { + return request({ + url: '/api/tbShopPurveyor', + method: 'get', + params + }) +} +// 桌型列表 +export function callTable(params) { + return request({ + url: '/callTable', + method: 'get', + params + }) +} +// 排队列表 +export function callTablequeue(params) { + return request({ + url: '/callTable/queue', + method: 'get', + params + }) +} +// 取号 +export function callTabletakeNumber(data) { + return request({ + url: '/callTable/takeNumber', + method: 'post', + data: { + ...data + } + }) +} +// 增减余额 +export function midfiyAccount(data) { + return request({ + url: '/api/tbShopUser/midfiyAccount', + method: 'post', + data: { + ...data + } + }) +} +// 新增会员 +export function member(data) { + return request({ + url: '/api/member', + method: 'post', + data: { + ...data + } + }) +} +// 修改会员 +export function tbShopUser(data) { + return request({ + url: `/api/tbShopUser`, + method: "put", + data + }); +} +export function callTablecallRecord(params) { + return request({ + url: '/callTable/callRecord', + method: 'get', + params + }) +} +export function callTableput(data) { + return request({ + url: `/callTable/updateState`, + method: "put", + data + }); +} +// 叫号 +export function callTablecall(data) { + return request({ + url: `/callTable/call`, + method: 'post', + data + }); +} +// 获取员工列表 +export function rolesGet(params) { + return request({ + url: `/api/tbPlussShopStaff`, + method: "get", + params + }); +} +// 删除员工 +export function shopStaffDelete(data) { + return request({ + url: `/api/tbPlussShopStaff`, + method: "delete", + data + }); +} +// 新增员工获取权限 +export function tbShopPermissionList() { + return request({ + url: `/api/tbShopPermission/list`, + method: "get" + }); +} + +// 获取角色权限 +export function getroles() { + return request({ + url: `/api/roles`, + method: "get" + }); +} +export function tbConsTypes() { + return request({ + url: `/api/tbConsType`, + method: "get" + }); +} +export function tbPlussShopStaff(data) { + return request({ + url: `/api/tbPlussShopStaff`, + method: data.id ? "put" : "post", + data + }); +} +// 耗材列表 +export function viewConInfoFlowget(data) { + return request({ + url: `/api/tbConsInfo/allAndPro`, + method: 'post', + data + }); +} +// 耗材记录 +export function tbConsInfoFlowstock(data) { + return request({ + url: `/api/tbConsInfoFlow/stock`, + method: 'post', + data + }); +} \ No newline at end of file diff --git a/http/yskApi/shop-user.js b/http/yskApi/shop-user.js new file mode 100644 index 0000000..4434d93 --- /dev/null +++ b/http/yskApi/shop-user.js @@ -0,0 +1,48 @@ +// 用户管理 +import http from './http.js' +import $API from '@/http/classApi.js' +import appConfig from '@/config/appConfig.js' +import { + Base64 +} from 'js-base64' +import infoBox from '@/commons/utils/infoBox.js' + +const request=http.request + +// 获取店铺会员二维码 +export function getwxacode(data) { + return request({ + url: `/shop/storage/getwxacode`, + method: "post", + data + }); +} +/** + * 商家用户列表 + * @returns + */ +export function queryAllShopUser(params) { + return request({ + url: `/api/tbShopUser/queryAllShopUser`, + method: "get", + params: { + shopId: uni.getStorageSync('shopId'), + ...params + } + }); +} +/** + * 查询商家用户概述信息 + * @returns + */ +export function queryAllShopInfo(params) { + return request({ + url: `/api/tbShopUser/summary`, + method: "get", + params: { + shopId: uni.getStorageSync('shopId'), + isVip:1, + ...params + } + }); +} diff --git a/http/yskApi/shop.js b/http/yskApi/shop.js new file mode 100644 index 0000000..9422701 --- /dev/null +++ b/http/yskApi/shop.js @@ -0,0 +1,735 @@ +import http from './http.js' +const request=http.request + + +/** + * 获取店铺列表 + * @returns + */ +export function getShopList(params) { + return request({ + url: `/api/tbShopInfo`, + method: 'get', + params: { + + } + }) +} + +/** + * 获取店铺数据 + * @returns + */ +export function getShopInfo(params) { + return request({ + url: `/api/tbShopInfo/${params}`, + method: 'get', + params: { + + } + }) +} + +/** + * 更改店铺信息 + * @returns + */ +export function editShopInfo(data) { + return request({ + url: `/api/tbShopInfo`, + method: 'put', + data:{ + // shopId: uni.getStorageSync('shopId'), + ...data + } + }) +} + + +/** + * 获取店铺图片 + * @returns + */ +export function getShopExtend(params) { + return request({ + url: `/tbShopExtend`, + method: 'get', + params:{ + shopId: uni.getStorageSync('shopId'), + } + }) +} + +/** + * 获取店铺图片 + * @returns + */ +export function editShopExtend(data) { + return request({ + url: `/tbShopExtend`, + method: 'put', + data:{ + shopId: uni.getStorageSync('shopId'), + ...data + } + }) +} +/** + * 商品列表 + * @returns + */ +export function tbProduct(params) { + return request({ + url: "/api/tbProduct", + method: "get", + params + }); +} + +/** + * 删除商品 + * @returns + */ +export function tbProductDelete(data) { + return request({ + url: "/api/tbProduct", + method: "delete", + data + }); +} + +/** + * 商品单位列表 + * @returns + */ +export function tbShopUnit(params) { + return request({ + url: "/api/tbShopUnit", + method: "get", + params + }); +} + +/** + * 店铺基本配置 + * @returns + */ +export function tbShopCurrency(shopId) { + return request({ + url: `/api/tbShopCurrency/${shopId}`, + method: "get" + }); +} + +/** + * 修改店铺信息 + * @returns + */ +export function tbShopCurrencyPut(data) { + return request({ + url: `/api/tbShopCurrency`, + method: "put", + data + }); +} + +/** + * 新增单位 + * @returns + */ +export function tbShopUnitPost(data) { + return request({ + url: `/api/tbShopUnit`, + method: "post", + data + }); +} + +/** + * 更改单位 + * @returns + */ +export function tbShopUnitPut(data) { + return request({ + url: `/api/tbShopUnit`, + method: "put", + data + }); +} + +/** + * 删除单位 + * @returns + */ +export function tbShopUnitDelete(data) { + return request({ + url: `/api/tbShopUnit`, + method: "delete", + data + }); +} + +/** + * 店铺基本配置 + * @returns + */ +export function tbShopCurrencyGet(params) { + return request({ + url: `/api/tbShopUnit`, + method: "get", + params:{ + sort:'id', + shopId: uni.getStorageSync("shopId"), + ...params, + } + }); +} + +/** + * 商品分类列表 + * @returns + */ +export function tbShopCategoryGet(params) { + return request({ + url: `/api/tbShopCategory`, + method: "get", + params + }); +} + +/** + * 新增、编辑分类/新增、编辑子分类 + * @returns + */ +export function tbShopCategoryPost(data, method = "post") { + return request({ + url: `/api/tbShopCategory`, + method: method, + data + }); +} + +/** + * 删除商品分类 + * @returns + */ +export function tbShopCategoryDelete(data) { + return request({ + url: `/api/tbShopCategory`, + method: "delete", + data + }); +} + +/** + * 规格增加 + * @returns + */ +export function tbProductSpecPost(data) { + return request({ + url: `/api/tbProductSpec`, + method: "post", + data + }); +} + +/** + * 规格列表 + * @returns + */ +export function tbProductSpecGet(params) { + return request({ + url: `/api/tbProductSpec`, + method: "get", + params + }); +} + +/** + * 规格更改 + * @returns + */ +export function tbProductSpecPut(data) { + return request({ + url: `/api/tbProductSpec`, + method: "put", + data + }); +} + +/** + * 删除规格 + * @returns + */ +export function tbProductSpecDelete(data) { + return request({ + url: `/api/tbProductSpec`, + method: "DELETE", + data + }); +} + +/** + * 新增分组 + * @returns + */ +export function tbProductGroupPost(data) { + return request({ + url: `/api/tbProductGroup`, + method: "post", + data + }); +} + +/** + * 更改分组 + * @returns + */ +export function tbProductGroupPut(data) { + return request({ + url: `/api/tbProductGroup`, + method: "PUT", + data + }); +} + +/** + * 商品分组列表 + * @returns + */ +export function tbProductGroupGet(params) { + return request({ + url: `/api/tbProductGroup`, + method: "get", + params + }); +} + +/** + * 商品列表(根据分组中的商品id) + * @returns + */ +export function productListGet(productGroup) { + return request({ + url: `/api/tbProductGroup/${productGroup}`, + method: "get" + }); +} + +/** + * 删除分组 + * @returns + */ +export function tbProductGroupDelete(data) { + return request({ + url: `/api/tbProductGroup`, + method: "DELETE", + data + }); +} + +/** + * 添加商品 + * @returns + */ +export function tbProductPost(data) { + return request({ + url: `/api/tbProduct`, + method: "post", + data + }); +} + +/** + * 添加商品 + * @returns + */ +export function tbProductPut(data) { + return request({ + url: `/api/tbProduct`, + method: "put", + data + }); +} + +/** + * 商品详情(单个商品) + * product 商品id + * @returns + */ +export function tbProductGetDetail(product) { + return request({ + url: `/api/tbProduct/${product}`, + method: "get" + }); +} + +/** + * 店铺列表 + * @returns + */ +export function tbShopInfo(params) { + return request({ + url: `/api/tbShopInfo`, + method: "get", + params + }); +} + +/** + * 增加激活码 + * @returns + */ +export function tbMerchantRegisterPost(data) { + return request({ + url: `/api/tbMerchantRegister`, + method: "post", + data + }); +} + +/** + * 激活码列表 + * @returns + */ +export function tbMerchantRegisterList(data) { + return request({ + url: `/api/tbMerchantRegister/list`, + method: "post", + data + }); +} + +/** + * 增加/编辑店铺 + * @returns + */ +export function tbShopInfoPost(data, method = "post") { + return request({ + url: `/api/tbShopInfo`, + method: method, + data + }); +} + +/** + * 详情(配置三方支付) + * @returns + */ +export function tbMerchantThirdApply(shopId) { + return request({ + url: `/api/tbMerchantThirdApply/${shopId}`, + method: "get" + }); +} + +/** + * 修改第三方配置 + * @returns + */ +export function tbMerchantThirdApplyPut(data) { + return request({ + url: `/api/tbMerchantThirdApply`, + method: "put", + data + }); +} + +/** + * 设置热销商品 + * @returns + */ +export function tbProductIsHot(params) { + return request({ + url: `/api/tbProduct/isHot`, + method: "get", + params + }); +} + +/** + * 增加/编辑优惠券 + * @returns + */ +export function tbMerchantCoupon(data, method = "post") { + return request({ + url: `/api/tbMerchantCoupon`, + method: method, + data + }); +} + +/** + * 设置热销商品 + * @returns + */ +export function tbMerchantCouponGet(params) { + return request({ + url: `/api/tbMerchantCoupon`, + method: "get", + params + }); +} + +/** + * 设置热销商品 + * @returns + */ +export function geocode(params) { + return request({ + url: `/api/geocode`, + method: "get", + params + }); +} + +/** + * 新增、修改活动 + * @returns + */ +export function modityActivate(data) { + return request({ + url: `/shop/storage/modityActivate`, + method: "post", + data + }); +} + +/** + * 活动列表 + * @returns + */ +export function findActivate(params) { + return request({ + url: `/shop/storage/findActivate`, + method: "get", + params + }); +} +// 获取店铺会员二维码 +export function getwxacode(data) { + return request({ + url: `/shop/storage/getwxacode`, + method: "post", + data + }); +} +/** + * 商家用户列表 + * @returns + */ +export function queryAllShopUser(params) { + return request({ + url: `/api/tbShopUser/queryAllShopUser`, + method: "get", + params: { + shopId: uni.getStorageSync("shopId"), + ...params + } + }); +} +/** + * 查询商家用户概述信息 + * @returns + */ +export function queryAllShopInfo(params) { + return request({ + url: `/api/tbShopUser/summary`, + method: "get", + params: { + shopId: uni.getStorageSync("shopId"), + ...params + } + }); +} + +/** + * 修改商品排序 + * @returns + */ +export function upProSort(data) { + return request({ + url: `/api/tbProduct/upProSort`, + method: "post", + data + }); +} + +/** + * 修改分组排序 + * @returns + */ +export function upGroupSort(data) { + return request({ + url: `/api/tbProductGroup/upGroupSort`, + method: "post", + data + }); +} + +/** + * 修改分类排序 + * @returns + */ +export function upCategorySort(data) { + return request({ + url: `/api/tbShopCategory/upCategorySort`, + method: "post", + data + }); +} + +/** + * 查询店铺充值记录 + * @returns + */ +export function tbShopUserRecharge(params) { + return request({ + url: `/api/tbShopUser/recharge`, + method: "get", + params: { + shopId: uni.getStorageSync("shopId"), + ...params + } + }); +} + +/** + * 导出充值记录 + * @returns + */ +export function downloadTableRecharge(data) { + return request({ + url: `/api/tbShopUser/recharge/download`, + method: "post", + data: { + shopId: uni.getStorageSync("shopId"), + ...data + }, + responseType: "blob" + }); +} + +/** + * 员工列表 + * @returns + */ +export function tbPlussShopStaffGet(params) { + return request({ + url: `/api/tbPlussShopStaff`, + method: "get", + params: { + shopId: uni.getStorageSync("shopId"), + ...params + } + }); +} + +/** + * 角色列表 + * @returns + */ +export function rolesGet() { + return request({ + url: `/api/roles`, + method: "get" + }); +} + +/** + * 增加员工 + * @returns + */ +export function tbPlussShopStaff(data) { + return request({ + url: `/api/tbPlussShopStaff`, + method: data.id ? "put" : "post", + data: { + shopId: uni.getStorageSync("shopId"), + ...data + } + }); +} + +/** + * 通过id获取员工信息 + * @returns + */ +export function tbPlussShopStaffDetail(id) { + return request({ + url: `/api/tbPlussShopStaff/${id}`, + method: "get" + }); +} + +/** + * 更改员工状态 + * @returns + */ +export function updateStatus(data) { + return request({ + url: `/api/tbPlussShopStaff/updateStatus`, + method: "put", + data + }); +} + +/** + * 员工删除 + * @returns + */ +export function shopStaffDelete(data) { + return request({ + url: `/api/tbPlussShopStaff`, + method: "delete", + data + }); +} + +//增减余额 +export function midfiyAccount(data) { + return request({ + url: `/api/tbShopUser/midfiyAccount`, + method: "post", + data + }); +} +// 编辑用户 +export function tbShopUseredit(data) { + return request({ + url: `/api/tbShopUser`, + method: "put", + data + }); +} +// 通过活动id获取赠送商品列表 +export function activate(id) { + return request({ + url: `shop/storage/activate/${id}`, + method: "get" + }); +} + +// 通过活动id获取赠送商品列表 +export function queryShopUserFlow(params) { + return request({ + url: `/api/tbShopUser/queryShopUserFlow`, + method: "get", + params + }); +} + +//新增 + +// 查询员工是否拥有权限 +export function $hasPermission(params) { + return request({ + url: '/api/tbShopPermission/hasPermission', + method: "get", + params:{ + userId: uni.getStorageSync("shopUserId"), + ...params + } + }); +} + diff --git a/http/yskApi/sku.js b/http/yskApi/sku.js new file mode 100644 index 0000000..d65e86f --- /dev/null +++ b/http/yskApi/sku.js @@ -0,0 +1,13 @@ +import http from './http.js' +import $API from '@/http/classApi.js' +import appConfig from '@/config/appConfig.js' +import { + Base64 +} from 'js-base64' +import infoBox from '@/commons/utils/infoBox.js' + +/* 查询库存 */ +export function $getProductSku(productId) { + return http.req('/api/stock/sku', {productId,shopId:uni.getStorageSync('shopId')}, 'GET') +} + diff --git a/http/yskApi/table.js b/http/yskApi/table.js new file mode 100644 index 0000000..796f756 --- /dev/null +++ b/http/yskApi/table.js @@ -0,0 +1,50 @@ +// 桌台管理 +import http from './http.js' +const request = http.request +import $API from '@/http/classApi.js' +import appConfig from '@/config/appConfig.js' +import { + Base64 +} from 'js-base64' +import infoBox from '@/commons/utils/infoBox.js' + +/* 台桌区域 */ +export const $tableArea = new $API('/api/tbShopArea', http.req) +/* 台桌 */ +export const $table = new $API('/api/tbShopTable', http.req) +/* 绑定 */ +// export const $bind=new $API('/api/tbShopTable/bind',http.req) +export function $bind(data) { + return request({ + url: "/api/tbShopTable/bind", + method: "post", + data: { + shopId: uni.getStorageSync('shopId'), + ...data + } + }); +} +//获取台桌详情状态 +export function $returnTableDetail(data) { + return request({ + url: '/api/tbShopTable/state', + method: "get", + params: { + shopId: uni.getStorageSync('shopId'), + ...data + } + }); +} + + +// 选择台桌 +export function $choseTable(data) { + return request({ + url: '/api/place/choseTable', + method: "put", + data: { + shopId: uni.getStorageSync('shopId'), + ...data + } + }); +} \ No newline at end of file diff --git a/http/yskApi/user.js b/http/yskApi/user.js new file mode 100644 index 0000000..1b46450 --- /dev/null +++ b/http/yskApi/user.js @@ -0,0 +1,25 @@ +import http from './http.js' +const request=http.request +/** + * 用户详情 + * @returns + */ +export function tbShopInfo(shopId) { + const _shopId=uni.getStorageSync('shopId') + return request({ + url: `/api/tbShopInfo/${shopId||_shopId}`, + method: 'get' + }) +} + +/** + * 修改店铺信息 + * @returns + */ +export function tbShopInfoPut(data) { + return request({ + url: `/api/tbShopInfo`, + method: 'put', + data + }) +} \ No newline at end of file diff --git a/http/yskApi/version.js b/http/yskApi/version.js new file mode 100644 index 0000000..9929361 --- /dev/null +++ b/http/yskApi/version.js @@ -0,0 +1,15 @@ +import http from './http.js' +const request=http.request + + +/** + * 查询所属渠道升级版本 + * @returns + */ +export function getFindBySource(params) { + return request({ + url: `/api/tbVersion/findBySource`, + method: 'get', + params + }) +} diff --git a/index.html b/index.html new file mode 100644 index 0000000..c3ff205 --- /dev/null +++ b/index.html @@ -0,0 +1,20 @@ + + + + + + + + + + +
+ + + diff --git a/js_sdk/js-base64/.attic/test-moment/dankogai.js b/js_sdk/js-base64/.attic/test-moment/dankogai.js new file mode 100644 index 0000000..b631414 --- /dev/null +++ b/js_sdk/js-base64/.attic/test-moment/dankogai.js @@ -0,0 +1,44 @@ +/* + * $Id: dankogai.js,v 0.4 2012/08/24 05:23:18 dankogai Exp dankogai $ + * + * use mocha to test me + * http://visionmedia.github.com/mocha/ + */ +var assert = assert || require("assert"); +var Base64 = Base64 || require('../base64.js').Base64; +var is = function (a, e, m) { + return function () { + assert.equal(a, e, m) + } +}; + +describe('basic', function () { + it('d', is(Base64.encode('d'), 'ZA==')); + it('da', is(Base64.encode('da'), 'ZGE=')); + it('dan', is(Base64.encode('dan'), 'ZGFu')); + it('ZA==', is(Base64.decode('ZA=='), 'd' )); + it('ZGE=', is(Base64.decode('ZGE='), 'da' )); + it('ZGFu', is(Base64.decode('ZGFu'), 'dan' )); +}); + +describe('whitespace', function () { + it('Z A==', is(Base64.decode('ZA =='), 'd' )); + it('ZG E=', is(Base64.decode('ZG E='), 'da' )); + it('ZGF u', is(Base64.decode('ZGF u'), 'dan' )); +}); + +describe('null', function () { + it('\\0', is(Base64.encode('\0'), 'AA==')); + it('\\0\\0', is(Base64.encode('\0\0'), 'AAA=')); + it('\\0\\0\\0', is(Base64.encode('\0\0\0'), 'AAAA')); + it('AA==', is(Base64.decode('AA=='), '\0' )); + it('AAA=', is(Base64.decode('AAA='), '\0\0' )); + it('AAAA', is(Base64.decode('AAAA'), '\0\0\0')); +}); + +describe('Base64', function () { + it('.encode', is(Base64.encode('小飼弾'), '5bCP6aO85by+')); + it('.encodeURI', is(Base64.encodeURI('小飼弾'), '5bCP6aO85by-')); + it('.decode', is(Base64.decode('5bCP6aO85by+'), '小飼弾')); + it('.decode', is(Base64.decode('5bCP6aO85by-'), '小飼弾')); +}); diff --git a/js_sdk/js-base64/.attic/test-moment/es5.js b/js_sdk/js-base64/.attic/test-moment/es5.js new file mode 100644 index 0000000..ef134f6 --- /dev/null +++ b/js_sdk/js-base64/.attic/test-moment/es5.js @@ -0,0 +1,24 @@ +/* + * $Id: es5.js,v 0.1 2012/08/23 19:43:17 dankogai Exp dankogai $ + * + * use mocha to test me + * http://visionmedia.github.com/mocha/ + */ +var assert = assert || require("assert"); +var Base64 = Base64 || require('../base64.js').Base64; +var is = function (a, e, m) { + return function () { + assert.equal(a, e, m) + } +}; + +if ('extendString' in Base64){ + Base64.extendString(); + describe('String', function () { + it('.toBase64', is('小飼弾'.toBase64(), '5bCP6aO85by+')); + it('.toBase64', is('小飼弾'.toBase64(true), '5bCP6aO85by-')); + it('.toBase64URI', is('小飼弾'.toBase64URI(), '5bCP6aO85by-')); + it('.fromBase64', is('5bCP6aO85by+'.fromBase64(), '小飼弾')); + it('.fromBase64', is('5bCP6aO85by-'.fromBase64(), '小飼弾')); + }); +} diff --git a/js_sdk/js-base64/.attic/test-moment/es6.js b/js_sdk/js-base64/.attic/test-moment/es6.js new file mode 100644 index 0000000..7dbe475 --- /dev/null +++ b/js_sdk/js-base64/.attic/test-moment/es6.js @@ -0,0 +1,25 @@ +/* + * $Id: es6.js,v 0.1 2017/11/29 21:43:17 ufolux Exp ufolux $ + * + * use mocha to test me + * http://visionmedia.github.com/mocha/ + */ +import {Base64} from '../base64' + +var assert = assert || require("assert"); +var is = function (a, e, m) { + return function () { + assert.equal(a, e, m) + } +}; + +if ('extendString' in Base64){ + Base64.extendString(); + describe('String', function () { + it('.toBase64', is('小飼弾'.toBase64(), '5bCP6aO85by+')); + it('.toBase64', is('小飼弾'.toBase64(true), '5bCP6aO85by-')); + it('.toBase64URI', is('小飼弾'.toBase64URI(), '5bCP6aO85by-')); + it('.fromBase64', is('5bCP6aO85by+'.fromBase64(), '小飼弾')); + it('.fromBase64', is('5bCP6aO85by-'.fromBase64(), '小飼弾')); + }); +} diff --git a/js_sdk/js-base64/.attic/test-moment/index.html b/js_sdk/js-base64/.attic/test-moment/index.html new file mode 100644 index 0000000..13136c9 --- /dev/null +++ b/js_sdk/js-base64/.attic/test-moment/index.html @@ -0,0 +1,40 @@ + + + + Mocha Tests + + + +
+ + + + + + + + + + + + + + + + $Id: index.html,v 0.3 2017/09/11 08:43:43 dankogai Exp dankogai $ +
+ + diff --git a/js_sdk/js-base64/.attic/test-moment/large.js b/js_sdk/js-base64/.attic/test-moment/large.js new file mode 100644 index 0000000..20d7842 --- /dev/null +++ b/js_sdk/js-base64/.attic/test-moment/large.js @@ -0,0 +1,25 @@ +/* + * $Id: large.js,v 0.3 2012/08/23 19:14:37 dankogai Exp dankogai $ + * + * use mocha to test me + * http://visionmedia.github.com/mocha/ + */ +var assert = assert || require("assert"); +var Base64 = Base64 || require('../base64.js').Base64; +var is = function (a, e, m) { + return function () { + assert.equal(a, e, m) + } +}; +var seed = function () { + var a, i; + for (a = [], i = 0; i < 256; i++) { + a.push(String.fromCharCode(i)); + } + return a.join(''); +}(); +describe('Base64', function () { + for (var i = 0, str = seed; i < 16; str += str, i++) { + it(''+str.length, is(Base64.decode(Base64.encode(str)), str)); + } +}); diff --git a/js_sdk/js-base64/.attic/test-moment/moment.js b/js_sdk/js-base64/.attic/test-moment/moment.js new file mode 100644 index 0000000..71b15f9 --- /dev/null +++ b/js_sdk/js-base64/.attic/test-moment/moment.js @@ -0,0 +1,4535 @@ +//! moment.js +//! version : 2.20.1 +//! authors : Tim Wood, Iskren Chernev, Moment.js contributors +//! license : MIT +//! momentjs.com + +;(function (global, factory) { + typeof exports === 'object' && typeof module !== 'undefined' ? module.exports = factory() : + typeof define === 'function' && define.amd ? define(factory) : + global.moment = factory() +}(this, (function () { 'use strict'; + +var hookCallback; + +function hooks () { + return hookCallback.apply(null, arguments); +} + +// This is done to register the method called with moment() +// without creating circular dependencies. +function setHookCallback (callback) { + hookCallback = callback; +} + +function isArray(input) { + return input instanceof Array || Object.prototype.toString.call(input) === '[object Array]'; +} + +function isObject(input) { + // IE8 will treat undefined and null as object if it wasn't for + // input != null + return input != null && Object.prototype.toString.call(input) === '[object Object]'; +} + +function isObjectEmpty(obj) { + if (Object.getOwnPropertyNames) { + return (Object.getOwnPropertyNames(obj).length === 0); + } else { + var k; + for (k in obj) { + if (obj.hasOwnProperty(k)) { + return false; + } + } + return true; + } +} + +function isUndefined(input) { + return input === void 0; +} + +function isNumber(input) { + return typeof input === 'number' || Object.prototype.toString.call(input) === '[object Number]'; +} + +function isDate(input) { + return input instanceof Date || Object.prototype.toString.call(input) === '[object Date]'; +} + +function map(arr, fn) { + var res = [], i; + for (i = 0; i < arr.length; ++i) { + res.push(fn(arr[i], i)); + } + return res; +} + +function hasOwnProp(a, b) { + return Object.prototype.hasOwnProperty.call(a, b); +} + +function extend(a, b) { + for (var i in b) { + if (hasOwnProp(b, i)) { + a[i] = b[i]; + } + } + + if (hasOwnProp(b, 'toString')) { + a.toString = b.toString; + } + + if (hasOwnProp(b, 'valueOf')) { + a.valueOf = b.valueOf; + } + + return a; +} + +function createUTC (input, format, locale, strict) { + return createLocalOrUTC(input, format, locale, strict, true).utc(); +} + +function defaultParsingFlags() { + // We need to deep clone this object. + return { + empty : false, + unusedTokens : [], + unusedInput : [], + overflow : -2, + charsLeftOver : 0, + nullInput : false, + invalidMonth : null, + invalidFormat : false, + userInvalidated : false, + iso : false, + parsedDateParts : [], + meridiem : null, + rfc2822 : false, + weekdayMismatch : false + }; +} + +function getParsingFlags(m) { + if (m._pf == null) { + m._pf = defaultParsingFlags(); + } + return m._pf; +} + +var some; +if (Array.prototype.some) { + some = Array.prototype.some; +} else { + some = function (fun) { + var t = Object(this); + var len = t.length >>> 0; + + for (var i = 0; i < len; i++) { + if (i in t && fun.call(this, t[i], i, t)) { + return true; + } + } + + return false; + }; +} + +function isValid(m) { + if (m._isValid == null) { + var flags = getParsingFlags(m); + var parsedParts = some.call(flags.parsedDateParts, function (i) { + return i != null; + }); + var isNowValid = !isNaN(m._d.getTime()) && + flags.overflow < 0 && + !flags.empty && + !flags.invalidMonth && + !flags.invalidWeekday && + !flags.weekdayMismatch && + !flags.nullInput && + !flags.invalidFormat && + !flags.userInvalidated && + (!flags.meridiem || (flags.meridiem && parsedParts)); + + if (m._strict) { + isNowValid = isNowValid && + flags.charsLeftOver === 0 && + flags.unusedTokens.length === 0 && + flags.bigHour === undefined; + } + + if (Object.isFrozen == null || !Object.isFrozen(m)) { + m._isValid = isNowValid; + } + else { + return isNowValid; + } + } + return m._isValid; +} + +function createInvalid (flags) { + var m = createUTC(NaN); + if (flags != null) { + extend(getParsingFlags(m), flags); + } + else { + getParsingFlags(m).userInvalidated = true; + } + + return m; +} + +// Plugins that add properties should also add the key here (null value), +// so we can properly clone ourselves. +var momentProperties = hooks.momentProperties = []; + +function copyConfig(to, from) { + var i, prop, val; + + if (!isUndefined(from._isAMomentObject)) { + to._isAMomentObject = from._isAMomentObject; + } + if (!isUndefined(from._i)) { + to._i = from._i; + } + if (!isUndefined(from._f)) { + to._f = from._f; + } + if (!isUndefined(from._l)) { + to._l = from._l; + } + if (!isUndefined(from._strict)) { + to._strict = from._strict; + } + if (!isUndefined(from._tzm)) { + to._tzm = from._tzm; + } + if (!isUndefined(from._isUTC)) { + to._isUTC = from._isUTC; + } + if (!isUndefined(from._offset)) { + to._offset = from._offset; + } + if (!isUndefined(from._pf)) { + to._pf = getParsingFlags(from); + } + if (!isUndefined(from._locale)) { + to._locale = from._locale; + } + + if (momentProperties.length > 0) { + for (i = 0; i < momentProperties.length; i++) { + prop = momentProperties[i]; + val = from[prop]; + if (!isUndefined(val)) { + to[prop] = val; + } + } + } + + return to; +} + +var updateInProgress = false; + +// Moment prototype object +function Moment(config) { + copyConfig(this, config); + this._d = new Date(config._d != null ? config._d.getTime() : NaN); + if (!this.isValid()) { + this._d = new Date(NaN); + } + // Prevent infinite loop in case updateOffset creates new moment + // objects. + if (updateInProgress === false) { + updateInProgress = true; + hooks.updateOffset(this); + updateInProgress = false; + } +} + +function isMoment (obj) { + return obj instanceof Moment || (obj != null && obj._isAMomentObject != null); +} + +function absFloor (number) { + if (number < 0) { + // -0 -> 0 + return Math.ceil(number) || 0; + } else { + return Math.floor(number); + } +} + +function toInt(argumentForCoercion) { + var coercedNumber = +argumentForCoercion, + value = 0; + + if (coercedNumber !== 0 && isFinite(coercedNumber)) { + value = absFloor(coercedNumber); + } + + return value; +} + +// compare two arrays, return the number of differences +function compareArrays(array1, array2, dontConvert) { + var len = Math.min(array1.length, array2.length), + lengthDiff = Math.abs(array1.length - array2.length), + diffs = 0, + i; + for (i = 0; i < len; i++) { + if ((dontConvert && array1[i] !== array2[i]) || + (!dontConvert && toInt(array1[i]) !== toInt(array2[i]))) { + diffs++; + } + } + return diffs + lengthDiff; +} + +function warn(msg) { + if (hooks.suppressDeprecationWarnings === false && + (typeof console !== 'undefined') && console.warn) { + console.warn('Deprecation warning: ' + msg); + } +} + +function deprecate(msg, fn) { + var firstTime = true; + + return extend(function () { + if (hooks.deprecationHandler != null) { + hooks.deprecationHandler(null, msg); + } + if (firstTime) { + var args = []; + var arg; + for (var i = 0; i < arguments.length; i++) { + arg = ''; + if (typeof arguments[i] === 'object') { + arg += '\n[' + i + '] '; + for (var key in arguments[0]) { + arg += key + ': ' + arguments[0][key] + ', '; + } + arg = arg.slice(0, -2); // Remove trailing comma and space + } else { + arg = arguments[i]; + } + args.push(arg); + } + warn(msg + '\nArguments: ' + Array.prototype.slice.call(args).join('') + '\n' + (new Error()).stack); + firstTime = false; + } + return fn.apply(this, arguments); + }, fn); +} + +var deprecations = {}; + +function deprecateSimple(name, msg) { + if (hooks.deprecationHandler != null) { + hooks.deprecationHandler(name, msg); + } + if (!deprecations[name]) { + warn(msg); + deprecations[name] = true; + } +} + +hooks.suppressDeprecationWarnings = false; +hooks.deprecationHandler = null; + +function isFunction(input) { + return input instanceof Function || Object.prototype.toString.call(input) === '[object Function]'; +} + +function set (config) { + var prop, i; + for (i in config) { + prop = config[i]; + if (isFunction(prop)) { + this[i] = prop; + } else { + this['_' + i] = prop; + } + } + this._config = config; + // Lenient ordinal parsing accepts just a number in addition to + // number + (possibly) stuff coming from _dayOfMonthOrdinalParse. + // TODO: Remove "ordinalParse" fallback in next major release. + this._dayOfMonthOrdinalParseLenient = new RegExp( + (this._dayOfMonthOrdinalParse.source || this._ordinalParse.source) + + '|' + (/\d{1,2}/).source); +} + +function mergeConfigs(parentConfig, childConfig) { + var res = extend({}, parentConfig), prop; + for (prop in childConfig) { + if (hasOwnProp(childConfig, prop)) { + if (isObject(parentConfig[prop]) && isObject(childConfig[prop])) { + res[prop] = {}; + extend(res[prop], parentConfig[prop]); + extend(res[prop], childConfig[prop]); + } else if (childConfig[prop] != null) { + res[prop] = childConfig[prop]; + } else { + delete res[prop]; + } + } + } + for (prop in parentConfig) { + if (hasOwnProp(parentConfig, prop) && + !hasOwnProp(childConfig, prop) && + isObject(parentConfig[prop])) { + // make sure changes to properties don't modify parent config + res[prop] = extend({}, res[prop]); + } + } + return res; +} + +function Locale(config) { + if (config != null) { + this.set(config); + } +} + +var keys; + +if (Object.keys) { + keys = Object.keys; +} else { + keys = function (obj) { + var i, res = []; + for (i in obj) { + if (hasOwnProp(obj, i)) { + res.push(i); + } + } + return res; + }; +} + +var defaultCalendar = { + sameDay : '[Today at] LT', + nextDay : '[Tomorrow at] LT', + nextWeek : 'dddd [at] LT', + lastDay : '[Yesterday at] LT', + lastWeek : '[Last] dddd [at] LT', + sameElse : 'L' +}; + +function calendar (key, mom, now) { + var output = this._calendar[key] || this._calendar['sameElse']; + return isFunction(output) ? output.call(mom, now) : output; +} + +var defaultLongDateFormat = { + LTS : 'h:mm:ss A', + LT : 'h:mm A', + L : 'MM/DD/YYYY', + LL : 'MMMM D, YYYY', + LLL : 'MMMM D, YYYY h:mm A', + LLLL : 'dddd, MMMM D, YYYY h:mm A' +}; + +function longDateFormat (key) { + var format = this._longDateFormat[key], + formatUpper = this._longDateFormat[key.toUpperCase()]; + + if (format || !formatUpper) { + return format; + } + + this._longDateFormat[key] = formatUpper.replace(/MMMM|MM|DD|dddd/g, function (val) { + return val.slice(1); + }); + + return this._longDateFormat[key]; +} + +var defaultInvalidDate = 'Invalid date'; + +function invalidDate () { + return this._invalidDate; +} + +var defaultOrdinal = '%d'; +var defaultDayOfMonthOrdinalParse = /\d{1,2}/; + +function ordinal (number) { + return this._ordinal.replace('%d', number); +} + +var defaultRelativeTime = { + future : 'in %s', + past : '%s ago', + s : 'a few seconds', + ss : '%d seconds', + m : 'a minute', + mm : '%d minutes', + h : 'an hour', + hh : '%d hours', + d : 'a day', + dd : '%d days', + M : 'a month', + MM : '%d months', + y : 'a year', + yy : '%d years' +}; + +function relativeTime (number, withoutSuffix, string, isFuture) { + var output = this._relativeTime[string]; + return (isFunction(output)) ? + output(number, withoutSuffix, string, isFuture) : + output.replace(/%d/i, number); +} + +function pastFuture (diff, output) { + var format = this._relativeTime[diff > 0 ? 'future' : 'past']; + return isFunction(format) ? format(output) : format.replace(/%s/i, output); +} + +var aliases = {}; + +function addUnitAlias (unit, shorthand) { + var lowerCase = unit.toLowerCase(); + aliases[lowerCase] = aliases[lowerCase + 's'] = aliases[shorthand] = unit; +} + +function normalizeUnits(units) { + return typeof units === 'string' ? aliases[units] || aliases[units.toLowerCase()] : undefined; +} + +function normalizeObjectUnits(inputObject) { + var normalizedInput = {}, + normalizedProp, + prop; + + for (prop in inputObject) { + if (hasOwnProp(inputObject, prop)) { + normalizedProp = normalizeUnits(prop); + if (normalizedProp) { + normalizedInput[normalizedProp] = inputObject[prop]; + } + } + } + + return normalizedInput; +} + +var priorities = {}; + +function addUnitPriority(unit, priority) { + priorities[unit] = priority; +} + +function getPrioritizedUnits(unitsObj) { + var units = []; + for (var u in unitsObj) { + units.push({unit: u, priority: priorities[u]}); + } + units.sort(function (a, b) { + return a.priority - b.priority; + }); + return units; +} + +function zeroFill(number, targetLength, forceSign) { + var absNumber = '' + Math.abs(number), + zerosToFill = targetLength - absNumber.length, + sign = number >= 0; + return (sign ? (forceSign ? '+' : '') : '-') + + Math.pow(10, Math.max(0, zerosToFill)).toString().substr(1) + absNumber; +} + +var formattingTokens = /(\[[^\[]*\])|(\\)?([Hh]mm(ss)?|Mo|MM?M?M?|Do|DDDo|DD?D?D?|ddd?d?|do?|w[o|w]?|W[o|W]?|Qo?|YYYYYY|YYYYY|YYYY|YY|gg(ggg?)?|GG(GGG?)?|e|E|a|A|hh?|HH?|kk?|mm?|ss?|S{1,9}|x|X|zz?|ZZ?|.)/g; + +var localFormattingTokens = /(\[[^\[]*\])|(\\)?(LTS|LT|LL?L?L?|l{1,4})/g; + +var formatFunctions = {}; + +var formatTokenFunctions = {}; + +// token: 'M' +// padded: ['MM', 2] +// ordinal: 'Mo' +// callback: function () { this.month() + 1 } +function addFormatToken (token, padded, ordinal, callback) { + var func = callback; + if (typeof callback === 'string') { + func = function () { + return this[callback](); + }; + } + if (token) { + formatTokenFunctions[token] = func; + } + if (padded) { + formatTokenFunctions[padded[0]] = function () { + return zeroFill(func.apply(this, arguments), padded[1], padded[2]); + }; + } + if (ordinal) { + formatTokenFunctions[ordinal] = function () { + return this.localeData().ordinal(func.apply(this, arguments), token); + }; + } +} + +function removeFormattingTokens(input) { + if (input.match(/\[[\s\S]/)) { + return input.replace(/^\[|\]$/g, ''); + } + return input.replace(/\\/g, ''); +} + +function makeFormatFunction(format) { + var array = format.match(formattingTokens), i, length; + + for (i = 0, length = array.length; i < length; i++) { + if (formatTokenFunctions[array[i]]) { + array[i] = formatTokenFunctions[array[i]]; + } else { + array[i] = removeFormattingTokens(array[i]); + } + } + + return function (mom) { + var output = '', i; + for (i = 0; i < length; i++) { + output += isFunction(array[i]) ? array[i].call(mom, format) : array[i]; + } + return output; + }; +} + +// format date using native date object +function formatMoment(m, format) { + if (!m.isValid()) { + return m.localeData().invalidDate(); + } + + format = expandFormat(format, m.localeData()); + formatFunctions[format] = formatFunctions[format] || makeFormatFunction(format); + + return formatFunctions[format](m); +} + +function expandFormat(format, locale) { + var i = 5; + + function replaceLongDateFormatTokens(input) { + return locale.longDateFormat(input) || input; + } + + localFormattingTokens.lastIndex = 0; + while (i >= 0 && localFormattingTokens.test(format)) { + format = format.replace(localFormattingTokens, replaceLongDateFormatTokens); + localFormattingTokens.lastIndex = 0; + i -= 1; + } + + return format; +} + +var match1 = /\d/; // 0 - 9 +var match2 = /\d\d/; // 00 - 99 +var match3 = /\d{3}/; // 000 - 999 +var match4 = /\d{4}/; // 0000 - 9999 +var match6 = /[+-]?\d{6}/; // -999999 - 999999 +var match1to2 = /\d\d?/; // 0 - 99 +var match3to4 = /\d\d\d\d?/; // 999 - 9999 +var match5to6 = /\d\d\d\d\d\d?/; // 99999 - 999999 +var match1to3 = /\d{1,3}/; // 0 - 999 +var match1to4 = /\d{1,4}/; // 0 - 9999 +var match1to6 = /[+-]?\d{1,6}/; // -999999 - 999999 + +var matchUnsigned = /\d+/; // 0 - inf +var matchSigned = /[+-]?\d+/; // -inf - inf + +var matchOffset = /Z|[+-]\d\d:?\d\d/gi; // +00:00 -00:00 +0000 -0000 or Z +var matchShortOffset = /Z|[+-]\d\d(?::?\d\d)?/gi; // +00 -00 +00:00 -00:00 +0000 -0000 or Z + +var matchTimestamp = /[+-]?\d+(\.\d{1,3})?/; // 12.4.8789 123456789.123 + +// any word (or two) characters or numbers including two/three word month in arabic. +// includes scottish gaelic two word and hyphenated months +var matchWord = /[0-9]{0,256}['a-z\u00A0-\u05FF\u0700-\uD7FF\uF900-\uFDCF\uFDF0-\uFF07\uFF10-\uFFEF]{1,256}|[\u0600-\u06FF\/]{1,256}(\s*?[\u0600-\u06FF]{1,256}){1,2}/i; + + +var regexes = {}; + +function addRegexToken (token, regex, strictRegex) { + regexes[token] = isFunction(regex) ? regex : function (isStrict, localeData) { + return (isStrict && strictRegex) ? strictRegex : regex; + }; +} + +function getParseRegexForToken (token, config) { + if (!hasOwnProp(regexes, token)) { + return new RegExp(unescapeFormat(token)); + } + + return regexes[token](config._strict, config._locale); +} + +// Code from http://stackoverflow.com/questions/3561493/is-there-a-regexp-escape-function-in-javascript +function unescapeFormat(s) { + return regexEscape(s.replace('\\', '').replace(/\\(\[)|\\(\])|\[([^\]\[]*)\]|\\(.)/g, function (matched, p1, p2, p3, p4) { + return p1 || p2 || p3 || p4; + })); +} + +function regexEscape(s) { + return s.replace(/[-\/\\^$*+?.()|[\]{}]/g, '\\$&'); +} + +var tokens = {}; + +function addParseToken (token, callback) { + var i, func = callback; + if (typeof token === 'string') { + token = [token]; + } + if (isNumber(callback)) { + func = function (input, array) { + array[callback] = toInt(input); + }; + } + for (i = 0; i < token.length; i++) { + tokens[token[i]] = func; + } +} + +function addWeekParseToken (token, callback) { + addParseToken(token, function (input, array, config, token) { + config._w = config._w || {}; + callback(input, config._w, config, token); + }); +} + +function addTimeToArrayFromToken(token, input, config) { + if (input != null && hasOwnProp(tokens, token)) { + tokens[token](input, config._a, config, token); + } +} + +var YEAR = 0; +var MONTH = 1; +var DATE = 2; +var HOUR = 3; +var MINUTE = 4; +var SECOND = 5; +var MILLISECOND = 6; +var WEEK = 7; +var WEEKDAY = 8; + +// FORMATTING + +addFormatToken('Y', 0, 0, function () { + var y = this.year(); + return y <= 9999 ? '' + y : '+' + y; +}); + +addFormatToken(0, ['YY', 2], 0, function () { + return this.year() % 100; +}); + +addFormatToken(0, ['YYYY', 4], 0, 'year'); +addFormatToken(0, ['YYYYY', 5], 0, 'year'); +addFormatToken(0, ['YYYYYY', 6, true], 0, 'year'); + +// ALIASES + +addUnitAlias('year', 'y'); + +// PRIORITIES + +addUnitPriority('year', 1); + +// PARSING + +addRegexToken('Y', matchSigned); +addRegexToken('YY', match1to2, match2); +addRegexToken('YYYY', match1to4, match4); +addRegexToken('YYYYY', match1to6, match6); +addRegexToken('YYYYYY', match1to6, match6); + +addParseToken(['YYYYY', 'YYYYYY'], YEAR); +addParseToken('YYYY', function (input, array) { + array[YEAR] = input.length === 2 ? hooks.parseTwoDigitYear(input) : toInt(input); +}); +addParseToken('YY', function (input, array) { + array[YEAR] = hooks.parseTwoDigitYear(input); +}); +addParseToken('Y', function (input, array) { + array[YEAR] = parseInt(input, 10); +}); + +// HELPERS + +function daysInYear(year) { + return isLeapYear(year) ? 366 : 365; +} + +function isLeapYear(year) { + return (year % 4 === 0 && year % 100 !== 0) || year % 400 === 0; +} + +// HOOKS + +hooks.parseTwoDigitYear = function (input) { + return toInt(input) + (toInt(input) > 68 ? 1900 : 2000); +}; + +// MOMENTS + +var getSetYear = makeGetSet('FullYear', true); + +function getIsLeapYear () { + return isLeapYear(this.year()); +} + +function makeGetSet (unit, keepTime) { + return function (value) { + if (value != null) { + set$1(this, unit, value); + hooks.updateOffset(this, keepTime); + return this; + } else { + return get(this, unit); + } + }; +} + +function get (mom, unit) { + return mom.isValid() ? + mom._d['get' + (mom._isUTC ? 'UTC' : '') + unit]() : NaN; +} + +function set$1 (mom, unit, value) { + if (mom.isValid() && !isNaN(value)) { + if (unit === 'FullYear' && isLeapYear(mom.year()) && mom.month() === 1 && mom.date() === 29) { + mom._d['set' + (mom._isUTC ? 'UTC' : '') + unit](value, mom.month(), daysInMonth(value, mom.month())); + } + else { + mom._d['set' + (mom._isUTC ? 'UTC' : '') + unit](value); + } + } +} + +// MOMENTS + +function stringGet (units) { + units = normalizeUnits(units); + if (isFunction(this[units])) { + return this[units](); + } + return this; +} + + +function stringSet (units, value) { + if (typeof units === 'object') { + units = normalizeObjectUnits(units); + var prioritized = getPrioritizedUnits(units); + for (var i = 0; i < prioritized.length; i++) { + this[prioritized[i].unit](units[prioritized[i].unit]); + } + } else { + units = normalizeUnits(units); + if (isFunction(this[units])) { + return this[units](value); + } + } + return this; +} + +function mod(n, x) { + return ((n % x) + x) % x; +} + +var indexOf; + +if (Array.prototype.indexOf) { + indexOf = Array.prototype.indexOf; +} else { + indexOf = function (o) { + // I know + var i; + for (i = 0; i < this.length; ++i) { + if (this[i] === o) { + return i; + } + } + return -1; + }; +} + +function daysInMonth(year, month) { + if (isNaN(year) || isNaN(month)) { + return NaN; + } + var modMonth = mod(month, 12); + year += (month - modMonth) / 12; + return modMonth === 1 ? (isLeapYear(year) ? 29 : 28) : (31 - modMonth % 7 % 2); +} + +// FORMATTING + +addFormatToken('M', ['MM', 2], 'Mo', function () { + return this.month() + 1; +}); + +addFormatToken('MMM', 0, 0, function (format) { + return this.localeData().monthsShort(this, format); +}); + +addFormatToken('MMMM', 0, 0, function (format) { + return this.localeData().months(this, format); +}); + +// ALIASES + +addUnitAlias('month', 'M'); + +// PRIORITY + +addUnitPriority('month', 8); + +// PARSING + +addRegexToken('M', match1to2); +addRegexToken('MM', match1to2, match2); +addRegexToken('MMM', function (isStrict, locale) { + return locale.monthsShortRegex(isStrict); +}); +addRegexToken('MMMM', function (isStrict, locale) { + return locale.monthsRegex(isStrict); +}); + +addParseToken(['M', 'MM'], function (input, array) { + array[MONTH] = toInt(input) - 1; +}); + +addParseToken(['MMM', 'MMMM'], function (input, array, config, token) { + var month = config._locale.monthsParse(input, token, config._strict); + // if we didn't find a month name, mark the date as invalid. + if (month != null) { + array[MONTH] = month; + } else { + getParsingFlags(config).invalidMonth = input; + } +}); + +// LOCALES + +var MONTHS_IN_FORMAT = /D[oD]?(\[[^\[\]]*\]|\s)+MMMM?/; +var defaultLocaleMonths = 'January_February_March_April_May_June_July_August_September_October_November_December'.split('_'); +function localeMonths (m, format) { + if (!m) { + return isArray(this._months) ? this._months : + this._months['standalone']; + } + return isArray(this._months) ? this._months[m.month()] : + this._months[(this._months.isFormat || MONTHS_IN_FORMAT).test(format) ? 'format' : 'standalone'][m.month()]; +} + +var defaultLocaleMonthsShort = 'Jan_Feb_Mar_Apr_May_Jun_Jul_Aug_Sep_Oct_Nov_Dec'.split('_'); +function localeMonthsShort (m, format) { + if (!m) { + return isArray(this._monthsShort) ? this._monthsShort : + this._monthsShort['standalone']; + } + return isArray(this._monthsShort) ? this._monthsShort[m.month()] : + this._monthsShort[MONTHS_IN_FORMAT.test(format) ? 'format' : 'standalone'][m.month()]; +} + +function handleStrictParse(monthName, format, strict) { + var i, ii, mom, llc = monthName.toLocaleLowerCase(); + if (!this._monthsParse) { + // this is not used + this._monthsParse = []; + this._longMonthsParse = []; + this._shortMonthsParse = []; + for (i = 0; i < 12; ++i) { + mom = createUTC([2000, i]); + this._shortMonthsParse[i] = this.monthsShort(mom, '').toLocaleLowerCase(); + this._longMonthsParse[i] = this.months(mom, '').toLocaleLowerCase(); + } + } + + if (strict) { + if (format === 'MMM') { + ii = indexOf.call(this._shortMonthsParse, llc); + return ii !== -1 ? ii : null; + } else { + ii = indexOf.call(this._longMonthsParse, llc); + return ii !== -1 ? ii : null; + } + } else { + if (format === 'MMM') { + ii = indexOf.call(this._shortMonthsParse, llc); + if (ii !== -1) { + return ii; + } + ii = indexOf.call(this._longMonthsParse, llc); + return ii !== -1 ? ii : null; + } else { + ii = indexOf.call(this._longMonthsParse, llc); + if (ii !== -1) { + return ii; + } + ii = indexOf.call(this._shortMonthsParse, llc); + return ii !== -1 ? ii : null; + } + } +} + +function localeMonthsParse (monthName, format, strict) { + var i, mom, regex; + + if (this._monthsParseExact) { + return handleStrictParse.call(this, monthName, format, strict); + } + + if (!this._monthsParse) { + this._monthsParse = []; + this._longMonthsParse = []; + this._shortMonthsParse = []; + } + + // TODO: add sorting + // Sorting makes sure if one month (or abbr) is a prefix of another + // see sorting in computeMonthsParse + for (i = 0; i < 12; i++) { + // make the regex if we don't have it already + mom = createUTC([2000, i]); + if (strict && !this._longMonthsParse[i]) { + this._longMonthsParse[i] = new RegExp('^' + this.months(mom, '').replace('.', '') + '$', 'i'); + this._shortMonthsParse[i] = new RegExp('^' + this.monthsShort(mom, '').replace('.', '') + '$', 'i'); + } + if (!strict && !this._monthsParse[i]) { + regex = '^' + this.months(mom, '') + '|^' + this.monthsShort(mom, ''); + this._monthsParse[i] = new RegExp(regex.replace('.', ''), 'i'); + } + // test the regex + if (strict && format === 'MMMM' && this._longMonthsParse[i].test(monthName)) { + return i; + } else if (strict && format === 'MMM' && this._shortMonthsParse[i].test(monthName)) { + return i; + } else if (!strict && this._monthsParse[i].test(monthName)) { + return i; + } + } +} + +// MOMENTS + +function setMonth (mom, value) { + var dayOfMonth; + + if (!mom.isValid()) { + // No op + return mom; + } + + if (typeof value === 'string') { + if (/^\d+$/.test(value)) { + value = toInt(value); + } else { + value = mom.localeData().monthsParse(value); + // TODO: Another silent failure? + if (!isNumber(value)) { + return mom; + } + } + } + + dayOfMonth = Math.min(mom.date(), daysInMonth(mom.year(), value)); + mom._d['set' + (mom._isUTC ? 'UTC' : '') + 'Month'](value, dayOfMonth); + return mom; +} + +function getSetMonth (value) { + if (value != null) { + setMonth(this, value); + hooks.updateOffset(this, true); + return this; + } else { + return get(this, 'Month'); + } +} + +function getDaysInMonth () { + return daysInMonth(this.year(), this.month()); +} + +var defaultMonthsShortRegex = matchWord; +function monthsShortRegex (isStrict) { + if (this._monthsParseExact) { + if (!hasOwnProp(this, '_monthsRegex')) { + computeMonthsParse.call(this); + } + if (isStrict) { + return this._monthsShortStrictRegex; + } else { + return this._monthsShortRegex; + } + } else { + if (!hasOwnProp(this, '_monthsShortRegex')) { + this._monthsShortRegex = defaultMonthsShortRegex; + } + return this._monthsShortStrictRegex && isStrict ? + this._monthsShortStrictRegex : this._monthsShortRegex; + } +} + +var defaultMonthsRegex = matchWord; +function monthsRegex (isStrict) { + if (this._monthsParseExact) { + if (!hasOwnProp(this, '_monthsRegex')) { + computeMonthsParse.call(this); + } + if (isStrict) { + return this._monthsStrictRegex; + } else { + return this._monthsRegex; + } + } else { + if (!hasOwnProp(this, '_monthsRegex')) { + this._monthsRegex = defaultMonthsRegex; + } + return this._monthsStrictRegex && isStrict ? + this._monthsStrictRegex : this._monthsRegex; + } +} + +function computeMonthsParse () { + function cmpLenRev(a, b) { + return b.length - a.length; + } + + var shortPieces = [], longPieces = [], mixedPieces = [], + i, mom; + for (i = 0; i < 12; i++) { + // make the regex if we don't have it already + mom = createUTC([2000, i]); + shortPieces.push(this.monthsShort(mom, '')); + longPieces.push(this.months(mom, '')); + mixedPieces.push(this.months(mom, '')); + mixedPieces.push(this.monthsShort(mom, '')); + } + // Sorting makes sure if one month (or abbr) is a prefix of another it + // will match the longer piece. + shortPieces.sort(cmpLenRev); + longPieces.sort(cmpLenRev); + mixedPieces.sort(cmpLenRev); + for (i = 0; i < 12; i++) { + shortPieces[i] = regexEscape(shortPieces[i]); + longPieces[i] = regexEscape(longPieces[i]); + } + for (i = 0; i < 24; i++) { + mixedPieces[i] = regexEscape(mixedPieces[i]); + } + + this._monthsRegex = new RegExp('^(' + mixedPieces.join('|') + ')', 'i'); + this._monthsShortRegex = this._monthsRegex; + this._monthsStrictRegex = new RegExp('^(' + longPieces.join('|') + ')', 'i'); + this._monthsShortStrictRegex = new RegExp('^(' + shortPieces.join('|') + ')', 'i'); +} + +function createDate (y, m, d, h, M, s, ms) { + // can't just apply() to create a date: + // https://stackoverflow.com/q/181348 + var date = new Date(y, m, d, h, M, s, ms); + + // the date constructor remaps years 0-99 to 1900-1999 + if (y < 100 && y >= 0 && isFinite(date.getFullYear())) { + date.setFullYear(y); + } + return date; +} + +function createUTCDate (y) { + var date = new Date(Date.UTC.apply(null, arguments)); + + // the Date.UTC function remaps years 0-99 to 1900-1999 + if (y < 100 && y >= 0 && isFinite(date.getUTCFullYear())) { + date.setUTCFullYear(y); + } + return date; +} + +// start-of-first-week - start-of-year +function firstWeekOffset(year, dow, doy) { + var // first-week day -- which january is always in the first week (4 for iso, 1 for other) + fwd = 7 + dow - doy, + // first-week day local weekday -- which local weekday is fwd + fwdlw = (7 + createUTCDate(year, 0, fwd).getUTCDay() - dow) % 7; + + return -fwdlw + fwd - 1; +} + +// https://en.wikipedia.org/wiki/ISO_week_date#Calculating_a_date_given_the_year.2C_week_number_and_weekday +function dayOfYearFromWeeks(year, week, weekday, dow, doy) { + var localWeekday = (7 + weekday - dow) % 7, + weekOffset = firstWeekOffset(year, dow, doy), + dayOfYear = 1 + 7 * (week - 1) + localWeekday + weekOffset, + resYear, resDayOfYear; + + if (dayOfYear <= 0) { + resYear = year - 1; + resDayOfYear = daysInYear(resYear) + dayOfYear; + } else if (dayOfYear > daysInYear(year)) { + resYear = year + 1; + resDayOfYear = dayOfYear - daysInYear(year); + } else { + resYear = year; + resDayOfYear = dayOfYear; + } + + return { + year: resYear, + dayOfYear: resDayOfYear + }; +} + +function weekOfYear(mom, dow, doy) { + var weekOffset = firstWeekOffset(mom.year(), dow, doy), + week = Math.floor((mom.dayOfYear() - weekOffset - 1) / 7) + 1, + resWeek, resYear; + + if (week < 1) { + resYear = mom.year() - 1; + resWeek = week + weeksInYear(resYear, dow, doy); + } else if (week > weeksInYear(mom.year(), dow, doy)) { + resWeek = week - weeksInYear(mom.year(), dow, doy); + resYear = mom.year() + 1; + } else { + resYear = mom.year(); + resWeek = week; + } + + return { + week: resWeek, + year: resYear + }; +} + +function weeksInYear(year, dow, doy) { + var weekOffset = firstWeekOffset(year, dow, doy), + weekOffsetNext = firstWeekOffset(year + 1, dow, doy); + return (daysInYear(year) - weekOffset + weekOffsetNext) / 7; +} + +// FORMATTING + +addFormatToken('w', ['ww', 2], 'wo', 'week'); +addFormatToken('W', ['WW', 2], 'Wo', 'isoWeek'); + +// ALIASES + +addUnitAlias('week', 'w'); +addUnitAlias('isoWeek', 'W'); + +// PRIORITIES + +addUnitPriority('week', 5); +addUnitPriority('isoWeek', 5); + +// PARSING + +addRegexToken('w', match1to2); +addRegexToken('ww', match1to2, match2); +addRegexToken('W', match1to2); +addRegexToken('WW', match1to2, match2); + +addWeekParseToken(['w', 'ww', 'W', 'WW'], function (input, week, config, token) { + week[token.substr(0, 1)] = toInt(input); +}); + +// HELPERS + +// LOCALES + +function localeWeek (mom) { + return weekOfYear(mom, this._week.dow, this._week.doy).week; +} + +var defaultLocaleWeek = { + dow : 0, // Sunday is the first day of the week. + doy : 6 // The week that contains Jan 1st is the first week of the year. +}; + +function localeFirstDayOfWeek () { + return this._week.dow; +} + +function localeFirstDayOfYear () { + return this._week.doy; +} + +// MOMENTS + +function getSetWeek (input) { + var week = this.localeData().week(this); + return input == null ? week : this.add((input - week) * 7, 'd'); +} + +function getSetISOWeek (input) { + var week = weekOfYear(this, 1, 4).week; + return input == null ? week : this.add((input - week) * 7, 'd'); +} + +// FORMATTING + +addFormatToken('d', 0, 'do', 'day'); + +addFormatToken('dd', 0, 0, function (format) { + return this.localeData().weekdaysMin(this, format); +}); + +addFormatToken('ddd', 0, 0, function (format) { + return this.localeData().weekdaysShort(this, format); +}); + +addFormatToken('dddd', 0, 0, function (format) { + return this.localeData().weekdays(this, format); +}); + +addFormatToken('e', 0, 0, 'weekday'); +addFormatToken('E', 0, 0, 'isoWeekday'); + +// ALIASES + +addUnitAlias('day', 'd'); +addUnitAlias('weekday', 'e'); +addUnitAlias('isoWeekday', 'E'); + +// PRIORITY +addUnitPriority('day', 11); +addUnitPriority('weekday', 11); +addUnitPriority('isoWeekday', 11); + +// PARSING + +addRegexToken('d', match1to2); +addRegexToken('e', match1to2); +addRegexToken('E', match1to2); +addRegexToken('dd', function (isStrict, locale) { + return locale.weekdaysMinRegex(isStrict); +}); +addRegexToken('ddd', function (isStrict, locale) { + return locale.weekdaysShortRegex(isStrict); +}); +addRegexToken('dddd', function (isStrict, locale) { + return locale.weekdaysRegex(isStrict); +}); + +addWeekParseToken(['dd', 'ddd', 'dddd'], function (input, week, config, token) { + var weekday = config._locale.weekdaysParse(input, token, config._strict); + // if we didn't get a weekday name, mark the date as invalid + if (weekday != null) { + week.d = weekday; + } else { + getParsingFlags(config).invalidWeekday = input; + } +}); + +addWeekParseToken(['d', 'e', 'E'], function (input, week, config, token) { + week[token] = toInt(input); +}); + +// HELPERS + +function parseWeekday(input, locale) { + if (typeof input !== 'string') { + return input; + } + + if (!isNaN(input)) { + return parseInt(input, 10); + } + + input = locale.weekdaysParse(input); + if (typeof input === 'number') { + return input; + } + + return null; +} + +function parseIsoWeekday(input, locale) { + if (typeof input === 'string') { + return locale.weekdaysParse(input) % 7 || 7; + } + return isNaN(input) ? null : input; +} + +// LOCALES + +var defaultLocaleWeekdays = 'Sunday_Monday_Tuesday_Wednesday_Thursday_Friday_Saturday'.split('_'); +function localeWeekdays (m, format) { + if (!m) { + return isArray(this._weekdays) ? this._weekdays : + this._weekdays['standalone']; + } + return isArray(this._weekdays) ? this._weekdays[m.day()] : + this._weekdays[this._weekdays.isFormat.test(format) ? 'format' : 'standalone'][m.day()]; +} + +var defaultLocaleWeekdaysShort = 'Sun_Mon_Tue_Wed_Thu_Fri_Sat'.split('_'); +function localeWeekdaysShort (m) { + return (m) ? this._weekdaysShort[m.day()] : this._weekdaysShort; +} + +var defaultLocaleWeekdaysMin = 'Su_Mo_Tu_We_Th_Fr_Sa'.split('_'); +function localeWeekdaysMin (m) { + return (m) ? this._weekdaysMin[m.day()] : this._weekdaysMin; +} + +function handleStrictParse$1(weekdayName, format, strict) { + var i, ii, mom, llc = weekdayName.toLocaleLowerCase(); + if (!this._weekdaysParse) { + this._weekdaysParse = []; + this._shortWeekdaysParse = []; + this._minWeekdaysParse = []; + + for (i = 0; i < 7; ++i) { + mom = createUTC([2000, 1]).day(i); + this._minWeekdaysParse[i] = this.weekdaysMin(mom, '').toLocaleLowerCase(); + this._shortWeekdaysParse[i] = this.weekdaysShort(mom, '').toLocaleLowerCase(); + this._weekdaysParse[i] = this.weekdays(mom, '').toLocaleLowerCase(); + } + } + + if (strict) { + if (format === 'dddd') { + ii = indexOf.call(this._weekdaysParse, llc); + return ii !== -1 ? ii : null; + } else if (format === 'ddd') { + ii = indexOf.call(this._shortWeekdaysParse, llc); + return ii !== -1 ? ii : null; + } else { + ii = indexOf.call(this._minWeekdaysParse, llc); + return ii !== -1 ? ii : null; + } + } else { + if (format === 'dddd') { + ii = indexOf.call(this._weekdaysParse, llc); + if (ii !== -1) { + return ii; + } + ii = indexOf.call(this._shortWeekdaysParse, llc); + if (ii !== -1) { + return ii; + } + ii = indexOf.call(this._minWeekdaysParse, llc); + return ii !== -1 ? ii : null; + } else if (format === 'ddd') { + ii = indexOf.call(this._shortWeekdaysParse, llc); + if (ii !== -1) { + return ii; + } + ii = indexOf.call(this._weekdaysParse, llc); + if (ii !== -1) { + return ii; + } + ii = indexOf.call(this._minWeekdaysParse, llc); + return ii !== -1 ? ii : null; + } else { + ii = indexOf.call(this._minWeekdaysParse, llc); + if (ii !== -1) { + return ii; + } + ii = indexOf.call(this._weekdaysParse, llc); + if (ii !== -1) { + return ii; + } + ii = indexOf.call(this._shortWeekdaysParse, llc); + return ii !== -1 ? ii : null; + } + } +} + +function localeWeekdaysParse (weekdayName, format, strict) { + var i, mom, regex; + + if (this._weekdaysParseExact) { + return handleStrictParse$1.call(this, weekdayName, format, strict); + } + + if (!this._weekdaysParse) { + this._weekdaysParse = []; + this._minWeekdaysParse = []; + this._shortWeekdaysParse = []; + this._fullWeekdaysParse = []; + } + + for (i = 0; i < 7; i++) { + // make the regex if we don't have it already + + mom = createUTC([2000, 1]).day(i); + if (strict && !this._fullWeekdaysParse[i]) { + this._fullWeekdaysParse[i] = new RegExp('^' + this.weekdays(mom, '').replace('.', '\.?') + '$', 'i'); + this._shortWeekdaysParse[i] = new RegExp('^' + this.weekdaysShort(mom, '').replace('.', '\.?') + '$', 'i'); + this._minWeekdaysParse[i] = new RegExp('^' + this.weekdaysMin(mom, '').replace('.', '\.?') + '$', 'i'); + } + if (!this._weekdaysParse[i]) { + regex = '^' + this.weekdays(mom, '') + '|^' + this.weekdaysShort(mom, '') + '|^' + this.weekdaysMin(mom, ''); + this._weekdaysParse[i] = new RegExp(regex.replace('.', ''), 'i'); + } + // test the regex + if (strict && format === 'dddd' && this._fullWeekdaysParse[i].test(weekdayName)) { + return i; + } else if (strict && format === 'ddd' && this._shortWeekdaysParse[i].test(weekdayName)) { + return i; + } else if (strict && format === 'dd' && this._minWeekdaysParse[i].test(weekdayName)) { + return i; + } else if (!strict && this._weekdaysParse[i].test(weekdayName)) { + return i; + } + } +} + +// MOMENTS + +function getSetDayOfWeek (input) { + if (!this.isValid()) { + return input != null ? this : NaN; + } + var day = this._isUTC ? this._d.getUTCDay() : this._d.getDay(); + if (input != null) { + input = parseWeekday(input, this.localeData()); + return this.add(input - day, 'd'); + } else { + return day; + } +} + +function getSetLocaleDayOfWeek (input) { + if (!this.isValid()) { + return input != null ? this : NaN; + } + var weekday = (this.day() + 7 - this.localeData()._week.dow) % 7; + return input == null ? weekday : this.add(input - weekday, 'd'); +} + +function getSetISODayOfWeek (input) { + if (!this.isValid()) { + return input != null ? this : NaN; + } + + // behaves the same as moment#day except + // as a getter, returns 7 instead of 0 (1-7 range instead of 0-6) + // as a setter, sunday should belong to the previous week. + + if (input != null) { + var weekday = parseIsoWeekday(input, this.localeData()); + return this.day(this.day() % 7 ? weekday : weekday - 7); + } else { + return this.day() || 7; + } +} + +var defaultWeekdaysRegex = matchWord; +function weekdaysRegex (isStrict) { + if (this._weekdaysParseExact) { + if (!hasOwnProp(this, '_weekdaysRegex')) { + computeWeekdaysParse.call(this); + } + if (isStrict) { + return this._weekdaysStrictRegex; + } else { + return this._weekdaysRegex; + } + } else { + if (!hasOwnProp(this, '_weekdaysRegex')) { + this._weekdaysRegex = defaultWeekdaysRegex; + } + return this._weekdaysStrictRegex && isStrict ? + this._weekdaysStrictRegex : this._weekdaysRegex; + } +} + +var defaultWeekdaysShortRegex = matchWord; +function weekdaysShortRegex (isStrict) { + if (this._weekdaysParseExact) { + if (!hasOwnProp(this, '_weekdaysRegex')) { + computeWeekdaysParse.call(this); + } + if (isStrict) { + return this._weekdaysShortStrictRegex; + } else { + return this._weekdaysShortRegex; + } + } else { + if (!hasOwnProp(this, '_weekdaysShortRegex')) { + this._weekdaysShortRegex = defaultWeekdaysShortRegex; + } + return this._weekdaysShortStrictRegex && isStrict ? + this._weekdaysShortStrictRegex : this._weekdaysShortRegex; + } +} + +var defaultWeekdaysMinRegex = matchWord; +function weekdaysMinRegex (isStrict) { + if (this._weekdaysParseExact) { + if (!hasOwnProp(this, '_weekdaysRegex')) { + computeWeekdaysParse.call(this); + } + if (isStrict) { + return this._weekdaysMinStrictRegex; + } else { + return this._weekdaysMinRegex; + } + } else { + if (!hasOwnProp(this, '_weekdaysMinRegex')) { + this._weekdaysMinRegex = defaultWeekdaysMinRegex; + } + return this._weekdaysMinStrictRegex && isStrict ? + this._weekdaysMinStrictRegex : this._weekdaysMinRegex; + } +} + + +function computeWeekdaysParse () { + function cmpLenRev(a, b) { + return b.length - a.length; + } + + var minPieces = [], shortPieces = [], longPieces = [], mixedPieces = [], + i, mom, minp, shortp, longp; + for (i = 0; i < 7; i++) { + // make the regex if we don't have it already + mom = createUTC([2000, 1]).day(i); + minp = this.weekdaysMin(mom, ''); + shortp = this.weekdaysShort(mom, ''); + longp = this.weekdays(mom, ''); + minPieces.push(minp); + shortPieces.push(shortp); + longPieces.push(longp); + mixedPieces.push(minp); + mixedPieces.push(shortp); + mixedPieces.push(longp); + } + // Sorting makes sure if one weekday (or abbr) is a prefix of another it + // will match the longer piece. + minPieces.sort(cmpLenRev); + shortPieces.sort(cmpLenRev); + longPieces.sort(cmpLenRev); + mixedPieces.sort(cmpLenRev); + for (i = 0; i < 7; i++) { + shortPieces[i] = regexEscape(shortPieces[i]); + longPieces[i] = regexEscape(longPieces[i]); + mixedPieces[i] = regexEscape(mixedPieces[i]); + } + + this._weekdaysRegex = new RegExp('^(' + mixedPieces.join('|') + ')', 'i'); + this._weekdaysShortRegex = this._weekdaysRegex; + this._weekdaysMinRegex = this._weekdaysRegex; + + this._weekdaysStrictRegex = new RegExp('^(' + longPieces.join('|') + ')', 'i'); + this._weekdaysShortStrictRegex = new RegExp('^(' + shortPieces.join('|') + ')', 'i'); + this._weekdaysMinStrictRegex = new RegExp('^(' + minPieces.join('|') + ')', 'i'); +} + +// FORMATTING + +function hFormat() { + return this.hours() % 12 || 12; +} + +function kFormat() { + return this.hours() || 24; +} + +addFormatToken('H', ['HH', 2], 0, 'hour'); +addFormatToken('h', ['hh', 2], 0, hFormat); +addFormatToken('k', ['kk', 2], 0, kFormat); + +addFormatToken('hmm', 0, 0, function () { + return '' + hFormat.apply(this) + zeroFill(this.minutes(), 2); +}); + +addFormatToken('hmmss', 0, 0, function () { + return '' + hFormat.apply(this) + zeroFill(this.minutes(), 2) + + zeroFill(this.seconds(), 2); +}); + +addFormatToken('Hmm', 0, 0, function () { + return '' + this.hours() + zeroFill(this.minutes(), 2); +}); + +addFormatToken('Hmmss', 0, 0, function () { + return '' + this.hours() + zeroFill(this.minutes(), 2) + + zeroFill(this.seconds(), 2); +}); + +function meridiem (token, lowercase) { + addFormatToken(token, 0, 0, function () { + return this.localeData().meridiem(this.hours(), this.minutes(), lowercase); + }); +} + +meridiem('a', true); +meridiem('A', false); + +// ALIASES + +addUnitAlias('hour', 'h'); + +// PRIORITY +addUnitPriority('hour', 13); + +// PARSING + +function matchMeridiem (isStrict, locale) { + return locale._meridiemParse; +} + +addRegexToken('a', matchMeridiem); +addRegexToken('A', matchMeridiem); +addRegexToken('H', match1to2); +addRegexToken('h', match1to2); +addRegexToken('k', match1to2); +addRegexToken('HH', match1to2, match2); +addRegexToken('hh', match1to2, match2); +addRegexToken('kk', match1to2, match2); + +addRegexToken('hmm', match3to4); +addRegexToken('hmmss', match5to6); +addRegexToken('Hmm', match3to4); +addRegexToken('Hmmss', match5to6); + +addParseToken(['H', 'HH'], HOUR); +addParseToken(['k', 'kk'], function (input, array, config) { + var kInput = toInt(input); + array[HOUR] = kInput === 24 ? 0 : kInput; +}); +addParseToken(['a', 'A'], function (input, array, config) { + config._isPm = config._locale.isPM(input); + config._meridiem = input; +}); +addParseToken(['h', 'hh'], function (input, array, config) { + array[HOUR] = toInt(input); + getParsingFlags(config).bigHour = true; +}); +addParseToken('hmm', function (input, array, config) { + var pos = input.length - 2; + array[HOUR] = toInt(input.substr(0, pos)); + array[MINUTE] = toInt(input.substr(pos)); + getParsingFlags(config).bigHour = true; +}); +addParseToken('hmmss', function (input, array, config) { + var pos1 = input.length - 4; + var pos2 = input.length - 2; + array[HOUR] = toInt(input.substr(0, pos1)); + array[MINUTE] = toInt(input.substr(pos1, 2)); + array[SECOND] = toInt(input.substr(pos2)); + getParsingFlags(config).bigHour = true; +}); +addParseToken('Hmm', function (input, array, config) { + var pos = input.length - 2; + array[HOUR] = toInt(input.substr(0, pos)); + array[MINUTE] = toInt(input.substr(pos)); +}); +addParseToken('Hmmss', function (input, array, config) { + var pos1 = input.length - 4; + var pos2 = input.length - 2; + array[HOUR] = toInt(input.substr(0, pos1)); + array[MINUTE] = toInt(input.substr(pos1, 2)); + array[SECOND] = toInt(input.substr(pos2)); +}); + +// LOCALES + +function localeIsPM (input) { + // IE8 Quirks Mode & IE7 Standards Mode do not allow accessing strings like arrays + // Using charAt should be more compatible. + return ((input + '').toLowerCase().charAt(0) === 'p'); +} + +var defaultLocaleMeridiemParse = /[ap]\.?m?\.?/i; +function localeMeridiem (hours, minutes, isLower) { + if (hours > 11) { + return isLower ? 'pm' : 'PM'; + } else { + return isLower ? 'am' : 'AM'; + } +} + + +// MOMENTS + +// Setting the hour should keep the time, because the user explicitly +// specified which hour he wants. So trying to maintain the same hour (in +// a new timezone) makes sense. Adding/subtracting hours does not follow +// this rule. +var getSetHour = makeGetSet('Hours', true); + +// months +// week +// weekdays +// meridiem +var baseConfig = { + calendar: defaultCalendar, + longDateFormat: defaultLongDateFormat, + invalidDate: defaultInvalidDate, + ordinal: defaultOrdinal, + dayOfMonthOrdinalParse: defaultDayOfMonthOrdinalParse, + relativeTime: defaultRelativeTime, + + months: defaultLocaleMonths, + monthsShort: defaultLocaleMonthsShort, + + week: defaultLocaleWeek, + + weekdays: defaultLocaleWeekdays, + weekdaysMin: defaultLocaleWeekdaysMin, + weekdaysShort: defaultLocaleWeekdaysShort, + + meridiemParse: defaultLocaleMeridiemParse +}; + +// internal storage for locale config files +var locales = {}; +var localeFamilies = {}; +var globalLocale; + +function normalizeLocale(key) { + return key ? key.toLowerCase().replace('_', '-') : key; +} + +// pick the locale from the array +// try ['en-au', 'en-gb'] as 'en-au', 'en-gb', 'en', as in move through the list trying each +// substring from most specific to least, but move to the next array item if it's a more specific variant than the current root +function chooseLocale(names) { + var i = 0, j, next, locale, split; + + while (i < names.length) { + split = normalizeLocale(names[i]).split('-'); + j = split.length; + next = normalizeLocale(names[i + 1]); + next = next ? next.split('-') : null; + while (j > 0) { + locale = loadLocale(split.slice(0, j).join('-')); + if (locale) { + return locale; + } + if (next && next.length >= j && compareArrays(split, next, true) >= j - 1) { + //the next array item is better than a shallower substring of this one + break; + } + j--; + } + i++; + } + return null; +} + +function loadLocale(name) { + var oldLocale = null; + // TODO: Find a better way to register and load all the locales in Node + if (!locales[name] && (typeof module !== 'undefined') && + module && module.exports) { + try { + oldLocale = globalLocale._abbr; + var aliasedRequire = require; + aliasedRequire('./locale/' + name); + getSetGlobalLocale(oldLocale); + } catch (e) {} + } + return locales[name]; +} + +// This function will load locale and then set the global locale. If +// no arguments are passed in, it will simply return the current global +// locale key. +function getSetGlobalLocale (key, values) { + var data; + if (key) { + if (isUndefined(values)) { + data = getLocale(key); + } + else { + data = defineLocale(key, values); + } + + if (data) { + // moment.duration._locale = moment._locale = data; + globalLocale = data; + } + } + + return globalLocale._abbr; +} + +function defineLocale (name, config) { + if (config !== null) { + var parentConfig = baseConfig; + config.abbr = name; + if (locales[name] != null) { + deprecateSimple('defineLocaleOverride', + 'use moment.updateLocale(localeName, config) to change ' + + 'an existing locale. moment.defineLocale(localeName, ' + + 'config) should only be used for creating a new locale ' + + 'See http://momentjs.com/guides/#/warnings/define-locale/ for more info.'); + parentConfig = locales[name]._config; + } else if (config.parentLocale != null) { + if (locales[config.parentLocale] != null) { + parentConfig = locales[config.parentLocale]._config; + } else { + if (!localeFamilies[config.parentLocale]) { + localeFamilies[config.parentLocale] = []; + } + localeFamilies[config.parentLocale].push({ + name: name, + config: config + }); + return null; + } + } + locales[name] = new Locale(mergeConfigs(parentConfig, config)); + + if (localeFamilies[name]) { + localeFamilies[name].forEach(function (x) { + defineLocale(x.name, x.config); + }); + } + + // backwards compat for now: also set the locale + // make sure we set the locale AFTER all child locales have been + // created, so we won't end up with the child locale set. + getSetGlobalLocale(name); + + + return locales[name]; + } else { + // useful for testing + delete locales[name]; + return null; + } +} + +function updateLocale(name, config) { + if (config != null) { + var locale, tmpLocale, parentConfig = baseConfig; + // MERGE + tmpLocale = loadLocale(name); + if (tmpLocale != null) { + parentConfig = tmpLocale._config; + } + config = mergeConfigs(parentConfig, config); + locale = new Locale(config); + locale.parentLocale = locales[name]; + locales[name] = locale; + + // backwards compat for now: also set the locale + getSetGlobalLocale(name); + } else { + // pass null for config to unupdate, useful for tests + if (locales[name] != null) { + if (locales[name].parentLocale != null) { + locales[name] = locales[name].parentLocale; + } else if (locales[name] != null) { + delete locales[name]; + } + } + } + return locales[name]; +} + +// returns locale data +function getLocale (key) { + var locale; + + if (key && key._locale && key._locale._abbr) { + key = key._locale._abbr; + } + + if (!key) { + return globalLocale; + } + + if (!isArray(key)) { + //short-circuit everything else + locale = loadLocale(key); + if (locale) { + return locale; + } + key = [key]; + } + + return chooseLocale(key); +} + +function listLocales() { + return keys(locales); +} + +function checkOverflow (m) { + var overflow; + var a = m._a; + + if (a && getParsingFlags(m).overflow === -2) { + overflow = + a[MONTH] < 0 || a[MONTH] > 11 ? MONTH : + a[DATE] < 1 || a[DATE] > daysInMonth(a[YEAR], a[MONTH]) ? DATE : + a[HOUR] < 0 || a[HOUR] > 24 || (a[HOUR] === 24 && (a[MINUTE] !== 0 || a[SECOND] !== 0 || a[MILLISECOND] !== 0)) ? HOUR : + a[MINUTE] < 0 || a[MINUTE] > 59 ? MINUTE : + a[SECOND] < 0 || a[SECOND] > 59 ? SECOND : + a[MILLISECOND] < 0 || a[MILLISECOND] > 999 ? MILLISECOND : + -1; + + if (getParsingFlags(m)._overflowDayOfYear && (overflow < YEAR || overflow > DATE)) { + overflow = DATE; + } + if (getParsingFlags(m)._overflowWeeks && overflow === -1) { + overflow = WEEK; + } + if (getParsingFlags(m)._overflowWeekday && overflow === -1) { + overflow = WEEKDAY; + } + + getParsingFlags(m).overflow = overflow; + } + + return m; +} + +// Pick the first defined of two or three arguments. +function defaults(a, b, c) { + if (a != null) { + return a; + } + if (b != null) { + return b; + } + return c; +} + +function currentDateArray(config) { + // hooks is actually the exported moment object + var nowValue = new Date(hooks.now()); + if (config._useUTC) { + return [nowValue.getUTCFullYear(), nowValue.getUTCMonth(), nowValue.getUTCDate()]; + } + return [nowValue.getFullYear(), nowValue.getMonth(), nowValue.getDate()]; +} + +// convert an array to a date. +// the array should mirror the parameters below +// note: all values past the year are optional and will default to the lowest possible value. +// [year, month, day , hour, minute, second, millisecond] +function configFromArray (config) { + var i, date, input = [], currentDate, expectedWeekday, yearToUse; + + if (config._d) { + return; + } + + currentDate = currentDateArray(config); + + //compute day of the year from weeks and weekdays + if (config._w && config._a[DATE] == null && config._a[MONTH] == null) { + dayOfYearFromWeekInfo(config); + } + + //if the day of the year is set, figure out what it is + if (config._dayOfYear != null) { + yearToUse = defaults(config._a[YEAR], currentDate[YEAR]); + + if (config._dayOfYear > daysInYear(yearToUse) || config._dayOfYear === 0) { + getParsingFlags(config)._overflowDayOfYear = true; + } + + date = createUTCDate(yearToUse, 0, config._dayOfYear); + config._a[MONTH] = date.getUTCMonth(); + config._a[DATE] = date.getUTCDate(); + } + + // Default to current date. + // * if no year, month, day of month are given, default to today + // * if day of month is given, default month and year + // * if month is given, default only year + // * if year is given, don't default anything + for (i = 0; i < 3 && config._a[i] == null; ++i) { + config._a[i] = input[i] = currentDate[i]; + } + + // Zero out whatever was not defaulted, including time + for (; i < 7; i++) { + config._a[i] = input[i] = (config._a[i] == null) ? (i === 2 ? 1 : 0) : config._a[i]; + } + + // Check for 24:00:00.000 + if (config._a[HOUR] === 24 && + config._a[MINUTE] === 0 && + config._a[SECOND] === 0 && + config._a[MILLISECOND] === 0) { + config._nextDay = true; + config._a[HOUR] = 0; + } + + config._d = (config._useUTC ? createUTCDate : createDate).apply(null, input); + expectedWeekday = config._useUTC ? config._d.getUTCDay() : config._d.getDay(); + + // Apply timezone offset from input. The actual utcOffset can be changed + // with parseZone. + if (config._tzm != null) { + config._d.setUTCMinutes(config._d.getUTCMinutes() - config._tzm); + } + + if (config._nextDay) { + config._a[HOUR] = 24; + } + + // check for mismatching day of week + if (config._w && typeof config._w.d !== 'undefined' && config._w.d !== expectedWeekday) { + getParsingFlags(config).weekdayMismatch = true; + } +} + +function dayOfYearFromWeekInfo(config) { + var w, weekYear, week, weekday, dow, doy, temp, weekdayOverflow; + + w = config._w; + if (w.GG != null || w.W != null || w.E != null) { + dow = 1; + doy = 4; + + // TODO: We need to take the current isoWeekYear, but that depends on + // how we interpret now (local, utc, fixed offset). So create + // a now version of current config (take local/utc/offset flags, and + // create now). + weekYear = defaults(w.GG, config._a[YEAR], weekOfYear(createLocal(), 1, 4).year); + week = defaults(w.W, 1); + weekday = defaults(w.E, 1); + if (weekday < 1 || weekday > 7) { + weekdayOverflow = true; + } + } else { + dow = config._locale._week.dow; + doy = config._locale._week.doy; + + var curWeek = weekOfYear(createLocal(), dow, doy); + + weekYear = defaults(w.gg, config._a[YEAR], curWeek.year); + + // Default to current week. + week = defaults(w.w, curWeek.week); + + if (w.d != null) { + // weekday -- low day numbers are considered next week + weekday = w.d; + if (weekday < 0 || weekday > 6) { + weekdayOverflow = true; + } + } else if (w.e != null) { + // local weekday -- counting starts from begining of week + weekday = w.e + dow; + if (w.e < 0 || w.e > 6) { + weekdayOverflow = true; + } + } else { + // default to begining of week + weekday = dow; + } + } + if (week < 1 || week > weeksInYear(weekYear, dow, doy)) { + getParsingFlags(config)._overflowWeeks = true; + } else if (weekdayOverflow != null) { + getParsingFlags(config)._overflowWeekday = true; + } else { + temp = dayOfYearFromWeeks(weekYear, week, weekday, dow, doy); + config._a[YEAR] = temp.year; + config._dayOfYear = temp.dayOfYear; + } +} + +// iso 8601 regex +// 0000-00-00 0000-W00 or 0000-W00-0 + T + 00 or 00:00 or 00:00:00 or 00:00:00.000 + +00:00 or +0000 or +00) +var extendedIsoRegex = /^\s*((?:[+-]\d{6}|\d{4})-(?:\d\d-\d\d|W\d\d-\d|W\d\d|\d\d\d|\d\d))(?:(T| )(\d\d(?::\d\d(?::\d\d(?:[.,]\d+)?)?)?)([\+\-]\d\d(?::?\d\d)?|\s*Z)?)?$/; +var basicIsoRegex = /^\s*((?:[+-]\d{6}|\d{4})(?:\d\d\d\d|W\d\d\d|W\d\d|\d\d\d|\d\d))(?:(T| )(\d\d(?:\d\d(?:\d\d(?:[.,]\d+)?)?)?)([\+\-]\d\d(?::?\d\d)?|\s*Z)?)?$/; + +var tzRegex = /Z|[+-]\d\d(?::?\d\d)?/; + +var isoDates = [ + ['YYYYYY-MM-DD', /[+-]\d{6}-\d\d-\d\d/], + ['YYYY-MM-DD', /\d{4}-\d\d-\d\d/], + ['GGGG-[W]WW-E', /\d{4}-W\d\d-\d/], + ['GGGG-[W]WW', /\d{4}-W\d\d/, false], + ['YYYY-DDD', /\d{4}-\d{3}/], + ['YYYY-MM', /\d{4}-\d\d/, false], + ['YYYYYYMMDD', /[+-]\d{10}/], + ['YYYYMMDD', /\d{8}/], + // YYYYMM is NOT allowed by the standard + ['GGGG[W]WWE', /\d{4}W\d{3}/], + ['GGGG[W]WW', /\d{4}W\d{2}/, false], + ['YYYYDDD', /\d{7}/] +]; + +// iso time formats and regexes +var isoTimes = [ + ['HH:mm:ss.SSSS', /\d\d:\d\d:\d\d\.\d+/], + ['HH:mm:ss,SSSS', /\d\d:\d\d:\d\d,\d+/], + ['HH:mm:ss', /\d\d:\d\d:\d\d/], + ['HH:mm', /\d\d:\d\d/], + ['HHmmss.SSSS', /\d\d\d\d\d\d\.\d+/], + ['HHmmss,SSSS', /\d\d\d\d\d\d,\d+/], + ['HHmmss', /\d\d\d\d\d\d/], + ['HHmm', /\d\d\d\d/], + ['HH', /\d\d/] +]; + +var aspNetJsonRegex = /^\/?Date\((\-?\d+)/i; + +// date from iso format +function configFromISO(config) { + var i, l, + string = config._i, + match = extendedIsoRegex.exec(string) || basicIsoRegex.exec(string), + allowTime, dateFormat, timeFormat, tzFormat; + + if (match) { + getParsingFlags(config).iso = true; + + for (i = 0, l = isoDates.length; i < l; i++) { + if (isoDates[i][1].exec(match[1])) { + dateFormat = isoDates[i][0]; + allowTime = isoDates[i][2] !== false; + break; + } + } + if (dateFormat == null) { + config._isValid = false; + return; + } + if (match[3]) { + for (i = 0, l = isoTimes.length; i < l; i++) { + if (isoTimes[i][1].exec(match[3])) { + // match[2] should be 'T' or space + timeFormat = (match[2] || ' ') + isoTimes[i][0]; + break; + } + } + if (timeFormat == null) { + config._isValid = false; + return; + } + } + if (!allowTime && timeFormat != null) { + config._isValid = false; + return; + } + if (match[4]) { + if (tzRegex.exec(match[4])) { + tzFormat = 'Z'; + } else { + config._isValid = false; + return; + } + } + config._f = dateFormat + (timeFormat || '') + (tzFormat || ''); + configFromStringAndFormat(config); + } else { + config._isValid = false; + } +} + +// RFC 2822 regex: For details see https://tools.ietf.org/html/rfc2822#section-3.3 +var rfc2822 = /^(?:(Mon|Tue|Wed|Thu|Fri|Sat|Sun),?\s)?(\d{1,2})\s(Jan|Feb|Mar|Apr|May|Jun|Jul|Aug|Sep|Oct|Nov|Dec)\s(\d{2,4})\s(\d\d):(\d\d)(?::(\d\d))?\s(?:(UT|GMT|[ECMP][SD]T)|([Zz])|([+-]\d{4}))$/; + +function extractFromRFC2822Strings(yearStr, monthStr, dayStr, hourStr, minuteStr, secondStr) { + var result = [ + untruncateYear(yearStr), + defaultLocaleMonthsShort.indexOf(monthStr), + parseInt(dayStr, 10), + parseInt(hourStr, 10), + parseInt(minuteStr, 10) + ]; + + if (secondStr) { + result.push(parseInt(secondStr, 10)); + } + + return result; +} + +function untruncateYear(yearStr) { + var year = parseInt(yearStr, 10); + if (year <= 49) { + return 2000 + year; + } else if (year <= 999) { + return 1900 + year; + } + return year; +} + +function preprocessRFC2822(s) { + // Remove comments and folding whitespace and replace multiple-spaces with a single space + return s.replace(/\([^)]*\)|[\n\t]/g, ' ').replace(/(\s\s+)/g, ' ').trim(); +} + +function checkWeekday(weekdayStr, parsedInput, config) { + if (weekdayStr) { + // TODO: Replace the vanilla JS Date object with an indepentent day-of-week check. + var weekdayProvided = defaultLocaleWeekdaysShort.indexOf(weekdayStr), + weekdayActual = new Date(parsedInput[0], parsedInput[1], parsedInput[2]).getDay(); + if (weekdayProvided !== weekdayActual) { + getParsingFlags(config).weekdayMismatch = true; + config._isValid = false; + return false; + } + } + return true; +} + +var obsOffsets = { + UT: 0, + GMT: 0, + EDT: -4 * 60, + EST: -5 * 60, + CDT: -5 * 60, + CST: -6 * 60, + MDT: -6 * 60, + MST: -7 * 60, + PDT: -7 * 60, + PST: -8 * 60 +}; + +function calculateOffset(obsOffset, militaryOffset, numOffset) { + if (obsOffset) { + return obsOffsets[obsOffset]; + } else if (militaryOffset) { + // the only allowed military tz is Z + return 0; + } else { + var hm = parseInt(numOffset, 10); + var m = hm % 100, h = (hm - m) / 100; + return h * 60 + m; + } +} + +// date and time from ref 2822 format +function configFromRFC2822(config) { + var match = rfc2822.exec(preprocessRFC2822(config._i)); + if (match) { + var parsedArray = extractFromRFC2822Strings(match[4], match[3], match[2], match[5], match[6], match[7]); + if (!checkWeekday(match[1], parsedArray, config)) { + return; + } + + config._a = parsedArray; + config._tzm = calculateOffset(match[8], match[9], match[10]); + + config._d = createUTCDate.apply(null, config._a); + config._d.setUTCMinutes(config._d.getUTCMinutes() - config._tzm); + + getParsingFlags(config).rfc2822 = true; + } else { + config._isValid = false; + } +} + +// date from iso format or fallback +function configFromString(config) { + var matched = aspNetJsonRegex.exec(config._i); + + if (matched !== null) { + config._d = new Date(+matched[1]); + return; + } + + configFromISO(config); + if (config._isValid === false) { + delete config._isValid; + } else { + return; + } + + configFromRFC2822(config); + if (config._isValid === false) { + delete config._isValid; + } else { + return; + } + + // Final attempt, use Input Fallback + hooks.createFromInputFallback(config); +} + +hooks.createFromInputFallback = deprecate( + 'value provided is not in a recognized RFC2822 or ISO format. moment construction falls back to js Date(), ' + + 'which is not reliable across all browsers and versions. Non RFC2822/ISO date formats are ' + + 'discouraged and will be removed in an upcoming major release. Please refer to ' + + 'http://momentjs.com/guides/#/warnings/js-date/ for more info.', + function (config) { + config._d = new Date(config._i + (config._useUTC ? ' UTC' : '')); + } +); + +// constant that refers to the ISO standard +hooks.ISO_8601 = function () {}; + +// constant that refers to the RFC 2822 form +hooks.RFC_2822 = function () {}; + +// date from string and format string +function configFromStringAndFormat(config) { + // TODO: Move this to another part of the creation flow to prevent circular deps + if (config._f === hooks.ISO_8601) { + configFromISO(config); + return; + } + if (config._f === hooks.RFC_2822) { + configFromRFC2822(config); + return; + } + config._a = []; + getParsingFlags(config).empty = true; + + // This array is used to make a Date, either with `new Date` or `Date.UTC` + var string = '' + config._i, + i, parsedInput, tokens, token, skipped, + stringLength = string.length, + totalParsedInputLength = 0; + + tokens = expandFormat(config._f, config._locale).match(formattingTokens) || []; + + for (i = 0; i < tokens.length; i++) { + token = tokens[i]; + parsedInput = (string.match(getParseRegexForToken(token, config)) || [])[0]; + // console.log('token', token, 'parsedInput', parsedInput, + // 'regex', getParseRegexForToken(token, config)); + if (parsedInput) { + skipped = string.substr(0, string.indexOf(parsedInput)); + if (skipped.length > 0) { + getParsingFlags(config).unusedInput.push(skipped); + } + string = string.slice(string.indexOf(parsedInput) + parsedInput.length); + totalParsedInputLength += parsedInput.length; + } + // don't parse if it's not a known token + if (formatTokenFunctions[token]) { + if (parsedInput) { + getParsingFlags(config).empty = false; + } + else { + getParsingFlags(config).unusedTokens.push(token); + } + addTimeToArrayFromToken(token, parsedInput, config); + } + else if (config._strict && !parsedInput) { + getParsingFlags(config).unusedTokens.push(token); + } + } + + // add remaining unparsed input length to the string + getParsingFlags(config).charsLeftOver = stringLength - totalParsedInputLength; + if (string.length > 0) { + getParsingFlags(config).unusedInput.push(string); + } + + // clear _12h flag if hour is <= 12 + if (config._a[HOUR] <= 12 && + getParsingFlags(config).bigHour === true && + config._a[HOUR] > 0) { + getParsingFlags(config).bigHour = undefined; + } + + getParsingFlags(config).parsedDateParts = config._a.slice(0); + getParsingFlags(config).meridiem = config._meridiem; + // handle meridiem + config._a[HOUR] = meridiemFixWrap(config._locale, config._a[HOUR], config._meridiem); + + configFromArray(config); + checkOverflow(config); +} + + +function meridiemFixWrap (locale, hour, meridiem) { + var isPm; + + if (meridiem == null) { + // nothing to do + return hour; + } + if (locale.meridiemHour != null) { + return locale.meridiemHour(hour, meridiem); + } else if (locale.isPM != null) { + // Fallback + isPm = locale.isPM(meridiem); + if (isPm && hour < 12) { + hour += 12; + } + if (!isPm && hour === 12) { + hour = 0; + } + return hour; + } else { + // this is not supposed to happen + return hour; + } +} + +// date from string and array of format strings +function configFromStringAndArray(config) { + var tempConfig, + bestMoment, + + scoreToBeat, + i, + currentScore; + + if (config._f.length === 0) { + getParsingFlags(config).invalidFormat = true; + config._d = new Date(NaN); + return; + } + + for (i = 0; i < config._f.length; i++) { + currentScore = 0; + tempConfig = copyConfig({}, config); + if (config._useUTC != null) { + tempConfig._useUTC = config._useUTC; + } + tempConfig._f = config._f[i]; + configFromStringAndFormat(tempConfig); + + if (!isValid(tempConfig)) { + continue; + } + + // if there is any input that was not parsed add a penalty for that format + currentScore += getParsingFlags(tempConfig).charsLeftOver; + + //or tokens + currentScore += getParsingFlags(tempConfig).unusedTokens.length * 10; + + getParsingFlags(tempConfig).score = currentScore; + + if (scoreToBeat == null || currentScore < scoreToBeat) { + scoreToBeat = currentScore; + bestMoment = tempConfig; + } + } + + extend(config, bestMoment || tempConfig); +} + +function configFromObject(config) { + if (config._d) { + return; + } + + var i = normalizeObjectUnits(config._i); + config._a = map([i.year, i.month, i.day || i.date, i.hour, i.minute, i.second, i.millisecond], function (obj) { + return obj && parseInt(obj, 10); + }); + + configFromArray(config); +} + +function createFromConfig (config) { + var res = new Moment(checkOverflow(prepareConfig(config))); + if (res._nextDay) { + // Adding is smart enough around DST + res.add(1, 'd'); + res._nextDay = undefined; + } + + return res; +} + +function prepareConfig (config) { + var input = config._i, + format = config._f; + + config._locale = config._locale || getLocale(config._l); + + if (input === null || (format === undefined && input === '')) { + return createInvalid({nullInput: true}); + } + + if (typeof input === 'string') { + config._i = input = config._locale.preparse(input); + } + + if (isMoment(input)) { + return new Moment(checkOverflow(input)); + } else if (isDate(input)) { + config._d = input; + } else if (isArray(format)) { + configFromStringAndArray(config); + } else if (format) { + configFromStringAndFormat(config); + } else { + configFromInput(config); + } + + if (!isValid(config)) { + config._d = null; + } + + return config; +} + +function configFromInput(config) { + var input = config._i; + if (isUndefined(input)) { + config._d = new Date(hooks.now()); + } else if (isDate(input)) { + config._d = new Date(input.valueOf()); + } else if (typeof input === 'string') { + configFromString(config); + } else if (isArray(input)) { + config._a = map(input.slice(0), function (obj) { + return parseInt(obj, 10); + }); + configFromArray(config); + } else if (isObject(input)) { + configFromObject(config); + } else if (isNumber(input)) { + // from milliseconds + config._d = new Date(input); + } else { + hooks.createFromInputFallback(config); + } +} + +function createLocalOrUTC (input, format, locale, strict, isUTC) { + var c = {}; + + if (locale === true || locale === false) { + strict = locale; + locale = undefined; + } + + if ((isObject(input) && isObjectEmpty(input)) || + (isArray(input) && input.length === 0)) { + input = undefined; + } + // object construction must be done this way. + // https://github.com/moment/moment/issues/1423 + c._isAMomentObject = true; + c._useUTC = c._isUTC = isUTC; + c._l = locale; + c._i = input; + c._f = format; + c._strict = strict; + + return createFromConfig(c); +} + +function createLocal (input, format, locale, strict) { + return createLocalOrUTC(input, format, locale, strict, false); +} + +var prototypeMin = deprecate( + 'moment().min is deprecated, use moment.max instead. http://momentjs.com/guides/#/warnings/min-max/', + function () { + var other = createLocal.apply(null, arguments); + if (this.isValid() && other.isValid()) { + return other < this ? this : other; + } else { + return createInvalid(); + } + } +); + +var prototypeMax = deprecate( + 'moment().max is deprecated, use moment.min instead. http://momentjs.com/guides/#/warnings/min-max/', + function () { + var other = createLocal.apply(null, arguments); + if (this.isValid() && other.isValid()) { + return other > this ? this : other; + } else { + return createInvalid(); + } + } +); + +// Pick a moment m from moments so that m[fn](other) is true for all +// other. This relies on the function fn to be transitive. +// +// moments should either be an array of moment objects or an array, whose +// first element is an array of moment objects. +function pickBy(fn, moments) { + var res, i; + if (moments.length === 1 && isArray(moments[0])) { + moments = moments[0]; + } + if (!moments.length) { + return createLocal(); + } + res = moments[0]; + for (i = 1; i < moments.length; ++i) { + if (!moments[i].isValid() || moments[i][fn](res)) { + res = moments[i]; + } + } + return res; +} + +// TODO: Use [].sort instead? +function min () { + var args = [].slice.call(arguments, 0); + + return pickBy('isBefore', args); +} + +function max () { + var args = [].slice.call(arguments, 0); + + return pickBy('isAfter', args); +} + +var now = function () { + return Date.now ? Date.now() : +(new Date()); +}; + +var ordering = ['year', 'quarter', 'month', 'week', 'day', 'hour', 'minute', 'second', 'millisecond']; + +function isDurationValid(m) { + for (var key in m) { + if (!(indexOf.call(ordering, key) !== -1 && (m[key] == null || !isNaN(m[key])))) { + return false; + } + } + + var unitHasDecimal = false; + for (var i = 0; i < ordering.length; ++i) { + if (m[ordering[i]]) { + if (unitHasDecimal) { + return false; // only allow non-integers for smallest unit + } + if (parseFloat(m[ordering[i]]) !== toInt(m[ordering[i]])) { + unitHasDecimal = true; + } + } + } + + return true; +} + +function isValid$1() { + return this._isValid; +} + +function createInvalid$1() { + return createDuration(NaN); +} + +function Duration (duration) { + var normalizedInput = normalizeObjectUnits(duration), + years = normalizedInput.year || 0, + quarters = normalizedInput.quarter || 0, + months = normalizedInput.month || 0, + weeks = normalizedInput.week || 0, + days = normalizedInput.day || 0, + hours = normalizedInput.hour || 0, + minutes = normalizedInput.minute || 0, + seconds = normalizedInput.second || 0, + milliseconds = normalizedInput.millisecond || 0; + + this._isValid = isDurationValid(normalizedInput); + + // representation for dateAddRemove + this._milliseconds = +milliseconds + + seconds * 1e3 + // 1000 + minutes * 6e4 + // 1000 * 60 + hours * 1000 * 60 * 60; //using 1000 * 60 * 60 instead of 36e5 to avoid floating point rounding errors https://github.com/moment/moment/issues/2978 + // Because of dateAddRemove treats 24 hours as different from a + // day when working around DST, we need to store them separately + this._days = +days + + weeks * 7; + // It is impossible to translate months into days without knowing + // which months you are are talking about, so we have to store + // it separately. + this._months = +months + + quarters * 3 + + years * 12; + + this._data = {}; + + this._locale = getLocale(); + + this._bubble(); +} + +function isDuration (obj) { + return obj instanceof Duration; +} + +function absRound (number) { + if (number < 0) { + return Math.round(-1 * number) * -1; + } else { + return Math.round(number); + } +} + +// FORMATTING + +function offset (token, separator) { + addFormatToken(token, 0, 0, function () { + var offset = this.utcOffset(); + var sign = '+'; + if (offset < 0) { + offset = -offset; + sign = '-'; + } + return sign + zeroFill(~~(offset / 60), 2) + separator + zeroFill(~~(offset) % 60, 2); + }); +} + +offset('Z', ':'); +offset('ZZ', ''); + +// PARSING + +addRegexToken('Z', matchShortOffset); +addRegexToken('ZZ', matchShortOffset); +addParseToken(['Z', 'ZZ'], function (input, array, config) { + config._useUTC = true; + config._tzm = offsetFromString(matchShortOffset, input); +}); + +// HELPERS + +// timezone chunker +// '+10:00' > ['10', '00'] +// '-1530' > ['-15', '30'] +var chunkOffset = /([\+\-]|\d\d)/gi; + +function offsetFromString(matcher, string) { + var matches = (string || '').match(matcher); + + if (matches === null) { + return null; + } + + var chunk = matches[matches.length - 1] || []; + var parts = (chunk + '').match(chunkOffset) || ['-', 0, 0]; + var minutes = +(parts[1] * 60) + toInt(parts[2]); + + return minutes === 0 ? + 0 : + parts[0] === '+' ? minutes : -minutes; +} + +// Return a moment from input, that is local/utc/zone equivalent to model. +function cloneWithOffset(input, model) { + var res, diff; + if (model._isUTC) { + res = model.clone(); + diff = (isMoment(input) || isDate(input) ? input.valueOf() : createLocal(input).valueOf()) - res.valueOf(); + // Use low-level api, because this fn is low-level api. + res._d.setTime(res._d.valueOf() + diff); + hooks.updateOffset(res, false); + return res; + } else { + return createLocal(input).local(); + } +} + +function getDateOffset (m) { + // On Firefox.24 Date#getTimezoneOffset returns a floating point. + // https://github.com/moment/moment/pull/1871 + return -Math.round(m._d.getTimezoneOffset() / 15) * 15; +} + +// HOOKS + +// This function will be called whenever a moment is mutated. +// It is intended to keep the offset in sync with the timezone. +hooks.updateOffset = function () {}; + +// MOMENTS + +// keepLocalTime = true means only change the timezone, without +// affecting the local hour. So 5:31:26 +0300 --[utcOffset(2, true)]--> +// 5:31:26 +0200 It is possible that 5:31:26 doesn't exist with offset +// +0200, so we adjust the time as needed, to be valid. +// +// Keeping the time actually adds/subtracts (one hour) +// from the actual represented time. That is why we call updateOffset +// a second time. In case it wants us to change the offset again +// _changeInProgress == true case, then we have to adjust, because +// there is no such time in the given timezone. +function getSetOffset (input, keepLocalTime, keepMinutes) { + var offset = this._offset || 0, + localAdjust; + if (!this.isValid()) { + return input != null ? this : NaN; + } + if (input != null) { + if (typeof input === 'string') { + input = offsetFromString(matchShortOffset, input); + if (input === null) { + return this; + } + } else if (Math.abs(input) < 16 && !keepMinutes) { + input = input * 60; + } + if (!this._isUTC && keepLocalTime) { + localAdjust = getDateOffset(this); + } + this._offset = input; + this._isUTC = true; + if (localAdjust != null) { + this.add(localAdjust, 'm'); + } + if (offset !== input) { + if (!keepLocalTime || this._changeInProgress) { + addSubtract(this, createDuration(input - offset, 'm'), 1, false); + } else if (!this._changeInProgress) { + this._changeInProgress = true; + hooks.updateOffset(this, true); + this._changeInProgress = null; + } + } + return this; + } else { + return this._isUTC ? offset : getDateOffset(this); + } +} + +function getSetZone (input, keepLocalTime) { + if (input != null) { + if (typeof input !== 'string') { + input = -input; + } + + this.utcOffset(input, keepLocalTime); + + return this; + } else { + return -this.utcOffset(); + } +} + +function setOffsetToUTC (keepLocalTime) { + return this.utcOffset(0, keepLocalTime); +} + +function setOffsetToLocal (keepLocalTime) { + if (this._isUTC) { + this.utcOffset(0, keepLocalTime); + this._isUTC = false; + + if (keepLocalTime) { + this.subtract(getDateOffset(this), 'm'); + } + } + return this; +} + +function setOffsetToParsedOffset () { + if (this._tzm != null) { + this.utcOffset(this._tzm, false, true); + } else if (typeof this._i === 'string') { + var tZone = offsetFromString(matchOffset, this._i); + if (tZone != null) { + this.utcOffset(tZone); + } + else { + this.utcOffset(0, true); + } + } + return this; +} + +function hasAlignedHourOffset (input) { + if (!this.isValid()) { + return false; + } + input = input ? createLocal(input).utcOffset() : 0; + + return (this.utcOffset() - input) % 60 === 0; +} + +function isDaylightSavingTime () { + return ( + this.utcOffset() > this.clone().month(0).utcOffset() || + this.utcOffset() > this.clone().month(5).utcOffset() + ); +} + +function isDaylightSavingTimeShifted () { + if (!isUndefined(this._isDSTShifted)) { + return this._isDSTShifted; + } + + var c = {}; + + copyConfig(c, this); + c = prepareConfig(c); + + if (c._a) { + var other = c._isUTC ? createUTC(c._a) : createLocal(c._a); + this._isDSTShifted = this.isValid() && + compareArrays(c._a, other.toArray()) > 0; + } else { + this._isDSTShifted = false; + } + + return this._isDSTShifted; +} + +function isLocal () { + return this.isValid() ? !this._isUTC : false; +} + +function isUtcOffset () { + return this.isValid() ? this._isUTC : false; +} + +function isUtc () { + return this.isValid() ? this._isUTC && this._offset === 0 : false; +} + +// ASP.NET json date format regex +var aspNetRegex = /^(\-|\+)?(?:(\d*)[. ])?(\d+)\:(\d+)(?:\:(\d+)(\.\d*)?)?$/; + +// from http://docs.closure-library.googlecode.com/git/closure_goog_date_date.js.source.html +// somewhat more in line with 4.4.3.2 2004 spec, but allows decimal anywhere +// and further modified to allow for strings containing both week and day +var isoRegex = /^(-|\+)?P(?:([-+]?[0-9,.]*)Y)?(?:([-+]?[0-9,.]*)M)?(?:([-+]?[0-9,.]*)W)?(?:([-+]?[0-9,.]*)D)?(?:T(?:([-+]?[0-9,.]*)H)?(?:([-+]?[0-9,.]*)M)?(?:([-+]?[0-9,.]*)S)?)?$/; + +function createDuration (input, key) { + var duration = input, + // matching against regexp is expensive, do it on demand + match = null, + sign, + ret, + diffRes; + + if (isDuration(input)) { + duration = { + ms : input._milliseconds, + d : input._days, + M : input._months + }; + } else if (isNumber(input)) { + duration = {}; + if (key) { + duration[key] = input; + } else { + duration.milliseconds = input; + } + } else if (!!(match = aspNetRegex.exec(input))) { + sign = (match[1] === '-') ? -1 : 1; + duration = { + y : 0, + d : toInt(match[DATE]) * sign, + h : toInt(match[HOUR]) * sign, + m : toInt(match[MINUTE]) * sign, + s : toInt(match[SECOND]) * sign, + ms : toInt(absRound(match[MILLISECOND] * 1000)) * sign // the millisecond decimal point is included in the match + }; + } else if (!!(match = isoRegex.exec(input))) { + sign = (match[1] === '-') ? -1 : (match[1] === '+') ? 1 : 1; + duration = { + y : parseIso(match[2], sign), + M : parseIso(match[3], sign), + w : parseIso(match[4], sign), + d : parseIso(match[5], sign), + h : parseIso(match[6], sign), + m : parseIso(match[7], sign), + s : parseIso(match[8], sign) + }; + } else if (duration == null) {// checks for null or undefined + duration = {}; + } else if (typeof duration === 'object' && ('from' in duration || 'to' in duration)) { + diffRes = momentsDifference(createLocal(duration.from), createLocal(duration.to)); + + duration = {}; + duration.ms = diffRes.milliseconds; + duration.M = diffRes.months; + } + + ret = new Duration(duration); + + if (isDuration(input) && hasOwnProp(input, '_locale')) { + ret._locale = input._locale; + } + + return ret; +} + +createDuration.fn = Duration.prototype; +createDuration.invalid = createInvalid$1; + +function parseIso (inp, sign) { + // We'd normally use ~~inp for this, but unfortunately it also + // converts floats to ints. + // inp may be undefined, so careful calling replace on it. + var res = inp && parseFloat(inp.replace(',', '.')); + // apply sign while we're at it + return (isNaN(res) ? 0 : res) * sign; +} + +function positiveMomentsDifference(base, other) { + var res = {milliseconds: 0, months: 0}; + + res.months = other.month() - base.month() + + (other.year() - base.year()) * 12; + if (base.clone().add(res.months, 'M').isAfter(other)) { + --res.months; + } + + res.milliseconds = +other - +(base.clone().add(res.months, 'M')); + + return res; +} + +function momentsDifference(base, other) { + var res; + if (!(base.isValid() && other.isValid())) { + return {milliseconds: 0, months: 0}; + } + + other = cloneWithOffset(other, base); + if (base.isBefore(other)) { + res = positiveMomentsDifference(base, other); + } else { + res = positiveMomentsDifference(other, base); + res.milliseconds = -res.milliseconds; + res.months = -res.months; + } + + return res; +} + +// TODO: remove 'name' arg after deprecation is removed +function createAdder(direction, name) { + return function (val, period) { + var dur, tmp; + //invert the arguments, but complain about it + if (period !== null && !isNaN(+period)) { + deprecateSimple(name, 'moment().' + name + '(period, number) is deprecated. Please use moment().' + name + '(number, period). ' + + 'See http://momentjs.com/guides/#/warnings/add-inverted-param/ for more info.'); + tmp = val; val = period; period = tmp; + } + + val = typeof val === 'string' ? +val : val; + dur = createDuration(val, period); + addSubtract(this, dur, direction); + return this; + }; +} + +function addSubtract (mom, duration, isAdding, updateOffset) { + var milliseconds = duration._milliseconds, + days = absRound(duration._days), + months = absRound(duration._months); + + if (!mom.isValid()) { + // No op + return; + } + + updateOffset = updateOffset == null ? true : updateOffset; + + if (months) { + setMonth(mom, get(mom, 'Month') + months * isAdding); + } + if (days) { + set$1(mom, 'Date', get(mom, 'Date') + days * isAdding); + } + if (milliseconds) { + mom._d.setTime(mom._d.valueOf() + milliseconds * isAdding); + } + if (updateOffset) { + hooks.updateOffset(mom, days || months); + } +} + +var add = createAdder(1, 'add'); +var subtract = createAdder(-1, 'subtract'); + +function getCalendarFormat(myMoment, now) { + var diff = myMoment.diff(now, 'days', true); + return diff < -6 ? 'sameElse' : + diff < -1 ? 'lastWeek' : + diff < 0 ? 'lastDay' : + diff < 1 ? 'sameDay' : + diff < 2 ? 'nextDay' : + diff < 7 ? 'nextWeek' : 'sameElse'; +} + +function calendar$1 (time, formats) { + // We want to compare the start of today, vs this. + // Getting start-of-today depends on whether we're local/utc/offset or not. + var now = time || createLocal(), + sod = cloneWithOffset(now, this).startOf('day'), + format = hooks.calendarFormat(this, sod) || 'sameElse'; + + var output = formats && (isFunction(formats[format]) ? formats[format].call(this, now) : formats[format]); + + return this.format(output || this.localeData().calendar(format, this, createLocal(now))); +} + +function clone () { + return new Moment(this); +} + +function isAfter (input, units) { + var localInput = isMoment(input) ? input : createLocal(input); + if (!(this.isValid() && localInput.isValid())) { + return false; + } + units = normalizeUnits(!isUndefined(units) ? units : 'millisecond'); + if (units === 'millisecond') { + return this.valueOf() > localInput.valueOf(); + } else { + return localInput.valueOf() < this.clone().startOf(units).valueOf(); + } +} + +function isBefore (input, units) { + var localInput = isMoment(input) ? input : createLocal(input); + if (!(this.isValid() && localInput.isValid())) { + return false; + } + units = normalizeUnits(!isUndefined(units) ? units : 'millisecond'); + if (units === 'millisecond') { + return this.valueOf() < localInput.valueOf(); + } else { + return this.clone().endOf(units).valueOf() < localInput.valueOf(); + } +} + +function isBetween (from, to, units, inclusivity) { + inclusivity = inclusivity || '()'; + return (inclusivity[0] === '(' ? this.isAfter(from, units) : !this.isBefore(from, units)) && + (inclusivity[1] === ')' ? this.isBefore(to, units) : !this.isAfter(to, units)); +} + +function isSame (input, units) { + var localInput = isMoment(input) ? input : createLocal(input), + inputMs; + if (!(this.isValid() && localInput.isValid())) { + return false; + } + units = normalizeUnits(units || 'millisecond'); + if (units === 'millisecond') { + return this.valueOf() === localInput.valueOf(); + } else { + inputMs = localInput.valueOf(); + return this.clone().startOf(units).valueOf() <= inputMs && inputMs <= this.clone().endOf(units).valueOf(); + } +} + +function isSameOrAfter (input, units) { + return this.isSame(input, units) || this.isAfter(input,units); +} + +function isSameOrBefore (input, units) { + return this.isSame(input, units) || this.isBefore(input,units); +} + +function diff (input, units, asFloat) { + var that, + zoneDelta, + delta, output; + + if (!this.isValid()) { + return NaN; + } + + that = cloneWithOffset(input, this); + + if (!that.isValid()) { + return NaN; + } + + zoneDelta = (that.utcOffset() - this.utcOffset()) * 6e4; + + units = normalizeUnits(units); + + switch (units) { + case 'year': output = monthDiff(this, that) / 12; break; + case 'month': output = monthDiff(this, that); break; + case 'quarter': output = monthDiff(this, that) / 3; break; + case 'second': output = (this - that) / 1e3; break; // 1000 + case 'minute': output = (this - that) / 6e4; break; // 1000 * 60 + case 'hour': output = (this - that) / 36e5; break; // 1000 * 60 * 60 + case 'day': output = (this - that - zoneDelta) / 864e5; break; // 1000 * 60 * 60 * 24, negate dst + case 'week': output = (this - that - zoneDelta) / 6048e5; break; // 1000 * 60 * 60 * 24 * 7, negate dst + default: output = this - that; + } + + return asFloat ? output : absFloor(output); +} + +function monthDiff (a, b) { + // difference in months + var wholeMonthDiff = ((b.year() - a.year()) * 12) + (b.month() - a.month()), + // b is in (anchor - 1 month, anchor + 1 month) + anchor = a.clone().add(wholeMonthDiff, 'months'), + anchor2, adjust; + + if (b - anchor < 0) { + anchor2 = a.clone().add(wholeMonthDiff - 1, 'months'); + // linear across the month + adjust = (b - anchor) / (anchor - anchor2); + } else { + anchor2 = a.clone().add(wholeMonthDiff + 1, 'months'); + // linear across the month + adjust = (b - anchor) / (anchor2 - anchor); + } + + //check for negative zero, return zero if negative zero + return -(wholeMonthDiff + adjust) || 0; +} + +hooks.defaultFormat = 'YYYY-MM-DDTHH:mm:ssZ'; +hooks.defaultFormatUtc = 'YYYY-MM-DDTHH:mm:ss[Z]'; + +function toString () { + return this.clone().locale('en').format('ddd MMM DD YYYY HH:mm:ss [GMT]ZZ'); +} + +function toISOString(keepOffset) { + if (!this.isValid()) { + return null; + } + var utc = keepOffset !== true; + var m = utc ? this.clone().utc() : this; + if (m.year() < 0 || m.year() > 9999) { + return formatMoment(m, utc ? 'YYYYYY-MM-DD[T]HH:mm:ss.SSS[Z]' : 'YYYYYY-MM-DD[T]HH:mm:ss.SSSZ'); + } + if (isFunction(Date.prototype.toISOString)) { + // native implementation is ~50x faster, use it when we can + if (utc) { + return this.toDate().toISOString(); + } else { + return new Date(this._d.valueOf()).toISOString().replace('Z', formatMoment(m, 'Z')); + } + } + return formatMoment(m, utc ? 'YYYY-MM-DD[T]HH:mm:ss.SSS[Z]' : 'YYYY-MM-DD[T]HH:mm:ss.SSSZ'); +} + +/** + * Return a human readable representation of a moment that can + * also be evaluated to get a new moment which is the same + * + * @link https://nodejs.org/dist/latest/docs/api/util.html#util_custom_inspect_function_on_objects + */ +function inspect () { + if (!this.isValid()) { + return 'moment.invalid(/* ' + this._i + ' */)'; + } + var func = 'moment'; + var zone = ''; + if (!this.isLocal()) { + func = this.utcOffset() === 0 ? 'moment.utc' : 'moment.parseZone'; + zone = 'Z'; + } + var prefix = '[' + func + '("]'; + var year = (0 <= this.year() && this.year() <= 9999) ? 'YYYY' : 'YYYYYY'; + var datetime = '-MM-DD[T]HH:mm:ss.SSS'; + var suffix = zone + '[")]'; + + return this.format(prefix + year + datetime + suffix); +} + +function format (inputString) { + if (!inputString) { + inputString = this.isUtc() ? hooks.defaultFormatUtc : hooks.defaultFormat; + } + var output = formatMoment(this, inputString); + return this.localeData().postformat(output); +} + +function from (time, withoutSuffix) { + if (this.isValid() && + ((isMoment(time) && time.isValid()) || + createLocal(time).isValid())) { + return createDuration({to: this, from: time}).locale(this.locale()).humanize(!withoutSuffix); + } else { + return this.localeData().invalidDate(); + } +} + +function fromNow (withoutSuffix) { + return this.from(createLocal(), withoutSuffix); +} + +function to (time, withoutSuffix) { + if (this.isValid() && + ((isMoment(time) && time.isValid()) || + createLocal(time).isValid())) { + return createDuration({from: this, to: time}).locale(this.locale()).humanize(!withoutSuffix); + } else { + return this.localeData().invalidDate(); + } +} + +function toNow (withoutSuffix) { + return this.to(createLocal(), withoutSuffix); +} + +// If passed a locale key, it will set the locale for this +// instance. Otherwise, it will return the locale configuration +// variables for this instance. +function locale (key) { + var newLocaleData; + + if (key === undefined) { + return this._locale._abbr; + } else { + newLocaleData = getLocale(key); + if (newLocaleData != null) { + this._locale = newLocaleData; + } + return this; + } +} + +var lang = deprecate( + 'moment().lang() is deprecated. Instead, use moment().localeData() to get the language configuration. Use moment().locale() to change languages.', + function (key) { + if (key === undefined) { + return this.localeData(); + } else { + return this.locale(key); + } + } +); + +function localeData () { + return this._locale; +} + +function startOf (units) { + units = normalizeUnits(units); + // the following switch intentionally omits break keywords + // to utilize falling through the cases. + switch (units) { + case 'year': + this.month(0); + /* falls through */ + case 'quarter': + case 'month': + this.date(1); + /* falls through */ + case 'week': + case 'isoWeek': + case 'day': + case 'date': + this.hours(0); + /* falls through */ + case 'hour': + this.minutes(0); + /* falls through */ + case 'minute': + this.seconds(0); + /* falls through */ + case 'second': + this.milliseconds(0); + } + + // weeks are a special case + if (units === 'week') { + this.weekday(0); + } + if (units === 'isoWeek') { + this.isoWeekday(1); + } + + // quarters are also special + if (units === 'quarter') { + this.month(Math.floor(this.month() / 3) * 3); + } + + return this; +} + +function endOf (units) { + units = normalizeUnits(units); + if (units === undefined || units === 'millisecond') { + return this; + } + + // 'date' is an alias for 'day', so it should be considered as such. + if (units === 'date') { + units = 'day'; + } + + return this.startOf(units).add(1, (units === 'isoWeek' ? 'week' : units)).subtract(1, 'ms'); +} + +function valueOf () { + return this._d.valueOf() - ((this._offset || 0) * 60000); +} + +function unix () { + return Math.floor(this.valueOf() / 1000); +} + +function toDate () { + return new Date(this.valueOf()); +} + +function toArray () { + var m = this; + return [m.year(), m.month(), m.date(), m.hour(), m.minute(), m.second(), m.millisecond()]; +} + +function toObject () { + var m = this; + return { + years: m.year(), + months: m.month(), + date: m.date(), + hours: m.hours(), + minutes: m.minutes(), + seconds: m.seconds(), + milliseconds: m.milliseconds() + }; +} + +function toJSON () { + // new Date(NaN).toJSON() === null + return this.isValid() ? this.toISOString() : null; +} + +function isValid$2 () { + return isValid(this); +} + +function parsingFlags () { + return extend({}, getParsingFlags(this)); +} + +function invalidAt () { + return getParsingFlags(this).overflow; +} + +function creationData() { + return { + input: this._i, + format: this._f, + locale: this._locale, + isUTC: this._isUTC, + strict: this._strict + }; +} + +// FORMATTING + +addFormatToken(0, ['gg', 2], 0, function () { + return this.weekYear() % 100; +}); + +addFormatToken(0, ['GG', 2], 0, function () { + return this.isoWeekYear() % 100; +}); + +function addWeekYearFormatToken (token, getter) { + addFormatToken(0, [token, token.length], 0, getter); +} + +addWeekYearFormatToken('gggg', 'weekYear'); +addWeekYearFormatToken('ggggg', 'weekYear'); +addWeekYearFormatToken('GGGG', 'isoWeekYear'); +addWeekYearFormatToken('GGGGG', 'isoWeekYear'); + +// ALIASES + +addUnitAlias('weekYear', 'gg'); +addUnitAlias('isoWeekYear', 'GG'); + +// PRIORITY + +addUnitPriority('weekYear', 1); +addUnitPriority('isoWeekYear', 1); + + +// PARSING + +addRegexToken('G', matchSigned); +addRegexToken('g', matchSigned); +addRegexToken('GG', match1to2, match2); +addRegexToken('gg', match1to2, match2); +addRegexToken('GGGG', match1to4, match4); +addRegexToken('gggg', match1to4, match4); +addRegexToken('GGGGG', match1to6, match6); +addRegexToken('ggggg', match1to6, match6); + +addWeekParseToken(['gggg', 'ggggg', 'GGGG', 'GGGGG'], function (input, week, config, token) { + week[token.substr(0, 2)] = toInt(input); +}); + +addWeekParseToken(['gg', 'GG'], function (input, week, config, token) { + week[token] = hooks.parseTwoDigitYear(input); +}); + +// MOMENTS + +function getSetWeekYear (input) { + return getSetWeekYearHelper.call(this, + input, + this.week(), + this.weekday(), + this.localeData()._week.dow, + this.localeData()._week.doy); +} + +function getSetISOWeekYear (input) { + return getSetWeekYearHelper.call(this, + input, this.isoWeek(), this.isoWeekday(), 1, 4); +} + +function getISOWeeksInYear () { + return weeksInYear(this.year(), 1, 4); +} + +function getWeeksInYear () { + var weekInfo = this.localeData()._week; + return weeksInYear(this.year(), weekInfo.dow, weekInfo.doy); +} + +function getSetWeekYearHelper(input, week, weekday, dow, doy) { + var weeksTarget; + if (input == null) { + return weekOfYear(this, dow, doy).year; + } else { + weeksTarget = weeksInYear(input, dow, doy); + if (week > weeksTarget) { + week = weeksTarget; + } + return setWeekAll.call(this, input, week, weekday, dow, doy); + } +} + +function setWeekAll(weekYear, week, weekday, dow, doy) { + var dayOfYearData = dayOfYearFromWeeks(weekYear, week, weekday, dow, doy), + date = createUTCDate(dayOfYearData.year, 0, dayOfYearData.dayOfYear); + + this.year(date.getUTCFullYear()); + this.month(date.getUTCMonth()); + this.date(date.getUTCDate()); + return this; +} + +// FORMATTING + +addFormatToken('Q', 0, 'Qo', 'quarter'); + +// ALIASES + +addUnitAlias('quarter', 'Q'); + +// PRIORITY + +addUnitPriority('quarter', 7); + +// PARSING + +addRegexToken('Q', match1); +addParseToken('Q', function (input, array) { + array[MONTH] = (toInt(input) - 1) * 3; +}); + +// MOMENTS + +function getSetQuarter (input) { + return input == null ? Math.ceil((this.month() + 1) / 3) : this.month((input - 1) * 3 + this.month() % 3); +} + +// FORMATTING + +addFormatToken('D', ['DD', 2], 'Do', 'date'); + +// ALIASES + +addUnitAlias('date', 'D'); + +// PRIOROITY +addUnitPriority('date', 9); + +// PARSING + +addRegexToken('D', match1to2); +addRegexToken('DD', match1to2, match2); +addRegexToken('Do', function (isStrict, locale) { + // TODO: Remove "ordinalParse" fallback in next major release. + return isStrict ? + (locale._dayOfMonthOrdinalParse || locale._ordinalParse) : + locale._dayOfMonthOrdinalParseLenient; +}); + +addParseToken(['D', 'DD'], DATE); +addParseToken('Do', function (input, array) { + array[DATE] = toInt(input.match(match1to2)[0]); +}); + +// MOMENTS + +var getSetDayOfMonth = makeGetSet('Date', true); + +// FORMATTING + +addFormatToken('DDD', ['DDDD', 3], 'DDDo', 'dayOfYear'); + +// ALIASES + +addUnitAlias('dayOfYear', 'DDD'); + +// PRIORITY +addUnitPriority('dayOfYear', 4); + +// PARSING + +addRegexToken('DDD', match1to3); +addRegexToken('DDDD', match3); +addParseToken(['DDD', 'DDDD'], function (input, array, config) { + config._dayOfYear = toInt(input); +}); + +// HELPERS + +// MOMENTS + +function getSetDayOfYear (input) { + var dayOfYear = Math.round((this.clone().startOf('day') - this.clone().startOf('year')) / 864e5) + 1; + return input == null ? dayOfYear : this.add((input - dayOfYear), 'd'); +} + +// FORMATTING + +addFormatToken('m', ['mm', 2], 0, 'minute'); + +// ALIASES + +addUnitAlias('minute', 'm'); + +// PRIORITY + +addUnitPriority('minute', 14); + +// PARSING + +addRegexToken('m', match1to2); +addRegexToken('mm', match1to2, match2); +addParseToken(['m', 'mm'], MINUTE); + +// MOMENTS + +var getSetMinute = makeGetSet('Minutes', false); + +// FORMATTING + +addFormatToken('s', ['ss', 2], 0, 'second'); + +// ALIASES + +addUnitAlias('second', 's'); + +// PRIORITY + +addUnitPriority('second', 15); + +// PARSING + +addRegexToken('s', match1to2); +addRegexToken('ss', match1to2, match2); +addParseToken(['s', 'ss'], SECOND); + +// MOMENTS + +var getSetSecond = makeGetSet('Seconds', false); + +// FORMATTING + +addFormatToken('S', 0, 0, function () { + return ~~(this.millisecond() / 100); +}); + +addFormatToken(0, ['SS', 2], 0, function () { + return ~~(this.millisecond() / 10); +}); + +addFormatToken(0, ['SSS', 3], 0, 'millisecond'); +addFormatToken(0, ['SSSS', 4], 0, function () { + return this.millisecond() * 10; +}); +addFormatToken(0, ['SSSSS', 5], 0, function () { + return this.millisecond() * 100; +}); +addFormatToken(0, ['SSSSSS', 6], 0, function () { + return this.millisecond() * 1000; +}); +addFormatToken(0, ['SSSSSSS', 7], 0, function () { + return this.millisecond() * 10000; +}); +addFormatToken(0, ['SSSSSSSS', 8], 0, function () { + return this.millisecond() * 100000; +}); +addFormatToken(0, ['SSSSSSSSS', 9], 0, function () { + return this.millisecond() * 1000000; +}); + + +// ALIASES + +addUnitAlias('millisecond', 'ms'); + +// PRIORITY + +addUnitPriority('millisecond', 16); + +// PARSING + +addRegexToken('S', match1to3, match1); +addRegexToken('SS', match1to3, match2); +addRegexToken('SSS', match1to3, match3); + +var token; +for (token = 'SSSS'; token.length <= 9; token += 'S') { + addRegexToken(token, matchUnsigned); +} + +function parseMs(input, array) { + array[MILLISECOND] = toInt(('0.' + input) * 1000); +} + +for (token = 'S'; token.length <= 9; token += 'S') { + addParseToken(token, parseMs); +} +// MOMENTS + +var getSetMillisecond = makeGetSet('Milliseconds', false); + +// FORMATTING + +addFormatToken('z', 0, 0, 'zoneAbbr'); +addFormatToken('zz', 0, 0, 'zoneName'); + +// MOMENTS + +function getZoneAbbr () { + return this._isUTC ? 'UTC' : ''; +} + +function getZoneName () { + return this._isUTC ? 'Coordinated Universal Time' : ''; +} + +var proto = Moment.prototype; + +proto.add = add; +proto.calendar = calendar$1; +proto.clone = clone; +proto.diff = diff; +proto.endOf = endOf; +proto.format = format; +proto.from = from; +proto.fromNow = fromNow; +proto.to = to; +proto.toNow = toNow; +proto.get = stringGet; +proto.invalidAt = invalidAt; +proto.isAfter = isAfter; +proto.isBefore = isBefore; +proto.isBetween = isBetween; +proto.isSame = isSame; +proto.isSameOrAfter = isSameOrAfter; +proto.isSameOrBefore = isSameOrBefore; +proto.isValid = isValid$2; +proto.lang = lang; +proto.locale = locale; +proto.localeData = localeData; +proto.max = prototypeMax; +proto.min = prototypeMin; +proto.parsingFlags = parsingFlags; +proto.set = stringSet; +proto.startOf = startOf; +proto.subtract = subtract; +proto.toArray = toArray; +proto.toObject = toObject; +proto.toDate = toDate; +proto.toISOString = toISOString; +proto.inspect = inspect; +proto.toJSON = toJSON; +proto.toString = toString; +proto.unix = unix; +proto.valueOf = valueOf; +proto.creationData = creationData; + +// Year +proto.year = getSetYear; +proto.isLeapYear = getIsLeapYear; + +// Week Year +proto.weekYear = getSetWeekYear; +proto.isoWeekYear = getSetISOWeekYear; + +// Quarter +proto.quarter = proto.quarters = getSetQuarter; + +// Month +proto.month = getSetMonth; +proto.daysInMonth = getDaysInMonth; + +// Week +proto.week = proto.weeks = getSetWeek; +proto.isoWeek = proto.isoWeeks = getSetISOWeek; +proto.weeksInYear = getWeeksInYear; +proto.isoWeeksInYear = getISOWeeksInYear; + +// Day +proto.date = getSetDayOfMonth; +proto.day = proto.days = getSetDayOfWeek; +proto.weekday = getSetLocaleDayOfWeek; +proto.isoWeekday = getSetISODayOfWeek; +proto.dayOfYear = getSetDayOfYear; + +// Hour +proto.hour = proto.hours = getSetHour; + +// Minute +proto.minute = proto.minutes = getSetMinute; + +// Second +proto.second = proto.seconds = getSetSecond; + +// Millisecond +proto.millisecond = proto.milliseconds = getSetMillisecond; + +// Offset +proto.utcOffset = getSetOffset; +proto.utc = setOffsetToUTC; +proto.local = setOffsetToLocal; +proto.parseZone = setOffsetToParsedOffset; +proto.hasAlignedHourOffset = hasAlignedHourOffset; +proto.isDST = isDaylightSavingTime; +proto.isLocal = isLocal; +proto.isUtcOffset = isUtcOffset; +proto.isUtc = isUtc; +proto.isUTC = isUtc; + +// Timezone +proto.zoneAbbr = getZoneAbbr; +proto.zoneName = getZoneName; + +// Deprecations +proto.dates = deprecate('dates accessor is deprecated. Use date instead.', getSetDayOfMonth); +proto.months = deprecate('months accessor is deprecated. Use month instead', getSetMonth); +proto.years = deprecate('years accessor is deprecated. Use year instead', getSetYear); +proto.zone = deprecate('moment().zone is deprecated, use moment().utcOffset instead. http://momentjs.com/guides/#/warnings/zone/', getSetZone); +proto.isDSTShifted = deprecate('isDSTShifted is deprecated. See http://momentjs.com/guides/#/warnings/dst-shifted/ for more information', isDaylightSavingTimeShifted); + +function createUnix (input) { + return createLocal(input * 1000); +} + +function createInZone () { + return createLocal.apply(null, arguments).parseZone(); +} + +function preParsePostFormat (string) { + return string; +} + +var proto$1 = Locale.prototype; + +proto$1.calendar = calendar; +proto$1.longDateFormat = longDateFormat; +proto$1.invalidDate = invalidDate; +proto$1.ordinal = ordinal; +proto$1.preparse = preParsePostFormat; +proto$1.postformat = preParsePostFormat; +proto$1.relativeTime = relativeTime; +proto$1.pastFuture = pastFuture; +proto$1.set = set; + +// Month +proto$1.months = localeMonths; +proto$1.monthsShort = localeMonthsShort; +proto$1.monthsParse = localeMonthsParse; +proto$1.monthsRegex = monthsRegex; +proto$1.monthsShortRegex = monthsShortRegex; + +// Week +proto$1.week = localeWeek; +proto$1.firstDayOfYear = localeFirstDayOfYear; +proto$1.firstDayOfWeek = localeFirstDayOfWeek; + +// Day of Week +proto$1.weekdays = localeWeekdays; +proto$1.weekdaysMin = localeWeekdaysMin; +proto$1.weekdaysShort = localeWeekdaysShort; +proto$1.weekdaysParse = localeWeekdaysParse; + +proto$1.weekdaysRegex = weekdaysRegex; +proto$1.weekdaysShortRegex = weekdaysShortRegex; +proto$1.weekdaysMinRegex = weekdaysMinRegex; + +// Hours +proto$1.isPM = localeIsPM; +proto$1.meridiem = localeMeridiem; + +function get$1 (format, index, field, setter) { + var locale = getLocale(); + var utc = createUTC().set(setter, index); + return locale[field](utc, format); +} + +function listMonthsImpl (format, index, field) { + if (isNumber(format)) { + index = format; + format = undefined; + } + + format = format || ''; + + if (index != null) { + return get$1(format, index, field, 'month'); + } + + var i; + var out = []; + for (i = 0; i < 12; i++) { + out[i] = get$1(format, i, field, 'month'); + } + return out; +} + +// () +// (5) +// (fmt, 5) +// (fmt) +// (true) +// (true, 5) +// (true, fmt, 5) +// (true, fmt) +function listWeekdaysImpl (localeSorted, format, index, field) { + if (typeof localeSorted === 'boolean') { + if (isNumber(format)) { + index = format; + format = undefined; + } + + format = format || ''; + } else { + format = localeSorted; + index = format; + localeSorted = false; + + if (isNumber(format)) { + index = format; + format = undefined; + } + + format = format || ''; + } + + var locale = getLocale(), + shift = localeSorted ? locale._week.dow : 0; + + if (index != null) { + return get$1(format, (index + shift) % 7, field, 'day'); + } + + var i; + var out = []; + for (i = 0; i < 7; i++) { + out[i] = get$1(format, (i + shift) % 7, field, 'day'); + } + return out; +} + +function listMonths (format, index) { + return listMonthsImpl(format, index, 'months'); +} + +function listMonthsShort (format, index) { + return listMonthsImpl(format, index, 'monthsShort'); +} + +function listWeekdays (localeSorted, format, index) { + return listWeekdaysImpl(localeSorted, format, index, 'weekdays'); +} + +function listWeekdaysShort (localeSorted, format, index) { + return listWeekdaysImpl(localeSorted, format, index, 'weekdaysShort'); +} + +function listWeekdaysMin (localeSorted, format, index) { + return listWeekdaysImpl(localeSorted, format, index, 'weekdaysMin'); +} + +getSetGlobalLocale('en', { + dayOfMonthOrdinalParse: /\d{1,2}(th|st|nd|rd)/, + ordinal : function (number) { + var b = number % 10, + output = (toInt(number % 100 / 10) === 1) ? 'th' : + (b === 1) ? 'st' : + (b === 2) ? 'nd' : + (b === 3) ? 'rd' : 'th'; + return number + output; + } +}); + +// Side effect imports +hooks.lang = deprecate('moment.lang is deprecated. Use moment.locale instead.', getSetGlobalLocale); +hooks.langData = deprecate('moment.langData is deprecated. Use moment.localeData instead.', getLocale); + +var mathAbs = Math.abs; + +function abs () { + var data = this._data; + + this._milliseconds = mathAbs(this._milliseconds); + this._days = mathAbs(this._days); + this._months = mathAbs(this._months); + + data.milliseconds = mathAbs(data.milliseconds); + data.seconds = mathAbs(data.seconds); + data.minutes = mathAbs(data.minutes); + data.hours = mathAbs(data.hours); + data.months = mathAbs(data.months); + data.years = mathAbs(data.years); + + return this; +} + +function addSubtract$1 (duration, input, value, direction) { + var other = createDuration(input, value); + + duration._milliseconds += direction * other._milliseconds; + duration._days += direction * other._days; + duration._months += direction * other._months; + + return duration._bubble(); +} + +// supports only 2.0-style add(1, 's') or add(duration) +function add$1 (input, value) { + return addSubtract$1(this, input, value, 1); +} + +// supports only 2.0-style subtract(1, 's') or subtract(duration) +function subtract$1 (input, value) { + return addSubtract$1(this, input, value, -1); +} + +function absCeil (number) { + if (number < 0) { + return Math.floor(number); + } else { + return Math.ceil(number); + } +} + +function bubble () { + var milliseconds = this._milliseconds; + var days = this._days; + var months = this._months; + var data = this._data; + var seconds, minutes, hours, years, monthsFromDays; + + // if we have a mix of positive and negative values, bubble down first + // check: https://github.com/moment/moment/issues/2166 + if (!((milliseconds >= 0 && days >= 0 && months >= 0) || + (milliseconds <= 0 && days <= 0 && months <= 0))) { + milliseconds += absCeil(monthsToDays(months) + days) * 864e5; + days = 0; + months = 0; + } + + // The following code bubbles up values, see the tests for + // examples of what that means. + data.milliseconds = milliseconds % 1000; + + seconds = absFloor(milliseconds / 1000); + data.seconds = seconds % 60; + + minutes = absFloor(seconds / 60); + data.minutes = minutes % 60; + + hours = absFloor(minutes / 60); + data.hours = hours % 24; + + days += absFloor(hours / 24); + + // convert days to months + monthsFromDays = absFloor(daysToMonths(days)); + months += monthsFromDays; + days -= absCeil(monthsToDays(monthsFromDays)); + + // 12 months -> 1 year + years = absFloor(months / 12); + months %= 12; + + data.days = days; + data.months = months; + data.years = years; + + return this; +} + +function daysToMonths (days) { + // 400 years have 146097 days (taking into account leap year rules) + // 400 years have 12 months === 4800 + return days * 4800 / 146097; +} + +function monthsToDays (months) { + // the reverse of daysToMonths + return months * 146097 / 4800; +} + +function as (units) { + if (!this.isValid()) { + return NaN; + } + var days; + var months; + var milliseconds = this._milliseconds; + + units = normalizeUnits(units); + + if (units === 'month' || units === 'year') { + days = this._days + milliseconds / 864e5; + months = this._months + daysToMonths(days); + return units === 'month' ? months : months / 12; + } else { + // handle milliseconds separately because of floating point math errors (issue #1867) + days = this._days + Math.round(monthsToDays(this._months)); + switch (units) { + case 'week' : return days / 7 + milliseconds / 6048e5; + case 'day' : return days + milliseconds / 864e5; + case 'hour' : return days * 24 + milliseconds / 36e5; + case 'minute' : return days * 1440 + milliseconds / 6e4; + case 'second' : return days * 86400 + milliseconds / 1000; + // Math.floor prevents floating point math errors here + case 'millisecond': return Math.floor(days * 864e5) + milliseconds; + default: throw new Error('Unknown unit ' + units); + } + } +} + +// TODO: Use this.as('ms')? +function valueOf$1 () { + if (!this.isValid()) { + return NaN; + } + return ( + this._milliseconds + + this._days * 864e5 + + (this._months % 12) * 2592e6 + + toInt(this._months / 12) * 31536e6 + ); +} + +function makeAs (alias) { + return function () { + return this.as(alias); + }; +} + +var asMilliseconds = makeAs('ms'); +var asSeconds = makeAs('s'); +var asMinutes = makeAs('m'); +var asHours = makeAs('h'); +var asDays = makeAs('d'); +var asWeeks = makeAs('w'); +var asMonths = makeAs('M'); +var asYears = makeAs('y'); + +function clone$1 () { + return createDuration(this); +} + +function get$2 (units) { + units = normalizeUnits(units); + return this.isValid() ? this[units + 's']() : NaN; +} + +function makeGetter(name) { + return function () { + return this.isValid() ? this._data[name] : NaN; + }; +} + +var milliseconds = makeGetter('milliseconds'); +var seconds = makeGetter('seconds'); +var minutes = makeGetter('minutes'); +var hours = makeGetter('hours'); +var days = makeGetter('days'); +var months = makeGetter('months'); +var years = makeGetter('years'); + +function weeks () { + return absFloor(this.days() / 7); +} + +var round = Math.round; +var thresholds = { + ss: 44, // a few seconds to seconds + s : 45, // seconds to minute + m : 45, // minutes to hour + h : 22, // hours to day + d : 26, // days to month + M : 11 // months to year +}; + +// helper function for moment.fn.from, moment.fn.fromNow, and moment.duration.fn.humanize +function substituteTimeAgo(string, number, withoutSuffix, isFuture, locale) { + return locale.relativeTime(number || 1, !!withoutSuffix, string, isFuture); +} + +function relativeTime$1 (posNegDuration, withoutSuffix, locale) { + var duration = createDuration(posNegDuration).abs(); + var seconds = round(duration.as('s')); + var minutes = round(duration.as('m')); + var hours = round(duration.as('h')); + var days = round(duration.as('d')); + var months = round(duration.as('M')); + var years = round(duration.as('y')); + + var a = seconds <= thresholds.ss && ['s', seconds] || + seconds < thresholds.s && ['ss', seconds] || + minutes <= 1 && ['m'] || + minutes < thresholds.m && ['mm', minutes] || + hours <= 1 && ['h'] || + hours < thresholds.h && ['hh', hours] || + days <= 1 && ['d'] || + days < thresholds.d && ['dd', days] || + months <= 1 && ['M'] || + months < thresholds.M && ['MM', months] || + years <= 1 && ['y'] || ['yy', years]; + + a[2] = withoutSuffix; + a[3] = +posNegDuration > 0; + a[4] = locale; + return substituteTimeAgo.apply(null, a); +} + +// This function allows you to set the rounding function for relative time strings +function getSetRelativeTimeRounding (roundingFunction) { + if (roundingFunction === undefined) { + return round; + } + if (typeof(roundingFunction) === 'function') { + round = roundingFunction; + return true; + } + return false; +} + +// This function allows you to set a threshold for relative time strings +function getSetRelativeTimeThreshold (threshold, limit) { + if (thresholds[threshold] === undefined) { + return false; + } + if (limit === undefined) { + return thresholds[threshold]; + } + thresholds[threshold] = limit; + if (threshold === 's') { + thresholds.ss = limit - 1; + } + return true; +} + +function humanize (withSuffix) { + if (!this.isValid()) { + return this.localeData().invalidDate(); + } + + var locale = this.localeData(); + var output = relativeTime$1(this, !withSuffix, locale); + + if (withSuffix) { + output = locale.pastFuture(+this, output); + } + + return locale.postformat(output); +} + +var abs$1 = Math.abs; + +function sign(x) { + return ((x > 0) - (x < 0)) || +x; +} + +function toISOString$1() { + // for ISO strings we do not use the normal bubbling rules: + // * milliseconds bubble up until they become hours + // * days do not bubble at all + // * months bubble up until they become years + // This is because there is no context-free conversion between hours and days + // (think of clock changes) + // and also not between days and months (28-31 days per month) + if (!this.isValid()) { + return this.localeData().invalidDate(); + } + + var seconds = abs$1(this._milliseconds) / 1000; + var days = abs$1(this._days); + var months = abs$1(this._months); + var minutes, hours, years; + + // 3600 seconds -> 60 minutes -> 1 hour + minutes = absFloor(seconds / 60); + hours = absFloor(minutes / 60); + seconds %= 60; + minutes %= 60; + + // 12 months -> 1 year + years = absFloor(months / 12); + months %= 12; + + + // inspired by https://github.com/dordille/moment-isoduration/blob/master/moment.isoduration.js + var Y = years; + var M = months; + var D = days; + var h = hours; + var m = minutes; + var s = seconds ? seconds.toFixed(3).replace(/\.?0+$/, '') : ''; + var total = this.asSeconds(); + + if (!total) { + // this is the same as C#'s (Noda) and python (isodate)... + // but not other JS (goog.date) + return 'P0D'; + } + + var totalSign = total < 0 ? '-' : ''; + var ymSign = sign(this._months) !== sign(total) ? '-' : ''; + var daysSign = sign(this._days) !== sign(total) ? '-' : ''; + var hmsSign = sign(this._milliseconds) !== sign(total) ? '-' : ''; + + return totalSign + 'P' + + (Y ? ymSign + Y + 'Y' : '') + + (M ? ymSign + M + 'M' : '') + + (D ? daysSign + D + 'D' : '') + + ((h || m || s) ? 'T' : '') + + (h ? hmsSign + h + 'H' : '') + + (m ? hmsSign + m + 'M' : '') + + (s ? hmsSign + s + 'S' : ''); +} + +var proto$2 = Duration.prototype; + +proto$2.isValid = isValid$1; +proto$2.abs = abs; +proto$2.add = add$1; +proto$2.subtract = subtract$1; +proto$2.as = as; +proto$2.asMilliseconds = asMilliseconds; +proto$2.asSeconds = asSeconds; +proto$2.asMinutes = asMinutes; +proto$2.asHours = asHours; +proto$2.asDays = asDays; +proto$2.asWeeks = asWeeks; +proto$2.asMonths = asMonths; +proto$2.asYears = asYears; +proto$2.valueOf = valueOf$1; +proto$2._bubble = bubble; +proto$2.clone = clone$1; +proto$2.get = get$2; +proto$2.milliseconds = milliseconds; +proto$2.seconds = seconds; +proto$2.minutes = minutes; +proto$2.hours = hours; +proto$2.days = days; +proto$2.weeks = weeks; +proto$2.months = months; +proto$2.years = years; +proto$2.humanize = humanize; +proto$2.toISOString = toISOString$1; +proto$2.toString = toISOString$1; +proto$2.toJSON = toISOString$1; +proto$2.locale = locale; +proto$2.localeData = localeData; + +// Deprecations +proto$2.toIsoString = deprecate('toIsoString() is deprecated. Please use toISOString() instead (notice the capitals)', toISOString$1); +proto$2.lang = lang; + +// Side effect imports + +// FORMATTING + +addFormatToken('X', 0, 0, 'unix'); +addFormatToken('x', 0, 0, 'valueOf'); + +// PARSING + +addRegexToken('x', matchSigned); +addRegexToken('X', matchTimestamp); +addParseToken('X', function (input, array, config) { + config._d = new Date(parseFloat(input, 10) * 1000); +}); +addParseToken('x', function (input, array, config) { + config._d = new Date(toInt(input)); +}); + +// Side effect imports + + +hooks.version = '2.20.1'; + +setHookCallback(createLocal); + +hooks.fn = proto; +hooks.min = min; +hooks.max = max; +hooks.now = now; +hooks.utc = createUTC; +hooks.unix = createUnix; +hooks.months = listMonths; +hooks.isDate = isDate; +hooks.locale = getSetGlobalLocale; +hooks.invalid = createInvalid; +hooks.duration = createDuration; +hooks.isMoment = isMoment; +hooks.weekdays = listWeekdays; +hooks.parseZone = createInZone; +hooks.localeData = getLocale; +hooks.isDuration = isDuration; +hooks.monthsShort = listMonthsShort; +hooks.weekdaysMin = listWeekdaysMin; +hooks.defineLocale = defineLocale; +hooks.updateLocale = updateLocale; +hooks.locales = listLocales; +hooks.weekdaysShort = listWeekdaysShort; +hooks.normalizeUnits = normalizeUnits; +hooks.relativeTimeRounding = getSetRelativeTimeRounding; +hooks.relativeTimeThreshold = getSetRelativeTimeThreshold; +hooks.calendarFormat = getCalendarFormat; +hooks.prototype = proto; + +// currently HTML5 input type only supports 24-hour formats +hooks.HTML5_FMT = { + DATETIME_LOCAL: 'YYYY-MM-DDTHH:mm', // + DATETIME_LOCAL_SECONDS: 'YYYY-MM-DDTHH:mm:ss', // + DATETIME_LOCAL_MS: 'YYYY-MM-DDTHH:mm:ss.SSS', // + DATE: 'YYYY-MM-DD', // + TIME: 'HH:mm', // + TIME_SECONDS: 'HH:mm:ss', // + TIME_MS: 'HH:mm:ss.SSS', // + WEEK: 'YYYY-[W]WW', // + MONTH: 'YYYY-MM' // +}; + +return hooks; + +}))); diff --git a/js_sdk/js-base64/.attic/test-moment/yoshinoya.js b/js_sdk/js-base64/.attic/test-moment/yoshinoya.js new file mode 100644 index 0000000..4576c79 --- /dev/null +++ b/js_sdk/js-base64/.attic/test-moment/yoshinoya.js @@ -0,0 +1,19 @@ +/* + * use mocha to test me + * http://visionmedia.github.com/mocha/ + */ +var assert = assert || require("assert"); +var Base64 = Base64 || require('../base64.js').Base64; +var is = function (a, e, m) { + return function () { + assert.equal(a, e, m) + } +}; + +describe('Yoshinoya', function () { + it('.encode', is(Base64.encode('𠮷野家'), '8KCut+mHjuWutg==')); + it('.encodeURI', is(Base64.encodeURI('𠮷野家'), '8KCut-mHjuWutg')); + it('.decode', is(Base64.decode('8KCut+mHjuWutg=='), '𠮷野家')); + it('.decode', is(Base64.decode('8KCut-mHjuWutg'), '𠮷野家')); + /* it('.decode', is(Base64.decode('7aGC7b636YeO5a62'), '𠮷野家')); */ +}); diff --git a/js_sdk/js-base64/1x1.png b/js_sdk/js-base64/1x1.png new file mode 100644 index 0000000..909c66d Binary files /dev/null and b/js_sdk/js-base64/1x1.png differ diff --git a/js_sdk/js-base64/LICENSE.md b/js_sdk/js-base64/LICENSE.md new file mode 100644 index 0000000..fd579a4 --- /dev/null +++ b/js_sdk/js-base64/LICENSE.md @@ -0,0 +1,27 @@ +Copyright (c) 2014, Dan Kogai +All rights reserved. + +Redistribution and use in source and binary forms, with or without +modification, are permitted provided that the following conditions are met: + +* Redistributions of source code must retain the above copyright notice, this + list of conditions and the following disclaimer. + +* Redistributions in binary form must reproduce the above copyright notice, + this list of conditions and the following disclaimer in the documentation + and/or other materials provided with the distribution. + +* Neither the name of {{{project}}} nor the names of its + contributors may be used to endorse or promote products derived from + this software without specific prior written permission. + +THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE +FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. diff --git a/js_sdk/js-base64/README.md b/js_sdk/js-base64/README.md new file mode 100644 index 0000000..1dfb104 --- /dev/null +++ b/js_sdk/js-base64/README.md @@ -0,0 +1,94 @@ +[![build status](https://secure.travis-ci.org/dankogai/js-base64.png)](http://travis-ci.org/dankogai/js-base64) + +# base64.js + +Yet another Base64 transcoder + +## Install + +```javascript +$ npm install --save js-base64 +``` + +If you are using it on ES6 transpilers, you may also need: + +```javascript +$ npm install --save babel-preset-env +``` + +Note `js-base64` itself is stand-alone so its `package.json` has no `dependencies`.  However, it is also tested on ES6 environment so `"babel-preset-env": "^1.7.0"` is on `devDependencies`. + + +## Usage + +### In Browser + +```html + +``` + +### node.js + +```javascript +var Base64 = require('js-base64').Base64; +``` + +## es6+ + +```javascript +import { Base64 } from 'js-base64'; +``` + +## SYNOPSIS + +```javascript +Base64.encode('dankogai'); // ZGFua29nYWk= +Base64.encode('小飼弾'); // 5bCP6aO85by+ +Base64.encodeURI('小飼弾'); // 5bCP6aO85by- + +Base64.decode('ZGFua29nYWk='); // dankogai +Base64.decode('5bCP6aO85by+'); // 小飼弾 +// note .decodeURI() is unnecessary since it accepts both flavors +Base64.decode('5bCP6aO85by-'); // 小飼弾 +``` + +### String Extension for ES5 + +```javascript +if (Base64.extendString) { + // you have to explicitly extend String.prototype + Base64.extendString(); + // once extended, you can do the following + 'dankogai'.toBase64(); // ZGFua29nYWk= + '小飼弾'.toBase64(); // 5bCP6aO85by+ + '小飼弾'.toBase64(true); // 5bCP6aO85by- + '小飼弾'.toBase64URI(); // 5bCP6aO85by- + 'ZGFua29nYWk='.fromBase64(); // dankogai + '5bCP6aO85by+'.fromBase64(); // 小飼弾 + '5bCP6aO85by-'.fromBase64(); // 小飼弾 +} +``` + +### TypeScript + +TypeScript 2.0 type definition was added to the [DefinitelyTyped repository](https://github.com/DefinitelyTyped/DefinitelyTyped). + +```bash +$ npm install --save @types/js-base64 +``` + +## `.decode()` vs `.atob` (and `.encode()` vs `btoa()`) + +Suppose you have: + +``` +var pngBase64 = + "iVBORw0KGgoAAAANSUhEUgAAAAEAAAABCAQAAAC1HAwCAAAAC0lEQVR42mNkYAAAAAYAAjCB0C8AAAAASUVORK5CYII="; +``` + +Which is a Base64-encoded 1x1 transparent PNG, **DO NOT USE** `Base64.decode(pngBase64)`.  Use `Base64.atob(pngBase64)` instead.  `Base64.decode()` decodes to UTF-8 string while `Base64.atob()` decodes to bytes, which is compatible to browser built-in `atob()` (Which is absent in node.js).  The same rule applies to the opposite direction. + + +## SEE ALSO + ++ http://en.wikipedia.org/wiki/Base64 diff --git a/js_sdk/js-base64/base64.html b/js_sdk/js-base64/base64.html new file mode 100644 index 0000000..dd18305 --- /dev/null +++ b/js_sdk/js-base64/base64.html @@ -0,0 +1,47 @@ + + + + + +Demo for base64.js + + +

Demo for base64.js

+

$Id: base64.html,v 1.1 2009/03/01 22:00:28 dankogai Exp dankogai $

+ + + + + + + + + + + +
TextBase64 +(URL Safe )
Roundtripiframe w/ data: (no IE)
+ + + + + + diff --git a/js_sdk/js-base64/base64.js b/js_sdk/js-base64/base64.js new file mode 100644 index 0000000..bac1cb2 --- /dev/null +++ b/js_sdk/js-base64/base64.js @@ -0,0 +1,231 @@ +/* + * base64.js + * + * Licensed under the BSD 3-Clause License. + * http://opensource.org/licenses/BSD-3-Clause + * + * References: + * http://en.wikipedia.org/wiki/Base64 + */ +;(function (global, factory) { + typeof exports === 'object' && typeof module !== 'undefined' + ? module.exports = factory(global) + : typeof define === 'function' && define.amd + ? define(factory) : factory(global) +}(( + typeof self !== 'undefined' ? self + : typeof window !== 'undefined' ? window + : typeof global !== 'undefined' ? global +: this +), function(global) { + 'use strict'; + // existing version for noConflict() + var _Base64 = global.Base64; + var version = "2.4.9"; + // if node.js and NOT React Native, we use Buffer + var buffer; + if (typeof module !== 'undefined' && module.exports) { + try { + buffer = eval("require('buffer').Buffer"); + } catch (err) { + buffer = undefined; + } + } + // constants + var b64chars + = 'ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/'; + var b64tab = function(bin) { + var t = {}; + for (var i = 0, l = bin.length; i < l; i++) t[bin.charAt(i)] = i; + return t; + }(b64chars); + var fromCharCode = String.fromCharCode; + // encoder stuff + var cb_utob = function(c) { + if (c.length < 2) { + var cc = c.charCodeAt(0); + return cc < 0x80 ? c + : cc < 0x800 ? (fromCharCode(0xc0 | (cc >>> 6)) + + fromCharCode(0x80 | (cc & 0x3f))) + : (fromCharCode(0xe0 | ((cc >>> 12) & 0x0f)) + + fromCharCode(0x80 | ((cc >>> 6) & 0x3f)) + + fromCharCode(0x80 | ( cc & 0x3f))); + } else { + var cc = 0x10000 + + (c.charCodeAt(0) - 0xD800) * 0x400 + + (c.charCodeAt(1) - 0xDC00); + return (fromCharCode(0xf0 | ((cc >>> 18) & 0x07)) + + fromCharCode(0x80 | ((cc >>> 12) & 0x3f)) + + fromCharCode(0x80 | ((cc >>> 6) & 0x3f)) + + fromCharCode(0x80 | ( cc & 0x3f))); + } + }; + var re_utob = /[\uD800-\uDBFF][\uDC00-\uDFFFF]|[^\x00-\x7F]/g; + var utob = function(u) { + return u.replace(re_utob, cb_utob); + }; + var cb_encode = function(ccc) { + var padlen = [0, 2, 1][ccc.length % 3], + ord = ccc.charCodeAt(0) << 16 + | ((ccc.length > 1 ? ccc.charCodeAt(1) : 0) << 8) + | ((ccc.length > 2 ? ccc.charCodeAt(2) : 0)), + chars = [ + b64chars.charAt( ord >>> 18), + b64chars.charAt((ord >>> 12) & 63), + padlen >= 2 ? '=' : b64chars.charAt((ord >>> 6) & 63), + padlen >= 1 ? '=' : b64chars.charAt(ord & 63) + ]; + return chars.join(''); + }; + var btoa = global.btoa ? function(b) { + return global.btoa(b); + } : function(b) { + return b.replace(/[\s\S]{1,3}/g, cb_encode); + }; + var _encode = buffer ? + buffer.from && Uint8Array && buffer.from !== Uint8Array.from + ? function (u) { + return (u.constructor === buffer.constructor ? u : buffer.from(u)) + .toString('base64') + } + : function (u) { + return (u.constructor === buffer.constructor ? u : new buffer(u)) + .toString('base64') + } + : function (u) { return btoa(utob(u)) } + ; + var encode = function(u, urisafe) { + return !urisafe + ? _encode(String(u)) + : _encode(String(u)).replace(/[+\/]/g, function(m0) { + return m0 == '+' ? '-' : '_'; + }).replace(/=/g, ''); + }; + var encodeURI = function(u) { return encode(u, true) }; + // decoder stuff + var re_btou = new RegExp([ + '[\xC0-\xDF][\x80-\xBF]', + '[\xE0-\xEF][\x80-\xBF]{2}', + '[\xF0-\xF7][\x80-\xBF]{3}' + ].join('|'), 'g'); + var cb_btou = function(cccc) { + switch(cccc.length) { + case 4: + var cp = ((0x07 & cccc.charCodeAt(0)) << 18) + | ((0x3f & cccc.charCodeAt(1)) << 12) + | ((0x3f & cccc.charCodeAt(2)) << 6) + | (0x3f & cccc.charCodeAt(3)), + offset = cp - 0x10000; + return (fromCharCode((offset >>> 10) + 0xD800) + + fromCharCode((offset & 0x3FF) + 0xDC00)); + case 3: + return fromCharCode( + ((0x0f & cccc.charCodeAt(0)) << 12) + | ((0x3f & cccc.charCodeAt(1)) << 6) + | (0x3f & cccc.charCodeAt(2)) + ); + default: + return fromCharCode( + ((0x1f & cccc.charCodeAt(0)) << 6) + | (0x3f & cccc.charCodeAt(1)) + ); + } + }; + var btou = function(b) { + return b.replace(re_btou, cb_btou); + }; + var cb_decode = function(cccc) { + var len = cccc.length, + padlen = len % 4, + n = (len > 0 ? b64tab[cccc.charAt(0)] << 18 : 0) + | (len > 1 ? b64tab[cccc.charAt(1)] << 12 : 0) + | (len > 2 ? b64tab[cccc.charAt(2)] << 6 : 0) + | (len > 3 ? b64tab[cccc.charAt(3)] : 0), + chars = [ + fromCharCode( n >>> 16), + fromCharCode((n >>> 8) & 0xff), + fromCharCode( n & 0xff) + ]; + chars.length -= [0, 0, 2, 1][padlen]; + return chars.join(''); + }; + var atob = global.atob ? function(a) { + return global.atob(a); + } : function(a){ + return a.replace(/[\s\S]{1,4}/g, cb_decode); + }; + var _decode = buffer ? + buffer.from && Uint8Array && buffer.from !== Uint8Array.from + ? function(a) { + return (a.constructor === buffer.constructor + ? a : buffer.from(a, 'base64')).toString(); + } + : function(a) { + return (a.constructor === buffer.constructor + ? a : new buffer(a, 'base64')).toString(); + } + : function(a) { return btou(atob(a)) }; + var decode = function(a){ + return _decode( + String(a).replace(/[-_]/g, function(m0) { return m0 == '-' ? '+' : '/' }) + .replace(/[^A-Za-z0-9\+\/]/g, '') + ); + }; + var noConflict = function() { + var Base64 = global.Base64; + global.Base64 = _Base64; + return Base64; + }; + // export Base64 + global.Base64 = { + VERSION: version, + atob: atob, + btoa: btoa, + fromBase64: decode, + toBase64: encode, + utob: utob, + encode: encode, + encodeURI: encodeURI, + btou: btou, + decode: decode, + noConflict: noConflict, + __buffer__: buffer + }; + // if ES5 is available, make Base64.extendString() available + if (typeof Object.defineProperty === 'function') { + var noEnum = function(v){ + return {value:v,enumerable:false,writable:true,configurable:true}; + }; + global.Base64.extendString = function () { + Object.defineProperty( + String.prototype, 'fromBase64', noEnum(function () { + return decode(this) + })); + Object.defineProperty( + String.prototype, 'toBase64', noEnum(function (urisafe) { + return encode(this, urisafe) + })); + Object.defineProperty( + String.prototype, 'toBase64URI', noEnum(function () { + return encode(this, true) + })); + }; + } + // + // export Base64 to the namespace + // + if (global['Meteor']) { // Meteor.js + Base64 = global.Base64; + } + // module.exports and AMD are mutually exclusive. + // module.exports has precedence. + if (typeof module !== 'undefined' && module.exports) { + module.exports.Base64 = global.Base64; + } + else if (typeof define === 'function' && define.amd) { + // AMD. Register as an anonymous module. + define([], function(){ return global.Base64 }); + } + // that's it! + return {Base64: global.Base64} +})); diff --git a/js_sdk/js-base64/base64.min.js b/js_sdk/js-base64/base64.min.js new file mode 100644 index 0000000..df072aa --- /dev/null +++ b/js_sdk/js-base64/base64.min.js @@ -0,0 +1 @@ +(function(global,factory){typeof exports==="object"&&typeof module!=="undefined"?module.exports=factory(global):typeof define==="function"&&define.amd?define(factory):factory(global)})(typeof self!=="undefined"?self:typeof window!=="undefined"?window:typeof global!=="undefined"?global:this,function(global){"use strict";var _Base64=global.Base64;var version="2.4.9";var buffer;if(typeof module!=="undefined"&&module.exports){try{buffer=eval("require('buffer').Buffer")}catch(err){buffer=undefined}}var b64chars="ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/";var b64tab=function(bin){var t={};for(var i=0,l=bin.length;i>>6)+fromCharCode(128|cc&63):fromCharCode(224|cc>>>12&15)+fromCharCode(128|cc>>>6&63)+fromCharCode(128|cc&63)}else{var cc=65536+(c.charCodeAt(0)-55296)*1024+(c.charCodeAt(1)-56320);return fromCharCode(240|cc>>>18&7)+fromCharCode(128|cc>>>12&63)+fromCharCode(128|cc>>>6&63)+fromCharCode(128|cc&63)}};var re_utob=/[\uD800-\uDBFF][\uDC00-\uDFFFF]|[^\x00-\x7F]/g;var utob=function(u){return u.replace(re_utob,cb_utob)};var cb_encode=function(ccc){var padlen=[0,2,1][ccc.length%3],ord=ccc.charCodeAt(0)<<16|(ccc.length>1?ccc.charCodeAt(1):0)<<8|(ccc.length>2?ccc.charCodeAt(2):0),chars=[b64chars.charAt(ord>>>18),b64chars.charAt(ord>>>12&63),padlen>=2?"=":b64chars.charAt(ord>>>6&63),padlen>=1?"=":b64chars.charAt(ord&63)];return chars.join("")};var btoa=global.btoa?function(b){return global.btoa(b)}:function(b){return b.replace(/[\s\S]{1,3}/g,cb_encode)};var _encode=buffer?buffer.from&&Uint8Array&&buffer.from!==Uint8Array.from?function(u){return(u.constructor===buffer.constructor?u:buffer.from(u)).toString("base64")}:function(u){return(u.constructor===buffer.constructor?u:new buffer(u)).toString("base64")}:function(u){return btoa(utob(u))};var encode=function(u,urisafe){return!urisafe?_encode(String(u)):_encode(String(u)).replace(/[+\/]/g,function(m0){return m0=="+"?"-":"_"}).replace(/=/g,"")};var encodeURI=function(u){return encode(u,true)};var re_btou=new RegExp(["[À-ß][€-¿]","[à-ï][€-¿]{2}","[ð-÷][€-¿]{3}"].join("|"),"g");var cb_btou=function(cccc){switch(cccc.length){case 4:var cp=(7&cccc.charCodeAt(0))<<18|(63&cccc.charCodeAt(1))<<12|(63&cccc.charCodeAt(2))<<6|63&cccc.charCodeAt(3),offset=cp-65536;return fromCharCode((offset>>>10)+55296)+fromCharCode((offset&1023)+56320);case 3:return fromCharCode((15&cccc.charCodeAt(0))<<12|(63&cccc.charCodeAt(1))<<6|63&cccc.charCodeAt(2));default:return fromCharCode((31&cccc.charCodeAt(0))<<6|63&cccc.charCodeAt(1))}};var btou=function(b){return b.replace(re_btou,cb_btou)};var cb_decode=function(cccc){var len=cccc.length,padlen=len%4,n=(len>0?b64tab[cccc.charAt(0)]<<18:0)|(len>1?b64tab[cccc.charAt(1)]<<12:0)|(len>2?b64tab[cccc.charAt(2)]<<6:0)|(len>3?b64tab[cccc.charAt(3)]:0),chars=[fromCharCode(n>>>16),fromCharCode(n>>>8&255),fromCharCode(n&255)];chars.length-=[0,0,2,1][padlen];return chars.join("")};var atob=global.atob?function(a){return global.atob(a)}:function(a){return a.replace(/[\s\S]{1,4}/g,cb_decode)};var _decode=buffer?buffer.from&&Uint8Array&&buffer.from!==Uint8Array.from?function(a){return(a.constructor===buffer.constructor?a:buffer.from(a,"base64")).toString()}:function(a){return(a.constructor===buffer.constructor?a:new buffer(a,"base64")).toString()}:function(a){return btou(atob(a))};var decode=function(a){return _decode(String(a).replace(/[-_]/g,function(m0){return m0=="-"?"+":"/"}).replace(/[^A-Za-z0-9\+\/]/g,""))};var noConflict=function(){var Base64=global.Base64;global.Base64=_Base64;return Base64};global.Base64={VERSION:version,atob:atob,btoa:btoa,fromBase64:decode,toBase64:encode,utob:utob,encode:encode,encodeURI:encodeURI,btou:btou,decode:decode,noConflict:noConflict,__buffer__:buffer};if(typeof Object.defineProperty==="function"){var noEnum=function(v){return{value:v,enumerable:false,writable:true,configurable:true}};global.Base64.extendString=function(){Object.defineProperty(String.prototype,"fromBase64",noEnum(function(){return decode(this)}));Object.defineProperty(String.prototype,"toBase64",noEnum(function(urisafe){return encode(this,urisafe)}));Object.defineProperty(String.prototype,"toBase64URI",noEnum(function(){return encode(this,true)}))}}if(global["Meteor"]){Base64=global.Base64}if(typeof module!=="undefined"&&module.exports){module.exports.Base64=global.Base64}else if(typeof define==="function"&&define.amd){define([],function(){return global.Base64})}return{Base64:global.Base64}}); \ No newline at end of file diff --git a/js_sdk/js-base64/bower.json b/js_sdk/js-base64/bower.json new file mode 100644 index 0000000..1a6df79 --- /dev/null +++ b/js_sdk/js-base64/bower.json @@ -0,0 +1,18 @@ +{ + "name": "js-base64", + "version": "2.4.9", + "license": "BSD-3-Clause", + "main": [ + "./base64.js" + ], + "ignore": [ + "old", + "test", + ".gitignore", + ".travis.yml", + "base64.html", + "package.json" + ], + "dependencies": { + } +} diff --git a/js_sdk/js-base64/package.js b/js_sdk/js-base64/package.js new file mode 100644 index 0000000..5b56425 --- /dev/null +++ b/js_sdk/js-base64/package.js @@ -0,0 +1,9 @@ +Package.describe({ + summary: "Yet another Base64 transcoder" +}) + +Package.on_use(function(api){ + api.export('Base64'); + + api.add_files(['base64.js'], 'server'); +}); \ No newline at end of file diff --git a/js_sdk/js-base64/package.json b/js_sdk/js-base64/package.json new file mode 100644 index 0000000..ea1aa18 --- /dev/null +++ b/js_sdk/js-base64/package.json @@ -0,0 +1,59 @@ +{ + "_from": "js-base64", + "_id": "js-base64@2.4.9", + "_inBundle": false, + "_integrity": "sha512-xcinL3AuDJk7VSzsHgb9DvvIXayBbadtMZ4HFPx8rUszbW1MuNMlwYVC4zzCZ6e1sqZpnNS5ZFYOhXqA39T7LQ==", + "_location": "/js-base64", + "_phantomChildren": {}, + "_requested": { + "type": "tag", + "registry": true, + "raw": "js-base64", + "name": "js-base64", + "escapedName": "js-base64", + "rawSpec": "", + "saveSpec": null, + "fetchSpec": "latest" + }, + "_requiredBy": [ + "#DEV:/", + "#USER" + ], + "_resolved": "https://registry.npmjs.org/js-base64/-/js-base64-2.4.9.tgz", + "_shasum": "748911fb04f48a60c4771b375cac45a80df11c03", + "_spec": "js-base64", + "_where": "C:\\Users\\dcloud\\Documents\\HBuilderProjects\\test-npm", + "author": { + "name": "Dan Kogai" + }, + "bugs": { + "url": "https://github.com/dankogai/js-base64/issues" + }, + "bundleDependencies": false, + "deprecated": false, + "description": "Yet another Base64 transcoder in pure-JS", + "devDependencies": { + "babel-preset-env": "^1.7.0", + "babel-register": "^6.26.0", + "mocha": "*" + }, + "directories": { + "test": "test" + }, + "gitHead": "8bfa436f733bec60c95c720e1d720c28b43ae0b2", + "homepage": "https://github.com/dankogai/js-base64#readme", + "keywords": [ + "base64" + ], + "license": "BSD-3-Clause", + "main": "base64.js", + "name": "js-base64", + "repository": { + "type": "git", + "url": "git://github.com/dankogai/js-base64.git" + }, + "scripts": { + "test": "mocha --compilers js:babel-register" + }, + "version": "2.4.9" +} diff --git a/js_sdk/js-base64/test/dankogai.js b/js_sdk/js-base64/test/dankogai.js new file mode 100644 index 0000000..b631414 --- /dev/null +++ b/js_sdk/js-base64/test/dankogai.js @@ -0,0 +1,44 @@ +/* + * $Id: dankogai.js,v 0.4 2012/08/24 05:23:18 dankogai Exp dankogai $ + * + * use mocha to test me + * http://visionmedia.github.com/mocha/ + */ +var assert = assert || require("assert"); +var Base64 = Base64 || require('../base64.js').Base64; +var is = function (a, e, m) { + return function () { + assert.equal(a, e, m) + } +}; + +describe('basic', function () { + it('d', is(Base64.encode('d'), 'ZA==')); + it('da', is(Base64.encode('da'), 'ZGE=')); + it('dan', is(Base64.encode('dan'), 'ZGFu')); + it('ZA==', is(Base64.decode('ZA=='), 'd' )); + it('ZGE=', is(Base64.decode('ZGE='), 'da' )); + it('ZGFu', is(Base64.decode('ZGFu'), 'dan' )); +}); + +describe('whitespace', function () { + it('Z A==', is(Base64.decode('ZA =='), 'd' )); + it('ZG E=', is(Base64.decode('ZG E='), 'da' )); + it('ZGF u', is(Base64.decode('ZGF u'), 'dan' )); +}); + +describe('null', function () { + it('\\0', is(Base64.encode('\0'), 'AA==')); + it('\\0\\0', is(Base64.encode('\0\0'), 'AAA=')); + it('\\0\\0\\0', is(Base64.encode('\0\0\0'), 'AAAA')); + it('AA==', is(Base64.decode('AA=='), '\0' )); + it('AAA=', is(Base64.decode('AAA='), '\0\0' )); + it('AAAA', is(Base64.decode('AAAA'), '\0\0\0')); +}); + +describe('Base64', function () { + it('.encode', is(Base64.encode('小飼弾'), '5bCP6aO85by+')); + it('.encodeURI', is(Base64.encodeURI('小飼弾'), '5bCP6aO85by-')); + it('.decode', is(Base64.decode('5bCP6aO85by+'), '小飼弾')); + it('.decode', is(Base64.decode('5bCP6aO85by-'), '小飼弾')); +}); diff --git a/js_sdk/js-base64/test/es5.js b/js_sdk/js-base64/test/es5.js new file mode 100644 index 0000000..ef134f6 --- /dev/null +++ b/js_sdk/js-base64/test/es5.js @@ -0,0 +1,24 @@ +/* + * $Id: es5.js,v 0.1 2012/08/23 19:43:17 dankogai Exp dankogai $ + * + * use mocha to test me + * http://visionmedia.github.com/mocha/ + */ +var assert = assert || require("assert"); +var Base64 = Base64 || require('../base64.js').Base64; +var is = function (a, e, m) { + return function () { + assert.equal(a, e, m) + } +}; + +if ('extendString' in Base64){ + Base64.extendString(); + describe('String', function () { + it('.toBase64', is('小飼弾'.toBase64(), '5bCP6aO85by+')); + it('.toBase64', is('小飼弾'.toBase64(true), '5bCP6aO85by-')); + it('.toBase64URI', is('小飼弾'.toBase64URI(), '5bCP6aO85by-')); + it('.fromBase64', is('5bCP6aO85by+'.fromBase64(), '小飼弾')); + it('.fromBase64', is('5bCP6aO85by-'.fromBase64(), '小飼弾')); + }); +} diff --git a/js_sdk/js-base64/test/es6.js b/js_sdk/js-base64/test/es6.js new file mode 100644 index 0000000..7dbe475 --- /dev/null +++ b/js_sdk/js-base64/test/es6.js @@ -0,0 +1,25 @@ +/* + * $Id: es6.js,v 0.1 2017/11/29 21:43:17 ufolux Exp ufolux $ + * + * use mocha to test me + * http://visionmedia.github.com/mocha/ + */ +import {Base64} from '../base64' + +var assert = assert || require("assert"); +var is = function (a, e, m) { + return function () { + assert.equal(a, e, m) + } +}; + +if ('extendString' in Base64){ + Base64.extendString(); + describe('String', function () { + it('.toBase64', is('小飼弾'.toBase64(), '5bCP6aO85by+')); + it('.toBase64', is('小飼弾'.toBase64(true), '5bCP6aO85by-')); + it('.toBase64URI', is('小飼弾'.toBase64URI(), '5bCP6aO85by-')); + it('.fromBase64', is('5bCP6aO85by+'.fromBase64(), '小飼弾')); + it('.fromBase64', is('5bCP6aO85by-'.fromBase64(), '小飼弾')); + }); +} diff --git a/js_sdk/js-base64/test/index.html b/js_sdk/js-base64/test/index.html new file mode 100644 index 0000000..4232d33 --- /dev/null +++ b/js_sdk/js-base64/test/index.html @@ -0,0 +1,39 @@ + + + + Mocha Tests + + + +
+ + + + + + + + + + + + + + + $Id: index.html,v 0.3 2017/09/11 08:43:43 dankogai Exp dankogai $ +
+ + diff --git a/js_sdk/js-base64/test/large.js b/js_sdk/js-base64/test/large.js new file mode 100644 index 0000000..20d7842 --- /dev/null +++ b/js_sdk/js-base64/test/large.js @@ -0,0 +1,25 @@ +/* + * $Id: large.js,v 0.3 2012/08/23 19:14:37 dankogai Exp dankogai $ + * + * use mocha to test me + * http://visionmedia.github.com/mocha/ + */ +var assert = assert || require("assert"); +var Base64 = Base64 || require('../base64.js').Base64; +var is = function (a, e, m) { + return function () { + assert.equal(a, e, m) + } +}; +var seed = function () { + var a, i; + for (a = [], i = 0; i < 256; i++) { + a.push(String.fromCharCode(i)); + } + return a.join(''); +}(); +describe('Base64', function () { + for (var i = 0, str = seed; i < 16; str += str, i++) { + it(''+str.length, is(Base64.decode(Base64.encode(str)), str)); + } +}); diff --git a/js_sdk/js-base64/test/yoshinoya.js b/js_sdk/js-base64/test/yoshinoya.js new file mode 100644 index 0000000..4576c79 --- /dev/null +++ b/js_sdk/js-base64/test/yoshinoya.js @@ -0,0 +1,19 @@ +/* + * use mocha to test me + * http://visionmedia.github.com/mocha/ + */ +var assert = assert || require("assert"); +var Base64 = Base64 || require('../base64.js').Base64; +var is = function (a, e, m) { + return function () { + assert.equal(a, e, m) + } +}; + +describe('Yoshinoya', function () { + it('.encode', is(Base64.encode('𠮷野家'), '8KCut+mHjuWutg==')); + it('.encodeURI', is(Base64.encodeURI('𠮷野家'), '8KCut-mHjuWutg')); + it('.decode', is(Base64.decode('8KCut+mHjuWutg=='), '𠮷野家')); + it('.decode', is(Base64.decode('8KCut-mHjuWutg'), '𠮷野家')); + /* it('.decode', is(Base64.decode('7aGC7b636YeO5a62'), '𠮷野家')); */ +}); diff --git a/main.js b/main.js new file mode 100644 index 0000000..3ddcaeb --- /dev/null +++ b/main.js @@ -0,0 +1,38 @@ +// 设置env配置文件 +import envConfig from '@/env/config.js' +// 全局配置项 +import appConfig from '@/config/appConfig.js' +import storageManage from '@/commons/utils/storageManage.js' +import uviewPlus from 'uview-plus' + +// 设置node环境 +envConfig.changeEnv(storageManage.env()) + +// #ifndef VUE3 + +import App from './App' + +import Vue from 'vue' +Vue.config.productionTip = false + +App.mpType = 'app' + +const app = new Vue({ + ...App +}) +app.$mount() +// #endif + +// #ifdef VUE3 +import { createSSRApp } from 'vue' +import App from './App.vue' +export function createApp() { + const app = createSSRApp(App) + app.use(uviewPlus) + app.config.globalProperties.$appName = appConfig.appName + uni.$appName = appConfig.appName + return { + app + } +} +// #endif \ No newline at end of file diff --git a/manifest.json b/manifest.json new file mode 100644 index 0000000..aaae265 --- /dev/null +++ b/manifest.json @@ -0,0 +1,249 @@ +{ + "name" : "银收客", + "appid" : "__UNI__02A31D8", + "description" : "", + "versionName" : "1.0.2", + "versionCode" : 100, + "transformPx" : false, + "app-plus" : { + /* 5+App特有相关 */ + "usingComponents" : true, + "nvueCompiler" : "uni-app", + "nvueStyleCompiler" : "uni-app", + "splashscreen" : { + "alwaysShowBeforeRender" : true, + "waiting" : true, + "autoclose" : true, + "delay" : 0 + }, + "modules" : { + "Canvas" : "nvue canvas", //使用Canvas模块 + "Geolocation" : {}, + "Maps" : {}, + "Barcode" : {}, + "Camera" : {} + }, + /* 模块配置 */ + "distribute" : { + /* 应用发布信息 */ + "android" : { + /* android打包配置 */ + "permissions" : [ + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "", + "" + ], + "abiFilters" : [ "armeabi-v7a" ], + "permissionExternalStorage" : { + "request" : "none", + "prompt" : "应用保存运行状态等信息,需要获取读写手机存储(系统提示为访问设备上的照片、媒体内容和文件)权限,请允许。" + }, + "permissionPhoneState" : { + "request" : "none", + "prompt" : "为保证您正常、安全地使用,需要获取设备识别码(部分手机提示为获取手机号码)使用权限,请允许。" + }, + "autoSdkPermissions" : true, + "targetSdkVersion" : 26, + "minSdkVersion" : 21 + }, + "ios" : { + "dSYMs" : false + }, + /* ios打包配置 */ + "sdkConfigs" : { + "geolocation" : { + "amap" : { + "__platform__" : [ "ios", "android" ], + "appkey_ios" : "0b9be2631525ee5e218ac26d333f215c", + "appkey_android" : "9d1e62050f8558a082f7aa3ad5bb3c68" + } + }, + "maps" : { + "amap" : { + "appkey_ios" : "0b9be2631525ee5e218ac26d333f215c", + "appkey_android" : "9d1e62050f8558a082f7aa3ad5bb3c68" + } + }, + "ad" : {}, + "push" : {} + }, + "icons" : { + "android" : { + "hdpi" : "unpackage/res/icons/72x72.png", + "xhdpi" : "unpackage/res/icons/96x96.png", + "xxhdpi" : "unpackage/res/icons/144x144.png", + "xxxhdpi" : "unpackage/res/icons/192x192.png" + }, + "ios" : { + "appstore" : "unpackage/res/icons/1024x1024.png", + "ipad" : { + "app" : "unpackage/res/icons/76x76.png", + "app@2x" : "unpackage/res/icons/152x152.png", + "notification" : "unpackage/res/icons/20x20.png", + "notification@2x" : "unpackage/res/icons/40x40.png", + "proapp@2x" : "unpackage/res/icons/167x167.png", + "settings" : "unpackage/res/icons/29x29.png", + "settings@2x" : "unpackage/res/icons/58x58.png", + "spotlight" : "unpackage/res/icons/40x40.png", + "spotlight@2x" : "unpackage/res/icons/80x80.png" + }, + "iphone" : { + "app@2x" : "unpackage/res/icons/120x120.png", + "app@3x" : "unpackage/res/icons/180x180.png", + "notification@2x" : "unpackage/res/icons/40x40.png", + "notification@3x" : "unpackage/res/icons/60x60.png", + "settings@2x" : "unpackage/res/icons/58x58.png", + "settings@3x" : "unpackage/res/icons/87x87.png", + "spotlight@2x" : "unpackage/res/icons/80x80.png", + "spotlight@3x" : "unpackage/res/icons/120x120.png" + } + } + }, + "splashscreen" : { + "androidStyle" : "common", + "android" : { + "hdpi" : "E:/oem-infos/0.收银呗科技/前端打包文件/商户通/启动图/480.png", + "xhdpi" : "E:/oem-infos/0.收银呗科技/前端打包文件/商户通/启动图/720.png", + "xxhdpi" : "E:/oem-infos/0.收银呗科技/前端打包文件/商户通/启动图/1080.png" + }, + "useOriginalMsgbox" : true + } + } + }, + /* SDK配置 */ + "quickapp" : {}, + /* 快应用特有相关 */ + "mp-weixin" : { + "appid" : "wxcf0fe8cdba153fd6", + "setting" : { + "urlCheck" : false, + "minified" : true, + "postcss" : true, + "es6" : true + }, + "optimization" : { + "subPackages" : true + }, + "usingComponents" : true, + "permission" : { + "scope.userLocation" : { + "desc" : "您的位置信息将用于确定门店位置" + } + }, + "requiredPrivateInfos" : [ "chooseLocation", "getLocation" ], + "unipush" : { + "enable" : true + }, + // "plugins" : { + // "WechatSI" : { + // "version" : "0.3.5", + // "provider" : "wx069ba97219f66d99" + // } + // }, + "requiredBackgroundModes" : [ "audio", "location" ], + "__usePrivacyCheck__" : true, + "libVersion" : "latest" + }, + "vueVersion" : "3", + "h5" : { + "unipush" : { + "enable" : true + }, + "devServer" : { + "disableHostCheck" : true, + "proxy" : { + "/shopApi" : { + // 需要被代理的后台地址 + "target" : "https://wxcashiertest.sxczgkj.cn/cashierService", + "changeOrigin" : true, + "secure" : false, + "pathRewrite" : { + "^/shopApi" : "" + } + }, + "/mch" : { + // 需要被代理的后台地址 + "target" : "https://b.rscygroup.com", + "changeOrigin" : true, + "secure" : false, + "pathRewrite" : { + "^/mch" : "" + } + }, + "/server1" : { + // 需要被代理的后台地址 + "target" : "http://101.37.12.135:8080", + "changeOrigin" : true, + "secure" : false, + "pathRewrite" : { + "^/server1" : "" + } + }, + "/server3" : { + // 需要被代理的后台地址 + "target" : "http://101.37.12.135:8080", + "changeOrigin" : true, + "secure" : false, + "pathRewrite" : { + "^/server3" : "" + } + }, + "/ysk" : { + // 需要被代理的后台地址 + "target" : "https://admintestpapi.sxczgkj.cn", + "changeOrigin" : true, + "secure" : false, + "pathRewrite" : { + "/ysk" : "" + } + }, + "/yufabu" : { + // 需要被代理的后台地址 + "target" : "https://pre-cashier.sxczgkj.cn", + "changeOrigin" : true, + "secure" : false, + "pathRewrite" : { + "/yufabu" : "" + } + }, + "/ww" : { + // 需要被代理的后台地址 + "target" : "http://192.168.1.15:8000", + "changeOrigin" : true, + "secure" : false, + "pathRewrite" : { + "/ww" : "" + } + } + } + }, + "sdkConfigs" : { + "maps" : { + "amap" : { + "key" : "6033c97e67bf2e9ceac306e1a3fa35f8", + "securityJsCode" : "0547b69252ef0ed14e11f5c4ac152f07", + "serviceHost" : "" + } + } + } + }, + "mp-alipay" : { + "appid" : "2021004128648214" + } +} diff --git a/package-lock.json b/package-lock.json new file mode 100644 index 0000000..0e18f38 --- /dev/null +++ b/package-lock.json @@ -0,0 +1,629 @@ +{ + "requires": true, + "lockfileVersion": 1, + "dependencies": { + "@nodelib/fs.scandir": { + "version": "2.1.5", + "resolved": "https://registry.npmmirror.com/@nodelib/fs.scandir/-/fs.scandir-2.1.5.tgz", + "integrity": "sha512-vq24Bq3ym5HEQm2NKCr3yXDwjc7vTsEThRDnkp2DK9p1uqLR+DHurm/NOTo0KG7HYHU7eppKZj3MyqYuMBf62g==", + "dev": true, + "requires": { + "@nodelib/fs.stat": "2.0.5", + "run-parallel": "^1.1.9" + } + }, + "@nodelib/fs.stat": { + "version": "2.0.5", + "resolved": "https://registry.npmmirror.com/@nodelib/fs.stat/-/fs.stat-2.0.5.tgz", + "integrity": "sha512-RkhPPp2zrqDAQA/2jNhnztcPAlv64XdhIp7a7454A5ovI7Bukxgt7MX7udwAu3zg1DcpPU0rz3VV1SeaqvY4+A==", + "dev": true + }, + "@nodelib/fs.walk": { + "version": "1.2.8", + "resolved": "https://registry.npmmirror.com/@nodelib/fs.walk/-/fs.walk-1.2.8.tgz", + "integrity": "sha512-oGB+UxlgWcgQkgwo8GcEGwemoTFt3FIO9ababBmaGwXIoBKZ+GTy0pP185beGg7Llih/NSHSV2XAs1lnznocSg==", + "dev": true, + "requires": { + "@nodelib/fs.scandir": "2.1.5", + "fastq": "^1.6.0" + } + }, + "@sindresorhus/merge-streams": { + "version": "2.3.0", + "resolved": "https://registry.npmmirror.com/@sindresorhus/merge-streams/-/merge-streams-2.3.0.tgz", + "integrity": "sha512-LtoMMhxAlorcGhmFYI+LhPgbPZCkgP6ra1YL604EeF6U98pLlQ3iWIGMdWSC+vWmPBWBNgmDBAhnAobLROJmwg==", + "dev": true + }, + "@types/json-schema": { + "version": "7.0.15", + "resolved": "https://registry.npmmirror.com/@types/json-schema/-/json-schema-7.0.15.tgz", + "integrity": "sha512-5+fP8P8MFNC+AyZCDxrB2pkZFPGzqQWUzpSeuuVLvm8VMcorNYavBqoFcxK8bQz4Qsbn4oUEEem4wDLfcysGHA==", + "dev": true + }, + "ajv": { + "version": "8.16.0", + "resolved": "https://registry.npmmirror.com/ajv/-/ajv-8.16.0.tgz", + "integrity": "sha512-F0twR8U1ZU67JIEtekUcLkXkoO5mMMmgGD8sK/xUFzJ805jxHQl92hImFAqqXMyMYjSPOyUPAwHYhB72g5sTXw==", + "dev": true, + "requires": { + "fast-deep-equal": "^3.1.3", + "json-schema-traverse": "^1.0.0", + "require-from-string": "^2.0.2", + "uri-js": "^4.4.1" + } + }, + "ajv-formats": { + "version": "2.1.1", + "resolved": "https://registry.npmmirror.com/ajv-formats/-/ajv-formats-2.1.1.tgz", + "integrity": "sha512-Wx0Kx52hxE7C18hkMEggYlEifqWZtYaRgouJor+WMdPnQyEK13vgEWyVNup7SoeeoLMsr4kf5h6dOW11I15MUA==", + "dev": true, + "requires": { + "ajv": "^8.0.0" + } + }, + "ajv-keywords": { + "version": "5.1.0", + "resolved": "https://registry.npmmirror.com/ajv-keywords/-/ajv-keywords-5.1.0.tgz", + "integrity": "sha512-YCS/JNFAUyr5vAuhk1DWm1CBxRHW9LbJ2ozWeemrIqpbsqKjHVxYPyi5GC0rjZIT5JxJ3virVTS8wk4i/Z+krw==", + "dev": true, + "requires": { + "fast-deep-equal": "^3.1.3" + } + }, + "anymatch": { + "version": "3.1.3", + "resolved": "https://registry.npmmirror.com/anymatch/-/anymatch-3.1.3.tgz", + "integrity": "sha512-KMReFUr0B4t+D+OBkjR3KYqvocp2XaSzO55UcB6mgQMd3KbcE+mWTyvVV7D/zsdEbNnV6acZUutkiHQXvTr1Rw==", + "dev": true, + "requires": { + "normalize-path": "^3.0.0", + "picomatch": "^2.0.4" + } + }, + "base64-js": { + "version": "1.5.1", + "resolved": "https://registry.npmmirror.com/base64-js/-/base64-js-1.5.1.tgz", + "integrity": "sha512-AKpaYlHn8t4SVbOHCy+b5+KKgvR4vrsD8vbvrbiQJps7fKDTkjkDry6ji0rUJjC0kzbNePLwzxq8iypo41qeWA==" + }, + "big.js": { + "version": "5.2.2", + "resolved": "https://registry.npmmirror.com/big.js/-/big.js-5.2.2.tgz", + "integrity": "sha512-vyL2OymJxmarO8gxMr0mhChsO9QGwhynfuu4+MHTAW6czfq9humCB7rKpUjDd9YUiDPU4mzpyupFSvOClAwbmQ==", + "dev": true + }, + "binary-extensions": { + "version": "2.3.0", + "resolved": "https://registry.npmmirror.com/binary-extensions/-/binary-extensions-2.3.0.tgz", + "integrity": "sha512-Ceh+7ox5qe7LJuLHoY0feh3pHuUDHAcRUeyL2VYghZwfpkNIy/+8Ocg0a3UuSoYzavmylwuLWQOf3hl0jjMMIw==", + "dev": true + }, + "braces": { + "version": "3.0.3", + "resolved": "https://registry.npmmirror.com/braces/-/braces-3.0.3.tgz", + "integrity": "sha512-yQbXgO/OSZVD2IsiLlro+7Hf6Q18EJrKSEsdoMzKePKXct3gvD8oLcOQdIzGupr5Fj+EDe8gO/lxc1BzfMpxvA==", + "dev": true, + "requires": { + "fill-range": "^7.1.1" + } + }, + "buffer": { + "version": "5.7.1", + "resolved": "https://registry.npmmirror.com/buffer/-/buffer-5.7.1.tgz", + "integrity": "sha512-EHcyIPBQ4BSGlvjB16k5KgAJ27CIsHY/2JBmCRReo48y9rQ3MaUzWX3KVlBa4U7MyX02HdVj0K7C3WaB3ju7FQ==", + "requires": { + "base64-js": "^1.3.1", + "ieee754": "^1.1.13" + } + }, + "chokidar": { + "version": "3.6.0", + "resolved": "https://registry.npmmirror.com/chokidar/-/chokidar-3.6.0.tgz", + "integrity": "sha512-7VT13fmjotKpGipCW9JEQAusEPE+Ei8nl6/g4FBAmIm0GOOLMua9NDDo/DWp0ZAxCr3cPq5ZpBqmPAQgDda2Pw==", + "dev": true, + "requires": { + "anymatch": "~3.1.2", + "braces": "~3.0.2", + "fsevents": "~2.3.2", + "glob-parent": "~5.1.2", + "is-binary-path": "~2.1.0", + "is-glob": "~4.0.1", + "normalize-path": "~3.0.0", + "readdirp": "~3.6.0" + }, + "dependencies": { + "glob-parent": { + "version": "5.1.2", + "resolved": "https://registry.npmmirror.com/glob-parent/-/glob-parent-5.1.2.tgz", + "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", + "dev": true, + "requires": { + "is-glob": "^4.0.1" + } + } + } + }, + "clipboard": { + "version": "2.0.11", + "resolved": "https://registry.npmmirror.com/clipboard/-/clipboard-2.0.11.tgz", + "integrity": "sha512-C+0bbOqkezLIsmWSvlsXS0Q0bmkugu7jcfMIACB+RDEntIzQIkdr148we28AfSloQLRdZlYL/QYyrq05j/3Faw==", + "requires": { + "good-listener": "^1.2.2", + "select": "^1.1.2", + "tiny-emitter": "^2.0.0" + } + }, + "copy-webpack-plugin": { + "version": "12.0.2", + "resolved": "https://registry.npmmirror.com/copy-webpack-plugin/-/copy-webpack-plugin-12.0.2.tgz", + "integrity": "sha512-SNwdBeHyII+rWvee/bTnAYyO8vfVdcSTud4EIb6jcZ8inLeWucJE0DnxXQBjlQ5zlteuuvooGQy3LIyGxhvlOA==", + "dev": true, + "requires": { + "fast-glob": "^3.3.2", + "glob-parent": "^6.0.1", + "globby": "^14.0.0", + "normalize-path": "^3.0.0", + "schema-utils": "^4.2.0", + "serialize-javascript": "^6.0.2" + } + }, + "dayjs": { + "version": "1.11.13", + "resolved": "https://registry.npmmirror.com/dayjs/-/dayjs-1.11.13.tgz", + "integrity": "sha512-oaMBel6gjolK862uaPQOVTA7q3TZhuSvuMQAAglQDOWYO9A91IrAOUJEyKVlqJlHE0vq5p5UXxzdPfMH/x6xNg==" + }, + "delegate": { + "version": "3.2.0", + "resolved": "https://registry.npmmirror.com/delegate/-/delegate-3.2.0.tgz", + "integrity": "sha512-IofjkYBZaZivn0V8nnsMJGBr4jVLxHDheKSW88PyxS5QC4Vo9ZbZVvhzlSxY87fVq3STR6r+4cGepyHkcWOQSw==" + }, + "emojis-list": { + "version": "3.0.0", + "resolved": "https://registry.npmmirror.com/emojis-list/-/emojis-list-3.0.0.tgz", + "integrity": "sha512-/kyM18EfinwXZbno9FyUGeFh87KC8HRQBQGildHZbEuRyWFOmv1U10o9BBp8XVZDVNNuQKyIGIu5ZYAAXJ0V2Q==", + "dev": true + }, + "fast-deep-equal": { + "version": "3.1.3", + "resolved": "https://registry.npmmirror.com/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", + "dev": true + }, + "fast-glob": { + "version": "3.3.2", + "resolved": "https://registry.npmmirror.com/fast-glob/-/fast-glob-3.3.2.tgz", + "integrity": "sha512-oX2ruAFQwf/Orj8m737Y5adxDQO0LAB7/S5MnxCdTNDd4p6BsyIVsv9JQsATbTSq8KHRpLwIHbVlUNatxd+1Ow==", + "dev": true, + "requires": { + "@nodelib/fs.stat": "^2.0.2", + "@nodelib/fs.walk": "^1.2.3", + "glob-parent": "^5.1.2", + "merge2": "^1.3.0", + "micromatch": "^4.0.4" + }, + "dependencies": { + "glob-parent": { + "version": "5.1.2", + "resolved": "https://registry.npmmirror.com/glob-parent/-/glob-parent-5.1.2.tgz", + "integrity": "sha512-AOIgSQCepiJYwP3ARnGx+5VnTu2HBYdzbGP45eLw1vr3zB3vZLeyed1sC9hnbcOc9/SrMyM5RPQrkGz4aS9Zow==", + "dev": true, + "requires": { + "is-glob": "^4.0.1" + } + } + } + }, + "fast-json-stable-stringify": { + "version": "2.1.0", + "resolved": "https://registry.npmmirror.com/fast-json-stable-stringify/-/fast-json-stable-stringify-2.1.0.tgz", + "integrity": "sha512-lhd/wF+Lk98HZoTCtlVraHtfh5XYijIjalXck7saUtuanSDyLMxnHhSXEDJqHxD7msR8D0uCmqlkwjCV8xvwHw==", + "dev": true + }, + "fastq": { + "version": "1.17.1", + "resolved": "https://registry.npmmirror.com/fastq/-/fastq-1.17.1.tgz", + "integrity": "sha512-sRVD3lWVIXWg6By68ZN7vho9a1pQcN/WBFaAAsDDFzlJjvoGx0P8z7V1t72grFJfJhu3YPZBuu25f7Kaw2jN1w==", + "dev": true, + "requires": { + "reusify": "^1.0.4" + } + }, + "fill-range": { + "version": "7.1.1", + "resolved": "https://registry.npmmirror.com/fill-range/-/fill-range-7.1.1.tgz", + "integrity": "sha512-YsGpe3WHLK8ZYi4tWDg2Jy3ebRz2rXowDxnld4bkQB00cc/1Zw9AWnC0i9ztDJitivtQvaI9KaLyKrc+hBW0yg==", + "dev": true, + "requires": { + "to-regex-range": "^5.0.1" + } + }, + "fsevents": { + "version": "2.3.3", + "resolved": "https://registry.npmmirror.com/fsevents/-/fsevents-2.3.3.tgz", + "integrity": "sha512-5xoDfX+fL7faATnagmWPpbFtwh/R77WmMMqqHGS65C3vvB0YHrgF+B1YmZ3441tMj5n63k0212XNoJwzlhffQw==", + "dev": true, + "optional": true + }, + "glob-parent": { + "version": "6.0.2", + "resolved": "https://registry.npmmirror.com/glob-parent/-/glob-parent-6.0.2.tgz", + "integrity": "sha512-XxwI8EOhVQgWp6iDL+3b0r86f4d6AX6zSU55HfB4ydCEuXLXc5FcYeOu+nnGftS4TEju/11rt4KJPTMgbfmv4A==", + "dev": true, + "requires": { + "is-glob": "^4.0.3" + } + }, + "globby": { + "version": "14.0.2", + "resolved": "https://registry.npmmirror.com/globby/-/globby-14.0.2.tgz", + "integrity": "sha512-s3Fq41ZVh7vbbe2PN3nrW7yC7U7MFVc5c98/iTl9c2GawNMKx/J648KQRW6WKkuU8GIbbh2IXfIRQjOZnXcTnw==", + "dev": true, + "requires": { + "@sindresorhus/merge-streams": "^2.1.0", + "fast-glob": "^3.3.2", + "ignore": "^5.2.4", + "path-type": "^5.0.0", + "slash": "^5.1.0", + "unicorn-magic": "^0.1.0" + } + }, + "gm-crypto": { + "version": "0.1.8", + "resolved": "https://registry.npmmirror.com/gm-crypto/-/gm-crypto-0.1.8.tgz", + "integrity": "sha512-gbTkobkbj3F70HJDQNhN9JNTvcR3O1YQJ0xGc8jTc4bZ1KuikmkjuFm5kZhyUbWxK/PwWDpPuTNyGwRYOopBLw==", + "requires": { + "buffer": "^5.7.0", + "jsbn": "^1.1.0", + "to-arraybuffer": "^1.0.1" + } + }, + "good-listener": { + "version": "1.2.2", + "resolved": "https://registry.npmmirror.com/good-listener/-/good-listener-1.2.2.tgz", + "integrity": "sha512-goW1b+d9q/HIwbVYZzZ6SsTr4IgE+WA44A0GmPIQstuOrgsFcT7VEJ48nmr9GaRtNu0XTKacFLGnBPAM6Afouw==", + "requires": { + "delegate": "^3.1.2" + } + }, + "ieee754": { + "version": "1.2.1", + "resolved": "https://registry.npmmirror.com/ieee754/-/ieee754-1.2.1.tgz", + "integrity": "sha512-dcyqhDvX1C46lXZcVqCpK+FtMRQVdIMN6/Df5js2zouUsqG7I6sFxitIC+7KYK29KdXOLHdu9zL4sFnoVQnqaA==" + }, + "ignore": { + "version": "5.3.1", + "resolved": "https://registry.npmmirror.com/ignore/-/ignore-5.3.1.tgz", + "integrity": "sha512-5Fytz/IraMjqpwfd34ke28PTVMjZjJG2MPn5t7OE4eUCUNf8BAa7b5WUS9/Qvr6mwOQS7Mk6vdsMno5he+T8Xw==", + "dev": true + }, + "immutable": { + "version": "4.3.7", + "resolved": "https://registry.npmmirror.com/immutable/-/immutable-4.3.7.tgz", + "integrity": "sha512-1hqclzwYwjRDFLjcFxOM5AYkkG0rpFPpr1RLPMEuGczoS7YA8gLhy8SWXYRAA/XwfEHpfo3cw5JGioS32fnMRw==", + "dev": true + }, + "is-binary-path": { + "version": "2.1.0", + "resolved": "https://registry.npmmirror.com/is-binary-path/-/is-binary-path-2.1.0.tgz", + "integrity": "sha512-ZMERYes6pDydyuGidse7OsHxtbI7WVeUEozgR/g7rd0xUimYNlvZRE/K2MgZTjWy725IfelLeVcEM97mmtRGXw==", + "dev": true, + "requires": { + "binary-extensions": "^2.0.0" + } + }, + "is-extglob": { + "version": "2.1.1", + "resolved": "https://registry.npmmirror.com/is-extglob/-/is-extglob-2.1.1.tgz", + "integrity": "sha512-SbKbANkN603Vi4jEZv49LeVJMn4yGwsbzZworEoyEiutsN3nJYdbO36zfhGJ6QEDpOZIFkDtnq5JRxmvl3jsoQ==", + "dev": true + }, + "is-glob": { + "version": "4.0.3", + "resolved": "https://registry.npmmirror.com/is-glob/-/is-glob-4.0.3.tgz", + "integrity": "sha512-xelSayHH36ZgE7ZWhli7pW34hNbNl8Ojv5KVmkJD4hBdD3th8Tfk9vYasLM+mXWOZhFkgZfxhLSnrwRr4elSSg==", + "dev": true, + "requires": { + "is-extglob": "^2.1.1" + } + }, + "is-number": { + "version": "7.0.0", + "resolved": "https://registry.npmmirror.com/is-number/-/is-number-7.0.0.tgz", + "integrity": "sha512-41Cifkg6e8TylSpdtTpeLVMqvSBEVzTttHvERD741+pnZ8ANv0004MRL43QKPDlK9cGvNp6NZWZUBlbGXYxxng==", + "dev": true + }, + "js-base64": { + "version": "3.7.2", + "resolved": "https://registry.npmmirror.com/js-base64/-/js-base64-3.7.2.tgz", + "integrity": "sha512-NnRs6dsyqUXejqk/yv2aiXlAvOs56sLkX6nUdeaNezI5LFFLlsZjOThmwnrcwh5ZZRwZlCMnVAY3CvhIhoVEKQ==" + }, + "jsbn": { + "version": "1.1.0", + "resolved": "https://registry.npmmirror.com/jsbn/-/jsbn-1.1.0.tgz", + "integrity": "sha512-4bYVV3aAMtDTTu4+xsDYa6sy9GyJ69/amsu9sYF2zqjiEoZA5xJi3BrfX3uY+/IekIu7MwdObdbDWpoZdBv3/A==" + }, + "jsencrypt": { + "version": "3.3.2", + "resolved": "https://registry.npmmirror.com/jsencrypt/-/jsencrypt-3.3.2.tgz", + "integrity": "sha512-arQR1R1ESGdAxY7ZheWr12wCaF2yF47v5qpB76TtV64H1pyGudk9Hvw8Y9tb/FiTIaaTRUyaSnm5T/Y53Ghm/A==" + }, + "json-schema-traverse": { + "version": "1.0.0", + "resolved": "https://registry.npmmirror.com/json-schema-traverse/-/json-schema-traverse-1.0.0.tgz", + "integrity": "sha512-NM8/P9n3XjXhIZn1lLhkFaACTOURQXjWhV4BA/RnOv8xvgqtqpAX9IO4mRQxSx1Rlo4tqzeqb0sOlruaOy3dug==", + "dev": true + }, + "json5": { + "version": "2.2.3", + "resolved": "https://registry.npmmirror.com/json5/-/json5-2.2.3.tgz", + "integrity": "sha512-XmOWe7eyHYH14cLdVPoyg+GOH3rYX++KpzrylJwSW98t3Nk+U8XOl8FWKOgwtzdb8lXGf6zYwDUzeHMWfxasyg==", + "dev": true + }, + "klona": { + "version": "2.0.6", + "resolved": "https://registry.npmmirror.com/klona/-/klona-2.0.6.tgz", + "integrity": "sha512-dhG34DXATL5hSxJbIexCft8FChFXtmskoZYnoPWjXQuebWYCNkVeV3KkGegCK9CP1oswI/vQibS2GY7Em/sJJA==", + "dev": true + }, + "loader-utils": { + "version": "2.0.4", + "resolved": "https://registry.npmmirror.com/loader-utils/-/loader-utils-2.0.4.tgz", + "integrity": "sha512-xXqpXoINfFhgua9xiqD8fPFHgkoq1mmmpE92WlDbm9rNRd/EbRb+Gqf908T2DMfuHjjJlksiK2RbHVOdD/MqSw==", + "dev": true, + "requires": { + "big.js": "^5.2.2", + "emojis-list": "^3.0.0", + "json5": "^2.1.2" + } + }, + "lodash": { + "version": "4.17.21", + "resolved": "https://registry.npmmirror.com/lodash/-/lodash-4.17.21.tgz", + "integrity": "sha512-v2kDEe57lecTulaDIuNTPy3Ry4gLGJ6Z1O3vE1krgXZNrsQ+LFTGHVxVjcXPs17LhbZVGedAJv8XZ1tvj5FvSg==" + }, + "merge2": { + "version": "1.4.1", + "resolved": "https://registry.npmmirror.com/merge2/-/merge2-1.4.1.tgz", + "integrity": "sha512-8q7VEgMJW4J8tcfVPy8g09NcQwZdbwFEqhe/WZkoIzjn/3TGDwtOCYtXGxA3O8tPzpczCCDgv+P2P5y00ZJOOg==", + "dev": true + }, + "micromatch": { + "version": "4.0.7", + "resolved": "https://registry.npmmirror.com/micromatch/-/micromatch-4.0.7.tgz", + "integrity": "sha512-LPP/3KorzCwBxfeUuZmaR6bG2kdeHSbe0P2tY3FLRU4vYrjYz5hI4QZwV0njUx3jeuKe67YukQ1LSPZBKDqO/Q==", + "dev": true, + "requires": { + "braces": "^3.0.3", + "picomatch": "^2.3.1" + } + }, + "neo-async": { + "version": "2.6.2", + "resolved": "https://registry.npmmirror.com/neo-async/-/neo-async-2.6.2.tgz", + "integrity": "sha512-Yd3UES5mWCSqR+qNT93S3UoYUkqAZ9lLg8a7g9rimsWmYGK8cVToA4/sF3RrshdyV3sAGMXVUmpMYOw+dLpOuw==", + "dev": true + }, + "normalize-path": { + "version": "3.0.0", + "resolved": "https://registry.npmmirror.com/normalize-path/-/normalize-path-3.0.0.tgz", + "integrity": "sha512-6eZs5Ls3WtCisHWp9S2GUy8dqkpGi4BVSz3GaqiE6ezub0512ESztXUwUB6C6IKbQkY2Pnb/mD4WYojCRwcwLA==", + "dev": true + }, + "path-type": { + "version": "5.0.0", + "resolved": "https://registry.npmmirror.com/path-type/-/path-type-5.0.0.tgz", + "integrity": "sha512-5HviZNaZcfqP95rwpv+1HDgUamezbqdSYTyzjTvwtJSnIH+3vnbmWsItli8OFEndS984VT55M3jduxZbX351gg==", + "dev": true + }, + "picomatch": { + "version": "2.3.1", + "resolved": "https://registry.npmmirror.com/picomatch/-/picomatch-2.3.1.tgz", + "integrity": "sha512-JU3teHTNjmE2VCGFzuY8EXzCDVwEqB2a8fsIvwaStHhAWJEeVd1o1QD80CU6+ZdEXXSLbSsuLwJjkCBWqRQUVA==", + "dev": true + }, + "punycode": { + "version": "2.3.1", + "resolved": "https://registry.npmmirror.com/punycode/-/punycode-2.3.1.tgz", + "integrity": "sha512-vYt7UD1U9Wg6138shLtLOvdAu+8DsC/ilFtEVHcH+wydcSpNE20AfSOduf6MkRFahL5FY7X1oU7nKVZFtfq8Fg==", + "dev": true + }, + "queue-microtask": { + "version": "1.2.3", + "resolved": "https://registry.npmmirror.com/queue-microtask/-/queue-microtask-1.2.3.tgz", + "integrity": "sha512-NuaNSa6flKT5JaSYQzJok04JzTL1CA6aGhv5rfLW3PgqA+M2ChpZQnAC8h8i4ZFkBS8X5RqkDBHA7r4hej3K9A==", + "dev": true + }, + "randombytes": { + "version": "2.1.0", + "resolved": "https://registry.npmmirror.com/randombytes/-/randombytes-2.1.0.tgz", + "integrity": "sha512-vYl3iOX+4CKUWuxGi9Ukhie6fsqXqS9FE2Zaic4tNFD2N2QQaXOMFbuKK4QmDHC0JO6B1Zp41J0LpT0oR68amQ==", + "dev": true, + "requires": { + "safe-buffer": "^5.1.0" + } + }, + "readdirp": { + "version": "3.6.0", + "resolved": "https://registry.npmmirror.com/readdirp/-/readdirp-3.6.0.tgz", + "integrity": "sha512-hOS089on8RduqdbhvQ5Z37A0ESjsqz6qnRcffsMU3495FuTdqSm+7bhJ29JvIOsBDEEnan5DPu9t3To9VRlMzA==", + "dev": true, + "requires": { + "picomatch": "^2.2.1" + } + }, + "require-from-string": { + "version": "2.0.2", + "resolved": "https://registry.npmmirror.com/require-from-string/-/require-from-string-2.0.2.tgz", + "integrity": "sha512-Xf0nWe6RseziFMu+Ap9biiUbmplq6S9/p+7w7YXP/JBHhrUDDUhwa+vANyubuqfZWTveU//DYVGsDG7RKL/vEw==", + "dev": true + }, + "reusify": { + "version": "1.0.4", + "resolved": "https://registry.npmmirror.com/reusify/-/reusify-1.0.4.tgz", + "integrity": "sha512-U9nH88a3fc/ekCF1l0/UP1IosiuIjyTh7hBvXVMHYgVcfGvt897Xguj2UOLDeI5BG2m7/uwyaLVT6fbtCwTyzw==", + "dev": true + }, + "run-parallel": { + "version": "1.2.0", + "resolved": "https://registry.npmmirror.com/run-parallel/-/run-parallel-1.2.0.tgz", + "integrity": "sha512-5l4VyZR86LZ/lDxZTR6jqL8AFE2S0IFLMP26AbjsLVADxHdhB/c0GUsH+y39UfCi3dzz8OlQuPmnaJOMoDHQBA==", + "dev": true, + "requires": { + "queue-microtask": "^1.2.2" + } + }, + "safe-buffer": { + "version": "5.2.1", + "resolved": "https://registry.npmmirror.com/safe-buffer/-/safe-buffer-5.2.1.tgz", + "integrity": "sha512-rp3So07KcdmmKbGvgaNxQSJr7bGVSVk5S9Eq1F+ppbRo70+YeaDxkw5Dd8NPN+GD6bjnYm2VuPuCXmpuYvmCXQ==", + "dev": true + }, + "sass": { + "version": "1.78.0", + "resolved": "https://registry.npmmirror.com/sass/-/sass-1.78.0.tgz", + "integrity": "sha512-AaIqGSrjo5lA2Yg7RvFZrlXDBCp3nV4XP73GrLGvdRWWwk+8H3l0SDvq/5bA4eF+0RFPLuWUk3E+P1U/YqnpsQ==", + "dev": true, + "requires": { + "chokidar": ">=3.0.0 <4.0.0", + "immutable": "^4.0.0", + "source-map-js": ">=0.6.2 <2.0.0" + } + }, + "sass-loader": { + "version": "10.5.2", + "resolved": "https://registry.npmmirror.com/sass-loader/-/sass-loader-10.5.2.tgz", + "integrity": "sha512-vMUoSNOUKJILHpcNCCyD23X34gve1TS7Rjd9uXHeKqhvBG39x6XbswFDtpbTElj6XdMFezoWhkh5vtKudf2cgQ==", + "dev": true, + "requires": { + "klona": "^2.0.4", + "loader-utils": "^2.0.0", + "neo-async": "^2.6.2", + "schema-utils": "^3.0.0", + "semver": "^7.3.2" + }, + "dependencies": { + "ajv": { + "version": "6.12.6", + "resolved": "https://registry.npmmirror.com/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", + "dev": true, + "requires": { + "fast-deep-equal": "^3.1.1", + "fast-json-stable-stringify": "^2.0.0", + "json-schema-traverse": "^0.4.1", + "uri-js": "^4.2.2" + } + }, + "ajv-keywords": { + "version": "3.5.2", + "resolved": "https://registry.npmmirror.com/ajv-keywords/-/ajv-keywords-3.5.2.tgz", + "integrity": "sha512-5p6WTN0DdTGVQk6VjcEju19IgaHudalcfabD7yhDGeA6bcQnmL+CpveLJq/3hvfwd1aof6L386Ougkx6RfyMIQ==", + "dev": true + }, + "json-schema-traverse": { + "version": "0.4.1", + "resolved": "https://registry.npmmirror.com/json-schema-traverse/-/json-schema-traverse-0.4.1.tgz", + "integrity": "sha512-xbbCH5dCYU5T8LcEhhuh7HJ88HXuW3qsI3Y0zOZFKfZEHcpWiHU/Jxzk629Brsab/mMiHQti9wMP+845RPe3Vg==", + "dev": true + }, + "schema-utils": { + "version": "3.3.0", + "resolved": "https://registry.npmmirror.com/schema-utils/-/schema-utils-3.3.0.tgz", + "integrity": "sha512-pN/yOAvcC+5rQ5nERGuwrjLlYvLTbCibnZ1I7B1LaiAz9BRBlE9GMgE/eqV30P7aJQUf7Ddimy/RsbYO/GrVGg==", + "dev": true, + "requires": { + "@types/json-schema": "^7.0.8", + "ajv": "^6.12.5", + "ajv-keywords": "^3.5.2" + } + } + } + }, + "schema-utils": { + "version": "4.2.0", + "resolved": "https://registry.npmmirror.com/schema-utils/-/schema-utils-4.2.0.tgz", + "integrity": "sha512-L0jRsrPpjdckP3oPug3/VxNKt2trR8TcabrM6FOAAlvC/9Phcmm+cuAgTlxBqdBR1WJx7Naj9WHw+aOmheSVbw==", + "dev": true, + "requires": { + "@types/json-schema": "^7.0.9", + "ajv": "^8.9.0", + "ajv-formats": "^2.1.1", + "ajv-keywords": "^5.1.0" + } + }, + "select": { + "version": "1.1.2", + "resolved": "https://registry.npmmirror.com/select/-/select-1.1.2.tgz", + "integrity": "sha512-OwpTSOfy6xSs1+pwcNrv0RBMOzI39Lp3qQKUTPVVPRjCdNa5JH/oPRiqsesIskK8TVgmRiHwO4KXlV2Li9dANA==" + }, + "semver": { + "version": "7.6.3", + "resolved": "https://registry.npmmirror.com/semver/-/semver-7.6.3.tgz", + "integrity": "sha512-oVekP1cKtI+CTDvHWYFUcMtsK/00wmAEfyqKfNdARm8u1wNVhSgaX7A8d4UuIlUI5e84iEwOhs7ZPYRmzU9U6A==", + "dev": true + }, + "serialize-javascript": { + "version": "6.0.2", + "resolved": "https://registry.npmmirror.com/serialize-javascript/-/serialize-javascript-6.0.2.tgz", + "integrity": "sha512-Saa1xPByTTq2gdeFZYLLo+RFE35NHZkAbqZeWNd3BpzppeVisAqpDjcp8dyf6uIvEqJRd46jemmyA4iFIeVk8g==", + "dev": true, + "requires": { + "randombytes": "^2.1.0" + } + }, + "slash": { + "version": "5.1.0", + "resolved": "https://registry.npmmirror.com/slash/-/slash-5.1.0.tgz", + "integrity": "sha512-ZA6oR3T/pEyuqwMgAKT0/hAv8oAXckzbkmR0UkUosQ+Mc4RxGoJkRmwHgHufaenlyAgE1Mxgpdcrf75y6XcnDg==", + "dev": true + }, + "source-map-js": { + "version": "1.2.1", + "resolved": "https://registry.npmmirror.com/source-map-js/-/source-map-js-1.2.1.tgz", + "integrity": "sha512-UXWMKhLOwVKb728IUtQPXxfYU+usdybtUrK/8uGE8CQMvrhOpwvzDBwj0QhSL7MQc7vIsISBG8VQ8+IDQxpfQA==", + "dev": true + }, + "tiny-emitter": { + "version": "2.1.0", + "resolved": "https://registry.npmmirror.com/tiny-emitter/-/tiny-emitter-2.1.0.tgz", + "integrity": "sha512-NB6Dk1A9xgQPMoGqC5CVXn123gWyte215ONT5Pp5a0yt4nlEoO1ZWeCwpncaekPHXO60i47ihFnZPiRPjRMq4Q==" + }, + "to-arraybuffer": { + "version": "1.0.1", + "resolved": "https://registry.npmmirror.com/to-arraybuffer/-/to-arraybuffer-1.0.1.tgz", + "integrity": "sha512-okFlQcoGTi4LQBG/PgSYblw9VOyptsz2KJZqc6qtgGdes8VktzUQkj4BI2blit072iS8VODNcMA+tvnS9dnuMA==" + }, + "to-regex-range": { + "version": "5.0.1", + "resolved": "https://registry.npmmirror.com/to-regex-range/-/to-regex-range-5.0.1.tgz", + "integrity": "sha512-65P7iz6X5yEr1cwcgvQxbbIw7Uk3gOy5dIdtZ4rDveLqhrdJP+Li/Hx6tyK0NEb+2GCyneCMJiGqrADCSNk8sQ==", + "dev": true, + "requires": { + "is-number": "^7.0.0" + } + }, + "unicorn-magic": { + "version": "0.1.0", + "resolved": "https://registry.npmmirror.com/unicorn-magic/-/unicorn-magic-0.1.0.tgz", + "integrity": "sha512-lRfVq8fE8gz6QMBuDM6a+LO3IAzTi05H6gCVaUpir2E1Rwpo4ZUog45KpNXKC/Mn3Yb9UDuHumeFTo9iV/D9FQ==", + "dev": true + }, + "uri-js": { + "version": "4.4.1", + "resolved": "https://registry.npmmirror.com/uri-js/-/uri-js-4.4.1.tgz", + "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", + "dev": true, + "requires": { + "punycode": "^2.1.0" + } + }, + "uview-plus": { + "version": "3.3.32", + "resolved": "https://registry.npmmirror.com/uview-plus/-/uview-plus-3.3.32.tgz", + "integrity": "sha512-rl/Bw9uH7sNY8GAzKVv3Wel27wvUx08UuADEPxQB5U2LrkdHD2r6Cvk6BTbQbLKDTpFR7rrbVTQiK/DNKFIe4Q==", + "requires": { + "clipboard": "^2.0.11", + "dayjs": "^1.11.3" + } + } + } +} diff --git a/package.json b/package.json new file mode 100644 index 0000000..e93d886 --- /dev/null +++ b/package.json @@ -0,0 +1,17 @@ +{ + "dependencies": { + "clipboard": "^2.0.11", + "dayjs": "^1.11.13", + "gm-crypto": "^0.1.8", + "immutable": "^4.3.7", + "js-base64": "^3.7.2", + "jsencrypt": "^3.3.2", + "lodash": "^4.17.21", + "uview-plus": "^3.3.32" + }, + "devDependencies": { + "copy-webpack-plugin": "^12.0.2", + "sass": "^1.78.0", + "sass-loader": "^10.5.2" + } +} diff --git a/pageBooking/index/index.vue b/pageBooking/index/index.vue new file mode 100644 index 0000000..82c3328 --- /dev/null +++ b/pageBooking/index/index.vue @@ -0,0 +1,12 @@ + + + + + diff --git a/pageBwc/index/index.vue b/pageBwc/index/index.vue new file mode 100644 index 0000000..98d3c26 --- /dev/null +++ b/pageBwc/index/index.vue @@ -0,0 +1,173 @@ + + + + + \ No newline at end of file diff --git a/pageCategory/edit-category/components/edit-category.vue b/pageCategory/edit-category/components/edit-category.vue new file mode 100644 index 0000000..02409e3 --- /dev/null +++ b/pageCategory/edit-category/components/edit-category.vue @@ -0,0 +1,8 @@ + + + + + \ No newline at end of file diff --git a/pageCategory/edit-category/edit-category - 副本.vue b/pageCategory/edit-category/edit-category - 副本.vue new file mode 100644 index 0000000..09506b5 --- /dev/null +++ b/pageCategory/edit-category/edit-category - 副本.vue @@ -0,0 +1,565 @@ + + + + + \ No newline at end of file diff --git a/pageCategory/edit-category/edit-category.vue b/pageCategory/edit-category/edit-category.vue new file mode 100644 index 0000000..05d9209 --- /dev/null +++ b/pageCategory/edit-category/edit-category.vue @@ -0,0 +1,865 @@ + + + + + \ No newline at end of file diff --git a/pageCategory/edit-category/timer.vue b/pageCategory/edit-category/timer.vue new file mode 100644 index 0000000..1675176 --- /dev/null +++ b/pageCategory/edit-category/timer.vue @@ -0,0 +1,213 @@ + + + + + \ No newline at end of file diff --git a/pageCategory/index/components/category.vue b/pageCategory/index/components/category.vue new file mode 100644 index 0000000..002994b --- /dev/null +++ b/pageCategory/index/components/category.vue @@ -0,0 +1,253 @@ + + + + + \ No newline at end of file diff --git a/pageCategory/index/index - 副本.vue b/pageCategory/index/index - 副本.vue new file mode 100644 index 0000000..07aaf95 --- /dev/null +++ b/pageCategory/index/index - 副本.vue @@ -0,0 +1,414 @@ + + + + + \ No newline at end of file diff --git a/pageCategory/index/index.vue b/pageCategory/index/index.vue new file mode 100644 index 0000000..cfbed1d --- /dev/null +++ b/pageCategory/index/index.vue @@ -0,0 +1,479 @@ + + + + + \ No newline at end of file diff --git a/pageConsumables/addConsumables.vue b/pageConsumables/addConsumables.vue new file mode 100644 index 0000000..8bdc68f --- /dev/null +++ b/pageConsumables/addConsumables.vue @@ -0,0 +1,222 @@ + + + + + \ No newline at end of file diff --git a/pageConsumables/addType.vue b/pageConsumables/addType.vue new file mode 100644 index 0000000..98460e7 --- /dev/null +++ b/pageConsumables/addType.vue @@ -0,0 +1,221 @@ + + + + + \ No newline at end of file diff --git a/pageConsumables/addsupplier.vue b/pageConsumables/addsupplier.vue new file mode 100644 index 0000000..42027d2 --- /dev/null +++ b/pageConsumables/addsupplier.vue @@ -0,0 +1,160 @@ + + + + + + \ No newline at end of file diff --git a/pageConsumables/bg.png b/pageConsumables/bg.png new file mode 100644 index 0000000..cc24745 Binary files /dev/null and b/pageConsumables/bg.png differ diff --git a/pageConsumables/billPayment.vue b/pageConsumables/billPayment.vue new file mode 100644 index 0000000..c61fc9c --- /dev/null +++ b/pageConsumables/billPayment.vue @@ -0,0 +1,81 @@ + + + + + \ No newline at end of file diff --git a/pageConsumables/components/my-action-sheet.vue b/pageConsumables/components/my-action-sheet.vue new file mode 100644 index 0000000..4111f2e --- /dev/null +++ b/pageConsumables/components/my-action-sheet.vue @@ -0,0 +1,108 @@ + + + + + \ No newline at end of file diff --git a/pageConsumables/components/my-date-pickerview.vue b/pageConsumables/components/my-date-pickerview.vue new file mode 100644 index 0000000..f634983 --- /dev/null +++ b/pageConsumables/components/my-date-pickerview.vue @@ -0,0 +1,448 @@ + + + + + \ No newline at end of file diff --git a/pageConsumables/components/my-reportDamage.vue b/pageConsumables/components/my-reportDamage.vue new file mode 100644 index 0000000..54770f8 --- /dev/null +++ b/pageConsumables/components/my-reportDamage.vue @@ -0,0 +1,368 @@ + + + + + \ No newline at end of file diff --git a/pageConsumables/editConsumables.vue b/pageConsumables/editConsumables.vue new file mode 100644 index 0000000..e548a7b --- /dev/null +++ b/pageConsumables/editConsumables.vue @@ -0,0 +1,212 @@ + + + + + \ No newline at end of file diff --git a/pageConsumables/editsupplier.vue b/pageConsumables/editsupplier.vue new file mode 100644 index 0000000..e7bae30 --- /dev/null +++ b/pageConsumables/editsupplier.vue @@ -0,0 +1,148 @@ + + + + + + \ No newline at end of file diff --git a/pageConsumables/index.vue b/pageConsumables/index.vue new file mode 100644 index 0000000..bbf34e2 --- /dev/null +++ b/pageConsumables/index.vue @@ -0,0 +1,491 @@ + + + + + \ No newline at end of file diff --git a/pageConsumables/inventoryCheck.vue b/pageConsumables/inventoryCheck.vue new file mode 100644 index 0000000..60eebad --- /dev/null +++ b/pageConsumables/inventoryCheck.vue @@ -0,0 +1,212 @@ + + + + + + \ No newline at end of file diff --git a/pageConsumables/outbound.vue b/pageConsumables/outbound.vue new file mode 100644 index 0000000..d6c9426 --- /dev/null +++ b/pageConsumables/outbound.vue @@ -0,0 +1,291 @@ + + + + + + \ No newline at end of file diff --git a/pageConsumables/paymentSettlement.vue b/pageConsumables/paymentSettlement.vue new file mode 100644 index 0000000..8885e16 --- /dev/null +++ b/pageConsumables/paymentSettlement.vue @@ -0,0 +1,424 @@ + + + + + \ No newline at end of file diff --git a/pageConsumables/profile.png b/pageConsumables/profile.png new file mode 100644 index 0000000..b5bf633 Binary files /dev/null and b/pageConsumables/profile.png differ diff --git a/pageConsumables/supplier.vue b/pageConsumables/supplier.vue new file mode 100644 index 0000000..54a6f11 --- /dev/null +++ b/pageConsumables/supplier.vue @@ -0,0 +1,199 @@ + + + + + \ No newline at end of file diff --git a/pageConsumables/time.png b/pageConsumables/time.png new file mode 100644 index 0000000..0f07e71 Binary files /dev/null and b/pageConsumables/time.png differ diff --git a/pageConsumables/viewrecords.vue b/pageConsumables/viewrecords.vue new file mode 100644 index 0000000..f8f0883 --- /dev/null +++ b/pageConsumables/viewrecords.vue @@ -0,0 +1,312 @@ + + + + + \ No newline at end of file diff --git a/pageConsumables/warehouseEntry.vue b/pageConsumables/warehouseEntry.vue new file mode 100644 index 0000000..da08283 --- /dev/null +++ b/pageConsumables/warehouseEntry.vue @@ -0,0 +1,309 @@ + + + + + + \ No newline at end of file diff --git a/pageCoupon/components/select-goods.vue b/pageCoupon/components/select-goods.vue new file mode 100644 index 0000000..2bda69c --- /dev/null +++ b/pageCoupon/components/select-goods.vue @@ -0,0 +1,178 @@ + + + + + \ No newline at end of file diff --git a/pageCoupon/discountCoupons.vue b/pageCoupon/discountCoupons.vue new file mode 100644 index 0000000..f596c45 --- /dev/null +++ b/pageCoupon/discountCoupons.vue @@ -0,0 +1,330 @@ + + + + \ No newline at end of file diff --git a/pageCoupon/editCertificate.vue b/pageCoupon/editCertificate.vue new file mode 100644 index 0000000..132cfb6 --- /dev/null +++ b/pageCoupon/editCertificate.vue @@ -0,0 +1,206 @@ + + + + \ No newline at end of file diff --git a/pageCoupon/index.vue b/pageCoupon/index.vue new file mode 100644 index 0000000..ccacc99 --- /dev/null +++ b/pageCoupon/index.vue @@ -0,0 +1,408 @@ + + + + + \ No newline at end of file diff --git a/pageCreditBuyer/addDebtor.vue b/pageCreditBuyer/addDebtor.vue new file mode 100644 index 0000000..0a95187 --- /dev/null +++ b/pageCreditBuyer/addDebtor.vue @@ -0,0 +1,203 @@ + + + + \ No newline at end of file diff --git a/pageCreditBuyer/bg.png b/pageCreditBuyer/bg.png new file mode 100644 index 0000000..3ccc766 Binary files /dev/null and b/pageCreditBuyer/bg.png differ diff --git a/pageCreditBuyer/components/my-action-sheet.vue b/pageCreditBuyer/components/my-action-sheet.vue new file mode 100644 index 0000000..4111f2e --- /dev/null +++ b/pageCreditBuyer/components/my-action-sheet.vue @@ -0,0 +1,108 @@ + + + + + \ No newline at end of file diff --git a/pageCreditBuyer/components/my-date-pickerview.vue b/pageCreditBuyer/components/my-date-pickerview.vue new file mode 100644 index 0000000..f634983 --- /dev/null +++ b/pageCreditBuyer/components/my-date-pickerview.vue @@ -0,0 +1,448 @@ + + + + + \ No newline at end of file diff --git a/pageCreditBuyer/components/my-repayment.vue b/pageCreditBuyer/components/my-repayment.vue new file mode 100644 index 0000000..e62b2e8 --- /dev/null +++ b/pageCreditBuyer/components/my-repayment.vue @@ -0,0 +1,275 @@ + + + + + \ No newline at end of file diff --git a/pageCreditBuyer/creditDetail.vue b/pageCreditBuyer/creditDetail.vue new file mode 100644 index 0000000..ab03f7a --- /dev/null +++ b/pageCreditBuyer/creditDetail.vue @@ -0,0 +1,474 @@ + + + + \ No newline at end of file diff --git a/pageCreditBuyer/index.vue b/pageCreditBuyer/index.vue new file mode 100644 index 0000000..d1a8940 --- /dev/null +++ b/pageCreditBuyer/index.vue @@ -0,0 +1,362 @@ + + + + + \ No newline at end of file diff --git a/pageCreditBuyer/rePaymentRecord.vue b/pageCreditBuyer/rePaymentRecord.vue new file mode 100644 index 0000000..00aeb62 --- /dev/null +++ b/pageCreditBuyer/rePaymentRecord.vue @@ -0,0 +1,149 @@ + + + + \ No newline at end of file diff --git a/pageDevice/adManager/components/AdItems.vue b/pageDevice/adManager/components/AdItems.vue new file mode 100644 index 0000000..a479001 --- /dev/null +++ b/pageDevice/adManager/components/AdItems.vue @@ -0,0 +1,106 @@ + + + + + \ No newline at end of file diff --git a/pageDevice/adManager/edit.vue b/pageDevice/adManager/edit.vue new file mode 100644 index 0000000..9ec3e17 --- /dev/null +++ b/pageDevice/adManager/edit.vue @@ -0,0 +1,144 @@ + + + + + \ No newline at end of file diff --git a/pageDevice/adManager/index.vue b/pageDevice/adManager/index.vue new file mode 100644 index 0000000..1f3b825 --- /dev/null +++ b/pageDevice/adManager/index.vue @@ -0,0 +1,123 @@ + + + + + diff --git a/pageDevice/adManager/view.vue b/pageDevice/adManager/view.vue new file mode 100644 index 0000000..f7d0451 --- /dev/null +++ b/pageDevice/adManager/view.vue @@ -0,0 +1,125 @@ + + + + + diff --git a/pageDevice/appManage/appDetails.vue b/pageDevice/appManage/appDetails.vue new file mode 100644 index 0000000..9396fe1 --- /dev/null +++ b/pageDevice/appManage/appDetails.vue @@ -0,0 +1,98 @@ + + + + + diff --git a/pageDevice/appManage/appManage.vue b/pageDevice/appManage/appManage.vue new file mode 100644 index 0000000..d97ccbc --- /dev/null +++ b/pageDevice/appManage/appManage.vue @@ -0,0 +1,40 @@ + + + + + diff --git a/pageDevice/appManage/payConfig.vue b/pageDevice/appManage/payConfig.vue new file mode 100644 index 0000000..86cb78e --- /dev/null +++ b/pageDevice/appManage/payConfig.vue @@ -0,0 +1,98 @@ + + + + + diff --git a/pageDevice/autoPos/edit.vue b/pageDevice/autoPos/edit.vue new file mode 100644 index 0000000..b6273a6 --- /dev/null +++ b/pageDevice/autoPos/edit.vue @@ -0,0 +1,187 @@ + + + + + diff --git a/pageDevice/autoPos/index.vue b/pageDevice/autoPos/index.vue new file mode 100644 index 0000000..1e77e20 --- /dev/null +++ b/pageDevice/autoPos/index.vue @@ -0,0 +1,68 @@ + + + + + diff --git a/pageDevice/autoPos/view.vue b/pageDevice/autoPos/view.vue new file mode 100644 index 0000000..0083520 --- /dev/null +++ b/pageDevice/autoPos/view.vue @@ -0,0 +1,92 @@ + + + + + diff --git a/pageDevice/commons/CommonPageByDevice.vue b/pageDevice/commons/CommonPageByDevice.vue new file mode 100644 index 0000000..ad41510 --- /dev/null +++ b/pageDevice/commons/CommonPageByDevice.vue @@ -0,0 +1,158 @@ + + + + + + diff --git a/pageDevice/device/device.vue b/pageDevice/device/device.vue new file mode 100644 index 0000000..d1795bf --- /dev/null +++ b/pageDevice/device/device.vue @@ -0,0 +1,26 @@ + + + + + diff --git a/pageDevice/editPage/editCode.vue b/pageDevice/editPage/editCode.vue new file mode 100644 index 0000000..cea1c54 --- /dev/null +++ b/pageDevice/editPage/editCode.vue @@ -0,0 +1,81 @@ + + + + + diff --git a/pageDevice/editPage/editPage.vue b/pageDevice/editPage/editPage.vue new file mode 100644 index 0000000..ba59670 --- /dev/null +++ b/pageDevice/editPage/editPage.vue @@ -0,0 +1,74 @@ + + + + + diff --git a/pageDevice/editPage/editPosition.vue b/pageDevice/editPage/editPosition.vue new file mode 100644 index 0000000..da1adf9 --- /dev/null +++ b/pageDevice/editPage/editPosition.vue @@ -0,0 +1,61 @@ + + + + + diff --git a/pageDevice/editPage/editPrint.vue b/pageDevice/editPage/editPrint.vue new file mode 100644 index 0000000..deb4851 --- /dev/null +++ b/pageDevice/editPage/editPrint.vue @@ -0,0 +1,64 @@ + + + + + diff --git a/pageDevice/face/edit.vue b/pageDevice/face/edit.vue new file mode 100644 index 0000000..3ea86b1 --- /dev/null +++ b/pageDevice/face/edit.vue @@ -0,0 +1,162 @@ + + + + + diff --git a/pageDevice/face/index.vue b/pageDevice/face/index.vue new file mode 100644 index 0000000..b921a85 --- /dev/null +++ b/pageDevice/face/index.vue @@ -0,0 +1,68 @@ + + + + + diff --git a/pageDevice/face/view.vue b/pageDevice/face/view.vue new file mode 100644 index 0000000..e4bd4a4 --- /dev/null +++ b/pageDevice/face/view.vue @@ -0,0 +1,147 @@ + + + + + + \ No newline at end of file diff --git a/pageDevice/lite/edit.vue b/pageDevice/lite/edit.vue new file mode 100644 index 0000000..a81d8aa --- /dev/null +++ b/pageDevice/lite/edit.vue @@ -0,0 +1,225 @@ + + + + + diff --git a/pageDevice/lite/index.vue b/pageDevice/lite/index.vue new file mode 100644 index 0000000..9081b77 --- /dev/null +++ b/pageDevice/lite/index.vue @@ -0,0 +1,68 @@ + + + + + diff --git a/pageDevice/lite/view.vue b/pageDevice/lite/view.vue new file mode 100644 index 0000000..4659f93 --- /dev/null +++ b/pageDevice/lite/view.vue @@ -0,0 +1,160 @@ + + + + + diff --git a/pageDevice/printer/edit.vue b/pageDevice/printer/edit.vue new file mode 100644 index 0000000..4a6bbc0 --- /dev/null +++ b/pageDevice/printer/edit.vue @@ -0,0 +1,190 @@ + + + + + diff --git a/pageDevice/printer/index.vue b/pageDevice/printer/index.vue new file mode 100644 index 0000000..dd6236d --- /dev/null +++ b/pageDevice/printer/index.vue @@ -0,0 +1,66 @@ + + + + + diff --git a/pageDevice/printer/view.vue b/pageDevice/printer/view.vue new file mode 100644 index 0000000..7bfcb69 --- /dev/null +++ b/pageDevice/printer/view.vue @@ -0,0 +1,155 @@ + + + + + diff --git a/pageDevice/qrc/components/hornCard.vue b/pageDevice/qrc/components/hornCard.vue new file mode 100644 index 0000000..a62fd65 --- /dev/null +++ b/pageDevice/qrc/components/hornCard.vue @@ -0,0 +1,49 @@ + + + + diff --git a/pageDevice/qrc/edit.vue b/pageDevice/qrc/edit.vue new file mode 100644 index 0000000..2d674ae --- /dev/null +++ b/pageDevice/qrc/edit.vue @@ -0,0 +1,230 @@ + + + + + diff --git a/pageDevice/qrc/index.vue b/pageDevice/qrc/index.vue new file mode 100644 index 0000000..7ba1116 --- /dev/null +++ b/pageDevice/qrc/index.vue @@ -0,0 +1,75 @@ + + + + + diff --git a/pageDevice/qrc/view.vue b/pageDevice/qrc/view.vue new file mode 100644 index 0000000..6bdb9f4 --- /dev/null +++ b/pageDevice/qrc/view.vue @@ -0,0 +1,243 @@ + + + + + diff --git a/pageDevice/scanPos/edit.vue b/pageDevice/scanPos/edit.vue new file mode 100644 index 0000000..d59314b --- /dev/null +++ b/pageDevice/scanPos/edit.vue @@ -0,0 +1,205 @@ + + + + + diff --git a/pageDevice/scanPos/index.vue b/pageDevice/scanPos/index.vue new file mode 100644 index 0000000..9483add --- /dev/null +++ b/pageDevice/scanPos/index.vue @@ -0,0 +1,64 @@ + + + + + diff --git a/pageDevice/scanPos/view.vue b/pageDevice/scanPos/view.vue new file mode 100644 index 0000000..ac7d5bc --- /dev/null +++ b/pageDevice/scanPos/view.vue @@ -0,0 +1,126 @@ + + + + + diff --git a/pageDevice/speaker/components/qrcCode.vue b/pageDevice/speaker/components/qrcCode.vue new file mode 100644 index 0000000..1f208b1 --- /dev/null +++ b/pageDevice/speaker/components/qrcCode.vue @@ -0,0 +1,53 @@ + + + + diff --git a/pageDevice/speaker/components/selectedQrcId.vue b/pageDevice/speaker/components/selectedQrcId.vue new file mode 100644 index 0000000..b65b5e7 --- /dev/null +++ b/pageDevice/speaker/components/selectedQrcId.vue @@ -0,0 +1,165 @@ + + + + + diff --git a/pageDevice/speaker/edit.vue b/pageDevice/speaker/edit.vue new file mode 100644 index 0000000..648ff34 --- /dev/null +++ b/pageDevice/speaker/edit.vue @@ -0,0 +1,158 @@ + + + + + diff --git a/pageDevice/speaker/index.vue b/pageDevice/speaker/index.vue new file mode 100644 index 0000000..3682781 --- /dev/null +++ b/pageDevice/speaker/index.vue @@ -0,0 +1,67 @@ + + + + + diff --git a/pageDevice/speaker/view.vue b/pageDevice/speaker/view.vue new file mode 100644 index 0000000..8d56096 --- /dev/null +++ b/pageDevice/speaker/view.vue @@ -0,0 +1,225 @@ + + + + + diff --git a/pageDevice/staffManage/edit.vue b/pageDevice/staffManage/edit.vue new file mode 100644 index 0000000..be730ac --- /dev/null +++ b/pageDevice/staffManage/edit.vue @@ -0,0 +1,322 @@ + + + + + + diff --git a/pageDevice/staffManage/staffDetails.vue b/pageDevice/staffManage/staffDetails.vue new file mode 100644 index 0000000..86335d3 --- /dev/null +++ b/pageDevice/staffManage/staffDetails.vue @@ -0,0 +1,249 @@ + + + + + + diff --git a/pageDevice/staffManage/staffManage.vue b/pageDevice/staffManage/staffManage.vue new file mode 100644 index 0000000..66436a5 --- /dev/null +++ b/pageDevice/staffManage/staffManage.vue @@ -0,0 +1,126 @@ + + + + + \ No newline at end of file diff --git a/pageDevice/static/detailsLislImg/code-none.svg b/pageDevice/static/detailsLislImg/code-none.svg new file mode 100644 index 0000000..f54e1a7 --- /dev/null +++ b/pageDevice/static/detailsLislImg/code-none.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/detailsLislImg/code-white.svg b/pageDevice/static/detailsLislImg/code-white.svg new file mode 100644 index 0000000..78b5eea --- /dev/null +++ b/pageDevice/static/detailsLislImg/code-white.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/detailsLislImg/horn-none.svg b/pageDevice/static/detailsLislImg/horn-none.svg new file mode 100644 index 0000000..3af44f9 --- /dev/null +++ b/pageDevice/static/detailsLislImg/horn-none.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/detailsLislImg/horn-white.svg b/pageDevice/static/detailsLislImg/horn-white.svg new file mode 100644 index 0000000..b96a21a --- /dev/null +++ b/pageDevice/static/detailsLislImg/horn-white.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/detailsLislImg/icon-lite.svg b/pageDevice/static/detailsLislImg/icon-lite.svg new file mode 100644 index 0000000..79c1590 --- /dev/null +++ b/pageDevice/static/detailsLislImg/icon-lite.svg @@ -0,0 +1,9 @@ + + + + + + + + + diff --git a/pageDevice/static/detailsLislImg/lite-none.svg b/pageDevice/static/detailsLislImg/lite-none.svg new file mode 100644 index 0000000..e7fcaa4 --- /dev/null +++ b/pageDevice/static/detailsLislImg/lite-none.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/detailsLislImg/lite-white.svg b/pageDevice/static/detailsLislImg/lite-white.svg new file mode 100644 index 0000000..9c9c56d --- /dev/null +++ b/pageDevice/static/detailsLislImg/lite-white.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/detailsLislImg/pos-none.svg b/pageDevice/static/detailsLislImg/pos-none.svg new file mode 100644 index 0000000..1c8be8c --- /dev/null +++ b/pageDevice/static/detailsLislImg/pos-none.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/detailsLislImg/pos-white.svg b/pageDevice/static/detailsLislImg/pos-white.svg new file mode 100644 index 0000000..133f538 --- /dev/null +++ b/pageDevice/static/detailsLislImg/pos-white.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/detailsLislImg/print-none.svg b/pageDevice/static/detailsLislImg/print-none.svg new file mode 100644 index 0000000..6a236dc --- /dev/null +++ b/pageDevice/static/detailsLislImg/print-none.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/detailsLislImg/print-white.svg b/pageDevice/static/detailsLislImg/print-white.svg new file mode 100644 index 0000000..d463a30 --- /dev/null +++ b/pageDevice/static/detailsLislImg/print-white.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/detailsLislImg/scanPos-none.svg b/pageDevice/static/detailsLislImg/scanPos-none.svg new file mode 100644 index 0000000..f9e53af --- /dev/null +++ b/pageDevice/static/detailsLislImg/scanPos-none.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/detailsLislImg/scanPos-white.svg b/pageDevice/static/detailsLislImg/scanPos-white.svg new file mode 100644 index 0000000..f03a2c0 --- /dev/null +++ b/pageDevice/static/detailsLislImg/scanPos-white.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/detailsLislImg/term-white.svg b/pageDevice/static/detailsLislImg/term-white.svg new file mode 100644 index 0000000..b38e297 --- /dev/null +++ b/pageDevice/static/detailsLislImg/term-white.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/detailsLislImg/trm-none.svg b/pageDevice/static/detailsLislImg/trm-none.svg new file mode 100644 index 0000000..96d8939 --- /dev/null +++ b/pageDevice/static/detailsLislImg/trm-none.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/devIconImg/default-img.svg b/pageDevice/static/devIconImg/default-img.svg new file mode 100644 index 0000000..40999f7 --- /dev/null +++ b/pageDevice/static/devIconImg/default-img.svg @@ -0,0 +1,7 @@ + + + + + + + diff --git a/pageDevice/static/devIconImg/icon-ad-view.svg b/pageDevice/static/devIconImg/icon-ad-view.svg new file mode 100644 index 0000000..666039c --- /dev/null +++ b/pageDevice/static/devIconImg/icon-ad-view.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/devIconImg/icon-arrow-down.svg b/pageDevice/static/devIconImg/icon-arrow-down.svg new file mode 100644 index 0000000..c92791d --- /dev/null +++ b/pageDevice/static/devIconImg/icon-arrow-down.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/devIconImg/icon-arrow-sex.svg b/pageDevice/static/devIconImg/icon-arrow-sex.svg new file mode 100644 index 0000000..d9eb857 --- /dev/null +++ b/pageDevice/static/devIconImg/icon-arrow-sex.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/devIconImg/icon-code.svg b/pageDevice/static/devIconImg/icon-code.svg new file mode 100644 index 0000000..01e19cf --- /dev/null +++ b/pageDevice/static/devIconImg/icon-code.svg @@ -0,0 +1,9 @@ + + + + + + + + + diff --git a/pageDevice/static/devIconImg/icon-default.svg b/pageDevice/static/devIconImg/icon-default.svg new file mode 100644 index 0000000..517cc46 --- /dev/null +++ b/pageDevice/static/devIconImg/icon-default.svg @@ -0,0 +1,10 @@ + + + + + + + + + + diff --git a/pageDevice/static/devIconImg/icon-edit.svg b/pageDevice/static/devIconImg/icon-edit.svg new file mode 100644 index 0000000..deeb883 --- /dev/null +++ b/pageDevice/static/devIconImg/icon-edit.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/devIconImg/icon-face-0.svg b/pageDevice/static/devIconImg/icon-face-0.svg new file mode 100644 index 0000000..5df201c --- /dev/null +++ b/pageDevice/static/devIconImg/icon-face-0.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/devIconImg/icon-face-1.svg b/pageDevice/static/devIconImg/icon-face-1.svg new file mode 100644 index 0000000..4e7082a --- /dev/null +++ b/pageDevice/static/devIconImg/icon-face-1.svg @@ -0,0 +1,9 @@ + + + + + + + + + diff --git a/pageDevice/static/devIconImg/icon-face-white.svg b/pageDevice/static/devIconImg/icon-face-white.svg new file mode 100644 index 0000000..54e906b --- /dev/null +++ b/pageDevice/static/devIconImg/icon-face-white.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/devIconImg/icon-gps.svg b/pageDevice/static/devIconImg/icon-gps.svg new file mode 100644 index 0000000..d6ade7a --- /dev/null +++ b/pageDevice/static/devIconImg/icon-gps.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/devIconImg/icon-horn.svg b/pageDevice/static/devIconImg/icon-horn.svg new file mode 100644 index 0000000..1ea06af --- /dev/null +++ b/pageDevice/static/devIconImg/icon-horn.svg @@ -0,0 +1,9 @@ + + + + + + + + + diff --git a/pageDevice/static/devIconImg/icon-man.svg b/pageDevice/static/devIconImg/icon-man.svg new file mode 100644 index 0000000..9587b78 --- /dev/null +++ b/pageDevice/static/devIconImg/icon-man.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/pageDevice/static/devIconImg/icon-more-white.svg b/pageDevice/static/devIconImg/icon-more-white.svg new file mode 100644 index 0000000..88e22cd --- /dev/null +++ b/pageDevice/static/devIconImg/icon-more-white.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/pageDevice/static/devIconImg/icon-noDefault.svg b/pageDevice/static/devIconImg/icon-noDefault.svg new file mode 100644 index 0000000..13947d8 --- /dev/null +++ b/pageDevice/static/devIconImg/icon-noDefault.svg @@ -0,0 +1,4 @@ + + + + diff --git a/pageDevice/static/devIconImg/icon-pos.svg b/pageDevice/static/devIconImg/icon-pos.svg new file mode 100644 index 0000000..65a901e --- /dev/null +++ b/pageDevice/static/devIconImg/icon-pos.svg @@ -0,0 +1,9 @@ + + + + + + + + + diff --git a/pageDevice/static/devIconImg/icon-print.svg b/pageDevice/static/devIconImg/icon-print.svg new file mode 100644 index 0000000..bf85464 --- /dev/null +++ b/pageDevice/static/devIconImg/icon-print.svg @@ -0,0 +1,9 @@ + + + + + + + + + diff --git a/pageDevice/static/devIconImg/icon-save.svg b/pageDevice/static/devIconImg/icon-save.svg new file mode 100644 index 0000000..c55e0f6 --- /dev/null +++ b/pageDevice/static/devIconImg/icon-save.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/devIconImg/icon-scan-code.svg b/pageDevice/static/devIconImg/icon-scan-code.svg new file mode 100644 index 0000000..e733574 --- /dev/null +++ b/pageDevice/static/devIconImg/icon-scan-code.svg @@ -0,0 +1,7 @@ + + + + + + + diff --git a/pageDevice/static/devIconImg/icon-scanPos.svg b/pageDevice/static/devIconImg/icon-scanPos.svg new file mode 100644 index 0000000..6576a71 --- /dev/null +++ b/pageDevice/static/devIconImg/icon-scanPos.svg @@ -0,0 +1,9 @@ + + + + + + + + + diff --git a/pageDevice/static/devIconImg/icon-term.svg b/pageDevice/static/devIconImg/icon-term.svg new file mode 100644 index 0000000..376411f --- /dev/null +++ b/pageDevice/static/devIconImg/icon-term.svg @@ -0,0 +1,9 @@ + + + + + + + + + diff --git a/pageDevice/static/devIconImg/icon-woman.svg b/pageDevice/static/devIconImg/icon-woman.svg new file mode 100644 index 0000000..5a41ec0 --- /dev/null +++ b/pageDevice/static/devIconImg/icon-woman.svg @@ -0,0 +1,5 @@ + + + + + diff --git a/pageDevice/static/icon/ad-add.svg b/pageDevice/static/icon/ad-add.svg new file mode 100644 index 0000000..29c2d8c --- /dev/null +++ b/pageDevice/static/icon/ad-add.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/static/icon/ad-white.svg b/pageDevice/static/icon/ad-white.svg new file mode 100644 index 0000000..666039c --- /dev/null +++ b/pageDevice/static/icon/ad-white.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageDevice/storePage/components/list.vue b/pageDevice/storePage/components/list.vue new file mode 100644 index 0000000..64d387e --- /dev/null +++ b/pageDevice/storePage/components/list.vue @@ -0,0 +1,329 @@ + + + + + + diff --git a/pageDevice/storePage/edit.vue b/pageDevice/storePage/edit.vue new file mode 100644 index 0000000..ac60aa7 --- /dev/null +++ b/pageDevice/storePage/edit.vue @@ -0,0 +1,345 @@ + + + + + diff --git a/pageDevice/storePage/storeDetails.vue b/pageDevice/storePage/storeDetails.vue new file mode 100644 index 0000000..dc9156d --- /dev/null +++ b/pageDevice/storePage/storeDetails.vue @@ -0,0 +1,216 @@ + + + + + diff --git a/pageDevice/storePage/storeList.vue b/pageDevice/storePage/storeList.vue new file mode 100644 index 0000000..77e13cc --- /dev/null +++ b/pageDevice/storePage/storeList.vue @@ -0,0 +1,153 @@ + + + + diff --git a/pageDevice/terminal/edit.vue b/pageDevice/terminal/edit.vue new file mode 100644 index 0000000..1fc3efb --- /dev/null +++ b/pageDevice/terminal/edit.vue @@ -0,0 +1,300 @@ + + + + + diff --git a/pageDevice/terminal/index.vue b/pageDevice/terminal/index.vue new file mode 100644 index 0000000..b954eaa --- /dev/null +++ b/pageDevice/terminal/index.vue @@ -0,0 +1,64 @@ + + + + + diff --git a/pageDevice/terminal/view.vue b/pageDevice/terminal/view.vue new file mode 100644 index 0000000..cad1578 --- /dev/null +++ b/pageDevice/terminal/view.vue @@ -0,0 +1,162 @@ + + + + + diff --git a/pageGoodsGroup/edit-group-goods/components/bind-goods-list.vue b/pageGoodsGroup/edit-group-goods/components/bind-goods-list.vue new file mode 100644 index 0000000..02409e3 --- /dev/null +++ b/pageGoodsGroup/edit-group-goods/components/bind-goods-list.vue @@ -0,0 +1,8 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/edit-group-goods/components/category.vue b/pageGoodsGroup/edit-group-goods/components/category.vue new file mode 100644 index 0000000..3e86e9f --- /dev/null +++ b/pageGoodsGroup/edit-group-goods/components/category.vue @@ -0,0 +1,106 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/edit-group-goods/components/control.vue b/pageGoodsGroup/edit-group-goods/components/control.vue new file mode 100644 index 0000000..9345bd7 --- /dev/null +++ b/pageGoodsGroup/edit-group-goods/components/control.vue @@ -0,0 +1,166 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/edit-group-goods/components/goods.vue b/pageGoodsGroup/edit-group-goods/components/goods.vue new file mode 100644 index 0000000..75f1569 --- /dev/null +++ b/pageGoodsGroup/edit-group-goods/components/goods.vue @@ -0,0 +1,287 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/edit-group-goods/edit-group-goods.vue b/pageGoodsGroup/edit-group-goods/edit-group-goods.vue new file mode 100644 index 0000000..8cac28d --- /dev/null +++ b/pageGoodsGroup/edit-group-goods/edit-group-goods.vue @@ -0,0 +1,586 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/edit-group/components/edit-category.vue b/pageGoodsGroup/edit-group/components/edit-category.vue new file mode 100644 index 0000000..02409e3 --- /dev/null +++ b/pageGoodsGroup/edit-group/components/edit-category.vue @@ -0,0 +1,8 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/edit-group/edit-group.vue b/pageGoodsGroup/edit-group/edit-group.vue new file mode 100644 index 0000000..58bd39d --- /dev/null +++ b/pageGoodsGroup/edit-group/edit-group.vue @@ -0,0 +1,642 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/edit-group/timer.vue b/pageGoodsGroup/edit-group/timer.vue new file mode 100644 index 0000000..1675176 --- /dev/null +++ b/pageGoodsGroup/edit-group/timer.vue @@ -0,0 +1,213 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/index/components/category.vue b/pageGoodsGroup/index/components/category.vue new file mode 100644 index 0000000..8e1063d --- /dev/null +++ b/pageGoodsGroup/index/components/category.vue @@ -0,0 +1,231 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/index/components/edit-name.vue b/pageGoodsGroup/index/components/edit-name.vue new file mode 100644 index 0000000..b62b6b4 --- /dev/null +++ b/pageGoodsGroup/index/components/edit-name.vue @@ -0,0 +1,128 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/index/components/edit-sort.vue b/pageGoodsGroup/index/components/edit-sort.vue new file mode 100644 index 0000000..0bb4974 --- /dev/null +++ b/pageGoodsGroup/index/components/edit-sort.vue @@ -0,0 +1,128 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/index/components/edit-time.vue b/pageGoodsGroup/index/components/edit-time.vue new file mode 100644 index 0000000..0263be1 --- /dev/null +++ b/pageGoodsGroup/index/components/edit-time.vue @@ -0,0 +1,183 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/index/index - 副本.vue b/pageGoodsGroup/index/index - 副本.vue new file mode 100644 index 0000000..22b9d59 --- /dev/null +++ b/pageGoodsGroup/index/index - 副本.vue @@ -0,0 +1,483 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/index/index.vue b/pageGoodsGroup/index/index.vue new file mode 100644 index 0000000..212e307 --- /dev/null +++ b/pageGoodsGroup/index/index.vue @@ -0,0 +1,509 @@ + + + + + \ No newline at end of file diff --git a/pageGoodsGroup/static/image/icon-edit.svg b/pageGoodsGroup/static/image/icon-edit.svg new file mode 100644 index 0000000..d19e690 --- /dev/null +++ b/pageGoodsGroup/static/image/icon-edit.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pageInvoicing/category-management/add-products.vue b/pageInvoicing/category-management/add-products.vue new file mode 100644 index 0000000..e2fc9ad --- /dev/null +++ b/pageInvoicing/category-management/add-products.vue @@ -0,0 +1,369 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/category-management/category-management.vue b/pageInvoicing/category-management/category-management.vue new file mode 100644 index 0000000..2c28f11 --- /dev/null +++ b/pageInvoicing/category-management/category-management.vue @@ -0,0 +1,69 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/category-management/components/list-item.vue b/pageInvoicing/category-management/components/list-item.vue new file mode 100644 index 0000000..ae673a9 --- /dev/null +++ b/pageInvoicing/category-management/components/list-item.vue @@ -0,0 +1,120 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/category-management/edit-category.vue b/pageInvoicing/category-management/edit-category.vue new file mode 100644 index 0000000..716278b --- /dev/null +++ b/pageInvoicing/category-management/edit-category.vue @@ -0,0 +1,62 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/category-management/look-records.vue b/pageInvoicing/category-management/look-records.vue new file mode 100644 index 0000000..0da4254 --- /dev/null +++ b/pageInvoicing/category-management/look-records.vue @@ -0,0 +1,210 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/category-management/warehouse-entry.vue b/pageInvoicing/category-management/warehouse-entry.vue new file mode 100644 index 0000000..a35d7a9 --- /dev/null +++ b/pageInvoicing/category-management/warehouse-entry.vue @@ -0,0 +1,240 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/components/empty.vue b/pageInvoicing/components/empty.vue new file mode 100644 index 0000000..8f881e0 --- /dev/null +++ b/pageInvoicing/components/empty.vue @@ -0,0 +1,29 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/index/components/product-item.vue b/pageInvoicing/index/components/product-item.vue new file mode 100644 index 0000000..de47ba2 --- /dev/null +++ b/pageInvoicing/index/components/product-item.vue @@ -0,0 +1,89 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/index/index - 副本.vue b/pageInvoicing/index/index - 副本.vue new file mode 100644 index 0000000..09e2671 --- /dev/null +++ b/pageInvoicing/index/index - 副本.vue @@ -0,0 +1,300 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/index/index.vue b/pageInvoicing/index/index.vue new file mode 100644 index 0000000..37e2f93 --- /dev/null +++ b/pageInvoicing/index/index.vue @@ -0,0 +1,336 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/inventory-records/components/list-item.vue b/pageInvoicing/inventory-records/components/list-item.vue new file mode 100644 index 0000000..ec6626f --- /dev/null +++ b/pageInvoicing/inventory-records/components/list-item.vue @@ -0,0 +1,163 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/inventory-records/inventory-records.vue b/pageInvoicing/inventory-records/inventory-records.vue new file mode 100644 index 0000000..18491a6 --- /dev/null +++ b/pageInvoicing/inventory-records/inventory-records.vue @@ -0,0 +1,265 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/outbound-record/components/list-item.vue b/pageInvoicing/outbound-record/components/list-item.vue new file mode 100644 index 0000000..db93638 --- /dev/null +++ b/pageInvoicing/outbound-record/components/list-item.vue @@ -0,0 +1,168 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/outbound-record/outbound-record.vue b/pageInvoicing/outbound-record/outbound-record.vue new file mode 100644 index 0000000..09a5a10 --- /dev/null +++ b/pageInvoicing/outbound-record/outbound-record.vue @@ -0,0 +1,280 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/static/images/icon-arrow-down-fill.svg b/pageInvoicing/static/images/icon-arrow-down-fill.svg new file mode 100644 index 0000000..4275b7e --- /dev/null +++ b/pageInvoicing/static/images/icon-arrow-down-fill.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pageInvoicing/static/images/icon-category.svg b/pageInvoicing/static/images/icon-category.svg new file mode 100644 index 0000000..0dae28f --- /dev/null +++ b/pageInvoicing/static/images/icon-category.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pageInvoicing/static/images/icon-empty.svg b/pageInvoicing/static/images/icon-empty.svg new file mode 100644 index 0000000..e991ff1 --- /dev/null +++ b/pageInvoicing/static/images/icon-empty.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pageInvoicing/static/images/icon-in.svg b/pageInvoicing/static/images/icon-in.svg new file mode 100644 index 0000000..f660a20 --- /dev/null +++ b/pageInvoicing/static/images/icon-in.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pageInvoicing/static/images/icon-order.svg b/pageInvoicing/static/images/icon-order.svg new file mode 100644 index 0000000..d90f91f --- /dev/null +++ b/pageInvoicing/static/images/icon-order.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pageInvoicing/static/images/icon-out.svg b/pageInvoicing/static/images/icon-out.svg new file mode 100644 index 0000000..403aed7 --- /dev/null +++ b/pageInvoicing/static/images/icon-out.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pageInvoicing/static/images/icon-saoma.svg b/pageInvoicing/static/images/icon-saoma.svg new file mode 100644 index 0000000..fcfab1f --- /dev/null +++ b/pageInvoicing/static/images/icon-saoma.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pageInvoicing/storage-record/components/list-item.vue b/pageInvoicing/storage-record/components/list-item.vue new file mode 100644 index 0000000..ba37472 --- /dev/null +++ b/pageInvoicing/storage-record/components/list-item.vue @@ -0,0 +1,122 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/storage-record/storage-record.vue b/pageInvoicing/storage-record/storage-record.vue new file mode 100644 index 0000000..d58ff04 --- /dev/null +++ b/pageInvoicing/storage-record/storage-record.vue @@ -0,0 +1,266 @@ + + + + + \ No newline at end of file diff --git a/pageInvoicing/type-record/type-record.vue b/pageInvoicing/type-record/type-record.vue new file mode 100644 index 0000000..04afb5d --- /dev/null +++ b/pageInvoicing/type-record/type-record.vue @@ -0,0 +1,210 @@ + + + + + \ No newline at end of file diff --git a/pageLineUp/avation.svg b/pageLineUp/avation.svg new file mode 100644 index 0000000..b5d2d82 --- /dev/null +++ b/pageLineUp/avation.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pageLineUp/callRecord.vue b/pageLineUp/callRecord.vue new file mode 100644 index 0000000..721f89c --- /dev/null +++ b/pageLineUp/callRecord.vue @@ -0,0 +1,199 @@ + + + + + \ No newline at end of file diff --git a/pageLineUp/index.vue b/pageLineUp/index.vue new file mode 100644 index 0000000..d3d6788 --- /dev/null +++ b/pageLineUp/index.vue @@ -0,0 +1,490 @@ + + + + + \ No newline at end of file diff --git a/pageNotification/index.vue b/pageNotification/index.vue new file mode 100644 index 0000000..a2ce120 --- /dev/null +++ b/pageNotification/index.vue @@ -0,0 +1,130 @@ + + + + diff --git a/pagePrinter/add-printer/add-printer.vue b/pagePrinter/add-printer/add-printer.vue new file mode 100644 index 0000000..e3cb299 --- /dev/null +++ b/pagePrinter/add-printer/add-printer.vue @@ -0,0 +1,433 @@ + + + + + \ No newline at end of file diff --git a/pagePrinter/add-printer/components/choose-category.vue b/pagePrinter/add-printer/components/choose-category.vue new file mode 100644 index 0000000..c1b5c89 --- /dev/null +++ b/pagePrinter/add-printer/components/choose-category.vue @@ -0,0 +1,46 @@ + + + + + \ No newline at end of file diff --git a/pagePrinter/add-printer/components/my-radio-group.vue b/pagePrinter/add-printer/components/my-radio-group.vue new file mode 100644 index 0000000..ef2ca22 --- /dev/null +++ b/pagePrinter/add-printer/components/my-radio-group.vue @@ -0,0 +1,70 @@ + + + + + \ No newline at end of file diff --git a/pagePrinter/add-printer/components/picker-item.vue b/pagePrinter/add-printer/components/picker-item.vue new file mode 100644 index 0000000..f6a4511 --- /dev/null +++ b/pagePrinter/add-printer/components/picker-item.vue @@ -0,0 +1,63 @@ + + + + + \ No newline at end of file diff --git a/pagePrinter/devices.js b/pagePrinter/devices.js new file mode 100644 index 0000000..f06e712 --- /dev/null +++ b/pagePrinter/devices.js @@ -0,0 +1,63 @@ +export const brand = [{ + value: 'yxyPrinter', + name: '云想印' + }, + { + value: 'fePrinter', + name: '飞鹅' + } +] +export const receipts = [{ + value: 'label', + name: '标签' + }, + { + value: 'kitchen', + name: '出品' + }, + { + value: 'cash', + name: '小票' + } +] +export const devices = [{ + value: 'printer', + name: '本地' + }, + { + value: 'yxyPrinter', + name: '云想印' + }, + { + value: 'fePrinter', + name: '飞鹅' + } +] + +export const models = [{ + value: 'normal', + name: '普通出单' + }, + { + value: 'one', + name: '一菜一品' + }, + { + value: 'category', + name: '分类出单' + } +] + +export const subTypes = [{ + value: 'kitchen', + name: '出品' + }, + { + value: 'cash', + name: '小票' + }, + { + value: 'label', + name: '标签' + } +] \ No newline at end of file diff --git a/pagePrinter/index/components/printer-item.vue b/pagePrinter/index/components/printer-item.vue new file mode 100644 index 0000000..d5fbe42 --- /dev/null +++ b/pagePrinter/index/components/printer-item.vue @@ -0,0 +1,154 @@ + + + + + \ No newline at end of file diff --git a/pagePrinter/index/editPrinter.vue b/pagePrinter/index/editPrinter.vue new file mode 100644 index 0000000..d3d2ff8 --- /dev/null +++ b/pagePrinter/index/editPrinter.vue @@ -0,0 +1,175 @@ + + + + + \ No newline at end of file diff --git a/pagePrinter/index/index.vue b/pagePrinter/index/index.vue new file mode 100644 index 0000000..2393a9c --- /dev/null +++ b/pagePrinter/index/index.vue @@ -0,0 +1,69 @@ + + + + + \ No newline at end of file diff --git a/pagePrinter/static/icon/icon-category.svg b/pagePrinter/static/icon/icon-category.svg new file mode 100644 index 0000000..2ebc211 --- /dev/null +++ b/pagePrinter/static/icon/icon-category.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pagePrinter/static/icon/icon-setting.svg b/pagePrinter/static/icon/icon-setting.svg new file mode 100644 index 0000000..335683f --- /dev/null +++ b/pagePrinter/static/icon/icon-setting.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pagePrinter/static/icon/icon-type.svg b/pagePrinter/static/icon/icon-type.svg new file mode 100644 index 0000000..90ab06b --- /dev/null +++ b/pagePrinter/static/icon/icon-type.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pagePrinter/static/icon/icon-warning.svg b/pagePrinter/static/icon/icon-warning.svg new file mode 100644 index 0000000..faef0e0 --- /dev/null +++ b/pagePrinter/static/icon/icon-warning.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pageProduct/add-Product/add-Product - 副本.vue b/pageProduct/add-Product/add-Product - 副本.vue new file mode 100644 index 0000000..e08499a --- /dev/null +++ b/pageProduct/add-Product/add-Product - 副本.vue @@ -0,0 +1,1878 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-Product/add-Product-9-19-back.vue b/pageProduct/add-Product/add-Product-9-19-back.vue new file mode 100644 index 0000000..adae269 --- /dev/null +++ b/pageProduct/add-Product/add-Product-9-19-back.vue @@ -0,0 +1,2026 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-Product/add-Product.vue b/pageProduct/add-Product/add-Product.vue new file mode 100644 index 0000000..dbc6850 --- /dev/null +++ b/pageProduct/add-Product/add-Product.vue @@ -0,0 +1,2318 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-Product/components/choose-coupon-category.vue b/pageProduct/add-Product/components/choose-coupon-category.vue new file mode 100644 index 0000000..982f54e --- /dev/null +++ b/pageProduct/add-Product/components/choose-coupon-category.vue @@ -0,0 +1,177 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-Product/components/choose-danwei.vue b/pageProduct/add-Product/components/choose-danwei.vue new file mode 100644 index 0000000..0509317 --- /dev/null +++ b/pageProduct/add-Product/components/choose-danwei.vue @@ -0,0 +1,163 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-Product/components/choose-goods.vue b/pageProduct/add-Product/components/choose-goods.vue new file mode 100644 index 0000000..bcd3b0e --- /dev/null +++ b/pageProduct/add-Product/components/choose-goods.vue @@ -0,0 +1,268 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-Product/components/choose-guige.vue b/pageProduct/add-Product/components/choose-guige.vue new file mode 100644 index 0000000..29bfa51 --- /dev/null +++ b/pageProduct/add-Product/components/choose-guige.vue @@ -0,0 +1,164 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-Product/components/choose-haocai - 副本.vue b/pageProduct/add-Product/components/choose-haocai - 副本.vue new file mode 100644 index 0000000..7ef8774 --- /dev/null +++ b/pageProduct/add-Product/components/choose-haocai - 副本.vue @@ -0,0 +1,57 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-Product/components/choose-haocai.vue b/pageProduct/add-Product/components/choose-haocai.vue new file mode 100644 index 0000000..f4dc2d6 --- /dev/null +++ b/pageProduct/add-Product/components/choose-haocai.vue @@ -0,0 +1,149 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-Product/components/edit-haocai.vue b/pageProduct/add-Product/components/edit-haocai.vue new file mode 100644 index 0000000..562e6cf --- /dev/null +++ b/pageProduct/add-Product/components/edit-haocai.vue @@ -0,0 +1,440 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-Product/components/price-number-box.vue b/pageProduct/add-Product/components/price-number-box.vue new file mode 100644 index 0000000..7b00a90 --- /dev/null +++ b/pageProduct/add-Product/components/price-number-box.vue @@ -0,0 +1,109 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-Product/timer - 副本.vue b/pageProduct/add-Product/timer - 副本.vue new file mode 100644 index 0000000..3e0c104 --- /dev/null +++ b/pageProduct/add-Product/timer - 副本.vue @@ -0,0 +1,224 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-Product/timer.vue b/pageProduct/add-Product/timer.vue new file mode 100644 index 0000000..0556a3b --- /dev/null +++ b/pageProduct/add-Product/timer.vue @@ -0,0 +1,254 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-specifications/add-specifications - 副本 (2).vue b/pageProduct/add-specifications/add-specifications - 副本 (2).vue new file mode 100644 index 0000000..1b8fcac --- /dev/null +++ b/pageProduct/add-specifications/add-specifications - 副本 (2).vue @@ -0,0 +1,499 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-specifications/add-specifications - 副本.vue b/pageProduct/add-specifications/add-specifications - 副本.vue new file mode 100644 index 0000000..46772d8 --- /dev/null +++ b/pageProduct/add-specifications/add-specifications - 副本.vue @@ -0,0 +1,464 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-specifications/add-specifications.vue b/pageProduct/add-specifications/add-specifications.vue new file mode 100644 index 0000000..1036f63 --- /dev/null +++ b/pageProduct/add-specifications/add-specifications.vue @@ -0,0 +1,526 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/add-specifications/choose-specifications.vue b/pageProduct/add-specifications/choose-specifications.vue new file mode 100644 index 0000000..e1fa0d1 --- /dev/null +++ b/pageProduct/add-specifications/choose-specifications.vue @@ -0,0 +1,826 @@ + + + + \ No newline at end of file diff --git a/pageProduct/add-specifications/components/fast-edit.vue b/pageProduct/add-specifications/components/fast-edit.vue new file mode 100644 index 0000000..77cdacf --- /dev/null +++ b/pageProduct/add-specifications/components/fast-edit.vue @@ -0,0 +1,160 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/components/my-tabs.vue b/pageProduct/components/my-tabs.vue new file mode 100644 index 0000000..960a5d7 --- /dev/null +++ b/pageProduct/components/my-tabs.vue @@ -0,0 +1,44 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/goodsData.js b/pageProduct/goodsData.js new file mode 100644 index 0000000..3fa480a --- /dev/null +++ b/pageProduct/goodsData.js @@ -0,0 +1,74 @@ +import dayjs from "dayjs"; +export const $types = [{ + title: "计量商品", + desc: '单价购买', + value: 'normal' + }, + { + title: "多规格", + desc: '多种不同规格', + value: 'sku' + }, + { + title: "套餐组合", + desc: '选择多种组合', + value: 'group' + }, + { + title: "称重商品", + desc: '按重量售卖', + value: 'weight' + }, + { + title: "时价商品", + desc: '收银端可更改价格', + value: 'currentPrice' + } +] + +// 商品默认sku +export const $defaultSku = { + salePrice: '', + memberPrice: '', + costPrice: '', + originPrice: '', + // stockNumber: '', + firstShared: '', + suit: 1, + barCode: `${uni.getStorageSync("shopId")}${dayjs().valueOf()}`, +} + + +// 库存记录筛选类型 +export const $invoicingType = [{ + text: '全部', + value: '' + }, + { + text: '供应商入库', + value: 'purveyor' + }, + { + text: '供应商退货', + value: 'reject' + }, + { + text: '其他入库', + value: 'purchase' + }, + { + text: '其他出库', + value: 'other-out' + } +] + +// 页面常用数据 +export const $pageData = { + query: { + page: 0, + size: 10 + }, + totalElements: 0, + list: [], + hasAjax: false, +} \ No newline at end of file diff --git a/pageProduct/index/components/baosun.vue b/pageProduct/index/components/baosun.vue new file mode 100644 index 0000000..7680e7c --- /dev/null +++ b/pageProduct/index/components/baosun.vue @@ -0,0 +1,149 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/index/components/category - 副本 (2).vue b/pageProduct/index/components/category - 副本 (2).vue new file mode 100644 index 0000000..ebf1a34 --- /dev/null +++ b/pageProduct/index/components/category - 副本 (2).vue @@ -0,0 +1,120 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/index/components/category - 副本.vue b/pageProduct/index/components/category - 副本.vue new file mode 100644 index 0000000..8134f5a --- /dev/null +++ b/pageProduct/index/components/category - 副本.vue @@ -0,0 +1,93 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/index/components/category.vue b/pageProduct/index/components/category.vue new file mode 100644 index 0000000..3e86e9f --- /dev/null +++ b/pageProduct/index/components/category.vue @@ -0,0 +1,106 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/index/components/control.vue b/pageProduct/index/components/control.vue new file mode 100644 index 0000000..f26e667 --- /dev/null +++ b/pageProduct/index/components/control.vue @@ -0,0 +1,166 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/index/components/edit-guige.vue b/pageProduct/index/components/edit-guige.vue new file mode 100644 index 0000000..89de8c2 --- /dev/null +++ b/pageProduct/index/components/edit-guige.vue @@ -0,0 +1,171 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/index/components/edit-price.vue b/pageProduct/index/components/edit-price.vue new file mode 100644 index 0000000..f4c77eb --- /dev/null +++ b/pageProduct/index/components/edit-price.vue @@ -0,0 +1,251 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/index/components/edit-stock.vue b/pageProduct/index/components/edit-stock.vue new file mode 100644 index 0000000..cbd9303 --- /dev/null +++ b/pageProduct/index/components/edit-stock.vue @@ -0,0 +1,280 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/index/components/goods.vue b/pageProduct/index/components/goods.vue new file mode 100644 index 0000000..7eb9cf3 --- /dev/null +++ b/pageProduct/index/components/goods.vue @@ -0,0 +1,410 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/index/index.vue b/pageProduct/index/index.vue new file mode 100644 index 0000000..d0a60e3 --- /dev/null +++ b/pageProduct/index/index.vue @@ -0,0 +1,777 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/invoicing-check/components/list-item.vue b/pageProduct/invoicing-check/components/list-item.vue new file mode 100644 index 0000000..7e69259 --- /dev/null +++ b/pageProduct/invoicing-check/components/list-item.vue @@ -0,0 +1,171 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/invoicing-check/invoicing-check.vue b/pageProduct/invoicing-check/invoicing-check.vue new file mode 100644 index 0000000..7670be8 --- /dev/null +++ b/pageProduct/invoicing-check/invoicing-check.vue @@ -0,0 +1,204 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/invoicing-list/components/list-item.vue b/pageProduct/invoicing-list/components/list-item.vue new file mode 100644 index 0000000..50c0b9a --- /dev/null +++ b/pageProduct/invoicing-list/components/list-item.vue @@ -0,0 +1,140 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/invoicing-list/invoicing-list.vue b/pageProduct/invoicing-list/invoicing-list.vue new file mode 100644 index 0000000..807c62c --- /dev/null +++ b/pageProduct/invoicing-list/invoicing-list.vue @@ -0,0 +1,314 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/specification-template/components/specifications-item.vue b/pageProduct/specification-template/components/specifications-item.vue new file mode 100644 index 0000000..91a4827 --- /dev/null +++ b/pageProduct/specification-template/components/specifications-item.vue @@ -0,0 +1,128 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/specification-template/specification-template.vue b/pageProduct/specification-template/specification-template.vue new file mode 100644 index 0000000..6de52a4 --- /dev/null +++ b/pageProduct/specification-template/specification-template.vue @@ -0,0 +1,183 @@ + + + + + \ No newline at end of file diff --git a/pageProduct/static/images/icon-arrow-down-fill.svg b/pageProduct/static/images/icon-arrow-down-fill.svg new file mode 100644 index 0000000..4275b7e --- /dev/null +++ b/pageProduct/static/images/icon-arrow-down-fill.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pageProduct/static/images/icon-arrow-right.svg b/pageProduct/static/images/icon-arrow-right.svg new file mode 100644 index 0000000..3af849c --- /dev/null +++ b/pageProduct/static/images/icon-arrow-right.svg @@ -0,0 +1,3 @@ + + + diff --git a/pageProduct/static/images/icon-guige.svg b/pageProduct/static/images/icon-guige.svg new file mode 100644 index 0000000..5cd55a6 --- /dev/null +++ b/pageProduct/static/images/icon-guige.svg @@ -0,0 +1 @@ + \ No newline at end of file diff --git a/pageProduct/util.js b/pageProduct/util.js new file mode 100644 index 0000000..eff220a --- /dev/null +++ b/pageProduct/util.js @@ -0,0 +1,41 @@ +import { + $types +} from '@/commons/goodsData.js' +export function returnSkuSnap(goods) { + const selectSpec = typeof goods.selectSpec === 'string' ? JSON.parse(goods.selectSpec) : goods.selectSpec + let result = selectSpec.map(v => { + return { + name: v.name, + value: v.selectSpecResult.join(',') + } + }) + return result +} +export function returnTypeEnum(typeEnum) { + const item = $types.find(v => v.title == typeEnum) + let result = item ? item.value : undefined + return result +} +export function returnCategory(cateName, cateList) { + console.log(cateName); + console.log(cateList); + const item = cateList.find(v => v.name == cateName) + let result = item ? item : undefined + return result +} +export function returnAllCategory(arr) { + const result = arr.reduce((prve, cur) => { + prve.push(...[{ + ...cur, + name: '' + cur.name, + childrenList: undefined + }, ...cur.childrenList.map(v => { + return { + ...v, + name: '' + v.name + } + })]) + return prve + }, []) + return result +} diff --git a/pageRecharge/add-recharge-item.vue b/pageRecharge/add-recharge-item.vue new file mode 100644 index 0000000..3bba432 --- /dev/null +++ b/pageRecharge/add-recharge-item.vue @@ -0,0 +1,623 @@ + + + + + \ No newline at end of file diff --git a/pageRecharge/components/recharge-item.vue b/pageRecharge/components/recharge-item.vue new file mode 100644 index 0000000..6809d65 --- /dev/null +++ b/pageRecharge/components/recharge-item.vue @@ -0,0 +1,79 @@ + + + + + \ No newline at end of file diff --git a/pageRecharge/index.vue b/pageRecharge/index.vue new file mode 100644 index 0000000..0fcd180 --- /dev/null +++ b/pageRecharge/index.vue @@ -0,0 +1,299 @@ +