简答题1. JDBC中的Statement、PreparedStatement和CallableStatement有何区别?
三者都是JDBC执行SQL语句的API,都是接口。
Statement继承Wrapper,提供了执行SQL语句和获取结果的基本方法;Statement每次执行SQL语句,数据库都要执行SQL语句的编译,如果用于仅执行一次查询并返回结果的情形,效率高于PreparedStatement。
PreparedStatement继承了Statement,增加了设置IN参数的方法;支持预编译、参数化查询,编译一次、执行多次,效率高,安全性好,有效防止SQL注入等问题,支持批量更新、批量删除。
CallableStatement继承了PreparedStatement。增加了设置和返回OUT参数的方法,支持调用存储过程,提供了对输入、输出参数的支持。
[考点] JDBC相关
2. Redis如何设置密码及验证密码?
Redis可通过命令设置密码,命令如config set requirepass 123456。这样就将密码设置为123456,这种方式不重启即可生效,但是在重启后失效。
如果需要密码一直有效,可以在redis.conf中配置requirepass参数。增加参数配置如requirepass 123456也是将密码设置为123456,这种方式需要重启后生效。
先连接Redis,后验证密码时用auth命令,如auth 123456。
验证通过后,可以查看,命令如config getrequirepass。
直接登录连接Redis则可如redis-cli -p 6379 -a 123456。
[考点] Redis
3. 在Spring Boot中如何使用其他嵌入式web服务器?
如果项目中Web服务器的Starter依赖项为spring-boot-starter-tomcat,只要将这个依赖项替换成其他Web服务器依赖项(如spring-boot-starter-jetty或spring-boot-start-undertow)便可。
[考点] Spring Boot
4. Maven与Ant的区别是什么?
Maven与Ant都用于项目构建,但是Maven的功能强大得多。Ant仅仅是软件构建工具,而Maven是软件项目管理和构建工具。在基于“约定优于配置”的原则下,提供标准的Java项目结构,同时能为应用自动管理依赖。
Ant操作简单,没有约定,没有项目生命周期,它是命令式的。所有操作都要手动去创建、配置,build.xml文件也需要手动创建。
Maven除了具备Ant的功能外,还增加了以下主要的功能。
使用Project Object Model(简POM),实际就是定义一个pom.xml来对软件进行项目管理,内置了更多的隐式规则,使得构建文件更加简单。
Maven有中央仓库,也可以构建私服仓库,并且内置依赖管理和Repository来实现依赖的管理和统一存储。
内置了软件构建的生命周期,如执行mvn install命令就可以自动执行编译、测试、打包等构建过程。
拥有约定,就知道原有的代码在哪里,新的代码放到哪里去。
[考点] Maven
5. 用于网络连接的是哪两个配置文件?
客户端连接服务器需要配置两个文件:sqlnet.ora、tnsnames.ora。文件目录:$oraclehome/network/admin/。tnsnames.ora用于解析用户连接服务使用的service name,sqlnet.ora用于设定连接方式。
[考点] Oracle数据库
6. Nginx的expires功能有何作用?
Nginx缓存的过期时间设置可以提高网站性能,对于网站的图片,尤其是新闻网站,图片一旦发布,改动的可能是非常小的,为了减小对服务器请求的压力,减少对带宽的占用,提高用户浏览速度,可以通过设置Nginx中的expires,让用户访问一次后,将图片缓存在用户的浏览器中,且时间比较长的缓存。这种缓存方式只能在用户不对浏览器强制刷新的情况下生效。
expires配置在location指令作用域块或location内的if里面。如下所示:
location~image {
root/root/images/;
expires 1d; #缓存过期时间为一天
}
[考点] Nginx
7. RabbitMQ的一个Queue中存放的Message有数量限制吗?
在数量上没有明确限制,实际上服务器内存的大小决定了最终的消息存放数量,当然也与消息大小有关。要明白的一点是消息过多会导致处理效率的下降。
[考点] 消息队列综合
8. 什么是文件上传攻击?如何防范文件上传攻击?
文件上传攻击就是网站对用户上传的文件类型判断不完善或者有其他漏洞,攻击者可以上传含有可执行程序的文件,文件可以是木马、病毒、恶意脚本或者WebShell等。这里程序在某种情况下上传文件目录被Web服务器执行或者在用户浏览网页时被触发执行,从而达到攻击的目的。当然达成攻击的前提条件是,这些上传文件上传后可以被访问,或者有在上传目录执行命令的权限。
如何让文件上传功能尽可能安全呢?这里建议几种方法。
●设置保存上传文件的目录为不可执行。这样可有效保证服务器的安全。
●判断文件类型:在判断文件类型时,可以结合使用MIME Type、后缀检查等方式。在文件类型检查中,强烈建议采用白名单的方式。此外,对于图片的处理可以使用压缩函数或者resize函数,在处理图片的同时破坏图片中可能包含的恶意代码。
●对文件上传内容进行安全检测,检查是否包含病毒、木马或其他恶意脚本。
●使用随机数改写文件名和文件路径。
[考点] 软件安全知识
9. Redis的Key的过期时间和永久有效设置命令是什么?如何查看过期时间?
设置过期时间使用expire命令,格式为expire Key1 100,表示Key1在100s后过期。
设置永久有效使用persist命令,格式为persist Key1,清除Key1的过期时间。
查看Key的有效期使用ttl命令,格式为ttl Key1,如果返回值大于0,表示Key1剩余的有效期秒数,如果返回值为-2,表示Key1在Redis中不存在,如果返回值为-1,表示Key1持久化,永久有效。
[考点] Redis
10. 如何把某个请求映射到特定的方法上面?
在方法上面添加@RequestMapping、@CetMapping、@PostMapping(当然还有@PutMapping、@DeleteMapping等,只不过它们极少被使用)注解中的一个,其中写明映射的路径即可,如@CetMapping("/getPwd")。
[考点] SpringMVC
11. Dubbo用ZooKeeper做注册中心,如果注册中心集群都崩溃,服务提供者和消费者相互还能通信吗?
当ZooKeeper注册中心崩溃时,服务提供者和消费者是可以通信的。原因如下。
启动Dubbo时,消费者会从ZooKeeper拉取注册的生产者的地址接口等数据,缓存在本地,每次调用时,按照本地存储的地址进行调用。注册中心集群任意一台宕机后,将会切换到另一台,注册中心全部宕机后,服务的提供者和消费者仍能通过本地缓存通信。服务提供者无状态,任一台宕机后,不影响使用,服务提供者全部宕机,服务消费者会无法使用,并无限次重连等待服务者恢复。注册中心崩溃,不影响已注册服务的使用,只是无法增加新的服务。
[考点] Dubbo框架
12. 注解@EnableDiscoveryClient与@EnableEurekaClient有何区别?
两者都用于开启客户端的服务发现功能。@EnableEurekaClient只能用于发现注册中心为Eureka的服务。而@EnableDiscoveryClient可以发现Nacos、Eureka、ZooKeeper、Consul等其他注册中心的服务。
[考点] Spring Cloud与微服务架构
13. Spring通知有哪些类型?
Spring通知(Advice)分成五类。
1)前置通知(Before Advice):在连接点前面执行,前置通知不会影响连接点的执行,除非此处抛出异常。
2)正常返回通知(After Returning Advice):只在连接点正常执行完成后才会执行。如果连接点抛出异常,此时后置通知不会执行。
3)异常返回通知(After Throwing Advice):在连接点抛出异常后执行。
4)返回通知(After Advice):在连接点执行完成后执行,不管是正常执行完成,还是抛出异常,都会执行返回通知中的内容。
5)环绕通知(Around Advice):环绕通知围绕在连接点前后,能在连接点前后自定义一些操作,通常也是一个方法调用的前后,这是最强大的通知类型。另外,环绕通知还会负责决定是继续处理Join Point(调用ProceedingJoinPoint的proceed方法)还是中断执行。
[考点] Spring基础
14. Maven如何做到打包时不带版本号?
Maven打包后,jar或war文件名中默认会带有版本号信息。如果想去掉版本号,则在pom.xml文件的<build/>标签中如下配置即可:
<build>
<! --产生构件的文件名,默认值是${artifactId}-${version} -->
<finalName>$(artifactId}</finalName>
</build>
[考点] Maven
15. Nginx其它的防盗链解决办法有哪些?
上面介绍了一般的防盗链办法,这里再介绍两种防盗链办法:
1)针对图片目录防止盗链,配置与防图片盗链相似:
location /images/ {
alias /data/images/;
valid_referers *.mycloud.com, *.mycloud01.com;
if ($invalid_referer) {return 403;}
}
2)使用第三方模块ngx_http_accesskey_module实现Nginx防盗链,这里忽略第三方模块的安装,安装好之后,只要修Nginx的conf文件,添加以下几行便可:
location /images/ {
accesskey on; #模块开关
accesskey_hashmethod md5; #加密方式
accesskey_arg "key"; #url中的关键字参数
accesskey_signature "mypass$remote_addr"; #加密值
}
[考点] Nginx
16. 同步操作和异步操作有什么区别?
同步是阻塞的,异步是非阻塞的。同步操作一旦发起必须等待它执行完毕才能执行其他请求。异步操作浏览器在发起请求后,就可以继续执行其他事情。异步操作执行完返回数据时通知浏览器,浏览器把返回的数据再渲染到页面,进行局部更新。
[考点] AJAX与JavaScript
17. Spring Cloud Config配置加密有哪两种方式?如何实现?
为了保证安全性,通常需要对敏感信息(如密码)进行加密。Spring Cloud Config提供了对称加密和非对称加密两种方式。
对称加密的实现步骤如下。
1)首先下载与JDK版本对应的JCE增强版,即无限制权限策略版本,解压覆盖到Java-home/jre/lib/security目录。
2)在bootstrap中配置对称密钥encrypt.Key=mycloud(mycloud就是密钥)。启动config server(假定端口8090),通过地址http://127.0.0.1: 8090/encrypt/status可以查看其状态,如果状态是ok说明是可用的。
3)通过命令curl http://localhsot: 8090/enrypt -d mysercet。将字符串'mysercet'用密钥加密生成加密串。每次生成的字符串都不一样。但解密结果都会一样。执行解密命令curl http://localhost: 8080/decrypt -d加密串,则会得到字符串'mysercet'。
4)加密串前有{cipher}标识的是对称加密串。
5)为方便测试,最好关闭安全管理:
management.security.enabled=false
非对称加密复杂一些,安全性相对也高一些。下面介绍RSA算法非对称加密的实现。当然首先也要安装JCE。然后用JDK中自带的Keytool工具生成密钥文件,操作步骤如下(CMD中执行):
Keytool -genKeypair -alias myrsaKey -Keyalg RSA -dname "CN =Web Servert, OU=Unit, O=Organization,L=City,S=State,C=US"-Keypass dongfang -Keystroe server.jks -storepass estpwd
在CMD的当前位置会获得一个文件server.jks。默认有效期90天,将这个文件复制到config服务端的resource目录下,然后在配置文件中做如下配置:
encrypt.KeyStore.location=classpath:/server.jks #jks文件的路径
encrypt.KeyStore.password=testpwd #storepass
encrypt.KeyStore.alias=myrsaKey #alias
encrypt.KeyStore.secret=dongfang #Keypass
参数要与生成密钥文件时的参数一致,否则肯定出错。后面的步骤与对称加密的步骤一样。
[考点] Spring Cloud与微服务架构
18. Memcached和服务器的Local Cache相比,有什么优缺点?
Memcached和服务器的Local Cache相比,各有优缺点。Local Cache能够利用的内存容量受到(单台)服务器空闲内存空间的限制。不过,Local Cache有一点比Memcached要好,那就是它可以存储任意的数据,而且没有网络存取的延迟。
Local Cache的数据查询更快。可以考虑把常用的数据放在Local Cache中。如果每个页面都需要加载一些数量较少的数据,可以考虑把它们放在Local Cache中。
Local Cache缺少集体失效(Croup Invalidation)的特性。在Memcached集群中,删除或更新一个Key会让所有的观察者觉察到。但是在Local Cache中,只能通知所有的服务器刷新Cache(很慢,不具扩展性),或者仅仅依赖缓存超时失效机制。
Local Cache另一个不足是受服务器的内存限制。
[考点] Memcached
19. RabbitMQ如何分发消息?
若该队列至少有一个消费者订阅,消息将以循环(round-robin)的方式发送给消费者。每条消息只会分发给一个订阅的消费者(前提是消费者能够正常处理消息并进行确认)。
RabbitMQ通过路由可实现多消费的功能。
[考点] 消息队列综合
20. Spring框架的事务隔离级别有哪些?
Spring有五种事务隔离级别。
●Isolation.DEFAULT:这是Spring的默认配置,是PlatfromTransactionManager默认的隔离级别,使用数据库默认的事务隔离级别。
●Isolation.READ_UNCOMMITTED:未提交读。最低事务隔离级别,可以读取其他事务未提交数据(会出现脏读,不可重复读),基本不使用。
●Isolation.READ_COMMITTED:提交读。只能读取其他事务已提交数据(会出现不可重复读和幻读)
●Isolation.REPEATABLE_READ:可重复读。可以防止脏读,不可重复读。但是可能出现幻像读。它的意思是多次读取同一个数据时,其值都和事务开始时的内容一致。它除了保证一个事务不能读取另一个事务未提交的数据。
●Isolation.SERIALIZABLE:串行化。最高事务级别,事务被处理为顺序执行。除了防止脏读,不可重复读外,还避免了幻像读。
在事务注解中做个性化的事务隔离级别配置示例如下:
@Transactional (isolation=Isolation.READ_UNCOMMITTED)
下面是一些与事务隔离级别相关的名词解释。
●脏读:一个事务读取到另一事务未提交的更新数据。
●不可重复读:在同一事务中,多次读取同一数据返回的结果有所不同,换句话说,后续读取可以读到另一事务已提交的更新数据。
●幻像读:也叫幻读,一个事务读到另一个事务已提交的insert数据。
不可重复读重点在于update和delete,而幻读的重点在于insert。
[考点] Spring基础