Showing
4 changed files
with
235 additions
and
61 deletions
| 1 | var express = require('express'); | 1 | var express = require('express'); |
| 2 | const request = require('request'); | 2 | const request = require('request'); |
| 3 | const TARGET_URL = 'https://api.line.me/v2/bot/message/reply' | 3 | const TARGET_URL = 'https://api.line.me/v2/bot/message/reply' |
| 4 | -const TOKEN = 'OVIxKODBqM8Pn2dpFtFeSLsDbBvApfTu88rh8wFGOzfvgvPjmBH0A4XKii97VxIDO9shYyTix4qGq32vwvL895Rbss5VSVEiU/XG5lOdyTLgECkSQKOdObSetZwcVHbGmzZJ+0Cz5vZrB5KuImOwrwdB04t89/1O/w1cDnyilFU=' | 4 | +const TOKEN = "sGB5EZq14+Lu4sc6Gt6NJ1Sx/rDtE1BsTyfZeNX42XVVjcgX1kk6/Uj1H40IQ1X3y8MzJLvKGifhioNCJLWQkWH2i95EtNDQyGn7Iqu6MnQRE7pg/z7klGgswS9974s0EKX90FcCfAIndNSYAG+d5gdB04t89/1O/w1cDnyilFU=" |
| 5 | const fs = require('fs'); | 5 | const fs = require('fs'); |
| 6 | const path = require('path'); | 6 | const path = require('path'); |
| 7 | const HTTPS = require('https'); | 7 | const HTTPS = require('https'); |
| 8 | -const domain = "2017103989.oss2021.tk" | 8 | +const domain = "2016100990.oss2021.tk" |
| 9 | const sslport = 23023; | 9 | const sslport = 23023; |
| 10 | const bodyParser = require('body-parser'); | 10 | const bodyParser = require('body-parser'); |
| 11 | var app = express(); | 11 | var app = express(); |
| 12 | 12 | ||
| 13 | var stockarr = []; | 13 | var stockarr = []; |
| 14 | - | 14 | +var pastreply = ""; |
| 15 | +var tatic =""; | ||
| 15 | app.use('/simages', express.static(__dirname + '/src')); | 16 | app.use('/simages', express.static(__dirname + '/src')); |
| 16 | app.use(bodyParser.json()); | 17 | app.use(bodyParser.json()); |
| 17 | app.post('/hook', function (req, res) { | 18 | app.post('/hook', function (req, res) { |
| ... | @@ -25,33 +26,154 @@ app.post('/hook', function (req, res) { | ... | @@ -25,33 +26,154 @@ app.post('/hook', function (req, res) { |
| 25 | console.log('[request message]', eventObj.message); | 26 | console.log('[request message]', eventObj.message); |
| 26 | if(eventObj.type == 'postback') | 27 | if(eventObj.type == 'postback') |
| 27 | { | 28 | { |
| 28 | - if(eventObj.postback.data == 'action=datetemp&selectId=1') | 29 | + if(eventObj.postback.data == 'action=datetemp&selectId=1' && pastreply == "비중 추천"){ |
| 30 | + console.log(stockarr); | ||
| 31 | + weight_recommend(eventObj.replyToken, eventObj.postback.params.date) | ||
| 32 | + tatic = "" | ||
| 33 | + pastreply = "" | ||
| 34 | + } | ||
| 35 | + else | ||
| 29 | { | 36 | { |
| 30 | - | ||
| 31 | optimizer(eventObj.replyToken, eventObj.postback.params.date) | 37 | optimizer(eventObj.replyToken, eventObj.postback.params.date) |
| 32 | stockarr.splice(0, stockarr.length); | 38 | stockarr.splice(0, stockarr.length); |
| 33 | } | 39 | } |
| 34 | } | 40 | } |
| 35 | else | 41 | else |
| 36 | - { | 42 | + { console.log(eventObj.message.text) |
| 43 | + console.log(pastreply) | ||
| 37 | if(eventObj.message.text == '도움말' || eventObj.message.text == '주가 도움말' || eventObj.message.text == '비중 추천 도움말' || eventObj.message.text == '백테스트 도움말') | 44 | if(eventObj.message.text == '도움말' || eventObj.message.text == '주가 도움말' || eventObj.message.text == '비중 추천 도움말' || eventObj.message.text == '백테스트 도움말') |
| 38 | { | 45 | { |
| 39 | printhelp(eventObj.replyToken, eventObj.message.text) | 46 | printhelp(eventObj.replyToken, eventObj.message.text) |
| 40 | } | 47 | } |
| 41 | - else if(eventObj.message.text.indexOf(' ') != -1) | 48 | + else if(eventObj.message.text == '백테스트') |
| 42 | { | 49 | { |
| 43 | date(eventObj.replyToken, eventObj.message.text) | 50 | date(eventObj.replyToken, eventObj.message.text) |
| 44 | } | 51 | } |
| 45 | - else | 52 | + else if (eventObj.message.text == '주가') |
| 46 | { | 53 | { |
| 54 | + basicinform_pre(eventObj.replyToken, eventObj.message.text) | ||
| 55 | + pastreply = '주가' | ||
| 56 | + console.log(pastreply); | ||
| 57 | + } | ||
| 58 | + else if ( pastreply == '주가' && eventObj.message.text.indexOf(' ') == -1){ | ||
| 47 | basicinform(eventObj.replyToken, eventObj.message.text) | 59 | basicinform(eventObj.replyToken, eventObj.message.text) |
| 48 | } | 60 | } |
| 61 | + else if (eventObj.message.text == '비중 추천'){ | ||
| 62 | + weight_1(eventObj.replyToken, eventObj.message.text) | ||
| 63 | + pastreply = '비중 추천' | ||
| 64 | + } | ||
| 65 | + else if (pastreply = '비중 추천' && eventObj.message.text.indexOf(' ') != -1){ | ||
| 66 | + var holder = eventObj.message.text.split(' ') | ||
| 67 | + console.log("holder",holder) | ||
| 68 | + var i; | ||
| 69 | + for(i = 0; i < holder.length; i++) | ||
| 70 | + { | ||
| 71 | + stockarr[i] = holder[i]; | ||
| 72 | + } | ||
| 73 | + weight_2(eventObj.replyToken, eventObj.message.text); | ||
| 74 | + pastreply = "전략" | ||
| 75 | + } | ||
| 76 | + | ||
| 77 | + else if (pastreply = "전략" && (eventObj.message.text == 'gmv' || eventObj.message.text == 'ms') || eventObj.message.text == 'rp'){ | ||
| 78 | + tatic = eventObj.message.text | ||
| 79 | + pastreply = "비중 추천" | ||
| 80 | + date(eventObj.replyToken, eventObj.message.text) | ||
| 81 | + } | ||
| 82 | + else { | ||
| 83 | + errormessage(eventObj.replyToken, eventObj.message.text); | ||
| 84 | + pastreply = '' | ||
| 85 | + } | ||
| 49 | } | 86 | } |
| 50 | 87 | ||
| 51 | res.sendStatus(200); | 88 | res.sendStatus(200); |
| 52 | 89 | ||
| 53 | }); | 90 | }); |
| 54 | 91 | ||
| 92 | +function errormessage(replyToken, message){ | ||
| 93 | + request.post( | ||
| 94 | + { | ||
| 95 | + url: TARGET_URL, | ||
| 96 | + headers: { | ||
| 97 | + 'Authorization': `Bearer ${TOKEN}` | ||
| 98 | + }, | ||
| 99 | + json: { | ||
| 100 | + "replyToken":replyToken, | ||
| 101 | + "messages":[ | ||
| 102 | + { | ||
| 103 | + "type":"text", | ||
| 104 | + "text":"정해진 양식대로 입력하지 않으셨어요. \n 처음부터 다시 진행해주세요 :)" | ||
| 105 | + } | ||
| 106 | + ] | ||
| 107 | + } | ||
| 108 | + },(error, response, body) => { | ||
| 109 | + console.log(body) | ||
| 110 | + }); | ||
| 111 | +} | ||
| 112 | + | ||
| 113 | + | ||
| 114 | +function weight_1(replyToken, message){ | ||
| 115 | + request.post( | ||
| 116 | + { | ||
| 117 | + url: TARGET_URL, | ||
| 118 | + headers: { | ||
| 119 | + 'Authorization': `Bearer ${TOKEN}` | ||
| 120 | + }, | ||
| 121 | + json: { | ||
| 122 | + "replyToken":replyToken, | ||
| 123 | + "messages":[ | ||
| 124 | + { | ||
| 125 | + "type":"text", | ||
| 126 | + "text":"포트폴리오에 넣을 종목을 입력해주세요. \n 두 종목 이상을 띄어쓰기로 구분해서 입력해주세요!" | ||
| 127 | + } | ||
| 128 | + ] | ||
| 129 | + } | ||
| 130 | + },(error, response, body) => { | ||
| 131 | + console.log(body) | ||
| 132 | + }); | ||
| 133 | +} | ||
| 134 | + | ||
| 135 | +function weight_2(replyToken, message){ | ||
| 136 | + request.post( | ||
| 137 | + { | ||
| 138 | + url: TARGET_URL, | ||
| 139 | + headers: { | ||
| 140 | + 'Authorization': `Bearer ${TOKEN}` | ||
| 141 | + }, | ||
| 142 | + json: { | ||
| 143 | + "replyToken":replyToken, | ||
| 144 | + "messages":[ | ||
| 145 | + { | ||
| 146 | + "type":"text", | ||
| 147 | + "text":"전략을 입력해주세요 \n gmv, ms, rp 중 하나를 정확히 입력해주세요!" | ||
| 148 | + } | ||
| 149 | + ] | ||
| 150 | + } | ||
| 151 | + },(error, response, body) => { | ||
| 152 | + console.log(body) | ||
| 153 | + }); | ||
| 154 | +} | ||
| 155 | + | ||
| 156 | +function basicinform_pre(replyToken, message){ | ||
| 157 | + request.post( | ||
| 158 | + { | ||
| 159 | + url: TARGET_URL, | ||
| 160 | + headers: { | ||
| 161 | + 'Authorization': `Bearer ${TOKEN}` | ||
| 162 | + }, | ||
| 163 | + json: { | ||
| 164 | + "replyToken":replyToken, | ||
| 165 | + "messages":[ | ||
| 166 | + { | ||
| 167 | + "type":"text", | ||
| 168 | + "text":"종목명을 입력해주세요!" | ||
| 169 | + } | ||
| 170 | + ] | ||
| 171 | + } | ||
| 172 | + },(error, response, body) => { | ||
| 173 | + console.log(body) | ||
| 174 | + }); | ||
| 175 | +} | ||
| 176 | + | ||
| 55 | function printhelp(replyToken, message){ | 177 | function printhelp(replyToken, message){ |
| 56 | if(message == '도움말'){ | 178 | if(message == '도움말'){ |
| 57 | request.post( | 179 | request.post( |
| ... | @@ -195,7 +317,7 @@ function basicinform(replyToken, message) { | ... | @@ -195,7 +317,7 @@ function basicinform(replyToken, message) { |
| 195 | const Callback = (data) => { | 317 | const Callback = (data) => { |
| 196 | pystring = data.toString(); | 318 | pystring = data.toString(); |
| 197 | if(pystring[0] == '1') | 319 | if(pystring[0] == '1') |
| 198 | - { | 320 | + { pastreply ="" |
| 199 | pystring = pystring.replace('1현', '현'); | 321 | pystring = pystring.replace('1현', '현'); |
| 200 | request.post( | 322 | request.post( |
| 201 | { | 323 | { |
| ... | @@ -209,11 +331,6 @@ function basicinform(replyToken, message) { | ... | @@ -209,11 +331,6 @@ function basicinform(replyToken, message) { |
| 209 | { | 331 | { |
| 210 | "type":"text", | 332 | "type":"text", |
| 211 | "text":pystring | 333 | "text":pystring |
| 212 | - }, | ||
| 213 | - { | ||
| 214 | - "type":"image", | ||
| 215 | - "originalContentUrl": "https://2017103989.oss2021.tk:23023/simages/test.png", | ||
| 216 | - "previewImageUrl": "https://2017103989.oss2021.tk:23023/simages/test.png" | ||
| 217 | } | 334 | } |
| 218 | ] | 335 | ] |
| 219 | } | 336 | } |
| ... | @@ -222,7 +339,7 @@ function basicinform(replyToken, message) { | ... | @@ -222,7 +339,7 @@ function basicinform(replyToken, message) { |
| 222 | }); | 339 | }); |
| 223 | } | 340 | } |
| 224 | else | 341 | else |
| 225 | - { | 342 | + { |
| 226 | var candarr = pystring.split('\n') | 343 | var candarr = pystring.split('\n') |
| 227 | request.post( | 344 | request.post( |
| 228 | { | 345 | { |
| ... | @@ -274,6 +391,7 @@ function basicinform(replyToken, message) { | ... | @@ -274,6 +391,7 @@ function basicinform(replyToken, message) { |
| 274 | } | 391 | } |
| 275 | }; | 392 | }; |
| 276 | process.stdout.on("data", Callback); | 393 | process.stdout.on("data", Callback); |
| 394 | + | ||
| 277 | } | 395 | } |
| 278 | 396 | ||
| 279 | function optimizer(replyToken, sdate) { | 397 | function optimizer(replyToken, sdate) { |
| ... | @@ -317,13 +435,59 @@ function optimizer(replyToken, sdate) { | ... | @@ -317,13 +435,59 @@ function optimizer(replyToken, sdate) { |
| 317 | process.stdout.on("data", Callback); | 435 | process.stdout.on("data", Callback); |
| 318 | } | 436 | } |
| 319 | 437 | ||
| 438 | +function weight_recommend(replyToken, sdate) { | ||
| 439 | + sdate = sdate.toString(); | ||
| 440 | + var pystring = '' | ||
| 441 | + var i; | ||
| 442 | + for(i = 0; i < stockarr.length; i++) | ||
| 443 | + { | ||
| 444 | + pystring += stockarr[i]; | ||
| 445 | + pystring += ',' | ||
| 446 | + } | ||
| 447 | + pystring += sdate; | ||
| 448 | + console.log(pystring); | ||
| 449 | + const spawn = require("child_process").spawn; | ||
| 450 | + const process = spawn("python", ["optimizer.py", pystring ,"weight",tatic]); | ||
| 451 | + const Callback = (data) => { | ||
| 452 | + pystring = data.toString(); | ||
| 453 | + pystring = pystring.slice(1,-2) | ||
| 454 | + pastreply == "" | ||
| 455 | + request.post( | ||
| 456 | + { | ||
| 457 | + url: TARGET_URL, | ||
| 458 | + headers: { | ||
| 459 | + 'Authorization': `Bearer ${TOKEN}` | ||
| 460 | + }, | ||
| 461 | + json: { | ||
| 462 | + "replyToken":replyToken, | ||
| 463 | + "messages":[ | ||
| 464 | + { | ||
| 465 | + "type":"text", | ||
| 466 | + "text": "비중 추천 결과입니다!" | ||
| 467 | + }, | ||
| 468 | + { | ||
| 469 | + "type":"text", | ||
| 470 | + "text":pystring | ||
| 471 | + } | ||
| 472 | + ] | ||
| 473 | + } | ||
| 474 | + },(error, response, body) => { | ||
| 475 | + console.log(body) | ||
| 476 | + }); | ||
| 477 | + } | ||
| 478 | + process.stdout.on("data", Callback); | ||
| 479 | +} | ||
| 480 | + | ||
| 320 | function date(replyToken, message) { | 481 | function date(replyToken, message) { |
| 482 | + | ||
| 483 | + /* | ||
| 321 | var holder = message.split(' ') | 484 | var holder = message.split(' ') |
| 322 | var i; | 485 | var i; |
| 323 | for(i = 0; i < holder.length; i++) | 486 | for(i = 0; i < holder.length; i++) |
| 324 | { | 487 | { |
| 325 | stockarr[i] = holder[i]; | 488 | stockarr[i] = holder[i]; |
| 326 | } | 489 | } |
| 490 | + */ | ||
| 327 | var today = new Date(); | 491 | var today = new Date(); |
| 328 | var year = today.getFullYear(); | 492 | var year = today.getFullYear(); |
| 329 | var month = today.getMonth() + 1; | 493 | var month = today.getMonth() + 1; | ... | ... |
| ... | @@ -10,12 +10,8 @@ def get_matches(query, choices, limit=3): | ... | @@ -10,12 +10,8 @@ def get_matches(query, choices, limit=3): |
| 10 | return result | 10 | return result |
| 11 | 11 | ||
| 12 | def basicinform(input): | 12 | def basicinform(input): |
| 13 | -<<<<<<< HEAD | ||
| 14 | - stocks = pd.read_csv('stockcodename.csv', index_col=0) | ||
| 15 | -======= | ||
| 16 | stocks = pd.read_csv('stockcodename.csv', names=['Symbol', 'Market', 'Name' | 13 | stocks = pd.read_csv('stockcodename.csv', names=['Symbol', 'Market', 'Name' |
| 17 | , 'Sector', 'Industry', 'ListingDate', 'SettleMonth', 'Represetitive', 'HomePage', 'Region'], index_col=0) | 14 | , 'Sector', 'Industry', 'ListingDate', 'SettleMonth', 'Represetitive', 'HomePage', 'Region'], index_col=0) |
| 18 | ->>>>>>> f1c2d34f3272bc7cfebf6e887b72493185c4c57c | ||
| 19 | symbol = '' | 15 | symbol = '' |
| 20 | 16 | ||
| 21 | for i in enumerate(stocks.Name): | 17 | for i in enumerate(stocks.Name): |
| ... | @@ -50,10 +46,7 @@ def basicinform(input): | ... | @@ -50,10 +46,7 @@ def basicinform(input): |
| 50 | return value | 46 | return value |
| 51 | 47 | ||
| 52 | 48 | ||
| 53 | -<<<<<<< HEAD | ||
| 54 | -======= | ||
| 55 | # print(basicinform('호텔신라')) | 49 | # print(basicinform('호텔신라')) |
| 56 | 50 | ||
| 57 | ->>>>>>> f1c2d34f3272bc7cfebf6e887b72493185c4c57c | ||
| 58 | args = sys.argv | 51 | args = sys.argv |
| 59 | -print(basicinform(args[0])) | 52 | +print(basicinform(args[1])) | ... | ... |
| ... | @@ -583,42 +583,59 @@ class back_test: | ... | @@ -583,42 +583,59 @@ class back_test: |
| 583 | # print(back_test().backtest_data(['삼성전자','LG전자'],[0.9,0.1],'2010-01-01', '2021-01-01',10000000,3, 'monthly', 'gmv')['pfo_return'][0]['acc_return_ratio']) | 583 | # print(back_test().backtest_data(['삼성전자','LG전자'],[0.9,0.1],'2010-01-01', '2021-01-01',10000000,3, 'monthly', 'gmv')['pfo_return'][0]['acc_return_ratio']) |
| 584 | # print(back_test().backtest_data(['삼성전자','LG전자'],[0.9,0.1],'2018-01-01', '2021-01-01',10000000,6, 'monthly', 'gmv')) | 584 | # print(back_test().backtest_data(['삼성전자','LG전자'],[0.9,0.1],'2018-01-01', '2021-01-01',10000000,6, 'monthly', 'gmv')) |
| 585 | 585 | ||
| 586 | -args = sys.argv[1].split(",") | 586 | + |
| 587 | - | 587 | +if (sys.argv[2] == "weight"): |
| 588 | -assets = [] | 588 | + args = sys.argv[1].split(",") |
| 589 | -gravity = [] | 589 | + assets = [] |
| 590 | -for i in range(len(args)-1): | 590 | + gravity = [] |
| 591 | - assets.append(args[i]) | 591 | + for i in range(len(args)-1): |
| 592 | - gravity.append(0) | 592 | + assets.append(args[i]) |
| 593 | - | 593 | + gravity.append(0) |
| 594 | -data = back_test().backtest_data(assets,gravity,args[-1], '2021-01-02',10000000,6, 'monthly', 'gmv') | 594 | + |
| 595 | - | 595 | + if (sys.argv[3] == 'gmv'): |
| 596 | - | 596 | + print(c_Models(assets, gravity, args[-1],'2021-06-01').gmv_opt()) |
| 597 | -#data = back_test().backtest_data(['삼성전자','LG전자','호텔신라'],[0.1,0.1,0.8],'2020-01-01', '2021-01-02',10000000,6, 'monthly', 'gmv') | 597 | + elif (sys.argv[3] == 'ms'): |
| 598 | -# data = back_test().backtest_data(['삼성전자','LG전자'],[0.1,0.1],'2020-01-01', '2021-01-02',10000000,6, 'monthly', 'gmv') | 598 | + print(c_Models(assets, gravity, args[-1],'2021-06-01').ms_opt()) |
| 599 | -x = data['pfo_return'][0]['Date'] | 599 | + elif (sys.argv[3] == 'rp'): |
| 600 | -y = data['pfo_return'][0]['acc_return ratio'] | 600 | + print(c_Models(assets, gravity, args[-1],'2021-06-01').rp_opt()) |
| 601 | -y2 = data['bench'][0]['KOSPI_acc_return'] | 601 | + |
| 602 | -y3 = data['bench'][0]['S&P500_acc_return'] | 602 | +else: |
| 603 | -x_ticks = [] | 603 | + args = sys.argv[1].split(",") |
| 604 | -for i,j in enumerate(x): | 604 | + assets = [] |
| 605 | - if (i % 6) == 0: | 605 | + gravity = [] |
| 606 | - x_ticks.append(j) | 606 | + for i in range(len(args)-1): |
| 607 | - else: | 607 | + assets.append(args[i]) |
| 608 | - x_ticks.append('') | 608 | + gravity.append(0) |
| 609 | -x_ticks[-1]= x[-1] | 609 | + |
| 610 | -plt.figure(figsize=(10,5)) | 610 | + data = back_test().backtest_data(assets,gravity,args[-1], '2021-06-01',10000000,6, 'monthly', 'gmv') |
| 611 | -ax=plt.gca() | 611 | + |
| 612 | -ax.xaxis.set_major_locator(ticker.MultipleLocator(12)) | 612 | + |
| 613 | -plt.plot(x,y,label = 'gmv result') | 613 | + #data = back_test().backtest_data(['삼성전자','LG전자','호텔신라'],[0.1,0.1,0.8],'2020-01-01', '2021-01-02',10000000,6, 'monthly', 'gmv') |
| 614 | -plt.plot(x,y2 ,label = 'kospi result') | 614 | + # data = back_test().backtest_data(['삼성전자','LG전자'],[0.1,0.1],'2020-01-01', '2021-01-02',10000000,6, 'monthly', 'gmv') |
| 615 | -plt.plot(x,y3, label = 's&p500 result') | 615 | + x = data['pfo_return'][0]['Date'] |
| 616 | -plt.xticks(x_ticks,rotation=60) | 616 | + y = data['pfo_return'][0]['acc_return ratio'] |
| 617 | -plt.xlabel('Date') | 617 | + y2 = data['bench'][0]['KOSPI_acc_return'] |
| 618 | -plt.ylabel('Return') | 618 | + y3 = data['bench'][0]['S&P500_acc_return'] |
| 619 | -plt.title('result') | 619 | + x_ticks = [] |
| 620 | -plt.legend() | 620 | + for i,j in enumerate(x): |
| 621 | -plt.show() | 621 | + if (i % 6) == 0: |
| 622 | -plt.savefig("./src/test.png", dpi = 100) | 622 | + x_ticks.append(j) |
| 623 | -print("end") | 623 | + else: |
| 624 | + x_ticks.append('') | ||
| 625 | + x_ticks[-1]= x[-1] | ||
| 626 | + plt.figure(figsize=(10,5)) | ||
| 627 | + ax=plt.gca() | ||
| 628 | + ax.xaxis.set_major_locator(ticker.MultipleLocator(12)) | ||
| 629 | + plt.plot(x,y,label = 'gmv result') | ||
| 630 | + plt.plot(x,y2 ,label = 'kospi result') | ||
| 631 | + plt.plot(x,y3, label = 's&p500 result') | ||
| 632 | + plt.xticks(x_ticks,rotation=60) | ||
| 633 | + plt.xlabel('Date') | ||
| 634 | + plt.ylabel('Return') | ||
| 635 | + plt.title('result') | ||
| 636 | + plt.legend() | ||
| 637 | + plt.show() | ||
| 638 | + plt.savefig("./src/test.png", dpi = 100) | ||
| 639 | + print("end") | ||
| 640 | + | ||
| 624 | 641 | ... | ... |
server/src/test.png
0 → 100644
45 KB
-
Please register or login to post a comment