private static void registerDefaultProviders() { if (providers == null || defaultProvider == null) { Map<String, FilePath> map = Collections.synchronizedMap(New.<String, FilePath>hashMap()); // 默认是org.h2.store.fs.FilePathDisk, 所以这里不包含它 // 但是少了org.h2.store.fs.FilePathRec、org.h2.mvstore.cache.FilePathCache // 不过org.h2.store.fs.FilePathRec是通过org.h2.store.fs.FilePath.register(FilePath)这个方法注册 // 见org.h2.store.fs.FilePathRec.register(), // 在org.h2.engine.ConnectionInfo.ConnectionInfo(String, Properties)调用它了 for (String c : new String[] { "org.h2.store.fs.FilePathDisk", "org.h2.store.fs.FilePathMem", "org.h2.store.fs.FilePathMemLZF", "org.h2.store.fs.FilePathNioMem", "org.h2.store.fs.FilePathNioMemLZF", "org.h2.store.fs.FilePathSplit", "org.h2.store.fs.FilePathNio", "org.h2.store.fs.FilePathNioMapped", "org.h2.store.fs.FilePathZip" }) { try { FilePath p = (FilePath) Class.forName(c).newInstance(); map.put(p.getScheme(), p); if (defaultProvider == null) { defaultProvider = p; } } catch (Exception e) { // ignore - the files may be excluded in purpose } } providers = map; } }
/** * Try to open the file. * * @param fileName the file name * @param readOnly whether the file should only be opened in read-only mode, even if the file is * writable * @param encryptionKey the encryption key, or null if encryption is not used */ public void open(String fileName, boolean readOnly, char[] encryptionKey) { if (file != null) { return; } if (fileName != null) { FilePath p = FilePath.get(fileName); // if no explicit scheme was specified, NIO is used if (p instanceof FilePathDisk && !fileName.startsWith(p.getScheme() + ":")) { // ensure the NIO file system is registered FilePathNio.class.getName(); fileName = "nio:" + fileName; } } this.fileName = fileName; FilePath f = FilePath.get(fileName); FilePath parent = f.getParent(); if (parent != null && !parent.exists()) { throw DataUtils.newIllegalArgumentException("Directory does not exist: {0}", parent); } if (f.exists() && !f.canWrite()) { readOnly = true; } this.readOnly = readOnly; try { file = f.open(readOnly ? "r" : "rw"); if (encryptionKey != null) { byte[] key = FilePathEncrypt.getPasswordBytes(encryptionKey); encryptedFile = file; file = new FilePathEncrypt.FileEncrypt(fileName, key, file); } file = FilePathCache.wrap(file); try { if (readOnly) { fileLock = file.tryLock(0, Long.MAX_VALUE, true); } else { fileLock = file.tryLock(); } } catch (OverlappingFileLockException e) { throw DataUtils.newIllegalStateException( DataUtils.ERROR_FILE_LOCKED, "The file is locked: {0}", fileName, e); } if (fileLock == null) { throw DataUtils.newIllegalStateException( DataUtils.ERROR_FILE_LOCKED, "The file is locked: {0}", fileName); } fileSize = file.size(); } catch (IOException e) { throw DataUtils.newIllegalStateException( DataUtils.ERROR_READING_FAILED, "Could not open file {0}", fileName, e); } }
/** * Unregister a file provider. * * @param provider the file provider */ public static void unregister(FilePath provider) { registerDefaultProviders(); providers.remove(provider.getScheme()); }
/** * Register a file provider. * * @param provider the file provider */ public static void register(FilePath provider) { registerDefaultProviders(); providers.put(provider.getScheme(), provider); }