Community Tip - Did you get called away in the middle of writing a post? Don't worry you can find your unfinished post later in the Drafts section of your profile page. X
I'm looking to download a zip from my windchill server(temp location) to the client machine.
The zip was actually created as a result of an custom action.
So basically, when I click on the action a zip should get downloaded, that's my requirement.
Please suggest me your ideas or share me any existing solution.
Many thanks in advance.
Solved! Go to Solution.
Hi @MV_10441462
depends how do you start your function.
usually you get request and get the outputstream from it and flush (send) the data to the client as @avillanueva's example shows you. .
here is short snip with a zipStream but you need to learn how to add files to the zip stream
HTTPResponse resp; // you need to get respons from commandBean or whereever HttpServletResponse response = nmCommandBean.getResponse();
ByteArrayOutputStream zipOut = new ByteArrayOutputStream();
CheckedOutputStream checksum = new CheckedOutputStream(zipOut, new Adler32());
ZipOutputStream zipOutputStream = new ZipOutputStream(new BufferedOutputStream(checksum));
InputStream contentStream = ContentServerHelper.service.findContentStream(appDatatToZip);
// definice filename s cestou v zip
String fileZipEntry = appDatatToZip.getFileName();
addStreamToZip(fileZipEntry, zipOutputStream, contentStream); // annother sub method where the content is writen to zip
zipOutputStream.close();
OutputStream output = resp.getOutputStream();
resp.setHeader("Content-disposition", "attachment; filename=zipDownloadFile.zip");
resp.setHeader("Content-Type", "application/zip");
output.write(zipOut.toByteArray()); // zip stream written to the respons outputStream
output.flush();
output.close();
PetrH
I did this with a JSP tied to that custom action:
BOMExportExcelUtility excelUtil=BOMExportExcelUtilityImpl.createBOMExportExcelUtility();
//7. Sub-module create Excel File for user download
response.reset();
excelUtil.createExcelFile(response.getOutputStream(),sheet1,sheet2);
ServletOutputStream outs = response.getOutputStream();
response.setHeader("Content-type","application/ms-excel");
String version=VersionControlHelper.getVersionIdentifier((Versioned)bom).getValue();
if (version.indexOf('.')!=-1)
version=version.substring(0, version.indexOf('.')); //just get first part
String filename=bom.getNumber()+version;
response.setHeader("Content-disposition","attachment; filename="+filename+".XLS");//should prompt for download
excelUtil.writeFile();
//8. Return response to user's browser session.
outs.flush();
outs.close();
This is the section where my code creates an XLS file and streams it back to the client. User downloads the file.
Hi @MV_10441462
example from @avillanueva is very good one how to download file.
I would add that you need to write own sollution.
Create zip in java
Collect files from Windchill
Add files to the zip
push the zip stream to the client user
PetrH
Hi @MV_10441462
depends how do you start your function.
usually you get request and get the outputstream from it and flush (send) the data to the client as @avillanueva's example shows you. .
here is short snip with a zipStream but you need to learn how to add files to the zip stream
HTTPResponse resp; // you need to get respons from commandBean or whereever HttpServletResponse response = nmCommandBean.getResponse();
ByteArrayOutputStream zipOut = new ByteArrayOutputStream();
CheckedOutputStream checksum = new CheckedOutputStream(zipOut, new Adler32());
ZipOutputStream zipOutputStream = new ZipOutputStream(new BufferedOutputStream(checksum));
InputStream contentStream = ContentServerHelper.service.findContentStream(appDatatToZip);
// definice filename s cestou v zip
String fileZipEntry = appDatatToZip.getFileName();
addStreamToZip(fileZipEntry, zipOutputStream, contentStream); // annother sub method where the content is writen to zip
zipOutputStream.close();
OutputStream output = resp.getOutputStream();
resp.setHeader("Content-disposition", "attachment; filename=zipDownloadFile.zip");
resp.setHeader("Content-Type", "application/zip");
output.write(zipOut.toByteArray()); // zip stream written to the respons outputStream
output.flush();
output.close();
PetrH
@HelesicPetr- how can I overwrite the HttpServletResponse from NmCommandBean::getResponse() when whenever I try to use this method I retrieve IllegalStateException - Already using writer?
I want to perform downloading .zip file generated on the server-side from Wizard's FormProcessor. Is there any solution for that? Here is my example code of custom FormProcessor:
private ExportPackageFileManager fileManager;
@Override
public FormResult doOperation(NmCommandBean nmCommandBean, List<ObjectBean> list) throws WTException {
FormResult result = super.doOperation(nmCommandBean, list);
WTPart contextPart = (WTPart) WizardUtils.getContextObject(nmCommandBean);
setFileManager(contextPart);
HttpServletResponse response = nmCommandBean.getResponse();
Path path = fileManager.getZipFilePath();
String fileName = path.getFileName().toString();
response.reset();
try(ServletOutputStream outputStream = response.getOutputStream()) {
response.setStatus(200);
response.setHeader("X-Content-Type-Options", null);
response.setHeader("Content-Type", "application/zip");
response.setHeader("Content-disposition", "attachment; filename=" + fileName);
response.setContentLength((int) path.toFile().length());
Files.copy(path, outputStream);
result.addDynamicRefreshInfo(new DynamicRefreshInfo(contextPart, contextPart, DynamicRefreshInfo.Action.UPDATE));
return result;
} catch (IOException | IllegalStateException e) {
throw new WTException("Could not send file!");
}
}
Whole logic for fetching files, zipping them works just fine. Whenever I click "Submit" button on my Wizard - window freezes and won't close automatically.
response.reset() is being used to avoid getting IllegalStateException but on the other hand it causes the window to freeze.
Thanks in advance.
HI @mprotas
Why do you use the file.copy?
try to use the output.write() with transferred file to the byte.
PetrH
Hi @HelesicPetr,
Changing from Files.copy() to more extensive writing to OutputStream object do not change anything in the freezing of Wizard's window after performing download of .zip file.
It looks like this:
Here is the current version of code:
@Override
public FormResult doOperation(NmCommandBean nmCommandBean, List<ObjectBean> list) throws WTException {
FormResult result = super.doOperation(nmCommandBean, list);
WTPart contextPart = (WTPart) WizardUtils.getContextObject(nmCommandBean);
setFileManager(contextPart);
HttpServletResponseWrapper response = new HttpServletResponseWrapper(nmCommandBean.getResponse());
Path path = fileManager.getZipFilePath();
String fileName = path.getFileName().toString();
response.reset();
try(ServletOutputStream outputStream = response.getOutputStream()) {
response.setStatus(200);
response.setHeader("X-Content-Type-Options", null);
response.setHeader("Content-Type", "application/zip");
response.setHeader("Content-disposition", "attachment; filename=" + fileName);
response.setContentLength((int) path.toFile().length());
//Files.copy(path, outputStream);
File file = new File(fileManager.getZipFilePath().toString());
ByteArrayOutputStream bos = new ByteArrayOutputStream();
try(FileInputStream fis = new FileInputStream(file)) {
byte[] buf = new byte[1024];
for (int readNum; (readNum = fis.read(buf)) != -1;) {
bos.write(buf, 0, readNum);
}
}
catch (IOException e) {
System.out.println("Test");
}
outputStream.write(bos.toByteArray());
outputStream.flush();
outputStream.close();
result.addDynamicRefreshInfo(new DynamicRefreshInfo(contextPart, contextPart, DynamicRefreshInfo.Action.UPDATE));
return result;
} catch (IOException | IllegalStateException e) {
throw new WTException("Could not send file!");
}
}
Hi @mprotas
The point is that you can not use the reset method to reset the response.
If you use the reset, then you lost the connection to your wizard window.
Remove it.
You need to solve the IllegalStateException issue, and .reset method is not the solution.
PetrH
Yeah, but without this reset() method I receive that IllegalStateException mentioned above. Is there any workaround to perform downloading file from FormProcessor Wizard's window?