日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

OpenTSDB 开发指南之 查询数据

發布時間:2024/8/23 编程问答 45 豆豆
生活随笔 收集整理的這篇文章主要介紹了 OpenTSDB 开发指南之 查询数据 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.

前面博主寫了一篇文章去介紹opentsdb的http接口的使用方法,但是某一些接口的使用還是比較復雜,這篇文章會通過example來詳細講述opentsdb的一些特性。

本文的舉的例子有這些:

  • 基本的寫入和查詢
  • 數據的注釋和說明
  • 子查詢
  • 查詢中的filters使用
  • 查詢數據的rate(增長率)
  • 直方圖中百分位數(percentiles)的查詢
  • Downsampling(下采樣)
  • query/exp 的使用(查詢中使用表達式)
  • trees詳解
  • 一、基本的寫入和查詢

    這個功能是最基本,也是最常用的。
    寫數據:寫入數據post接口為 /api/put?details,details表示會將寫入的詳細結果返回回來:

    ?

    #請求體 [{"metric": "sys.cpu.nice","timestamp": 1346846402,"value": 18,"tags": {"host": "web01","dc": "lga"}} ] #寫入成功返回的內容 {"success": 1,"failed": 0,"errors": [] }

    查數據:寫入成功之后,當然可以去查詢。查詢post接口為 /api/query:

    ?

    #請求體 {"start": 1346846402,"end": 1346846403,#返回數據對應的tsUID"showTSUIDs":"true", "queries": [{"aggregator": "avg","metric": "sys.cpu.nice","tags": {"host": "web01","dc": "lga"}}] } #返回數據 [{"metric": "sys.cpu.nice","tags": {"host": "web01","dc": "lga"},"aggregateTags": [],"tsuids": ["000001000001000001000002000002" #數據對應的tsUID],"dps": {"1346846402": 18}} ]

    這里需要對tsUID進行說明一下,opentsdb是由metric+tags來區分數據的,當metric和tags相同時,其tsUID就會相同,代表著同一系列的數據。那么,假如我們想對這一系列數據進行標注和說明呢?見下一個example。

    二、數據的注釋和說明

    數據的注釋和說明是用到了 /api/annotation 接口,post方式是寫入annotation數據,get是查詢annotation數據。

    ?

    #post接口的請求body {"startTime":"1346846402",#和返回前面一個example返回tsUID相同,這樣時間序列數據就和annotation數據關聯了起來,可作為時間序列數據的注釋和說明"tsuid":"000001000001000001000002000002","description": "Testing Annotations","notes": "These would be details about the event, the description is just a summary","custom": {"owner": "jdoe","dept": "ops"} }

    當寫入成功時間,再次運行查詢example1中的 /api/query 請求,即可得到:

    ?

    [{"metric": "sys.cpu.nice","tags": {"host": "web01","dc": "lga"},"aggregateTags": [],"tsuids": ["000001000001000001000002000002"],"annotations": [{"tsuid": "000001000001000001000002000002","description": "Testing Annotations","notes": "These would be details about the event, the description is just a summary","custom": {"owner": "jdoe","dept": "ops"},"startTime": 1346846402,"endTime": 0}],"dps": {"1346846402": 18}} ]

    可見,此次在返回數據的清楚上,把相關聯的注釋(annotation數據)也一起返回回來,注釋一般可以用來解釋和說明數據。

    三、子查詢

    在 /api/query 接口中,body中有一個參數是queries,它表示可以含有多個子查詢,所謂子查詢就是只要數據滿足其中的一個子查詢,數據就會返回回來。注意每次查詢至少需要一個子查詢。

    在example1中寫入一條數據的前提下,這里再向tsdb中寫入一條數據:

    ?

    [{"metric": "sys.cpu.nice","timestamp": 1346846402,"value": 9,"tags": {"host": "web02","dc": "lga"}} ] # 通過 /api/query 接口我們可以查得該條數據的tsUID為000001000001000003000002000002

    下面查詢body就表示有兩個子查詢:

    ?

    //請求體 {"start": 1346846401,"end": 1346846403,"showTSUIDs":"true","queries": [{ //第一個子查詢,查詢的是example1中寫入的數據"aggregator": "avg","metric": "sys.cpu.nice","tags": {"host": "web01","dc": "lga"}},{ //第二個子查詢,查詢的是剛剛寫入的數據"aggregator": "avg","tsuids":["000001000001000003000002000002"]}] }//返回結果 [{ //第一個子查詢對應的數據"metric": "sys.cpu.nice","tags": {"host": "web01","dc": "lga"},"aggregateTags": [],"tsuids": ["000001000001000001000002000002"],"annotations": [{"tsuid": "000001000001000001000002000002","description": "Testing Annotations","notes": "These would be details about the event, the description is just a summary","custom": {"owner": "jdoe","dept": "ops"},"startTime": 1346846402,"endTime": 0}],"dps": {"1346846402": 18}},{ //第二個子查詢對應的數據"metric": "sys.cpu.nice","tags": {"host": "web02","dc": "lga"},"aggregateTags": [],"tsuids": ["000001000001000003000002000002"],"dps": {"1346846402": 9}} ]

    在平常使用過程中我們可以使用單個或者多個子查詢,還有需要注意對于每個子查詢而言,主要有兩種類型:

  • metric查詢方式:子查詢指定metric和tags(optional)進行查詢,本次查詢中的第一個子查詢就是采用這種方式。
  • TSUID查詢方式:需要給出一個或者多個tsuid,對應本次查詢中的第二個子查詢。
  • 四、查詢中的filters使用

    從opentsdb2.2版本便支持filter,它其實是用于過濾tags的,可以作為tags查詢的替代者,并且比tags更加靈活。請求body如下:

    ?

    {"start": 1346846401,"end": 1346846403,"showTSUIDs":"true","queries": [ {"aggregator": "avg","metric": "sys.cpu.nice","filters": [{ "type":"literal_or", "tagk":"host","filter":"web01|web02","groupBy":true}]}] } 參數意義
    type過濾器的類型,可以訪問 /api/config/filters 接口查看支持的所有類型,這里 literal_or 表示value是一個枚舉
    tagk指定過濾的key
    filter和相type對應,這里表示對web01和web02都進行匹配
    groupBy是否對匹配到的數據進行分組

    這里使用literal_or,filter里面的多個tagV以豎線相隔,這個過濾器的意思是對tagK為host進行匹配,并且value為web01和web02都數據都會匹配成功。
    返回結果:

    ?

    [{"metric": "sys.cpu.nice","tags": {"host": "web01","dc": "lga"},"aggregateTags": [],"tsuids": ["000001000001000001000002000002"],"annotations": [{"tsuid": "000001000001000001000002000002","description": "Testing Annotations","notes": "These would be details about the event, the description is just a summary","custom": {"owner": "jdoe","dept": "ops"},"startTime": 1346846402,"endTime": 0}],"dps": {"1346846402": 18}},{"metric": "sys.cpu.nice","tags": {"host": "web02","dc": "lga"},"aggregateTags": [],"tsuids": ["000001000001000003000002000002"],"dps": {"1346846402": 9}} ]

    可見本次filter查詢用一個子查詢的結果和example3中用了兩個子查詢的效果是一樣的。

    五、查詢數據的rate(增長率)

    在某些情況下,我們查詢的可能并不是數據的本身,而是它的增長率。恰巧opentsdb有幫我們提供這個功能:子查詢中的rate參數。
    首先我們先寫入3條數據,時間分別間隔兩秒,數據分別為0、64000和1000。

    ?

    [{"metric": "sys.cpu.nice","timestamp": 1346846410,"value": 0,"tags": {"host": "web03","dc": "lga"}},{"metric": "sys.cpu.nice","timestamp": 1346846412,"value": 64000,"tags": {"host": "web03","dc": "lga"}},{"metric": "sys.cpu.nice","timestamp": 1346846414,"value": 1000,"tags": {"host": "web03","dc": "lga"}} ]

    查詢增長率的請求body如下:

    ?

    {"start": 1346846409,"end": 1346846414,"showTSUIDs":"true","queries": [ {"aggregator": "avg","metric": "sys.cpu.nice","rate":true, # 查詢增長率"rateOptions":{"counter":false },"tags": {"host": "web03","dc": "lga"}}] }# 響應結果 [{"metric": "sys.cpu.nice","tags": {"host": "web03","dc": "lga"},"aggregateTags": [],"tsuids": ["000001000001000007000002000002"],"dps": {"1346846412": 32000,"1346846414": -31500}} ]

    3200=(6400-0)/2,-31500=(1000-6400)/2,可見增長率是以秒為單位。

    六、直方圖中百分位數(percentiles)的查詢

    opentsdb在2.4版本對直方圖(histogram進行了支持),本個example中首先寫入直方圖數據,然后根據數據對百分位數(percentile)進行查詢。
    寫入數據的body如下:buckets是直方圖數據,意思為0到1.75區間的數值為12,1.75到3.5區間的數值為16.

    ?

    {"metric": "sys.cpu.nice","timestamp": 1356998400,"overflow": 1,"underflow": 0,"buckets": { "0,1.75": 12,"1.75,3.5": 16},"tags": {"host": "web01","dc": "lga"} }

    關于百分位的定義可以自行查資料進行詳細認識,本次查詢中percentiles列表里面就是需要查詢的百分位,需要注意的是列表里面的數字的取值區間是[0,100],并且可以不按照順序排列。查詢body如下:

    ?

    {"start": 1356998400,"end": 1356998401,"showTSUIDs":"true","queries": [ {"aggregator": "sum","percentiles": [100,99,43,42,1],"metric": "sys.cpu.nice","tags": {"host": "web01","dc": "lga"}}] }

    請求的結果如下:

    ?

    [{"metric": "sys.cpu.nice_pct_1.0","tags": {"host": "web01","dc": "lga"},"aggregateTags": [],"tsuids": ["000001000001000001000002000002"],"dps": {"1356998400": 0.875}},{"metric": "sys.cpu.nice_pct_42.0",···"dps": {"1356998400": 0.875}},{"metric": "sys.cpu.nice_pct_43.0",···"dps": {"1356998400": 2.625}},{"metric": "sys.cpu.nice_pct_99.0",···"dps": {"1356998400": 2.625}},{"metric": "sys.cpu.nice_pct_100.0",···"dps": {"1356998400": 2.625}} ]

    返回內容如上:其中相同部分已經省略,返回的metric由 原始metric_pct_number 組成,下面講述它們的計算方式:
    第一個區間的數值為12,第二個區間的數值為16,12/(12+16)=0.428。

    • 我們看到1和42的百分位的取值都是0.875,0.875=1.75/2,取的第一個區間的中點坐標,可以得到在0.428之前的百分位的數值都為0.875。
    • 43、99、100百分位對應的數值都為2.625,2.625=1.75+(3.5-1.75)/2,2.625的物理意義就是第二個區間中點的橫坐標,因此43到100之間的百分位取值都為2.525。

    七、Downsampling(下采樣)

    下采樣即讓濃密數據變稀疏的過程,首先寫入10條數據,數值分別為0到9,相鄰數據的時間間隔為1s:

    ?

    [{"timestamp": 1562068000,"value": 0,"metric": "sys.cpu.nice","tags": {"host": "web01","dc": "lga"}},······{"metric": "sys.cpu.nice","timestamp": 1562068009,"value": 9,"tags": {"host": "web01","dc": "lga"}} ]

    下采樣查詢如下,downsample字段是一個字符串,該字段由 interval-aggregate-fill policy 組成,分別表示時間間隔、聚合方法、缺少的值補齊的方法。本次查詢下采樣間隔為2s,聚合方法是取聚合區間的最小值,并且缺少的值用0補齊:

    ?

    {"start": 1562068000,"end": 1562068009,"queries": [ {"aggregator": "avg","metric": "sys.cpu.nice","downsample":"2s-min-zero","tags": {"host": "web01","dc": "lga"}}] }

    返回結果如下,可見原本每秒一個數據在結果中是每兩秒返回一個數據,并且在每個間隔中,都是取的最小值。

    ?

    [{"metric": "sys.cpu.nice","tags": {"host": "web01","dc": "lga"},"aggregateTags": [],"dps": {"1562068000": 0,"1562068002": 2,"1562068004": 4,"1562068006": 6,"1562068008": 8}} ]

    八、query/exp 的使用(查詢中使用表達式)

    這個接口允許使用表達式進行查詢,可以對查詢的多個結果進行操作。
    在example7寫入數據的基礎上,再寫入如下數據,相比example7的數據而言僅僅是metric發生了變化:

    ?

    [{"timestamp": 1562068000,"value": 0,"metric": "sys.cpu.nice1","tags": {"host": "web01","dc": "lga"}},······{"metric": "sys.cpu.nice1","timestamp": 1562068009,"value": 9,"tags": {"host": "web01","dc": "lga"}} ]

    緊接著使用表達式進行查詢,查詢body如下,

    • time 定義了查詢的時間區間和聚合方式
    • filters 定義了一個過濾器f1
    • metric 中指定了對sys.cpu.nice和sys.cpu.nice1兩個metric進行查詢,并且兩個metric都使用同一個filter:f1
    • expressions 中是語法表達式,e就等于結果a加上結果b,e2就等于e乘以2
    • outputs 指定需要輸出的表達式計算結果

    ?

    {"time": {"start": "1562068000","end":"1562068009","aggregator":"sum"},"filters": [{ "tags": [{"type": "wildcard","tagk": "host","filter": "web*","groupBy": true}],"id": "f1"}],"metrics": [{"id": "a","metric": "sys.cpu.nice","filter": "f1","fillPolicy":{"policy":"nan"}},{"id": "b", "metric": "sys.cpu.nice1","filter": "f1","fillPolicy":{"policy":"nan"}}],"expressions": [{"id": "e","expr": "a + b"},{"id":"e2","expr": "e * 2"}],"outputs":[{"id":"e", "alias":"e"},{"id":"e2", "alias":"e2"}]}

    查詢結果如下,query是里面是關于查詢請求body的信息,為了節約空間這里省略。可以得知表達式計算是對同一個時間點進行計算的。

    • outputs中的e,時間點1562068001000對應的值為2,sys.cpu.nice和sys.cpu.nice1在1562068001000對應的數值都為1,便可和表達式中 e=a+b 對應起來。
    • e2中時間點1562068001000對應的值為4,便可和表達式中 e2=ex2 對應起來。

    ?

    {"outputs": [{"id": "e","alias": "e","dps": [ [1562068000000,0],[1562068001000,2],[1562068002000,4],[ 1562068003000, 6],[1562068004000,8],[1562068005000,10],[1562068006000,12],[1562068007000,14],[1562068008000,16],[1562068009000,18] ],"dpsMeta": { "firstTimestamp": 1562068000000,"lastTimestamp": 1562068009000, "setCount": 10,"series": 1},"meta": [{"index":0,"metrics":["timestamp"]},{"index":1,"metrics":["sys.cpu.nice","sys.cpu.nice1"],"commonTags":{"host":"web01","dc":"lga"},"aggregatedTags":[]}]},{"id": "e2","alias": "e2","dps": [[1562068000000,0],[1562068001000,4],[1562068002000,8],[1562068003000,12],[1562068004000,16],[1562068005000,20],[1562068006000,24],[1562068007000,28],[1562068008000,32],[1562068009000,36]],"dpsMeta": { "firstTimestamp": 1562068000000,"lastTimestamp": 1562068009000,"setCount": 10,"series": 1},"meta": [{"index":0,"metrics":["timestamp"]},{"index":1,"metrics":["sys.cpu.nice","sys.cpu.nice1"],"commonTags":{"host":"web01","dc":"lga"},"aggregatedTags":[]}]}],"query": {······} }

    九、trees詳解

    opentsdb2.0版本引入了tree的概念,tree可以將一些時間序列組織起來使其具有層次結構,和文件系統一樣,tree中的葉子類比于文件系統的文件,tree中的branch類比于文件系統的文件夾,還可以繼續在里面創建新的文件夾。其相關定義可參考官網。

    在tsdb中創建一棵樹步驟如下:

  • 首先創建一棵樹,此時數的enable屬性為false。
  • 為這棵樹定義一些規則,數的形狀和數據是由這些規則確定。
  • 可以通過/api/tree/test接口對這棵樹進行測試,看其接口是否滿足要求。
  • 將樹的enable設為true。
  • 運行./tsdb uid treesync掃描TSMeta中的全部對象,將符合條件的時間序列加入到樹中。注意:若需要每創建一個TSMeta對象時,都試圖將對象加入到enable tree中,那么在啟動tsdb時需要加上 tsd.core.tree.enable_processing=true 配置。
  • 現在按照上面的流程進行操作實際一遍,首先對時間序列、數的規則進行說明。

    現在我們有如下的時間序列數據:

    圖1

    這些時間序列需要滿足如下規則(rules),level表示數的第幾層,order表示同一level的不同rule有不同的優先級。level 0 有兩個rule,當滿足order為0的rule時,會跳過order為1的rule;反之order為1的rule就會生效。

    圖2

    基于上面的時間序列和tree的規則,可以得到下面的tree:

    圖3

    下面按照步步驟對這棵樹進行生成:

  • 寫入圖一中的輸入,請求body此處略。
  • 創建一棵樹,post接口為 /api/tree,請求body如下:
  • ?

    {"name":"Network","description":"","notes":"","rules":null,"created":1368964815,"strictMatch":false,"storeFailures":false,"enabled":false}

    創建成功后 可以用 get方式請求 /api/tree 接口查詢tree的相關信息,并可以獲得新創建tree的id,treeId下面也會用到。

  • 利用接口 /api/tree/rule接口,依次創建圖2中的4個rule,請求body分別如下:
  • ?

    {"type":"tagk","field":"dc","description":"a tagk named data center","level":0,"order":0,"treeId":1}{"type":"tagk","field":"host","description":"a tagk named host","regex":".*\\.(.*)\\.mysite\\.com","level":0,"order":1,"treeId":1}{"type":"tagk","field":"host","description":"a tagk named host","separator":"\\.","level":1,"order":0,"treeId":1}{"type":"metric","description":"metric","separator":"\\.","level":2,"order":0,"treeId":1}
  • 利用/api/tree/test 接口測試我們新創建的tree,get請求有兩個參數:
  • 參數名意義
    treeId用于指定測試的tree
    tsuids指定時間序列,試圖將這些時間序列放入這顆樹中進行測試,多個tsuid以 ","相隔

    這里的tsuids當然是指圖1中時間序列對應的tsuid,可以用 /api/query接口進行查詢。
    /api/tree/test會返回這些時間序列基于這棵樹的層次關系,若這個層次結構不滿足需求則需要對rule進行修改,若滿則需求則可進行下一步。

  • 在tsdb的build文件夾運行 ./tsdb uid treesync 命令,它會掃描全部的 tsdb-uid,將符合條件的序列加入到tree的結構中。
  • 至此這棵樹的定義就已經完成,可以用 /api/tree/branch 接口對tree的分支進行查詢,查詢的參數有兩個:

    參數名意義
    treeidtree的id
    branchbranch的id

    兩個參數只需要一個,當傳遞treeid時,就會返回root branch的信息。當只傳遞branch時,就會返回對應branch的信息。當兩個參數都傳遞時,參數treeid就會被忽略。

    ?

    總結

    以上是生活随笔為你收集整理的OpenTSDB 开发指南之 查询数据的全部內容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。