- 종목명 검색 개선

- 엑셀 핸들러 추가
- 기타 코드 정리
This commit is contained in:
2017-01-10 19:22:02 +09:00
parent 349de89a05
commit ea5165a4aa
8 changed files with 286 additions and 159 deletions

View File

@@ -55,11 +55,29 @@ namespace NewsCrawler
if(Util.IsDebugging() == false) if(Util.IsDebugging() == false)
return; return;
SearchCode("[클릭 e종목]로엔, 본격적으로 시작되는 카카오 시너"); Console.WriteLine("Code Search Test");
SearchCode("[클릭 e종목]\"SK텔레콤, 투자심리 개선 가능성 주목해");
SearchCode("[클릭 e종목]SK하이닉스, 추가 상승 낙관적"); Console.WriteLine(SearchCode("[클릭 e종목]로엔, 본격적으로 시작되는 카카오 시너"));
SearchCode("MBK, 45억 규모 유상증자 결정"); Console.WriteLine(SearchCode("[클릭 e종목]\"SK텔레콤, 투자심리 개선 가능성 주목해"));
SearchCode("다음주 코스피 1960~1990…산유량 감산여부에 주목"); Console.WriteLine(SearchCode("[클릭 e종목]SK하이닉스, 추가 상승 낙관적"));
Console.WriteLine(SearchCode("MBK, 45억 규모 유상증자 결정"));
Console.WriteLine(SearchCode("다음주 코스피 1960~1990…산유량 감산여부에 주목"));
Console.WriteLine(SearchCode("\"사세요 일색 보고서\" 증권사 투자등급 공시 '"));
Console.WriteLine(SearchCode("허서홍 GS에너지 상무, GS 보통주 5.1만주 매수"));
Console.WriteLine(SearchCode("엠씨넥스, 아이클론 프리미엄 블랙박스 'i5 W"));
Console.WriteLine(SearchCode("에스아이티글로벌, 김의서 대표이사 체제로 변"));
Console.WriteLine(SearchCode("시몬스침대, 일산 가구공단에 프리미엄 매장 오"));
Console.WriteLine(SearchCode("[유럽증시]美 고용지표 앞두고 짙은 관망세"));
Console.WriteLine(SearchCode("코스콤, 강신 신임 전무이사 선임"));
Console.WriteLine(SearchCode("[베스트리포트]원자현미경, 반도체의 질문에 답"));
Console.WriteLine(SearchCode("거래소, 인콘에 최대주주 지분매각 추진설 조회"));
Console.WriteLine(SearchCode("와이제이엠게임즈, 서울 강남구로 본점 이전"));
Console.WriteLine(SearchCode("[특징주] 에이치엘비-생명, 아파티닙 글로벌 임상 3상 최종 승인 소식에 상승세"));
Console.WriteLine(SearchCode("진도군, 112건의 계약심사 통해 예산 10억원 절감"));
Console.WriteLine("Test End");
} }
void MakeList() void MakeList()
@@ -75,6 +93,8 @@ namespace NewsCrawler
if(Code.m_strCode[0] == 'A') if(Code.m_strCode[0] == 'A')
m_CodeList.Add(Code); m_CodeList.Add(Code);
} }
m_CodeList.Sort((a, b) => b.m_strName.Length-a.m_strName.Length);
} }
void LoadCodeType(string strPath, CODE_TYPE enType) void LoadCodeType(string strPath, CODE_TYPE enType)
@@ -221,6 +241,8 @@ namespace NewsCrawler
m_SynonymList.Add(Code); m_SynonymList.Add(Code);
} }
} }
m_SynonymList.Sort((a, b) => b.m_strName.Length-a.m_strName.Length);
} }
} }
@@ -232,19 +254,6 @@ namespace NewsCrawler
string[] words = strReplace.Trim().Split(' '); string[] words = strReplace.Trim().Split(' ');
string strCodeWord = words[0]; string strCodeWord = words[0];
//int iBracesPos = strText.Trim().IndexOfAny(new char[] { ']', '>', ')' });
//string[] astrWords = strText.Substring(iBracesPos).Trim().Split(' ');
//string[] astrWords = strText.Trim().Split(' ');
//if(astrWords.Length < 1)
// return null;
//string strCodeWord;
//if(astrWords.Length > 1 && astrWords[0].IndexOfAny(new char[] { ']', '>', ')' }) >= 0)
// strCodeWord = astrWords[1];
//else
// strCodeWord = astrWords[0];
CODE_VALUE Result = m_CodeList.Find(s => strCodeWord.Contains(s.m_strName)); CODE_VALUE Result = m_CodeList.Find(s => strCodeWord.Contains(s.m_strName));
if(Result != null) if(Result != null)
return Result; return Result;

View File

@@ -449,12 +449,12 @@ namespace NewsCrawler
if(strErrCode == "020") if(strErrCode == "020")
{ {
Config.SetDartAPIKeyLimit(State.m_strAuthKey); Config.SetDartAPIKeyLimit(State.m_strAuthKey);
Util.Log(Util.LOG_TYPE.ERROR, string.Format("[DartAPI] {0} ({1})", jObj["err_msg"], m_iDartAPIRetry)); Util.Log(Util.LOG_TYPE.ERROR, string.Format("[DartAPI] {0} (key:{1}, retry:{2})", jObj["err_msg"], State.m_strAuthKey, m_iDartAPIRetry));
return; return;
} }
else if(strErrCode != "000") else if(strErrCode != "000")
{ {
Util.Log(Util.LOG_TYPE.ERROR, string.Format("[DartAPI] {0} ({1})", jObj["err_msg"], m_iDartAPIRetry)); Util.Log(Util.LOG_TYPE.ERROR, string.Format("[DartAPI] {0} (key:{1}, retry:{2})", jObj["err_msg"], State.m_strAuthKey, m_iDartAPIRetry));
m_iDartAPIRetry--; m_iDartAPIRetry--;
return; return;
} }
@@ -475,7 +475,7 @@ namespace NewsCrawler
m_Listener.InsertItem(strTitle, strCodeName, "", m_Listener.InsertItem(strTitle, strCodeName, "",
DateTime.ParseExact(strTime, "HH:mm", CultureInfo.CurrentCulture), DateTime.ParseExact(strTime, "HH:mm", CultureInfo.CurrentCulture),
DateTime.Now, DateTime.Now,
strURL, "DART API", State.m_Timer.Elapsed.TotalMilliseconds, bInitial); strURL, "DartAPI", State.m_Timer.Elapsed.TotalMilliseconds, bInitial);
} }
} }
} }

