Files
AutoJudge-Flutter/lib/utils/exceptions.dart
2025-11-13 09:14:49 +08:00

149 lines
3.4 KiB
Dart

/// Base exception class for all application exceptions
abstract class AppException implements Exception {
final String message;
final String? details;
final StackTrace? stackTrace;
AppException(this.message, [this.details, this.stackTrace]);
@override
String toString() {
if (details != null) {
return '$runtimeType: $message\nDetails: $details';
}
return '$runtimeType: $message';
}
}
/// Exception thrown when network operations fail
class NetworkException extends AppException {
final int? statusCode;
final String? url;
NetworkException(
super.message, [
super.details,
super.stackTrace,
this.statusCode,
this.url,
]);
@override
String toString() {
final buffer = StringBuffer('NetworkException: $message');
if (statusCode != null) {
buffer.write('\nStatus Code: $statusCode');
}
if (url != null) {
buffer.write('\nURL: $url');
}
if (details != null) {
buffer.write('\nDetails: $details');
}
return buffer.toString();
}
}
/// Exception thrown when authentication fails
class AuthenticationException extends AppException {
final String? userId;
final AuthenticationFailureReason? reason;
AuthenticationException(
super.message, [
super.details,
super.stackTrace,
this.userId,
this.reason,
]);
@override
String toString() {
final buffer = StringBuffer('AuthenticationException: $message');
if (userId != null) {
buffer.write('\nUser ID: $userId');
}
if (reason != null) {
buffer.write('\nReason: ${reason!.name}');
}
if (details != null) {
buffer.write('\nDetails: $details');
}
return buffer.toString();
}
}
/// Reasons for authentication failure
enum AuthenticationFailureReason {
invalidCredentials,
sessionExpired,
networkError,
serverError,
unknown,
}
/// Exception thrown when parsing fails
class ParseException extends AppException {
final String? source;
final String? expectedFormat;
ParseException(
super.message, [
super.details,
super.stackTrace,
this.source,
this.expectedFormat,
]);
@override
String toString() {
final buffer = StringBuffer('ParseException: $message');
if (expectedFormat != null) {
buffer.write('\nExpected Format: $expectedFormat');
}
if (source != null && source!.length <= 100) {
buffer.write('\nSource: $source');
} else if (source != null) {
buffer.write('\nSource: ${source!.substring(0, 100)}...');
}
if (details != null) {
buffer.write('\nDetails: $details');
}
return buffer.toString();
}
}
/// Exception thrown when validation fails
class ValidationException extends AppException {
final String? fieldName;
final dynamic invalidValue;
final List<String>? validationRules;
ValidationException(
super.message, [
super.details,
super.stackTrace,
this.fieldName,
this.invalidValue,
this.validationRules,
]);
@override
String toString() {
final buffer = StringBuffer('ValidationException: $message');
if (fieldName != null) {
buffer.write('\nField: $fieldName');
}
if (invalidValue != null) {
buffer.write('\nInvalid Value: $invalidValue');
}
if (validationRules != null && validationRules!.isNotEmpty) {
buffer.write('\nValidation Rules: ${validationRules!.join(", ")}');
}
if (details != null) {
buffer.write('\nDetails: $details');
}
return buffer.toString();
}
}