开发者博客 – IT技术 尽在开发者博客

开发者博客 – 科技是第一生产力


  • 首页

  • 归档

  • 搜索

【弄nèng - Skywalking】应用篇(一) ——

发表于 2021-10-21

小知识,大挑战!本文正在参与“程序员必备小知识”创作活动

本文同时参与「掘力星计划」,赢取创作大礼包,挑战创作激励金

该篇博客是Skywalking的安装使用
官方文档:
github.com/apache/skyw…

参考www.jianshu.com/p/8b9aad421…

一. 简介

Skywalking概念相关的介绍请看官方文档官方文档

Skywalking用于分布式系统的应用程序性能监视工具,特别为微服务、云本机和基于容器(Docker, K8s, Mesos)架构设计。

二. Skywalking架构

在这里插入图片描述
从逻辑上讲,SkyWalking分为四个部分

  • 探针(Agent):收集数据并重新格式化以符合SkyWalking的要求(不同的探针支持不同的来源)。
  • 后端(Oap):支持数据聚合,分析并驱动从探针到UI的流程。该分析包括SkyWalking本机跟踪和度量,第三方,包括Istio和Envoy遥测,Zipkin跟踪格式等。您甚至可以通过使用针对本机度量的Observability Analysis Language和针对扩展度量的Meter System来定制聚合和分析。
  • 存储:通过开放/可插入的界面存储SkyWalking数据。您可以选择现有的实现,例如ElasticSearch,H2或由Sharding-Sphere管理的MySQL集群,也可以实现自己的实现。欢迎为新的存储实现者打补丁!
  • UI:是一个高度可定制的基于Web的界面,允许SkyWalking最终用户可视化和管理SkyWalking数据。

后端(Oap)又分为三个角色

  • 混合Mixed(默认):默认角色,OAP应承担以下责任,1.接收代理跟踪或指标,2.进行L1聚合,3.内部通讯(发送/接收),4.进行L2聚合,5.持久化,6.报警
  • 接收者Receiver:1.接收代理跟踪或指标,2.进行L1聚合,3.内部通讯(发送/接收)
  • 聚合器Aggregator:4.进行L2聚合,5.持久化,6.报警

可以利用Receiver和Aggregator进行高级部署,来区分节点责任,缓解压力、
注意:Receiver节点也可以进行持久化,继承Record类的实体在进行L1聚合时持久化

三. 安装OAP

3.1 前置

本教程使用的是最新版8.0.1,使用的数据源是es7,如果你要部署集群环境就适用zookeeper
所以需要安装es7和zk(可选,集群需要)
请自行安装,本教程重点是skywalking

3.2 下载

点击进入下载页
下载最新版8.0.1
在这里插入图片描述
解压后
在这里插入图片描述

3.3 修改配置application.yml

在这里插入图片描述

/config/application.yml部分配置

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
yml复制代码cluster:
selector: ${SW_CLUSTER:standalone}
# 单节点模式
standalone:
# zk用于管理collector集群协作.
# zookeeper:
# 多个zk连接地址用逗号分隔.
# hostPort: localhost:2181
# sessionTimeout: 100000
# 分布式 kv 存储设施,类似于zk,但没有zk重型(除了etcd,consul、Nacos等都是类似功能)
# etcd:
# serviceName: ${SW_SERVICE_NAME:"SkyWalking_OAP_Cluster"}
# 多个节点用逗号分隔, 如: 10.0.0.1:2379,10.0.0.2:2379,10.0.0.3:2379
# hostPort: ${SW_CLUSTER_ETCD_HOST_PORT:localhost:2379}
core:
selector: ${SW_CORE:default}
default:
# 混合角色:接收代理数据,1级聚合、2级聚合
# 接收者:接收代理数据,1级聚合点
# 聚合器:2级聚合点
role: ${SW_CORE_ROLE:Mixed} # Mixed/Receiver/Aggregator

# rest 服务地址和端口
restHost: ${SW_CORE_REST_HOST:localhost}
restPort: ${SW_CORE_REST_PORT:12800}
restContextPath: ${SW_CORE_REST_CONTEXT_PATH:/}

# gRPC 服务地址和端口
gRPCHost: ${SW_CORE_GRPC_HOST:localhost}
gRPCPort: ${SW_CORE_GRPC_PORT:11800}

downsampling:
- Hour
- Day
- Month

# 设置度量数据的超时。超时过期后,度量数据将自动删除.
# 单位分钟
recordDataTTL: ${SW_CORE_RECORD_DATA_TTL:90}

# 单位分钟
minuteMetricsDataTTL: ${SW_CORE_MINUTE_METRIC_DATA_TTL:90}

# 单位小时
hourMetricsDataTTL: ${SW_CORE_HOUR_METRIC_DATA_TTL:36}

# 单位天
dayMetricsDataTTL: ${SW_CORE_DAY_METRIC_DATA_TTL:45}

# 单位月
monthMetricsDataTTL: ${SW_CORE_MONTH_METRIC_DATA_TTL:18}

storage:
selector: ${SW_STORAGE:elasticsearch7}
elasticsearch7:
# elasticsearch 的集群名称
nameSpace: ${SW_NAMESPACE:"TEST-ES"}

# elasticsearch 集群节点的地址及端口
clusterNodes: ${SW_STORAGE_ES_CLUSTER_NODES:192.168.1.1:9200}

# elasticsearch 的用户名和密码
user: ${SW_ES_USER:""}
password: ${SW_ES_PASSWORD:""}

# 设置 elasticsearch 索引分片数量
indexShardsNumber: ${SW_STORAGE_ES_INDEX_SHARDS_NUMBER:2}

# 设置 elasticsearch 索引副本数
indexReplicasNumber: ${SW_STORAGE_ES_INDEX_REPLICAS_NUMBER:0}

# 批量处理配置
# 每2000个请求执行一次批量
bulkActions: ${SW_STORAGE_ES_BULK_ACTIONS:2000}

# 每 20mb 刷新一次内存块
bulkSize: ${SW_STORAGE_ES_BULK_SIZE:20}

# 无论请求的数量如何,每10秒刷新一次堆
flushInterval: ${SW_STORAGE_ES_FLUSH_INTERVAL:10}

# 并发请求的数量
concurrentRequests: ${SW_STORAGE_ES_CONCURRENT_REQUESTS:2}

# elasticsearch 查询的最大数量
metadataQueryMaxSize: ${SW_STORAGE_ES_QUERY_MAX_SIZE:5000}

# elasticsearch 查询段最大数量
segmentQueryMaxSize: ${SW_STORAGE_ES_QUERY_SEGMENT_SIZE:200}

profileTaskQueryMaxSize: ${SW_STORAGE_ES_QUERY_PROFILE_TASK_SIZE:200}
advanced: ${SW_STORAGE_ES_ADVANCED:""}

主要修改,SW_CLUSTER, SW_CORE_ROLE,SW_STORAGE,SW_NAMESPACE ,SW_STORAGE_ES_CLUSTER_NODES

  • SW_CLUSTER 默认standalone单机模式
  • SW_CORE_ROLE 默认Mixed混合模式
  • SW_STORAGE 存储,我使用的是es7,所以设置成elasticsearch7
  • SW_NAMESPACE es的namespace
  • SW_STORAGE_ES_CLUSTER_NODES es地址,多个地址以,分割

3.4 webapp配置

可以在这里修改前端工程端口,默认8080
webapp/webapp.yml

1
2
3
4
5
6
7
8
9
yml复制代码server:
port: 8080

collector:
path: /graphql
ribbon:
ReadTimeout: 10000
# Point to all backend's restHost:restPort, split by ,
listOfServers: 127.0.0.1:12800

3.5 启动

进入bin目录,执行启动文件,windows下startup.bat,linux为startup.sh。startup.bat包含后端启动文件oapService.bat和前端启动文件webappService.bat。

后端工程会启动两个端口11800和12800,大多数代理使用11800端口,只有少数不支持grpc的代理使用12800。
前端工程使用12800

启动成功后访问**http://localhost:8080**显示如下:
在这里插入图片描述

四. 使用Agent

Agent官方文档

agent目录
在这里插入图片描述

4.1 修改配置

有四种方式配置,优先级如下

探针配置 > JVM配置 > 系统环境变量配置 > agent.config文件

1.JVM配置覆盖

1
ini复制代码-Dskywalking.agent.service_name = demo-provider

2.探针配置覆盖

1
2
ini复制代码-javaagent:/var/local/agent/skywalking-agent.jar=agent.service_name=service-pfm
# 默认格式是 -javaagent:agent.jar=[option1]=[value1],[option2]=[value2]

我们使用JVM 配置,所以此处不修改。

/agent/config/agent.config主要配置

1
2
3
4
5
6
7
8
9
10
11
12
13
14
yml复制代码# 不同的namespace会导致调用链路追踪中断
agent.namespace=${SW_AGENT_NAMESPACE:default-namespace}

# 页面上展示的service的名称,也可以通过-Dskywalking.agent.service_name=xxx指定
agent.service_name=${SW_AGENT_NAME:service-pfm}

# 平台的调用地址,也可以通过-Dskywalking.collector.backend_service=127.0.0.1:11800指定
collector.backend_service=${SW_AGENT_COLLECTOR_BACKEND_SERVICES:127.0.0.1:11800}

# 忽略指定后缀的请求收集
agent.ignore_suffix=${SW_AGENT_IGNORE_SUFFIX:.jpg,.jpeg,.js,.css,.png,.bmp,.gif,.ico,.mp3,.mp4,.html,.svg}

# 每3秒的采样率,负数代表100%
agent.sample_n_per_3_secs=${SW_AGENT_SAMPLE:-1}

注意:如果Collector以集群方式部署,比如:Acollector和Bcollector,建议Acollector.sampleRate = Bcollector.sampleRate

4.2 启动工程接入Agent

在jvm启动参数上添加

1
javascript复制代码-javaagent:/var/local/apache-skywalking-apm-bin/agent/skywalking-agent.jar

完整的启动命令

1
ini复制代码java -javaagent:/var/local/apache-skywalking-apm-bin/agent/skywalking-agent.jar -Dskywalking.agent.service_name=service-pfm   -Dskywalking.collector.backend_service=127.0.0.1:11800  -jar simple-skywalking-test.jar

IDEA中启动
在这里插入图片描述
添加参数,直接正常启动就可以了

启动成功后访问API,页面会看到数据

排错需要观察agent的日志,路径为/agent/logs/skywalking-api.log
和skywalking的运行日志,路径为logs/skywalking-oap-server.log


本文转载自: 掘金

开发者博客 – 和开发相关的 这里全都有

更好的 java 重试框架 sisyphus 配置的 2 种

发表于 2021-10-21

回顾

我们前面学习了

更好的 java 重试框架 sisyphus 入门简介

更好的 java 重试框架 sisyphus 背后的故事

这一节让我们一起学习下 sisyphus 基于函数式的配置和注解式的配置。

函数式配置概览

为了满足更加方便的配置,Retryer 类提供了许多可以配置的信息。

默认配置

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
java复制代码/**
* 默认配置测试
*/
public void defaultConfigTest() {
Retryer.<String>newInstance()
.condition(RetryConditions.hasExceptionCause())
.retryWaitContext(RetryWaiter.<String>retryWait(NoRetryWait.class).context())
.maxAttempt(3)
.listen(RetryListens.noListen())
.recover(Recovers.noRecover())
.callable(new Callable<String>() {
@Override
public String call() throws Exception {
System.out.println("called...");
throw new RuntimeException();
}
}).retryCall();
}

和下面的代码是等价的:

1
2
3
4
5
6
7
8
9
10
java复制代码public void helloTest() {
Retryer.<String>newInstance()
.callable(new Callable<String>() {
@Override
public String call() throws Exception {
System.out.println("called...");
throw new RuntimeException();
}
}).retryCall();
}

