package com.schneeloch.bostonbusmap_library.parser; import com.google.common.base.Optional; import com.google.common.collect.ImmutableMap; import com.google.common.collect.Lists; import org.xml.sax.Attributes; import org.xml.sax.SAXException; import java.io.BufferedReader; import java.io.IOException; import java.io.Reader; import java.util.HashMap; import java.util.List; import java.util.Map; import com.google.common.collect.Maps; import com.google.gson.Gson; import com.schneeloch.bostonbusmap_library.data.HubwayStopData; import com.schneeloch.bostonbusmap_library.data.HubwayStopLocation; import com.schneeloch.bostonbusmap_library.data.Locations; import com.schneeloch.bostonbusmap_library.data.PredictionStopLocationPair; import com.schneeloch.bostonbusmap_library.data.RouteConfig; import com.schneeloch.bostonbusmap_library.data.SimplePrediction; import com.schneeloch.bostonbusmap_library.data.StopLocation; import com.schneeloch.bostonbusmap_library.parser.gson.stationInfo.InfoRoot; import com.schneeloch.bostonbusmap_library.parser.gson.stationInfo.InfoStation; import com.schneeloch.bostonbusmap_library.parser.gson.stationStatus.StatusRoot; import com.schneeloch.bostonbusmap_library.parser.gson.stationStatus.StatusStation; import com.schneeloch.bostonbusmap_library.transit.HubwayTransitSource; /** * Created by schneg on 9/1/13. */ public class HubwayParser { private final RouteConfig routeConfig; private final List<HubwayStopData> hubwayStopData = Lists.newArrayList(); public HubwayParser(RouteConfig routeConfig) { this.routeConfig = routeConfig; } public void runParse(Reader infoReader, Reader statusReader) { BufferedReader bufferedInfoReader = new BufferedReader(infoReader, 2048); BufferedReader bufferedStatusReader = new BufferedReader(statusReader, 2048); InfoRoot infoRoot = new Gson().fromJson(bufferedInfoReader, InfoRoot.class); StatusRoot statusRoot = new Gson().fromJson(bufferedStatusReader, StatusRoot.class); Map<Integer, StatusStation> statusLookup = Maps.newHashMap(); for (StatusStation station : statusRoot.data.stations) { statusLookup.put(station.station_id, station); } for (InfoStation infoStation : infoRoot.data.stations) { StatusStation statusStation = statusLookup.get(infoStation.station_id); if (statusStation != null) { String tag = HubwayTransitSource.stopTagPrefix + statusStation.station_id; boolean installed = statusStation.is_installed == 1; boolean locked = !(statusStation.is_renting == 1 && statusStation.is_returning == 1); HubwayStopData data = new HubwayStopData( tag, String.valueOf(statusStation.station_id), infoStation.lat, infoStation.lon, infoStation.name, String.valueOf(statusStation.num_bikes_available), String.valueOf(statusStation.num_docks_available), locked, installed ); hubwayStopData.add(data); } } } /** * For Hubway we need to update the stop list here, we don't receive it ahead of time. */ public void addMissingStops(Locations locations) throws IOException { ImmutableMap.Builder<String, StopLocation> builder = ImmutableMap.builder(); for (HubwayStopData data : hubwayStopData) { HubwayStopLocation.HubwayBuilder hubwayBuilder = new HubwayStopLocation.HubwayBuilder(data.latitude, data.longitude, data.tag, data.name, Optional.<String>absent()); HubwayStopLocation newStop = hubwayBuilder.build(); newStop.addRoute(routeConfig.getRouteName()); builder.put(data.tag, newStop); } ImmutableMap<String, StopLocation> stopsToReplace = builder.build(); locations.replaceStops(routeConfig.getRouteName(), stopsToReplace); } public List<PredictionStopLocationPair> getPairs() { List<PredictionStopLocationPair> pairs = Lists.newArrayList(); for (HubwayStopData data : hubwayStopData) { StopLocation stop = routeConfig.getStop(data.tag); if (stop != null && data.name.equals(stop.getTitle())) { String text = makeText(data.numberBikes, data.numberEmptyDocks, data.locked, data.installed); SimplePrediction prediction = new SimplePrediction(routeConfig.getRouteName(), routeConfig.getRouteTitle(), text); PredictionStopLocationPair pair = new PredictionStopLocationPair(prediction, stop); pairs.add(pair); } } return pairs; } private static String makeText(String numberBikes, String numberEmptyDocks, boolean locked, boolean installed) { StringBuilder ret = new StringBuilder(); ret.append("Bikes: ").append(numberBikes).append("<br />"); ret.append("Empty Docks: ").append(numberEmptyDocks).append("<br />"); if (locked) { ret.append("<b>Locked</b><br />"); } if (!installed) { ret.append("<b>Not installed</b><br />"); } return ret.toString(); } }