SNOTEL_Data.java [src/java/datadownload] Revision: default Date:
package datadownload;
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import java.net.URL;
import java.net.URLConnection;
import java.util.ArrayList;
import java.util.Iterator;
/**
* Last Updated: 29-December-2016
* @author Tyler Wible
* @since 7-July-2014
*/
public class SNOTEL_Data {
/**
* Finds data for the specified station out of the SNOWTEL Database
* @param stationID the station ID number for the SNOTEL station
* @param state the name of the state in which the SNOTEL station exists
* @param dataType
* @return a String[][] containing column1 = date(if dataType = "daily": yyyy-MM-dd format, if dataType = "hourly": yyyy-MM-dd HH:mm format), column2 = flowValue
* @throws Exception
*/
public static Object[] getSNOTELdata(String stationID, String state, String dataType) throws Exception {
//Get the webpage of data for the USGS flow station
ArrayList<String> webpageAll = DownloadSNOTELwebpage(stationID, state);
//Pull out new arraylist of only the desired data from the arraylist to return as the web page result
Iterator<String> iterate = webpageAll.iterator( );
ArrayList<String> textData = new ArrayList<String>();
int dataIndex = 0;
while(iterate.hasNext()){
String temp_pageData = (String) iterate.next();
String[] f = temp_pageData.split(",");
if(!temp_pageData.contains("#") && (f[0].equals("Date"))){
//If in header of data, determine which column to get:
//Date
//Snow Water Equivalent (in)
//Precipitation Accumulation (in)
//Air Temperature Maximum (degF)
//Air Temperature Minimum (degF)
//Air Temperature Average (degF)
//Precipitation Increment (in)
for(int i=0; i<f.length; i++){
if(dataType.equalsIgnoreCase("snow") && f[i].contains("Snow Water Equivalent")){
dataIndex = i;
}else if(dataType.equalsIgnoreCase("precip_cummulative") && f[i].contains("Precipitation Accumulation")){
dataIndex = i;
}else if(dataType.equalsIgnoreCase("temp_max") && f[i].contains("Air Temperature Maximum")){
dataIndex = i;
}else if(dataType.equalsIgnoreCase("temp_min") && f[i].contains("Air Temperature Minimum")){
dataIndex = i;
}else if(dataType.equalsIgnoreCase("temp_ave") && f[i].contains("Air Temperature Average")){
dataIndex = i;
}else if(dataType.equalsIgnoreCase("precip_incremental") && f[i].contains("Precipitation Increment")){
dataIndex = i;
}
}
}else if(!temp_pageData.contains("#") && (!f[0].equals("Date"))){
//Pull desired data
if(dataIndex > 0 && f.length > dataIndex && !f[dataIndex].equalsIgnoreCase("")){
textData.add(f[0] + "\t" + f[dataIndex]);
}
}
}
//convert Array list into String[][] array (column1 = date, column2 = value)
String[][] stringArray = new String[textData.size()][2];
for(int i=0; i<stringArray.length; i++){
String[] currentColumns = textData.get(i).split("\t");
//currentColumns[0] = date
//currentColumns[1] = value
stringArray[i][0] = currentColumns[0];
stringArray[i][1] = currentColumns[1];
}
//Save analysis results
String start = "-1";
String end = "-1";
if(stringArray.length > 0){
start = stringArray[0][0];
end = stringArray[stringArray.length - 1][0];
}
Object[] returnArray = {webpageAll, stringArray, start, end};
return returnArray;
}
/**
* Opens a web connection to USGS and returns the contents of a search for all flow data for the specific station and date range
* @param stationID the USGS station ID for the current station
* @param state the name of the state in which the SNOTEL station exists
* @return an ArrayList<String> containing the results of the search for flow data using the above inputs
* @throws IOException
*/
public static ArrayList<String> DownloadSNOTELwebpage(String stationID, String state) throws IOException {
//Specify flow website from inputs
//https://www.wcc.sc.egov.usda.gov/reportGenerator/view_csv/customSingleStationReport/daily/946:AK:SNTL%7Cid=%22%22%7Cname/POR_BEGIN,POR_END/WTEQ::value,PREC::value,TMAX::value,TMIN::value,TAVG::value,PRCP::value
state = changeStateCode(state, true);
String website = "https://wcc.sc.egov.usda.gov/reportGenerator/view_csv/customSingleStationReport/daily/"
+ stationID + ":"
+ state + ":SNTL%7Cid=%22%22%7Cname/POR_BEGIN,POR_END/WTEQ::value,PREC::value,TMAX::value,TMIN::value,TAVG::value,PRCP::value";
//Open the provided website
URL webpage = new URL(website);
URLConnection yc = webpage.openConnection();
BufferedReader in = new BufferedReader(new InputStreamReader(yc.getInputStream()));
//Read out all of the webpage out into an ArrayList<String>
String inputLine;
ArrayList<String> pageData = new ArrayList<String>( );
while((inputLine = in.readLine()) != null){
pageData.add(inputLine);
}
in.close();
return pageData;
}
private static String changeStateCode(String incomingState, boolean changeToStateCode){
String[][] stateList = {{"Alaska", "ak"},
{"Arizona", "az"},
{"California", "ca"},
{"Colorado", "co"},
{"Idaho", "id"},
{"Montana", "mt"},
{"Nevada", "nv"},
{"New Mexico", "nm"},
{"Oregon", "or"},
{"South Dakota", "sd"},
{"Utah", "ut"},
{"Washington", "wa"},
{"Wyoming", "wy"}};
String outgoingState = "";
for(int i=0; i<stateList.length; i++){
if(changeToStateCode){
//Take the provided state and get it's state code
if(stateList[i][0].equalsIgnoreCase(incomingState)){
outgoingState = stateList[i][1];
break;
}
}else{
//Take the provided state code and get it's state name
if(stateList[i][1].equalsIgnoreCase(incomingState)){
outgoingState = stateList[i][0];
break;
}
}
}
return outgoingState;
}
}