I have added the following class in my Roo app:
/**
* A central place to register application converters and formatters.
*/
#RooConversionService
public class ApplicationConversionServiceFactoryBean extends FormattingConversionServiceFactoryBean {
#Override
protected void installFormatters(FormatterRegistry registry) {
super.installFormatters(registry);
}
}
I have registered the class as follows in webmvc-config.xml:
<mvc:annotation-driven conversion-service="applicationConversionService"/>
and in applicationContext.xml:
<bean class="com.bignibou.converter.ApplicationConversionServiceFactoryBean" id="applicationConversionService"/>
Note that I don't use JSP but Thymeleaf instead so that I have not run the "web mvc all" command at all and therefore I have no web Scaffolds.
Can anyone please tell me why the ITDs for the RooConversionService are not generated??
As you can read the in the Spring Roo Docs:
"Roo will automatically maintain an ITD with Converter registrations for every associated entity that needs to be displayed somewhere in a view" (Page 97)
This logically would mean that if you have no scaffolded views then Roo isn't governing the Conversion Service and you need to author and register these manually.
Related
I have a Spring Boot app with a few Controllers I want to track their dependencies (including outbound Http requests). That all works as expected. However, I have one controller for a health check (returning 204) that I do not want telemetry for. All other responses mention custom code components, but according to the documentation, this should be doable within the AI-Agent.xml config.
<BuiltInProcessors>
<Processor type="RequestTelemetryFilter">
<Add name="NotNeededResponseCodes" value="204" />
</Processor>
</BuiltInProcessors>
I notice on the classpath that there are two RequestTelemtryFilter instances (one from ai-core and one from ai-web, neither of which get hit when i debug).
Configuring the Agent (via AI-Agent.xml) is different than configuring custom telemetry (via Applicationinsights.xml). Spring boot + the agent requires the use of a custom Telemetry Processor and pulling into your configuration via #Bean. No additional XML in the AI-Agent is necessary.
public class HealthCheckTelemetryFilter implements TelemetryProcessor
{
public HealthCheckTelemetryFilter()
{
// TODO Auto-generated constructor stub
}
#Override
public boolean process(Telemetry telemetry)
{
RequestTelemetry reqTel = (RequestTelemetry) telemetry;
if(reqTel.getResponseCode().equals(HttpStatus.NO_CONTENT.toString()))
return false;
else
return true;
}
}
NOTE: dont forget appropriate type check
Having upgraded to spring security 4.2.4 I discovered that StrictHttpFirewall is now the default.
Unfortunately it doesn't play well with spring MVC #MatrixVariable since ";" are not allowed anymore.
How to get around that?
Example:
#GetMapping(path = "/{param}")
public void example(#PathVariable String param,
#MatrixVariable Map<String, String> matrix) {
//...
}
This could be called like this:
mockMvc.perform(get("/someparam;key=value"))
And the matrix map would be populated.
Now spring security blocks it.
org.springframework.security.web.firewall.RequestRejectedException: The request was rejected because the URL contained a potentially malicious String ";"
at org.springframework.security.web.firewall.StrictHttpFirewall.rejectedBlacklistedUrls(StrictHttpFirewall.java:140)
I could use a custom HttpFirewall that would allow semicolons.
Is there a way to use #MatrixVariable without using forbidden characters?
BTW: the javadoc is incorrect https://docs.spring.io/autorepo/docs/spring-security/4.2.x/apidocs/index.html?org/springframework/security/web/firewall/StrictHttpFirewall.html
Since:
5.0.1
I guess it was backported?
You can dilute the default spring security firewall using your custom defined instance of StrictHttpFirewall (at your own risk)
#Bean
public HttpFirewall allowUrlEncodedSlashHttpFirewall() {
StrictHttpFirewall firewall = new StrictHttpFirewall();
firewall.setAllowUrlEncodedSlash(true);
firewall.setAllowSemicolon(true);
return firewall;
}
And then use this custom firewall bean in WebSecurity (Spring boot does not need this change)
#Override
public void configure(WebSecurity web) throws Exception {
super.configure(web);
// #formatter:off
web.httpFirewall(allowUrlEncodedSlashHttpFirewall());
...
}
That shall work with Spring Security 4.2.4+, but of-course that brings some risks!
As mentioned by Крис in a comment if you prefer to use a XML approach, you can add the following part to your securityContext.xml (or whatever your spring-security related xml-config is called):
<bean id="allowSemicolonHttpFirewall"
class="org.springframework.security.web.firewall.StrictHttpFirewall">
<property name="allowSemicolon" value="true"/>
</bean>
<security:http-firewall ref="allowSemicolonHttpFirewall"/>
The <bean> part defines a new StrictHttpFirewall bean with the id allowSemicolonHttpFirewall which is then set as default http-firewall in the <security> tag by referencing the id.
I used combination of following two
https://stackoverflow.com/a/48636757/6780127
https://stackoverflow.com/a/30539991/6780127
First one resolved the
The request was rejected because the URL contained a potentially malicious String ";"
Second one Resolved the
Spring MVC Missing matrix variable
As I am using Spring Security with Spring Web I had to do both And the issue is now Resolved.
I found using #MatrixVariable Following Pattern is useful. First in Url {num} has to be mentioned to use it as #MatrixVariable
#RequestMapping(method = RequestMethod.GET,value = "/test{num}")
#ResponseBody
public ResponseEntity<String> getDetail(#MatrixVariable String num){
return new ResponseEntity<>("test"+num, HttpStatus.OK);
}
I am new to the Swagger and trying to implement it in the Spring MVC. I'm using latest dependency swagger-springmvc from http://mvnrepository.com/artifact/com.mangofactory/swagger-springmvc. So based on link https://dzone.com/articles/documenting-your-spring-api. I added following configuration in mvc-config.xml.
<!-- Serve static content - required for Swagger -->
<mvc:default-servlet-handler/>
<!-- to enable the default documentation controller-->
<context:component-scan base-package="com.mangofactory.swagger.controllers"/>
<!-- to pick up the bundled spring configuration-->
<context:component-scan base-package="com.mangofactory.swagger.configuration"/>
<!-- Direct static mappings -->
<mvc:resources mapping="*.html" location="/, classpath:/swagger-ui"/>
Also I used following from link shown above.
<bean class="com.xxx.xx.xx.SwaggerConfig"/>
Then I added
git clone https://github.com/wordnik/swagger-ui
cp -r swagger-ui/dist ~/dev/x-auth-security/src/main/webapps/docs
When I launch the site: http://localhost:8080/dp-rest/api-docs I don't see UI format, it only gives JSON format.
{"apiVersion":"1.0","swaggerVersion":"1.2","apis":[{"path":"/default/student-service","description":"Manage Student Service","position":0},{"path":"/default/student-service","description":"Manage Student Service","position":0}],"authorizations":[],"info":{"title":"Student API's","description":"API for Student ","termsOfServiceUrl":"terms.html","contact":"test#yahoo.com","license":"Commercial Proprietary","licenseUrl":"http://www.adbc.com"}}
Ny
#Configuration
#EnableSwagger
public class SwaggerConfig {
private SpringSwaggerConfig springSwaggerConfig;
#Autowired
public void setSpringSwaggerConfig(SpringSwaggerConfig springSwaggerConfig) {
this.springSwaggerConfig = springSwaggerConfig;
}
#Bean
// Don't forget the #Bean annotation
public SwaggerSpringMvcPlugin customImplementation() {
return new SwaggerSpringMvcPlugin(this.springSwaggerConfig).apiInfo(
apiInfo()).includePatterns(".*");
}
private ApiInfo apiInfo() {
return new ApiInfo("Student API", "API for Student",
"term.html", "test#tahoo.com",
"Commercial Proprietary", "http://www.test.com");
}
}
Why UI format not coming when we launch the http://localhost:8080/sample-rest/api-docs site?
Then only I see raw JSON response not any ui, What is missing here? What I need to changed/add/modify my code?
According to the article you'll see a section that tells you where to find the documentation. I'm not sure if you're using spring-boot but...
After making these changes, I was able to open fire up the app with "mvn spring-boot:run" and view http://localhost:8080/docs/index.html in my browser.
In any case, swagger-springmvc is now called springfox and supports the latest swagger specification (2.0). There is also documentation available to help you get started. I would recommend using the latest version (2.3.1 as of this writing) of springfox instead.
I've started working on a web application in Spring Weblow. The idea is to write as much as possible in Java, rather than XML. So I started off with a JavaConfig file for both the MVC configuration and the Web Flow configuration. But I ran into a problem when needing converters for entering and submitting a form with Spring Web Flow.
I did a lot of research on ConversionService and Converters. I found plenty examples of implementing a custom ConversionService and custom Converters, but I found no examples to to add the ConversionService to the Web Flow configuration in JavaConfig (configuration was always XML).
I did try to reproduce the XML config in Java, which nearly worked. In a form page, a list of POJOs (Employee) was represented as a dropdownlist. The input was List<Employee> and the converter (subclass of StringToObject) worked to represent each Employee as a String. But when submitting the form, I got the error that no converter was found for String to Employee. So basically, the custom converter was found and used when rendering the page, but when submitting the form, the same converter could not be found for the reverse process.
I eventually got it fixed by rolling the JavaConfig back to XML config and adding a custom Formatter to the ConversionService of the MVC config. But I'd like to make this work in JavaConfig if it is at all possible.
I believe the problem is that a ConversionService bean (org.springframework.core.convert package) needs to be added to the MVC config, because this bean needs to be set as a delegate ConversionService in the ConversionService bean to be added to the Web Flow Config (the latter from the org.springframework.binding.convert package). But I don't know how to add this core ConversionService in JavaConfig like in the mvc:annotation-driven tag in the code below.
It all boils down to needing the JavaConfig version of the following code:
<mvc:annotation-driven conversion-service="typeConversionService" ... />
<bean id="typeConversionService" class="org.springframework.format.support.FormattingConversionServiceFactoryBean">
<property name="formatters">
<list>
<bean class="some.package.holidays.formatter.EmployeeFormatter">
<constructor-arg ref="employeeService"/>
</bean>
<bean class="org.springframework.format.datetime.DateFormatter">
<constructor-arg value="dd/MM/yyyy"/>
</bean>
</list>
</property>
</bean>
If anyone would know about JavaConfig for Spring Webflow, especially about adding a ConversionService, please let me know, it would be a great help.
I had the same thing to do in a project and this is how I did it. I know it might be late for you, but maybe somebody else needs the answer to this:
#Configuration
public class WebFlowConfig extends AbstractFlowConfiguration {
#Autowired
private MvcConfig webMvcConfig;
#Bean
public FlowBuilderServices flowBuilderServices() {
return getFlowBuilderServicesBuilder()
.setViewFactoryCreator(mvcViewFactoryCreator())
.setValidator(this.webMvcConfig.validator())
.setConversionService(conversionService())
.setDevelopmentMode(true)
.build();
}
#Bean
DefaultConversionService conversionService() {
return new DefaultConversionService(conversionServiceFactoryBean().getObject());
}
#Bean
FormattingConversionServiceFactoryBean conversionServiceFactoryBean() {
FormattingConversionServiceFactoryBean fcs = new FormattingConversionServiceFactoryBean();
Set<Formatter> fmts = new HashSet<>();
fmts.add(this.webMvcConfig.dateFormatter());
fmts.add(this.webMvcConfig.employeeFormatter());
fcs.setFormatters(fmts);
return fcs;
} }
I upvoted the accepted answer but would also like to add this. I kept getting the below error.
'conversionService': Requested bean is currently in creation: Is there an unresolvable circular reference?
To fix this, remove conversionService bean like this. (note the setConversionService difference).
#Bean
public FlowBuilderServices flowBuilderServices() {
return getFlowBuilderServicesBuilder()
.setViewFactoryCreator(mvcViewFactoryCreator())
.setValidator(localValidatorFactoryBean)
.setConversionService(new DefaultConversionService(conversionServiceFactoryBean().getObject()))
.setDevelopmentMode(true)
.build();
}
#Bean
FormattingConversionServiceFactoryBean conversionServiceFactoryBean() {
FormattingConversionServiceFactoryBean fcs = new FormattingConversionServiceFactoryBean();
Set<Formatter> fmts = new HashSet<>();
fmts.add(this.webMvcConfig.dateFormatter());
fmts.add(this.webMvcConfig.employeeFormatter());
fcs.setFormatters(fmts);
return fcs;
}
I have some business validation logic of the form "X is valid IFF Service Y returns Z", where X and Z are known at compile time, and Y's location is loaded from a Spring configuration file.
I'd like to use JSR-303 annotation-based validation, together with the Spring config, so I can write code like the following:
Custom class level constraint annotation:
#MyValidation
public class X { .... }
ConstraintValidator for #MyValidation:
public class MyValidationValidator implements ConstraintValidator<MyValidation, X> {
private MyService service;
public MyService getService() { return service; }
public void setService(MyService serv) { this.service = serv; }
//Validation Logic...
}
Spring config:
<bean id="ServiceY" class="...">
...
</bean>
<bean id="mvv" class="MyValidationValidator">
<property name="service" value="ServiceY" />
</bean>
But my attempts at combining these in that fashion are failing, as the validator's property is not getting set.
Right now, I'm using Spring AOP Interceptors as a workaround, but that's not ideal in my mind.
One of the other questions here, made me think of using a properties file/property, but wouldn't that require me to repeat the service's configuration?
Another mentioned defining the constraint mapping programmatically, but if I'm doing that, I'm probably better-off with my workaround.
Any clues on how to do that dynamic configuration?
You should use Spring's LocalValidatorFactoryBean to set up a Bean Validation validator:
<bean id="validator"
class="org.springframework.validation.beanvalidation.LocalValidatorFactoryBean"/>
A validator set up that way will internally use a ConstraintValidatorFactoryimplementation that performs dependency injection on the created validator instances, just mark the service field in your validator with #Inject or #Autowired. Note that it's not required to set up the constraint validator itself as Spring bean.
You can find more details in the Spring reference guide.