【问题标题】:Google drive persistant authentication for a web application用于 Web 应用程序的 Google 驱动器持久身份验证
【发布时间】:2017-05-22 10:01:08
【问题描述】:

我正在使用 Oauth2.0 和 drive v2 API 处理 Google Drive 身份验证。我在谷歌应用程序控制台中为我新创建的应用程序获得了 clientId 、客户端密码和重定向 URI。我正在尝试使用这些 clientID 和客户端密码对驱动器进行身份验证。 这是我用于通过 google drive 进行身份验证并从中获取文件的代码。

    public class GoolgeDriveUpload3 {

    private static String CLIENT_ID = "xxxxxxxxxx";
    private static String CLIENT_SECRET = "yyyyyyyyyy";
    static HttpTransport HTTP_TRANSPORT = new NetHttpTransport();
    static JsonFactory jsonFactory = new JacksonFactory();
    private static FileDataStoreFactory DATA_STORE_FACTORY;

    private static final java.io.File DATA_STORE_DIR = new java.io.File(System.getProperty("user.home"),
            ".credentials/drive-java-quickstart");

    static {
        try {
            HTTP_TRANSPORT = GoogleNetHttpTransport.newTrustedTransport();
            DATA_STORE_FACTORY = new FileDataStoreFactory(DATA_STORE_DIR);
        } catch (Throwable t) {
            t.printStackTrace();
            System.exit(1);
        }
    }

    public static void main(String[] args) throws IOException {
        GoogleAuthorizationCodeFlow flow = new GoogleAuthorizationCodeFlow.Builder(HTTP_TRANSPORT, jsonFactory,
                CLIENT_ID, CLIENT_SECRET, Arrays.asList(DriveScopes.DRIVE_FILE)).setDataStoreFactory(DATA_STORE_FACTORY)
                        .setAccessType("online").setApprovalPrompt("auto").build();
        Credential credential = new AuthorizationCodeInstalledApp(flow, new LocalCallbackServer()).authorize("user");
        Drive service = new Drive.Builder(HTTP_TRANSPORT, jsonFactory, credential).build();
        List<File> result = new ArrayList<File>();
        Files.List request = null;
        request = service.files().list();
        FileList files = request.setQ("'root' in parents and trashed=false  ").execute();
        result.addAll(files.getItems());
        request.setPageToken(files.getNextPageToken());

        for (File f : result) {
            System.out.println("Files are: " + f.getTitle() + " " + f.getId() + " " + f.getAlternateLink());
        }
     }
  }

public class LocalCallbackServer implements VerificationCodeReceiver {

    volatile String code;
    private final int LOCAL_SERVER_PORT = 9058;

    @Override
    public synchronized String waitForCode() {

        try {
            this.wait();
        } catch (Exception ex) {
        }
        System.out.println("returning code is -> " + code);
        return code;

    }

    @Override
    public String getRedirectUri() {

        new Thread(new MyThread()).start();
        return "http://127.0.0.1:" + LOCAL_SERVER_PORT;
    }

    @Override
    public void stop() {
    }

    class MyThread implements Runnable {

        @Override
        public void run() {
            try {
                // return GoogleOAuthConstants.OOB_REDIRECT_URI;
                ServerSocket ss = new ServerSocket(LOCAL_SERVER_PORT);
                System.out.println("server is ready...");
                Socket socket = ss.accept();
                System.out.println("new request....");
                InputStream is = socket.getInputStream();
                StringWriter writer = new StringWriter();
                String firstLine = null;

                InputStreamReader isr = new InputStreamReader(is);
                StringBuilder sb = new StringBuilder();
                BufferedReader br = new BufferedReader(isr);
                String read = br.readLine();
                firstLine = read;
                OutputStream os = socket.getOutputStream();
                PrintWriter out = new PrintWriter(os, true);

                StringTokenizer st = new StringTokenizer(firstLine, " ");
                st.nextToken();
                String codeLine = st.nextToken();
                st = new StringTokenizer(codeLine, "=");
                st.nextToken();
                code = st.nextToken();

                out.write("RETURNED CODE IS " + code + "");
                out.flush();
                // is.close();

                socket.close();

                System.out.println("Extracted coded is " + code);

                synchronized (LocalCallbackServer.this) {
                    LocalCallbackServer.this.notify();
                }
                System.out.println("return is " + sb.toString());

            } catch (IOException ex) {
                Logger.getLogger(LocalCallbackServer.class.getName()).log(Level.SEVERE, null, ex);
            }
        }
    }
}

当我运行它时,我会在浏览器中看到一个新窗口,其中包含我指定的 URI 和允许访问的 google 帐户权限。身份验证完成后,我将上传一些文件到驱动器。我希望此身份验证是持久的,以便我可以在后台执行这些操作。但我认为每 3600 秒我都会获得一个新窗口以允许访问。有什么办法可以解决这个问题吗?

【问题讨论】:

    标签: java oauth-2.0 google-drive-api google-oauth


    【解决方案1】:

    setAccessType 更改为offline。这将产生访问令牌和刷新令牌。理论上,库会根据需要自动使用 RT 获取新的 AT。

    【讨论】:

      【解决方案2】:

      您需要将 Credential 对象保存到本地存储以供以后重复使用。如果使用 access_type = 'offline'(https://developers.google.com/identity/protocols/OAuth2WebServer 的“刷新访问令牌(离线访问)”部分),则凭证对象创建一天或无限次(使用刷新访问令牌)

      【讨论】:

        猜你喜欢
        • 2015-02-22
        • 1970-01-01
        • 1970-01-01
        • 2014-07-10
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2018-08-11
        • 2012-09-09
        相关资源
        最近更新 更多