frindlymap/lib/modules/transport/src/memory_transport.dart

61 lines
1.6 KiB
Dart

import 'dart:async';
import 'package:friendly_map/modules/core/core.dart';
/// 메모리 안에서 여러 기기를 흉내 내는 연결망 (시험·화면 미리보기용).
/// 받는 사람이 꺼져 있으면 보관함처럼 쌓아 두었다가 [MemoryTransport.fetchPending] 으로 가져간다.
class MemoryHub {
final Map<String, MemoryTransport> _online = {};
final Map<String, List<Envelope>> _mailbox = {};
/// 지금까지 오간 봉투 수 (시험에서 확인용).
int delivered = 0;
/// 보관함에 쌓인 것을 쓰지 않는 직접 연결만 흉내 내려면 false.
bool mailboxEnabled = true;
bool _deliver(Envelope e) {
final target = _online[e.to];
if (target != null && target._started) {
delivered++;
target._in.add(e);
return true;
}
if (!mailboxEnabled) return false;
_mailbox.putIfAbsent(e.to, () => []).add(e);
return true;
}
}
class MemoryTransport implements Transport {
MemoryTransport(this.phone, this._hub) {
_hub._online[phone] = this;
}
final String phone;
final MemoryHub _hub;
final StreamController<Envelope> _in = StreamController<Envelope>.broadcast(sync: true);
bool _started = false;
@override
Stream<Envelope> get incoming => _in.stream;
@override
Future<void> start() async => _started = true;
@override
Future<void> stop() async => _started = false;
@override
Future<bool> send(Envelope envelope) async => _hub._deliver(envelope);
@override
Future<int> fetchPending() async {
final items = _hub._mailbox.remove(phone) ?? const <Envelope>[];
for (final e in items) {
_in.add(e);
}
return items.length;
}
}