31

Is possible to query only for the last value (or n-th value) of the results of a query?

For example, in the query:

SELECT value FROM response_times WHERE time > now() - 1h limit 1000;

Is possible to get only the last value, i.e. the one more far ago in time (possibly the 1000-th element)?

Of course I can retrieve them all and then skip to the last one, but I don't want to waste bandwith this way.

dukebody
  • 7,025
  • 3
  • 36
  • 61

7 Answers7

51

If you are using InfluxDB 0.8 dont use FIRST() or LAST() if you have not GROUP BY because its very slow :(

So if you want to get the these Values you shoud use:

First Value:

SELECT * FROM <SERIES> GROUP BY * ORDER BY ASC LIMIT 1

Last Value:

SELECT * FROM <SERIES> GROUP BY * ORDER BY DESC LIMIT 1

Don't delete the GROUP BY * because then it could be possible that you get unexpected values then.

Mark Amery
  • 143,130
  • 81
  • 406
  • 459
kpalatzky
  • 1,213
  • 1
  • 11
  • 26
  • Do you have any explanation on what these unexpected values look like and why they show up? – Daniel F Dec 12 '17 at 04:20
  • 4
    -1 for [FUD](https://en.wikipedia.org/wiki/Fear,_uncertainty_and_doubt). If you want to assert that something is broken, provide a demonstration of the brokenness - not a vague and untestable assertion that *"it could be possible that you get unexpected values "*. – Mark Amery Feb 05 '18 at 11:32
  • Running InfluxDB 1.7.9, this query returns more than a single result for a table/measurement. Evidently this is only good for a series. – computercarguy Nov 18 '19 at 19:15
  • 1
    Just checked with "EXPLAIN" and using "LAST()" with "WHERE time > now() - 1h" seems better/faster then using "ORDER BY ... LIMIT" even with "GROUP BY" - the latter used all the shards. – Radoslaw Garbacz Nov 18 '19 at 19:25
  • 1
    So using FIRST() in InfluxDB version > 0.8 is fast? – rojikada Mar 11 '21 at 12:00
23
SELECT last(value) FROM response_times WHERE time > now() - 1h;

That should return the last value of the column.

However, if you want you can split up the sequence in smaller pieces and select the last value. For instance:

 SELECT last(value) FROM response_times WHERE time > now() - 1h GROUP BY time(60s);

It will split up the sequence in 60-second fragments and will pick up for each fragment the latest value.

José Molina
  • 529
  • 2
  • 7
6

In the API, have a look at first/last to select the first or last record of a column. You also have top/bottom to select more than one record

[edit] top/bottom seem to return higest/lowest values of the time frame

Pi Home Server
  • 487
  • 1
  • 3
  • 17
  • Where is this documented? I cannot find it at http://influxdb.com/docs/v0.9/query_language/querying_data.html or http://influxdb.com/docs/v0.8/api/query_language.html – dukebody Apr 09 '15 at 08:20
  • 2
    For 0.8 it's in the aggregate functions : http://influxdb.com/docs/v0.8/api/aggregate_functions.html#first/last sorry to not have provided the link before ! – Pi Home Server Apr 09 '15 at 08:28
  • 1
    I'm most interested in getting the times for the first/last values...any way to do that? – tslater Sep 17 '15 at 00:38
6

If like me you are looking for the same feature but with the Flux DSL (influx 2).

You can use the tail function https://docs.influxdata.com/influxdb/v2.0/reference/flux/stdlib/built-in/transformations/tail/

(...)
  |> tail(n: 1)

The last function didn't work out for me.

Bertrand P
  • 820
  • 7
  • 24
4

here is a concrete sample, suppose we have data:

> select *,tag from measurement
name: measurement
time                 field_1    tag_1
----                 -------    ------
2019-05-15T03:07:52Z 100      A
2019-05-15T03:07:52Z 101      B
2019-05-15T03:09:52Z 100      A
2019-05-15T03:09:52Z 101      B

and you would like to take the last two columns(latest records per tag_1), then you can do this:

> select last(field_1),* from measurement group by *
name: measurement
tags: tag_1=A
time                 last     field_1 
----                 ----    ------- 
2019-05-15T03:09:52Z 100        100     

name: measurement
tags: tag_1=B
time                 last  field_1 
----                 ----  ------- 
2019-05-15T03:09:52Z 101    101 

and also the visualization on grafana, it'll always show the last records per tag enter image description here

LIU YUE
  • 1,593
  • 11
  • 19
2
SELECT * FROM <SERIES> ORDER BY ASC LIMIT 1
IsaacE
  • 305
  • 2
  • 10
1

There is no bug or any issue about LIMIT. Yes there is one, but it's about SLIMIT (Series Limit). LIMIT can be safely used for getting first n records.

So in short, the syntax for LIMIT:

SELECT_clause [INTO_clause] FROM_clause [WHERE_clause] [GROUP_BY_clause] [ORDER_BY_clause] LIMIT <N>

the syntax for SLIMIT:

SELECT_clause [INTO_clause] FROM_clause [WHERE_clause] GROUP BY *[,time(<time_interval>)] [ORDER_BY_clause] SLIMIT <N>

You see that GROUP BY clause is [ optional ] in LIMIT.

For detailed explanation about usages of LIMIT and SLIMIT, here is version 1.5 document. And here is the ongoing issue about SLIMIT.

stratovarius
  • 3,720
  • 1
  • 30
  • 26