Skip to content

Commit 48d31e1

Browse files
authored
Merge pull request #224 from davidmorgan/really-support-mixins
Pick up field declarations from mixins
2 parents ad130fa + 5cfc61f commit 48d31e1

File tree

8 files changed

+194
-3
lines changed

8 files changed

+194
-3
lines changed

CHANGELOG.md

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,9 @@
11
# Changelog
22

3-
## 4.0.1 (unreleased)
3+
## 4.1.0 (unreleased)
44

55
- Improved annotation handling for corner cases.
6+
- Pick up field declarations from mixins as well as interfaces.
67

78
## 4.0.0
89

built_value_generator/lib/src/fields.dart

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@
44

55
import 'dart:collection';
66
import 'package:analyzer/dart/element/element.dart';
7+
import 'package:analyzer/dart/element/type.dart';
78
import 'package:built_collection/built_collection.dart';
89

910
/// Gets fields, including from interfaces.
@@ -15,8 +16,10 @@ BuiltList<FieldElement> collectFields(ClassElement element) {
1516
// Add fields from this class before interfaces, so they're added to the set
1617
// first below. Re-added fields from interfaces are ignored.
1718
fields.addAll(element.fields);
18-
element.interfaces
19-
.forEach((interface) => fields.addAll(collectFields(interface.element)));
19+
20+
new Set<InterfaceType>.from(element.interfaces)
21+
..addAll(element.mixins)
22+
..forEach((interface) => fields.addAll(collectFields(interface.element)));
2023

2124
// Overridden fields have multiple declarations, so deduplicate by adding
2225
// to a set that compares on field name.

end_to_end_test/lib/polymorphism.dart

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,16 @@ abstract class Fish extends Object
3636
Fish._();
3737
}
3838

39+
// Fields should come via mixins with no need for interfaces.
40+
abstract class Robot extends Object
41+
with Swimmer, Walker
42+
implements Built<Robot, RobotBuilder> {
43+
static Serializer<Robot> get serializer => _$robotSerializer;
44+
45+
factory Robot([updates(RobotBuilder b)]) = _$Robot;
46+
Robot._();
47+
}
48+
3949
abstract class Walker {
4050
int get legs;
4151

end_to_end_test/lib/polymorphism.g.dart

Lines changed: 130 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

end_to_end_test/lib/serializers.dart

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -33,6 +33,7 @@ part 'serializers.g.dart';
3333
NamedFactoryValue,
3434
NestedGenericContainer,
3535
PrimitivesValue,
36+
Robot,
3637
SecondTestEnum,
3738
SimpleValue,
3839
StandardJsonValue,

end_to_end_test/lib/serializers.g.dart

Lines changed: 1 addition & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

end_to_end_test/test/polymorphism_serializer_test.dart

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,27 @@ void main() {
2929
});
3030
});
3131

32+
group('Robot', () {
33+
final data = new Robot((b) => b
34+
..legs = 4
35+
..fins = 3);
36+
final serialized = [
37+
'Robot',
38+
'fins',
39+
3,
40+
'legs',
41+
4,
42+
];
43+
44+
test('can be serialized', () {
45+
expect(serializers.serialize(data), serialized);
46+
});
47+
48+
test('can be deserialized', () {
49+
expect(serializers.deserialize(serialized), data);
50+
});
51+
});
52+
3253
group('HasField', () {
3354
final data = new BuiltList<HasField<dynamic>>([
3455
new HasString((b) => b..field = 'hello'),

end_to_end_test/test/polymorphism_test.dart

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -46,6 +46,30 @@ void main() {
4646
});
4747
});
4848

49+
group('Robot', () {
50+
test('can be instantiated', () {
51+
new Robot((b) => b
52+
..legs = 0
53+
..fins = 2);
54+
});
55+
56+
test('has method from mixin', () {
57+
expect(
58+
new Robot((b) => b
59+
..legs = 0
60+
..fins = 2).canWalk,
61+
false);
62+
});
63+
64+
test('has method from second mixin', () {
65+
expect(
66+
new Robot((b) => b
67+
..legs = 0
68+
..fins = 2).canSwim,
69+
true);
70+
});
71+
});
72+
4973
group('Animal', () {
5074
test('can be used as an interface, including builder', () {
5175
final animals = [

0 commit comments

Comments
 (0)