中間件--ClickHouse-12--案例-1-日志分析和監控

1、案例背景

一家互聯網公司需要實時分析其服務器日志、應用日志和用戶行為日志,以快速發現潛在問題并優化系統性能。

2、需求分析

  • 目標:實時分析日志數據,快速發現問題并優化系統性能。
  • 數據來源:
    • 服務器日志:如 Nginx、Tomcat、Docker等日志。
    • 應用日志:業務系統的運行日志。
    • 用戶行為日志:用戶操作記錄(如點擊、瀏覽、下單等)。
  • 輸出:
    • 錯誤率、請求延遲、用戶行為路徑等關鍵指標。
    • 實時監控儀表盤。

3、解決思路

  • 日志采集:使用工具(如Filebeat或Fluentd)將日志數據寫入Kafka。
  • 數據存儲與分析:Kafka中的數據被導入到ClickHouse,利用其高效的壓縮和查詢性能進行日志分析。
  • 可視化:通過 Grafana 或 Redash 構建儀表盤,展示關鍵指標(如錯誤率、請求延遲等)。

4、技術選型

  • 日志采集:Filebeat 或 Fluentd。
  • 消息隊列:Kafka(用于緩沖和傳輸日志數據)。
  • 存儲與分析:ClickHouse(高性能 OLAP 數據庫)。
  • 可視化:Grafana 或 Redash。

5、ClickHouse的作用

  • 高效存儲:日志數據量通常非常龐大,ClickHouse的列式存儲和高壓縮比顯著降低了存儲成本。
  • 實時分析:支持毫秒級響應的復雜查詢,適合對海量日志進行實時分析。
  • 靈活擴展:支持分布式部署,能夠處理PB級別的日志數據。

6、基本實現步驟

(1)、日志采集

1. 安裝 Filebeat:

bash示例:

sudo apt-get install filebeat
2. 配置 Filebeat:

