mirror of
https://github.com/dart-lang/sdk
synced 2024-10-02 23:59:16 +00:00
Add InternetAddress.tryParse
Closes #40692 Allows a better pattern for parsing user input than catching an `ArgumentError`. - Add a new static method to InternetAddress and implement it in all patch files. - Add tests which match the tests for the constructor. Change-Id: Idc76fc4875578f7a381219c0e7e12d1931d98fd8 Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/136406 Commit-Queue: Nate Bosch <nbosch@google.com> Reviewed-by: Lasse R.H. Nielsen <lrn@google.com> Auto-Submit: Nate Bosch <nbosch@google.com>
This commit is contained in:
parent
cea45271b3
commit
9b34bee90b
|
@ -15,6 +15,7 @@
|
|||
|
||||
* Class `OSError` now implements `Exception`. This change means `OSError` will
|
||||
now be caught in catch clauses catching `Exception`s.
|
||||
* Added `InternetAddress.tryParse`.
|
||||
|
||||
### Tools
|
||||
|
||||
|
|
|
@ -427,6 +427,11 @@ class InternetAddress {
|
|||
InternetAddress address, String host) {
|
||||
throw UnsupportedError("InternetAddress._cloneWithNewHost");
|
||||
}
|
||||
|
||||
@patch
|
||||
static InternetAddress tryParse(String address) {
|
||||
throw UnsupportedError("InternetAddress.tryParse");
|
||||
}
|
||||
}
|
||||
|
||||
@patch
|
||||
|
|
|
@ -427,6 +427,11 @@ class InternetAddress {
|
|||
InternetAddress address, String host) {
|
||||
throw new UnsupportedError("InternetAddress._cloneWithNewHost");
|
||||
}
|
||||
|
||||
@patch
|
||||
static InternetAddress tryParse(String address) {
|
||||
throw new UnsupportedError("InternetAddress.tryParse");
|
||||
}
|
||||
}
|
||||
|
||||
@patch
|
||||
|
|
|
@ -92,6 +92,11 @@ class InternetAddress {
|
|||
InternetAddress address, String host) {
|
||||
return (address as _InternetAddress)._cloneWithNewHost(host);
|
||||
}
|
||||
|
||||
@patch
|
||||
static InternetAddress tryParse(String address) {
|
||||
return _InternetAddress.tryParse(address);
|
||||
}
|
||||
}
|
||||
|
||||
@patch
|
||||
|
@ -253,6 +258,18 @@ class _InternetAddress implements InternetAddress {
|
|||
}
|
||||
}
|
||||
|
||||
static _InternetAddress tryParse(String address) {
|
||||
if (address == null) {
|
||||
throw ArgumentError("Invalid internet address $address");
|
||||
}
|
||||
var addressBytes = _parse(address);
|
||||
if (addressBytes == null) return null;
|
||||
var type = addressBytes.length == _IPv4AddrLength
|
||||
? InternetAddressType.IPv4
|
||||
: InternetAddressType.IPv6;
|
||||
return _InternetAddress(type, address, null, addressBytes);
|
||||
}
|
||||
|
||||
factory _InternetAddress.fixed(int id) {
|
||||
switch (id) {
|
||||
case _addressLoopbackIPv4:
|
||||
|
|
|
@ -215,6 +215,12 @@ abstract class InternetAddress {
|
|||
*/
|
||||
external static InternetAddress _cloneWithNewHost(
|
||||
InternetAddress address, String host);
|
||||
|
||||
/// Attempts to parse [address] as a numeric address.
|
||||
///
|
||||
/// Returns `null` if [address] is not a numeric IPv4 (dotted-decimal
|
||||
/// notation) or IPv6 (hexadecimal representation) address.
|
||||
external static InternetAddress tryParse(String address);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -425,6 +425,11 @@ class InternetAddress {
|
|||
InternetAddress address, String host) {
|
||||
throw UnsupportedError("InternetAddress._cloneWithNewHost");
|
||||
}
|
||||
|
||||
@patch
|
||||
static InternetAddress? tryParse(String address) {
|
||||
throw UnsupportedError("InternetAddress.tryParse");
|
||||
}
|
||||
}
|
||||
|
||||
@patch
|
||||
|
|
|
@ -425,6 +425,11 @@ class InternetAddress {
|
|||
InternetAddress address, String host) {
|
||||
throw new UnsupportedError("InternetAddress._cloneWithNewHost");
|
||||
}
|
||||
|
||||
@patch
|
||||
static InternetAddress? tryParse(String address) {
|
||||
throw UnsupportedError("InternetAddress.tryParse");
|
||||
}
|
||||
}
|
||||
|
||||
@patch
|
||||
|
|
|
@ -7,7 +7,7 @@
|
|||
/// patches of that library. We plan to change this when we have a shared front
|
||||
/// end and simply use parts.
|
||||
|
||||
import "dart:_internal" show VMLibraryHooks, patch;
|
||||
import "dart:_internal" show VMLibraryHooks, patch, checkNotNullable;
|
||||
|
||||
import "dart:async"
|
||||
show
|
||||
|
|
|
@ -89,6 +89,11 @@ class InternetAddress {
|
|||
InternetAddress address, String host) {
|
||||
return (address as _InternetAddress)._cloneWithNewHost(host);
|
||||
}
|
||||
|
||||
@patch
|
||||
static InternetAddress? tryParse(String address) {
|
||||
return _InternetAddress.tryParse(address);
|
||||
}
|
||||
}
|
||||
|
||||
@patch
|
||||
|
@ -255,6 +260,16 @@ class _InternetAddress implements InternetAddress {
|
|||
}
|
||||
}
|
||||
|
||||
static _InternetAddress? tryParse(String address) {
|
||||
checkNotNullable(address, "address");
|
||||
var addressBytes = _parse(address);
|
||||
if (addressBytes == null) return null;
|
||||
var type = addressBytes.length == _IPv4AddrLength
|
||||
? InternetAddressType.IPv4
|
||||
: InternetAddressType.IPv6;
|
||||
return _InternetAddress(type, address, null, addressBytes);
|
||||
}
|
||||
|
||||
factory _InternetAddress.fixed(int id) {
|
||||
switch (id) {
|
||||
case _addressLoopbackIPv4:
|
||||
|
|
|
@ -213,6 +213,12 @@ abstract class InternetAddress {
|
|||
*/
|
||||
external static InternetAddress _cloneWithNewHost(
|
||||
InternetAddress address, String host);
|
||||
|
||||
/// Attempts to parse [address] as a numeric address.
|
||||
///
|
||||
/// Returns `null` If [address] is not a numeric IPv4 (dotted-decimal
|
||||
/// notation) or IPv6 (hexadecimal representation) address.
|
||||
external static InternetAddress? tryParse(String address);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -74,6 +74,56 @@ void testConstructor() {
|
|||
Expect.throwsArgumentError(() => new InternetAddress("::FFFF::1"));
|
||||
}
|
||||
|
||||
void testTryParse() {
|
||||
var loopback4 = InternetAddress.tryParse("127.0.0.1")!;
|
||||
Expect.equals(InternetAddressType.IPv4, loopback4.type);
|
||||
Expect.equals("127.0.0.1", loopback4.host);
|
||||
Expect.equals("127.0.0.1", loopback4.address);
|
||||
Expect.isFalse(loopback4.isMulticast);
|
||||
|
||||
var loopback6 = InternetAddress.tryParse("::1")!;
|
||||
Expect.equals(InternetAddressType.IPv6, loopback6.type);
|
||||
Expect.equals("::1", loopback6.host);
|
||||
Expect.equals("::1", loopback6.address);
|
||||
Expect.isFalse(loopback6.isMulticast);
|
||||
|
||||
var ip4 = InternetAddress.tryParse("10.20.30.40")!;
|
||||
Expect.equals(InternetAddressType.IPv4, ip4.type);
|
||||
Expect.equals("10.20.30.40", ip4.host);
|
||||
Expect.equals("10.20.30.40", ip4.address);
|
||||
Expect.isFalse(ip4.isMulticast);
|
||||
|
||||
var ip6 = InternetAddress.tryParse("10:20::30:40")!;
|
||||
Expect.equals(InternetAddressType.IPv6, ip6.type);
|
||||
Expect.equals("10:20::30:40", ip6.host);
|
||||
Expect.equals("10:20::30:40", ip6.address);
|
||||
Expect.isFalse(ip6.isMulticast);
|
||||
|
||||
var multicast4 = InternetAddress.tryParse("224.1.2.3")!;
|
||||
Expect.equals(InternetAddressType.IPv4, multicast4.type);
|
||||
Expect.isTrue(multicast4.isMulticast);
|
||||
|
||||
var multicast6 = InternetAddress.tryParse("FF00::1:2:3")!;
|
||||
Expect.equals(InternetAddressType.IPv6, multicast6.type);
|
||||
Expect.isTrue(multicast6.isMulticast);
|
||||
|
||||
var lowercase = InternetAddress.tryParse("ff00::1:2:3")!;
|
||||
Expect.equals(InternetAddressType.IPv6, lowercase.type);
|
||||
Expect.equals("ff00::1:2:3", lowercase.host);
|
||||
Expect.equals("ff00::1:2:3", lowercase.address);
|
||||
|
||||
Expect.isNull(InternetAddress.tryParse("1.2.3"));
|
||||
Expect.isNull(InternetAddress.tryParse("1.2.3.4.5"));
|
||||
Expect.isNull(InternetAddress.tryParse("192.168.256.0"));
|
||||
Expect.isNull(InternetAddress.tryParse("192.168.999.0"));
|
||||
Expect.isNull(InternetAddress.tryParse("1.-2.3.4"));
|
||||
Expect.isNull(InternetAddress.tryParse("01.02.03.04"));
|
||||
Expect.isNull(InternetAddress.tryParse(""));
|
||||
Expect.isNull(InternetAddress.tryParse("FFFG::0"));
|
||||
Expect.isNull(InternetAddress.tryParse("FFF@::0"));
|
||||
Expect.isNull(InternetAddress.tryParse("::FFFF::1"));
|
||||
}
|
||||
|
||||
void testEquality() {
|
||||
Expect.equals(
|
||||
new InternetAddress("127.0.0.1"), new InternetAddress("127.0.0.1"));
|
||||
|
@ -163,6 +213,7 @@ void testRawPath() {
|
|||
void main() {
|
||||
testDefaultAddresses();
|
||||
testConstructor();
|
||||
testTryParse();
|
||||
testEquality();
|
||||
testLookup();
|
||||
testReverseLookup();
|
||||
|
|
|
@ -74,6 +74,56 @@ void testConstructor() {
|
|||
Expect.throwsArgumentError(() => new InternetAddress("::FFFF::1"));
|
||||
}
|
||||
|
||||
void testTryParse() {
|
||||
var loopback4 = InternetAddress.tryParse("127.0.0.1");
|
||||
Expect.equals(InternetAddressType.IPv4, loopback4.type);
|
||||
Expect.equals("127.0.0.1", loopback4.host);
|
||||
Expect.equals("127.0.0.1", loopback4.address);
|
||||
Expect.isFalse(loopback4.isMulticast);
|
||||
|
||||
var loopback6 = InternetAddress.tryParse("::1");
|
||||
Expect.equals(InternetAddressType.IPv6, loopback6.type);
|
||||
Expect.equals("::1", loopback6.host);
|
||||
Expect.equals("::1", loopback6.address);
|
||||
Expect.isFalse(loopback6.isMulticast);
|
||||
|
||||
var ip4 = InternetAddress.tryParse("10.20.30.40");
|
||||
Expect.equals(InternetAddressType.IPv4, ip4.type);
|
||||
Expect.equals("10.20.30.40", ip4.host);
|
||||
Expect.equals("10.20.30.40", ip4.address);
|
||||
Expect.isFalse(ip4.isMulticast);
|
||||
|
||||
var ip6 = InternetAddress.tryParse("10:20::30:40");
|
||||
Expect.equals(InternetAddressType.IPv6, ip6.type);
|
||||
Expect.equals("10:20::30:40", ip6.host);
|
||||
Expect.equals("10:20::30:40", ip6.address);
|
||||
Expect.isFalse(ip6.isMulticast);
|
||||
|
||||
var multicast4 = InternetAddress.tryParse("224.1.2.3");
|
||||
Expect.equals(InternetAddressType.IPv4, multicast4.type);
|
||||
Expect.isTrue(multicast4.isMulticast);
|
||||
|
||||
var multicast6 = InternetAddress.tryParse("FF00::1:2:3");
|
||||
Expect.equals(InternetAddressType.IPv6, multicast6.type);
|
||||
Expect.isTrue(multicast6.isMulticast);
|
||||
|
||||
var lowercase = InternetAddress.tryParse("ff00::1:2:3");
|
||||
Expect.equals(InternetAddressType.IPv6, lowercase.type);
|
||||
Expect.equals("ff00::1:2:3", lowercase.host);
|
||||
Expect.equals("ff00::1:2:3", lowercase.address);
|
||||
|
||||
Expect.isNull(InternetAddress.tryParse("1.2.3"));
|
||||
Expect.isNull(InternetAddress.tryParse("1.2.3.4.5"));
|
||||
Expect.isNull(InternetAddress.tryParse("192.168.256.0"));
|
||||
Expect.isNull(InternetAddress.tryParse("192.168.999.0"));
|
||||
Expect.isNull(InternetAddress.tryParse("1.-2.3.4"));
|
||||
Expect.isNull(InternetAddress.tryParse("01.02.03.04"));
|
||||
Expect.isNull(InternetAddress.tryParse(""));
|
||||
Expect.isNull(InternetAddress.tryParse("FFFG::0"));
|
||||
Expect.isNull(InternetAddress.tryParse("FFF@::0"));
|
||||
Expect.isNull(InternetAddress.tryParse("::FFFF::1"));
|
||||
}
|
||||
|
||||
void testEquality() {
|
||||
Expect.equals(
|
||||
new InternetAddress("127.0.0.1"), new InternetAddress("127.0.0.1"));
|
||||
|
@ -162,6 +212,7 @@ void testRawPath() {
|
|||
void main() {
|
||||
testDefaultAddresses();
|
||||
testConstructor();
|
||||
testTryParse();
|
||||
testEquality();
|
||||
testLookup();
|
||||
testReverseLookup();
|
||||
|
|
Loading…
Reference in a new issue