package hu.ppke.itk.itkStock.SaveDailyDatas; import hu.ppke.itk.itkStock.server.db.dbAccess.DatabaseConnector; import hu.ppke.itk.itkStock.server.db.historicData.StockData; import hu.ppke.itk.itkStock.server.db.historicData.StockDate; import hu.ppke.itk.itkStock.server.db.historicData.StockTime; import hu.ppke.itk.itkStock.server.db.historicData.Transaction; import hu.ppke.itk.itkStock.util.Pair; import java.sql.SQLException; import java.util.ArrayList; import java.util.Collections; import java.util.Date; import java.util.HashMap; import java.util.List; import java.util.Map; import java.util.SortedMap; import java.util.TreeMap; /** * Kötés manager osztály Ez felel a kötések adatbázisban rögzítésélrt és a Cache * kezeléséért is. Innen történő lekérdezés először megnézi, hogy a memóriából * oda tudja-e adni a kért adatot és csak akkor fordul az adatbázishoz, ha ez * nem lehetséges. * * @author ki-csen * */ public class StockDataManager { protected Map<String, SortedMap<StockDate, SortedMap<StockTime, Transaction>>> Cache = new HashMap<String, SortedMap<StockDate, SortedMap<StockTime, Transaction>>>(); protected Pair<Date, Date> s_interval; // / Cachelt intervallum protected StockDataSaver Sdatasaver = null; // /dbManager protected List<StockDataObserver> observers = new ArrayList<StockDataObserver>(); protected List<StockDataRecord> datalist = new ArrayList<StockDataRecord>(); // /átmeneti // tár // a // beolvasáshoz /** * StockDate+StockTime To Date * * @param date * StockDate * @param time * StockTime * @return date + time [Date] */ @SuppressWarnings("deprecation") public static Date StockDatetimeToDate(StockDate date, StockTime time) { // Depricated de nem tudok vele mit tenni. Nem én implementáltam a // használt típusokat. return new Date(date.getYear(), date.getMonth(), date.getDay(), time.getHour(), time.getMinute(), time.getSecond()); } /** * @param dbc * dbConnector ezt kívülről kapja, hogy a közöset használja. Nem * figyel a bezárásra. Idő elötti bezárása —> SQLExc * @throws SQLException */ public StockDataManager(DatabaseConnector dbc) throws SQLException { super(); Sdatasaver = new StockDataSaver(dbc); } /** * Beolvasott adatok intervallumának megállapítása, adatok rögzítése és * Cachelése Átmeneti tár törlése * * @return siker * @throws ImplementationLogicException */ synchronized public boolean comit() throws ImplementationLogicException { List<String> updatedStock = new ArrayList<String>(); Date lastdate = StockDatetimeToDate(datalist.get(0).getDate(), datalist .get(0).getTime()); Date firstdate = null; StockDataRecord prev = null; Collections.sort(datalist); for (StockDataRecord record : datalist) { if (!add(record) && !record.equals(prev)) { firstdate = StockDatetimeToDate(record.getDate(), record.getTime()); System.out.println("Braked: " + record.getPapername() + ", " + record.getTime().toString() + " :" + record.equals(prev)); break; } else { if (!updatedStock.contains(record.getPapername())) { updatedStock.add(record.getPapername()); } System.out.println("Pushed: " + record.getPapername() + ", " + record.getTime().toString()); } prev = record; } refresh_intervals(firstdate, lastdate); notifyUpdatedStock(updatedStock); this.datalist = new ArrayList<StockDataRecord>(); return true; } /** * Beolvasott kötés rögzítése az átmeneti tárban * * @param papername * @param date * @param time * @param transaction */ synchronized public void add(String papername, StockDate date, StockTime time, Transaction transaction) { datalist.add(new StockDataRecord(Sdatasaver, 0, papername, date, time, transaction)); } /** * Kőtás rögzítése az adatbázisban és a Cacheben * * @param record * Kötés * @return siker * @throws ImplementationLogicException */ protected boolean add(StockDataRecord record) throws ImplementationLogicException { try { if (isInCache(record)) { return false; } record.create(); } catch (Exception e) { e.printStackTrace(); return false; } pushToCache(record.getPapername(), record.getDate(), record.getTime(), record.getTransaction()); return true; } /** * Cachelt kötések intervallumának frissítése * * @param start * hozzáadott intervallum kezdete * @param stop * hozzáadott intervallum vége */ protected void refresh_intervals(Date start, Date stop) { if (this.s_interval == null) { this.s_interval = new Pair<Date, Date>(start, stop); } else if (this.s_interval.snd.equals(start)) { Date fstart = this.s_interval.fst; this.s_interval = new Pair<Date, Date>(fstart, stop); } else { // /Nincs implementálva az összes eset this.s_interval = new Pair<Date, Date>(start, stop); } } /** * Kötés hozzáadása a Cachehez * * @param papername * @param date * @param time * @param transaction * @return */ protected boolean pushToCache(String papername, StockDate date, StockTime time, Transaction transaction) { if (Cache.containsKey(papername)) { if (Cache.get(papername).containsKey(date)) { if (!Cache.get(papername).get(date).containsKey(time)) { Cache.get(papername).get(date).put(time, transaction); } else { Transaction prev = Cache.get(papername).get(date).get(time); Cache.get(papername).get(date) .put(time, Transaction.merge(prev, transaction)); } } else { TreeMap<StockTime, Transaction> timetree = new TreeMap<StockTime, Transaction>(); timetree.put(time, transaction); Cache.get(papername).put(date, timetree); } } else { TreeMap<StockTime, Transaction> timetree = new TreeMap<StockTime, Transaction>(); timetree.put(time, transaction); TreeMap<StockDate, SortedMap<StockTime, Transaction>> tree = new TreeMap<StockDate, SortedMap<StockTime, Transaction>>(); Cache.put(papername, tree); } return true; } /** * Benne van ez a kötés a Cacheben? * * @param papername * @param date * @param time * @param transaction * @return * @throws SQLException */ protected boolean isInCache(StockDataRecord record) throws SQLException { if (Cache.containsKey(record.getPapername())) { if (Cache.get(record.getPapername()).containsKey(record.getDate())) { if (Cache.get(record.getPapername()).get(record.getDate()) .containsKey(record.getTime())) { if (record.Existence()) { return true; } } } } return false; } /** * Árfolyamfigyelő értesítése * * @param updatedStocks * Megváltozott kötések nevei */ protected void notifyUpdatedStock(List<String> updatedStocks) { for (StockDataObserver observer : this.observers) { observer.notify(updatedStocks); } } /** * Megfigyelő hozzáadása * * @param observer */ public void addObserver(StockDataObserver observer) { this.observers.add(observer); } /** * get daily transaction data from the server about a certain stock. * * @param ticker * Name of the stock. * @param date * The date on which the transactions happened. Only the * year-month-day bit of the StockDate object is taken into * account. * @return A Map holding the transactions for which transaction->date = date * and transaction->stock = ticker */ public Map<String, SortedMap<StockDate, SortedMap<StockTime, Transaction>>> getData( String ticker, StockDate date) throws SQLException { return StockData.fetchData(ticker, date); } /** * get transaction data from the server about a certain interval, about a * certain ticker. * * @param ticker * Names of the stock. * @param from * The start date of the interval, inclusive. Only the * year-month-day bit of the StockDate object is taken into * account. * @param to * The end date of the interval, inclusive. Only the * year-month-day bit of the StockDate object is taken into * account. * @return A Map holding the transactions for which: from <= * transaction->datettime <= to and transaction->ticker = ticker. */ public Map<String, SortedMap<StockDate, SortedMap<StockTime, Transaction>>> getData( String ticker, StockDate from, StockDate to) throws SQLException { return StockData.fetchData(ticker, from, to); } /** * get daily transaction data from the server about a certain stock. * * @param tickers * Names of the stocks. * @param from * The start date of the interval, inclusive. Only the * year-month-day bit of the StockDate object is taken into * account. * @param to * The end date of the interval, inclusive. Only the * year-month-day bit of the StockDate object is taken into * account. * @return A Map holding the transactions for which transaction->date = date * and transaction->stock in tickers */ public Map<String, SortedMap<StockDate, SortedMap<StockTime, Transaction>>> getData( String[] tickers, StockDate date) throws SQLException { return StockData.fetchData(tickers, date); } /** * get transaction data from the server about a certain interval, about a * set of tickers. * * @param tickers * Names of the stocks. * @param from * The start date of the interval, inclusive. Only the * year-month-day bit of the StockDate object is taken into * account. * @param to * The end date of the interval, inclusive. Only the * year-month-day bit of the StockDate object is taken into * account. * @return A Map holding the transactions for which: from <= * transaction->datettime <= to and transaction->ticker in tickers. */ public Map<String, SortedMap<StockDate, SortedMap<StockTime, Transaction>>> getData( String[] tickers, StockDate from, StockDate to) throws SQLException { return StockData.fetchData(tickers, from, to); } /** * get all transaction data about a specific day. * * @param date * The date. Only the year-month-day bit of the StockDate object * is taken into account. * @return A Map holding the transactions for which: transaction->date = * date. */ public Map<String, SortedMap<StockDate, SortedMap<StockTime, Transaction>>> getData( StockDate date) throws SQLException { return StockData.fetchData(date); } /** * get all transaction data about a specific interval * * @param from * The start date of the interval, inclusive. Only the * year-month-day bit of the StockDate object is taken into * account. * @param to * The end date of the interval, inclusive. Only the * year-month-day bit of the StockDate object is taken into * account. * @return A Map holding the transactions for which: from <= * transaction->datettime <= to. */ public Map<String, SortedMap<StockDate, SortedMap<StockTime, Transaction>>> getData( StockDate from, StockDate to) throws SQLException { return StockData.fetchData(from, to); } }