130 lines
4.3 KiB
Dart
130 lines
4.3 KiB
Dart
|
|
import 'package:flutter_test/flutter_test.dart';
|
||
|
|
import 'package:twp_softphone/models/call_info.dart';
|
||
|
|
|
||
|
|
void main() {
|
||
|
|
group('CallInfo', () {
|
||
|
|
test('default state is idle', () {
|
||
|
|
const info = CallInfo();
|
||
|
|
expect(info.state, CallState.idle);
|
||
|
|
expect(info.callSid, isNull);
|
||
|
|
expect(info.callerNumber, isNull);
|
||
|
|
expect(info.duration, Duration.zero);
|
||
|
|
expect(info.isMuted, false);
|
||
|
|
expect(info.isSpeakerOn, false);
|
||
|
|
expect(info.isOnHold, false);
|
||
|
|
});
|
||
|
|
|
||
|
|
test('isActive returns true for ringing, connecting, connected', () {
|
||
|
|
expect(const CallInfo(state: CallState.ringing).isActive, true);
|
||
|
|
expect(const CallInfo(state: CallState.connecting).isActive, true);
|
||
|
|
expect(const CallInfo(state: CallState.connected).isActive, true);
|
||
|
|
});
|
||
|
|
|
||
|
|
test('isActive returns false for idle and disconnected', () {
|
||
|
|
expect(const CallInfo(state: CallState.idle).isActive, false);
|
||
|
|
expect(const CallInfo(state: CallState.disconnected).isActive, false);
|
||
|
|
});
|
||
|
|
|
||
|
|
test('copyWith preserves unmodified fields', () {
|
||
|
|
const original = CallInfo(
|
||
|
|
state: CallState.connected,
|
||
|
|
callSid: 'CA123',
|
||
|
|
callerNumber: '+1234567890',
|
||
|
|
isMuted: true,
|
||
|
|
);
|
||
|
|
|
||
|
|
final modified = original.copyWith(isSpeakerOn: true);
|
||
|
|
expect(modified.state, CallState.connected);
|
||
|
|
expect(modified.callSid, 'CA123');
|
||
|
|
expect(modified.callerNumber, '+1234567890');
|
||
|
|
expect(modified.isMuted, true);
|
||
|
|
expect(modified.isSpeakerOn, true);
|
||
|
|
});
|
||
|
|
|
||
|
|
test('copyWith can change state', () {
|
||
|
|
const info = CallInfo(state: CallState.connecting);
|
||
|
|
final updated = info.copyWith(state: CallState.connected);
|
||
|
|
expect(updated.state, CallState.connected);
|
||
|
|
});
|
||
|
|
|
||
|
|
test('copyWith with callerNumber preserves it', () {
|
||
|
|
const info = CallInfo(callerNumber: '+19095737372');
|
||
|
|
final updated = info.copyWith(state: CallState.connected);
|
||
|
|
expect(updated.callerNumber, '+19095737372');
|
||
|
|
});
|
||
|
|
|
||
|
|
test('reset to idle clears all fields', () {
|
||
|
|
// Verify a complex state exists
|
||
|
|
const connected = CallInfo(
|
||
|
|
state: CallState.connected,
|
||
|
|
callSid: 'CA123',
|
||
|
|
callerNumber: '+1234567890',
|
||
|
|
isMuted: true,
|
||
|
|
isSpeakerOn: true,
|
||
|
|
isOnHold: true,
|
||
|
|
duration: Duration(seconds: 30),
|
||
|
|
);
|
||
|
|
expect(connected.isActive, true);
|
||
|
|
|
||
|
|
// Simulating what callEnded does
|
||
|
|
const reset = CallInfo();
|
||
|
|
expect(reset.state, CallState.idle);
|
||
|
|
expect(reset.callSid, isNull);
|
||
|
|
expect(reset.callerNumber, isNull);
|
||
|
|
expect(reset.isActive, false);
|
||
|
|
});
|
||
|
|
});
|
||
|
|
|
||
|
|
group('CallState transitions', () {
|
||
|
|
test('outbound call flow: idle -> connecting -> connected -> idle', () {
|
||
|
|
var info = const CallInfo();
|
||
|
|
expect(info.state, CallState.idle);
|
||
|
|
|
||
|
|
// makeCall sets connecting + callerNumber
|
||
|
|
info = info.copyWith(state: CallState.connecting, callerNumber: '+19095737372');
|
||
|
|
expect(info.state, CallState.connecting);
|
||
|
|
expect(info.callerNumber, '+19095737372');
|
||
|
|
expect(info.isActive, true);
|
||
|
|
|
||
|
|
// SDK fires connected
|
||
|
|
info = info.copyWith(state: CallState.connected);
|
||
|
|
expect(info.state, CallState.connected);
|
||
|
|
expect(info.callerNumber, '+19095737372'); // preserved
|
||
|
|
expect(info.isActive, true);
|
||
|
|
|
||
|
|
// callEnded resets
|
||
|
|
info = const CallInfo();
|
||
|
|
expect(info.state, CallState.idle);
|
||
|
|
expect(info.isActive, false);
|
||
|
|
});
|
||
|
|
|
||
|
|
test('inbound call flow: idle -> ringing -> connected -> idle', () {
|
||
|
|
var info = const CallInfo();
|
||
|
|
|
||
|
|
info = info.copyWith(state: CallState.ringing);
|
||
|
|
expect(info.isActive, true);
|
||
|
|
|
||
|
|
// callerNumber set from active.from
|
||
|
|
info = info.copyWith(callerNumber: '+18005551234');
|
||
|
|
expect(info.callerNumber, '+18005551234');
|
||
|
|
|
||
|
|
info = info.copyWith(state: CallState.connected);
|
||
|
|
expect(info.state, CallState.connected);
|
||
|
|
|
||
|
|
info = const CallInfo();
|
||
|
|
expect(info.state, CallState.idle);
|
||
|
|
});
|
||
|
|
|
||
|
|
test('outbound callerNumber not overwritten by null copyWith', () {
|
||
|
|
var info = const CallInfo(
|
||
|
|
state: CallState.connecting,
|
||
|
|
callerNumber: '+19095737372',
|
||
|
|
);
|
||
|
|
|
||
|
|
// copyWith without callerNumber should preserve it
|
||
|
|
info = info.copyWith(state: CallState.connected);
|
||
|
|
expect(info.callerNumber, '+19095737372');
|
||
|
|
});
|
||
|
|
});
|
||
|
|
}
|