Issues Connecting Client from MicroPython to Raspberry Pi Pico Server - sockets

I have been trying to develop an IoT-based application. I thought using WebSockets with my Raspberry Pi Pico W as the server would be a good idea to transfer information to my react application in real-time. I am new to socket programming and I am having issues transferring information between the React App and the Pico W. For some more context, my Server side code looks like the following:
addr = socket.getaddrinfo('0.0.0.0', 80)[0][-1]
s = socket.socket()
s.bind(addr)
s.listen(1)
print('Listening On ' + str(addr))
while True:
try:
cl,addr = s.accept()
print('Client connected from ' + str(addr))
cl.send('HTTP/1.0 200 OK\r\nContent-type: text/html\r\n\r\n')
cl.send("Hello")
time.sleep(3)
cl.close()
except:
cl.close()
break
In React Native Client-side code looks like follows:
import io from "socket.io-client"
import {useEffect } from 'react';
export default function App() {
useEffect(() => {
const socket_2 = io("http://<IP_ADDRESS_NOT_SHOWN_HERE>:80")
socket_2.emit('message', 'data');
socket_2.on('message', (data) => {
console.log(data);
});
console.log(socket_2)
}, []);
The interesting thing is that I am sure the server side is working because when I connect from the browser is sends me the "Hello" response. Additionally when I connect from React App I see a bunch of logs in Python Resembling the following:
Client connected from ('<IP_ADDRESS_NOT_SHOWN_HERE>', 62518)
Client connected from ('<IP_ADDRESS_NOT_SHOWN_HERE>', 62540)
Client connected from ('<IP_ADDRESS_NOT_SHOWN_HERE>', 62541)
Client connected from ('<IP_ADDRESS_NOT_SHOWN_HERE>', 62554)
Client connected from ('<IP_ADDRESS_NOT_SHOWN_HERE>', 62567)
Client connected from ('<IP_ADDRESS_NOT_SHOWN_HERE>', 62573)
Client connected from ('<IP_ADDRESS_NOT_SHOWN_HERE>', 62580)
To sum it up there are two primary things I am questioning here.
1-) I am not sure why it keeps making new connections
2-) I am also not sure why my information is not being transferred in between React Native and my Raspberry Pi Pico W server properly
Any help would be appreciated I am a socket-programming noob :/
I have tried using Socket IO and also I have tried using the react native socket library. I believe the socket io is much easier but I just cannot understand what is happening here

Here, you just accept connection, you are not doing anything with received message from your React application, you send response an close connection. Its not how websockets works
this explains both of your questions: why you get new connection each time (you close connection) and why it does not work properly (its not proper WS server implementation)
As far as I know it- micropython does not have proper WS implementation. Here is something about websockets (no experience, just decided to share)
https://github.com/marcidy/micropython-uasyncio-websockets
https://github.com/miguelgrinberg/microdot/tree/main/examples/websocket
You need to get down to very basics, study WS protocol and implement it if you want to have web sockets available in your pico.
Extremely simplified WS pseodocode:
accept connection
while new messages available
read message and send response
wait for messages
close connection when connection breaks

Related

how to detect missed acknowledge in socket.io client

i used socket.io and node.js for server and i used unity socket.io for client in my game.
now, my question is, How can I be notified when client missed receive acknowledge.
for example, client emit this:
socket.Emit("testClient", data,ackCallBack);// client emit testClient to server
// get acknowledge in this callback method
public void ackCallBack(JSONObject data)
{
Debug.Log("---------ackCallBack----------" + data);
}
but i cant detect if acknowledge missed.
How to solve this problem.
I don't know much about client/server architectures but I believe socket.io use TCP, therefore if a packet is lost it is sent again.
Again I'm not 100% confident about this subject, wait for network guru to come by x)

nodemcu _ esp8266 server recieved data from android app and forward to esp8266 client

I am new programmer esp8266 with lua. I have 2 esp8266 and 1 android phone. One esp8266 is my server and another esp8266 is client. I want to send data from android app to server and server forward this data to esp8266 client. I programed server and client but i think it's wrong, the server received data from phone but not forward it to client.
The server listen on port 9000 and when received data forward it on the port 9999.and esp8266 client listen port 9999.
it is my esp8266 server code:
Can anyone help me?
wifi.setmode(wifi.SOFTAP)
wifi.ap.config({ssid="novin",pwd="12345678"})
print(wifi.ap.getip())
if sv~=nil then
sv:close()
end
function creat_server()
sv = net.createServer(net.TCP)
sv:listen(8080, function(c)
c:on("receive", function(c, pl)
if(pl~=nil) then
print(pl)
data=pl
pl=nil
end
end)
end)
if(data~=nil) then
sck(data)
data=nil
end
end
function sck(data)
sv:listen(9000,function(cc)
cc:send(data)
cc:on("receive", function(cc, dt)
print(dt)
data1=dt
end)
cc:on("sent",function(cc)
print("data send!!!!!!!!!!")
end)
end)
end
creat_server()
I saw your other question which was put on hold, your idea has a little bit problem. The esp which is server can't "Forward" data as you mean it, what I mean is that it can't be server and client at the same time, let it be server all the time. So let's review and recreate the scenario again:
You have android application which acts as a client and it will send some data to server node via POST method, there you get it and store it. you can then get the data on client node via GET method from previous server node. this is one way.
About the way you mentioned, first of all the ports in the code you have provided are different from what you have said in your question, other than that you need to first init node as SOFTAP and get the data and after that config it as STATION and send data via http module.
To simply put it, the code you have provided is too imperfect.
EDIT:
You can get all the docs and mini-examples you need from this site,
and in case you need http module, check out this part of that site.
Here's the doc indicating how to configure your wifi correctly according to your needs.
P.S. Http module has been added recently to the firmware, in case you want to use it and your IDE won't recognize it's syntax, use build cloud to build your own firmware, it will take only 5 minutes.
Also it was much easier for me to move forward with documents rather than example codes in the websites, it's up to you to chose which ever you want.

Delphi Indy TCP Client/Server communication best approach

I have a client and a server application that is communicating just fine, there is a TIdCmdTCPServer in the server and a TIdTCPClient in the client.
The client has to authenticate in the server, the client asks the server for the newest version information and downloads any updates, and other communications. All this communication with TIdTCPClient.SendCmd() and TIdTCPClient.LastCmdResult.Text.Text.
The way it is, the server receives commands and replies, the clients only receives replies, never commands, and I would like to implement a way to make the client receives commands. But as I heard, if the client uses SendCmd it should never be listening for data like ReadLn() as it would interfere with the reply expected in SendCmd.
I thought of making a command to check for commands, for example, the client would send a command like "IsThereCommandForMe" and the server would have a pool of commands to each client and when the client asks, the server send it in the reply, but I think it would not be a good approach as there would be a big delay between the commands being available and the client asking for it. I also thought of making a new connection with new components, for example a TIdCmdTcpClient, but then there would be 2 connections for each client, I don't like that idea as I think it could easily give problems in the communication.
The reason I want this, is that I want to implement a chat functionality in the client, and it should be receiving messages from the server without asking for it all the time, imagine all clients continually asking the server if there is message for them. And I would like to be able to inform the client when there is an update available instead the client being asking if there is any. And with this I could send more commands to the client too.
what are your thoughts about this ? how can I make the server receiving commands from the clients, but also sends them ?
TCP sockets are bidirectional by design. Once the connection between 'client' and 'server' has been established, they are symmetric and data can be sent at any time from any side over the same socket.
It only depends on the protocol (which is just written 'contract' for the communication) which communication model is used. HTTP for example uses a request/reply model. With Telnet for example, both sides can initate data transmissions. (If you take a look at the Indy implementation for Telnet, you will see that it uses a background thread to listen for server data, but it uses the same socket connection in the main thread to send data from client to server).
A "full duplex" protocol which supports both request/response and server push, and also is firewall-friendly, is WebSockets. With WebSockets (a HTTP upgrade), the server can send data to the connected client(s) any time. This would meet your 'chat' requirement.
If you use TIdTCPClient / TIdCmdTCPServer, corporate firewalls might block the communication.

Setting up the source Port/IP on an TCP/IP connection

I have setup a TCP/IP client/server connection that will open and close the connection every time a request is exchaged. It works perfectly; the client app opens the connection, sends the request and waits. The server application receives the request produces a response and sends it back and closes the connection. Cient and server apps do that hundreds of times.
Now I was trying to go to the next step: setup the source IP address and port.
The code was supposed to work on both Linux and Windows, so SO_BINDTODEVICE is out of question, since it is only supported on Linux/Unix.
I tried to bind the source port and ANYADRR on the client socket. And it works... For a while. Eventually it thorws error 10038. I've read over the internet several articles but without clear answer... The selection of the source IP remains unclear.
Please, note that I also have a UNICAST and MULTICAST mode on the same library (connectionless UDP communication modes), a sender and receiver, and I was able to setup the source port/IP on the MULTICAST mode, UNICAST I didn't try yet.
Anyway, anyone know anything that could be of help? I'm using WinSock 2.2 and trying to be as much as possible platform indemendent.
Winsock error 10038 is WSAENOTSOCK, which means you have a bug in your code somewhere. You are trying to do something with a SOCKET handle that is not pointing at a valid socket object. That has nothing to do with the bind() function itself. Either you are calling socket() and not checking its result for an error, or you are trying to use a SOCKET handle that has already been closed by your app, or you have a memory overflow somewhere that is corrupting your SOCKET handle.

Nodejs networking - realtime communication

I'm new to node.js and I want to ask a simple question about how it works.
I have used FMs in the past for client to client communication and real time applications. For example, for creating a collaborative application where you need to see what other users are doing. I want to explore that using NodeJS.
I have couple of questions:
1) How does NodeJs handle server-to-client communication? Is thee any way to push information to the client? or the client needs to be making requests constantly to the server to see if anything has changed?
2) Is there such thing like permanent connections between the server and the clients?
3) How Can be handle client-to-client communication (of course thru the server)?
Thanks in advance.
3) How Can be handle client-to-client
communication (of course thru the
server)?
A simple solution is to open a websocket between the server and each client :
[Client A] <==websocket==> [Server] <==websocket==> [Client B]
If you go with Socket.IO for example, it is very easy to do client-to-client communication this way.
When the server receives a message from one client, you just broadcast it to all clients or send it to one specific client depending on your use case.
Some example code using Socket.IO :
var socket = io.listen(server);
socket.on('connection', function(client) {
client.on('message', function(msg) {
broadcast(msg); // broadcast message to all clients
// OR
socket.clients[session_id].send(msg); // send message to one client
});
client.on('disconnect', function( ) {
console.log('Client Disconnected.');
});
});
Quite a lot of Node.js questions from you recently ;)
As Toby already said, Node can do HTTP, TCP/UDP and Unix Sockets. When you establish a permanent connection, you can of course push data to the clients.
Since you are talking about Browser based clients, there a numerous ways to achieve this. You could for example use WebSockets with a Flash fallback. In case you are not interested in the low level details and want a complete package, take a look at Socket.IO.
WebSockets can't do this, Flash can't do it either as far as I know. So unless you want to enter Java/Silverlight land, you'll need to route the requests through your server.