awips2/cave/com.raytheon.viz.hydro.timeseries/src/com/raytheon/viz/hydro/timeseries/TimeSeriesDataManager.java

1589 lines
60 KiB
Java
Raw Normal View History

2022-05-05 12:34:50 -05:00
/**
* This software was developed and / or modified by Raytheon Company,
* pursuant to Contract DG133W-05-CQ-1067 with the US Government.
*
* U.S. EXPORT CONTROLLED TECHNICAL DATA
* This software product contains export-restricted data whose
* export/transfer/disclosure is restricted by U.S. law. Dissemination
* to non-U.S. persons whether in the United States or abroad requires
* an export license or other authorization.
*
* Contractor Name: Raytheon Company
* Contractor Address: 6825 Pine Street, Suite 340
* Mail Stop B8
* Omaha, NE 68106
* 402.291.0100
*
* See the AWIPS II Master Rights File ("Master Rights File.pdf") for
* further licensing information.
**/
package com.raytheon.viz.hydro.timeseries;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Calendar;
import java.util.Collections;
import java.util.Date;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;
import java.util.TimeZone;
import org.apache.commons.lang.time.DateUtils;
import com.raytheon.uf.common.dataplugin.persist.PersistableDataObject;
import com.raytheon.uf.common.dataplugin.shef.tables.Fcstheight;
import com.raytheon.uf.common.dataplugin.shef.tables.FcstheightId;
import com.raytheon.uf.common.dataplugin.shef.tables.Rejecteddata;
import com.raytheon.uf.common.dataplugin.shef.tables.RejecteddataId;
import com.raytheon.uf.common.dataquery.db.QueryResult;
import com.raytheon.uf.common.ohd.AppsDefaults;
import com.raytheon.uf.common.status.IUFStatusHandler;
import com.raytheon.uf.common.status.UFStatus;
import com.raytheon.uf.viz.core.catalog.DirectDbQuery;
import com.raytheon.uf.viz.core.catalog.DirectDbQuery.QueryLanguage;
import com.raytheon.uf.viz.core.exception.VizException;
import com.raytheon.uf.viz.core.localization.LocalizationManager;
import com.raytheon.viz.hydro.timeseries.table.DataRecord;
import com.raytheon.viz.hydro.timeseries.table.SiteInfo;
import com.raytheon.viz.hydro.timeseries.table.TabularData;
import com.raytheon.viz.hydro.timeseries.util.TimeSeriesUtil;
import com.raytheon.viz.hydrocommon.HydroConstants;
import com.raytheon.viz.hydrocommon.data.ForecastData;
import com.raytheon.viz.hydrocommon.datamanager.HydroDataManager;
import com.raytheon.viz.hydrocommon.datamanager.SqlBuilder;
import com.raytheon.viz.hydrocommon.util.HydroUtils;
/**
* Class for managing database query calls. TimeSeriesDataManager.java
*
* <pre>
* SOFTWARE HISTORY
*
* Date Ticket# Engineer Description
* ------------- ----------- ------------ --------------------------
* 03Sept2008 1509 dhladky Initial Creation.
* Oct 20, 2008 1520 mpduff Add Timeseries queries.
* Nov 04, 2009 2639 mpduff Fixed some queries, code cleanup.
* Jul 21, 2010 5964 lbousaidi Added contingencyValue table name to
* addDataRecord routine.
* Oct 25, 2010 2640 lbousaidi changed obstime to productime in
* getTabularData select query
* Apr 05, 2011 8732 jpiatt Added product_id to getGraphData
* query.
* Jun 01, 2011 9499 djingtao add dur in getGraphData()
* Jul 25, 2011 10082 djingtao modify edit()
* May 30, 2012 14967 wkwock overload insertRejectedData method
* Feb 22, 2013 14676 lbousaidi check when producttime is null
* Mar 25, 2013 1781 mpduff Constrain time series table query with
* a start time.
* May 12, 2014 16705 lbousaidi update revision and shef_qual_code in
* edit routine.
* Dec 14, 2014 16388 xwei updated the insertion of rejecteddata
* table.
* Jul 21, 2015 4500 rjpeter Use Number in blind cast.
* Aug 05, 2015 4486 rjpeter Changed Timestamp to Date.
* Aug 18, 2015 4793 rjpeter Use Number in blind cast.
* Nov 06, 2015 17846 lbousaidi modify edit and insertRejectedData so
* that quality_code. is reset from Bad
* to Good after data QC.
* Feb 16, 2016 5342 bkowal Ensure two rejected records with the
* same key values are not inserted at
* the same second.
* Mar 08, 2017 17643 jdeng Fix errors when deleting/setting data
* to missing
* Apr 12, 2018 6619 randerso Code cleanup.
* Jun 27, 2018 6748 randerso Use UFStatus instead of slf4j Logger
* in CAVE. Fixed query in getDataFromDB
* to correctly format dates in GMT
* regardless of local time zone setting.
* Sep 21, 2018 7379 mduff Moved for PDC Refactor.
*
* </pre>
*
* @author dhladky
*/
public class TimeSeriesDataManager extends HydroDataManager {
private final IUFStatusHandler statusHandler = UFStatus
.getHandler(getClass());
private static final String TIME_SERIES_DATA_QUERY = "select lid,obstime,lid,product_id from latestobsvalue";
private static final String INGEST_FILTER_QUERY = "select lid,pe,ts,extremum,dur from ingestfilter where lid=':lid' and ingest = 'T' order by pe asc,ts_rank asc,ts asc,dur asc,extremum asc";
private static final String SHEF_PE_QUERY = "select name||' '|| eng_unit from shefpe where pe=':pe'";
private static final String SHEF_PE_GENERIC_UNITS = "Generic Units";
/** Quality control value for manual "Good" */
private static final int QC_MANUAL_PASSED = 121;
private static SimpleDateFormat dateFormat;
static {
dateFormat = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
dateFormat.setTimeZone(TimeZone.getTimeZone("GMT"));
}
private static TimeSeriesDataManager manager = null;
private Map<String, String> stationData;
private boolean sortChanged = false;
/**
* Map holding the location id and display class.
*/
private Map<String, String> stnDisplayMap = null;
/**
* private constructor
*/
private TimeSeriesDataManager() {
}
/**
* Get an instance of this singleton object
*
* @return instance of this class
*/
public static synchronized TimeSeriesDataManager getInstance() {
if (manager == null) {
manager = new TimeSeriesDataManager();
}
return manager;
}
/**
* Get TimeSeriesData from the DB
*
* @return Object[]
*/
public Object[] getTimeSeriesData() {
List<Object[]> data;
try {
data = DirectDbQuery.executeQuery(TIME_SERIES_DATA_QUERY,
HydroConstants.IHFS, QueryLanguage.SQL);
if (data != null) {
return data.get(0);
}
} catch (VizException e) {
statusHandler.error("Error retrieving time series data", e);
}
return null;
}
/**
* Get TimeSeriesStationData from the DB
*
* @return map
*/
public Map<String, String> getTimeSeriesStationData() {
return getTimeSeriesStationData(false);
}
/**
* Get the station list data sorted by lid.
*
* @param sortByName
* boolean
* @return map
*/
public Map<String, String> getTimeSeriesStationData(boolean sortByName) {
boolean stnDisplayMapSet = true;
StringBuilder sql = new StringBuilder("Select ");
sql.append("distinct location.lid, ingestfilter.pe, ");
sql.append("upper(location.name) as uppername, stnclass.disp_Class ");
sql.append("from ingestfilter, location, stnclass ");
sql.append("where ingest='T' and location.lid = stnclass.lid ");
sql.append("and location.lid=ingestfilter.lid ");
if (sortByName) {
sql.append("order by uppername asc");
} else {
sql.append("order by lid asc");
}
// if the sort changed then requery for the data
if (sortChanged != sortByName) {
sortChanged = true;
}
if (stnDisplayMap == null) {
stnDisplayMap = new HashMap<>();
stnDisplayMapSet = false;
}
if (stationData == null || sortChanged) {
stationData = new LinkedHashMap<>();
List<Object[]> data;
try {
data = DirectDbQuery.executeQuery(sql.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
for (Object[] rowData : data) {
if (rowData[2] == null) {
rowData[2] = "";
}
stationData.put((String) rowData[0], (String) rowData[2]);
if (!stnDisplayMapSet) {
stnDisplayMap.put((String) rowData[0],
(String) rowData[3]);
}
}
} catch (VizException e) {
statusHandler.error("Error retrieving station data", e);
}
}
return stationData;
}
/**
* Get the site's PE data for graphical display
*
* @param lid
* The lid to query for
* @return ArrayList of Object[] of data
* @throws VizException
*/
public List<Object[]> getSitePEData(String lid) throws VizException {
return DirectDbQuery.executeQuery(
INGEST_FILTER_QUERY.replace(":lid", lid), HydroConstants.IHFS,
QueryLanguage.SQL);
}
/**
* Get the site's PE data for tabular display
*
* @param lid
* The lid to query for
* @return List of SiteInfo objects
* @throws VizException
*/
public List<SiteInfo> getTabularPEData(String lid) throws VizException {
StringBuilder sql = new StringBuilder("select ");
sql.append("lid, pe, dur, ts, extremum from Ingestfilter ");
sql.append("where lid = '").append(lid).append("' and ingest = 'T' ");
sql.append("order by pe, dur, ts, extremum asc");
List<Object[]> results = DirectDbQuery.executeQuery(sql.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
List<SiteInfo> returnData = new ArrayList<>();
for (int i = 0; i < results.size(); i++) {
Object[] oa = results.get(i);
SiteInfo si = new SiteInfo();
si.setLid((String) oa[0]);
si.setPe((String) oa[1]);
si.setDur(((Number) oa[2]).intValue());
si.setTs((String) oa[3]);
si.setExt((String) oa[4]);
returnData.add(si);
}
return returnData;
}
/**
* Checks the record count in the Location and Stnclass tables.
*
* @return true if same count, otherwise false
* @throws VizException
*/
public boolean checkLidCount() throws VizException {
/* Set up a location query */
String locationTable = "locview";
String stnClassTable = "stnclass";
StringBuilder errMessage = null;
errMessage = new StringBuilder(
"Error querying the Location table, no data returned");
/* Execute the location query */
long locationCount = recordCount(locationTable, "");
if (locationCount <= 0) {
throw new VizException(errMessage.toString());
}
errMessage.setLength(0);
errMessage.setLength(0);
errMessage
.append("Error querying the Stnclass table, no data returned");
/* Execute the Stnclass query */
long stnClassCount = recordCount(stnClassTable, "");
if (stnClassCount <= 0) {
throw new VizException(errMessage.toString());
}
if (stnClassCount == locationCount) {
return true;
}
return false;
}
/**
* Get the shef pe data from IHFS.
*
* @param pe
* The PE value
* @return The units of the data
* @throws VizException
*/
public String getShefPE(String pe) throws VizException {
List<Object[]> data = DirectDbQuery.executeQuery(
SHEF_PE_QUERY.replace(":pe", pe), HydroConstants.IHFS,
QueryLanguage.SQL);
if (data != null && !data.isEmpty()) {
Object[] sa = data.get(0);
return (String) sa[0];
}
return SHEF_PE_GENERIC_UNITS;
}
/**
* Query the table.
*
* @param tablename
* The table to query
* @param lid
* The location id
* @param pe
* The physical element
* @param ts
* The type source
* @param dur
* The duration
* @param extremum
* The extremum
* @param startTime
* The start time
* @param endTime
* The end time
* @return The List of Object[] data
* @throws VizException
* @throws ClassNotFoundException
*/
public List<Object[]> getGraphData(String tablename, String lid, String pe,
String ts, int dur, String extremum, Date startTime, Date endTime)
throws VizException {
StringBuilder graphQuery = new StringBuilder(
"select lid,obstime,value,product_id from ");
graphQuery.append(tablename + " where lid = '" + lid + "' and pe = '"
+ pe + "' " + "and dur = '" + dur + "' ");
graphQuery.append("and ts = '" + ts + "' and extremum = '"
+ extremum.toUpperCase() + "' and obstime ");
graphQuery.append("between '"
+ HydroConstants.DATE_FORMAT.format(startTime) + "' ");
graphQuery.append(
"and '" + HydroConstants.DATE_FORMAT.format(endTime) + "' ");
graphQuery.append("order by obstime asc");
return DirectDbQuery.executeQuery(graphQuery.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
}
/**
* Query the Riverstat table for the flood/action stage/flow.
*
* @param lid
* The Location Id
* @return The list of flood stage values
* @throws VizException
*/
public List<Object[]> getFloodStage(String lid) throws VizException {
/* Query the floodCat table for the flood stage data */
String floodQuerySql = "select lid,fs,fq,wstg,action_Flow from riverstat where lid = '"
+ lid + "'";
return DirectDbQuery.executeQuery(floodQuerySql, HydroConstants.IHFS,
QueryLanguage.SQL);
}
/**
* Query the floodcat table for the flood stage.
*
* @param lid
* The Location Id
* @return The flood stage value as a String
* @throws VizException
*/
public List<Object[]> getFloodCategories(String lid) throws VizException {
String floodQuerySql = "select " + HydroConstants.LID + ","
+ HydroConstants.MINOR_STAGE + ","
+ HydroConstants.MODERATE_STAGE + ","
+ HydroConstants.MAJOR_STAGE + "," + HydroConstants.MINOR_FLOW
+ "," + HydroConstants.MODERATE_FLOW + ","
+ HydroConstants.MAJOR_FLOW + " from floodcat where lid = '"
+ lid + "'";
return DirectDbQuery.executeQuery(floodQuerySql, HydroConstants.IHFS,
QueryLanguage.SQL);
}
/**
* Get the Station name and river name.
*
* @param lid
* Location Id of the station
* @return List of Object[] containing the data
* @throws VizException
*/
public String[] getStnRiverName(String lid) throws VizException {
StringBuilder sql = new StringBuilder("select ");
sql.append("name ");
sql.append("from location ");
sql.append(" where lid = '" + lid + "'");
List<Object[]> result1 = DirectDbQuery.executeQuery(sql.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
sql.setLength(0);
sql.append("select stream from riverstat where lid = '" + lid + "'");
List<Object[]> result2 = DirectDbQuery.executeQuery(sql.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
List<String> sa = new ArrayList<>();
if (result1 != null && !result1.isEmpty()) {
sa.add((String) result1.get(0)[0]);
} else {
sa.add(HydroConstants.UNDEFINED);
}
if (result2 != null && !result2.isEmpty()) {
sa.add((String) result2.get(0)[0]);
} else {
sa.add(HydroConstants.UNDEFINED);
}
return sa.toArray(new String[sa.size()]);
}
/**
* Gets a unique list of basis times.
*
* @param table
* The table to query
* @param lid
* The lid to query on
* @param pe
* The pe to query on
* @param dur
* The duration to query on
* @param ts
* The type source to query on
* @param ext
* The extremum to query on
* @param begin
* The beginning time
* @param end
* The ending time
* @return List of Object arrays
* @throws VizException
* @throws ClassNotFoundException
*/
public List<Object[]> getUniqueList(String table, String lid, String pe,
int dur, String ts, String ext, Date begin, Date end)
throws VizException, ClassNotFoundException {
StringBuilder sql = new StringBuilder("select ");
sql.append("distinct(basistime) from " + table + " ");
sql.append("where lid = '" + lid + "' and ts = '" + ts + "' and ");
sql.append("dur = '" + dur + "' and extremum = '" + ext + "' and ");
sql.append("validtime > '" + dateFormat.format(begin) + "' and ");
sql.append("validtime < '" + dateFormat.format(end) + "' ");
sql.append("order by basistime desc");
return DirectDbQuery.executeQuery(sql.toString(), HydroConstants.IHFS,
QueryLanguage.SQL);
}
/**
* Query for the data records
*
* @param tablename
* The table to query
* @param lid
* The lid to query on
* @param pe
* The pe to query on
* @param ts
* The type source to query on
* @param dur
* The duration to query on
* @param ext
* The extremum to query on
* @param startTime
* The start time of the data
* @param endTime
* The end time of the data
* @param basisTime
* The forecast basis time, null if not forecast data
* @param forecastData
* true if forecast data
* @return ArrayList of TabularData
* @throws VizException
*/
public List<TabularData> getTabularData(String tablename, String lid,
String pe, String ts, String dur, String ext, Date startTime,
Date endTime, String basisTime, boolean forecastData)
throws VizException {
StringBuilder sql = new StringBuilder("select ");
if (forecastData) {
sql.append("lid, validtime, value, revision, shef_qual_code, ");
sql.append("quality_code, product_id, producttime, postingtime, ");
sql.append("basistime, probability ");
sql.append("from ").append(tablename);
sql.append(" where lid = '").append(lid).append("'");
sql.append(" and pe = '").append(pe).append("'");
sql.append(" and ts = '").append(ts).append("'");
sql.append(" and dur = ").append(dur);
sql.append(" and extremum = '").append(ext).append("'");
sql.append(" and validtime > '")
.append(dateFormat.format(startTime)).append("'");
sql.append(" and validtime < '").append(dateFormat.format(endTime))
.append("'");
sql.append(" and basistime = '").append(basisTime).append("'");
sql.append(" order by validtime desc");
} else {
sql.append("lid, obstime, value, revision, shef_qual_code, ");
sql.append("quality_code, product_id, producttime, postingtime ");
sql.append("from ").append(tablename);
sql.append(" where lid = '").append(lid).append("'");
sql.append(" and pe = '").append(pe).append("'");
sql.append(" and ts = '").append(ts).append("'");
sql.append(" and dur = ").append(dur);
sql.append(" and extremum = '").append(ext).append("'");
sql.append(" and obstime > '").append(dateFormat.format(startTime))
.append("'");
sql.append(" and obstime < '").append(dateFormat.format(endTime))
.append("'");
sql.append(" order by obstime desc");
}
AppsDefaults ad = AppsDefaults.getInstance();
boolean debug = ad.getBoolean(HydroConstants.DEBUG_HYDRO_DB_TOKEN,
false);
if (debug) {
/*
* Since debug is set by Apps Defaults and not via logger
* configuration, these message will be logged as info messages to
* ensure that they are output even if debug messages have been
* disabled at the logger level.
*/
statusHandler.info(ad.getToken(HydroConstants.PGHOST) + ":"
+ ad.getToken(HydroConstants.PGPORT) + ":"
+ ad.getToken(HydroConstants.DB_NAME));
statusHandler.info("Query: " + sql.toString());
}
List<TabularData> tabularData = new ArrayList<>();
List<Object[]> results = DirectDbQuery.executeQuery(sql.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
for (int i = 0; i < results.size(); i++) {
Object[] oa = results.get(i);
TabularData td = new TabularData();
td.setLid((String) oa[0]);
td.setObsTime((Date) oa[1]);
td.setValue((Double) oa[2]);
td.setRevision(((Number) oa[3]).intValue());
td.setShefQualCode((String) oa[4]);
td.setQualityCode(((Number) oa[5]).intValue());
td.setProductId((String) oa[6]);
td.setProductTime((Date) oa[7]);
td.setPostingTime((Date) oa[8]);
if (forecastData) {
td.setValidTime((Date) oa[9]);
td.setProbability(((Number) oa[10]).floatValue());
}
tabularData.add(td);
}
return tabularData;
}
/**
* Get the record count of the table.
*
* @param table
* The table to query
* @param where
* The where statement
* @return Number of rows in the table, or -1 if error
* @throws VizException
*/
public long recordCount(String table, String where) throws VizException {
if (table == null || table.isEmpty()) {
return -1;
}
String sql = "select count(*) from " + table + where;
AppsDefaults ad = AppsDefaults.getInstance();
boolean debug = ad.getBoolean(HydroConstants.DEBUG_HYDRO_DB_TOKEN,
false);
if (debug) {
statusHandler.info(ad.getToken(HydroConstants.PGHOST) + ":"
+ ad.getToken(HydroConstants.PGPORT) + ":"
+ ad.getToken(HydroConstants.DB_NAME));
statusHandler.info("Query: " + sql);
}
List<Object[]> results = DirectDbQuery.executeQuery(sql,
HydroConstants.IHFS, QueryLanguage.SQL);
if (results == null || results.get(0) == null) {
return -1;
}
return ((Number) results.get(0)[0]).longValue();
}
/**
* Delete the record.
*
* @param tablename
* The tablename to query
* @param where
* The where statement
* @throws VizException
*/
public void deleteRecord(String tablename, String where)
throws VizException {
String sql = "delete from " + tablename + " " + where;
AppsDefaults ad = AppsDefaults.getInstance();
boolean debug = ad.getBoolean(HydroConstants.DEBUG_HYDRO_DB_TOKEN,
false);
if (debug) {
statusHandler.info(ad.getToken(HydroConstants.PGHOST) + ":"
+ ad.getToken(HydroConstants.PGPORT) + ":"
+ ad.getToken(HydroConstants.DB_NAME));
statusHandler.info("Query: " + sql);
}
DirectDbQuery.executeStatement(sql, HydroConstants.IHFS,
QueryLanguage.SQL);
}
/**
* Delete a list of items.
*
* @param queryList
* list of queries
* @throws VizException
*/
public void deleteRecords(List<String> queryList) throws VizException {
StringBuilder sb = new StringBuilder();
for (String query : queryList) {
sb.append(query);
}
DirectDbQuery.executeStatement(sb.toString(), HydroConstants.IHFS,
QueryLanguage.SQL);
}
/**
* Add a data record.
*
* @param tablename
* The tablename to query
* @param dr
* The data record to add
* @return int
* @throws VizException
*/
public int addDataRecord(String tablename, DataRecord dr)
throws VizException {
StringBuilder sb = new StringBuilder();
Date now = Calendar.getInstance(TimeZone.getTimeZone("GMT")).getTime();
if (tablename.startsWith("Fcst") || tablename.startsWith("fcst")
|| tablename.startsWith("Contingency")) {
sb.append("insert into " + tablename
+ "(lid, pe, dur, ts, extremum, ");
sb.append(
"probability, validtime, basistime, value, quality_code, ");
sb.append(
"shef_qual_code, revision, product_id, producttime, postingtime) ");
sb.append("values ('" + dr.getLid() + "', '"
+ dr.getPe().toUpperCase() + "', ");
sb.append(dr.getDur() + ", '" + dr.getTs().toUpperCase() + "', '");
sb.append(dr.getExt().toUpperCase() + "', -1, ");
sb.append("'" + dateFormat.format(dr.getObsTime()) + "', '");
sb.append(dr.getBasisTime() + "', " + dr.getValue() + ", ");
sb.append(
dr.getQualityCode() + ", '" + dr.getShefQualCode() + "', ");
sb.append(dr.getRevision() + ", '" + dr.getProductId() + "', ");
sb.append("'" + dateFormat.format(dr.getProductTime()) + "', '");
sb.append(dateFormat.format(now) + "')");
} else {
sb.append("insert into " + tablename
+ "(lid, pe, dur, ts, extremum, ");
sb.append(
"obstime, postingtime, value, quality_code, shef_qual_code, productTime, ");
sb.append("revision, product_Id) ");
sb.append("values ('" + dr.getLid() + "', '"
+ dr.getPe().toUpperCase() + "', ");
sb.append(dr.getDur() + ", '" + dr.getTs().toUpperCase() + "', '");
sb.append(dr.getExt().toUpperCase() + "', ");
sb.append("'" + dateFormat.format(dr.getObsTime()) + "', '");
sb.append(dateFormat.format(now) + "', ");
sb.append(dr.getValue() + ", ");
sb.append(dr.getQualityCode() + ", '");
sb.append(dr.getShefQualCode() + "', '");
sb.append(dr.getProductTime() + "', ");
sb.append("0, '" + dr.getProductId() + "')");
}
AppsDefaults ad = AppsDefaults.getInstance();
boolean debug = ad.getBoolean(HydroConstants.DEBUG_HYDRO_DB_TOKEN,
false);
if (debug) {
statusHandler.info(ad.getToken(HydroConstants.PGHOST) + ":"
+ ad.getToken(HydroConstants.PGPORT) + ":"
+ ad.getToken(HydroConstants.DB_NAME));
statusHandler.info("Query: " + sb.toString());
}
return DirectDbQuery.executeStatement(sb.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
}
/**
* Update sql.
*
* @param sql
* The sql string
* @return int
* @throws VizException
*/
public int update(String sql) throws VizException {
AppsDefaults ad = AppsDefaults.getInstance();
boolean debug = ad.getBoolean(HydroConstants.DEBUG_HYDRO_DB_TOKEN,
false);
if (debug) {
statusHandler.info(ad.getToken(HydroConstants.PGHOST) + ":"
+ ad.getToken(HydroConstants.PGPORT) + ":"
+ ad.getToken(HydroConstants.DB_NAME));
statusHandler.info("Query: " + sql);
}
return DirectDbQuery.executeStatement(sql, HydroConstants.IHFS,
QueryLanguage.SQL);
}
/**
* Insert rejected data record.
*
* @param dr
* The data record
* @return int
* @throws VizException
*/
public int insertRejectedData(DataRecord dr) throws VizException {
Rejecteddata rd = new Rejecteddata();
RejecteddataId rdid = new RejecteddataId();
Date d = Calendar.getInstance(TimeZone.getTimeZone("GMT")).getTime();
/* set basistime to obstime for observed data */
if (dr.getBasisTime() != null) {
try {
rdid.setBasistime(
HydroConstants.DATE_FORMAT.parse(dr.getBasisTime()));
} catch (ParseException e) {
rdid.setBasistime(dr.getObsTime());
}
} else {
rdid.setBasistime(dr.getObsTime());
}
rdid.setDur((short) dr.getDur());
rdid.setExtremum(dr.getExt());
rdid.setLid(dr.getLid());
rdid.setPe(dr.getPe());
/* set postingtime to current time */
rdid.setPostingtime(d);
rdid.setProbability(-1);
rdid.setTs(dr.getTs());
rdid.setValidtime(dr.getValidTime());
rd.setId(rdid);
rd.setProductId(dr.getProductId());
rd.setProducttime(dr.getProductTime());
rd.setQualityCode((int) dr.getQualityCode());
/* set reject_type to M for Manual */
rd.setRejectType("M");
rd.setRevision((short) dr.getRevision());
rd.setShefQualCode(dr.getShefQualCode());
rd.setUserid(LocalizationManager.getInstance().getCurrentUser());
rd.setValue(dr.getValue());
/* set validtime for observed data */
if (rdid.getValidtime() == null) {
rdid.setValidtime(dr.getObsTime());
}
return DirectDbQuery.saveOrUpdate(rd, HydroConstants.IHFS);
}
/**
* Insert a list of items into the rejected table
*
* @param recordList
* List of DataRecord objects
* @param origVal
* @return number of rows inserted
* @throws VizException
*/
public int insertRejectedData(List<DataRecord> recordList, double origVal)
throws VizException {
StringBuilder sb = new StringBuilder();
Date d = Calendar.getInstance(TimeZone.getTimeZone("GMT")).getTime();
for (DataRecord dr : recordList) {
sb.append("insert into rejecteddata(lid, pe, dur, ts, extremum, ");
sb.append(
"probability, validtime, basistime, postingtime, value, ");
sb.append(
"revision, shef_qual_code, product_id, producttime, quality_code, ");
sb.append("reject_type, userid) VALUES(");
sb.append("'" + dr.getLid() + "', ");
sb.append("'" + dr.getPe() + "', ");
sb.append(dr.getDur() + ", ");
sb.append("'" + dr.getTs() + "', ");
sb.append("'" + dr.getExt() + "', ");
sb.append(-1 + ", ");
/* set validtime for observed data */
if (dr.getValidTime() != null) {
sb.append("'"
+ HydroConstants.DATE_FORMAT.format(dr.getValidTime())
+ "', ");
} else {
sb.append(
"'" + HydroConstants.DATE_FORMAT.format(dr.getObsTime())
+ "', ");
}
if (dr.getBasisTime() != null) {
try {
sb.append("'" + HydroConstants.DATE_FORMAT
.parse(dr.getBasisTime()) + "', ");
} catch (ParseException e) {
sb.append("'"
+ HydroConstants.DATE_FORMAT.format(dr.getObsTime())
+ "', ");
}
} else {
sb.append(
"'" + HydroConstants.DATE_FORMAT.format(dr.getObsTime())
+ "', ");
}
sb.append("'" + HydroConstants.DATE_FORMAT.format(d) + "', ");
sb.append(origVal + ", ");
sb.append(dr.getRevision() + ", ");
sb.append("'" + dr.getShefQualCode() + "', ");
sb.append("'" + dr.getProductId() + "', ");
sb.append(
"'" + HydroConstants.DATE_FORMAT.format(dr.getProductTime())
+ "', ");
sb.append(dr.getQualityCode() + ", ");
sb.append("'M', ");
sb.append("'" + LocalizationManager.getInstance().getCurrentUser()
+ "');");
}
AppsDefaults ad = AppsDefaults.getInstance();
boolean debug = ad.getBoolean(HydroConstants.DEBUG_HYDRO_DB_TOKEN,
false);
if (debug) {
statusHandler.info(ad.getToken(HydroConstants.PGHOST) + ":"
+ ad.getToken(HydroConstants.PGPORT) + ":"
+ ad.getToken(HydroConstants.DB_NAME));
statusHandler.info("Query: " + sb.toString());
}
return DirectDbQuery.executeStatement(sb.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
}
private Object getDataFromDB(ForecastData dr, String field) {
StringBuilder sql = new StringBuilder("select " + field + " from ");
String tablename = HydroUtils.getTableName(dr.getPe(), dr.getTs());
sql.append(tablename + " where ");
sql.append("lid = '" + dr.getLid() + "' ");
sql.append("and pe = '" + dr.getPe().toUpperCase() + "' ");
sql.append("and dur =" + dr.getDur() + " ");
sql.append("and ts = '" + dr.getTs().toUpperCase() + "' ");
sql.append("and extremum = '" + dr.getExtremum().toUpperCase() + "' ");
if (dr.getTs().toUpperCase().startsWith("F")
|| dr.getTs().toUpperCase().startsWith("C")) {
sql.append("and validtime = '"
+ HydroConstants.DATE_FORMAT.format(dr.getValidTime())
+ "' ");
sql.append("and basistime = '"
+ HydroConstants.DATE_FORMAT.format(dr.getBasisTime())
+ "';");
} else {
// obs data
sql.append("and obstime = '"
+ HydroConstants.DATE_FORMAT.format(dr.getObsTime())
+ "';");
}
List<Object[]> sqlResult;
try {
sqlResult = DirectDbQuery.executeQuery(sql.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
if (sqlResult != null && !sqlResult.isEmpty()
&& sqlResult.get(0)[0] != null) {
return sqlResult.get(0)[0];
}
} catch (VizException e) {
statusHandler.error(
"Failed to retrieve data from table: " + tablename + ".",
e);
}
return null;
}
/**
* @param editList
* @param rejectedSecondsMap
* @param insertStartTime
* @return number of rows inserted
* @throws VizException
*/
public int insertSetMRejectedData(List<ForecastData> editList,
Map<RejecteddataId, Integer> rejectedSecondsMap,
Date insertStartTime) throws VizException {
StringBuilder sb = new StringBuilder();
/*
* part of the primary key. So, should be unique with each record
* insert.
*/
for (ForecastData dr : editList) {
/*
* This will ensure that records that would normally have the same
* id will at least be offset by a second. This is needed because
* the dynamic time field that is part of the primary key only has a
* resolution out to the seconds field. The insert of a record does
* not take an entire second. This implementation is limited by the
* fact that only sixty of a particular record can be inserted
* without conflicting with a potential future insert less than a
* minute later. The inserts are mapped by id to reduce the amount
* of data manipulation that would occur when there is a lack of
* duplicate records. The ideal scenario would be to alter the data
* record so that it would not be necessary to offset the posting
* time by a second to ensure uniqueness; however, a changeset that
* large is far outside the scope of DR #5342.
*/
RejecteddataId id = new RejecteddataId();
id.setLid(dr.getLid());
id.setPe(dr.getPe());
id.setDur((short) dr.getDur());
id.setTs(dr.getTs());
id.setExtremum(dr.getExtremum());
id.setProbability((float) dr.getProbability());
id.setValidtime(dr.getValidTime());
id.setBasistime(dr.getBasisTime());
id.setPostingtime(insertStartTime);
Integer offsetSeconds = rejectedSecondsMap.get(id);
if (offsetSeconds == null) {
offsetSeconds = 0;
} else {
offsetSeconds += 1;
}
rejectedSecondsMap.put(id, offsetSeconds);
final Date postingTime = DateUtils.addSeconds(insertStartTime,
offsetSeconds);
int probability = -1;
int revision = 1;
if (dr.getTs().toUpperCase().startsWith("F")
|| dr.getTs().toUpperCase().startsWith("C")) {
probability = 0;
}
Date productTime = dr.getProductTime();
if (productTime == null) {
productTime = (Date) getDataFromDB(dr, "producttime");
}
String productID = (String) getDataFromDB(dr, "product_id");
if (productID == null) {
productID = dr.getProductID();
}
dr.setQualityCode(TimeSeriesUtil.setQcCode(QC_MANUAL_PASSED,
dr.getQualityCode()));
sb.append("insert into rejecteddata(lid, pe, dur, ts, extremum, ");
sb.append(
"probability, validtime, basistime, postingtime, value, ");
sb.append(
"revision, shef_qual_code, product_id, producttime, quality_code, ");
sb.append("reject_type, userid) VALUES(");
sb.append("'" + dr.getLid() + "', ");
sb.append("'" + dr.getPe().toUpperCase() + "', ");
sb.append(dr.getDur() + ", ");
sb.append("'" + dr.getTs().toUpperCase() + "', ");
sb.append("'" + dr.getExtremum().toUpperCase() + "', ");
sb.append(probability + ", ");
/* set validtime for observed data */
if (dr.getValidTime() != null) {
sb.append("'"
+ HydroConstants.DATE_FORMAT.format(dr.getValidTime())
+ "', ");
} else {
sb.append(
"'" + HydroConstants.DATE_FORMAT.format(dr.getObsTime())
+ "', ");
}
if (dr.getBasisTime() != null) {
sb.append("'" + dr.getBasisTime() + "', ");
} else {
sb.append(
"'" + HydroConstants.DATE_FORMAT.format(dr.getObsTime())
+ "', ");
}
sb.append("'" + HydroConstants.DATE_FORMAT.format(postingTime)
+ "', ");
sb.append(dr.getPreviousValue() + ", ");
sb.append(revision + ", ");
// shef_qual_code always M
sb.append("'M', ");
sb.append("'" + productID + "', ");
sb.append("'" + HydroConstants.DATE_FORMAT.format(productTime)
+ "', ");
sb.append(dr.getQualityCode() + ", ");
sb.append("'M', ");
sb.append("'" + LocalizationManager.getInstance().getCurrentUser()
+ "');");
}
AppsDefaults ad = AppsDefaults.getInstance();
boolean debug = ad.getBoolean(HydroConstants.DEBUG_HYDRO_DB_TOKEN,
false);
if (debug) {
statusHandler.info(ad.getToken(HydroConstants.PGHOST) + ":"
+ ad.getToken(HydroConstants.PGPORT) + ":"
+ ad.getToken(HydroConstants.DB_NAME));
statusHandler.info("Query: " + sb.toString());
}
return DirectDbQuery.executeStatement(sb.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
}
/**
* @param deleteList
* @param rejectedSecondsMap
* @param insertStartTime
* @return number of rows inserted
* @throws VizException
*/
public int insertDelRejectedData(List<ForecastData> deleteList,
Map<RejecteddataId, Integer> rejectedSecondsMap,
Date insertStartTime) throws VizException {
StringBuilder sb = new StringBuilder();
/*
* part of the primary key. So, should be unique with each record
* insert.
*/
for (ForecastData dr : deleteList) {
/*
* This will ensure that records that would normally have the same
* id will at least be offset by a second. This is needed because
* the dynamic time field that is part of the primary key only has a
* resolution out to the seconds field. The insert of a record does
* not take an entire second. This implementation is limited by the
* fact that only sixty of a particular record can be inserted
* without conflicting with a potential future insert less than a
* minute later. The inserts are mapped by id to reduce the amount
* of data manipulation that would occur when there is a lack of
* duplicate records. The ideal scenario would be to alter the data
* record so that it would not be necessary to offset the posting
* time by a second to ensure uniqueness; however, a changeset that
* large is far outside the scope of DR #5342.
*/
RejecteddataId id = new RejecteddataId();
id.setLid(dr.getLid());
id.setPe(dr.getPe());
id.setDur((short) dr.getDur());
id.setTs(dr.getTs());
id.setExtremum(dr.getExtremum());
id.setProbability((float) dr.getProbability());
id.setValidtime(dr.getValidTime());
id.setBasistime(dr.getBasisTime());
id.setPostingtime(insertStartTime);
Integer offsetSeconds = rejectedSecondsMap.get(id);
if (offsetSeconds == null) {
offsetSeconds = 0;
} else {
offsetSeconds += 1;
}
rejectedSecondsMap.put(id, offsetSeconds);
final Date postingTime = DateUtils.addSeconds(insertStartTime,
offsetSeconds);
int probability = -1;
if (dr.getTs().toUpperCase().startsWith("F")
|| dr.getTs().toUpperCase().startsWith("C")) {
probability = 0;
}
Date productTime = dr.getProductTime();
if (productTime == null) {
productTime = (Date) getDataFromDB(dr, "producttime");
}
String productID = (String) getDataFromDB(dr, "product_id");
if (productID == null) {
productID = dr.getProductID();
}
Integer qualityCode = ((Number) getDataFromDB(dr, "quality_code"))
.intValue();
String shefQualCode = (String) getDataFromDB(dr, "shef_qual_code");
sb.append("insert into rejecteddata(lid, pe, dur, ts, extremum, ");
sb.append(
"probability, validtime, basistime, postingtime, value, ");
sb.append(
"revision, shef_qual_code, product_id, producttime, quality_code, ");
sb.append("reject_type, userid) VALUES(");
sb.append("'").append(dr.getLid()).append("', ");
sb.append("'").append(dr.getPe().toUpperCase()).append("', ");
sb.append(dr.getDur()).append(", ");
sb.append("'").append(dr.getTs().toUpperCase()).append("', ");
sb.append("'").append(dr.getExtremum().toUpperCase()).append("', ");
sb.append(probability).append(", ");
/* set validtime for observed data */
if (dr.getValidTime() != null) {
sb.append("'").append(
HydroConstants.DATE_FORMAT.format(dr.getValidTime()))
.append("', ");
} else {
sb.append("'").append(
HydroConstants.DATE_FORMAT.format(dr.getObsTime()))
.append("', ");
}
if (dr.getBasisTime() != null) {
sb.append("'").append(dr.getBasisTime()).append("', ");
} else {
sb.append("'").append(
HydroConstants.DATE_FORMAT.format(dr.getObsTime()))
.append("', ");
}
sb.append("'")
.append(HydroConstants.DATE_FORMAT.format(postingTime))
.append("', ");
sb.append(dr.getPreviousValue()).append(", ");
sb.append(dr.getRevision()).append(", ");
sb.append("'").append(shefQualCode).append("', ");
sb.append("'").append(productID).append("', ");
sb.append("'")
.append(HydroConstants.DATE_FORMAT.format(productTime))
.append("', ");
sb.append(qualityCode).append(", ");
sb.append("'M', ");
sb.append("'")
.append(LocalizationManager.getInstance().getCurrentUser())
.append("');");
}
AppsDefaults ad = AppsDefaults.getInstance();
boolean debug = ad.getBoolean(HydroConstants.DEBUG_HYDRO_DB_TOKEN,
false);
if (debug) {
statusHandler.info(ad.getToken(HydroConstants.PGHOST) + ":"
+ ad.getToken(HydroConstants.PGPORT) + ":"
+ ad.getToken(HydroConstants.DB_NAME));
statusHandler.info("Query: " + sb.toString());
}
return DirectDbQuery.executeStatement(sb.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
}
/**
* Deletes a list of Observations.
*
* @param deleteList
* List of Observations to delete.
* @return The number of rows modified
* @throws VizException
*/
public int delete(List<ForecastData> deleteList) throws VizException {
int status = -1;
for (int i = 0; i < deleteList.size(); i++) {
ForecastData data = deleteList.get(i);
String tablename = HydroUtils.getTableName(data.getPe(),
data.getTs());
StringBuilder sql = new StringBuilder("delete from ");
sql.append(tablename + " where ");
sql.append("lid = '" + data.getLid() + "' ");
sql.append("and pe = '" + data.getPe().toUpperCase() + "' ");
sql.append("and dur = " + data.getDur() + " ");
sql.append("and ts = '" + data.getTs().toUpperCase() + "' ");
sql.append("and extremum = '" + data.getExtremum().toUpperCase()
+ "' ");
if (data.getValidTime() != null) {
sql.append("and validtime = '"
+ dbFormat.format(data.getValidTime()) + "'");
} else {
sql.append("and obstime = '"
+ dbFormat.format(data.getObsTime()) + "'");
}
AppsDefaults ad = AppsDefaults.getInstance();
boolean debug = ad.getBoolean(HydroConstants.DEBUG_HYDRO_DB_TOKEN,
false);
if (debug) {
statusHandler.info(ad.getToken(HydroConstants.PGHOST) + ":"
+ ad.getToken(HydroConstants.PGPORT) + ":"
+ ad.getToken(HydroConstants.DB_NAME));
statusHandler.info("Query: " + sql);
}
status = DirectDbQuery.executeStatement(sql.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
}
return status;
}
/**
* Inserts a list of Observations.
*
* @param insertList
* List of Observations to insert.
* @return The number of rows modified
* @throws VizException
*/
public int insert(List<ForecastData> insertList) throws VizException {
int status = -1;
Date now = Calendar.getInstance(TimeZone.getTimeZone("GMT")).getTime();
for (int i = 0; i < insertList.size(); i++) {
ForecastData data = insertList.get(i);
String tablename = HydroUtils.getTableName(data.getPe(),
data.getTs());
SqlBuilder sql = new SqlBuilder(tablename);
sql.setSqlType(SqlBuilder.INSERT);
sql.addString("lid", data.getLid());
sql.addString("pe", data.getPe().toUpperCase());
sql.addInt("dur", data.getDur());
sql.addString("ts", data.getTs().toUpperCase());
sql.addString("extremum", data.getExtremum().toUpperCase());
sql.addString("product_id", data.getProductID().toUpperCase());
if (data.getValidTime() != null) {
sql.addString("validTime",
dateFormat.format(data.getValidTime()));
sql.addInt("probability", -1);
sql.addString("basisTime",
dateFormat.format(data.getBasisTime()));
if (data.getProductTime() == null) {
sql.addString("producttime",
dateFormat.format(Calendar
.getInstance(TimeZone.getTimeZone("GMT"))
.getTime()));
} else {
sql.addString("producttime",
dateFormat.format(data.getProductTime()));
}
} else {
sql.addString("obstime", dateFormat.format(data.getObsTime()));
sql.addString("producttime",
dateFormat.format(data.getObsTime()));
}
sql.addDouble("value", data.getValue());
sql.addString("shef_qual_code", "M");
sql.addInt("quality_code", TimeSeriesUtil.DEFAULT_QC_VALUE);
sql.addInt("revision", 0);
sql.addString("postingtime", dateFormat.format(now));
AppsDefaults ad = AppsDefaults.getInstance();
boolean debug = ad.getBoolean(HydroConstants.DEBUG_HYDRO_DB_TOKEN,
false);
if (debug) {
statusHandler.info(ad.getToken(HydroConstants.PGHOST) + ":"
+ ad.getToken(HydroConstants.PGPORT) + ":"
+ ad.getToken(HydroConstants.DB_NAME));
statusHandler.info("Query: " + sql.toString());
}
status = DirectDbQuery.executeStatement(sql.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
}
return status;
}
/**
* Edits a list of Observations.
*
* @param editList
* List of Observations to edit.
* @return The number of rows modified
* @throws VizException
*/
public int edit(List<ForecastData> editList) throws VizException {
int status = -1;
Date now = Calendar.getInstance(TimeZone.getTimeZone("GMT")).getTime();
for (int i = 0; i < editList.size(); i++) {
ForecastData data = editList.get(i);
String tablename = HydroUtils.getTableName(data.getPe(),
data.getTs());
// set the QC to GOOD when you set data to missing.
data.setQualityCode(TimeSeriesUtil.setQcCode(QC_MANUAL_PASSED,
data.getQualityCode()));
SqlBuilder sql = new SqlBuilder(tablename);
sql.setSqlType(SqlBuilder.UPDATE);
sql.addDouble("value", data.getValue());
sql.addString("shef_qual_code", "M");
sql.addInt("quality_code", data.getQualityCode());
sql.addInt("revision", 1);
sql.addString("postingTime",
HydroConstants.DATE_FORMAT.format(now));
if (data.getProductTime() == null) {
sql.addString("producttime",
HydroConstants.DATE_FORMAT.format(Calendar
.getInstance(TimeZone.getTimeZone("GMT"))
.getTime()));
}
StringBuilder where = new StringBuilder();
where.append(" where lid = '" + data.getLid().toUpperCase() + "' ");
where.append("and dur = " + data.getDur() + " ");
where.append("and ts = '" + data.getTs().toUpperCase() + "' ");
where.append("and extremum = '" + data.getExtremum().toUpperCase()
+ "' ");
if (data.getValidTime() != null) {
where.append("and validtime = '"
+ dateFormat.format(data.getValidTime()) + "'");
where.append(" and basistime = '"
+ dateFormat.format(data.getBasisTime()) + "'");
} else {
where.append("and obstime = '"
+ dateFormat.format(data.getObsTime()) + "'");
}
sql.setWhereClause(where.toString());
AppsDefaults ad = AppsDefaults.getInstance();
boolean debug = ad.getBoolean(HydroConstants.DEBUG_HYDRO_DB_TOKEN,
false);
if (debug) {
statusHandler.info(ad.getToken(HydroConstants.PGHOST) + ":"
+ ad.getToken(HydroConstants.PGPORT) + ":"
+ ad.getToken(HydroConstants.DB_NAME));
statusHandler.info("Query: " + sql);
}
DirectDbQuery.executeStatement(sql.toString(), HydroConstants.IHFS,
QueryLanguage.SQL);
}
return status;
}
/**
* Get the product's productId and productTime.
*
* @param where
* The where statement
* @param table
* The table to get the data from
* @return List of String[] productId, productTime
* @throws VizException
*/
public String[] getProductIdTime(final String where, final String table)
throws VizException {
StringBuilder sql = new StringBuilder();
sql.append("select product_id, productTime from " + table);
sql.append(where);
AppsDefaults ad = AppsDefaults.getInstance();
boolean debug = ad.getBoolean(HydroConstants.DEBUG_HYDRO_DB_TOKEN,
false);
if (debug) {
statusHandler.info(ad.getToken(HydroConstants.PGHOST) + ":"
+ ad.getToken(HydroConstants.PGPORT) + ":"
+ ad.getToken(HydroConstants.DB_NAME));
statusHandler.info("Query: " + sql);
}
List<Object[]> rs = DirectDbQuery.executeQuery(sql.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
String[] sa = null;
if (rs != null && !rs.isEmpty()) {
Object[] item = rs.get(0);
sa = new String[2];
sa[0] = (String) item[0];
sa[1] = dateFormat.format((Date) item[1]);
}
return sa;
}
/**
* Get the list of forecast data.
*
* @param where
* The where statement
* @param table
* The table to get the data from
* @return List of String[] productId, productTime
* @throws VizException
*/
public List<Fcstheight> getForecast(final String where, final String table)
throws VizException {
StringBuilder query = new StringBuilder("select ");
query.append("lid, pe, dur, ts, extremum, probability, validtime, ");
query.append("basistime, value, shef_qual_code, quality_code, ");
query.append("revision, product_id, producttime, postingtime ");
query.append("from " + table + " " + where);
AppsDefaults ad = AppsDefaults.getInstance();
boolean debug = ad.getBoolean(HydroConstants.DEBUG_HYDRO_DB_TOKEN,
false);
if (debug) {
statusHandler.info(ad.getToken(HydroConstants.PGHOST) + ":"
+ ad.getToken(HydroConstants.PGPORT) + ":"
+ ad.getToken(HydroConstants.DB_NAME));
statusHandler.info("Query: " + query.toString());
}
QueryResult results = DirectDbQuery.executeMappedQuery(query.toString(),
HydroConstants.IHFS, QueryLanguage.SQL);
if (results == null || results.getResultCount() == 0) {
return Collections.emptyList();
}
List<Fcstheight> returnList = new ArrayList<>(results.getResultCount());
for (int i = 0; i < results.getResultCount(); i++) {
Fcstheight fh = new Fcstheight();
FcstheightId fhid = new FcstheightId();
fhid.setLid((String) results.getRowColumnValue(i, "lid"));
fhid.setPe((String) results.getRowColumnValue(i, "pe"));
fhid.setDur(((Number) results.getRowColumnValue(i, "dur"))
.shortValue());
fhid.setTs((String) results.getRowColumnValue(i, "ts"));
fhid.setExtremum((String) results.getRowColumnValue(i, "extremum"));
fhid.setProbability(
((Number) results.getRowColumnValue(i, "probability"))
.floatValue());
fhid.setValidtime((Date) results.getRowColumnValue(i, "validtime"));
fhid.setBasistime((Date) results.getRowColumnValue(i, "basistime"));
fh.setId(fhid);
fh.setValue((Double) results.getRowColumnValue(i, "value"));
fh.setShefQualCode(
(String) results.getRowColumnValue(i, "shef_qual_code"));
fh.setQualityCode(
((Number) results.getRowColumnValue(i, "quality_code"))
.intValue());
fh.setRevision(((Number) results.getRowColumnValue(i, "revision"))
.shortValue());
fh.setProductId(
(String) results.getRowColumnValue(i, "product_id"));
fh.setProducttime(
(Date) results.getRowColumnValue(i, "producttime"));
fh.setPostingtime(
(Date) results.getRowColumnValue(i, "postingtime"));
returnList.add(fh);
}
return returnList;
}
/**
* Insert/Update the forecast tables.
*
* @param dataObj
* The persistent data object to insert/update
* @return The number of objects inserted/updated
* @throws VizException
*/
public int putForecast(PersistableDataObject<?> dataObj)
throws VizException {
int rv = 0;
rv = DirectDbQuery.saveOrUpdate(dataObj, HydroConstants.IHFS);
return rv;
}
/**
* Get the station display map.
*
* @return The map of station displays
*/
public Map<String, String> getStationDisplayMap() {
return stnDisplayMap;
}
}