ValueStreamHelper.java :  » Database-ORM » ODAL » com » completex » objective » components » persistency » type » Java Open Source

Java Open Source » Database ORM » ODAL 
ODAL » com » completex » objective » components » persistency » type » ValueStreamHelper.java
package com.completex.objective.components.persistency.type;

import com.completex.objective.components.persistency.ColumnType;
import com.completex.objective.components.persistency.xml.XmlRuntimeException;
import com.completex.objective.util.XmlDomHelper;
import sun.misc.BASE64Encoder;
import sun.misc.BASE64Decoder;

import java.io.ByteArrayInputStream;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.ObjectOutputStream;
import java.io.ObjectInputStream;
import java.io.InputStream;
import java.math.BigDecimal;
import java.math.BigInteger;
import java.sql.Blob;
import java.sql.Clob;
import java.sql.Time;
import java.sql.Timestamp;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;

/**
 * @author Gennady Krizhevsky
 */
public class ValueStreamHelper {

    public static final Map NUMERIC = new HashMap();
    public static final LongFactory LONG_FACTORY = new LongFactory();
    public static final IntegerFactory INTEGER_FACTORY = new IntegerFactory();
    public static final ShortFactory SHORT_FACTORY = new ShortFactory();
    public static final FloatFactory FLOAT_FACTORY = new FloatFactory();
    public static final DoubleFactory DOUBLE_FACTORY = new DoubleFactory();
    public static final ByteFactory BYTE_FACTORY = new ByteFactory();

    static {
        NUMERIC.put(Long.class.getName(), LONG_FACTORY);
        NUMERIC.put(Integer.class.getName(), INTEGER_FACTORY);
        NUMERIC.put(Short.class.getName(), SHORT_FACTORY);
        NUMERIC.put(Float.class.getName(), FLOAT_FACTORY);
        NUMERIC.put(Double.class.getName(), DOUBLE_FACTORY);
        NUMERIC.put(Byte.class.getName(), BYTE_FACTORY);
        NUMERIC.put(BigDecimal.class.getName(), new BigDecimalFactory());
        NUMERIC.put(BigInteger.class.getName(), new BigIntegerFactory());
        //
        // Primitives:
        //
        NUMERIC.put(long.class.getName(), LONG_FACTORY);
        NUMERIC.put(int.class.getName(), INTEGER_FACTORY);
        NUMERIC.put(short.class.getName(), SHORT_FACTORY);
        NUMERIC.put(float.class.getName(), FLOAT_FACTORY);
        NUMERIC.put(double.class.getName(), DOUBLE_FACTORY);
        NUMERIC.put(byte.class.getName(), BYTE_FACTORY);
    }

    public static final Map DATE = new HashMap();

    static {
        DATE.put(Date.class.getName(), new DateFactory());
        DATE.put(java.sql.Date.class.getName(), new SqlDateFactory());
        DATE.put(Time.class.getName(), new SqlTimeFactory());
        DATE.put(Timestamp.class.getName(), new SqlTimestampFactory());
    }

    public static final Map BOOLEAN = new HashMap();

    public static final BooleanFactory BOOLEAN_FACTORY = new BooleanFactory();

    static {
        BOOLEAN.put(Boolean.class.getName(), BOOLEAN_FACTORY);
        //
        // Primitives:
        //
        BOOLEAN.put(boolean.class.getName(), BOOLEAN_FACTORY);
    }

    public static final Map VALUE_FACTORIES = new HashMap();
    public static final ByteArrayInputStream NULL_BYTE_ARRAY_INPUT_STREAM = new ByteArrayInputStream(new byte [0]);

    static {
        VALUE_FACTORIES.putAll(NUMERIC);
        VALUE_FACTORIES.putAll(DATE);
        VALUE_FACTORIES.putAll(BOOLEAN);
    }


