초기 커밋.

This commit is contained in:
2026-04-01 20:20:09 +09:00
parent c286f362e5
commit fd1a2cba32
172 changed files with 43588 additions and 0 deletions

View File

@@ -0,0 +1,6 @@
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.7.2" />
</startup>
</configuration>

View File

@@ -0,0 +1,34 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace updateServer
{
internal class DEFINE
{
//VSPN접근키
internal const string RIOT_API_KEY = "x-api-key:N1TFxzzmYk5E5sByoRNsi5ovhf2EjaCw7wx49wh2";
//WDG접근키
//internal const string RIOT_API_KEY = "x-api-key:oYiHmI77ur7tFl3joHh0z8onOVDnfiys3pezolAv";
//internal const string RIOT_API_KEY = "x-api-key:cqW7ayuV2o10P0g4F7HlXa9DALZRfAME4Pv1UjcN";
internal const string _이벤트행데이터_REQUEST_URL = "https://raw-stats-api.ewp.gg/livestatsRaw/v1/platformGames/";
//internal const string 라이엇_게임리스트_REQUEST_URL = "https://raw-stats-api.ewp.gg/livestatsRaw/v1/platformGames?state=";
internal const string _게임리스트_REQUEST_URL = "https://raw-stats-api.ewp.gg/livestatsRaw/v1/";
//internal const string 몽고DB_접속정보 = "mongodb://root:veryhardpassword123@211.53.30.8:50003";
internal const string DB_접속정보 = "mongodb://root:veryhardpassword123@127.0.0.1:50003";
//internal const string 몽고DB_접속정보 = "mongodb://root:veryhardpassword123@211.42.188.8:50003";
//internal const string 몽고DB_접속정보 = "mongodb://root:veryhardpassword123@203.251.148.27:50002";
internal const int ms = 1000;
}
}

View File

@@ -0,0 +1,270 @@
namespace updateServer
{
partial class Form1
{
/// <summary>
/// 필수 디자이너 변수입니다.
/// </summary>
private System.ComponentModel.IContainer components = null;
/// <summary>
/// 사용 중인 모든 리소스를 정리합니다.
/// </summary>
/// <param name="disposing">관리되는 리소스를 삭제해야 하면 true이고, 그렇지 않으면 false입니다.</param>
protected override void Dispose(bool disposing)
{
if (disposing && (components != null))
{
components.Dispose();
}
base.Dispose(disposing);
}
#region Windows Form
/// <summary>
/// 디자이너 지원에 필요한 메서드입니다.
/// 이 메서드의 내용을 코드 편집기로 수정하지 마세요.
/// </summary>
private void InitializeComponent()
{
this.button1 = new System.Windows.Forms.Button();
this.label5 = new System.Windows.Forms.Label();
this.button2 = new System.Windows.Forms.Button();
this.lstBoxUpdateGameList = new System.Windows.Forms.ListBox();
this.txbGameID = new System.Windows.Forms.TextBox();
this.label1 = new System.Windows.Forms.Label();
this.label2 = new System.Windows.Forms.Label();
this.txbPlatformID = new System.Windows.Forms.TextBox();
this.label3 = new System.Windows.Forms.Label();
this.lbServerStatus = new System.Windows.Forms.Label();
this.listBox1 = new System.Windows.Forms.ListBox();
this.button3 = new System.Windows.Forms.Button();
this.button4 = new System.Windows.Forms.Button();
this.button5 = new System.Windows.Forms.Button();
this.btnExport = new System.Windows.Forms.Button();
this.button6 = new System.Windows.Forms.Button();
this.label4 = new System.Windows.Forms.Label();
this.SuspendLayout();
//
// button1
//
this.button1.Font = new System.Drawing.Font("굴림", 20F);
this.button1.Location = new System.Drawing.Point(260, 99);
this.button1.Name = "button1";
this.button1.Size = new System.Drawing.Size(262, 58);
this.button1.TabIndex = 0;
this.button1.Text = "서버 켜기";
this.button1.UseVisualStyleBackColor = true;
this.button1.Click += new System.EventHandler(this.button1_Click);
//
// label5
//
this.label5.AutoSize = true;
this.label5.Font = new System.Drawing.Font("굴림", 15F);
this.label5.Location = new System.Drawing.Point(38, 177);
this.label5.Name = "label5";
this.label5.Size = new System.Drawing.Size(206, 20);
this.label5.TabIndex = 2;
this.label5.Text = "최근 요청받은 게임 ID";
//
// button2
//
this.button2.Font = new System.Drawing.Font("굴림", 20F);
this.button2.Location = new System.Drawing.Point(260, 266);
this.button2.Name = "button2";
this.button2.Size = new System.Drawing.Size(262, 123);
this.button2.TabIndex = 6;
this.button2.Text = "플랫폼 아이디 업데이트 진행";
this.button2.UseVisualStyleBackColor = true;
this.button2.Click += new System.EventHandler(this.button2_Click);
//
// lstBoxUpdateGameList
//
this.lstBoxUpdateGameList.FormattingEnabled = true;
this.lstBoxUpdateGameList.ItemHeight = 12;
this.lstBoxUpdateGameList.Location = new System.Drawing.Point(54, 33);
this.lstBoxUpdateGameList.Name = "lstBoxUpdateGameList";
this.lstBoxUpdateGameList.Size = new System.Drawing.Size(180, 124);
this.lstBoxUpdateGameList.TabIndex = 4;
//
// txbGameID
//
this.txbGameID.Font = new System.Drawing.Font("굴림", 15F);
this.txbGameID.Location = new System.Drawing.Point(250, 174);
this.txbGameID.Name = "txbGameID";
this.txbGameID.Size = new System.Drawing.Size(272, 30);
this.txbGameID.TabIndex = 7;
//
// label1
//
this.label1.AutoSize = true;
this.label1.Font = new System.Drawing.Font("굴림", 15F);
this.label1.Location = new System.Drawing.Point(25, 217);
this.label1.Name = "label1";
this.label1.Size = new System.Drawing.Size(219, 20);
this.label1.TabIndex = 2;
this.label1.Text = "최근가져오는 플랫폼 ID";
//
// label2
//
this.label2.AutoSize = true;
this.label2.Font = new System.Drawing.Font("굴림", 15F);
this.label2.Location = new System.Drawing.Point(12, 9);
this.label2.Name = "label2";
this.label2.Size = new System.Drawing.Size(236, 20);
this.label2.TabIndex = 2;
this.label2.Text = "업데이트중인 경기리스트";
//
// txbPlatformID
//
this.txbPlatformID.Font = new System.Drawing.Font("굴림", 15F);
this.txbPlatformID.Location = new System.Drawing.Point(250, 214);
this.txbPlatformID.Name = "txbPlatformID";
this.txbPlatformID.Size = new System.Drawing.Size(272, 30);
this.txbPlatformID.TabIndex = 7;
//
// label3
//
this.label3.AutoSize = true;
this.label3.Font = new System.Drawing.Font("굴림", 15F);
this.label3.Location = new System.Drawing.Point(330, 9);
this.label3.Name = "label3";
this.label3.Size = new System.Drawing.Size(89, 20);
this.label3.TabIndex = 2;
this.label3.Text = "서버상태";
//
// lbServerStatus
//
this.lbServerStatus.BackColor = System.Drawing.SystemColors.ActiveCaptionText;
this.lbServerStatus.Font = new System.Drawing.Font("굴림", 20F);
this.lbServerStatus.ForeColor = System.Drawing.SystemColors.ControlLightLight;
this.lbServerStatus.Location = new System.Drawing.Point(269, 33);
this.lbServerStatus.Name = "lbServerStatus";
this.lbServerStatus.Size = new System.Drawing.Size(244, 51);
this.lbServerStatus.TabIndex = 8;
this.lbServerStatus.Text = "STOP";
this.lbServerStatus.TextAlign = System.Drawing.ContentAlignment.MiddleCenter;
//
// listBox1
//
this.listBox1.FormattingEnabled = true;
this.listBox1.ItemHeight = 12;
this.listBox1.Location = new System.Drawing.Point(542, 56);
this.listBox1.Name = "listBox1";
this.listBox1.Size = new System.Drawing.Size(428, 316);
this.listBox1.TabIndex = 4;
this.listBox1.SelectedIndexChanged += new System.EventHandler(this.listBox1_SelectedIndexChanged);
//
// button3
//
this.button3.Location = new System.Drawing.Point(756, 12);
this.button3.Name = "button3";
this.button3.Size = new System.Drawing.Size(214, 38);
this.button3.TabIndex = 9;
this.button3.Text = "진행중인 경기목록 가져오기";
this.button3.UseVisualStyleBackColor = true;
this.button3.Click += new System.EventHandler(this.button3_Click);
//
// button4
//
this.button4.Location = new System.Drawing.Point(542, 12);
this.button4.Name = "button4";
this.button4.Size = new System.Drawing.Size(208, 38);
this.button4.TabIndex = 9;
this.button4.Text = "테스트경기 목록 가져오기";
this.button4.UseVisualStyleBackColor = true;
this.button4.Click += new System.EventHandler(this.button4_Click);
//
// button5
//
this.button5.Location = new System.Drawing.Point(12, 326);
this.button5.Name = "button5";
this.button5.Size = new System.Drawing.Size(65, 46);
this.button5.TabIndex = 10;
this.button5.Text = "과거자료방리스트업데이트";
this.button5.UseVisualStyleBackColor = true;
this.button5.Click += new System.EventHandler(this.button5_Click);
//
// btnExport
//
this.btnExport.Location = new System.Drawing.Point(120, 266);
this.btnExport.Name = "btnExport";
this.btnExport.Size = new System.Drawing.Size(117, 54);
this.btnExport.TabIndex = 11;
this.btnExport.Text = "데이터백업";
this.btnExport.UseVisualStyleBackColor = true;
this.btnExport.Click += new System.EventHandler(this.btnExport_Click);
//
// button6
//
this.button6.Location = new System.Drawing.Point(85, 326);
this.button6.Name = "button6";
this.button6.Size = new System.Drawing.Size(152, 45);
this.button6.TabIndex = 12;
this.button6.Text = "데이터초기화";
this.button6.UseVisualStyleBackColor = true;
this.button6.Click += new System.EventHandler(this.button6_Click);
//
// label4
//
this.label4.BackColor = System.Drawing.SystemColors.ActiveCaptionText;
this.label4.Font = new System.Drawing.Font("굴림", 20F);
this.label4.ForeColor = System.Drawing.SystemColors.ControlLightLight;
this.label4.Location = new System.Drawing.Point(12, 266);
this.label4.Name = "label4";
this.label4.Size = new System.Drawing.Size(102, 51);
this.label4.TabIndex = 8;
this.label4.Text = "0/0";
this.label4.TextAlign = System.Drawing.ContentAlignment.MiddleCenter;
//
// Form1
//
this.AutoScaleDimensions = new System.Drawing.SizeF(7F, 12F);
this.AutoScaleMode = System.Windows.Forms.AutoScaleMode.Font;
this.ClientSize = new System.Drawing.Size(982, 401);
this.Controls.Add(this.button6);
this.Controls.Add(this.btnExport);
this.Controls.Add(this.button5);
this.Controls.Add(this.button4);
this.Controls.Add(this.button3);
this.Controls.Add(this.label4);
this.Controls.Add(this.lbServerStatus);
this.Controls.Add(this.txbPlatformID);
this.Controls.Add(this.txbGameID);
this.Controls.Add(this.button2);
this.Controls.Add(this.listBox1);
this.Controls.Add(this.lstBoxUpdateGameList);
this.Controls.Add(this.label3);
this.Controls.Add(this.label2);
this.Controls.Add(this.label1);
this.Controls.Add(this.label5);
this.Controls.Add(this.button1);
this.Name = "Form1";
this.Text = "LCK CL 업데이트서버 250525 - WDG";
this.ResumeLayout(false);
this.PerformLayout();
}
#endregion
private System.Windows.Forms.Label label5;
private System.Windows.Forms.Button button2;
private System.Windows.Forms.Label label1;
private System.Windows.Forms.Label label2;
private System.Windows.Forms.Label label3;
public System.Windows.Forms.Button button1;
public System.Windows.Forms.ListBox lstBoxUpdateGameList;
public System.Windows.Forms.TextBox txbGameID;
public System.Windows.Forms.TextBox txbPlatformID;
public System.Windows.Forms.Label lbServerStatus;
public System.Windows.Forms.ListBox listBox1;
private System.Windows.Forms.Button button3;
private System.Windows.Forms.Button button4;
private System.Windows.Forms.Button button5;
private System.Windows.Forms.Button btnExport;
private System.Windows.Forms.Button button6;
public System.Windows.Forms.Label label4;
}
}

View File

@@ -0,0 +1,247 @@
using MongoDB.Bson;
using MongoDB.Bson.IO;
using MongoDB.Bson.Serialization;
using MongoDB.Driver;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Net;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace updateServer
{
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
}
private void button1_Click(object sender, EventArgs e)
{
NetManager manager = new NetManager();
manager.start();
UpdateManager.getInstance().init();
///ESPORTSTMNT06_1730991크로노
//UpdateManager.getInstance().startUpdateEventRaw("ESPORTSTMNT02_1921265", false);
//UpdateManager.getInstance().GameListUpdateWorker(true);
}
private void button2_Click(object sender, EventArgs e)
{
UpdateManager.getInstance().startUpdateEventRaw(txbPlatformID.Text, false);
}
private void button3_Click(object sender, EventArgs e)
{
UpdateManager.getInstance().GameListUpdateWorker(false);
}
private void button4_Click(object sender, EventArgs e)
{
UpdateManager.getInstance().GameListUpdateWorker(true);
//UpdateManager.getInstance().startUpdateEventRaw("ESPORTSTMNT06_1721059", false);
//UpdateManager.getInstance().finishGameListUpdateWorker();
}
private void listBox1_SelectedIndexChanged(object sender, EventArgs e)
{
if (listBox1.SelectedItems.Count < 1) return;
string[] selectedItem = listBox1.SelectedItems[0].ToString().Split('_');
txbGameID.Text = selectedItem.Last();
txbPlatformID.Text = selectedItem[0] + "_" + selectedItem[1];
UpdateManager.getInstance().GameKey = txbGameID.Text;
UpdateManager.getInstance().GameName = txbPlatformID.Text;
}
public void removeWorkerList()
{
/*
List<string> items = new List<string>();
foreach (string s in UpdateManager.getInstance().mUpdateWorkerTable.Keys)
items.Add(s);
foreach (string s in items)
{
MessageBox.Show("!!" + s);
UpdateManager.getInstance().mUpdateWorkerTable.Remove(s);
}
*/
}
public void updateWorkerList()
{
this.Invoke(new MethodInvoker(() => {
lstBoxUpdateGameList.Items.Clear();
foreach (string item in UpdateManager.getInstance().mUpdateWorkerTable.Keys)
{
lstBoxUpdateGameList.Items.Add(item);
}
}));
}
public void Msg()
{
//MessageBox.Show("!!");
}
public void updateGameRoomList(List<string> recvData)
{
this.Invoke(new MethodInvoker(() => {
listBox1.Items.Clear();
foreach (string item in recvData)
{
listBox1.Items.Add(item);
}
}));
}
private void button5_Click(object sender, EventArgs e)
{
UpdateManager.getInstance().finishGameListUpdateWorker();
}
async void exportDB()
{
string basicfileName = DateTime.Now.Date.ToString("yyyyMMdd"); // initialize to the output file
MongoClient dd = new MongoClient(DEFINE.DB_접속정보);
List<string> collectionNames = dd.GetDatabase("datalol").ListCollectionNames().ToList();
int endedTask = 0;
this.Invoke(new MethodInvoker(() => label4.Text = endedTask + "/" + collectionNames.Count().ToString()));
DirectoryInfo di = new DirectoryInfo(@"c:\lol_db_backup\" + basicfileName);
if (!di.Exists)
{
di.Create();
}
foreach (string item in collectionNames)
{
IMongoCollection<BsonDocument> collection = dd.GetDatabase("datalol").GetCollection<BsonDocument>(item); // initialize to the collection to read from
using (var streamWriter = new StreamWriter(@"c:\lol_db_backup\" + basicfileName + @"\" + item + ".json"))
{
await collection.Find(new BsonDocument())
.ForEachAsync(async (document) =>
{
using (var stringWriter = new StringWriter())
using (var jsonWriter = new JsonWriter(stringWriter))
{
var context = MongoDB.Bson.Serialization.BsonSerializationContext.CreateRoot(jsonWriter);
collection.DocumentSerializer.Serialize(context, document);
var line = stringWriter.ToString();
await streamWriter.WriteLineAsync(line);
}
}
);
endedTask += 1;
this.Invoke(new MethodInvoker(() => label4.Text = endedTask + "/" + collectionNames.Count().ToString()));
}
}
}
async void importDB()
{
//MongoClient dd = new MongoClient(DEFINE.몽고DB_접속정보);
MongoClient dd = new MongoClient("mongodb://root:veryhardpassword123@211.42.188.8:50003");
List<string> collectionNames = dd.GetDatabase("datalol").ListCollectionNames().ToList();
//List<string> collectionNames = new List<string>();
//collectionNames.Remove("building_destroyed");
//collectionNames.Add("game_end");
//collectionNames.Add("game_info");
string basicfileName = DateTime.Now.Date.ToString("yyyyMMdd");
foreach (var item in collectionNames)
{
//IMongoCollection<BsonDocument> collection = dd.GetDatabase("data_lol_test_seed").GetCollection<BsonDocument>(item);
IMongoCollection<BsonDocument> collection = dd.GetDatabase("datalol").GetCollection<BsonDocument>(item);
using (var streamReader = new StreamReader(@"c:\lol_db_backup\" + basicfileName + @"\" + item + ".json"))
{
string line;
while ((line = await streamReader.ReadLineAsync()) != null)
{
using (var jsonReader = new JsonReader(line))
{
var context = BsonDeserializationContext.CreateRoot(jsonReader);
var document = collection.DocumentSerializer.Deserialize(context);
await collection.InsertOneAsync(document);
}
}
}
}
}
async void clearDB()
{
MongoClient dd = new MongoClient(DEFINE.DB_접속정보);
List<string> collectionNames = dd.GetDatabase("datalol").ListCollectionNames().ToList();
string basicfileName = DateTime.Now.Date.ToShortDateString();
var mEventDataBaseTarget = dd.GetDatabase("datalol");
foreach (string item in collectionNames)
{
await mEventDataBaseTarget.GetCollection<BsonValue>(item)
.DeleteManyAsync(x => true);
}
UpdateManager.getInstance().mUpdateWorkerTable.Clear();
updateWorkerList();
}
private void btnExport_Click(object sender, EventArgs e)
{
exportDB();
//importDB();
}
private void button6_Click(object sender, EventArgs e)
{
clearDB();
}
}
}

View File

@@ -0,0 +1,120 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:import namespace="http://www.w3.org/XML/1998/namespace" />
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" use="required" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
<xsd:attribute ref="xml:space" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@@ -0,0 +1,256 @@
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();
}
}
}

