How to get status for circuit breaker status with netflix hystrix? - java

This is my AppService Class, where I need to add logic for getting the status for the circuit breaker if it's open or closed but I am unable to find a way. Also, i have made use of ignoreExceptions but seems like trouble is there. Just new to coding and this feature and unable to get an appropriate answer. I am not sure how to use isCircuitBreakerOpen().
#Service
public class AppService {
private static final Logger LOG = LoggerFactory.getLogger(AppService.class);
private final RestTemplate restTemplate;
public AppService(RestTemplate rest) {
this.restTemplate = rest;
}
#HystrixCommand(fallbackMethod = "reliable", commandProperties= {
#HystrixProperty(name = HystrixPropertiesManager.CIRCUIT_BREAKER_ERROR_THRESHOLD_PERCENTAGE, value = "100"),
#HystrixProperty(name = HystrixPropertiesManager.CIRCUIT_BREAKER_SLEEP_WINDOW_IN_MILLISECONDS, value = "10000"),
#HystrixProperty(name = HystrixPropertiesManager.CIRCUIT_BREAKER_REQUEST_VOLUME_THRESHOLD, value = "10")
})
public ResponseEntity<String> answerList() throws Exception {
return callingDownStreamService404();
}
#HystrixCommand(fallbackMethod = "reliable", commandProperties= {
#HystrixProperty(name = HystrixPropertiesManager.CIRCUIT_BREAKER_ERROR_THRESHOLD_PERCENTAGE, value = "100"),
#HystrixProperty(name = HystrixPropertiesManager.CIRCUIT_BREAKER_SLEEP_WINDOW_IN_MILLISECONDS, value = "10000"),
#HystrixProperty(name = HystrixPropertiesManager.CIRCUIT_BREAKER_REQUEST_VOLUME_THRESHOLD, value = "10")
})
public ResponseEntity<String> answerList503() throws Exception {
return callingDownStreamService503();
}
private ResponseEntity<String> callingDownStreamService404() throws Exception {
URI uri = URI.create("http://localhost:8090/recommended/404");
RestTemplate restTemplate = new RestTemplate();
HttpHeaders headers = new HttpHeaders();
HttpEntity<Object> entity = new HttpEntity<Object>(headers);
ResponseEntity<String> out = restTemplate.exchange(uri, HttpMethod.GET, entity, String.class);
System.out.println("Application code : " + out.getStatusCode());
return out;
}
private ResponseEntity<String> callingDownStreamService503() throws Exception {
URI uri = URI.create("http://localhost:8090/recommended/503");
RestTemplate restTemplate = new RestTemplate();
HttpHeaders headers = new HttpHeaders();
HttpEntity<Object> entity = new HttpEntity<Object>(headers);
ResponseEntity<String> out = restTemplate.exchange(uri, HttpMethod.GET, entity, String.class);
System.out.println("Application code : " + out.getStatusCode());
if (out.getStatusCode().toString().startsWith("5")) {
throw new HystrixBadRequestException("bad request messageg");
}
return out;
}
#HystrixCommand(commandKey = "MyHystrixCommand",fallbackMethod = "myHystrixFallback", threadPoolKey = "ThreadPoolKey",commandProperties= {
#HystrixProperty(name = HystrixPropertiesManager.CIRCUIT_BREAKER_ERROR_THRESHOLD_PERCENTAGE, value = "100"),
#HystrixProperty(name = HystrixPropertiesManager.CIRCUIT_BREAKER_SLEEP_WINDOW_IN_MILLISECONDS, value = "10000"),
#HystrixProperty(name = HystrixPropertiesManager.CIRCUIT_BREAKER_REQUEST_VOLUME_THRESHOLD, value = "10")},
ignoreExceptions = {HttpServerErrorException.class, HystrixBadRequestException.class, HttpClientErrorException.class})
public ResponseEntity<String> getServiceCallResponse(String serviceUrl, HttpEntity<?> entity) {
serviceUrl = "http://localhost:8090/recommended/500";
ResponseEntity<String> resp = null;
try {
System.out.println("Calling -----" + serviceUrl);
resp = restTemplate.exchange(serviceUrl, HttpMethod.POST, entity, String.class);
}
catch(RestClientException e) {
System.out.println("Calling -----" + serviceUrl + "Exception is this" + e.getRootCause());
handleExceptionForHystrix("getServiceCallResponse", e);
}
return resp;
}
private void handleExceptionForHystrix(String function, Exception e) {
if (e instanceof HttpStatusCodeException) {
HttpStatus httpStatusCode = ((HttpStatusCodeException)e).getStatusCode();
if(httpStatusCode.equals(HttpStatus.BAD_REQUEST) || httpStatusCode.equals(HttpStatus.INTERNAL_SERVER_ERROR)) {
throw new HystrixBadRequestException("Hystrix Bad Request Exception Occurred" + httpStatusCode, e);
}
throw new RuntimeException(function, e);
}
throw new RuntimeException(function, e);
}
public ResponseEntity<String> myHystrixFallback(String serviceUrl, HttpEntity<?> entity, Throwable hystrixCommandExp) {
return new ResponseEntity<String>(HttpStatus.INTERNAL_SERVER_ERROR);
}
#Recover()
public ResponseEntity<String> reliable() {
return new ResponseEntity<String>(
"The downstream application is unavailable and the circuit is open", HttpStatus.OK);
}
}
this is the main class where i have placed the endpoints. I am also making use of AppStore which is the downstream app and same enpoints are configured there.
#EnableHystrixDashboard
#EnableCircuitBreaker
#RestController
#SpringBootApplication
public class DavinciCircuitbreakerApplication {
#Autowired
private AppService appService;
#Bean
public RestTemplate rest(RestTemplateBuilder builder) {
return builder.build();
}
#RequestMapping("/to-answer/404")
public ResponseEntity<String> toAnswer() {
ResponseEntity<String> response = null;
try{
response = appService.answerList();
}catch(Exception e){
System.out.println("excpetion"+ e.getMessage());
return new ResponseEntity<String>("failure", HttpStatus.valueOf(500));
}
return response;
}
#RequestMapping("/to-answer/503")
public ResponseEntity<String> toAnswer503() {
ResponseEntity<String> response = null;
try{
response = appService.answerList503();
}catch(Exception e){
System.out.println("excpetion"+ e.getMessage());
return new ResponseEntity<String>("failure", HttpStatus.valueOf(503));
}
return response;
}
#RequestMapping("/to-answer/500")
public ResponseEntity<String> toAnswer500() {
ResponseEntity<String> response = null;
try{
response = appService.getServiceCallResponse(null, response);
}catch(Exception e){
System.out.println("excpetion"+ e.getMessage());
return new ResponseEntity<String>("Internal Server Error", HttpStatus.valueOf(500));
}
return response;
}
public static void main(String[] args) {
SpringApplication.run(DavinciCircuitbreakerApplication.class, args);
}
}

