第四周(实际是n+周)
1. tomcat启动报错
报错内容:ERROR RUNNING 'TOMCAT': UNABLE TO OPEN DEBUGGER PORT (127.0.0.1:38667): JAVA.NET.SOCKETEXCEPTION "SOCKET CLOSED
原因:tomcat 1089端口被占用
解决办法:
netstat -ano | find "1099"
// 查看是被哪个进程占用
tasklist|findstr "20856"
taskkill -f -pid 20856
2.@CrossOrigin(origins="*")
@CrossOrigin中的2个参数:
- origins: 允许可访问的域列表
- maxAge:准备响应前的缓存持续的最大时间(以秒为单位)
跨域,指的是浏览器不能执行其他网站的脚本。它是由浏览器的同源策略造成的,是浏览器施加的安全限制。
所谓同源是指,域名,协议,端口均相同,只要有一个不同,就是跨域。不明白没关系,举个栗子:
http://www.123.com/index.html 调用 http://www.123.com/server.php (非跨域)
http://www.123.com/index.html 调用 http://www.456.com/server.php (主域名不同:123/456,跨域)
http://abc.123.com/index.html 调用 http://def.123.com/server.php (子域名不同:abc/def,跨域)
http://www.123.com:8080/index.html 调用 http://www.123.com:8081/server.php (端口不同:8080/8081,跨域)
http://www.123.com/index.html 调用 https://www.123.com/server.php (协议不同:http/https,跨域)
请注意:localhost和127.0.0.1虽然都指向本机,但也属于跨域。
浏览器执行javascript脚本时,会检查这个脚本属于哪个页面,如果不是同源页面,就不会被执行。
跨域会阻止什么操作?
浏览器是从两个方面去做这个同源策略的,一是针对接口的请求,二是针对Dom的查询
1.阻止接口请求比较好理解,比如用ajax从http://192.168.100.150:8020/实验/jsonp.html页面向http://192.168.100.150:8081/zhxZone/webmana/dict/jsonp发起请求,由于两个url端口不同,所以属于跨域,在console打印台会报No 'Access-Control-Allow-Origin' header is present on the requested resource
值得说的是虽然浏览器禁止用户对请求返回数据的显示和操作,但浏览器确实是去请求了,如果服务器没有做限制的话会返回数据的,在调试模式的network中可以看到返回状态为200,且可看到返回数据
3.一篇通俗易懂的git介绍
git为啥不需要网络就能用git_Army-海军的博客-CSDN博客
SVN更新的原则是要随时更新,随时提交。当完成了一个小功能,能够通过编译并且自己测试之后,谨慎地提交。
如果在修改的期间别人也更改了svn的对应文件,那么commit就可能会失败。
4.vscode 下载慢问题
将下载链接中的az764295.vo.msecnd.net
更换为vscode.cdn.azure.cn
,实际上是切换为了国内镜像
5. mybatis中foreach遍历问题
<select id="selectOnlineRecordG100ByIds" resultMap="OnlineRecordG100Result" parameterType="string">
<include refid="selectOnlineRecordG100Vo"/>
where vin is not null
and id in
<foreach item="id" collection="array" open="(" separator="," close=")">
#{id}
</foreach>
</select>
当查询结果是有条件时,会获取符合条件对应得数据
<delete id="deleteOnlineRecordG100ByIds" parameterType="String">
delete from online_record_g100 where id in
<foreach item="id" collection="array" open="(" separator="," close=")">
#{id}
</foreach>
</delete>
当删除时,只有全都符合,才会删除,否则都不删除
5. sql语句 case when then end
SELECT id,made_status,made_date FROM g100_produce_queue
order by made_status desc ,
case when made_status = 'FM' then made_date end asc,
case when made_status = 'UM' then made_date end asc,
case when made_status = 'WM' then made_date end asc;
SELECT id,made_status,made_date FROM g100_produce_queue
order by case when made_status = 'WM' then 0
when made_status = 'UM' then 1
when made_status = 'FM' then 2 end asc,made_date asc;
SELECT id,made_status,made_date FROM g100_produce_queue ORDER BY made_status desc , made_date asc;
先根据
made_status
按照WM、UM、FM
的顺序显示,再按照made——date
显示,以上三条sql效果一样第一种鸡肋
第二种可应对
made_status
字母无法排序的状态第三种适用于需求是状态首字母恰好排序出来的数据
6. log日志中加号和占位符
// 加号是最终会拼接为一个字符串
void error(String var1);
// 占位符是一个字符串,一个throwable异常
void error(String var1, Throwable var2);
示例:
// 下面这个是调用的纯字符串那个方法,其中e.getMessage()可能会报空指针
log.error("XXXX异常:" + e.getMessage());
// 下面这个是调用的字符串和异常那个方法,如果e为null,只会显示字符串
log.error("XXXX异常:{}",e.getMessage());
7. 将java项目由GBK格式编码改为UTF-8格式编码
import org.apache.commons.io.FileUtils;
import java.io.File;
import java.io.IOException;
import java.util.Collection;
public class tt {
public static void main(String[] args) {
//GBK编码格式源码路径
String srcDirPath = "D:\\Program Files\\JetBrains\\OtherProjects\\design-pattern\\src";
//转为UTF-8编码格式源码路径
String utf8DirPath = "D:\\Program Files\\JetBrains\\OtherProjects\\design-pattern\\src2";
//获取所有java文件
Collection<File> javaGbkFileCol = FileUtils.listFiles(new File(srcDirPath), new String[]{"java"}, true);
for (File javaGbkFile : javaGbkFileCol) {
//UTF8格式文件路径
String utf8FilePath = utf8DirPath + javaGbkFile.getAbsolutePath().substring(srcDirPath.length());
//使用GBK读取数据,然后用UTF-8写入数据
try {
FileUtils.writeLines(new File(utf8FilePath), "UTF-8", FileUtils.readLines(javaGbkFile, "GBK"));
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
// 所需依赖 <dependency> <groupId>commons-io</groupId> <artifactId>commons-io</artifactId> <version>2.11.0</version> </dependency>
8. 云服务器上的数据库被勒索比特币
起因:nacos页面报mysql连接被拒绝(Access denied for user 'root'@'xx.xx.xx.xx' (using password: YES)
),使用navicat连接mysql也是这个错
第一步:以为mysql版本自动更新了,导致root用户权限不够,所以重新查看当前root权限并赋权
第二步:之后是可以连接了,用了navicat发现数据库里的数据表都没了,且每个数据库都有一个命名为readme
的数据库表,内容是告诉我数据被他删了,需要0.003比特币(网上换算了下约966rmb),支付他给恢复(这种人好脏)
第三步:思考,有三个途径破解,第一种是通过gitee上我的公开代码中找到的mysql配置信息,直接就登上去了;第二种是通过刷ip和密码,由于我的mysql端口是3306,密码简单,被刷出来了;第三种认识且知道我ip的人作案(概率不大)
第四步:吸取教训,重置mysql库,改端口,改密码,重新导入数据(因为有备份),将gitee仓库私有(开发完了统一清理下敏感信息再打开吧),恰好用到了腾讯的cos存储,遇到这个事件给了提醒,如果放到公有仓库,被盗刷的风险很大
以下是此次重新安装过程用到的资料:
查看当前mysql的root权限并赋权:https://blog.csdn.net/ichen820/article/details/117130736
docker安装mysql:https://blog.csdn.net/mameng1988/article/details/83782831
nacos_config数据库sql脚本:https://blog.csdn.net/AOSIDIN/article/details/115059725
9. 修改commit备注
git commit --amend
10. 使用了startPage(),但是分页不成功bug
只显示10条数据,总条数是10,但其实数据库中不止10条,查看若依文档
- 常见坑点2:添加了
startPage
方法。也没有正常分页。例如下面这段代码startPage(); Post post = postService.selectPostById(1L); List<User> list = userService.selectUserList(user); return getDataTable(list);
原因分析:只对该语句以后的第一个查询
(Select)
语句得到的数据进行分页。
上面这个代码,应该写成下面这个样子才能正常分页。Post post = postService.selectPostById(1L); startPage(); List<User> list = userService.selectUserList(user); return getDataTable(list);
以为是这个原因,经过多次尝试,原来是select方法中使用了stream流遍历后重新Collections.toList()方法,这个新生产的list不是interface page,所以在getDataTable(list)方法中校验失败,total也就成为了第一页list的长度(10条),所以才会只有10条
return userMapper.selectUserList(User).stream().peek(user -> {
user.setName("zhangsan");
}).collect(Collectors.toList());
改为以下的写法:
List<User> list = userMapper.selectUserList(User);
for (User user : list) {
user.setName("zhangsan");
}
return list;
更新:
又遇到这个问题,这次的需求查询大量的数据发送给第三方并更新发送状态,采用分页查询数据防止oom,但是当执行完第一页查询后,更改了前十页的某个字段状态,导致再进行第二页查询时总条数对不上,所以第二页始终查不到数据
总结:
- startPage() 后只会对第一个select生效
- startPage()后的list不能更改,不能从新new一个list,也不能使用stream流中的Collectors.toList()方法,
- startPage()后的list查完第一页后不能更改list的条数,改了要重新查询总条数,否则会有问题