View File

@@ -0,0 +1,63 @@
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Security.Principal;
using System.Threading.Tasks;
using System.Windows.Forms;
namespace updateServer
{
static class Program
{
/// <summary>
/// 해당 응용 프로그램의 주 진입점입니다.
/// </summary>
[STAThread]
static void Main()
{
/*
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
mMainForm = new Form1();
Application.Run(mMainForm);
*/
if (IsAdministrator() == false)
{
ProcessStartInfo processStartInfo = new ProcessStartInfo();
processStartInfo.UseShellExecute = true;
processStartInfo.FileName = Application.ExecutablePath;
processStartInfo.WorkingDirectory = Environment.CurrentDirectory;
processStartInfo.Verb = "runas";
Process.Start(processStartInfo);
}
else
{
Application.EnableVisualStyles();
Application.SetCompatibleTextRenderingDefault(false);
mMainForm = new Form1();
Application.Run(mMainForm);
}
}
public static bool IsAdministrator()
{
WindowsIdentity identity = WindowsIdentity.GetCurrent();
if (identity != null)
{
WindowsPrincipal principal = new WindowsPrincipal(identity);
return principal.IsInRole(WindowsBuiltInRole.Administrator);
}
return false;
}
public static Form1 mMainForm = null;
}
}

View File

@@ -0,0 +1,36 @@
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;
// 어셈블리에 대한 일반 정보는 다음 특성 집합을 통해
// 제어됩니다. 어셈블리와 관련된 정보를 수정하려면
// 이러한 특성 값을 변경하세요.
[assembly: AssemblyTitle("updateServer")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("updateServer")]
[assembly: AssemblyCopyright("Copyright © 2021")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]
// ComVisible을 false로 설정하면 이 어셈블리의 형식이 COM 구성 요소에
// 표시되지 않습니다. COM에서 이 어셈블리의 형식에 액세스하려면
// 해당 형식에 대해 ComVisible 특성을 true로 설정하세요.
[assembly: ComVisible(false)]
// 이 프로젝트가 COM에 노출되는 경우 다음 GUID는 typelib의 ID를 나타냅니다.
[assembly: Guid("a0ebc173-c85f-41d6-bd9a-088efa361113")]
// 어셈블리의 버전 정보는 다음 네 가지 값으로 구성됩니다.
//
// 주 버전
// 부 버전
// 빌드 번호
// 수정 버전
//
// 모든 값을 지정하거나 아래와 같이 '*'를 사용하여 빌드 번호 및 수정 번호가 자동으로
// 지정되도록 할 수 있습니다.
// [assembly: AssemblyVersion("1.0.*")]
[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]

View File

@@ -0,0 +1,71 @@
//------------------------------------------------------------------------------
// <auto-generated>
// 이 코드는 도구를 사용하여 생성되었습니다.
// 런타임 버전:4.0.30319.42000
//
// 파일 내용을 변경하면 잘못된 동작이 발생할 수 있으며, 코드를 다시 생성하면
// 이러한 변경 내용이 손실됩니다.
// </auto-generated>
//------------------------------------------------------------------------------
namespace updateServer.Properties
{
/// <summary>
/// 지역화된 문자열 등을 찾기 위한 강력한 형식의 리소스 클래스입니다.
/// </summary>
// 이 클래스는 ResGen 또는 Visual Studio와 같은 도구를 통해 StronglyTypedResourceBuilder
// 클래스에서 자동으로 생성되었습니다.
// 멤버를 추가하거나 제거하려면 .ResX 파일을 편집한 다음 /str 옵션을 사용하여
// ResGen을 다시 실행하거나 VS 프로젝트를 다시 빌드하십시오.
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("System.Resources.Tools.StronglyTypedResourceBuilder", "4.0.0.0")]
[global::System.Diagnostics.DebuggerNonUserCodeAttribute()]
[global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()]
internal class Resources
{
private static global::System.Resources.ResourceManager resourceMan;
private static global::System.Globalization.CultureInfo resourceCulture;
[global::System.Diagnostics.CodeAnalysis.SuppressMessageAttribute("Microsoft.Performance", "CA1811:AvoidUncalledPrivateCode")]
internal Resources()
{
}
/// <summary>
/// 이 클래스에서 사용하는 캐시된 ResourceManager 인스턴스를 반환합니다.
/// </summary>
[global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)]
internal static global::System.Resources.ResourceManager ResourceManager
{
get
{
if ((resourceMan == null))
{
global::System.Resources.ResourceManager temp = new global::System.Resources.ResourceManager("updateServer.Properties.Resources", typeof(Resources).Assembly);
resourceMan = temp;
}
return resourceMan;
}
}
/// <summary>
/// 이 강력한 형식의 리소스 클래스를 사용하여 모든 리소스 조회에 대해 현재 스레드의 CurrentUICulture 속성을
/// 재정의합니다.
/// </summary>
[global::System.ComponentModel.EditorBrowsableAttribute(global::System.ComponentModel.EditorBrowsableState.Advanced)]
internal static global::System.Globalization.CultureInfo Culture
{
get
{
return resourceCulture;
}
set
{
resourceCulture = value;
}
}
}
}

