策略设计模式

3
我有一个支持URLConnection的AuthenticationHandler接口,但现在我正在使用Apache HTTP Client。我希望为两种连接类型(URLConnection和HTTP Client)都拥有通用的身份验证接口,但它们具有不同的参数并且功能不同。
我该如何设计这个接口?是否可以使用策略模式?
import java.net.URLConnection;
import java.util.List;

public interface AuthenticationHandler {

/**
 * this needs to be called by everyone that needs direct access to a link which may have
 * security access rules.
 */
void trustAll();

/**
 *
 * @param URLconnection where you set access state parameters or anything access related
 * @param slice where you could get access config
 * @param initializeSlice is true if you want the proxy to hibernate initialize all hibernated objects
 * @return
 * @throws ConnectionException
 */
void authenticate(URLConnection conn) throws ConnectionException;

List<String> getSingleCookie();

void setSingleCookie(List<String> singleCookies);

CookieManager getCookieManager();

void setCookieManager(CookieManager cookieManager);

boolean isKeepGeneratedCookie();

void setKeepGeneratedCookie(boolean keepGeneratedCookie);

}

我的主要关注点是:
void authenticate(URLConnection conn) throws ConnectionException;

原本代码中使用的是 URLConnection conn,现在我们还想添加对 HTTP 客户端的支持。

2个回答

6
对于策略模式,您应该使用类似以下的代码:
public class AuthenticationHandlerImpl implements AuthenticationHandler {

    private Authenticator authenticator;

    void authenticate() throws ConnectionException {
        authenticator.authenticate();
    };

    public void setAuthenticator(final Authenticator  authenticator){
        this.authenticator = authenticator;
    }

}

interface Authenticator {
    void authenticate();
    void setLogin(String login);
    void setPassword(String password);
}

class URLAuthenticator implements Authenticator {
    public void authenticate() {
        //use URLConnection
    };
}

class HTTPClientAuthenticator implements Authenticator {
    public void authenticate() {
        //use HTTPClient
    };
}

使用示例:

AuthenticationHandler handler = new AuthenticationHandlerImpl();
Authenticator authenticator = new HTTPClientAuthenticator();
//or
//Authenticator authenticator = new URLAuthenticator();
authenticator.setLogin(...);
authenticator.setPassword(...);
handler.setAuthenticator(authenticator)

handler.authenticate();

创建 Authenticator 可以使用 FactoryMethod 设计模式:
class AuthenticatorFactory {

    private AuthenticatorFactory(){}

    //type of param may be enum or other
    public static Authenticator createAuthenticator(... param) {
        if (param == ...) {
            return new URLAuthenticator();
        } else if (param == ...) {
            return new HTTPClientAuthenticator();
        }
    }
}

1
不错。将AuthenticatorFactory更改为AuthenticatorContext,并在构造函数中预先创建所有可能的实现。提供getter方法以返回特定策略。 - Ravindra babu
在这里使用AuthenticationHandlerImpl有什么好处?为什么我们不能直接在使用示例中调用authenticator.authenticate()? - gonephishing

0

你可以进行重载

void authenticate(HTTPClient client) throws ConnectionException;

或者将输入/输出流作为参数传递,或者使用类似于doLogin的面向任务的回调,并传递类似凭据的内容。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接