分类目录归档:无主题

Linux根据端口号查进程信息

只知道端口号不知道进程相关信息,那能不能通过端口号查询进程号呢?

使用lsof找出pid

lsof -i:22

例:

[root@xuchengen ~]# lsof -i:80
COMMAND   PID  USER   FD   TYPE   DEVICE SIZE/OFF NODE NAME
nginx   15673  root    6u  IPv4 14231513      0t0  TCP *:http (LISTEN)
nginx   15674 nginx    6u  IPv4 14231513      0t0  TCP *:http (LISTEN)

使用netstat找出pid

# 找出非监听端口
netstat -ntp | grep ":22"

例:

[root@xuchengen ~]# netstat -ntp | grep ":3389"
tcp        0      0 172.21.0.16:33464       47.96.175.183:3389      ESTABLISHED 1260/appnode-ccente 
tcp        0      0 172.21.0.16:33544       47.96.175.183:3389      ESTABLISHED 1260/appnode-ccente
# 找出监听端口
netstat -ntpl | grep ":22"

例:

[root@xuchengen ~]# netstat -ntpl | grep ":3389"
tcp        0      0 0.0.0.0:3389            0.0.0.0:*               LISTEN      1264/sshd

使用ps找出进程名

ps -ef|grep $pid

例:

[root@xuchengen ~]# ps -ef|grep 1264
root      1264     1  0 Nov05 ?        00:00:04 /usr/sbin/sshd -D
root     11148  5090  0 16:24 pts/0    00:00:00 grep --color=auto 1264

 

开发者必备Linux基础命令行

作为一名开发者熟练操作Linux命令行算是一项基本功。通常小公司没有运维所以呢开发及运维!

TOP命令

Linux top命令用于实时显示当前操作系统进程的动态。

第1行:系统时间、运行时间、登陆终端数、系统负载(分别为1分钟、5分钟、15分钟内的平均值)

第2行:进程总数、运行中的进程数、睡眠中的进程数、停止的进程数、僵死的进程数。

第3行:用户占用资源百分比、系统内核占用资源百分比、改变过优先级的进程资源百分比、空闲的资源百分比。

第4行:物理内存总量、空闲内存总量、内存使用量、作为内核缓存的内存量。

第5行:虚拟内存总量、空闲虚拟内存总量、虚拟内存使用量、①被提前加载的内存量。

《菜鸟教程Linux top命令》

HTOP命令

htop作为top的升级版可以更加直观的方式显示当前系统的状态。默认情况下Centos不会安装htop命令行程序需要手动安装。

# 安装htop命令
yum -y install htop

htop命令

IFCONFIG命令

Linux ifconfig命令用于显示或设置网络设备。

ifconfig可设置网络设备的状态,或是显示目前的设置。

默认情况下Centos7不会安装ifconfig命令需要手动安装。

# 安装ifconfig命令
yum -y install net-tools

《菜鸟教程Linux ifconfig命令》

TELNET命令

Linux telnet命令用于远端登入。

执行telnet指令开启终端机阶段作业,并登入远端主机。

一般而言我们会使用telnet命令探测目标服务器是否开放指定端口。

手动安装telnet命令程序:

# 安装telnet命令
yum -y install telnet

探测目标端口是否开放:

# 探测目标端口
telnet 127.0.0.1 3306
# 回显表明目标端口是开放状态
Trying 127.0.0.1...
Connected to 127.0.0.1.
Escape character is '^]'.

《菜鸟教程Linux telnet命令》

SSH命令

Linux ssh命令执行远程登录。

windows端使用Xshell客户端登录Linux服务器。

Mac端直接使用终端就够了。

默认22端口:

# ssh登录Linux服务器
ssh root@127.0.0.1

指定其他端口:

# ssh指定其他端口
ssh root@127.0.0.1 -p 3389

SCP命令

Linux scp 命令用于 Linux 之间复制文件和目录。

scp 是 secure copy 的缩写, scp 是 linux 系统下基于 ssh 登陆进行安全的远程文件拷贝命令。

scp 是加密的,rcp 是不加密的,scp 是 rcp 的加强版。

这个命令用的不多,一般也有替代客户端走sftp协议进行上传文件。

《菜鸟教程Linux SCP命令》

SZ命令

sz命令可以将服务器上的文件下载到本地。

通常我们排查应用程序日志会使用cat、tail亦或是vi、vim等命令,如果日志文件过于庞大排查起来也是很困难还不如下载下来用文本编辑器排查,这时候sz命令就派上用场。

