【发布时间】:2017-01-07 14:21:55
【问题描述】:
我想使用套接字连接到服务。当我使用 Socket.Connect 时,响应是 200 ok,我可以成功接收数据,但是当我使用 Socket.ConnectAsync 时,响应是 400 bad request。
这里是 Socket.Connect 的代码:
SocketAsyncEventArgs myev;
private void Receive(SocketAsyncEventArgs e)
{
myev = e;
SocketAsyncEventArgs readEventArgs = m_readWritePool.Pop();
readEventArgs.RemoteEndPoint = remote;
Socket connectSocket;
connectSocket = new Socket(remote.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
connectSocket.Connect(remote);//Sync Connect
ProcessConnect(readEventArgs);
}
private void ProcessConnect(SocketAsyncEventArgs e)
{
AsyncUserToken token = (AsyncUserToken)myev.UserToken;
if (myev.BytesTransferred > 0 && myev.SocketError == SocketError.Success)
{
e.SetBuffer(myev.Offset, myev.BytesTransferred);
bool willRaiseEvent = ((AsyncUserToken)e.UserToken).Socket.SendAsync(e);
if (!willRaiseEvent)
{
ProcessServerSend(e);
}
}
else
{
CloseClientSocket(e);
}
}
这里是 Socket.ConnectAsync 的代码:
SocketAsyncEventArgs myev;
private void Receive(SocketAsyncEventArgs e)
{
myev = e;
SocketAsyncEventArgs readEventArgs = m_readWritePool.Pop();
readEventArgs.RemoteEndPoint = remote;
Socket connectSocket;
connectSocket = new Socket(remote.AddressFamily, SocketType.Stream, ProtocolType.Tcp);
((AsyncUserToken)readEventArgs.UserToken).Socket = connectSocket;
bool willRaiseEvent = connectSocket.ConnectAsync(readEventArgs);//Async Connect
if (!willRaiseEvent)
{
ProcessConnect(readEventArgs);
}
}
private void ProcessConnect(SocketAsyncEventArgs e)
{
AsyncUserToken token = (AsyncUserToken)myev.UserToken;
if (myev.BytesTransferred > 0 && myev.SocketError == SocketError.Success)
{
e.SetBuffer(myev.Offset, myev.BytesTransferred);
bool willRaiseEvent = ((AsyncUserToken)e.UserToken).Socket.SendAsync(e);
if (!willRaiseEvent)
{
ProcessServerSend(e);
}
}
else
{
CloseClientSocket(e);
}
}
请注意,我们已将 m_readWritePool 定义为 SocketAsyncEventArgsPool m_readWritePool; 并填充了 1000 个项目。
我们已将ProcessServerSend 定义为:
private void ProcessServerSend(SocketAsyncEventArgs e)
{
if (e.SocketError == SocketError.Success)
{
AsyncUserToken token = (AsyncUserToken)e.UserToken;
SocketAsyncEventArgs readEventArgs = m_readWritePool.Pop();
((AsyncUserToken)readEventArgs.UserToken).Socket = token.Socket;
bool willRaiseEvent = token.Socket.ReceiveAsync(readEventArgs);
if (!willRaiseEvent)
{
ProcessServerReceive(readEventArgs);
}
}
else
{
CloseServerSocket(e);
}
}
而ProcessServerReceive 是:
private void ProcessServerReceive(SocketAsyncEventArgs e)
{
AsyncUserToken token = (AsyncUserToken)myev.UserToken;
if (e.BytesTransferred > 0 && e.SocketError == SocketError.Success)
{
myev.SetBuffer(e.Offset, e.BytesTransferred);
byte[] buf = new byte[e.BytesTransferred];
for (int i = 0; i < e.BytesTransferred; i++)
{
buf[i] = e.Buffer[e.Offset + i];
}
string message = Encoding.UTF8.GetString(buf);
//The message contains '200 ok' or '400 bad request' when using Connect or ConnectAsync respectively.
bool willRaiseEvent = token.Socket.SendAsync(myev);
if (!willRaiseEvent)
{
ProcessSend(myev);
}
}
else
{
CloseServerSocket(e);
}
}
请注意,除了连接方法之外,所有功能都相同!我检查了发送的消息是否相同!
更新:
回复是:
错误请求 - 无效动词
HTTP 错误 400。请求动词无效。
【问题讨论】:
-
你在哪里将 myev 传递给异步连接方法?
-
@jdweng 实际上我正在使用此代码从套接字 A 获取数据并将其发送到另一个套接字 B 并接收来自 B 的响应并将其发送回 A。
myev是一个 @ 987654330@专门用于接收来自A的数据,所以为了连接到B我定义了一个新的。