Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

PAYARA-3434 optimise FileArchive #3616

Merged
merged 7 commits into from Feb 26, 2019
Merged
Show file tree
Hide file tree
Changes from 2 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
Expand Up @@ -37,7 +37,7 @@
* only if the new code is made subject to such option by the copyright
* holder.
*
* Portions Copyright [2018] Payara Foundation and/or affiliates
* Portions Copyright [2018-2019] Payara Foundation and/or affiliates
*/

package com.sun.enterprise.deploy.shared;
Expand All @@ -63,6 +63,7 @@
import java.util.jar.Manifest;
import java.net.URI;
import java.nio.file.Files;
import java.nio.file.Path;

import org.glassfish.logging.annotation.LogMessageInfo;

Expand Down Expand Up @@ -138,6 +139,12 @@ public class FileArchive extends AbstractReadableArchive implements WritableArch
* be sure that the staleFileManager field has been set.
*/
private boolean isOpenedOrCreated = false;

/**
* Cache for {@link #entries()}. This is done as a static variable instead of a service
* because FileArchive is commonly created by constructor rather than through injection.
*/
private static Map<Integer, Enumeration> entriesCache = new HashMap<Integer, Enumeration>();
Cousjava marked this conversation as resolved.
Show resolved Hide resolved

/**
* Open an abstract archive
Expand Down Expand Up @@ -296,12 +303,19 @@ public Enumeration<String> entries(Enumeration embeddedArchives) {
* @return an enumeration of the archive file entries.
*/
@Override
public Enumeration<String> entries(String prefix) {
public Enumeration<String> entries(String prefix) {
prefix = prefix.replace('/', File.separatorChar);
File file = new File(archive, prefix);
List<String> namesList = new ArrayList<>();
getListOfFiles(file, namesList, null);
return Collections.enumeration(namesList);

if (entriesCache.containsKey(file.hashCode())) {
return entriesCache.get(file.hashCode());
} else {
List<String> namesList = new ArrayList<String>();
getListOfFiles(file, namesList, null);
Enumeration entries = Collections.enumeration(namesList);
entriesCache.put(file.hashCode(), entries);
Cousjava marked this conversation as resolved.
Show resolved Hide resolved
return entries;
}
}

/**
Expand Down Expand Up @@ -575,14 +589,14 @@ private boolean deleteDir(File directory) throws IOException {
*/
if (!Files.isSymbolicLink(directory.toPath())) {
File[] entries = directory.listFiles();
for (int i = 0;entries != null && i < entries.length;i++) {
if (entries[i].isDirectory()) {
allDeletesSucceeded &= deleteDir(entries[i]);
for (File entrie : entries) {
Cousjava marked this conversation as resolved.
Show resolved Hide resolved
if (entrie.isDirectory()) {
allDeletesSucceeded &= deleteDir(entrie);
} else {
if ( ! entries[i].equals(StaleFileManager.Util.markerFile(archive))) {
final boolean fileDeleteOK = FileUtils.deleteFileWithWaitLoop(entries[i]);
if (!entrie.equals(StaleFileManager.Util.markerFile(archive))) {
final boolean fileDeleteOK = FileUtils.deleteFileWithWaitLoop(entrie);
if (fileDeleteOK) {
myStaleFileManager().recordDeletedEntry(entries[i]);
myStaleFileManager().recordDeletedEntry(entrie);
}
allDeletesSucceeded &= fileDeleteOK;
}
Expand Down Expand Up @@ -799,15 +813,15 @@ public static void markDeletedArchive(final File archiveFile) {
return;
}

final URI archiveURI = archiveFile.toURI();
final Path archivePath = archiveFile.toPath();
PrintStream ps = null;
try {
ps = new PrintStream(markerFile(archiveFile));
} catch (FileNotFoundException ex) {
throw new RuntimeException(ex);
}
for ( ; staleFileIt.hasNext(); ) {
Cousjava marked this conversation as resolved.
Show resolved Hide resolved
final URI relativeURI = archiveURI.relativize(staleFileIt.next().toURI());
final Path relativeURI = archivePath.relativize(staleFileIt.next().toPath());
ps.println(relativeURI);
deplLogger.log(DEBUG_LEVEL, "FileArchive.StaleFileManager recording left-over file {0}", relativeURI);
}
Expand Down Expand Up @@ -939,15 +953,15 @@ public void flush() {
*/
private static class StaleFileManagerImpl implements StaleFileManager {

private final static String LINE_SEP = System.getProperty("line.separator");
private final static String LINE_SEP = System.lineSeparator();
private final File archiveFile;
private final URI archiveURI;
private final Path archivePath;
private final Collection<String> staleEntryNames;
private final File markerFile;

private StaleFileManagerImpl(final File archive) throws FileNotFoundException, IOException {
archiveFile = archive;
archiveURI = archive.toURI();
archivePath = archive.toPath();
markerFile = StaleFileManager.Util.markerFile(archive);
staleEntryNames = readStaleEntryNames(markerFile);
}
Expand All @@ -964,13 +978,11 @@ private static Collection<String> readStaleEntryNames(final File markerFile) thr
if ( ! markerFile.exists()) {
return result;
}
LineNumberReader reader = null;
try {
reader = new LineNumberReader(new FileReader(markerFile));
try (LineNumberReader reader = new LineNumberReader(new FileReader(markerFile))) {

// Avoid some work if logging is coarser than FINE.
final boolean isShowEntriesToBeSkipped = deplLogger.isLoggable(DEBUG_LEVEL);
final StringBuffer entriesToSkip = isShowEntriesToBeSkipped ? new StringBuffer() : null;
final StringBuilder entriesToSkip = isShowEntriesToBeSkipped ? new StringBuilder() : null;
String line;
while ((line = reader.readLine()) != null) {
result.add(line);
Expand All @@ -983,10 +995,6 @@ private static Collection<String> readStaleEntryNames(final File markerFile) thr
new Object[] {LINE_SEP, entriesToSkip.toString()});
}
return result;
} finally {
if (reader != null) {
reader.close();
}
}
}

Expand All @@ -998,12 +1006,11 @@ public boolean isEntryValid(final File f, final boolean isLogging) {

@Override
public boolean isEntryValid(final File f, final boolean isLogging, final Logger logger) {
final boolean result = ( ! isEntryMarkerFile(f)) &&
( ! staleEntryNames.contains(archiveURI.relativize(f.toURI()).getPath()));
if ( ! result && ! isEntryMarkerFile(f) && isLogging) {
final boolean result = ( ! isEntryMarkerFile(f)) && ( !staleEntryNames.contains(archivePath.relativize(f.toPath()).toString()));
if (!result && !isEntryMarkerFile(f) && isLogging) {
deplLogger.log(Level.WARNING,
STALE_FILES_SKIPPED,
new Object[] {archiveURI.relativize(f.toURI()).toASCIIString(), archiveFile.getAbsolutePath()});
new Object[] {archivePath.relativize(f.toPath()).toString(), archiveFile.getAbsolutePath()});
}
return result;
}
Expand Down Expand Up @@ -1057,7 +1064,7 @@ public void recordDeletedEntry(File f) {
}

private boolean isStaleEntryInDir(final File dir) {
final String dirURIPath = archiveURI.relativize(dir.toURI()).getPath();
final String dirURIPath = archivePath.relativize(dir.toPath()).toString();
for (String staleEntryName : staleEntryNames) {
if (staleEntryName.startsWith(dirURIPath) && ! staleEntryName.equals(dirURIPath)) {
deplLogger.log(DEBUG_LEVEL, "FileArchive.StaleFileManager.isStaleEntryInDir found remaining stale entry {0} in {1}",
Expand All @@ -1074,7 +1081,7 @@ private boolean updateStaleEntry(File f, final String msg) {
return false;
}

final String entryName = archiveURI.relativize(f.toURI()).toASCIIString();
final String entryName = archivePath.relativize(f.toPath()).toString();
final boolean wasStale = staleEntryNames.remove(entryName);
if (wasStale) {
deplLogger.log(DEBUG_LEVEL, msg,
Expand Down
Expand Up @@ -37,6 +37,7 @@
* only if the new code is made subject to such option by the copyright
* holder.
*/
// Portions Copyright [2019] Payara Foundation and/or affiliates

package com.sun.enterprise.deploy.shared;

Expand Down Expand Up @@ -79,7 +80,7 @@ public class FileArchiveTest {

public static final Logger deplLogger = org.glassfish.deployment.common.DeploymentContextImpl.deplLogger;

private final static String LINE_SEP = System.getProperty("line.separator");
private final static String LINE_SEP = System.lineSeparator();
private final static String STALE_ENTRY = "oldLower/oldFile.txt";
private final static String SUBARCHIVE_NAME = "subarch";

Expand Down