포트폴리오 서비스(DB 저장하기)

·2023년 12월 12일

Portfolio Backtest

목록 보기
6/31

생각한 것

  • 주식 정보를 저장하는데, 일자마다 종목의 수가 조금 차이가 난다.
    -> 가장 최근의 일자로 저장하고 추후 추가하는 방향으로 고려
  • json에서 데이터를 가져와서 저장하는 부분을 어디다가 구현 할 것인가?
    -> 객체 지향의 관점에서 보았을 때, 새로운 클래스로 구현하는 것이 좋을거 같다는 생각을 했다.
  • 저장하는 부분을 @Component로 구현해서 관리자가 사용할 수 있도록 구현하자
    -> CommandLine을 고려하기도 하였는데 데이터가 추후에 추가 될 가능성이 많기 때문에 관리자를 위한 페이지를 구성하는게 좋아보였다.

StockDataLoader 클래스

@Component
public class StockDataLoader {
    private final StockInfoService stockInfoService;
    private final StockPriceService stockPriceService;
    private final DataPortalApi dataPortalApi;

    public StockDataLoader(StockInfoService stockInfoService, StockPriceService stockPriceService, DataPortalApi dataPortalApi) {
        this.stockInfoService = stockInfoService;
        this.stockPriceService = stockPriceService;
        this.dataPortalApi = dataPortalApi;
    }

    public void loadStockInfoByBaseDate(String baseDate) {
        JsonArray stockJson = dataPortalApi.getStock(baseDate);

        if(stockJson == null){
            return;
        }

        for(int i = 0 ; i < stockJson.size() ; i++){
            StockInfo stockInfo = new StockInfo();
            stockInfo.setItmsNm(stockJson.get(i).getAsJsonObject().get("itmsNm").getAsString());
            stockInfo.setMrktCtg(stockJson.get(i).getAsJsonObject().get("mrktCtg").getAsString());
            stockInfo.setSrtnCd(stockJson.get(i).getAsJsonObject().get("srtnCd").getAsString());
            stockInfo.setIsinCd(stockJson.get(i).getAsJsonObject().get("isinCd").getAsString());

            stockInfoService.save(stockInfo);
        }
    }

    public void loadStockPriceByBaseDate(String baseDate) {
        JsonArray stockJson = dataPortalApi.getStock(baseDate);

        if(stockJson == null){
            return;
        }

        for(int i = 0 ; i < stockJson.size() ; i++){
            StockPrice stockPrice = new StockPrice();
            stockPrice.setItmsNm(stockJson.get(i).getAsJsonObject().get("itmsNm").getAsString());
            stockPrice.setMkp(Long.parseLong(stockJson.get(i).getAsJsonObject().get("mkp").getAsString()));
            stockPrice.setClpr(Long.parseLong(stockJson.get(i).getAsJsonObject().get("clpr").getAsString()));
            stockPrice.setHipr(Long.parseLong(stockJson.get(i).getAsJsonObject().get("hipr").getAsString()));
            stockPrice.setLopr(Long.parseLong(stockJson.get(i).getAsJsonObject().get("lopr").getAsString()));
            stockPrice.setTrqu(Long.parseLong(stockJson.get(i).getAsJsonObject().get("trqu").getAsString()));
            stockPrice.setTrPrc(Long.parseLong(stockJson.get(i).getAsJsonObject().get("trPrc").getAsString()));
            stockPrice.setMrktTotAmt(Long.parseLong(stockJson.get(i).getAsJsonObject().get("mrktTotAmt").getAsString()));
            String basDt = stockJson.get(i).getAsJsonObject().get("basDt").getAsString();
            LocalDate date = LocalDate.parse(basDt, DateTimeFormatter.ofPattern("yyyyMMdd"));
            stockPrice.setBasDt(date);

            stockPriceService.save(stockPrice);
        }
    }

    public void loadStockPriceByTerm(String startDate, String endDate){
        LocalDate start = LocalDate.parse(startDate, DateTimeFormatter.ofPattern("yyyyMMdd"));
        LocalDate end = LocalDate.parse(endDate, DateTimeFormatter.ofPattern("yyyyMMdd")).plusDays(1);
        LocalDate date = start;
        while(date.isBefore(end)){
            loadStockPriceByBaseDate(date.format(DateTimeFormatter.ofPattern("yyyyMMdd")));
            date = date.plusDays(1);
        }
    }
}

날짜를 입력받아 StockInfo, StockPrice를 저장하는 함수와 시작날짜와 끝날짜를 받아 StockPrice를 저장하는 함수를 구현하였다.

DataPortalApi 클래스 수정

    public String getStockJson(String baseDate) {
        String path = "json/stock/"+baseDate.substring(0, 4)+"/"+baseDate+".json";
        if(JsonUtility.getJsonFromFile(path) != null){
            return JsonUtility.getJsonFromFile(path);
        }

        String apiUrl = dataPortalUrl+"/getStockPriceInfo";
        String queryParams = "?serviceKey=" + dataPortalKey
                + "&numOfRows=10000&resultType=json"
                + "&basDt=" + baseDate;
        String json = JsonUtility.getJsonFromUrl(apiUrl + queryParams);
        return json;
    }

resources/json/stock/(year)/basedate에 json 파일이 있을 경우 파일에서 데이터를 가져오도록 수정하였다.
또한, 다른 파일에서도 데이터가 없는 경우 null을 반환하도록 하였다.

다음번에는 DB를 관리하는 관리자 페이지와 Controller를 만들어보자!

0개의 댓글