ServerCore
Repository.cs
using Model;
using ServerOnlineCity.Model;
using OCUnion;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Runtime.Serialization.Formatters.Binary;
using System.Text;
using Transfer;
using Util;
using ServerOnlineCity.Services;
namespace ServerOnlineCity
{
public clast Repository
{
private static Repository Current = new Repository();
public static Repository Get { get { return Current; } }
public static BaseContainer GetData { get { return Get.Data; } }
public static RepositorySaveData GetSaveData { get { return Get.RepSaveData; } }
public BaseContainer Data;
public bool ChangeData;
public readonly WorkTimer Timer;
public string SaveFileName;
public string SaveFolderDataPlayers => Path.Combine(Path.GetDirectoryName(SaveFileName), "DataPlayers");
private RepositorySaveData RepSaveData;
public static PlayerServer GetPlayerByLogin(string login)
{
if (string.IsNullOrEmpty(login))
{
return null;
}
Repository.GetData.PlayersAllDic.TryGetValue(login, out var res);
return res;
}
///
/// Проверка на блокировку по оборудованию.
/// Функция подверждает если ключь есть.
/// Вешает ограничение, если ключа не пришло (чтобы можно было обновить клиент и только).
/// Дисконнект, если ключь в блокировке
///
///
/// Поле с ключами между @@@. До первого разделителя игнорируется
/// Часть key до первого разделителя @@@
public static string CheckIsIntruder(ServiceContext context, string key, string login)
{
if (key == null
|| !key.Contains("@@@"))
{
context.PossiblyIntruder = true;
Loger.Log($"Is possibly intruder or not update {login} (empty key)");
return key;
}
else
{
context.IntruderKeys = "";
var keys = key.Split(new string[] { "@@@" }, StringSplitOptions.None);
for (int i = 1; i < keys.Length; i++)
{
if (string.IsNullOrEmpty(keys[i])) continue;
context.IntruderKeys += "@@@" + keys[i];
if (Repository.CheckIsIntruder(keys[i]))
{
Loger.Log($"Is intruder {login} key={keys[i]}");
context.Disconnect("intruder");
break;
}
}
Loger.Log($"Checked {login} key={key.Substring(key.IndexOf("@@@") + 3)}");
return keys[0];
}
}
private static HashSet Blockkey = null;
private static DateTime BlockkeyUpdate = DateTime.MinValue;
public static bool CheckIsIntruder(string key)
{
if ((DateTime.UtcNow - BlockkeyUpdate).TotalSeconds > 30)
{
var fileName = Loger.PathLog + "blockkey.txt";
BlockkeyUpdate = DateTime.UtcNow;
if (!File.Exists(fileName)) Blockkey = new HashSet();
else
try
{
var listBlock = File.ReadAllLines(fileName, Encoding.UTF8)
.Select(b => b.Replace("@@@", "").Trim())
.Select(b => b.Contains(" ") ? b.Substring(0, b.IndexOf(" ")) : b)
.Where(b => b != String.Empty)
.ToArray();
Blockkey = new HashSet(listBlock);
}
catch (Exception exp)
{
Loger.Log("CheckIsIntruder error " + exp.Message);
Blockkey = new HashSet();
return false;
}
}
var k = key.Replace("@@@", "").Trim();
return Blockkey.Contains(k);
}
private static HashSet Blockip = null;
private static DateTime BlockipUpdate = DateTime.MinValue;
public static bool CheckIsBanIP(string IP)
{
if ((DateTime.UtcNow - BlockipUpdate).TotalSeconds > 30)
{
var fileName = Loger.PathLog + "blockip.txt";
BlockipUpdate = DateTime.UtcNow;
if (!File.Exists(fileName)) Blockip = new HashSet();
else
try
{
var listBlock = File.ReadAllLines(fileName, Encoding.UTF8);
if (listBlock.Any(b => b.Contains("/")))
{
listBlock = listBlock
.SelectMany(b =>
{
var bb = b.Trim();
var comment = "";
var ic = bb.IndexOf(" ");
if (ic > 0)
{
comment = bb.Substring(ic);
bb = bb.Substring(0, ic);
}
if (bb.Any(c => !char.IsDigit(c) && c != '.' && c != '/')) return new List();
var ls = bb.LastIndexOf("/");
if (ls < 0) return new List() { bb + comment };
var lp = bb.LastIndexOf(".");
if (lp p.Public.Login).Aggregate((string)null, (r, i) => (r == null ? "" : r + ", ") + i)
);
ChatManager.Instance.NewChatManager(Data.MaxIdChat, Data.PlayerSystem.Chats.Keys.First());
}
}
if (needResave)
Save();
ChangeData = false;
}
private void convertToLastVersion()
{
if (Data.VersionNum < 30033)
{
ChatManager.Instance.PublicChat.PartyLogin.Clear();
foreach (var player in Data.PlayersAll)
{
player.Public.Grants = player.Public.Grants | Grants.UsualUser;
if (player.IsAdmin)
player.Public.Grants = player.Public.Grants | Grants.SuperAdmin;
//if (player.IdChats == null || !player.IdChats.Any())
//{
// player.IdChats = new HashSet() { ChatManager.PublicChatId };
//}
ChatManager.Instance.PublicChat.PartyLogin.Add(player.Public.Login);
}
}
Data.Version = MainHelper.VersionInfo;
Data.VersionNum = MainHelper.VersionNum;
}
public void Save(bool onlyChangeData = false)
{
if (onlyChangeData && !ChangeData) return;
Loger.Log("Server Saving");
try
{
if (File.Exists(SaveFileName))
{
if (File.Exists(SaveFileName + ".bak")) File.Delete(SaveFileName + ".bak");
File.Move(SaveFileName, SaveFileName + ".bak");
}
Data.MaxIdChat = ChatManager.Instance.MaxChatId;
using (var fs = File.OpenWrite(SaveFileName))
{
var bf = new BinaryFormatter();
bf.Serialize(fs, Data);
}
ChangeData = false;
}
catch
{
if (File.Exists(SaveFileName + ".bak"))
File.Copy(SaveFileName + ".bak", SaveFileName, true);
throw;
}
Loger.Log("Server Saved");
}
public static string NormalizeLogin(string login)
{
char[] invalidFileChars = Path.GetInvalidFileNameChars();
foreach (var c in invalidFileChars) if (login.Contains(c)) login = login.Replace(c, '_');
return login.ToLowerInvariant();
}
}
}