CcmNG: ThemeProvider serving themes from the file system using CcmFiles
git-svn-id: https://svn.libreccm.org/ccm/ccm_ng@5678 8810af33-2d31-482b-a856-94f89814c4df
Former-commit-id: afc596e2ea
pull/2/head
parent
623f18d9e2
commit
4b0e83dfca
|
|
@ -385,6 +385,24 @@ public class CcmFiles {
|
||||||
return getFileSystemAdapter().listFiles(getDataPath(path));
|
return getFileSystemAdapter().listFiles(getDataPath(path));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public String getMimeType(final String path) throws FileAccessException {
|
||||||
|
|
||||||
|
return getFileSystemAdapter().getMimeType(path);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void copyFile(final String sourcePath,
|
||||||
|
final String targetPath) throws FileAccessException {
|
||||||
|
|
||||||
|
getFileSystemAdapter().copy(sourcePath, targetPath, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
public void copyFile(final String sourcePath,
|
||||||
|
final String targetPath,
|
||||||
|
final boolean recursive) throws FileAccessException{
|
||||||
|
|
||||||
|
getFileSystemAdapter().copy(sourcePath, targetPath, recursive);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Delete a file or directory. If the file is a directory the directory must
|
* Delete a file or directory. If the file is a directory the directory must
|
||||||
* be empty.
|
* be empty.
|
||||||
|
|
|
||||||
|
|
@ -135,6 +135,14 @@ public interface FileSystemAdapter {
|
||||||
throws FileAccessException,
|
throws FileAccessException,
|
||||||
InsufficientPermissionsException;
|
InsufficientPermissionsException;
|
||||||
|
|
||||||
|
String getMimeType(String path) throws FileAccessException;
|
||||||
|
|
||||||
|
long getSize(String path) throws FileAccessException;
|
||||||
|
|
||||||
|
void copy(String sourcePath,
|
||||||
|
String targetPath,
|
||||||
|
boolean recursive) throws FileAccessException;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* checks if the provided path points to a directory.
|
* checks if the provided path points to a directory.
|
||||||
*
|
*
|
||||||
|
|
|
||||||
|
|
@ -20,15 +20,31 @@ package org.libreccm.files;
|
||||||
|
|
||||||
import org.libreccm.configuration.ConfigurationManager;
|
import org.libreccm.configuration.ConfigurationManager;
|
||||||
|
|
||||||
|
import java.io.FileInputStream;
|
||||||
|
import java.io.FileNotFoundException;
|
||||||
|
import java.io.FileOutputStream;
|
||||||
|
import java.io.IOException;
|
||||||
|
import java.io.InputStream;
|
||||||
|
import java.io.InputStreamReader;
|
||||||
|
import java.io.OutputStream;
|
||||||
|
import java.io.OutputStreamWriter;
|
||||||
|
import java.io.Reader;
|
||||||
|
import java.io.Writer;
|
||||||
|
|
||||||
import javax.annotation.PostConstruct;
|
import javax.annotation.PostConstruct;
|
||||||
import javax.enterprise.context.RequestScoped;
|
import javax.enterprise.context.RequestScoped;
|
||||||
import javax.inject.Inject;
|
import javax.inject.Inject;
|
||||||
|
|
||||||
import java.io.*;
|
|
||||||
import java.nio.charset.Charset;
|
import java.nio.charset.Charset;
|
||||||
|
import java.nio.file.FileVisitResult;
|
||||||
|
import java.nio.file.FileVisitor;
|
||||||
import java.nio.file.Files;
|
import java.nio.file.Files;
|
||||||
|
import java.nio.file.LinkOption;
|
||||||
import java.nio.file.Path;
|
import java.nio.file.Path;
|
||||||
import java.nio.file.Paths;
|
import java.nio.file.Paths;
|
||||||
|
import java.nio.file.StandardCopyOption;
|
||||||
|
import java.nio.file.attribute.BasicFileAttributes;
|
||||||
|
import java.rmi.UnexpectedException;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.stream.Collectors;
|
import java.util.stream.Collectors;
|
||||||
import java.util.stream.Stream;
|
import java.util.stream.Stream;
|
||||||
|
|
@ -190,6 +206,122 @@ public class NIOFileSystemAdapter implements FileSystemAdapter {
|
||||||
return Files.exists(nioPath);
|
return Files.exists(nioPath);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getMimeType(final String path) throws FileAccessException {
|
||||||
|
|
||||||
|
final Path nioPath = Paths.get(path);
|
||||||
|
try {
|
||||||
|
return Files.probeContentType(nioPath);
|
||||||
|
} catch (IOException ex) {
|
||||||
|
throw new FileAccessException(path, ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public long getSize(final String path) throws FileAccessException {
|
||||||
|
|
||||||
|
final Path nioPath = Paths.get(path);
|
||||||
|
try {
|
||||||
|
return Files.size(nioPath);
|
||||||
|
} catch (IOException ex) {
|
||||||
|
throw new FileAccessException(path, ex);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void copy(final String sourcePath,
|
||||||
|
final String targetPath,
|
||||||
|
boolean recursive) throws FileAccessException {
|
||||||
|
|
||||||
|
final Path nioSourcePath = Paths.get(sourcePath);
|
||||||
|
final Path nioTargetPath = Paths.get(targetPath);
|
||||||
|
|
||||||
|
if (recursive) {
|
||||||
|
|
||||||
|
try {
|
||||||
|
Files.walkFileTree(
|
||||||
|
nioTargetPath,
|
||||||
|
new FileVisitor<Path>() {
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public FileVisitResult preVisitDirectory(
|
||||||
|
final Path dir,
|
||||||
|
final BasicFileAttributes attrs)
|
||||||
|
throws IOException {
|
||||||
|
|
||||||
|
return FileVisitResult.CONTINUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public FileVisitResult visitFile(
|
||||||
|
final Path file,
|
||||||
|
final BasicFileAttributes attrs) throws IOException {
|
||||||
|
|
||||||
|
Files.copy(
|
||||||
|
file,
|
||||||
|
nioTargetPath
|
||||||
|
.resolve(nioSourcePath.relativize(file)),
|
||||||
|
StandardCopyOption.ATOMIC_MOVE,
|
||||||
|
StandardCopyOption.COPY_ATTRIBUTES,
|
||||||
|
StandardCopyOption.REPLACE_EXISTING,
|
||||||
|
LinkOption.NOFOLLOW_LINKS);
|
||||||
|
|
||||||
|
return FileVisitResult.CONTINUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public FileVisitResult visitFileFailed(
|
||||||
|
final Path file,
|
||||||
|
final IOException ex) throws IOException {
|
||||||
|
|
||||||
|
return FileVisitResult.CONTINUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public FileVisitResult postVisitDirectory(
|
||||||
|
final Path dir,
|
||||||
|
final IOException ex)
|
||||||
|
throws IOException {
|
||||||
|
|
||||||
|
return FileVisitResult.CONTINUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
});
|
||||||
|
} catch (IOException ex) {
|
||||||
|
throw new FileAccessException(targetPath, ex);
|
||||||
|
}
|
||||||
|
// );
|
||||||
|
// source -> {
|
||||||
|
//
|
||||||
|
// Files.copy(
|
||||||
|
// source,
|
||||||
|
// nioTargetPath
|
||||||
|
// .resolve(nioSourcePath.relativize(
|
||||||
|
// source,
|
||||||
|
// StandardCopyOption.ATOMIC_MOVE,
|
||||||
|
// StandardCopyOption.COPY_ATTRIBUTES,
|
||||||
|
// StandardCopyOption.REPLACE_EXISTING,
|
||||||
|
// LinkOption.NOFOLLOW_LINKS)));
|
||||||
|
// }
|
||||||
|
//
|
||||||
|
// );
|
||||||
|
|
||||||
|
} else {
|
||||||
|
try {
|
||||||
|
Files.copy(nioSourcePath,
|
||||||
|
nioTargetPath,
|
||||||
|
StandardCopyOption.ATOMIC_MOVE,
|
||||||
|
StandardCopyOption.COPY_ATTRIBUTES,
|
||||||
|
StandardCopyOption.REPLACE_EXISTING,
|
||||||
|
LinkOption.NOFOLLOW_LINKS);
|
||||||
|
} catch (IOException ex) {
|
||||||
|
throw new FileAccessException(sourcePath, ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public boolean isDirectory(final String path) throws FileAccessException,
|
public boolean isDirectory(final String path) throws FileAccessException,
|
||||||
FileDoesNotExistException,
|
FileDoesNotExistException,
|
||||||
|
|
|
||||||
|
|
@ -0,0 +1,310 @@
|
||||||
|
/*
|
||||||
|
* Copyright (C) 2018 LibreCCM Foundation.
|
||||||
|
*
|
||||||
|
* This library is free software; you can redistribute it and/or
|
||||||
|
* modify it under the terms of the GNU Lesser General Public
|
||||||
|
* License as published by the Free Software Foundation; either
|
||||||
|
* version 2.1 of the License, or (at your option) any later version.
|
||||||
|
*
|
||||||
|
* This library is distributed in the hope that it will be useful,
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||||
|
* Lesser General Public License for more details.
|
||||||
|
*
|
||||||
|
* You should have received a copy of the GNU Lesser General Public
|
||||||
|
* License along with this library; if not, write to the Free Software
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
|
||||||
|
* MA 02110-1301 USA
|
||||||
|
*/
|
||||||
|
package org.libreccm.theming;
|
||||||
|
|
||||||
|
import org.libreccm.core.UnexpectedErrorException;
|
||||||
|
import org.libreccm.files.CcmFiles;
|
||||||
|
import org.libreccm.files.DirectoryNotEmptyException;
|
||||||
|
import org.libreccm.files.FileAccessException;
|
||||||
|
import org.libreccm.files.FileDoesNotExistException;
|
||||||
|
import org.libreccm.files.InsufficientPermissionsException;
|
||||||
|
import org.libreccm.theming.manifest.ThemeManifest;
|
||||||
|
import org.libreccm.theming.manifest.ThemeManifestUtil;
|
||||||
|
|
||||||
|
import java.io.InputStream;
|
||||||
|
import java.io.OutputStream;
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Optional;
|
||||||
|
import java.util.stream.Collectors;
|
||||||
|
|
||||||
|
import javax.enterprise.context.RequestScoped;
|
||||||
|
import javax.inject.Inject;
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @author <a href="mailto:jens.pelzetter@googlemail.com">Jens Pelzetter</a>
|
||||||
|
*/
|
||||||
|
@RequestScoped
|
||||||
|
public class FileSystemThemeProvider implements ThemeProvider {
|
||||||
|
|
||||||
|
private static final long serialVersionUID = 1L;
|
||||||
|
|
||||||
|
private static final String BASE_PATH = "/themes";
|
||||||
|
private static final String DRAFT_THEMES_PATH = "/themes" + "/draft";
|
||||||
|
private static final String LIVE_THEMES_PATH = "/themes" + "/live";
|
||||||
|
|
||||||
|
private static final String THEME_JSON = "%s/theme.json";
|
||||||
|
private static final String THEME_XML = "%s/theme.xml";
|
||||||
|
|
||||||
|
@Inject
|
||||||
|
private CcmFiles ccmFiles;
|
||||||
|
|
||||||
|
@Inject
|
||||||
|
private ThemeManifestUtil manifestUtil;
|
||||||
|
|
||||||
|
@Inject
|
||||||
|
private ThemeFileInfoUtil themeFileInfoUtil;
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<ThemeInfo> getThemes() {
|
||||||
|
|
||||||
|
try {
|
||||||
|
|
||||||
|
if (!ccmFiles.isDirectory(BASE_PATH)
|
||||||
|
|| !ccmFiles.isDirectory(DRAFT_THEMES_PATH)) {
|
||||||
|
|
||||||
|
return Collections.emptyList();
|
||||||
|
}
|
||||||
|
|
||||||
|
return ccmFiles
|
||||||
|
.listFiles(DRAFT_THEMES_PATH)
|
||||||
|
.stream()
|
||||||
|
.map(themePath -> readInfo(themePath))
|
||||||
|
.filter(info -> info.isPresent())
|
||||||
|
.map(info -> info.get())
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
|
||||||
|
} catch (FileAccessException
|
||||||
|
| FileDoesNotExistException
|
||||||
|
| InsufficientPermissionsException ex) {
|
||||||
|
|
||||||
|
throw new UnexpectedErrorException(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<ThemeInfo> getLiveThemes() {
|
||||||
|
|
||||||
|
try {
|
||||||
|
if (!ccmFiles.isDirectory(BASE_PATH)
|
||||||
|
|| !ccmFiles.isDirectory(DRAFT_THEMES_PATH)) {
|
||||||
|
|
||||||
|
return Collections.emptyList();
|
||||||
|
}
|
||||||
|
|
||||||
|
return ccmFiles
|
||||||
|
.listFiles(LIVE_THEMES_PATH)
|
||||||
|
.stream()
|
||||||
|
.map(themePath -> readInfo(themePath))
|
||||||
|
.filter(info -> info.isPresent())
|
||||||
|
.map(info -> info.get())
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
} catch (FileAccessException
|
||||||
|
| FileDoesNotExistException
|
||||||
|
| InsufficientPermissionsException ex) {
|
||||||
|
|
||||||
|
throw new UnexpectedErrorException(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Optional<ThemeInfo> getThemeInfo(final String theme,
|
||||||
|
final ThemeVersion version) {
|
||||||
|
|
||||||
|
final String themePath = createThemePath(theme, version);
|
||||||
|
return readInfo(themePath);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean providesTheme(final String theme,
|
||||||
|
final ThemeVersion version) {
|
||||||
|
|
||||||
|
final String themePath = createThemePath(theme, version);
|
||||||
|
|
||||||
|
try {
|
||||||
|
return ccmFiles.existsFile(themePath);
|
||||||
|
} catch (FileAccessException | InsufficientPermissionsException ex) {
|
||||||
|
throw new UnexpectedErrorException(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public List<ThemeFileInfo> listThemeFiles(final String theme,
|
||||||
|
final ThemeVersion version,
|
||||||
|
final String path) {
|
||||||
|
|
||||||
|
final String themePath = createThemePath(theme, version);
|
||||||
|
final String filePath = String.join(themePath, path, "/");
|
||||||
|
|
||||||
|
try {
|
||||||
|
|
||||||
|
return ccmFiles
|
||||||
|
.listFiles(filePath)
|
||||||
|
.stream()
|
||||||
|
.map(currentPath -> buildThemeFileInfo(currentPath))
|
||||||
|
.collect(Collectors.toList());
|
||||||
|
|
||||||
|
} catch (FileAccessException
|
||||||
|
| FileDoesNotExistException
|
||||||
|
| InsufficientPermissionsException ex) {
|
||||||
|
|
||||||
|
throw new UnexpectedErrorException(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public Optional<InputStream> getThemeFileAsStream(
|
||||||
|
final String theme, final ThemeVersion version, final String path) {
|
||||||
|
|
||||||
|
final String themePath = createThemePath(theme, version);
|
||||||
|
final String filePath = String.join(theme, path, "/");
|
||||||
|
|
||||||
|
try {
|
||||||
|
if (ccmFiles.existsFile(path)) {
|
||||||
|
return Optional.empty();
|
||||||
|
} else {
|
||||||
|
return Optional.of(ccmFiles.createInputStream(filePath));
|
||||||
|
}
|
||||||
|
} catch (FileAccessException
|
||||||
|
| FileDoesNotExistException
|
||||||
|
| InsufficientPermissionsException ex) {
|
||||||
|
|
||||||
|
throw new UnexpectedErrorException(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public OutputStream getOutputStreamForThemeFile(final String theme,
|
||||||
|
final String path) {
|
||||||
|
|
||||||
|
final String themePath = createThemePath(theme, ThemeVersion.DRAFT);
|
||||||
|
final String filePath = String.join(themePath, path, "/");
|
||||||
|
|
||||||
|
try {
|
||||||
|
|
||||||
|
return ccmFiles.createOutputStream(filePath);
|
||||||
|
|
||||||
|
} catch (FileAccessException
|
||||||
|
| InsufficientPermissionsException ex) {
|
||||||
|
|
||||||
|
throw new UnexpectedErrorException(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void deleteThemeFile(final String theme, final String path) {
|
||||||
|
|
||||||
|
final String themePath = createThemePath(theme, ThemeVersion.DRAFT);
|
||||||
|
final String filePath = String.join(themePath, path, "/");
|
||||||
|
|
||||||
|
try {
|
||||||
|
ccmFiles.deleteFile(filePath, true);
|
||||||
|
} catch (FileAccessException
|
||||||
|
| FileDoesNotExistException
|
||||||
|
| DirectoryNotEmptyException
|
||||||
|
| InsufficientPermissionsException ex) {
|
||||||
|
|
||||||
|
throw new UnexpectedErrorException(ex);
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean supportsChanges() {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean supportsDraftThemes() {
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void publishTheme(final String theme) {
|
||||||
|
|
||||||
|
final String draftThemePath = createThemePath(theme,
|
||||||
|
ThemeVersion.DRAFT);
|
||||||
|
final String liveThemePath = createThemePath(theme,
|
||||||
|
ThemeVersion.LIVE);
|
||||||
|
|
||||||
|
try {
|
||||||
|
ccmFiles.copyFile(draftThemePath, liveThemePath, true);
|
||||||
|
} catch (FileAccessException ex) {
|
||||||
|
throw new UnexpectedErrorException();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private String createThemePath(final String theme,
|
||||||
|
final ThemeVersion version) {
|
||||||
|
|
||||||
|
switch (version) {
|
||||||
|
|
||||||
|
case DRAFT:
|
||||||
|
return String.format(DRAFT_THEMES_PATH, theme);
|
||||||
|
case LIVE:
|
||||||
|
return String.format(LIVE_THEMES_PATH, theme);
|
||||||
|
default:
|
||||||
|
throw new IllegalArgumentException(String
|
||||||
|
.format("Illegal argument for ThemeVersion \"%s\".",
|
||||||
|
version));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private Optional<ThemeInfo> readInfo(final String themePath) {
|
||||||
|
|
||||||
|
final ThemeManifest manifest;
|
||||||
|
try {
|
||||||
|
final InputStream inputStream = ccmFiles
|
||||||
|
.createInputStream(String.format(THEME_JSON,
|
||||||
|
themePath));
|
||||||
|
if (ccmFiles.existsFile(String.format(THEME_JSON,
|
||||||
|
themePath))) {
|
||||||
|
|
||||||
|
manifest = manifestUtil.loadManifest(inputStream, "theme.json");
|
||||||
|
} else if (ccmFiles.existsFile(String.format(THEME_XML,
|
||||||
|
themePath))) {
|
||||||
|
manifest = manifestUtil.loadManifest(inputStream, "theme.xml");
|
||||||
|
} else {
|
||||||
|
return Optional.empty();
|
||||||
|
}
|
||||||
|
} catch (FileAccessException
|
||||||
|
| FileDoesNotExistException
|
||||||
|
| InsufficientPermissionsException ex) {
|
||||||
|
|
||||||
|
throw new UnexpectedErrorException(ex);
|
||||||
|
}
|
||||||
|
|
||||||
|
final ThemeInfo themeInfo = new ThemeInfo();
|
||||||
|
themeInfo.setManifest(manifest);
|
||||||
|
|
||||||
|
return Optional.of(themeInfo);
|
||||||
|
}
|
||||||
|
|
||||||
|
private ThemeFileInfo buildThemeFileInfo(final String filePath) {
|
||||||
|
|
||||||
|
final ThemeFileInfo fileInfo = new ThemeFileInfo();
|
||||||
|
|
||||||
|
try {
|
||||||
|
fileInfo.setDirectory(ccmFiles.isDirectory(filePath));
|
||||||
|
fileInfo.setMimeType(ccmFiles.getMimeType(filePath));
|
||||||
|
fileInfo.setName(filePath);
|
||||||
|
fileInfo.setWritable(true);
|
||||||
|
|
||||||
|
return fileInfo;
|
||||||
|
} catch (FileAccessException
|
||||||
|
| FileDoesNotExistException
|
||||||
|
| InsufficientPermissionsException ex) {
|
||||||
|
|
||||||
|
throw new UnexpectedErrorException(ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
@ -51,8 +51,6 @@ import javax.json.Json;
|
||||||
import javax.json.JsonArray;
|
import javax.json.JsonArray;
|
||||||
import javax.json.JsonObject;
|
import javax.json.JsonObject;
|
||||||
import javax.json.JsonReader;
|
import javax.json.JsonReader;
|
||||||
import javax.json.JsonStructure;
|
|
||||||
import javax.json.JsonValue;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
|
|
@ -61,7 +59,7 @@ import javax.json.JsonValue;
|
||||||
@RequestScoped
|
@RequestScoped
|
||||||
public class StaticThemeProvider implements ThemeProvider {
|
public class StaticThemeProvider implements ThemeProvider {
|
||||||
|
|
||||||
private static final long serialVersionUID = 7174370298224448067L;
|
private static final long serialVersionUID = 1L;
|
||||||
private static final Logger LOGGER = LogManager.getLogger(
|
private static final Logger LOGGER = LogManager.getLogger(
|
||||||
StaticThemeProvider.class);
|
StaticThemeProvider.class);
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -14,6 +14,7 @@ import org.xadisk.filesystem.exceptions.LockingFailedException;
|
||||||
import org.xadisk.filesystem.exceptions.NoTransactionAssociatedException;
|
import org.xadisk.filesystem.exceptions.NoTransactionAssociatedException;
|
||||||
|
|
||||||
import java.io.File;
|
import java.io.File;
|
||||||
|
import java.io.IOException;
|
||||||
|
|
||||||
import javax.resource.ResourceException;
|
import javax.resource.ResourceException;
|
||||||
|
|
||||||
|
|
@ -23,23 +24,27 @@ import java.io.OutputStream;
|
||||||
import java.io.OutputStreamWriter;
|
import java.io.OutputStreamWriter;
|
||||||
import java.io.Reader;
|
import java.io.Reader;
|
||||||
import java.io.Writer;
|
import java.io.Writer;
|
||||||
|
import java.nio.file.Files;
|
||||||
|
import java.nio.file.Path;
|
||||||
|
import java.nio.file.Paths;
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Optional;
|
import java.util.Optional;
|
||||||
|
|
||||||
|
import javax.activation.MimetypesFileTypeMap;
|
||||||
import javax.enterprise.context.RequestScoped;
|
import javax.enterprise.context.RequestScoped;
|
||||||
import javax.naming.InitialContext;
|
import javax.naming.InitialContext;
|
||||||
import javax.naming.NamingException;
|
import javax.naming.NamingException;
|
||||||
import javax.transaction.Transactional;
|
import javax.transaction.Transactional;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* An implementation of the {@link FileSystemAdapter} which uses XADisk to provides
|
* An implementation of the {@link FileSystemAdapter} which uses XADisk to
|
||||||
* a transaction safe access to the file system.
|
* provides a transaction safe access to the file system.
|
||||||
*
|
*
|
||||||
* This {@link FileSystemAdapter} requires that XADisk.rar is deployed into the
|
* This {@link FileSystemAdapter} requires that XADisk.rar is deployed into the
|
||||||
* application server and that a resource adapter is configured to provided
|
* application server and that a resource adapter is configured to provided
|
||||||
* access to the file system. Please refer the documentation of this module
|
* access to the file system. Please refer the documentation of this module for
|
||||||
* for more information.
|
* more information.
|
||||||
*
|
*
|
||||||
* @see http://xadisk.java.net
|
* @see http://xadisk.java.net
|
||||||
*
|
*
|
||||||
|
|
@ -204,9 +209,66 @@ public class XAFileSystemAdapter implements FileSystemAdapter {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getMimeType(final String path) throws FileAccessException {
|
||||||
|
|
||||||
|
final File file = new File(path);
|
||||||
|
|
||||||
|
return MimetypesFileTypeMap
|
||||||
|
.getDefaultFileTypeMap()
|
||||||
|
.getContentType(file);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public long getSize(final String path) throws FileAccessException {
|
||||||
|
|
||||||
|
final XADiskConnection connection = connect();
|
||||||
|
|
||||||
|
final File file = new File(path);
|
||||||
|
try {
|
||||||
|
return connection.getFileLength(file);
|
||||||
|
} catch (FileNotExistsException
|
||||||
|
| InsufficientPermissionOnFileException
|
||||||
|
| LockingFailedException
|
||||||
|
| NoTransactionAssociatedException
|
||||||
|
| InterruptedException ex) {
|
||||||
|
|
||||||
|
throw new FileAccessException(path, ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void copy(final String sourcePath,
|
||||||
|
final String targetPath,
|
||||||
|
boolean recursive) throws FileAccessException {
|
||||||
|
|
||||||
|
final XADiskConnection connection = connect();
|
||||||
|
final File sourceFile = new File(sourcePath);
|
||||||
|
final File targetFile = new File(targetPath);
|
||||||
|
|
||||||
|
try {
|
||||||
|
if (connection.fileExists(targetFile)) {
|
||||||
|
connection.deleteFile(targetFile);
|
||||||
|
connection.copyFile(sourceFile, targetFile);
|
||||||
|
}
|
||||||
|
connection.copyFile(sourceFile, targetFile);
|
||||||
|
} catch (org.xadisk.filesystem.exceptions.DirectoryNotEmptyException
|
||||||
|
| org.xadisk.filesystem.exceptions.FileAlreadyExistsException
|
||||||
|
| FileNotExistsException
|
||||||
|
| FileUnderUseException
|
||||||
|
| InsufficientPermissionOnFileException
|
||||||
|
| InterruptedException
|
||||||
|
| LockingFailedException
|
||||||
|
| NoTransactionAssociatedException ex) {
|
||||||
|
|
||||||
|
throw new FileAccessException(targetPath, ex);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
@Transactional(Transactional.TxType.REQUIRED)
|
@Transactional(Transactional.TxType.REQUIRED)
|
||||||
@Override
|
@Override
|
||||||
public boolean isDirectory(final String path) throws FileAccessException,
|
public boolean isDirectory(final String path)
|
||||||
|
throws FileAccessException,
|
||||||
FileDoesNotExistException,
|
FileDoesNotExistException,
|
||||||
InsufficientPermissionsException {
|
InsufficientPermissionsException {
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue