/* * Licensed to the Apache Software Foundation (ASF) under one or more * contributor license agreements. See the NOTICE file distributed with * this work for additional information regarding copyright ownership. * The ASF licenses this file to You under the Apache License, Version 2.0 * (the "License"); you may not use this file except in compliance with * the License. You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package org.apache.commons.collections4; import static org.junit.Assert.*; import java.util.ArrayList; import java.util.Collection; import java.util.Collections; import java.util.HashMap; import java.util.Map; import org.apache.commons.collections4.functors.EqualPredicate; import org.apache.commons.collections4.functors.ExceptionClosure; import org.apache.commons.collections4.functors.FalsePredicate; import org.apache.commons.collections4.functors.NOPClosure; import org.apache.commons.collections4.functors.TruePredicate; import org.junit.Test; /** * Tests the ClosureUtils class. * * @since 3.0 * @version $Id$ */ public class ClosureUtilsTest { private static final Object cString = "Hello"; static class MockClosure<T> implements Closure<T> { int count = 0; @Override public void execute(final T object) { count++; } public void reset() { count = 0; } } static class MockTransformer<T> implements Transformer<T, T> { int count = 0; @Override public T transform(final T object) { count++; return object; } } // exceptionClosure //------------------------------------------------------------------ @Test public void testExceptionClosure() { assertNotNull(ClosureUtils.exceptionClosure()); assertSame(ClosureUtils.exceptionClosure(), ClosureUtils.exceptionClosure()); try { ClosureUtils.exceptionClosure().execute(null); } catch (final FunctorException ex) { try { ClosureUtils.exceptionClosure().execute(cString); } catch (final FunctorException ex2) { return; } } fail(); } // nopClosure //------------------------------------------------------------------ @Test public void testNopClosure() { final StringBuilder buf = new StringBuilder("Hello"); ClosureUtils.nopClosure().execute(null); assertEquals("Hello", buf.toString()); ClosureUtils.nopClosure().execute("Hello"); assertEquals("Hello", buf.toString()); } // invokeClosure //------------------------------------------------------------------ @Test public void testInvokeClosure() { StringBuffer buf = new StringBuffer("Hello"); // Only StringBuffer has setLength() method ClosureUtils.invokerClosure("reverse").execute(buf); assertEquals("olleH", buf.toString()); buf = new StringBuffer("Hello"); ClosureUtils.invokerClosure("setLength", new Class[] {Integer.TYPE}, new Object[] {Integer.valueOf(2)}).execute(buf); assertEquals("He", buf.toString()); } // forClosure //------------------------------------------------------------------ @Test public void testForClosure() { final MockClosure<Object> cmd = new MockClosure<Object>(); ClosureUtils.forClosure(5, cmd).execute(null); assertEquals(5, cmd.count); assertSame(NOPClosure.INSTANCE, ClosureUtils.forClosure(0, new MockClosure<Object>())); assertSame(NOPClosure.INSTANCE, ClosureUtils.forClosure(-1, new MockClosure<Object>())); assertSame(NOPClosure.INSTANCE, ClosureUtils.forClosure(1, null)); assertSame(NOPClosure.INSTANCE, ClosureUtils.forClosure(3, null)); assertSame(cmd, ClosureUtils.forClosure(1, cmd)); } // whileClosure //------------------------------------------------------------------ @Test public void testWhileClosure() { MockClosure<Object> cmd = new MockClosure<Object>(); ClosureUtils.whileClosure(FalsePredicate.falsePredicate(), cmd).execute(null); assertEquals(0, cmd.count); cmd = new MockClosure<Object>(); ClosureUtils.whileClosure(PredicateUtils.uniquePredicate(), cmd).execute(null); assertEquals(1, cmd.count); try { ClosureUtils.whileClosure(null, ClosureUtils.nopClosure()); fail(); } catch (final NullPointerException ex) {} try { ClosureUtils.whileClosure(FalsePredicate.falsePredicate(), null); fail(); } catch (final NullPointerException ex) {} try { ClosureUtils.whileClosure(null, null); fail(); } catch (final NullPointerException ex) {} } // doWhileClosure //------------------------------------------------------------------ @Test public void testDoWhileClosure() { MockClosure<Object> cmd = new MockClosure<Object>(); ClosureUtils.doWhileClosure(cmd, FalsePredicate.falsePredicate()).execute(null); assertEquals(1, cmd.count); cmd = new MockClosure<Object>(); ClosureUtils.doWhileClosure(cmd, PredicateUtils.uniquePredicate()).execute(null); assertEquals(2, cmd.count); try { ClosureUtils.doWhileClosure(null, null); fail(); } catch (final NullPointerException ex) {} } // chainedClosure //------------------------------------------------------------------ @Test @SuppressWarnings("unchecked") public void testChainedClosure() { MockClosure<Object> a = new MockClosure<Object>(); MockClosure<Object> b = new MockClosure<Object>(); ClosureUtils.chainedClosure(a, b).execute(null); assertEquals(1, a.count); assertEquals(1, b.count); a = new MockClosure<Object>(); b = new MockClosure<Object>(); ClosureUtils.<Object>chainedClosure(new Closure[] {a, b, a}).execute(null); assertEquals(2, a.count); assertEquals(1, b.count); a = new MockClosure<Object>(); b = new MockClosure<Object>(); Collection<Closure<Object>> coll = new ArrayList<Closure<Object>>(); coll.add(b); coll.add(a); coll.add(b); ClosureUtils.<Object>chainedClosure(coll).execute(null); assertEquals(1, a.count); assertEquals(2, b.count); assertSame(NOPClosure.INSTANCE, ClosureUtils.<Object>chainedClosure(new Closure[0])); assertSame(NOPClosure.INSTANCE, ClosureUtils.<Object>chainedClosure(Collections.<Closure<Object>>emptyList())); try { ClosureUtils.chainedClosure(null, null); fail(); } catch (final NullPointerException ex) {} try { ClosureUtils.<Object>chainedClosure((Closure[]) null); fail(); } catch (final NullPointerException ex) {} try { ClosureUtils.<Object>chainedClosure((Collection<Closure<Object>>) null); fail(); } catch (final NullPointerException ex) {} try { ClosureUtils.<Object>chainedClosure(new Closure[] {null, null}); fail(); } catch (final NullPointerException ex) {} try { coll = new ArrayList<Closure<Object>>(); coll.add(null); coll.add(null); ClosureUtils.chainedClosure(coll); fail(); } catch (final NullPointerException ex) {} } // ifClosure //------------------------------------------------------------------ @Test public void testIfClosure() { MockClosure<Object> a = new MockClosure<Object>(); MockClosure<Object> b = null; ClosureUtils.ifClosure(TruePredicate.truePredicate(), a).execute(null); assertEquals(1, a.count); a = new MockClosure<Object>(); ClosureUtils.ifClosure(FalsePredicate.<Object>falsePredicate(), a).execute(null); assertEquals(0, a.count); a = new MockClosure<Object>(); b = new MockClosure<Object>(); ClosureUtils.ifClosure(TruePredicate.<Object>truePredicate(), a, b).execute(null); assertEquals(1, a.count); assertEquals(0, b.count); a = new MockClosure<Object>(); b = new MockClosure<Object>(); ClosureUtils.ifClosure(FalsePredicate.<Object>falsePredicate(), a, b).execute(null); assertEquals(0, a.count); assertEquals(1, b.count); } // switchClosure //------------------------------------------------------------------ @Test @SuppressWarnings("unchecked") public void testSwitchClosure() { final MockClosure<String> a = new MockClosure<String>(); final MockClosure<String> b = new MockClosure<String>(); ClosureUtils.<String>switchClosure( new Predicate[] { EqualPredicate.equalPredicate("HELLO"), EqualPredicate.equalPredicate("THERE") }, new Closure[] { a, b }).execute("WELL"); assertEquals(0, a.count); assertEquals(0, b.count); a.reset(); b.reset(); ClosureUtils.<String>switchClosure( new Predicate[] { EqualPredicate.equalPredicate("HELLO"), EqualPredicate.equalPredicate("THERE") }, new Closure[] { a, b }).execute("HELLO"); assertEquals(1, a.count); assertEquals(0, b.count); a.reset(); b.reset(); final MockClosure<String> c = new MockClosure<String>(); ClosureUtils.<String>switchClosure( new Predicate[] { EqualPredicate.equalPredicate("HELLO"), EqualPredicate.equalPredicate("THERE") }, new Closure[] { a, b }, c).execute("WELL"); assertEquals(0, a.count); assertEquals(0, b.count); assertEquals(1, c.count); a.reset(); b.reset(); final Map<Predicate<String>, Closure<String>> map = new HashMap<Predicate<String>, Closure<String>>(); map.put(EqualPredicate.equalPredicate("HELLO"), a); map.put(EqualPredicate.equalPredicate("THERE"), b); ClosureUtils.<String>switchClosure(map).execute(null); assertEquals(0, a.count); assertEquals(0, b.count); a.reset(); b.reset(); map.clear(); map.put(EqualPredicate.equalPredicate("HELLO"), a); map.put(EqualPredicate.equalPredicate("THERE"), b); ClosureUtils.switchClosure(map).execute("THERE"); assertEquals(0, a.count); assertEquals(1, b.count); a.reset(); b.reset(); c.reset(); map.clear(); map.put(EqualPredicate.equalPredicate("HELLO"), a); map.put(EqualPredicate.equalPredicate("THERE"), b); map.put(null, c); ClosureUtils.switchClosure(map).execute("WELL"); assertEquals(0, a.count); assertEquals(0, b.count); assertEquals(1, c.count); assertEquals(NOPClosure.INSTANCE, ClosureUtils.<String>switchClosure(new Predicate[0], new Closure[0])); assertEquals(NOPClosure.INSTANCE, ClosureUtils.<String>switchClosure(new HashMap<Predicate<String>, Closure<String>>())); map.clear(); map.put(null, null); assertEquals(NOPClosure.INSTANCE, ClosureUtils.switchClosure(map)); try { ClosureUtils.switchClosure(null, null); fail(); } catch (final NullPointerException ex) {} try { ClosureUtils.<String>switchClosure((Predicate<String>[]) null, (Closure<String>[]) null); fail(); } catch (final NullPointerException ex) {} try { ClosureUtils.<String>switchClosure((Map<Predicate<String>, Closure<String>>) null); fail(); } catch (final NullPointerException ex) {} try { ClosureUtils.<String>switchClosure(new Predicate[2], new Closure[2]); fail(); } catch (final NullPointerException ex) {} try { ClosureUtils.<String>switchClosure( new Predicate[] { TruePredicate.<String>truePredicate() }, new Closure[] { a, b }); fail(); } catch (final IllegalArgumentException ex) {} } // switchMapClosure //------------------------------------------------------------------ @Test public void testSwitchMapClosure() { final MockClosure<String> a = new MockClosure<String>(); final MockClosure<String> b = new MockClosure<String>(); final Map<String, Closure<String>> map = new HashMap<String, Closure<String>>(); map.put("HELLO", a); map.put("THERE", b); ClosureUtils.switchMapClosure(map).execute(null); assertEquals(0, a.count); assertEquals(0, b.count); a.reset(); b.reset(); map.clear(); map.put("HELLO", a); map.put("THERE", b); ClosureUtils.switchMapClosure(map).execute("THERE"); assertEquals(0, a.count); assertEquals(1, b.count); a.reset(); b.reset(); map.clear(); final MockClosure<String> c = new MockClosure<String>(); map.put("HELLO", a); map.put("THERE", b); map.put(null, c); ClosureUtils.switchMapClosure(map).execute("WELL"); assertEquals(0, a.count); assertEquals(0, b.count); assertEquals(1, c.count); assertEquals(NOPClosure.INSTANCE, ClosureUtils.switchMapClosure(new HashMap<String, Closure<String>>())); try { ClosureUtils.switchMapClosure(null); fail(); } catch (final NullPointerException ex) {} } // asClosure //------------------------------------------------------------------ @Test public void testTransformerClosure() { final MockTransformer<Object> mock = new MockTransformer<Object>(); final Closure<Object> closure = ClosureUtils.asClosure(mock); closure.execute(null); assertEquals(1, mock.count); closure.execute(null); assertEquals(2, mock.count); assertEquals(ClosureUtils.nopClosure(), ClosureUtils.asClosure(null)); } // misc tests //------------------------------------------------------------------ /** * Test that all Closure singletons hold singleton pattern in * serialization/deserialization process. */ @Test public void testSingletonPatternInSerialization() { final Object[] singletones = new Object[] { ExceptionClosure.INSTANCE, NOPClosure.INSTANCE, }; for (final Object original : singletones) { TestUtils.assertSameAfterSerialization( "Singletone patern broken for " + original.getClass(), original ); } } }