Springframework webflow variable class name not found - spring

I have problem with initialization of spring webflow variables.
I have two flows xml's and they looks same, but when opens one of them spring throws this exception. In flows are two kind of variables initialization:
<var name="bean" bean="beanName" scope="flow" />
and
<set attribute="id" value="${'someId'}" scope="flow" />
Here is exception:
Caused by: java.lang.IllegalArgumentException: Name must not be null
at org.springframework.util.Assert.notNull(Assert.java:112)
at org.springframework.util.ClassUtils.forName(ClassUtils.java:222)
at org.springframework.webflow.engine.builder.model.FlowModelFlowBuilder.toClass(FlowModelFlowBuilder.java:958)
at org.springframework.webflow.engine.builder.model.FlowModelFlowBuilder.parseFlowVariable(FlowModelFlowBuilder.java:389)
at org.springframework.webflow.engine.builder.model.FlowModelFlowBuilder.buildVariables(FlowModelFlowBuilder.java:172)
at org.springframework.webflow.engine.builder.FlowAssembler.directAssembly(FlowAssembler.java:103)
at org.springframework.webflow.engine.builder.FlowAssembler.assembleFlow(FlowAssembler.java:91)
at org.springframework.webflow.engine.builder.DefaultFlowHolder.assembleFlow(DefaultFlowHolder.java:109)
at org.springframework.webflow.engine.builder.DefaultFlowHolder.getFlowDefinition(DefaultFlowHolder.java:84)
at org.springframework.webflow.definition.registry.FlowDefinitionRegistryImpl.getFlowDefinition(FlowDefinitionRegistryImpl.java:61)
at org.springframework.webflow.executor.FlowExecutorImpl.launchExecution(FlowExecutorImpl.java:138)
at org.springframework.webflow.mvc.servlet.FlowHandlerAdapter.handle(FlowHandlerAdapter.java:193)
at com.exigen.base.ui.flow.DefaultFlowController.handleRequest(DefaultFlowController.java:56)
at org.springframework.web.servlet.mvc.SimpleControllerHandlerAdapter.handle(SimpleControllerHandlerAdapter.java:48)
at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:923)
at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:852)
at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:882)
... 82 more

I am not sure what you are trying to do but if you want to use <var> element you NEED both name and class attributes.
like
<var name="myVar" class="com.example.var.MyVar"/>
plus, you don't need to define beans in wefblow, you can automatically use the ones defined in your applicationContext

I resolved issue. Problem was in webflow schemes versions mismatch. One of my flow xml using 1.0, while system using 2.0.

Related

Rest DSL path typing to a POJO, can I register the POJO as a Bean and call the id to reference it?