# sz命令
sz xxx.log

 

Redis缓存击穿解决方案

缓存击穿:key对应的数据存在,但在redis中过期,此时若有大量并发请求过来,这些请求发现缓存过期一般都会从后端DB加载数据并回设到缓存,这个时候大并发的请求可能会瞬间把后端DB压垮。

缓存击穿

key可能会在某些时间点被超高并发地访问,是一种非常“热点”的数据。这个时候,需要考虑一个问题:缓存被“击穿”的问题。

解决方案

使用互斥锁(mutex key)

业界比较常用的做法,是使用mutex。简单地来说,就是在缓存失效的时候(判断拿出来的值为空),不是立即去load db,而是先使用缓存工具的某些带成功操作返回值的操作(比如Redis的SETNX或者Memcache的ADD)去set一个mutex key,当操作返回成功时,再进行load db的操作并回设缓存;否则,就重试整个get缓存的方法。

SETNX,是「SET if Not eXists」的缩写,也就是只有不存在的时候才设置,可以利用它来实现锁的效果。

public String get(key) {
    String value = redis.get(key);
    if (value == null) { //代表缓存值过期
        //设置3min的超时,防止del操作失败的时候,下次缓存过期一直不能load db
        if (redis.setnx(key_mutex, 1, 3 * 60) == 1) {  //代表设置成功
            value = db.get(key);
            redis.set(key, value, expire_secs);
            redis.del(key_mutex);
        } else {  //这个时候代表同时候的其他线程已经load db并回设到缓存了,这时候重试获取缓存值即可
            sleep(50);
            get(key);  //重试
        }
    } else {
        return value;
    }
}

Memcache

if (memcache.get(key) == null) {  
    // 3 min timeout to avoid mutex holder crash  
    if (memcache.add(key_mutex, 3 * 60 * 1000) == true) {  
        value = db.get(key);  
        memcache.set(key, value);  
        memcache.delete(key_mutex);  
    } else {  
        sleep(50);  
        retry();  
    }  
}

 

Redis缓存穿透解决方案

缓存穿透:key对应的数据在数据源并不存在,每次针对此key的请求从缓存获取不到,请求都会到数据源,从而可能压垮数据源。比如用一个不存在的用户id获取用户信息,不论缓存还是数据库都没有,若黑客利用此漏洞进行攻击可能压垮数据库。

缓存穿透

一个一定不存在缓存及查询不到的数据,由于缓存是不命中时被动写的,并且出于容错考虑,如果从存储层查不到数据则不写入缓存,这将导致这个不存在的数据每次请求都要到存储层去查询,失去了缓存的意义。

方案一

有很多种方法可以有效地解决缓存穿透问题,最常见的则是采用布隆过滤器,将所有可能存在的数据哈希到一个足够大的bitmap中,一个一定不存在的数据会被 这个bitmap拦截掉,从而避免了对底层存储系统的查询压力。

方案二

另外也有一个更为简单粗暴的方法(我们采用的就是这种),如果一个查询返回的数据为空(不管是数据不存在,还是系统故障),我们仍然把这个空结果进行缓存,但它的过期时间会很短,最长不超过五分钟。

//伪代码
public object GetProductListNew() {
    int cacheTime = 30;
    String cacheKey = "product_list";

    String cacheValue = CacheHelper.Get(cacheKey);
    if (cacheValue != null) {
        return cacheValue;
    }

    cacheValue = CacheHelper.Get(cacheKey);
    if (cacheValue != null) {
        return cacheValue;
    } else {
        //数据库查询不到,为空
        cacheValue = GetProductListFromDB();
        if (cacheValue == null) {
            //如果发现为空,设置个默认值,也缓存起来
            cacheValue = string.Empty;
        }
        CacheHelper.Add(cacheKey, cacheValue, cacheTime);
        return cacheValue;
    }
}

 

使用Portainer搭建你的实验靶场

Portainer简化了Docker,Swarm,Kubernetes,ACI和EDGE环境中的容器管理。工程师和DevOps团队使用它来加速软件部署,解决问题并简化迁移。

作为一名后端开发工程师苦于敲各种各样的命令行,亦或是学习中间件的时候常常要搭建各式各样的基础设施而浪费大量时间。

Portainer的可视化操作方便了开发者搭建各式各样的基础设施,使得开发者有更多的时间进行业务开发。