方法说明

condition

重试触发的条件,可以指定多个条件。

默认为抛出异常。

retryWaitContext

重试等待的策略,可以指定多个。

默认为不做任何等待。

maxAttempt

指定最大重试次数,包括第一次执行。

默认值:3 次。

listen

指定重试的监听实现,默认为不做监听。

recover

当重试完成之后,依然满足重试条件,则可以指定恢复的策略。

默认不做恢复。

callable

待重试执行的方法。

retryCall

触发重试执行。

接口的详细介绍

接口及其实现

所有的接口,都可以直接查看对应的子类实例。

用户自定义

基于替换的灵活性,用户可以实现接口,定义更符合自己业务的实现。

sisyphus 注解

配置具有很高的灵活性,但是对于开发人员的使用,就没有注解那样简单灵活。

所以本框架也实现了基于注解的重试。

设计的规范

保证接口和注解二者的统一性。

maven 引入

1
2
3
4
5
xml复制代码<dependency>
<groupId>${project.groupId}</groupId>
<artifactId>sisyphus-annotation</artifactId>
<version>${project.version}</version>
</dependency>

注解

核心注解主要有两个。

Retry

用于指定重试的相关配置。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
java复制代码/**
* 重试注解
* 1. 实际需要,只允许放在方法上。
* 2. 如果放在接口上,是否所有的子类都生效?为了简单明确,不提供这种实现。
* 3. 保持注解和接口的一致性。{@link com.github.houbb.sisyphus.api.core.Retry} 接口
* @author binbin.hou
* @since 0.0.3
*/
@Documented
@Inherited
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
@RetryAble(DefaultRetryAbleHandler.class)
public @interface Retry {

/**
* 重试类实现
* @return 重试
* @since 0.0.5
*/
Class<? extends com.github.houbb.sisyphus.api.core.Retry> retry() default DefaultRetry.class;

/**
* 最大尝试次数
* 1. 包含方法第一次正常执行的次数
* @return 次数
*/
int maxAttempt() default 3;

/**
* 重试触发的场景
* @return 重试触发的场景
*/
Class<? extends RetryCondition> condition() default ExceptionCauseRetryCondition.class;

/**
* 监听器
* 1. 默认不进行监听
* @return 监听器
*/
Class<? extends RetryListen> listen() default NoRetryListen.class;

/**
* 恢复操作
* 1. 默认不进行任何恢复操作
* @return 恢复操作对应的类
*/
Class<? extends Recover> recover() default NoRecover.class;

/**
* 等待策略
* 1. 支持指定多个,如果不指定,则不进行任何等待,
* @return 等待策略
*/
RetryWait[] waits() default {};

}

RetryWait

用于指定重试的等待策略。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
java复制代码package com.github.houbb.sisyphus.annotation.annotation;

import com.github.houbb.sisyphus.annotation.annotation.metadata.RetryWaitAble;
import com.github.houbb.sisyphus.annotation.handler.impl.DefaultRetryWaitAbleHandler;
import com.github.houbb.sisyphus.core.constant.RetryWaitConst;
import com.github.houbb.sisyphus.core.support.wait.NoRetryWait;

import java.lang.annotation.*;

/**
* 重试等待策略
* 1. 为了对应重试策略,所有的内置注解应该实现当前的注解。
* 2. 是否允许自定义注解?
*
* 当注解+对象同时出现的时候,视为组合。
*
* @author binbin.hou
* @since 0.0.3
*/
@Retention(RetentionPolicy.RUNTIME)
@Inherited
@Documented
@Target(ElementType.ANNOTATION_TYPE)
@RetryWaitAble(DefaultRetryWaitAbleHandler.class)
public @interface RetryWait {

/**
* 默认值
* 1. fixed 模式,则对应固定等待时间
* 2. 递增
* @return 默认值
*/
long value() default RetryWaitConst.VALUE_MILLS;

/**
* 最小值
* @return 最小值
*/
long min() default RetryWaitConst.MIN_MILLS;

/**
* 最大值
* @return 最大值
*/
long max() default RetryWaitConst.MAX_MILLS;

/**
* 影响因数
* 1. 递增重试,默认为 {@link RetryWaitConst#INCREASE_MILLS_FACTOR}
* 2. 指数模式。默认为 {@link RetryWaitConst#MULTIPLY_FACTOR}
* @return 影响因数
*/
double factor() default Double.MIN_VALUE;

/**
* 指定重试的等待时间 class 信息
* @return 重试等待时间 class
*/
Class<? extends com.github.houbb.sisyphus.api.support.wait.RetryWait> retryWait() default NoRetryWait.class;

}

注解的使用

定义好了注解,肯定要有注解的相关使用。

关于注解的使用,主要有两种方式。

Proxy+CGLIB

基于代理模式和字节码增强。

如果是项目中没有使用 spring,直接使用这种方式比较方便。

Spring-AOP

可以和 spring 直接整合。

使用方式和 spring-retry 是一样的。

这些内容将放在下一节进行详细讲解。

小结

灵活的配置才能更加符合实际生产使用中的各种需求。

一般实际使用推荐使用注解的配置方式,非常的简单方便。

java 重试框架 sisyphus 开源地址

希望本文对你有所帮助,如果喜欢,欢迎点赞收藏转发一波。

我是老马,期待与你的下次重逢。

NO_SIGN.png

本文转载自: 掘金

开发者博客 – 和开发相关的 这里全都有

霸主Java跌落神坛背后,云原生都做了什么?

发表于 2021-10-21

10 月的 TIOBE 编程语言排行榜发布了最新一期榜单,雄踞榜首多年的 Java 终于让出了榜首位置,Python 成功登顶。一时间,对于 Python 的吹捧与对 Java 的看衰持续引发热议。“世界上只有两种编程语言,一种广为诟病,另一种没人用”。C++之父的这句名言用来形容 Java 同样合适,作为企业级的编程语言,Java 不仅在中国互联网大厂中有着广泛的应用,在世界范围内更是有着庞大的生态和就业机会。

编程语言之争是技术圈经久不衰的话题,国内开发者培训业务多了起来以后,关于编程语言的话题炒作更是此起彼伏。但雄踞榜首多年,Java 的下滑也并非空穴来风,而是有其深刻的历史背景所在。这个背景,或许就是云原生时代的来临。

以容器为代表的云原生技术或者说理念,有着弹性可扩展、松耦合、容错性好、易于管理、解放运维、可频繁变更的优势,这极大地降低了开发部署的门槛,让云计算大大地往前、向下走了一步。这本该是一次编写,到处运行的 Java 优势所在。但 Java 的其他特性,比如语法稍显啰嗦、面向大规模、长时间服务端应用设计,在云原生时代的微服务化趋势下,又有所偏差。

因此,在云计算和运维等方面,Java 已经不再是企业的首选语言,这个位置开始被 Go 语言所取代。但 Java 作为一门诞生 25 年之久的老牌编程语言,一方面具备规模庞大的开发者社区,Java 虚拟机技术也跑在世界上的云端虚拟化环境的各个角落,另一方面也在持续地优化自身以适应新的时代需求。

10 月 27、28 日,稀土掘金技术社区主办的 「稀土开发者大会」 专门设置了 「Java 实战」 和 「云原生技术应用」 专题,为 Java 语言从业者在云原生时代锚定自己的位置,也为 Java 未来的发展提出一些猜想和建议。

大会 免费预约报名
通道即将关闭,还未报名的同学请火速抢占最后的位置!

Java 实战

演讲一:Jakarta EE 技术演进适应云原生发展

  • 演讲嘉宾:张建锋——永源中间件 总经理

Jakarta EE 是 Java EE 重新命名后,整个 Java 社区参与并推动发展的开发框架,也是 Java 中间件规范。本话题详细介绍当前 Jakarta EE 技术演进情况,未来发展路线,更好的适应云原生,以及 Jakarta EE 在国内的应用实践。

演讲二:面向内存漫谈 Java 垃圾收集器演进

  • 演讲嘉宾:童寅(公与)——PerfMa 云端创新事业部 XLab 首席架构师

基于 Java 垃圾收集器的演进以及当下对 ZGC 的热烈讨论,系统的介绍 Java 垃圾收集器的演进历史,并且面向内存结构详细介绍几个关键垃圾收集器的实现原理,并系统的讨论不同垃圾收集器的调优手段与依据,最后阐述无暂停垃圾收集器的实现原理、利弊。

演讲三:Visual Studio Code - 开发云原生 Java 应用的新机会

  • 演讲嘉宾:李榕——微软 开发工具首席研发经理

云原生时代,Java 应用被大量部署到云端,我们的开发体验能否也在云端完成呢,答案是肯定的。Visual Studio Code(VSCode)是近年崛起的开发工具,它在架构方面的特色决定了它能很好的运行于云端,解锁了新的可能性。本次分享将介绍 VS Code 给 Java 开发者带来的体验,以及它云原生特性背后的奥秘。

云原生技术应用

演讲一:高德 Serverless 平台建设及实践

  • 演讲嘉宾:邓学祥——阿里巴巴 高级技术专家

高德是阿里集团内 Serverless 应用落地规模最大的 BG,Serverless 应用峰值超十万 qps 量级。高德为什么要建设 Serverless,遇到了哪些技术难题,技术方案是怎样的,在哪些业务场景中落地了 Serverless,收益如何,本次分享将会解答这些问题。

演讲二:基于容器云构建企业 AI 开发基础设施

  • 演讲嘉宾:贺龙华——百度 基础架构部资深研发工程师

随着 AI 技术的快速发展,不管是互联网公司还是传统公司都已普遍应用 AI 技术; 但随着 AI 业务的规模化应用,企业对于 AI 的基础设施提出了更高的要求。本次分享将讲述百度以及百度的客户是如何基于 kubernetes 来构建高效的 AI 容器底座。

演讲三:从 0 到 1 打造新一代开源函数计算平台

  • 演讲嘉宾:霍秉杰——青云科技 KubeSphere 资深架构师

Serverless 是继 IaaS,PaaS 之后云计算发展的下一波浪潮,而函数计算是 Serverless 领域的代表技术。近年来云原生技术的迅速发展为打造新一代函数计算平台打下了良好的基础。本次演讲将介绍函数计算概念、参考架构及发展趋势,介绍云原生 Serverless 领域的最新进展,进而阐述如何利用云原生技术从 0 到 1 打造新一代开源函数计算平台 OpenFunction。

演讲四:K8S 在生产环境下的安全困境和解决方案

  • 演讲嘉宾:张晋涛——支流科技 技术专家

Kubernetes 作为云原生的基石,已经应用的越来越广泛了。但是随着引入 Kubernetes ,也带来了很多安全问题。那么生产环境下的 Kubernetes 所面临的安全困境应该如何解决呢?本次分享将分析 K8S 面临的 8 类主要的安全问题,并给出生产实践的解决方案。


隔绝炒作的喧闹,回归技术的本源。

10 月 27、28 日,稀土开发者大会,坐等各位大驾光临。

本文转载自: 掘金

开发者博客 – 和开发相关的 这里全都有

String系列:Java的String类一(String)

发表于 2021-10-21

小知识,大挑战!本文正在参与「程序员必备小知识」创作活动

本文已参与 「掘力星计划」 ,赢取创作大礼包,挑战创作激励金。

📖前言

1
复制代码心态好了,就没那么累了。心情好了,所见皆是明媚风景。

“一时解决不了的问题,那就利用这个契机,看清自己的局限性,对自己进行一场拨乱反正。”正如老话所说,一念放下,万般自在。如果你正被烦心事扰乱心神,不妨学会断舍离。断掉胡思乱想,社区垃圾情绪,离开负面能量。心态好了,就没那么累了。心情好了,所见皆是明媚风景。