View File

@@ -17,9 +17,6 @@ namespace NewsCrawler
CPSYSDIBLib.StockChart m_StockChart = new CPSYSDIBLib.StockChart(); CPSYSDIBLib.StockChart m_StockChart = new CPSYSDIBLib.StockChart();
bool m_bInitialized = false; bool m_bInitialized = false;
System.Timers.Timer m_timer = new System.Timers.Timer();
ushort m_uiLastReqT = 0;
DSCBO1Lib.CpSvr8092S m_Cp8092S = new DSCBO1Lib.CpSvr8092S(); DSCBO1Lib.CpSvr8092S m_Cp8092S = new DSCBO1Lib.CpSvr8092S();
NewsForm m_Listener = null; NewsForm m_Listener = null;
@@ -53,10 +50,6 @@ namespace NewsCrawler
break; break;
} }
m_timer.Interval = 1000;
m_timer.Elapsed += M_timer_Elapsed;
//m_timer.Start();
m_Cp8092S.SetInputValue(0, "*"); m_Cp8092S.SetInputValue(0, "*");
m_Cp8092S.Received += Cp8092S_Received; m_Cp8092S.Received += Cp8092S_Received;
m_Cp8092S.Subscribe(); m_Cp8092S.Subscribe();
@@ -82,52 +75,6 @@ namespace NewsCrawler
//Console.WriteLine(string.Format("[8092S] {0} ({1}:{2})", strContents, strName, strCode)); //Console.WriteLine(string.Format("[8092S] {0} ({1}:{2})", strContents, strName, strCode));
} }
private void M_timer_Elapsed(object sender, System.Timers.ElapsedEventArgs e)
{
m_timer.Enabled = false;
if(GetLimitRemainCountRQ() < 5)
return;
CPSYSDIBLib.CpMarketWatch Watch = new CPSYSDIBLib.CpMarketWatch();
Watch.SetInputValue(0, "*");
Watch.SetInputValue(1, "1,2");
Watch.SetInputValue(2, 0);
Watch.BlockRequest2(0);
ushort uiLatestT = 0;
int iCount = Watch.GetHeaderValue(2);
if(iCount > 0)
uiLatestT = Watch.GetDataValue(0, 0);
for(int i = 0; i<iCount; i++)
{
ushort uiTime = Watch.GetDataValue(0, i);
string strCode = Watch.GetDataValue(1, i);
string strName = Watch.GetDataValue(2, i);
ushort uiType = Watch.GetDataValue(3, i);
string strContents = Watch.GetDataValue(4, i);
if(uiTime <= m_uiLastReqT)
break;
if(m_uiLastReqT > 0)
{
m_Listener.InsertItem(strContents, "", strCode,
DateTime.ParseExact(uiTime.ToString("0000"), "HHmm", CultureInfo.CurrentCulture),
DateTime.Now,
"", "CYBOS", 0, m_uiLastReqT>0);
}
//Console.WriteLine(string.Format("[{0}][{1}] {2} ({3}:{4})", uiTime, uiType, strContents, strName, strCode));
}
m_uiLastReqT = uiLatestT;
m_timer.Enabled = true;
}
public string[] GetAccounts() public string[] GetAccounts()
{ {
return m_CPUtil.AccountNumber; return m_CPUtil.AccountNumber;

97
ExcelHandler.cs Normal file
View File

@@ -0,0 +1,97 @@
using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using System.Threading.Tasks;
using Excel = Microsoft.Office.Interop.Excel;
using System.Reflection;
namespace NewsCrawler
{
public class ExcelHandler
{
bool m_bAvailable = false;
string m_strFileName = "";
string m_strToday = DateTime.Now.ToString("yyyy-MM-dd");
Excel.Application m_App = null;
public ExcelHandler(string strFileName)
{
m_App = new Excel.Application();
if(m_App == null)
{
Util.Log(Util.LOG_TYPE.ERROR, "엑셀이 설치되지 않음");
m_bAvailable = false;
return;
}
m_strFileName = strFileName;
}
~ExcelHandler()
{
Marshal.ReleaseComObject(m_App);
}
public bool IsAvailable()
{
return m_bAvailable;
}
private void Create()
{
Excel._Workbook Workbook = m_App.Workbooks.Add(Missing.Value);
Excel._Worksheet Worksheet = Workbook.ActiveSheet;
Worksheet.Cells[1, 1] = "날짜";
Worksheet.Cells[1, 2] = "기사 시간";
Worksheet.Cells[1, 3] = "받은 시간";
Worksheet.Cells[1, 4] = "출처";
Worksheet.Cells[1, 5] = "제목";
Worksheet.Cells[1, 6] = "요청 시간";
Worksheet.Cells[1, 7] = "시가";
Worksheet.Cells[1, 8] = "저가";
Worksheet.Cells[1, 9] = "대비";
Worksheet.Cells[1, 10] = "고가";
Worksheet.Cells[1, 11] = "대비";
Worksheet.Cells[1, 12] = "링크";
Workbook.SaveAs(m_strFileName, Excel.XlFileFormat.xlOpenXMLWorkbook, Missing.Value,
Missing.Value, false, false, Excel.XlSaveAsAccessMode.xlNoChange,
Excel.XlSaveConflictResolution.xlUserResolution, true,
Missing.Value, Missing.Value, Missing.Value);
Workbook.Close();
}
public void AddRow(string strNewsTime, string strResTime, string strRef, string strTitle, float fReqTime, int iPriceS, int iPriceLow, float fPriceLowP, int iPriceHigh, float fPriceHighP, string strLink)
{
if(m_bAvailable == false)
return;
if(File.Exists(m_strFileName) == false)
Create();
Excel._Workbook Workbook = m_App.Workbooks.Open(m_strFileName);
Excel._Worksheet Worksheet = Workbook.ActiveSheet;
int iRow = Worksheet.Cells.SpecialCells(Excel.XlCellType.xlCellTypeLastCell, Type.Missing).Row+1;
Worksheet.Cells[iRow, 1] = m_strToday;
Worksheet.Cells[iRow, 2] = strNewsTime;
Worksheet.Cells[iRow, 3] = strResTime;
Worksheet.Cells[iRow, 4] = strRef;
Worksheet.Cells[iRow, 5] = strTitle;
Worksheet.Cells[iRow, 6] = fReqTime;
Worksheet.Cells[iRow, 7] = iPriceS;
Worksheet.Cells[iRow, 8] = iPriceLow;
Worksheet.Cells[iRow, 9] = fPriceLowP;
Worksheet.Cells[iRow, 10] = iPriceHigh;
Worksheet.Cells[iRow, 11] = fPriceHighP;
Worksheet.Cells[iRow, 12] = strLink;
Workbook.Save();
Workbook.Close();
}
}
}

View File

@@ -89,6 +89,7 @@
<Reference Include="System.Xml" /> <Reference Include="System.Xml" />
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<Compile Include="ArrayList.cs" />
<Compile Include="CodeList.cs" /> <Compile Include="CodeList.cs" />
<Compile Include="Config.cs" /> <Compile Include="Config.cs" />
<Compile Include="ConfigForm.cs"> <Compile Include="ConfigForm.cs">
@@ -99,6 +100,7 @@
</Compile> </Compile>
<Compile Include="Crawler.cs" /> <Compile Include="Crawler.cs" />
<Compile Include="CybosHelper.cs" /> <Compile Include="CybosHelper.cs" />
<Compile Include="ExcelHandler.cs" />
<Compile Include="ModelessPopup.cs"> <Compile Include="ModelessPopup.cs">
<SubType>Form</SubType> <SubType>Form</SubType>
</Compile> </Compile>
@@ -212,6 +214,33 @@
<Isolated>False</Isolated> <Isolated>False</Isolated>
<EmbedInteropTypes>True</EmbedInteropTypes> <EmbedInteropTypes>True</EmbedInteropTypes>
</COMReference> </COMReference>
<COMReference Include="Microsoft.Office.Core">
<Guid>{2DF8D04C-5BFA-101B-BDE5-00AA0044DE52}</Guid>
<VersionMajor>2</VersionMajor>
<VersionMinor>4</VersionMinor>
<Lcid>0</Lcid>
<WrapperTool>primary</WrapperTool>
<Isolated>False</Isolated>
<EmbedInteropTypes>True</EmbedInteropTypes>
</COMReference>
<COMReference Include="Microsoft.Office.Interop.Excel">
<Guid>{00020813-0000-0000-C000-000000000046}</Guid>
<VersionMajor>1</VersionMajor>
<VersionMinor>6</VersionMinor>
<Lcid>0</Lcid>
<WrapperTool>primary</WrapperTool>
<Isolated>False</Isolated>
<EmbedInteropTypes>True</EmbedInteropTypes>
</COMReference>
<COMReference Include="VBIDE">
<Guid>{0002E157-0000-0000-C000-000000000046}</Guid>
<VersionMajor>5</VersionMajor>
<VersionMinor>3</VersionMinor>
<Lcid>0</Lcid>
<WrapperTool>primary</WrapperTool>
<Isolated>False</Isolated>
<EmbedInteropTypes>True</EmbedInteropTypes>
</COMReference>
</ItemGroup> </ItemGroup>
<ItemGroup> <ItemGroup>
<BootstrapperPackage Include=".NETFramework,Version=v4.5.2"> <BootstrapperPackage Include=".NETFramework,Version=v4.5.2">
@@ -226,6 +255,15 @@
</BootstrapperPackage> </BootstrapperPackage>
</ItemGroup> </ItemGroup>
<Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" /> <Import Project="$(MSBuildToolsPath)\Microsoft.CSharp.targets" />
<PropertyGroup>
<PostBuildEvent>if NOT "$(ConfigurationName)" == "Release" (goto :nocopy)
copy $(TargetPath) $(ProjectDir)publish\ /y
copy $(TargetDir)*.dll $(ProjectDir)publish\ /y
:nocopy
</PostBuildEvent>
</PropertyGroup>
<!-- To modify your build process, add your task inside one of the targets below and uncomment it. <!-- To modify your build process, add your task inside one of the targets below and uncomment it.
Other similar extension points exist, see Microsoft.Common.targets. Other similar extension points exist, see Microsoft.Common.targets.
<Target Name="BeforeBuild"> <Target Name="BeforeBuild">

12
NewsForm.Designer.cs generated
View File

@@ -123,25 +123,27 @@
// chPriceS // chPriceS
// //
this.chPriceS.Text = "시가"; this.chPriceS.Text = "시가";
this.chPriceS.Width = 66; this.chPriceS.Width = 65;
// //
// chPriceLow // chPriceLow
// //
this.chPriceLow.Text = "최저가"; this.chPriceLow.Text = "최저가";
this.chPriceLow.Width = 75; this.chPriceLow.Width = 61;
// //
// chPriceLowP // chPriceLowP
// //
this.chPriceLowP.Text = "최저가 대비(%)"; this.chPriceLowP.Text = "대비";
this.chPriceLowP.Width = 33;
// //
// chPriceHigh // chPriceHigh
// //
this.chPriceHigh.Text = "최고가"; this.chPriceHigh.Text = "최고가";
this.chPriceHigh.Width = 73; this.chPriceHigh.Width = 58;
// //
// chPriceHighP // chPriceHighP
// //
this.chPriceHighP.Text = "최고가 대비(%)"; this.chPriceHighP.Text = "대비";
this.chPriceHighP.Width = 35;
// //
// chLink // chLink
// //

View File

@@ -19,6 +19,35 @@ namespace NewsCrawler
{ {
public partial class NewsForm : Form public partial class NewsForm : Form
{ {
class NEWS_ITEM
{
public NEWS_ITEM(int iID, string strTitle, string strName, string strCode, DateTime NewsTime, DateTime ResTime, string strRef, string strURL, float fElapseT)
{
m_iID = iID;
m_strCode = strCode;
m_NewsTime = NewsTime;
m_ResTime = ResTime;
m_strRef = strRef;
m_strTitle = strTitle;
m_strURL = strURL;
m_fElapseT = fElapseT;
}
public int m_iID;
public string m_strCode;
public CodeList.CODE_VALUE m_Code = null;
public DateTime m_NewsTime;
public DateTime m_ResTime;
public string m_strRef;
public string m_strTitle;
public string m_strURL;
public float m_fElapseT;
}
class PRICE_CHECK_DATA class PRICE_CHECK_DATA
{ {
public int m_iID; public int m_iID;
@@ -28,8 +57,9 @@ namespace NewsCrawler
public int m_iPriceHigh = 0; public int m_iPriceHigh = 0;
public DateTime m_StartTime; public DateTime m_StartTime;
public int m_iTryCnt = 0; public int m_iTryCnt = 0;
}
public NEWS_ITEM m_NewsItem;
}
CybosHelper m_CybosHelper = null; CybosHelper m_CybosHelper = null;
CodeList m_CodeList = null; CodeList m_CodeList = null;
@@ -40,6 +70,8 @@ namespace NewsCrawler
int m_iCrawlInterval = 500; int m_iCrawlInterval = 500;
bool m_bBuy = false; bool m_bBuy = false;
List<string> m_URLs = new List<string>();
System.Timers.Timer m_SystemTimer = new System.Timers.Timer(); System.Timers.Timer m_SystemTimer = new System.Timers.Timer();
ConcurrentQueue<PRICE_CHECK_DATA> m_PriceCheckList = new ConcurrentQueue<PRICE_CHECK_DATA>(); ConcurrentQueue<PRICE_CHECK_DATA> m_PriceCheckList = new ConcurrentQueue<PRICE_CHECK_DATA>();
@@ -50,10 +82,15 @@ namespace NewsCrawler
Crawler m_Crawler = null; Crawler m_Crawler = null;
ExcelHandler m_Excel = null;
float m_fSupplyContractRate; float m_fSupplyContractRate;
object m_lvListLock = new object(); object m_lvListLock = new object();
public NewsForm() public NewsForm()
{ {
InitializeComponent(); InitializeComponent();
@@ -73,7 +110,7 @@ namespace NewsCrawler
m_Crawler.ReadKIND(true); m_Crawler.ReadKIND(true);
m_Crawler.ReadDart(true); m_Crawler.ReadDart(true);
m_Crawler.ReadEtoday(true); m_Crawler.ReadEtoday(true);
m_Crawler.ReadEtoday2(true); //m_Crawler.ReadEtoday2(true);
m_Crawler.ReadAsiaE(true); m_Crawler.ReadAsiaE(true);
m_Crawler.ReadEdaily(true); m_Crawler.ReadEdaily(true);
m_Crawler.ReadMoneyToday(true); m_Crawler.ReadMoneyToday(true);
@@ -108,6 +145,7 @@ namespace NewsCrawler
col.Width = -2; col.Width = -2;
} }
m_Excel = new ExcelHandler(Util.GetLogPath()+"/PriceCheck"+DateTime.Now.ToString("yyyy-MM-dd")+".xlsx");
m_CrawlTimer.Elapsed+=CrawlTimer_Tick; m_CrawlTimer.Elapsed+=CrawlTimer_Tick;
m_CrawlTimer.Interval = m_iCrawlInterval; m_CrawlTimer.Interval = m_iCrawlInterval;
@@ -129,17 +167,6 @@ namespace NewsCrawler
if(Util.IsDebugging() == false) if(Util.IsDebugging() == false)
return; return;
Console.WriteLine(m_CodeList.SearchCode("\"사세요 일색 보고서\" 증권사 투자등급 공시 '"));
Console.WriteLine(m_CodeList.SearchCode("허서홍 GS에너지 상무, GS 보통주 5.1만주 매수"));
Console.WriteLine(m_CodeList.SearchCode("엠씨넥스, 아이클론 프리미엄 블랙박스 'i5 W"));
Console.WriteLine(m_CodeList.SearchCode("에스아이티글로벌, 김의서 대표이사 체제로 변"));
Console.WriteLine(m_CodeList.SearchCode("시몬스침대, 일산 가구공단에 프리미엄 매장 오"));
Console.WriteLine(m_CodeList.SearchCode("[유럽증시]美 고용지표 앞두고 짙은 관망세"));
Console.WriteLine(m_CodeList.SearchCode("코스콤, 강신 신임 전무이사 선임"));
Console.WriteLine(m_CodeList.SearchCode("[베스트리포트]원자현미경, 반도체의 질문에 답"));
Console.WriteLine(m_CodeList.SearchCode("거래소, 인콘에 최대주주 지분매각 추진설 조회"));
Console.WriteLine(m_CodeList.SearchCode("와이제이엠게임즈, 서울 강남구로 본점 이전"));
InsertItem("[test] 덕산하이메탈, 덕산네오룩스 66만여주 취득14:38", "", "", new DateTime(2016, 11, 30, 00, 00, 00), DateTime.Now, "http://www.asiae.co.kr/news/sokbo/sokbo_view.htm?idxno=2016112914371817318", "asiae", 0, false); InsertItem("[test] 덕산하이메탈, 덕산네오룩스 66만여주 취득14:38", "", "", new DateTime(2016, 11, 30, 00, 00, 00), DateTime.Now, "http://www.asiae.co.kr/news/sokbo/sokbo_view.htm?idxno=2016112914371817318", "asiae", 0, false);
InsertItem("[test] 자연과환경, 12월15일~22일 주주명부폐쇄14:19", "", "", new DateTime(2016, 11, 30, 00, 00, 00), DateTime.Now, "http://www.asiae.co.kr/news/sokbo/sokbo_view.htm?idxno=2016112914193170301", "asiae", 0, false); InsertItem("[test] 자연과환경, 12월15일~22일 주주명부폐쇄14:19", "", "", new DateTime(2016, 11, 30, 00, 00, 00), DateTime.Now, "http://www.asiae.co.kr/news/sokbo/sokbo_view.htm?idxno=2016112914193170301", "asiae", 0, false);
InsertItem("[test] 이엠코리아, 한국항공우주산업과 3억원 규모 공급계약14:06", "", "", new DateTime(2016, 11, 30, 00, 00, 00), DateTime.Now, "http://www.asiae.co.kr/news/sokbo/sokbo_view.htm?idxno=2016112914055964082", "asiae", 0, false); InsertItem("[test] 이엠코리아, 한국항공우주산업과 3억원 규모 공급계약14:06", "", "", new DateTime(2016, 11, 30, 00, 00, 00), DateTime.Now, "http://www.asiae.co.kr/news/sokbo/sokbo_view.htm?idxno=2016112914055964082", "asiae", 0, false);
@@ -172,55 +199,58 @@ namespace NewsCrawler
BuyItem(Code); BuyItem(Code);
} }
void CheckPrice(int iID, CodeList.CODE_VALUE Code) void CheckPrice(NEWS_ITEM NewsItem)
{ {
if(DateTime.Now.Hour < 9 || DateTime.Now.Hour >= 15) if(DateTime.Now.Hour < 9 || DateTime.Now.Hour >= 15)
return; return;
PRICE_CHECK_DATA CheckData = new PRICE_CHECK_DATA(); PRICE_CHECK_DATA CheckData = new PRICE_CHECK_DATA();
CheckData.m_iID = iID; CheckData.m_iID = NewsItem.m_iID;
CheckData.m_Code = Code; CheckData.m_Code = NewsItem.m_Code;
CheckData.m_StartTime = DateTime.Now; CheckData.m_StartTime = DateTime.Now;
CheckData.m_NewsItem = NewsItem;
m_PriceCheckList.Enqueue(CheckData); m_PriceCheckList.Enqueue(CheckData);
} }
void ProcessSearchAndBuy(string strTitle, string strName, string strCode, string strRef, int iID) void ProcessSearchAndBuy(NEWS_ITEM NewsItem)
{ {
CodeList.CODE_VALUE Code = null; CodeList.CODE_VALUE Code = null;
if(strCode == "") if(NewsItem.m_strCode == "")
Code = m_CodeList.SearchCode(strTitle); Code = m_CodeList.SearchCode(NewsItem.m_strTitle);
else else
Code = m_CodeList.GetCode(strCode); Code = m_CodeList.GetCode(NewsItem.m_strCode);
if(Code == null) if(Code == null)
return; return;
TextCondition.RESULT MatchResult = m_Condition.Match(strTitle); NewsItem.m_Code = Code;
TextCondition.RESULT MatchResult = m_Condition.Match(NewsItem.m_strTitle);
switch(MatchResult.m_enType) switch(MatchResult.m_enType)
{ {
case TextCondition.TYPE.NEGATIVE: case TextCondition.TYPE.NEGATIVE:
Util.Log(Util.LOG_TYPE.NEGATIVE, string.Format("[{0}] {1} (keyword:{2}, code:{3})", strRef, strTitle, MatchResult.m_strKeyword, Code.ToString())); Util.Log(Util.LOG_TYPE.NEGATIVE, string.Format("[{0}] {1} (keyword:{2}, code:{3})", NewsItem.m_strRef, NewsItem.m_strTitle, MatchResult.m_strKeyword, Code.ToString()));
break; break;
case TextCondition.TYPE.POSITIVE: case TextCondition.TYPE.POSITIVE:
if((Code.m_enType&CodeList.CODE_TYPE.DENIAL) == CodeList.CODE_TYPE.DENIAL) if((Code.m_enType&CodeList.CODE_TYPE.DENIAL) == CodeList.CODE_TYPE.DENIAL)
Util.Log(Util.LOG_TYPE.DENIAL, string.Format("[{0}] {1} (keyword:{2}, code:{3})", strRef, strTitle, MatchResult.m_strKeyword, Code.ToString())); Util.Log(Util.LOG_TYPE.DENIAL, string.Format("[{0}] {1} (keyword:{2}, code:{3})", NewsItem.m_strRef, NewsItem.m_strTitle, MatchResult.m_strKeyword, Code.ToString()));
else if((Code.m_enType&CodeList.CODE_TYPE.DUPLICATED) == CodeList.CODE_TYPE.DUPLICATED) else if((Code.m_enType&CodeList.CODE_TYPE.DUPLICATED) == CodeList.CODE_TYPE.DUPLICATED)
Util.Log(Util.LOG_TYPE.DUPLICATED, string.Format("[{0}] {1} (keyword:{2}, code:{3})", strRef, strTitle, MatchResult.m_strKeyword, Code.ToString())); Util.Log(Util.LOG_TYPE.DUPLICATED, string.Format("[{0}] {1} (keyword:{2}, code:{3})", NewsItem.m_strRef, NewsItem.m_strTitle, MatchResult.m_strKeyword, Code.ToString()));
else if((Code.m_enType&CodeList.CODE_TYPE.MANUAL) == CodeList.CODE_TYPE.MANUAL) else if((Code.m_enType&CodeList.CODE_TYPE.MANUAL) == CodeList.CODE_TYPE.MANUAL)
{ {
Util.Log(Util.LOG_TYPE.MANUAL_CODE, string.Format("[{0}] {1} (keyword:{2}, code:{3})", strRef, strTitle, MatchResult.m_strKeyword, Code.ToString())); Util.Log(Util.LOG_TYPE.MANUAL_CODE, string.Format("[{0}] {1} (keyword:{2}, code:{3})", NewsItem.m_strRef, NewsItem.m_strTitle, MatchResult.m_strKeyword, Code.ToString()));
ModelessPopup ManualPopup = new ModelessPopup(this); ModelessPopup ManualPopup = new ModelessPopup(this);
ManualPopup.SetMessage(string.Format("{0}\n[{1}] {2}\n(keyword:{3}, code:{4})\n\n매수하시겠습니까?", ManualPopup.SetMessage(string.Format("{0}\n[{1}] {2}\n(keyword:{3}, code:{4})\n\n매수하시겠습니까?",
DateTime.Now.ToString("[hh:mm:ss]"), DateTime.Now.ToString("[hh:mm:ss]"),
strRef, strTitle, MatchResult.m_strKeyword, Code), Code); NewsItem.m_strRef, NewsItem.m_strTitle, MatchResult.m_strKeyword, Code), Code);
ManualPopup.TopMost = true; ManualPopup.TopMost = true;
ManualPopup.Show(); ManualPopup.Show();
} }
else else
{ {
Util.Log(Util.LOG_TYPE.POSITIVE, string.Format("[{0}] {1} (keyword:{2}, code:{3})", strRef, strTitle, MatchResult.m_strKeyword, Code.ToString())); Util.Log(Util.LOG_TYPE.POSITIVE, string.Format("[{0}] {1} (keyword:{2}, code:{3})", NewsItem.m_strRef, NewsItem.m_strTitle, MatchResult.m_strKeyword, Code.ToString()));
BuyItem(Code); BuyItem(Code);
} }
@@ -228,14 +258,14 @@ namespace NewsCrawler
break; break;
case TextCondition.TYPE.MANUAL: case TextCondition.TYPE.MANUAL:
Util.Log(Util.LOG_TYPE.MANUAL_KEYWORD, string.Format("[{0}] {1} (keyword:{2}, code:{3})", strRef, strTitle, MatchResult.m_strKeyword, Code.ToString())); Util.Log(Util.LOG_TYPE.MANUAL_KEYWORD, string.Format("[{0}] {1} (keyword:{2}, code:{3})", NewsItem.m_strRef, NewsItem.m_strTitle, MatchResult.m_strKeyword, Code.ToString()));
if(m_bBuy == true) if(m_bBuy == true)
{ {
ModelessPopup ManualPopup = new ModelessPopup(this); ModelessPopup ManualPopup = new ModelessPopup(this);
ManualPopup.SetMessage(string.Format("{0}\n[{1}] {2}\n(keyword:{3}, code:{4})\n\n매수하시겠습니까?", ManualPopup.SetMessage(string.Format("{0}\n[{1}] {2}\n(keyword:{3}, code:{4})\n\n매수하시겠습니까?",
DateTime.Now.ToString("[hh:mm:ss]"), DateTime.Now.ToString("[hh:mm:ss]"),
strRef, strTitle, MatchResult.m_strKeyword, Code), Code); NewsItem.m_strRef, NewsItem.m_strTitle, MatchResult.m_strKeyword, Code), Code);
ManualPopup.TopMost = true; ManualPopup.TopMost = true;
ManualPopup.Show(); ManualPopup.Show();
} }
@@ -244,11 +274,11 @@ namespace NewsCrawler
break; break;
case TextCondition.TYPE.NOT_MATCHED: case TextCondition.TYPE.NOT_MATCHED:
Util.Log(Util.LOG_TYPE.DEBUG, string.Format("[NOT_MATCHED] [{0}] {1}({2})", strRef, strTitle, Code.ToString())); Util.Log(Util.LOG_TYPE.DEBUG, string.Format("[NOT_MATCHED] [{0}] {1}({2})", NewsItem.m_strRef, NewsItem.m_strTitle, Code.ToString()));
break; break;
} }
CheckPrice(iID, Code); CheckPrice(NewsItem);
} }
public void OnReceivedSupplyContract(string strCodeName, float fRate) public void OnReceivedSupplyContract(string strCodeName, float fRate)
@@ -256,17 +286,17 @@ namespace NewsCrawler
CodeList.CODE_VALUE Code = m_CodeList.GetCodeByName(strCodeName); CodeList.CODE_VALUE Code = m_CodeList.GetCodeByName(strCodeName);
if(Code == null) if(Code == null)
{ {
Util.Log(Util.LOG_TYPE.VERVOSE, string.Format("[공급계약체결] 종목을 찾을 수 없음({0}, {1}%", strCodeName, fRate)); Util.Log(Util.LOG_TYPE.VERVOSE, string.Format("[DartAPI][공급계약체결] 종목을 찾을 수 없음({0}, {1}%", strCodeName, fRate));
return; return;
} }
if(fRate < m_fSupplyContractRate) if(fRate < m_fSupplyContractRate)
{ {
Util.Log(Util.LOG_TYPE.VERVOSE, string.Format("[공급계약체결] 매출액 대비율 낮음({0}, {1}% / {2}%)", strCodeName, fRate, m_fSupplyContractRate)); Util.Log(Util.LOG_TYPE.VERVOSE, string.Format("[DartAPI][공급계약체결] 매출액 대비율 낮음({0}, {1}% / {2}%)", strCodeName, fRate, m_fSupplyContractRate));
return; return;
} }
string strRef = "Dart API"; string strRef = "DartAPI";
string strTitle = string.Format("공급계약체결 - {0} {1:n2}%", strCodeName, fRate); string strTitle = string.Format("공급계약체결 - {0} {1:n2}%", strCodeName, fRate);
if((Code.m_enType&CodeList.CODE_TYPE.DENIAL) == CodeList.CODE_TYPE.DENIAL) if((Code.m_enType&CodeList.CODE_TYPE.DENIAL) == CodeList.CODE_TYPE.DENIAL)
@@ -277,6 +307,8 @@ namespace NewsCrawler
{ {
Util.Log(Util.LOG_TYPE.MANUAL_CODE, string.Format("[{0}] {1}", strRef, strTitle)); Util.Log(Util.LOG_TYPE.MANUAL_CODE, string.Format("[{0}] {1}", strRef, strTitle));
if(m_bBuy == true)
{
ModelessPopup ManualPopup = new ModelessPopup(this); ModelessPopup ManualPopup = new ModelessPopup(this);
ManualPopup.SetMessage(string.Format("{0}\n[{1}] {2}\n\n매수하시겠습니까?", ManualPopup.SetMessage(string.Format("{0}\n[{1}] {2}\n\n매수하시겠습니까?",
DateTime.Now.ToString("[hh:mm:ss]"), DateTime.Now.ToString("[hh:mm:ss]"),
@@ -284,6 +316,7 @@ namespace NewsCrawler
ManualPopup.TopMost = true; ManualPopup.TopMost = true;
ManualPopup.Show(); ManualPopup.Show();
} }
}
else else
{ {
Util.Log(Util.LOG_TYPE.POSITIVE, string.Format("[{0}] {1}", strRef, strTitle)); Util.Log(Util.LOG_TYPE.POSITIVE, string.Format("[{0}] {1}", strRef, strTitle));
@@ -302,25 +335,16 @@ namespace NewsCrawler
delegate bool IsDuplicatedURLDelegate(string strURL); delegate bool IsDuplicatedURLDelegate(string strURL);
public bool IsDuplicatedURL(string strURL) public bool IsDuplicatedURL(string strURL)
{ {
if(lvList.InvokeRequired) return (strURL != "" && m_URLs.Any(s => s == strURL));
{
lock(m_lvListLock)
return (bool)lvList.Invoke(new IsDuplicatedURLDelegate(IsDuplicatedURL), strURL);
}
else
{
lock(m_lvListLock)
return (strURL != "" && lvList.Items.Cast<ListViewItem>().Any(s => s.SubItems[chLink.Index].Text == strURL));
}
} }
public void InsertItem(string strTitle, string strName, string strCode, DateTime time, DateTime ResTime, string strURL, string strRef, double responseT, bool bInitial) public void InsertItem(string strTitle, string strName, string strCode, DateTime time, DateTime ResTime, string strURL, string strRef, double dElapseT, bool bInitial)
{ {
try try
{ {
if(this.InvokeRequired) if(this.InvokeRequired)
{ {
this.Invoke(m_InsertListViewDelegate, strTitle, strName, strCode, time, ResTime, strURL, strRef, responseT, bInitial); this.Invoke(m_InsertListViewDelegate, strTitle, strName, strCode, time, ResTime, strURL, strRef, dElapseT, bInitial);
} }
else else
{ {
@@ -330,24 +354,23 @@ namespace NewsCrawler
int iID = lvList.Items.Count+1; int iID = lvList.Items.Count+1;
if(bInitial == false) if(bInitial == false)
ProcessSearchAndBuy(strTitle, strName, strCode, strRef, iID); ProcessSearchAndBuy(new NEWS_ITEM(iID, strTitle, strName, strCode, time, ResTime, strRef, strURL, (float)dElapseT));
lock(m_lvListLock)
{
lvList.Items.Add(new ListViewItem(new string[] { lvList.Items.Add(new ListViewItem(new string[] {
iID.ToString(), iID.ToString(),
time.ToString("HH:mm:ss"), time.ToString("HH:mm:ss"),
ResTime.ToString("HH:mm:ss:fff"), ResTime.ToString("HH:mm:ss:fff"),
strRef, strRef,
strTitle, strTitle,
string.Format("{0:0.0000} ms", responseT), string.Format("{0:n4} ms", dElapseT),
"", "",
"", "",
"", "",
"", "",
"", "",
strURL })); strURL }));
}
m_URLs.Add(strURL);
if(bInitial == false) if(bInitial == false)
lvList.Sort(); lvList.Sort();
@@ -390,7 +413,7 @@ namespace NewsCrawler
m_Crawler.ReadDart(); m_Crawler.ReadDart();
m_Crawler.ReadDartAPI(); m_Crawler.ReadDartAPI();
m_Crawler.ReadEtoday(); m_Crawler.ReadEtoday();
m_Crawler.ReadEtoday2(); //m_Crawler.ReadEtoday2();
m_Crawler.ReadAsiaE(); m_Crawler.ReadAsiaE();
m_Crawler.ReadEdaily(); m_Crawler.ReadEdaily();
m_Crawler.ReadMoneyToday(); m_Crawler.ReadMoneyToday();
@@ -410,56 +433,72 @@ namespace NewsCrawler
{ {
ListViewItem item = lvList.Items.Cast<ListViewItem>().FirstOrDefault(s => s.SubItems[chId.Index].Text == iID.ToString()); ListViewItem item = lvList.Items.Cast<ListViewItem>().FirstOrDefault(s => s.SubItems[chId.Index].Text == iID.ToString());
item.SubItems[chPriceS.Index].Text = iPrice.ToString("n0"); item.SubItems[chPriceS.Index].Text = iPrice.ToString("n0");
lvList.Columns[chPriceS.Index].Width = -1;
}); });
} }
else else
{ {
ListViewItem item = lvList.Items.Cast<ListViewItem>().FirstOrDefault(s => s.SubItems[chId.Index].Text == iID.ToString()); ListViewItem item = lvList.Items.Cast<ListViewItem>().FirstOrDefault(s => s.SubItems[chId.Index].Text == iID.ToString());
item.SubItems[chPriceS.Index].Text = iPrice.ToString("n0"); item.SubItems[chPriceS.Index].Text = iPrice.ToString("n0");
lvList.Columns[chPriceS.Index].Width = -1;
} }
} }
private void UpdateLowHighPrice(int iID, int iPriceStart, int iPriceLow, int iPriceHigh) private void UpdateLowHighPrice(PRICE_CHECK_DATA Data)
{ {
if(lvList.InvokeRequired) if(lvList.InvokeRequired)
{ {
lvList.BeginInvoke((MethodInvoker)delegate () lvList.BeginInvoke((MethodInvoker)delegate ()
{ {
ListViewItem item = lvList.Items.Cast<ListViewItem>().FirstOrDefault(s => s.SubItems[chId.Index].Text == iID.ToString()); ListViewItem item = lvList.Items.Cast<ListViewItem>().FirstOrDefault(s => s.SubItems[chId.Index].Text == Data.m_iID.ToString());
item.SubItems[chPriceLow.Index].Text = string.Format("{0:n0}", iPriceLow); item.SubItems[chPriceLow.Index].Text = string.Format("{0:n0}", Data.m_iPriceLow);
float fLowRate = (iPriceLow-iPriceStart)*100/(float)iPriceStart; float fLowRate = (Data.m_iPriceLow-Data.m_iPriceStart)*100/(float)Data.m_iPriceStart;
item.UseItemStyleForSubItems = false;
item.SubItems[chPriceLowP.Index].Text = string.Format("{0:n}", fLowRate); item.SubItems[chPriceLowP.Index].Text = string.Format("{0:n}", fLowRate);
if(fLowRate > 0) if(fLowRate > 0)
item.SubItems[chPriceLowP.Index].ForeColor = Color.Red; item.SubItems[chPriceLowP.Index].ForeColor = Color.Red;
else if(fLowRate < 0) else if(fLowRate < 0)
item.SubItems[chPriceLowP.Index].ForeColor = Color.Blue; item.SubItems[chPriceLowP.Index].ForeColor = Color.Blue;
item.SubItems[chPriceHigh.Index].Text = string.Format("{0:n0}", iPriceHigh); item.SubItems[chPriceHigh.Index].Text = string.Format("{0:n0}", Data.m_iPriceHigh);
float fLowHigh = (iPriceHigh-iPriceStart)*100/(float)iPriceStart; float fLowHigh = (Data.m_iPriceHigh-Data.m_iPriceStart)*100/(float)Data.m_iPriceStart;
item.SubItems[chPriceHighP.Index].Text = string.Format("{0:n}", fLowHigh); item.SubItems[chPriceHighP.Index].Text = string.Format("{0:n}", fLowHigh);
if(fLowHigh > 0) if(fLowHigh > 0)
item.SubItems[chPriceHighP.Index].ForeColor = Color.Red; item.SubItems[chPriceHighP.Index].ForeColor = Color.Red;
else if(fLowHigh < 0) else if(fLowHigh < 0)
item.SubItems[chPriceHighP.Index].ForeColor = Color.Blue; item.SubItems[chPriceHighP.Index].ForeColor = Color.Blue;
lvList.Columns[chPriceHighP.Index].Width = -1;
lvList.Columns[chPriceLowP.Index].Width = -1;
}); });
} }
else else
{ {
ListViewItem item = lvList.Items.Cast<ListViewItem>().FirstOrDefault(s => s.SubItems[chId.Index].Text == iID.ToString()); ListViewItem item = lvList.Items.Cast<ListViewItem>().FirstOrDefault(s => s.SubItems[chId.Index].Text == Data.m_iID.ToString());
item.SubItems[chPriceLow.Index].Text = string.Format("{0:n0}", iPriceLow); item.SubItems[chPriceLow.Index].Text = string.Format("{0:n0}", Data.m_iPriceLow);
float fLowRate = (iPriceLow-iPriceStart)*100/(float)iPriceStart; float fLowRate = (Data.m_iPriceLow-Data.m_iPriceStart)*100/(float)Data.m_iPriceStart;
item.SubItems[chPriceLowP.Index].Text = string.Format("{0:n}", fLowRate); item.SubItems[chPriceLowP.Index].Text = string.Format("{0:n}", fLowRate);
item.UseItemStyleForSubItems = false;
if(fLowRate > 0) if(fLowRate > 0)
item.SubItems[chPriceLowP.Index].ForeColor = Color.Red; item.SubItems[chPriceLowP.Index].ForeColor = Color.Red;
else if(fLowRate < 0) else if(fLowRate < 0)
item.SubItems[chPriceLowP.Index].ForeColor = Color.Blue; item.SubItems[chPriceLowP.Index].ForeColor = Color.Blue;
item.SubItems[chPriceHigh.Index].Text = string.Format("{0:n0}", iPriceHigh); item.SubItems[chPriceHigh.Index].Text = string.Format("{0:n0}", Data.m_iPriceHigh);
float fLowHigh = (iPriceHigh-iPriceStart)*100/(float)iPriceStart; float fLowHigh = (Data.m_iPriceHigh-Data.m_iPriceStart)*100/(float)Data.m_iPriceStart;
item.SubItems[chPriceHighP.Index].Text = string.Format("{0:n}", fLowHigh); item.SubItems[chPriceHighP.Index].Text = string.Format("{0:n}", fLowHigh);
if(fLowHigh > 0) if(fLowHigh > 0)
item.SubItems[chPriceHighP.Index].ForeColor = Color.Red; item.SubItems[chPriceHighP.Index].ForeColor = Color.Red;
else if(fLowHigh < 0) else if(fLowHigh < 0)
item.SubItems[chPriceHighP.Index].ForeColor = Color.Blue; item.SubItems[chPriceHighP.Index].ForeColor = Color.Blue;
lvList.Columns[chPriceHighP.Index].Width = -1;
lvList.Columns[chPriceLowP.Index].Width = -1;
} }
m_Excel.AddRow(Data.m_NewsItem.m_NewsTime.ToString("HH:mm:ss:fff"), Data.m_NewsItem.m_ResTime.ToString("HH:mm:ss:fff"), Data.m_NewsItem.m_strRef, Data.m_NewsItem.m_strTitle, Data.m_NewsItem.m_fElapseT,
Data.m_iPriceStart,
Data.m_iPriceLow, (Data.m_iPriceLow-Data.m_iPriceStart)*100/(float)Data.m_iPriceStart,
Data.m_iPriceHigh, (Data.m_iPriceHigh-Data.m_iPriceStart)*100/(float)Data.m_iPriceStart,
Data.m_NewsItem.m_strURL);
} }
private void PriceCheckTimer_Elapsed(object sender, System.Timers.ElapsedEventArgs e) private void PriceCheckTimer_Elapsed(object sender, System.Timers.ElapsedEventArgs e)
@@ -482,7 +521,7 @@ namespace NewsCrawler
m_CybosHelper.GetLowHighPrice(data.m_Code, data.m_StartTime, 5, out data.m_iPriceLow, out data.m_iPriceHigh); m_CybosHelper.GetLowHighPrice(data.m_Code, data.m_StartTime, 5, out data.m_iPriceLow, out data.m_iPriceHigh);
data.m_iTryCnt++; data.m_iTryCnt++;
if(data.m_iPriceHigh > 0) if(data.m_iPriceHigh > 0)
UpdateLowHighPrice(data.m_iID, data.m_iPriceStart, data.m_iPriceLow, data.m_iPriceHigh); UpdateLowHighPrice(data);
} }
} }

13
Util.cs
View File

@@ -28,6 +28,9 @@ namespace NewsCrawler
static string m_strLogFile = null; static string m_strLogFile = null;
static RichTextBox m_LogBox = null; static RichTextBox m_LogBox = null;
delegate void InsertLogDelegate(RichTextBox LogBox, LOG_TYPE enType, string strLog);
static InsertLogDelegate m_InsertLogDelegate = new InsertLogDelegate(InsertLog);
public static void SetLogView(RichTextBox logBox) public static void SetLogView(RichTextBox logBox)
{ {
m_LogBox = logBox; m_LogBox = logBox;
@@ -38,16 +41,11 @@ namespace NewsCrawler
m_LogBox = null; m_LogBox = null;
} }
delegate void InsertLogDelegate(RichTextBox LogBox, LOG_TYPE enType, string strLog);
static void InsertLog(RichTextBox LogBox, LOG_TYPE enType, string strLog) static void InsertLog(RichTextBox LogBox, LOG_TYPE enType, string strLog)
{ {
Form mainForm = (Application.OpenForms.Count > 0) ? Application.OpenForms[0] : null;
bool bInvoke = mainForm != null ? mainForm.InvokeRequired || LogBox.InvokeRequired : LogBox.InvokeRequired;
if(LogBox.InvokeRequired) if(LogBox.InvokeRequired)
{ {
LogBox.Invoke(new InsertLogDelegate(InsertLog), LogBox, enType, strLog); LogBox.Invoke(m_InsertLogDelegate, LogBox, enType, strLog);
} }
else else
{ {
@@ -93,9 +91,6 @@ namespace NewsCrawler
public static void Log(LOG_TYPE enType, string strLog) public static void Log(LOG_TYPE enType, string strLog)
{ {
if(strLog.Contains("인덱스"))
Console.WriteLine("ddddddddd");
if(Directory.Exists(GetLogPath()) == false) if(Directory.Exists(GetLogPath()) == false)
Directory.CreateDirectory(GetLogPath()); Directory.CreateDirectory(GetLogPath());