All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.redkale.convert.bson.BsonWriter Maven / Gradle / Ivy

/*
 * To change this license header, choose License Headers in Project Properties.
 * To change this template file, choose Tools | Templates
 * and open the template in the editor.
 */
package org.redkale.convert.bson;

import java.nio.ByteBuffer;
import org.redkale.convert.*;
import org.redkale.util.*;

/**
 *
 * 

* 详情见: https://redkale.org * * @author zhangjx */ public class BsonWriter extends Writer { private static final int defaultSize = Integer.getInteger("convert.bson.writer.buffer.defsize", 1024); private byte[] content; protected int count; protected boolean tiny; public static ObjectPool createPool(int max) { return new ObjectPool<>(max, (Object... params) -> new BsonWriter(), null, (t) -> t.recycle()); } public byte[] toArray() { if (count == content.length) return content; byte[] newdata = new byte[count]; System.arraycopy(content, 0, newdata, 0, count); return newdata; } public ByteBuffer[] toBuffers() { return new ByteBuffer[]{ByteBuffer.wrap(content, 0, count)}; } protected BsonWriter(byte[] bs) { this.content = bs; } public BsonWriter() { this(defaultSize); } public BsonWriter(int size) { this.content = new byte[size > 128 ? size : 128]; } @Override public final boolean tiny() { return tiny; } public BsonWriter tiny(boolean tiny) { this.tiny = tiny; return this; } //----------------------------------------------------------------------- //----------------------------------------------------------------------- /** * 扩充指定长度的缓冲区 * * @param len 扩容长度 * * @return 固定0 */ protected int expand(int len) { int newcount = count + len; if (newcount <= content.length) return 0; byte[] newdata = new byte[Math.max(content.length * 3 / 2, newcount)]; System.arraycopy(content, 0, newdata, 0, count); this.content = newdata; return 0; } public void writeTo(final byte ch) { expand(1); content[count++] = ch; } public final void writeTo(final byte... chs) { writeTo(chs, 0, chs.length); } public void writeTo(final byte[] chs, final int start, final int len) { expand(len); System.arraycopy(chs, start, content, count, len); count += len; } protected boolean recycle() { this.count = 0; this.specify = null; if (this.content.length > defaultSize) { this.content = new byte[defaultSize]; } return true; } @Override public String toString() { return this.getClass().getSimpleName() + "[count=" + this.count + "]"; } //------------------------------------------------------------------------ public final int count() { return this.count; } @Override public final void writeBoolean(boolean value) { writeTo(value ? (byte) 1 : (byte) 0); } @Override public final void writeByte(byte value) { writeTo(value); } @Override public final void writeByteArray(byte[] values) { if (values == null) { writeNull(); return; } writeArrayB(values.length, null, values); boolean flag = false; for (byte v : values) { if (flag) writeArrayMark(); writeByte(v); flag = true; } writeArrayE(); } @Override public final void writeChar(final char value) { writeTo((byte) ((value & 0xFF00) >> 8), (byte) (value & 0xFF)); } @Override public final void writeShort(short value) { writeTo((byte) (value >> 8), (byte) value); } @Override public final void writeInt(int value) { writeTo((byte) (value >> 24), (byte) (value >> 16), (byte) (value >> 8), (byte) value); } @Override public final void writeLong(long value) { writeTo((byte) (value >> 56), (byte) (value >> 48), (byte) (value >> 40), (byte) (value >> 32), (byte) (value >> 24), (byte) (value >> 16), (byte) (value >> 8), (byte) value); } @Override public final void writeFloat(float value) { writeInt(Float.floatToIntBits(value)); } @Override public final void writeDouble(double value) { writeLong(Double.doubleToLongBits(value)); } @Override public final boolean needWriteClassName() { return true; } @Override public final void writeClassName(String clazz) { writeSmallString(clazz == null ? "" : clazz); } @Override public final int writeObjectB(Object obj) { super.writeObjectB(obj); writeSmallString(""); writeShort(BsonReader.SIGN_OBJECTB); return -1; } @Override public final void writeObjectE(Object obj) { writeByte(BsonReader.SIGN_NONEXT); writeShort(BsonReader.SIGN_OBJECTE); } @Override public final void writeFieldName(EnMember member) { Attribute attribute = member.getAttribute(); writeByte(BsonReader.SIGN_HASNEXT); writeSmallString(attribute.field()); byte typeval = 127; //字段的类型值 final Class type = attribute.type(); if (type == boolean.class || type == Boolean.class) { typeval = 1; } else if (type == byte.class || type == Byte.class) { typeval = 2; } else if (type == short.class || type == Short.class) { typeval = 3; } else if (type == char.class || type == Character.class) { typeval = 4; } else if (type == int.class || type == Integer.class) { typeval = 5; } else if (type == long.class || type == Long.class) { typeval = 6; } else if (type == float.class || type == Float.class) { typeval = 7; } else if (type == double.class || type == Double.class) { typeval = 8; } else if (type == String.class) { typeval = 9; } else if (type == boolean[].class || type == Boolean[].class) { typeval = 101; } else if (type == byte[].class || type == Byte[].class) { typeval = 102; } else if (type == short[].class || type == Short[].class) { typeval = 103; } else if (type == char[].class || type == Character[].class) { typeval = 104; } else if (type == int[].class || type == Integer[].class) { typeval = 105; } else if (type == long[].class || type == Long[].class) { typeval = 106; } else if (type == float[].class || type == Float[].class) { typeval = 107; } else if (type == double[].class || type == Double[].class) { typeval = 108; } else if (type == String[].class) { typeval = 109; } writeByte(typeval); } /** * 对于类的字段名、枚举值这些长度一般不超过255且不会出现双字节字符的字符串采用writeSmallString处理, readSmallString用于读取 * * @param value String值 */ @Override public final void writeSmallString(String value) { if (value.isEmpty()) { writeTo((byte) 0); return; } char[] chars = Utility.charArray(value); if (chars.length > 255) throw new ConvertException("'" + value + "' have very long length"); byte[] bytes = new byte[chars.length + 1]; bytes[0] = (byte) chars.length; for (int i = 0; i < chars.length; i++) { if (chars[i] > Byte.MAX_VALUE) throw new ConvertException("'" + value + "' have double-word"); bytes[i + 1] = (byte) chars[i]; } writeTo(bytes); } @Override public final void writeString(String value) { if (value == null) { writeInt(Reader.SIGN_NULL); return; } else if (value.isEmpty()) { writeInt(0); return; } byte[] bytes = Utility.encodeUTF8(value); writeInt(bytes.length); writeTo(bytes); } @Override public final void writeNull() { writeShort(Reader.SIGN_NULL); } @Override public final int writeArrayB(int size, Encodeable encoder, Object obj) { writeInt(size); return -1; } @Override public final void writeArrayMark() { } @Override public final void writeArrayE() { } @Override public int writeMapB(int size, Encodeable keyEncoder, Encodeable valueEncoder, Object obj) { writeArrayB(size, valueEncoder, obj); return -1; } @Override public final void writeMapMark() { } @Override public final void writeMapE() { } }





© 2015 - 2024 Weber Informatics LLC | Privacy Policy