I'm using jsonnet to configure my panels in Grafana. I'm using itfor the first time and I like it a lot. However, I'm having a hard time understanding certain aspects.
I have something similar to the following:
.addTemplate(
template.new(
microservices,
datasource='',
query=std.join(',', std.map(function(x) x.text, service['microservices'])),
label= services,
)
What I am trying to do now is to obtain, given a microservice, the position it occupies in order to be able to assign it to the variable service (and then get my custom values whit the query=std.join(',', std.map(function(x) x.text, service['microservices'])),).
local services = std.extVar('services');
local service = services[x?];
The variable service has the following form:
[
{
// I'm trying to get this array position where my value is
"key": "asd",
"microservices": [
{
"key": "I HAVE THIS VALUE",
"text": "ads"
},
{
"key": "asd",
"text": "ads"
},
{
"key": "asd",
"text": "asd"
}
],
"name": "bca",
"services: [
{
"key": "bca",
"name": "bca"
}
]
},
{
"key": "bca",
"microservices": [
{
"key": "bca",
"text": "bca"
},
{
"key": "bca",
"text": "bca"
}
],
"name": "bca",
"services: [
{
"key": "bca",
"name": "bca"
}
]
},
{
"key": "abc",
"microservices": [
{
"key": "bca",
"text": "bca"
}
],
"name": "abc",
"services: [
{
"key": "ccc",
"name": "ccc"
}
]
}
]
In any other language it seems to me a very basic operation.
var srv type
for x, service := range services{
for _, microservice := range service.microservices{
if microservice.key == "my value"{
srv= services[x]
}
}
Any tip?
Thank you so much.
It is also a very simple operation in Jsonnet. The most natural way to do it is with array comprehensions, which also conveniently support filtering:
local service2 = [
s for s in services
if [ms for ms in s.microservices if ms.key == "I HAVE THIS VALUE"] != []
][0];
Please note the indexing [0]
- in general there may be more than one or none matching services in general. So if you want to get the first one, you need to take it explicitly.
The code above is written with the assumption that you don't care about the actual index, you only want to retrieve this service. If you need it, it gets a tiny bit more complicated:
local serviceIndex = [
x for x in std.range(0, std.length(services) - 1)
if [ms for ms in services[x].microservices if ms.key == "I HAVE THIS VALUE"] != []
][0];
BTW you could achieve the same result with functions such as std.filter
, but that would be a bit more verbose.
BTW2 I would also consider extracting a function hasMicroservice(service, msKey)
to enhance readability of filtering.