@@ -4,7 +4,6 @@ import 'dart:typed_data';
44
55import 'package:http/http.dart' as http;
66import 'package:logging/logging.dart' ;
7- import 'package:logging/logging.dart' ;
87import 'package:meta/meta.dart' ;
98import 'package:powersync_core/src/abort_controller.dart' ;
109import 'package:powersync_core/src/exceptions.dart' ;
@@ -450,6 +449,7 @@ class StreamingSyncImplementation implements StreamingSync {
450449 case UploadCompleted ():
451450 // Only relevant for the Rust sync implementation.
452451 break ;
452+ case AbortCurrentIteration ():
453453 case TokenRefreshComplete ():
454454 // We have a new token, so stop the iteration.
455455 shouldStopIteration = true ;
@@ -585,6 +585,7 @@ typedef BucketDescription = ({
585585
586586final class _ActiveRustStreamingIteration {
587587 final StreamingSyncImplementation sync ;
588+ var _isActive = true ;
588589
589590 StreamSubscription <void >? _completedUploads;
590591 final Completer <void > _completedStream = Completer ();
@@ -597,6 +598,7 @@ final class _ActiveRustStreamingIteration {
597598 assert (_completedStream.isCompleted, 'Should have started streaming' );
598599 await _completedStream.future;
599600 } finally {
601+ _isActive = true ;
600602 _completedUploads? .cancel ();
601603 await _stop ();
602604 }
@@ -610,7 +612,7 @@ final class _ActiveRustStreamingIteration {
610612 final events = addBroadcast (
611613 _receiveLines (request.request), sync ._nonLineSyncEvents.stream);
612614
613- listen :
615+ loop :
614616 await for (final event in events) {
615617 switch (event) {
616618 case ReceivedLine (line: final Uint8List line):
@@ -619,10 +621,10 @@ final class _ActiveRustStreamingIteration {
619621 await _control ('line_text' , line);
620622 case UploadCompleted ():
621623 await _control ('completed_upload' );
624+ case AbortCurrentIteration ():
625+ break loop;
622626 case TokenRefreshComplete ():
623627 await _control ('refreshed_token' );
624- case AbortRequested ():
625- break listen;
626628 }
627629 }
628630 }
@@ -653,11 +655,20 @@ final class _ActiveRustStreamingIteration {
653655 _completedStream.complete (_handleLines (instruction));
654656 case UpdateSyncStatus (: final status):
655657 sync ._state.updateStatus ((m) => m.applyFromCore (status));
656- case FetchCredentials ():
657- // TODO: Handle this case.
658- throw UnimplementedError ();
658+ case FetchCredentials (: final didExpire):
659+ if (didExpire) {
660+ await sync .connector.prefetchCredentials (invalidate: true );
661+ } else {
662+ sync .connector.prefetchCredentials ().then ((_) {
663+ if (_isActive && ! sync .aborted) {
664+ sync ._nonLineSyncEvents.add (const TokenRefreshComplete ());
665+ }
666+ }, onError: (Object e, StackTrace s) {
667+ sync .logger.warning ('Could not prefetch credentials' , e, s);
668+ });
669+ }
659670 case CloseSyncStream ():
660- sync ._nonLineSyncEvents.add (AbortRequested ());
671+ sync ._nonLineSyncEvents.add (const AbortCurrentIteration ());
661672 case FlushFileSystem ():
662673 await sync .adapter.flushFileSystem ();
663674 case DidCompleteSync ():
@@ -683,3 +694,7 @@ final class UploadCompleted implements SyncEvent {
683694final class TokenRefreshComplete implements SyncEvent {
684695 const TokenRefreshComplete ();
685696}
697+
698+ final class AbortCurrentIteration implements SyncEvent {
699+ const AbortCurrentIteration ();
700+ }
0 commit comments