SPL函数

Logstore中的时序数据通过SPL指令处理后,可以调用时序SPL函数进行结果可视化。

函数列表

函数名称

说明

second_to_nano函数

时间转换函数:将秒级时间戳转为纳秒级,适用于高精度场景。

series_forecast函数

时间序列预测函数:基于历史数据预测未来趋势,适用于监控、分析和规划。

series_pattern_anomalies函数

异常检测函数:基于机器学习算法,识别时间序列中的异常点或异常模式,适用于监控、告警和数据分析等场景。

series_decompose_anomalies函数

时间序列分解与异常检测函数:基于时间序列分解算法,将原始数据拆分为趋势、季节性和残差分量,并通过统计方法分析残差分量以识别异常点,适用于实时监控、根因分析及数据质量检测等场景。

series_drilldown函数

用于时间序列分析的下钻函数,允许在时间分组统计的基础上,进一步对特定时间段内的数据进行细粒度分析。

cluster函数

支持对多条时间序列(或向量数据)进行快速分组分析,识别相似形态的指标曲线、检测异常模式或归类数据模式。

second_to_nano函数

时间转换函数,用于将秒级时间戳转换为纳秒级时间戳。它通常用于处理日志中的时间字段,尤其是在需要更高精度时间戳的场景下。

重要
  • 精度:确保数据库和应用程序支持足够的精度,以处理纳秒级别的时间数据。

  • 数据类型:需要选择合适的数据类型来存储纳秒级的数据,比如 BIGINT,以避免溢出或精度丢失。

语法

second_to_nano(seconds)

参数说明

参数

说明

seconds

秒级时间戳(可以是整数或浮点数)。

返回值

返回对应的纳秒级时间戳(以整数形式表示)。

示例

统计不同时间段(纳秒级)不同请求的数量。

  • 查询分析语句

    * | extend ts = second_to_nano(__time__)
    | stats count=count(*) by ts,request_method
  • 输出结果

    image

series_forecast函数

用于时间序列预测。它基于历史时间序列数据,利用机器学习算法对未来的时间点进行预测。该函数常用于监控、趋势分析和容量规划等场景。

使用限制

  • 已经通过make-series构造出series格式数据,并且时间单位为纳秒。

  • 每行的时间点数量至少为31个 。

语法

series_forecast(array(T) field, bigint periods)

series_forecast(array(T) field, bigint periods, varchar params)

参数说明

参数

说明

field

输入时间序列的指标列。

periods

期望预测结果中时间点的数量。

params

可选。算法参数,json 格式。

返回值

row(
  time_series array(bigint),
  metric_series array(double),
  forecast_metric_series array(double),
  forecast_metric_upper_series array(double),
  forecast_metric_lower_series array(double),
  forecast_start_index bigint,
  forecast_length bigint,
  error_msg varchar)

列名

类型

说明

time_series

array(bigint)

纳秒级时间戳数组。包含输入时间段的时间戳和预测时间段的时间戳。

metric_series

array(double)

metric 数组,长度和 time_series 一致。

对原始输入 metric 进行修改(修改 NaN 等)并用 NaN 扩充预测时间段。

forecast_metric_series

array(double)

预测结果数组,长度和 time_series 一致。

包含对输入 metric 的拟合值以及预测时间段的预测值。

forecast_metric_upper_series

array(double)

预测结果上界数组,长度和 time_series 一致。

forecast_metric_lower_series

array(double)

预测结果下界数组,长度和 time_series 一致。

forecast_start_index

bigint

表示时间戳数组中预测时间段的起始下标。

forecast_length

bigint

表示时间戳数组中预测时间段时间点的数量。

error_msg

varchar

错误信息。为 null 则表示该行时间序列预测成功,否则展示失败原因。

示例

统计不同request_method接下来10个时间点的数量。

  • SPL语句

    * | extend ts = second_to_nano(__time__ - __time__ % 60)
      | stats latency_avg = max(cast(status as double)), inflow_avg = min(cast (status as double)) by ts, request_method
      | make-series   latency_avg  default = 'last',
                    inflow_avg default = 'last'
                    on ts 
                    from 'min' to 'max'
                     step '1m' 
                    by request_method
     | extend test=series_forecast(inflow_avg, 10)
  • 输出结果

    image

算法参数

"pred":"10min"

期望预测结果中时间点的间隔, 单位支持

D        daily frequency
H        hourly frequency
T, min   minutely frequency
S        secondly frequency

"uncertainty_config": {"interval_width": 0.9999}

  • uncertainty_config.interval_width 取值范围是 (0, 1),取值越大预测结果中上下界之间的范文越大

"seasonality_config":