1
2
3
4
5
6
7
8
9
10
11
text复制代码十年生死两茫茫,写程序,到天亮。

千行代码,Bug何处藏。

纵使上线又怎样,朝令改,夕断肠。

领导每天新想法,天天改,日日忙。

相顾无言,惟有泪千行。

每晚灯火阑珊处,夜难寐,再写两行!

🎇创建字符串


在Java语言中将字符串作为对象来管理,因此可以像创建其他类对象一样来创建字符串对象。创建对象要使用类的构造方法。String类的常用构造方法如下:

1
2
3
java复制代码String str1 = "abc";
char a[] = {'n','i','c','e'};
String str2 = new String(a,1,3);

注意:

String 类是不可改变的,所以你一旦创建了 String 对象,那它的值就无法改变了(详看笔记部分解析)。

如果需要对字符串做很多修改,那么应该选择使用 StringBuffer & StringBuilder 类。历史文章:Java基础之String:为什么需要用stringbuffer或者StringBuilder去拼接字符串——而不用string——以及stringbuffer的基本了解


连接字符串

“+”运算符是最简单、最快捷,也是使用最多的字符串连接方式。在使用“+”运算符连接字符串和 int 型(或 double 型)数据时,“+”将 int(或 double)型数据自动转换成 String 类型。

下面的实例使用“+”运算符连接了 3 个数组和 1 个字符串。

1
2
3
4
5
6
7
8
9
10
11
12
java复制代码public static void main(String[] args)
{
int[] no=new int[]{501,101,204,102,334}; //定义学号数组
String[] names=new String[]{"陈永佳","王梦霞","郭士才","刘森川","王安岭"}; //定义姓名数组
String[] classes=newString[]{"数学","语文","数学","英语","英语"}; //定义课程数组
System.out.println("本次考试学生信息如下:");
//循环遍历数组,连接字符串
for(int i=0;i<no.length;i++)
{
System.out.println("学号:"+no[i]+"|姓名:"+names[i]+"|课程:"+dasses[i]+"|班级:"+"初二(三)班");
}
}

上述代码首先创建了 3 个包含有 5 个元素的数组,然后循环遍历数组,遍历的次数为 5。在循环体内输出学号、姓名和课程,并使用“+”运算符连接班级最终形成一个字符串。程序运行后输出结果如下:

1
2
3
4
5
6
java复制代码本次考试学生信息如下:
学号:501|姓名:陈永佳|课程:数学|班级:初二(三)班
学号:101|姓名:王梦霞|课程:语文丨班级:初二(三)班
学号:204|姓名:郭士才|课程:数学|班级:初二(三)班
学号:102|姓名:刘森川|课程:英语|班级:初二(三)班
学号:334|姓名:王安岭|课程:英语|班级;初二(三)班

当定义的字符串值的长度过长时,可以分作多行来写,这样比较容易阅读。例如:

1
java复制代码String str="Welcome to"+"Luoyang"+"欢迎来到"+"洛阳。"+"洛阳我的故乡。";

使用 concat() 方法

在 Java 中,String 类的 concat() 方法实现了将一个字符串连接到另一个字符串的后面。concat() 方法语法格式如下:

1
ajva复制代码字符串 1.concat(字符串 2);

执行结果是字符串 2 被连接到字符串 1 后面,形成新的字符串。

如 concat() 方法的语法所示,concat() 方法一次只能连接两个字符串,如果需要连接多个字符串,需要调用多次 concat() 方法。

下面创建一个实例代码来演示如何使用 concat() 方法连接多个字符串。

1
2
3
4
5
6
7
8
9
10
java复制代码public static void main(String[] args)
{
String info="三国演义、";
info=info.concat("西游记、");
info=info.concat("水漭传、");
info=info.concat("红楼梦");
System.out.println(info);
String cn="中国";
System.out.println(cn.concat("洛阳").concat("洛龙区").concat("龙门石窟"));
}

执行该段代码,输出的结果如下所示。

1
2
java复制代码三国演义、西游记、水浒传、红楼梦
中国洛阳洛龙区龙门石窟

连接其他类型数据

前面介绍的例子都是字符串与字符串进行连接,其实字符串也可同其他基本数据类型进行连接。如果将字符串同这些数据类型数据进行连接,此时会将这些数据直接转换成字符串。

编写一个 Java 程序,实现将字符串与整型、浮点型变量相连并输出结果。实现代码如下:

1
2
3
4
5
6
7
java复制代码public static void main(String[] args)
{
String book="三国演义"; //字符串
int price=59; //整型变量
float readtime=2.5f; //浮点型变量
System.out.println("我买了一本图书,名字是:"+book+"\n价格是:"+price+"\n我每天阅读"+readtime+"小时");
}

上述代码实现的是将字符串变量 book 与整型变量 price 和浮点型变量 readtime 相连后将结果输出。在这里定义的 price 和 readtime 都不是字符串,当它们与字符串相连时会自动调用自身的 toString() 方法将其转换成字符串形式,然后再参与连接运算。因此,程序运行后的结果如下所示:

1
2
3
java复制代码我买了一本图书,名字是:三国演义
价格是:59
我每天阅读2.5小时

假设将本例中的输出语句修改为如下形式:

1
java复制代码System.out.println("我买了一本图书,名字是:"+book+"\n 价格是:"+price+"\n我每天阅读"+(price+readtime)+"小时");

因为运算符具有优先级,而圆括号的优先级最高,所以先计算 price 与 readtime 的和,再将结果转换成字符串进行连接。此时的运行结果如下所示:

1
2
3
java复制代码我买了一本图书,名字是:三国演义
价格是:59
我每天阅读61.5小时

注意:只要“+”运算符的一个操作数是字符串,编译器就会将另一个操作数转换成字符串形式,所以应该谨慎地将其他数据类型与字符串相连,以免出现意想不到的结果。


PS:最后感谢大家耐心观看完毕,留个点赞收藏是您对我最大的鼓励!


🎉总结:

  • 更多参考精彩博文请看这里:《陈永佳的博客》
  • 喜欢博主的小伙伴可以加个关注、点个赞哦,持续更新嘿嘿!

本文转载自: 掘金

开发者博客 – 和开发相关的 这里全都有

Spring源码解析(7)之循环依赖解决 一、前言 二、什么

发表于 2021-10-21

一、前言

在之前的博客中已经介绍到了Spring的bean的实例化过程,但是介绍到doCreateBean并没有详细去介绍,这里会接着去介绍doCreateBean具体做了什么事情,大家如果没有阅读过之前的博客,可以先去了解一下bean的加载过程,在我之前的博客都有具体的介绍。[Spring源码解析(5)之bean实例化过程(上)\_jokeMqc的博客-CSDN博客](https://blog.csdn.net/jokeMqc/article/details/120805886?spm=1001.2014.3001.5501)


下面是Spring解决循环依赖的草图,大家要理解这张图才能够对Spring是如何解决循环依赖以及有哪些循环依赖是Spring无法解决的。

二、什么是循环依赖

循环依赖就是循环引用,就是两个或多个bean相互之间的持有对方,比如A引用B,B引用A。

2.1Spring如何解决循环依赖

Spring容器循环依赖包括构造器循环依赖和setter循环依赖。Spring依赖主要分为一下几种情况。

2.1.1 构造器循环依赖

表示通过构造器注入构成的循环依赖,次依赖是无法解决的,只能抛出异常。为什么呢?在前面的源码解析中已经看到了,Spring容器将每一个正在创建的单例的放在一个"正在创建的bean"的缓存池里面,如果该bean正在创建过程中,这个缓存一直存在。
1
2
3
4
5
6
7
java复制代码  <bean id="instanceA"  class="com.tuling.circulardependencies.InstanceA" >
<constructor-arg name="instanceB" ref="instanceB"></constructor-arg>
</bean>

<bean id="instanceB" class="com.tuling.circulardependencies.InstanceB" >
<constructor-arg name="instanceA" ref="instanceA"></constructor-arg>
</bean>
针对以上的代码的分析如下:
  1. Spring容器创建”InstanceA”bean,首先去”当前创建的bean的缓存池”查找当前的bean是否正在创建,如果没有发现,则创建该bean,然后把当前的bean放到”当前创建的bean的缓存池”中然后准备其需要的构造参数”InstanceB”。
  2. Spring创建”InstanceB”,首先去”当前创建的bean的缓存池”查找当前的bean是否正在创建,如果没有发现,则创建该bean,然后把当前的bean放到”当前创建的bean的缓存池”中然后准备其需要的构造参数”InstanceA”。
  3. 此时Spring容器需要去创建”InstanceA”,就会发现该bean正在创建,因为表示循环依赖,就会抛出异常。

2.1.2 sertter循环依赖

表示通过setter注入方式构成的循环依赖,对于setter注入造成的循环依赖是通过Spring容器提前暴露刚完成但未初始化的bean来完成的,而且只能够解决单例作用域的bean,因为prototype并不会提前放入到缓存中。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
java复制代码		// Eagerly cache singletons to be able to resolve circular references
// even when triggered by lifecycle interfaces like BeanFactoryAware.
boolean earlySingletonExposure = (mbd.isSingleton() && this.allowCircularReferences &&
isSingletonCurrentlyInCreation(beanName));
if (earlySingletonExposure) {
if (logger.isDebugEnabled()) {
logger.debug("Eagerly caching bean '" + beanName +
"' to allow for resolving potential circular references");
}
addSingletonFactory(beanName, new ObjectFactory<Object>() {
@Override
public Object getObject() throws BeansException {
return getEarlyBeanReference(beanName, mbd, bean);
}
});
}
具体步骤如下:
  1. Spring容器创建单例”InstanceA”bean,首先根据午餐构造器创建bean,会判断当前bean, “是否单例&是否允许循环依赖&是否正在创建bean”,如果满足会提前将该早期对象(ObjectFactory)提前暴露到三级缓存中,然后进行属性赋值,setter注入”InstanceB”。
  2. Spring容器创建单例”InstanceB”,首先根据无参构造器创建bean,然后会将该bean提前暴露到三级缓存中,然后setter注入”IntanceA”.
  3. 进行注入”InstanceA”由于提前暴露了ObjectFactory工厂,从而使用它返回提前暴露一个创建中的bean。

2.1.3 prototype范围的依赖处理

对于"prototype"作用域bean,Spring容器无法完成依赖注入,因为Spring容器不进行缓存"prototype"作用域的bean,因此无法提前暴露一个创建中的bean。

本文转载自: 掘金

开发者博客 – 和开发相关的 这里全都有

Spring注解开发 1 Spring原始注解 2 xm

发表于 2021-10-21

简介: Spring注解开发

  1. Spring原始注解

  • Spring是轻代码而重配置的框架,配置比较繁重,影响开发效率,所以注解开发是一种趋势,注解代替xml配置文件可以简化配置,提高开发效率。
  • Spring原始注解主要是替代的配置

  • 注意:

使用注解进行开发时,需要在applicationContext.xml中配置组件扫描,作用是指定哪个包及其子包下的Bean需要进行扫描以便识别使用注解配置的类、字段和方法。

1
2
xml复制代码<!--注解的组件扫描-->
<context:component-scan base-package="com.xdr630"></context:component-scan>
  1. xml 方式配置实现

userDao

1
2
3
csharp复制代码public interface UserDao {
public void save();
}

userDaoImpl

1
2
3
4
5
6
typescript复制代码public class UserDaoImpl implements UserDao {
@Override
public void save() {
System.out.println("save running...");
}
}

userService

1
2
3
csharp复制代码public interface UserService {
public void save();
}

userServiceImpl

1
2
3
4
5
6
7
8
9
10
11
12
13
typescript复制代码public class UserServiceImpl implements UserService {

private UserDao userDao;

public void setUserDao(UserDao userDao) {
this.userDao = userDao;
}

@Override
public void save() {
userDao.save();
}
}

applicationContext.xml

1
2
3
4
5
ini复制代码<bean id="userDao" class="com.xdr630.dao.impl.UserDaoImpl"></bean>

<bean id="userService" class="com.xdr630.service.impl.UserServiceImpl">
<property name="userDao" ref="userDao"/>
</bean>

UserController

1
2
3
4
5
6
7
arduino复制代码public class UserController {
public static void main(String[] args) {
ApplicationContext app = new ClassPathXmlApplicationContext("applicationContext.xml");
UserService userService = app.getBean(UserService.class);
userService.save();
}
}

  1. 注解配置方式实现

  • 在 UserDaoImpl 下的注解,@Component(“userDao”) 来替代 下面 bean 的配置

@Component(“userDao”)

  • userServiceImpl 下

  • 在 applicationContext.xml 下配置组件要扫描的包

<context:component-scan base-package=”com.xdr630”>

  • 测试:

  • xml配置和注解配置达到相同的效果
  • 使用 @Component 注解不能马上意识到是哪一层,所以Spring衍生了三个注解:@Repository、@Service、@Controller ,效果和@Component效果是一样的,可读性好点。

  • 注意:使用注解方式时,可以省略 set 方法。如:把 userServiceImpl 中的 set 方法删掉,也能成功运行:

  • 因为把注解放在属性上,直接通过反射为属性赋值,下面的方法也可以使用被赋值的属性了

  • 但如果使用 xml 配置的时候 set 方法是不能省略的
  • 把上面的 @Qualifier(“userDao”) 注释掉,也能成功运行,直接写@Autowired也能注入。因为@Autowired 是按照数据类型从Spring容器中进行匹配的,当Spring扫描到这个注解之后,它会直接从Spring容器当中找一个 userDao 类型的 bean,找到之后直接注入。如果容器中 UserDao 类型有多个bean,就不能这样写了 。
  • 按照类型注入,@Autowired
  • 按照名称注入,@Autowired 和 @Qualifier 要一起使用

  • @Resources 相当于@Autowired 和 @Qualifier

  • @Value 注入普通数据类型,如:把 hello 注入给 driver

  • 使用@Value进行字符串的注入

  • 使用@Scope标注Bean的范围

  • 使用@PostConstruct标注初始化方法,使用@PreDestroy标注销毁方法

  • 这里没打印销毁的方法原因是:因为容器还没有关闭程序就执行完了,所以造成销毁的方法还没打印出来
  • 手动关闭就可以看到销毁的方法打印了

  1. Spring新注解

使用上面的注解还不能全部替代xml配置文件,还需要使用注解替代的配置如下:

  • 非自定义的Bean的配置:
  • 加载properties文件的配置:context:property-placeholder
  • 组件扫描的配置:context:component-scan
  • 引入其他文件:

  • 下面是实现下使用注解完全替代 xml 文件配置

  • 新建一个核心配置类:SpringConfiguration,相当于总配置

//标志改类是Spring核心配置类
@Configuration
//<context:component-scan base-package=”com.xdr630”>
@ComponentScan(“com.xdr630”)
//
@Import({DataSourceConfiguration.class})
public class SpringConfiguration {

}

  • @Import({DataSourceConfiguration.class}) 里面的值其实是一个数组,可以加载多个类,如:

@Import({DataSourceConfiguration.class,xxx.class})

  • 新建数据源配置类:DataSourceConfiguration,相当于分配置

//<context:property-placeholder location=”classpath:jdbc.properties”/>
@PropertySource(“classpath:jdbc.properties”)
public class DataSourceConfiguration {

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
kotlin复制代码@Value("${jdbc.driver}")
private String driver;

@Value("${jdbc.url}")
private String url;

@Value("${jdbc.username}")
private String username;

@Value("${jdbc.password}")
private String password;

@Bean("dataSource") //Spring会将当前方法的返回值以指定名称存到Spring容器当中
public DataSource getDataSource() throws PropertyVetoException {
ComboPooledDataSource dataSource = new ComboPooledDataSource();
dataSource.setDriverClass(driver);
dataSource.setJdbcUrl(url);
dataSource.setUser(username);
dataSource.setPassword(password);
return dataSource;
}

}

  • 测试加载核心配置类创建Spring容器

public class UserController {
public static void main(String[] args) {
//ApplicationContext app = new ClassPathXmlApplicationContext(“applicationContext.xml”);
ApplicationContext app = new AnnotationConfigApplicationContext(SpringConfiguration.class);
UserService userService = app.getBean(UserService.class);
userService.save();
}
}

原文链接

本文为阿里云原创内容,未经允许不得转载。

本文转载自: 掘金

开发者博客 – 和开发相关的 这里全都有

一次服务器被黑的全过程排查和思考

发表于 2021-10-21

​本文已参与「掘力星计划」,赢取创作大礼包,挑战创作激励金。

前一阵子腾讯云搞活动,哈C我买了个轻量级的服务器,部署了自己的网站。

一切都井然有条的进行中。

直到某天清晨,我一如既往的打开我的网站,发现网站竟然打不开了。

于是我进行了一系列的排查。

1、排查日志

第一时间想到的就是登录服务器,查看异常登录的日志。

好家伙,我发现服务器竟然无法登录了!

1)VNC登录服务器