編輯 filebeat.yml 文件,指定日志文件路徑和 Kafka 輸出:
yaml示例:

  filebeat.inputs:- type: logpaths:- /var/log/nginx/*.log- /var/log/application/*.logoutput.kafka:hosts: ["kafka-broker:9092"]topic: "logs" 

解釋:
Input為采集日志相關配置,如nginx的log日志文件,應用程序的log日志文件,output指定輸出到kafka。

3. 啟動 Filebeat:

bash示例:

sudo service filebeat start

(2)、消息隊列(Kafka)

1. 安裝 Kafka:

bash示例:

wget https://downloads.apache.org/kafka/3.0.0/kafka_2.13-3.0.0.tgz
tar -xzf kafka_2.13-3.0.0.tgz
cd kafka_2.13-3.0.0
2. 啟動 Kafka:

bash示例:

bin/zookeeper-server-start.sh config/zookeeper.properties
bin/kafka-server-start.sh config/server.properties

(3)、數據消費與寫入ClickHouse

1. 創建 ClickHouse 表:

sql示例:

   CREATE TABLE logs (timestamp DateTime,level String,message String,source String) ENGINE = MergeTree()ORDER BY (timestamp);

(4)、可視化

1. 安裝 Grafana:

bash示例:

sudo apt-get install grafana
sudo service grafana-server start
2. 配置 ClickHouse 數據源:

在 Grafana 中添加 ClickHouse 數據源,配置連接信息。

3. 構建儀表盤:

創建圖表展示日志的關鍵指標,如錯誤率、請求延遲等。

7、Spring Boot代碼示例

使用Spring Boot消費Kafka數據并寫入 ClickHouse。

(1)、添加依賴

<dependencies><!-- Spring Boot Starter --><dependency><groupId>org.springframework.boot</groupId><artifactId>spring-boot-starter</artifactId></dependency><!-- Kafka --><dependency><groupId>org.springframework.kafka</groupId><artifactId>spring-kafka</artifactId></dependency><!-- ClickHouse JDBC --><dependency><groupId>com.clickhouse</groupId><artifactId>clickhouse-jdbc</artifactId><version>0.3.2</version></dependency><!-- Jackson for JSON Parsing --><dependency><groupId>com.fasterxml.jackson.core</groupId><artifactId>jackson-databind</artifactId></dependency>
</dependencies>

(2)、配置 Kafka 和 ClickHouse

在 application.yml 中配置 Kafka 和 ClickHouse:

spring:kafka:bootstrap-servers: kafka-broker:9092consumer:group-id: clickhouse-groupauto-offset-reset: earliestdatasource:url: jdbc:clickhouse://clickhouse-server:8123/defaultdriver-class-name: com.clickhouse.jdbc.ClickHouseDriverusername: defaultpassword: 

(3)、Kafka 消費者

import org.springframework.kafka.annotation.KafkaListener;
import org.springframework.stereotype.Service;@Service
public class LogConsumer {private final LogRepository logRepository;public LogConsumer(LogRepository logRepository) {this.logRepository = logRepository;}@KafkaListener(topics = "logs", groupId = "clickhouse-group")public void consume(String message) {// 解析日志消息Log log = parseLog(message);// 寫入 ClickHouselogRepository.save(log);}private Log parseLog(String message) {// 假設日志是 JSON 格式ObjectMapper objectMapper = new ObjectMapper();try {return objectMapper.readValue(message, Log.class);} catch (Exception e) {throw new RuntimeException("Failed to parse log message", e);}}
}

(4)、ClickHouse 數據訪問層

創建Repository類。

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.stereotype.Repository;@Repository
public class LogRepository {private final JdbcTemplate jdbcTemplate;@Autowiredpublic LogRepository(JdbcTemplate jdbcTemplate) {this.jdbcTemplate = jdbcTemplate;}public void save(Log log) {String sql = "INSERT INTO logs (timestamp, level, message, source) VALUES (?, ?, ?, ?)";jdbcTemplate.update(sql, log.getTimestamp(), log.getLevel(), log.getMessage(), log.getSource());}
}

(5)、日志實體類

import java.time.LocalDateTime;public class Log {private LocalDateTime timestamp;private String level;private String message;private String source;// Getters and Setters
}

(6)、 Service 層(LogService.java)

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.stereotype.Service;
import java.util.List;
import java.util.Map;@Service
public class LogService {@Autowiredprivate JdbcTemplate jdbcTemplate;// 查詢最近5分鐘的錯誤率public List<Map<String, Object>> getErrorRate() {String sql = "SELECT program, error_count * 100.0 / total_requests AS error_percent " +"FROM log_errors_mv " +"WHERE minute >= now() - interval 5 minute " +"GROUP BY program";return jdbcTemplate.queryForList(sql);}// 查詢指定時間段的響應時間分布public List<Map<String, Object>> getResponseTimeStats(String startTime, String endTime) {String sql = "SELECT percentileState(upstream_response_time, 0.95) AS p95 " +"FROM log_main " +"WHERE timestamp BETWEEN ? AND ?";return jdbcTemplate.queryForList(sql, startTime, endTime);}
}

(7)、Controller 層(LogController.java)

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.bind.annotation.RestController;
import java.util.List;
import java.util.Map;@RestController
public class LogController {@Autowiredprivate LogService logService;@GetMapping("/error-rate")public List<Map<String, Object>> getErrorRate() {return logService.getErrorRate();}@GetMapping("/response-time")public List<Map<String, Object>> getResponseTime(@RequestParam String startTime,@RequestParam String endTime) {return logService.getResponseTimeStats(startTime, endTime);}
}

8、關鍵優化與注意事項

以上僅為簡單的示例,實際生產中每一步都會比較復雜,需要結合實際需求在做詳細的數據庫設計以及接口設計等。這里我們主要是理解做的思路。

(1)、表設計優化

  • 分區策略:按 toYYYYMMDD(timestamp) 分區,便于按天清理舊數據。
  • 物化視圖:預聚合高頻查詢指標(如錯誤率、響應時間),避免重復計算。
  • 索引與排序:在 program 和 timestamp 字段上建立索引,加速過濾查詢。

(2)、ClickHouse 配置優化

  • 資源分配:增大 max_threads 和 max_memory_usage,提升并發處理能力。
  • 日志壓縮:使用 gzip 或 lz4 壓縮日志數據,減少存儲開銷。

(3)、Spring Boot 性能調優

  • 連接池配置:使用 HikariCP 管理數據庫連接(通過 spring.datasource.hikari.* 配置)。
  • 緩存機制:對高頻查詢結果使用 Redis 緩存(如錯誤率統計)。

逆風成長,Dare To Be!!!

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/news/902134.shtml
繁體地址,請注明出處:http://hk.pswp.cn/news/902134.shtml
英文地址,請注明出處:http://en.pswp.cn/news/902134.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

多道程序和多任務操作系統區別

多道程序 vs. 多道任務&#xff1a;對比分析 ? 共同點 方面共同特征核心機制都依賴于進程/任務切換執行需求實現多個程序或任務"并發"執行系統支持都需要操作系統的支持&#xff08;如調度算法、內存管理&#xff09;本質目標提高資源利用率&#xff08;CPU不空轉…

齊次坐標變換+Unity矩陣變換

矩陣變換 變換&#xff08;transform)&#xff1a;指的是我們把一些數據&#xff0c;如點&#xff0c;方向向量甚至是顏色&#xff0c;通過某種方式&#xff08;矩陣運算&#xff09;&#xff0c;進行轉換的過程。 變換類型 線性變換&#xff1a;保留矢量加和標量乘的計算 f(x)…

閑來無事,用HTML+CSS+JS打造一個84鍵機械鍵盤模擬器

今天閑來無聊&#xff0c;突發奇想要用前端技術模擬一個機械鍵盤。說干就干&#xff0c;花了點時間搞出來了這么一個有模有樣的84鍵機械鍵盤模擬器。來看看效果吧&#xff01; 升級版的模擬器 屏幕錄制 2025-04-18 155308 是不是挺像那么回事的&#xff1f;哈哈&#xff01; 它…

智慧城市:如同為城市裝上智能大腦,開啟智慧生活

智慧城市的概念隨著信息技術的飛速發展而逐漸興起&#xff0c;它通過集成物聯網、大數據、人工智能和數字孿生等先進技術&#xff0c;為城市管理和居民生活帶來了前所未有的智能化變革。本文將深入探討這些核心技術及其在智慧城市的典型應用場景&#xff0c;展示智慧城市如何提…

科技快訊 | 智譜開源最新GLM模型系列;“AI 洗頭店”現身廣州;ChatGPT上線圖庫功能

智譜開源最新GLM模型系列&#xff0c;啟用全球域名“Z.ai” 4月15日&#xff0c;智譜開源最新GLM模型系列&#xff0c;包括32B和9B尺寸&#xff0c;涵蓋基座、推理、沉思三類模型&#xff0c;全部遵循MIT開源許可協議。推理模型GLM-Z1-32B-0414實測推理速度達200 tokens/秒&…

第32講:衛星遙感與深度學習融合 —— 讓地球“讀懂”算法的語言

目錄 ?? 一、講講“遙感+深度學習”到底是干啥的? ? 能解決什么問題? ?? 二、基礎原理串講:深度學習如何“看懂”遙感圖? ?? 遙感圖像數據類型: ?? CNN的基本思路: ?? 三、實戰案例:用CNN對遙感圖像做地類分類 ?? 所需R包: ??? 步驟一:構建訓…

【多線程5】面試常考鎖知識點

文章目錄 悲觀/樂觀鎖掛起等待鎖/自旋鎖偏向鎖輕量級/重量級鎖鎖升級CASCAS引發的ABA問題解決方案 原子類 公平/不公平鎖可重入鎖ReentrantLock讀寫鎖 Callable接口 這里的“悲觀”“樂觀”“掛起等待”“自旋”“輕量級”“重量級”“公平”“非公平”“可重入”僅代表某個鎖的…

第三屆世界科學智能大賽新能源賽道:新能源發電功率預測-數據處理心得體會1

看懂數據 比賽數據說明&#xff1a; 文檔&#xff08;報名之后可以下載&#xff09;大小操作初賽測試集.zip94MB下載初賽訓練集.zip632MB下載output.zip145KB下載 任務和主題 AI新能源功率預報&#xff1a;根據歷史發電功率數據和對應時段多類別氣象預測數據&#xff0c;實…

【云馨AI-大模型】2025年4月第三周AI領域全景觀察:硬件革命、生態博弈與國產化突圍

一、硬件算力突破點燃多智能體時代 谷歌在4月12日Cloud Next大會發布第七代TPU Ironwood&#xff0c;單芯片算力達4614 TFLOPs&#xff0c;較前代內存提升6倍&#xff0c;專為AI推理場景優化。配合發布的Gemini 2.5 Flash模型通過"思考"功能實現成本優化&#xff0c…

第3章 垃圾收集器與內存分配策略《深入理解Java虛擬機:JVM高級特性與最佳實踐(第3版)》

第3章 垃圾收集器與內存分配策略 3.2 對象已死 Java世界中的所有對象實例&#xff0c;垃圾收集器進行回收前就是確定對象哪些是活著的&#xff0c;哪些已經死去。 3.2.1 引用計數算法 常見的回答是&#xff1a;給對象中添加一個引用計數器&#xff0c;有地方引用&#xff0…

超詳細VMware虛擬機擴容磁盤容量-無坑版

1.環境&#xff1a; 虛擬機&#xff1a;VMware Workstation 17 Pro-17.5.2 Linux系統&#xff1a;Ubuntu 22.04 LTS 2.硬盤容量 虛擬機當前硬盤容量180G -> 擴展至 300G 3.操作步驟 &#xff08;1&#xff09;在虛擬機關機的狀態下&#xff0c;虛擬機硬盤擴容之前必…

HarmonyOS:1.4 - HarmonyOS應用程序框架基礎

判斷題 1.在基于Stage模型開發的應用項目中都存在一個app.json5配置文件、以及一個或多個module.json5配置文件。 正確(True) 2.一個應用只可以包含一個UIAbility組件。 錯誤(False) 3.Background狀態在UIAbility實例銷毀時觸發。可以在onDestroy()回調中進行系統資源的釋…

HTTP HTTPS RSA

推薦閱讀 小林coding HTTP篇 文章目錄 HTTP 80HTTP 響應碼1xx&#xff1a;信息性狀態碼&#xff08;Informational&#xff09;2xx&#xff1a;成功狀態碼&#xff08;Success&#xff09;3xx&#xff1a;重定向狀態碼&#xff08;Redirection&#xff09;4xx&#xff1a;客戶端…

ORACLE數據庫轉國產阿里OceanBase數據庫

1.BLOB類型修改 將接口內oracle.sql.BLOB改為java.sql.Blob 2.REGEXP_LIKE 判斷函數正則表達式中字符轉義問題 OB的正則表達式使用的是標準的Linux模式,oracle是黑盒子,在處理部分轉義符([])的時候, Oracle無需使用轉義符,OB務必使用轉義符,加/轉義處理,例如在regexp_like(t…

STM32的三種啟動方式

目錄 一、從主閃存存儲器啟動&#xff08;Main Flash Memory&#xff09; 二、從系統存儲器啟動&#xff08;System Memory&#xff09; 三、從內置SRAM啟動&#xff08;Embedded SRAM&#xff09; 一、從主閃存存儲器啟動&#xff08;Main Flash Memory&#xff09; >&g…

Flutter使用flutter_driver進行自動化測試

Flutter自動化測試實踐指南 作為一名iOS開發者&#xff0c;我最近對Flutter的自動化測試產生了濃厚興趣。在開發過程中&#xff0c;我發現自動化測試對于保證應用質量至關重要&#xff0c;特別是像我們這樣的創業團隊&#xff0c;測試資源有限的情況下。 搭建Flutter自動化測…

Halcon應用:九點標定-手眼標定

提示&#xff1a;若沒有查找的算子&#xff0c;可以評論區留言&#xff0c;會盡快更新 Halcon應用&#xff1a;九點標定-手眼標定 前言一、Halcon應用&#xff1f;二、應用實戰1、圖形理解[eye-to-hand]&#xff1a;1.1、開始應用2、 圖形理解[eye-in-hand]2.1、 開始應用 前言…

【C++11】列表初始化、右值引用、完美轉發、lambda表達式

&#x1f4da; 博主的專欄 &#x1f427; Linux | &#x1f5a5;? C | &#x1f4ca; 數據結構 | &#x1f4a1;C 算法 | &#x1f310; C 語言 上篇文章&#xff1a;unordered_map、unordered_set底層編寫 下篇文章&#xff1a;C11&#xff1a;新的類功能、模板的可…

Pandas取代Excel?

有人在知乎上提問&#xff1a;為什么大公司不用pandas取代excel&#xff1f; 而且列出了幾個理由&#xff1a;Pandas功能比Excel強大&#xff0c;運行速度更快&#xff0c;Excel除了簡單和可視化界面外&#xff0c;沒有其他更多的優勢。 有個可怕的現實是&#xff0c;對比Exce…

Vue 3 中將 ref 創建的響應式對象數據轉換為普通(非響應式)的數據

Vue 3 中使用 ref 創建的響應式對象數據轉換為普通&#xff08;非響應式&#xff09;的數據&#xff0c;有以下幾種方法&#xff1a; 1. 訪問 .value 屬性: 這是最直接、最常見的方法。 由于 ref 對象的值存儲在其 .value 屬性中&#xff0c;直接訪問該屬性即可獲得普通數據。…