运维安全: Linux检测登录失败记录并自动拉入黑名单脚本

58 篇文章 1 订阅
3 篇文章 1 订阅

效果

使用效果

源码

from subprocess import getoutput, getstatusoutput
from datetime import datetime, timedelta
from ColorInfo import ColorLogger


class LoginBlocking:
	def __init__(self, failed=2, day=-30):
		"""
		登录拦截
		:param day: 设置往前的天数
		:param failed: 设置需要拉黑的IP攻击次数,默认: 2
		"""
		self.failed = failed
		self.os_type = getoutput("""grep ^ID /etc/os-release | sed 's/ID=//' | sed -n 1p | sed 's#\"##g'""")
		self.logger = ColorLogger()
		self.res = []
		self.Blacklist = []  # 黑名单列表
		self.WriteFile = "/etc/hosts.deny"  # 写入黑名单文件
		self.Source = ""
		self.dateStart = datetime.now() + timedelta(days=day)
		self.dateStart = self.dateStart.date()
		self.IpDic = {"10.2.2.4": 3}  # 记录IP登录次数{10.2.2.4: 3}
		self.UserDic = {}  # 记录用户名登录次数{liumou: 3}

	def Read(self, file):
		"""
		读取源配置信息
		:return:
		"""
		self.Source = getoutput("cat " + file)

	def Write(self):
		"""
		开始写入
		:return:
		"""

		self.Read(self.WriteFile)
		OldIpList = getoutput("awk '{print $2}' /etc/hosts.deny").split("\n")
		ba = len(OldIpList)
		ws = 0
		for ip in self.IpDic:
			s = "\nALL: " + ip
			if self.IpDic[ip] >= self.failed and ip not in OldIpList:
				# 如果IP失败次数大于或等于设置阈值,且不在旧名单中则加入源
				self.logger.debug("新增黑名单: ", ip)
				self.Source = self.Source + s
				ws += 1
			else:
				self.logger.debug("黑名单已存在: ", ip)
		if ws > 0:
			try:
				with open(file=self.WriteFile, mode='w', encoding="utf-8") as w:
					w.write(self.Source)
					w.close()
				self.logger.info("黑名单写入成功,本次新增增加: ", ws, "个IP")
				ba += ws
			except Exception as e:
				self.logger.error(str(e))
		else:
			self.logger.info("检测结束,本次未新增任何IP")
		self.logger.info("累计添加黑名单数量: ", ba)

	def check(self):
		cmd = """lastb --time-format iso  | awk '{print $1,$3,$4}'"""
		# 得到样式:
		# zxcloudsetup 103.147.242.68 2021-12-18T18:42:51+08:00
		# zxcloudsetup 143.110.224.148 2021-12-18T18:42:51+08:00
		self.res = getstatusoutput(cmd)
		if self.res[0] == 0:
			self.logger.warning("检测到有用户登录失败记录")
		else:
			self.logger.debug("未检测到用户登录失败信息")

	def handel(self):
		data = self.res[1].split("\n")
		for i in data:
			sliceI = str(i).split(" ")
			# i: zxcloudsetup 103.147.242.68
			user = sliceI[0]
			ip = sliceI[1]
			date = sliceI[2].split("T")[0]  # 得到日期,如: 2021-12-14
			sliceDate = str(date).split("-")
			if len(sliceDate) != 3:
				continue
			ys = sliceDate[0]
			ms = sliceDate[1]
			ds = sliceDate[2]
			if len(ys) == 4 and len(ms) == 2 and len(ds) == 2:
				y = int(ys.replace("\n", '').replace(" ", ''))
				m = str(ms.replace("\n", '').replace(" ", ''))
				if len(m) > 1:
					if m[0] == "0":
						m = int(m[1])
				d = ds.replace("\n", '').replace(" ", '')
				if len(d) > 1:
					if d[0] == "0":
						d = int(d[1])
				stop = datetime(int(y), int(m), int(d)).date()
				if stop > self.dateStart:
					# 如果日期大于设置开始日期则记录
					ip = str(ip).replace(" ", '')
					user = str(user).replace(" ", '')
					print("用户: ", user, "- IP: ", ip)
					if ip in self.IpDic:
						s = self.IpDic[ip] + 1
						self.IpDic[ip] = int(s)
					else:
						self.IpDic[ip] = 1
					if user in self.UserDic:
						self.UserDic[user] = self.UserDic[user] + 1
					else:
						self.UserDic[user] = 1
		for i in self.IpDic:
			print("黑名单地址: ", i, " 攻击次数: ", self.IpDic[i])

	def start(self):
		self.check()
		self.handel()
		self.Write()


if __name__ == "__main__":
	ss = LoginBlocking()
	ss.start()
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

坐公交也用券

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值