Hi friends I am using Angularjs and rest-servies but when I am calling rest services from service.js file something is goning wrong and it is throwing 400(bad request )
main.js
garantiesService.getTarifs($scope.recap.ageDirigeant,$scope.selectedCompany.zipcode)
.success(function(){
console.log('in success');
})
service.js
healthApp.factory('garantiesService', ['$http', function($http) {
var service = {
getTarifs: function(age,zipcode)
{
console.log("age : "+age);
console.log("zipcode : "+zipcode);
var directorHealthInsuranceInfo = {};
directorHealthInsuranceInfo.age=age;
directorHealthInsuranceInfo.department=zipcode;
return $http.post('rest-service/quotes/health /director',directorHealthInsuranceInfo);
}
};
return service;
HealthInsuranceController.java
#Controller
public class HealthInsuranceQuoteResource {
#RequestMapping("quotes/health/director")
#ResponseBody
public String quoteDirector(#RequestBody DirectorHealthInsuranceInfo info) {
System.out.println("------HealthInsuranceQuoteResult------");
return "hi";
}
DirectorHealthInsuranceInfo.java
#Value
public class DirectorHealthInsuranceInfo {
private String department;
private int age;
}
when I am sending the request it is throwing Bad Request 400 error.
I see that there is a space in the url you supplied to the http.post method.
"rest-service/quotes/health /director"
I don't know if that is causing it.
But I also see that you POST your request to the service. Are you sure that your endpoint has been set up for POST requests?
I would recommend creating a basic endpoint that you call with a GET request, and no parameters. Just to root out the problem.
Related
I am looking for a way to get an Endpoint in Springboot that catches all requests send to /. Ideally everything behind / should be handed in as a String parameter.
An example request could look like this: http://myproxy.com/foo/bar?blah=blubb
I tried a RestController for /
#RestController
public class ProxyRestController {
#RequestMapping("/{restOfPath}", method = RequestMethod.GET)
public ResponseEntity<String> handleGetRequests(#PathVarialbe("restOfPath") String path) {
return ResponseEntity.of(Optional.of(""));
}
}
The endpoint doesn't catch the example because it would be routed to /foo/bar whereas /foo is caught.
How would I achieve a "catch all" endpoint in SpringBoot? It could also be in another way than a #RestController I just need to be inside a component and send a http response back to the caller.
Adapt this code to match yours:
#Controller
public class RestController {
#RequestMapping(value = "/**/{path:.*}")
public String index(final HttpServletRequest request) {
final String url = request.getRequestURI();
return "something";
}
}
I am trying to access the POST API from my spring app to angular but little bit confused how to use and access the given API in my angular app.
Spring REST API
#RequestMapping(value = "/getWelcomeMessage", method = RequestMethod.POST)
public String getLoginWelcomeMessage() {
return details.getLoginWelcomeMessage();
}
The given API is fetching the welcome message details from my oracle DB and returning a string value. I am trying to access the given REST API in my angular code through services. I had define the post service as follows
export class LoginService {
constructor(private http : HttpClient) { }
welcomeMessageService(){
const headers = {'content-type':'application/text'}
return this.http.put("http://localhost:8080/API/getWelcomeMessage",null,
{'headers':headers});
}
}
As the post method requires three arguments URL, Body and header. But in my case my spring REST API doesn't contain any body and returning a string. So, I had define the body as null and change the header type to text as it is JASON by default.
At last, I am trying to access the given service method by injecting it in my component as follows-
export class LoginComponent implements OnInit {
message:string;
constructor(private loginService : LoginService) { }
ngOnInit(): void {
this.loginService.welcomeMessageService().subscribe(
response =>{
console.log(response);
this.message = response;
}
)
}
}
But when I am trying to assign the response to the string I am getting the error that string cannot be assigned to the object. I am little bit confused why this error is occurring as I had also changed the header type to string while defining my service but still getting the error.
It can be a great help if anybody guide me regarding this as I am new to angular and little bit confused with integration part of API with angular.
Use { responseType: 'text' } and also send an empty body not null
export class LoginService {
constructor(private http : HttpClient) { }
welcomeMessageService(){
return this.http.put("http://localhost:8080/API/getWelcomeMessage",{},
{ responseType: 'text' });
}
}
Maybe you have copied the function wrong but check also here
#RequestMapping(value = "/getWelcomeMessage", method = RequestMethod.POST)
public String getLoginWelcomeMessage() {
return details.getLoginWelcomeMessage();
}
This is a Post method not a put that you are trying to call
As for cors error add the following to the backend just above #Controller or #RestControler whatever you have
#CrossOrigin(value = {"http://localhost:4200"}, methods = {GET,POST,PUT,DELETE})
Hello I'm trying to create a POST method and I keep getting the "404 Request method 'GET' not supported" error. Below I'll post my Rest controller and below that I'll post my service class. The only thing not working is the #PostMapping method.
#RequestMapping("/ATM")
public class ATMController {
private ATMService atmService;
#Autowired
public ATMController(ATMService atmService) {
this.atmService = atmService;
}
#GetMapping(path = "/{id}")
public ATM getATMById(#PathVariable long id){
return atmService.getByID(id);
}
#PostMapping(path = "/{id}/withdraw/{amount}")
public List<Bill> withdrawMoney(#PathVariable long id,#PathVariable float amount){
return atmService.withdrawMoney(id,amount);
}
}
#Service
public class ATMService {
private ATMRepository atmRepository;
private BillRepository billRepository;
#Autowired
public ATMService(ATMRepository atmRepository, BillRepository billRepository) {
this.atmRepository = atmRepository;
this.billRepository = billRepository;
}
public void save(ATM atm) {
atmRepository.save(atm);
}
public ATM getByID(Long id) {
return atmRepository.findById(id).get();
}
public List<Bill> getBillList(Long id) {
return atmRepository.findById(id).get().getBillList();
}
#Transactional
public List<Bill> withdrawMoney(Long id, float amount) {
List<Bill> allBills = getBillList(id);
List<Bill> billsToWithdraw = new ArrayList<>();
float amountTransferred = 0;
for (Bill bill : allBills) {
if (bill.getValue() == 100) {
billsToWithdraw.add(bill);
amountTransferred += bill.getValue();
}
if (amountTransferred == amount) {
for (Bill billToWithdraw : billsToWithdraw) {
billRepository.delete(billToWithdraw);
}
return billsToWithdraw;
}
}
return null;
}
}
I don't see the issue, I've tried switching to #GetMapping and removed the actual transaction "billRepository.delete(billToWithdraw);" and the method then returns the correct bills.
As the error says 404 Request method 'GET' not supported means you are making a GET request instead of POST.
You can make use of tools like Postman to make a post request. Hitting /{id}/withdraw/{amount} via any browser will prompt a GET request and not a POST request.
The issue is that you are sending a GET request to an end point that is configured to accept only POST request. This will probably help you to test them.
How to test
In case you GET requests -
You CAN directly check the api from the browser address bar. Type in the api and hit enter.Its that Simple!
You can use a tool such as Postman, SoapUI, etc to send a GET request.
You could write an html form with action="get mapping uri" and method="GET"
If your API uses any documentation or design tools such as swagger you can test it from its interface.
In case you POST requests -
You CANNOT directly check the api from the browser address bar.
You can use a tool such as Postman, SoapUI to send a POST request.
You could write an html form with action="post mapping uri" and method="POST".
If your API uses any documentation or design tools such as swagger you can test it from its interface.
In my case the problem was that I called https://localhost:8080/my-service but the port 8080 not supports HTTPS so I changed my call to http://localhost:8080 and resolved my problem. However when calling a http with https spring makes internally a GET Request
I consider using fluent-http in a project.
I started with a simple "login/password" page. I create a simple POJO with fields login and password :
public class LoginRequest() {
private String login;
private String password;
//...
}
And I send it to fluent-http via a Resource :
#Prefix("/user")
public class PersonResource {
#Post("/")
public String get(LoginRequest loginRequest) {
//[...]
}
}
And it works well :)
Now, I wondered if it was possible to send a response with code HTTP 200 in case of success and code HTTP 401 in case of failure.
So I tried to inject the Response :
#Post("/")
public String login(LoginRequest loginRequest, Response response) {
if(loginRequest.getPassword().equals("helloworld")) {
response.setStatus(200);
return "SUCCESS";
} else {
response.setStatus(401);
return "ERROR";
}
}
The correct String is returned but the status code does not seem to be used. In both cases, the response has a code HTTP 200.
Note : I found that some status code are pre-implemented :
In case of exception, a code 500 is returned.
In case of resource not found, a code 400 is returned.
Any idea?
If you want to change the default content-type, status or headers, the method should return a net.codestory.http.payload.Payload.
Here's what you should write:
#Post("/")
public Payload login(LoginRequest loginRequest) {
if(!loginRequest.getPassword().equals("helloworld")) {
return new Payload("ERROR").withCode(HttpStatus.UNAUTHORIZED);
}
return new Payload("SUCCESS").withCode(HttpStatus.CREATED);
}
I have question that interest me.
Assume that I have some rest controller and some rest client writing in javascript. This client send request to a controller and during a processing occur some error. How should behave controller in this situation? Should return null? or string with message?
For example, We have controller like this:
#RequestMapping("/user", method = RequestMethod.POST)
public #ResponseBody String createUser(User user) {
try {
userService.create(user);
} catch(UserCreationException e) {
}
}
This is very simple example but is many different examples of controllers like controller which return some resources or only change state on the server side and I don't know what to do when occur error.
in improving developer(your consumers) experience , it is a good idea to respond with appropriate error messages on the response body in addition to the Http status code.
Here is an example with spring, mainly throw an exception that you can deal with by extending ResponseEntityExceptionHandler #ControllerAdvice
#ResponseStatus(HttpStatus.NOT_FOUND)
public class ResourceNotFoundException extends RuntimeException{
private static final long serialVersionUID = 1L;
public ResourceNotFoundException(String message) {
super(message);
}
}
#Controller
#RequestMapping("/XXXXXs")
public class DoctypesController {
#RequestMapping( method = RequestMethod.GET , value="/xxx")
public ResponseEntity<?> getXXXXXX(HttpServletRequest request) {
if (XXX == null ) {
throw new ResourceNotFoundException("XXXX Not found for);
}else{
response = buildResponse(xxxx)
}
return response;
}
}
#ControllerAdvice
public class XXXXEntityExceptionHandler extends ResponseEntityExceptionHandler {
#ExceptionHandler(value = { ResourceNotFoundException.class })
protected ResponseEntity<Object> handleMissingResource(RuntimeException ex, final WebRequest request) {
HttpStatus status = HttpStatus.NOT_FOUND;
return new ResponseEntity<Object>(new Error(String.valueOf(status.value()), status.getReasonPhrase(),ex.getMessage()),status);
}
}
According http specifications, the server must return a error code >= 500 in case of internal error during processing.
If the error is caused because the client did a wrong request : the server must return a error code >= 400 and < 500
Of course, on client side you must take care to handle those errors properly (i.e. displaying a friendly error message or something like that).
You should really use the HTTP Error codes and handle the HTTP error codes using your client-side technology, ie. JavaScript in your case.
For example: given a user who is unauthorised to read/access a Resource, then the 403 error code should be returned to the client. By using the standard HTTP/REST Error codes, you conform to an API that can be understood by any client, whether JavaScript or something else.
With Spring MVC and Rest controllers, it's really easy. Create a simple class for your Exception and annotate the class with the HTTP Error code, e.g. #ResponseStatus(value = HttpStatus.FORBIDDEN) for a 403 error. Then in your Controller, you can throw the exception which would in turn return the HTTP error code.