Crystal Report DB authentication in java - java

I'm facing a problem in Crystal Report with Eclipse.
I am using a servlet to render the crystal report viewer by writing the viewer object to the response like:
public class ReportViewer extends HttpServlet {
#SuppressWarnings("deprecation")
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
try {
String reportName = "WEB-INF/includes/reports/"+request.getParameter("ReportName");
ReportClientDocument clientDoc = (ReportClientDocument) request.getSession().getAttribute(reportName);
if (clientDoc == null) {
// Report can be opened from the relative location specified in the CRConfig.xml, or the report location
// tag can be removed to open the reports as Java resources or using an absolute path
// (absolute path not recommended for Web applications).
clientDoc = new ReportClientDocument();
// Open report
clientDoc.open(reportName, OpenReportOptions._discardSavedData);
// Store the report document in session
ConnectionInfo info = new ConnectionInfo();
info.setUserName("sa");
info.setPassword("sa");
Tables t = clientDoc.getDatabaseController().getDatabase().getTables();
for (com.crystaldecisions.sdk.occa.report.data.ITable table : t) {
IConnectionInfo Ic = table.getConnectionInfo();
Ic.setPassword("sa");
Ic.setUserName("sa");
table.setConnectionInfo(Ic);
}
request.getSession().setAttribute(reportName, clientDoc);
}
// Create the CrystalReportViewer object
CrystalReportViewer crystalReportPageViewer = new CrystalReportViewer();
// set the reportsource property of the viewer
IReportSource reportSource = clientDoc.getReportSource();
crystalReportPageViewer.setReportSource(reportSource);
// set viewer attributes
crystalReportPageViewer.setOwnPage(true);
crystalReportPageViewer.setOwnForm(true);
// Apply the viewer preference attributes
// Process the report
crystalReportPageViewer.processHttpRequest(request, response, request.getSession(false).getServletContext(), null);
} catch (ReportSDKExceptionBase e) {
System.out.println(e);
}
}
public void doPost(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
doGet(request, response);
}
}
When I am trying to request this servlet it redirects me to jdbc login page then it goes back to this servlet. I need to avoid jdbc login step by hardcoding it somewhere. please help me, every single comment will be appreciated.

Have you checked out the wiki over at https://wiki.sdn.sap.com/wiki/display/BOBJ/Crystal%20Reports%20Java%20%20SDK%20Samples
There are a JSP example you maybe could use:
<%# page import="com.crystaldecisions.sdk.occa.report.application.OpenReportOptions,
com.crystaldecisions.sdk.occa.report.application.ReportClientDocument,
com.crystaldecisions.sdk.occa.report.exportoptions.ReportExportFormat,
java.io.ByteArrayInputStream,
java.util.Calendar"
%><%
String reportPath;
String db_username;
String db_password;
ReportClientDocument reportClientDocument;
ByteArrayInputStream byteArrayInputStream;
byte[] byteArray;
int bytesRead;
reportPath = request.getParameter("report_path");
db_username = request.getParameter("db_username");
db_password = request.getParameter("db_password");
/*
* Instantiate ReportClientDocument and specify the Java Print Engine as the report processor.
* Open a rpt file.
*/
reportClientDocument = new ReportClientDocument();
reportClientDocument.setReportAppServer(ReportClientDocument.inprocConnectionString);
reportClientDocument.open(reportPath, OpenReportOptions._openAsReadOnly);
/*
* Set the database logon for all connections in main report.
*/
reportClientDocument.getDatabaseController().logon(db_username, db_password);
/*
* Retrieve PDF format of report and stream out to web browser.
*/
byteArrayInputStream = (ByteArrayInputStream) reportClientDocument
.getPrintOutputController().export(ReportExportFormat.PDF);
response.reset();
response.setHeader("Content-disposition", "inline;filename=crreport.pdf");
response.setContentType("application/pdf");
byteArray = new byte[1024];
while((bytesRead = byteArrayInputStream.read(byteArray)) != -1) {
response.getOutputStream().write(byteArray, 0, bytesRead);
}
response.getOutputStream().flush();
response.getOutputStream().close();
reportClientDocument.close();
%>

