日志分析

本文介绍了日志分析的重要性,从日志采集、存储到分析的流程,特别是利用生产者消费者模型构建消息队列分发器,用于日志的高效处理。通过注册分析算法,如IP、PV和浏览器分析器,实现对日志数据的深度分析。
摘要由CSDN通过智能技术生成

日志分析

概述

生成中会生成大量的系统日志、应用程序日志、安全日志等等日志,通过对日志的分析可以了解服务器的负载、健 康状况,可以分析客户的分布情况、客户的行为,甚至基于这些分析可以做出预测。
一般采集流程 日志产出 -> 采集(Logstash、Flume、Scribe) -> 存储 -> 分析 -> 存储(数据库、NoSQL) -> 可视化
开源实时日志分析ELK平台 Logstash收集日志,并存放到ElasticSearch集群中,Kibana则从ES集群中查询数据生成图表,返回浏览器端

  • 半结构化数据
    日志是半结构化数据,是有组织的,有格式的数据。可以分割成行和列,就可以当做表理解和处理了,当然也可以 分析里面的数据。
  • 文本分析
    日志是文本文件,需要依赖文件IO、字符串操作、正则表达式等技术。
    通过这些技术就能够把日志中需要的数据提取出来。
    日志文件下载地址

加载日志文件,解析日志

from pathlib import Path
import re,datetime,threading
from queue import Queue
from collections import defaultdict
from user_agents import parse
from urllib.parse import urlparse

expdict = {
   
    "datetime":lambda x:datetime.datetime.strptime(x,"%d/%b/%Y:%H:%M:%S %z"),
    "length":int,
    "status":int,
    "useragent":lambda ua: parse(ua)
}

#解析日志
def loganalysis(file:str,encoding=None):
    restr = '''^(?P<address>[\d.]{7,}) - . \[(?P<datetime>[^\]]*)\] "(?P<method>[^ ]+) (?P<url>[^ ]+) (?P<protocol>[^ ]+)" (?P<status>\d{3}) (?P<length>\d)+ "[^ ]*" "(?P<useragent>[^"]+)"'''
    req = re.compile(restr)
    with Path(file).open(encoding=encoding) as f:
        for line in f:
            regex = req.match(line)
            if regex: #日志行解析成功
                yield {
   k:expdict.get(k,lambda x:x)(v) for k,v in regex.groupdict().items()}
            else: #解析失败
                raise Exception("No match. {}".format(line))

#加载日志文件
def load(*paths,ext:str="*.log",recursive:bool=False,encoding:str="utf8"):
    for filepath in paths:
        path = Path(filepath)
        ext = [ext] if isinstance(ext,str) else list(ext)
        if path.is_dir(): #是目录
            for et in ext:
                for f in (path.rglob if recursive else path.rglob)(et):
                    yield from loganalysis(f.absolute(),encoding)
        else: #是文件,直接读取
            yield from loganalysis(path.absolute(),encoding)

构建消息队列分发器

生产者消费者模型

一个系统的健康运行,需要监控并处理很多数据,包括日志。对其中已有数据进行采集、分析。 被监控对象就是数据的生产者producer,数据的处理程序就是数据的消费者consumer。

  • 传统的生产者和消费者模型
    log002
    传统的生产者消费者模型,生产者生产,消费者消费。但这种模型有些问题。 生产者和消费者代码耦合太高,代码实现上要么是生产者产生一个数据就调用消费者,要么就是消费者处理完一个 数据就调用生产者一次。如果生成规模扩大,不易扩展,生产和消费的速度很难匹配等。
  • 带入消息队列的生产者和消费者模型
  • 作用——解耦、缓冲。
    log003
    日志生产者往往会部署好几个程序,日志产生的也很多,而消费者也会有多个程序,去提取日志分析处理
    数据的生产是不稳定的!可能会造成短时间数据的“潮涌”,需要缓冲。 消费者消费能力不一样,有快有慢,消费者可以自己决定消费缓冲区中的数据。
    单机时,可以使用标准库queue模块的类来构建进程内的队列,满足多个线程间的生产消费需要。 大型系统可以使用第三方消息中间件——RabbitMQ、RocketMQ、Kafka等。
    数据处理所需模块—队列
  • queue模块–多队列,提供了一个先进先出的队列Queue
  • threading模块–线程。帮助队列不断获取数据。
    为了让生产者的生产数据和消费者的消费数据同时进行,可以使用不同的线程。

数据处理流程

  • 生产者(数据源)生产数据,缓冲到消息队列中
    log004

分发器的实现

数据分析的程序有很多,例如PV分析、IP分析、UserAgent分析等。
同一套数据可能要被多个分析程序并行处理:

  • 需要使用多线程来并行处理
  • 多个分析程序又需要同一份数据,这就是一份变多份
    log005
    这是一个典型的分发器
  • 注册统计分析函数,并为其提供一个单独的数据队列
  • 收集日志数据
  • 将一份日志数据发送到多个已注册的分析函数的队列中去
  • 为了并行,每一个分析函数都在一个独立的线程中执行
######消息队列分发
def dispatchar(src):
    handler = []
    queueler = []

    #队列注册
    def reg(fun):
        q = Queue()
        handler.append(threading.Thread(target=fun,args=(q,)
  • 1
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值