/** * Copyright (C) 2014 - present by OpenGamma Inc. and the OpenGamma group of companies * * Please see distribution for license. */ package com.opengamma.sesame.proxy; import static com.opengamma.sesame.config.ConfigBuilder.config; import static com.opengamma.sesame.config.ConfigBuilder.implementations; import static org.hamcrest.MatcherAssert.assertThat; import static org.hamcrest.Matchers.containsString; import static org.hamcrest.Matchers.is; import java.lang.reflect.Proxy; import org.testng.annotations.Test; import com.opengamma.sesame.config.EngineUtils; import com.opengamma.sesame.config.FunctionModelConfig; import com.opengamma.sesame.engine.ComponentMap; import com.opengamma.sesame.function.FunctionMetadata; import com.opengamma.sesame.function.Output; import com.opengamma.sesame.graph.FunctionBuilder; import com.opengamma.sesame.graph.FunctionModel; import com.opengamma.util.result.Result; import com.opengamma.util.test.TestGroup; /** * Tests to check that the ExceptionWrappingProxy behaves as expected. */ @Test(groups= TestGroup.UNIT) public class ExceptionWrappingProxyTest { @Test public void testNoProxyCreatedWhenNoMethodsReturnResult() { FunctionModelConfig config = config(implementations(MockSingleFn.class, HappyMockSingleFn.class)); FunctionMetadata metadata = EngineUtils.createMetadata(MockSingleFn.class, "doSomethingWithoutResult"); FunctionModel functionModel = FunctionModel.forFunction(metadata, config, ComponentMap.EMPTY.getComponentTypes(), ExceptionWrappingProxy.INSTANCE); Object fn = functionModel.build(new FunctionBuilder(), ComponentMap.EMPTY).getReceiver(); assertThat(fn instanceof MockSingleFn, is(true)); assertThat(Proxy.isProxyClass(fn.getClass()), is(false)); } @Test public void testProxyCreatedWhenMethodsReturnResult() { // Counterpoint to the test above MockFn fn = createHappyResultReturner(); assertThat(Proxy.isProxyClass(fn.getClass()), is(true)); } @Test public void nonExceptionMethodReturnsNormally() { MockFn fn = createHappyNonResultReturner(); assertThat(fn.doSomethingElse(), is(true)); } @Test public void nonExceptionResultMethodReturnsNormally() { MockFn fn = createHappyResultReturner(); Result<Boolean> result = fn.doSomething(); assertThat(result.isSuccess(), is(true)); assertThat(result.getValue(), is(true)); } @Test(expectedExceptions = RuntimeException.class) public void exceptionMethodThrowsException() { MockFn fn = createUnappyNonResultReturner(); assertThat(fn.doSomethingElse(), is(true)); } @Test public void exceptionResultMethodReturnsNormally() { MockFn fn = createUnhappyResultReturner(); Result<Boolean> result = fn.doSomething(); assertThat(result.isSuccess(), is(false)); assertThat(result.getFailureMessage(), containsString("so unhappy")); } private MockFn createHappyResultReturner() { return createMockFn(HappyMockFn.class); } private MockFn createHappyNonResultReturner() { return createMockFn(HappyMockFn.class); } private MockFn createUnhappyResultReturner() { return createMockFn(UnhappyMockFn.class); } private MockFn createUnappyNonResultReturner() { return createMockFn(UnhappyMockFn.class); } private MockFn createMockFn(Class<? extends MockFn> implementationClass) { FunctionModelConfig config = config(implementations(MockFn.class, implementationClass)); return FunctionModel.build(MockFn.class, config, ComponentMap.EMPTY, ExceptionWrappingProxy.INSTANCE); } private interface MockFn { @Output("this") Result<Boolean> doSomething(); @Output("that") boolean doSomethingElse(); } public static class HappyMockFn implements MockFn { public Result<Boolean> doSomething() { return Result.success(true); } @Override public boolean doSomethingElse() { return true; } } public static class UnhappyMockFn implements MockFn { public Result<Boolean> doSomething() { throw new RuntimeException("so unhappy"); } @Override public boolean doSomethingElse() { throw new RuntimeException("so sad"); } } private interface MockSingleFn { @Output(value = "that") boolean doSomethingWithoutResult(); } public static class HappyMockSingleFn implements MockSingleFn { @Override public boolean doSomethingWithoutResult() { return true; } } }