blob: fb55c55a87c3d63df7d86c060eb53a663e7f744f [file] [log] [blame]
/*
* Copyright 2009-2010 by The Regents of the University of California
* 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 from
*
* 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.
*/
package edu.uci.ics.asterix.metadata.bootstrap;
import java.io.File;
import java.util.ArrayList;
import java.util.List;
import edu.uci.ics.asterix.common.exceptions.AsterixRuntimeException;
import edu.uci.ics.asterix.formats.nontagged.AqlBinaryComparatorFactoryProvider;
import edu.uci.ics.asterix.formats.nontagged.AqlBinaryHashFunctionFactoryProvider;
import edu.uci.ics.asterix.formats.nontagged.AqlSerializerDeserializerProvider;
import edu.uci.ics.asterix.formats.nontagged.AqlTypeTraitProvider;
import edu.uci.ics.asterix.metadata.api.IMetadataIndex;
import edu.uci.ics.asterix.om.types.ARecordType;
import edu.uci.ics.asterix.om.types.IAType;
import edu.uci.ics.asterix.runtime.transaction.TreeLogger;
import edu.uci.ics.asterix.transaction.management.exception.ACIDException;
import edu.uci.ics.asterix.transaction.management.service.logging.DataUtil;
import edu.uci.ics.hyracks.algebricks.core.algebra.operators.logical.OrderOperator.IOrder.OrderKind;
import edu.uci.ics.hyracks.api.dataflow.value.IBinaryComparatorFactory;
import edu.uci.ics.hyracks.api.dataflow.value.IBinaryHashFunctionFactory;
import edu.uci.ics.hyracks.api.dataflow.value.ISerializerDeserializer;
import edu.uci.ics.hyracks.api.dataflow.value.ITypeTraits;
import edu.uci.ics.hyracks.api.dataflow.value.RecordDescriptor;
/**
* Descriptor for a primary or secondary index on metadata datasets.
*/
public final class MetadataIndex implements IMetadataIndex {
// Name of dataset that is indexed.
protected final String datasetName;
// Name of index. null for primary indexes. non-null for secondary indexes.
protected final String indexName;
// Types of key fields.
protected final IAType[] keyTypes;
// Names of key fields. Used to compute partitionExprs.
protected final String[] keyNames;
// Field permutation for BTree insert. Auto-created based on numFields.
protected final int[] fieldPermutation;
// Type of payload record for primary indexes. null for secondary indexes.
protected final ARecordType payloadType;
// Record descriptor of btree tuple. Created in c'tor.
protected final RecordDescriptor recDesc;
// Type traits of btree tuple. Created in c'tor.
protected final ITypeTraits[] typeTraits;
// Comparator factories for key fields of btree tuple. Created in c'tor.
protected final IBinaryComparatorFactory[] bcfs;
// Hash function factories for key fields of btree tuple. Created in c'tor.
protected final IBinaryHashFunctionFactory[] bhffs;
// Identifier of file BufferCache backing this metadata btree index.
protected int fileId;
// Resource id of this index for use in transactions.
protected byte[] indexResourceId;
// Logger for tree indexes.
private TreeLogger treeLogger;
public MetadataIndex(String datasetName, String indexName, int numFields, IAType[] keyTypes, String[] keyNames,
ARecordType payloadType) throws AsterixRuntimeException {
// Sanity checks.
if (keyTypes.length != keyNames.length) {
throw new AsterixRuntimeException("Unequal number of key types and names given.");
}
if (keyTypes.length > numFields) {
throw new AsterixRuntimeException("Number of keys given is greater than total number of fields.");
}
// Set simple fields.
this.datasetName = datasetName;
if (indexName == null) {
this.indexName = datasetName;
} else {
this.indexName = indexName;
}
this.keyTypes = keyTypes;
this.keyNames = keyNames;
this.payloadType = payloadType;
// Create field permutation.
fieldPermutation = new int[numFields];
for (int i = 0; i < numFields; i++) {
fieldPermutation[i] = i;
}
// Create serdes for RecordDescriptor;
@SuppressWarnings("rawtypes")
ISerializerDeserializer[] serdes = new ISerializerDeserializer[numFields];
for (int i = 0; i < keyTypes.length; i++) {
serdes[i] = AqlSerializerDeserializerProvider.INSTANCE.getSerializerDeserializer(keyTypes[i]);
}
// For primary indexes, add payload field serde.
if (fieldPermutation.length > keyTypes.length) {
serdes[numFields - 1] = AqlSerializerDeserializerProvider.INSTANCE.getSerializerDeserializer(payloadType);
}
recDesc = new RecordDescriptor(serdes);
// Create type traits.
typeTraits = new ITypeTraits[fieldPermutation.length];
for (int i = 0; i < keyTypes.length; i++) {
typeTraits[i] = AqlTypeTraitProvider.INSTANCE.getTypeTrait(keyTypes[i]);
}
// For primary indexes, add payload field.
if (fieldPermutation.length > keyTypes.length) {
typeTraits[fieldPermutation.length - 1] = AqlTypeTraitProvider.INSTANCE.getTypeTrait(payloadType);
}
// Create binary comparator factories.
bcfs = new IBinaryComparatorFactory[keyTypes.length];
for (int i = 0; i < keyTypes.length; i++) {
bcfs[i] = AqlBinaryComparatorFactoryProvider.INSTANCE
.getBinaryComparatorFactory(keyTypes[i], true);
}
// Create binary hash function factories.
bhffs = new IBinaryHashFunctionFactory[keyTypes.length];
for (int i = 0; i < keyTypes.length; i++) {
bhffs[i] = AqlBinaryHashFunctionFactoryProvider.INSTANCE.getBinaryHashFunctionFactory(keyTypes[i]);
}
}
@Override
public String getIndexedDatasetName() {
return datasetName;
}
@Override
public int[] getFieldPermutation() {
return fieldPermutation;
}
@Override
public int getKeyFieldCount() {
return keyTypes.length;
}
@Override
public int getFieldCount() {
return fieldPermutation.length;
}
@Override
public String getDataverseName() {
return MetadataConstants.METADATA_DATAVERSE_NAME;
}
@Override
public String getNodeGroupName() {
return MetadataConstants.METADATA_NODEGROUP_NAME;
}
@Override
public List<String> getPartitioningExpr() {
ArrayList<String> partitioningExpr = new ArrayList<String>();
for (int i = 0; i < keyNames.length; i++) {
partitioningExpr.add(keyNames[i]);
}
return partitioningExpr;
}
@Override
public String getIndexName() {
return indexName;
}
@Override
public ITypeTraits[] getTypeTraits() {
return typeTraits;
}
@Override
public RecordDescriptor getRecordDescriptor() {
return recDesc;
}
@Override
public IBinaryComparatorFactory[] getKeyBinaryComparatorFactory() {
return bcfs;
}
@Override
public IBinaryHashFunctionFactory[] getKeyBinaryHashFunctionFactory() {
return bhffs;
}
@Override
public String getFileNameRelativePath() {
return getDataverseName() + File.separator + getIndexedDatasetName() + "_idx_" + getIndexName();
}
@Override
public void setFileId(int fileId) {
this.fileId = fileId;
this.indexResourceId = DataUtil.intToByteArray(fileId);
}
@Override
public void initTreeLogger() throws ACIDException {
this.treeLogger = new TreeLogger(indexResourceId);
}
@Override
public int getFileId() {
return fileId;
}
@Override
public ARecordType getPayloadRecordType() {
return payloadType;
}
@Override
public byte[] getResourceId() {
return indexResourceId;
}
public TreeLogger getTreeLogger() {
return treeLogger;
}
}