How to split de code into Service, repository and controller (Spring mvc)
this code work for me but not good split.
Big table large table to expose API REST
#ApiOperation(value = "Search all customers",response = GoldenCustomer.class)
#RequestMapping(value = "/goldenall/",method = RequestMethod.GET, produces = "application/json")
#ResponseBody
public ResponseEntity<?> getAllCustomers(HttpServletResponse response){
LOGGER.info("Get all Golden Customers...");
List<GoldenCustomer> goldenCustomers = null;
String message = "Unknown exception";
try {
PreparedStatement st = session.prepare("select * from ckm_d_pilot.golden_clusters_by_customer where solr_query=?");
//TODO
String input_string = "*";
String solrQuery = "{\"q\": \"*:"+input_string+"\", \"paging\": \"driver\"}";
BoundStatement boundSt = st.bind(solrQuery);
ResultSet rs = session.execute(boundSt.setFetchSize(1000));
response.setContentType("text/csv");
response.setHeader("Content-Disposition", "attachment; filename=export.csv;");
ServletOutputStream os = response.getOutputStream();
for(Row row: rs){
String csvLine = row.getString("cluster_id")+","+row.getString("src_customer_id")+"\n";
os.write(csvLine.getBytes("UTF-8"));
}
response.flushBuffer();
}catch (Exception e){
LOGGER.error("Intetrnal error WebService exception not found "+ message, e);
throw new ReportInternalException(message);
}
return new ResponseEntity<>(HttpStatus.OK);
}
Here is the minimum refactored code which gives you some information on how it can be done.
#ApiOperation(value = "Search all customers",response = GoldenCustomer.class)
#RequestMapping(value = "/goldenall/",method = RequestMethod.GET, produces = "application/json")
#ResponseBody
public ResponseEntity<?> getAllCustomers(HttpServletResponse response){
LOGGER.info("Get all Golden Customers...");
List<GoldenCustomer> goldenCustomers = null;
String message = "Unknown exception";
try {
String custCsv = new CustomerServiceImpl().getAllCustomers();
response.setContentType("text/csv");
response.setHeader("Content-Disposition", "attachment; filename=export.csv;");
ServletOutputStream os = response.getOutputStream();
os.write(custCsv.getBytes("UTF-8"));
response.flushBuffer();
}catch (Exception e){
LOGGER.error("Intetrnal error WebService exception not found "+ message, e);
throw new ReportInternalException(message);
}
return new ResponseEntity<>(HttpStatus.OK);
}
public class CustomerServiceImpl {
public String getAllCustomers () {
return new CustomersDAOImpl().getAllCustomers();
}
}
public class CustomersDAOImpl() {
public String getAllCustomers() {
StringBuilder sb = new StringBuilder();
PreparedStatement st = session.prepare("select * from ckm_d_pilot.golden_clusters_by_customer where solr_query=?");
//TODO
String input_string = "*";
String solrQuery = "{\"q\": \"*:"+input_string+"\", \"paging\": \"driver\"}";
BoundStatement boundSt = st.bind(solrQuery);
ResultSet rs = session.execute(boundSt.setFetchSize(1000));
for(Row row: rs){
String csvLine = row.getString("cluster_id")+","+row.getString("src_customer_id")+"\n";
sb.append(csvLine);
}
return sb.toString();
}
}
Note:- I have not tested the below code
Related
I need to upload a file through the spring MVC rest template for the below params shown in the image.
I have tried different approaches but it's not working giving exception 401 Unauthorized.
I need code that uploads files through spring MVC RestTemplate.
I have shared my code below which is not working.I have tried different ways to attach file but they are not working please check my code.
My Code Sample:
#RequestMapping(value = "/uploadPEFile", method = { RequestMethod.POST},
produces = "application/json")
#ResponseBody
public String uploadPEFile(#RequestParam(value = "file", required = false) MultipartFile file,
HttpServletRequest request, HttpServletResponse httpResponse) {
JsonResponse objResponse = null;
String enterpriseId = "";
String enterpriseName = "";
String type = "";
String productId = "";
String userIds = "";
String title = "";
String description = "";
String date = "";
String externalUrl = "";
String presenterName = "";
try {
enterpriseId = request.getParameter("enterpriseId");
enterpriseName = request.getParameter("enterpriseName");
type = request.getParameter("type");
productId = request.getParameter("productId");
userIds = request.getParameter("userIds");
title = request.getParameter("title");
description = request.getParameter("description");
date = request.getParameter("date");
if(date != null && !date.isEmpty())
{
String [] dateArray = date.split(" ");
date = dateArray[2]+" "+getMonth(dateArray[1])+", "+dateArray[3];
}
externalUrl = request.getParameter("externalURL");
presenterName = request.getParameter("presenterName");
JsonObject jsonBody = new JsonObject();
jsonBody.addProperty("title", title);
jsonBody.addProperty("description", description);
jsonBody.addProperty("date", date);
jsonBody.addProperty("external_url", externalUrl);
jsonBody.addProperty("presenter_name", presenterName);
String cmsDeviceId = PortalUtil.getPropertyValue("cms.device.id");
if (file != null) {
final String filename = file.getOriginalFilename();
ByteArrayResource fileAsResource = new ByteArrayResource(file.getBytes()) {
#Override
public String getFilename() {
return filename;
}
};
String filePath = "/persivia edge/"+type+"/"+filename;
File userFile = new File(System.getProperty(PortalConstants.cdnPath) + filePath);
if(!userFile.exists()) {
userFile.mkdirs();
}
file.transferTo(userFile);
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.MULTIPART_FORM_DATA);
MultiValueMap<String, Object> body = new LinkedMultiValueMap<>();
body.add("device_id",cmsDeviceId);
// body.add("attachment",fileAsResource);
// body.add("attachment",new MultipartInputStreamFileResource(file.getInputStream(), file.getOriginalFilename()));
body.add("attachment",new FileSystemResource(filePath));
body.add("source", "web");
body.add("filename", filename);
body.add("enterprise_id", enterpriseId);
body.add("enterpriseName", enterpriseName);
body.add("type", type);
body.add("product_id",productId);
body.add("userIds",userIds);
body.add("body", jsonBody.toString());
HttpEntity<MultiValueMap<String, Object>> requestEntity = new HttpEntity<>(body, headers);
RestTemplate restTemplate = new RestTemplate();
String requestUrl = PortalUtil.getPropertyValue("cms.api.url")+"wp-json/wp/v2/upload_content";
String response = restTemplate.postForObject(requestUrl, requestEntity, String.class);
httpResponse.setStatus(HttpServletResponse.SC_OK);
JsonObject data = new JsonObject();
objResponse = JsonResponse.build(ResponseStatus.status200, ResponseStatus.message200,
"Logo info updated successfully", data);
}
} catch (Exception e) {
e.printStackTrace();
logger.error(e.getMessage(), e.getCause());
objResponse = JsonResponse.build(ResponseStatus.status500, ResponseStatus.message500,
e.getMessage(), null);
httpResponse.setStatus(HttpServletResponse.SC_INTERNAL_SERVER_ERROR);
}
return new Gson().toJson(objResponse);
}
We need to apply version control for our API, when the user send a request to our API endpoint i.e."http://mycompany/item?version=1", it will forwarded the request to itemServer_V1.java.
To achieve this goal, we have configured our web.xml as follows.
<servlet>
<servlet-name>item</servlet-name>
<servlet-class>com.mycompany.Servlet.ItemRequestHandler</servlet-class>
</servlet>
<servlet-mapping>
<servlet-name>item</servlet-name>
<url-pattern>/item</url-pattern>
</servlet-mapping>
We create a table in MySQL database.
database table
ItemRequestHandler is a class which extends HttpServlet, and it supposed to forward the request to ItemServiceV1 or ItemServiceV2 according to the version parameter in the request.
I have finish the ItemService class but I don't know how to forward the request from ItemRequestHandler to ItemService class. Could someone let me know how to do that please?
ItemRequestHandler class is as follows
public void doGet(HttpServletRequest req, HttpServletResponse res) throws ServletException , IOException
{
String version = req.getParameter("version");
String fcd = req.getParameter("fcd");
String client = req.getParameter("client");
//Find the targetClass from database using the above information.
targetClass.doGet(req, res);
}
I find out a solution.
protected void doPost(HttpServletRequest req, HttpServletResponse res) throws ServletException, IOException {
System.out.println("LoginRequestHandler doPost");
String className = "";
String version = "";
String fcd = "login";
String compid = "";
RequestWrapper currentReq = new RequestWrapper(req);
version = currentReq.getParameter("Version");
compid = currentReq.getParameter("Compid ");
try {
className = findServletByVersion(compid, version, fcd);
Class<?> serviceClass = Class.forName(className);
Method method = serviceClass.getDeclaredMethod(MethodName.doPost.toString(), HttpServletRequest.class, HttpServletResponse.class);
method.invoke(serviceClass.newInstance(), currentReq, res);
return;
}catch(Exception e) {
System.out.println(e.toString());
} catch (DataNotFound e) {
System.out.println(e.toString());
}
}
}
Code of RequestWrapper
public class RequestWrapper extends HttpServletRequestWrapper {
private String _body;
public RequestWrapper(HttpServletRequest request) throws IOException {
super(request);
_body = "";
BufferedReader bufferedReader = request.getReader();
String line;
while ((line = bufferedReader.readLine()) != null){
_body += line;
}
}
#Override
public ServletInputStream getInputStream() throws IOException {
final ByteArrayInputStream byteArrayInputStream = new ByteArrayInputStream(_body.getBytes());
return new ServletInputStream() {
public int read() throws IOException {
return byteArrayInputStream.read();
}
};
}
#Override
public BufferedReader getReader() throws IOException {
return new BufferedReader(new InputStreamReader(this.getInputStream()));
}
}
Code of findServletByVersion
public String findServletByVersion(String compid, String version, String fcd) throws SQLException, ClassNotFoundException, DataNotFound {
String clsName = "";
Connection con = null;
Statement stmt = null;
User user = null;
try {
Class.forName("com.mysql.jdbc.Driver");
con = DriverManager.getConnection("jdbc:mysql://YourIpAddress:PortNum/"+schemaName,"account","password");
String query = "SELECT * FROM "+compid+".restfcd "
+ "WHERE 1=1 "
+ "AND compid = '"+compid+"'"
+ "AND version = '"+version+"'"
+ "AND fcd = '"+fcd+"'"
+ "ORDER BY compid desc";
System.out.println(query);
stmt = con.createStatement();
ResultSet rs = stmt.executeQuery(query);
if(rs!=null) {
while (rs.next()) {
clsName = rs.getString("fcdcls");
}
}
if(Func.isEmpty(clsName)) {
throw new DataNotFound("findServletByVersion : no match result!");
}
return clsName;
} catch (SQLException e) {
throw new SQLException("findServletByVersion : SQLException!");
} catch (ClassNotFoundException e) {
throw new ClassNotFoundException("findServletByVersion : ClassNotFoundException!");
} finally {
try {
con.close();
stmt.close();
} catch (SQLException sqlee) {
throw new SQLException("Cannot close conection/statement!");
}
}
}
Hi I am looking into using Java (to be deployed as servlets in Websphere 8.5) to integrate with SSRS. I have looked into some of the sample codes out there and try it out.
private static SoapHeader createExecutionIdSoapHeader(String executionId) {
Document doc = DOMUtils.createDocument();
Element executionHeaderElement = doc.createElement("ExecutionHeader");
executionHeaderElement.setAttribute("xmlns", XML_NAMESPACE);
Element executionIdElement = doc.createElement("ExecutionID");
executionIdElement.setTextContent(executionId);
executionHeaderElement.appendChild(executionIdElement);
SoapHeader soapH = new SoapHeader(new QName(XML_NAMESPACE, "ExecutionHeader"), executionHeaderElement);
return soapH;
}
public static Holder<byte[]> getReportResult(String output_type, String reportFolder, String reportName, ArrayOfParameterValue arrayOfParameterValue) {
Holder<byte[]> result = null;
try {
String historyID = null;
String executionID = null;
ReportExecutionServiceSoap service = getExecutionService();
BindingProvider bp = (BindingProvider) service;
bp.getRequestContext().put(BindingProvider.USERNAME_PROPERTY, authenticator.getUsername());
bp.getRequestContext().put(BindingProvider.PASSWORD_PROPERTY, authenticator.getPassword());
ExecutionInfo info = new ExecutionInfo();
info = service.loadReport(REPORT_PATH, historyID);
executionID = info.getExecutionID();
List<Header> headers = new ArrayList<Header>();
SoapHeader header = createExecutionIdSoapHeader(executionID);
headers.add(header);
bp.getRequestContext().put(Header.HEADER_LIST, headers);
if (!arrayOfParameterValue.getParameterValue().isEmpty()) {
service.setExecutionParameters(arrayOfParameterValue, "en-us");
}
// Default to return HTML4.0
String deviceInfo = "";
if (output_type == null || output_type.isEmpty()) {
output_type = "HTML4.0";
}
if ("IMAGE".equalsIgnoreCase(output_type)) {
deviceInfo = RENDER_DEVICE_INFO_IMAGE;
} else {
deviceInfo = RENDER_DEVICE_INFO_HTML;
}
result = new Holder<byte[]>();
Holder<String> extension = new Holder<String>();
Holder<String> mimeType = new Holder<String>();
Holder<String> encoding = new Holder<String>();
Holder<ArrayOfWarning> warnings = new Holder<ArrayOfWarning>();
Holder<ArrayOfString> streamIDs = new Holder<ArrayOfString>();
service.render(output_type, deviceInfo, result, extension, mimeType, encoding, warnings, streamIDs);
} catch (Throwable th) {
th.printStackTrace();
}
return result;
}
protected void doGet(HttpServletRequest request, HttpServletResponse response)
throws ServletException, IOException {
try {
ArrayOfParameterValue arrayOfParameterValue = new ArrayOfParameterValue();
List<ParameterValue> parameters = arrayOfParameterValue.getParameterValue();
ParameterValue parameterValue = new ParameterValue();
parameterValue.setName(PARAMETER_NAME);
parameterValue.setValue(PARAMETER_VALUE);
parameters.add(parameterValue);
Holder<byte[]> result = GenerateReport.getReportResult(REPORT_FORMAT, REPORT_FOLDER, REPORT_NAME,
arrayOfParameterValue);
System.out.println("--------------------------------- Writing to Browser --------------------------------");
ServletOutputStream out = response.getOutputStream();
out.write(result.value);
out.flush();
out.close();
System.out.println("--------------------------------- Writing to File -----------------------------------");
DateFormat df = new SimpleDateFormat("dd_MM_yy_HH_mm_ss_");
Date date = new Date();
String filename = df.format(date) + "SSRS_Report.pdf";
FileOutputStream o = new FileOutputStream("C:\\Users\\keh\\Desktop\\Temp\\" + filename);
o.write(result.value);
o.flush();
o.close();
} catch (Exception e) {
e.printStackTrace();
}
}
When I run the codes, I have this error :
[5/17/17 19:21:02:704 SGT] 000000c4 SystemErr R javax.xml.ws.soap.SOAPFaultException: The session identifier is missing. A session identifier is required for this operation. ---> Microsoft.ReportingServices.Diagnostics.Utilities.MissingSessionIdException: The session identifier is missing. A session identifier is required for this operation.
Any expert out there can point me to a solution pls?
P.S. I have tried to use WSBindingProvider as shown in Surendra Gurjar's Blog and it ran beautifully on an Apache server, but I got a ClassCastException when I deploy it to Websphere.
So I am getting a 400 for my HTTP response code when it should be 200. I am passing in a byte[] object to the endpoint but it doesn't seem to be adding the content-type correctly? Any suggestions?
#RequestMapping(value = "/test", method = RequestMethod.POST, consumes = "application/octet-stream")
public ResponseEntity<String> receiveCompressedBinary(#RequestHeader String site, #RequestHeader String customer,
#RequestHeader String table, #RequestBody byte[] binary, #RequestHeader String loadStatus) {
if(binary.length < maxFileSize) {
return new ResponseEntity<String>(HttpStatus.OK);
}
else{
return new ResponseEntity<String>(HttpStatus.PAYLOAD_TOO_LARGE);
}
}
My test:
#Test
public void testUploadCompressedBinaryInitialRunning() throws Exception{
File file = new File("src/test/resources/testFile.txt");
String site = "site";
String customer = "customer";
String table = "table";
String loadStatus = "INITIALRUNNING";
this.mockMvc.perform(post("/test").header("site",site).param("customer",customer).
param("table", table).content(compress(file)).param("loadStatus",loadStatus)
.with(user("user"))).andExpect(status().isOk());
this.mockMvc.perform(post("/uploadCompressedBinary")).andDo(print()).andExpect(status().isOk());
}
Compress method:
public static byte[] compress(File file) throws IOException {
if (file.length() == 0) {
return null;
}
FileInputStream fileInputStream = null;
byte[] fileInBytes = new byte[(int)file.length()];
try {
//convert file into array of bytes
fileInputStream = new FileInputStream(file);
fileInputStream.read(fileInBytes);
fileInputStream.close();
} catch (IOException e) {
System.out.println("Exception whilst compressing the file: " + e.getMessage());
}
ByteArrayOutputStream obj = new ByteArrayOutputStream();
GZIPOutputStream gzip = new GZIPOutputStream(obj);
gzip.write(fileInBytes);
gzip.close();
return obj.toByteArray();
}
UPDATE: Got past it, rather than .param, I should be using .header
It does not look like you are setting the content type when you are posting.
Try
this.mockMvc.perform(post("/test").header("site",site).param("customer",customer).
param("table", table).content(compress(file)).contentType("application/octet-stream").param("loadStatus",loadStatus)
.with(user("user"))).andExpect(status().isOk());
I am trying to configure birt report in a spring boot applications, the client is an angular 2 application, here is where I run the report:
#PostConstruct
public void startUp() {
if(inputDir == null)
throw new RuntimeException("Cannot start application since birt report input directory was not specified.");
try {
EngineConfig engineConfig = new EngineConfig();
engineConfig.getAppContext().put("spring", this.context);
RegistryProviderFactory.releaseDefault();
Platform.startup(engineConfig);
IReportEngineFactory reportEngineFactory = (IReportEngineFactory) Platform.createFactoryObject(IReportEngineFactory.EXTENSION_REPORT_ENGINE_FACTORY);
birtReportEngine = reportEngineFactory.createReportEngine(engineConfig);
} catch (BirtException e) {
}
reportOutputDirectory = env.getProperty("birt_temp_file_output_dir");
}
#Override
public ByteArrayOutputStream runReport(Report birtReport) {
ByteArrayOutputStream byteArrayOutputStream;
File rptDesignFile;
try {
rptDesignFile = getReportFromFilesystem(birtReport.getName());
} catch (Exception e) {
throw new RuntimeException("Could not find report");
}
Map<String, String> parsedParameters = parseParametersAsMap(birtReport.getParameters());
byteArrayOutputStream = new ByteArrayOutputStream();
try {
IReportRunnable reportDesign = birtReportEngine.openReportDesign(rptDesignFile.getPath());
IRunTask runTask = birtReportEngine.createRunTask(reportDesign);
if (parsedParameters.size() > 0) {
for (Map.Entry<String, String> entry : parsedParameters.entrySet()) {
runTask.setParameterValue(entry.getKey(), entry.getValue());
}
}
runTask.validateParameters();
String rptdocument = reportOutputDirectory + File.separator
+ "generated" + File.separator
+ birtReport.getName() + ".rptdocument";
runTask.run(rptdocument);
IReportDocument reportDocument = birtReportEngine.openReportDocument(rptdocument);
IRenderTask renderTask = birtReportEngine.createRenderTask(reportDocument);
PDFRenderOption pdfRenderOption = new PDFRenderOption();
pdfRenderOption.setOption(IPDFRenderOption.REPAGINATE_FOR_PDF, new Boolean(true));
pdfRenderOption.setOption(IPDFRenderOption.PAGE_OVERFLOW, IPDFRenderOption.OUTPUT_TO_MULTIPLE_PAGES );
pdfRenderOption.setOption(IPDFRenderOption.PDF_TEXT_WRAPPING , true);
pdfRenderOption.setOption(IPDFRenderOption.PDF_HYPHENATION , true);
pdfRenderOption.setOutputFormat("pdf");
pdfRenderOption.setOutputStream(byteArrayOutputStream);
renderTask.setRenderOption(pdfRenderOption);
renderTask.render();
renderTask.close();
} catch (EngineException e) {
throw new RuntimeException();
}
return byteArrayOutputStream;
}
and this is the api service that returns the byte array:
#RequestMapping(value = "/birt", method = RequestMethod.POST)
public ResponseEntity<byte[]> getBIRTReport(#RequestBody ReportRequest reportRequest) {
byte[] reportBytes;
ResponseEntity<byte[]> responseEntity;
try {
reportBytes =
new BIRTReport(
reportRequest.getReportName(),
reportRequest.getReportParameters(),
reportRunner)
.runReport().getReportContent().toByteArray();
HttpHeaders httpHeaders = new HttpHeaders();
httpHeaders.setContentType(MediaType.parseMediaType("application/pdf"));
String fileName = reportRequest.getReportName() + ".pdf";
httpHeaders.setContentDispositionFormData(fileName, fileName);
httpHeaders.setCacheControl("must-revalidate, post-check=0, pre-check=0");
responseEntity = new ResponseEntity<byte[]>(reportBytes, httpHeaders, HttpStatus.OK);
} catch (Exception e) {
responseEntity = new ResponseEntity<byte[]>(HttpStatus.NOT_IMPLEMENTED);
return responseEntity;
}
return responseEntity;
}
and that is the angular 2 code:
public getReport():Observable<any>{
let params = {
"reportName":"my report name",
"reportParameters":"my params"
};
let headers = new Headers();
headers.append('Content-Type','application/json');
let options = new RequestOptions({headers: headers});
return this.http.post("http://localhost:8080/reports/birt",JSON.stringify(params), options);
}
call the service:
getReport(){
this.reportService.getReport().subscribe(
data => {
var blob = new Blob([data._body], { type: 'application/pdf'})
saveAs(blob, "myPdf.pdf");
var fileUrl = URL.createObjectURL(blob);
window.open(fileUrl);
}
)
}
This method returns a corrupt file, can anyone figure out the problem?
The problem is that you are missing responseType in options
let options = new RequestOptions({headers: headers, **responseType: ResponseContentType.Blob**});
After that you can just do
window['saveAs'](response.blob(), 'filename.zip');