This is a very low impact "issue" and I'm just looking out to learn something new about Camel and how it works.
I'm working to build a springboot service using camel context routes, and while it's working fine (so far), I'd like to set the rest path type to a class without having to explicitly call the package location, and instead, reference the class as a bean and use it's id to call it.
I have defined a camelContext, I have the rest, restConfigurations and the necessary http methods (get, post, put...), here's a mock of what I have right now.
I've registered a ServiceImpl class as a bean and have given it the id Service. In the Route, I can call the bean using a ref to it's id, and select the method that I want.
<beans xmlns ...>
...
<!-- start services -->
<bean class="com.daniel.rest-project.services.ServiceImpl" id="Service"/>
<!-- end services -->
...
<camelContext id="context" xmlns="http://camel.apache.org/schema/spring">
<rest bindingMode="au <!-- <to id="to-7b30ace2-b26d-4301-8bb0-ef007d566ab3" uri="direct:501"/> -->to" enableCORS="true" id="rest">
...
<post consumes="application/json" id="newTask" produces="application/json" uri="/task" type="com.daniel.rest-project.vo.TaskVO">
<description>New Task Object</description>
<param description="Task Object Body." name="body" required="true" type="body"/>
<to uri="direct:newTask"/>
</post>
...
</rest>
...
<route id="route-task-new">
<from id="from-task-new" uri="
<bean id="to-task-new" method="newTask" ref="Service"/>
</route>
...
</camelContext>
</beans>
Now, I've actually got implemented around 150 routes (project is pretty big) and I'm tired of having to declare the rest post type, right now it's using something not really similar to com.daniel.rest-project.vo..
There's a ton of classes that are named similarly and due to internal reasons, best practices are scarce, naming conventions are weird, there's more than one package I need to go to, etc.
It would feel a lot more organized to just define all the objects I need at the start of the XML file and reference them as I go, instead of having to state the whole way there every time, so, is there a way I can define those classes at the start, just like the services, and tell the post rest path to use the id of the bean, instead of having to give it the whole class location? There must be a way and I'm sure I've just been blind enough not to see it in the documentation for the past weeks.
Here's one of the methods I've tried thus far:
<!-- start classes -->
<bean class="com.daniel.rest-project.vo.TaskVO" id="TaskVO"/>
<!-- end classes -->
and then, tell the path to do something like this
<post consumes="application/json" id="newTask" produces="application/json" uri="/task" type="TaskVO">
<description>New Task Object</description>
<param description="Task Object Body." name="body" required="true" type="body"/>
<to uri="direct:newTask"/>
</post>
Which resulted in the following error:
Caused by: org.apache.camel.FailedToCreateRouteException: Failed to create route newTask: Route(newTask)[[From[rest:post:/task?routeId=newTask&... because of java.lang.ClassNotFoundException: TaskVO
at org.apache.camel.model.RouteDefinition.addRoutes(RouteDefinition.java:209)
at org.apache.camel.impl.DefaultCamelContext.startRoute(DefaultCamelContext.java:1143)
..........
Caused by: org.apache.camel.RuntimeCamelException: java.lang.ClassNotFoundException: TaskvO
at org.apache.camel.util.ObjectHelper.wrapRuntimeCamelException(ObjectHelper.java:1830)
at org.apache.camel.impl.DefaultRouteContext.commit(DefaultRouteContext.java:206)
at org.apache.camel.model.RouteDefinition.addRoutes(RouteDefinition.java:1307)
at org.apache.camel.model.RouteDefinition.addRoutes(RouteDefinition.java:204)
TaskVO implements Serializable, and only has one, empty, public constructor, followed by all of it's getters and setters.

Mule invoke message processor

I came across "invoke" element (link) that can be used to invoke java methods from inside the flow. It seemed a perfect solutions for me, since I don't want to use Callable and entry points resolvers and I want to pass extra parameter to the method.
<invoke object-ref="yourBean"
method="yourMethod"
methodArguments="#[message.inboundProperties['inboundPropertyName']]" />
<set-property propertyName="outboundPropertyName"
value="#[payload]" />
I did something like the code above. My question is: how should I create "yourBean"?
I tried to create:
<spring:bean name="yourBean" class="class"/>
but got:
org.springframework.beans.factory.NoSuchBeanDefinitionException: No bean named 'yourBean' is defined
I also have other beans defined in my tag, but others seemed to work. Does anyone have similar issue?
EDIT:
When I deleted other beans definitions besides "yourBean" everything started to work, but when I add more beans definitions I got following error when I tried to use "yourBean":
Exception stack is:
1. null (java.lang.NullPointerException)
org.mule.processor.InvokerMessageProcessor:280 (null)
2. null (java.lang.NullPointerException). Message payload is of type: String (org.mule.api.MessagingException)
org.mule.execution.ExceptionToMessagingExceptionExecutionInterceptor:35 (http://www.mulesoft.org/docs/site/current3/apidocs/org/mule/api/MessagingException.ht
ml)
--------------------------------------------------------------------------------
Root Exception stack trace:
java.lang.NullPointerException
at org.mule.processor.InvokerMessageProcessor.transformArgument(InvokerMessageProcessor.java:280)
at org.mule.processor.InvokerMessageProcessor.evaluateArguments(InvokerMessageProcessor.java:200)
at org.mule.processor.InvokerMessageProcessor.process(InvokerMessageProcessor.java:164)
+ 3 more (set debug level logging or '-Dmule.verbose.exceptions=true' for everything)
********************************************************************************
Which for me seems like the "yourBean" is not instantiated. But why?
My bean definitions:
<bean id="yourBean" class="com.example.BpmService"/>
<bean id="StatusUpdateContext" class="javax.xml.bind.JAXBContext" factory-method="newInstance">
<constructor-arg>
<array>
<value type="java.lang.Class">
com.example.OrderStatusUpdate
</value>
</array>
</constructor-arg>
</bean>
EDIT: Ok, id/name both some to work for Mule invoke. I have had no problems using invoke with multiple bean definitions. This sounds more like an issue with your beans, which you are not sharing, and/or Spring than Mule invoke.

Spring AOP IllegalArgumentException: Cannot convert value of type [$Proxy12

I am trying to configure one advice in an existing spring project.
Following configuration works fine for a single package but when pointcut expression try to apply that advice on all packages its giving following error.
My Configuration:
<aop:config>
<aop:pointcut id="loggingPointcut" expression="execution(* com.abc.businessprocess.operation..*.execute(..))" />
<aop:advisor id="methodLoggingAdvisor" advice-ref="methodLoggingAdvice" pointcut-ref="loggingPointcut" />
</aop:config>
I tried with annotation also but it was giving same error.
I tried with CGLIB also even after using that its giving same error.
Error:
Caused by: org.springframework.beans.TypeMismatchException: Failed to convert property value of type [$Proxy12 implementing com.fmr.ast.common.businessprocess.util.Timeable,com.fmr.ast.common.businessprocess.operation.Operation,com.fmr.commons.taskmanager.core.Task,org.springframework.aop.SpringProxy,org.springframework.aop.framework.Advised] to required type [com.fmr.ips.businessprocess.operation.goalsetup.GetLeveledIRGExpInc] for property 'getRawDetailedLeveledExpInc'; nested exception is java.lang.IllegalArgumentException: Cannot convert value of type [$Proxy12 implementing com.fmr.ast.common.businessprocess.util.Timeable,com.fmr.ast.common.businessprocess.operation.Operation,com.fmr.commons.taskmanager.core.Task,org.springframework.aop.SpringProxy,org.springframework.aop.framework.Advised] to required type [com.fmr.ips.businessprocess.operation.goalsetup.GetLeveledIRGExpInc] for property 'getRawDetailedLeveledExpInc': no matching editors or conversion strategy found
at org.springframework.beans.BeanWrapperImpl.convertForProperty(BeanWrapperImpl.java:391)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.convertForProperty(AbstractAutowireCapableBeanFactory.java:1289)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.applyPropertyValues(AbstractAutowireCapableBeanFactory.java:1250)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1010)
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:472)
... 33 more
Caused by: java.lang.IllegalArgumentException: Cannot convert value of type [$Proxy12 implementing com.fmr.ast.common.businessprocess.util.Timeable,com.fmr.ast.common.businessprocess.operation.Operation,com.fmr.commons.taskmanager.core.Task,org.springframework.aop.SpringProxy,org.springframework.aop.framework.Advised] to required type [com.fmr.ips.businessprocess.operation.goalsetup.GetLeveledIRGExpInc] for property 'getRawDetailedLeveledExpInc': no matching editors or conversion strategy found
at org.springframework.beans.TypeConverterDelegate.convertIfNecessary(TypeConverterDelegate.java:231)
at org.springframework.beans.TypeConverterDelegate.convertIfNecessary(TypeConverterDelegate.java:138)
at org.springframework.beans.BeanWrapperImpl.convertForProperty(BeanWrapperImpl.java:386)
... 37 more
Looking at the exception trace this is what I suspect:
GetLeveledIRGExpInc is a concrete class that implements three interfaces: Timeable, Operation, Task. You have a bean of this type declared in your context, which gets proxied because of your AOP config. This means that the runtime type of the bean won't be GetLeveledIRGExpInc any more, it will be $Proxy12 (JDK proxy) which still implements the above three interfaces, but is not a subtype of the concrete class GetLeveledIRGExpInc.
There is another bean somewhere in your context that needs a bean of this type to be injected into a property named getRawDetailedLeveledExpInc. When Spring tries to inject the proxied bean into that property, it fails, because the property's type is incompatible with the bean's runtime type.
The fundamental problem is that you try to apply a very generic logging aspect using JDK proxying mechanism which can only advise methods declared on interfaces. Try using <aop:config proxy-target-class="true"> so that classes without implemented interfaces can be advised as well. This would resolve the above detailed problem, as the generated CGLIB proxy for GetLeveledIRGExpInc will actually be a subtype of it. (Don't forget to add cglib to your dependencies for this to work.)

A simple pointcut expression in Spring

I'm using Spring security 3.2.0 with the same version of the Spring framework. Spring security works well in my project. In order to protect methods in my DAO classes (and others), I want to use the following pointcut approach (in the spring-security.xml file).
<global-method-security>
<protect-pointcut expression="execution(*controller.*.*(..))" access="ROLE_ADMIN"/>
</global-method-security>
I expect the pointcut expression as specified to protect all the methods in all classes inside the controller package and to be accessed only by the users who have the authority ROLE_ADMIN as specified.
But when I try to use this expression, the process terminates with following exception on saving my spring-security.xml file.
PropertyAccessException 1:
org.springframework.beans.MethodInvocationException: Property
'pointcutMap' threw exception; nested exception is
java.lang.IllegalArgumentException: Pointcut is not well-formed:
expecting 'name pattern' at character position 26
execution(controller..*(..))
^
I'm trying to follow the approach as specified by the reference document in the Adding Security Pointcuts using protect-pointcut sub-section of the 3.4.1 The <global-method-security> Element section.
What is correct expression syntax in this scenario?
EDIT:
Adding Security Pointcuts using protect-pointcut
The use of protect-pointcut is particularly powerful, as it allows you to apply security to many beans with only a simple declaration. Consider the following example:
<global-method-security>
<protect-pointcut expression="execution(* com.mycompany.*Service.*(..))" access="ROLE_USER"/>
</global-method-security>
This will protect all methods on beans declared in the application context whose classes are in the com.mycompany package and whose class names end in "Service". Only users with the ROLE_USER role will be able to invoke these methods. As with URL matching, the most specific matches must come first in the list of pointcuts, as the first matching expression will be used. Security annotations take precedence over pointcuts.
Copy & pasted the section explained in the reference document (as someone may find it to be tedious to scroll the document).
Try with this expression :
<protect-pointcut expression="execution(* your.package.controller.*.*(..))" access="ROLE_ADMIN"/>

Error while injecting a Spring bean into a JSF ManagedBean

I have a JSF ManagedBean which has a property that should be set by Spring. However, I get the following error:
Caused by: javax.el.ELException: java.lang.IllegalArgumentException: Cannot convert persistence.AuthDao#2f6e6ad9 of type class $Proxy166 to class persistence.AuthDao
at com.sun.el.ExpressionFactoryImpl.coerceToType(ExpressionFactoryImpl.java:68)
at com.sun.faces.el.ELUtils.coerce(ELUtils.java:536)
at com.sun.faces.mgbean.BeanBuilder$Expression.evaluate(BeanBuilder.java:592)
at com.sun.faces.mgbean.ManagedBeanBuilder$BakedBeanProperty.set(ManagedBeanBuilder.java:606)
... 57 more
Caused by: java.lang.IllegalArgumentException: Cannot convert persistence.AuthDao#2f6e6ad9 of type class $Proxy166 to class persistence.AuthDao
at com.sun.el.lang.ELSupport.coerceToType(ELSupport.java:397)
at com.sun.el.ExpressionFactoryImpl.coerceToType(ExpressionFactoryImpl.java:66)
I have the ELresolver in faces-config.xml.
<managed-bean>
<managed-bean-name>authController</managed-bean-name>
<managed-bean-class>controllers.AuthController</managed-bean-class>
<managed-bean-scope>session</managed-bean-scope>
<managed-property>
<property-name>authDao</property-name>
<value>#{authDao}</value>
</managed-property>
</managed-bean>
<application>
<el-resolver>org.springframework.web.jsf.el.SpringBeanFacesELResolver</el-resolver>
</application>
It seems that it can find the class, but the class is of another type ($Proxy166?, not sure where that comes from).
PS: Removing the ELResolver seems to do the trick; I thought explicitly providing managed-bean in faces-config.xml would override ELResolver. Is there any way of both of these to coexist, then? Similarly, if I provide both annotation and XML configuration for a bean, which one of these is preferred, or is there a way to merge them, provide some properties in annotation, some in XML?
PPS: After adding interfaces and changing my current classes to implement them, I get the following error:
Error occurred during deployment: Exception while loading the app :
java.lang.IllegalStateException: ContainerBase.addChild: start:
org.apache.catalina.LifecycleException:
org.springframework.beans.factory.BeanCreationException: Error
creating bean with name 'authDao' defined in ServletContext resource
[/WEB-INF/applicationContext.xml]: Initialization of bean failed;
nested exception is
org.springframework.beans.ConversionNotSupportedException: Failed to
convert property value of type '$Proxy157 implementing
persistence.UserDao,org.springframework.aop.SpringProxy,org.springframework.aop.framework.Advised'
to required type 'persistence.UserDaoImpl' for property 'userDao';
nested exception is java.lang.IllegalStateException: Cannot convert
value of type [$Proxy157 implementing
persistence.UserDao,org.springframework.aop.SpringProxy,org.springframework.aop.framework.Advised]
to required type [persistence.UserDaoImpl] for property 'userDao': no
matching editors or conversion strategy found. Please see server.log
for more details.
This is a proxy of your class. You are implementing an interface, so spring creates a proxy around the interface, but you are trying to inject by concrete type. Switch to the interface instead (in the managed bean).
If you really need for some reason to inject by concrete class, you can use #Scoped(proxyMode=ScopeProxyMode.TARGET_CLASS)

Resources