org.dishevelled.bio.alignment.sam.SamHeaderParser.java Source code

Java tutorial

Introduction

Here is the source code for org.dishevelled.bio.alignment.sam.SamHeaderParser.java

Source

/*
    
dsh-bio-alignment  Aligments.
Copyright (c) 2013-2019 held jointly by the individual authors.
    
This library is free software; you can redistribute it and/or modify it
under the terms of the GNU Lesser General Public License as published
by the Free Software Foundation; either version 3 of the License, or (at
your option) any later version.
    
This library is distributed in the hope that it will be useful, but WITHOUT
ANY WARRANTY; with out even the implied warranty of MERCHANTABILITY or
FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Lesser General Public
License for more details.
    
You should have received a copy of the GNU Lesser General Public License
along with this library;  if not, write to the Free Software Foundation,
Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307  USA.
    
> http://www.fsf.org/licensing/licenses/lgpl.html
> http://www.opensource.org/licenses/lgpl-license.php
    
*/
package org.dishevelled.bio.alignment.sam;

import static com.google.common.base.Preconditions.checkNotNull;

import java.io.IOException;

import java.util.Map;

import javax.annotation.concurrent.Immutable;

import com.google.common.collect.ImmutableMap;

/**
 * SAM header parser.
 *
 * @since 1.1
 * @author  Michael Heuer
 */
@Immutable
public final class SamHeaderParser {

    /**
     * Private no-arg constructor.
     */
    private SamHeaderParser() {
        // empty
    }

    /**
     * Read the SAM header from the specified readable.
     *
     * @param readable readable to read from, must not be null
     * @return the SAM header read from the specified readable
     * @throws IOException if an I/O error occurs
     */
    public static SamHeader header(final Readable readable) throws IOException {
        checkNotNull(readable);
        ParseListener parseListener = new ParseListener();
        SamParser.parse(readable, parseListener);
        return parseListener.getHeader();
    }

    /**
     * Parse SAM header fields.
     *
     * @param values value to parse, must not be null
     * @return map of SAM header fields
     */
    static Map<String, String> parseFields(final String value) {
        checkNotNull(value);
        ImmutableMap.Builder<String, String> fields = ImmutableMap.builder();
        String[] tokens = value.split("\t");
        for (String token : tokens) {
            if (token.length() < 4) {
                throw new IllegalArgumentException(
                        "invalid field " + token + ", must have at least four characters, e.g. AH:*");
            }
            String k = token.substring(0, 2);
            String v = token.substring(3);
            fields.put(k, v);
        }
        return fields.build();
    }

    /**
     * Parse listener.
     */
    static final class ParseListener extends SamParseAdapter {
        /** Line number. */
        private long lineNumber = 0L;

        /** SAM header builder. */
        private final SamHeader.Builder builder = SamHeader.builder();

        @Override
        public void lineNumber(final long lineNumber) {
            this.lineNumber = lineNumber;
        }

        @Override
        public void headerLine(final String headerLine) throws IOException {
            try {
                if (headerLine.startsWith("@HD")) {
                    builder.withHeaderLine(SamHeaderLine.valueOf(headerLine));
                } else if (headerLine.startsWith("@SQ")) {
                    builder.withSequenceHeaderLine(SamSequenceHeaderLine.valueOf(headerLine));
                } else if (headerLine.startsWith("@RG")) {
                    builder.withReadGroupHeaderLine(SamReadGroupHeaderLine.valueOf(headerLine));
                } else if (headerLine.startsWith("@PG")) {
                    builder.withProgramHeaderLine(SamProgramHeaderLine.valueOf(headerLine));
                } else if (headerLine.startsWith("@CO")) {
                    builder.withCommentHeaderLine(SamCommentHeaderLine.valueOf(headerLine));
                } else {
                    String tag = headerLine.substring(0, Math.min(3, headerLine.length()));
                    throw new IOException(
                            "found invalid SAM header line tag " + tag + " at line number " + lineNumber);
                }
            } catch (IllegalArgumentException e) {
                throw new IOException("could not parse SAM header line at line number " + lineNumber + ", caught "
                        + e.getMessage(), e);
            }
        }

        @Override
        public boolean complete() {
            return false;
        }

        /**
         * Return the SAM header.
         *
         * @return the SAM header
         * @throws IOException if an I/O error occurs
         */
        SamHeader getHeader() throws IOException {
            try {
                return builder.build();
            } catch (IllegalArgumentException e) {
                throw new IOException("could not parse SAM header, caught " + e.getMessage(), e);
            }
        }
    }
}