国产一级a片免费看高清,亚洲熟女中文字幕在线视频,黄三级高清在线播放,免费黄色视频在线看

打開APP
userphoto
未登錄

開通VIP,暢享免費電子書等14項超值服

開通VIP
如何使用HttpClient認證機制
本文介紹HttpClient的認證機制,并給出示例代碼。author: ZJ 07-11-21
Blog: http://zhangjunhd.blog.51cto.com/
英文版(無代碼示例): http://hc.apache.org/httpclient-3.x/authentication.html
<!--[if !vml]--><!--[endif]-->     HttpClient三種不同的認證方案: Basic, Digest and NTLM. 這些方案可用于服務器或代理對客戶端的認證,簡稱服務器認證或代理認證。1.服務器認證(Server Authentication)
HttpClient處理服務器認證幾乎是透明的,僅需要開發(fā)人員提供登錄信息(login credentials)。登錄信息保存在HttpState類的實例中,可以通過 setCredentials(String realm, Credentials cred)和getCredentials(String realm)來獲取或設置。
HttpClient內(nèi)建的自動認證,可以通過HttpMethod類的setDoAuthentication(boolean doAuthentication)方法關閉,而且這次關閉只影響HttpMethod當前的實例。
1.1搶先認證(Preemptive Authentication)
在這種模式時,HttpClient會主動將basic認證應答信息傳給服務器,即使在某種情況下服務器可能返回認證失敗的應答,這樣做主要是為了減少連接的建立。使用該機制如下所示:
client.getParams().setAuthenticationPreemptive(true);
搶先認證模式也提供對于特定目標或代理的缺省認證。如果沒有提供缺省的認證信息,則該模式會失效。
Credentials defaultcreds = new UsernamePasswordCredentials("username", "password");
client.getState().setCredentials(new AuthScope("myhost", 80, AuthScope.ANY_REALM), defaultcreds);
Httpclient實現(xiàn)的搶先認證遵循rfc2617.
A client SHOULD assume that all paths at or deeper than the depth of the last symbolic element in the path field of the Request-URI also are within the protection space specified by the Basic realm value of the current challenge. A client MAY preemptively send the corresponding Authorization header with requests for resources in that space without receipt of another challenge from the server. Similarly, when a client sends a request to a proxy, it may reuse a userid and password in the Proxy-Authorization header field without receiving another challenge from the proxy server.
1.2服務器認證的安全方面考慮
當需要與不被信任的站點或web應用通信時,應該謹慎使用缺省的認證機制。當啟動(activate)搶先認證模式,或者認證中沒有明確給出認證域,主機的HttpClient將使用缺省的認證機制去試圖獲得目標站點的授權。
如果你提供的認證信息是敏感的,你應該指定認證域。不推薦將認證域指定為AuthScope.ANY。(只有在debugging情況下,才使用)
// To be avoided unless in debug mode
Credentials defaultcreds = new UsernamePasswordCredentials("username", "password");
client.getState().setCredentials(AuthScope.ANY, defaultcreds);
2.代理認證(proxy authentication)
除了登錄信息需單獨存放以外,代理認證與服務器認證幾乎一致。用 setProxyCredentials(String realm, Credentials cred)和 getProxyCredentials(String realm)設、取登錄信息。
3.認證方案(authentication schemes)
3.1Basic
是HTTP中規(guī)定最早的也是最兼容的方案,遺憾的是也是最不安全的一個方案,因為它以明碼傳送用戶名和密碼。它要求一個UsernamePasswordCredentials實例,可以指定服務器端的訪問空間或采用默認的登錄信息。
3.2 Digest
是在HTTP1.1 中增加的一個方案,雖然不如Basic得到的軟件支持多,但還是有廣泛的使用。Digest方案比Basic方案安全得多,因它根本就不通過網(wǎng)絡傳送實際的密碼,傳送的是利用這個密碼對從服務器傳來的一個隨機數(shù)(nonce)的加密串。
它要求一個UsernamePasswordCredentials實例,可以指定服務器端的訪問空間或采用默認的登錄信息。
3.3 NTLM
這是HttpClient支持的最復雜的認證協(xié)議。它Microsoft設計的一個私有協(xié)議,沒有公開的規(guī)范說明。一開始由于設計的缺陷,NTLM的安全性比 Digest差,后來經(jīng)過一個ServicePack補丁后,安全性則比較Digest高。
NTLM需要一個NTCredentials實例。 注意,由于NTLM不使用訪問空間(realms)的概念,HttpClient利用服務器的域名作訪問空間的名字。還需要注意,提供給 NTCredentials的用戶名,不要用域名的前綴 - 如: "adrian" 是正確的,而 "DOMAIN\adrian" 則是錯的。
NTLM認證的工作機制與basic和digest有很大的差別。這些差別一般由HttpClient處理,但理解這些差別有助避免在使用NTLM認證時出現(xiàn)錯誤。
[1] 從HttpClientAPI的角度來看,NTLM與其它認證方式一樣的工作,差別是需要提供'NTCredentials'實例而不是'UsernamePasswordCredentials'(其實,前者只是擴展了后者)
[2] 對NTLM認證,訪問空間是連接到的機器的域名,這對多域名主機會有一些麻煩。只有HttpClient連接中指定的域名才是認證用的域名。建議將realm設為null以使用默認的設置。
[3] NTLM只是認證了一個連接而不是一請求,所以每當一個新的連接建立就要進行一次認證,且在認證的過程中保持連接是非常重要的。 因此,NTLM不能同時用于代理認證和服務器認證,也不能用于HTTP1.0連接或服務器不支持持久連接(keep-alives)的情況。
關于NTLM認證機制更詳細的研究,可參考http://davenport.sourceforge.net/ntlm.html 。
3.4選擇認證
一些服務器支持多種認證方案。假設一次只能使用一種認證方案,HttpClient必須選擇使用哪種。HttpClient選擇是基于NTLM, Digest, Basic順序的。
在具體情況下,可以更改該順序。可通過參數(shù)'http.auth.scheme-priority'來實現(xiàn),該參數(shù)值應該被存放在一個String類型的List中。選擇優(yōu)先級是按插入順序確定的。
HttpClient client = new HttpClient();
List authPrefs = new ArrayList(2);
authPrefs.add(AuthPolicy.DIGEST);
authPrefs.add(AuthPolicy.BASIC);
// This will exclude the NTLM authentication scheme
client.getParams().setParameter(AuthPolicy.AUTH_SCHEME_PRIORITY, authPrefs);
3.5定制認證方案
HttpClient本身支持basic, digest, and NTLM這三種認證方案。同時,它也提供了加載額外定制的認證方案的功能(通過AuthScheme接口實現(xiàn))。需要使用定制的認證方案,必須實現(xiàn)下面的步驟:
[1]實現(xiàn)AuthScheme接口。
[2]通過AuthPolicy.registerAuthScheme() 注冊定制的AuthScheme。
[3]將定制的AuthScheme加入到AuthPolicy.AUTH_SCHEME_PRIORITY中。
4.示例
4.1Basic authentication
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.UsernamePasswordCredentials;
import org.apache.commons.httpclient.auth.AuthScope;
import org.apache.commons.httpclient.methods.GetMethod;
/**
* A simple example that uses HttpClient to perform a GET using Basic
* Authentication. Can be run standalone without parameters.
*
* You need to have JSSE on your classpath for JDK prior to 1.4
*
* @author Michael Becke
*/
public class BasicAuthenticationExample {
/**
* Constructor for BasicAuthenticatonExample.
*/
public BasicAuthenticationExample() {
super();
}
public static void main(String[] args) throws Exception {
HttpClient client = new HttpClient();
// pass our credentials to HttpClient, they will only be used for
// authenticating to servers with realm "realm" on the host
// "www.verisign.com", to authenticate against
// an arbitrary realm or host change the appropriate argument to null.
client.getState().setCredentials(
new AuthScope("www.verisign.com", 443, "realm"),
new UsernamePasswordCredentials("username", "password")
);
// create a GET method that reads a file over HTTPS, we're assuming
// that this file requires basic authentication using the realm above.
GetMethod get = new GetMethod("https://www.verisign.com/products/index.html");
// Tell the GET method to automatically handle authentication. The
// method will use any appropriate credentials to handle basic
// authentication requests.  Setting this value to false will cause
// any request for authentication to return with a status of 401.
// It will then be up to the client to handle the authentication.
get.setDoAuthentication( true );
try {
// execute the GET
int status = client.executeMethod( get );
// print the status and response
System.out.println(status + "\n" + get.getResponseBodyAsString());
} finally {
// release any connection resources used by the method
get.releaseConnection();
}
}
}
4.2 Alternate authentication
import java.util.ArrayList;
import java.util.List;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.UsernamePasswordCredentials;
import org.apache.commons.httpclient.auth.AuthPolicy;
import org.apache.commons.httpclient.auth.AuthScope;
import org.apache.commons.httpclient.methods.GetMethod;
/**
* <p>A simple example that uses alternate authentication scheme selection
* if several authentication challenges are returned.
* </p>
*
* <p>Per default HttpClient picks the authentication challenge in the following
*  order of preference: NTLM, Digest, Basic. In certain cases it may be desirable to
*  force the use of a weaker authentication scheme.
* </p>
*
* @author Oleg Kalnichevski
*/
public class AlternateAuthenticationExample {
/**
* Constructor for BasicAuthenticatonExample.
*/
public AlternateAuthenticationExample() {
super();
}
public static void main(String[] args) throws Exception {
HttpClient client = new HttpClient();
client.getState().setCredentials(
new AuthScope("myhost", 80, "myrealm"),
new UsernamePasswordCredentials("username", "password"));
// Suppose the site supports several authetication schemes: NTLM and Basic
// Basic authetication is considered inherently insecure. Hence, NTLM authentication
// is used per default
// This is to make HttpClient pick the Basic authentication scheme over NTLM & Digest
List<String> authPrefs = new ArrayList<String>(3);
authPrefs.add(AuthPolicy.BASIC);
authPrefs.add(AuthPolicy.NTLM);
authPrefs.add(AuthPolicy.DIGEST);
client.getParams().setParameter(AuthPolicy.AUTH_SCHEME_PRIORITY, authPrefs);
GetMethod httpget = new GetMethod("http://myhost/protected/auth-required.html");
try {
int status = client.executeMethod(httpget);
// print the status and response
System.out.println(status);
System.out.println(httpget.getStatusLine());
System.out.println(httpget.getResponseBodyAsString());
} finally {
// release any connection resources used by the method
httpget.releaseConnection();
}
}
}
4.3 Custom authentication
import java.util.ArrayList;
import java.util.Collection;
import org.apache.commons.httpclient.Credentials;
import org.apache.commons.httpclient.HttpMethod;
import org.apache.commons.httpclient.auth.AuthPolicy;
import org.apache.commons.httpclient.auth.AuthScheme;
import org.apache.commons.httpclient.auth.AuthenticationException;
import org.apache.commons.httpclient.auth.MalformedChallengeException;
import org.apache.commons.httpclient.params.DefaultHttpParams;
import org.apache.commons.httpclient.params.HttpParams;
/**
* A simple custom AuthScheme example.  The included auth scheme is meant
* for demonstration purposes only.  It does not actually implement a usable
* authentication method.
*/
public class CustomAuthenticationExample {
@SuppressWarnings("unchecked")
public static void main(String[] args) {
// register the auth scheme
AuthPolicy.registerAuthScheme(SecretAuthScheme.NAME, SecretAuthScheme.class);
// include the scheme in the AuthPolicy.AUTH_SCHEME_PRIORITY preference,
// this can be done on a per-client or per-method basis but we'll do it
// globally for this example
HttpParams params = DefaultHttpParams.getDefaultParams();
ArrayList<String> schemes = new ArrayList<String>();
schemes.add(SecretAuthScheme.NAME);
schemes.addAll( (Collection) params.getParameter(AuthPolicy.AUTH_SCHEME_PRIORITY));
params.setParameter(AuthPolicy.AUTH_SCHEME_PRIORITY, schemes);
// now that our scheme has been registered we can execute methods against
// servers that require "Secret" authentication...
}
/**
* A custom auth scheme that just uses "Open Sesame" as the authentication
* string.
*/
private class SecretAuthScheme implements AuthScheme {
public static final String NAME = "Secret";
public SecretAuthScheme() {
// All auth schemes must have a no arg constructor.
}
public String authenticate(Credentials credentials, HttpMethod method)
throws AuthenticationException {
return "Open Sesame";
}
public String authenticate(Credentials credentials, String method,
String uri) throws AuthenticationException {
return "Open Sesame";
}
public String getID() {
return NAME;
}
public String getParameter(String name) {
// this scheme does not use parameters, see RFC2617Scheme for an example
return null;
}
public String getRealm() {
// this scheme does not use realms
return null;
}
public String getSchemeName() {
return NAME;
}
public boolean isConnectionBased() {
return false;
}
public void processChallenge(String challenge)
throws MalformedChallengeException {
// Nothing to do here, this is not a challenge based
// auth scheme.  See NTLMScheme for a good example.
}
public boolean isComplete() {
// again we're not a challenge based scheme so this is always true
return true;
}
}
}
4.4 Interactive authentication
import java.io.BufferedReader;
import java.io.IOException;
import java.io.InputStreamReader;
import org.apache.commons.httpclient.Credentials;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.NTCredentials;
import org.apache.commons.httpclient.UsernamePasswordCredentials;
import org.apache.commons.httpclient.auth.AuthScheme;
import org.apache.commons.httpclient.auth.CredentialsNotAvailableException;
import org.apache.commons.httpclient.auth.CredentialsProvider;
import org.apache.commons.httpclient.auth.NTLMScheme;
import org.apache.commons.httpclient.auth.RFC2617Scheme;
import org.apache.commons.httpclient.methods.GetMethod;
/**
* A simple example that uses HttpClient to perform interactive
* authentication.
*
* @author Oleg Kalnichevski
*/
public class InteractiveAuthenticationExample {
/**
* Constructor for InteractiveAuthenticationExample.
*/
public InteractiveAuthenticationExample() {
super();
}
public static void main(String[] args) throws Exception {
InteractiveAuthenticationExample demo = new InteractiveAuthenticationExample();
demo.doDemo();
}
private void doDemo() throws IOException {
HttpClient client = new HttpClient();
client.getParams().setParameter(
CredentialsProvider.PROVIDER, new ConsoleAuthPrompter());
GetMethod httpget = new GetMethod("http://target-host/requires-auth.html");
httpget.setDoAuthentication(true);
try {
// execute the GET
int status = client.executeMethod(httpget);
// print the status and response
System.out.println(status);
System.out.println(httpget.getStatusLine().toString());
System.out.println(httpget.getResponseBodyAsString());
} finally {
// release any connection resources used by the method
httpget.releaseConnection();
}
}
public class ConsoleAuthPrompter implements CredentialsProvider {
private BufferedReader in = null;
public ConsoleAuthPrompter() {
super();
this.in = new BufferedReader(new InputStreamReader(System.in));
}
private String readConsole() throws IOException {
return this.in.readLine();
}
public Credentials getCredentials(
final AuthScheme authscheme,
final String host,
int port,
boolean proxy)
throws CredentialsNotAvailableException
{
if (authscheme == null) {
return null;
}
try{
if (authscheme instanceof NTLMScheme) {
System.out.println(host + ":" + port + " requires Windows authentication");
System.out.print("Enter domain: ");
String domain = readConsole();
System.out.print("Enter username: ");
String user = readConsole();
System.out.print("Enter password: ");
String password = readConsole();
return new NTCredentials(user, password, host, domain);
} else
if (authscheme instanceof RFC2617Scheme) {
System.out.println(host + ":" + port + " requires authentication with the realm '"
+ authscheme.getRealm() + "'");
System.out.print("Enter username: ");
String user = readConsole();
System.out.print("Enter password: ");
String password = readConsole();
return new UsernamePasswordCredentials(user, password);
} else {
throw new CredentialsNotAvailableException("Unsupported authentication scheme: " +
authscheme.getSchemeName());
}
} catch (IOException e) {
throw new CredentialsNotAvailableException(e.getMessage(), e);
}
}
}
}
本站僅提供存儲服務,所有內(nèi)容均由用戶發(fā)布,如發(fā)現(xiàn)有害或侵權內(nèi)容,請點擊舉報
打開APP,閱讀全文并永久保存 查看更多類似文章
猜你喜歡
類似文章
HttpClient中使用代理連接
HttpClient登錄人人網(wǎng)
SSL雙向認證Java實現(xiàn) Tomcat篇 - 螢火蟲 - ITeye技術網(wǎng)站
[總結]radius認證在H3C防火墻、交換機、無線AP上的應用
HttpClient的3種超時
使用HTTP Client構建Web客戶端
更多類似文章 >>
生活服務
分享 收藏 導長圖 關注 下載文章
綁定賬號成功
后續(xù)可登錄賬號暢享VIP特權!
如果VIP功能使用有故障,
可點擊這里聯(lián)系客服!

聯(lián)系客服