Skip to content

Commit 0ae2ac1

Browse files
stereotype441Commit Queue
authored and
Commit Queue
committed
Language test of record demotion behavior.
When a local variable is promoted to a record type, and then an assignment statement is used to assign a record literal to that local variable, if the fields of the new record literal are not assignable to the fields of the promoted record type, that's not a problem; both the analyzer and front end agree that the local variable is simply demoted. But the spec implies that if the old and new record _shapes_ are the same, then a compile-time error will occur instead of a demotion. I've created dart-lang/language#3613 to bring the spec in line with the implementations. This test demonstrates the current behavior of the implementations, and makes sure that it doesn't regress. Change-Id: I0eacd7ca7f6579a35dbc34687113a2112418f368 Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/352462 Reviewed-by: Bob Nystrom <rnystrom@google.com> Commit-Queue: Paul Berry <paulberry@google.com>
1 parent c9e2b01 commit 0ae2ac1

File tree

1 file changed

+72
-0
lines changed

1 file changed

+72
-0
lines changed
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,72 @@
1+
// Copyright (c) 2024, the Dart project authors. Please see the AUTHORS file
2+
// for details. All rights reserved. Use of this source code is governed by a
3+
// BSD-style license that can be found in the LICENSE file.
4+
5+
/// Test that if an assignment is made to a local variable that's been promoted
6+
/// to a record type, and the newly assigned value doesn't match the previously
7+
/// promoted type, no error occurs (the variable is simply demoted).
8+
9+
import '../static_type_helper.dart';
10+
11+
void testPositionalFieldTypeMismatch(Object o) {
12+
if (o is (int,)) {
13+
o.expectStaticType<Exactly<(int,)>>();
14+
// Note: prior to https://github.com/dart-lang/language/pull/3613 this would
15+
// have been a compile-time error, since there is no coercion from `String`
16+
// to `int`.
17+
o = ('',)..expectStaticType<Exactly<(String,)>>();
18+
o.expectStaticType<Exactly<Object>>();
19+
}
20+
}
21+
22+
void testNamedFieldTypeMismatch(Object o) {
23+
if (o is ({int f1})) {
24+
o.expectStaticType<Exactly<({int f1})>>();
25+
// Note: prior to https://github.com/dart-lang/language/pull/3613 this would
26+
// have been a compile-time error, since there is no coercion from `String`
27+
// to `int`.
28+
o = (f1: '')..expectStaticType<Exactly<({String f1})>>();
29+
o.expectStaticType<Exactly<Object>>();
30+
}
31+
}
32+
33+
void testAdditionalPositionalField(Object o) {
34+
if (o is (int,)) {
35+
o.expectStaticType<Exactly<(int,)>>();
36+
o = (1, 2)..expectStaticType<Exactly<(int, int)>>();
37+
o.expectStaticType<Exactly<Object>>();
38+
}
39+
}
40+
41+
void testAdditionalNamedField(Object o) {
42+
if (o is ({int f1})) {
43+
o.expectStaticType<Exactly<({int f1})>>();
44+
o = (f1: 1, f2: 2)..expectStaticType<Exactly<({int f1, int f2})>>();
45+
o.expectStaticType<Exactly<Object>>();
46+
}
47+
}
48+
49+
void testMissingPositionalField(Object o) {
50+
if (o is (int, int)) {
51+
o.expectStaticType<Exactly<(int, int)>>();
52+
o = (1,);
53+
o.expectStaticType<Exactly<Object>>();
54+
}
55+
}
56+
57+
void testMissingNamedField(Object o) {
58+
if (o is ({int f1, int f2})) {
59+
o.expectStaticType<Exactly<({int f1, int f2})>>();
60+
o = (f1: 1);
61+
o.expectStaticType<Exactly<Object>>();
62+
}
63+
}
64+
65+
main() {
66+
testPositionalFieldTypeMismatch((1,));
67+
testNamedFieldTypeMismatch((f1: 1));
68+
testAdditionalPositionalField((1,));
69+
testAdditionalNamedField((f1: 1));
70+
testMissingPositionalField((1, 2));
71+
testMissingNamedField((f1: 1, f2: 2));
72+
}

0 commit comments

Comments
 (0)