{"seasons": [{"name": "month", "period": 30.5, "fourier_order": 1}]}

  • seasonality_config.seasons 中包含自定义的时序周期

    • name 周期名称

    • periods 每一个周期包含多少天

    • fourier_order 周期拟合强度

  • 服务默认设置了天、周和年周期,如果需要拟合其他周期,在 seasonality_config.seasons 中配置

series_pattern_anomalies函数

用于检测时间序列数据中异常模式。它基于机器学习算法,能够自动识别时间序列中的异常点或异常模式,适用于监控、告警和数据分析等场景。

使用限制

  • 已经通过make-series构造出series格式数据,并且时间单位为纳秒。

  • 每行的时间点数量至少为11个 。

语法

series_pattern_anomalies(array(T) metric_series)

参数说明

参数

说明

metric_series

输入时间序列的指标列,仅支持数值类型。

返回值

row(
  anomalies_score_series array(double),
  anomalies_type_series array(varchar)
  error_msg varchar)
) 

列名

类型

说明

anomalies_score_series

array(double)

异常分数序列,与输入时间序列相对应。范围为 [0,1] 代表每个时间点的异常分数。

anomalies_type_series

array(varchar)

异常类型描述序列,与输入时间序列相对应。代表每个时间点的异常类型。非异常的时间点表示为null。

error_msg

varchar

错误信息。值为null则表示该行时间序列异常检测成功,否则展示失败原因。

示例

检测当前时间点的序列是否有异常。

  • SPL语句

    * | extend ts = second_to_nano(__time__ - __time__ % 60)
      | stats latency_avg = max(cast(status as double)), inflow_avg = min(cast (status as double)) by ts, request_method
      | where request_method is not null
      | make-series   latency_avg  default = 'last',
                    inflow_avg default = 'last'
                    on ts 
                    from 'min' to 'max'
                     step '1m' 
                    by request_method
     | extend test=series_pattern_anomalies(inflow_avg)
  • 输出结果

    image

series_decompose_anomalies函数

用于时间序列分解和异常检测的函数。它基于时间序列分解算法,将原始时间序列数据拆分为趋势分量、季节性分量和残差分量,并通过分析残差分量来检测异常点。

使用限制

  • 已经通过make-series构造出series格式数据,并且时间单位为纳秒。

  • 每行的时间点数量至少为11个 。

语法

series_decompose_anomalies(array(T) metric_series)

series_decompose_anomalies(array(T) metric_series, varchar params)

参数说明

参数

说明

metric_series

输入时间序列的指标列。

params

可选。算法参数,json 格式。

返回值

row(
  metric_baseline_series array(double)
  anomalies_score_series array(double),
  anomalies_type_series array(varchar)
  error_msg varchar)
) 

列名

类型

说明

metric_baseline_series

array(double)

算法拟合的 metric 数据。

anomalies_score_series

array(double)

异常分数序列,与输入时间序列相对应。范围为 [0,1] 代表每个时间点的异常分数。

anomalies_type_series

array(varchar)

异常类型描述序列,与输入时间序列相对应。代表每个时间点的异常类型。非异常的时间点表示为 null。

error_msg

varchar

错误信息。值为null则表示该行时间序列异常检测成功,否则展示失败原因。

示例

对所有时间线异常检测之后,保留最近 5 min 异常分数值大于等于0的时间线。

  • SPL语句

    * | extend ts = second_to_nano(__time__ - __time__ % 60)
      | stats latency_avg = max(cast(status as double)), inflow_avg = min(cast (status as double)) by ts, request_method
      | where request_method is not null
      | make-series   latency_avg  default = 'last',
                    inflow_avg default = 'last'
                    on ts 
                    from 'min' to 'max'
                     step '1m' 
                    by request_method
     | extend test=series_decompose_anomalies(inflow_avg, '{"confidence":"0.005"}')
     | extend anomalies_score_series = test.anomalies_score_series
     | where array_max(slice(anomalies_score_series, -5, 5)) >= 0
  • 输出结果

    image

算法参数

参数

类型

示例

描述

auto_period

string

"true"

只能设置 "true" 或 "false"。表示是否开启时序周期自动检测。如果设置为 "true",自定义的 period_num 和 period_unit 不生效。

period_num

string

"[1440]"

序列周期包含多少个时间点。可以输入多个周期长度,目前服务只考虑长度最长的一个周期。

period_unit

string

"[\"min\"]"

序列周期的每个时间点的时间单位。可以输入多个时间单位,时间单位的数量必须和设置的周期的数量相同。

period_config

string

"{\"cpu_util\": {\"auto_period\":\"true\", \"period_num\":\"720\", \"period_unit\":\"min\"}}"

如果需要针对不同的特征设置不同的周期,可以配置 period_config 字段,prediod_config 中的字段名为要设置的特征的名称,字段值为 object,在其中设置 auto_period,period_num,period_unit 三个字段。

trend_sampling_step

string

"8"

时序分解时对于趋势成分的下采样率,需要可以转换成正整数。采样率越大,趋势成分的拟合速度越快,趋势成分的拟合精度会降低。默认为 "1"。

season_sampling_step

string

"1"

时序分解时对于周期成分的下采样率,需要可以转换成正整数。采样率越大,周期成分的拟合速度越快,周期成分的拟合精度降低,默认为 "1"。

batch_size

string

"2880"

异常分析时使用滑动窗口的形式分段处理。batch_size 表示窗口的大小。窗口越小,分析的速度越快,准确度可能会降低。默认窗口的大小与序列的长度一致。

confidence

string

"0.005"

异常分析的敏感度,需要可以转换成浮点数,取值范围是(0,1.0)。数值越小,算法对异常的敏感度越低,检测到的异常数量减少。

confidence_trend

string

"0.005"

在分析趋势项时,对于异常的敏感度。设置该参数后自动忽略 confidence。数值越小,算法对于趋势项的异常的敏感度越低,趋势项检测到的异常数量减少。

confidence_noise

string

"0.005"

在分析残差项时,对于异常的敏感度。设置该参数后自动忽略 confidence。数值越小,算法对于残差项的异常的敏感度越低,残差项检测到的异常数量减少。

series_drilldown函数

用于时间序列分析的下钻函数,允许在时间分组统计的基础上,进一步对特定时间段内的数据进行细粒度分析。

语法

series_drilldown(array(varchar) label_0_array,array(varchar) label_1_array,array(varchar) label_2_array, ... ,array(array(bigint)) time_series_array,array(array(double)) metric_series_array,bigint begin_time,bigint end_time)

series_drilldown(array(varchar) label_0_array,array(varchar) label_1_array,array(varchar) label_2_array, ... ,array(array(bigint)) time_series_array,array(array(double)) metric_series_array,bigint begin_time,bigint end_time,varchar config)

参数说明

参数

说明

label_x_array

数组中每个元素为对应时间序列的label。函数重载最多支持 7 个 label array。

time_series_array

外层数组中每个元素为一个 time series。

metric_sereis_array

外层数组中每个元素为一个 metric series

begin_time

需要进行根因下探的开始时间点,一般设置为异常的开始时间,单位为纳秒。

end_time

需要进行根因下探的结束时间点,一般设置为异常的结束时间,单位为纳秒。

config

可选。算法参数,json 格式。

返回值

row(dirlldown_result varchar, error_msg varchar)

列名

类型

说明

dirlldown_result

varchar

下探的结果,JSON格式。

error_msg

varchar

错误信息。为 null 则表示该行时间序列预测成功,否则展示失败原因。

dirlldown_result参数说明

{
  "attrs": [
    {
      "api": "/ids/ml/annotationdataset",
      "resource": "test"
    },
    {
      "api": "/console/logs/getLogs"
    }
  ],
  "statistics": {
    "relative_ratio": 0.5003007763190033,
    "relative_ratio_predict": 1.0000575873881987,
    "unexpected_difference": -4.998402840764594,
    "relative_unexpected_difference": -0.499660063545782,
    "difference": -4.999183856137503,
    "predict": 5.005203022057271,
    "relative_ratio_real": 1.9987568734256989,
    "real": 10.004386878194774,
    "support": 50
  }
}
attrs参数说明

该参数用于标识该统计结果对应的维度筛选条件。数组中的各个条件为或的关系。

  • 示例中表示api/ids/ml/annotationdataset或者/console/logs/getLogs

      "attrs": [
        {
          "api": "/ids/ml/annotationdataset",
          "resource": "test"
        },
        {
          "api": "/console/logs/getLogs"
        }
      ]
  • attrs中第一个元素表示api/ids/ml/annotationdataset并且resourcetest

        {
          "api": "/ids/ml/annotationdataset",
          "resource": "test"
        }
statistics参数说明

该参数提供时间序列的统计分析结果,用于根因分析或异常检测。

指标名

类型

说明

support

int

在当前根因范围内,统计样本量(如数据点数量)。

real

float

在当前根因范围内,指标的实际观测值。

predict

float

在当前根因范围内,指标的预测值。

difference

float

在当前根因范围内,指标的实际值与预测值的绝对差。计算公式:predict - real。

unexpected_difference

float

在当前根因范围内,指标的预测值和去除正常波动后的真实值(预期内的变化)的差值(非预期内的变化)。

relative_unexpected_difference

float

在当前根因范围内,指标的非预期内的变化与预期内的变化的比值。

relative_ratio

float

在当前根因范围内,指标的实际值与基准值的比例。计算公式:predict/real。

relative_ratio_predict

float

在当前根因范围内,指标的预测值与根因范围外的指标的预测值的比值。

relative_ratio_real

float

在当前根因范围内,指标的真实值与根因范围外的指标的真实值的比值。

