示例#1
0
        /// <summary>
        /// Określa jaka odpowiedź ma być zwrócona do klienta w przypadku nieudanej autoryzacji
        /// </summary>
        /// <returns>Obiekt JSON do przekazania do klienta</returns>
        protected virtual JObject GetAuthorizationResponseFailed()
        {
            var resp = new StandardResponseSerializer()
            {
                Status  = "FORBIDDEN",
                Message = "Authorization failed"
            };

            return(resp.GetApiObject());
        }
示例#2
0
        /// <summary>
        /// Określa jaka odpowiedź ma być zwrócona do klienta w przypadku udanej autoryzacji
        /// </summary>
        /// <returns>Obiekt JSON do przekazania do klienta</returns>
        protected virtual JObject GetAuthorizationResponseSuccessful()
        {
            var resp = new StandardResponseSerializer()
            {
                Status  = "OK",
                Message = "Authorization successful"
            };

            return(resp.GetApiObject());
        }
示例#3
0
        /// <summary>
        /// Treść komunikatu przy odłączeniu klienta od serwera przez zbyt długi czas autoryzacji
        /// </summary>
        /// <returns>Obiekt JSON do przekazania do klienta</returns>
        protected virtual JObject GetAuthorizationTimeoutSignal()
        {
            var resp = new StandardResponseSerializer()
            {
                Status  = "AUTHORIZATION_TIMEOUT",
                Message = "Authorization failed - timeout"
            };
            var result = new StandardCommunicateSerializer()
            {
                CommunicateType = StandardCommunicateSerializer.TYPE_AUTHORIZATION,
                Data            = resp.GetApiObject()
            };

            return(result.GetApiObject());
        }
示例#4
0
        /// <summary>
        /// Treść komunikatu przy odłączeniu klienta od serwera
        /// </summary>
        /// <returns>Obiekt JSON do przekazania do klienta</returns>
        protected virtual JObject GetDisconnectedSignal()
        {
            var resp = new StandardResponseSerializer()
            {
                Status  = "DISCONNECTED",
                Message = "You have been disconnected"
            };
            var result = new StandardCommunicateSerializer()
            {
                CommunicateType = StandardCommunicateSerializer.TYPE_SERVER_SIGNAL,
                Data            = resp.GetApiObject()
            };

            return(result.GetApiObject());
        }
