1 /******************************************************************************* 2 * Copyright (c) 2007, 2008 Matthew Hall and others. 3 * 4 * This program and the accompanying materials 5 * are made available under the terms of the Eclipse Public License 2.0 6 * which accompanies this distribution, and is available at 7 * https://www.eclipse.org/legal/epl-2.0/ 8 * 9 * SPDX-License-Identifier: EPL-2.0 10 * 11 * Contributors: 12 * Matthew Hall - initial API and implementation (bug 212468) 13 * Matthew Hall - bug 213145 14 ******************************************************************************/ 15 16 package org.eclipse.core.tests.internal.databinding.observable; 17 18 import static org.junit.Assert.assertEquals; 19 import static org.junit.Assert.assertFalse; 20 import static org.junit.Assert.assertTrue; 21 22 import java.util.concurrent.atomic.AtomicInteger; 23 24 import org.eclipse.core.databinding.observable.AbstractObservable; 25 import org.eclipse.core.databinding.observable.IObservable; 26 import org.eclipse.core.databinding.observable.Observables; 27 import org.eclipse.core.databinding.observable.Realm; 28 import org.eclipse.core.databinding.observable.value.IObservableValue; 29 import org.eclipse.core.databinding.observable.value.WritableValue; 30 import org.eclipse.core.internal.databinding.observable.StalenessObservableValue; 31 import org.eclipse.jface.databinding.conformance.ObservableValueContractTest; 32 import org.eclipse.jface.databinding.conformance.delegate.AbstractObservableValueContractDelegate; 33 import org.eclipse.jface.tests.databinding.AbstractDefaultRealmTestCase; 34 import org.junit.Test; 35 36 import junit.framework.TestSuite; 37 38 /** 39 * Tests for StalenessObservableValue 40 * 41 * @since 1.1 42 */ 43 public class StalenessObservableValueTest extends AbstractDefaultRealmTestCase { 44 45 /** 46 * Test that {@link StalenessObservableValue#getValue} returns the new value 47 * when called inside the value change listener. 48 */ 49 @Test valueDuringListenerCallback()50 public void valueDuringListenerCallback() { 51 IObservableValue<String> source = new WritableValue<>("a", String.class); 52 IObservableValue<String> delayed = Observables.observeDelayedValue(1, source); 53 IObservableValue<Boolean> stale = Observables.observeStale(delayed); 54 55 AtomicInteger nrStaleEvents = new AtomicInteger(); 56 57 stale.addValueChangeListener(e -> { 58 if (nrStaleEvents.incrementAndGet() == 1) { 59 assertTrue(stale.getValue()); 60 assertTrue(e.diff.getNewValue()); 61 assertFalse(e.diff.getOldValue()); 62 } else { 63 assertFalse(stale.getValue()); 64 assertFalse(e.diff.getNewValue()); 65 assertTrue(e.diff.getOldValue()); 66 } 67 }); 68 69 source.setValue("b"); 70 71 // Makes the observable non-stale 72 delayed.getValue(); 73 74 assertEquals(2, nrStaleEvents.get()); 75 } 76 addConformanceTest(TestSuite suite)77 public static void addConformanceTest(TestSuite suite) { 78 suite.addTest(ObservableValueContractTest.suite(new Delegate())); 79 } 80 81 static class ObservableStub extends AbstractObservable { 82 boolean stale; 83 ObservableStub(Realm realm)84 public ObservableStub(Realm realm) { 85 super(realm); 86 } 87 88 @Override isStale()89 public boolean isStale() { 90 return stale; 91 } 92 setStale(boolean stale)93 public void setStale(boolean stale) { 94 if (this.stale == stale) 95 return; 96 97 this.stale = stale; 98 if (stale) { 99 fireStale(); 100 } else { 101 fireChange(); 102 } 103 } 104 } 105 106 static class StalenessObservableValueStub extends StalenessObservableValue { 107 ObservableStub target; 108 StalenessObservableValueStub(ObservableStub target)109 StalenessObservableValueStub(ObservableStub target) { 110 super(target); 111 this.target = target; 112 } 113 } 114 115 static class Delegate extends AbstractObservableValueContractDelegate { 116 @Override createObservableValue(Realm realm)117 public IObservableValue<?> createObservableValue(Realm realm) { 118 return new StalenessObservableValueStub(new ObservableStub(realm)); 119 } 120 121 @Override change(IObservable observable)122 public void change(IObservable observable) { 123 ObservableStub target = ((StalenessObservableValueStub) observable).target; 124 target.setStale(!target.isStale()); 125 } 126 127 @Override getValueType(IObservableValue<?> observable)128 public Object getValueType(IObservableValue<?> observable) { 129 return Boolean.TYPE; 130 } 131 } 132 }