257 lines
10 KiB
C#
257 lines
10 KiB
C#
using System;
|
|
using System.Collections.Generic;
|
|
using System.Linq;
|
|
using System.Net;
|
|
using System.Text;
|
|
using System.Threading;
|
|
using System.Threading.Tasks;
|
|
|
|
namespace updateServer
|
|
{
|
|
|
|
//롤 데이터코더로부터 경기요청 및 등록정보를 요청받는다.
|
|
public class NetManager
|
|
{
|
|
const string TAG = "NETMANAGER";
|
|
|
|
HttpListener listener = null;
|
|
|
|
bool doListen = false;
|
|
|
|
Thread mListenTaskWorker = null;
|
|
|
|
ManualResetEvent mThreadCloseObserver = new ManualResetEvent(false);
|
|
|
|
internal void stop()
|
|
{
|
|
doListen = false;
|
|
listener.Stop();
|
|
mThreadCloseObserver.WaitOne();
|
|
}
|
|
|
|
internal bool IsAlive()
|
|
{
|
|
|
|
|
|
if (mListenTaskWorker == null || !mListenTaskWorker.IsAlive)
|
|
{
|
|
return false;
|
|
}
|
|
else
|
|
{
|
|
return true;
|
|
}
|
|
}
|
|
|
|
internal void start()
|
|
{
|
|
doListen = true;
|
|
Program.mMainForm.lbServerStatus.Text = "OK";
|
|
mListenTaskWorker = new Thread(listenTask);
|
|
mListenTaskWorker.IsBackground = true;
|
|
mListenTaskWorker.Start();
|
|
}
|
|
|
|
private void listenTask()
|
|
{
|
|
listener = new HttpListener();
|
|
listener.Prefixes.Clear();
|
|
listener.Prefixes.Add("http://+:60003/");
|
|
|
|
listener.AuthenticationSchemes = AuthenticationSchemes.Basic | AuthenticationSchemes.Anonymous;
|
|
|
|
listener.Start();
|
|
|
|
while (doListen)
|
|
{
|
|
try
|
|
{
|
|
var context = listener.GetContext();
|
|
HandleRequest(context);
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
|
|
}
|
|
}
|
|
|
|
|
|
mThreadCloseObserver.Set();
|
|
|
|
Program.mMainForm.Invoke(new System.Windows.Forms.MethodInvoker(() => { Program.mMainForm.lbServerStatus.Text = "CLOSE"; }));
|
|
|
|
}
|
|
|
|
//기존에 저장한 값들을 배열로 저장하여 관리한다.
|
|
List<string> beforeKeys = new List<string>();
|
|
|
|
private void HandleRequest(object state)
|
|
{
|
|
|
|
HttpListenerContext context = (HttpListenerContext)state;
|
|
|
|
HttpListenerRequest request = context.Request;
|
|
|
|
string returnValue = "";
|
|
|
|
try
|
|
{
|
|
|
|
|
|
if (request.RawUrl != "/favicon.ico")
|
|
{
|
|
|
|
returnValue = request.RawUrl;
|
|
|
|
bool isTest = false;
|
|
|
|
var bytes = Encoding.UTF8.GetBytes(returnValue);
|
|
if (returnValue.Contains("/RemoveAll"))
|
|
{
|
|
UpdateManager.getInstance().RemoveAllEventRaw();
|
|
UpdateManager.getInstance().RemoveBackup();
|
|
}
|
|
else if (returnValue.Contains("/GameInfoGet"))
|
|
{
|
|
returnValue = UpdateManager.getInstance().GameKey + Environment.NewLine + UpdateManager.getInstance().GameName;
|
|
}
|
|
else if (returnValue.Contains("/ConnectionGameKey"))
|
|
{
|
|
string mPlatformKeyName = returnValue.Split(':')[1].Replace("%7C", "|").Replace("%20", " ");
|
|
|
|
lock (UpdateManager.getInstance().mWorkerTableLocker)
|
|
{
|
|
if (!UpdateManager.getInstance().mUpdateWorkerTable.ContainsKey(mPlatformKeyName))
|
|
{
|
|
UpdateManager.getInstance().startUpdateEventRaw(mPlatformKeyName, false);
|
|
returnValue = "1_" + mPlatformKeyName + "_REQUEST_START_OK_";
|
|
}
|
|
else
|
|
{
|
|
returnValue = "2_" + mPlatformKeyName + "_UPDATED_LAST";
|
|
}
|
|
}
|
|
}
|
|
////REQUEST:게임아이디
|
|
else if (returnValue.Contains("/REAL") || returnValue.Contains("/TEST"))
|
|
{
|
|
Dictionary<string, string> reqValue = null;
|
|
if (returnValue.Contains("/REAL"))
|
|
{
|
|
isTest = false;
|
|
}
|
|
else
|
|
{
|
|
isTest = true;
|
|
}
|
|
|
|
///라이엇에 진행중인 게임리스트를 요청
|
|
reqValue = UpdateManager.getInstance().GameListUpdateWorker(isTest);
|
|
|
|
string requestGameName = returnValue.Split(':')[1].Replace("%7C", "|").Replace("%20", " ");
|
|
|
|
if (reqValue.ContainsValue(requestGameName))
|
|
{
|
|
lock (UpdateManager.getInstance().mWorkerTableLocker)
|
|
{
|
|
|
|
string mPlatformKeyName = "";
|
|
|
|
//게임리스트에서 현재 요청받은 게임이름이 있는지 찾는다.
|
|
if (reqValue.Where(r => r.Value == requestGameName).Count() > 1)
|
|
{
|
|
//이미 기존에 저장된 값이 있는지 확인하는 절차
|
|
var target = reqValue.Where(r => r.Value == requestGameName);
|
|
List<string> noneSavedKey = new List<string>();
|
|
|
|
foreach (var v in target)
|
|
{
|
|
if (!beforeKeys.Contains(v.Key)) noneSavedKey.Add(v.Key);
|
|
}
|
|
|
|
if (noneSavedKey.Count == 1)
|
|
{
|
|
// 1개만 존재하면 해당 값으로 진행
|
|
mPlatformKeyName = noneSavedKey[0];
|
|
beforeKeys.Add(mPlatformKeyName);
|
|
}
|
|
else if (noneSavedKey.Count == 0)
|
|
{
|
|
//카운트가 0이면, target의 key 중에서 beforeKeys에 인덱스가 가장 높은 값으로 진행한다.
|
|
int maxIndex = -1;
|
|
foreach (var key in target.Select(x => x.Key))
|
|
{
|
|
int idx = beforeKeys.IndexOf(key);
|
|
if (idx > maxIndex)
|
|
{
|
|
maxIndex = idx;
|
|
mPlatformKeyName = key;
|
|
}
|
|
}
|
|
}
|
|
else
|
|
{
|
|
// 새로운 키가 2개 이상이면, 새로 발견된 키들을 모두 등록하고
|
|
// 마지막 키를 선택
|
|
foreach (var key in noneSavedKey)
|
|
{
|
|
beforeKeys.Add(key);
|
|
}
|
|
mPlatformKeyName = noneSavedKey.Last();
|
|
}
|
|
|
|
//기존 방식 : 가장 최근의 값으로 진행
|
|
//mPlatformKeyName = reqValue.LastOrDefault(x => x.Value == requestGameName).Key;
|
|
|
|
}
|
|
else if (reqValue.Where(r => r.Value == requestGameName).Count() == 1)
|
|
{
|
|
mPlatformKeyName = reqValue.FirstOrDefault(x => x.Value == requestGameName).Key;
|
|
if (!beforeKeys.Contains(mPlatformKeyName)) beforeKeys.Add(mPlatformKeyName);
|
|
}
|
|
|
|
//현재 받고있는 게임중에 클라이언트와 라이엇에서 요청받는게 중복되는지 확인한다.
|
|
if (!UpdateManager.getInstance().mUpdateWorkerTable.ContainsKey(mPlatformKeyName))
|
|
{
|
|
UpdateManager.getInstance().startUpdateEventRaw(mPlatformKeyName, false);
|
|
returnValue = "1_" + mPlatformKeyName + "_REQUEST_START_OK_";
|
|
}
|
|
else
|
|
{
|
|
returnValue = "2_" + mPlatformKeyName + "_UPDATED_LAST";
|
|
}
|
|
}
|
|
}
|
|
//라이엇에서 클라이언트가 요청한 게임아이디가 없는경우.
|
|
else
|
|
{
|
|
returnValue = "3_" + requestGameName + "_CANT_FIND_GAME";
|
|
}
|
|
|
|
}
|
|
//클라이언트의 요청 자체가 이상한 경우.
|
|
else
|
|
{
|
|
returnValue = "4_" + returnValue + "_ELIGAL_REQUEST";
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
//알수없는에러
|
|
Console.WriteLine(ex.ToString());
|
|
returnValue = "5_BAD_SERVER_STATS_" + ex.ToString();
|
|
}
|
|
|
|
var rtnbytes = Encoding.UTF8.GetBytes(returnValue);
|
|
|
|
context.Response.OutputStream.Write(rtnbytes, 0, rtnbytes.Length);
|
|
context.Response.OutputStream.Flush();
|
|
context.Response.OutputStream.Close();
|
|
}
|
|
|
|
}
|
|
}
|