Copying a value from a field to another field can be an important use case to make dashboards working smooth. Per default Kibana dashboards filtering every visualization when a new filter is set. In some cases you want to have a general filter for the full dashboard.
Lets say you’ve build a dashboard that is only relevant for one of your observed APM services. You could build in the filter for the desired service into every single visualization or as a general filter in the dashboard. However if you build it as a general filter you need to set the service name for all visualizations in the same field. Same holds for e.g. IP addresses, host names and other fields that contain important data. Copy the value from one indexed field into a new runtime field can be good option to solve that issue.
Another important use case for this kind of Elastic runtime field is to change the mapping of one field without reindexing. Let’s say you indexed a field as text that you would like to use as a keyword field. Before we had runtime fields you had to reindex the data and make the mapping right. Using runtime fields you can just copy the value and use new keyword mapping to achieve the same result.
Here is the null safe example code for a runtime field that can copy the value from one source field to the new runtime field.
if (doc.containsKey('source.field.name')) {
def source = doc['source.field.name'].value;
if (source != "") {
emit(source);
}
}
The first if is checking that the field exists in every document. This is important if you have documents with different fields. Especially if the source field is not existing in every document of your source indices. The second if is checking that there is a value in the field. Most likely you don’t want to populate a new field when the source is empty.
The above example does not work if you want to copy a geo_point value. In order to do that the emit function needs to have to parameters. The following example shows a runtime field that is using a geo_point field that was wrongly mapped as text and keyword. The target of the copy to another field runtime field is to change the mapping to geo_point again.
if (doc.containsKey('enriched.location.keyword')) {
def source = doc['enriched.location.keyword'].value;
def geo_point = source.splitOnToken(",");
if (source != "") {
def lat = Double.parseDouble(geo_point[0]);
def lon = Double.parseDouble(geo_point[1]);
emit(lat,lon);
}
}