tradingview / lightweight-charts

Performant financial charts built with HTML5 canvas
https://www.tradingview.com/lightweight-charts/
Apache License 2.0
9.09k stars 1.57k forks source link

I'm getting a timestamp error #1263

Closed yigiterdall closed 1 year ago

yigiterdall commented 1 year ago

Hello everyone,

I want to graph OHLC data from api with candlestick chart. I have no problem with Binance api. I have no problem with Coinecko api. These two APIs are also written in similar ways. But when I get data from a different source, the date part comes as follows:

  {
    "date": "2023-02-07 15:10:00",
    "open": 4140.41016,
    "low": 4140.41016,
    "high": 4143.85986,
    "close": 4143.85986,
    "volume": 4944000
  },
  {
    "date": "2023-02-07 15:06:00",
    "open": 4146.8501,
    "low": 4144.83984,
    "high": 4147.22998,
    "close": 4144.87012,
    "volume": 4284000
  },
  {
    "date": "2023-02-07 15:05:00",
    "open": 4144.99023,
    "low": 4144.99023,
    "high": 4146.97998,
    "close": 4146.81982,
    "volume": 4654000
  },
  {
    "date": "2023-02-07 14:50:00",
    "open": 4143.89014,
    "low": 4142.20996,
    "high": 4144.43018,
    "close": 4143.75,
    "volume": 3893000
  }
]

I'm converting this to timestamp in the code help below and when I write it to the console it's fine. But javascript says data is empty.

My conversion code:

var dateString = d["date"];
var date = new Date(dateString);
var timestamp = date.getTime();
console.log(timestamp);

Error Received:

Uncaught Error: Value is null
    at e (lightweight-charts.standalone.production.js:7:510)
    at t.Hr (lightweight-charts.standalone.production.js:7:46896)
    at t.As (lightweight-charts.standalone.production.js:7:46466)
    at i.cs (lightweight-charts.standalone.production.js:7:30724)
    at lightweight-charts.standalone.production.js:7:26093
    at Array.map (<anonymous>)
    at i.Gn (lightweight-charts.standalone.production.js:7:26067)
    at t.Jn (lightweight-charts.standalone.production.js:7:23294)
    at i.dt (lightweight-charts.standalone.production.js:7:30441)
    at t.Wd (lightweight-charts.standalone.production.js:7:121718)
e @ lightweight-charts.standalone.production.js:7
t.Hr @ lightweight-charts.standalone.production.js:7
t.As @ lightweight-charts.standalone.production.js:7
i.cs @ lightweight-charts.standalone.production.js:7
(anonymous) @ lightweight-charts.standalone.production.js:7
i.Gn @ lightweight-charts.standalone.production.js:7
t.Jn @ lightweight-charts.standalone.production.js:7
i.dt @ lightweight-charts.standalone.production.js:7
t.Wd @ lightweight-charts.standalone.production.js:7
t.Vd @ lightweight-charts.standalone.production.js:7
t.W_ @ lightweight-charts.standalone.production.js:7
t.W_ @ lightweight-charts.standalone.production.js:7
t.Aw @ lightweight-charts.standalone.production.js:7
(anonymous) @ lightweight-charts.standalone.production.js:7
requestAnimationFrame (async)
t.ff @ lightweight-charts.standalone.production.js:7
t.mf @ lightweight-charts.standalone.production.js:7
t.Rr @ lightweight-charts.standalone.production.js:7
t.ho @ lightweight-charts.standalone.production.js:7
t.Be @ lightweight-charts.standalone.production.js:7
i.Z @ lightweight-charts.standalone.production.js:7
(anonymous) @ lightweight-charts.standalone.production.js:7
t.DM @ lightweight-charts.standalone.production.js:7
t._M @ lightweight-charts.standalone.production.js:7
t.setData @ lightweight-charts.standalone.production.js:7
(anonymous) @ VM809 indexdetail:458
Promise.then (async)
(anonymous) @ VM809 indexdetail:442

All Codes:

<script>
        const log = console.log;

        const chartProperties = {
            width:300,
            height:400,
            timeScale:{
                timeVisible:true,
                secondsVisible:false,
            }
        }

        const domElement = document.getElementById('chart');
        const chart = LightweightCharts.createChart(domElement,chartProperties);
        const candleSeries = chart.addCandlestickSeries();

        fetch('JSON API')
            .then(res => res.json())
            .then(data => {
                const cdata = data.map(d => {

                    var dateString = d["date"];
                    var date = new Date(dateString);
                    var timestamp = date.getTime();
                    console.log(timestamp);

                    return {time:timestamp,open:parseFloat(d["open"]),high:parseFloat(d["high"]),low:parseFloat(d["low"]),close:parseFloat(d["close"])}
                });
                candleSeries.setData(cdata);
            })
        .catch(err => log(err))

    </script>
SlicedSilver commented 1 year ago

I believe that the issue is: Lightweight charts expects the time value to be in seconds, not milliseconds. Could you try divide the time value by 1000?

For example:

var timestamp = date.getTime() / 1000;

Additionally, if you use the development build of the library instead of the production build then you will get more helpful console errors.

yigiterdall commented 1 year ago

I believe that the issue is: Lightweight charts expects the time value to be in seconds, not milliseconds. Could you try divide the time value by 1000?

For example:

var timestamp = date.getTime() / 1000;

Additionally, if you use the development build of the library instead of the production build then you will get more helpful console errors.

Thank you for your answer, but I had tried this before. I tried again and the problem persists. I don't know exactly what you're saying about console errors, can you give an example please?

By the way, the timestamp example is as follows:

1675771800 1675771740 1675771680 1675771620 1675771560 1675771500

SlicedSilver commented 1 year ago

If you run your example with the development build of the library then you will get the following error in the console:

Assertion failed: data must be asc ordered by time, index=1, time=1675782360, prev time=1675782600

This means that the data is not in the correct order. The timestamps in the array should be in ascending order. You still need to divide by 1000.

Example: https://codesandbox.io/s/timestamps-lwc-5tjgrh?file=/src/index.js


Depending on how you load the library will determine how to load the development version.

Looks like you are using the standalone version. So you can change your script tag from

<script 
   type="text/javascript"
   src="https://unpkg.com/lightweight-charts/dist/lightweight-charts.standalone.production.js"
></script>

to:

<script 
   type="text/javascript"
   src="https://unpkg.com/lightweight-charts/dist/lightweight-charts.standalone.development.js"
></script>
yigiterdall commented 1 year ago

If you run your example with the development build of the library then you will get the following error in the console:

Assertion failed: data must be asc ordered by time, index=1, time=1675782360, prev time=1675782600

This means that the data is not in the correct order. The timestamps in the array should be in ascending order. You still need to divide by 1000.

Example: https://codesandbox.io/s/timestamps-lwc-5tjgrh?file=/src/index.js

Depending on how you load the library will determine how to load the development version.

Looks like you are using the standalone version. So you can change your script tag from

<script 
   type="text/javascript"
   src="https://unpkg.com/lightweight-charts/dist/lightweight-charts.standalone.production.js"
></script>

to:

<script 
   type="text/javascript"
   src="https://unpkg.com/lightweight-charts/dist/lightweight-charts.standalone.development.js"
></script>

Solved! Thank you very much. I was having a problem with the exact data inversion.

I am sharing all the code to help. I hope it will be a solution for someone else as well.

<script src="https://unpkg.com/lightweight-charts/dist/lightweight-charts.standalone.development.js"></script>

    <script>
        const log = console.log;

        const chartProperties = {
            width:300,
            height:400,
            timeScale:{
                timeVisible:true,
                secondsVisible:false,
            }
        }

        const domElement = document.getElementById('chart');
        const chart = LightweightCharts.createChart(domElement,chartProperties);
        const candleSeries = chart.addCandlestickSeries();

        fetch('YOURJSON API LINK HERE')
            .then(res => res.json())
            .then(data => {
                data.reverse()
                const cdata = data.map(d => {

                    var dateString = d["date"];
                    var date = new Date(dateString);
                    var timestamp = date.getTime() / 1000;
                    console.log(timestamp);

                    return {time:timestamp,open:parseFloat(d["open"]),high:parseFloat(d["high"]),low:parseFloat(d["low"]),close:parseFloat(d["close"])}
                });
                candleSeries.setData(cdata);
            })
        .catch(err => log(err))

    </script>