![Maven Central Adds Sigstore Signature Validation](https://cdn.sanity.io/images/cgdhsj6q/production/7da3bc8a946cfb5df15d7fcf49767faedc72b483-1024x1024.webp?w=400&fit=max&auto=format)
Security News
Maven Central Adds Sigstore Signature Validation
Maven Central now validates Sigstore signatures, making it easier for developers to verify the provenance of Java packages.
github.com/open-telemetry/opentelemetry-collector-contrib/pkg/telemetryquerylanguage
The Telemetry Query Language is a query language for transforming open telemetry data based on the OpenTelemetry Collector Processing Exploration.
This package reads in TQL queries and converts them to invokable Booleans and functions based on the TQL's grammar.
The TQL is signal agnostic; it is not aware of the type of telemetry on which it will operate. Instead, the Booleans and functions returned by the package must be passed a TransformContext
, which provide access to the signal's telemetry. Telemetry data can be accessed and updated through Getters and Setters.
The TQL grammar includes Invocations, Values and Expressions.
Invocations represent a function call. Invocations are made up of 2 parts:
_
).()
).The TQL does not define any function implementations. Users must supply a map between string identifiers and the actual function implementation. The TQL will use this map and reflection to generate Invocations, that can then be invoked by the user.
Example Invocations
drop()
set(field, 1)
The TQL will use reflection to determine parameter types when parsing an invocation within a statement. When interpreting slice parameter types, the TQL will attempt to build the slice from all remaining Values in the Invocation's arguments. As a result, function implementations of Invocations may only contain one slice argument and it must be the last argument in the function definition. See function syntax guidelines for more details.
The following types are supported for single parameter values:
Setter
GetSetter
Getter
Enum
string
float64
int64
bool
For slice parameters, the following types are supported:
string
float64
int64
uint8
. Slices of bytes will be interpreted as a byte array.Getter
Values are passed as input to an Invocation or are used in an Expression. Values can take the form of:
Invocations as Values allows calling functions as parameters to other functions. See Invocations for details on Invocation syntax.
A Path Value is a reference to a telemetry field. Paths are made up of lowercase identifiers, dots (.
), and square brackets combined with a string key (["key"]
). The interpretation of a Path is NOT implemented by the TQL. Instead, the user must provide a PathExpressionParser
that the TQL can use to interpret paths. As a result, how the Path parts are used is up to the user. However, it is recommended, that the parts be used like so:
.
) are used to separate nested fields.["key"]
) are used to access maps or slices.Example Paths
name
value_double
resource.name
resource.attributes["key"]
Literals are literal interpretations of the Value into a Go value. Accepted literals are:
""
).+
) or minus (-
). Internally the TQL represents all ints as int64
.
), optionally prepended by plus (+
) or minus (-
). The leading digit is optional. Internally the TQL represents all Floats as float64
.true
and false
.nil
.0x
Example Literals
"a string"
1
, -1
1.5
, -.5
true
, false
nil
,0x0001
Enums are uppercase identifiers that get interpreted during parsing and converted to an int64
. The interpretation of an Enum is NOT implemented by the TQL. Instead, the user must provide a EnumParser
that the TQL can use to interpret the Enum. The EnumParser
returns an int64
instead of a function, which means that the Enum's numeric value is retrieved during parsing instead of during execution.
Within the grammar Enums are always used as int64
. As a result, the Enum's symbol can be used as if it is an Int value.
When defining a function that will be used as an Invocation by the TQL, if the function needs to take an Enum then the function must use the Enum
type for that argument, not an int64
.
Expressions allow a decision to be made about whether an Invocation should be called. Expressions are optional. When used, the parsed query will include a Condition
, which can be used to evaluate the result of the query's Expression. Expressions always evaluate to a boolean value (true or false).
Expressions consist of the literal string where
followed by one or more Booleans (see below).
Booleans can be joined with the literal strings and
and or
.
Note that and
expressions have higher precedence than or
.
Expressions can be grouped with parentheses to override evaluation precedence.
Booleans can be either:
true
or false
).Operators determine how the two Values are compared.
The valid operators are:
==
). Tests if the left and right Values are equal (see the Comparison Rules below).!=
). Tests if the left and right Values are not equal.<
). Tests if left is less than right.>
). Tests if left is greater than right.<=
). Tests if left is less than or equal to right.>=
). Tests if left is greater than or equal to right.The table below describes what happens when two Values are compared. Value types are provided by the user of TQL. All of the value types supported by TQL are listed in this table.
If numeric values are of different types, they are compared as float64
.
For numeric values and strings, the comparison rules are those implemented by Go. Numeric values are done with signed comparisons. For binary values, false
is considered to be less than true
.
For values that are not one of the basic primitive types, the only valid comparisons are Equal and Not Equal, which are implemented using Go's standard ==
and !=
operators.
A not equal
notation in the table below means that the "!=" operator returns true, but any other operator returns false. Note that a nil byte array is considered equivalent to nil.
base type | bool | int64 | float64 | string | Bytes | nil |
---|---|---|---|---|---|---|
bool | normal, T>F | not equal | not equal | not equal | not equal | not equal |
int64 | not equal | compared as largest | compared as float64 | not equal | not equal | not equal |
float64 | not equal | compared as float64 | compared as largest | not equal | not equal | not equal |
string | not equal | not equal | not equal | normal (compared as Go strings) | not equal | not equal |
Bytes | not equal | not equal | not equal | not equal | byte-for-byte comparison | []byte(nil) == nil |
nil | not equal | not equal | not equal | not equal | []byte(nil) == nil | true for equality only |
Access to signal telemetry is provided to TQL functions through a TransformContext
that is created by the user and passed during statement evaluation. To allow functions to operate on the TransformContext
, the TQL provides Getter
, Setter
, and GetSetter
interfaces.
Getters allow for reading the following types of data. See the respective section of each Value type for how they are interpreted.
It is possible to update the Value in a telemetry field using a Setter. For read and write access, the GetSetter
interface extends both interfaces.
To emit logs inside a TQL function, add a parameter of type Logger
to the function signature. The TQL will then inject a logger instance provided by the component that can be used to emit logs.
These examples contain a SQL-like declarative language. Applied statements interact with only one signal, but statements can be declared across multiple signals. Functions used in examples are indicative of what could be useful, but are not implemented by the TQL itself.
traces:
delete(attributes["http.request.header.authorization"])
metrics:
delete(attributes["http.request.header.authorization"])
logs:
delete(attributes["http.request.header.authorization"])
traces:
keep_keys(attributes, "http.method", "http.status_code")
metrics:
keep_keys(attributes, "http.method", "http.status_code")
logs:
keep_keys(attributes, "http.method", "http.status_code")
traces:
replace_match(attributes["http.target"], "/user/*/list/*", "/user/{userId}/list/{listId}")
traces:
replace_match(name, "GET /user/*/list/*", "GET /user/{userId}/list/{listId}")
traces:
replace_all_matches(attributes, "/user/*/list/*", "/user/{userId}/list/{listId}")
traces:
delete(resource.attributes["process.command_line"])
metrics:
delete(resource.attributes["process.command_line"])
logs:
delete(resource.attributes["process.command_line"])
metrics:
drop() where attributes["http.target"] == "/health"
metrics:
set(attributes["k8s_pod"], resource.attributes["k8s.pod.name"])
traces:
set(attributes["whose_fault"], "theirs") where attributes["http.status"] == 400 or attributes["http.status"] == 404
set(attributes["whose_fault"], "ours") where attributes["http.status"] == 500
traces:
group_by(trace_id, 2m)
logs:
set(span_id, SpanID(0x0000000000000000))
traces:
set(span_id, SpanID(0x0000000000000000))
metrics:
create_gauge("pod.cpu.utilized", read_gauge("pod.cpu.usage") / read_gauge("node.cpu.limit")
FAQs
Unknown package
Did you know?
Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.
Security News
Maven Central now validates Sigstore signatures, making it easier for developers to verify the provenance of Java packages.
Security News
CISOs are racing to adopt AI for cybersecurity, but hurdles in budgets and governance may leave some falling behind in the fight against cyber threats.
Research
Security News
Socket researchers uncovered a backdoored typosquat of BoltDB in the Go ecosystem, exploiting Go Module Proxy caching to persist undetected for years.