Printing datastream from socket - time-series

I am trying to connect to a socket which provides a feed of stock prices (stockID,price), and then print it. The stream is endless. My problem is that I cannot print it.
To begin with, I create a connection:
con <- socketConnection(host = "88.99.38.191", port = 1337, open = "r")
then i set a variable reading all the lines.
data <- readLines(con,-1)
Then print(data)
the problem is that depending on the time gap between executing the connection and setting variable data, the latter receives a different number of values, and that's it.
I am trying to print somehow the entire stream. If I use
while (TRUE) { print(data) }
it just prints endlessly the data in loops.
Any idea how to implement that?
My ultimate goal is to calculate the moving average for each ID.

For those interested this is the answer.
con <- socketConnection(host = "88.99.38.191", port = 1337, open ="r",blocking = T,server=FALSE)
while(TRUE) {
data <- readLines(con,1)
print(data)
}
The problem with my initial approach was that I didn't use the blocking = T property for socketConnection. Further info can be found here.

Related

Frame.msg not working with db_decode from cantools

I want to use the can_msgs/Frame.msg for decoding can messages using db.decode_message(Frame.id, Frame.data) but it is giving error
I want to try and write a new Frame.msg format but will it help?
def callback(Frame):
rospy.loginfo(rospy.get_caller_id() + "I heard %s", Frame.data)
Temp = db.decode_message(Frame.id, Frame.data)
temp.data = Temp
pub.publish(temp)
I want to print the message in the dbc format that the cantools package helps decoding.
Error:
File "safa.py", line 42, in callback
temp = db.decode_message(Frame.id, Frame.data)
File "build/bdist.linux-x86_64/egg/cantools/database/can/database.py", line 379, in decode_message
message = self._name_to_message[frame_id_or_name]
KeyError: 10
Looking at the cantools documentation for db.decode_message, the KeyError is a bad description/error msg for the following.
db is a database (class cantools.database.can.Database), which stores all the weird encodings we may choose to use with cantools. To decode a message, it must already have an encoding stored within it, using one of the db.add_* methods with the class.
Edit:
The definition of the can_msgs/Frame is
std_msgs/Header header
uint32 id
bool is_rtr
bool is_extended
bool is_error
uint8 dlc
uint8[8] data
The data term requires an array/list of 8 uint8 values, not a string. Any CANbus data encoding must finish in this form.
Additionally, ROS provides an interface to the CANbus already: socketcan_bridge can be called in a launch file with your node at the same time.
Before you can decode messages you should setup the database e.g by loading a dbc file:
try:
dbc_file_object = open(dbc_file, 'r')
except IOError as e:
rospy.loginfo('Unable to open file {}'.format(e))
sys.exit(-1)
self.db = cantools.db.load(dbc_file_object)

Dart: getElementsByClassName returns a 0 element list but the data is there

I'm writing a function that will parse certain websites and fetch data from there, which will be used to create instances of a class. I'm able to successfully extract the data when it is retrieved using the getElementById() function, but for some reason, the getElementsByClassName() always returns a node list with 0 elements.
The site I'm currently parsing is here.
If you search for 'datas-nev', you will find exactly one match:
<p class="datas-nev"><b>Kutya neve: </b>Jhonny</p>
And here is the code use for parsing:
import 'package:html/parser.dart' show parse;
...
final response = await http.get(URL);
var document = parse(response.body);
var detailsContainer = document.getElementById('husky_details_container_right');
var dogName = new List<Node>();
dogName = document.getElementsByClassName('datas-nev');
The contents of the detailsContainer can be extracted successfully, for example this gives me back a string of relevant data I will use later:
var humanBehaviourValue;
try { humanBehaviourValue = detailsContainer.nodes[1].nodes[19].nodes[1].nodes[7].nodes[1].toString(); }
catch (e) { humanBehaviourValue = 'N/A'; }
But when I check the value of dogName in the debug window, I get the following:
dogName = {_growableList} size = 0
I already tried initializing the dogName 'properly' by List<Node> dogName = new List<Node>(); but it didn't help. I also tried other datas-* values, but it seems the parser can't find them. I even tried using just datas (because that is a div, while others are paragraphs), but that didn't help either.
Basically I could just hardwire the name and some data (breed, color, etc) as those never really change, but the location of the shelter can change, and keeping it up-to-date by scraping the data seems better than pushing updates out manually. That means I mostly need the value of datas-helyszin but that isn't parsed either.
As #Günter Zöchbauer pointed out, the code actually works. I was just looking for the value too soon, before it was actually fetched...

