package org.tmatesoft.svn.core.wc2;
import java.io.File;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Set;
import java.util.logging.Level;
import org.tmatesoft.svn.core.ISVNCanceller;
import org.tmatesoft.svn.core.SVNCancelException;
import org.tmatesoft.svn.core.SVNErrorCode;
import org.tmatesoft.svn.core.SVNErrorMessage;
import org.tmatesoft.svn.core.SVNException;
import org.tmatesoft.svn.core.SVNProperty;
import org.tmatesoft.svn.core.auth.ISVNAuthenticationManager;
import org.tmatesoft.svn.core.internal.db.SVNSqlJetDb.Mode;
import org.tmatesoft.svn.core.internal.wc.SVNErrorManager;
import org.tmatesoft.svn.core.internal.wc.SVNExternal;
import org.tmatesoft.svn.core.internal.wc.SVNFileType;
import org.tmatesoft.svn.core.internal.wc.SVNFileUtil;
import org.tmatesoft.svn.core.internal.wc.admin.SVNAdminArea;
import org.tmatesoft.svn.core.internal.wc.admin.SVNAdminAreaFactory;
import org.tmatesoft.svn.core.internal.wc.admin.SVNVersionedProperties;
import org.tmatesoft.svn.core.internal.wc.admin.SVNWCAccess;
import org.tmatesoft.svn.core.internal.wc17.SVNExternalsStore;
import org.tmatesoft.svn.core.internal.wc17.SVNWCContext;
import org.tmatesoft.svn.core.internal.wc17.db.ISVNWCDb;
import org.tmatesoft.svn.core.internal.wc17.db.ISVNWCDb.SVNWCDbKind;
import org.tmatesoft.svn.core.internal.wc17.db.ISVNWCDb.SVNWCDbOpenMode;
import org.tmatesoft.svn.core.internal.wc17.db.ISVNWCDb.SVNWCDbStatus;
import org.tmatesoft.svn.core.internal.wc17.db.ISVNWCDb.WCDbInfo;
import org.tmatesoft.svn.core.internal.wc17.db.ISVNWCDb.WCDbInfo.InfoField;
import org.tmatesoft.svn.core.internal.wc17.db.SVNWCDb;
import org.tmatesoft.svn.core.internal.wc17.db.SVNWCDb.DirParsedInfo;
import org.tmatesoft.svn.core.internal.wc17.db.SVNWCDbDir;
import org.tmatesoft.svn.core.internal.wc17.db.SVNWCDbRoot;
import org.tmatesoft.svn.core.internal.wc17.db.SvnWcDbPristines;
import org.tmatesoft.svn.core.internal.wc2.ISvnCommitRunner;
import org.tmatesoft.svn.core.internal.wc2.SvnOperationRunner;
import org.tmatesoft.svn.core.internal.wc2.SvnWcGeneration;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryCatImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryCopyRevisionPropertiesImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryCreateImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryDumpImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryFilterImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetAuthorImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetChangedDirectoriesImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetChangedImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetDateImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetDiffImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetFileSizeImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetHistoryImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetInfoImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetLockImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetLogImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetPropertiesImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetPropertyImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetRevisionPropertiesImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetRevisionPropertyImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetTreeImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetUUIDImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryGetYoungestImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryHotCopyImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryInitializeImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryListLocksImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryListTransactionsImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryLoadImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryPackImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryRecoverImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryRemoveLocksImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryRemoveTransactionsImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositorySetUUIDImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositorySyncInfoImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositorySynchronizeImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryUpgradeImpl;
import org.tmatesoft.svn.core.internal.wc2.admin.SvnRepositoryVerifyImpl;
import org.tmatesoft.svn.core.internal.wc2.ng.*;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldAdd;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldAnnotate;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldCanonicalizeUrls;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldCat;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldCheckout;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldCleanup;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldCommit;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldCopy;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldDiff;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldExport;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldGetChangelistPaths;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldGetInfo;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldGetMergeInfo;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldGetProperties;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldGetStatus;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldGetStatusSummary;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldImport;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldList;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldLogMergeInfo;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldMarkReplaced;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldMerge;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldRelocate;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldRemoteCopy;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldRemove;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldResolve;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldRevert;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldSetChangelist;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldSetLock;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldSetProperty;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldSuggestMergeSources;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldSwitch;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldUnlock;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldUpdate;
import org.tmatesoft.svn.core.internal.wc2.old.SvnOldUpgrade;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnNgReposToReposCopy;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteAnnotate;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteCat;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteDiff;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteExport;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteGetInfo;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteGetProperties;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteGetRevisionProperties;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteList;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteLog;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteRemoteDelete;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteRemoteMkDir;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteSetLock;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteSetPropertyImpl;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteSetRevisionProperty;
import org.tmatesoft.svn.core.internal.wc2.remote.SvnRemoteUnlock;
import org.tmatesoft.svn.core.wc.DefaultSVNRepositoryPool;
import org.tmatesoft.svn.core.wc.ISVNEventHandler;
import org.tmatesoft.svn.core.wc.ISVNOptions;
import org.tmatesoft.svn.core.wc.ISVNRepositoryPool;
import org.tmatesoft.svn.core.wc.SVNEvent;
import org.tmatesoft.svn.core.wc.SVNWCUtil;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryCat;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryCopyRevisionProperties;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryCreate;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryDump;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryFilter;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetAuthor;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetChanged;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetChangedDirectories;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetDate;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetDiff;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetFileSize;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetHistory;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetInfo;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetLock;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetLog;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetProperties;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetProperty;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetRevisionProperties;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetRevisionProperty;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetTree;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetUUID;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryGetYoungest;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryHotCopy;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryInitialize;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryListLocks;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryListTransactions;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryLoad;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryPack;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryRecover;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryRemoveLocks;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryRemoveTransactions;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositorySetUUID;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositorySyncInfo;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositorySynchronize;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryUpgrade;
import org.tmatesoft.svn.core.wc2.admin.SvnRepositoryVerify;
import org.tmatesoft.svn.util.SVNLogType;
/**
* Represents factory for the Svn* operations.
* Contains corresponding create*() methods for all supported operations.
* Provides operation options by implementing {@link ISvnOperationOptionsProvider} interface.
* Handles working copy access and provides access to it {@link #getWcContext()}, {@link #isAutoCloseContext()}.
* Has set of working copy utility methods: {@link #getWorkingCopyRoot(File, boolean)}, {@link #isWorkingCopyRoot(File)},
* {@link #isVersionedDirectory(File)}, {@link #detectWcGeneration(File, boolean)},
* {@link #setPrimaryWcGeneration(SvnWcGeneration)}, {@link #isPrimaryWcGenerationOnly()}
*
* @author TMate Software Ltd.
* @version 1.7
*/
public class SvnOperationFactory implements ISvnOperationOptionsProvider {
private Map<Class<?>, List<ISvnOperationRunner<?, SvnOperation<?>>>> anyFormatOperationRunners;
private Map<Class<?>, List<ISvnOperationRunner<?, SvnOperation<?>>>> noneOperationRunners;
private Map<Class<?>, List<ISvnOperationRunner<?, SvnOperation<?>>>> v17OperationRunners;
private Map<Class<?>, List<ISvnOperationRunner<?, SvnOperation<?>>>> v16OperationRunners;
private ISVNAuthenticationManager authenticationManager;
private ISVNCanceller canceller;
private ISVNEventHandler eventHandler;
private ISVNOptions options;
private ISVNRepositoryPool repositoryPool;
private ISvnOperationHandler operationHandler;
private boolean autoCloseContext;
private boolean autoDisposeRepositoryPool;
private SVNWCContext wcContext;
private SvnWcGeneration primaryWcGeneration;
private int runLevel;
private SvnWcGeneration detectedWcGeneration = SvnWcGeneration.NOT_DETECTED;
private boolean isWcGenerationSticky;
/**
* Creates operation factory and initializes it with empty <code>context</code>.
*/
public SvnOperationFactory() {
this(null);
runLevel = 0;
}
/**
* Creates operation factory and initializes it with <code>context</code>.
* If <code>context</code> is set, retrieves its <code>options</code> and <code>eventHandler</code>
* and sets <code>autoCloseContext</code> to <code>false</code>, otherwise
* sets <code>autoCloseContext</code> to <code>true</code>.
*
* @param context operation's context
*/
public SvnOperationFactory(SVNWCContext context) {
wcContext = context;
if (wcContext != null) {
options = wcContext.getOptions();
eventHandler = wcContext.getEventHandler();
}
setAutoCloseContext(wcContext == null);
registerRunners();
}
private void registerRunners() {
v17OperationRunners = new HashMap<Class<?>, List<ISvnOperationRunner<?, SvnOperation<?>>>>();
v16OperationRunners = new HashMap<Class<?>, List<ISvnOperationRunner<?, SvnOperation<?>>>>();
anyFormatOperationRunners = new HashMap<Class<?>, List<ISvnOperationRunner<?, SvnOperation<?>>>>();
noneOperationRunners = new HashMap<Class<?>, List<ISvnOperationRunner<?, SvnOperation<?>>>>();
registerOperationRunner(SvnGetInfo.class, new SvnRemoteGetInfo());
registerOperationRunner(SvnGetInfo.class, new SvnNgGetInfo());
registerOperationRunner(SvnGetInfo.class, new SvnOldGetInfo());
registerOperationRunner(SvnGetProperties.class, new SvnRemoteGetRevisionProperties());
registerOperationRunner(SvnGetProperties.class, new SvnRemoteGetProperties());
registerOperationRunner(SvnGetProperties.class, new SvnNgGetProperties());
registerOperationRunner(SvnGetProperties.class, new SvnOldGetProperties());
registerOperationRunner(SvnGetStatus.class, new SvnNgGetStatus());
registerOperationRunner(SvnGetStatus.class, new SvnOldGetStatus());
registerOperationRunner(SvnCheckout.class, new SvnNgCheckout());
registerOperationRunner(SvnCheckout.class, new SvnOldCheckout());
registerOperationRunner(SvnSwitch.class, new SvnNgSwitch());
registerOperationRunner(SvnSwitch.class, new SvnOldSwitch());
registerOperationRunner(SvnUpdate.class, new SvnNgUpdate());
registerOperationRunner(SvnUpdate.class, new SvnOldUpdate());
registerOperationRunner(SvnExport.class, new SvnRemoteExport());
registerOperationRunner(SvnExport.class, new SvnNgExport());
registerOperationRunner(SvnExport.class, new SvnOldExport());
registerOperationRunner(SvnRelocate.class, new SvnNgRelocate());
registerOperationRunner(SvnRelocate.class, new SvnOldRelocate());
registerOperationRunner(SvnScheduleForAddition.class, new SvnNgAdd());
registerOperationRunner(SvnScheduleForAddition.class, new SvnOldAdd());
registerOperationRunner(SvnScheduleForRemoval.class, new SvnNgRemove());
registerOperationRunner(SvnScheduleForRemoval.class, new SvnOldRemove());
registerOperationRunner(SvnCommit.class, new SvnNgCommit());
registerOperationRunner(SvnCommit.class, new SvnOldCommit());
registerOperationRunner(SvnRevert.class, new SvnNgRevert());
registerOperationRunner(SvnRevert.class, new SvnOldRevert());
registerOperationRunner(SvnMarkReplaced.class, new SvnNgMarkReplaced());
registerOperationRunner(SvnMarkReplaced.class, new SvnOldMarkReplaced());
registerOperationRunner(SvnSetProperty.class, new SvnRemoteSetRevisionProperty());
registerOperationRunner(SvnSetProperty.class, new SvnOldSetProperty());
registerOperationRunner(SvnSetProperty.class, new SvnNgSetProperty());
registerOperationRunner(SvnSetLock.class, new SvnRemoteSetLock());
registerOperationRunner(SvnSetLock.class, new SvnOldSetLock());
registerOperationRunner(SvnSetLock.class, new SvnNgSetLock());
registerOperationRunner(SvnUnlock.class, new SvnRemoteUnlock());
registerOperationRunner(SvnUnlock.class, new SvnOldUnlock());
registerOperationRunner(SvnUnlock.class, new SvnNgUnlock());
registerOperationRunner(SvnCat.class, new SvnRemoteCat());
registerOperationRunner(SvnCat.class, new SvnNgCat());
registerOperationRunner(SvnCat.class, new SvnOldCat());
registerOperationRunner(SvnDiffSummarize.class, new SvnNgDiffSummarize());
registerOperationRunner(SvnCopy.class, new SvnNgWcToWcCopy());
registerOperationRunner(SvnCopy.class, new SvnNgReposToWcCopy());
registerOperationRunner(SvnCopy.class, new SvnOldCopy());
registerOperationRunner(SvnRemoteCopy.class, new SvnOldRemoteCopy());
registerOperationRunner(SvnRemoteCopy.class, new SvnNgWcToReposCopy());
registerOperationRunner(SvnRemoteCopy.class, new SvnNgReposToReposCopy());
registerOperationRunner(SvnLog.class, new SvnRemoteLog());
registerOperationRunner(SvnAnnotate.class, new SvnOldAnnotate());
registerOperationRunner(SvnAnnotate.class, new SvnRemoteAnnotate());
registerOperationRunner(SvnSetChangelist.class, new SvnOldSetChangelist());
registerOperationRunner(SvnSetChangelist.class, new SvnNgSetChangelist());
registerOperationRunner(SvnGetChangelistPaths.class, new SvnOldGetChangelistPaths());
registerOperationRunner(SvnGetChangelistPaths.class, new SvnNgGetChangelistPaths());
registerOperationRunner(SvnRemoteMkDir.class, new SvnRemoteRemoteMkDir());
registerOperationRunner(SvnRemoteDelete.class, new SvnRemoteRemoteDelete());
registerOperationRunner(SvnRemoteSetProperty.class, new SvnRemoteSetPropertyImpl());
registerOperationRunner(SvnMerge.class, new SvnOldMerge());
registerOperationRunner(SvnMerge.class, new SvnNgMergePegged());
registerOperationRunner(SvnMerge.class, new SvnNgMergeReintegrate());
registerOperationRunner(SvnMerge.class, new SvnNgMerge());
registerOperationRunner(SvnDiff.class, new SvnOldDiff());
registerOperationRunner(SvnDiff.class, new SvnNgDiff());
registerOperationRunner(SvnDiff.class, new SvnRemoteDiff());
registerOperationRunner(SvnPatch.class, new SvnNgPatch());
registerOperationRunner(SvnCleanup.class, new SvnOldCleanup());
registerOperationRunner(SvnCleanup.class, new SvnNgCleanup());
registerOperationRunner(SvnImport.class, new SvnOldImport());
registerOperationRunner(SvnResolve.class, new SvnOldResolve());
registerOperationRunner(SvnResolve.class, new SvnNgResolve());
registerOperationRunner(SvnList.class, new SvnOldList());
registerOperationRunner(SvnList.class, new SvnRemoteList());
registerOperationRunner(SvnLogMergeInfo.class, new SvnOldLogMergeInfo());
registerOperationRunner(SvnLogMergeInfo.class, new SvnNgLogMergeInfo());
registerOperationRunner(SvnGetMergeInfo.class, new SvnOldGetMergeInfo());
registerOperationRunner(SvnGetMergeInfo.class, new SvnNgGetMergeInfo());
registerOperationRunner(SvnSuggestMergeSources.class, new SvnNgSuggestMergeSources());
registerOperationRunner(SvnSuggestMergeSources.class, new SvnOldSuggestMergeSources());
registerOperationRunner(SvnCanonicalizeUrls.class, new SvnNgCanonicalizeUrls());
registerOperationRunner(SvnCanonicalizeUrls.class, new SvnOldCanonicalizeUrls());
registerOperationRunner(SvnRepositoryDump.class, new SvnRepositoryDumpImpl());
registerOperationRunner(SvnRepositoryCreate.class, new SvnRepositoryCreateImpl());
registerOperationRunner(SvnRepositoryHotCopy.class, new SvnRepositoryHotCopyImpl());
registerOperationRunner(SvnRepositoryLoad.class, new SvnRepositoryLoadImpl());
registerOperationRunner(SvnRepositoryListLocks.class, new SvnRepositoryListLocksImpl());
registerOperationRunner(SvnRepositoryListTransactions.class, new SvnRepositoryListTransactionsImpl());
registerOperationRunner(SvnRepositoryPack.class, new SvnRepositoryPackImpl());
registerOperationRunner(SvnRepositoryRecover.class, new SvnRepositoryRecoverImpl());
registerOperationRunner(SvnRepositoryRemoveLocks.class, new SvnRepositoryRemoveLocksImpl());
registerOperationRunner(SvnRepositoryRemoveTransactions.class, new SvnRepositoryRemoveTransactionsImpl());
registerOperationRunner(SvnRepositorySetUUID.class, new SvnRepositorySetUUIDImpl());
registerOperationRunner(SvnRepositoryUpgrade.class, new SvnRepositoryUpgradeImpl());
registerOperationRunner(SvnRepositoryVerify.class, new SvnRepositoryVerifyImpl());
registerOperationRunner(SvnRepositoryInitialize.class, new SvnRepositoryInitializeImpl());
registerOperationRunner(SvnRepositorySyncInfo.class, new SvnRepositorySyncInfoImpl());
registerOperationRunner(SvnRepositoryCopyRevisionProperties.class, new SvnRepositoryCopyRevisionPropertiesImpl());
registerOperationRunner(SvnRepositorySynchronize.class, new SvnRepositorySynchronizeImpl());
registerOperationRunner(SvnRepositoryFilter.class, new SvnRepositoryFilterImpl());
registerOperationRunner(SvnRepositoryGetAuthor.class, new SvnRepositoryGetAuthorImpl());
registerOperationRunner(SvnRepositoryGetDate.class, new SvnRepositoryGetDateImpl());
registerOperationRunner(SvnRepositoryGetInfo.class, new SvnRepositoryGetInfoImpl());
registerOperationRunner(SvnRepositoryGetLock.class, new SvnRepositoryGetLockImpl());
registerOperationRunner(SvnRepositoryGetLog.class, new SvnRepositoryGetLogImpl());
registerOperationRunner(SvnRepositoryGetUUID.class, new SvnRepositoryGetUUIDImpl());
registerOperationRunner(SvnRepositoryGetYoungest.class, new SvnRepositoryGetYoungestImpl());
registerOperationRunner(SvnRepositoryGetProperty.class, new SvnRepositoryGetPropertyImpl());
registerOperationRunner(SvnRepositoryGetRevisionProperty.class, new SvnRepositoryGetRevisionPropertyImpl());
registerOperationRunner(SvnRepositoryGetProperties.class, new SvnRepositoryGetPropertiesImpl());
registerOperationRunner(SvnRepositoryGetRevisionProperties.class, new SvnRepositoryGetRevisionPropertiesImpl());
registerOperationRunner(SvnRepositoryCat.class, new SvnRepositoryCatImpl());
registerOperationRunner(SvnRepositoryGetChanged.class, new SvnRepositoryGetChangedImpl());
registerOperationRunner(SvnRepositoryGetChangedDirectories.class, new SvnRepositoryGetChangedDirectoriesImpl());
registerOperationRunner(SvnRepositoryGetDiff.class, new SvnRepositoryGetDiffImpl());
registerOperationRunner(SvnRepositoryGetHistory.class, new SvnRepositoryGetHistoryImpl());
registerOperationRunner(SvnRepositoryGetTree.class, new SvnRepositoryGetTreeImpl());
registerOperationRunner(SvnRepositoryGetFileSize.class, new SvnRepositoryGetFileSizeImpl());
registerOperationRunner(SvnUpgrade.class, new SvnOldUpgrade());
registerOperationRunner(SvnUpgrade.class, new SvnNgUpgrade());
registerOperationRunner(SvnGetStatusSummary.class, new SvnOldGetStatusSummary());
registerOperationRunner(SvnGetStatusSummary.class, new SvnNgGetStatusSummary());
}
/**
* Returns whether to dispose context when operation finishes.
*
* @return <code>true</code> if the context should be disposed, otherwise <code>false</code>
*/
public boolean isAutoCloseContext() {
return autoCloseContext;
}
/**
* Sets whether to dispose context when operation finishes.
*
* @param autoCloseContext <code>true</code> if the context should be disposed, otherwise <code>false</code>
*/
public void setAutoCloseContext(boolean autoCloseContext) {
this.autoCloseContext = autoCloseContext;
}
/**
* Gets operation's authentication manager.
* If not set, creates default authentication manager.
*
* @return authentication manager
*/
public ISVNAuthenticationManager getAuthenticationManager() {
if (authenticationManager == null) {
authenticationManager = SVNWCUtil.createDefaultAuthenticationManager();
}
return authenticationManager;
}
/**
* Gets the cancel handler of the operation.
* If client's <code>canceler</code> is not set,
* returns <code>eventHandler</code> as a canceler.
*
* @return cancel handler
*/
public ISVNCanceller getCanceller() {
if (canceller == null && getEventHandler() != null) {
return getEventHandler();
}
return canceller;
}
/**
* Gets the event handler for the operation. This event handler will be
* dispatched {@link SVNEvent} objects to provide detailed information about
* actions and progress state of version control operations.
* If <code>wcContext</code> is set, returns {@link SVNWCContext#getEventHandler()}
*
* @return handler for events
* @see ISVNEventHandler
*/
public ISVNEventHandler getEventHandler() {
if (getWcContext() != null) {
return getWcContext().getEventHandler();
}
return eventHandler;
}
/**
* Get a callback that is called before and after each operation
* @return a callback that is called before and after each operation
*/
public ISvnOperationHandler getOperationHandler() {
if (operationHandler == null) {
operationHandler = ISvnOperationHandler.NOOP;
}
return operationHandler;
}
/**
* Gets the pool of repositories.
* If pool is not created, creates {@link DefaultSVNRepositoryPool}
* with the authentication manager, options, and <code>autoDisposeRepositoryPool</code> = <code>true</code>.
*
* @return pool of repositories
*/
public ISVNRepositoryPool getRepositoryPool() {
if (repositoryPool == null) {
repositoryPool = new DefaultSVNRepositoryPool(getAuthenticationManager(), getOptions());
setAutoDisposeRepositoryPool(true);
}
return repositoryPool;
}
/**
* Gets operation's options.
* If options are not set, creates default readonly options.
*
* @return options of the operation
*/
public ISVNOptions getOptions() {
if (options == null) {
options = SVNWCUtil.createDefaultOptions(true);
}
return options;
}
/**
* Sets operation's authentication manager.
* If <code>repositoryPool</code> is set, set its authentication manager to this value.
*
* @param authenticationManager authentication manager
*/
public void setAuthenticationManager(ISVNAuthenticationManager authenticationManager) {
this.authenticationManager = authenticationManager;
if (repositoryPool != null) {
repositoryPool.setAuthenticationManager(authenticationManager);
}
}
/**
* Sets the cancel handler of the operation.
*
* @param canceller cancel handler
*/
public void setCanceller(ISVNCanceller canceller) {
this.canceller = canceller;
}
/**
* Sets the event handler for the operation. This event handler will be
* dispatched {@link SVNEvent} objects to provide detailed information about
* actions and progress state of version control operations.
* If <code>wcContext</code> is set, sets its event handler to this one.
* If <code>wcContext</code> is not set, disposes it.
*
* @param eventHandler handler for events
* @see ISVNEventHandler
*/
public void setEventHandler(ISVNEventHandler eventHandler) {
this.eventHandler = eventHandler;
if (this.wcContext != null) {
this.wcContext.setEventHandler(eventHandler);
} else {
disposeWcContext();
}
}
/**
* Sets operation's options and disposes working copy context.
*
* @param options options of the operation
*/
public void setOptions(ISVNOptions options) {
this.options = options;
disposeWcContext();
}
/**
* Sets pool of repositories.
* If <code>repositoryPool</code> is not <code>null</code>sets <code>autoDisposeRepositoryPool</code> to <code>false</code>,
* otherwise to <code>true</code>
*
* @param repositoryPool pool of repositories
*/
public void setRepositoryPool(ISVNRepositoryPool repositoryPool) {
this.repositoryPool = repositoryPool;
setAutoDisposeRepositoryPool(repositoryPool == null);
}
/**
* Sets a callback that is called before and after each operation
* @param operationHandler callback to call before and after operation
*/
public void setOperationHandler(ISvnOperationHandler operationHandler) {
this.operationHandler = operationHandler;
}
/**
* Disposes context and repository pool if needed.
*/
public void dispose() {
disposeWcContext();
if (isAutoDisposeRepositoryPool() && repositoryPool != null) {
repositoryPool.dispose();
}
}
/**
* Creates annotate operation.
* @return new <code>SvnAnnotate</code> object
*/
public SvnAnnotate createAnnotate() {
return new SvnAnnotate(this);
}
/**
* Creates cat operation.
* @return new <code>SvnCat</code> object
*/
public SvnCat createCat() {
return new SvnCat(this);
}
/**
* Creates import operation.
* @return new <code>SvnImport</code> object
*/
public SvnImport createImport() {
return new SvnImport(this);
}
/**
* Creates copy operation.
* @return new <code>SvnCat</code> object
*/
public SvnCopy createCopy() {
return new SvnCopy(this);
}
/**
* Creates remote copy operation.
* @return new <code>SvnRemoteCopy</code> object
*/
public SvnRemoteCopy createRemoteCopy() {
return new SvnRemoteCopy(this);
}
/**
* Creates remote make directory operation.
* @return new <code>SvnRemoteMkDir</code> object
*/
public SvnRemoteMkDir createRemoteMkDir() {
return new SvnRemoteMkDir(this);
}
/**
* Creates remote set property operation.
* @return new <code>SvnRemoteSetProperty</code> object
*/
public SvnRemoteSetProperty createRemoteSetProperty() {
return new SvnRemoteSetProperty(this);
}
/**
* Creates set changelist operation.
* @return new <code>SvnSetChangelist</code> object
*/
public SvnSetChangelist createSetChangelist() {
return new SvnSetChangelist(this);
}
/**
* Creates get changelist paths operation.
* @return new <code>SvnGetChangelistPaths</code> object
*/
public SvnGetChangelistPaths createGetChangelistPaths() {
return new SvnGetChangelistPaths(this);
}
/**
* Creates set lock operation.
* @return new <code>SvnSetLock</code> object
*/
public SvnSetLock createSetLock() {
return new SvnSetLock(this);
}
/**
* Creates unlock operation.
* @return new <code>SvnUnlock</code> object
*/
public SvnUnlock createUnlock() {
return new SvnUnlock(this);
}
/**
* Creates upgrade operation.
* @return new <code>SvnUpgrade</code> object
*/
public SvnUpgrade createUpgrade() {
return new SvnUpgrade(this);
}
/**
* Creates get info operation.
* @return new <code>SvnGetInfo</code> object
*/
public SvnGetInfo createGetInfo() {
return new SvnGetInfo(this);
}
/**
* Creates get properties operation.
* @return new <code>SvnGetProperties</code> object
*/
public SvnGetProperties createGetProperties() {
return new SvnGetProperties(this);
}
/**
* Creates get status operation.
* @return new <code>SvnGetStatus</code> object
*/
public SvnGetStatus createGetStatus() {
return new SvnGetStatus(this);
}
/**
* Creates update operation.
* @return new <code>SvnUpdate</code> object
*/
public SvnUpdate createUpdate() {
return new SvnUpdate(this);
}
/**
* Creates switch operation.
* @return new <code>SvnSwitch</code> object
*/
public SvnSwitch createSwitch() {
return new SvnSwitch(this);
}
/**
* Creates checkout operation.
* @return new <code>SvnCheckout</code> object
*/
public SvnCheckout createCheckout() {
return new SvnCheckout(this);
}
/**
* Creates relocate operation.
* @return new <code>SvnRelocate</code> object
*/
public SvnRelocate createRelocate() {
return new SvnRelocate(this);
}
/**
* Creates export operation.
* @return new <code>SvnExport</code> object
*/
public SvnExport createExport() {
return new SvnExport(this);
}
/**
* Creates add operation.
* @return new <code>SvnScheduleForAddition</code> object
*/
public SvnScheduleForAddition createScheduleForAddition() {
return new SvnScheduleForAddition(this);
}
/**
* Creates commit operation.
* @return new <code>SvnCommit</code> object
*/
public SvnCommit createCommit() {
return new SvnCommit(this);
}
/**
* Creates delete operation.
* @return new <code>SvnScheduleForRemoval</code> object
*/
public SvnScheduleForRemoval createScheduleForRemoval() {
return new SvnScheduleForRemoval(this);
}
/**
* Creates mark replaced operation.
* @return new <code>SvnMarkReplaced</code> object
*/
public SvnMarkReplaced createMarkReplaced() {
return new SvnMarkReplaced(this);
}
/**
* Creates revert operation.
* @return new <code>SvnRevert</code> object
*/
public SvnRevert createRevert() {
return new SvnRevert(this);
}
/**
* Creates set property operation.
* @return new <code>SvnSetProperty</code> object
*/
public SvnSetProperty createSetProperty() {
return new SvnSetProperty(this);
}
/**
* Creates log operation.
* @return new <code>SvnLog</code> object
*/
public SvnLog createLog() {
return new SvnLog(this);
}
/**
* Creates remote make directory operation.
* @return new <code>SvnRemoteMkDir</code> object
*/
public SvnRemoteMkDir createMkDir() {
return new SvnRemoteMkDir(this);
}
/**
* Creates remote delete operation.
* @return new <code>SvnRemoteDelete</code> object
*/
public SvnRemoteDelete createRemoteDelete() {
return new SvnRemoteDelete(this);
}
/**
* Creates merge operation.
* @return new <code>SvnMerge</code> object
*/
public SvnMerge createMerge() {
return new SvnMerge(this);
}
/**
* Creates diff operation.
* @return new <code>SvnDiff</code> object
*/
public SvnDiff createDiff() {
return new SvnDiff(this);
}
/**
* Creates patch operation.
* @return new <code>SvnPatch</code> object
*/
public SvnPatch createPatch() {
return new SvnPatch(this);
}
/**
* Creates diff summarize operation.
* @return new <code>SvnDiffSummarize</code> object
*/
public SvnDiffSummarize createDiffSummarize() {
return new SvnDiffSummarize(this);
}
/**
* Creates suggest merge sources operation.
* @return new <code>SvnSuggestMergeSources</code> object
*/
public SvnSuggestMergeSources createSuggestMergeSources() {
return new SvnSuggestMergeSources(this);
}
/**
* Creates get merge info operation.
* @return new <code>SvnGetMergeInfo</code> object
*/
public SvnGetMergeInfo createGetMergeInfo() {
return new SvnGetMergeInfo(this);
}
/**
* Creates log merge info operation.
* @return new <code>SvnLogMergeInfo</code> object
*/
public SvnLogMergeInfo createLogMergeInfo() {
return new SvnLogMergeInfo(this);
}
/**
* Creates resolve operation.
* @return new <code>SvnResolve</code> object
*/
public SvnResolve createResolve() {
return new SvnResolve(this);
}
/**
* Creates cleanup operation.
* @return new <code>SvnCleanup</code> object
*/
public SvnCleanup createCleanup() {
return new SvnCleanup(this);
}
/**
* Creates list operation.
* @return new <code>SvnList</code> object
*/
public SvnList createList() {
return new SvnList(this);
}
/**
* Creates canonicalize URLs operation.
* @return new <code>SvnCanonicalizeUrls</code> object
*/
public SvnCanonicalizeUrls createCanonicalizeUrls() {
return new SvnCanonicalizeUrls(this);
}
/**
* Creates repository dump administrative operation.
* @return new <code>SvnRepositoryDump</code> object
*/
public SvnRepositoryDump createRepositoryDump() {
return new SvnRepositoryDump(this);
}
/**
* Creates repository create administrative operation.
* @return new <code>SvnRepositoryCreate</code> object
*/
public SvnRepositoryCreate createRepositoryCreate() {
return new SvnRepositoryCreate(this);
}
/**
* Creates repository hot copy administrative operation.
* @return new <code>SvnRepositoryHotCopy</code> object
*/
public SvnRepositoryHotCopy createRepositoryHotCopy() {
return new SvnRepositoryHotCopy(this);
}
/**
* Creates repository load administrative operation.
* @return new <code>SvnRepositoryLoad</code> object
*/
public SvnRepositoryLoad createRepositoryLoad() {
return new SvnRepositoryLoad(this);
}
/**
* Creates administrative operation for retrieving list of locks from the repository.
* @return new <code>SvnRepositoryListLocks</code> object
*/
public SvnRepositoryListLocks createRepositoryListLocks() {
return new SvnRepositoryListLocks(this);
}
/**
* Creates administrative operation for retrieving list of transactions from the repository.
* @return new <code>SvnRepositoryListTransactions</code> object
*/
public SvnRepositoryListTransactions createRepositoryListTransactions() {
return new SvnRepositoryListTransactions(this);
}
/**
* Creates repository pack administrative operation.
* @return new <code>SvnRepositoryPack</code> object
*/
public SvnRepositoryPack createRepositoryPack() {
return new SvnRepositoryPack(this);
}
/**
* Creates repository recover administrative operation.
* @return new <code>SvnRepositoryRecover</code> object
*/
public SvnRepositoryRecover createRepositoryRecover() {
return new SvnRepositoryRecover(this);
}
/**
* Creates repository remove locks administrative operation.
* @return new <code>SvnRepositoryRemoveLocks</code> object
*/
public SvnRepositoryRemoveLocks createRepositoryRemoveLocks() {
return new SvnRepositoryRemoveLocks(this);
}
/**
* Creates repository remove transactions administrative operation.
* @return new <code>SvnRepositoryRemoveTransactions</code> object
*/
public SvnRepositoryRemoveTransactions createRepositoryRemoveTransactions() {
return new SvnRepositoryRemoveTransactions(this);
}
/**
* Creates repository set UUID administrative operation.
* @return new <code>SvnRepositorySetUUID</code> object
*/
public SvnRepositorySetUUID createRepositorySetUUID() {
return new SvnRepositorySetUUID(this);
}
/**
* Creates repository upgrade administrative operation.
* @return new <code>SvnRepositoryUpgrade</code> object
*/
public SvnRepositoryUpgrade createRepositoryUpgrade() {
return new SvnRepositoryUpgrade(this);
}
/**
* Creates repository verify administrative operation.
* @return new <code>SvnRepositoryVerify</code> object
*/
public SvnRepositoryVerify createRepositoryVerify() {
return new SvnRepositoryVerify(this);
}
/**
* Creates initialize synchronization operation.
* @return new <code>SvnRepositoryInitialize</code> object
*/
public SvnRepositoryInitialize createRepositoryInitialize() {
return new SvnRepositoryInitialize(this);
}
/**
* Creates operation for retrieving repository synchronization info.
* @return new <code>SvnRepositorySyncInfo</code> object
*/
public SvnRepositorySyncInfo createRepositorySyncInfo() {
return new SvnRepositorySyncInfo(this);
}
/**
* Creates copy revision properties synchronization operation.
* @return new <code>SvnRepositoryCopyRevisionProperties</code> object
*/
public SvnRepositoryCopyRevisionProperties createRepositoryCopyRevisionProperties() {
return new SvnRepositoryCopyRevisionProperties(this);
}
/**
* Creates repository synchronize operation.
* @return new <code>SvnRepositorySynchronize</code> object
*/
public SvnRepositorySynchronize createRepositorySynchronize() {
return new SvnRepositorySynchronize(this);
}
/**
* Creates dumpfilter operation.
* @return new <code>SvnRepositoryFilter</code> object
*/
public SvnRepositoryFilter createRepositoryFilter() {
return new SvnRepositoryFilter(this);
}
/**
* Creates operation for retrieving author from the repository.
* @return new <code>SvnRepositoryGetAuthor</code> object
*/
public SvnRepositoryGetAuthor createRepositoryGetAuthor() {
return new SvnRepositoryGetAuthor(this);
}
/**
* Creates operation for retrieving date from the repository.
* @return new <code>SvnRepositoryGetDate</code> object
*/
public SvnRepositoryGetDate createRepositoryGetDate() {
return new SvnRepositoryGetDate(this);
}
/**
* Creates operation for retrieving info from the repository.
* @return new <code>SvnRepositoryGetInfo</code> object
*/
public SvnRepositoryGetInfo createRepositoryGetInfo() {
return new SvnRepositoryGetInfo(this);
}
/**
* Creates operation for retrieving the lock from the repository.
* @return new <code>SvnRepositoryGetLock</code> object
*/
public SvnRepositoryGetLock createRepositoryGetLock() {
return new SvnRepositoryGetLock(this);
}
/**
* Creates operation for retrieving repository log.
* @return new <code>SvnRepositoryGetLog</code> object
*/
public SvnRepositoryGetLog createRepositoryGetLog() {
return new SvnRepositoryGetLog(this);
}
/**
* Creates operation for retrieving repository UUID.
* @return new <code>SvnRepositoryGetUUID</code> object
*/
public SvnRepositoryGetUUID createRepositoryGetUUID() {
return new SvnRepositoryGetUUID(this);
}
/**
* Creates operation for retrieving the latest revision from the repository.
* @return new <code>SvnRepositoryGetYoungest</code> object
*/
public SvnRepositoryGetYoungest createRepositoryGetYoungest() {
return new SvnRepositoryGetYoungest(this);
}
/**
* Creates operation for retrieving property from the repository.
* @return new <code>SvnRepositoryGetProperty</code> object
*/
public SvnRepositoryGetProperty createRepositoryGetProperty() {
return new SvnRepositoryGetProperty(this);
}
/**
* Creates operation for retrieving revision property from the repository.
* @return new <code>SvnRepositoryGetRevisionProperty</code> object
*/
public SvnRepositoryGetRevisionProperty createRepositoryGetRevisionProperty() {
return new SvnRepositoryGetRevisionProperty(this);
}
/**
* Creates operation for retrieving properties from the repository.
* @return new <code>SvnRepositoryGetProperties</code> object
*/
public SvnRepositoryGetProperties createRepositoryGetProperties() {
return new SvnRepositoryGetProperties(this);
}
/**
* Creates operation for retrieving file contents from the repository.
* @return new <code>SvnRepositoryCat</code> object
*/
public SvnRepositoryCat createRepositoryGetCat() {
return new SvnRepositoryCat(this);
}
/**
* Creates operation for retrieving changed paths from the repository.
* @return new <code>SvnRepositoryGetChanged</code> object
*/
public SvnRepositoryGetChanged createRepositoryGetChanged() {
return new SvnRepositoryGetChanged(this);
}
/**
* Creates operation for retrieving changed directories from the repository.
* @return new <code>SvnRepositoryGetChangedDirectories</code> object
*/
public SvnRepositoryGetChangedDirectories createRepositoryGetChangedDirectories() {
return new SvnRepositoryGetChangedDirectories(this);
}
/**
* Creates repository diff operation.
* @return new <code>SvnRepositoryGetDiff</code> object
*/
public SvnRepositoryGetDiff createRepositoryGetDiff() {
return new SvnRepositoryGetDiff(this);
}
/**
* Creates operation for retrieving the history from the repository.
* @return new <code>SvnRepositoryGetHistory</code> object
*/
public SvnRepositoryGetHistory createRepositoryGetHistory() {
return new SvnRepositoryGetHistory(this);
}
/**
* Creates operation for retrieving items tree from the repository.
* @return new <code>SvnRepositoryGetTree</code> object
*/
public SvnRepositoryGetTree createRepositoryGetTree() {
return new SvnRepositoryGetTree(this);
}
/**
* Creates operation for retrieving revision properties from the repository.
* @return new <code>SvnRepositoryGetRevisionProperties</code> object
*/
public SvnRepositoryGetRevisionProperties createRepositoryGetRevisionProperties() {
return new SvnRepositoryGetRevisionProperties(this);
}
/**
* Creates operation for retrieving file size from the repository
* @return new <code>SvnRepositoryGetFileSize</code> object
*/
public SvnRepositoryGetFileSize createGetRepositoryFileSize() {
return new SvnRepositoryGetFileSize(this);
}
/**
* Creates get status summary operation.
* @return new <code>SvnStatusSummary</code> object
*/
public SvnGetStatusSummary createGetStatusSummary() {
return new SvnGetStatusSummary(this);
}
public SvnSetWCDbVersion createSetWCDbVersion() {
return new SvnSetWCDbVersion(this);
}
/**
* Sets whether to dispose repository pool on {@link #dispose()} call.
* This flag has sense only if <code>repositoryPool</code> field is not <code>null</code>.
* Otherwise the flag value can be overwritten by {@link #setRepositoryPool(ISVNRepositoryPool)} or
* {@link #getRepositoryPool()} calls.
* @param dispose whether to dispose repository pool on {@link #dispose()} call
*/
public void setAutoDisposeRepositoryPool(boolean dispose) {
autoDisposeRepositoryPool = dispose;
}
protected Object run(SvnOperation<?> operation) throws SVNException {
ISvnOperationRunner<?, SvnOperation<?>> runner = getImplementation(operation);
if (runner != null) {
SVNWCContext wcContext = null;
runLevel++;
try {
wcContext = obtainWcContext(operation);
if (runLevel == 1 && wcContext != null) {
wcContext.setSqliteJournalMode(operation.getSqliteJournalMode());
}
runner.setWcContext(wcContext);
getOperationHandler().beforeOperation(operation);
Object result = runner.run(operation);
getOperationHandler().afterOperationSuccess(operation);
assertRefCount(operation, wcContext);
return result;
} catch (SVNException e) {
getOperationHandler().afterOperationFailure(operation);
throw e;
} finally {
runLevel--;
if (runLevel == 0) {
if (wcContext != null) {
wcContext.setSqliteJournalMode(null);
}
releaseWcContext(wcContext);
}
}
}
return null;
}
private void releaseWcContext(SVNWCContext wcContext) throws SVNException {
// check is wcContext is empty of unfinished transactions
if (wcContext != null) {
wcContext.ensureNoUnfinishedTransactions();
}
if (isAutoCloseContext() && wcContext != null) {
if (this.wcContext == wcContext) {
disposeWcContext();
} else {
wcContext.close();
}
}
}
private SVNWCContext obtainWcContext(SvnOperation<?> operation) {
if (wcContext == null) {
wcContext = new SVNWCContext(SVNWCDbOpenMode.ReadWrite, getOptions(), false, true, getEventHandler());
}
wcContext.setOperation(operation);
return wcContext;
}
private void disposeWcContext() {
if (wcContext != null) {
wcContext.close();
wcContext = null;
}
}
private boolean isAutoDisposeRepositoryPool() {
return autoDisposeRepositoryPool;
}
protected ISvnOperationRunner<?, SvnOperation<?>> getImplementation(SvnOperation<?> operation) throws SVNException {
if (operation == null) {
return null;
}
final boolean isAdditionMode = operation.getClass() == SvnScheduleForAddition.class;
SvnWcGeneration wcGeneration = SvnWcGeneration.NOT_DETECTED;
if (operation.getOperationalWorkingCopy() != null) {
if (isWcGenerationSticky && detectedWcGeneration != SvnWcGeneration.NOT_DETECTED) {
wcGeneration = detectedWcGeneration;
} else {
if (operation.getClass() == SvnCheckout.class) {
if (SVNWCUtil.isVersionedDirectory(operation.getOperationalWorkingCopy())) {
wcGeneration = detectWcGeneration(operation.getOperationalWorkingCopy(), false, isAdditionMode);
} else {
SvnCheckout checkout = (SvnCheckout) operation;
final int targetWorkingCopyFormat = checkout.getTargetWorkingCopyFormat();
if (targetWorkingCopyFormat > 0) {
if (targetWorkingCopyFormat >= SVNWCContext.WC_NG_VERSION) {
wcGeneration = SvnWcGeneration.V17;
} else {
wcGeneration = SvnWcGeneration.V16;
}
} else {
wcGeneration = getPrimaryWcGeneration();
}
}
} else {
wcGeneration = detectWcGeneration(operation.getOperationalWorkingCopy(), false, isAdditionMode);
}
}
if (isWcGenerationSticky && wcGeneration != SvnWcGeneration.NOT_DETECTED) {
detectedWcGeneration = wcGeneration;
}
}
if (wcGeneration == SvnWcGeneration.V16 && isPrimaryWcGenerationOnly() && operation.getClass() != SvnUpgrade.class) {
File wcPath = operation.getOperationalWorkingCopy();
int format = SVNAdminAreaFactory.checkWC(wcPath, true);
if (format > 0) {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.WC_UPGRADE_REQUIRED, "Working copy ''{0}'' is too old (format {1}, created by Subversion 1.6)",
new Object[] {wcPath, new Integer(format)});
SVNErrorManager.error(err, SVNLogType.WC);
}
}
final List<ISvnOperationRunner<?, SvnOperation<?>>> candidateRunners = new LinkedList<ISvnOperationRunner<?, SvnOperation<?>>>();
candidateRunners.addAll(getRunners(operation.getClass(), anyFormatOperationRunners));
if (wcGeneration == SvnWcGeneration.NOT_DETECTED) {
candidateRunners.addAll(getRunners(operation.getClass(), noneOperationRunners));
} else if (wcGeneration == SvnWcGeneration.V16) {
candidateRunners.addAll(getRunners(operation.getClass(), v16OperationRunners));
} else if (wcGeneration == SvnWcGeneration.V17) {
candidateRunners.addAll(getRunners(operation.getClass(), v17OperationRunners));
}
ISvnOperationRunner<?, SvnOperation<?>> runner = null;
for (ISvnOperationRunner<?, SvnOperation<?>> candidateRunner : candidateRunners) {
boolean isApplicable = candidateRunner.isApplicable(operation, wcGeneration);
if (!isApplicable) {
continue;
}
runner = candidateRunner;
break;
}
if (runner != null) {
//we should NOT reuse already running runners (i.e. runners with operation != null)
//instead we should create new runner of the same class
if ((runner instanceof SvnOperationRunner) && (((SvnOperationRunner) runner).getOperation() != null)) {
final Class<? extends ISvnOperationRunner> runnerClass = runner.getClass();
try {
runner = (ISvnOperationRunner<?, SvnOperation<?>>)runnerClass.newInstance();
} catch (InstantiationException e) {
SVNErrorMessage errorMessage = SVNErrorMessage.create(SVNErrorCode.ASSERTION_FAIL, e);
SVNErrorManager.error(errorMessage, SVNLogType.WC);
} catch (IllegalAccessException e) {
SVNErrorMessage errorMessage = SVNErrorMessage.create(SVNErrorCode.ASSERTION_FAIL, e);
SVNErrorManager.error(errorMessage, SVNLogType.WC);
}
}
runner.reset(wcGeneration);
} else {
SVNErrorMessage err = SVNErrorMessage.create(SVNErrorCode.UNSUPPORTED_FEATURE, "Runner for ''{0}'' command have not been found; probably not yet implement in this API.",
operation.getClass().getName());
SVNErrorManager.error(err, SVNLogType.WC);
}
return runner;
}
/**
* Returns whether the operations should work only on primary working copy generation
* (for example only on SVN 1.7 working copy) or on both primary and secondary generations.
*
* @return <code>true</code> operations should work only on primary working copy generation,
* if <code>false</code> both primary and secondary generations are supported
*/
public boolean isPrimaryWcGenerationOnly() {
return "true".equalsIgnoreCase(System.getProperty("svnkit.wc.17only", null));
}
public boolean isAssertRefCount() {
return "true".equalsIgnoreCase(System.getProperty("svnkit.wc.assertRefCount", null));
}
@SuppressWarnings("unchecked")
protected void registerOperationRunner(Class<?> operationClass, ISvnOperationRunner<?, ? extends SvnOperation<?>> runner) {
if (operationClass == null || runner == null) {
return;
}
Collection<Map<Class<?>, List<ISvnOperationRunner<?, SvnOperation<?>>>>> maps = new ArrayList<Map<Class<?>,List<ISvnOperationRunner<?, SvnOperation<?>>>>>();
SvnWcGeneration[] scope = getRunnerScope(runner);
if (scope == null || scope.length == 0) {
maps.add(anyFormatOperationRunners);
} else {
Set<SvnWcGeneration> formatsSet = new HashSet<SvnWcGeneration>();
formatsSet.addAll(Arrays.asList(scope));
if (formatsSet.contains(SvnWcGeneration.NOT_DETECTED)) {
maps.add(noneOperationRunners);
}
if (formatsSet.contains(SvnWcGeneration.V17)) {
maps.add(v17OperationRunners);
}
if (formatsSet.contains(SvnWcGeneration.V16)) {
maps.add(v16OperationRunners);
}
}
for (Map<Class<?>, List<ISvnOperationRunner<?, SvnOperation<?>>>> runnerMap : maps) {
List<ISvnOperationRunner<?, SvnOperation<?>>> runners = runnerMap.get(operationClass);
if (runners == null) {
runners = new LinkedList<ISvnOperationRunner<?, SvnOperation<?>>>();
runnerMap.put(operationClass, runners);
}
runners.add((ISvnOperationRunner<?, SvnOperation<?>>) runner);
}
}
/**
* Detects whether the versioned directory is working copy root.
*
* @param versionedDir directory to check
* @return <code>true</code> if the directory is working copy root, otherwise <code>false</code>
*/
public static boolean isWorkingCopyRoot(File versionedDir) {
SVNWCDb db = new SVNWCDb();
try {
db.open(SVNWCDbOpenMode.ReadOnly, null, false, false);
if (db.isWCRoot(versionedDir.getAbsoluteFile())) {
return true;
}
} catch(SVNException e) {
} finally {
db.close();
}
SVNWCAccess wcAccess = SVNWCAccess.newInstance(null);
try {
wcAccess.open(versionedDir, false, false, false, 0, Level.FINEST);
return wcAccess.isWCRoot(versionedDir);
} catch (SVNException e) {
} finally {
try {
wcAccess.close();
} catch (SVNException e) {}
}
return false;
}
/**
* Detects whether the directory is versioned directory.
*
* @param directory directory to check
* @return <code>true</code> if the directory is versioned directory, otherwise <code>false</code>
*/
public static boolean isVersionedDirectory(File directory) {
return isVersionedDirectory(directory, false);
}
/**
* Detects whether the directory is versioned directory in or (not in) the addition mode.
*
* @param directory directory to check
* @param isAdditionMode <code>true</code> if it is addition mode, otherwise <code>false</code>
* @return <code>true</code> if the directory is versioned directory, otherwise <code>false</code>
*/
public static boolean isVersionedDirectory(File directory, boolean isAdditionMode) {
if (directory == null) {
return false;
}
final File localAbsPath = directory.getAbsoluteFile();
if (localAbsPath.isFile()) {
// obstruction.
return false;
}
SVNWCDb db = new SVNWCDb();
db.open(SVNWCDbOpenMode.ReadOnly, null, false, false);
try {
DirParsedInfo info = db.parseDir(localAbsPath, Mode.ReadOnly, true, isAdditionMode);
if (info != null
&& info.wcDbDir != null
&& SVNWCDbDir.isUsable(info.wcDbDir)) {
WCDbInfo nodeInfo = db.readInfo(localAbsPath, InfoField.status, InfoField.kind);
if (nodeInfo != null) {
if (nodeInfo.kind != SVNWCDbKind.Dir) {
// obstruction
return false;
} else if (!(nodeInfo.status == SVNWCDbStatus.Excluded || nodeInfo.status == SVNWCDbStatus.ServerExcluded || nodeInfo.status == SVNWCDbStatus.NotPresent)) {
return true;
}
}
}
} catch (SVNException e1) {
} finally {
db.close();
}
File adminDirectory = new File(directory, SVNFileUtil.getAdminDirectoryName());
if (adminDirectory.isDirectory()) {
SVNWCAccess wcAccess = SVNWCAccess.newInstance(null);
try {
wcAccess.open(directory, false, false, false, 0, Level.FINEST);
return true;
} catch (SVNException e) {
} finally {
try {
wcAccess.close();
} catch (SVNException e) {
//
}
}
}
return false;
}
/**
* Searches working copy root path by the versioned directory.
*
* @param versionedDir versioned directory
* @param stopOnExternals <code>true</code> if externals should not be searched, otherwise <code>false</code>
* @return working copy root
* @throws SVNException
*/
public static File getWorkingCopyRoot(File versionedDir, boolean stopOnExternals) throws SVNException {
if (versionedDir == null || (!isVersionedDirectory(versionedDir) && !isVersionedDirectory(versionedDir.getParentFile()))) {
return null;
}
versionedDir = versionedDir.getAbsoluteFile();
SvnWcGeneration wcGeneration = SvnOperationFactory.detectWcGeneration(versionedDir, false);
if (wcGeneration == SvnWcGeneration.NOT_DETECTED) {
return null;
} else if (wcGeneration == SvnWcGeneration.V17) {
return getWorkingCopyRootNg(versionedDir, stopOnExternals);
} else if (wcGeneration == SvnWcGeneration.V16) {
return getWorkingCopyRootOld(versionedDir, stopOnExternals);
}
return null;
}
private static File getWorkingCopyRootOld(File versionedDir, boolean stopOnExternals) throws SVNException {
if (versionedDir == null || (!isVersionedDirectory(versionedDir) && !isVersionedDirectory(versionedDir.getParentFile()))) {
// both this dir and its parent are not versioned.
return null;
}
File parent = versionedDir.getParentFile();
if (parent == null) {
return versionedDir;
}
if (isWorkingCopyRoot(versionedDir)) {
// this is root.
if (stopOnExternals) {
return versionedDir;
}
File parentRoot = getWorkingCopyRoot(parent, stopOnExternals);
if (parentRoot == null) {
// if parent is not versioned return this dir.
return versionedDir;
}
// parent is versioned. we have to check if it contains externals
// definition for this dir.
while (parent != null) {
SVNWCAccess parentAccess = SVNWCAccess.newInstance(null);
try {
SVNAdminArea dir = parentAccess.open(parent, false, 0);
SVNVersionedProperties props = dir.getProperties(dir.getThisDirName());
final String externalsProperty = props.getStringPropertyValue(SVNProperty.EXTERNALS);
SVNExternal[] externals = externalsProperty != null ? SVNExternal.parseExternals(dir.getRoot().getAbsolutePath(), externalsProperty) : new SVNExternal[0];
// now externals could point to our dir.
for (int i = 0; i < externals.length; i++) {
SVNExternal external = externals[i];
File externalFile = new File(parent, external.getPath());
if (externalFile.equals(versionedDir)) {
return parentRoot;
}
}
} catch (SVNException e) {
if (e instanceof SVNCancelException) {
throw e;
}
} finally {
parentAccess.close();
}
if (parent.equals(parentRoot)) {
break;
}
parent = parent.getParentFile();
}
return versionedDir;
}
return getWorkingCopyRootOld(parent, stopOnExternals);
}
private static File getWorkingCopyRootNg(File versionedDir, boolean stopOnExternals) throws SVNException {
SVNWCDb db = new SVNWCDb();
try {
db.open(SVNWCDbOpenMode.ReadOnly, null, false, false);
File wcRoot = db.getWCRoot(versionedDir);
if (wcRoot == null) {
return null;
}
if (stopOnExternals || wcRoot.getParentFile() == null) {
return wcRoot;
}
// check if our root is external in the parent wc.
try {
File parentWcRoot = db.getWCRoot(wcRoot.getParentFile());
SVNExternalsStore storage = new SVNExternalsStore();
db.gatherExternalDefinitions(parentWcRoot, storage);
for(File defPath : storage.getNewExternals().keySet()) {
String externalDefinition = storage.getNewExternals().get(defPath);
SVNExternal[] externals = SVNExternal.parseExternals(defPath, externalDefinition);
for (int i = 0; i < externals.length; i++) {
File targetAbsPath = SVNFileUtil.createFilePath(defPath, externals[i].getPath());
if (targetAbsPath.equals(wcRoot)) {
return getWorkingCopyRootNg(parentWcRoot, stopOnExternals);
}
}
}
return wcRoot;
} catch (SVNException e) {
return wcRoot;
}
} finally {
db.close();
}
}
/**
*
* Detects working copy generation (1.6 or 1.7 format) by the working copy path.
* Recursively searches the by path's parents up to the root if <code>climbUp</code> is <code>true</code>.
*
* @param path working copy path
* @param climbUp <code>true</code> if search recursively in path's parents, otherwise <code>false</code>
* @return working copy generation
* @throws SVNException
*/
public static SvnWcGeneration detectWcGeneration(File path, boolean climbUp) throws SVNException {
return detectWcGeneration(path, climbUp, false);
}
/**
*
* Detects working copy generation (1.6 or 1.7 format) by the working copy path in (not in) the addition mode.
* Recursively searches the by path's parents up to the root if <code>climbUp</code> is <code>true</code>.
*
* @param path working copy path
* @param climbUp <code>true</code> if search recursively in path's parents, otherwise <code>false</code>
* @param isAdditionMode <code>true</code> if it is addition mode, otherwise <code>false</code>
* @return working copy generation
* @throws SVNException
*/
public static SvnWcGeneration detectWcGeneration(File path, boolean climbUp, boolean isAdditionMode) throws SVNException {
while(true) {
if (path == null) {
return SvnWcGeneration.NOT_DETECTED;
}
SVNWCDb db = new SVNWCDb();
try {
db.open(SVNWCDbOpenMode.ReadOnly, (ISVNOptions) null, false, false);
DirParsedInfo info = db.parseDir(path, Mode.ReadOnly, true, isAdditionMode);
if (info != null && SVNWCDbDir.isUsable(info.wcDbDir)) {
return SvnWcGeneration.V17;
} else if (info != null
&& info.wcDbDir != null
&& info.wcDbDir.getWCRoot() != null
&& info.wcDbDir.getWCRoot().getSDb() == null) {
return SvnWcGeneration.V16;
}
return SvnWcGeneration.NOT_DETECTED;
} catch (SVNException e) {
if (e.getErrorMessage().getErrorCode() == SVNErrorCode.WC_NOT_WORKING_COPY) {
path = SVNFileUtil.getParentFile(path);
if (!climbUp) {
SVNWCAccess wcAccess = SVNWCAccess.newInstance(null);
try {
SVNAdminArea area = wcAccess.open(path, false, 0);
if (area != null) {
return SvnWcGeneration.V16;
}
} catch (SVNException inner) {
//
} finally {
wcAccess.close();
}
return SvnWcGeneration.NOT_DETECTED;
}
continue;
} else if (e.getErrorMessage().getErrorCode() == SVNErrorCode.WC_UNSUPPORTED_FORMAT) {
// there should be an exception for an 'add' and 'checkout' operations.
SVNWCAccess wcAccess = SVNWCAccess.newInstance(null);
if (SVNFileType.getType(path) != SVNFileType.DIRECTORY) {
path = SVNFileUtil.getParentFile(path);
if (path == null || SVNFileType.getType(path) != SVNFileType.DIRECTORY) {
if (climbUp) {
continue;
}
return SvnWcGeneration.NOT_DETECTED;
}
}
try {
SVNAdminArea area = wcAccess.open(path, false, 0);
if (area != null) {
return SvnWcGeneration.V16;
}
} catch (SVNException inner) {
if (climbUp && inner.getErrorMessage().getErrorCode() == SVNErrorCode.WC_NOT_DIRECTORY) {
path = SVNFileUtil.getParentFile(path);
continue;
}
} finally {
wcAccess.close();
}
return SvnWcGeneration.NOT_DETECTED;
} else {
throw e;
}
} finally {
db.close();
}
}
}
private static List<ISvnOperationRunner<?, SvnOperation<?>>> getRunners(Class<?> clazz, Map<Class<?>, List<ISvnOperationRunner<?,SvnOperation<?>>>> map) {
List<ISvnOperationRunner<?, SvnOperation<?>>> list = map.get(clazz);
if (list == null) {
list = Collections.emptyList();
}
return list;
}
/**
* Returns working copy context.
*
* @return working copy context
*/
public SVNWCContext getWcContext() {
return wcContext;
}
/**
* Returns primary (default) working copy generation.
*
* @return working copy generation
*/
public SvnWcGeneration getPrimaryWcGeneration() {
if (primaryWcGeneration == null) {
String systemProperty = System.getProperty("svnkit.wc.17", "true");
if (Boolean.toString(true).equalsIgnoreCase(systemProperty)) {
primaryWcGeneration = SvnWcGeneration.V17;
} else {
primaryWcGeneration = SvnWcGeneration.V16;
}
}
return primaryWcGeneration;
}
/**
* Returns secondary working copy generation.
*
* @return working copy generation
*/
public SvnWcGeneration getSecondaryWcGeneration() {
return getPrimaryWcGeneration() == SvnWcGeneration.V17 ? SvnWcGeneration.V16 : SvnWcGeneration.V17;
}
/**
* (Re)sets primary (default) working copy generation.
* If <code>primaryWcGeneration</code> is not <code>null</code>,
* registers operations' runners.
*
* @param primaryWcGeneration
*/
public void setPrimaryWcGeneration(SvnWcGeneration primaryWcGeneration) {
if (primaryWcGeneration == null) {
return;
}
this.primaryWcGeneration = primaryWcGeneration;
registerRunners();
}
/**
* When set to true, first encountered working copy generation becomes 'sticky'
* for this instance of {@link SvnOperationFactory} and no working copy format detection
* will be performed for subsequent operation.
*
* @param isWcGenerationSticky
*/
public void setWcGenerationSticky(boolean isWcGenerationSticky) {
detectedWcGeneration = SvnWcGeneration.NOT_DETECTED;
this.isWcGenerationSticky = isWcGenerationSticky;
}
/**
* @see #setWcGenerationSticky(boolean)
* @return true when this instance of {@link SvnOperationFactory}
*/
public boolean isWcGenerationSticky() {
return this.isWcGenerationSticky;
}
private SvnWcGeneration[] getRunnerScope(ISvnOperationRunner<?, ? extends SvnOperation<?>> runner) {
if (runner.getWcGeneration() == getPrimaryWcGeneration()) {
return new SvnWcGeneration[] { getPrimaryWcGeneration(), SvnWcGeneration.NOT_DETECTED};
} else if (runner.getWcGeneration() == getSecondaryWcGeneration()) {
return new SvnWcGeneration[] { getSecondaryWcGeneration() };
} else {
// any.
return new SvnWcGeneration[] { };
}
}
SvnCommitPacket collectCommitItems(SvnCommit operation) throws SVNException {
ISvnOperationRunner<?, SvnOperation<?>> runner = getImplementation(operation);
if (runner instanceof ISvnCommitRunner) {
SVNWCContext wcContext = null;
runLevel++;
try {
wcContext = obtainWcContext(operation);
runner.setWcContext(wcContext);
return ((ISvnCommitRunner) runner).collectCommitItems(operation);
} finally {
// do not release context, it keeps locks.
runLevel--;
}
}
return new SvnCommitPacket();
}
private void assertRefCount(SvnOperation<?> operation, SVNWCContext wcContext) throws SVNException {
if (!isAssertRefCount()) {
return;
}
ISVNWCDb wcdb = wcContext.getDb();
if (operation.isChangesWorkingCopy() && wcdb instanceof SVNWCDb) {
File operationalWorkingCopy = operation.getOperationalWorkingCopy();
if (operationalWorkingCopy != null) {
DirParsedInfo dirParsedInfo = ((SVNWCDb) wcdb).parseDir(operationalWorkingCopy, Mode.ReadOnly);
if (SVNWCDbDir.isUsable(dirParsedInfo.wcDbDir)) {
SVNWCDbRoot root = dirParsedInfo.wcDbDir.getWCRoot();
SvnWcDbPristines.checkPristineChecksumRefcounts(root);
}
}
}
}
}