View File

@@ -0,0 +1,117 @@
<?xml version="1.0" encoding="utf-8"?>
<root>
<!--
Microsoft ResX Schema
Version 2.0
The primary goals of this format is to allow a simple XML format
that is mostly human readable. The generation and parsing of the
various data types are done through the TypeConverter classes
associated with the data types.
Example:
... ado.net/XML headers & schema ...
<resheader name="resmimetype">text/microsoft-resx</resheader>
<resheader name="version">2.0</resheader>
<resheader name="reader">System.Resources.ResXResourceReader, System.Windows.Forms, ...</resheader>
<resheader name="writer">System.Resources.ResXResourceWriter, System.Windows.Forms, ...</resheader>
<data name="Name1"><value>this is my long string</value><comment>this is a comment</comment></data>
<data name="Color1" type="System.Drawing.Color, System.Drawing">Blue</data>
<data name="Bitmap1" mimetype="application/x-microsoft.net.object.binary.base64">
<value>[base64 mime encoded serialized .NET Framework object]</value>
</data>
<data name="Icon1" type="System.Drawing.Icon, System.Drawing" mimetype="application/x-microsoft.net.object.bytearray.base64">
<value>[base64 mime encoded string representing a byte array form of the .NET Framework object]</value>
<comment>This is a comment</comment>
</data>
There are any number of "resheader" rows that contain simple
name/value pairs.
Each data row contains a name, and value. The row also contains a
type or mimetype. Type corresponds to a .NET class that support
text/value conversion through the TypeConverter architecture.
Classes that don't support this are serialized and stored with the
mimetype set.
The mimetype is used for serialized objects, and tells the
ResXResourceReader how to depersist the object. This is currently not
extensible. For a given mimetype the value must be set accordingly:
Note - application/x-microsoft.net.object.binary.base64 is the format
that the ResXResourceWriter will generate, however the reader can
read any of the formats listed below.
mimetype: application/x-microsoft.net.object.binary.base64
value : The object must be serialized with
: System.Serialization.Formatters.Binary.BinaryFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.soap.base64
value : The object must be serialized with
: System.Runtime.Serialization.Formatters.Soap.SoapFormatter
: and then encoded with base64 encoding.
mimetype: application/x-microsoft.net.object.bytearray.base64
value : The object must be serialized into a byte array
: using a System.ComponentModel.TypeConverter
: and then encoded with base64 encoding.
-->
<xsd:schema id="root" xmlns="" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:msdata="urn:schemas-microsoft-com:xml-msdata">
<xsd:element name="root" msdata:IsDataSet="true">
<xsd:complexType>
<xsd:choice maxOccurs="unbounded">
<xsd:element name="metadata">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" />
<xsd:attribute name="type" type="xsd:string" />
<xsd:attribute name="mimetype" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="assembly">
<xsd:complexType>
<xsd:attribute name="alias" type="xsd:string" />
<xsd:attribute name="name" type="xsd:string" />
</xsd:complexType>
</xsd:element>
<xsd:element name="data">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
<xsd:element name="comment" type="xsd:string" minOccurs="0" msdata:Ordinal="2" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" msdata:Ordinal="1" />
<xsd:attribute name="type" type="xsd:string" msdata:Ordinal="3" />
<xsd:attribute name="mimetype" type="xsd:string" msdata:Ordinal="4" />
</xsd:complexType>
</xsd:element>
<xsd:element name="resheader">
<xsd:complexType>
<xsd:sequence>
<xsd:element name="value" type="xsd:string" minOccurs="0" msdata:Ordinal="1" />
</xsd:sequence>
<xsd:attribute name="name" type="xsd:string" use="required" />
</xsd:complexType>
</xsd:element>
</xsd:choice>
</xsd:complexType>
</xsd:element>
</xsd:schema>
<resheader name="resmimetype">
<value>text/microsoft-resx</value>
</resheader>
<resheader name="version">
<value>2.0</value>
</resheader>
<resheader name="reader">
<value>System.Resources.ResXResourceReader, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
<resheader name="writer">
<value>System.Resources.ResXResourceWriter, System.Windows.Forms, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089</value>
</resheader>
</root>

View File

@@ -0,0 +1,30 @@
//------------------------------------------------------------------------------
// <auto-generated>
// This code was generated by a tool.
// Runtime Version:4.0.30319.42000
//
// Changes to this file may cause incorrect behavior and will be lost if
// the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------
namespace updateServer.Properties
{
[global::System.Runtime.CompilerServices.CompilerGeneratedAttribute()]
[global::System.CodeDom.Compiler.GeneratedCodeAttribute("Microsoft.VisualStudio.Editors.SettingsDesigner.SettingsSingleFileGenerator", "11.0.0.0")]
internal sealed partial class Settings : global::System.Configuration.ApplicationSettingsBase
{
private static Settings defaultInstance = ((Settings)(global::System.Configuration.ApplicationSettingsBase.Synchronized(new Settings())));
public static Settings Default
{
get
{
return defaultInstance;
}
}
}
}

View File

@@ -0,0 +1,7 @@
<?xml version='1.0' encoding='utf-8'?>
<SettingsFile xmlns="http://schemas.microsoft.com/VisualStudio/2004/01/settings" CurrentProfile="(Default)">
<Profiles>
<Profile Name="(Default)" />
</Profiles>
<Settings />
</SettingsFile>

View File

