时序数据库 InfluxDB
目錄
一、介紹
二、安裝
三、inflxudb保留字
四、基本語法
1、客戶端操作
1. 數(shù)據(jù)庫操作
2. 數(shù)據(jù)表和數(shù)據(jù)操作
3. series 操作
4.Shard?
5. 用戶操作
2、API操作
狀態(tài)碼
3、Java操作
五、常用函數(shù)?
六、存儲策略
1.查看策略
2.創(chuàng)建策略
3、修改策略
4. 刪除
七、目錄與文件結(jié)構(gòu)
八、數(shù)據(jù)備份
1、備份和恢復(fù)DB數(shù)據(jù)
一、DB備份
二、DB恢復(fù)
二、備份和恢復(fù)元數(shù)據(jù)
1、備份元數(shù)據(jù)
2、恢復(fù)元數(shù)據(jù)
一、介紹
???????InfluxDB 是一個時間序列數(shù)據(jù)庫,GO 編寫的,旨在處理高寫入和查詢負(fù)載。InfluxDB 旨在用作涉及大量時間戳數(shù)據(jù)的任何用例的后備存儲,包括 DevOps 監(jiān)控、應(yīng)用程序指標(biāo)、物聯(lián)網(wǎng)傳感器數(shù)據(jù)和實時分析。
特點:
- 專門為時間序列數(shù)據(jù)編寫的自定義高性能數(shù)據(jù)存儲。TSM 引擎允許高速攝取和數(shù)據(jù)壓縮
- 完全用 Go 編寫。它編譯成一個沒有外部依賴性的二進(jìn)制文件。
- 簡單、高性能的寫入和查詢 HTTP API。
- 插件支持其他數(shù)據(jù)攝取協(xié)議,例如 Graphite、collectd 和 OpenTSDB。
- 專為輕松查詢聚合數(shù)據(jù)而定制的類似 SQL 的表達(dá)查詢語言。
- 標(biāo)簽允許為系列建立索引以實現(xiàn)快速高效的查詢。
- 保留策略有效地自動使陳舊數(shù)據(jù)過期。
- 連續(xù)查詢自動計算聚合數(shù)據(jù),使頻繁查詢更高效。
InfluxDB有三大特性:?
????Time Series (時間序列):你可以使用與時間有關(guān)的相關(guān)函數(shù)(如最大,最小,求和等)? ? ? ??
?? ?Metrics(度量):你可以實時對大量數(shù)據(jù)進(jìn)行計算?
????Eevents(事件):它支持任意的事件數(shù)據(jù)
InfluxDB 提供三種操作方式:
InfluxDB 和傳統(tǒng)數(shù)據(jù)庫(如:MySQL)區(qū)別:
| database | 數(shù)據(jù)庫 |
| measurement | 數(shù)據(jù)庫中的表 |
| points | 每個表里某個時刻的某個條件下的一個 field 的數(shù)據(jù),因為體現(xiàn)在圖表上就是一個點,于是將其稱為 point。Point 由時間戳(time)、數(shù)據(jù)(field)、標(biāo)簽(tags)組成 |
| series | 序列,所有在數(shù)據(jù)庫中的數(shù)據(jù),都需要通過圖表來展示,而這個 series 表示這個表里面的數(shù)據(jù),可以在圖表上畫成幾條線。具體可以通過?SHOW SERIES FROM "表名"?進(jìn)行查詢 |
| Retention policy | 數(shù)據(jù)保留策略,可以定義數(shù)據(jù)保留的時長,每個數(shù)據(jù)庫可以有多個數(shù)據(jù)保留策略,但只能有一個默認(rèn)策略 |
注意:??point???由3部分組成??time+fields+tags??。
| time | 每行記錄都有一列time,主索引,記錄時間戳,單位納秒,時區(qū)UTC(東八區(qū)減8小時) |
| fields | 普通列,key-value結(jié)構(gòu),value數(shù)據(jù)類型支持型(float、integer、string、boolean) |
| tags | 索引列,key-value結(jié)構(gòu),value數(shù)據(jù)類型只支持string |
說明:
- 在插入新數(shù)據(jù)時,tag、field 和 time之間用空格分隔?。
- fields和tags key名稱嚴(yán)格區(qū)分大小寫。
?fields數(shù)據(jù)類型:
| 類型 | 備注 |
| float | influxdb的fields默認(rèn)是float浮點型 |
| integer | 整型,insert語句如需寫入field是整型,需在數(shù)值后面加個i |
| string | 字符串,insert語句如需寫入field是字符串,需英文雙引號包含數(shù)值 |
| boolean | 布爾型,真可以用 t , T , true , True , TRUE表示;假可以用 f , F , false , False 或者 FALSE表示 |
注意
????????在influxdb中,字段必須存在。因為字段是沒有索引的。如果使用字段作為查詢條件,會掃描符合查詢條件的所有字段值,性能不及tag。tags是可選的,但是強(qiáng)烈建議你用上它,因為tag是有索引的,tags相當(dāng)于SQL中的有索引的列。tag value只能是string類型。
端口
- 8083:Web admin 管理服務(wù)的端口,?http://localhost:8083
- 8086:HTTP API 的端口
- 8088:集群端口 (目前還不是很清楚, 配置在全局的 bind-address,默認(rèn)不配置就是開啟的)
二、安裝
docker pull influxdb:1.8.3 docker run -d -p 18083:8083 -p 18088:8088 -p 18086:8086 --name my_influxdb influxdb:1.8.3 docker container update --restart=always my_influxdb可視化工具:
1、web界面?
2、influxDB Studio?
客戶端為綠色版,下載解壓打開即可。
下載地址:Releases · CymaticLabs/InfluxDBStudio
案例數(shù)據(jù):
curl https://s3.amazonaws.com/noaa.water-database/NOAA_data.txt -o NOAA_data.txt?
導(dǎo)入數(shù)據(jù):?
influx -import -path=NOAA_data.txt -precision=s -database=NOAA_water_database?
三、inflxudb保留字
?
四、基本語法
docker exec -it my_influxdb ?bash
cd /etc/influxdb/
influx?
1、客戶端操作
1. 數(shù)據(jù)庫操作
# 查看所有數(shù)據(jù)庫
show databases;
# 建庫
create database dbname;
# 刪庫
drop database daname
# 切換使用數(shù)據(jù)庫
use dbname
2. 數(shù)據(jù)表和數(shù)據(jù)操作
查看所有表
show measurements
數(shù)據(jù)中的時間字段默認(rèn)顯示的是一個納秒時間戳,改成可讀格式。時間默認(rèn)是UTC時間
precision rfc3339; # 之后再查詢,時間就是rfc3339標(biāo)準(zhǔn)格式?
# 或可以在連接數(shù)據(jù)庫的時候,直接帶該參數(shù)
influx -precision rfc3339
查看一個measurement中所有的tag key
show tag keys
?查看一個measurement中所有的field key
show field keys
查看一個measurement中所有的保存策略(可以有多個,一個標(biāo)識為default)
?show retention policies;
插入數(shù)據(jù)
????????標(biāo)準(zhǔn)格式,注意在寫數(shù)據(jù)的時候如果不添加時間戳,系統(tǒng)會默認(rèn)添加一個時間。InfluxDB 中沒有顯式的新建表的語句,只能通過 insert 數(shù)據(jù)的方式來建立新表。
insert <measurement>[,<tag-key>=<tag-value>...] <field-key>=<field-value>[,<field2-key>=<field2-value>...] [unix-nano-timestamp]insert 表名,tags fileds;#插入fields,和tags.
insert student,a=1,b=2,c=3 name="sa",age=12,emial="xxx@163.com";
#只插入??fields???,可以沒有??tags
insert student name="sa",age=12,emial="xxx@163.com";
刪表
drop measurement student
?查詢?
SELECT field keys [time | tag kyes | * ] FROM measurements WHERE conditions GROUP BY [tag keys | time] ORDER BY time [asc | desc] LIMIT number [OFFSET number]
正則?
#每個表輸出一行(支持 Go 語言的正則表達(dá)式、支持類似于 MySQL 中的 limit 語句)
SELECT * FROM /.*/ LIMIT 1
limit
limit???可單獨使用,也可配合??offset???使用,??offset??偏移量的意思
select * from student limit 2;
排序
?order by??? 只能對??time???進(jìn)行排序,??asc???升序,??desc??降序。
select * from student ?order by time desc;
分組
SELECT <function>(<field_key>) FROM_clause WHERE <time_range> GROUP BY time(time_interval,[<offset_interval])[,tag_key] [fill(<fill_option>)]?
(1)group by tag
select * from h2o_pH group by location limit 2
(2)group by time(1m)?
????????對??time???分組時并不是簡單的??group by time???,??time???后面還需要加一個分組聚合的持續(xù)時間,如??group by time(1m)??。支持的持續(xù)時間單位有:
(3)fill(0)填充null
????????可以看到??values???結(jié)果集中有??null???的情況,可在查詢語句中加??fill(0)???,遇到??null???用??0???來填充。??fill()??中只能填數(shù)字。
條件查詢
select * from student where a='1' and age=12; # a字段是tag :字符串
select sum(age) as ageNums from student where time < now() group by a order by time desc;
格式化顯示查詢數(shù)據(jù)
format json
select * from student where a='1' and age=12;
模糊查詢(正則表達(dá)式)
# location名稱中包含coyote的數(shù)據(jù)
select * from h2o_quality where location=~/.*coyote.*/ limit 10
沒有in還有or
select * from h2o_pH where location='coyote_creek' or location='santa_monica' limit 4
from多表查詢?
????????多表查詢,以時間進(jìn)行連接,不存在的值用null填充。一般情況連接的兩張表tag和field上有一定的聯(lián)系和比較,毫不相干的兩表連接查詢沒什么價值。
select * from h2o_feet,h2o_pH limit 1
注意:
1.field tag是關(guān)鍵字 如果字段名是這兩個,則需要加上單引號。
2.tags???之間用逗號分隔,??fields??之間用逗號分隔,???tags??和??fields??之間用空格分隔?。
3.tags???都是字符串類型,但是不用雙引號括起來;??fields??中有字符串類型需要用?英文雙引號?括起來,如果不用英文雙引號,會報語法錯誤??invalid boolean??,會認(rèn)為是無效的布爾值,因為布爾類型無需加雙引號。
4.tags???中設(shè)置布爾值就是字符串,??fields???中有布爾值,可用 ??t , T , true , True , TRUE,f , F , false , False??表示。
3. series 操作
????????series 相當(dāng)于是 InfluxDB 中一些數(shù)據(jù)的集合,在同一個 database 中,retention policy、measurement、tag sets 完全相同的數(shù)據(jù)同屬于一個 series,同一個 series 的數(shù)據(jù)在物理上會按照時間順序排列存儲在一起。
??shard???主要由4部分組成??Cache???、??Wal???、??Tsm file???、??Compactor??。
#series 表示這個表里面的數(shù)據(jù),可以在圖表上畫成幾條線,series 主要通過 tags 排列組合算出來。
show series from student;
4.Shard?
????????shard 在 InfluxDB 中是一個比較重要的概念,它和 retention policy 相關(guān)聯(lián)。每一個存儲策略下會存在許多 shard,每一個 shard 存儲一個指定時間段內(nèi)的數(shù)據(jù),并且不重復(fù),例如 7點-8點 的數(shù)據(jù)落入 shard0 中,8點-9點的數(shù)據(jù)則落入 shard1 中。每一個 shard 都對應(yīng)一個底層的 tsm 存儲引擎,有獨立的 cache、wal、tsm file。
????????如果創(chuàng)建一個新的 retention policy 設(shè)置數(shù)據(jù)的保留時間為 1 天,則單個 shard 所存儲數(shù)據(jù)的時間間隔為 1 小時,超過1個小時的數(shù)據(jù)會被存放到下一個 shard 中。
5. 用戶操作
# 顯示用戶
SHOW USERS
# 創(chuàng)建用戶
CREATE USER "username" WITH PASSWORD 'password'
# 創(chuàng)建管理員權(quán)限的用戶?
#influxdb 的權(quán)限設(shè)置比較簡單,只有讀、寫、ALL 幾種。
CREATE USER "username" WITH PASSWORD 'password' WITH ALL PRIVILEGES
# 刪除用戶
DROP USER "username"
2、API操作
狀態(tài)碼
- 2xx:服務(wù)請求正常
- 4xx:代表請求語法有問題
- 5xx:服務(wù)端出問題,導(dǎo)致超時等故障
官方地址
3、Java操作
<dependency><groupId>org.influxdb</groupId><artifactId>influxdb-java</artifactId><version>2.23</version> </dependency> spring:application:name: spring-lean-influxdbinflux:url: http://192.168.56.22:18086user:password:database: test import lombok.Data; import org.springframework.beans.factory.annotation.Value; import org.springframework.context.annotation.Configuration; @Data @Configuration public class InfluxDBConfig {@Value("${spring.influx.user}")public String userName;@Value("${spring.influx.password}")public String password;@Value("${spring.influx.url}")public String url;//數(shù)據(jù)庫@Value("${spring.influx.database}")public String database; } import lombok.Builder; import lombok.Data; import org.influxdb.annotation.Column; import org.influxdb.annotation.Measurement; import org.influxdb.annotation.TimeColumn;import java.util.Date;@Builder @Data @Measurement(name = "t_log") public class LogInfo {// Column中的name為measurement中的列名// 此外,需要注意InfluxDB中時間戳均是以UTC時保存,在保存以及提取過程中需要注意時區(qū)轉(zhuǎn)換@Column(name = "time")private String time;// 注解中添加tag = true,表示當(dāng)前字段內(nèi)容為tag內(nèi)容@Column(name = "module", tag = true)private String module;@Column(name = "level", tag = true)private String level;@Column(name = "device_id", tag = true)private String deviceId;@Column(name = "msg")private String msg;@TimeColumnprivate Date createTime; } import com.lean.influxdb.config.InfluxDBConfig; import org.influxdb.InfluxDB; import org.influxdb.InfluxDBFactory; import org.influxdb.dto.BatchPoints; import org.influxdb.dto.Point; import org.influxdb.dto.Query; import org.influxdb.dto.QueryResult; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import org.springframework.util.StringUtils;import javax.annotation.PostConstruct; import java.util.ArrayList; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.concurrent.TimeUnit;@Service public class InfluxDBService {@Autowiredprivate InfluxDBConfig influxDBConfig;@PostConstructpublic void initInfluxDb() {this.retentionPolicy = retentionPolicy == null || "".equals(retentionPolicy) ? "autogen" : retentionPolicy;this.influxDB = influxDbBuild();}//保留策略private String retentionPolicy;private InfluxDB influxDB;/*** 連接時序數(shù)據(jù)庫;獲得InfluxDB**/private InfluxDB influxDbBuild() {if (influxDB == null) {if(StringUtils.isEmpty(influxDBConfig.userName)){influxDB = InfluxDBFactory.connect(influxDBConfig.url);}else {influxDB = InfluxDBFactory.connect(influxDBConfig.url, influxDBConfig.userName, influxDBConfig.password);}influxDB.setDatabase(influxDBConfig.database);}return influxDB;}/*** 插入*/public void insertPoint(Point point) {influxDbBuild();influxDB.write(point);}/*** 插入** @param measurement 表* @param tags 標(biāo)簽* @param fields 字段*/public void insert(String measurement, Map<String, String> tags, Map<String, Object> fields) {influxDbBuild();Point.Builder builder = Point.measurement(measurement);builder.time(System.currentTimeMillis(), TimeUnit.MILLISECONDS);builder.tag(tags);builder.fields(fields);influxDB.write(influxDBConfig.database, "", builder.build());}/*** @param measurement* @param time* @param tags* @param fields* @return void* @desc 插入, 帶時間time*/public void insert(String measurement, long time, Map<String, String> tags, Map<String, Object> fields) {influxDbBuild();Point.Builder builder = Point.measurement(measurement);builder.time(time, TimeUnit.MILLISECONDS);builder.tag(tags);builder.fields(fields);influxDB.write(influxDBConfig.database, "", builder.build());}/*** 查詢** @param command 查詢語句* @return*/public QueryResult query(String command) {influxDbBuild();return influxDB.query(new Query(command, influxDBConfig.database));}/*** @param queryResult* @desc 查詢結(jié)果處理*/public List<Map<String, Object>> queryResultProcess(QueryResult queryResult) {List<Map<String, Object>> mapList = new ArrayList<>();List<QueryResult.Result> resultList = queryResult.getResults();//把查詢出的結(jié)果集轉(zhuǎn)換成對應(yīng)的實體對象,聚合成listfor (QueryResult.Result query : resultList) {List<QueryResult.Series> seriesList = query.getSeries();if (seriesList != null && seriesList.size() != 0) {for (QueryResult.Series series : seriesList) {List<String> columns = series.getColumns();String[] keys = columns.toArray(new String[columns.size()]);List<List<Object>> values = series.getValues();if (values != null && values.size() != 0) {for (List<Object> value : values) {Map<String, Object> map = new HashMap(keys.length);for (int i = 0; i < keys.length; i++) {map.put(keys[i], value.get(i));}mapList.add(map);}}}}}return mapList;}/*** @desc InfluxDB 查詢 count總條數(shù)*/public long countResultProcess(QueryResult queryResult) {long count = 0;List<Map<String, Object>> list = queryResultProcess(queryResult);if (list != null && list.size() != 0) {Map<String, Object> map = list.get(0);double num = (Double) map.get("count");count = new Double(num).longValue();}return count;}/*** 創(chuàng)建數(shù)據(jù)庫* @param dbName 創(chuàng)建數(shù)據(jù)庫* @return*/public void createDB(String dbName) {influxDbBuild();influxDB.createDatabase(dbName);}/*** 批量寫入測點* @param batchPoints*/public void batchInsert(BatchPoints batchPoints) {influxDbBuild();influxDB.write(batchPoints);}/*** 批量寫入數(shù)據(jù)** @param database 數(shù)據(jù)庫* @param retentionPolicy 保存策略* @param consistency 一致性* @param records 要保存的數(shù)據(jù)(調(diào)用BatchPoints.lineProtocol()可得到一條record)*/public void batchInsert(final String database, final String retentionPolicy,final InfluxDB.ConsistencyLevel consistency, final List<String> records) {influxDbBuild();influxDB.write(database, retentionPolicy, consistency, records);}/*** @param consistency* @param records* @desc 批量寫入數(shù)據(jù)*/public void batchInsert(final InfluxDB.ConsistencyLevel consistency, final List<String> records) {influxDbBuild();influxDB.write(influxDBConfig.database, "", consistency, records);}} import com.lean.influxdb.entity.LogInfo; import com.lean.influxdb.service.InfluxDBService; import org.influxdb.dto.Point; import org.influxdb.dto.QueryResult; import org.junit.jupiter.api.Test; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.boot.test.context.SpringBootTest;import java.util.Date; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.concurrent.TimeUnit;@SpringBootTest class SpringLeanInfluxdbApplicationTests {@Testvoid contextLoads() {}@Autowiredprivate InfluxDBService influxDBService;@Testpublic void test() {LogInfo logInfo = LogInfo.builder().level("1").module("log").deviceId("1").msg("消息").createTime(new Date()).build();Point point = Point.measurementByPOJO(logInfo.getClass()).addFieldsFromPOJO(logInfo).time(System.currentTimeMillis(), TimeUnit.MILLISECONDS).build();influxDBService.insertPoint(point);}@Testpublic void test1() {Integer pageSize = 15;Integer pageNum = 1;// InfluxDB支持分頁查詢,因此可以設(shè)置分頁查詢條件String pageQuery = " LIMIT " + pageSize + " OFFSET " + ((pageNum - 1) * pageSize);// 此處查詢所有內(nèi)容,如果String queryCmd = "SELECT * FROM student ORDER BY time DESC " + pageQuery;QueryResult queryResult = influxDBService.query(queryCmd);List<Map<String, Object>> maps = influxDBService.queryResultProcess(queryResult);maps.stream().forEach(s->{s.forEach((k,v)->{System.out.printf("k",k);System.out.printf("v",v);});});List<QueryResult.Result> resultList = queryResult.getResults();System.out.println(resultList);}@Testpublic void testSave() {String measurement = "student";Map<String, String> tags = new HashMap<>();tags.put("code", "1");tags.put("studentNums", "1");Map<String, Object> fields = new HashMap<>();fields.put("name", "張三");fields.put("age", "11");influxDBService.insert(measurement, tags, fields);}@Testpublic void testGetdata() {String command = "select * from student";QueryResult queryResult = influxDBService.query(command);List<Map<String, Object>> result = influxDBService.queryResultProcess(queryResult);for (Map map : result) {System.out.println("time:" + map.get("time")+ " code:" + map.get("code")+ " studentNums:" + map.get("studentNums")+ " name:" + map.get("name")+ " age:" + map.get("age"));}}}五、常用函數(shù)?
| COUNT() | BOTTOM() | CEILING() |
| DISTINCT() | FIRST() | DERIVATIVE() |
| INTEGRAL() | LAST() | DIFFERENCE() |
| MEAN() | MAX() | ELAPSED() |
| MEDIAN() | MIN() | FLOOR() |
| SPREAD() | PERCENTILE() | HISTOGRAM() |
| SUM() | TOP() | MOVING_AVERAGE() |
| NON_NEGATIVE_DERIVATIVE() | ||
| STDDEV() |
更多查看官網(wǎng):地址
六、存儲策略
????????InfluxDB 每秒可以處理成千上萬條數(shù)據(jù),要將這些數(shù)據(jù)全部保存下來會占用大量的存儲空間,有時需要自動清理歷史數(shù)據(jù)。
1.查看策略
?????????一個database可以有多個保留策略??retention policy???,但是只能有一個默認(rèn)??retention policy??。
show retention policies on databaseName
2.創(chuàng)建策略
數(shù)據(jù)庫新建都會分配一個默認(rèn)的保留策略:
- name??,保留策略的名稱。
- ??duration???,數(shù)據(jù)保留的持續(xù)時長,最小為??1h???。如果設(shè)置為0,數(shù)據(jù)永久保存(官方默認(rèn)RP),否則過期清理。它具有各種時間參數(shù),比如:h(小時),w(星期)
- ??shardGroupDuration???,數(shù)據(jù)存儲在??shardGroup???的時間跨度。??shardGroup???是??influxdb???的一個邏輯存儲結(jié)構(gòu),其下包含多個??shard??。
- ??replicaN??,全稱replication,復(fù)制因子,它決定在集群中存儲多少個數(shù)據(jù)副本。inflxudb集群中跨N個數(shù)據(jù)節(jié)點復(fù)制數(shù)據(jù),其中N就是復(fù)制因子。復(fù)制因子對單個節(jié)點實例不起作用,單機(jī)版默認(rèn)是1。
- ??default??,true為默認(rèn)保留策略。
基本語法:
CREATE RETENTION POLICY <retention_policy_name> ON <database_name> DURATION <duration> REPLICATION <n> [SHARD DURATION <duration>] [DEFAULT]
- retention_policy_name??: 策略名。
- ??database_name??: 數(shù)據(jù)庫名(db必須存在)。
- ??duration??: 數(shù)據(jù)保留時長。
- ??REPLICATION??: 復(fù)制因子,單機(jī)版設(shè)置為1即可。
- ??SHARD DURATION???:設(shè)置??shardGroupDuration???時長,表示每個??shard group??時間跨度時長。可不填,默認(rèn)根據(jù)RP的duration計算。
- ??default??: true為設(shè)置該RP為默認(rèn)RP。
CREATE RETENTION POLICY "策略名稱" ON "表名稱" DURATION 30d REPLICATION 1 DEFAULT
3、修改策略
?ALTER RETENTION POLICY "策略名稱" ON "表名稱" DURATION 3w DEFAULT
4. 刪除
DROP RETENTION POLICY "策略名稱" ON "表名稱"
七、目錄與文件結(jié)構(gòu)
InfluxDB 的數(shù)據(jù)存儲主要有三個目錄。默認(rèn)情況下是 meta, wal 以及 data 三個目錄。
?shard:
? ? ? ? ??influxdb???存儲引擎??TSM???的具體實現(xiàn)。??TSM TREE???是專門為??influxdb???構(gòu)建的數(shù)據(jù)存儲格式。與現(xiàn)有的??B+ tree???或??LSM tree???實現(xiàn)相比,??TSM tree??具有更好的壓縮和更高的讀寫吞吐量。主要由4部分組成??Cache???、??Wal???、??Tsm file???、??Compactor??。
shard group:
??????????存儲??shard???的邏輯容器,每一個??shard group???都有一個不重疊的時間跨度,可根據(jù)保留策略??retention policy???的??duration???換算而得。數(shù)據(jù)根據(jù)不同的時間跨度存儲在不同的??shard group??中。
cache :?
????????在內(nèi)存中是一個簡單的 map 結(jié)構(gòu),這里的 key 為 seriesKey + 分隔符 + filedName,目前代碼中的分隔符為 #!~#,entry 相當(dāng)于是一個按照時間排序的存放實際值的數(shù)組。
????????插入數(shù)據(jù)時,實際上是同時往 cache 與 wal 中寫入數(shù)據(jù),可以認(rèn)為 cache 是 wal 文件中的數(shù)據(jù)在內(nèi)存中的緩存。當(dāng) InfluxDB啟動時,會遍歷所有的 wal 文件,重新構(gòu)造 cache,這樣即使系統(tǒng)出現(xiàn)故障,也不會導(dǎo)致數(shù)據(jù)的丟失。
wal:
?????????對數(shù)據(jù)的修改以日志的形式持久化存儲在磁盤上。
????????內(nèi)容與內(nèi)存中的 cache 相同,其作用就是為了持久化數(shù)據(jù),當(dāng)系統(tǒng)崩潰后可以通過 wal 文件恢復(fù)還沒有寫入到 tsm 文件中的數(shù)據(jù)。
????????文件中的一條數(shù)據(jù),對應(yīng)的是一個 key(measument + tags + fieldName) 下的所有 value 數(shù)據(jù),按照時間排序。
tsm file:
????????真實存放數(shù)據(jù)的文件,單個 tsm file 大小最大為 2GB。每隔一段時間,內(nèi)存中的時序數(shù)據(jù)就會執(zhí)行flush操作將數(shù)據(jù)寫入到文件。
compactor:
????????在后臺持續(xù)運行,每隔 1 秒會檢查一次是否有需要壓縮合并的數(shù)據(jù)。主要進(jìn)行兩種操作,一種是 cache 中的數(shù)據(jù)大小達(dá)到閥值后,進(jìn)行快照,之后轉(zhuǎn)存到一個新的 tsm 文件中。另外一種就是合并當(dāng)前的 tsm 文件,將多個小的 tsm 文件合并成一個,使每一個文件盡量達(dá)到單個文件的最大大小,減少文件的數(shù)量,并且一些數(shù)據(jù)的刪除操作也是在這個時候完成。
數(shù)據(jù)存儲
LSM-Tree VS B-Tree
八、數(shù)據(jù)備份
????????兩種備份方式:1.db備份 2.元數(shù)據(jù)備份。元數(shù)據(jù)備份的備份是整個備份,不能拆分,而db數(shù)據(jù)的備份,完整的、增量的(從 RFC3339 格式的時間開始),或者針對特定的分片 ID。
1、備份和恢復(fù)DB數(shù)據(jù)
一、DB備份
基本語法:
通過??influxd backup -h??查看??backup??有哪些可選參數(shù)。
?Usage: influxd backup [options] PATH
-portable: 默認(rèn)
-host <host:port> # 需要備份的influxdb服務(wù)機(jī)器地址,可選,Defaults to 127.0.0.1:8088.
-database <name> # 需要備份的db名稱,可選,若沒有指定,將備份所有數(shù)據(jù)庫
-retention <name> # 備份某個保留策略的數(shù)據(jù),未指定,則備份所有rp的數(shù)據(jù)。
-shard <id> # 需要備份的shard id,可選,若指定了備份shard,必須先選擇rp
-start # 起始時間,日期必須采用 RFC3339格式(例如, 2015-12-24T08:12:23Z). 不能和-since一起使用
-end # 結(jié)束時間,日期必須采用 RFC3339格式(例如, 2015-12-24T08:12:23Z) 不能和-since一起使用
-since # 備份這個timestamp之后的數(shù)據(jù),建議用-start <timestamp>代替
-skip-errors # 可選,當(dāng)備份shards時,跳過備份失敗的shard,繼續(xù)備份其他shard。
influxd backup -database <mydatabase> <path-to-backup>
mydatabase是您要備份的數(shù)據(jù)庫的名稱,以及path-to-backup備份數(shù)據(jù)應(yīng)該存儲的位置。
注意:?Metastore 備份也包含在每個數(shù)據(jù)庫的備份中
案例:
1.備份所有數(shù)據(jù)庫
influxd backup -portable /path/to/backup-directory
2.備份school庫的所有數(shù)據(jù)。
influxd backup -portable -db school ~/tmp/influx_backup/
3.備份school 庫昨天的數(shù)據(jù)。
influxd backup -portable -db school -start 2022-11-14T13:24:52.085243953Z -end 2020-11-15T13:24:52.085243953Z ~/tmp/influx_backup_yesterday/
4.只備份school ???的??shard=2??的數(shù)據(jù)
influxd backup -portable -db school -shard 2 ~/tmp/influx_backup_2/
5.遠(yuǎn)程備份(所有數(shù)據(jù)庫)
influxd backup -portable -host 1192.168.56.11:8088 /path/to/backup-directory
二、DB恢復(fù)
使用該influxd restore實用程序?qū)r間序列數(shù)據(jù)和元數(shù)據(jù)從 InfluxDB 備份還原到 InfluxDB。?
?influxd restore -h??查看restore可選參數(shù):
Usage: influxd restore -portable [options] PATH
Note: Restore using the '-portable' option consumes files in an improved Enterprise-compatible?
? format that includes a file manifest.
Options:
? ? -portable?
? ? ? ? ? ??
? ? -host ?<host:port>
? ? ? ? ? ??
? ? -db ? ?<name>
? ? ? ? ? ? 從備份數(shù)據(jù)的哪個庫恢復(fù)數(shù)據(jù)
? ? -newdb <name>
? ? ? ? ? ? 數(shù)據(jù)恢復(fù)到新庫名稱,若沒有指定,選擇-db <name>的名稱。
?? ??? ??? ?newdb不存在,恢復(fù)時會自動創(chuàng)建
? ? -rp ? ?<name>
? ? ? ? ? ? 從備份數(shù)據(jù)的哪個rp恢復(fù)數(shù)據(jù),指定了-rp,必須指定-db
? ? -newrp <name>
? ? ? ? ? ? 恢復(fù)數(shù)據(jù)新的rp名稱,newrp必須存在。指定了-rp,未指定-newrp則使用-rp
? ? -shard <id>
? ? ? ? ? ? 需要恢復(fù)的shard,如果指定了'-db <db_name>' and '-rp <rp_name>',必須-shard<id>
? ? PATH
? ? ? ? ? ? 備份數(shù)據(jù)文件list?
案例:
1.恢復(fù)??~/tmp/influx_backup/???下??school???庫數(shù)據(jù)到新庫??new_school。
influxd restore -portable ?-db school -newdb new_school ?~/tmp/influx_backup/
?2.恢復(fù)??~/tmp/influx_backup/???下??school???庫,??rp???為??rp_3???數(shù)據(jù)到新庫??new_school1??。
influxd restore -portable ?-db school -rp rp_3 -newdb new_school1 ?~/tmp/influx_backup/
3.恢復(fù)??~/tmp/influx_backup/???下??school???庫,??rp???為??rp_3???,??shard???為2的數(shù)據(jù)到新庫??new_school2???,并重命名??rp???的名稱為??rp_3days??。
influxd restore -portable ?-db school -rp rp_3 -shard 2 ?-newdb new_school2 ? -newrp rp_3days ~/tmp/influx_backup/
注意:
二、備份和恢復(fù)元數(shù)據(jù)
1、備份元數(shù)據(jù)
influxd backup <path-to-backup>
備份元數(shù)據(jù),沒有任何其他參數(shù),備份將只轉(zhuǎn)移當(dāng)前狀態(tài)的系統(tǒng)元數(shù)據(jù)到??path-to-backup???。??path-to-backup??為備份保存的目錄,不存在會自動創(chuàng)建。
influxd backup tmp/mata_backup
?
?
2、恢復(fù)元數(shù)據(jù)
?基本語法:
influxd restore -metadir <path-to-meta-or-data-directory> <path-to-backup>
參考來源:?
influxdb官方英文文檔
influxdb中文文檔
https://segmentfault.com/a/1190000012385313
總結(jié)
以上是生活随笔為你收集整理的时序数据库 InfluxDB的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: #806.宝箱 思维
- 下一篇: Springboot毕设项目基于Spri