    public static ValueStringResult value2string(ColumnType type, Object value) {
        ValueStringResult result = new ValueStringResult();
        if (value == null) {
            return result;
        }
        try {
            if (ColumnType.isBinary(type)) {
                if (value == ColumnType.NULL_BINARY_OBJECT) {
                    value = null;
                }
                BASE64Encoder encoder = new BASE64Encoder();
                if (value instanceof Blob) {
                    Blob blob = (Blob) value;
                    long len = blob.length();
                    validateIntLen(len);
                    result.setValueString(encoder.encode(blob.getBytes(1, (int) len)));
                } else if (value instanceof Clob) {
                    Clob clob = (Clob) value;
                    long len = clob.length();
                    validateIntLen(len);
                    result.setValueString(clob.getSubString(1, (int) len));
                } else if (value instanceof ByteArrayInputStream) {
                    ByteArrayInputStream bin = (ByteArrayInputStream) value;
                    ByteArrayOutputStream bout = new ByteArrayOutputStream(bin.available());
                    BlobImpl.writeBlob(bin, bout);
                    result.setValueString(encoder.encode(bout.toByteArray()));
                } else {
                    result = value2string(value);
                }
            } else if (ColumnType.isDate(type)) {
                Date date = (Date) value;
                result.setValueString(XmlDomHelper.D2S(date));
            } else if (ColumnType.isBoolean(type)) {
                Boolean date = (Boolean) value;
                result.setValueString(XmlDomHelper.B2S(date));
            } else if (ColumnType.isObject(type)) {
                result = value2string(value);
            } else {
                result.setValueString(String.valueOf(value));
            }
        } catch (Exception e) {
            throw new XmlRuntimeException("Cannot convert value " +
                    "of type [" + type + "] to String", e);
        }
        return result;
    }

    public static ValueStringResult value2string(Object value) throws IOException {
        ValueStringResult result = new ValueStringResult();
        String valueString = null;
        if (value instanceof String) {
            valueString = ((String) value);
        } else if (isNumericValue(value)) {
            valueString = String.valueOf(value);
        } else if (isDate(value)) {
            valueString = XmlDomHelper.D2S(((Date) value));
        } else if (isBoolean(value)) {
            valueString = XmlDomHelper.B2S(((Boolean) value));
        } else if (value != null) {
            valueString = unknownBinary2string(value);
            result.setBinary(true);
        }
        result.setValueString(valueString);
        return result;
    }

    protected static String unknownBinary2string(Object value) throws IOException {
        BASE64Encoder encoder = new BASE64Encoder();
        ByteArrayOutputStream os = new ByteArrayOutputStream();
        ObjectOutputStream out = new ObjectOutputStream(os);
        out.writeObject(value);
        out.flush();
        out.close();
        byte[] bytes = os.toByteArray();
        return encoder.encode(bytes);
    }

    protected static boolean isNumericValue(Object value) {
        if (value == null) {
            return false;
        }
        return isNumericClass(value.getClass().getName());
    }

    protected static boolean isNumericClass(String className) {
        return NUMERIC.containsKey(className);
    }

    protected static boolean isDate(Object value) {
        if (value == null) {
            return false;
        }
        return isDateClass(value);
    }

    protected static boolean isDateClass(Object className) {
        return DATE.containsKey(className);
    }

    protected static boolean isBoolean(Object value) {
        if (value == null) {
            return false;
        }
        return isBooleanClass(value.getClass().getName());
    }

    protected static boolean isBooleanClass(String className) {
        return BOOLEAN.containsKey(className);
    }

    protected static void validateIntLen(long len) {
        if (len > Integer.MAX_VALUE) {
            throw new XmlRuntimeException("len > Integer.MAX_VALUE");
        }
    }


    /**
     * Value factory
     */
    protected static interface ValueFactory {
        Object newValueInstance(String valueString);
    }

    /**
     * Numeric:
     */
    protected static class LongFactory implements ValueFactory {
        public Object newValueInstance(String valueString) {
            return Long.valueOf(valueString);
        }
    }

    protected static class IntegerFactory implements ValueFactory {
        public Object newValueInstance(String valueString) {
            return Integer.valueOf(valueString);
        }
    }

    protected static class ShortFactory implements ValueFactory {
        public Object newValueInstance(String valueString) {
            return Short.valueOf(valueString);
        }
    }

    protected static class FloatFactory implements ValueFactory {
        public Object newValueInstance(String valueString) {
            return Float.valueOf(valueString);
        }
    }

    protected static class DoubleFactory implements ValueFactory {
        public Object newValueInstance(String valueString) {
            return Double.valueOf(valueString);
        }
    }

    protected static class ByteFactory implements ValueFactory {
        public Object newValueInstance(String valueString) {
            return Byte.valueOf(valueString);
        }
    }

    protected static class BigDecimalFactory implements ValueFactory {
        public Object newValueInstance(String valueString) {
            return new BigDecimal(valueString);
        }
    }

    protected static class BigIntegerFactory implements ValueFactory {
        public Object newValueInstance(String valueString) {
            return new BigInteger(valueString);
        }
    }

    /**
     * Date
     */
    protected static class DateFactory implements ValueFactory {
        public Object newValueInstance(String valueString) {
            return XmlDomHelper.S2D(valueString);
        }
    }

    protected static class SqlDateFactory implements ValueFactory {
        public Object newValueInstance(String valueString) {
            Date date = XmlDomHelper.S2D(valueString);
            return new java.sql.Date(date.getTime());
        }
    }

