use of com.mucommander.ui.dialog.auth.AuthDialog in project mucommander by mucommander.
the class BrowseLocationThread method run.
@Override
public void run() {
LOGGER.debug("starting folder change...");
boolean folderChangedSuccessfully = false;
// Show some progress in the progress bar to give hope
folderPanel.setProgressValue(10);
boolean userCancelled = false;
CredentialsMapping newCredentialsMapping = null;
// True if Guest authentication was selected in the authentication dialog (guest credentials must not be
// added to CredentialsManager)
boolean guestCredentialsSelected = false;
AuthenticationType authenticationType = folderURL.getAuthenticationType();
if (credentialsMapping != null) {
newCredentialsMapping = credentialsMapping;
CredentialsManager.authenticate(folderURL, newCredentialsMapping);
} else // avoid waiting for an AuthException to be thrown.
if (!folderURL.containsCredentials() && ((authenticationType == AuthenticationType.AUTHENTICATION_REQUIRED) || (authenticationType == AuthenticationType.AUTHENTICATION_OPTIONAL && CredentialsManager.getMatchingCredentials(folderURL).length > 0))) {
AuthDialog authDialog = popAuthDialog(folderURL, false, null);
newCredentialsMapping = authDialog.getCredentialsMapping();
guestCredentialsSelected = authDialog.guestCredentialsSelected();
// User cancelled the authentication dialog, stop
if (newCredentialsMapping == null)
userCancelled = true;
else // Use the provided credentials and invalidate the folder AbstractFile instance (if any) so that
// it gets recreated with the new credentials
{
CredentialsManager.authenticate(folderURL, newCredentialsMapping);
folder = null;
}
}
if (!userCancelled) {
boolean canonicalPathFollowed = false;
do {
// Set cursor to hourglass/wait
mainFrame.setCursor(new Cursor(Cursor.WAIT_CURSOR));
// Render all actions inactive while changing folder
mainFrame.setNoEventsMode(true);
try {
// Thread was created using a FileURL
if (folder == null) {
AbstractFile file = FileFactory.getFile(folderURL, true);
synchronized (KILL_LOCK) {
if (killed) {
LOGGER.debug("this thread has been killed, returning");
break;
}
}
// File resolved -> 25% complete
folderPanel.setProgressValue(25);
// or doesn't exist
if (file == null || !file.exists()) {
// Restore default cursor
mainFrame.setCursor(Cursor.getDefaultCursor());
locationChanger.showFolderDoesNotExistDialog();
break;
}
if (!file.canRead()) {
// Restore default cursor
mainFrame.setCursor(Cursor.getDefaultCursor());
showFailedToReadFolderDialog();
break;
}
// File is a regular directory, all good
if (file.isDirectory()) {
// Just continue
} else // File is a browsable file (Zip archive for instance) but not a directory : Browse or Download ? => ask the user
if (file.isBrowsable()) {
// of the OpenAction (enter pressed on the file). This works well enough in practice.
if (!globalHistory.contains(folderURL) && !file.equals(folderPanel.getFileTable().getSelectedFile())) {
// Restore default cursor
mainFrame.setCursor(Cursor.getDefaultCursor());
// Download or browse file ?
QuestionDialog dialog = new QuestionDialog(mainFrame, null, Translator.get("table.download_or_browse"), mainFrame, Arrays.asList(BrowseLocationThreadAction.BROWSE, BrowseLocationThreadAction.DOWNLOAD, BrowseLocationThreadAction.CANCEL), 0);
DialogAction ret = dialog.getActionValue();
if (ret == DIALOG_DISPOSED_ACTION || ret == BrowseLocationThreadAction.CANCEL)
break;
// Download file
if (ret == BrowseLocationThreadAction.DOWNLOAD) {
showDownloadDialog(file);
break;
}
// Continue if BROWSE
// Set cursor to hourglass/wait
mainFrame.setCursor(new Cursor(Cursor.WAIT_CURSOR));
}
// else just continue and browse file's contents
} else // File is a regular file: show download dialog which allows to download (copy) the file
// to a directory specified by the user
{
showDownloadDialog(file);
break;
}
this.folder = file;
} else // Thread was created using an AbstractFile instance, check file existence
if (!folder.exists()) {
// Find a 'workable' folder if the requested folder doesn't exist anymore
if (findWorkableFolder) {
AbstractFile newFolder = locationChanger.getWorkableFolder(folder);
if (newFolder.equals(folder)) {
// If we've already tried the returned folder, give up (avoids a potentially endless loop)
locationChanger.showFolderDoesNotExistDialog();
break;
}
// Try again with the new folder
folder = newFolder;
folderURL = folder.getURL();
// Discard the file to select, if any
fileToSelect = null;
continue;
} else {
locationChanger.showFolderDoesNotExistDialog();
break;
}
} else if (!folder.canRead()) {
showFailedToReadFolderDialog();
break;
}
// resolved again.
if (!canonicalPathFollowed && followCanonicalPath(folder)) {
try {
// Recreate the FileURL using the file's canonical path
FileURL newURL = FileURL.getFileURL(folder.getCanonicalPath());
// Keep the credentials and properties (if any)
newURL.setCredentials(folderURL.getCredentials());
newURL.importProperties(folderURL);
this.folderURL = newURL;
// Invalidate the AbstractFile instance
this.folder = null;
// There won't be any further attempts after this one
canonicalPathFollowed = true;
// Loop the resolve the file
continue;
} catch (MalformedURLException e) {
// In the unlikely event of the canonical path being malformed, the AbstractFile
// and FileURL instances are left untouched
}
}
synchronized (KILL_LOCK) {
if (killed) {
LOGGER.debug("this thread has been killed, returning");
break;
}
}
// File tested -> 50% complete
folderPanel.setProgressValue(50);
synchronized (KILL_LOCK) {
if (killed) {
LOGGER.debug("this thread has been killed, returning");
break;
}
// From now on, thread cannot be killed (would comprise table integrity)
doNotKill = true;
}
// files listed -> 75% complete
folderPanel.setProgressValue(75);
LOGGER.trace("calling setCurrentFolder");
// Change the file table's current folder and select the specified file (if any)
locationChanger.setCurrentFolder(folder, fileToSelect, changeLockedTab, true);
// folder set -> 95% complete
folderPanel.setProgressValue(95);
// Do not add the credentials if guest credentials were selected by the user.
if (newCredentialsMapping != null && !guestCredentialsSelected)
CredentialsManager.addCredentials(newCredentialsMapping);
// All good !
folderChangedSuccessfully = true;
break;
} catch (Exception e) {
LOGGER.debug("Caught exception", e);
if (killed) {
// If #tryKill() called #interrupt(), the exception we just caught was most likely
// thrown as a result of the thread being interrupted.
//
// The exception can be a java.lang.InterruptedException (Thread throws those),
// a java.nio.channels.ClosedByInterruptException (InterruptibleChannel throws those)
// or any other exception thrown by some code that swallowed the original exception
// and threw a new one.
LOGGER.debug("Thread was interrupted, ignoring exception");
break;
}
// Restore default cursor
mainFrame.setCursor(Cursor.getDefaultCursor());
if (e instanceof AuthException) {
AuthException authException = (AuthException) e;
// Retry (loop) if user provided new credentials, if not stop
AuthDialog authDialog = popAuthDialog(authException.getURL(), true, authException.getMessage());
newCredentialsMapping = authDialog.getCredentialsMapping();
guestCredentialsSelected = authDialog.guestCredentialsSelected();
if (newCredentialsMapping != null) {
// Invalidate the existing AbstractFile instance
folder = null;
// Use the provided credentials
CredentialsManager.authenticate(folderURL, newCredentialsMapping);
continue;
}
} else {
// Find a 'workable' folder if the requested folder doesn't exist anymore
if (findWorkableFolder) {
AbstractFile newFolder = locationChanger.getWorkableFolder(folder);
if (newFolder.equals(folder)) {
// If we've already tried the returned folder, give up (avoids a potentially endless loop)
locationChanger.showFolderDoesNotExistDialog();
break;
}
// Try again with the new folder
folder = newFolder;
folderURL = folder.getURL();
// Discard the file to select, if any
fileToSelect = null;
continue;
}
showAccessErrorDialog(e);
}
// Stop looping!
break;
}
} while (true);
}
synchronized (KILL_LOCK) {
// Clean things up
cleanup(folderChangedSuccessfully);
}
}
use of com.mucommander.ui.dialog.auth.AuthDialog in project mucommander by mucommander.
the class BrowseLocationThread method popAuthDialog.
/**
* Pops up an {@link AuthDialog authentication dialog} prompting the user to select or enter credentials in order to
* be granted the access to the file or folder represented by the given {@link FileURL}.
* The <code>AuthDialog</code> instance is returned, allowing to retrieve the credentials that were selected
* by the user (if any).
*
* @param fileURL the file or folder to ask credentials for
* @param errorMessage optional (can be null), an error message describing a prior authentication failure
* @return the AuthDialog that contains the credentials selected by the user (if any)
*/
private AuthDialog popAuthDialog(FileURL fileURL, boolean authFailed, String errorMessage) {
AuthDialog authDialog = new AuthDialog(mainFrame, fileURL, authFailed, errorMessage);
authDialog.showDialog();
return authDialog;
}
use of com.mucommander.ui.dialog.auth.AuthDialog in project mucommander by mucommander.
the class ConfFileTableTab method getInitialAbstractPaths.
/**
* Returns a valid initial abstract path for the specified frame.
* <p>
* This method does its best to interpret <code>path</code> properly, or to fail
* politely if it can't. This means that:<br/>
* - we first try to see whether <code>path</code> is a legal, existing URI.<br/>
* - if it's not, we check whether it might be a legal local, existing file path.<br/>
* - if it's not, we'll just use the default initial path for the frame.<br/>
* - if <code>path</code> is browsable (eg directory, archive, ...), use it as is.<br/>
* - if it's not, use its parent.<br/>
* - if it does not have a parent, use the default initial path for the frame.<br/>
* </p>
*
* @param path path to the folder we want to open in <code>frame</code>.
* @param folderPanelType identifier of the panel we want to compute the path for (either {@link com.mucommander.ui.main.FolderPanel.FolderPanelType.LEFT} or
* {@link #@link com.mucommander.ui.main.FolderPanel.FolderPanelType.RIGHT}).
* @return our best shot at what was actually requested.
*/
private FileURL getInitialAbstractPaths(String path) {
// This is one of those cases where a null value actually has a proper meaning.
if (path == null)
return MainFrameBuilder.getHomeFolder().getURL();
// Tries the specified path as-is.
AbstractFile file;
CredentialsMapping newCredentialsMapping;
while (true) {
try {
file = FileFactory.getFile(path, true);
if (!file.exists())
file = null;
break;
}// If an AuthException occurred, gets login credential from the user.
catch (Exception e) {
if (e instanceof AuthException) {
// Prompts the user for a login and password.
AuthException authException = (AuthException) e;
FileURL url = authException.getURL();
AuthDialog authDialog = new AuthDialog(WindowManager.getCurrentMainFrame(), url, true, authException.getMessage());
authDialog.showDialog();
newCredentialsMapping = authDialog.getCredentialsMapping();
if (newCredentialsMapping != null) {
// Use the provided credentials
CredentialsManager.authenticate(url, newCredentialsMapping);
path = url.toString(true);
} else // If the user cancels, we fall back to the default path.
{
return MainFrameBuilder.getHomeFolder().getURL();
}
} else {
file = null;
break;
}
}
}
// If the specified path does not work out,
if (file == null)
// Tries the specified path as a relative path.
if ((file = FileFactory.getFile(new File(path).getAbsolutePath())) == null || !file.exists())
// Defaults to home.
return MainFrameBuilder.getHomeFolder().getURL();
// If the specified path is a non-browsable, uses its parent.
if (!file.isBrowsable()) {
fileToSelect = file;
// a file without a parent directory.
if ((file = file.getParent()) == null)
return MainFrameBuilder.getHomeFolder().getURL();
}
return file.getURL();
}
Aggregations