@@ -391,14 +391,30 @@ class FileController {
391391
392392 await Future .delayed (Duration (milliseconds: 100 ));
393393
394- final dir = (await bind.sessionGetPeerOption (
394+ final savedDir = (await bind.sessionGetPeerOption (
395395 sessionId: sessionId, name: isLocal ? "local_dir" : "remote_dir" ));
396- openDirectory (dir.isEmpty ? options.value.home : dir);
396+ Future <bool > tryOpenReadyDirs () async {
397+ final dirs = < String > {
398+ if (directory.value.path.isNotEmpty) directory.value.path,
399+ if (savedDir.isNotEmpty) savedDir,
400+ options.value.home,
401+ };
402+ for (final dir in dirs) {
403+ if (await _openDirectoryPath (dir, isBack: true )) {
404+ return true ;
405+ }
406+ }
407+ return false ;
408+ }
409+
410+ var opened = await tryOpenReadyDirs ();
397411
398412 await Future .delayed (Duration (seconds: 1 ));
399413
400- if (directory.value.path.isEmpty) {
401- openDirectory (options.value.home);
414+ if (! opened) {
415+ // The peer may become ready during the reconnect delay, so retry the
416+ // same candidates instead of only retrying the default home directory.
417+ await tryOpenReadyDirs ();
402418 }
403419 }
404420
@@ -429,19 +445,23 @@ class FileController {
429445 });
430446 }
431447
432- Future <void > refresh () async {
433- await openDirectory (directory.value.path);
448+ Future <bool > refresh () async {
449+ // "." can be both a refresh command and a real remote directory path.
450+ // Refresh must bypass openDirectory's command dispatch to avoid recursion.
451+ return await _openDirectoryPath (directory.value.path, isBack: true );
434452 }
435453
436- Future <void > openDirectory (String path, {bool isBack = false }) async {
437- if (path == "." ) {
438- refresh ();
439- return ;
454+ Future <bool > openDirectory (String path, {bool isBack = false }) async {
455+ if (! isBack && path == "." ) {
456+ return await refresh ();
440457 }
441- if (path == ".." ) {
442- goToParentDirectory ();
443- return ;
458+ if (! isBack && path == ".." ) {
459+ return await _goToParentDirectory (isBack: isBack);
444460 }
461+ return await _openDirectoryPath (path, isBack: isBack);
462+ }
463+
464+ Future <bool > _openDirectoryPath (String path, {bool isBack = false }) async {
445465 if (! isBack) {
446466 pushHistory ();
447467 }
@@ -458,8 +478,10 @@ class FileController {
458478 final fd = await fileFetcher.fetchDirectory (path, isLocal, showHidden);
459479 fd.format (isWindows, sort: sortBy.value);
460480 directory.value = fd;
481+ return true ;
461482 } catch (e) {
462483 debugPrint ("Failed to openDirectory $path : $e " );
484+ return false ;
463485 }
464486 }
465487
@@ -487,19 +509,22 @@ class FileController {
487509 goBack ();
488510 return ;
489511 }
490- openDirectory ( path, isBack: true );
512+ unawaited ( _openDirectoryPath ( path, isBack: true ). then < void >((_) {}) );
491513 }
492514
493515 void goToParentDirectory () {
516+ unawaited (_goToParentDirectory ().then <void >((_) {}));
517+ }
518+
519+ Future <bool > _goToParentDirectory ({bool isBack = false }) async {
494520 final isWindows = options.value.isWindows;
495521 final dirPath = directory.value.path;
496522 var parent = PathUtil .dirname (dirPath, isWindows);
497523 // specially for C:\, D:\, goto '/'
498524 if (parent == dirPath && isWindows) {
499- openDirectory ('/' );
500- return ;
525+ return await _openDirectoryPath ('/' , isBack: isBack);
501526 }
502- openDirectory (parent);
527+ return await _openDirectoryPath (parent, isBack : isBack );
503528 }
504529
505530 // TODO deprecated this
0 commit comments