@@ -0,0 +1,743 @@
using MongoDB.Bson;
using MongoDB.Bson.Serialization;
using MongoDB.Driver;
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
namespace updateServer
{
internal class UpdateManager
{
public static UpdateManager mInstance = null;
public static UpdateManager getInstance()
{
if (mInstance == null)
{
mInstance = new UpdateManager();
}
return mInstance;
}
private UpdateManager()
{
init();
ServicePointManager.SecurityProtocol = SecurityProtocolType.Ssl3 | SecurityProtocolType.Tls | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls12;
}
MongoClient mDBClient = null;
IMongoDatabase mEventDataBase = null;
string mReceivedEventToken = "";
bool isUpdateWork = false;
public string GameKey = "";
public string GameName = "";
public bool init()
{
try
{
mDBClient = new MongoClient(DEFINE.DB_접속정보);
mEventDataBase = mDBClient.GetDatabase("datalol");
//mUpdateWorkerTable = new Dictionary<string, List<updateWorkObject>>();
mUpdateWorkerTable = new Dictionary<string, updateWorkObject>();
return true;
}
catch (Exception ex)
{
#if (DEBUG)
{
System.Windows.Forms.MessageBox.Show(ex.ToString());
}
#endif
return false;
}
}
//internal Dictionary<string, List<updateWorkObject>> mUpdateWorkerTable = null;
internal object mWorkerTableLocker = new object();
internal Dictionary<string, updateWorkObject> mUpdateWorkerTable = null;
internal void startUpdateEventRaw(string gameID, bool isProgress)
{
lock (mWorkerTableLocker)
{
//bool isRemoved = false;
List<string> keys = new List<string>();
foreach (string s in mUpdateWorkerTable.Keys) keys.Add(s);
foreach (string s in keys)
{
mUpdateWorkerTable[s].stopUpdateWork();
mUpdateWorkerTable.Remove(s);
//isRemoved = true;
}
//if (isRemoved) Program.mMainForm.Msg();
if (mUpdateWorkerTable.ContainsKey(gameID))
{
mUpdateWorkerTable[gameID].stopUpdateWork();
mUpdateWorkerTable.Remove(gameID);
}
mUpdateWorkerTable.Add(gameID, new updateWorkObject(gameID, isProgress));
mUpdateWorkerTable[gameID].startUpdateWork();
}
}
internal void RemoveAllEventRaw()
{
lock (mWorkerTableLocker)
{
//bool isRemoved = false;
List<string> keys = new List<string>();
foreach (string s in mUpdateWorkerTable.Keys) keys.Add(s);
foreach (string s in keys)
{
mUpdateWorkerTable[s].stopUpdateWork();
mUpdateWorkerTable.Remove(s);
}
}
}
public async Task RemoveBackup()
{
MongoClient dd = new MongoClient(DEFINE.DB_접속정보);
var collectionNames = dd.GetDatabase("datalol").ListCollectionNames().ToList();
var mEventDataBaseTarget = dd.GetDatabase("datalol");
foreach (string item in collectionNames)
{
await mEventDataBaseTarget.GetCollection<BsonValue>(item)
.DeleteManyAsync(x => true);
}
mUpdateWorkerTable.Clear();
}
/// <summary>
/// 라이엇 API에 경기중인 게임리스트를 요청한다.
/// </summary>
/// <param name="isTest"></param>
/// <returns></returns>
internal Dictionary<string, string> GameListUpdateWorker(bool isTest)
{
//string bufRequestURL = DEFINE.라이엇_게임리스트_REQUEST_URL + (isTest ? "platformGames" : "esportsGames") + "?state=in_progress";;
string bufRequestURL = DEFINE._게임리스트_REQUEST_URL + (isTest ? "platformGames" : "esportsGames") + "?state=in_progress"; ;
//string bufRequestURL = DEFINE.라이엇_게임리스트_REQUEST_URL + "esportsGames" + "?state=finished"; ;
string recvValue = requestRiotData(bufRequestURL);
IEnumerable<BsonValue> bufGameList = null;
List<string> updateRoomList = new List<string>();
Dictionary<String, string> rtnValue = new Dictionary<string, string>();
///가져온 데이터가 null이 아니라면 데이터를 Game단위(Document)로 짤라서 Enumarable화 하고, 아니면 빈 결과를 리턴한다.
if (recvValue != null)
{
bufGameList = BsonSerializer.Deserialize<BsonArray>(recvValue).Select(p => p.AsBsonDocument);
}
else
{
Program.mMainForm.updateGameRoomList(updateRoomList);
return rtnValue;
}
//가져온 데이터에서 방제와 플랫폼게임ID를 파싱해서 KV페어로 만든다.
foreach (BsonValue item in bufGameList)
{
string bufString = "";
///20210615테스트할부분 방을 새로만든부분이 있을경우 Document 순서에서 나중에 들어오므로 과거에 들어왔던 데이터를 버린다.
///혹시 모르니 안버린다.
//if (rtnValue.ContainsValue(item["gameName"].ToString()))
//{
// rtnValue.Remove(rtnValue.FirstOrDefault(x => x.Value == item["gameName"].ToString()).Key);
//}
if (isTest)
{
rtnValue.Add(item["platformGameId"].ToString(), item["gameName"].ToString());
bufString = item["platformGameId"].ToString() + "_" + item["gameName"].ToString();
updateRoomList.Add(bufString);
}
else
{
BsonDocument itemDocument = item.AsBsonDocument["platformGames"].AsBsonArray.Last().ToBsonDocument();
rtnValue.Add(itemDocument["platformGameId"].ToString(), itemDocument["gameName"].ToString());
bufString = itemDocument["platformGameId"].ToString() + "_" + itemDocument["gameName"].ToString();
updateRoomList.Add(bufString);
}
#if (DEBUG)
{
Console.WriteLine(bufString);
}
#endif
}
///완성된 방 정보를 UI에 업데이트한다.
Program.mMainForm.updateGameRoomList(updateRoomList);
return rtnValue;
}
/// <summary>
/// 끝난경기의 정보는 방제만으로 알 수 없기때문에 선수를 검색해서 경기를 찾기위한 게임 구조 클래스
/// </summary>
internal class game
{
internal string gamename = "";
internal List<string> playerList = new List<string>();
}
/// <summary>
/// 라이엇 API에서 끝난경기의 정보를 받아와서 gamelist.txt파일로 저장한다.
/// </summary>
/// <returns></returns>
internal void finishGameListUpdateWorker()
{
try
{
Dictionary<string, game> rtnValue = new Dictionary<string, game>();
string bufRequestURL = DEFINE._게임리스트_REQUEST_URL + "esportsGames" + "?state=finished"; ;
string recvValue = requestRiotData(bufRequestURL);
IEnumerable<BsonValue> bufGameList = null;
if (recvValue != null)
{
bufGameList = BsonSerializer.Deserialize<BsonArray>(recvValue).Select(p => p["platformGames"]);
}
else
{
return;
}
foreach (BsonArray item in bufGameList)
{
BsonDocument selectItem = item.Last().ToBsonDocument();
game bufGame = new game();
bufGame.gamename = selectItem["gameName"].ToString();
BsonArray players = selectItem["participants"].AsBsonArray;
List<string> bufplayerList = new List<string>();
foreach (BsonDocument itemp in players)
{
bufplayerList.Add(itemp["summonerName"].ToString());
}
if (players.Count == 0)
{
string dd = "";
}
bufGame.playerList = bufplayerList;
rtnValue.Add(selectItem["platformGameId"].ToString(), bufGame);
string players123 = "";
foreach (string item2 in bufGame.playerList)
{
players123 += item2 + "_";
}
File.AppendAllText("gameList.txt", selectItem["platformGameId"].ToString() + " " + selectItem["gameName"].ToString() + " " + players123 + Environment.NewLine);
}
}
catch (Exception ex)
{
System.Windows.Forms.MessageBox.Show("오류발생 - " + ex.Message);
}
}
/// <summary>
/// 완성된 URL을 통해 라이엇에 데이터를 요청하여 BsonDocument Type으로 결과를 리턴받는다.
/// </summary>
/// <param name="requestURL"></param>
/// <returns></returns>
string requestRiotData(string requestURL)
{
try
{
///20210809 SSL접속문제로 인해 서버인증기능을 끈 부분을 추가한다 이거 이래도 되나?
//ServicePointManager.ServerCertificateValidationCallback = delegate { return true; };
///가져온 URL에 맞춰 리퀘스트를 만든다.
HttpWebRequest req = (HttpWebRequest)WebRequest.Create(requestURL);
WebHeaderCollection hd = new WebHeaderCollection();
hd.Add(DEFINE.RIOT_API_KEY);
req.Headers = hd;
WebResponse rsp = req.GetResponse();
string result = "";
///가져온 데이터를 문자열화 하고, Bson형태로 파싱해서 리턴한다.
using (var reader = new StreamReader(rsp.GetResponseStream()))
{
result = reader.ReadToEnd();
}
if (result.Trim() == "[]")
{
return null;
}
return result;
}
catch (Exception ex)
{
return ex.ToString();
}
}
/// <summary>
/// EventRaw를 데이터를 업데이트 하기위한 UpdateWorker Class
/// </summary>
internal class updateWorkObject
{
string mGameID = "";
bool mIsProgress = false;
object tokenLocker = new object();
string receviedEventToken = "";
internal string mReceivedEventToken
{
get
{
lock (tokenLocker)
{
return receviedEventToken;
}
}
set
{
lock (tokenLocker)
{
receviedEventToken = value;
}
}
}
Thread mUpdateWorker = null;
internal bool isUpdateWork = false;
internal updateWorkObject(string gameID, bool recvProgress)
{
this.mGameID = gameID;
this.mIsProgress = recvProgress;
}
internal void startUpdateWork()
{
//mUpdateWorker = new Thread(updateTestDataWork);
Program.mMainForm.Invoke(new System.Windows.Forms.MethodInvoker(() => { Program.mMainForm.removeWorkerList(); }));
mUpdateWorker = new Thread(updateWork);
//mUpdateWorker = new Thread(updateWorkTest);
mUpdateWorker.IsBackground = true;
isUpdateWork = true;
mUpdateWorker.Start();
Program.mMainForm.Invoke(new System.Windows.Forms.MethodInvoker(() => { Program.mMainForm.updateWorkerList(); }));
//Program.mMainForm.Invoke(new System.Windows.Forms.MethodInvoker(() => { Program.mMainForm.Msg(); }));
}
int tokenCount = 0;
internal void stopUpdateWork()
{
isUpdateWork = false;
}
void updateWork()
{
while (isUpdateWork)
{
try
{
string bufRequestURL = DEFINE._이벤트행데이터_REQUEST_URL + mGameID + "/events?paginationToken=" + mReceivedEventToken;
BsonDocument bufRecvPayload = BsonDocument.Parse(UpdateManager.getInstance().requestRiotData(bufRequestURL));
///경기가 끝났음
if (bufRecvPayload.Contains("missingEventsStatus"))
{
if (bufRecvPayload["missingEventsStatus"].ToString() == "lost_permanently")
{
isUpdateWork = false;
}
else
{
mReceivedEventToken = bufRecvPayload["nextPageToken"].ToString();
}
}
else if (bufRecvPayload.Contains("nextPageToken"))
{
mReceivedEventToken = bufRecvPayload["nextPageToken"].ToString();
}
//다음페이지토큰이 들어오지 않는 상황에는 updatework를 종료하도록 유도함.
else if (!bufRecvPayload.Contains("nextPageToken"))
{
isUpdateWork = false;
}
///20210516 이 방식대로 데이터를 쌓게 되면 데이터를 파싱하는데 너무 복잡하고 오래걸림
//UpdateManager.getInstance().mEventDataBase.GetCollection<BsonValue>((mIsProgress ? "in_progress_" : "") + "event_raw")
// .UpdateOne(
// x => x["nextPageToken"] == bufRecvPayload["nextPageToken"],
// Builders<BsonValue>.Update.Set(x => x["events"], bufRecvPayload["events"]),
// new UpdateOptions() { IsUpsert = true }
// );
///토큰에 할당된 이벤트로우를 배열로 가져옴
BsonArray bufDataList = bufRecvPayload["events"].AsBsonArray;
///DB에 Duplicate를 할 수 있는 bulkwrite를 하기위한 WriteModel형식으로 만듬.
///Bulkwrite를 선택하면서 DB에서 한번에 유지할수있는 경기의 수가 많이 줄어들었다.
Dictionary<string, List<WriteModel<BsonValue>>> bufDataTable = new Dictionary<string, List<WriteModel<BsonValue>>>();
foreach (BsonDocument item in bufDataList)
{
BsonDocument bufUpdateValue = new BsonDocument();
///rfc461Schema에 해당 event의 종류가 들어있음.
string bufStatus = item["rfc461Schema"].ToString();
//DB에서 경기를 관리하기 위한 Key로 RequestGameID와 sequenceIndex를 사용.
bufUpdateValue.Add("RequestGameID", mGameID);
bufUpdateValue.Add(new BsonElement("sequenceIndex", Convert.ToInt32(item["sequenceIndex"])));
var gameFilter = Builders<BsonValue>.Filter.Eq(x => x["RequestGameID"], mGameID);
var sequanceFilter = Builders<BsonValue>.Filter.Eq(x => x["sequenceIndex"], item["sequenceIndex"]);
var Parentfilter = Builders<BsonValue>.Filter.And(gameFilter, sequanceFilter);
///Value를 eventDocument에 탑재.
bufUpdateValue.Add("eventDocument", item);
UpdateOneModel<BsonValue> updateRaw = new UpdateOneModel<BsonValue>(
Parentfilter,
Builders<BsonValue>.Update.Set(x => x["eventDocument"], item)
)
{ IsUpsert = true };
if (!bufDataTable.ContainsKey(bufStatus))
{
bufDataTable.Add(bufStatus, new List<WriteModel<BsonValue>>());
}
bufDataTable[bufStatus].Add(updateRaw);
}
foreach (var item in bufDataTable)
{
UpdateManager.getInstance().mEventDataBase.GetCollection<BsonValue>((mIsProgress ? "in_progress_" : "") + item.Key)
.BulkWriteAsync(item.Value);
}
Console.WriteLine(tokenCount + " : " + bufDataList.Count() + " : " + DateTime.Now.ToLongTimeString() + " : " + mReceivedEventToken);
tokenCount += 1;
Thread.Sleep(500);
}
catch (Exception ex)
{
Console.WriteLine(ex.ToString());
isUpdateWork = false;
}
}
//isUpdate가 false로 빠지는 경우 업데이트중인 게임 목록에서 해당 게임을 지운다.
lock (UpdateManager.getInstance().mWorkerTableLocker)
{
UpdateManager.getInstance().mUpdateWorkerTable.Remove(this.mGameID);
}
Program.mMainForm.Invoke(new System.Windows.Forms.MethodInvoker(() => { Program.mMainForm.updateWorkerList(); }));
}
void updateWorkTest()
{
while (isUpdateWork)
{
ThreadPool.QueueUserWorkItem(o => { updateRoutineForTest(); });
Thread.Sleep(1000);
}
lock (UpdateManager.getInstance().mWorkerTableLocker)
{
UpdateManager.getInstance().mUpdateWorkerTable.Remove(this.mGameID);
}
Program.mMainForm.Invoke(new System.Windows.Forms.MethodInvoker(() => { Program.mMainForm.updateWorkerList(); }));
}
//테스트를위한 업데이트루틴
void updateRoutineForTest()
{
try
{
string bufRequestURL = DEFINE._이벤트행데이터_REQUEST_URL + mGameID + "/events?paginationToken=" + mReceivedEventToken;
BsonDocument bufRecvPayload = BsonDocument.Parse(UpdateManager.getInstance().requestRiotData(bufRequestURL));
///경기가 끝났음
if (bufRecvPayload.Contains("missingEventsStatus"))
{
if (bufRecvPayload.Contains("lost_permanently"))
{
isUpdateWork = false;
}
else
{
mReceivedEventToken = bufRecvPayload["nextPageToken"].ToString();
}
}
else if (bufRecvPayload.Contains("nextPageToken"))
{
mReceivedEventToken = bufRecvPayload["nextPageToken"].ToString();
}
//다음페이지토큰이 들어오지 않는 상황에는 updatework를 종료하도록 유도함.
else if (!bufRecvPayload.Contains("nextPageToken"))
{
isUpdateWork = false;
}
///20210516 이 방식대로 데이터를 쌓게 되면 데이터를 파싱하는데 너무 복잡하고 오래걸림
//UpdateManager.getInstance().mEventDataBase.GetCollection<BsonValue>((mIsProgress ? "in_progress_" : "") + "event_raw")
// .UpdateOne(
// x => x["nextPageToken"] == bufRecvPayload["nextPageToken"],
// Builders<BsonValue>.Update.Set(x => x["events"], bufRecvPayload["events"]),
// new UpdateOptions() { IsUpsert = true }
// );
var filterGameID = Builders<BsonValue>.Filter.Eq(x => x["RequestGameID"], mGameID);
BsonArray bufDataList = bufRecvPayload["events"].AsBsonArray;
//var filter = Builders<BsonDocument>.Filter.Eq("_id", ObjectId.Parse(dbPro.Id));
//var update = Builders<BsonDocument>.Update.Push("tags", buildBsonArrayFromTags(pro.Tags));
//var result = collection.UpdateOne(filter, update);
//if (result.IsModifiedCountAvailable)
//{
// if (result.ModifiedCount == 1)
// {
// return true;
// }
//}
//벌크인서트를 위한 해시테이블
//Dictionary<string, BsonArray> bufBulkInsertTable = new Dictionary<string, BsonArray>();
//foreach (BsonDocument item in bufDataList)
//{
// ///이벤트네임을 키값으로 하고 벌크인서트를 위해 데이터를 나눔.
// string bufEventName = item["rfc461Schema"].ToString();
// if (!bufBulkInsertTable.ContainsKey(bufEventName))
// {
// bufBulkInsertTable.Add(bufEventName, new BsonArray());
// }
// bufBulkInsertTable[bufEventName].Add(item);
//}
// Dictionary<string, List<WriteModel<BsonDocument>>> bulkModel = new Dictionary<string, List<WriteModel<BsonDocument>>>();
// //경기정보를위해 전체정보를 각각의 이벤트에 맞는 콜렉션에 저장함(누락을 막기위해 동기화).
// foreach (var item in bufDataList)
// {
// var bufFilter = Builders<BsonDocument>.Filter.Eq("RequestGameID", mGameID);
// var bufUpdate = Builders<BsonDocument>.Update.Push("events", item);
// UpdateOneModel<BsonDocument> updateRaw = new UpdateOneModel<BsonDocument>(
// bufFilter, bufUpdate) { IsUpsert = true };
// if (!bulkModel.ContainsKey(item["rfc461Schema"].ToString()))
// {
// bulkModel.Add(item["rfc461Schema"].ToString(), new List<WriteModel<BsonDocument>>());
// }
// bulkModel[item["rfc461Schema"].ToString()].Add(updateRaw);
//// var resultOne = collectionEvent.UpdateMany(bufFilter, bufUpdate, new UpdateOptions() { IsUpsert = true });
// }
// foreach (var item in bulkModel)
// {
// var result = UpdateManager.getInstance().mEventDataBase.GetCollection<BsonDocument>(item.Key).BulkWrite(item.Value);
// }
foreach (var item in bufDataList)
{
var bufFilter = Builders<BsonDocument>.Filter.Eq("RequestGameID", mGameID);
var bufUpdate = Builders<BsonDocument>.Update.Push("events", item);
var collectionEvent = UpdateManager.getInstance().mEventDataBase.GetCollection<BsonDocument>(item["rfc461Schema"].ToString());
var resultOne = collectionEvent.UpdateOne(bufFilter, bufUpdate, new UpdateOptions() { IsUpsert = true });
}
////로그를위해 전체정보를 eventraws콜렉션에 저장함(비동기).
//var collectionAll = UpdateManager.getInstance().mEventDataBase.GetCollection<BsonDocument>("eventraws");
//var filterAll = Builders<BsonDocument>.Filter.Eq("RequestGameID", mGameID);
//foreach (var item in collection)
//{
//}
//var updateAll = Builders<BsonDocument>.Update.Push("events", bufDataList);
//var result2 = collectionAll.UpdateManyAsync(filterAll, updateAll, new UpdateOptions() { IsUpsert = true });
Console.WriteLine(tokenCount + " : " + bufDataList.Count() + " : " + DateTime.Now.ToLongTimeString() + " : " + mReceivedEventToken);
tokenCount += 1;
Thread.Sleep(1000);
}
catch (Exception ex)
{
Console.WriteLine(ex.ToString());
isUpdateWork = false;
}
}
}
}
}

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@@ -0,0 +1,19 @@
<?xml version="1.0" encoding="utf-8"?>
<packages>
<package id="DnsClient" version="1.4.0" targetFramework="net472" />
<package id="MongoDB.Bson" version="2.12.3" targetFramework="net472" />
<package id="MongoDB.Driver" version="2.12.3" targetFramework="net472" />
<package id="MongoDB.Driver.Core" version="2.12.3" targetFramework="net472" />
<package id="MongoDB.Libmongocrypt" version="1.2.1" targetFramework="net472" />
<package id="SharpCompress" version="0.23.0" targetFramework="net472" />
<package id="System.Buffers" version="4.5.1" targetFramework="net472" />
<package id="System.IO" version="4.3.0" targetFramework="net472" />
<package id="System.Net.Http" version="4.3.4" targetFramework="net472" />
<package id="System.Runtime" version="4.3.0" targetFramework="net472" />
<package id="System.Runtime.CompilerServices.Unsafe" version="5.0.0" targetFramework="net472" />
<package id="System.Runtime.InteropServices.RuntimeInformation" version="4.3.0" targetFramework="net472" />
<package id="System.Security.Cryptography.Algorithms" version="4.3.0" targetFramework="net472" />
<package id="System.Security.Cryptography.Encoding" version="4.3.0" targetFramework="net472" />
<package id="System.Security.Cryptography.Primitives" version="4.3.0" targetFramework="net472" />
<package id="System.Security.Cryptography.X509Certificates" version="4.3.0" targetFramework="net472" />
</packages>

