1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18 package org.apache.hadoop.hbase.master.snapshot;
19
20 import static org.junit.Assert.assertFalse;
21 import static org.junit.Assert.assertTrue;
22
23 import java.io.IOException;
24 import java.util.*;
25
26 import com.google.common.collect.Iterables;
27 import org.apache.commons.logging.Log;
28 import org.apache.commons.logging.LogFactory;
29 import org.apache.hadoop.fs.FileStatus;
30 import org.apache.hadoop.fs.FileSystem;
31 import org.apache.hadoop.fs.Path;
32 import org.apache.hadoop.hbase.HBaseTestingUtility;
33 import org.apache.hadoop.hbase.testclassification.MediumTests;
34 import org.apache.hadoop.hbase.snapshot.SnapshotDescriptionUtils;
35 import org.apache.hadoop.hbase.snapshot.SnapshotReferenceUtil;
36 import org.apache.hadoop.hbase.snapshot.SnapshotTestingUtils.SnapshotMock;
37 import org.apache.hadoop.hbase.util.FSUtils;
38 import org.junit.After;
39 import org.junit.AfterClass;
40 import org.junit.BeforeClass;
41 import org.junit.Ignore;
42 import org.junit.Test;
43 import org.junit.experimental.categories.Category;
44
45
46
47
48 @Category(MediumTests.class)
49 public class TestSnapshotFileCache {
50
51 private static final Log LOG = LogFactory.getLog(TestSnapshotFileCache.class);
52 private static final HBaseTestingUtility UTIL = new HBaseTestingUtility();
53 private static long sequenceId = 0;
54 private static FileSystem fs;
55 private static Path rootDir;
56
57 @BeforeClass
58 public static void startCluster() throws Exception {
59 UTIL.startMiniDFSCluster(1);
60 fs = UTIL.getDFSCluster().getFileSystem();
61 rootDir = UTIL.getDefaultRootDirPath();
62 }
63
64 @AfterClass
65 public static void stopCluster() throws Exception {
66 UTIL.shutdownMiniDFSCluster();
67 }
68
69 @After
70 public void cleanupFiles() throws Exception {
71
72 Path snapshotDir = SnapshotDescriptionUtils.getSnapshotsDir(rootDir);
73 fs.delete(snapshotDir, true);
74 }
75
76 @Test(timeout = 10000000)
77 @Ignore("See HBASE-19275")
78 public void testLoadAndDelete() throws IOException {
79
80 long period = Long.MAX_VALUE;
81 SnapshotFileCache cache = new SnapshotFileCache(fs, rootDir, period, 10000000,
82 "test-snapshot-file-cache-refresh", new SnapshotFiles());
83
84 createAndTestSnapshotV1(cache, "snapshot1a", false, true);
85
86 createAndTestSnapshotV2(cache, "snapshot2a", false, true);
87 }
88
89 @Test
90 @Ignore("See HBASE-19275")
91 public void testReloadModifiedDirectory() throws IOException {
92
93 long period = Long.MAX_VALUE;
94 SnapshotFileCache cache = new SnapshotFileCache(fs, rootDir, period, 10000000,
95 "test-snapshot-file-cache-refresh", new SnapshotFiles());
96
97 createAndTestSnapshotV1(cache, "snapshot1", false, true);
98
99 createAndTestSnapshotV1(cache, "snapshot1", false, false);
100
101 createAndTestSnapshotV2(cache, "snapshot2", false, true);
102
103 createAndTestSnapshotV2(cache, "snapshot2", false, false);
104 }
105
106 @Test
107 public void testSnapshotTempDirReload() throws IOException {
108 long period = Long.MAX_VALUE;
109
110 SnapshotFileCache cache = new SnapshotFileCache(fs, rootDir, period, 10000000,
111 "test-snapshot-file-cache-refresh", new SnapshotFiles());
112
113
114 createAndTestSnapshotV1(cache, "snapshot0v1", false, false);
115 createAndTestSnapshotV1(cache, "snapshot0v2", false, false);
116 }
117
118 class SnapshotFiles implements SnapshotFileCache.SnapshotFileInspector {
119 public Collection<String> filesUnderSnapshot(final Path snapshotDir) throws IOException {
120 Collection<String> files = new HashSet<String>();
121 files.addAll(SnapshotReferenceUtil.getHFileNames(UTIL.getConfiguration(), fs, snapshotDir));
122 return files;
123 }
124 };
125
126 private SnapshotMock.SnapshotBuilder createAndTestSnapshotV1(final SnapshotFileCache cache,
127 final String name, final boolean tmp, final boolean removeOnExit) throws IOException {
128 SnapshotMock snapshotMock = new SnapshotMock(UTIL.getConfiguration(), fs, rootDir);
129 SnapshotMock.SnapshotBuilder builder = snapshotMock.createSnapshotV1(name, name);
130 createAndTestSnapshot(cache, builder, tmp, removeOnExit);
131 return builder;
132 }
133
134 private void createAndTestSnapshotV2(final SnapshotFileCache cache, final String name,
135 final boolean tmp, final boolean removeOnExit) throws IOException {
136 SnapshotMock snapshotMock = new SnapshotMock(UTIL.getConfiguration(), fs, rootDir);
137 SnapshotMock.SnapshotBuilder builder = snapshotMock.createSnapshotV2(name, name);
138 createAndTestSnapshot(cache, builder, tmp, removeOnExit);
139 }
140
141 private void createAndTestSnapshot(final SnapshotFileCache cache,
142 final SnapshotMock.SnapshotBuilder builder,
143 final boolean tmp, final boolean removeOnExit) throws IOException {
144 List<Path> files = new ArrayList<Path>();
145 for (int i = 0; i < 3; ++i) {
146 for (Path filePath: builder.addRegion()) {
147 files.add(filePath);
148 }
149 }
150
151
152 builder.commit();
153
154
155 for (Path path: files) {
156 Iterable<FileStatus> nonSnapshotFiles = getNonSnapshotFiles(cache, path);
157 assertFalse("Cache didn't find " + path.getName(),
158 Iterables.contains(nonSnapshotFiles, path.getName()));
159 }
160
161 FSUtils.logFileSystemState(fs, rootDir, LOG);
162 if (removeOnExit) {
163 LOG.debug("Deleting snapshot.");
164 fs.delete(builder.getSnapshotsDir(), true);
165 FSUtils.logFileSystemState(fs, rootDir, LOG);
166
167
168 for (Path filePath: files) {
169 Iterable<FileStatus> nonSnapshotFiles = getNonSnapshotFiles(cache, filePath);
170 assertFalse("Cache didn't find " + filePath.getName(), Iterables.contains(nonSnapshotFiles,
171 filePath.getName()));
172 }
173
174
175 cache.triggerCacheRefreshForTesting();
176
177
178 for (Path filePath: files) {
179 Iterable<FileStatus> nonSnapshotFiles = getNonSnapshotFiles(cache, filePath);
180 assertTrue("Cache found '" + filePath.getName() + "', but it shouldn't have.",
181 !Iterables.contains(nonSnapshotFiles, filePath.getName()));
182 }
183 }
184 }
185
186 private Iterable<FileStatus> getNonSnapshotFiles(SnapshotFileCache cache, Path storeFile)
187 throws IOException {
188 return cache.getUnreferencedFiles(
189 Arrays.asList(FSUtils.listStatus(fs, storeFile.getParent())), null
190 );
191 }
192 }