Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
25 changes: 11 additions & 14 deletions lib/src/codecs/byte/byte_decoder.dart
Original file line number Diff line number Diff line change
@@ -1,36 +1,33 @@
import 'dart:convert';
import 'dart:typed_data';

import '../../helpers/whitespace.dart';

class XsdByteDecoder extends Converter<String, int> {
const XsdByteDecoder();

static const int _minValue = -128;
static const int _maxValue = 127;

@override
int convert(String input) {
final String collapsedInput = processWhiteSpace(input, Whitespace.collapse);

if (collapsedInput.isEmpty) {
throw const FormatException('The input string cannot be empty.');
}

final int? value = int.tryParse(collapsedInput);
if (value == null) {
// If int.tryParse fails, it could be a lexical error or a number too large
// for a platform int. We use BigInt.tryParse to differentiate.
if (BigInt.tryParse(collapsedInput) != null) {
// The string is a valid integer, but it's too large to be parsed as a
// platform int, so it's definitely out of range for xsd:byte.
throw FormatException(
"Value '$collapsedInput' is out of range for xsd:byte. Must be between $_minValue and $_maxValue.",
);
}
throw FormatException(
"Invalid xsd:byte lexical format: '$input' (collapsed to '$collapsedInput')",
);
}

if (value < _minValue || value > _maxValue) {
// Use Int8List to validate that the value fits within 8 bits (wraps on overflow).
final list = Int8List(1);
list[0] = value;

if (list[0] != value) {
throw FormatException(
"Value '$collapsedInput' is out of range for xsd:byte. Must be between $_minValue and $_maxValue.",
"Value '$collapsedInput' is out of range for xsd:byte.",
);
}

Expand Down
14 changes: 7 additions & 7 deletions lib/src/codecs/byte/byte_encoder.dart
Original file line number Diff line number Diff line change
@@ -1,17 +1,17 @@
import 'dart:convert';
import 'dart:typed_data';

/// A [Converter] that converts an [int] to an XSD `byte` compatable string.
class XsdByteEncoder extends Converter<int, String> {
const XsdByteEncoder();

static const int _minValue = -128;
static const int _maxValue = 127;

@override
String convert(int input) {
if (input < _minValue || input > _maxValue) {
throw FormatException(
"Value '$input' is out of range for xsd:byte. Must be between $_minValue and $_maxValue.",
);
// Use Int8List to validate that the value fits within 8 bits (wraps on overflow).
final list = Int8List(1);
list[0] = input;
if (list[0] != input) {
throw FormatException("Value '$input' is out of range for xsd:byte.");
}
return input.toString();
}
Expand Down
25 changes: 11 additions & 14 deletions lib/src/codecs/int/int_decoder.dart
Original file line number Diff line number Diff line change
@@ -1,36 +1,33 @@
import 'dart:convert';
import 'dart:typed_data';

import '../../helpers/whitespace.dart';

class XsdIntDecoder extends Converter<String, int> {
const XsdIntDecoder();

static const int _minValue = -2147483648;
static const int _maxValue = 2147483647;

@override
int convert(String input) {
final String collapsedInput = processWhiteSpace(input, Whitespace.collapse);

if (collapsedInput.isEmpty) {
throw const FormatException('The input string cannot be empty.');
}

final int? value = int.tryParse(collapsedInput);
if (value == null) {
// If int.tryParse fails, it could be a lexical error or a number too large
// for a platform int. We use BigInt.tryParse to differentiate.
if (BigInt.tryParse(collapsedInput) != null) {
// The string is a valid integer, but it's too large to be parsed as a
// platform int, so it's definitely out of range for xsd:int.
throw FormatException(
"Value '$collapsedInput' is out of range for xsd:int. Must be between $_minValue and $_maxValue.",
);
}
throw FormatException(
"Invalid XSD int lexical format: '$input' (collapsed to '$collapsedInput')",
);
}

if (value < _minValue || value > _maxValue) {
// Use Int32List to validate that the value fits within 32 bits (wraps on overflow).
final list = Int32List(1);
list[0] = value;

if (list[0] != value) {
throw FormatException(
"Value '$collapsedInput' is out of range for xsd:int. Must be between $_minValue and $_maxValue.",
"Value '$collapsedInput' is out of range for xsd:int.",
);
}
return value;
Expand Down
13 changes: 6 additions & 7 deletions lib/src/codecs/int/int_encoder.dart
Original file line number Diff line number Diff line change
@@ -1,17 +1,16 @@
import 'dart:convert';
import 'dart:typed_data';

class XsdIntEncoder extends Converter<int, String> {
const XsdIntEncoder();

static const int _minValue = -2147483648;
static const int _maxValue = 2147483647;

@override
String convert(int input) {
if (input < _minValue || input > _maxValue) {
throw FormatException(
"Value '$input' is out of range for xsd:int. Must be between $_minValue and $_maxValue.",
);
// Use Int32List to validate that the value fits within 32 bits (wraps on overflow).
final list = Int32List(1);
list[0] = input;
if (list[0] != input) {
throw FormatException("Value '$input' is out of range for xsd:int.");
}
return input.toString();
}
Expand Down
27 changes: 16 additions & 11 deletions lib/src/codecs/short/short_decoder.dart
Original file line number Diff line number Diff line change
@@ -1,30 +1,35 @@
import 'dart:convert';
import 'dart:typed_data';

import '../../helpers/whitespace.dart';

class XsdShortDecoder extends Converter<String, int> {
const XsdShortDecoder();

static const int _minValue = -32768;
static const int _maxValue = 32767;

@override
int convert(String input) {
final String collapsedInput = processWhiteSpace(input, Whitespace.collapse);
final str = processWhiteSpace(input, Whitespace.collapse);

if (str.isEmpty) {
throw const FormatException('The input string cannot be empty.');
}

final value = int.tryParse(str);

final int? value = int.tryParse(collapsedInput);
if (value == null) {
throw FormatException(
"Invalid XSD short lexical format: '$input' (collapsed to '$collapsedInput')",
);
throw FormatException('The input "$str" is not a valid integer.');
}

// Check bounds for xsd:short
if (value < _minValue || value > _maxValue) {
// Use Int16List to validate that the value fits within 16 bits (wraps on overflow).
final list = Int16List(1);
list[0] = value;

if (list[0] != value) {
throw FormatException(
"Value '$collapsedInput' is out of range for xsd:short. Must be between $_minValue and $_maxValue.",
'The value "$value" is out of range for xsd:short.',
);
}

return value;
}
}
13 changes: 8 additions & 5 deletions lib/src/codecs/short/short_encoder.dart
Original file line number Diff line number Diff line change
@@ -1,18 +1,21 @@
import 'dart:convert';
import 'dart:typed_data';

/// A [Converter] that converts an [int] to an XSD `short` string.
class XsdShortEncoder extends Converter<int, String> {
const XsdShortEncoder();

static const int _minValue = -32768;
static const int _maxValue = 32767;

@override
String convert(int input) {
if (input < _minValue || input > _maxValue) {
// Use Int16List to validate that the value fits within 16 bits (wraps on overflow).
final list = Int16List(1);
list[0] = input;
if (list[0] != input) {
throw FormatException(
"Value '$input' is out of range for xsd:short. Must be between $_minValue and $_maxValue.",
'The value "$input" is out of range for xsd:short.',
);
}

return input.toString();
}
}
16 changes: 11 additions & 5 deletions lib/src/codecs/unsigned_byte/unsigned_byte_decoder.dart
Original file line number Diff line number Diff line change
@@ -1,27 +1,33 @@
import 'dart:convert';
import 'dart:typed_data';

import '../../helpers/whitespace.dart';

class XsdUnsignedByteDecoder extends Converter<String, int> {
const XsdUnsignedByteDecoder();

static const int _minValue = 0;
static const int _maxValue = 255;

@override
int convert(String input) {
final String collapsedInput = processWhiteSpace(input, Whitespace.collapse);

if (collapsedInput.isEmpty) {
throw const FormatException('The input string cannot be empty.');
}

final int? value = int.tryParse(collapsedInput);
if (value == null) {
throw FormatException(
"Invalid XSD unsignedByte lexical format: '$input' (collapsed to '$collapsedInput')",
);
}

if (value < _minValue || value > _maxValue) {
// Use Uint8List to validate that the value fits within 8 bits (wraps on overflow).
final list = Uint8List(1);
list[0] = value;

if (list[0] != value) {
throw FormatException(
"Value '$collapsedInput' is out of range for xsd:unsignedByte. Must be between $_minValue and $_maxValue.",
"Value '$collapsedInput' is out of range for xsd:unsignedByte.",
);
}
return value;
Expand Down
12 changes: 7 additions & 5 deletions lib/src/codecs/unsigned_byte/unsigned_byte_encoder.dart
Original file line number Diff line number Diff line change
@@ -1,16 +1,18 @@
import 'dart:convert';
import 'dart:typed_data';

/// A [Converter] that converts an [int] to an XSD `unsignedByte` string.
class XsdUnsignedByteEncoder extends Converter<int, String> {
const XsdUnsignedByteEncoder();

static const int _minValue = 0;
static const int _maxValue = 255;

@override
String convert(int input) {
if (input < _minValue || input > _maxValue) {
// Use Uint8List to validate that the value fits within 8 bits (wraps on overflow).
final list = Uint8List(1);
list[0] = input;
if (list[0] != input) {
throw FormatException(
"Value '$input' is out of range for xsd:unsignedByte. Must be between $_minValue and $_maxValue.",
"Value '$input' is out of range for xsd:unsignedByte.",
);
}
return input.toString();
Expand Down
8 changes: 4 additions & 4 deletions lib/src/codecs/unsigned_short/unsigned_short_codec.dart
Original file line number Diff line number Diff line change
Expand Up @@ -3,12 +3,12 @@ import 'dart:convert';
import 'unsigned_short_decoder.dart';
import 'unsigned_short_encoder.dart';

class XmlUnsignedShortCodec extends Codec<int, String> {
const XmlUnsignedShortCodec();
class XsdUnsignedShortCodec extends Codec<int, String> {
const XsdUnsignedShortCodec();

@override
Converter<String, int> get decoder => const XmlUnsignedShortDecoder();
Converter<String, int> get decoder => const XsdUnsignedShortDecoder();

@override
Converter<int, String> get encoder => const XmlUnsignedShortEncoder();
Converter<int, String> get encoder => const XsdUnsignedShortEncoder();
}
16 changes: 9 additions & 7 deletions lib/src/codecs/unsigned_short/unsigned_short_decoder.dart
Original file line number Diff line number Diff line change
@@ -1,12 +1,10 @@
import 'dart:convert';
import 'dart:typed_data';

import '../../helpers/whitespace.dart';

class XmlUnsignedShortDecoder extends Converter<String, int> {
const XmlUnsignedShortDecoder();

static const int _minValue = 0;
static const int _maxValue = 65535;
class XsdUnsignedShortDecoder extends Converter<String, int> {
const XsdUnsignedShortDecoder();

@override
int convert(String input) {
Expand All @@ -22,9 +20,13 @@ class XmlUnsignedShortDecoder extends Converter<String, int> {
throw FormatException('The input "$str" is not a valid integer.');
}

if (value < _minValue || value > _maxValue) {
// Use Uint16List to validate that the value fits within 16 bits (wraps on overflow).
final list = Uint16List(1);
list[0] = value;

if (list[0] != value) {
throw FormatException(
'The value "$value" must be between $_minValue and $_maxValue.',
'The value "$value" is out of range for xsd:unsignedShort.',
);
}

Expand Down
15 changes: 8 additions & 7 deletions lib/src/codecs/unsigned_short/unsigned_short_encoder.dart
Original file line number Diff line number Diff line change
@@ -1,16 +1,17 @@
import 'dart:convert';
import 'dart:typed_data';

class XmlUnsignedShortEncoder extends Converter<int, String> {
const XmlUnsignedShortEncoder();

static const int _minValue = 0;
static const int _maxValue = 65535;
class XsdUnsignedShortEncoder extends Converter<int, String> {
const XsdUnsignedShortEncoder();

@override
String convert(int input) {
if (input < _minValue || input > _maxValue) {
// Use Uint16List to validate that the value fits within 16 bits (wraps on overflow).
final list = Uint16List(1);
list[0] = input;
if (list[0] != input) {
throw FormatException(
'The value "$input" must be between $_minValue and $_maxValue.',
'The value "$input" is out of range for xsd:unsignedShort.',
);
}

Expand Down
6 changes: 3 additions & 3 deletions test/codecs/unsigned_short_codec_test.dart
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,8 @@ import 'package:test/test.dart';
import 'package:xsd/src/codecs/unsigned_short/unsigned_short_codec.dart';

void main() {
test('XML Unsigned Short Codec -> Decode', () {
const codec = XmlUnsignedShortCodec();
test('XSD Unsigned Short Codec -> Decode', () {
const codec = XsdUnsignedShortCodec();
final decoder = codec.decoder;

expect(decoder.convert('12345'), equals(12345));
Expand All @@ -16,7 +16,7 @@ void main() {
});

test('XML Unsigned Short Codec -> Encode', () {
const codec = XmlUnsignedShortCodec();
const codec = XsdUnsignedShortCodec();
final encoder = codec.encoder;

expect(encoder.convert(12345), equals('12345'));
Expand Down