Пример #1
0
        public async Task <Session> GetSessionAsync(IPEndPoint endpoint)
        {
            if (endpoint == null)
            {
                throw new ArgumentNullException(nameof(endpoint),
                                                ResourceStrings.DatabaseCache_GetSessionAsync_NullEndpointException);
            }

            await using var ctx = new UchuContext();

            string key;
            var    timeout = 1000;

            while (!_keys.TryGetValue(endpoint.ToString(), out key))
            {
                if (timeout <= 0)
                {
                    throw new TimeoutException();
                }

                await Task.Delay(50).ConfigureAwait(false);

                timeout -= 50;
            }

            var session = ctx.SessionCaches.First(s => s.Key == key);

            return(new Session
            {
                Key = key,
                CharacterId = session.CharacterId,
                UserId = session.UserId,
                ZoneId = session.ZoneId
            });
        }
Пример #2
0
        public InventoryItem FindItem()
        {
            using var ctx = new UchuContext();

            var id = (long)Value;

            return(ctx.InventoryItems.FirstOrDefault(
                       i => i.Id == id
                       ));
        }
Пример #3
0
        public async Task <InventoryItem> FindItemAsync()
        {
            await using var ctx = new UchuContext();

            var id = (long)Value;

            return(await ctx.InventoryItems.FirstOrDefaultAsync(
                       i => i.Id == id
                       ).ConfigureAwait(false));
        }
Пример #4
0
        public void SetZone(IPEndPoint endpoint, ZoneId zone)
        {
            using var ctx = new UchuContext();

            var key = _keys[endpoint.ToString()];

            var session = ctx.SessionCaches.First(s => s.Key == key);

            session.ZoneId = (int)zone;

            ctx.SaveChanges();
        }
Пример #5
0
        public void CreateSession(long userId, string key)
        {
            using var ctx = new UchuContext();

            ctx.SessionCaches.Add(new SessionCache
            {
                Key    = key,
                UserId = userId
            });

            ctx.SaveChanges();
        }
Пример #6
0
        public void SetCharacter(IPEndPoint endpoint, long characterId)
        {
            using var ctx = new UchuContext();

            var key = _keys[endpoint.ToString()];

            var session = ctx.SessionCaches.First(s => s.Key == key);

            session.CharacterId = characterId;

            ctx.SaveChanges();
        }
Пример #7
0
        public void DeleteSession(IPEndPoint endpoint)
        {
            using var ctx = new UchuContext();

            var key = _keys[endpoint.ToString()];

            var session = ctx.SessionCaches.First(s => s.Key == key);

            ctx.SessionCaches.Remove(session);

            ctx.SaveChanges();
        }
Пример #8
0
        public void SetZone(IPEndPoint endpoint, ZoneId zone)
        {
            if (endpoint == null)
            {
                throw new ArgumentNullException(nameof(endpoint),
                                                ResourceStrings.DatabaseCache_SetZone_NullEndpointException);
            }

            using var ctx = new UchuContext();
            var key     = _keys[endpoint.ToString()];
            var session = ctx.SessionCaches.First(s => s.Key == key);

            session.ZoneId = zone;

            ctx.SaveChanges();
        }
Пример #9
0
        public string CreateSession(long userId)
        {
            using var ctx = new UchuContext();

            var key = GenerateKey();

            ctx.SessionCaches.Add(new SessionCache
            {
                Key    = key,
                UserId = userId
            });

            ctx.SaveChanges();

            return(key);
        }
Пример #10
0
        public Session GetSession(IPEndPoint endpoint)
        {
            using var ctx = new UchuContext();

            var key = _keys[endpoint.ToString()];

            var session = ctx.SessionCaches.First(s => s.Key == key);

            return(new Session
            {
                Key = key,
                CharacterId = session.CharacterId,
                UserId = session.UserId,
                ZoneId = session.ZoneId
            });
        }
Пример #11
0
        public void DeleteSession(IPEndPoint endpoint)
        {
            if (endpoint == null)
            {
                throw new ArgumentNullException(nameof(endpoint),
                                                ResourceStrings.DatabaseCache_DeleteSession_NullEndpointException);
            }

            using var ctx = new UchuContext();

            var key     = _keys[endpoint.ToString()];
            var session = ctx.SessionCaches.First(s => s.Key == key);

            ctx.SessionCaches.Remove(session);

            ctx.SaveChanges();
        }
