I have added the swagger config class as below,
#Configuration
#SecurityScheme(
name = "Bearer Authentication",
type = SecuritySchemeType.HTTP,
bearerFormat = "JWT",
scheme = "bearer"
)
public class SwaggerConfig {
#Bean
public OpenAPI customOpenAPI() {
return new OpenAPI().info(new Info().title("Tutor Student API")
.version("1.0.0")
.description("Desc"));
}
And in the controller I have added like this.
#CrossOrigin("*")
#RestController
#RequestMapping("/api/v1/tutors/")
#SecurityRequirement(name = "bearerAuth")
public class tutorController {
#PostMapping(save")
public ResponseEntity<TutorResponse> saveTutor(Authentication authentication,
#Valid #RequestBody(required = true) Tutor tutor, BindingResult bindingResult) {
Here after all these changes still I can submit a post request without the Bearer token and get 200 Success response.
In the controller :
#SecurityRequirement(name = "bearerAuth") has to name the right requirement name :
try :
#SecurityRequirement(name = "Bearer Authentication")
Regards
Related
I have a requirement to integrate OpenAPI 3 documentation for my Spring Boot 2 project. We did not used modals/DTOs on controllers.
Here is the sample controller:
#RestController
#RequestMapping(value = "/pet")
public class PetController {
#RequestMapping(value = "/save", method = RequestMethod.POST, produces = MediaType.APPLICATION_JSON_VALUE)
#ResponseBody
public ResponseEntity<Map<String, Object>> savePet(
#RequestBody Map<String, Object> petObj, HttpServletRequest request)
throws Exception {
String petResponse = petDAO.savePet(petObj, request, true);
return new ResponseEntity<Map<String, Object>>(petResponse, HttpStatus.OK);
}
}
Request body:
{
"name":"Test",
"category":"school"
}
My response:
{
"petId":"1",
"petName":"Test",
"petCategory":"school",
"petStaus":"active"
}
I am not able to find a way to add the OpenAPI doc for my custom Map object. I want to add key, description, type, example(s) for each property in my Map manually.
Can anyone suggest how to do this?
This is the default behaviour of the springdoc-openapi library in order to ignore other injectable parameters supported by Spring MVC.
https://docs.spring.io/spring/docs/5.1.x/spring-framework-reference/web.html#mvc-ann-arguments
If you want to change this behaviour, you can just exlcude it as follow:
SpringDocUtils.getConfig().removeRequestWrapperToIgnore(Map.class);
I have this mapping:
User 1----------------------------* Expertises
I'm using the controller SpringBoot, My contoller is
#RestController
#CrossOrigin(origins = "http://localhost:4200", "http://localhost:6227")
#RequestMapping("/api/auth")
public class UserController
{
#PostMapping("/signup/{expertises}")
public ResponseEntity<String> registerUser(#Valid #RequestBody SignUpForm signUpRequest, #PathVariable List<String> expertises)
{
}
}
I add the annotation #CrossOrigin to all the repositories
#CrossOrigin(origins = {"http://localhost:4200", "http://localhost:6227"}, methods = { RequestMethod.GET, RequestMethod.POST, RequestMethod.DELETE }, maxAge = 3600)
#Repository
public interface UserRepository extends JpaRepository<User, Long> {}
The main class is:
#SpringBootApplication
public class SpringBootJwtAuthenticationApplication {
public static void main(String[] args) {
SpringApplication.run(SpringBootJwtAuthenticationApplication.class, args);
}
#Bean
public WebMvcConfigurer configurer()
{
return new WebMvcConfigurer()
{
#Override
public void addCorsMappings(CorsRegistry registry)
{
registry.addMapping("/*")
.allowedOrigins("http://localhost:4200", "http://localhost:6227");
}
};
}
}
I added the file MyConfiguration (as Sir Ananthapadmanabhan proposed)
Front-End (Angular6)
So I want to add a list of expertises to one user using this method:
onSubmit()
{
this.submitted = true;
console.log('---------SelectedExpertise:' + this.selectedExpertiseCheckBox);
this.userService.signUpUser(this.user,
this.selectedExpertiseCheckBox)
.subscribe(data => console.log("---------------Create user:" + data)
,error => console.log(error));
this.user = new User();
}
where
signUpUser(value: any, listExp: String[]): Observable<Object>
{
return this.http.post(`${this.baseUrl}/signup/${listExp}`, value);
}
I can't do that cause adding the list of expertises. That produces this error
Have you please any idea about solving that ?.
Thanks.
As indicated on the console; it was a problem with CORS.
But in reality, it wasn't.
In fact, this bug is caused by a bad use of localStorage with front-end:
the list of strings have to be called like that:
var storedExpertises = JSON.parse(localStorage.getItem("explib"));
and not like that:
localStorage.getItem("explib")
Big thanks Sir #Ananthapadmanabhan for your help and advices.
You have enabled CORS for the endpoint http://localhost:4200 on port address 4200. But it seems you are running the angular 6 app separately on local and the request is being made from the port address 6227 , which might be causing the issue since the CORS policy that you have enabled only allows same origin. Try adding the following in CORS :
#CrossOrigin(origins = "http://localhost:6227")
and if you are still having issues with , Cross-Origin Request Blocked (Reason: CORS header ‘Access-Control-Allow-Origin’ missing) then check this post :
CORS policy conflict in Spring boot
Even through you have enabled the CORS. The requests from different ports will not go through. You need to enable HTTP.OPTIONS.
I am trying to auto-generate the swagger page for a RestAPI in Spring Boot using annotations.
Code of Controller:
#RestController
#Api(value="UserManagementAPI", produces = MediaType.APPLICATION_JSON_VALUE)
public class UserManagementController {
#RequestMapping("/")
public String index() {
return "Greetings from Spring Boot!";
}
#ApiOperation(value="add a pro",consumes="application/json")
#RequestMapping(value = "/getUser", method = RequestMethod.GET, produces="application/json")
public static List<UserDetails> getUser(#PathVariable(name="id") String id) throws UserException
{
return UserHelper.getUserByEmail(id);
}
Application.java
#SpringBootApplication
#EnableSwagger2
#Configuration
#ComponentScan({ "userManagement"})
#EnableAutoConfiguration
public class Application {
#Bean
public Docket simpleDiffServiceApi() {
return new Docket(DocumentationType.SWAGGER_2).groupName("userManagement").apiInfo(apiInfo()).select()
.apis(RequestHandlerSelectors.any())
// .paths(PathSelectors.any())
// Will also include the basic error controllers by default
.paths(Predicates.not(PathSelectors.regex("/error")))
// Exclude basic error controllers
.build().pathMapping("/");
}
private ApiInfo apiInfo() {
return new ApiInfoBuilder().title("Business Location Service")
.description("Spring Boot REST APIs for Business Location Service")
.contact(new Contact("EntSol-IoT (Niche Technology Delivery Group)", "http://somewebsite.com",
"some#mail.com"))
.version("1.0").build();
}
In the swagger page, I can see all my APIs. But there are more. It is showing all possible method type (e.g POST, GET, PUT etc.) though in Controller I only wrote GET method.
Another issue is that there is no Textbox in the swagger page under the API where I can search for the id. May be I am missing something. I have been trying to resolve it for past two days. But couldn't help myself. Thanks in advance.
I got the problem. Your getUser method is declared as static. Please remove static, for it to work.
public List<UserDetails> getUser(#PathVariable(name="id") String id) throws UserException { }
I am trying to test a Multi Module Spring WebMVC API endpoint using Postman. This is Spring-MVC web app & using other frameworks too.
I want to know how to make a request to this URL.
My Controller File looks like this.
#Controller
#RequestMapping(value = "/xyz")
public class XyzWebController {
#CrossOrigin(origins = "*")
#RequestMapping(value = "", method = RequestMethod.GET)
#ResponseBody
public List<XyzChild> getProperties(#RequestParam XyzQueryDTO query) {
return childService.getAll(query);
}
...
}
XyzQueryDTO.java looks like this.
public class XyzQueryDTO {
List<String> properties;
List<String> applications;
public XyzQueryDTO() {
}
public XyzQueryDTO(List<String> properties,
List<String> applications) {
super();
this.properties = properties;
this.applications = applications;
}
...
}
Please assist me with the URL with which i can test this API.
Thanks in Advance.
It's more simple and correct to use RequestMethod.POST instead of RequestMethod.GET and #RequestBody instead of #RequestParam
#RequestMapping(value = "", method = RequestMethod.POST)
#ResponseBody
public List<XyzChild> getProperties(#RequestBody XyzQueryDTO query) {
return childService.getAll(query);
}
And you can use #RestController instead of #Controller and remove #ResponseBody
For data type conversion use jackson librairy.
<dependency>
<groupId>com.fasterxml.jackson.core</groupId>
<artifactId>jackson-databind</artifactId>
<version>2.8.8</version>
</dependency>
In Postman you can fill your XyzQueryDTO in the BODY as json
I want to consume a REST webservice from a server which protects his resources using oauth2.
I use Spring boot (JHipster).
To do this i have in SecurityConfiguration class this :
#Value("${oauth.resource:http://sercverUsingOAuth2}")
private String baseUrl;
#Value("${oauth.authorize:http://sercverUsingOAuth2/rest/oauth/token}")
private String authorizeUrl;
#Value("${oauth.token:http://sercverUsingOAuth2/rest/oauth/token}")
private String tokenUrl;
#Bean
public OAuth2RestOperations oauth2RestTemplate() {
AccessTokenRequest atr = new DefaultAccessTokenRequest();
return new OAuth2RestTemplate(resource(),
new DefaultOAuth2ClientContext(atr));
}
#Bean
protected OAuth2ProtectedResourceDetails resource() {
AuthorizationCodeResourceDetails resource = new AuthorizationCodeResourceDetails();
resource.setAccessTokenUri(tokenUrl);
resource.setUserAuthorizationUri(authorizeUrl);
resource.setClientId("client_id");
resource.setClientSecret("client_secret");
resource.setGrantType("grant_type");
return resource;
}
This class (SecurityConfiguration) is annoted using :
#Configuration
#EnableWebSecurity
#EnableOAuth2Client
And this is my controller (Spring MVC) :
#RestController
#RequestMapping("/consume")
public class MyContrtoller {
#Inject
private OAuth2RestOperations oauth2RestTemplate;
#RequestMapping(value = "/oauth2", method = RequestMethod.GET, produces = MediaType.APPLICATION_JSON_VALUE)
public List<DataModel> getProducts() {
ResponseEntity<MyModel> forEntity = oauth2RestTemplate
.getForEntity("http://sercverUsingOAuth2/rest/resourceToConsume",
MyModel.class);
return forEntity.getBody().getData();
}
}
However when i want to consume my webservice (http://myHost/consume/oauth2) i get this Exception :
org.springframework.security.oauth2.client.resource.OAuth2AccessDeniedException:
Unable to obtain a new access token for resource 'null'. The provider manager
is not configured to support it.
I have googled and i found this :
github
stackoverflow
But it doesn't help me.
Thanks.
You are using the same URL for the authorization url and the token url. That was my first clue, then I saw your comments.
Even though you are changing the grant type, you are still using "AuthorizationCodeResourceDetails" when you should be using "ClientCredentialsResourceDetails" instead. This type of ResourceDetails is meant to be used for the case you are explaining.
ClientCredentialsResourceDetails resource = new ClientCredentialsResourceDetails();
resource.setAccessTokenUri(TOKEN_URL);
resource.setClientId(CLIENT_ID);
resource.setClientSecret(CLIENT_SECRET);
resource.setClientAuthenticationScheme(AuthenticationScheme.form); //This line isn't always needed
return resource;