Commit edd43a1945d87c5d7ae1354615abb250b2197b8e

Authored by 徐烜
2 parents 8af90812 b40c9fd3

PSM-17

Too many changes to show.

To preserve performance only 11 of 13 files are displayed.

src/main/java/com/bsth/controller/BaseController.java
... ... @@ -17,6 +17,7 @@ import org.springframework.web.multipart.MultipartFile;
17 17  
18 18 import javax.servlet.http.HttpServletResponse;
19 19 import java.io.*;
  20 +import java.util.ArrayList;
20 21 import java.util.HashMap;
21 22 import java.util.List;
22 23 import java.util.Map;
... ... @@ -54,18 +55,31 @@ public class BaseController<T, ID extends Serializable> {
54 55 @RequestParam(defaultValue = "id") String order,
55 56 @RequestParam(defaultValue = "DESC") String direction){
56 57  
57   - Direction d;
58   -
59   - if(null != direction && direction.equals("ASC"))
60   - d = Direction.ASC;
61   - else
62   - d = Direction.DESC;
63   -
64 58 // 允许多个字段排序,order可以写单个字段,也可以写多个字段
65 59 // 多个字段格式:{col1},{col2},{col3},....,{coln}
66   - // 每个字段的排序方向都是一致,这个以后再看要不要改
67   - List<String> list = Splitter.on(",").trimResults().splitToList(order);
68   - return baseService.list(map, new PageRequest(page, size, new Sort(d, list)));
  60 + List<String> order_columns = Splitter.on(",").trimResults().splitToList(order);
  61 + // 多字段排序:DESC,ASC...
  62 + List<String> order_dirs = Splitter.on(",").trimResults().splitToList(direction);
  63 +
  64 + if (order_dirs.size() == 1) { // 所有字段采用一种排序
  65 + if (null != order_dirs.get(0) && order_dirs.get(0).equals("ASC")) {
  66 + return baseService.list(map, new PageRequest(page, size, new Sort(Direction.ASC, order_columns)));
  67 + } else {
  68 + return baseService.list(map, new PageRequest(page, size, new Sort(Direction.DESC, order_columns)));
  69 + }
  70 + } else if (order_columns.size() == order_dirs.size()) {
  71 + List<Sort.Order> orderList = new ArrayList<>();
  72 + for (int i = 0; i < order_columns.size(); i++) {
  73 + if (null != order_dirs.get(i) && order_dirs.get(i).equals("ASC")) {
  74 + orderList.add(new Sort.Order(Direction.ASC, order_columns.get(i)));
  75 + } else {
  76 + orderList.add(new Sort.Order(Direction.DESC, order_columns.get(i)));
  77 + }
  78 + }
  79 + return baseService.list(map, new PageRequest(page, size, new Sort(orderList)));
  80 + } else {
  81 + throw new RuntimeException("多字段排序参数格式问题,排序顺序和字段数不一致");
  82 + }
69 83 }
70 84  
71 85 /**
... ...
src/main/java/com/bsth/controller/CarDeviceController.java
1 1 package com.bsth.controller;
2 2  
  3 +import com.bsth.common.ResponseCode;
3 4 import com.bsth.entity.CarDevice;
  5 +import com.bsth.service.CarDeviceService;
  6 +import org.joda.time.DateTime;
  7 +import org.springframework.beans.factory.annotation.Autowired;
4 8 import org.springframework.web.bind.annotation.RequestBody;
5 9 import org.springframework.web.bind.annotation.RequestMapping;
6 10 import org.springframework.web.bind.annotation.RequestMethod;
7 11 import org.springframework.web.bind.annotation.RestController;
8 12  
  13 +import java.util.HashMap;
  14 +import java.util.Iterator;
9 15 import java.util.Map;
10 16  
11 17 /**
... ... @@ -14,7 +20,8 @@ import java.util.Map;
14 20 @RestController
15 21 @RequestMapping("cde")
16 22 public class CarDeviceController extends BaseController<CarDevice, Long> {
17   -
  23 + @Autowired
  24 + private CarDeviceService carDeviceService;
18 25 /**
19 26 * 覆写方法,因为form提交的方式参数不全,改用 json形式提交 @RequestBody
20 27 * @Title: save
... ... @@ -28,4 +35,22 @@ public class CarDeviceController extends BaseController&lt;CarDevice, Long&gt; {
28 35 public Map<String, Object> save(@RequestBody CarDevice t){
29 36 return baseService.save(t);
30 37 }
  38 +
  39 + @RequestMapping(value = "/validate/qyrq", method = RequestMethod.GET)
  40 + public Map<String, Object> validateQyrq(String qyrq, Integer xl, Integer cl) {
  41 + // 验证启用日期,必须是最大的日期,就是最晚的日期
  42 + Map<String, Object> obj = new HashMap<>();
  43 + obj.put("xl_eq", xl);
  44 + obj.put("cl_eq", cl);
  45 + obj.put("qyrq_ge", new DateTime(qyrq).toDate());
  46 + Iterator<CarDevice> iterator = carDeviceService.list(obj).iterator();
  47 + if (iterator.hasNext()) {
  48 + obj.clear();
  49 + obj.put("status", ResponseCode.ERROR);
  50 + } else {
  51 + obj.clear();
  52 + obj.put("status", ResponseCode.SUCCESS);
  53 + }
  54 + return obj;
  55 + }
31 56 }
... ...
src/main/java/com/bsth/entity/search/PredicatesBuilder.java
1 1 package com.bsth.entity.search;
2 2  
  3 +import javax.persistence.criteria.CriteriaBuilder;
  4 +import javax.persistence.criteria.Path;
  5 +import javax.persistence.criteria.Predicate;
3 6 import java.text.NumberFormat;
4 7 import java.text.ParseException;
5 8 import java.text.SimpleDateFormat;
6 9 import java.util.Date;
7 10  
8   -import javax.persistence.criteria.CriteriaBuilder;
9   -import javax.persistence.criteria.Path;
10   -import javax.persistence.criteria.Predicate;
11   -
12 11 /**
13 12 *
14 13 * @ClassName: PredicatesBuilder
... ... @@ -44,13 +43,22 @@ public class PredicatesBuilder {
44 43 }
45 44 }
46 45  
47   - public static Predicate ge(CriteriaBuilder cb,Path<Number> expression, Object object){
48   - try {
49   - return cb.ge(expression, nf.parse(object.toString()));
50   - } catch (ParseException e) {
51   - e.printStackTrace();
52   - return null;
53   - }
  46 + public static Predicate ge(CriteriaBuilder cb,Path<?> expression, Object object){
  47 + Class<?> leftType = expression.getJavaType();
  48 + Class<?> rightType = object.getClass();
  49 +
  50 + if (leftType.isAssignableFrom(Number.class) &&
  51 + rightType.isAssignableFrom(Number.class)) { // 判定是否是Number类型的子类
  52 + return cb.ge((Path<Number>) expression, (Number) object);
  53 + } else if (leftType.isAssignableFrom(String.class) &&
  54 + rightType.isAssignableFrom(String.class)) { // 判定是否是String类型的子类
  55 + return cb.greaterThanOrEqualTo((Path<String>) expression, (String) object);
  56 + } else if (leftType.isAssignableFrom(Date.class) &&
  57 + rightType.isAssignableFrom(Date.class)) { // 判定是否是Date类型的子类
  58 + return cb.greaterThanOrEqualTo((Path<Date>) expression, (Date) object);
  59 + } else {
  60 + throw new RuntimeException("ge 不支持类型组合:" + expression.getJavaType() + ">=" + object.getClass());
  61 + }
54 62 }
55 63  
56 64 public static Predicate lt(CriteriaBuilder cb,Path<Number> expression, Object object){
... ... @@ -62,13 +70,22 @@ public class PredicatesBuilder {
62 70 }
63 71 }
64 72  
65   - public static Predicate le(CriteriaBuilder cb,Path<Number> expression, Object object){
66   - try {
67   - return cb.le(expression, nf.parse(object.toString()));
68   - } catch (ParseException e) {
69   - e.printStackTrace();
70   - return null;
71   - }
  73 + public static Predicate le(CriteriaBuilder cb,Path<?> expression, Object object){
  74 + Class<?> leftType = expression.getJavaType();
  75 + Class<?> rightType = object.getClass();
  76 +
  77 + if (leftType.isAssignableFrom(Number.class) &&
  78 + rightType.isAssignableFrom(Number.class)) { // 判定是否是Number类型的子类
  79 + return cb.le((Path<Number>) expression, (Number) object);
  80 + } else if (leftType.isAssignableFrom(String.class) &&
  81 + rightType.isAssignableFrom(String.class)) { // 判定是否是String类型的子类
  82 + return cb.lessThanOrEqualTo((Path<String>) expression, (String) object);
  83 + } else if (leftType.isAssignableFrom(Date.class) &&
  84 + rightType.isAssignableFrom(Date.class)) { // 判定是否是Date类型的子类
  85 + return cb.lessThanOrEqualTo((Path<Date>) expression, (Date) object);
  86 + } else {
  87 + throw new RuntimeException("ge 不支持类型组合:" + expression.getJavaType() + ">=" + object.getClass());
  88 + }
72 89 }
73 90  
74 91 public static Predicate prefixLike(CriteriaBuilder cb,Path<String> expression, Object object){
... ...
src/main/java/com/bsth/service/impl/CarDeviceServiceImpl.java
... ... @@ -2,8 +2,10 @@ package com.bsth.service.impl;
2 2  
3 3 import com.bsth.common.ResponseCode;
4 4 import com.bsth.entity.CarDevice;
  5 +import com.bsth.entity.Cars;
5 6 import com.bsth.entity.schedule.rule.RerunRule;
6 7 import com.bsth.repository.CarDeviceRepository;
  8 +import com.bsth.repository.CarsRepository;
7 9 import com.bsth.service.CarDeviceService;
8 10 import org.springframework.beans.factory.annotation.Autowired;
9 11 import org.springframework.stereotype.Service;
... ... @@ -17,9 +19,31 @@ import java.util.Map;
17 19 */
18 20 @Service
19 21 public class CarDeviceServiceImpl extends BaseServiceImpl<CarDevice, Long> implements CarDeviceService {
20   -
21 22 @Autowired
22 23 private CarDeviceRepository carDeviceRepository;
  24 + @Autowired
  25 + private CarsRepository carsRepository;
  26 +
  27 + @Transactional
  28 + @Override
  29 + public Map<String, Object> save(CarDevice carDevice) {
  30 + Map<String, Object> map = new HashMap<>();
  31 +
  32 + try {
  33 + // 查找对应的车辆基础信息,更新设备编号数据
  34 + Cars cars = carsRepository.findOne(carDevice.getCl());
  35 + cars.setEquipmentCode(carDevice.getNewDeviceNo());
  36 + // 保存车辆设备信息
  37 + carDeviceRepository.save(carDevice);
  38 + map.put("status", ResponseCode.SUCCESS);
  39 + map.put("t", carDevice);
  40 + } catch(Exception e) {
  41 + map.put("status", ResponseCode.ERROR);
  42 + logger.error("save erro.", e);
  43 + }
  44 +
  45 + return map;
  46 + }
23 47  
24 48 @Transactional
25 49 @Override
... ...
src/main/resources/static/pages/scheduleApp/module/basicInfo/busInfoManage/edit.html
... ... @@ -45,7 +45,10 @@
45 45 <div class="col-md-3">
46 46 <input type="text" class="form-control"
47 47 name="insideCode" ng-model="ctrl.busInfoForSave.insideCode"
48   - required ng-maxlength="8" remote-Validaton rvtype="insideCode"
  48 + required ng-maxlength="8"
  49 + remote-Validation
  50 + remotevtype="cl1"
  51 + remotevparam="{{ {'insideCode_eq': ctrl.busInfoForSave.insideCode} | json}}"
49 52 placeholder="请输入车辆内部编码"/>
50 53 </div>
51 54 <!-- 隐藏块,显示验证信息 -->
... ...
src/main/resources/static/pages/scheduleApp/module/basicInfo/busInfoManage/form.html
... ... @@ -45,7 +45,10 @@
45 45 <div class="col-md-3">
46 46 <input type="text" class="form-control"
47 47 name="insideCode" ng-model="ctrl.busInfoForSave.insideCode"
48   - required ng-maxlength="8" remote-Validaton rvtype="insideCode"
  48 + required ng-maxlength="8"
  49 + remote-Validation
  50 + remotevtype="cl1"
  51 + remotevparam="{{ {'insideCode_eq': ctrl.busInfoForSave.insideCode} | json}}"
49 52 placeholder="请输入车辆内部编码"/>
50 53 </div>
51 54 <!-- 隐藏块,显示验证信息 -->
... ...
src/main/resources/static/pages/scheduleApp/module/basicInfo/deviceInfoManage/edit.html
... ... @@ -144,7 +144,10 @@
144 144 name="qyrq" placeholder="请选择启用日期..."
145 145 uib-datepicker-popup="yyyy年MM月dd日"
146 146 is-open="ctrl.qyrqOpen" required
147   - ng-model="ctrl.deviceInfoForSave.qyrq" readonly/>
  147 + ng-model="ctrl.deviceInfoForSave.qyrq" readonly
  148 + remote-Validation
  149 + remotevtype="cde1"
  150 + remotevparam="{{ {'qyrq': ctrl.deviceInfoForSave.qyrq} | json}}"/>
148 151 <span class="input-group-btn">
149 152 <button type="button" class="btn btn-default" ng-click="ctrl.qyrq_open()">
150 153 <i class="glyphicon glyphicon-calendar"></i>
... ...
src/main/resources/static/pages/scheduleApp/module/basicInfo/deviceInfoManage/form.html
... ... @@ -144,7 +144,10 @@
144 144 name="qyrq" placeholder="请选择启用日期..."
145 145 uib-datepicker-popup="yyyy年MM月dd日"
146 146 is-open="ctrl.qyrqOpen" required
147   - ng-model="ctrl.deviceInfoForSave.qyrq" readonly/>
  147 + ng-model="ctrl.deviceInfoForSave.qyrq" readonly
  148 + remote-Validation
  149 + remotevtype="cde1"
  150 + remotevparam="{{ {'qyrq': ctrl.deviceInfoForSave.qyrq, 'xl': ctrl.deviceInfoForSave.xl, 'cl': ctrl.deviceInfoForSave.cl} | json}}"/>
148 151 <span class="input-group-btn">
149 152 <button type="button" class="btn btn-default" ng-click="ctrl.qyrq_open()">
150 153 <i class="glyphicon glyphicon-calendar"></i>
... ... @@ -156,6 +159,9 @@
156 159 <div class="alert alert-danger well-sm" ng-show="myForm.qyrq.$error.required">
157 160 启用日期必须选择
158 161 </div>
  162 + <div class="alert alert-danger well-sm" ng-show="myForm.qyrq.$error.remote">
  163 + 启用日期必须比历史的启用日期大
  164 + </div>
159 165 </div>
160 166  
161 167 <!-- 其他form-group -->
... ...
src/main/resources/static/pages/scheduleApp/module/common/dts1/ttt.txt deleted 100644 → 0
src/main/resources/static/pages/scheduleApp/module/common/dts1/validation/remoteValidaton.js
1   -angular.module('ScheduleApp').directive("remoteValidaton", [
2   - 'BusInfoManageService_g',
3   - 'EmployeeInfoManageService_g',
4   - 'TimeTableManageService_g',
5   - function(
6   - busInfoManageService_g,
7   - employeeInfoManageService_g,
8   - timeTableManageService_g
9   - ) {
10   - /**
11   - * 远端验证指令,依赖于ngModel
12   - * 指令名称 remote-Validation
13   - * 需要属性 rvtype 表示验证类型
14   - */
15   - return {
16   - restrict: "A",
17   - require: "^ngModel",
18   - link: function(scope, element, attr, ngModelCtrl) {
19   - element.bind("keyup", function() {
20   - var modelValue = ngModelCtrl.$modelValue;
21   - var rv1_attr = attr["rv1"];
22   - if (attr["rvtype"]) {
  1 +/**
  2 + * remoteValidatio指令,远程数据验证验证,作为属性放在某个指令上,依赖与指令的ngModel。
  3 + * 属性如下:
  4 + * remotevtype(必须):验证类型(在service中有对应映射),如rvtype="xl"
  5 + * remotevparam(必须):后端判定查询参数,如rvparam={{ {'xl.id_eq': '123'} | json }}
  6 + *
  7 + */
  8 +angular.module('ScheduleApp').directive('remoteValidation', [
  9 + '$$SearchInfoService_g',
  10 + function($$SearchInfoService_g) {
  11 + return {
  12 + restrict: "A", // 属性
  13 + require: "^ngModel", // 依赖所属指令的ngModel
  14 + compile: function(tElem, tAttrs) {
  15 + // 验证属性
  16 + if (!tAttrs["remotevtype"]) { // 验证类型
  17 + throw new Error("remotevtype属性必须填写");
  18 + } else if (!$$SearchInfoService_g.validate[tAttrs["remotevtype"]]) {
  19 + throw new Error(!tAttrs["remotevtype"] + "验证类型不存在");
  20 + }
  21 + if (!tAttrs["remotevparam"]) { // 查询参数
  22 + throw new Error("remotevparam属性必须填写");
  23 + }
23 24  
24   - // 根据rvtype的值,确定使用那个远端验证的url,
25   - // rv1, rv2, rv3是关联比较值,暂时使用rv1
26   - // 这个貌似没法通用,根据业务变换
27   - // TODO:暂时有点乱以后改
28   - if (attr["rvtype"] == "insideCode") {
29   - busInfoManageService_g.validate.insideCode(
30   - {"insideCode_eq": modelValue, type: "equale"},
31   - function(result) {
32   - //console.log(result);
33   - if (result.status == "SUCCESS") {
34   - ngModelCtrl.$setValidity('remote', true);
35   - } else {
36   - ngModelCtrl.$setValidity('remote', false);
37   - }
38   - },
39   - function(result) {
40   - //console.log(result);
41   - ngModelCtrl.$setValidity('remote', true);
42   - }
43   - );
44   - } else if (attr["rvtype"] == "jobCode") {
45   - if (!rv1_attr) {
46   - ngModelCtrl.$setValidity('remote', false);
47   - return;
48   - }
  25 + // 监听获取的数据
  26 + var $watch_rvtype = undefined;
  27 + var $watch_rvparam_obj = undefined;
49 28  
50   - employeeInfoManageService_g.validate.jobCode(
51   - {"jobCode_eq": modelValue, "companyCode_eq": rv1_attr, type: "equale"},
52   - function(result) {
53   - //console.log(result);
54   - if (result.status == "SUCCESS") {
55   - ngModelCtrl.$setValidity('remote', true);
56   - } else {
57   - ngModelCtrl.$setValidity('remote', false);
58   - }
59   - },
60   - function(result) {
61   - //console.log(result);
  29 + // 验证数据
  30 + var $$internal_validate = function(ngModelCtrl) {
  31 + if ($watch_rvtype && $watch_rvparam_obj) {
  32 + // 获取查询参数模版
  33 + var paramTemplate = $$SearchInfoService_g.validate[$watch_rvtype].template;
  34 + if (!paramTemplate) {
  35 + throw new Error($watch_rvtype + "查询模版不存在");
  36 + }
  37 + // 判定如果参数对象不全,没有完全和模版参数里对应上,则不验证
  38 + var isParamAll = true;
  39 + for (var key in paramTemplate) {
  40 + if (!$watch_rvparam_obj[key]) {
  41 + isParamAll = false;
  42 + break;
  43 + }
  44 + }
  45 + if (!isParamAll) {
  46 + ngModelCtrl.$setValidity('remote', true);
  47 + } else { // 开始验证
  48 + $$SearchInfoService_g.validate[$watch_rvtype].remote.do(
  49 + $watch_rvparam_obj,
  50 + function(result) {
  51 + if (result.status == "SUCCESS") {
62 52 ngModelCtrl.$setValidity('remote', true);
  53 + } else {
  54 + ngModelCtrl.$setValidity('remote', false);
63 55 }
64   - );
65   - } else if (attr["rvtype"] == "ttinfoname") {
66   - if (!rv1_attr) {
67   - ngModelCtrl.$setValidity('remote', false);
68   - return;
  56 + },
  57 + function(result) {
  58 + ngModelCtrl.$setValidity('remote', true);
69 59 }
70   -
71   - timeTableManageService_g.validate.ttinfoname(
72   - {"name_eq": modelValue, "xl.id_eq": rv1_attr, type: "equale"},
73   - function(result) {
74   - //console.log(result);
75   - if (result.status == "SUCCESS") {
76   - ngModelCtrl.$setValidity('remote', true);
77   - } else {
78   - ngModelCtrl.$setValidity('remote', false);
79   - }
80   - },
81   - function(result) {
82   - //console.log(result);
83   - ngModelCtrl.$setValidity('remote', true);
84   - }
85   - );
86   -
87   - }
88   - } else {
89   - // 没有rvtype,就不用远端验证了
90   - ngModelCtrl.$setValidity('remote', true);
  60 + );
91 61 }
  62 + }
  63 + };
92 64  
93   - attr.$observe("rv1", function(value) {
94   - if (attr["rvtype"] == "jobCode") {
95   - if (!value) {
96   - ngModelCtrl.$setValidity('remote', false);
97   - return;
98   - }
  65 + return {
  66 + pre: function(scope, element, attr) {
99 67  
100   - employeeInfoManageService_g.validate.jobCode(
101   - {"jobCode_eq": modelValue, "companyCode_eq": rv1_attr, type: "equale"},
102   - function(result) {
103   - //console.log(result);
104   - if (result.status == "SUCCESS") {
105   - ngModelCtrl.$setValidity('remote', true);
106   - } else {
107   - ngModelCtrl.$setValidity('remote', false);
108   - }
109   - },
110   - function(result) {
111   - //console.log(result);
112   - ngModelCtrl.$setValidity('remote', true);
113   - }
114   - );
115   - } else if (attr["rvtype"] == "ttinfoname") {
116   - if (!value) {
117   - ngModelCtrl.$setValidity('remote', false);
  68 + },
  69 +
  70 + post: function(scope, element, attr, ngModelCtrl) {
  71 + /**
  72 + * 监控验证类型属性变化。
  73 + */
  74 + attr.$observe("remotevtype", function(value) {
  75 + if (value && value != "") {
  76 + $watch_rvtype = value;
  77 + $$internal_validate(ngModelCtrl);
  78 + }
  79 + });
  80 + /**
  81 + * 监控查询结果属性变化。
  82 + */
  83 + attr.$observe("remotevparam", function(value) {
  84 + if (value && value != "") {
  85 + if (!ngModelCtrl.$dirty) { // 没有修改过模型数据,不验证
118 86 return;
119 87 }
120   -
121   - console.log("rv1:" + value);
122   -
123   - timeTableManageService_g.validate.ttinfoname(
124   - {"name_eq": modelValue, "xl.id_eq": value, type: "equale"},
125   - function(result) {
126   - //console.log(result);
127   - if (result.status == "SUCCESS") {
128   - ngModelCtrl.$setValidity('remote', true);
129   - } else {
130   - ngModelCtrl.$setValidity('remote', false);
131   - }
132   - },
133   - function(result) {
134   - //console.log(result);
135   - ngModelCtrl.$setValidity('remote', true);
136   - }
137   - );
  88 + $watch_rvparam_obj = JSON.parse(value);
  89 + $$internal_validate(ngModelCtrl);
138 90 }
139   -
140 91 });
141   - });
142   - }
143   - };
  92 + }
  93 + };
  94 + }
144 95 }
145   - ]
146   -);
147 96 \ No newline at end of file
  97 + }
  98 +]);
... ...
src/main/resources/static/pages/scheduleApp/module/common/dts1/validation/temp.txt 0 → 100644
  1 +busInfoManage
  2 +
  3 +employeeInfoManage
  4 +
  5 +timeTableManage
0 6 \ No newline at end of file
... ...