//
// JmsaBytesMessage.java - JMS Adapter BytesMessage
//
// Notice that you can either do raw bytes level stuff,
// or there are handy getters/setters that serialise/deserialise for you.
// Not sure why this isn't handled by some common library, rather than
// forcing every JMS implementation to do the same implementation.
//

package nyangau.jmsadapter;

import java.io.*;
import javax.jms.*;

public class JmsaBytesMessage extends JmsaMessage implements BytesMessage
  {
  // when bro
  protected byte[]               b;
  protected ByteArrayInputStream bais;
  protected DataInputStream      dis;

  // when !bro
  protected ByteArrayOutputStream baos;
  protected DataOutputStream      dos;

//...sBoolean:2:
public boolean readBoolean()
  throws JMSException
  {
  checkRead();
  try
    {
    return dis.readBoolean();
    }
  catch ( IOException e )
    {
    throw new MessageEOFException("");
    }
  }

public void writeBoolean(boolean value)
  throws JMSException
  {
  checkWrite();
  try
    {
    dos.writeBoolean(value);
    }
  catch ( IOException e )
    {
    }
  }
//...e
//...sCharacter:2:
public char readChar()
  throws JMSException
  {
  checkRead();
  try
    {
    return dis.readChar();
    }
  catch ( IOException e )
    {
    throw new MessageEOFException("");
    }
  }

public void writeChar(char value)
  throws JMSException
  {
  checkWrite();
  try
    {
    dos.writeChar(value);
    }
  catch ( IOException e )
    {
    }
  }
//...e
//...sByte:2:
public byte readByte()
  throws JMSException
  {
  checkRead();
  try
    {
    return dis.readByte();
    }
  catch ( IOException e )
    {
    throw new MessageEOFException("");
    }
  }

public int readUnsignedByte()
  throws JMSException
  {
  checkRead();
  try
    {
    return dis.readUnsignedByte();
    }
  catch ( IOException e )
    {
    throw new MessageEOFException("");
    }
  }

public void writeByte(byte value)
  throws JMSException
  {
  checkWrite();
  try
    {
    dos.writeByte(value);
    }
  catch ( IOException e )
    {
    }
  }
//...e
//...sShort:2:
public short readShort()
  throws JMSException
  {
  checkRead();
  try
    {
    return dis.readShort();
    }
  catch ( IOException e )
    {
    throw new MessageEOFException("");
    }
  }

public int readUnsignedShort()
  throws JMSException
  {
  checkRead();
  try
    {
    return dis.readUnsignedShort();
    }
  catch ( IOException e )
    {
    throw new MessageEOFException("");
    }
  }

public void writeShort(short value)
  throws JMSException
  {
  checkWrite();
  try
    {
    dos.writeShort(value);
    }
  catch ( IOException e )
    {
    }
  }
//...e
//...sInt:2:
public int readInt()
  throws JMSException
  {
  checkRead();
  try
    {
    return dis.readInt();
    }
  catch ( IOException e )
    {
    throw new MessageEOFException("");
    }
  }

public void writeInt(int value)
  throws JMSException
  {
  checkWrite();
  try
    {
    dos.writeInt(value);
    }
  catch ( IOException e )
    {
    }
  }
//...e
//...sLong:2:
public long readLong()
  throws JMSException
  {
  checkRead();
  try
    {
    return dis.readLong();
    }
  catch ( IOException e )
    {
    throw new MessageEOFException("");
    }
  }

public void writeLong(long value)
  throws JMSException
  {
  checkWrite();
  try
    {
    dos.writeLong(value);
    }
  catch ( IOException e )
    {
    }
  }
//...e
//...sFloat:2:
public float readFloat()
  throws JMSException
  {
  checkRead();
  try
    {
    return dis.readFloat();
    }
  catch ( IOException e )
    {
    throw new MessageEOFException("");
    }
  }

public void writeFloat(float value)
  throws JMSException
  {
  checkWrite();
  try
    {
    dos.writeFloat(value);
    }
  catch ( IOException e )
    {
    }
  }
//...e
//...sDouble:2:
public double readDouble()
  throws JMSException
  {
  checkRead();
  try
    {
    return dis.readDouble();
    }
  catch ( IOException e )
    {
    throw new MessageEOFException("");
    }
  }

public void writeDouble(double value)
  throws JMSException
  {
  checkWrite();
  try
    {
    dos.writeDouble(value);
    }
  catch ( IOException e )
    {
    }
  }
//...e
//...sUTF:2:
public String readUTF()
  throws JMSException
  {
  checkRead();
  try
    {
    return dis.readUTF();
    }
  catch ( IOException e )
    {
    throw new MessageEOFException("");
    }
  }

public void writeUTF(String value)
  throws JMSException
  {
  checkWrite();
  try
    {
    dos.writeUTF(value);
    }
  catch ( IOException e )
    {
    }
  }
//...e
//...sBytes:2:
public int readBytes(byte[] value)
  throws JMSException
  { return readBytes(value, value.length); }

public int readBytes(byte[] value, int length)
  throws JMSException
  {
  checkRead();
  try
    {
    return dis.read(value, 0, length);
    }
  catch ( IOException e )
    {
    throw new MessageEOFException("");
    }
  }

public void writeBytes(byte[] value)
  throws JMSException
  { writeBytes(value, 0, value.length); }

public void writeBytes(byte[] value, int offset, int length)
  throws JMSException
  {
  checkWrite();
  try
    {
    dos.write(value, offset, length);
    }
  catch ( IOException e )
    {
    }
  }
//...e
//...sObject:2:
// There is no readObject, which is to be expected, given unlike a
// StreamMessage there is no way to know which object to decode

public void writeObject(Object value)
  throws JMSException
  {
  checkWrite();
  if ( value == null )
    throw new MessageFormatException("object cannot be null");
  else if ( value instanceof byte[] )
    writeBytes((byte[])value);
  else if ( value instanceof Boolean )
    writeBoolean(((Boolean)value).booleanValue());
  else if ( value instanceof Byte )
    writeByte(((Byte)value).byteValue());
  else if ( value instanceof Character )
    writeChar(((Character)value).charValue());
  else if ( value instanceof Short )
    writeShort(((Short)value).shortValue());
  else if ( value instanceof Integer )
    writeInt(((Integer)value).intValue());
  else if ( value instanceof Long )
    writeLong(((Long)value).longValue());
  else if ( value instanceof Float )
    writeFloat(((Float)value).floatValue());
  else if ( value instanceof Double )
    writeDouble(((Double)value).doubleValue());
  else if ( value instanceof String )
    writeUTF((String)value);
  else
    throw new MessageFormatException("value is of invalid class: " + value.getClass().getName());
  }
//...e

//...sreset:2:
public void reset()
  {
  if ( !bro )
    {
    try
      {
      dos.flush(); // ensure all everything is in baos below
      }
    catch ( IOException e )
      {
      }
    b    = baos.toByteArray();
    baos = null;
    dos  = null;
    bro  = true;
    }
  // else
    // we are re-reading the same data, already in b
  bais = new ByteArrayInputStream(b);
  dis  = new DataInputStream(bais);
  }
//...e
//...sgetBodyLength:2:
public long getBodyLength()
  throws JMSException
  {
  checkRead();
  return b.length;
  }
//...e
//...sclearBody:2:
public void clearBody()
  throws JMSException
  {
  b    = null;
  bais = null;
  dis  = null;
  baos = new ByteArrayOutputStream();
  dos  = new DataOutputStream(baos);
  bro  = false;
  }
//...e

//...sprotect:2:
// Before passing a newly received JmsaMessage to the caller,
// ensure it is not modifiable, as per JMS spec.

public void protect()
  {
  pro = true;
  reset();
  }
//...e

//...sJmsaBytesMessage:2:
// Called by JmsaSession
public JmsaBytesMessage()
  {
  super();
  b    = null;
  bais = null;
  dis  = null;
  baos = new ByteArrayOutputStream();
  dos  = new DataOutputStream(baos);
  }

// For newly received messages, or foreign outbound messages
public JmsaBytesMessage(BytesMessage m)
  throws JMSException // super(m), m.reset() and m.getBodyLength() can cause this
  {
  super(m);

  b = new byte[(int) m.getBodyLength()];
  m.readBytes(b);
  bais = new ByteArrayInputStream(b);
  dis  = new DataInputStream(bais);
  baos = null;
  dos  = null;
  bro  = true;
  }

// For converting between message formats
public JmsaBytesMessage(JmsaMessage m)
  {
  super(m);
  b    = null;
  bais = null;
  dis  = null;
  baos = new ByteArrayOutputStream();
  dos  = new DataOutputStream(baos);
  }
//...e
  }