View File

@@ -0,0 +1,170 @@
<?xml version="1.0" encoding="utf-8"?>
<Project ToolsVersion="15.0" xmlns="http://schemas.microsoft.com/developer/msbuild/2003">
<Import Project="$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props" Condition="Exists('$(MSBuildExtensionsPath)\$(MSBuildToolsVersion)\Microsoft.Common.props')" />
<PropertyGroup>
<Configuration Condition=" '$(Configuration)' == '' ">Debug</Configuration>
<Platform Condition=" '$(Platform)' == '' ">AnyCPU</Platform>
<ProjectGuid>{A0EBC173-C85F-41D6-BD9A-088EFA361113}</ProjectGuid>
<OutputType>WinExe</OutputType>
<RootNamespace>updateServer</RootNamespace>
<AssemblyName>updateServer</AssemblyName>
<TargetFrameworkVersion>v4.7.2</TargetFrameworkVersion>
<FileAlignment>512</FileAlignment>
<AutoGenerateBindingRedirects>true</AutoGenerateBindingRedirects>
<Deterministic>true</Deterministic>
<NuGetPackageImportStamp>
</NuGetPackageImportStamp>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Debug|AnyCPU' ">
<PlatformTarget>AnyCPU</PlatformTarget>
<DebugSymbols>true</DebugSymbols>
<DebugType>full</DebugType>
<Optimize>false</Optimize>
<OutputPath>bin\Debug\</OutputPath>
<DefineConstants>DEBUG;TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<PropertyGroup Condition=" '$(Configuration)|$(Platform)' == 'Release|AnyCPU' ">
<PlatformTarget>AnyCPU</PlatformTarget>
<DebugType>pdbonly</DebugType>
<Optimize>true</Optimize>
<OutputPath>bin\Release\</OutputPath>
<DefineConstants>TRACE</DefineConstants>
<ErrorReport>prompt</ErrorReport>
<WarningLevel>4</WarningLevel>
</PropertyGroup>
<ItemGroup>
<Reference Include="DnsClient, Version=1.4.0.0, Culture=neutral, PublicKeyToken=4574bb5573c51424, processorArchitecture=MSIL">
<HintPath>..\packages\DnsClient.1.4.0\lib\net471\DnsClient.dll</HintPath>
</Reference>
<Reference Include="MongoDB.Bson, Version=2.12.3.0, Culture=neutral, processorArchitecture=MSIL">
<HintPath>..\packages\MongoDB.Bson.2.12.3\lib\net452\MongoDB.Bson.dll</HintPath>
</Reference>
<Reference Include="MongoDB.Driver, Version=2.12.3.0, Culture=neutral, processorArchitecture=MSIL">
<HintPath>..\packages\MongoDB.Driver.2.12.3\lib\net452\MongoDB.Driver.dll</HintPath>
</Reference>
<Reference Include="MongoDB.Driver.Core, Version=2.12.3.0, Culture=neutral, processorArchitecture=MSIL">
<HintPath>..\packages\MongoDB.Driver.Core.2.12.3\lib\net452\MongoDB.Driver.Core.dll</HintPath>
</Reference>
<Reference Include="MongoDB.Libmongocrypt, Version=1.2.1.0, Culture=neutral, processorArchitecture=MSIL">
<HintPath>..\packages\MongoDB.Libmongocrypt.1.2.1\lib\net452\MongoDB.Libmongocrypt.dll</HintPath>
</Reference>
<Reference Include="SharpCompress, Version=0.23.0.0, Culture=neutral, PublicKeyToken=afb0a02973931d96, processorArchitecture=MSIL">
<HintPath>..\packages\SharpCompress.0.23.0\lib\net45\SharpCompress.dll</HintPath>
</Reference>
<Reference Include="System" />
<Reference Include="System.Buffers, Version=4.0.3.0, Culture=neutral, PublicKeyToken=cc7b13ffcd2ddd51, processorArchitecture=MSIL">
<HintPath>..\packages\System.Buffers.4.5.1\lib\net461\System.Buffers.dll</HintPath>
</Reference>
<Reference Include="System.ComponentModel.Composition" />
<Reference Include="System.Core" />
<Reference Include="System.IO, Version=4.1.1.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
<HintPath>..\packages\System.IO.4.3.0\lib\net462\System.IO.dll</HintPath>
<Private>True</Private>
<Private>True</Private>
</Reference>
<Reference Include="System.Net.Http, Version=4.1.1.3, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
<HintPath>..\packages\System.Net.Http.4.3.4\lib\net46\System.Net.Http.dll</HintPath>
<Private>True</Private>
<Private>True</Private>
</Reference>
<Reference Include="System.Runtime, Version=4.1.1.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
<HintPath>..\packages\System.Runtime.4.3.0\lib\net462\System.Runtime.dll</HintPath>
<Private>True</Private>
<Private>True</Private>
</Reference>
<Reference Include="System.Runtime.CompilerServices.Unsafe, Version=5.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
<HintPath>..\packages\System.Runtime.CompilerServices.Unsafe.5.0.0\lib\net45\System.Runtime.CompilerServices.Unsafe.dll</HintPath>
</Reference>
<Reference Include="System.Runtime.InteropServices.RuntimeInformation, Version=4.0.1.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
<HintPath>..\packages\System.Runtime.InteropServices.RuntimeInformation.4.3.0\lib\net45\System.Runtime.InteropServices.RuntimeInformation.dll</HintPath>
<Private>True</Private>
<Private>True</Private>
</Reference>
<Reference Include="System.Security.Cryptography.Algorithms, Version=4.2.1.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
<HintPath>..\packages\System.Security.Cryptography.Algorithms.4.3.0\lib\net463\System.Security.Cryptography.Algorithms.dll</HintPath>
<Private>True</Private>
<Private>True</Private>
</Reference>
<Reference Include="System.Security.Cryptography.Encoding, Version=4.0.1.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
<HintPath>..\packages\System.Security.Cryptography.Encoding.4.3.0\lib\net46\System.Security.Cryptography.Encoding.dll</HintPath>
<Private>True</Private>
<Private>True</Private>
</Reference>
<Reference Include="System.Security.Cryptography.Primitives, Version=4.0.1.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
<HintPath>..\packages\System.Security.Cryptography.Primitives.4.3.0\lib\net46\System.Security.Cryptography.Primitives.dll</HintPath>
<Private>True</Private>
<Private>True</Private>
</Reference>
<Reference Include="System.Security.Cryptography.X509Certificates, Version=4.1.1.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a, processorArchitecture=MSIL">
<HintPath>..\packages\System.Security.Cryptography.X509Certificates.4.3.0\lib\net461\System.Security.Cryptography.X509Certificates.dll</HintPath>
<Private>True</Private>
<Private>True</Private>
</Reference>
<Reference Include="System.Xml.Linq" />
<Reference Include="System.Data.DataSetExtensions" />
<Reference Include="Microsoft.CSharp" />
<Reference Include="System.Data" />
<Reference Include="System.Deployment" />
<Reference Include="System.Drawing" />
<Reference Include="System.Windows.Forms" />
<Reference Include="System.Xml" />
</ItemGroup>
<ItemGroup>
<Compile Include="DEFINE.cs" />
<Compile Include="Form1.cs">
<SubType>Form</SubType>
</Compile>
<Compile Include="Form1.Designer.cs">
<DependentUpon>Form1.cs</DependentUpon>
</Compile>
<Compile Include="NetManager.cs" />
<Compile Include="Program.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
<Compile Include="UpdateManager.cs" />
<EmbeddedResource Include="Form1.resx">
<DependentUpon>Form1.cs</DependentUpon>
</EmbeddedResource>
<EmbeddedResource Include="Properties\Resources.resx">
<Generator>ResXFileCodeGenerator</Generator>
<LastGenOutput>Resources.Designer.cs</LastGenOutput>
<SubType>Designer</SubType>
</EmbeddedResource>
<Compile Include="Properties\Resources.Designer.cs">
<AutoGen>True</AutoGen>
<DependentUpon>Resources.resx</DependentUpon>
</Compile>
<None Include="libmongocrypt.dylib" />
<None Include="libmongocrypt.so" />
<None Include="packages.config" />
<None Include="Properties\Settings.settings">
<Generator>SettingsSingleFileGenerator</Generator>
<LastGenOutput>Settings.Designer.cs</LastGenOutput>
</None>
<Compile Include="Properties\Settings.Designer.cs">
<AutoGen>True</AutoGen>
<DependentUpon>Settings.settings</DependentUpon>
<DesignTimeSharedInput>True</DesignTimeSharedInput>
</Compile>
</ItemGroup>
<ItemGroup>
<None Include="App.config" />
</ItemGroup>
<ItemGroup>
<Content Include="Core\Compression\Snappy\lib\win\snappy32.dll" />
<Content Include="Core\Compression\Snappy\lib\win\snappy64.dll" />
<Content Include="Core\Compression\Zstandard\lib\win\libzstd.dll" />
<Content Include="mongocrypt.dll" />
</ItemGroup>
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
<Import Project="..\packages\MongoDB.Libmongocrypt.1.2.1\build\MongoDB.Libmongocrypt.targets" Condition="Exists('..\packages\MongoDB.Libmongocrypt.1.2.1\build\MongoDB.Libmongocrypt.targets')" />
<Target Name="EnsureNuGetPackageBuildImports" BeforeTargets="PrepareForBuild">
<PropertyGroup>
<ErrorText>이 프로젝트는 이 컴퓨터에 없는 NuGet 패키지를 참조합니다. 해당 패키지를 다운로드하려면 NuGet 패키지 복원을 사용하십시오. 자세한 내용은 http://go.microsoft.com/fwlink/?LinkID=322105를 참조하십시오. 누락된 파일은 {0}입니다.</ErrorText>
</PropertyGroup>
<Error Condition="!Exists('..\packages\MongoDB.Libmongocrypt.1.2.1\build\MongoDB.Libmongocrypt.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\MongoDB.Libmongocrypt.1.2.1\build\MongoDB.Libmongocrypt.targets'))" />
<Error Condition="!Exists('..\packages\MongoDB.Driver.Core.2.12.3\build\MongoDB.Driver.Core.targets')" Text="$([System.String]::Format('$(ErrorText)', '..\packages\MongoDB.Driver.Core.2.12.3\build\MongoDB.Driver.Core.targets'))" />
</Target>
<Import Project="..\packages\MongoDB.Driver.Core.2.12.3\build\MongoDB.Driver.Core.targets" Condition="Exists('..\packages\MongoDB.Driver.Core.2.12.3\build\MongoDB.Driver.Core.targets')" />
</Project>

Binary file not shown.