001/* 002 * Licensed to the Apache Software Foundation (ASF) under one 003 * or more contributor license agreements. See the NOTICE file 004 * distributed with this work for additional information 005 * regarding copyright ownership. The ASF licenses this file 006 * to you under the Apache License, Version 2.0 (the 007 * "License"); you may not use this file except in compliance 008 * with the License. You may obtain a copy of the License at 009 * 010 * http://www.apache.org/licenses/LICENSE-2.0 011 * 012 * Unless required by applicable law or agreed to in writing, software 013 * distributed under the License is distributed on an "AS IS" BASIS, 014 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 015 * See the License for the specific language governing permissions and 016 * limitations under the License. 017 */ 018package org.apache.hadoop.hbase.backup; 019 020import static org.junit.jupiter.api.Assertions.assertEquals; 021import static org.junit.jupiter.api.Assertions.assertFalse; 022 023import java.io.IOException; 024import java.nio.ByteBuffer; 025import java.util.ArrayList; 026import java.util.List; 027import java.util.Map; 028import java.util.UUID; 029import org.apache.hadoop.fs.FileSystem; 030import org.apache.hadoop.fs.LocatedFileStatus; 031import org.apache.hadoop.fs.Path; 032import org.apache.hadoop.fs.RemoteIterator; 033import org.apache.hadoop.hbase.TableName; 034import org.apache.hadoop.hbase.backup.impl.BackupAdminImpl; 035import org.apache.hadoop.hbase.backup.impl.BackupManifest; 036import org.apache.hadoop.hbase.backup.impl.ColumnFamilyMismatchException; 037import org.apache.hadoop.hbase.tool.BulkLoadHFiles; 038import org.apache.hadoop.hbase.util.Bytes; 039import org.apache.hadoop.hbase.util.CommonFSUtils; 040import org.apache.hadoop.hbase.util.HFileTestUtil; 041import org.junit.jupiter.api.BeforeAll; 042 043import org.apache.hbase.thirdparty.com.google.common.base.Throwables; 044 045public class IncrementalBackupRestoreTestBase extends TestBackupBase { 046 047 private static final byte[] BULKLOAD_START_KEY = new byte[] { 0x00 }; 048 private static final byte[] BULKLOAD_END_KEY = new byte[] { Byte.MAX_VALUE }; 049 050 @BeforeAll 051 public static void setUp() throws Exception { 052 provider = "multiwal"; 053 TestBackupBase.setUp(); 054 } 055 056 protected void checkThrowsCFMismatch(IOException ex, List<TableName> tables) { 057 Throwable cause = Throwables.getRootCause(ex); 058 assertEquals(cause.getClass(), ColumnFamilyMismatchException.class); 059 ColumnFamilyMismatchException e = (ColumnFamilyMismatchException) cause; 060 assertEquals(tables, e.getMismatchedTables()); 061 } 062 063 protected String takeFullBackup(List<TableName> tables, BackupAdminImpl backupAdmin) 064 throws IOException { 065 return takeFullBackup(tables, backupAdmin, false); 066 } 067 068 protected String takeFullBackup(List<TableName> tables, BackupAdminImpl backupAdmin, 069 boolean noChecksumVerify) throws IOException { 070 BackupRequest req = 071 createBackupRequest(BackupType.FULL, tables, BACKUP_ROOT_DIR, noChecksumVerify); 072 String backupId = backupAdmin.backupTables(req); 073 checkSucceeded(backupId); 074 return backupId; 075 } 076 077 protected static Path doBulkload(TableName tn, String regionName, byte[]... fams) 078 throws IOException { 079 Path regionDir = createHFiles(tn, regionName, fams); 080 Map<BulkLoadHFiles.LoadQueueItem, ByteBuffer> results = 081 BulkLoadHFiles.create(conf1).bulkLoad(tn, regionDir); 082 assertFalse(results.isEmpty()); 083 return regionDir; 084 } 085 086 private static Path createHFiles(TableName tn, String regionName, byte[]... fams) 087 throws IOException { 088 Path rootdir = CommonFSUtils.getRootDir(conf1); 089 Path regionDir = CommonFSUtils.getRegionDir(rootdir, tn, regionName); 090 091 FileSystem fs = FileSystem.get(TEST_UTIL.getConfiguration()); 092 fs.mkdirs(rootdir); 093 094 for (byte[] fam : fams) { 095 Path famDir = new Path(regionDir, Bytes.toString(fam)); 096 Path hFileDir = new Path(famDir, UUID.randomUUID().toString()); 097 HFileTestUtil.createHFile(conf1, fs, hFileDir, fam, qualName, BULKLOAD_START_KEY, 098 BULKLOAD_END_KEY, 1000); 099 } 100 101 return regionDir; 102 } 103 104 /** 105 * Check that backup manifest can be produced for a different root. Users may want to move 106 * existing backups to a different location. 107 */ 108 protected void validateRootPathCanBeOverridden(String originalPath, String backupId) 109 throws IOException { 110 String anotherRootDir = "/some/other/root/dir"; 111 Path anotherPath = new Path(anotherRootDir, backupId); 112 BackupManifest.BackupImage differentLocationImage = BackupManifest.hydrateRootDir( 113 HBackupFileSystem.getManifest(conf1, new Path(originalPath), backupId).getBackupImage(), 114 anotherPath); 115 assertEquals(differentLocationImage.getRootDir(), anotherRootDir); 116 for (BackupManifest.BackupImage ancestor : differentLocationImage.getAncestors()) { 117 assertEquals(anotherRootDir, ancestor.getRootDir()); 118 } 119 } 120 121 protected List<LocatedFileStatus> getBackupFiles() throws IOException { 122 FileSystem fs = TEST_UTIL.getTestFileSystem(); 123 RemoteIterator<LocatedFileStatus> iter = fs.listFiles(new Path(BACKUP_ROOT_DIR), true); 124 List<LocatedFileStatus> files = new ArrayList<>(); 125 126 while (iter.hasNext()) { 127 files.add(iter.next()); 128 } 129 130 return files; 131 } 132}