Improve partner onboarding and documentation navigation (#174)
Some checks failed
Validate knowledge index / validate-index (push) Has been cancelled
Validate AL review fixtures / validate-review-fixtures (push) Has been cancelled
Validate frontmatter and structure / validate (push) Has been cancelled

Lead with a complete plugin quick start and add task-oriented usage, troubleshooting, customization, and contribution guides. Preserve the broader plugin framing, correct conflicting contract guidance, support Agents folder reviews, and align repository validation. Convert existing sample references to clickable links without changing knowledge rules.

Co-authored-by: Jesper Schulz-Wedde <jesper.schulzwedde@microsoft.com>
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
This commit is contained in:
Jesper Schulz-Wedde 2026-09-09 17:31:03 +02:00 • committed by GitHub
parent a21edfec46
commit 2b5550c346
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
276 changed files with 1287 additions and 756 deletions

View file

@ -17,10 +17,10 @@ application-area: [all]
Use `ExtensionPublisher` for internal diagnostics that only the app publisher can interpret, such as cache behavior or private algorithm state. Use `All` for signals the tenant operator can act on, such as an integration failure, quota warning, or setup problem. Decide the audience independently from `DataClassification`; privacy guidance still governs whether the payload may be emitted at all.
See sample: `choose-telemetry-scope-by-audience.good.al`.
See sample: [`choose-telemetry-scope-by-audience.good.al`](choose-telemetry-scope-by-audience.good.al).
## Anti Pattern
Defaulting every call to `All`, including low-level implementation diagnostics, or defaulting every call to `ExtensionPublisher` and thereby hiding customer-actionable failures from environment telemetry. Review only when the message and surrounding branch make the intended audience clear; an ambiguous diagnostic is not enough to infer the wrong scope.
See sample: `choose-telemetry-scope-by-audience.bad.al`.
See sample: [`choose-telemetry-scope-by-audience.bad.al`](choose-telemetry-scope-by-audience.bad.al).

View file

@ -17,10 +17,10 @@ application-area: [all]
Log `Discovered` when the user encounters the feature, `Set up` after its setup is completed, and `Used` when the user attempts it. Keep the same feature name throughout the funnel. Review ordering only when the changed repository context shows the feature's lifecycle; a single isolated `Used` call cannot prove that earlier states are absent elsewhere.
See sample: `feature-uptake-transitions-in-order.good.al`.
See sample: [`feature-uptake-transitions-in-order.good.al`](feature-uptake-transitions-in-order.good.al).
## Anti Pattern
Introducing a feature whose only uptake call jumps directly to `Set up` or `Used`, or using different feature-name literals for successive states. The calls compile and run, but the funnel silently omits the invalid transition.
See sample: `feature-uptake-transitions-in-order.bad.al`.
See sample: [`feature-uptake-transitions-in-order.bad.al`](feature-uptake-transitions-in-order.bad.al).

View file

@ -17,10 +17,10 @@ application-area: [all]
Call `LogUsage` only after the operation has completed successfully. On a failure path, call `LogError` with the captured error text and call stack when the failure must be emitted explicitly. Use a past-tense event name for usage and a present-tense scenario name for errors.
See sample: `feature-usage-only-after-success.good.al`.
See sample: [`feature-usage-only-after-success.good.al`](feature-usage-only-after-success.good.al).
## Anti Pattern
Calling `LogUsage` before a Boolean result, `TryFunction`, `Codeunit.Run`, or HTTP status has been checked, or calling it in both success and failure branches. Do not flag an attempt recorded with `LogUptake(...Used)`; unlike `LogUsage`, that state intentionally records an attempt.
See sample: `feature-usage-only-after-success.bad.al`.
See sample: [`feature-usage-only-after-success.bad.al`](feature-usage-only-after-success.bad.al).

View file

@ -17,10 +17,10 @@ Business Central prefixes AL custom-dimension keys with `al` in Application Insi
Choose stable PascalCase keys such as `Operation`, `Result`, and `RecordCount`. Keep the key set and meaning stable for a shipped event ID; add a new event ID or coordinate a schema migration when the meaning must change. Privacy guidance separately governs whether a dimension value may contain customer data.
See sample: `keep-custom-dimension-schema-stable.good.al`.
See sample: [`keep-custom-dimension-schema-stable.good.al`](keep-custom-dimension-schema-stable.good.al).
## Anti Pattern
Keys such as `'order no'` or `'result_code'`, or renaming/removing a key while retaining the same shipped event ID. A naming-only issue is advisory; changing an existing event's schema is the material compatibility defect. New keys on a new event ID are not a breaking change.
See sample: `keep-custom-dimension-schema-stable.bad.al`.
See sample: [`keep-custom-dimension-schema-stable.bad.al`](keep-custom-dimension-schema-stable.bad.al).

View file

@ -17,10 +17,10 @@ application-area: [all]
Use `Error` for failed operations that need investigation and `Critical` only for abnormal termination or equivalent loss of service. Use `Warning` for degraded but completed behavior, `Normal` for successful business events, and `Verbose` for detailed diagnostics. Judge the outcome, not the procedure name: an expected optional lookup miss can legitimately remain `Normal` or `Verbose`.
See sample: `match-verbosity-to-signal-severity.good.al`.
See sample: [`match-verbosity-to-signal-severity.good.al`](match-verbosity-to-signal-severity.good.al).
## Anti Pattern
A `Session.LogMessage` in a failed `TryFunction`, failed `Codeunit.Run`, unsuccessful HTTP response, or other explicit failure branch that uses `Verbosity::Normal` or `Verbose` without evidence that the failure is expected and benign.
See sample: `match-verbosity-to-signal-severity.bad.al`.
See sample: [`match-verbosity-to-signal-severity.bad.al`](match-verbosity-to-signal-severity.bad.al).

View file

@ -17,10 +17,10 @@ The `Telemetry` and `Feature Telemetry` codeunits reach an extension publisher's
Place one internal logger implementation in one app for the publisher, forward its `LogMessage` method to `Session.LogMessage`, and register it from one event subscriber. Companion apps with the same publisher reuse that registration instead of each adding another. Evaluate absence only with repository or app-family context; a single-file diff cannot prove that no logger exists elsewhere.
See sample: `register-one-telemetry-logger-per-publisher.good.al`.
See sample: [`register-one-telemetry-logger-per-publisher.good.al`](register-one-telemetry-logger-per-publisher.good.al).
## Anti Pattern
Adding `FeatureTelemetry` calls to a complete app with no logger registration, or registering two logger implementations for apps that share the same publisher. The calls compile, but the telemetry module reports the missing or duplicate registration instead of behaving as intended.
See sample: `register-one-telemetry-logger-per-publisher.bad.al`.
See sample: [`register-one-telemetry-logger-per-publisher.bad.al`](register-one-telemetry-logger-per-publisher.bad.al).

View file

@ -23,10 +23,10 @@ The convention used by Microsoft first-party AL code is a short prefix identifyi
Assign each `Session.LogMessage` call a real, registered event ID drawn from the extension's catalogue. Treat the ID as part of the public contract of the event — renaming it is a breaking change for consumers. Keep IDs short, deterministic, and free of personal or environment-specific tokens.
See sample: `telemetry-event-id-stable-unique.good.al`.
See sample: [`telemetry-event-id-stable-unique.good.al`](telemetry-event-id-stable-unique.good.al).
## Anti Pattern
Calling `Session.LogMessage('0000', ...)` (or `'1234'`, `'TODO'`, an empty string, a GUID generated at runtime, or any other placeholder) leaves the event unsearchable and indistinguishable from every other event using the same placeholder. The catalogue entry never gets created because the developer "will fix it later", and the placeholder ships.
See sample: `telemetry-event-id-stable-unique.bad.al`.
See sample: [`telemetry-event-id-stable-unique.bad.al`](telemetry-event-id-stable-unique.bad.al).