Trying to connect to Ticket Printer using VB6 Winsock

I am trying to send data from a VB6 program to a ticket printer Via TCP/IP. The only VB6 way I have found to try and do this is using the WinSock Control.
I use the following code to connect
WinSock.Protocol = sckTCPProtocol
WinSock.RemoteHost = txtIPAddress.Text
WinSock.RemotePort = txtPort.Text
WinSock.Connect
And then try and send the data as follows
WinSock.SendData ("<F8>" & txtPrint.Text & "<p>")
Everytime I try and do this, it fails because the Winsock.State is 6 (Connecting). This just stays at connecting and never connects or fails. I am able to connect to the printer using this IP/Port combo outside of VB6. Is there anything I may be doing wrong? Can the WinSock control do this?
In a .net program provided, this seems to be accomplished by doing the following:
CONNECT
client = new TcpClient(ip_address, 9100);
s = client.GetStream(); //s is System.Net.Sockets.NetworkStream
s.ReadTimeout = 500; //attempt to read for up to 0.5 seconds
sr = new StreamReader(s); //create read stream
sw = new StreamWriter(s); //create write stream
sb = new BinaryWriter(s); //create binary stream
sw.AutoFlush = true; //set write stream to flush data when < full buffer
SEND:
sw.WriteLine(command);
Thank you.
You are missing up concepts. I remember this from 15 years ago.
Winsock is for work with a protocol. You must know the printer protocol. Is not just sample text.

How to receive UDP data in Vala?

another Vala problem occured: I try to send and receive data via UDP. The sending works and via Wireshark I can see that the server sends the expected result. Problem is: My program doesn't get the data.
I checked and I can see that, when a socket has been created to send the UDP data, the specific port stays open, which is confirmed by Wireshark because my PC doesn't send any of those ICMP messages back to the server.
What I got so far:
try
{
SocketClient mySocket = new SocketClient();
mySocket.protocol = SocketProtocol.UDP;
mySocket.type = SocketType.DATAGRAM;
var conn = mySocket.connect (new InetSocketAddress(addr,targetPort));
conn.output_stream.write(themessage_in_a_uint8_array);
DataInputStream response = new DataInputStream (conn.input_stream);
string resp ="";
char myChar;
try
{
do
{
myChar = (char)response.read_byte();
print ("Response" + myChar.to_string());
}while(true);
}
catch(Error e)
{
print(e.message);
}
}
catch(Error e)
{print(e.message);}
What currently happens: The message is send, the string 'Response' is printed once into the console and after that it just loops.
If I check response.get_available() it returns 0.
I can check with lsof | grep used_portnumber and sure enough, the used socket stays open. What am I doing wrong?
I am not sure but this is what I suspect:
UDP is a datagram protocol (data is explicitly chopped into data). Server have sent one datagram to client. Now in BSD Sockets (and after it everywhere) if the underlaying socket have datagram type then read reads the full packet. If the buffer have insufficient length the message is truncated.
The solution is read in one byte. For example
uint8[] buffer = new uint8[1 << 16]; // Maximum UDP length - we don't loose anything
unowned string locale;
bool need_convert = GLib.get_charset (out locale);
do {
ssize_t len = response.read (buffer);
string text;
if (need_convert) {
text = GLib.convert ((string)buffer, len, locale, "UTF-8");
} else {
text = (string)buffer;
}
stdout.print("Response " + text);
} while (true);
Edit I have change the code to print UTF-8 text - without assuming current locale is "UTF-8"-based.
PS 1 This is my guess as it is one gotcha of BSD Sockets (also Winsockets and everything that builds on this) that come to my mind. Please be graceful if the question will be more specific (i.e. it is not the answer to question).
PS 2 In general I would recommend against mixing bytes and chars. While in ASCII-compatible encodings (ISO, UTF-8) sending ASCII subset of chars is safe it will bite when attempt on CJK encodings or if sender will send 'ą' by UTF-8 and sender will treat it as ISO-8859-2 (where this character have different encoding). I assume it is for the toy-examples only. If not you may want to read What Every Programmer Absolutely, Positively Needs To Know About Encodings And Character Sets To Work With Text.

twisted buffer full in tcp connection

I´m having problems with receiving long data (>1024bytes) in a simple twisted server implementation.
From the beginning, I´m developing an ios App that has to synchronize with a twisted server. I prepare the information to send in JSON format. Then I start to send that data in chuncks (right now in chunck of 256bytes + 4 bytes for the command - Yes, I´m implementing my own protocol). The connection is ok, and I receive those packet´s in my server (in the dataReceived function of my own Protocol subclass).
The ios method: NSInteger writtenBytes =[self.outputStream write:[data bytes] maxLength:[data length]] return the written bytes into the stream. For the first 4 packets the value returned is the expected (260 bytes). If I have more available bytes to send, the next time I call that method it returns 0 (which apple documentation says: "If the receiver is a fixed-length stream and has reached its capacity, 0 is returned.").
So I deduce that the input buffer is full. I don´t know how to free that buffer (I don´t know how to reach that buffer). I don't know where is the limit of that buffer (it seems to me almost ridiculous).
This is a basic test of the server (Just the important things for this question with a basic based in strings protocol)
from twisted.internet.protocol import Protocol, Factory
from twisted.internet import reactor
class IphoneSync(Protocol):
def __init__(self):
self.__buffer = ""
def connectionMade(self):
self.transport.write("0:")
self.factory.clients.append(self)
print "clients are ", self.factory.clients
def connectionLost(self, reason):
self.factory.clients.remove(self)
def dataReceived(self, data):
#print "data is ", data
a = data.split(':')
if len(a) > 1:
command = a[0]
content = a[1]
msg = ""
if command == "iam":
#user&Pass checking
msg = "1"
elif command == "msg":
self.__buffer += data
msg = "1: continue"
elif command == "fin":
#procesaremos todo
#Convertir datos en json
#insertar/actualizar data en sqlite
#devolver respuesta
print "buffer is", self.__buffer
msg = "2: procesing"
print msg
self.transport.write(msg)
#for c in self.factory.clients:
#c.message(msg)
def message(self, message):
self.transport.write(message)
#self.transport.write(message + '\n')
factory = Factory()
factory.protocol = IphoneSync
factory.clients = []
dir(factory)
reactor.listenTCP(8000, factory)
print "Iphone Chat server started"
reactor.run()
I saw the LineReceiver class but i´m not sending lines. The transfered data could be very big (10Mb-50Mb). I´m thinking about the Consumer/Producer model, or RPC Protocols like (AMP, or PB) as a solution but i wanted to work with my own protocol.
If someone knows how to help me, i´ll appreciate very much. Thanks anyway.
The connection is ok, and I receive those packet´s in my server (in the dataReceived function of my own Protocol subclass).
Probably not. TCP is a "stream oriented" protocol. Your application's use of it is not in terms of packets but in terms of a sequence of bytes. There is no guarantee whatsoever that dataReceived will be called with the same string that you passed to outputStream write. If you write "hello, world", dataReceived may be called with "hello, world" - or it may be called twice, first with "hello," and then with " world". Or it may be called 12 times: first "h", then "e", then "l", etc.
And if you call outputStream write twice, once with "hello," and once with " world", then it's entirely possible dataReceived will be called just once with "hello, world". Or perhaps twice, but with "h" and then "ello, world".
So this brand new protocol you're inventing (which I see you mentioned you recognized you were doing, but you didn't explain why this is a good idea or an important part of your application, instead of just a large source of potential bugs and a poor use of time :) has to do something called "framing" in order to let you actually interpret the byte sequence being passed around. This is why there are protocols like AMP.
To actually answer your question, outputStream write returns the number of bytes it was actually able to buffer for sending. You must always check its return value and re-try writing any bytes it wasn't able to send, preferably after waiting for notification that there is more buffer space. Buffer space becomes available after bytes using that space are sent across the network and acknowledged by the receiver. This takes time, as networks are not instantaneous. Notification about buffer space being available comes in many forms, the oldest and most widespread of which (but not necessarily the best in your environment), the select(2) system call.
In addition to Jean-Paul Calderone's answer (ensuring that data are being sent completely from the obj-c side by using select or thread), for protocol part I would suggest using length-prefixed string (AKA Netstring) for simple use case.
Here's an implementation. Whenever something is received, you need to call NSBuffer.write then NSBuffer.extract to get available strings.

Resources