You can use HystrixCircuitBreaker.Factory.getInstance(...) to get instance of HystrixCommand. Refer to link for more details.
Further you can call isCircuitBreakerOpen() on this HystrixCommand instance.

Related

How to pass an unknown incoming requestParam to a post in spring boot?

In my spring boot project I'am trying to intercept a rest api post in this way:
Rest Controller:
#Rest Controller
#RequestMapping("/")
public class FourStoreControllerInterface {
#ApiOperation(value = "Manage Multiple 4Store Post")
#ApiResponses(value = { #ApiResponse(code = 401, message = "Unauthorized"),
#ApiResponse(code = 403, message = "Forbidden") })
#PostMapping("**")
public ResponseEntity<?> manageMultiplePost4StoreWithRestTemplate(
#RequestParam #ApiParam(hidden = true) Map<String, String> allParams) throws Exception{
final String methodName = "manageMultiplePost4StoreWithRestTemplate()";
try {
startLog(methodName);
return fourStoreService.managePostEndpointsWithRestTemplate(allParams);
} catch (final Exception e) {
this.errorLog(methodName, e);
throw e;
} finally {
endLog(methodName);
}
}
}
Service:
#ResponseBody
public ResponseEntity<?> managePostEndpointsWithRestTemplate(Map<String, String> allParams) {
final String methodName = "managePostEndpointsWithRestTemplate(Map<String, String> allParams, JSONObject jsonParams)";
try {
startLog(methodName);
return managePost(allParams);
} catch (Exception e) {
logger.error(e.getMessage());
throw e;
} finally {
endLog(methodName);
}
}
managePost (method implemented in AbstractService):
public ResponseEntity<?> managePost(Map<String, String> allParams) {
try {
try {
logger.debug("I AM HERE WITH MAP");
// REQUEST 1
HttpServletRequest request = ((ServletRequestAttributes) RequestContextHolder.getRequestAttributes())
.getRequest();
Route routeConfiguration = findRootPosts(request);
if (routeConfiguration != null) {
String url = routeConfiguration.getDestination().getProtocol()
+ routeConfiguration.getDestination().getIp() + ":"
+ routeConfiguration.getDestination().getPort() + request.getRequestURI();
boolean first = true;
for (String key : allParams.keySet()) {
logger.debug("OLD ALL PARAMETERS : {} ", key + "=" + allParams.get(key));
}
HttpHeaders headers = new HttpHeaders();
headers.setBasicAuth(routeConfiguration.getDestination().getUsername(),
routeConfiguration.getDestination().getPassword());
for (String headersName : Collections.list(request.getHeaderNames())) {
List<String> headersValue = Collections.list(request.getHeaders(headersName));
headers.put(headersName, headersValue);
logger.debug(" REQUEST 1 HEADERS : {} = {} ", headersName, headersValue);
}
for (Cookie c : request.getCookies()) {
logger.debug(" REQUEST 1 COOKIES : {} = {} ", c.getName(), c.getValue());
}
MultiValueMap<String, String> map = new LinkedMultiValueMap<String, String>();
// map.putAll(headers);
for (String key : allParams.keySet()) {
map.put(key, Arrays.asList(allParams.get(key)));
}
logger.debug("MAP OF PARAMETERS : {} ", map);
// REQUEST 2
HttpEntity<MultiValueMap<String, String>> request2;
if (allParams != null && !allParams.isEmpty())
request2 = new HttpEntity<MultiValueMap<String, String>>(map, headers);
else
request2 = new HttpEntity(headers);
logger.debug("BODY REQUEST 2: {} ", request2.getBody());
if (url.startsWith("https")) {
restTemplate = getRestTemplateForSelfSsl();
} else {
// restTemplate = new RestTemplate();
}
logger.debug("URL POST: {} ", url);
UriComponents uriComponents = UriComponentsBuilder.fromHttpUrl(url).build(true);
ResponseEntity<?> response;
if (xssResponseFilter) {
response = restTemplate.exchange(new URI(uriComponents.toUriString()), HttpMethod.POST,
request2, String.class);
} else {
response = restTemplate.exchange(new URI(uriComponents.toUriString()), HttpMethod.POST,
request2, byte[].class);
}
HttpStatus statusCode = response.getStatusCode();
logger.debug("STATUS POST: {} ", statusCode);
HttpHeaders responseHeaders = response.getHeaders();
logger.debug("RESPONSE HEADERS : {} ", responseHeaders);
logger.debug("RESPONSE POST: {} ", response);
if (xssResponseFilter) {
response = sanitizeResponseBody((ResponseEntity<String>) response);
}
return response;
}
} catch (HttpStatusCodeException e) {
logger.error(e.getMessage());
return ResponseEntity.status(e.getStatusCode()).body(e.getResponseBodyAsByteArray());
}
} catch (Exception e) {
logger.error(e.getMessage());
return ResponseEntity.status(HttpStatus.INTERNAL_SERVER_ERROR).body(e.getMessage());
}
return ResponseEntity.status(HttpStatus.NOT_FOUND).body("Not valid route found");
}
With some POST I have no problems, in fact I get 200, and I can also see all the parameters that are present in the map that I pass in input ... with other POST I get error 400 BAD REQUEST and I notice that the map of the input parameters comes to me printed blank. How can I solve the problem?
In my opinion the problem concerns the fact that at the entrance I find myself an empty map ... what should I do in these cases?
add #RestController annotation in the rest controller class.

