简体   繁体   English

具有NTLM到SharePoint的CXF SOAP客户端

[英]CXF SOAP Client with NTLM to SharePoint

I am writing a SOAP client using CXF Framework (version: 2.7.8) for SharePoint 2007. I have followed the online documentation for adding NTLM support here . 我正在使用SharePoint 2007的CXF Framework(版本:2.7.8)编写SOAP客户端。我已经按照在线文档的说明在此处添加NTLM支持。 I have the client working and tracing the HTTP session shows that NTLM credentials are being sent, however, I am still receiving a 401 Unauthorized response. 我有客户端在工作,并且跟踪HTTP会话显示正在发送NTLM凭据,但是,我仍然收到401未经授权的响应。

Code: 码:

Lists listService = new Lists();
ListsSoap port = listService.getListsSoap();

BindingProvider bp = (BindingProvider) port;
bp.getRequestContext().put("use.async.http.conduit", Boolean.TRUE);
Credentials creds = new NTCredentials(USER, PASS, "", DOMAIN);
bp.getRequestContext().put(Credentials.class.getName(), creds);

Client client = ClientProxy.getClient(proxy);
HTTPConduit http = (HTTPConduit) client.getConduit();
HTTPClientPolicy httpClientPolicy = new HTTPClientPolicy();
httpClientPolicy.setConnectionTimeout(36000);
httpClientPolicy.setAllowChunking(false);
httpClientPolicy.setAutoRedirect(true);
http.setClient(httpClientPolicy);

// Build request and execute

Interestingly, I wrote a similar client using HTTP PUT for WebDAV to upload documents using Apache HTTPClient library, and was able to successfully authenticate using NTLM. 有趣的是,我使用HTTP PUT为WebDAV编写了一个类似的客户端,以使用Apache HTTPClient库上载文档,并且能够使用NTLM成功进行身份验证。 Also, I was able to use SOAPUI to invoke the same Lists web service I am trying to build the Java client for and it successfully authenticated using NTLM as well. 另外,我能够使用SOAPUI调用我要为其构建Java客户端的相同的Lists Web服务,并且它也可以使用NTLM成功进行身份验证。

I'm assuming the implementation of NTLM is different between CXF and HTTPClient. 我假设CXF和HTTPClient之间NTLM的实现是不同的。 Any thoughts on what is wrong with my CXF implementation? 关于我的CXF实施有什么问题的任何想法? Or how I can get it to mirror the HTTPClient implementation? 或者如何获取它以镜像HTTPClient实现?

Please try this way! 请尝试这种方式!

HTTPConduit http = (HTTPConduit)client.getConduit();
AsyncHTTPConduit conduit = (AsyncHTTPConduit)http;
DefaultHttpAsyncClient defaultHttpAsyncClient;
defaultHttpAsyncClient = conduit.getHttpAsyncClient();
defaultHttpAsyncClient.getCredentialsProvider().setCredentials( AuthScope.ANY,
 new NTCredentials( USER,PWD, "", DOM ) );
conduit.getClient().setAllowChunking( false );
conduit.getClient().setAutoRedirect( true );

@lamarvannoy, I also got this error. @lamarvannoy,我也收到此错误。 But I found another way. 但是我找到了另一种方式。 You don't need to cast HTTPConduit to AsyncHTTPConduit. 您无需将HTTPConduit强制转换为AsyncHTTPConduit。 Let's try this stuff: 让我们尝试一下这些东西:

public class Test {

    static final String kuser = "yourDomain\\username";
    static final String kpass = "yourPassword";

    static class MyAuthenticator extends Authenticator {
        public PasswordAuthentication getPasswordAuthentication() {
            System.err.println("Feeding username and password for " + getRequestingScheme());
            return (new PasswordAuthentication(kuser, kpass.toCharArray()));
        }
    }

    public static void main(String[] args) throws Exception {
        Authenticator.setDefault(new MyAuthenticator());
        Lists listService = new Lists();
        ListsSoap port = listService.getListsSoap();

        Client client = ClientProxy.getClient(port);
        HTTPConduit http = (HTTPConduit) client.getConduit();
        HTTPClientPolicy httpClientPolicy = new HTTPClientPolicy();
        httpClientPolicy.setConnectionTimeout(36000);
        httpClientPolicy.setAllowChunking(false);
        http.setClient(httpClientPolicy);

        String listName = "S030_main";
        String rowLimit = "150";
        ArrayList<String> listColumnNames = new ArrayList<String>();
        listColumnNames.add("Title");     
        Test.displaySharePointList(port, listName, listColumnNames, rowLimit);       
    }
}

You may find the implementation of displaySharePointList() method in this post: http://davidsit.wordpress.com/2010/02/10/reading-a-sharepoint-list-with-java-tutorial/ 您可以在这篇文章中找到displaySharePointList()方法的实现: http : //davidsit.wordpress.com/2010/02/10/reading-a-sharepoint-list-with-java-tutorial/

I hope this will safe your and others time. 我希望这可以确保您和他人的时间安全。

This works for me: 这对我有用:

Client client = ClientProxy.getClient(port);
AsyncHTTPConduit conduit = (AsyncHTTPConduit)client.getConduit();
AuthorizationPolicy authorization = conduit.getAuthorization();
authorization.setUserName("domain\\username");
authorization.setPassword("password");

Actually this works for both NTLM and Basic 实际上,这对于NTLM和Basic均适用

This is what I had to do to get mine to work: 这是我必须要做的事情:

// Include a version of WSDL in class path, make URL point to that
URL url = MyClient.class.getResource("previouslydownloaded.wsdl");

MyCxFService ws = new MyCxFService(url);
MyCxfClient client = ws.getMyCxfServicePort(); 

BindingProvider prov = ((BindingProvider) client);
Binding binding = prov.getBinding();

// Set Username and Password
if ((this.user != null) && (!this.user.isEmpty())) {
  prov.getRequestContext().put(BindingProvider.USERNAME_PROPERTY, this.user);
  prov.getRequestContext().put(BindingProvider.PASSWORD_PROPERTY, this.passwd);
}

// Get address from config file to get rid error caused by using wsdl file:
// Caused by: java.lang.NullPointerException
//   at org.apache.cxf.transport.http.URLConnectionHTTPConduit.createConnection(URLConnectionHTTPConduit.java:104)
prov.getRequestContext().put(BindingProvider.ENDPOINT_ADDRESS_PROPERTY, this.portAddress);

Hope that might help someone. 希望对您有所帮助。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM