001    package com.imagero.uio.blob;
002    
003    import com.imagero.uio.blob.Blob;
004    
005    import java.io.ByteArrayInputStream;
006    import java.io.IOException;
007    
008    /**
009     * BlobInputStream.
010     * Read data from Blob.
011     *
012     * Data from Blob first filled into internal buffer and then read.
013     *
014     * Date: 23.07.2007
015     *
016     * @author Andrey Kuznetsov
017     */
018    public class BlobInputStream extends ByteArrayInputStream {
019        Blob blob;
020    
021        long start;
022        long length;
023    
024        boolean finished;
025    
026        public BlobInputStream(Blob blob) throws IOException {
027            super(new byte[2048]);
028            this.blob = blob;
029            fillBuffer();
030        }
031    
032        public int read() {
033            if (finished) {
034                return -1;
035            }
036            if (available() > 0) {
037                return super.read();
038            }
039            return -1;
040        }
041    
042        public synchronized long skip(long n) {
043            int k = available();
044            if(k < n) {
045                fillBuffer();
046            }
047            return super.skip(n);
048        }
049    
050        public synchronized int available() {
051            int k = super.available();
052            if (k > 0) {
053                return k;
054            } else {
055                fillBuffer();
056                return super.available();
057            }
058        }
059    
060        public synchronized int read(byte b[], int off, int len) {
061            if (finished) {
062                return -1;
063            }
064            int k = available();
065            return super.read(b, off, Math.min(k, len));
066        }
067    
068        private void fillBuffer() {
069            try {
070                length = blob.get(start, buf);
071            } catch (IOException ex) {
072                finished = true;
073                ex.printStackTrace();
074            }
075            if (length <= 0) {
076                finished = true;
077                return;
078            }
079            start += length;
080            pos = 0;
081        }
082    }