2

Hadoop ジョブ履歴サービスにアクセスして情報を取得するための Java プログラムを作成しています。

HTTPClient を使用して HttpGet 呼び出しを行っています。ユーザー名とパスワードを入力する代わりに、keytab ファイル (ファイルは ~/.ssh/ フォルダーにあります) からログインする必要があります。

私の質問は: HTTPClient の keytab からログインする方法は?

これが私のHTTPClientのセットアップ方法です

System.setProperty("java.security.krb5.conf", "krb5.conf");
System.setProperty("sun.security.krb5.debug", "true");
System.setProperty("javax.security.auth.useSubjectCredsOnly", "false");

System.setProperty("java.security.krb5.realm", prop.getProperty("krb5.realm"));
System.setProperty("java.security.krb5.kdc", prop.getProperty("krb5.kdc"));

PoolingHttpClientConnectionManager cm = new PoolingHttpClientConnectionManager();
cm.setMaxTotal(200);
cm.setDefaultMaxPerRoute(100);

//TODO login from keytab ?
CredentialsProvider credsProvider = new BasicCredentialsProvider();
credsProvider.setCredentials(AuthScope.ANY, new UsernamePasswordCredentials("DUMMY", null));

Lookup<AuthSchemeProvider> authRegistry = RegistryBuilder.<AuthSchemeProvider>create()
  .register(AuthSchemes.SPNEGO, new SPNegoSchemeFactory())
  .build();

httpClient = HttpClients.custom().setDefaultCredentialsProvider(credsProvider)
  .setDefaultAuthSchemeRegistry(authRegistry)
  .setConnectionManager(cm)
  .build();
HttpResponse response = httpClient.execute(request);

興味深いのは、このコードが IntelliJ で正常に実行できることです。しかし、コマンドラインからビルドして実行すると、ユーザー名とパスワードを尋ねる情報が表示されます。

私は認証が初めてです。誰かが助けてくれることを願っています。どうもありがとう。

4

1 に答える 1

2
    HttpClientBuilder builder = HttpClientBuilder.create();
    Lookup<AuthSchemeProvider> authSchemeRegistry = RegistryBuilder.<AuthSchemeProvider>create()
            .register(AuthSchemes.SPNEGO, new SPNegoSchemeFactory(true)).build();
    builder.setDefaultAuthSchemeRegistry(authSchemeRegistry);
    BasicCredentialsProvider credentialsProvider = new BasicCredentialsProvider();
    credentialsProvider.setCredentials(new AuthScope(null, -1, null), new Credentials() {
        @Override
        public Principal getUserPrincipal() {
            return null;
        }

        @Override
        public String getPassword() {
            return null;
        }
    });
    builder.setDefaultCredentialsProvider(credentialsProvider);
    final HttpClient httpClient = builder.build();

    final Subject subj = new Subject();
    Krb5LoginModule krb5 = new Krb5LoginModule();

    Map<String, String> options = new HashMap<>();
    options.put("doNotPrompt", "true");
    options.put("storeKey", "true");
    options.put("useKeyTab", "true");
    options.put("useTicketCache", "true");
    options.put("keyTab", keytabFilePath); //Path to keytab file
    options.put("principal", principal);   //Principal name
    options.put("debug", "true");

    krb5.initialize(subj, null, null, options);

    krb5.login();
    krb5.commit();

    HttpResponse response = Subject.doAs(subj, new PrivilegedExceptionAction<HttpResponse>() {
        @Override
        public HttpResponse run() throws Exception {
            return httpClient.execute(request);
        }
    });
于 2016-04-26T13:01:00.733 に答える