`
jianchen
  • 浏览: 334116 次
  • 性别: Icon_minigender_1
  • 来自: 杭州
社区版块
存档分类
最新评论

调用BIEE提供的web service

 
阅读更多

门户项目中准备用web service获取现有的制作好的报表进行展示。遂去研究了下,研究的过程也是满纠结的,总算根据多方资料,将demo跑通了。

本文参考了网上的一些资料,做一下总结而已。讲解下如何配置,成功的获取到相关报表。

 

biee的web service的介绍我就不说了了,官方文档如下:
http://download.oracle.com/docs/cd/E21764_01/bi.1111/e16364/soa_overview.htm

提供的服务如下:
http://download.oracle.com/docs/cd/E12096_01/books/AnyWebServ/AnyWebServTOC.html


使用axis生成WEB service的客户端代码:
步骤参考:
http://gerardnico.com/wiki/ide/eclipse/eclipse_how_to_consume_a_webservice_with_wtp
需要指定包名为:com.siebel.analytics.web.soap.v5

客户端代码生成后,在eclipse下由于下载了插件依赖包都是有的,所以可以直接写一个java程序去测试下是否调用web service成功。
如果用maven生成工程,或者最终发布的话,需要在pom。xml中增加如下的依赖配置:

        <dependency>
            <groupId>org.apache.axis</groupId>
            <artifactId>axis</artifactId>
            <version>1.4</version>
        </dependency>
        <dependency>
            <groupId>javax.xml</groupId>
            <artifactId>jaxrpc</artifactId>
            <version>1.1</version>
        </dependency>
        <dependency>
            <groupId>commons-discovery</groupId>
            <artifactId>commons-discovery</artifactId>
            <version>0.2</version>
        </dependency>
        <dependency>
            <groupId>wsdl4j</groupId>
            <artifactId>wsdl4j</artifactId>
            <version>1.6.2</version>
        </dependency>
        <dependency>
            <groupId>org.apache.httpcomponents</groupId>
            <artifactId>httpclient</artifactId>
            <version>4.1-beta1</version>
        </dependency>

 

测试代码如下:

public class TestReadCatalog {
    public static void main(String[] args) {
        String sessionID = "";
        SAWSessionServiceSoapProxy myPort = new SAWSessionServiceSoapProxy();
        try {
            sessionID = myPort.logon("jianchen", "jianchen");
        } catch (RemoteException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        //测试获取目录结构
        WebCatalogServiceSoapProxy catalogService = new WebCatalogServiceSoapProxy();
        try {
            CatalogObject catalogItems = catalogService.readObject("/shared", false, sessionID);
            System.out.println(catalogItems.getItemInfo().getPath());
            ItemInfo[] items = catalogService.getSubItems("/shared", "*", false, null, sessionID);
            for (ItemInfo item : items) {
                System.out.println(item.getCaption());
            }
        } catch (RemoteException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }
}

 

这里我用的登录账号是:rpd的账号。登录成功后会返回一个sessionID。跟服务器的交互必须要有sessionID作为参数。
执行后,的确能够获取到返回的catalog目录,输出目录名称。

最关键的来了,就是如何把biee中做好的报表展示到web页面上呢。biee提供了HtmlViewService,支持对biee report进行访问。
测试代码如下:

public class TestReadReport {

    /**
     * @param args
     */
    public static void main(String[] args) {
        String sessionID = "";
        SAWSessionParameters sessionparams = new SAWSessionParameters();
        SAWSessionServiceSoapProxy myPort = new SAWSessionServiceSoapProxy();
        try {
            sessionID = myPort.logon("jianchen", "jianchen");
        } catch (RemoteException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }

        HtmlViewServiceSoapProxy viewService = new HtmlViewServiceSoapProxy();
        ReportRef reportRef = new ReportRef();
        reportRef.setReportPath("/shared/");

        StartPageParams startPageParams = new StartPageParams();
        startPageParams.setIdsPrefix("beijixing"+Math.round(Math.random()*1000000));
        startPageParams.setDontUseHttpCookies(false);
        try {
            String pageID = viewService.startPage(startPageParams, sessionID);

            viewService.addReportToPage(pageID, "beijixing", reportRef, null, null, null, sessionID);

            StringBuffer reportHTML = new StringBuffer();
           /* reportHTML.append(viewService.getHeadersHtml(pageID, sessionID));
            reportHTML.append(viewService.getHtmlForReport(pageID, "beijixing", sessionID));*/
            reportHTML.append(viewService.getHtmlForPageWithOneReport("beijixing", reportRef, null, null, null, null, sessionID));
            System.out.println(reportHTML.toString());
        } catch (RemoteException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    }
}

 测试是能够获取到html代码的。但是在页面上展示这段代码时,只会出现一个“等待”,而没有真正的获取报表内容。
分析页面源代码:发现页面里的js以及css等资源的路径都是:“missing_xxx.css”之类的。说明获取的那些资源没有加载到。
还有一个很关键的点,在某篇老外的博客上提到:

写道
SAWLocale and SAWSessionParameters are quite important for the OBIEE report to be displayed. Many have tried and have seen only the rotating clock instead of the report. We too went through the same problem and realized that the OBIEE report javascript file paths are dependent on the Locale and the User-Agent.

 所以在登录服务器前,需要有如下代码段:

    SAWLocale sawlocale = new SAWLocale();
    sawlocale.setLanguage(request.getLocale().getLanguage());
    sawlocale.setCountry(request.getLocale().getCountry());

    SAWSessionParameters sessionparams = new SAWSessionParameters();
    sessionparams.setUserAgent(request.getHeader("User-Agent"));
    sessionparams.setLocale(sawlocale);
    sessionparams.setAsyncLogon(false);

 后仔细阅读文档,内容如下:

写道
To embed a report with active drilldown links, the HtmlViewService service allows the Web browser to issue callback requests from embedded reports to the Oracle BI Web Services server. Although it is possible to route requests directly to the Oracle BI Web Services server, in many cases it is preferable to route requests through the Presentation Services that originally serviced the third-party page. Also, in situations where Oracle BI Web Services and the third-party Web server do not belong to the same Domain Name Service (DNS) domain, users may get JavaScript errors related to browser security constraints for cross-domain scripting.

To avoid these issues, use the setBridge() method to modify callback URLs to point to the third-party Web server. Be aware that a Web component executed by the third-party Web server to re-route requests to Oracle BI Web Services is not provided. This function would need to be fulfilled by the third-party application. For more information about the setBridge() method, read setBridge() Method.

 就是说这些静态资源需要用桥接的方式向真正的服务器发起请求,返回给浏览器。

 桥接的实现,可以利用servlet,该servlet里要干的事情如下:

 
Read the RedirectURL argument of the request which will contain the absolute path to the OBIEE resources.
Make a URLConnection to the URL and read the content.
Write to the output stream.

当时为了立即看到效果,该bridge的代码我是借用了别人的(代码有点bug,比如连接未关闭,不能复用的bug),等正式开发用的时候可以考虑重新改写下,优化下性能。还是贴出来吧,方便下大众。

 

public class MyBridge extends HttpServlet {
	private static final long serialVersionUID = 1L;
	/**
	 * Default constructor.
	 */
	public MyBridge() {
		// TODO Auto-generated constructor stub
	}
	/**
	 * @see HttpServlet#doGet(HttpServletRequest request, HttpServletResponse
	 *      response)
	 */
	@SuppressWarnings("unchecked")
	protected void doGet(HttpServletRequest request,
			HttpServletResponse response) throws ServletException, IOException {
		String relatedtUrl = request.getParameter("RedirectURL");
		relatedtUrl = relatedtUrl.replaceAll("NoAuthGo", "Go");
		StringBuffer url = new StringBuffer("").append(relatedtUrl);
		System.out.println("relatedtUrl>>>>>*****>>>>>>>>>>" + relatedtUrl);

		List<NameValuePair> nvps = new ArrayList<NameValuePair>();
		Map parameterMap = request.getParameterMap();
		for (Iterator iterator = parameterMap.keySet().iterator(); iterator
				.hasNext();) {
			String parameterName = (String) iterator.next();
			String[] parameterValues = (String[]) parameterMap
					.get(parameterName);
			if (parameterValues != null && parameterValues.length > 0) {
				if (parameterName.equals("RedirectURL")) {
					continue;
				}

				for (int i = 0; i < parameterValues.length; i++) {
					NameValuePair pair = new BasicNameValuePair(parameterName,
							parameterValues[i]);
					nvps.add(pair);
				}
			}
		}
		HttpClient client = new DefaultHttpClient();
		if (!url.toString().endsWith(".js") && !url.toString().endsWith(".css")
				&& !url.toString().endsWith(".png") && !url.toString().endsWith(".gif")) {
			List<NameValuePair> tmp = new ArrayList<NameValuePair>();
			NameValuePair pair = new BasicNameValuePair("NQUser", "jianchen");
			NameValuePair pair1 = new BasicNameValuePair("NQPassword", "jianchen");
			tmp.add(pair);
			tmp.add(pair1);
			HttpPost lpost = new HttpPost(url.toString());
			lpost.setEntity(new UrlEncodedFormEntity(tmp, "GBK"));
			HttpResponse lresp = client.execute(lpost);
			System.out.println("登陆结果:"+lresp.getStatusLine().getStatusCode());
            lpost.abort();
		}
		if(url.toString().indexOf("?Go")<0 || url.toString().indexOf("?DocPart")>0){
			HttpPost post = new HttpPost(url.toString());
			post.setEntity(new UrlEncodedFormEntity(nvps,"GBK"));
			post.addHeader("Content-Type", "binary/data");
			post.addHeader("User-Agent", request.getHeader("USER-AGENT"));
			HttpResponse resp = client.execute(post);
			HttpEntity entity = resp.getEntity();
			InputStream in = entity.getContent();
			if(url.toString().indexOf("?DocPart")>0){
				FileOutputStream fout=new FileOutputStream("e:\\aaa.jpg");
				byte buffer1[] = new byte[1024 * 128];
				int k = 0;
				while ((k = in.read(buffer1)) != -1) {
					fout.write(buffer1, 0, k);
				}
				fout.flush();
				fout.close();
			}
			ServletOutputStream out = response.getOutputStream();
			byte buffer1[] = new byte[1024 * 128];
			int k = 0;
			while ((k = in.read(buffer1)) != -1) {
				out.write(buffer1, 0, k);
			}
			in.close();
			out.close();
		} else {
			HttpPost post = new HttpPost(url.toString());
			post.setEntity(new UrlEncodedFormEntity(nvps,"GBK"));
			post.addHeader("Content-Type", "binary/data");
			post.addHeader("User-Agent", request.getHeader("USER-AGENT"));
			HttpResponse resp = client.execute(post);
			HttpEntity entity = resp.getEntity();
			InputStream in = entity.getContent();
			InputStreamReader isr = new InputStreamReader(in);
			BufferedReader br = new BufferedReader(isr);
			StringBuffer sb = new StringBuffer();
			String r = br.readLine();
			sb.append(r);
			while (r != null) {
				r = br.readLine();
				sb.append(r);
			}
			String html = sb.toString();//TODO 本地
			InputStream sin = new ByteArrayInputStream(html.getBytes());
			ServletOutputStream out = response.getOutputStream();
			byte buffer1[] = new byte[1024 * 128];
			int k = 0;
			while ((k = sin.read(buffer1)) != -1) {
				out.write(buffer1, 0, k);
			}
			sin.close();
			out.close();
            post.abort();
		}

       
	}

	/**
	 * @see HttpServlet#doPost(HttpServletRequest request, HttpServletResponse
	 *      response)
	 */
	protected void doPost(HttpServletRequest request,
			HttpServletResponse response) throws ServletException, IOException {
		doGet(request, response);
	}

}

 

 

web.xml中配置servlet如下:

         <servlet>
		<description>
		</description>
		<display-name>MyBridge</display-name>
		<servlet-name>MyBridge</servlet-name>
		<servlet-class>com.taobao.service.kunshuo.webservice.MyBridge</servlet-class>
	</servlet>
	<servlet>
		<display-name>Apache-Axis Servlet</display-name>
		<servlet-name>AxisServlet</servlet-name>
		<servlet-class>org.apache.axis.transport.http.AxisServlet</servlet-class>
	</servlet>
	<servlet>
		<display-name>Axis Admin Servlet</display-name>
		<servlet-name>AdminServlet</servlet-name>
		<servlet-class>org.apache.axis.transport.http.AdminServlet</servlet-class>
		<load-on-startup>100</load-on-startup>
	</servlet>

    <servlet-mapping>
		<servlet-name>MyBridge</servlet-name>
		<url-pattern>/MyBridge</url-pattern>
	</servlet-mapping>
	<servlet-mapping>
		<servlet-name>AxisServlet</servlet-name>
		<url-pattern>/servlet/AxisServlet</url-pattern>
	</servlet-mapping>
	<servlet-mapping>
		<servlet-name>AxisServlet</servlet-name>
		<url-pattern>*.jws</url-pattern>
	</servlet-mapping>
	<servlet-mapping>
		<servlet-name>AxisServlet</servlet-name>
		<url-pattern>/services/*</url-pattern>
	</servlet-mapping>
	<servlet-mapping>
		<servlet-name>AdminServlet</servlet-name>
		<url-pattern>/servlet/AdminServlet</url-pattern>
	</servlet-mapping>

 

至此,将获取到的报表html增加到要展示的页面里,比如jsp,就可以直接展示报表了。

后面的获取xml结果,自己可以进行处理展示结果。还有待后续研究。

 

 

有几个开发同学跟我要源代码,都是通过邮箱发送的,这里我把我当时的demo发上来作为附件吧。

可以在附件中进行下载

  • 大小: 262 Bytes
  • 大小: 402 Bytes
  • 大小: 485.8 KB
分享到:
评论
17 楼 zy_mensheng 2018-03-14  
请问一下 怎么 js没有解析啊  还是钟表图..
16 楼 yanchangjun8102 2014-06-09  
楼主你好,我也最近在研究biee的webservice这块,按照你的配置桥接后报表始终显示不错了,一直就是一个时钟图片在转动,我用的是biee11.1.7的版本,看到网上说biee10可行,不知道是版本问题还是其他问题,楼主能否告知一下,非常感谢,如果有demo也麻烦您发个我一份,我邮箱1214103643@qq.com
15 楼 sacredon 2013-09-06  
  不错,楼主我是看着你的这篇文章写代码调用的BIEE的Web Service,完成了第一个Demo。
  另外补充一点,HtmlViewServiceSoap类提供setBridge方法。需要加在String pageID = viewService.startPage(startPageParams, sessionID)下面。不加的话还是会不出来。
14 楼 jianchen 2013-09-05  
xsxtchenz 写道
博主 你好,对于桥连接这块我不是很明白,可否发一份你怎么使用桥连接的代码给我?
634294836@qq.com

文章最后就有下载链接。
13 楼 xsxtchenz 2013-09-04  
博主 你好,对于桥连接这块我不是很明白,可否发一份你怎么使用桥连接的代码给我?
634294836@qq.com
12 楼 usermomo 2013-08-07  
大哥,
小弟最近也要用java写一个调用biee接口的实例,搞得很头疼。看到大哥这片文章感觉很不错。只是附件下载不了。可以麻烦发我一份吗?邮箱 754350704@qq.com
感激不尽呀
11 楼 jianchen 2013-05-12  
李仕亮 写道
我最经在搞Java调用BIEE报表,遇到点麻烦,看到大哥你的博客,是我需要的希望,你尽快发我一份研究下,谢谢。hnhhshun@126.com

已经发送邮件
10 楼 jianchen 2013-05-12  
5257007 写道
你好,不知道还有程序吗,方便发一份么,谢谢。jameschuh@126.com
已经将代码作为附件上传了.需要简单改改一部分内容才行.
9 楼 李仕亮 2013-05-08  
我最经在搞Java调用BIEE报表,遇到点麻烦,看到大哥你的博客,是我需要的希望,你尽快发我一份研究下,谢谢。hnhhshun@126.com
8 楼 5257007 2013-05-08  
你好,不知道还有程序吗,方便发一份么,谢谢。jameschuh@126.com
7 楼 jianchen 2012-06-01  
fly15521 写道
楼主你好,请问biee提供的webservice有没有提供方法支持根据报表查询条件导出数据文件(EXCEL、PDF等)的接口方法,就类似与BIEE界面的导出方法,有这个的接口方法支持吗?

10g里没有直接的接口导出文件什么的,要么传参数过去,报表用biee生成,然后指定可以下载。
要么自己取得数据,然后生成文件提供下载。
6 楼 fly15521 2012-05-29  
楼主你好,请问biee提供的webservice有没有提供方法支持根据报表查询条件导出数据文件(EXCEL、PDF等)的接口方法,就类似与BIEE界面的导出方法,有这个的接口方法支持吗?
5 楼 jianchen 2012-03-26  
chenkl1979@gmail.com
maninglove 写道
楼主说的没错,但我用eclipse生成的类,编译报错,希望楼主,把代码示例发一份,要具体点的,急……

邮箱都没留啊
4 楼 maninglove 2012-03-26  
楼主说的没错,但我用eclipse生成的类,编译报错,希望楼主,把代码示例发一份,要具体点的,急……
3 楼 小兵-夏 2012-03-21  
博主好厉害,我最近也在研究biee的webservice,不过才刚开始,博主能否将代码示例发我一份,  flyteen.xia@gmail.com  多谢了~
2 楼 jianchen 2012-01-17  
chenkl 写道
老大,能否提供代码示例啊,chenkl1979@gmail.com,多谢了

我貌似发你邮箱了,如果没收到请告知。
1 楼 chenkl 2012-01-13  
老大,能否提供代码示例啊,chenkl1979@gmail.com,多谢了

相关推荐

Global site tag (gtag.js) - Google Analytics