Commit b6799868b18fa309e0a45bbe20487b4f1ff0c59b
1 parent
44e03ed0
浦东车辆信息更新修正
1、修改新增同步任务界面,后台添加 vsTaskType 字典用于区分同步类型并修改界面 2、优化后台同步task的代码
Showing
6 changed files
with
137 additions
and
122 deletions
src/main/java/com/bsth/entity/schedule/datasync/VehicleDataSyncTask.java
src/main/java/com/bsth/service/schedule/datasync/VehicleDataSyncTaskServiceImpl.java
| @@ -148,28 +148,27 @@ public class VehicleDataSyncTaskServiceImpl extends BServiceImpl<VehicleDataSync | @@ -148,28 +148,27 @@ public class VehicleDataSyncTaskServiceImpl extends BServiceImpl<VehicleDataSync | ||
| 148 | .build()).start(); | 148 | .build()).start(); |
| 149 | // 3、等待同步结束 | 149 | // 3、等待同步结束 |
| 150 | countDownLatch.await(); | 150 | countDownLatch.await(); |
| 151 | - // 3-1、更新日志 | ||
| 152 | - task.setEndDate(new Date()); | ||
| 153 | - long runMills = task.getEndDate().getTime() - task.getStartDate().getTime(); | ||
| 154 | - task.setProcessSeconds((int) runMills / 1000); | ||
| 155 | - task.setStatus(VehicleDataSyncTaskStatusEnum.END); | ||
| 156 | - task.setProcessMsg("成功!"); | ||
| 157 | - super.save(task); | 151 | + |
| 158 | } catch (Exception exp) { | 152 | } catch (Exception exp) { |
| 159 | // 获取异常stack信息 | 153 | // 获取异常stack信息 |
| 160 | StringWriter sw = new StringWriter(); | 154 | StringWriter sw = new StringWriter(); |
| 161 | PrintWriter pw = new PrintWriter(sw); | 155 | PrintWriter pw = new PrintWriter(sw); |
| 162 | exp.printStackTrace(pw); | 156 | exp.printStackTrace(pw); |
| 157 | + task.setProcessMsg("有问题:" + StringUtils.substring(sw.toString(), 0, 1800)); // 日志限定长度 | ||
| 158 | + } finally { | ||
| 159 | + MDC.clear(); | ||
| 163 | 160 | ||
| 164 | - // 更新日志 | 161 | + // 3-1、更新执行信息 |
| 162 | + if (StringUtils.isEmpty(task.getProcessMsg())) { | ||
| 163 | + task.setProcessMsg("成功!"); | ||
| 164 | + } | ||
| 165 | + // 3-2、更新执行时间 | ||
| 165 | task.setEndDate(new Date()); | 166 | task.setEndDate(new Date()); |
| 166 | long runMills = task.getEndDate().getTime() - task.getStartDate().getTime(); | 167 | long runMills = task.getEndDate().getTime() - task.getStartDate().getTime(); |
| 167 | task.setProcessSeconds((int) runMills / 1000); | 168 | task.setProcessSeconds((int) runMills / 1000); |
| 168 | task.setStatus(VehicleDataSyncTaskStatusEnum.END); | 169 | task.setStatus(VehicleDataSyncTaskStatusEnum.END); |
| 169 | - task.setProcessMsg("有问题:" + StringUtils.substring(sw.toString(), 0, 1800)); // 日志限定长度 | 170 | + // 3-3、更新任务信息 |
| 170 | super.save(task); | 171 | super.save(task); |
| 171 | - } finally { | ||
| 172 | - MDC.clear(); | ||
| 173 | } | 172 | } |
| 174 | } | 173 | } |
| 175 | 174 |
src/main/java/com/bsth/service/schedule/datasync/task/VehicleDataSyncTaskThread.java
| @@ -104,8 +104,8 @@ public class VehicleDataSyncTaskThread implements Runnable { | @@ -104,8 +104,8 @@ public class VehicleDataSyncTaskThread implements Runnable { | ||
| 104 | vehicleDataSyncTask.setSyncUpdateCounts(Long.valueOf( | 104 | vehicleDataSyncTask.setSyncUpdateCounts(Long.valueOf( |
| 105 | processKtrStepMeatureMap.get("更新车辆数据输出").updates).intValue()); | 105 | processKtrStepMeatureMap.get("更新车辆数据输出").updates).intValue()); |
| 106 | vehicleDataSyncTask.setSyncErrorCounts(Long.valueOf( | 106 | vehicleDataSyncTask.setSyncErrorCounts(Long.valueOf( |
| 107 | - processKtrStepMeatureMap.get("新增车辆数据输出").errors + | ||
| 108 | - processKtrStepMeatureMap.get("更新车辆数据输出").errors).intValue()); | 107 | + processKtrStepMeatureMap.get("新增错误数据文件").writes + |
| 108 | + processKtrStepMeatureMap.get("更新错误数据文件").writes).intValue()); | ||
| 109 | 109 | ||
| 110 | LOG.info("ktr执行度量值:{}", processKtrStepMeatureMap); | 110 | LOG.info("ktr执行度量值:{}", processKtrStepMeatureMap); |
| 111 | 111 | ||
| @@ -190,7 +190,7 @@ public class VehicleDataSyncTaskThread implements Runnable { | @@ -190,7 +190,7 @@ public class VehicleDataSyncTaskThread implements Runnable { | ||
| 190 | ); | 190 | ); |
| 191 | LOG.info(stringBuffer.toString()); | 191 | LOG.info(stringBuffer.toString()); |
| 192 | 192 | ||
| 193 | - // 如果task内部有errors,更新日志 | 193 | + // 如果task内部有errors,更新执行信息 |
| 194 | if (processKtrStepMeatureMap.get("数据检验错误输出").writes > 0) { | 194 | if (processKtrStepMeatureMap.get("数据检验错误输出").writes > 0) { |
| 195 | task.setProcessMsg("有问题:存在数据检验错误,请查看日志!"); | 195 | task.setProcessMsg("有问题:存在数据检验错误,请查看日志!"); |
| 196 | } else if (processKtrStepMeatureMap.get("新增错误数据文件").writes > 0) { | 196 | } else if (processKtrStepMeatureMap.get("新增错误数据文件").writes > 0) { |
src/main/resources/datatools/ktrs/vehicleDataSync.ktr
| @@ -41,12 +41,12 @@ | @@ -41,12 +41,12 @@ | ||
| 41 | </parameter> | 41 | </parameter> |
| 42 | <parameter> | 42 | <parameter> |
| 43 | <name>paramFrom</name> | 43 | <name>paramFrom</name> |
| 44 | - <default_value>2021-01-01 00:00:00</default_value> | 44 | + <default_value/> |
| 45 | <description>参数-开始时间(格式:yyyy-MM-dd HH:mm:ss)</description> | 45 | <description>参数-开始时间(格式:yyyy-MM-dd HH:mm:ss)</description> |
| 46 | </parameter> | 46 | </parameter> |
| 47 | <parameter> | 47 | <parameter> |
| 48 | <name>paramTo</name> | 48 | <name>paramTo</name> |
| 49 | - <default_value>2021-05-01 00:00:00</default_value> | 49 | + <default_value/> |
| 50 | <description>参数-结束时间(格式:yyyy-MM-dd HH:mm:ss)</description> | 50 | <description>参数-结束时间(格式:yyyy-MM-dd HH:mm:ss)</description> |
| 51 | </parameter> | 51 | </parameter> |
| 52 | <parameter> | 52 | <parameter> |
| @@ -1032,6 +1032,41 @@ | @@ -1032,6 +1032,41 @@ | ||
| 1032 | </step> | 1032 | </step> |
| 1033 | 1033 | ||
| 1034 | <step> | 1034 | <step> |
| 1035 | + <name>判断是否报废更新</name> | ||
| 1036 | + <type>FilterRows</type> | ||
| 1037 | + <description/> | ||
| 1038 | + <distribute>Y</distribute> | ||
| 1039 | + <custom_distribution/> | ||
| 1040 | + <copies>1</copies> | ||
| 1041 | + <partitioning> | ||
| 1042 | + <method>none</method> | ||
| 1043 | + <schema_name/> | ||
| 1044 | + </partitioning> | ||
| 1045 | +<send_true_to>是否报废且曾经配置过线路</send_true_to> | ||
| 1046 | +<send_false_to/> | ||
| 1047 | + <compare> | ||
| 1048 | +<condition> | ||
| 1049 | + <negated>N</negated> | ||
| 1050 | + <conditions> | ||
| 1051 | + <condition> | ||
| 1052 | + <negated>N</negated> | ||
| 1053 | + <operator>OR</operator> | ||
| 1054 | + <leftvalue>isScrapUpdate</leftvalue> | ||
| 1055 | + <function>=</function> | ||
| 1056 | + <rightvalue/> | ||
| 1057 | + <value><name>constant</name><type>Boolean</type><text>Y</text><length>-1</length><precision>-1</precision><isnull>N</isnull><mask/></value> </condition> | ||
| 1058 | + </conditions> | ||
| 1059 | + </condition> | ||
| 1060 | + </compare> | ||
| 1061 | + <cluster_schema/> | ||
| 1062 | + <remotesteps> <input> </input> <output> </output> </remotesteps> <GUI> | ||
| 1063 | + <xloc>672</xloc> | ||
| 1064 | + <yloc>497</yloc> | ||
| 1065 | + <draw>Y</draw> | ||
| 1066 | + </GUI> | ||
| 1067 | + </step> | ||
| 1068 | + | ||
| 1069 | + <step> | ||
| 1035 | <name>字段选择</name> | 1070 | <name>字段选择</name> |
| 1036 | <type>SelectValues</type> | 1071 | <type>SelectValues</type> |
| 1037 | <description/> | 1072 | <description/> |
| @@ -1309,6 +1344,25 @@ | @@ -1309,6 +1344,25 @@ | ||
| 1309 | </step> | 1344 | </step> |
| 1310 | 1345 | ||
| 1311 | <step> | 1346 | <step> |
| 1347 | + <name>待处理更新数据</name> | ||
| 1348 | + <type>Dummy</type> | ||
| 1349 | + <description/> | ||
| 1350 | + <distribute>N</distribute> | ||
| 1351 | + <custom_distribution/> | ||
| 1352 | + <copies>1</copies> | ||
| 1353 | + <partitioning> | ||
| 1354 | + <method>none</method> | ||
| 1355 | + <schema_name/> | ||
| 1356 | + </partitioning> | ||
| 1357 | + <cluster_schema/> | ||
| 1358 | + <remotesteps> <input> </input> <output> </output> </remotesteps> <GUI> | ||
| 1359 | + <xloc>673</xloc> | ||
| 1360 | + <yloc>406</yloc> | ||
| 1361 | + <draw>Y</draw> | ||
| 1362 | + </GUI> | ||
| 1363 | + </step> | ||
| 1364 | + | ||
| 1365 | + <step> | ||
| 1312 | <name>待新增数据</name> | 1366 | <name>待新增数据</name> |
| 1313 | <type>Dummy</type> | 1367 | <type>Dummy</type> |
| 1314 | <description/> | 1368 | <description/> |
| @@ -2115,6 +2169,47 @@ | @@ -2115,6 +2169,47 @@ | ||
| 2115 | </step> | 2169 | </step> |
| 2116 | 2170 | ||
| 2117 | <step> | 2171 | <step> |
| 2172 | + <name>是否报废且曾经配置过线路</name> | ||
| 2173 | + <type>FilterRows</type> | ||
| 2174 | + <description/> | ||
| 2175 | + <distribute>Y</distribute> | ||
| 2176 | + <custom_distribution/> | ||
| 2177 | + <copies>1</copies> | ||
| 2178 | + <partitioning> | ||
| 2179 | + <method>none</method> | ||
| 2180 | + <schema_name/> | ||
| 2181 | + </partitioning> | ||
| 2182 | +<send_true_to>报废车辆管理设备数据处理</send_true_to> | ||
| 2183 | +<send_false_to/> | ||
| 2184 | + <compare> | ||
| 2185 | +<condition> | ||
| 2186 | + <negated>N</negated> | ||
| 2187 | + <conditions> | ||
| 2188 | + <condition> | ||
| 2189 | + <negated>N</negated> | ||
| 2190 | + <leftvalue>scrapState_update</leftvalue> | ||
| 2191 | + <function>=</function> | ||
| 2192 | + <rightvalue/> | ||
| 2193 | + <value><name>constant</name><type>String</type><text>1</text><length>-1</length><precision>-1</precision><isnull>N</isnull><mask/></value> </condition> | ||
| 2194 | + <condition> | ||
| 2195 | + <negated>N</negated> | ||
| 2196 | + <operator>AND</operator> | ||
| 2197 | + <leftvalue>xl</leftvalue> | ||
| 2198 | + <function>IS NOT NULL</function> | ||
| 2199 | + <rightvalue/> | ||
| 2200 | + </condition> | ||
| 2201 | + </conditions> | ||
| 2202 | + </condition> | ||
| 2203 | + </compare> | ||
| 2204 | + <cluster_schema/> | ||
| 2205 | + <remotesteps> <input> </input> <output> </output> </remotesteps> <GUI> | ||
| 2206 | + <xloc>513</xloc> | ||
| 2207 | + <yloc>585</yloc> | ||
| 2208 | + <draw>Y</draw> | ||
| 2209 | + </GUI> | ||
| 2210 | + </step> | ||
| 2211 | + | ||
| 2212 | + <step> | ||
| 2118 | <name>更新数据处理</name> | 2213 | <name>更新数据处理</name> |
| 2119 | <type>ScriptValueMod</type> | 2214 | <type>ScriptValueMod</type> |
| 2120 | <description/> | 2215 | <description/> |
| @@ -2192,7 +2287,7 @@ | @@ -2192,7 +2287,7 @@ | ||
| 2192 | <replace>N</replace> | 2287 | <replace>N</replace> |
| 2193 | </field> <field> <name>scrapDate_update</name> | 2288 | </field> <field> <name>scrapDate_update</name> |
| 2194 | <rename>scrapDate_update</rename> | 2289 | <rename>scrapDate_update</rename> |
| 2195 | - <type>String</type> | 2290 | + <type>Date</type> |
| 2196 | <length>-1</length> | 2291 | <length>-1</length> |
| 2197 | <precision>-1</precision> | 2292 | <precision>-1</precision> |
| 2198 | <replace>N</replace> | 2293 | <replace>N</replace> |
| @@ -2866,107 +2961,6 @@ | @@ -2866,107 +2961,6 @@ | ||
| 2866 | </GUI> | 2961 | </GUI> |
| 2867 | </step> | 2962 | </step> |
| 2868 | 2963 | ||
| 2869 | - <step> | ||
| 2870 | - <name>是否报废且曾经配置过线路</name> | ||
| 2871 | - <type>FilterRows</type> | ||
| 2872 | - <description/> | ||
| 2873 | - <distribute>Y</distribute> | ||
| 2874 | - <custom_distribution/> | ||
| 2875 | - <copies>1</copies> | ||
| 2876 | - <partitioning> | ||
| 2877 | - <method>none</method> | ||
| 2878 | - <schema_name/> | ||
| 2879 | - </partitioning> | ||
| 2880 | -<send_true_to>报废车辆管理设备数据处理</send_true_to> | ||
| 2881 | -<send_false_to/> | ||
| 2882 | - <compare> | ||
| 2883 | -<condition> | ||
| 2884 | - <negated>N</negated> | ||
| 2885 | - <conditions> | ||
| 2886 | - <condition> | ||
| 2887 | - <negated>N</negated> | ||
| 2888 | - <leftvalue>scrapState_update</leftvalue> | ||
| 2889 | - <function>=</function> | ||
| 2890 | - <rightvalue/> | ||
| 2891 | - <value><name>constant</name><type>String</type><text>1</text><length>-1</length><precision>-1</precision><isnull>N</isnull><mask/></value> </condition> | ||
| 2892 | - <condition> | ||
| 2893 | - <negated>N</negated> | ||
| 2894 | - <operator>AND</operator> | ||
| 2895 | - <leftvalue>xl</leftvalue> | ||
| 2896 | - <function>IS NOT NULL</function> | ||
| 2897 | - <rightvalue/> | ||
| 2898 | - </condition> | ||
| 2899 | - </conditions> | ||
| 2900 | - </condition> | ||
| 2901 | - </compare> | ||
| 2902 | - <cluster_schema/> | ||
| 2903 | - <remotesteps> <input> </input> <output> </output> </remotesteps> <GUI> | ||
| 2904 | - <xloc>513</xloc> | ||
| 2905 | - <yloc>585</yloc> | ||
| 2906 | - <draw>Y</draw> | ||
| 2907 | - </GUI> | ||
| 2908 | - </step> | ||
| 2909 | - | ||
| 2910 | - <step> | ||
| 2911 | - <name>判断是否报废更新</name> | ||
| 2912 | - <type>FilterRows</type> | ||
| 2913 | - <description/> | ||
| 2914 | - <distribute>Y</distribute> | ||
| 2915 | - <custom_distribution/> | ||
| 2916 | - <copies>1</copies> | ||
| 2917 | - <partitioning> | ||
| 2918 | - <method>none</method> | ||
| 2919 | - <schema_name/> | ||
| 2920 | - </partitioning> | ||
| 2921 | -<send_true_to>是否报废且曾经配置过线路</send_true_to> | ||
| 2922 | -<send_false_to/> | ||
| 2923 | - <compare> | ||
| 2924 | -<condition> | ||
| 2925 | - <negated>N</negated> | ||
| 2926 | - <conditions> | ||
| 2927 | - <condition> | ||
| 2928 | - <negated>N</negated> | ||
| 2929 | - <leftvalue>isGsUpdate</leftvalue> | ||
| 2930 | - <function>=</function> | ||
| 2931 | - <rightvalue/> | ||
| 2932 | - <value><name>constant</name><type>Boolean</type><text>Y</text><length>-1</length><precision>-1</precision><isnull>N</isnull><mask/></value> </condition> | ||
| 2933 | - <condition> | ||
| 2934 | - <negated>N</negated> | ||
| 2935 | - <operator>OR</operator> | ||
| 2936 | - <leftvalue>isScrapUpdate</leftvalue> | ||
| 2937 | - <function>=</function> | ||
| 2938 | - <rightvalue/> | ||
| 2939 | - <value><name>constant</name><type>Boolean</type><text>Y</text><length>-1</length><precision>-1</precision><isnull>N</isnull><mask/></value> </condition> | ||
| 2940 | - </conditions> | ||
| 2941 | - </condition> | ||
| 2942 | - </compare> | ||
| 2943 | - <cluster_schema/> | ||
| 2944 | - <remotesteps> <input> </input> <output> </output> </remotesteps> <GUI> | ||
| 2945 | - <xloc>672</xloc> | ||
| 2946 | - <yloc>497</yloc> | ||
| 2947 | - <draw>Y</draw> | ||
| 2948 | - </GUI> | ||
| 2949 | - </step> | ||
| 2950 | - | ||
| 2951 | - <step> | ||
| 2952 | - <name>待处理更新数据</name> | ||
| 2953 | - <type>Dummy</type> | ||
| 2954 | - <description/> | ||
| 2955 | - <distribute>N</distribute> | ||
| 2956 | - <custom_distribution/> | ||
| 2957 | - <copies>1</copies> | ||
| 2958 | - <partitioning> | ||
| 2959 | - <method>none</method> | ||
| 2960 | - <schema_name/> | ||
| 2961 | - </partitioning> | ||
| 2962 | - <cluster_schema/> | ||
| 2963 | - <remotesteps> <input> </input> <output> </output> </remotesteps> <GUI> | ||
| 2964 | - <xloc>673</xloc> | ||
| 2965 | - <yloc>406</yloc> | ||
| 2966 | - <draw>Y</draw> | ||
| 2967 | - </GUI> | ||
| 2968 | - </step> | ||
| 2969 | - | ||
| 2970 | <step_error_handling> | 2964 | <step_error_handling> |
| 2971 | <error> | 2965 | <error> |
| 2972 | <source_step>JavaScript解析json生成数据</source_step> | 2966 | <source_step>JavaScript解析json生成数据</source_step> |
src/main/resources/static/pages/scheduleApp/module/basicInfo/vehicleDataSyncManage/form.html
| @@ -35,14 +35,25 @@ | @@ -35,14 +35,25 @@ | ||
| 35 | <div class="form-body"> | 35 | <div class="form-body"> |
| 36 | 36 | ||
| 37 | <div class="form-group"> | 37 | <div class="form-group"> |
| 38 | + <label class="col-md-2 control-label">同步类型:</label> | ||
| 39 | + <div class="col-md-3"> | ||
| 40 | + <sa-Radiogroup model="ctrl.vsTaskType" dicgroup="vsTaskType" ></sa-Radiogroup> | ||
| 41 | + </div> | ||
| 42 | + </div> | ||
| 43 | + | ||
| 44 | + <div class="form-group" ng-if="ctrl.vsTaskType === 'singleV'"> | ||
| 38 | <label class="col-md-2 control-label">车辆自编号:</label> | 45 | <label class="col-md-2 control-label">车辆自编号:</label> |
| 39 | <div class="col-md-4"> | 46 | <div class="col-md-4"> |
| 40 | - <input type="text" class="form-control" ng-model="ctrl.dataSyncTask.paramClzbh" | 47 | + <input type="text" class="form-control" required name="paramClzbh" ng-model="ctrl.dataSyncTask.paramClzbh" |
| 41 | placeholder="请输入车辆自编号"/> | 48 | placeholder="请输入车辆自编号"/> |
| 42 | </div> | 49 | </div> |
| 50 | + <!-- 隐藏块,显示验证信息 --> | ||
| 51 | + <div class="alert alert-danger well-sm" ng-show="myForm.paramClzbh.$error.required"> | ||
| 52 | + 车辆自编号必须填写 | ||
| 53 | + </div> | ||
| 43 | </div> | 54 | </div> |
| 44 | 55 | ||
| 45 | - <div class="form-group has-success has-feedback"> | 56 | + <div class="form-group has-success has-feedback" ng-if="ctrl.vsTaskType === 'periodT'"> |
| 46 | <label class="col-md-2 control-label">开始日期*:</label> | 57 | <label class="col-md-2 control-label">开始日期*:</label> |
| 47 | <div class="col-md-3"> | 58 | <div class="col-md-3"> |
| 48 | <div class="input-group"> | 59 | <div class="input-group"> |
| @@ -64,7 +75,7 @@ | @@ -64,7 +75,7 @@ | ||
| 64 | </div> | 75 | </div> |
| 65 | </div> | 76 | </div> |
| 66 | 77 | ||
| 67 | - <div class="form-group has-success has-feedback"> | 78 | + <div class="form-group has-success has-feedback" ng-if="ctrl.vsTaskType === 'periodT'"> |
| 68 | <label class="col-md-2 control-label">结束日期*:</label> | 79 | <label class="col-md-2 control-label">结束日期*:</label> |
| 69 | <div class="col-md-3"> | 80 | <div class="col-md-3"> |
| 70 | <div class="input-group"> | 81 | <div class="input-group"> |
src/main/resources/static/pages/scheduleApp/module/basicInfo/vehicleDataSyncManage/module.js
| @@ -188,6 +188,9 @@ angular.module('ScheduleApp').controller( | @@ -188,6 +188,9 @@ angular.module('ScheduleApp').controller( | ||
| 188 | var self = this; | 188 | var self = this; |
| 189 | var Task = service.getAddTaskClass(); | 189 | var Task = service.getAddTaskClass(); |
| 190 | 190 | ||
| 191 | + // 同步任务类型 | ||
| 192 | + self.vsTaskType = "singleV"; | ||
| 193 | + | ||
| 191 | // 日期 日期控件开关 | 194 | // 日期 日期控件开关 |
| 192 | self.paramFrom = false; | 195 | self.paramFrom = false; |
| 193 | self.paramFrom_open = function() { | 196 | self.paramFrom_open = function() { |
| @@ -204,6 +207,14 @@ angular.module('ScheduleApp').controller( | @@ -204,6 +207,14 @@ angular.module('ScheduleApp').controller( | ||
| 204 | 207 | ||
| 205 | // 提交方法 | 208 | // 提交方法 |
| 206 | self.submit = function() { | 209 | self.submit = function() { |
| 210 | + // 根据同步任务类型做数据处理(和后台etl判定逻辑对应) | ||
| 211 | + if (self.vsTaskType === "singleV") { | ||
| 212 | + self.dataSyncTask.paramFrom = null; | ||
| 213 | + self.dataSyncTask.paramTo = null; | ||
| 214 | + } else if (self.vsTaskType === "periodT") { | ||
| 215 | + self.dataSyncTask.paramClzbh = null; | ||
| 216 | + } | ||
| 217 | + | ||
| 207 | console.log(self.dataSyncTask); | 218 | console.log(self.dataSyncTask); |
| 208 | 219 | ||
| 209 | self.dataSyncTask.$save(function() { | 220 | self.dataSyncTask.$save(function() { |