Related

WebSphere: How to get the decoded page name in doView portlet method?

I have a requirement where I need to get the page name from the request in the doView method and redirect it to page_name_SUFIX but I can't find a way to decode the WebSphere URL
When I request the view for 'pageName' I have to do something like this:
public void doView(RenderRequest req, RenderResponse res) {
String decodedURL = decodeURL(req); // This is the method that I need, decodedURL should be 'pageName'
(...)
}
I am working on WebSphere 8.0 and I've tried the following without results.
http://wpcertification.blogspot.com.ar/2010/05/getting-name-of-page-where-your-portlet.html (Here i've got the page title, but i don't know how to get the name)
WebSphere Portal decode url (I've decoded the URL but I can't find the page name in the XML)
There's some way to achieve this?
Thank you in advance!
So the question is of scope, from above it is unclear if you mean pageName as in the uniqueName of the page? If so once you have the objectid in a string or the actual object you can get the uniqueName from that object.
here is code to get the objectId of the current page
public ObjectID getCurrentPage(PortletRequest request,
PortletResponse response) throws StateException, NamingException,
IOException {
ObjectID oId = null;
try {
NavigationSelectionModelProvider provider = getNavigationSelectionModelProvider();
NavigationSelectionModel model = provider
.getNavigationSelectionModel(request, response);
NavigationNode node = (NavigationNode) model.getSelectedNode();
oId = node.getObjectID();
} catch (ModelException e) {
System.err.println("The current page could not be located = " + e);
}
return oId;
}
Now if your question is about a portlet parameter called pageName then it should be in the decoded url. is it the uniqueName you are looking for? that will not be in the xml but you can get that from the objectid object
you should be able to get the page id/uniqueName by using a doView method similar to this:
public void doView(RenderRequest request, RenderResponse response) throws PortletException, IOException {
// Set the MIME type for the render response
response.setContentType(request.getResponseContentType());
PortletServiceHome nsh = null;
javax.naming.Context ctx;
boolean serviceAvailable = false;
try {
ctx = new javax.naming.InitialContext();
nsh = (PortletServiceHome)ctx.lookup("portletservice/com.ibm.portal.portlet.service.model.NavigationSelectionModelProvider");
serviceAvailable = true;
} catch(NameNotFoundException nnfe) {
nnfe.printStackTrace();
} catch(NamingException ne) {
ne.printStackTrace();
}
// Check if portlet session exists
ShowPageLayoutPortletSessionBean sessionBean = getSessionBean(request);
if( sessionBean==null ) {
response.getWriter().println("<b>NO PORTLET SESSION YET</b>");
return;
} else if(!serviceAvailable) {
response.getWriter().println("<b>NO SERVICE AVAILABLE</b>");
return;
}
try {
NavigationSelectionModelProvider nsProvider = (NavigationSelectionModelProvider) nsh.getPortletService(NavigationSelectionModelProvider.class);
NavigationSelectionModel navmodel = nsProvider.getNavigationSelectionModel(request, response);
NavigationNode navNode = (NavigationNode)navmodel.getSelectedNode();
ContentPage contentPage = (ContentPage)navNode.getContentNode();
ObjectID pageId = contentPage.getObjectID();
// Invoke the JSP to render
PortletRequestDispatcher rd = getPortletContext().getRequestDispatcher(getJspFilePath(request, VIEW_JSP));
rd.include(request,response);
} catch(Exception ex) {
ex.printStackTrace();
}
}

Facing issue while fetching data with "&" special characters

