import React from 'react'; import PropTypes from 'prop-types'; import * as msgpack from 'msgpack-lite'; class DeviceHttpDataSource extends React.Component { constructor(props) { super(props); this.data = []; this.dataUrl = this.props.deviceUrl + "/api/session/data"; // msgpack setup this.msgpackCodec = msgpack.createCodec(); this.msgpackCodec.addExtUnpacker(205, function (byteArr) { const buffer = byteArr.buffer.slice(byteArr.byteOffset, byteArr.byteLength + byteArr.byteOffset); const result = new Int16Array(buffer); return result; }); this.fetchDataHttp = this.fetchDataHttp.bind(this); } getUrl(url) { return new Promise((accept, reject) => { var req = new XMLHttpRequest(); req.open("GET", url, true); req.responseType = "arraybuffer"; req.onload = function (event) { var resp = req.response; if (resp) { accept(resp); } }; req.send(null); }); //todo reject on error } async fetchDataHttp() { try { const url = this.dataUrl + "?startIdx=" + this.data.length; const arrayBuffer = await this.getUrl(url); const decoded = msgpack.decode(new Uint8Array(arrayBuffer), { codec: this.msgpackCodec }); const typedValueArr = decoded['values']; const newDataStart = this.data.length; for (let i = 0; i < typedValueArr.length; ++i) { this.data.push(typedValueArr[i]); } this.props.onNewData(this.data, newDataStart); } catch (err) { //console.log(err); } } componentDidMount() { this.timer = setInterval(this.fetchDataHttp, this.props.pollInterval); } componentWillUnmount() { clearInterval(this.timer); this.timer = null; } render() { return null; } } DeviceHttpDataSource.propTypes = { deviceUrl: PropTypes.string.isRequired, onNewData: PropTypes.func.isRequired, pollInterval: PropTypes.number // poll interval in ms }; DeviceHttpDataSource.defaultProps = { pollInterval: 20000 }; export default DeviceHttpDataSource;