2016-11-21简单的总结一下学到的知识点。作为一个目标而存在的东西,总是那么美丽而优雅。
一、PE中事务的编写
getTransactionTemplate().execute(new TransactionCallback() { public Object doInTransaction(TransactionStatus arg0) { getSqlMap().update("mt.updateSystemLimit",context.getDataMap());// 更新个人限额表 getSqlMap().update("mt.updateSystemLimitEnt",context.getDataMap());// 更新企业限额表 if(!"".equals(MinGuaranteeLimit)&&MinGuaranteeLimit!=null&&!"".equals(EarlyWarningLimit)&&EarlyWarningLimit!=null){ getSqlMap().update("mt.updateSystemLimitEnt",map2);// 更新企业垫资限额和保底限额 } return null; } }
二、日志的控制级别
error>warn>info>debug。
在spring中,若要打印框架内部的日志。需要将jcl的日志框架改成slf能够识别的日志规范。在spring中使用logback,需要以下的jar包。
<dependency> <groupId>ch.qos.logback</groupId> <artifactId>logback-classic</artifactId> <version>${logback-version}</version> </dependency> <dependency> <groupId>org.logback-extensions</groupId> <artifactId>logback-ext-spring</artifactId> <version>${logback-spring-version}</version> </dependency> <!-- 添加这个,可以打印spring内部的日志 --> <dependency> <groupId>org.slf4j</groupId> <artifactId>jcl-over-slf4j</artifactId> <version>1.7.21</version> </dependency>
三、Vue中的v-bind:value和v-model
首先v-model只是一种语法糖,以下两种写法是等价的。
<input v-model="something"> <input v-bind:value="something" v-on:input="something = $event.target.value">
以下是一个例子,便于理解:value和v-model的区别。html部分的代码:
<div id="app"> <input :value="username" @input="updateUsername"><br> <input v-model="username"><br> <div>{{username}}</div> </div>
- js的代码如下:
var password = "huhx"; new Vue({ el: "#app", data: { username: password, }, methods: { updateUsername: function(e) { password = "name is huhx"; } } });
运行的效果如下:password的改变并不影响this.username,也就是输入框的内容。
如果在updateUsername方法中,加上this.username = e.target.value;那么第一个输入框的修改,会影响所有的内容显示。这也就是上述所说的v-model类似
- 如果加上以下的内容:
computed: { username: function() { return password + ", name"; } },
运行的效果如下:修改两个输入框的内容,不改变this.username,而且this.username内容始终为:huhx, name。这说明了在渲染数据的时候,先是data里面的username,然后调用computed里面的username的get方法。
四、关于pe加载文件的部分笔稿
XmlBeanDefinitionReader 这个不一样,这里开始了重写。 XmlBeanDefinitionReader ApplicationConfigParser这个是解析的类 EntityResolver entityResolver = (EntityResolver)constructor0.newInstance(new Object[] { "pe-config.dtd", "/com/csii/pe/config/"}) tag-definitions.xml定义了pe的核心。 loadTagDefinitions Class parserClass0 = Class.forName("com.csii.pe.config.ApplicationConfigParser"); setParserClass(parserClass0); Class class0 = Class.forName("com.csii.pe.config.DtdResolver"); Constructor constructor0 = class0.getConstructor(new Class[] { java.lang.String.class, java.lang.String.class }); EntityResolver entityResolver = (EntityResolver)constructor0.newInstance(new Object[] { "pe-config.dtd", "/com/csii/pe/config/" }); setEntityResolver(entityResolver); logger.info("using entity resolver:" + entityResolver); }
五、对于js中装包的理解
首先js的代码如下:
function funTest() { var outerParam = "huhx"; innner("123456"); function innner(str) { console.log("hello world " + outerParam + ", " + str); } return function() { innner("linux"); outerParam = "chenhui"; console.log(outerParam); } }
- funTest():
hello world huhx, 123456
- funTest()():
hello world huhx, 123456
hello world huhx, linux
chenhui
- var test = new funTest(); test();
hello world huhx, 123456
hello world huhx, linux
chenhui
六、伪元素的基本使用
<!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <title>Document</title> <style type="text/css"> span:before { content: "I love you, " } span:after { content: "I hate you."; color: red; } </style> </head> <body> <p><span id="test">周长风</span></p> <script type="text/javascript"> var ele = document.getElementById("test").innerText; // 周长风 alert(ele); </script> </body> </html>
页面显示效果:
七、toString和String强制转换的区别
Object obj = null; System.out.println(obj.toString()); // 抛出空指针异常:java.lang.NullPointerException System.out.println((String)obj); // null
八、 抢火车票程序思路
1、访问12306网站,查询余票。通过console可以得到请求的url以及请求数据。 2、在项目中通过okhttp发送请求,可以得到返回的数据。 3、转换成json对象,对数据进行解析处理。 4、得到你想要的信息,根据要求判断是否发送邮件通知。 5、开启一个定时任务,不断的轮询火车票的状态,重复上述的操作。
一、访问12306网站:在console里面得到url为:参数2017-01-17是出发日,SHH是出发地上海,WHN是目的地武汉,ADULT是单选框选中的普通。
https://kyfw.12306.cn/otn/leftTicket/queryA?leftTicketDTO.train_date=2017-01-17&leftTicketDTO.from_station=SHH&leftTicketDTO.to_station=WHN&purpose_codes=ADULT
对url进行组装:
final String path = url + "queryA?leftTicketDTO.train_date=" + time + "&leftTicketDTO.from_station=" + from + "&leftTicketDTO.to_station=" + to + "&purpose_codes=" + purpose;
返回的数据在12306上显示大概如下:
二、通过okhttp发送的get请求,得到返回的数据:
Runnable runnable = new Runnable() { @SuppressWarnings("deprecation") @Override public void run() { OkHttpClient.Builder builder = new OkHttpClient.Builder(); List<InputStream> inputStreams = new ArrayList<>(); inputStreams.add(new ByteArrayInputStream(CER_12306.getBytes())); SSLSocketFactory sslSocketFactory = getSocketFactory(inputStreams); builder.sslSocketFactory(sslSocketFactory); OkHttpClient client = builder.build(); Request request = new Request.Builder().url(path).build(); try { Response response = client.newCall(request).execute(); ResponseBody body = response.body(); String string = body.string(); // 请求返回的数据 // 对返回的数据进行分析处理 getInfoFromResponse(string); System.out.println("string " + string); body.close(); } catch (IOException e) { e.printStackTrace(); } } };
三、对返回的数据做解析处理。
private static void getInfoFromResponse(String string) { boolean isEmailSend = true; JSONObject jsonObject = JSONObject.parseObject(string); String httpStatus = jsonObject.getString("httpstatus"); StringBuilder builder = new StringBuilder(); if (StringUtils.isEmpty(httpStatus) || !httpStatus.equals("200")) { return; } @SuppressWarnings("unchecked") List<Map<String, Map<String, String>>> dataObject = (List<Map<String, Map<String, String>>>) jsonObject.get("data"); System.out.println(dataObject.size()); builder.append(getInfoMessage(dataObject, isEmailSend)); if (isEmailSend) { SendMailUtils.sendMail(emailTo, "<span>" + builder.toString() + "</span>"); } }
四、针对解析处理的结果,看是否要发送邮件通知。
public static void sendMail(String to, String message) { Properties props = new Properties(); props.put("mail.smtp.host", "smtp.qq.com"); props.put("mail.smtp.port", 465); // 这个需要 props.put("mail.smtp.auth", "true"); props.put("mail.from", EMAIL_SEND_FROM); props.put("mail.smtp.socketFactory.class", "javax.net.ssl.SSLSocketFactory"); Session session = Session.getInstance(props, auth); MimeMessage msg = new MimeMessage(session); Address address; try { address = new InternetAddress(EMAIL_SEND_FROM); msg.setFrom(address); msg.setRecipients(Message.RecipientType.TO, to); msg.setSubject("胡红翔"); msg.setSentDate(new Date()); String html = "<html><body>" + message + "</body></html>"; msg.setText(html, "utf-8", "html"); Transport.send(msg); } catch (Exception e) { e.printStackTrace(); } }
五、开启定时任务
// 定时任务 ScheduledExecutorService service = Executors.newSingleThreadScheduledExecutor(); service.scheduleAtFixedRate(runnable, 0, watiTime, TimeUnit.MINUTES);
六、接收的邮件通知如下:不够人性化,但是数据都有,后续处理好说。
七、过程中遇到的问题
1、使用okhttp发送https请求时,会涉及到证书的知识。这方面不是很了解
2、线程中关于是否发送邮箱的变量isEmailSend有些不好把握,关于线程方面有待提高。
八、过程中学到的知识:
1、okhttp发送https请求,了解了一些关于证书的知识
2、定时任务的另外一种写法。