We have one screen/page in our application where we are showing different columns for different products. These all records in the columns are fetched from database.
Also, We have two export buttons at the bottom of the screen which is meant for showing all those records in the PDF and XLS format.
These functionalities are working fine except under one condition. We have one column name in the screen whose values are fetched from database. when any record under name column has & in it, the export functionality stopped working.
For example :-
for name "BOWOG BEHEER B.V.", the export is working fine for both pdf and xls.
But for the name "BOWOG & BEHEER B.V.", it stopped working. While clicking on export button, pdf and xls is showing as blank page.
Could anyone please help ?
Below is the piece of codes :- (not full code)
public class CVRExportServlet extends HttpServlet {
private final SimpleDateFormat sdf = new SimpleDateFormat("ddMMyyyy");
/** context. */
private ResourceContext context = null;
private Map createParametersFromRequest(final HttpServletRequest request) {
// copy all request parameters
final Map parameters = new HashMap();
final Enumeration names = request.getParameterNames();
while (names.hasMoreElements()) {
final String name = (String) names.nextElement();
final String[] values = request.getParameterValues(name);
if (values.length > 1) {
parameters.put(name, values);
} else {
parameters.put(name, values[0]);
}
}
// parse request uri to get type and format
final String requestURI = request.getRequestURI();
String type = StringUtils.left(requestURI, requestURI.lastIndexOf('.'));
type = StringUtils.substring(type, requestURI.lastIndexOf('/') + 1);
final String format = StringUtils.substring(requestURI, requestURI.lastIndexOf('.') + 1);
parameters.put(Constants.EXPORT_TYPE_PARAMETER, type);
parameters.put(Constants.EXPORT_FORMAT_PARAMETER, format);
// determine themeUrl
final String requestUrl = request.getRequestURL().toString();
final int index = requestUrl.indexOf(request.getContextPath());
String server = "";
if (index > -1) {
server = requestUrl.substring(0, index);
}
private void fillParameters(final HttpServletRequest request, final HttpServletResponse response, final Map parameters)
throws ApplicationException {
parameters.put("props", ResourceBundle.getBundle("messages"));
// Create search request using the search form
final SearchForm form = (SearchForm) request.getSession().getAttribute(
(String) request.getSession().getAttribute(CvrConstants.SESS_ATTR_CVR_SEARCH_FORM_NAME));
final SearchRequest searchRequest = form.getSearchRequest();
searchRequest.setPageNumber(1);
searchRequest.setRowsPerPage(10000);
parameters.put("searchRequest", searchRequest);
}
public void service(final HttpServletRequest request, final HttpServletResponse response)
throws ServletException, IOException {
final long startTime = System.currentTimeMillis();
// create parameters from request
final Map parameters = this.createParametersFromRequest(request);
parameters.put(ResourceContext.class.getName(), this.context);
try {
this.fillParameters(request, response, parameters);
final SearchRequest searchRequest = (SearchRequest) parameters.get("searchRequest");
if (searchRequest == null || searchRequest.getCounterPartyList() == null
|| searchRequest.getCounterPartyList().isEmpty()) {
throw new ExportException("Exception occurred while handling export: empty counterparty list");
} else {
if (searchRequest.getCounterPartyList().size() == 1) {
this.handleSingleReportExport(response, parameters);
} else {
this.handleMutlipleReportExport(response, parameters);
}
}
} catch (final Exception e) {
this.handleException(e, request, response);
}
}
private void handleSingleReportExport(final HttpServletResponse response, final Map parameters) throws Exception {
final XmlExportService exportService = this.getXmlExportService();
final ApplicationContext context = this.getApplicationContext();
final XmlTransformationService xmlTransformationService = (XmlTransformationService) context.getBean("transformationService");
// perform export
exportService.export(parameters);
// perform transformation
final ExportResult exportResult = xmlTransformationService.transform(parameters);
// write result to stream
response.setContentType(exportResult.getContentType());
response.setContentLength(exportResult.getContentLength());
if (parameters.get("format").equals("csv")) {
response.setContentType("text/csv");
response.setHeader("Content-disposition", "attachment; filename=export.csv");
} else if (parameters.get("format").equals("pdf")) {
response.setContentType("application/pdf");
response.setHeader("Content-disposition", "inline; filename=export.pdf");
}
final ServletOutputStream out = response.getOutputStream();
out.write(exportResult.getBytes());
out.flush();
out.close();
}
private void handleMutlipleReportExport(final HttpServletResponse response, final Map parameters) throws Exception {
final SearchRequest searchRequest = (SearchRequest) parameters.get("searchRequest");
response.setContentType("application/force-download");
response.setHeader("Content-Encoding" , "x-compress");
response.setHeader("Content-Disposition", "attachment; filename=export_" + parameters.get("format") + ".zip");
final XmlExportService exportService = this.getXmlExportService();
final ApplicationContext context = this.getApplicationContext();
final XmlTransformationService xmlTransformationService = (XmlTransformationService) context.getBean("transformationService");
// start the zip process
final ZipOutputStream zos = new ZipOutputStream(response.getOutputStream());
// create a file for each counterparty and add it to the zip file
for (final String counterPartyId : searchRequest.getCounterPartyList()) {
// make sure to reset the counterparty to the current one in the loop
searchRequest.setCounterPartyList(Arrays.asList(new String[] {counterPartyId}));
// perform export
exportService.export(parameters);
// perform transformation
final ExportResult exportResult = xmlTransformationService.transform(parameters);
// add the file to the zip
final String fileName = counterPartyId + "_" + sdf.format(searchRequest.getRevaluationDate()) + "." + parameters.get("format");
zos.putNextEntry(new ZipEntry(fileName));
zos.write(exportResult.getBytes());
zos.closeEntry();
}
// finish the zip process
zos.flush();
zos.close();
}
I have some idea now. actually the issue is there at vm (velocity template). The "name" column is fetched from vm file and code is something like this :-
$!{result.counterpartyName}
This is in for each loop for multiple records. Could anyone please suggest how can i ignore special characters in the vm file itself. so that we will be able to export correctly even if "name" column has "&" or "-" etc special characters.
It seems based on your code that you are using an XML transformation service.
I'd say it's probably your data in your parameters containing dangling & sign. To be valid XML ready for transformation, & should be &. However, based on the code given it is not possible to say where the XML data is coming from. You say it's coming from the database, so my guess is that the problem should be dealt with by modifying the data in the database.
Edit:
It seems I was partly right, but the database doesn't contain the XML - if I got this correctly, data is coming from database as raw tabular data, but is formatted to XML using velocity templates. If that's it, then XML escaping should be used in velocity template like this.

read updated data on client from file created by server JSP

I am creating a web application in java. On client side I have a bar chart that display some data stored in a tsv file created by the java server page. By clicking on a button the server updates these data in the file. Now I want to read the refreshed data, but I get the older ones. It seems that the browser cached the file so it can't get the changed file.
This is my servlet code:
public class GetDataServlet extends HttpServlet
{
private static final long serialVersionUID = 1L;
private User user;
Utility utility;
public void init() throws ServletException {
reset();
}
public void doGet (HttpServletRequest request,HttpServletResponse response) throws ServletException, IOException {
response.setHeader("Cache-Control", "no-cache");
response.setHeader("Pragma", "no-cache");
PrintWriter out = response.getWriter();
user.getProfile().get(0).setWeigth(user.getProfile().get(0).getWeigth()+0.03);
user.getProfile().get(1).setWeigth(user.getProfile().get(1).getWeigth()+0.02);
user.getProfile().get(5).setWeigth(user.getProfile().get(5).getWeigth()+0.01);
utility.createTsvFile(user, "/usr/local/apache-tomcat-7.0.50/webapps/Visualizer/data.tsv");
String message = String.format("data.tsv");
i++;
out.print(message);
}
public void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
if(request.getParameter("reset").compareTo("yes")==0)
reset();
}
private void reset(){
List<Concept> children = new ArrayList<Concept>();
Concept food = new Concept();
food.setWeigth(0.10);
food.setLabel("food");
food.setColor("#98abc5");
Concept dish = new Concept();
dish.setWeigth(0.08);
dish.setLabel("dish");
dish.setParent(food);
dish.setColor("#8a89a6");
Concept cuisine = new Concept();
cuisine.setWeigth(0.06);
cuisine.setLabel("cuisine");
cuisine.setParent(food);
cuisine.setColor("#8a89a6");
children.add(dish);
children.add(cuisine);
food.setChildren(children);
children.clear();
Concept pizza = new Concept();
pizza.setWeigth(0.05);
pizza.setLabel("pizza");
pizza.setParent(dish);
pizza.setColor("#6b486b");
Concept spaghetti = new Concept();
spaghetti.setWeigth(0.05);
spaghetti.setLabel("spaghetti");
spaghetti.setParent(dish);
spaghetti.setColor("#6b486b");
Concept sushi = new Concept();
sushi.setWeigth(0.06);
sushi.setLabel("sushi");
sushi.setParent(dish);
sushi.setColor("#6b486b");
children.add(pizza);
children.add(spaghetti);
children.add(sushi);
dish.setChildren(children);
List<Concept> profile = new ArrayList<Concept>();
profile.add(food);
profile.add(dish);
profile.add(cuisine);
profile.add(pizza);
profile.add(spaghetti);
profile.add(sushi);
user = new User("mario", profile);
utility = new Utility("");
}
}
This is the javascript code that calls the servlet:
function ajaxSyncRequest(reqURL) {
//Creating a new XMLHttpRequest object
var xmlhttp;
if (window.XMLHttpRequest) {
xmlhttp = new XMLHttpRequest(); //for IE7+, Firefox, Chrome, Opera, Safari
} else {
xmlhttp = new ActiveXObject("Microsoft.XMLHTTP"); //for IE6, IE5
}
//Create a asynchronous GET request
xmlhttp.open("GET", reqURL, false);
xmlhttp.send(null);
//Execution blocked till server send the response
if (xmlhttp.readyState == 4) {
if (xmlhttp.status == 200) {
document.getElementById("message").innerHTML = xmlhttp.responseText;
update(xmlhttp.responseText);
//alert(xmlhttp.responseText);
} else {
alert('Something is wrong !!');
}
}
}
function update(file){
d3.tsv(file, function(error, data) {
......
In the html page I have also put this:
<meta http-equiv="Cache-control" content="no-cache">
but it doesn't work.
With this code I can display the correct data the first time I call the servlet, than even if the data in the file tsv changes I get the first one.
Which is the best way to read the refreshed data in the file?
Okay I you are facing problem from browser caching problem like this so two hings can be done
1)You can create a filter and instruct in filter not to cache some what like this Prevent user from seeing previously visited secured page after logout
2)Each time you are hitting the url of tsv file add a random variable in end .(This is usually in case of internet exlorer)

Servlet mixes header and content and writing twice same in output?

I have implemented servlet which behaves not stable, sometimes it mixes header in content and writing same twice.
and sometimes it is returning file which contains response header mixed by content like this:
Server: Apache-Coyote/1.1
: W/"43-1353687036000"
DatCCoonntenntt--DDiissppoosittiioonn: : atatatacehnmte;n tf;i lfenlaemnea=m20=12201112211127325421_4W1_Wirnkgi_nSgc_Seern.xnlsx
sx
Content-Typ-eT: ype: applaipcatciaoti/on/toctestt-rstare
am
ConCtoententy-pTeype: appalicatcion/oon/octet-setarm
m
CCoonntent-Lnegtht h: 4199
Date: te: FriF,r i2,3 2No vNo2v0 120162: 215:25 :G4M2T
....
File content bytes ...
And again same header and content
UPDATE
*This situation happens on Tomcat7*
I have tested also on Tomcat6 and Jetty, in both cases there is no injection of HTTP-Header to response content but HTTP-Header is wrong and returns wrong file name, the file content is correct file. I have noticed that wrong return from servlet happens when
returns transfer-encoding is chunked.
When I am removing header stuff, and second part of bytes, it is valid file.
Is it possible that is synchronization issue ?
UPDATE
Here is full source of servlet :
public class ExcelDownloadServlet extends HttpServlet
{
private static final long serialVersionUID = 1L;
private static final Logger LOG = Logger
.getLogger (ExcelDownloadServlet.class);
#Override
protected void doGet (HttpServletRequest request,
HttpServletResponse response) throws ServletException, IOException
{
try
{
TransactionId transactionId = getTransactionId (request);
String fileName =
request.getParameter (GlobalConstants.EXCEL_FILE);
ExcelDownloadType downloadType =
ExcelDownloadType
.valueOf (request
.getParameter (GlobalConstants.EXCEL_DOWNLOAD_TYPE));
ActionContextFactory actionContextFactory =
ApplicationContext.getContext ()
.getActionContextFactory ();
//suppress warning. HttpServletRequest.getLocales does not support generics
#SuppressWarnings("unchecked")
ActionContext actionContext =
actionContextFactory.create (request.getSession ()
.getId (), Collections.<Locale> list (request
.getLocales ()));
GetExcelDataResponse dataResponse =
new GetExcelData (transactionId, fileName, downloadType)
.execute (actionContext);
writeToResponse (response, dataResponse.getFileName (),
dataResponse.getData ());
}
catch (InvalidSessionException e)
{
LOG.error ("Invalid session in Excel download", e);
throw new ServletException (e);
}
catch (ActionException e)
{
LOG.error ("Could not download into excel.", e);
throw new ServletException (e);
}
}
protected TransactionId getTransactionId (HttpServletRequest request)
{
return RequestParameterDeserializer.<TransactionId> deserialize (
request, GlobalConstants.TRANSACTION_ID);
}
protected void writeToResponse (HttpServletResponse response,
String rawFileName, byte[] data) throws IOException
{
ServletOutputStream sout = null;
try
{
response.setContentType ("application/octet-stream");
response.setContentLength (data.length);
// removing blanks from the file name, since FF cuts file names
// otherwise.
String fileNameWithTime = rawFileName.replaceAll (" ", "_");
response.setHeader ("Content-Disposition", "attachment; filename="
+ fileNameWithTime);
sout = response.getOutputStream ();
sout.write (data, 0, data.length);
}
finally
{
if (sout != null)
{
sout.close ();
}
}
}
UPDATE
*The call comes from GWT application when is generating the URL of servlet with required parameters and sets in IFrame, then servlet calls and file is downloading. Are there any suggestions ?*
I had a similar issue a long time ago.
It turned out that closing the ServletOutputStream triggered an unexpected behaviour on the request flow.
Servlets are not supposed to close the container provided OutputStream.
Another issue could be manually setting the content length, it is responsibility of the container producing the correct value.
To summarize, try removing out.close() and response.setContentLength()

Start download from servlet via gwt (http get)

I would like to start a file download from a clickevent in my gwt web app. So I wrote a Servlet which writes the data to the output and should start the download. The data is received via http get.
public void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
String data = request.getParameter("data");
String filename = request.getParameter("filename");
byte[] streamData = data.getBytes();
response.setContentType("application/force-download");
response.setHeader("Content-Disposition", "attachment; fileName="
+ filename + ".csv");
response.setContentLength(streamData.length);
ServletOutputStream out = response.getOutputStream();
out.write(streamData);
out.flush();
}
In the client I start the get method via requestBuilder.sendRequest():
RequestBuilder requestBuilder = new RequestBuilder(RequestBuilder.GET, /download");
requestBuilder.sendRequest("filename=dues&data="+ theDataAsString, new RequestCallback() {
#Override
public void onResponseReceived(Request request,
Response response) {
// Anything to do here?
}
#Override
public void onError(Request request, Throwable exception) {
exception.printStackTrace();
SC.warn("Error while creating export file.");
}
});
Nothing happens. But why? Shouldn't the browser ask to begin a download?
Does it, in this case, matter if i use post or get?
I don't want to use somthing like
Window.open("/download?data=myData&filename=filename", "_blank", "");
Any ideas?
On the client side, use an Anchor instead of a request builder and invoke the servlet directly.

Categories

Resources