com.ibm.common.activitystreams.legacy.Binary.java Source code

Java tutorial

Introduction

Here is the source code for com.ibm.common.activitystreams.legacy.Binary.java

Source

/**
 * Copyright 2013 OpenSocial Foundation
 * Copyright 2013 International Business Machines Corporation
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 *
 * Utility library for working with Activity Streams Actions
 * Requires underscorejs.
 *
 * @author James M Snell (jasnell@us.ibm.com)
 */
package com.ibm.common.activitystreams.legacy;

import java.io.IOException;
import java.io.InputStream;
import java.io.ObjectStreamException;
import java.io.OutputStream;
import java.io.StringReader;
import java.io.StringWriter;

import com.google.common.hash.Hashing;
import com.google.common.hash.HashingInputStream;
import com.google.common.hash.HashingOutputStream;
import com.google.common.io.BaseEncoding;
import com.google.common.net.MediaType;
import com.ibm.common.activitystreams.ASObject;

/**
 * The legacy "binary" objectType.
 * 
 * <pre>
 *   InputStream in = ...
 *   // will base64 encode, gzip compress and md5 sum the input data
 *   // will also set the length property accordingly
 *   Binary binary = 
 *     LegacyMakers.binary()
 *       .gzipData(in)
 *       .get();
 * </pre>
 * 
 * @author james
 *
 */
public final class Binary extends ASObject {

    public static final class Builder extends ASObject.AbstractBuilder<Binary, Builder> {

        Builder() {
            objectType("binary");
        }

        /**
         * Set the input data without any compression. Will automatically
         * set calculate the md5 sum and length properties
         * @param in InputStream
         * @return Builder
         * @throws IOException
         */
        public Builder data(InputStream in) throws IOException {
            return data(in, null);
        }

        /**
         * Set the input data with GZip compression. Will automatically
         * set calculate the md5 sum and length properties
         * @param in InputStream
         * @return Builder
         * @throws IOException
         */
        public Builder gzipData(InputStream in) throws IOException {
            return data(in, Compression.GZipCompression);
        }

        /**
         * Set the input data with Deflate compression. Will automatically
         * set calculate the md5 sum and length properties
         * @param in InputStream
         * @return Builder
         * @throws IOException
         */
        public Builder deflateData(InputStream in) throws IOException {
            return data(in, Compression.DeflateCompression);
        }

        /**
         * Set the input data the given Compression. Will automatically
         * set calculate the md5 sum and length properties
         * @param in InputStream
         * @return Builder
         * @throws IOException
         */
        public Builder data(InputStream in, Compression<?, ?> compression) throws IOException {
            StringWriter writer = new StringWriter();
            OutputStream out = BaseEncoding.base64Url().encodingStream(writer);
            if (compression != null)
                out = compression.compressor(out);
            HashingOutputStream hout = new HashingOutputStream(Hashing.md5(), out);
            byte[] buf = new byte[1024];
            int r = -1;
            long size = 0;
            while ((r = in.read(buf)) > -1) {
                hout.write(buf, 0, r);
                size += r;
            }
            set("length", size);
            if (compression != null) {
                set("compression", compression.label());
                compression.finish(out);
            }
            hout.close();
            set("md5", hout.hash().toString());
            return set("data", writer.toString());
        }

        /**
         * Manually set the md5 properties (this is not recommended. calling the data
         * methods will automatically generate the md5 checksum for you)
         * 
         * @param md5 String
         * @return Builder
         */
        public Builder md5(String md5) {
            return set("md5", md5);
        }

        /**
         * Set the fileUrl property
         * @param fileUrl String 
         * @return Builder
         */
        public Builder fileUrl(String fileUrl) {
            return set("fileUrl", fileUrl);
        }

        /**
         * Set the MIME Media Type using the Legacy "mimeType" property name
         * rather than the AS 2.0 "mediaType" property name
         * @param mt MediaType
         * @return Builder
         */
        @Override
        public Builder mediaType(MediaType mt) {
            return set("mimeType", mt);
        }

        /**
         * Get the built Binary object
         */
        public Binary get() {
            return new Binary(this);
        }

    }

    private Binary(Builder builder) {
        super(builder);
    }

    /**
     * Get the fileUrl property
     * @return String
     */
    public String fileUrl() {
        return getString("fileUrl");
    }

    /**
     * Get the length property
     * @return long
     */
    public long length() {
        return getLong("length");
    }

    /**
     * Get the compression property value (typically "gzip" or "deflate")
     * @return String
     */
    public String compression() {
        return getString("compression");
    }

    /**
     * True if compression = gzip
     * @return boolean
     */
    public boolean isGzip() {
        return "gzip".equalsIgnoreCase(compression());
    }

    /**
     * True if compression = deflate
     * @return boolean
     */
    public boolean isDeflate() {
        return "deflate".equalsIgnoreCase(compression());
    }

    /**
     * Return the md5 checksum
     * @return String
     */
    public String md5() {
        return getString("md5");
    }

    /**
     * Return the literal string content of the data property.
     * This will be base64 encoded and optionally compressed
     * @return String
     */
    public String data() {
        return getString("data");
    }

    /**
     * Return an InputStream for reading the data. Will
     * decompress and base64 decode as necessary
     * @return InputStream
     * @throws IOException
     */
    public InputStream read() throws IOException {
        Compression<?, ?> compression = isGzip() ? Compression.GZipCompression
                : isDeflate() ? Compression.DeflateCompression : null;
        return read(compression);
    }

    /**
     * Return an InputStream for reading the data
     * @param compression Compression
     * @return InputStream
     * @throws IOException
     */
    public InputStream read(Compression<?, ?> compression) throws IOException {
        StringReader reader = new StringReader(data());
        InputStream in = BaseEncoding.base64Url().decodingStream(reader);
        if (compression != null)
            in = compression.decompressor(in);
        if (has("md5"))
            in = new HashingInputStream(Hashing.md5(), in);
        return in;
    }

    /**
     * Return the MIME MediaType using the legacy "mimeType" property name
     * rather than the AS 2.0 "mediaType" name
     */
    @Override
    public MediaType mediaType() {
        return this.<MediaType>get("mimeType");
    }

    // Java Serialization Support

    Object writeReplace() throws java.io.ObjectStreamException {
        return new SerializedForm(this);
    }

    private static class SerializedForm extends AbstractSerializedForm<Binary> {
        private static final long serialVersionUID = -2060301713159936285L;

        protected SerializedForm(Binary obj) {
            super(obj);
        }

        Object readResolve() throws ObjectStreamException {
            return super.doReadResolve();
        }

        protected Binary.Builder builder() {
            return new Builder();
        }
    }
}