/// <summary> /// Used internally to notify the app that a connection has been closed. /// </summary> internal void ConnectionClosed(FCGIStream connection) { if (connection != null && OpenConnections.Contains(connection)) { OpenConnections.Remove(connection); } }
/// <summary> /// Processes all data available on the current FastCGI connection and handles the received data. /// </summary> /// <remarks> /// Call this repeatedly to process incoming requests. /// Alternatively, you can call <see cref="Run(int)"/> once, which will call <see cref="Listen(int)"/> and execute this method in an infinite loop. /// Internally, this method manages reconnections on the network socket and calls <see cref="ProcessSingleRecord(Stream, Stream)"/>. /// Returns true if a record was read, false otherwise. /// </remarks> public bool Process() { // When listening, but not currently connected, and not yet waiting for an incoming connection, start the connection accept if (ListeningSocket != null && AcceptAsyncResult == null) { AcceptAsyncResult = ListeningSocket.BeginAccept((r) => { AcceptIsReady = true; }, null); } if (AcceptAsyncResult != null && AcceptAsyncResult.IsCompleted) { var connection = ListeningSocket.EndAccept(AcceptAsyncResult); AcceptIsReady = false; AcceptAsyncResult = ListeningSocket.BeginAccept((r) => { AcceptIsReady = true; }, null); var stream = new FCGIStream(connection); OpenConnections.Add(stream); ApplyTimeoutSetting(); } bool readARecord = false; var currentConnections = OpenConnections.ToArray(); foreach (var stream in currentConnections) { if (!stream.IsConnected) { OpenConnections.Remove(stream); } else { readARecord |= ProcessStream(stream, stream); } } return(readARecord); }
/// <summary> /// Used internally to notify the app that a connection has been closed. /// </summary> internal void ConnectionClosed(FCGIStream connection) { OpenConnections.Remove(connection); connection.Socket.Disconnect(false); connection.Socket.Close(); }