第一时间想到的应该是密码登录被禁用了。

于是我在腾讯云后台使用VNC登录。

无法通过客户端SSH远程登录时,可以通过VNC登录来登录服务器.

2)查看sshd_config文件

查看了/etc/ssh/sshd_config 文件后,发现果然是被修改了:

PasswordAuthentication no #表示不允许密码登录

禁用了密码登录,那应该就是用被使用私钥登录了。

先改成yes,然后重启sshd

1
复制代码systemctl restart sshd

3)使用终端重新登录

修改完之后,再本地使用终端工具重新登录,因为VNC登录工具实在太难用了。

发现可以登录了。

查看 authorized_keys 文件

1
bash复制代码 vi /root/.ssh/authorized_keys

好家伙,不讲码德!

给我的服务器加了秘钥对:

4)查看登录日志

  • 使用 last 和 history 命令 查看一下登录日志和操作日志

last #查看所有登录的ip

history #查看操作的命令记录

发现并没有异常的IP,这倒是不奇怪,假如真的被登录了,登录日志被删除的可能性也是很大的。

  • 再用 lastb 命令查看一下:

lastb #用于列出登入系统失败的用户相关信息

图一

图二

lastb结果解释:

1
2
3
4
5
6
复制代码第一列:用户名
第二列:终端位置
第三列:登录ip或者内核
第四列:开始时间
第五列:结束时间(still login in 还未退出 down 直到正常关机 crash 直到强制关机)
第六列:持续时间

)

以上结果表示,服务器被暴力撞库了。

IP应该是通过代理的,第二张图对方直接使用root作为用户名不断的去撞库,看来是找对了用户名,最后真的是登录了然后修改了我的秘钥对。

查一下IP:

IP是国外的,很难查到位置,也有可能是代理IP。

2、找到木马文件

1)使用top命令看一下

普通的top命令根本无法显示木马进程,看起来像是很正常的样子,因为top命令很可能已经被入侵者修改:

普通top命令

2)busybox 命令

运行 busybox top可以看到隐藏的占用CPU的进程,原始的top已经被修改,不能显示病毒的进程,必须在busybox中执行

下载腾讯云给的排查工具busybox,

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
ini复制代码[root@VM-8-8-centos ~]# wget https://tao-1257166515.cos.ap-chengdu.myqcloud.com/busybox
--2020-12-14 15:12:59-- https://tao-1257166515.cos.ap-chengdu.myqcloud.com/busybox
Resolving tao-1257166515.cos.ap-chengdu.myqcloud.com (tao-1257166515.cos.ap-chengdu.myqcloud.com)... 132.232.176.6, 132.232.176.7, 139.155.60.205, ...
Connecting to tao-1257166515.cos.ap-chengdu.myqcloud.com (tao-1257166515.cos.ap-chengdu.myqcloud.com)|132.232.176.6|:443... connected.
HTTP request sent, awaiting response... 200 OK
Length: 1001112 (978K) [application/octet-stream]
Saving to: ‘busybox.1’

100%[======================================>] 1,001,112 1.36MB/s in 0.7s
[root@VM-8-8-centos ~]# cp busybox /usr/bin/
[root@VM-8-8-centos ~]# busybox top
-bash: /usr/bin/busybox: Permission denied
[root@VM-8-8-centos ~]# cd /usr/bin/
[root@VM-8-8-centos bin]# chmod 777 /usr/bin/busybox
[root@VM-8-8-centos ~]# busybox top

抓到了木马文件:

busybox top命令

以上看到CPU占用率达到了近100%,挖矿无疑了。

最后和腾讯云的技术一起排查了大半天,终于揪出了以下几个木马文件,目录:

1
2
3
4
5
bash复制代码/tmp/.X25-unix/.rsync/c/tsm64
/tmp/.X25-unix/.rsync/c/tsm32
/tmp/.X25-unix/.rsync/a/kswapd0
/usr/bin/systemd-network
/usr/bin/kswaped

最后锁定这个挖矿进程名称是pamdicks,接下来把木马进程杀掉,然后把木马文件删除,应该就可以了。

如果不输入全称,ls、ll、lsattr 文件查看命令是根本不会显示这个木马文件的:

无法显示木马文件,需要全名才行

删除前看看这个挖矿的进程究竟是啥:

1
bash复制代码ls -lh /proc/5445/fd

1
css复制代码 top -H -p 5445

这个pamdicks进程有6个子线程:

最后追踪到是个二进制文件,触及到知识范围了,无法打开,就直接删除吧。

3、删除木马文件

1)修改authorized_keys

先把authorized_keys 文件的公钥删除。当我执行 rm 命令的时候,入侵者把我的 authorized_keys 文件加了 +i 锁,不允许删除,so sad:

chattr +i /etc/authorized_keys

表示文件不能删除,不能更改,不能移动

真的是不讲码德,把我服务器的chattr命令也删除了,服务器被黑,删chattr命令是常见的操作。

果真找不到chattr命令了:

只能手动把chattr 装回来,centos安装过程:

1
复制代码yum install e2fsprogs

安装成功:

1
2
arduino复制代码[root@VM-8-8-centos run]# which chattr
/usr/bin/chattr

清空authorized_keys 文件:

1
2
3
csharp复制代码[root@VM-8-8-centos .ssh]# chattr -i authorized_keys
[root@VM-8-8-centos .ssh]# echo > authorized_keys
[root@VM-8-8-centos .ssh]# cat authorized_keys

2)执行 rm 命令,删除木马文件

kill掉并删除发现的木马文件:

1
2
3
4
5
6
bash复制代码[root@VM-8-8-centos .ssh]# kill -9 5445
[root@VM-8-8-centos .ssh]# chattr -i /usr/bin/pamdicks
[root@VM-8-8-centos .ssh]# rm /usr/bin/pamdicks
rm: remove regular file ‘/usr/bin/pamdicks’? y
[root@VM-8-8-centos .ssh]# rm /tmp/.X25-unix/.rsync/c/lib/64/tsm
rm: remove regular file ‘/tmp/.X25-unix/.rsync/c/lib/64/tsm’? y

删除之后CPU使用率就降下来了:

木马文件清理完毕,最后把服务器禁用密码登录,改用生成好的秘钥对登录。

暂时告一段落。

4、找到攻击的源头——Redis

过了几天,打开Redis的时候,发现Redis出现了奇怪的键值。

之前没有留意到这个问题。

Redis被黑

大意了!Redis开放了端口而且没有设置密码。

虽然看不懂这串东西是如何注入到我的服务器的。但是这个 crackit的键很奇怪。

网上找到了以下资料:

Redis Crackit漏洞:

