Example #1
0
  /**
   * Returns true if key is valid. Uses cache of keys so doesn't have to access database each time.
   * If key not in cache then will reread keys from database in case it was just added. But won't do
   * so more than every few seconds since more frequent access could allow an app with a bad key to
   * cause the db to be queried to often putting an unneeded burden on the db.
   *
   * <p>Synchronized because can have simultaneous access and using a cache.
   *
   * @param key The key to investigate
   * @return True if key is valid
   */
  public synchronized boolean isKeyValid(String key) {
    try {
      // If key is already in cache return true
      if (apiKeyCache.get(key) != null) return true;

      // Want to make sure a user doesn't overwhelm the system by
      // repeatedly trying to use an invalid key. So if the cache was
      // just updated a few x seconds ago then don't update it again
      // right now. Simply return false.
      if (System.currentTimeMillis()
          < lastTimeKeysReadIntoCache + lastTimeKeysReadLimitSec.getValue() * Time.MS_PER_SEC)
        return false;
      lastTimeKeysReadIntoCache = System.currentTimeMillis();

      // Key wasn't in cache so update the cache in case it was added
      apiKeyCache.clear();
      for (ApiKey apiKey : getApiKeys()) {
        apiKeyCache.put(apiKey.getKey(), apiKey);
      }

      return apiKeyCache.get(key) != null;
    } catch (Exception e) {
      logger.error("Problem checking key \"{}\" to see if valid.", key, e);
      return false;
    }
  }
Example #2
0
  /**
   * Called when AVL data is read from URL. Processes the JSON data and calls processAvlReport() for
   * each AVL report.
   */
  @Override
  protected Collection<AvlReport> processData(InputStream in) throws Exception {
    // Get the JSON string containing the AVL data
    String jsonStr = getJsonString(in);
    try {
      // Convert JSON string to a JSON object
      JSONObject jsonObj = new JSONObject(jsonStr);

      // The JSON feed is really odd. Instead of having an
      // array of vehicles there is a separate JSON object
      // for each vehicle, and the name of the object is the
      // trip ID. Therefore need to get names of all the objects
      // so that each one can be accessed by name.
      String tripNames[] = JSONObject.getNames(jsonObj);

      // The return value for the method
      Collection<AvlReport> avlReportsReadIn = new ArrayList<AvlReport>();

      // For each vehicle...
      for (String tripName : tripNames) {
        JSONObject v = jsonObj.getJSONObject(tripName);

        // Create the AvlReport from the JSON data
        String vehicleId = Integer.toString(v.getInt("vehicle_id"));
        Double lat = v.getDouble("vehicle_lat");
        Double lon = v.getDouble("vehicle_lon");
        // Guessing that the speed is in mph since getting values up to 58.
        // Therefore need to convert to m/s.
        float speed = (float) v.getDouble("vehicle_speed") * Geo.MPH_TO_MPS;
        // Not sure if bearing is the same as heading.
        float heading = (float) v.getDouble("vehicle_bearing");
        // The time is really strange. It is off by 4-5 hours for some
        // strange reason. It appears to be 4 hours off during daylight
        // savings time but 5 hours during normal winter hours. Yikes!
        // Therefore using the parameter keolisFeedAvlTimeOffset to
        // specify the offset.
        long gpsTime =
            v.getLong("vehicle_timestamp") * Time.MS_PER_SEC
                + keolisFeedAvlTimeOffset.getValue() * Time.HOUR_IN_MSECS;

        // Create the AvlReport
        AvlReport avlReport = new AvlReport(vehicleId, gpsTime, lat, lon, speed, heading, "Keolis");

        // Need to set assignment info separately. Unfortunately the
        // trip ID in the Keolis feed doesn't correspond exactly to the
        // trip IDs in the GTFS data. In Keolis feed it will be
        // something like "CR-FRAMINGHAM-Weekday-515" but in GTFS it will
        // be "CR-Worcester-CR-Weekday-Worcester-Jun15-515". Therefore
        // it is best to just use the trip short name, such as "515".
        String tripShortName = tripName.substring(tripName.lastIndexOf('-') + 1);

        // Actually set the assignment
        avlReport.setAssignment(tripShortName, AssignmentType.TRIP_SHORT_NAME);

        logger.debug("From KeolisAvlModule {}", avlReport);

        if (shouldProcessAvl) {
          avlReportsReadIn.add(avlReport);
        }
      }

      // Return all the AVL reports read in
      return avlReportsReadIn;
    } catch (JSONException e) {
      logger.error("Error parsing JSON. {}. {}", e.getMessage(), jsonStr, e);
      return new ArrayList<AvlReport>();
    }
  }