blob: 40c4438c41d9ad870d299267e602fb100f22883a [file] [log] [blame]
/**
* Licensed to the Apache Software Foundation (ASF) under one
* or more contributor license agreements. See the NOTICE file
* distributed with this work for additional information
* regarding copyright ownership. The ASF licenses this file
* to you 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.
*/
package org.apache.hadoop.hdfs.server.datanode;
import com.google.common.base.Preconditions;
import org.apache.hadoop.classification.InterfaceAudience;
import org.apache.hadoop.classification.InterfaceStability;
import org.apache.hadoop.conf.Configuration;
import org.apache.hadoop.hdfs.DFSConfigKeys;
import org.apache.hadoop.hdfs.protocol.ExtendedBlock;
import org.apache.hadoop.hdfs.server.datanode.fsdataset.impl.FsDatasetFactory;
import org.apache.hadoop.hdfs.server.datanode.fsdataset.FsVolumeSpi;
import org.apache.hadoop.util.ReflectionUtils;
import java.io.FileNotFoundException;
import java.io.IOException;
/**
* Provide block access for FsDataset white box tests.
*/
@InterfaceAudience.Private
@InterfaceStability.Unstable
public interface FsDatasetTestUtils {
abstract class Factory<D extends FsDatasetTestUtils> {
/**
* By default, it returns FsDatasetImplTestUtilsFactory.
*
* @return The configured Factory.
*/
public static Factory<?> getFactory(Configuration conf) {
String className = conf.get(
DFSConfigKeys.DFS_DATANODE_FSDATASET_FACTORY_KEY,
FsDatasetFactory.class.getName());
Preconditions.checkState(className.contains("Factory"));
className = className.replaceFirst("(\\$)?Factory$", "TestUtilsFactory");
final Class<? extends Factory> clazz = conf.getClass(
className,
FsDatasetImplTestUtilsFactory.class,
Factory.class);
return ReflectionUtils.newInstance(clazz, conf);
}
/**
* Create a new instance of FsDatasetTestUtils.
*/
public abstract D newInstance(DataNode datanode);
/**
* @return True for SimulatedFsDataset
*/
public boolean isSimulated() {
return false;
}
}
/**
* A replica to be corrupted.
*
* It is safe to corrupt this replica even if the MiniDFSCluster is shutdown.
*/
interface MaterializedReplica {
/**
* Corrupt the block file of the replica.
* @throws FileNotFoundException if the block file does not exist.
* @throws IOException if I/O error.
*/
void corruptData() throws IOException;
/**
* Corrupt the block file with the given content.
* @param newContent the new content written to the block file.
* @throws FileNotFoundException if the block file does not exist.
* @throws IOException if I/O error.
*/
void corruptData(byte[] newContent) throws IOException;
/**
* Truncate the block file of the replica to the newSize.
* @param newSize the new size of the block file.
* @throws FileNotFoundException if the block file does not exist.
* @throws IOException if I/O error.
*/
void truncateData(long newSize) throws IOException;
/**
* Delete the block file of the replica.
* @throws FileNotFoundException if the block file does not exist.
* @throws IOException if I/O error.
*/
void deleteData() throws IOException;
/**
* Corrupt the metadata file of the replica.
* @throws FileNotFoundException if the block file does not exist.
* @throws IOException if I/O error.
*/
void corruptMeta() throws IOException;
/**
* Delete the metadata file of the replcia.
* @throws FileNotFoundException if the block file does not exist.
* @throws IOException I/O error.
*/
void deleteMeta() throws IOException;
/**
* Truncate the metadata file of the replica to the newSize.
* @throws FileNotFoundException if the block file does not exist.
* @throws IOException I/O error.
*/
void truncateMeta(long newSize) throws IOException;
}
/**
* Get a materialized replica to corrupt its block / crc later.
* @param block the block of this replica begone to.
* @return a replica to corrupt. Return null if the replica does not exist
* in this dataset.
* @throws ReplicaNotFoundException if the replica does not exists on the
* dataset.
*/
MaterializedReplica getMaterializedReplica(ExtendedBlock block)
throws ReplicaNotFoundException;
/**
* Create a finalized replica and add it into the FsDataset.
*/
Replica createFinalizedReplica(ExtendedBlock block) throws IOException;
/**
* Create a finalized replica on a particular volume, and add it into
* the FsDataset.
*/
Replica createFinalizedReplica(FsVolumeSpi volume, ExtendedBlock block)
throws IOException;
/**
* Create a {@link ReplicaInPipeline} and add it into the FsDataset.
*/
Replica createReplicaInPipeline(ExtendedBlock block) throws IOException;
/**
* Create a {@link ReplicaInPipeline} and add it into the FsDataset.
*/
Replica createReplicaInPipeline(FsVolumeSpi volume, ExtendedBlock block)
throws IOException;
/**
* Create a {@link ReplicaBeingWritten} and add it into the FsDataset.
*/
Replica createRBW(ExtendedBlock block) throws IOException;
/**
* Create a {@link ReplicaBeingWritten} on the particular volume, and add it
* into the FsDataset.
*/
Replica createRBW(FsVolumeSpi volume, ExtendedBlock block) throws IOException;
/**
* Create a {@link ReplicaWaitingToBeRecovered} object and add it into the
* FsDataset.
*/
Replica createReplicaWaitingToBeRecovered(ExtendedBlock block)
throws IOException;
/**
* Create a {@link ReplicaWaitingToBeRecovered} on the particular volume,
* and add it into the FsDataset.
*/
Replica createReplicaWaitingToBeRecovered(
FsVolumeSpi volume, ExtendedBlock block) throws IOException;
/**
* Create a {@link ReplicaUnderRecovery} object and add it into the FsDataset.
*/
Replica createReplicaUnderRecovery(ExtendedBlock block, long recoveryId)
throws IOException;
/**
* Check the stored files / data of a replica.
* @param replica a replica object.
* @throws IOException
*/
void checkStoredReplica(final Replica replica) throws IOException;
/**
* Create dummy replicas for block data and metadata.
* @param block the block of which replica to be created.
* @throws IOException on I/O error.
*/
void injectCorruptReplica(ExtendedBlock block) throws IOException;
}