部署Portainer有多简单?

使用Docker安装Portainer

Portainer由两个元素组成,即Portainer服务器Portainer代理这两个元素都作为轻量级Docker容器在Docker引擎或Swarm集群中运行。由于Docker的性质,存在许多可能的部署方案,但是,我们在下面详细介绍了最常见的方案。请使用与您的配置匹配的方案(或者如果未列出您的配置,请参阅portainer.readthedocs.io以获取其他选项)。

请注意,使用Swarm时建议的部署模式是使用Portainer代理。

仅在Linux(CentOS 7和8,Ubuntu 16.04.6 LTS,18.04.4 LTS和20.04 LTS)和Windows(Win 10> 1909和Server 2019> 1909)上运行时才正式支持Portainer。Portainer未在MacOS或任何其他OS或OS系列/版本上进行测试。

独立的LINUX Docker主机 /单节​​点群集集群(或以“ Linux容器”模式运行的Windows 10 Docker主机)上部署Portainer Server 。

使用以下Docker命令部署Portainer服务器;请注意,在独立主机上不需要代理,但是如果使用代理,它会提供其他功能(请参阅下面的portainer和代理场景):

$ docker volume create portainer_data
$ docker run -d -p 8000:8000 -p 9000:9000 --name=portainer --restart=always -v /var/run/docker.sock:/var/run/docker.sock -v portainer_data:/data portainer/portainer

您只需要使用浏览器访问运行portainer的Docker引擎的9000端口。

注意:端口9000是Portainer用于UI访问的常规端口。EDGE代理仅将端口8000用于反向隧道功能。如果您不打算使用边缘代理,则不需要公开端口8000

注意-v /var/run/docker.sock:/var/run/docker.sock选项只能在Linux环境中使用。

独立的WINDOWS Docker主机(运行Windows容器)上部署Portainer Server –注意必须是Windows 1909或更高版本。

$ docker volume create portainer_data
$ docker run -d -p 8000:8000 -p 9000:9000 --name portainer --restart always -v \\.\pipe\docker_engine:\\.\pipe\docker_engine -v portainer_data:C:\data portainer/portainer

您只需要使用浏览器访问运行portainer的Docker引擎的9000端口。

《阿里巴巴编码规范》认证证书你值得拥有

Apsara Clouder基础技能认证:阿里巴巴编码规范

无规矩不成方圆,无规范不能协作。阿里近万名Java技术精英的经验总结,铸就了高含金量的《阿里巴巴Java开发手册》,并向业界开放,希望使团队在Java开发上更高效、容错、有协作性,提高代码质量并降低维护成本。本认证是对你的编码风格是否符合该手册的证明。

老徐趁着周末花了两天时间认真研读《阿里巴巴Java开发手册》,通过两次考试沉着应对临危不乱终于拿到认证证书。

设计模式分类(创建型模式、结构型模式、行为模式)

创建型模式

创建型模式,就是创建对象的模式,抽象了实例化的过程。它帮助一个系统独立于如何创建、组合和表示它的那些对象。关注的是对象的创建,创建型模式将创建对象的过程进行了抽象,也可以理解为将创建对象的过程进行了封装,作为客户程序仅仅需要去使用对象,而不再关系创建对象过程中的逻辑。

社会化的分工越来越细,自然在软件设计方面也是如此,因此对象的创建和对象的使用分开也就成为了必然趋势。因为对象的创建会消耗掉系统的很多资源,所以单独对对象的创建进行研究,从而能够高效地创建对象就是创建型模式要探讨的问题。这里有6个具体的创建型模式可供研究,它们分别是:

  • 简单工厂模式(Simple Factory)
  • 工厂方法模式(Factory Method)
  • 抽象工厂模式(Abstract Factory)
  • 创建者模式(Builder)
  • 原型模式(Prototype)
  • 单例模式(Singleton)

简单工厂模式不是GoF总结出来的23种设计模式之一

结构型模式

结构型模式是为解决怎样组装现有的类,设计它们的交互方式,从而达到实现一定的功能目的。结构型模式包容了对很多问题的解决。例如:扩展性(外观、组成、代理、装饰)、封装(适配器、桥接)。