黑客远程访问redis服务,清空redis数据库后写入他自己的ssh登录公钥,然后将redis数据库备份为/root/.ssh/authotrized_keys。

这就成功地将自己的公钥写入到ssh的authotrized_keys,无需密码直接root登录被黑的主机。

那就是说,极有可能我的服务器并不是被暴力撞库登录的,而是把Redis作为切入点被攻击了。

使用top命令看一下,我去!木马文件又起来了,看来这个Redis的键值不清理,木马文件还是会继续下载、执行:

kswapd0 伪装的木马

这个kswapd0 有点熟悉。

kswapd0 占用过高是因为 物理内存不足,使用swap分区与内存换页操作交换数据,导致CPU占用过高。

但是,这个kswapd0 是个障眼法,背后的 命令却是 执行木马文件/tmp/.x25-unix/.rsynckswapd0

所以说这个Redis没有解决,入侵者下次还是会继续利用你Redis的漏洞继续入侵你的服务器。

真正意义上的 kswapd0 进程却是这样的:

这才是正常kswapd0

为了重现这个过程,我把Redis的值的命令执行了一遍:

1
2
scss复制代码[root@VM-8-8-centos ~]# ping d.powerofwish.com
PING d.powerofwish.com (193.160.32.164) 56(84) bytes of data.

下载的是一个 pm.sh 脚本,打开这个脚本:

可以看到这个sh脚本,本质是下载一个png文件,而且赋予了可执行权限。

我直接也把这个png文件下载下来,赋予权限,然后执行, ./png

看到有一个伪装的bin脚本,先删除后写入到 /usr/bin 目录。

然后不断不断的刷~ 期间chattr命令被删除、authorized_keys文件被修改

最后应该是执行 /usr/bin/kswaped 这个脚本,开始挖矿。

再用top查看一下CPU,瞬间飙到接近100%

抓包看看:

1
scss复制代码tcpdump -i eth0 '((not port 45695) and (not host 127.0.0.1) and  (not host 183.60.83.19))'

发现这个104.27.129.57 的是美国的CDN节点,顺藤摸瓜,把抓到的包导出到WirteShark看看:

红色部分就是源IP了,还有就是对方的有请求数据库的操作(3306端口)。

也有可能我的服务器只是一个DDoS攻击节点 。所以为了维护网络安全,还是要及时处理木马文件。

分布式拒绝服务攻击(英文意思是Distributed Denial of Service,简称DDoS)是指处于不同位置的多个攻击者同时向一个或数个目标发动攻击,或者一个攻击者控制了位于不同位置的多台机器并利用这些机器对受害者同时实施攻击。由于攻击的发出点是分布在不同地方的,这类攻击称为分布式拒绝服务攻击,其中的攻击者可以有多个。

DDos攻击示意图

5、预防

服务器被攻击,主要的原因还是暴露的公网端口太多,特别是Redis6789,MySQL3306这种,还有就是服务器密码过于简单。

预防措施:

1)服务器

通过修改/etc/ssh/sshd_config文件

  • 关闭密码登录,只允许秘钥对登录
  • 改换ssh默认端口,防止暴力撞库被破解
  • 禁用root账户直接登录,开放特定的IP访问

如:

1
2
3
4
5
6
7
8
9
10
11
12
13
bash复制代码#只允许用户、IP访问
AllowUsers aliyun test@192.168.1.1,root@192.168.*

# 拒绝 zhangsan、aliyun 帐户通过 SSH 登录系统
DenyUsers zhangsan aliyun

#使用秘钥登录
AuthorizedKeysFile .ssh/authorized_keys
PubkeyAuthentication yes
RSAAuthentication yes

#禁用密码登录
PasswordAuthentication no

2)应用

  • Redis只允许本地访问,修改默认端口,不暴露给所有IP, Redis 默认 bind 127.0.0.1 是有原因的
  • MySQL只对需要的IP开放访问权限
  • 设置端口的防火墙访问规则

如果想要更安全,可以使用跳板机、堡垒机访问。

3)备份

定期备份数据,定期备份快照。

​

本文转载自: 掘金

开发者博客 – 和开发相关的 这里全都有

如何避免面向监狱编程? 💔 一、前言 💔 二、专栏推荐 💔

发表于 2021-10-21

本文已参与「掘力星计划」,赢取创作大礼包,挑战创作激励金。


  • 💬 如果文章对你有帮助、欢迎关注、点赞、收藏(一键三连)和订阅专栏哦。

💔 一、前言

  • 大家好,我是小诚,又到了愉快的学习时间,前两周写了面向接口编程和面向切面编程,小伙伴还没过瘾,竟然让我写面向监狱编程,也好,趁着这个文章就跟大家谈谈面向监狱编程!当做是饭后谈资吧!
  • 如果文章对你有帮助,可以帮忙一键三连和专栏订阅哦! 如面试中遇到一些奇怪或者比较新颖的题目,欢迎私信投稿,感谢阅读(私信我即可投稿)!

在这里插入图片描述

💔 二、专栏推荐

  JAVA和MySQL技术专栏还在免费分享哦,大家可以帮忙点点订阅哦!

  《JAVA知识大全》

  《玩转算法》

💔 三、面向监狱编程

💔 3.1、代码泄漏

  案例1:某疆员工代码泄密事件

  2017年9月初,某疆的漏洞举报邮箱收到来自海外的邮件-声称它们发现了某疆公司在网络安全上一个严重的漏洞,举报人和他的搭档整理了长达31页的漏洞报告,并指出该漏洞能让攻击者获取到SSL证书的私钥,从而获取到某疆服务器上敏感的信息(信息包括:用户信息、政府ID、驾照护照等),后面举报者因为某疆需要签署保密协议否则就起诉他们而放弃举报奖金,选择将整个事件进行曝光,在社会上引起了很大的轰动!

  经过某疆内部调查发现,代码泄漏事件与公司的某位前员工有关,该名员工参与了某农业无人机管理和喷洒系统的开发,在这过程中,曾将代码推送到Github平台的“公有仓库”中,从而导致后面事情的发生。

  经专业机构鉴定,被泄漏的代码具有非公知性,已经被某疆运用到农业无人机产品中,属于商业机密,代码泄漏对某疆造成了至少116.4万人民币的损失,虽然事发后该员工第一时间删除的相关代码,并且跟举报者写了邮件表明非故意泄漏代码,希望尽量减少事情的影响,且愿意积极配合调查,防止事态进一步扩大。

  后案件经过南山区检察院提起公诉,鉴于员工有自首行为,且愿意积极配合调查,最后一审做出判决,以侵犯商业秘密罪判处有期徒刑六个月,并处罚金20万元人民币。

image.png

  案件2:某站后台代码被员工泄漏

  同是2019年,某站员工在Github上创建了名为“go-common”的代码库,并将某站的网站后台代码推送上去,随后被人发现,事情迅速发酵,短短几个小时获得了6K+Star和Fork,代码中包含许多配置文件、密钥、密码等敏感信息。

  该站收到消息后第一时间做出响应,且对该代码库进行了【封杀】,但是还是避免不了造成的损失,该事件导致了该站股票直接下跌百分之4,虽然网上暂时找不到关于泄漏代码员工的一个处置结果,但是想来处罚力度也不会小。

  小结

  相似案例比比皆是,如:某为公司某干名工程师、设计员工在离职后还继续使用某为的终端知识产权来赚钱,最后被批捕等等,我们会发现,这种事情似乎就在我们周围,很多中小型公司的一个管理并不会很规范,有些人可能会认为我将代码传递到仓库,方便自己学习或者怎么样,殊不知,其实你已经一个脚踏入了违法犯罪的边界。

  如果我们细心点都会发现,在与公司签订合同时就有明文规定,公司公共财产,敏感数据禁止泄漏,就算你不传递到代码仓库,你复制自己的电脑上这个行为本身也是违法的,况且你又怎么能保证在你电脑上的就不会被泄漏出去呢(冠希哥深有体会。。。),所以,平时大家在对公司的财产进行操作的时候,一定要三思而后行,否则,一步错,就可能锒铛入狱了。

💔 3.2、删库跑路

  虽然,很多程序员在平常调侃或者吐槽时会说,大不了就”删库跑路“,但是真正实行起来,这可万万不行,吹牛逼归吹牛逼,别真把自己吹进去了!

  案例1:某盟员工删库事件

  当时这件事可足足上了两天热搜!2020年的某一天,某盟研发部的一位核心运维员工通过个人VPN登录到公司内网的跳板机进入生产环境,对线上生产环境进行恶意破坏,导致数百万用户线上业务受到直接影响,虽然,某盟在某云的协助下,花费了七天七夜最终将数据找回,但是,这次事故造成的影响非常严重, 不包含拿出1.5亿元赔偿客户,且某盟股价下帖超22%,累计市值蒸发超过30亿港元。

  关于该核心员工破坏生产环境的原因众说纷纭,但是这个行为确实违反了法律规定,最终上海市宝安区人民法院对该案一审宣判,该核心运维人员被判处6年有期徒刑,看到这里,多少有点唏嘘,可谓是两败俱伤,不止公司和个人受到了影响,更多的是使用这个平台的第三方也无奈躺着中枪。

image.png

在这里插入图片描述

  小结

  在现实中,想这种的案例并不少见,如18年,某科公司前员工在项目账户中部署了一段恶意代码,导致该公司的456个虚拟机被删除,该行为导致公司直接损失高达240万美元(约合人民币1652万),该员工可能面向5年有期徒刑和25万美元的罚款。

  所以,作为一名技术人员,删除跑路之类的话最好只是平时生活中和朋友的调侃,千万不要因为一时冲动,做出错误的决定,让自己陷入违法犯罪的地步,当然,有些一些删库是因为技术人员操作不当的原因,遇到这种情况,要以最快的速度跟技术主管报备,将损失降到最低。

💔 3.3、黄赌毒

  案例1、某大学毕业生搭建黄色网站获刑

  主角小郭,大学学学了一些网络技术,某次在一个黄色论坛里遇到了一个需要进行网页搬家的网页,在帮忙”搬家”的过程中,他发现这个是个黄色网站,于是留了个后门,他发现这个黄网每天可以通过收款链接拿到几百块钱收入,于是他心生一计,将收款链接改为自己的,被网站管理发现后管理员将服务器关闭了。

  通过这件事情,他发现搞黄色网站很容易赚钱,于是他在之前的黄色论坛下载一个搭建黄色网站的源码,根据上面的指示进行傻瓜式安装,这个黄色网站包含四个网页,且网页上没有任何会员充值功能,内容都是公开免费的(很有人道主义....)。

  在警察的审问中,他交代搭建黄色网站的目的一是为了测试自己的网络架构技术,二是为了赚钱,于是他疯狂的将链接分享到各个QQ群,不断的吸收”志同道合“的道友,他知道,只要浏览量上来,广告商就会自己来联系,到时候就可以赚到钱。

  但是,直到被抓他也没有收到一个广告商联系,后面x开发区人民法院一审判决,被告人小郭以牟利为目的,利用互联网传播淫秽图片629张,其行为已构成传播淫秽物品牟利罪,判处有期徒刑一年,处罚人民币八千元。

  案例2:深圳某公司4名员工开发赌博软件获刑

image.png

  据深圳某媒体报道,x公司在经营正规软件开发的同时,还未赌博网站进行软件开发,用以方便赌客参赌,唐某等4人作为公司的开发人员,明知道是开发赌博网站,却提供技术支持,且收费数额较大,属于开设赌场罪共犯,应该受到刑罚处罚。

  小结

  黄赌毒,指卖淫嫖娼,贩卖或者传播黄色信息、赌博、买卖或吸食毒品的违法犯罪现象。在中国,黄赌毒是法律严令禁止的活动,是政府主要打击的对象。黄赌毒的刑罚从拘留至死刑不等。千万不要碰赌毒,不然日子会越来越有判头

