/** * Copyright 2005-2012 Akiban Technologies, Inc. * * Licensed 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 com.persistit.ref; /** * An abstract superclass for implementations of {@link PersistitReference}. A * concrete subclass implements the method: <blockquote> * * <pre> * public Object lookup(Object id) * </pre> * * </blockquote> which should return the Object associated with the supplied id, * or <code>null</code> if there is none. The meaning of the identifier, and the * mechanism used to look up and deserialize the associated object (the * referent), are implementation-specific. * * @version 1.0 */ public abstract class AbstractReference implements PersistitReference { protected Object _id; protected boolean _knownNull; protected transient Object _referent; /** * No-arg constructor supplied for object serialization/deserialization. */ protected AbstractReference() { } /** * Construct a reference to the referent Object with the supplied persistent * identifier. For correct operation, the referent Object must be equivalent * to the object that would result from invoking <code>lookup</code> on the * persistent identifier. the object that would be returned by the lookup * * @param id * The persistent identifier. The value of the id must be * associated with a unique referent object, and must be stable * over time. * @param referent * The object identified by the id */ protected AbstractReference(final Object id, final Object referent) { _id = id; _referent = referent; _knownNull = referent == null; } /** * Construct a reference using the persistent identity of an object. A * subsequent invocation of the <code>get</code> method will cause the * object to be looked up and instantiated. * * @param id */ protected AbstractReference(final Object id) { _id = id; _knownNull = false; } /** * Gets the referent object. If the object has already been looked up, or if * this reference was created using the two-argument constructor, then this * merely returns the object. Otherwise this method attempts to look up and * instantiate the object using its persistent identifier. * * @return The referent object. */ @Override public Object get() { if (_id == null) { throw new IllegalStateException("identifier not initialized"); } if (_referent != null) return _referent; if (_knownNull) return null; _referent = lookup(_id); if (_referent == null) _knownNull = true; return _referent; } /** * Look up and instantiate an object using its persistent identifier. * Typically this will be done by setting up a * {@link com.persistit.Exchange} and fetching its value. * * @param id * The identifier * @return The referent object. */ protected abstract Object lookup(Object id); }