示例

  • SPL语句

    *
    | extend ts= (__time__- __time__%60)*1000000000
    | stats access_count = count(1) by ts, Method, ProjectName
    | extend access_count = cast( access_count as double)
    | make-series   access_count = access_count default = 'null'
                    on ts
                    from 'sls_begin_time' to 'sls_end_time'
                    step '1m'
                    by Method, ProjectName
    | stats m_arr = array_agg(Method), ProjectName = array_agg(ProjectName), ts_arr = array_agg(__ts__), metrics_arr = array_agg(access_count)
    | extend ret = series_drilldown(ARRAY['Method', 'Project'], m_arr, ProjectName, ts_arr, metrics_arr, 1739192700000000000, 1739193000000000000, '{"fill_na": "1", "gap_size": "3"}')
    | project ret
  • 输出结果

    image

cluster函数

支持对多条时间序列(或向量数据)进行快速分组分析,识别相似形态的指标曲线、检测异常模式或归类数据模式。

语法

cluster(array(array(double)) array_vector, varchar cluster_mode,varchar params)

参数说明

参数

说明

array_vector

一个二维向量,在二维向量中要确保每行的向量长度一致。

cluster_mode

聚类的模型,目前日志服务提供两种模式:

params

不同的聚类模型对应着不同的算法参数说明。

聚类模型

kmeans
{
  "n_clusters": "5",
  "max_iter": "100",
  "tol": "0.0001",
  "init_mode": "kmeans++"
}

在调整KMeans算法参数时的优化方法和建议,具体针对以下几个关键参数进行了说明:

  1. n_clusters(聚类数量):当前值为5。建议通过肘部法则选择合适的聚类数量,观察总误差平方和(SSE)的变化趋势,并根据实际效果调整为37等其他值。

  2. max_iter(最大迭代次数):当前值为100。对于大规模数据集,可能需要增加迭代次数以确保收敛;若结果提前稳定,则可减少此值以节省计算资源,常用范围为100300。

  3. tol(收敛容忍度):该参数控制算法的收敛条件,定义了簇中心变化幅度的阈值。高精度需求时可将值减小至0.00001,而对于大规模数据可适当放宽至0.001以提高效率,需权衡计算效率与精度。

  4. init_mode(初始模式):当前值为kmeans++,通常能提供较好的初始聚类中心。可根据需求尝试random初始化,但可能需要更多迭代次数。若初始聚类中心对结果影响较大,可探索不同的初始化策略。

dbscan
{
  "epsilon": "0.1", // 注意:当 epsilon 的值 小于等于 0 时,算法会自动的去推断这个参数。
  "min_samples": "5"
}

SPL函数文本介绍了DBSCAN(Density-Based Spatial Clustering of Applications with Noise)算法中的两个关键参数epsilon (ε) 和 min_samples,它们用于定义簇的密度标准:

  • epsilon (ε):定义点的邻域范围,用于判断点是否相邻。较小的ε可能导致更多噪声点,而较大的ε可能合并不相关的点。通常通过观察k距离图的肘部点来选择合适的ε值。

  • min_samples:定义形成密集簇所需的最小点数。较高的值会使算法更严格,减少簇数量并增加噪声点;较低的值可能包括不密集的区域。一般根据数据维度选择,如二维数据可选45。

这两个参数共同决定簇的形成和噪声点的识别。DBSCAN的优势在于能识别任意形状的簇且无需指定簇的数量,但其性能对参数选择非常敏感,通常需要结合实验和数据特性进行调整以获得最佳聚类效果。

返回值

row(
  n_clusters bigint, 
  cluster_sizes array(bigint), 
  assignments array(bigint),  
  error_msg varchar 
)

列名

类型

说明

n_clusters

bigint

返回的聚类结果的个数。

cluster_sizes

array(bigint)

每个聚类中心包含样本的个数。

assignments

array(bigint)

输入的每个样本对应的cluster_id的编号。

error_msg

varchar

当调用失败时,返回的错误信息。

示例

  • SPL语句

    * and __tag__:__job__: sql-calculate-metric
    | extend time = cast(time as bigint) - cast(time as bigint) % 300 
    | extend time = second_to_nano(time) 
    | stats avg_latency = avg(cast(sum_latency as double)) by time, Method 
    | make-series avg_latency = avg_latency default = '0' on time from 'sls_begin_time' to 'sls_end_time' step '5m' by Method 
    | stats method_array = array_agg(Method), ts_array = array_agg(__ts__), ds_array = array_agg(avg_latency)
    | extend ret = cluster(ds_array, 'kmeans', '{"n_clusters":"5"}')
    | extend n_clusters = ret.n_clusters, cluster_sizes = ret.cluster_sizes, assignments = ret.assignments, error_msg = ret.assignments
  • 输出结果

    image