💔 3.4、爬虫

  案例:2019年某天,小明(化名)正在工位上摸鱼,突然收到领导的一个需要,要求写一个爬虫程序批量从网络上的某个接口爬取数据,小明开发并测试没问题后边传递到了服务器,过了几天,不知道是因为需求变动还是小明想要优化程序,他将爬虫程序的线程数修改到一个比较大的值,然后传递到服务器上,速度还不错,小明挺满意。

  此时,在另外一个公司的开发者真急得头上冒火,不知什么原因,公司的服务器压力倍增,直接导致公司系统崩溃无法访问,经过技术人员的调查,发现公司的客户信息被抓取,接口的访问量剧增,经过进一步的排查,他们发现所有的线索都指向了一家大数据公司,而这家公司的主要业务就是出售简历数数据库,他们还在该家公司出售的数据中,发现了自己家公司客户的简历信息,上报领导后,公司决定报案。

  某天,小明还在工位上与产品经理争论需要细节,突然,一帮警察冲进来,将他们都带走了,后面,小明才知道是因为爬虫程序导致另一家公司服务器系统崩溃的问题,小明觉的自己是按照领导指示办事,应该跟自己关系不大,随着审讯进行,公司很多无关的人员如HR等被释放出来了,但是公司的核心人员(36人)被捕,大部分是公司系统的开发人员,据说小明一直不认为自己有罪,最后因为一直拒绝认罪而错过了取保候审的机会,目前事情还在继续审查过程。。。

image.png
  小结

  一位技术大牛曾说过:“技术本身并不可耻”,当你用着快播下着A片和免费的电影的时候,你会说:快播真棒,面对快播侵犯版权的时候,你又说:你说, 技术不道德,快播要负责。 技术本身无罪,但利用技术去做违法的事情,那就要承担相应的后果!爬虫是一个利器,如果运用到正途可以事半功倍,反之,也能让你坠落悬崖!

💔 3.5、外包

  外包的事件水太深,大家如果迫于无奈一定要去外包的时候,一定要擦亮眼啊! 原文描述得更清楚,我就不再这里班门弄斧了,传送门:程序员因接外包坐牢456天,看完在里面的经历你还敢么?

image.png

💔 3.6、外挂

  平常大家打游戏的时候,都羡慕别人牛逼,想想如果自己有个外挂就好了!有些东西想想就好,千万别去做,不然后果你可能承受不起!

  案例:19年,扬州市公安局广陵分局受到某游戏运营商报案,称网上有一款名为“冰焰”的外挂软件在兜售,给公司带来了巨大的经济损失,经过公安局调研,发现该软件开发团队有4人,分工明确,而软件的主要开发者为某科大博士,据调查,自16该软件被放到网上兜售到19年,三年多来,被销售60余万次,金额达到300余完,然而该博士生在团队的收入仅为每月400元的“咨询费”,但是截至案发时他已经非法获利12余万元。

  最终,该博士毕业生深某因犯侵入,非法控制计算机信息系统程序罪,被判处有期徒刑一年缓刑一年,并处罚金两万元。

image.png

💔 四、一些建议

  IT行业随着行业的发展,近些年来也逐渐鱼龙混杂,大家在入职时,一定要擦亮眼睛,了解清楚公司主营业务是否有涉及到违法范畴,现在网络这么发达,想要了解一家公司的业务并非难事,下面分享一下一些比较常见的涉及违法的业务!

  • 经营博彩,se情等违法网站的公司。
  • 以盈利为目的,非法盗用有著作权保护的作品
  • 所有爬虫数据里涉及个人信息和隐私的,都属于违法行为。【根据《网络安全法》第44条:任何个人和组织不得窃取或者以其他非法方式获取个人信息。因此,如果爬虫在未经用户同意的情况下大量抓取用户的个人信息,则有可能构成非法收集个人信息的违法行为。
  • 未按照相关规定,非法使用不被允许的爬虫接口。【爬取公开的数据,通常不会被认为是侵权。Google、百度等搜索引擎都是这么爬取的。只有两种行为造成了违法:不遵守Robots协议和绕过防护措施对数据的访问,强行突破反爬措施。】
  • 涉及集资,传销等业务的P2P公司
  • 制作、销售网络游戏外挂程序
  • 网络诈骗犯罪。【如:通过电脑等设备,使用虚拟定位让被害人搜索,伪装可以提供小姐上门服务的微信号,实施了诈骗行为】
  • 分布式拒绝服务(DDOS)攻击行为构成的犯罪。【有技术也不要乱秀,不然后果自负】
  • 以手机、电脑为载体,复制、贩卖淫秽电子信息行为。【就像来日方长歌曲中写到的:你要是不提 我不去回忆。有些东西自己”欣赏”就好】
  • ..

  相关的业务使用十篇文章也介绍不完,所以,最好的方式,了解相关法律法规,我特意给大家找了两个用于学习法律法规的网站,你想要的上面都有哦,大家不用再爬法律条文这么多,怎么才能找到自己想找的,不容错过哦!

  • 法律法规数据库
  • 北大法宝

💔 五、参考资料

  • 程序员们要小心:九类常见网络犯罪
  • 200名程序员被抓,程序员该如何善用爬虫获取数据

💔 六、写在最后

  看完文章,有木有发现小诚是个宝藏博主呀!上能写技术,下能吹牛逼!如有帮助,记得关注、一键三连、订阅专栏哦!如果想和博主谈技术、吹牛逼,可以到博主主页查看添加方式哦!

  JAVA和MySQL技术专栏还在免费分享哦,大家可以帮忙点点订阅哦!

  《JAVA知识大全》

  《算法修行》

本文转载自: 掘金

开发者博客 – 和开发相关的 这里全都有

HTTPS、SSL、TLS三者之间的联系和区别

发表于 2021-10-21

本文已参与「掘力星计划」,赢取创作大礼包,挑战创作激励金。

SSL(Secure Socket Layer 安全套接层)是基于HTTPS下的一个协议加密层,最初是由网景公司(Netscape)研发,后被IETF(The Internet Engineering Task Force - 互联网工程任务组)标准化后写入(RFCRequest For Comments 请求注释),RFC里包含了很多互联网技术的规范!

起初是因为HTTP在传输数据时使用的是明文(虽然说POST提交的数据时放在报体里看不到的,但是还是可以通过抓包工具窃取到)是不安全的,为了解决这一隐患网景公司推出了SSL安全套接字协议层,SSL是基于HTTP之下TCP之上的一个协议层,是基于HTTP标准并对TCP传输数据时进行加密,所以HPPTS是HTTP+SSL/TCP的简称。

由于HTTPS的推出受到了很多人的欢迎,在SSL更新到3.0时,IETF对SSL3.0进行了标准化,并添加了少数机制(但是几乎和SSL3.0无差异),标准化后的IETF更名为TLS1.0(Transport Layer Security 安全传输层协议),可以说TLS就是SSL的新版本3.1,并同时发布“RFC2246-TLS加密协议详解”,如果想更深层次的了解TLS的工作原理可以去RFC的官方网站:www.rfc-editor.org,搜索RFC2246即可找到RFC文档! ——以上就是历史背景

SSL 是指安全套接字层,简而言之,它是一项标准技术,可确保互联网连接安全,保护两个系统之间发送的任何敏感数据,防止网络犯罪分子读取和修改任何传输信息,包括个人资料。两个系统可能是指服务器和客户端(例如,浏览器和购物网站),或两个服务器之间(例如,含个人身份信息或工资单信息的应用程序)。

要说清楚 HTTPS 协议的实现原理,至少需要如下几个背景知识。

  1. 大致了解几个基本术语(HTTPS、SSL、TLS)的含义

  2. 大致了解 HTTP 和 TCP 的关系(尤其是“短连接”VS“长连接”)

  3. 大致了解加密算法的概念(尤其是“对称加密与非对称加密”的区别)

  4. 大致了解 CA 证书的用途 5.TCP通信协议的几次握手

TLS(传输层安全)是更为安全的升级版 SSL。由于 SSL 这一术语更为常用,因此我们仍然将我们的安全证书称作 SSL。但当您从赛门铁克购买 SSL 时,您真正购买的是最新的 TLS 证书,有 ECC、RSA 或 DSA 三种加密方式可以选择。

TLS/SSL是一种加密通道的规范

它利用对称加密、公私钥不对称加密及其密钥交换算法,CA系统进行加密且可信任的信息传输

在HTTP SSL中常用的对称加密算法有RC4,AES,3DES,Camellia等

SSL由从前的网景公司开发

有1,2,3三个版本,但现在只使用版本3

TLS是SSL的标准化后的产物

有1.0 1.1 1.2三个版本

默认使用1.0

TLS1.0和SSL3.0几乎没有区别

事实上我们现在用的都是TLS,但因为历史上习惯了SSL这个称呼

平常还是以SSL为多。

SSL(Secure Sockets Layer 安全套接层),及其继任者传输层安全(Transport Layer Security,TLS)是为网络通信提供安全及数据完整性的一种安全协议。TLS与SSL在传输层对网络连接进行加密。

SSL协议位于TCP/IP协议与各种应用层协议之间,为数据通讯提供安全支持。SSL协议可分为两层: SSL记录协议(SSL Record Protocol):它建立在可靠的传输协议(如TCP)之上,为高层协议提供数据封装、压缩、加密等基本功能的支持。 SSL握手协议(SSL Handshake Protocol):它建立在SSL记录协议之上,用于在实际的数据传输开始前,通讯双方进行身份认证、协商加密算法、交换加密密钥等。

安全传输层协议(TLS)用于在两个通信应用程序之间提供保密性和数据完整性。该协议由两层组成: TLS 记录协议(TLS Record)和 TLS 握手协议(TLS Handshake)。

TLS 的最大优势就在于:TLS 是独立于应用协议。高层协议可以透明地分布在 TLS 协议上面。然而,TLS 标准并没有规定应用程序如何在 TLS 上增加安全性;它把如何启动 TLS 握手协议以及如何解释交换的认证证书的决定权留给协议的设计者和实施者来判断。

 1、SSL加密

SSL是Netscape公司所提出的安全保密协议,在浏览器(如Internet Explorer、Netscape Navigator)和Web服务器(如Netscape的Netscape Enterprise Server、ColdFusion Server等等)之间构造安全通道来进行数据传输,SSL运行在TCP/IP层之上、应用层之下,为应用程序提供加密数据通道,它采用了RC4、MD5以及RSA等加密算法,使用40 位的密钥,适用于商业信息的加密。同时,Netscape公司相应开发了HTTPS协议并内置于其浏览器中,HTTPS实际上就是HTTP over SSL,它使用默认端口443,而不是像HTTP那样使用端口80来和TCP/IP进行通信。HTTPS协议使用SSL在发送方把原始数据进行加密,然后在接受方进行解密,加密和解密需要发送方和接受方通过交换共知的密钥来实现,因此,所传送的数据不容易被网络黑客截获和解密。 然而,加密和解密过程需要耗费系统大量的开销,严重降低机器的性能,相关测试数据表明使用HTTPS协议传输数据的工作效率只有使用HTTP协议传输的十分之一。假如为了安全保密,将一个网站所有的Web应用都启用SSL技术来加密,并使用HTTPS协议进行传输,那么该网站的性能和效率将会大大降低,而且没有这个必要,因为一般来说并不是所有数据都要求那么高的安全保密级别

2、TLS加密

TLS:安全传输层协议

TLS:Transport Layer Security

安全传输层协议(TLS)用于在两个通信应用程序之间提供保密性和数据完整性。该协议由两层组成: TLS 记录协议(TLS Record)和 TLS 握手协议(TLS Handshake)。较低的层为 TLS 记录协议,位于某个可靠的传输协议(例如 TCP)上面。

SSL与TLS的区别以及介绍

SSL:(Secure Socket Layer,安全套接字层),位于可靠的面向连接的网络层协议和应用层协议之间的一种协议层。SSL通过互相认证、使用数字签名确保完整性、使用加密确保私密性,以实现客户端和服务器之间的安全通讯。该协议由两层组成:SSL记录协议和SSL握手协议。

TLS:(Transport Layer Security,传输层安全协议),用于两个应用程序之间提供保密性和数据完整性。该协议由两层组成:TLS记录协议和TLS握手协议。

  SSL是Netscape开发的专门用于保护Web通讯的,目前版本为3.0.最新版本的TLS 1.0是IETE(工程任务组)指定的一种新的协议,它建立在SSL 3.0协议规范之上,是SSL 3.0的后续版本。两者差别极小,可以理解为SSL 3.1,它是写入了RFC的。

  SSL(Secure Socket Layer)

  为Netscape所研发,用以保障在Internet上数据传输之安全,利用数据加密(Encryption)技术,可确保数据在网络上之传输过程中不会被截取。

  当前版本为3.0。它已被广泛地用于Web浏览器与服务器之间的身份认证和加密数据传输。

  SSL协议位于TCP/IP协议与各种应用层协议之间,为数据通讯提供安全支持。SSL协议可分为两层:SSL记录协议(SSL Record Protocol):它建立在可靠的传输协议(如TCP)之上,为高层协议提供数据封装、压缩、加密等基本功能的支持。SSL握手协议(SSL Handshake Protocol):它建立在SSL记录协议之上,用于在实际的数据传输开始前,通讯双方进行身份认证、协商加密算法、交换加密密钥等。

  SSL协议提供的服务主要有:

  1)认证用户和服务器,确保数据发送到正确的客户机和服务器;

  2)加密数据以防止数据中途被窃取;

  3)维护数据的完整性,确保数据在传输过程中不被改变。

  SSL协议的工作流程:

  服务器认证阶段:

  1)客户端向服务器发送一个开始信息“Hello”以便开始一个新的会话连接;

  2)服务器根据客户的信息确定是否需要生成新的主密钥,如需要则服务器在响应客户的“Hello”信息时将包含生成主密钥所需的信息;

  3)客服根据收到的服务器响应信息,产生一个主密钥,并用服务器的公开密钥加密后传给服务器;

  4)服务器恢复该主密钥,并返回给客户一个用主密钥认证的信息,以此让客户认证服务器。

  用户认证阶段:在此之前,服务器已经通过了客户认证,这一阶段主要完成对客户的认证。经认证的服务器发送一个提问给客户,客户则返回(数字)签名后的提问和其公开密钥,从而向服务器提供认证。

  TLS(Transport Layer Security Protocol):安全传输层协议

  安全传输层协议(TLS)用于在两个通信应用程序之间提供保密性和数据完整性。该协议由两成组成:TLS记录协议(TLS Record)和TLS握手协议(TLS Handshake)。较低的层为TLS记录协议,位于某个可靠的传输协议(例如TCP)上面。

  TLS记录协议提供的连接安全性具有两个基本特性:

私有——对称加密用以数据加密(DES、RC4等)。对称加密所产生的密钥对每个连接都是唯一的,且此密钥基于另一个协议(如握手协议)协商。记录协议也可以不加密使用。

可靠——信息传输包括使用密钥的MAC进行信息完整性检查。安全哈希功能(SHA、MD5等)用于MAC计算。记录协议在没有MAC的情况下也能操作,但一般只能用于这种模式,即有另一个协议正在使用记录协议传输协商安全参数。

TLS记录协议用于封装各种高层协议。作为这种封装协议之一的握手协议允许服务器与客户机在应用程序协议传输和接收其第一个数据字节前彼此之间互相认证,协商加密算法和加密密钥。TLS握手协议提供的连接安全具有三个基本属性:

可以使用非对称的,或公共密钥的密码术来认证对等方的身份。该认证是可选的,但至少需要一个结点方。

共享解密密钥的协商是安全的。对偷窃者来说协商加密是难以获得的。此外经过认证过的连接不能获得加密,即使是进入连接中间的攻击者也不能。

协商是可靠的。没有经过通信方成员的检测,任何攻击者都不能修改通信协商。

TLS的最大优势就在于:TLS是独立于应用协议。高层协议可以透明地分布在TLS协议上面。然而,TLS标准并没有规定应用程序如何在TLS上增加安全性;它如何启动TLS握手协议以及如何解释交换的认证证书的决定权留给协议的设计者和实施者来判断。

  协议结构

  TLS协议包括两个协议组——TLS记录协议和TLS握手协议。

  TLS和SSL的关系:并列关系

  最新版本的TLS(Transport Layer Security,传输层安全协议)是IETF(Internet Engineering Task Force,Internet工程任务组)制定的一种新的协议,它建立在SSL 3.0协议规范之上,是SSL 3.0的后续版本。在TLS与SSL 3.0之间存在着显著的差别,主要是它们所支持的加密算法不同,所以TLS与SSL 3.0不能互操作。

  1.TLS与SSL的差异

  1)版本号:TLS记录格式与SSL记录格式相同,但版本号的值不同,TLS的版本1.0使用的版本号为SSLv3.1。

  2)报文鉴别码:SSLv3.0和TLS的MAC算法及MAC计算的范围不同。TLS使用RFC-2104定义的HMAC算法。SSLv3.0使用了相似的算法,两者差别在于SSLv3.0中,填充字节与密钥之间采用的是连接运算,而HMAC算法采用的异或运算。但是两者的安全程度是相同的。

  3)伪随机函数:TLS使用了称为PRF的伪随机函数来将密钥扩展成数据块,是更安全的方式。

  4)报警代码:TLS支持几乎所有的SSLv3.0报警代码,而且TLS还补充定义了很多报警代码,如解密失败(decryption_failed)、记录溢出(record_overflow)、未知CA(unknown_ca)、拒绝访问(access_denied)等。

  5)密文族和客户证书:SSLv3.0和TLS存在少量差别,即TLS不支持Fortezza密钥交换、加密算法和客户证书。

  6)certificate_verify和finished消息:SSLv3.0和TLS在用certificate_verify和finished消息计算MD5和SHA-1散列码时,计算的输入有少许差别,但安全性相当。

  7)加密计算:TLS和SSLv3.0在计算主密值(master secret)时采用的方式不同。

  8)填充:用户数据加密之前需要增加的填充字节。在SSL中,填充后的数据长度哟啊达到密文快长度的最小整数倍。而在TLS中,填充后的数据长度可以是密文块长度的任意整数倍(但填充的最大长度为255字节),这种方式可以防止基于对报文长度进行分析的攻击。

  2.TLS的主要增强内容

  TLS的主要目标是使SSL更安全,并使协议的规范更精确和完善。TLS在SSL v3.0的基础上,提供了以下增加内容:

  1)更安全的MAC算法

  2)更严密的警报

  3)“灰色区域”规范的更明确的定义

  3.TLS对于安全性的改进

  1)对于消息认证使用密钥散列法:TLS使用“消息认证代码的密钥散列法”(HMAC),当记录在开放的网络(如因特网)上传送时,该代码确保记录不会被变更。SSLv3.0还提供键控消息认证,但HMAC比SSLv3.0使用(消息认证代码)MAC功能更安全。

  2)增强的伪随机功能(PRF):PRF生成密钥数据。在TLS中,HMAC定义PRF。PRF使用两种散列算法保证其安全性。如果任一算法暴露了,只要第二种算法未暴露,则数据仍然是安全的。

  3)改进的已完成消息验证:TLS和SSLv3.0都对两个端点提供已完成的消息,该消息认证交换的消息没有被变更。然而,TLS将此已完成消息基于PRF和HMAC值之上,这也比SSLv3.0更安全。

  4)一致证书处理:与SSLv3.0不同,TLS试图指定必须在TLS之间实现交换的证书类型。

  5)特定警报消息:TLS提供更多的特定和附加警报,以指示任一会话端点检测到的问题。TLS还对何时应该发送某些警报进行记录。

[更多详细地介绍]

1、聊聊HTTPS和SSL/TLS协议 | 程序师 - 程序员、编程语言、软件开发、编程技术 www.techug.com/post/https-…

2、详解SSL/TLS www.mamicode.com/info-detail… (推荐阅读)

Buy me a cup of coffee :)

本文转载自: 掘金

开发者博客 – 和开发相关的 这里全都有

快速配置Let's encrypt通配符证书 CentOS7

发表于 2021-10-21

本文已参与「掘力星计划」,赢取创作大礼包,挑战创作激励金。

利用certbot工具配置Let’s encrypt通配符证书,所域名下所有的子域名都能方便的使用 https证书,而且完全免费。值得关注的是,Let’s encrypt通配符证书只是针对二级域名,并不能针对主域名,如*.hubinqiang.com和hubinqiang.com 被认为是两个域名,如果和我一样使用的是主域名,在申请的时候需要注意都要申请。

配置环境

操作系统:CentOS7

配置域名:hubinqiang.com,*.hubinqiang.com

步骤

1. 获取Certbot

1
2
3
4
5
6
7
bash复制代码# 下载

wget https://dl.eff.org/certbot-auto

# 设为可执行权限

chmod u+x certbot-auto

2. 申请证书

执行

1
2
3
bash复制代码./certbot-auto certonly  -d "*.9wuquan.com" -d "9wuquan.com" --manual --preferred-challenges dns-01  --server https://acme-v02.api.letsencrypt.org/directory

./certbot-auto certonly -d "*.lww123.com" -d "lww123.com" --manual --preferred-challenges dns-01 --server https://acme-v02.api.letsencrypt.org/directory

参数说明:

  • -certonly,表示安装模式,Certbot 有安装模式和验证模式两种类型的插件。
  • -manual,表示手动安装插件,Certbot 有很多插件,不同的插件都可以申请证书,用户可以根据需要自行选择。
  • -d,为哪些主机申请证书,如果是通配符,输入 *.hubinqiang.com(替换为自己的域名)。
  • -preferred-challenges,使用 DNS 方式校验域名所有权。
  • -server,Let’s Encrypt ACME v2 版本使用的服务器不同于 v1 版本,需要显示指定。

注意:将hubinqiang.com替换为自己的域名。可以通过多个-d 参数添加多个主机。

申请过程中需要如下确认:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
vbnet复制代码Saving debug log to /var/log/letsencrypt/letsencrypt.log

Plugins selected: Authenticator manual, Installer None

Enter email address (used for urgent renewal and security notices) (Enter 'c' to

cancel): hubinqiang@126.com

-------------------------------------------------------------------------------

Please read the Terms of Service at

https://letsencrypt.org/documents/LE-SA-v1.2-November-15-2017.pdf. You must

agree in order to register with the ACME server at

https://acme-v02.api.letsencrypt.org/directory

-------------------------------------------------------------------------------

(A)gree/(C)ancel: A

-------------------------------------------------------------------------------

Would you be willing to share your email address with the Electronic Frontier

Foundation, a founding partner of the Let's Encrypt project and the non-profit

organization that develops Certbot? We'd like to send you email about EFF and

our work to encrypt the web, protect its users and defend digital rights.

-------------------------------------------------------------------------------

(Y)es/(N)o: Y

Obtaining a new certificate

Performing the following challenges:

dns-01 challenge for hubinqiang.com

dns-01 challenge for hubinqiang.com

-------------------------------------------------------------------------------

NOTE: The IP of this machine will be publicly logged as having requested this

certificate. If you're running certbot in manual mode on a machine that is not

your server, please ensure you're okay with that.

Are you OK with your IP being logged?

-------------------------------------------------------------------------------

(Y)es/(N)o: Y

-------------------------------------------------------------------------------

在域名 DNS 解析中添加 TXT记录:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
vbnet复制代码-------------------------------------------------------------------------------

Please deploy a DNS TXT record under the name

_acme-challenge.hubinqiang.com with the following value:

kC-QHSWO1LdIeyIs7VQ66sTAyioISnfzIJU0bXgo-Z8

Before continuing, verify the record is deployed.

-------------------------------------------------------------------------------

Press Enter to Continue

-------------------------------------------------------------------------------

Please deploy a DNS TXT record under the name

_acme-challenge.hubinqiang.com with the following value:

6XnGyee8W48QfRl61m_18aRs8rfvn4T8kKzQil0IYw4

Before continuing, verify the record is deployed.

-------------------------------------------------------------------------------

Press Enter to Continue

Waiting for verification...

Cleaning up challenges

显示我两个主机的 TXT 记录有两条,根据要求分别在 DNS 解析中添加两条 TXT 记录,其中一条如下:_acme-challenge

注意:若申请了多个主机,需要添加多个 TXT 记录。要求给 _acme-challenge.hubinqiang.com 配置 TXT 记录,在没有确认 TXT 记录生效之前不要回车执行。

确认生效后会有如下提示:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
vbnet复制代码IMPORTANT NOTES:

- Congratulations! Your certificate and chain have been saved at:

/etc/letsencrypt/live/hubinqiang.com/fullchain.pem

Your key file has been saved at:

/etc/letsencrypt/live/hubinqiang.com/privkey.pem

Your cert will expire on 2018-08-12. To obtain a new or tweaked

version of this certificate in the future, simply run certbot-auto

again. To non-interactively renew *all* of your certificates, run

"certbot-auto renew"

- Your account credentials have been saved in your Certbot

configuration directory at /etc/letsencrypt. You should make a

secure backup of this folder now. This configuration directory will

also contain certificates and private keys obtained by Certbot so

making regular backups of this folder is ideal.

- If you like Certbot, please consider supporting our work by:

Donating to ISRG / Let's Encrypt: https://letsencrypt.org/donate

Donating to EFF: https://eff.org/donate-le
  • 1
  • 2

进入/etc/letsencrypt/live/hubinqiang.com/中可以看到几个文件,cert.pem、chain.pem、fullchain.pem、privkey.pem,说明已经成功获取证书和密钥。

  1. 配置证书

在 nginx 中配置的片段:

1
2
3
4
5
6
7
8
9
10
11
12
13
ini复制代码server {

server_name hubinqiang.com;

listen 443 http2 ssl;

ssl on;

ssl_certificate /etc/letsencrypt/live/hubinqiang.com/fullchain.pem;

ssl_certificate_key /etc/letsencrypt/live/hubinqiang.com/privkey.pem;

ssl_trusted_certificate /etc/letsencrypt/live/hubinqiang.com/chain.pem;
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8

重启 nginx 查看效果。

  1. 证书更新

Let’s encrypt 的免费证书默认有效期为 90 天,到期后如果要续期可以执行:

1. 获取Certbot 2. 申请证书

重新这2步就可以了证书更新

或者更新全部证书:

./certbot-auto

CentOS7Apache下上安装Let’s Encrypt

一、升级系统

  1. yum -y update

四、Apache下配置Let’s Encrypt

执行下条命令

  1. ./certbot-auto –apache

根据提示操作

Which names would you like to activate HTTPS for?


1: www.9wuquan.cn

2: www.lww123.cn


Select the appropriate numbers separated by commas and/or spaces, or leave input

blank to select all options shown (Enter ‘c’ to cancel): 1

输入1

Please choose whether or not to redirect HTTP traffic to HTTPS, removing HTTP access.


1: No redirect - Make no further changes to the webserver configuration.

2: Redirect - Make all requests redirect to secure HTTPS access. Choose this for

new sites, or if you’re confident your site works on HTTPS. You can undo this

change by editing your web server’s configuration.


Select the appropriate number [1-2] then [enter] (press ‘c’ to cancel): 2

输入2

五、打开防火墙iptables的443端口

六、编辑ssl.conf

vi /etc/httpd/conf.d/ssl.conf

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
bash复制代码<VirtualHost *:80>

DocumentRoot /var/www/jqbs

ServerName 9wuquan.cn

ServerAlias *.9wuquan.cn

<Directory />

Options FollowSymLinks

AllowOverride All

</Directory>

</VirtualHost>

<VirtualHost *:443>

DocumentRoot /var/www/jqbs

ServerName 9wuquan.cn

ServerAlias *.9wuquan.cn

SSLEngine on

SSLProtocol TLSv1 TLSv1.1 TLSv1.2

SSLCipherSuite HIGH:MEDIUM:!aNULL:!MD5

<Directory />

Options FollowSymLinks ExecCGI

AllowOverride All

Order allow,deny

Allow from all

Require all granted

</Directory>

SSLCertificateFile /etc/letsencrypt/live/9wuquan.cn/cert.pem

SSLCertificateKeyFile /etc/letsencrypt/live/9wuquan.cn/privkey.pem

Include /etc/letsencrypt/options-ssl-apache.conf

SSLCertificateChainFile /etc/letsencrypt/live/9wuquan.cn/chain.pem

</VirtualHost>

/etc/httpd/conf/httpd.conf配置文件的修改主要有以下几项:

(2.安装apache的mod_ssl.so模块yum -y install mod_ssl)

1
2
3
bash复制代码LoadModule ssl_module modules/mod_ssl.so

LoadModule rewrite_module modules/mod_rewrite.so
  1. ServerSignature On => ServerSignature Off // 配置错误页不显示Apache版本
  2. Options Indexes FollowSymLinks => Options FollowSymLinks // 配置Apache不能通过目录层级进行文件访问

<Directory “/var/www”>

1
css复制代码AllowOverride All
  1. AllowOverride None => AllowOverride All // 配置允许.htaccess
  2. DirectoryIndex index.html => DirectoryIndex index.html index.php // 配置Apache支持.php文件解析

重启Apache

systemctl restart httpd

七、这个时候网站HTTPS已经能够访问了,试一下

最后,通过.htaccess进行301转向

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
perl复制代码<IfModule mod_rewrite.c>

Options +FollowSymlinks -Multiviews

RewriteEngine On



RewriteCond %{HTTPS} !=on

RewriteRule ^(.*) https://%{SERVER_NAME}/$1 [L,R=302]

RewriteCond %{REQUEST_FILENAME} !-d

RewriteCond %{REQUEST_FILENAME} !-f

RewriteRule ^(.*)$ index.php?/$1 [QSA,PT,L]

</IfModule>

# 图片和Flash内容缓存一个月

<FilesMatch ".(flv|gif|jpg|jpeg|png|ico|swf)$">

Header set Cache-Control "max-age=2592000"

</FilesMatch>

<FilesMatch ".(ttf)$">

Header set Access-Control-Allow-Origin "*"

</FilesMatch>
  1. 八、大功告成证书更新

Let’s encrypt 的免费证书默认有效期为 90 天,到期后如果要续期可以执行:

更新全部证书:

./certbot-auto

怎么把申请到的证书导入到IIS中

由于我们申请的证书为pem格式,而IIS只支持pfx格式证书

所以我们要把输的人pem文件合并为pfx证书

这样我们就要用到openssl命令了

openssl pkcs12 -export -out 51tcsd.pfx -inkey privkey.pem -in fullchain.pem -certfile cert.pem

我们用此命令把pem文件合并为51tcsd.pfx文件,提示中要输入证书的密码,按提示输入即可

显示输出如下

https://images2018.cnblogs.com/blog/45026/201805/45026-20180525174216702-1789610871.png

我们可以看到,当前目录下成功生成了51tcsd.pfx文件

接下来我们就要把51tcsd.pfx文件导入到Windows系统

我们知道Ubuntu对于Windows来说只是一个应用,

所以Ubuntu里所有的文件,我们都可以通过Windows资源管理里看到,

我发现我的Ubuntu目录挂载在我的Windows目录的此位置

C:\Users\Administrator\AppData\Local\Packages\CanonicalGroupLimited.UbuntuonWindows_79rhkp1fndgsc\LocalState\rootfs

https://images2018.cnblogs.com/blog/45026/201805/45026-20180525174601519-1460102186.png

我们进到C:\Users\Administrator\AppData\Local\Packages\CanonicalGroupLimited.UbuntuonWindows_79rhkp1fndgsc\LocalState\rootfs\etc\letsencrypt\live\51tcsd.com-0001

就可以看到我们的pfx文件了

https://images2018.cnblogs.com/blog/45026/201805/45026-20180525174708392-773956879.png

( 1 ) 证书导入

• 开始 -〉运行 -〉MMC;

• 启动控制台程序,选择菜单“文件”中的”添加/删除管理单元”-> “添加”,从“可用的独立管理单元”列表中选择“证书”-> 选择“计算机帐户”;

• 在控制台的左侧显示证书树形列表,选择“个人”->“证书”,右键单击,选择“所有任务”-〉”导入”, 根据”证书导入向导”的提示,导入PFX文件(此过程当中有一步非常重要: “根据证书内容自动选择存储区”)。安装过程当中需要输入密码为您当时设置的密码。导入成功后,可以看到证书信息。

( 2 ) 分配服务器证书

• 打开 IIS8.0 管理器面板,找到待部署证书的站点,点击“绑定”。

• 设置参数选择“绑定”->“添加”->“类型选择 https” ->“端口 443” ->“ssl 证书【导入的证书名称】” ->“确定”。

SSL 缺省端口为 443 端口(请不要随便修改。 如果您使用其他端口如:8443,则访问时必须输入:www.domain.com:8443)。%E3%80%82/)

接下来。我们右键证书点安装pfx

https://images2018.cnblogs.com/blog/45026/201805/45026-20180525174903645-1223980533.png

https://images2018.cnblogs.com/blog/45026/201805/45026-20180525174934998-2047727718.png

输入刚刚openssl合并的时候输入的密码

https://images2018.cnblogs.com/blog/45026/201805/45026-20180525174959631-1344108232.png

https://images2018.cnblogs.com/blog/45026/201805/45026-20180525175044587-858536133.png

https://images2018.cnblogs.com/blog/45026/201805/45026-20180525175102458-361536214.png

点完成后。就会显示导入成功了

接下来。我们打开IIS管理器。看到服务器证书里面,就能发现我们申请的通配符证书了

https://images2018.cnblogs.com/blog/45026/201805/45026-20180525175317147-765263780.png

https://images2018.cnblogs.com/blog/45026/201805/45026-20180525175402347-596073691.png

接下来,我们给一个站点绑定随便一个二级域名,比如:a.51tcsd.com

首先把hosts文件把a.51tcsd.com解析到我本机127.0.0.1

https://images2018.cnblogs.com/blog/45026/201805/45026-20180525175608991-414872320.png

然后在IIS里选择站点”Default Web Site”选择右边的“绑定”

输入相关信息,并选择证书

https://images2018.cnblogs.com/blog/45026/201805/45026-20180525175819396-1302058709.png

然后我们在浏览器里访问a.51tcsd.com/

是不是看到惊喜了

https://images2018.cnblogs.com/blog/45026/201805/45026-20180525175945295-1026881646.png

HTTP 转HTTPS

HTTP和HTTPS交叉使用属于跨域的范畴,直接转接解决跨域问题的方法:

可以在相应的页面的里加上这句代码,意思是自动将http的不安全请求升级为https

IIS http转HTTPS

在web.cofg文件内加加入

<system.webServer>

</system.webServer>

Buy me a cup of coffee :)

本文转载自: 掘金

开发者博客 – 和开发相关的 这里全都有

1…479480481…956

开发者博客

9558 日志
1953 标签
RSS
© 2025 开发者博客
本站总访问量次
由 Hexo 强力驱动
|
主题 — NexT.Muse v5.1.4
0%