在解决了对象的创建问题之后,对象的组成以及对象之间的依赖关系就成了开发人员关注的焦点,因为如何设计对象的结构、继承和依赖关系会影响到后续程序的维护性、代码的健壮性、耦合性等。对象结构的设计很容易体现出设计人员水平的高低,这里有7个具体的结构型模式可供研究,它们分别是:

  • 外观模式/门面模式(Facade门面模式)
  • 适配器模式(Adapter)
  • 代理模式(Proxy)
  • 装饰模式(Decorator)
  • 桥梁模式/桥接模式(Bridge)
  • 组合模式(Composite)
  • 享元模式(Flyweight)

行为型模式

行为型模式涉及到算法和对象间职责的分配,行为模式描述了对象和类的模式,以及它们之间的通信模式,行为模式刻划了在程序运行时难以跟踪的复杂的控制流可分为行为类模式和行为对象模式。1. 行为类模式使用继承机制在类间分派行为。2. 行为对象模式使用对象聚合来分配行为。一些行为对象模式描述了一组对等的对象怎样相互协作以完成其中任何一个对象都无法单独完成的任务。

在对象的结构和对象的创建问题都解决了之后,就剩下对象的行为问题了,如果对象的行为设计的好,那么对象的行为就会更清晰,它们之间的协作效率就会提高,这里有11个具体的行为型模式可供研究,它们分别是:

  • 模板方法模式(Template Method)
  • 观察者模式(Observer)
  • 状态模式(State)
  • 策略模式(Strategy)
  • 职责链模式(Chain of Responsibility)
  • 命令模式(Command)
  • 访问者模式(Visitor)
  • 调停者模式(Mediator)
  • 备忘录模式(Memento)
  • 迭代器模式(Iterator)
  • 解释器模式(Interpreter)

三者之间的区别和联系

创建型模式提供生存环境,结构型模式提供生存理由,行为型模式提供如何生存。

  1. 创建型模式为其他两种模式使用提供了环境。
  2. 结构型模式侧重于接口的使用,它做的一切工作都是对象或是类之间的交互,提供一个门。
  3. 行为型模式顾名思义,侧重于具体行为,所以概念中才会出现职责分配和算法通信等内容。

设计原则

  1. 开闭原则: 对扩展开放,对修改关闭
  2. 里氏转换原则: 子类继承父类,单独完全可以运行
  3. 依赖倒转原则: 引用一个对象,如果这个对象有底层类型,直接引用底层类型
  4. 接口隔离原则: 每一个接口应该是一种角色
  5. 合成/聚合复用原则: 新的对象应使用一些已有的对象,使之成为新对象的一部分
  6. 迪米特原则: 一个对象应对其他对象有尽可能少的了解

CentOS7安装zookeeper后建立systemctl自启动脚本

Apache ZooKeeper是Apache软件基金会的一个软件项目,它为大型分布式计算提供开源的分布式配置服务、同步服务和命名注册。ZooKeeper曾经是Hadoop的一个子项目,但现在是一个独立的顶级项目。

ZooKeeper的架构通过冗余服务实现高可用性。因此,如果第一次无应答,客户端就可以询问另一台ZooKeeper主机。ZooKeeper节点将它们的数据存储于一个分层的命名空间,非常类似于一个文件系统或一个前缀树结构。客户端可以在节点读写,从而以这种方式拥有一个共享的配置服务。更新是全序的。

使用ZooKeeper的公司包括Rackspace、雅虎和eBay,以及类似于像Solr这样的开源企业级搜索系统。

systemctl自启动脚本

[Unit]
Description=Zookeeper
Requires=network.target
After=network.target

[Service]
User=java
Group=java
Type=forking
Environment=JAVA_HOME=/opt/java/java8
WorkingDirectory=/opt/zookeeper
ExecStart=/opt/zookeeper/bin/zkServer.sh start /opt/zookeeper/conf/zoo.cfg
ExecStop=/opt/zookeeper/bin/zkServer.sh stop /opt/zookeeper/conf/zoo.cfg
ExecReload=/opt/zookeeper/bin/zkServer.sh restart /opt/zookeeper/conf/zoo.cfg

[Install]
WantedBy=multi-user.target

 

升级MacOS Catalina10.15导致SVN或Git报错解决方案

最近把Mac升级到最新10.15版本导致SVN或GIT导项目时报错具体报错如下:

Git doesn't work on MacOS Catalina: “xcrun: error: invalid active developer 
path (/Library/Developer/CommandLineTools), missing” [duplicate]

在stackoverflow找到解决方案:

sudo rm -rf /Library/Developer/CommandLineTools
xcode-select --install

没权限记得加上sudo