Clover coverage report -
Coverage timestamp: Sun Nov 1 2009 23:08:24 UTC
file stats: LOC: 166   Methods: 5
NCLOC: 56   Classes: 2
 
 Source file Conditionals Statements Methods TOTAL
InlineMetaService.java 37.5% 69.6% 100% 66.7%
coverage coverage
 1    /*
 2    * Licensed to the Apache Software Foundation (ASF) under one or more
 3    * contributor license agreements. See the NOTICE file distributed with
 4    * this work for additional information regarding copyright ownership.
 5    * The ASF licenses this file to You under the Apache License, Version 2.0
 6    * (the "License"); you may not use this file except in compliance with
 7    * the License. You may obtain a copy of the License at
 8    *
 9    * http://www.apache.org/licenses/LICENSE-2.0
 10    *
 11    * Unless required by applicable law or agreed to in writing, software
 12    * distributed under the License is distributed on an "AS IS" BASIS,
 13    * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 14    * See the License for the specific language governing permissions and
 15    * limitations under the License.
 16    *
 17    * $Id: InlineMetaService.java 571950 2007-09-02 10:53:17Z vgritsenko $
 18    */
 19   
 20    package org.apache.xindice.core.meta.inline;
 21   
 22    import org.apache.commons.logging.Log;
 23    import org.apache.commons.logging.LogFactory;
 24    import org.apache.xindice.core.FaultCodes;
 25    import org.apache.xindice.core.data.Value;
 26   
 27    /**
 28    * If the documents in a collection have headers, the Collection
 29    * object holds an instance of this class. All services the collection
 30    * needs for working with inline metadata are provided by this class.
 31    *
 32    * @version $Revision: 571950 $, $Date: 2007-09-02 03:53:17 -0700 (Sun, 02 Sep 2007) $
 33    */
 34    public class InlineMetaService {
 35   
 36    private static final Log log = LogFactory.getLog(InlineMetaService.class);
 37   
 38    /**
 39    * The known readers. All readers for header versions up to
 40    * and including the current version must be present in this array.
 41    */
 42    public static final InlineMetaReader[] readerByVersion = {new NullReader(), new ResourceTypeReader()};
 43   
 44    /**
 45    * The writer corresponding to the current header version.
 46    */
 47    public static final InlineMetaWriter currentWriter = new ResourceTypeWriter();
 48   
 49    /**
 50    * The InlineMetaMap class associated with the current header
 51    * version. When the Collection fills in an InlineMetaMap object
 52    * prior to a store, it is working with this class.
 53    */
 54    public static final Class currentMapClass = ResourceTypeReader.ResourceTypeMap.class;
 55   
 56    /**
 57    * Get an <code>InlineMetaMap</code> instance corresponding to the
 58    * current header version. Used by <code>Collection</code> to inform
 59    * the InlineMeta code of the metadata values for the entry being stored.
 60    *
 61    * @return InlineMetaMap instance
 62    */
 63  1983 public InlineMetaMap getEmptyMap() {
 64  1983 try {
 65  1983 return (InlineMetaMap) currentMapClass.newInstance();
 66    } catch (Exception e) {
 67  0 String msg = "unable to create instance of current inline metadata map class '" + currentMapClass.getName() + "'";
 68    /*
 69    * This can only happen as a result of a programming error,
 70    * so log it and throw a runtime. Shouldn't happen in production.
 71    */
 72  0 if (log.isFatalEnabled()) {
 73  0 log.fatal(msg, e);
 74    }
 75  0 throw new IllegalStateException(msg);
 76    }
 77    }
 78   
 79    /**
 80    * Create a Value object containing the appropriate header and
 81    * data. This utility method takes the metadata and the data
 82    * for the entry to be stored in the database and creates a
 83    * <code>Value</code> object containing both, ready to store.
 84    *
 85    * @param map containing metadata
 86    * @param data containing entry to be stored in database
 87    * @param offset in the data to the beginning of the entry
 88    * @param length of the entry
 89    * @return Value object containing the header + entry, ready to store
 90    * @throws InlineMetaException if the metadata is incomplete
 91    */
 92  1983 public Value createValue(InlineMetaMap map, byte[] data, int offset, int length) throws InlineMetaException {
 93   
 94  1983 byte[] metadata = currentWriter.getMetadata(map);
 95   
 96  1983 return InlineHeaderBuilder.createValue(currentWriter.getVersion(), metadata, data, offset, length);
 97    }
 98   
 99    /**
 100    * Returns true if a reader is available for the specified
 101    * version.
 102    *
 103    * @param version of the header
 104    * @return true if a reader is available for the given version
 105    */
 106  34452 public boolean haveReaderForVersion(int version) {
 107  34452 return version < readerByVersion.length;
 108    }
 109   
 110    /**
 111    * Given a <code>Value</code> object from the database,
 112    * disassemble it into its component metadata and entry data
 113    * components.
 114    *
 115    * @param rawValue containing raw header + entry data from the backing store
 116    * @return DatabaseEntry containing metadata in an <code>InlineMetaMap</code>
 117    * and entry data in a <code>Value</code>.
 118    * @throws InlineMetaException if missing the reader for the header, or if
 119    * the header is corrupted.
 120    */
 121  34452 public DatabaseEntry readDatabaseEntry(Value rawValue) throws InlineMetaException {
 122  34452 if (log.isDebugEnabled()) {
 123  0 log.debug("readDatabaseEntry: rawData: length=" + rawValue.getLength() +
 124    " byte 0: " + rawValue.byteAt(0) + " byte 1: " + rawValue.byteAt(1));
 125    }
 126   
 127    /*
 128    * Read the header.
 129    */
 130   
 131  34452 int headerLen = rawValue.byteAt(0);
 132  34452 int version = rawValue.byteAt(1);
 133  34452 if (!haveReaderForVersion(version)) {
 134  0 throw new InlineMetaException(FaultCodes.GEN_CRITICAL_ERROR,
 135    "No inline metadata reader available for version " + version);
 136    }
 137   
 138  34452 final InlineMetaReader reader = readerByVersion[version];
 139  34452 InlineMetaMap map = reader.read(rawValue.valueAt(2, headerLen - 2));
 140  34452 if (log.isDebugEnabled()) {
 141  0 log.debug("readDatabaseEntry: map: type=" + map.get("type"));
 142    }
 143   
 144    /*
 145    * Exract the data into a Value object.
 146    */
 147   
 148  34452 Value value = rawValue.valueAt(headerLen, rawValue.getLength() - headerLen);
 149    // FIXME: May be Record should be used instead? new Record(null, value, map);
 150  34452 return new DatabaseEntry(map, value);
 151    }
 152   
 153    /**
 154    * Utility class for returning an InlineMetaMap and Value
 155    * from <code>readDatabaseEntry(Value)</code>.
 156    */
 157    public static class DatabaseEntry {
 158    public final InlineMetaMap map;
 159    public final Value value;
 160   
 161  34452 public DatabaseEntry(InlineMetaMap map, Value value) {
 162  34452 this.map = map;
 163  34452 this.value = value;
 164    }
 165    }
 166    }