Unverified Commit 8bec125a authored by Michael Goderbauer's avatar Michael Goderbauer Committed by GitHub

Avoid analyzing API example code twice, clean-up (#103548)

parent 2b19ecdc
......@@ -171,10 +171,10 @@ Future<void> run(List<String> arguments) async {
...arguments,
]);
// Analyze all the sample code in the repo.
print('$clock Sample code...');
// Analyze the code in `{@tool snippet}` sections in the repo.
print('$clock Snippet code...');
await runCommand(dart,
<String>[path.join(flutterRoot, 'dev', 'bots', 'analyze_sample_code.dart'), '--verbose'],
<String>[path.join(flutterRoot, 'dev', 'bots', 'analyze_snippet_code.dart'), '--verbose'],
workingDirectory: flutterRoot,
);
......
......@@ -25,7 +25,6 @@ function generate_docs() {
# Install and activate the snippets tool, which resides in the
# assets-for-api-docs repo:
# https://github.com/flutter/assets-for-api-docs/tree/master/packages/snippets
# >>> If you update this version, also update it in dev/bots/analyze_sample_code.dart <<<
"$DART" pub global activate snippets 0.2.5
# This script generates a unified doc set, and creates
......
......@@ -11,7 +11,7 @@ library dart.ui;
/// Annotation used by Flutter's Dart compiler to indicate that an
/// [Object.toString] override should not be replaced with a supercall.
///
/// {@tool sample --template=stateless_widget_material}
/// {@tool snippet}
/// A sample if using keepToString to prevent replacement by a supercall.
///
/// ```dart
......
......@@ -2,7 +2,7 @@
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.
// This file is used by ../analyze_sample_code_test.dart, which depends on the
// This file is used by ../analyze_snippet_code_test.dart, which depends on the
// precise contents (including especially the comments) of this file.
// Examples can assume:
......@@ -34,7 +34,7 @@
/// ```
/// {@end-tool}
///
/// {@tool dartpad --template=stateless_widget_material}
/// {@tool snippet}
/// Bla blabla blabla some [Text] when the `_blabla` blabla blabla is true, and
/// blabla it when it is blabla:
///
......@@ -121,7 +121,7 @@
/// ```
/// {@end-tool}
///
/// {@tool dartpad --template=stateless_widget_material}
/// {@tool snippet}
/// Dartpad with null-safe syntax
///
/// ```dart preamble
......
......@@ -14,58 +14,58 @@ void main() {
return;
}
test('analyze_sample_code smoke test', () {
test('analyze_snippet_code smoke test', () {
final ProcessResult process = Process.runSync(
'../../bin/cache/dart-sdk/bin/dart',
<String>['analyze_sample_code.dart', '--no-include-dart-ui', 'test/analyze-sample-code-test-input'],
<String>['analyze_snippet_code.dart', '--no-include-dart-ui', 'test/analyze-snippet-code-test-input'],
);
final List<String> stdoutLines = process.stdout.toString().split('\n');
final List<String> stderrLines = process.stderr.toString().split('\n');
expect(process.exitCode, isNot(equals(0)));
expect(stderrLines, containsAll(<Object>[
'In sample starting at dev/bots/test/analyze-sample-code-test-input/known_broken_documentation.dart:125: child: Text(title),',
'dev/bots/test/analyze-snippet-code-test-input/known_broken_documentation.dart:138:25: child: Text(title),',
matches(RegExp(r">>> error: The final variable 'title' can't be read because (it is|it's) potentially unassigned at this point \(read_potentially_unassigned_final\)")),
'dev/bots/test/analyze-sample-code-test-input/known_broken_documentation.dart:30:9: new Opacity(',
'dev/bots/test/analyze-snippet-code-test-input/known_broken_documentation.dart:30:9: new Opacity(',
'>>> info: Unnecessary new keyword (unnecessary_new)',
'dev/bots/test/analyze-sample-code-test-input/known_broken_documentation.dart:62:9: new Opacity(',
'dev/bots/test/analyze-snippet-code-test-input/known_broken_documentation.dart:62:9: new Opacity(',
'>>> info: Unnecessary new keyword (unnecessary_new)',
"dev/bots/test/analyze-sample-code-test-input/known_broken_documentation.dart:111:9: final String? bar = 'Hello';",
"dev/bots/test/analyze-snippet-code-test-input/known_broken_documentation.dart:111:9: final String? bar = 'Hello';",
'>>> info: Prefer const over final for declarations (prefer_const_declarations)',
'dev/bots/test/analyze-sample-code-test-input/known_broken_documentation.dart:112:9: final int foo = null;',
'dev/bots/test/analyze-snippet-code-test-input/known_broken_documentation.dart:112:9: final int foo = null;',
'>>> info: Prefer const over final for declarations (prefer_const_declarations)',
'dev/bots/test/analyze-sample-code-test-input/known_broken_documentation.dart:112:25: final int foo = null;',
'dev/bots/test/analyze-snippet-code-test-input/known_broken_documentation.dart:112:25: final int foo = null;',
">>> error: A value of type 'Null' can't be assigned to a variable of type 'int' (invalid_assignment)",
'dev/bots/test/analyze-sample-code-test-input/known_broken_documentation.dart:120:24: const SizedBox(),',
'>>> error: Unexpected comma at end of sample code. (missing_identifier)',
'Found 2 sample code errors.',
'dev/bots/test/analyze-snippet-code-test-input/known_broken_documentation.dart:120:24: const SizedBox(),',
'>>> error: Unexpected comma at end of snippet code. (missing_identifier)',
'Found 1 snippet code errors.',
]));
expect(stdoutLines, containsAll(<String>[
'Found 9 snippet code blocks, 0 sample code sections, and 2 dartpad sections.',
'Starting analysis of code samples.',
'Found 13 snippet code blocks',
'Starting analysis of code snippets.',
]));
});
test('Analyzes dart:ui code', () {
final ProcessResult process = Process.runSync(
'../../bin/cache/dart-sdk/bin/dart',
<String>[
'analyze_sample_code.dart',
'--dart-ui-location=test/analyze-sample-code-test-dart-ui',
'test/analyze-sample-code-test-input',
'analyze_snippet_code.dart',
'--dart-ui-location=test/analyze-snippet-code-test-dart-ui',
'test/analyze-snippet-code-test-input',
],
);
final List<String> stdoutLines = process.stdout.toString().split('\n');
final List<String> stderrLines = process.stderr.toString().split('\n');
expect(process.exitCode, isNot(equals(0)));
expect(stderrLines, containsAll(<String>[
'In sample starting at dev/bots/test/analyze-sample-code-test-dart-ui/ui.dart:15:class MyStatelessWidget extends StatelessWidget {',
">>> error: Missing concrete implementation of 'StatelessWidget.build' (non_abstract_class_inherits_abstract_member)",
'In sample starting at dev/bots/test/analyze-sample-code-test-dart-ui/ui.dart:15:class MyStringBuffer {',
">>> error: Classes can't be declared inside other classes (class_in_class)",
'dev/bots/test/analyze-snippet-code-test-dart-ui/ui.dart:19:11: error;',
">>> error: Variables must be declared using the keywords 'const', 'final', 'var' or a type name (missing_const_final_var_or_type)",
'dev/bots/test/analyze-snippet-code-test-dart-ui/ui.dart:23:11: @keepToString',
">>> error: Undefined name 'keepToString' used as an annotation (undefined_annotation)",
]));
expect(stdoutLines, containsAll(<String>[
// There is one sample code section in the test's dummy dart:ui code.
'Found 9 snippet code blocks, 1 sample code sections, and 2 dartpad sections.',
'Starting analysis of code samples.',
// There is one snippet code section in the test's dummy dart:ui code.
'Found 14 snippet code blocks',
'Starting analysis of code snippets.',
]));
});
}
# This file is also used by dev/bots/analyze_snippet_code.dart to analyze code snippets (`{@tool snippet}` sections).
include: ../../analysis_options.yaml
linter:
rules:
# Samples want to print things pretty often.
avoid_print: false
# TODO(goderbauer): enable when super params are more established and
# seeing them in the API samples is no longer surprising,
# https://github.com/flutter/flutter/issues/101068
......
# This file is also used by dev/bots/analyze_snippet_code.dart to analyze code snippets (`{@tool snippet}` sections).
name: flutter_api_samples
description: API code samples for the Flutter repo.
publish_to: 'none'
......
......@@ -3213,7 +3213,6 @@ mixin Diagnosticable {
/// value: isCurrent,
/// ifTrue: 'active',
/// ifFalse: 'inactive',
/// showName: false,
/// ));
///
/// properties.add(DiagnosticsProperty<bool>('keepAlive', keepAlive));
......
......@@ -171,7 +171,7 @@ class Checkbox extends StatefulWidget {
/// Checkbox(
/// value: true,
/// onChanged: (_){},
/// fillColor: MaterialStateProperty.resolveWith<Color>((states) {
/// fillColor: MaterialStateProperty.resolveWith<Color>((Set<MaterialState> states) {
/// if (states.contains(MaterialState.disabled)) {
/// return Colors.orange.withOpacity(.32);
/// }
......
......@@ -200,7 +200,7 @@ class Radio<T> extends StatefulWidget {
/// value: 1,
/// groupValue: 1,
/// onChanged: (_){},
/// fillColor: MaterialStateProperty.resolveWith<Color>((states) {
/// fillColor: MaterialStateProperty.resolveWith<Color>((Set<MaterialState> states) {
/// if (states.contains(MaterialState.disabled)) {
/// return Colors.orange.withOpacity(.32);
/// }
......
......@@ -238,7 +238,7 @@ class Switch extends StatelessWidget {
/// Switch(
/// value: true,
/// onChanged: (_) => true,
/// thumbColor: MaterialStateProperty.resolveWith<Color>((states) {
/// thumbColor: MaterialStateProperty.resolveWith<Color>((Set<MaterialState> states) {
/// if (states.contains(MaterialState.disabled)) {
/// return Colors.orange.withOpacity(.48);
/// }
......@@ -279,7 +279,7 @@ class Switch extends StatelessWidget {
/// Switch(
/// value: true,
/// onChanged: (_) => true,
/// thumbColor: MaterialStateProperty.resolveWith<Color>((states) {
/// thumbColor: MaterialStateProperty.resolveWith<Color>((Set<MaterialState> states) {
/// if (states.contains(MaterialState.disabled)) {
/// return Colors.orange.withOpacity(.48);
/// }
......
......@@ -201,9 +201,7 @@ enum MaterialTapTargetSize {
/// ```dart
/// MaterialApp(
/// theme: ThemeData(
/// colorScheme: ColorScheme.fromSwatch(
/// primarySwatch: Colors.blue,
/// ).copyWith(
/// colorScheme: ColorScheme.fromSwatch().copyWith(
/// secondary: Colors.green,
/// ),
/// textTheme: const TextTheme(bodyText2: TextStyle(color: Colors.purple)),
......
......@@ -267,20 +267,20 @@ abstract class BoxBorder extends ShapeBorder {
/// Container(
/// decoration: const BoxDecoration(
/// border: Border(
/// top: BorderSide(width: 1.0, color: Color(0xFFFFFFFF)),
/// left: BorderSide(width: 1.0, color: Color(0xFFFFFFFF)),
/// right: BorderSide(width: 1.0, color: Color(0xFF000000)),
/// bottom: BorderSide(width: 1.0, color: Color(0xFF000000)),
/// top: BorderSide(color: Color(0xFFFFFFFF)),
/// left: BorderSide(color: Color(0xFFFFFFFF)),
/// right: BorderSide(),
/// bottom: BorderSide(),
/// ),
/// ),
/// child: Container(
/// padding: const EdgeInsets.symmetric(horizontal: 20.0, vertical: 2.0),
/// decoration: const BoxDecoration(
/// border: Border(
/// top: BorderSide(width: 1.0, color: Color(0xFFDFDFDF)),
/// left: BorderSide(width: 1.0, color: Color(0xFFDFDFDF)),
/// right: BorderSide(width: 1.0, color: Color(0xFF7F7F7F)),
/// bottom: BorderSide(width: 1.0, color: Color(0xFF7F7F7F)),
/// top: BorderSide(color: Color(0xFFDFDFDF)),
/// left: BorderSide(color: Color(0xFFDFDFDF)),
/// right: BorderSide(color: Color(0xFF7F7F7F)),
/// bottom: BorderSide(color: Color(0xFF7F7F7F)),
/// ),
/// color: Color(0xFFBFBFBF),
/// ),
......
......@@ -49,7 +49,6 @@ import 'image_provider.dart';
/// fit: BoxFit.cover,
/// ),
/// border: Border.all(
/// color: Colors.black,
/// width: 8,
/// ),
/// borderRadius: BorderRadius.circular(12),
......
......@@ -857,8 +857,6 @@ class RadialGradient extends Gradient {
/// decoration: const BoxDecoration(
/// gradient: SweepGradient(
/// center: FractionalOffset.center,
/// startAngle: 0.0,
/// endAngle: math.pi * 2,
/// colors: <Color>[
/// Color(0xFF4285F4), // blue
/// Color(0xFF34A853), // green
......@@ -883,8 +881,6 @@ class RadialGradient extends Gradient {
/// decoration: const BoxDecoration(
/// gradient: SweepGradient(
/// center: FractionalOffset.center,
/// startAngle: 0.0,
/// endAngle: math.pi * 2,
/// colors: <Color>[
/// Color(0xFF4285F4), // blue
/// Color(0xFF34A853), // green
......
......@@ -118,7 +118,6 @@ class AnnotationResult<T> {
/// offset,
/// Offset.zero & size,
/// super.paint,
/// clipBehavior: Clip.hardEdge,
/// oldLayer: _clipRectLayer.layer,
/// );
/// }
......
......@@ -2098,7 +2098,6 @@ class SemanticsNode extends AbstractNode with DiagnosticableTreeMixin {
/// ```dart
/// PhysicalModel( // A
/// color: Colors.amber,
/// elevation: 0.0,
/// child: Semantics(
/// explicitChildNodes: true,
/// child: const PhysicalModel( // B
......
......@@ -198,6 +198,9 @@ class MethodChannel {
///
/// ```dart
/// class Music {
/// // Class cannot be instantiated.
/// const Music._();
///
/// static const MethodChannel _channel = MethodChannel('music');
///
/// static Future<bool> isLicensed() async {
......@@ -213,7 +216,7 @@ class MethodChannel {
/// // the actual values involved would support such a typed container.
/// // The correct type cannot be inferred with any value of `T`.
/// final List<dynamic>? songs = await _channel.invokeMethod<List<dynamic>>('getSongs');
/// return songs?.map(Song.fromJson).toList() ?? <Song>[];
/// return songs?.cast<Map<String, Object?>>().map<Song>(Song.fromJson).toList() ?? <Song>[];
/// }
///
/// static Future<void> play(Song song, double volume) async {
......@@ -225,7 +228,7 @@ class MethodChannel {
/// 'volume': volume,
/// });
/// } on PlatformException catch (e) {
/// throw 'Unable to play ${song.title}: ${e.message}';
/// throw ArgumentError('Unable to play ${song.title}: ${e.message}');
/// }
/// }
/// }
......@@ -237,8 +240,8 @@ class MethodChannel {
/// final String title;
/// final String artist;
///
/// static Song fromJson(dynamic json) {
/// return Song(json['id'] as String, json['title'] as String, json['artist'] as String);
/// static Song fromJson(Map<String, Object?> json) {
/// return Song(json['id']! as String, json['title']! as String, json['artist']! as String);
/// }
/// }
/// ```
......
......@@ -44,7 +44,6 @@ enum CrossFadeState {
/// ```dart
/// Widget defaultLayoutBuilder(Widget topChild, Key topChildKey, Widget bottomChild, Key bottomChildKey) {
/// return Stack(
/// fit: StackFit.loose,
/// children: <Widget>[
/// Positioned(
/// key: bottomChildKey,
......
......@@ -4566,7 +4566,6 @@ class Flex extends MultiChildRenderObjectWidget {
/// ),
/// Expanded(
/// child: FittedBox(
/// fit: BoxFit.contain, // otherwise the logo will be tiny
/// child: FlutterLogo(),
/// ),
/// ),
......@@ -4765,7 +4764,6 @@ class Row extends Flex {
/// Text('Craft beautiful UIs'),
/// Expanded(
/// child: FittedBox(
/// fit: BoxFit.contain, // otherwise the logo will be tiny
/// child: FlutterLogo(),
/// ),
/// ),
......
......@@ -11,7 +11,7 @@ import 'debug.dart';
import 'framework.dart';
// Examples can assume:
// class Intl { static String message(String s, { String? name, String? locale }) => ''; }
// class Intl { Intl._(); static String message(String s, { String? name, String? locale }) => ''; }
// Future<void> initializeMessages(String locale) => Future<void>.value();
// Used by loadAll() to record LocalizationsDelegate.load() futures we're
......
......@@ -108,7 +108,6 @@ import 'viewport.dart';
/// );
/// }
/// }
///
/// ```
/// {@end-tool}
class PageController extends ScrollController {
......
......@@ -27,7 +27,7 @@ import 'scroll_controller.dart';
import 'transitions.dart';
// Examples can assume:
// dynamic routeObserver;
// late RouteObserver<Route<void>> routeObserver;
// late NavigatorState navigator;
// late BuildContext context;
// Future<bool> askTheUserIfTheyAreSure() async { return true; }
......@@ -1058,7 +1058,7 @@ abstract class ModalRoute<T> extends TransitionRoute<T> with LocalHistoryRoute<T
/// defined in the same way.
///
/// ```dart
/// PageRouteBuilder(
/// PageRouteBuilder<void>(
/// pageBuilder: (BuildContext context,
/// Animation<double> animation,
/// Animation<double> secondaryAnimation,
......@@ -1105,7 +1105,7 @@ abstract class ModalRoute<T> extends TransitionRoute<T> with LocalHistoryRoute<T
/// route has been popped off.
///
/// ```dart
/// PageRouteBuilder(
/// PageRouteBuilder<void>(
/// pageBuilder: (BuildContext context,
/// Animation<double> animation,
/// Animation<double> secondaryAnimation,
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment