我无法使用Chrome应用程序通过TCP连接从服务器接收数据。我没有获得onReceived事件。它只是第二次工作,但不是第一次。我复制了文档中的所有内容,但代码不起作用,我不知道出了什么问题。我可以看到我的'ABCDEFGHI'字符串是由服务器在tcpdump窗口中发送的,但由于某些原因Chrome没有得到它。此示例中的错误完全可重现。以下是文件:
THE APP
[niko@dev1 nettest]$ ls -l
total 16
-rw-rw-r-- 1 niko niko 174 Aug 6 16:10 background.js
-rw-rw-r-- 1 niko niko 208 Aug 6 16:11 main.html
-rw-rw-r-- 1 niko niko 928 Aug 6 16:54 main.js
-rw-rw-r-- 1 niko niko 281 Aug 6 16:10 manifest.json
[niko@dev1 nettest]$
的manifest.json:
[niko@dev1 nettest]$ cat manifest.json
{
"name": "Receive Test",
"description": "Network receive test App.",
"version": "0.1",
"manifest_version": 2,
"app": {
"background": {
"scripts": ["background.js"]
}
},
"icons": {
},
"sockets": {
"tcp" : {
"connect": ["*"]
}
}
}
[niko@dev1 nettest]$
background.js:
[niko@dev1 nettest]$ cat background.js
chrome.app.runtime.onLaunched.addListener(function() {
chrome.app.window.create('main.html', {
'outerBounds': {
'width': 400,
'height': 500
}
});
});
[niko@dev1 nettest]$
main.html中:
[niko@dev1 nettest]$ cat main.html
<!DOCTYPE html>
<html>
<head>
<script type="text/javascript" src="/main.js"></script>
</head>
<body>
<div>Networking test app</div>
<a href="" id="connect_btn">conect</a>
</body>
</html>
[niko@dev1 nettest]$
main.js:
[niko@dev1 nettest]$ cat main.js
var socket;
window.addEventListener("load",init);
function init() {
var el;
el=document.getElementById('connect_btn');
if (el!=null) el.addEventListener("click",connect_click);
}
function connect_click(event) {
event.preventDefault();
chrome.sockets.tcp.create({}, function(createInfo) {
socket=createInfo.socketId;
chrome.sockets.tcp.setPaused(socket, false);
chrome.sockets.tcp.connect(socket,"localhost", 4433, connect_callback);
});
}
function connect_callback(info) {
console.log("connection accepted: "+info);
chrome.sockets.tcp.setPaused(socket, false);
chrome.sockets.tcp.onReceiveError.addListener(receive_error);
chrome.sockets.tcp.onReceive.addListener(data_received);
}
function data_received(info) {
console.log("the data has been received:");
console.log(info);
}
function receive_error(info) {
console.log("receive error");
console.log(info);
}
[niko@dev1 nettest]$
服务器代码:
[niko@dev1 src]$ cat server.c
#include <sys/socket.h>
#include <netinet/in.h>
#include <netinet/tcp.h>
#include <arpa/inet.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <errno.h>
#include <string.h>
#include <sys/types.h>
int main(int argc, char *argv[])
{
int flag=1;
int listenfd = 0, connfd = 0;
struct sockaddr_in serv_addr;
char data[10] = {'A','B','C','D','E','F','G','H','I','\n'};
int result;
listenfd = socket(AF_INET, SOCK_STREAM, 0);
memset(&serv_addr, '0', sizeof(serv_addr));
result = setsockopt(listenfd,IPPROTO_TCP,TCP_NODELAY,(char *) &flag, sizeof(int));
if (result<0) {
printf("result=%d\n",result);
return (1);
}
serv_addr.sin_family = AF_INET;
serv_addr.sin_addr.s_addr = htonl(INADDR_ANY);
serv_addr.sin_port = htons(4433);
bind(listenfd, (struct sockaddr*)&serv_addr, sizeof(serv_addr));
listen(listenfd, 10);
while(1)
{
connfd = accept(listenfd, (struct sockaddr*)NULL, NULL);
result = setsockopt(connfd,IPPROTO_TCP,TCP_NODELAY,(char *) &flag, sizeof(int));
if (result<0) {
printf("result=%d\n",result);
return (1);
}
printf("connection accepted, sending data\n");
write(connfd, &data, sizeof(data));
sleep(5);
close(connfd);
printf("connection closed\n");
sleep(1);
}
}
[niko@dev1 src]$
当我运行代码时,这是输出:
connection accepted: 0
main.js:31 receive error
main.js:32 Object {resultCode: -100, socketId: 18}
main.js:20 connection accepted: 0
main.js:27 the data has been received:
main.js:28 Object {data: ArrayBuffer, socketId: 19}
main.js:27 the data has been received:
main.js:28 Object {data: ArrayBuffer, socketId: 19}
main.js:31 receive error
main.js:32 Object {resultCode: -100, socketId: 19}
关于什么可能出错的任何想法?
答案 0 :(得分:0)
我发现了什么问题。必须在创建套接字后立即注册onReceived处理程序。否则,会发生什么:客户端发送SYN,但服务器回复ACK +数据。当Chrome获取此数据包时,它还没有设置onReceived处理程序,因此第一个数据包中的数据将丢失。 connect_click()函数必须像这样重写:
function connect_click(event) {
event.preventDefault();
chrome.sockets.tcp.create({}, function(createInfo) {
socket=createInfo.socketId;
chrome.sockets.tcp.setPaused(socket, false );
chrome.sockets.tcp.connect(socket,"localhost", 4433, connect_callback);
chrome.sockets.tcp.onReceive.addListener(data_received);
chrome.sockets.tcp.onReceiveError.addListener(receive_error);
});
}