Пример #12
0
        public virtual async Task ConfigureAsync(string configFile)
        {
            MasterPath = Path.GetDirectoryName(configFile);

            var serializer = new XmlSerializer(typeof(Configuration));

            if (!File.Exists(configFile))
            {
                throw new ArgumentException($"{configFile} config file does not exist.");
            }

            await using (var fs = File.OpenRead(configFile))
            {
                Logger.Config = Config = (Configuration)serializer.Deserialize(fs);

                UchuContextBase.Config = Config;
            }

            if (!string.IsNullOrWhiteSpace(Config.ResourcesConfiguration?.GameResourceFolder))
            {
                Resources = new LocalResources(Config);
            }

            ServerSpecification specification;

            await using (var ctx = new UchuContext())
            {
                specification = ctx.Specifications.First(s => s.Id == Id);
            }

            Port = specification.Port;

            ServerSpecification = specification;

            var certificateFilePath = Path.Combine(MasterPath, Config.Networking.Certificate);

            if (Config.Networking?.Certificate != default && File.Exists(certificateFilePath))
            {
                var cert = new X509Certificate2(certificateFilePath);

                Console.WriteLine($"PRIVATE KEY: {cert.HasPrivateKey} {cert.PrivateKey}");

                Certificate = cert;

                RakNetServer = new TcpUdpServer(Port, "3.25 ND1", Certificate, 150);
            }
            else
            {
                RakNetServer = new TcpUdpServer(Port, "3.25 ND1");
            }

            try
            {
                SessionCache = new RedisSessionCache();
            }
            catch (RedisConnectionException)
            {
                Logger.Error("Failed to establish Redis connection, falling back to database.");

                SessionCache = new DatabaseCache();
            }

            Logger.Information($"Server {Id} configured on port: {Port}");
        }
Пример #13
0
        public async Task StartAsync(Assembly assembly, bool acceptConsoleCommands = false)
        {
            Logger.Information("Registering assemblies...");

            RegisterAssembly(typeof(Server).Assembly);
            RegisterAssembly(assembly);

            RakNetServer.MessageReceived += HandlePacketAsync;

            Running = true;

            if (acceptConsoleCommands)
            {
                var _ = Task.Run(async() =>
                {
                    Logger.Information($"Ready to accept console command...");

                    while (Running)
                    {
                        var command = Console.ReadLine();

                        if (string.IsNullOrWhiteSpace(command))
                        {
                            continue;
                        }

                        Console.WriteLine(await HandleCommandAsync(command, null, GameMasterLevel.Console).ConfigureAwait(false));
                    }
                });
            }

            try
            {
                Logger.Information("Looking for requests...");

                await using (var ctx = new UchuContext())
                {
                    var request = ctx.WorldServerRequests.FirstOrDefault(w => w.SpecificationId == Id);

                    if (request == default)
                    {
                        Logger.Information($"Starting server...");

                        await RakNetServer.RunAsync().ConfigureAwait(false);

                        return;
                    }

                    Logger.Information($"Request found for {Id}");

                    request.State = WorldServerRequestState.Complete;

                    ctx.SaveChanges();
                }

                Logger.Information($"Starting server...");

                await RakNetServer.RunAsync().ConfigureAwait(false);
            }
            catch (Exception e)
            {
                Logger.Error(e);
            }
        }
Пример #14
0
 public bool IsKey(string key)
 {
     using var ctx = new UchuContext();
     return(ctx.SessionCaches.Any(c => c.Key == key));
 }
Пример #15
0
        public static async Task <ServerSpecification> RequestWorldServerAsync(ZoneId zoneId)
        {
            //
            // Check for servers
            //

            var worldServers = await GetServersByType(ServerType.World).ConfigureAwait(false);

            foreach (var worldServer in worldServers.Where(w => w.ZoneId == zoneId))
            {
                if (worldServer.ActiveUserCount >= worldServer.MaxUserCount)
                {
                    continue;
                }

                return(worldServer);
            }

            //
            // Start a new world server request.
            //

            var id = Guid.NewGuid();

            await using (var ctx = new UchuContext())
            {
                await ctx.WorldServerRequests.AddAsync(new WorldServerRequest
                {
                    Id     = id,
                    ZoneId = zoneId
                }).ConfigureAwait(false);

                await ctx.SaveChangesAsync().ConfigureAwait(false);
            }

            //
            // We have to have a timeout here, if the new server instance stops unexpectedly of whatever.
            //

            var timeout = 1000;

            while (timeout != default)
            {
                //
                // Get request.
                //

                await using var ctx = new UchuContext();

                var request = await ctx.WorldServerRequests.FirstAsync(
                    r => r.Id == id
                    ).ConfigureAwait(false);

                //
                // Check request state
                //

                switch (request.State)
                {
                case WorldServerRequestState.Unanswered:
                case WorldServerRequestState.Answered:
                    timeout--;

                    await Task.Delay(100).ConfigureAwait(false);

                    continue;

                case WorldServerRequestState.Complete:
                    break;

                case WorldServerRequestState.Error:
                    return(default);

                default:
                    return(default);
                }

                Logger.Information($"Request completed {id} {request.SpecificationId}");

                //
                // Finalize request.
                //

                ctx.WorldServerRequests.Remove(request);

                await ctx.SaveChangesAsync().ConfigureAwait(false);

                var specification = await ctx.Specifications.FirstAsync(s => s.Id == request.SpecificationId).ConfigureAwait(false);

                return(specification);
            }

            Logger.Error($"Request {id} timed out");

            return(default);