使用java离线访问Google日历

问题描述:

我们有代码将我们的应用程序日历与登录用户的Google日历同步。该代码使用AuthSub和CalendarService类,但它不提供使用访问令牌和刷新令牌的谷歌日历的离线访问,因为我想使用日历类来使用OAuth v3。我面临着将我的旧代码合并到没有getFeed()函数的新v3 Calendar类的问题。这里是我的应用程序的一些代码使用java离线访问Google日历

if(StringUtil.isValid(request.getQueryString())) { 
       onetimeUseToken = AuthSubUtil.getTokenFromReply(request.getQueryString()); 
      }  

      if(StringUtil.isValid(onetimeUseToken)) {   

        String sessionToken = AuthSubUtil.exchangeForSessionToken(onetimeUseToken,null); 
        CalendarService calendarService = new CalendarService("myapp"); 
        calendarService.setAuthSubToken(sessionToken, null);  
        session.setAttribute("calendarServicesession",calendarService); 
        userIDforCalendar = (String) session.getAttribute("calendar_user_no"); 
         } 

         CalendarFeed myResultsFeed1 =service.getFeed(new URL("https://www.google.com/calendar/feeds/default/allcalendars/full"),CalendarFeed.class); 

      for (int i = 0; i < myResultsFeed1.getEntries().size(); i++) { 
       CalendarEntry entry = myResultsFeed1.getEntries().get(i); 
          ..... 

} 

请给我提供一些方法使用CalendarService这样我就不必太大改变我的代码给离线访问。希望快速回复。

Thanks- Dravit古普塔

谷歌弃用的AuthSub从2012年4月20日因此,它是你迁移到OAuth 2.0用户和谷歌日历API V3的时间。首先从这些以下链接下载jar文件:

https://google-api-client-libraries.appspot.com/download/library/calendar/v3/java

http://google-oauth-java-client.googlecode.com/files/google-oauth-java-client-1.13.1-beta.zip

从您的项目中的旧日历的AuthSub jar文件,并从这个链接添加jar文件。

然后去谷歌api控制台得到您的客户端ID,客户端的秘密,并创建一个重定向的URI。 并从相同的api控制台启用谷歌日历api。

我给你一个样本代码,用于对用户进行身份验证并显示他必须存储输出中获取的刷新令牌并存储它的日历,以便可以脱机访问日历。

此功能用于OAuth授权。

public void authenticate(HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException { 
    String client_id    = "xxxx"; 
    String redirect_uri    = "xxxxxx"; 
    String scope     = "https://www.googleapis.com/auth/calendar"; 
    String client_secret   = "xxxxxx"; 
    List <String> scopes; 
    HttpTransport transport   = new NetHttpTransport(); 
    JsonFactory jsonFactory   = new JacksonFactory(); 

    scopes = new LinkedList<String>(); 
    scopes.add(scope); 
    GoogleAuthorizationCodeFlow flow = new GoogleAuthorizationCodeFlow.Builder(transport, jsonFactory, client_id, client_secret, scopes).build(); 
    GoogleAuthorizationCodeRequestUrl url = flow.newAuthorizationUrl(); 
    url.setRedirectUri(redirect_uri); 
    url.setApprovalPrompt("force"); 
    url.setAccessType("offline"); 
    String authorize_url = url.build(); 
    response.sendRedirect(authorize_url); 
} 

你要添加值的变量client_idclient_secretredirect_uri。所有这些值都在你的谷歌api控制台中。

授权功能将我转发给授权URL,授权URL给了我一个访问令牌和一个刷新令牌。但是,访问令牌在一段时间间隔后过期。因此,如果您需要访问令牌,则需要存储刷新令牌并使用该令牌在您访问日历API时生成它。

以下函数生成访问令牌和刷新令牌,并在用户的Google日历中打印日历列表。

public void importCalendarList(HttpServletRequest request, HttpServletResponse response) throws IOException, ServletException { 
    HttpSession session = request.getSession(); 
    String staffKey = (String) session.getAttribute("staffKey"); 
    ContactJdo staffDetails = staff.getStaffDetail(staffKey); 
    String code = request.getParameter("code"); 
    String calendarId=""; 

    GoogleAuthorizationCodeFlow flow = new GoogleAuthorizationCodeFlow.Builder(transport, jsonFactory, client_id, client_secret, scopes).build(); 
    GoogleTokenResponse res = flow.newTokenRequest(code).setRedirectUri(redirect_uri).execute(); 
    String refreshToken = res.getRefreshToken(); 
    String accessToken = res.getAccessToken(); 

    List <CalendarListEntry>list1= getCalendars(accessToken); 

    for(CalendarListEntry temp:list1) { 
     System.out.println(temp.getId()); 
    }} 

如果你看一下上面的函数,它会产生两种访问和刷新令牌。如果你想令牌生成访问再次使用此功能:

public static String getAccessToken(String refreshToken, String client_id, String client_secret) throws IOException { 
    HttpTransport transport   = new NetHttpTransport(); 
    JsonFactory jsonFactory   = new JacksonFactory(); 

    GoogleRefreshTokenRequest req = new GoogleRefreshTokenRequest(transport, jsonFactory, refreshToken, client_id, client_secret); 
    GoogleTokenResponse res = req.execute(); 
    String accessToken = res.getAccessToken(); 
    return accessToken; 
} 

商店刷新令牌的地方,你可以做到这一点是日历文件中所提及的所有操作。在此查找

https://google-api-client-libraries.appspot.com/documentation/calendar/v3/java/latest/index.html

+0

但是,如果用户已经做出了这样的授权?如果我只有accessToken(+ appToken + appSecret)会怎么样? v3有可能吗?你的getCalendars方法如何实现? – Karussell

+0

啊,它看起来应该是这样的:GoogleCredential凭证=新的GoogleCredential()。setAccessToken(“atoken”); client = new Calendar.Builder(new NetHttpTransport(),new JacksonFactory(),凭证) .setApplicationName(APPLICATION_NAME) .build(); - > https://groups.google.com/forum/#!topic/google-api-java-client/c33zpCkjJGk – Karussell

+0

是的,这工作+我必须启用日历API在谷歌控制台+以下maven deps:' com.google.apis谷歌的API服务,日历 V3-rev47-1.15.0-RC com.google.api客户端谷歌的API - 客户端 1 .15.0-RC com.google.http客户端谷歌-HTTP-客户jackson2' – Karussell