示例#5
0
        private void Listen()
        {
            TcpListener = new TcpListener(IpAddress, Port);
            TcpListener.Start();

            List <ClientConnection> toRemove            = new List <ClientConnection>();
            List <ClientConnection> currentlyAuthorized = new List <ClientConnection>();

            while (true)
            {
                // Komunikaty
                toRemove.Clear();
                foreach (var connection in AuthorizedConnections)
                {
                    try {
                        connection.SendCommunicates();
                    } catch (IOException) {
                        toRemove.Add(connection);
                    } catch (ObjectDisposedException) {
                        toRemove.Add(connection);
                    } catch (InvalidOperationException) {
                        toRemove.Add(connection);
                    } catch (Exception) {
                        Console.WriteLine("Nie można było wysłać komunikatów do klienta: " + connection.ToString());
                    }
                }
                // Usuwanie zamkniętych połączeń
                foreach (var connection in toRemove)
                {
                    connection.Dispose();
                    AuthorizedConnections.Remove(connection);
                }
                toRemove.Clear();
                foreach (var connection in UnauthorizedConnections)
                {
                    try {
                        connection.SendCommunicates();
                    } catch (IOException) {
                        toRemove.Add(connection);
                    } catch (ObjectDisposedException) {
                        toRemove.Add(connection);
                    } catch (InvalidOperationException) {
                        toRemove.Add(connection);
                    } catch (Exception) {
                        Console.WriteLine("Nie można było wysłać komunikatów do klienta: " + connection.ToString());
                    }
                }
                // Usuwanie zamkniętych połączeń
                foreach (var connection in toRemove)
                {
                    connection.Dispose();
                    UnauthorizedConnections.Remove(connection);
                }

                // Zautoryzowane połączenia
                bool canContinue;
                toRemove.Clear();
                foreach (var connection in AuthorizedConnections)
                {
                    if (connection.DataAvailable)
                    {
                        connection.LastActivateAt = DateTime.Now;
                        JObject data = connection.GetData();
                        JObject response;
                        canContinue = true;

                        // Inicjalna walidacja (Bierzemy kod zapytania, jeśli został podany)
                        var initialCheck = new StandardRequestSerializer(data);
                        try {
                            initialCheck.Validate();
                        } catch (ValidationException) {
                            // Inicjalny format nie przechodzi sprawdzenia
                            var result = new StandardCommunicateSerializer();
                            var resp   = new StandardResponseSerializer();

                            result.CommunicateType = StandardCommunicateSerializer.TYPE_REQUEST_ERROR;
                            resp.Status            = "INVALID_FORMAT";
                            resp.Message           = "Request failed initial validation";
                            result.Data            = resp.GetApiObject();

                            response = result.GetApiObject();
                            connection.WriteData(response);
                            connection.Flush();

                            canContinue = false;
                        }

                        if (canContinue)
                        {
                            try {
                                try {
                                    var resp        = HandleRequest(connection, initialCheck.Data);
                                    var respWrapper = new StandardCommunicateSerializer()
                                    {
                                        CommunicateType = StandardCommunicateSerializer.TYPE_RESPONSE,
                                        RequestCode     = initialCheck.RequestCode,
                                        Data            = resp
                                    };
                                    response = respWrapper.GetApiObject();
                                } catch (ValidationException e) {
                                    var resp        = e.GetJson();
                                    var respWrapper = new StandardCommunicateSerializer()
                                    {
                                        CommunicateType = StandardCommunicateSerializer.TYPE_RESPONSE,
                                        RequestCode     = initialCheck.RequestCode,
                                        Data            = resp
                                    };
                                    response = respWrapper.GetApiObject();
                                }
                            } catch (Exception e) {
                                var resp = new StandardResponseSerializer()
                                {
                                    Status  = "ERR_INTERNAL",
                                    Message = "Wystąpił wewnętrzny błąd serwera"
                                };
                                var respWrapper = new StandardCommunicateSerializer()
                                {
                                    CommunicateType = StandardCommunicateSerializer.TYPE_REQUEST_ERROR,
                                    RequestCode     = initialCheck.RequestCode,
                                    Data            = resp.GetApiObject()
                                };
                                response = respWrapper.GetApiObject();
                            }

                            try {
                                connection.WriteData(response);
                                connection.Flush();
                            } catch (IOException) {
                                toRemove.Add(connection);
                            } catch (InvalidOperationException) {
                                toRemove.Add(connection);
                            }
                        }
                    }
                    else if (TimeSpan.Compare(DateTime.Now - connection.LastActivateAt, MaxIdleTime) > 0)
                    {
                        Console.WriteLine("IDLE CHECK");
                        connection.LastActivateAt = DateTime.Now;
                        var wrappedResponse = new StandardCommunicateSerializer()
                        {
                            CommunicateType = StandardCommunicateSerializer.TYPE_CONNECTION_CHECK,
                            RequestCode     = -1,
                            Data            = null
                        };
                        try {
                            connection.WriteData(wrappedResponse.GetApiObject());
                        } catch (IOException) {
                            toRemove.Add(connection);
                        } catch (ObjectDisposedException) {
                            toRemove.Add(connection);
                        } catch (InvalidOperationException) {
                            toRemove.Add(connection);
                        } catch (Exception) {
                            Console.WriteLine("Nie można było wysłać komunikatów do klienta: " + connection.ToString());
                        }
                    }
                }

                // Usuwanie zamkniętych połączeń
                foreach (var connection in toRemove)
                {
                    connection.Dispose();
                    AuthorizedConnections.Remove(connection);
                }

                // Niezautoryzowane połączenia
                toRemove.Clear();
                foreach (var connection in UnauthorizedConnections)
                {
                    bool authorized = false;
                    if (connection.DataAvailable)
                    {
                        canContinue = true;
                        JObject data         = connection.GetData();
                        var     initialCheck = new StandardRequestSerializer(data);
                        try {
                            try {
                                initialCheck.Validate();
                            } catch (ValidationException e) {
                                var wrappedResponse = new StandardCommunicateSerializer()
                                {
                                    CommunicateType = StandardCommunicateSerializer.TYPE_AUTHORIZATION,
                                    RequestCode     = initialCheck.RequestCode,
                                    Data            = GetAuthorizationResponseFailed()
                                };
                                connection.WriteData(wrappedResponse.GetApiObject());
                                connection.Flush();
                                canContinue = false;
                            }
                            if (canContinue)
                            {
                                // Zero zaufania do niezautoryzowanych połączeń
                                try {
                                    if (AuthorizeConnection(connection, initialCheck.Data))
                                    {
                                        var response        = GetAuthorizationResponseSuccessful();
                                        var wrappedResponse = new StandardCommunicateSerializer()
                                        {
                                            CommunicateType = StandardCommunicateSerializer.TYPE_AUTHORIZATION,
                                            RequestCode     = initialCheck.RequestCode,
                                            Data            = response
                                        };
                                        authorized = true;

                                        // Informacja dla odbiorcy o poprawnej autoryzacji
                                        connection.WriteData(wrappedResponse.GetApiObject());
                                        connection.Flush();

                                        connection.LastActivateAt = DateTime.Now;

                                        currentlyAuthorized.Add(connection);
                                    }
                                    else
                                    {
                                        var response        = GetAuthorizationResponseFailed();
                                        var wrappedResponse = new StandardCommunicateSerializer()
                                        {
                                            CommunicateType = StandardCommunicateSerializer.TYPE_AUTHORIZATION,
                                            RequestCode     = initialCheck.RequestCode,
                                            Data            = response
                                        };
                                        connection.WriteData(wrappedResponse.GetApiObject());
                                        connection.Flush();
                                    }
                                } catch (ValidationException e) {
                                    var wrappedResponse = new StandardCommunicateSerializer()
                                    {
                                        CommunicateType = StandardCommunicateSerializer.TYPE_AUTHORIZATION,
                                        RequestCode     = initialCheck.RequestCode,
                                        Data            = GetAuthorizationResponseFailed()
                                    };
                                    connection.WriteData(wrappedResponse.GetApiObject());
                                    connection.Flush();
                                }
                            }
                        } catch (IOException e) {
                            // Połączenie socketu rozłączone
                            toRemove.Add(connection);
                        } catch (ObjectDisposedException e) {
                            // Połączenie socketu rozłączone
                            toRemove.Add(connection);
                        } catch (InvalidOperationException) {
                            toRemove.Add(connection);
                        } catch (Exception e) {
                            Console.WriteLine("Nieobsłużony wyjątek dla zapytania od połączenia " + connection.ToString() + "\n" + e.ToString());
                        }
                    }
                    if (!authorized && TimeSpan.Compare(connection.GetConnectionTime(), TimeForAuthorization) > 0)
                    {
                        connection.WriteData(GetAuthorizationTimeoutSignal());
                        connection.Flush();

                        connection.TcpClient.Close();
                        toRemove.Add(connection);
                    }
                }

                // Finalizacja przenoszenie połączenia po zautoryzowaniu lub zamknięciu
                foreach (var connection in currentlyAuthorized)
                {
                    UnauthorizedConnections.Remove(connection);
                    AuthorizedConnections.Add(connection);
                }
                currentlyAuthorized.Clear();
                foreach (var connection in toRemove)
                {
                    connection.Dispose();
                    UnauthorizedConnections.Remove(connection);
                }

                // Odłączanie klientów do odłączenia
                foreach (var connection in ClientsToDisconnect)
                {
                    if (AuthorizedConnections.Contains(connection))
                    {
                        try {
                            connection.WriteData(GetDisconnectedSignal());
                            connection.Flush();
                        } catch (Exception) { }

                        connection.Dispose();
                        AuthorizedConnections.Remove(connection);
                    }
                    else if (UnauthorizedConnections.Contains(connection))
                    {
                        try {
                            connection.WriteData(GetDisconnectedSignal());
                            connection.Flush();
                        } catch (Exception) { }

                        connection.Dispose();
                        UnauthorizedConnections.Remove(connection);
                    }
                }

                // Nowe połączenia
                HandleIncommingConnections();
            }
        }