I have a nullPointerException when I try mock a DataSourceTransactionManager, I just test one Method without access to DB.
Maybe I am do something wrong, but I don't know what.
TestClass
#RunWith(MockitoJUnitRunner.class)
public class VdpDirectshipDAOImplUT {
Logger logger = LoggerFactory.getLogger(getClass());
#InjectMocks
private VdpDirectshipDAOImpl dao;
#Mock
private DataSourceTransactionManager oracleTxManager;
#Mock
TransactionStatus transactionStatus;
#Mock
TransactionDefinition transactionDefinition;
#Test
public void testSubmitDSOrder() {
// given
int result = -1;
VdpDirectShipSession vdpDirectShipSession = new VdpDirectShipSession();
String vnetUserId = "10624802";
// when
try {
result = dao.submitDSOrder(vdpDirectShipSession, vnetUserId);
logger.info("result: {}", result);
} catch (DirectShipDataAccessException e) {
fail(e.getMessage());
}
// then
assertTrue("SKU invalid correction", result > 0);
}
#Before
public void setup() {
MockitoAnnotations.initMocks(this);
oracleTxManager = Mockito.mock(DataSourceTransactionManager.class);
Mockito.when(oracleTxManager.getTransaction(transactionDefinition)).thenReturn(Mockito.mock(TransactionStatus.class));
}
}
DAO
public class VdpDirectshipDAOImpl extends SimpleJdbcDaoSupport implements
VdpDirectshipDAO {
/**
* transactionManager for Oracle Database
*/
private DataSourceTransactionManager oracleTxManager;
....
#Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class )
public int submitDSOrder(final VdpDirectShipSession vdpDirectshipService,
final String vnetUserId) throws DirectShipDataAccessException {
...
final TransactionDefinition def = new DefaultTransactionDefinition();
final TransactionStatus status = oracleTxManager.getTransaction(def);
...
}
}
Trace
java.lang.NullPointerException
at org.springframework.transaction.support.AbstractPlatformTransactionManager.getTransaction(AbstractPlatformTransactionManager.java:317)
at com.autozone.vendornet.vdpdirectship.dao.VdpDirectshipDAOImplUT.setup(VdpDirectshipDAOImplUT.java:69)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:592)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)
at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:24)
at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)
at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
at org.mockito.internal.runners.JUnit45AndHigherRunnerImpl.run(JUnit45AndHigherRunnerImpl.java:37)
at org.mockito.runners.MockitoJUnitRunner.run(MockitoJUnitRunner.java:62)
at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:86)
at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:459)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:678)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:382)
at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:192)
I'm using Java 5, Spring 2.0, and junit 4.12 and I can't update their versions.
The correct implementation for my was the next.
#Spy
private DataSourceTransactionManager oracleTxManager;
...
oracleTxManager.setDataSource(Mockito.mock(DataSource.class, Mockito.RETURNS_MOCKS));
Related
I am learning Spring Batch Integration from here and I know how to launch a job when a message is received. Now, I wanted to get both the name and path of the message (which is a file). Below are my working codes. However, if I uncomment the setFileParameterName method, then I get the following exception:
java.lang.IllegalArgumentException: Found ambiguous parameter type [class java.lang.String] for method match: [public void com.example.batchprocessing.FileMessageToJobRequest.setFileParameterName(java.lang.String), public void com.example.batchprocessing.FileMessageToJobRequest.setJob(org.springframework.batch.core.Job)]
Why does this exception occur? The message makes no sense to me. I pass in a String and it is somehow confused between the two methods, but one of them takes in a String and the other a Job? Any help with this is appreciated.
FileMessageToJobRequest.java
public class FileMessageToJobRequest {
private String filePathParameterName;
private Job job;
private String fileParameterName;
public void setFilePathParameterName(String filePathParameterName) {
this.filePathParameterName = filePathParameterName;
}
public void setJob(Job job) {
this.job = job;
}
// public void setFileParameterName(String fileParameterName) {
// this.fileParameterName = fileParameterName;
// }
#Transformer
public JobLaunchRequest toRequest(Message<File> message) throws IOException {
JobParametersBuilder jobParametersBuilder = new JobParametersBuilder();
// jobParametersBuilder.addString(fileParameterName, message.getPayload().getName());
jobParametersBuilder.addString(filePathParameterName, message.getPayload().getCanonicalPath());
jobParametersBuilder.addDate("dummy", new Date()); // need to add at least one unique identifier so that it will run more than once
return new JobLaunchRequest(job, jobParametersBuilder.toJobParameters());
}
}
BatchIntegrationConfiguration.java
#Configuration
#EnableIntegration
#EnableBatchProcessing
public class BatchIntegrationConfiguration {
#Autowired
private JobBuilderFactory jobBuilderFactory;
#Autowired
private StepBuilderFactory stepBuilderFactory;
#Autowired
private JobRepository jobRepository;
#Bean
public MessageChannel files() {
return new DirectChannel();
}
#Bean
public FileMessageToJobRequest fileMessageToJobRequest() {
FileMessageToJobRequest fileMessageToJobRequest = new FileMessageToJobRequest();
// fileMessageToJobRequest.setFileParameterName("input.file.name")
fileMessageToJobRequest.setFilePathParameterName("input.file.path");
fileMessageToJobRequest.setJob(runBatchScriptJob());
return fileMessageToJobRequest;
}
#Bean
public JobLaunchingGateway jobLaunchingGateway() {
SimpleJobLauncher simpleJobLauncher = new SimpleJobLauncher();
simpleJobLauncher.setJobRepository(jobRepository);
simpleJobLauncher.setTaskExecutor(new SyncTaskExecutor());
JobLaunchingGateway jobLaunchingGateway = new JobLaunchingGateway(simpleJobLauncher);
return jobLaunchingGateway;
}
#Bean
public IntegrationFlow integrationFlow(JobLaunchingGateway jobLaunchingGateway) {
return IntegrationFlows.from(Files.inboundAdapter(new File("./src/main/resources")).
filter(new SimplePatternFileListFilter("simplebatchfile.bat")),
c -> c.poller(Pollers.fixedRate(10000).maxMessagesPerPoll(1))).
handle(fileMessageToJobRequest()).
handle(jobLaunchingGateway).
log(LoggingHandler.Level.WARN, "headers.id + ': ' + payload").
get();
}
#Bean
public Job runBatchScriptJob() {
return jobBuilderFactory.get("runBatchScriptJob")
.listener(new JobCompletionNotificationListener())
.start(runBatchScriptStep())
.build();
}
#Bean
public Step runBatchScriptStep() {
return stepBuilderFactory.get("runBatchScriptStep")
.tasklet(runBatchScriptTasklet(null))
.build();
}
#Bean
#StepScope
public Tasklet runBatchScriptTasklet(#Value("#{jobParameters['input.file.path']}") String filePath) {
RunBatchScriptTasklet tasklet = new RunBatchScriptTasklet();
tasklet.setFilePath(filePath);
return tasklet;
}
}
StackTrace
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'integrationFlow' defined in class path resource [com/example/batchprocessing/BatchIntegrationConfiguration.class]: Bean instantiation via factory method failed; nested exception is org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.integration.dsl.IntegrationFlow]: Factory method 'integrationFlow' threw exception; nested exception is java.lang.IllegalArgumentException: Found ambiguous parameter type [class java.lang.String] for method match: [public void com.example.batchprocessing.FileMessageToJobRequest.setFileParameterName(java.lang.String), public void com.example.batchprocessing.FileMessageToJobRequest.setJob(org.springframework.batch.core.Job)]
at org.springframework.beans.factory.support.ConstructorResolver.instantiate(ConstructorResolver.java:656) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.beans.factory.support.ConstructorResolver.instantiateUsingFactoryMethod(ConstructorResolver.java:636) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.instantiateUsingFactoryMethod(AbstractAutowireCapableBeanFactory.java:1338) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1177) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:557) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:517) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:323) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:222) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:321) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:202) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:879) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:878) ~[spring-context-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:550) ~[spring-context-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:747) [spring-boot-2.2.5.RELEASE.jar:2.2.5.RELEASE]
at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:397) [spring-boot-2.2.5.RELEASE.jar:2.2.5.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:315) [spring-boot-2.2.5.RELEASE.jar:2.2.5.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1226) [spring-boot-2.2.5.RELEASE.jar:2.2.5.RELEASE]
at org.springframework.boot.SpringApplication.run(SpringApplication.java:1215) [spring-boot-2.2.5.RELEASE.jar:2.2.5.RELEASE]
at com.example.batchprocessing.BatchProcessingApplication.main(BatchProcessingApplication.java:14) [classes/:na]
Caused by: org.springframework.beans.BeanInstantiationException: Failed to instantiate [org.springframework.integration.dsl.IntegrationFlow]: Factory method 'integrationFlow' threw exception; nested exception is java.lang.IllegalArgumentException: Found ambiguous parameter type [class java.lang.String] for method match: [public void com.example.batchprocessing.FileMessageToJobRequest.setFileParameterName(java.lang.String), public void com.example.batchprocessing.FileMessageToJobRequest.setJob(org.springframework.batch.core.Job)]
at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:185) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.beans.factory.support.ConstructorResolver.instantiate(ConstructorResolver.java:651) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
... 18 common frames omitted
Caused by: java.lang.IllegalArgumentException: Found ambiguous parameter type [class java.lang.String] for method match: [public void com.example.batchprocessing.FileMessageToJobRequest.setFileParameterName(java.lang.String), public void com.example.batchprocessing.FileMessageToJobRequest.setJob(org.springframework.batch.core.Job)]
at org.springframework.util.Assert.isNull(Assert.java:176) ~[spring-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.handler.support.MessagingMethodInvokerHelper.validateFallbackMethods(MessagingMethodInvokerHelper.java:755) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.handler.support.MessagingMethodInvokerHelper.findHandlerMethodsForTarget(MessagingMethodInvokerHelper.java:740) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.handler.support.MessagingMethodInvokerHelper.<init>(MessagingMethodInvokerHelper.java:294) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.handler.support.MessagingMethodInvokerHelper.<init>(MessagingMethodInvokerHelper.java:231) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.handler.support.MessagingMethodInvokerHelper.<init>(MessagingMethodInvokerHelper.java:225) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.handler.MethodInvokingMessageProcessor.<init>(MethodInvokingMessageProcessor.java:62) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.handler.ServiceActivatingHandler.<init>(ServiceActivatingHandler.java:39) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.dsl.BaseIntegrationFlowDefinition.handle(BaseIntegrationFlowDefinition.java:960) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.dsl.IntegrationFlowDefinition.handle(IntegrationFlowDefinition.java:510) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.dsl.IntegrationFlowDefinition.handle(IntegrationFlowDefinition.java:65) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.dsl.BaseIntegrationFlowDefinition.handle(BaseIntegrationFlowDefinition.java:939) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.dsl.IntegrationFlowDefinition.handle(IntegrationFlowDefinition.java:503) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.dsl.IntegrationFlowDefinition.handle(IntegrationFlowDefinition.java:65) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.dsl.BaseIntegrationFlowDefinition.handle(BaseIntegrationFlowDefinition.java:926) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.integration.dsl.IntegrationFlowDefinition.handle(IntegrationFlowDefinition.java:498) ~[spring-integration-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at com.example.batchprocessing.BatchIntegrationConfiguration.integrationFlow(BatchIntegrationConfiguration.java:78) ~[classes/:na]
at com.example.batchprocessing.BatchIntegrationConfiguration$$EnhancerBySpringCGLIB$$238a9f8a.CGLIB$integrationFlow$1(<generated>) ~[classes/:na]
at com.example.batchprocessing.BatchIntegrationConfiguration$$EnhancerBySpringCGLIB$$238a9f8a$$FastClassBySpringCGLIB$$b8a5aaf.invoke(<generated>) ~[classes/:na]
at org.springframework.cglib.proxy.MethodProxy.invokeSuper(MethodProxy.java:244) ~[spring-core-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at org.springframework.context.annotation.ConfigurationClassEnhancer$BeanMethodInterceptor.intercept(ConfigurationClassEnhancer.java:331) ~[spring-context-5.2.4.RELEASE.jar:5.2.4.RELEASE]
at com.example.batchprocessing.BatchIntegrationConfiguration$$EnhancerBySpringCGLIB$$238a9f8a.integrationFlow(<generated>) ~[classes/:na]
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) ~[na:1.8.0_211]
at sun.reflect.NativeMethodAccessorImpl.invoke(Unknown Source) ~[na:1.8.0_211]
at sun.reflect.DelegatingMethodAccessorImpl.invoke(Unknown Source) ~[na:1.8.0_211]
at java.lang.reflect.Method.invoke(Unknown Source) ~[na:1.8.0_211]
at org.springframework.beans.factory.support.SimpleInstantiationStrategy.instantiate(SimpleInstantiationStrategy.java:154) ~[spring-beans-5.2.4.RELEASE.jar:5.2.4.RELEASE]
... 19 common frames omitted
This one handle(fileMessageToJobRequest()) has to be changed to the transform(fileMessageToJobRequest()) since your FileMessageToJobRequest is really a #Transformer. The handle() doesn't understand that annotation and tries to figure out any candidate method to execute at runtime.
The message Found ambiguous parameter type means that there are several methods with different parameters which can be as message handling candidates. In this case we need to be more specific. Like your #Transformer is a good marker, but it is used from the wrong place - the handle() is for a #ServiceActivator.
Why does the code below give GroovyCastException?
class Main {
public static void main(String... args) {
Test test = new Test()
}
}
#CompileStatic #Newify
class Test {
private HashMap<String, A> hashMap = [:]
public Test() {
set()
test()
}
public void test() {
hashMap.each() { String string, A a ->
a.printString()
}
}
public void set() {
hashMap.put("aaa", B.new("xxx"))
hashMap.put("bbb", B.new("yyy"))
}
}
class A {
public String string = ""
public void printString() {
println(string)
}
}
class B extends A {
public B(String string) {
this.string = string
}
}
The stacktrace is:
Exception in thread "main" org.codehaus.groovy.runtime.typehandling.GroovyCastException: Cannot cast object 'main.Test#543e710e' with class 'main.Test' to class 'main.A'
at org.codehaus.groovy.runtime.typehandling.DefaultTypeTransformation.continueCastOnSAM(DefaultTypeTransformation.java:405)
at org.codehaus.groovy.runtime.typehandling.DefaultTypeTransformation.continueCastOnNumber(DefaultTypeTransformation.java:319)
at org.codehaus.groovy.runtime.typehandling.DefaultTypeTransformation.castToType(DefaultTypeTransformation.java:232)
at org.codehaus.groovy.runtime.ScriptBytecodeAdapter.castToType(ScriptBytecodeAdapter.java:603)
at main.Test$_test_closure1.doCall(Main.groovy:37)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:483)
at org.codehaus.groovy.reflection.CachedMethod.invoke(CachedMethod.java:93)
at groovy.lang.MetaMethod.doMethodInvoke(MetaMethod.java:325)
at org.codehaus.groovy.runtime.metaclass.ClosureMetaClass.invokeMethod(ClosureMetaClass.java:294)
at groovy.lang.MetaClassImpl.invokeMethod(MetaClassImpl.java:1019)
at groovy.lang.Closure.call(Closure.java:426)
at org.codehaus.groovy.runtime.DefaultGroovyMethods.callClosureForMapEntry(DefaultGroovyMethods.java:5226)
at org.codehaus.groovy.runtime.DefaultGroovyMethods.each(DefaultGroovyMethods.java:2107)
at main.Test.test(Main.groovy:36)
at main.Test.<init>(Main.groovy:32)
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:62)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.lang.reflect.Constructor.newInstance(Constructor.java:408)
at org.codehaus.groovy.reflection.CachedConstructor.invoke(CachedConstructor.java:80)
at org.codehaus.groovy.runtime.callsite.ConstructorSite$ConstructorSiteNoUnwrapNoCoerce.callConstructor(ConstructorSite.java:105)
at org.codehaus.groovy.runtime.callsite.CallSiteArray.defaultCallConstructor(CallSiteArray.java:60)
at org.codehaus.groovy.runtime.callsite.AbstractCallSite.callConstructor(AbstractCallSite.java:235)
at org.codehaus.groovy.runtime.callsite.AbstractCallSite.callConstructor(AbstractCallSite.java:239)
at main.Main.main(Main.groovy:19)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:483)
at com.intellij.rt.execution.application.AppMain.main(AppMain.java:140)
But when #CompileStatic is omitted, or when #Newify is omitted and B.new is replaced by new B, the code above gives no exception and runs as I expected.
The version of Groovy is 2.4.5.
It's probably a bug in groovy. You should maybe open an issue on JIRA.
If I decompile Test.test closure, I see :
public Object doCall(String string, A a) {
((A)ScriptBytecodeAdapter.castToType(((_test_closure1)this).getThisObject(), A.class))
.printString();
return null;
}
Groovy try to convert 'this' to A, not the variable a.
Without #Newify, the generation is correct :
public Object doCall(String k, A a) {
a.printString();
return null;
}
I use #Resource, #Bean to inject bean, But sometimes wrong bean injection. Why this?
-------- throw Exception
java.lang.ClassCastException: com.test.B cannot be cast to com.test.A at
com.test.ModelA.handle(ModelA.java:35) at
com.test.ModelA.handle(ModelA.java:35) at
com.test.AbstractModel.execute(AbstractRule.java:12) at
com.test.AbstractModel.execute(AbstractRule.java:9) at
com.test.modelChain.execute(modelChain.java:35) at
com.test.BManager.process(BManager.java:66) at
com.test.BManager.process(BManager.java:31) at
sun.reflect.GeneratedMethodAccessor121.invoke(Unknown Source) at
sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) at
java.lang.reflect.Method.invoke(Method.java:606) at
org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:317) at
org.springframework.aop.framework.ReflectiveMethodInvocation.invokeJoinpoint(ReflectiveMethodInvocation.java:190) at
org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:157) at
org.springframework.transaction.interceptor.TransactionInterceptor$1.proceedWithInvocation(TransactionInterceptor.java:98) at
org.springframework.transaction.interceptor.TransactionAspectSupport.invokeWithinTransaction(TransactionAspectSupport.java:262) at
org.springframework.transaction.interceptor.TransactionInterceptor.invoke(TransactionInterceptor.java:95) at
org.springframework.aop.framework.ReflectiveMethodInvocation.proceed(ReflectiveMethodInvocation.java:179) at
org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:207) at
com.sun.proxy.$Proxy41.process(Unknown Source) at
-----AConfig.class--------------------------------------------------
#Configuration
public class AConfig<T>{
#Autowired
private Model<T> modelA;
#Autowired
private Model<T> modelB;
#Bean
public List<Model<T>> getAModelList(){
List<Model<T>> lists = new ArrayList<Model<T>>();
lists.add(modelA);
return lists;
}
#Bean
public List<Model<T>> getBModelList(){
List<Model<T>> lists = new ArrayList<Model<T>>();
lists.add(modelB);
return lists;
}
}
-----AManager.class--------------------------------------------
#Component
public class AManager implements Manager<AA>{
#Autowired
private ModelChain<AA> modelChain;
#Resource(name="getAModelList")
private List<Model<AA>> aModelList;
public void process(){
modelChain.setModelList(aModelList);
// process Logic to use aModelList
}
}
-----BManager.class--------------------------------------------------
#Component
public class BManager implements Manager<BB>{
#Autowired
private ModelChain<BB> modelChain;
#Resource(name="getBModelList")
private List<Model<BB>> bModelList;
public void process(){
modelChain.setModelList(bModelList);
// process Logic to use bModelList
}
}
I'm looking to extend an inner class in Groovy, it's part of a mix-in pattern that needs a groovy calculation method to be added after class construction but natively use the accessors of the main class. Works in Java, not so much in Groovy. Help appreciated.
p.s. realize that with { } groovy construct may be an alternative... trying to get this to work
Base class (in Java):
public class JavaClass {
private String foo = "Foo";
private Calculation calculation;
public JavaClass() {
calculation = new Calculation();
}
public JavaClass(Calculation calculation) {
this.calculation = calculation;
}
public String getFoo() {
return foo;
}
public String getBar() {
return calculation.getBar();
}
public class Calculation {
public String getBar() {
return null;
}
}
}
I create a Groovy implementation: (I know it's a bit hokey, bear with me)
class GroovyCalculationClass extends JavaClass {
public GroovyCalculationClass() { }
public Calculation getCalculation() {
return new Calculation();
}
public class Calculation extends JavaClass.Calculation {
public String getBar() {
return getFoo() + "Bar";
}
}
}
Run this test:
class TestCalculation {
#Test
public void testCalculation() {
JavaClass javaClass = new JavaClass(
new GroovyCalculationClass().getCalculation());
Assert.assertEquals("FooBar", javaClass.getBar());
}
}
And get this:
java.lang.ArrayIndexOutOfBoundsException: 0
at com.modelshop.datacore.generator.GroovyCalculationClass$Calculation.(GroovyCalculationClass.groovy)
at sun.reflect.NativeConstructorAccessorImpl.newInstance0(Native Method)
at sun.reflect.NativeConstructorAccessorImpl.newInstance(NativeConstructorAccessorImpl.java:57)
at sun.reflect.DelegatingConstructorAccessorImpl.newInstance(DelegatingConstructorAccessorImpl.java:45)
at java.lang.reflect.Constructor.newInstance(Constructor.java:525)
at org.codehaus.groovy.reflection.CachedConstructor.invoke(CachedConstructor.java:77)
at org.codehaus.groovy.runtime.callsite.ConstructorSite$ConstructorSiteNoUnwrapNoCoerce.callConstructor(ConstructorSite.java:102)
at org.codehaus.groovy.runtime.callsite.CallSiteArray.defaultCallConstructor(CallSiteArray.java:57)
at org.codehaus.groovy.runtime.callsite.AbstractCallSite.callConstructor(AbstractCallSite.java:182)
at org.codehaus.groovy.runtime.callsite.AbstractCallSite.callConstructor(AbstractCallSite.java:190)
at com.modelshop.datacore.generator.GroovyCalculationClass.getCalculation(GroovyCalculationClass.groovy:12)
at com.modelshop.datacore.generator.GroovyCalculationClass$getCalculation.call(Unknown Source)
at org.codehaus.groovy.runtime.callsite.CallSiteArray.defaultCall(CallSiteArray.java:45)
at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:108)
at org.codehaus.groovy.runtime.callsite.AbstractCallSite.call(AbstractCallSite.java:112)
at com.modelshop.datacore.generator.TestCalculation.testCalculation(TestCalculation.groovy:17)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:45)
at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:15)
at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:42)
at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:20)
at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:263)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:68)
at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:47)
at org.junit.runners.ParentRunner$3.run(ParentRunner.java:231)
at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:60)
at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:229)
at org.junit.runners.ParentRunner.access$000(ParentRunner.java:50)
at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:222)
at org.junit.runners.ParentRunner.run(ParentRunner.java:300)
at org.junit.runner.JUnitCore.run(JUnitCore.java:157)
at com.intellij.junit4.JUnit4IdeaTestRunner.startRunnerWithArgs(JUnit4IdeaTestRunner.java:77)
at com.intellij.rt.execution.junit.JUnitStarter.prepareStreamsAndStart(JUnitStarter.java:195)
at com.intellij.rt.execution.junit.JUnitStarter.main(JUnitStarter.java:63)
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
at com.intellij.rt.execution.application.AppMain.main(AppMain.java:120)
Replace GroovyCalculationClass with identical JavaCalculationClass and everything works.
I have following setup:
2 FXML-Doxuments WelcomeScreen.fxml and Timesheet.fxml with it's both controllers WelcomeScreenController.java and TimesheetController.java.
On WelcomeScreenController I have an button action handler
createTimesheet(ActionEvent event){
// Some working code
final Calendar calendarStart = Calendar.getInstance();
calendarStart.setTime(sdf.parse(tfStartDate.getText()));
final Calendar calendarEnd = Calendar.getInstance();
calendarEnd.setTime(sdf.parse(tfEndDate.getText()));
final FXMLLoader loader = new FXMLLoader(getClass().getResource("Timesheet.fxml"));
final TimesheetControler timesheetControler = (TimesheetControler)loader.getController();
timesheetControler.setStartDate(calendarStart);
timesheetControler.setEndDate(calendarEnd);
timesheetControler.setHeadlineText("Timesheet (" + tfStartDate.getText() + " - " + tfEndDate.getText() + ")");
final Node node=(Node) event.getSource();
final Stage stage=(Stage) node.getScene().getWindow();
final Parent root = (Parent) loader.load();
stage.setScene(new Scene(root));
stage.show();
}
TimesheetController looks like this:
package de.liebich.work.report.emb.ui;
public class TimesheetControler implements Initializable {
#FXML
private Label lHeadline;
#FXML
private GridPane gTimesheetCheck;
private Calendar startDate;
private Calendar endDate;
private String user;
private String password;
private String baseURL;
private List<List<Label>> entries;
#Override
public void initialize(URL arg0, ResourceBundle arg1) {
}
public void setStartDate(Calendar startDate) {
this.startDate = startDate;
}
public void setEndDate(Calendar endDate) {
this.endDate = endDate;
}
public void setUser(String user) {
this.user = user;
}
public void setPassword(String pw) {
this.password = pw;
}
public void setBaseURL(String baseURL) {
this.baseURL = baseURL;
}
public void setHeadlineText(final String text){
lHeadline.setText(text);
}
}
When I call createTimesheet I get following error:
java.lang.RuntimeException: java.lang.reflect.InvocationTargetException
at javafx.fxml.FXMLLoader$ControllerMethodEventHandler.handle(FXMLLoader.java:1449)
at com.sun.javafx.event.CompositeEventHandler.dispatchBubblingEvent(CompositeEventHandler.java:69)
at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:217)
at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:170)
at com.sun.javafx.event.CompositeEventDispatcher.dispatchBubblingEvent(CompositeEventDispatcher.java:38)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:37)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:92)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:35)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:92)
at com.sun.javafx.event.EventUtil.fireEventImpl(EventUtil.java:53)
at com.sun.javafx.event.EventUtil.fireEvent(EventUtil.java:28)
at javafx.event.Event.fireEvent(Event.java:171)
at javafx.scene.Node.fireEvent(Node.java:6867)
at javafx.scene.control.Button.fire(Button.java:179)
at com.sun.javafx.scene.control.behavior.ButtonBehavior.mouseReleased(ButtonBehavior.java:193)
at com.sun.javafx.scene.control.skin.SkinBase$4.handle(SkinBase.java:336)
at com.sun.javafx.scene.control.skin.SkinBase$4.handle(SkinBase.java:329)
at com.sun.javafx.event.CompositeEventHandler.dispatchBubblingEvent(CompositeEventHandler.java:64)
at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:217)
at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:170)
at com.sun.javafx.event.CompositeEventDispatcher.dispatchBubblingEvent(CompositeEventDispatcher.java:38)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:37)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:92)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:35)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:92)
at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:35)
at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:92)
at com.sun.javafx.event.EventUtil.fireEventImpl(EventUtil.java:53)
at com.sun.javafx.event.EventUtil.fireEvent(EventUtil.java:33)
at javafx.event.Event.fireEvent(Event.java:171)
at javafx.scene.Scene$MouseHandler.process(Scene.java:3311)
at javafx.scene.Scene$MouseHandler.process(Scene.java:3151)
at javafx.scene.Scene$MouseHandler.access$1900(Scene.java:3106)
at javafx.scene.Scene.impl_processMouseEvent(Scene.java:1563)
at javafx.scene.Scene$ScenePeerListener.mouseEvent(Scene.java:2248)
at com.sun.javafx.tk.quantum.GlassViewEventHandler$MouseEventNotification.run(GlassViewEventHandler.java:250)
at com.sun.javafx.tk.quantum.GlassViewEventHandler$MouseEventNotification.run(GlassViewEventHandler.java:173)
at java.security.AccessController.doPrivileged(Native Method)
at com.sun.javafx.tk.quantum.GlassViewEventHandler.handleMouseEvent(GlassViewEventHandler.java:292)
at com.sun.glass.ui.View.handleMouseEvent(View.java:530)
at com.sun.glass.ui.View.notifyMouse(View.java:924)
at com.sun.glass.ui.win.WinApplication._runLoop(Native Method)
at com.sun.glass.ui.win.WinApplication.access$100(WinApplication.java:17)
at com.sun.glass.ui.win.WinApplication$3$1.run(WinApplication.java:67)
at java.lang.Thread.run(Thread.java:744)
Caused by: java.lang.reflect.InvocationTargetException
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:606)
at sun.reflect.misc.Trampoline.invoke(MethodUtil.java:75)
at sun.reflect.GeneratedMethodAccessor1.invoke(Unknown Source)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
at java.lang.reflect.Method.invoke(Method.java:606)
at sun.reflect.misc.MethodUtil.invoke(MethodUtil.java:279)
at javafx.fxml.FXMLLoader$ControllerMethodEventHandler.handle(FXMLLoader.java:1444)
... 44 more
Caused by: java.lang.NullPointerException
at de.liebich.work.report.emb.ui.WelcomeScreenControler.createTimesheet(WelcomeScreenControler.java:133)
... 54 more
What do I have to change to make my code working?
Call
loader.load();
before the line
final TimesheetControler timesheetControler = (TimesheetControler) loader.getController();
IMO there is no need to explain the reason of it. If you still doubt ask it in comment.
using
final TimesheetControler timesheetControler = (TimesheetControler)loader.load();