diff --git a/pkg/analysis_server_plugin/doc/using_plugins.md b/pkg/analysis_server_plugin/doc/using_plugins.md new file mode 100644 index 00000000000..0dce16f21af --- /dev/null +++ b/pkg/analysis_server_plugin/doc/using_plugins.md @@ -0,0 +1,39 @@ +# Using plugins + +This document describes how to enable an analyzer plugin. An analyzer plugin +can be enabled for a given package, so that the plugin can report diagnostics +(lints and warnings) and offer quick fixes. Plugins are enabled via the +`analysis_options.yaml` file under the top-level `plugins` section: + +``` +plugins: + my_plugin: ^1.0.0 +``` + +Note: This is similar to how analyzer plugins are enabled in the [legacy][] +analyzer plugin system. However, in the legacy system, this `plugins` section +is listed under the top-level `analyzer` section. In the new analyzer plugin +system, `plugins` is a top-level section. + +Individual plugins are listed similar to how dependencies are listed in a +`pubspec.yaml` file; they are listed as a key-value pair, with the package name +as the key. The value can either be + +* a package version constraint, in which case the package is downloaded from + https://pub.dev, +* a git dependency, +* an absolute path. + +For example, while developing a plugin locally, it can be enabled as: + +``` +plugins: + my_plugin: + path: /path/to/my_plugin +``` + +Note: after any change is made to the `plugins` section of an +`analysis_options.yaml` file, the Dart Analysis Server must be restarted to see +the effects. + +[legacy]: https://github.com/dart-lang/sdk/blob/main/pkg/analyzer_plugin/doc/tutorial/tutorial.md diff --git a/pkg/analysis_server_plugin/doc/writing_a_plugin.md b/pkg/analysis_server_plugin/doc/writing_a_plugin.md new file mode 100644 index 00000000000..4e37d6f1355 --- /dev/null +++ b/pkg/analysis_server_plugin/doc/writing_a_plugin.md @@ -0,0 +1,67 @@ +# Writing a plugin + +This document describes how to write an analyzer plugin, to provide custom +static analysis, or to offer custom quick fixes in an IDE. + +## The pubspec file + +An analyzer plugin is a Dart package, so let's start with the `pubspec.yaml` file: + +```yaml +name: test_analyzer_plugin +version: 0.0.1 + +environment: + sdk: '>=3.6.0 <4.0.0' + +dependencies: + analysis_server_plugin: any + analyzer: ^7.2.0 +``` + +There is nothing special about this pubspec; note that we need a dependency on +the `analysis_server_plugin` package, and on the `analyzer` package, supporting +at least 7.2.0. The version of the analyzer package needs to move lockstep with +the Dart SDK. For Dart 3.8.0-70.1.beta, `^7.2.0` is a good version constraint. + +## The main Dart file + +One source file is required, at `lib/main.dart`. Here is the basic layout: + +```dart +import 'package:analysis_server_plugin/plugin.dart'; +import 'package:analysis_server_plugin/registry.dart'; + +final plugin = SimplePlugin(); + +class SimplePlugin extends Plugin { + @override + void register(PluginRegistry registry) { + // Here we register analysis rules, and quick fixes. + } +} +``` + +Here we have a class, `SimplePlugin`, which extends the `Plugin` class from the +`analysis_server_plugin` package. This class has one method that we override: +`register`. In the `register` method, we can register analysis rules and quick +fixes (CorrectionProducers). See details in the [writing rules][] doc, and the +writing quick fixes doc (TODO). + +Additionally, we provide a top-level variable in this file called `plugin`, +which is an instance of our `SimplePlugin` class. When a running instance of +the Dart Analysis Server needs to use this analyzer plugin, it generates some +code that needs to _import_ this `lib/main.dart` file, and that references this +`plugin` top-level variable. + +# Debugging a plugin + +If a plugin is not behaving as expected (for example, warnings are not +appearing in the IDE), you can check the [analyzer diagnostics pages][]. If the +plugin isolate has crashed, the "plugins" screen will display the crash. + +`print` cannot be used in plugin code to debug. Instead, writing to a log file +can help in debugging plugin code. + +[writing rules]: https://github.com/dart-lang/sdk/blob/main/pkg/analysis_server_plugin/doc/writing_rules.md +[analyzer diagnostics pages]: https://github.com/dart-lang/sdk/blob/main/pkg/analysis_server/doc/tutorial/instrumentation.md#open-the-analyzer-diagnostics-pages diff --git a/pkg/analysis_server_plugin/doc/writing_rules.md b/pkg/analysis_server_plugin/doc/writing_rules.md index 9e547677439..3155e4dc948 100644 --- a/pkg/analysis_server_plugin/doc/writing_rules.md +++ b/pkg/analysis_server_plugin/doc/writing_rules.md @@ -26,7 +26,7 @@ class MyRule extends AnalysisRule { MyRule() : super( - name: LintNames.prefer_void_to_null, + name: 'my_rule', description: 'A longer description of the rule.', ); @@ -124,6 +124,13 @@ Let's look at each declaration individually: analysis. Typically, a 'visit' method like this is where we perform some analysis and maybe report lint(s) or warning(s). +Some rules do not require complex logic in the visitor class, but rules may +also need to walk up or down the syntax tree, or examine properties of nodes +carefully and thoroughly. For many examples of analysis rules and their visitor +classes, see the [lint rules] that ship with the Dart Analysis Server. + +[lint rules]: https://github.com/dart-lang/sdk/tree/main/pkg/linter/lib/src/rules + ## Registering an analysis rule In order for an analysis rule to be used in an analyzer plugin, it must be @@ -144,4 +151,6 @@ enabled by default. To register an analysis rule as a "lint rule," such that it must be specifically enabled from analysis options, use `registerLintRule` instead. -TODO(srawlins): Write up and link documentation for this Plugin subclass. +See [writing a plugin][] for for information about the `Plugin` class. + +[writing a plugin]: https://github.com/dart-lang/sdk/blob/main/pkg/analysis_server_plugin/doc/writing_rules.md \ No newline at end of file