Mockito doReturn throws Null Pointer Exception

I'm trying to mock a method call from class called RestClient in another called DiscoveryAdapter but as and when i'm trying to do a doReturn it throws a null pointer exception.
In test i'm trying to spy the restClient object in order to mock the method call in DiscoveryAdapter.discovery method but with it throws a null pointer exception when doReturn is called.
Please check the code below.
RestClient.class
#Component
#Scope("prototype")
public class RestClient {
private static final Logger logger = LoggerFactory.getLogger(RestClient.class);
private RestTemplate restTemplate = null;
private PoolingHttpClientConnectionManager syncConnectionManager;
public void init() {
restTemplate = new RestTemplate(new HttpComponentsClientHttpRequestFactory(buildhttpClient()));
}
public String queryRestEndpoints(HereMapsImpl mapType,String basePath,boolean isSSl) {
URI uriObject = null;
String uriPath = mapType.returnUri();
init();
try {
uriObject = RestUtils.buildUriFromString(basePath, isSSl, uriPath);
} catch (URISyntaxException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
logger.info("rest api is {}",uriObject);
//spring api
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.APPLICATION_JSON);
headers.setAccept(Arrays.asList(MediaType.APPLICATION_JSON));
HttpEntity<String> requestEntity = new HttpEntity<String>("",headers);
//rest api call with uriObject
ResponseEntity<String> responseEntity = restTemplate.exchange(uriObject,
HttpMethod.GET, requestEntity, String.class);
if(responseEntity.getStatusCodeValue() >=400 || responseEntity.getStatusCodeValue() <= 500)
logger.info("failed with status code {}",responseEntity.getStatusCodeValue() );
logger.info("checking my response");
logger.info("checking my response here {}",responseEntity.getBody());
return responseEntity.getBody();
}
private CloseableHttpClient buildhttpClient() {
CloseableHttpClient httpClient = null;
httpClient = HttpClientBuilder.create().setConnectionManager(getSyncConnectionManager())
.build();
return httpClient;
}
public PoolingHttpClientConnectionManager getSyncConnectionManager() {
syncConnectionManager = new PoolingHttpClientConnectionManager();
return syncConnectionManager;
}
DisoveryAdapter.class
#Component
public class DisoveryAdapter {
private static final Logger log = LoggerFactory.getLogger(DisoveryAdapter.class);
#Autowired
private RestClient restClient;
public void discovery() {
log.info("starting thread");
String response = restClient.queryRestEndpoints(eatDrink, completeUriPath, true);
log.info("oeat drink response {}",response);
}
}
DiscoveryAdapterTest.class
class HereMapsCheckImpTest {
private static final Logger log = LoggerFactory.getLogger(HereMapsCheckImpTest.class);
private RestClient restClient;
private HereMapsCheckImp hereMaps;
#Before
public void init() {
hereMaps = new HereMapsCheckImp();
restClient = new RestClient();
}
#Test
public void test() {
RestClient spyRestClient = spy(restClient);
log.info("with spring {}",spyRestClient);
doReturn("{\n" +
" color: \"red\",\n" +
" value: \"#f00\"\n" +
"}").when(spyRestClient).queryRestEndpoints(any(),any(),any());
hereMaps.discovery();
verify(spyRestClient).queryRestEndpoints(any(),any(),any());
}
}

Getting null in Environment variable

#Configuration
public class CustomRemoteTokenService implements ResourceServerTokenServices {
private static final Logger logger = LoggerFactory.getLogger(CustomRemoteTokenService.class);
#Resource
Environment environment;
private RestOperations restTemplate;
private String checkTokenEndpointUrl;
private String clientId;
private String clientSecret;
private String tokenName = "token";
private AccessTokenConverter tokenConverter = new DefaultAccessTokenConverter();
#Autowired
public CustomRemoteTokenService() {
restTemplate = new RestTemplate();
((RestTemplate) restTemplate).setErrorHandler(new DefaultResponseErrorHandler() {
#Override
// Ignore 400
public void handleError(ClientHttpResponse response) throws IOException {
if (response.getRawStatusCode() != 400
&& response.getRawStatusCode() != 403 /* && response.getRawStatusCode() != 401 */) {
super.handleError(response);
}
}
});
}
public void setRestTemplate(RestOperations restTemplate) {
this.restTemplate = restTemplate;
}
public void setCheckTokenEndpointUrl(String checkTokenEndpointUrl) {
this.checkTokenEndpointUrl = checkTokenEndpointUrl;
}
public void setClientId(String clientId) {
this.clientId = clientId;
}
public void setClientSecret(String clientSecret) {
this.clientSecret = clientSecret;
}
public void setAccessTokenConverter(AccessTokenConverter accessTokenConverter) {
this.tokenConverter = accessTokenConverter;
}
public void setTokenName(String tokenName) {
this.tokenName = tokenName;
}
#Override
public OAuth2Authentication loadAuthentication(String accessToken)
throws AuthenticationException, InvalidTokenException, GenericException {
/*
* This code needs to be more dynamic. Every time an API is added we have to add
* its entry in the if check for now. Should be changed later.
*/
HttpServletRequest request = Context.getCurrentInstance().getRequest();
MultiValueMap<String, String> formData = new LinkedMultiValueMap<String, String>();
formData.add(tokenName, accessToken);
formData.add("api", environment.getProperty("resource.api"));
/* formData.add("api", "5b64018880999103244f1fdd");*/
HttpHeaders headers = new HttpHeaders();
headers.set("Authorization", getAuthorizationHeader(clientId, clientSecret));
Map<String, Object> map = null;
try {
map = postForMap(checkTokenEndpointUrl, formData, headers);
} catch (ResourceAccessException e) {
logger.error("Socket Exception occured at " + System.currentTimeMillis() + "for client_id : " + clientId);
GenericException ge = new GenericException(
"Could not validate your access token. If this occurs too often please contact MapmyIndia support at apisupport#mapmyindia.com");
ge.setHttpErrorCode(504);
ge.setOauthError("Access Token validation failed");
throw ge;
}
if (map.containsKey("error")) {
logger.error("check_token returned error: " + map.get("error") + " for client id : " + clientId);
String temp = map.get("error").toString();
GenericException ge = new GenericException(map.get("error_description").toString());
ge.setHttpErrorCode(Integer.parseInt(map.get("responsecode").toString()));
ge.setOauthError(temp);
switch (temp) {
case "invalid_token":
throw new InvalidTokenException(accessToken);
default:
throw ge;
}
}
Assert.state(map.containsKey("client_id"), "Client id must be present in response from auth server");
return tokenConverter.extractAuthentication(map);
}
#Override
public OAuth2AccessToken readAccessToken(String accessToken) {
throw new UnsupportedOperationException("Not supported: read access token");
}
private String getAuthorizationHeader(String clientId, String clientSecret) {
String creds = String.format("%s:%s", clientId, clientSecret);
try {
return "Basic " + new String(Base64.encode(creds.getBytes("UTF-8")));
} catch (UnsupportedEncodingException e) {
throw new IllegalStateException("Could not convert String");
}
}
private Map<String, Object> postForMap(String path, MultiValueMap<String, String> formData, HttpHeaders headers)
throws RestClientException {
if (headers.getContentType() == null) {
headers.setContentType(MediaType.APPLICATION_FORM_URLENCODED);
}
#SuppressWarnings("rawtypes")
Map map = restTemplate.exchange(path, HttpMethod.POST,
new HttpEntity<MultiValueMap<String, String>>(formData, headers), Map.class).getBody();
#SuppressWarnings("unchecked")
Map<String, Object> result = map;
return result;
}
}
I autowired Environment and getting null when I do environment.getProperty("resource.api");
It is always returning null but in another classes I autowire Environment and successfully retrieve the value from properties.
You have to take this steps :
1.Register a Properties
You need to register you properties file by #PropertySource("classpath:foo.properties") as :
#Configuration
#PropertySource("classpath:foo.properties")
public class CustomRemoteTokenService implements ResourceServerTokenServices {
//...
}
2.Injecting Properties
To obtain the value of a property with the Environment API:
#Autowired
private Environment env;

Rest-Api Call Other Rest-Api In Spring boot Not Working for (Multipart-File)

I need your help. I have 2 Api in Same Class both use for Upload the file. I'm trying to upload the file from 1 api to other api by using of RestTemplate but it's show error like.
Error :- MessageType definition error: [simple type, class java.io.FileDescriptor]; nested exception is com.fasterxml.jackson.databind.exc.InvalidDefinitionException: No serializer found for class java.io.FileDescriptor and no properties discovered to create BeanSerializer (to avoid exception, disable SerializationFeature.FAIL_ON_EMPTY_BEANS) (through reference chain: org.springframework.web.multipart.support.StandardMultipartHttpServletRequest$StandardMultipartFile["inputStream"]->java.io.FileInputStream["fd"])
File Store Api Not Calling through RestTemplate due to above error.
API-1:- File Store Api
#RequestMapping(value = PathConst.UPLOAD_MULTIPART_FILE, method = RequestMethod.POST)
public ResponseEntity<?> uploadMultipleFiles(#RequestPart("files") #NotNull List<MultipartFile> files) {
try {
this.apiResponse = new APIResponse();
// Note :- 'here this upload file dto help to collect the non-support file info'
List<UploadFileDto> wrongTypeFile = files.stream().
filter(file -> {
return !isSupportedContentType(file.getContentType());
}).map(file -> {
UploadFileDto wrongTypeFileDto = new UploadFileDto();
wrongTypeFileDto.setSize(String.valueOf(file.getSize()));
wrongTypeFileDto.setFileName(file.getOriginalFilename());
wrongTypeFileDto.setContentType(file.getContentType());
return wrongTypeFileDto;
}).collect(Collectors.toList());
if(!wrongTypeFile.isEmpty()) { throw new FileStorageException(wrongTypeFile.toString()); }
this.apiResponse.setReturnCode(HttpStatus.OK.getReasonPhrase());
this.apiResponse.setMessage("File Store Success full");
this.apiResponse.setEntity(
files.stream().map(file -> {
String fileName = this.fileStoreManager.storeFile(file);
String fileDownloadUri = ServletUriComponentsBuilder.fromCurrentContextPath().path(PathConst.FILE + PathConst.DOWNLOAD_FILE).path(fileName).toUriString();
UploadFileDto uploadFile = new UploadFileDto();
uploadFile.setFileName(fileName);
uploadFile.setUrl(fileDownloadUri);
uploadFile.setSize(String.valueOf(file.getSize()));
return uploadFile;
}).collect(Collectors.toList()));
}catch (Exception e) {
System.out.println("Message" + e.getMessage());
this.errorResponse = new ExceptionResponse();
this.errorResponse.setErrorCode(HttpStatus.BAD_REQUEST.getReasonPhrase());
this.errorResponse.setErrorMessage("Sorry! Filename contains invalid Type's,");
this.errorResponse.setErrors(Collections.singletonList(e.getMessage()));
return new ResponseEntity<ExceptionResponse>(this.errorResponse, HttpStatus.BAD_REQUEST);
}
return new ResponseEntity<APIResponse>(this.apiResponse, HttpStatus.OK);
}
API-2:- Product Store Api With List Of Image File
#RequestMapping(value = "/save/product", method = RequestMethod.POST)
public ResponseEntity<?> saveProduct(#Valid #RequestPart("request") ProductDto productDto, #RequestPart("files") #NotNull List<MultipartFile> files) {
try {
this.apiResponse = new APIResponse();
this.restTemplate = new RestTemplate();
if(!files.isEmpty()) { new NullPointerException("List of File Empty"); }
// call-api of File controller
try {
// file's
MultiValueMap<String, Object> body = new LinkedMultiValueMap<>();
files.stream().forEach(file -> { body.add("files", file); });
// header-type
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.MULTIPART_FORM_DATA);
// request real form
HttpEntity<MultiValueMap<String, Object>> request = new HttpEntity<>(body, headers);
// request-url
this.RESOURCE_URL = ServletUriComponentsBuilder.fromCurrentContextPath().path(PathConst.FILE + PathConst.UPLOAD_MULTIPART_FILE).toUriString();
// response-result
System.out.println(this.restTemplate.exchange(this.RESOURCE_URL, HttpMethod.POST, request, Object.class).getStatusCode());
// if(!response.getStatusCode().equals(200)) {
// // error will send
// }
}catch (NullPointerException e) {
throw new NullPointerException("Product Image's Not Save Scuessfully. " + e);
}
}catch (Exception e) {
System.out.println("Message" + e.getMessage());
this.errorResponse = new ExceptionResponse();
this.errorResponse.setErrorCode(HttpStatus.NO_CONTENT.getReasonPhrase());
this.errorResponse.setErrorMessage(e.getMessage());
return new ResponseEntity<ExceptionResponse>(this.errorResponse, HttpStatus.BAD_REQUEST);
}
return new ResponseEntity<APIResponse>(this.apiResponse, HttpStatus.OK);
}
Main Code :-
try {
// file's
MultiValueMap<String, Object> body = new LinkedMultiValueMap<>();
files.stream().forEach(file -> { body.add("files", file); });
// header-type
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.MULTIPART_FORM_DATA);
// request real form
HttpEntity<MultiValueMap<String, Object>> request = new HttpEntity<>(body, headers);
// request-url
this.RESOURCE_URL = ServletUriComponentsBuilder.fromCurrentContextPath().path(PathConst.FILE + PathConst.UPLOAD_MULTIPART_FILE).toUriString();
// response-result
System.out.println(this.restTemplate.exchange(this.RESOURCE_URL, HttpMethod.POST, request, Object.class).getStatusCode());
//if(!response.getStatusCode().equals(200)) {
// // error will send
//}
}catch (NullPointerException e) {
throw new NullPointerException("Product Image's Not Save Scuessfully. " + e);
}
I was facing the same issue , but using the below code i fixed it.
#RequestMapping("/upload")
public void postData(#RequestParam("file") MultipartFile file) throws IOException {
String url = "https://localhost:8080/upload";
MultiValueMap<String, Object> bodyMap = new LinkedMultiValueMap<>();
bodyMap.add("file", new FileSystemResource(convert(file)));
HttpHeaders headers = new HttpHeaders();
headers.setContentType(MediaType.MULTIPART_FORM_DATA);
HttpEntity<MultiValueMap<String, Object>> requestEntity = new HttpEntity<>(bodyMap, headers);
RestTemplate restTemplate = new RestTemplate();
ResponseEntity<String> response = restTemplate.exchange(url,
HttpMethod.POST, requestEntity, String.class);
}
public static File convert(MultipartFile file)
{
File convFile = new File(file.getOriginalFilename());
try {
convFile.createNewFile();
FileOutputStream fos = new FileOutputStream(convFile);
fos.write(file.getBytes());
fos.close();
} catch (IOException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
return convFile;
}
I solve this issue by adding the these line's
files.stream().forEach(file -> {
System.out.println(file.getOriginalFilename());
Resource resouceFile = new FileSystemResource(file.getBytes(), file.getOriginalFilename());
body.add("files", resouceFile);
});
public static class FileSystemResource extends ByteArrayResource {
private String fileName;
public FileSystemResource(byte[] byteArray , String filename) {
super(byteArray);
this.fileName = filename;
}
public String getFilename() { return fileName; }
public void setFilename(String fileName) { this.fileName= fileName; }
}
Make use of multipartFile.getResource() - neat and simple solution
public void exFunction(MultipartFile multipartFile) throws IOException {
Resource multipartFile = multipartFile.getResource();
LinkedMultiValueMap<String, Object> parts = new LinkedMultiValueMap<>();
parts.add("file", multipartFile);
HttpHeaders httpHeaders = new HttpHeaders();
httpHeaders.setContentType(MediaType.MULTIPART_FORM_DATA);
HttpEntity<LinkedMultiValueMap<String, Object>> httpEntity = new
HttpEntity<>(parts, httpHeaders);
restTemplate.postForEntity("my/url", httpEntity, SommeClass.class);
}

Spring Boot RestTemplate.postForObject to Firebase Messaging not returning

I'm trying to tie Google's Firebase Messaging platform into my app, and I'm trying to use Spring's built in RestTemplate REST abstraction to simplify it.
I'm currently trying to:
RestTemplate restTemplate = new RestTemplate();
restTemplate.getMessageConverters().add(new GsonHttpMessageConverter());
MultiValueMap<String, String> headers = new LinkedMultiValueMap<>();
headers.add("Authorization", "key=" + Constants.FIREBASE_SERVER_KEY);
headers.add("Content-Type", "application/json");
HttpEntity<FireBasePost> entity = new HttpEntity<>(fbp, headers);
URI uri;
uri = new URI(firebaseApi);
FireBaseResponse fbr = restTemplate.postForObject(uri, entity, FireBaseResponse.class);
The FireBasePost object just contains the required fields for the POST Message API: Firebase API - and I have verified the request Entity works by posting with String.class, so the response is unmarshalled JSON.
However, with trying to get the response to marshall directly into the FireBaseResponse object, the call to postForObject hangs and never returns.
#JsonIgnoreProperties(ignoreUnknown = true)
public class FireBaseResponse {
public Integer multicast_id;
public Integer success;
public Integer failure;
public Integer canonical_ids;
public FireBaseResponse() {}
}
I'm having trouble understanding why this call never completes. I would love to be able to have the response directly into an object.
try like this:
package yourpackage;
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
#JsonIgnoreProperties(ignoreUnknown = true)
public class FirebaseResponse {
private long multicast_id;
private Integer success;
private Integer failure;
private Object canonical_ids;
public FirebaseResponse() {
}
//---- use this one ----
public boolean is_success() {
if (getSuccess() == 1) {
return true;
} else {
return false;
}
}
public long getMulticast_id() {
return multicast_id;
}
public void setMulticast_id(long multicast_id) {
this.multicast_id = multicast_id;
}
public Integer getSuccess() {
return success;
}
public void setSuccess(Integer success) {
this.success = success;
}
public Integer getFailure() {
return failure;
}
public void setFailure(Integer failure) {
this.failure = failure;
}
public Object getCanonical_ids() {
return canonical_ids;
}
public void setCanonical_ids(Object canonical_ids) {
this.canonical_ids = canonical_ids;
}
#Override
public String toString() {
return "FirebaseResponse{" +
"multicast_id=" + multicast_id +
", success=" + success +
", failure=" + failure +
", canonical_ids=" + canonical_ids +
'}';
}
}
//--------------- USAGE ------------------
ArrayList<ClientHttpRequestInterceptor> interceptors = new ArrayList<>();
interceptors.add(new HeaderRequestInterceptor("Authorization", "key=" + FIREBASE_SERVER_KEY));
interceptors.add(new HeaderRequestInterceptor("Content-Type", "application/json"));
restTemplate.setInterceptors(interceptors);
JSONObject body = new JSONObject();
// JsonArray registration_ids = new JsonArray();
// body.put("registration_ids", registration_ids);
body.put("to", "cfW930CZxxxxxxxxxxxxxxxxxxxxxxxxxxipdO-bjHLacHRqQzC0aSXlRFKdMHv_aNBxkRZLNxxxxxxxxxxx59sPW4Rw-5MtwKkZxxxxxxxgXlL-LliJuujPwZpLgLpji_");
body.put("priority", "high");
// body.put("dry_run", true);
JSONObject notification = new JSONObject();
notification.put("body", "body string here");
notification.put("title", "title string here");
// notification.put("icon", "myicon");
JSONObject data = new JSONObject();
data.put("key1", "value1");
data.put("key2", "value2");
body.put("notification", notification);
body.put("data", data);
HttpEntity<String> request = new HttpEntity<>(body.toString());
FirebaseResponse firebaseResponse = restTemplate.postForObject("https://fcm.googleapis.com/fcm/send", request, FirebaseResponse.class);
log.info("response is: " + firebaseResponse.toString());
return new ResponseEntity<>(firebaseResponse.toString(), HttpStatus.OK);
//--------------- HELPER CLASS ------------------
import org.springframework.http.HttpRequest;
import org.springframework.http.client.ClientHttpRequestExecution;
import org.springframework.http.client.ClientHttpRequestInterceptor;
import org.springframework.http.client.ClientHttpResponse;
import org.springframework.http.client.support.HttpRequestWrapper;
import java.io.IOException;
public class HeaderRequestInterceptor implements ClientHttpRequestInterceptor {
private final String headerName;
private final String headerValue;
public HeaderRequestInterceptor(String headerName, String headerValue) {
this.headerName = headerName;
this.headerValue = headerValue;
}
#Override
public ClientHttpResponse intercept(HttpRequest request, byte[] body, ClientHttpRequestExecution execution) throws IOException {
HttpRequest wrapper = new HttpRequestWrapper(request);
wrapper.getHeaders().set(headerName, headerValue);
return execution.execute(wrapper, body);
}
}

Categories