Java 从外部应用程序登录到内容导航器

Java 从外部应用程序登录到内容导航器,java,http,ibm-content-navigator,Java,Http,Ibm Content Navigator,我试图从Java应用程序(FileNetP8中的事件操作处理程序)访问Content Navigator上的PluginService。应用程序使用JAXRS登录服务从Content Navigator服务器接收security\u令牌。但是,如果我尝试调用PluginService,我会得到一个响应,即我的登录已过期 我能够获得安全令牌,如以下代码块所述: URL logonUrl = new URL("http://icn-host:9081/jaxrs/logon" + "?use

我试图从Java应用程序(FileNetP8中的事件操作处理程序)访问Content Navigator上的PluginService。应用程序使用JAXRS登录服务从Content Navigator服务器接收
security\u令牌。但是,如果我尝试调用PluginService,我会得到一个响应,即我的登录已过期

我能够获得安全令牌,如以下代码块所述:

URL logonUrl = new URL("http://icn-host:9081/jaxrs/logon"
    + "?userid=user"
    + "&password=password"
    + "&desktop=admin"
    + "&contextPath=%2Fnavigator");
HttpURLConnection logonConnection = (HttpURLConnection)logonUrl.openConnection();
logonConnection.setRequestMethod("POST");
logonConnection.setRequestProperty("Content-Type",
    "application/x-www-form-urlencoded");
logonConnection.setDoOutput(true);
InputStream logonResponse = logonConnection.getInputStream();
String responseText = IOUtils.toString(logonResponse, "UTF-8")
    .replaceFirst("^\\{}&&", "");
JSONObject responseJson = JSONObject.parse(responseText);
return (String)responseJson.get("security_token");
但当我尝试发出另一个请求时,我得到了一个错误响应:

URL requestUrl = new URL("http://icn-host:9081/plugin.do"
    + "?plugin=myPlugin&action=myPluginService&myRequestProps=foobar");
HttpURLConnection requestConnection =
    (HttpURLConnection)requestUrl.openConnection();
requestConnection.setRequestMethod("GET");
String securityToken = getSecurityToken(); // calls above code
requestConnection.setRequestProperty("security_token", securityToken);
equestConnection.setDoOutput(true);
InputStream responseStream = requestConnection.getInputStream();
String responseText = IOUtils.toString(responseStream, "UTF-8")
    .replaceFirst("^\\{}&&", "");
log.info("response was: " + responseText);
{
  "messagesEncoded":true,
  "errors": [
    {
      "adminResponse":null,
      "moreInformation":null,
      "explanation":"Your session expired because of inactivity.",
      "number":"1003",
      "userResponse":"Log in again.",
      "text":"Your session expired."
    }
  ]
}
我总是得到以下回应:

URL requestUrl = new URL("http://icn-host:9081/plugin.do"
    + "?plugin=myPlugin&action=myPluginService&myRequestProps=foobar");
HttpURLConnection requestConnection =
    (HttpURLConnection)requestUrl.openConnection();
requestConnection.setRequestMethod("GET");
String securityToken = getSecurityToken(); // calls above code
requestConnection.setRequestProperty("security_token", securityToken);
equestConnection.setDoOutput(true);
InputStream responseStream = requestConnection.getInputStream();
String responseText = IOUtils.toString(responseStream, "UTF-8")
    .replaceFirst("^\\{}&&", "");
log.info("response was: " + responseText);
{
  "messagesEncoded":true,
  "errors": [
    {
      "adminResponse":null,
      "moreInformation":null,
      "explanation":"Your session expired because of inactivity.",
      "number":"1003",
      "userResponse":"Log in again.",
      "text":"Your session expired."
    }
  ]
}
我也尝试过设置cookies,但没有成功

java.net.CookieManager cookieManager = new java.net.CookieManager();
Map<String, List<String>> headerFields = logonConnection.getHeaderFields();
List<String> cookiesHeader = headerFields.get("Set-Cookie");
if (cookiesHeader != null) {
  for (String cookie : cookiesHeader) {
    cookieManager.getCookieStore().add(null, HttpCookie.parse(cookie).get(0));
  }
}

// ...

StringBuilder cookieHeader = new StringBuilder();
List<HttpCookie> cookies = cookieManager.getCookieStore().getCookies();

for (int i = 0; i < cookies.size(); i++) {
  if (i > 0) {
    cookieHeader.append(";");
  }

  HttpCookie cookie = cookies.get(i);
  log.info("Cookie " + i + ": " + cookie.toString());
  cookieHeader.append(cookie.toString());
}

requestConnection.setRequestProperty("Cookie", cookieHeader.toString());

几个月前,我在一个客户机上遇到了类似的挑战,我必须自动安装插件并应用配置以实现CI目的

我发现,在登录后第一次调用api时获得桌面是会话“有效”的关键

因此,首先是jaxrs/logon,然后是jaxrs/getDesktop,然后是服务调用

有一点旁注:如果您计划稍后使用容器管理的身份验证,那么过程将有所不同。jaxrs/logon将不起作用,相反,jaxrs/getDesktop将提供安全令牌

不过有一点需要注意的是:如果有一个共享库,您可以从事件操作中使用它作为ICN服务,这不是一个更好的解决方案吗

使用共享库(参见Ivo的答案)绝对是最好的方法,调用
jaxrs/getDesktop
对我来说不起作用。相反,我只是使用Maven Assembly插件来包含较新版本的
org.apache.httpcomponents
依赖项,并使用HttpClient调用请求

我的最终代码如下所示:

CloseableHttpClient httpClient = HttpClients.custom()
  .setDefaultCookieStore(cookieStore)
  .setDefaultRequestConfig(requestConfig)
  .build();
HttpUriRequest logonRequest = RequestBuilder.post()
  .setUri("http://icn-host:9081/navigator/jarxrs/logon")
  .addParameter("desktop", "admin")
  .addParameter("contextPath", "/navigator")
  .addParameter("userid", "icnadmin")
  .addParameter("password", "password")
  .build();
CloseableHttpResponse logonResponse = httpClient.execute(logonRequest);
HttpEntity responseEntity = logonResponse.getEntity();
String responseText = EntityUtils.toString(responseEntity)
  .replaceFirst("^\\{}&&", "");
JSONObject responseJson = JSONObject.parse(responseText);
String securityToken = (String) responseJson.get("security_token");
HttpUriRequest request = RequestBuilder.get()
  .setUri("http://icn-host:9081/navigator/plugin.do")
  .addParameter("plugin", "myPlugin")
  .addParameter("action", "myPluginService")
  .addParameter("myRequestProps", "foobar")
  .addHeader("security_token", securityToken)
  .build();
HttpClientContext context = HttpClientContext.create();
CookieStore cookieStore = new BasicCookieStore();
context.setCookieStore(cookieStore);
CloseableHttpResponse response = httpClient.execute(request, context);

Content Navigator和FileNet安装在单独的WebSphere实例上。他们之间有可能有一个共享库吗?当然有。将允许您将utility.jar链接到FilenetEngine.ear和Navigator.ear的类加载器。