@RequestMapping(value = "/upgradeToken")
  public String upgradeToken(HttpServletRequest request, HttpServletResponse response)
      throws OAuthException, OAuthMessageSignerException, OAuthNotAuthorizedException,
          OAuthExpectationFailedException, OAuthCommunicationException {
    OAuthConsumer consumer =
        (OAuthConsumer) request.getSession().getAttribute(FRESHBOOKS_OAUTH_CONSUMER);
    OAuthProvider provider =
        (OAuthProvider) request.getSession().getAttribute(FRESHBOOKS_OAUTH_PROVIDER);
    String verifier = request.getParameter("oauth_verifier");
    provider.retrieveAccessToken(consumer, verifier);
    Guest guest = AuthHelper.getGuest();

    final Connector connector = Connector.getConnector("freshbooks");
    final ApiKey apiKey = guestService.createApiKey(guest.getId(), connector);

    guestService.setApiKeyAttribute(apiKey, "accessToken", consumer.getToken());
    guestService.setApiKeyAttribute(apiKey, "tokenSecret", consumer.getTokenSecret());

    return "redirect:/app/from/" + connector.getName();
  }
 /**
  * Calls updateConnector(...) for all of a guest's connector
  *
  * @param guestId
  * @return a list of objects that describe worker tasks that have been either modified or added to
  *     the update queue
  */
 @Override
 public List<ScheduleResult> updateAllConnectors(final long guestId) {
   List<ScheduleResult> scheduleResults = new ArrayList<ScheduleResult>();
   if (isShuttingDown) {
     StringBuilder sb =
         new StringBuilder(
                 "module=updateQueue component=updateAllConnectors" + " action=updateConnector")
             .append(" message=\"Service is shutting down... Refusing updates\"");
     logger.warn(sb.toString());
     return scheduleResults;
   }
   final List<ApiKey> connectors = guestService.getApiKeys(guestId);
   for (ApiKey key : connectors) {
     if (key != null && key.getConnector() != null) {
       List<ScheduleResult> updateRes = updateConnector(guestId, key.getConnector(), false);
       scheduleResults.addAll(updateRes);
     }
   }
   return scheduleResults;
 }
  @RequestMapping("/createAccount")
  public ModelAndView createAccount(
      @RequestParam("email") String email,
      @RequestParam("username") String username,
      @RequestParam("firstname") String firstname,
      @RequestParam("lastname") String lastname,
      @RequestParam("password1") String password,
      @RequestParam("password2") String password2,
      //		@RequestParam("recaptchaChallenge") String challenge,
      //		@RequestParam("recaptchaResponse") String uresponse,
      HttpServletRequest request,
      HttpServletResponse response)
      throws Exception {
    email = email.trim();
    password = password.trim();
    password2 = password2.trim();
    username = username.trim();
    firstname = firstname.trim();
    lastname = lastname.trim();

    List<String> required = new ArrayList<String>();
    List<String> errors = new ArrayList<String>();
    if (email == "") required.add("email");
    if (username == "") {
      required.add("username");
    } else if (guestService.getGuest(username) != null) {
      errors.add("usernameTaken");
    }
    if (password == "") required.add("password");
    if (password2 == "") required.add("password2");
    if (password.length() < 8) errors.add("passwordTooShort");
    if (!password.equals(password2)) errors.add("passwordsDontMatch");
    if (guestService.getGuestByEmail(email) != null) errors.add("userExists");

    //		String remoteAddr = request.getRemoteAddr();
    //        ReCaptchaImpl reCaptcha = new ReCaptchaImpl();
    //        reCaptcha.setPrivateKey("6LeXl8QSAAAAADjPASFlMINNRVwtlpcvGugcr2RI");
    //
    //        ReCaptchaResponse reCaptchaResponse = reCaptcha.checkAnswer(remoteAddr, challenge,
    // uresponse);
    //
    //		if (!reCaptchaResponse.isValid())
    //		errors.add("wrongCaptcha");

    if (errors.size() == 0 && required.size() == 0) {
      logger.info("action=register success=true username="******" email=" + email);
      guestService.createGuest(username, firstname, lastname, password, email);
      request.setAttribute("username", username);
      request.setAttribute("password", password);
      return new ModelAndView("accountCreationComplete");
    } else {
      logger.info("action=register errors=true");
      ModelAndView mav = new ModelAndView("createAccount");
      mav.addObject("email", email);
      mav.addObject("username", username);
      mav.addObject("firstname", firstname);
      mav.addObject("lastname", lastname);
      mav.addObject("errors", errors);
      mav.addObject("required", required);
      return mav;
    }
  }
  private JSONObject retrievePhotoHistory(UpdateInfo updateInfo, long from, long to, int page)
      throws Exception {
    long then = System.currentTimeMillis();

    String api_key = env.get("flickrConsumerKey");
    String nsid = guestService.getApiKeyAttribute(updateInfo.apiKey, "nsid");
    String token = guestService.getApiKeyAttribute(updateInfo.apiKey, "token");

    // The start/end upload dates should be in the form of a unix timestamp (see
    // http://www.flickr.com/services/api/flickr.people.getPhotos.htm)
    String startDate = String.valueOf(from / 1000);
    String endDate = String.valueOf(to / 1000);

    Map<String, String> params = new HashMap<String, String>();
    params.put("method", "flickr.people.getPhotos");
    params.put("per_page", String.valueOf(ITEMS_PER_PAGE));
    params.put("page", String.valueOf(page));
    params.put("api_key", api_key);
    params.put("user_id", nsid);
    params.put("auth_token", token);
    params.put("format", "json");
    params.put("nojsoncallback", "1");
    params.put("extras", "date_upload,date_taken,description,geo,tags");
    params.put("min_upload_date", startDate);
    params.put("max_upload_date", endDate);

    String api_sig = sign(params);

    String searchPhotosUrl =
        "http://api.flickr.com/services/rest/"
            + "?method=flickr.people.getPhotos&api_key="
            + api_key
            + "&per_page="
            + ITEMS_PER_PAGE
            + "&page="
            + page
            + "&api_key="
            + api_key
            + "&user_id="
            + nsid
            + "&auth_token="
            + token
            + "&format=json&nojsoncallback=1&extras=date_upload,date_taken,description,geo,tags"
            + "&min_upload_date="
            + startDate
            + "&max_upload_date="
            + endDate
            + "&api_sig="
            + api_sig;
    searchPhotosUrl = searchPhotosUrl.replace(" ", "%20");
    String photosJson = null;
    try {
      photosJson = fetch(searchPhotosUrl);
      countSuccessfulApiCall(updateInfo.apiKey, updateInfo.objectTypes, then, searchPhotosUrl);
    } catch (Exception e) {
      countFailedApiCall(
          updateInfo.apiKey, updateInfo.objectTypes, then, searchPhotosUrl, Utils.stackTrace(e));
      throw e;
    }

    if (photosJson == null || photosJson.equals(""))
      throw new Exception("empty json string returned from flickr API call");

    JSONObject feed = JSONObject.fromObject(photosJson);

    return feed;
  }
 public boolean checkAuthorization(GuestService guestService, long guestId) {
   ApiKey apiKey = guestService.getApiKey(guestId, Connector.getConnector("toodledo"));
   return apiKey != null;
 }