| /*========================================================================= |
| * Copyright (c) 2010-2014 Pivotal Software, Inc. All Rights Reserved. |
| * This product is protected by U.S. and international copyright |
| * and intellectual property laws. Pivotal products are covered by |
| * one or more patents listed at http://www.pivotal.io/patents. |
| *========================================================================= |
| */ |
| package com.gemstone.gemfire.pdx.internal; |
| |
| import java.nio.ByteBuffer; |
| import java.util.Date; |
| |
| import com.gemstone.gemfire.internal.InternalDataSerializer; |
| import com.gemstone.gemfire.internal.cache.GemFireCacheImpl; |
| import com.gemstone.gemfire.internal.tcp.ByteBufferInputStream.ByteSourceFactory; |
| import com.gemstone.gemfire.pdx.PdxInstance; |
| import com.gemstone.gemfire.pdx.PdxInstanceFactory; |
| import com.gemstone.gemfire.pdx.PdxUnreadFields; |
| |
| /** |
| * TODO |
| * without |
| * defining a real class. These PdxInstances can never be deserialized |
| * but you can access their fields just like any other pdx. |
| * <p>The current implementation of this interface is meant for internal use only. |
| * The way it defines a PdxType is expensive since it can never figure out it is |
| * already defined without doing an expensive check in the type registry. |
| * We should optimize this before making this a public feature. |
| * @author darrel |
| * |
| */ |
| public class PdxInstanceFactoryImpl implements |
| PdxInstanceFactory { |
| |
| private final PdxWriterImpl writer; |
| private boolean created = false; |
| |
| private PdxInstanceFactoryImpl(String name, boolean expectDomainClass) { |
| PdxOutputStream os = new PdxOutputStream(); |
| PdxType pt = new PdxType(name, expectDomainClass); |
| GemFireCacheImpl gfc = GemFireCacheImpl.getForPdx("PDX registry is unavailable because the Cache has been closed."); |
| TypeRegistry tr = gfc.getPdxRegistry(); |
| this.writer = new PdxWriterImpl(pt, tr, os); |
| } |
| |
| public static PdxInstanceFactory newCreator(String name, boolean expectDomainClass) { |
| return new PdxInstanceFactoryImpl(name, expectDomainClass); |
| } |
| |
| public PdxInstance create() { |
| if (this.created) { |
| throw new IllegalStateException("The create method can only be called once."); |
| } |
| this.created = true; |
| this.writer.completeByteStreamGeneration(); |
| return this.writer.makePdxInstance(); |
| } |
| |
| public PdxInstanceFactory writeChar(String fieldName, char value) { |
| this.writer.writeChar(fieldName, value); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeBoolean(String fieldName, boolean value) { |
| this.writer.writeBoolean(fieldName, value); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeByte(String fieldName, byte value) { |
| this.writer.writeByte(fieldName, value); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeShort(String fieldName, short value) { |
| this.writer.writeShort(fieldName, value); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeInt(String fieldName, int value) { |
| this.writer.writeInt(fieldName, value); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeLong(String fieldName, long value) { |
| this.writer.writeLong(fieldName, value); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeFloat(String fieldName, float value) { |
| this.writer.writeFloat(fieldName, value); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeDouble(String fieldName, double value) { |
| this.writer.writeDouble(fieldName, value); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeDate(String fieldName, Date date) { |
| this.writer.writeDate(fieldName, date); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeString(String fieldName, String value) { |
| this.writer.writeString(fieldName, value); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeObject(String fieldName, Object object) { |
| return writeObject(fieldName, object, false); |
| } |
| |
| public PdxInstanceFactory writeBooleanArray(String fieldName, boolean[] array) { |
| this.writer.writeBooleanArray(fieldName, array); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeCharArray(String fieldName, char[] array) { |
| this.writer.writeCharArray(fieldName, array); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeByteArray(String fieldName, byte[] array) { |
| this.writer.writeByteArray(fieldName, array); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeShortArray(String fieldName, short[] array) { |
| this.writer.writeShortArray(fieldName, array); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeIntArray(String fieldName, int[] array) { |
| this.writer.writeIntArray(fieldName, array); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeLongArray(String fieldName, long[] array) { |
| this.writer.writeLongArray(fieldName, array); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeFloatArray(String fieldName, float[] array) { |
| this.writer.writeFloatArray(fieldName, array); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeDoubleArray(String fieldName, double[] array) { |
| this.writer.writeDoubleArray(fieldName, array); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeStringArray(String fieldName, String[] array) { |
| this.writer.writeStringArray(fieldName, array); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeObjectArray(String fieldName, Object[] array) { |
| return writeObjectArray(fieldName, array, false); |
| } |
| |
| public PdxInstanceFactory writeUnreadFields(PdxUnreadFields unread) { |
| this.writer.writeUnreadFields(unread); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeRaw(PdxField field, ByteBuffer rawData) { |
| this.writer.writeRawField(field, ByteSourceFactory.create(rawData)); |
| return this; |
| } |
| |
| |
| public PdxInstanceFactory writeArrayOfByteArrays(String fieldName, |
| byte[][] array) { |
| this.writer.writeArrayOfByteArrays(fieldName, array); |
| return this; |
| } |
| |
| public <CT, VT extends CT> PdxInstanceFactory writeField(String fieldName, VT fieldValue, Class<CT> fieldType) { |
| return writeField(fieldName, fieldValue, fieldType, false); |
| } |
| |
| public PdxInstanceFactory markIdentityField(String fieldName) { |
| this.writer.markIdentityField(fieldName); |
| return this; |
| } |
| |
| public PdxInstanceFactory writeObject(String fieldName, Object value, |
| boolean checkPortability) { |
| if (InternalDataSerializer.is662SerializationEnabled()) { |
| boolean alreadyInProgress = InternalDataSerializer.isPdxSerializationInProgress(); |
| if (!alreadyInProgress) { |
| InternalDataSerializer.setPdxSerializationInProgress(true); |
| try { |
| this.writer.writeObject(fieldName, value, checkPortability); |
| } finally { |
| InternalDataSerializer.setPdxSerializationInProgress(false); |
| } |
| } else { |
| this.writer.writeObject(fieldName, value, checkPortability); |
| } |
| } else { |
| this.writer.writeObject(fieldName, value, checkPortability); |
| } |
| |
| return this; |
| } |
| |
| public PdxInstanceFactory writeObjectArray(String fieldName, Object[] value, |
| boolean checkPortability) { |
| if (InternalDataSerializer.is662SerializationEnabled()) { |
| boolean alreadyInProgress = InternalDataSerializer.isPdxSerializationInProgress(); |
| if (!alreadyInProgress) { |
| InternalDataSerializer.setPdxSerializationInProgress(true); |
| try { |
| this.writer.writeObjectArray(fieldName, value, checkPortability); |
| } finally { |
| InternalDataSerializer.setPdxSerializationInProgress(false); |
| } |
| } else { |
| this.writer.writeObjectArray(fieldName, value, checkPortability); |
| } |
| } else { |
| this.writer.writeObjectArray(fieldName, value, checkPortability); |
| } |
| return this; |
| } |
| |
| public <CT, VT extends CT> PdxInstanceFactory writeField(String fieldName, |
| VT fieldValue, Class<CT> fieldType, boolean checkPortability) { |
| if (InternalDataSerializer.is662SerializationEnabled()) { |
| boolean alreadyInProgress = InternalDataSerializer.isPdxSerializationInProgress(); |
| if (!alreadyInProgress) { |
| InternalDataSerializer.setPdxSerializationInProgress(true); |
| try { |
| this.writer.writeField(fieldName, fieldValue, fieldType, checkPortability); |
| } finally { |
| InternalDataSerializer.setPdxSerializationInProgress(false); |
| } |
| } else { |
| this.writer.writeField(fieldName, fieldValue, fieldType, checkPortability); |
| } |
| } else { |
| this.writer.writeField(fieldName, fieldValue, fieldType, checkPortability); |
| } |
| return this; |
| } |
| |
| public static PdxInstance createPdxEnum(String className, String enumName, int enumOrdinal, GemFireCacheImpl gfc) { |
| if (className == null) { |
| throw new IllegalArgumentException("className must not be null"); |
| } |
| if (enumName == null) { |
| throw new IllegalArgumentException("enumName must not be null"); |
| } |
| TypeRegistry tr = gfc.getPdxRegistry(); |
| EnumInfo ei = new EnumInfo(className, enumName, enumOrdinal); |
| return ei.getPdxInstance(tr.defineEnum(ei)); |
| } |
| |
| } |