    protected static class SqlTimeFactory implements ValueFactory {
        public Object newValueInstance(String valueString) {
            Date date = XmlDomHelper.S2D(valueString);
            return new java.sql.Time(date.getTime());
        }
    }

    protected static class SqlTimestampFactory implements ValueFactory {
        public Object newValueInstance(String valueString) {
            Date date = XmlDomHelper.S2D(valueString);
            return new java.sql.Timestamp(date.getTime());
        }
    }

    /**
     *  Boolean
     */
    protected static class BooleanFactory implements ValueFactory {
        public Object newValueInstance(String valueString) {
            return XmlDomHelper.S2B(valueString);
        }
    }
    
    
    //
    // Back:
    //
    public static Object string2value(boolean binary, String valueString, boolean origValue, ColumnType type, String columnName) {
        Object value = null;
        try {
            if (binary) {
                value = readUnknownBinary(valueString, origValue);
            } else if (type.isString()) {
                value = valueString;
            } else if (type.isBoolean()) {
                value = XmlDomHelper.S2B(valueString);
            } else if (type.getValueClass() == Long.class) {
                value = XmlDomHelper.S2L(valueString);
            } else if (type.isNumeric()) {
                value = XmlDomHelper.S2BigDecimal(valueString);
            } else if (type.isBinary()) {
                if (Blob.class.isAssignableFrom(type.getValueClass())) {
                    if (!origValue) {
                        BASE64Decoder decoder = new BASE64Decoder();
                        byte [] bytes = decoder.decodeBuffer(valueString);
                        value = new DetachedBlobImpl(bytes);
                    } else {
                        value = DetachedBlobImpl.NULL_BLOB;
                    }

                } else if (Clob.class.isAssignableFrom(type.getValueClass())) {
                    if (!origValue) {
                        value = new DetachedClobImpl(valueString);
                    } else {
                        value = DetachedClobImpl.NULL_CLOB;
                    }
                } else if (InputStream.class.isAssignableFrom(type.getValueClass())) {
                    if (!origValue) {
                        BASE64Decoder decoder = new BASE64Decoder();
                        byte [] bytes = decoder.decodeBuffer(valueString);
                        value = new ByteArrayInputStream(bytes);
                    } else {
                        value = NULL_BYTE_ARRAY_INPUT_STREAM;
                    }
                } else {
                    value = readUnknownBinary(valueString, origValue);
                }
            } else if (type.isDate()) {
                value = XmlDomHelper.S2D(valueString);
            } else if (type.isBoolean()) {
                value = XmlDomHelper.S2B(valueString);
            } else if (type.isObject()) {
                value = readUnknownBinary(valueString, origValue);
            } else {
                System.err.println("ERROR: XmlPersistentObjectInputStream::strings2values: Cannot handle type " + type);
            }
        } catch (Exception e) {
            throw new XmlRuntimeException("Cannot convert string of type [" + type +
                    "], column [" + columnName + "] to value", e);
        }
        return value;
    }
    
    public static Object string2value(String className, String valueString, boolean binary) throws IOException, ClassNotFoundException {
        Object value = null;
        if (valueString != null) {
            if (binary) {
                value = string2unknownBinary(valueString);
            } else if (String.class.getName().equals(className)) {
                value = valueString;
            } else if (isNumericClass(className)
                    || isDateClass(className)
                    || isBooleanClass(className)) {
                value = string2value0(className, valueString);
            } else {
                value = string2unknownBinary(valueString);
            }
        }
        return value;
    }
    
    protected static Object string2value0(String className, String valueString) {
        if (valueString == null) {
            return null;
        }

        ValueFactory valueFactory = (ValueFactory) VALUE_FACTORIES.get(className);
        if (valueFactory == null) {
            throw new XmlRuntimeException("Cannot find valueFactory for className " + className);
        }
        return valueFactory.newValueInstance(valueString);
    }
    
    protected static Object readUnknownBinary(String valueString, boolean origValue) throws IOException, ClassNotFoundException {
        Object value;
        if (!origValue) {
            value = string2unknownBinary(valueString);
        } else {
            value = ColumnType.NULL_BINARY_OBJECT;
        }

        return value;
    }
    
    protected static Object string2unknownBinary(String valueString) throws IOException, ClassNotFoundException {
        BASE64Decoder decoder = new BASE64Decoder();
        byte [] bytes = decoder.decodeBuffer(valueString);
        ByteArrayInputStream bin = new ByteArrayInputStream(bytes);
        ObjectInputStream in = new ObjectInputStream(bin);
        return in.readObject();
    }

}
java2s.com  | Contact Us | Privacy Policy
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.