Study guide

2.3: Multi-Root Workspaces & Project Dependencies

Microsoft Dynamics 365 Business Central Developer MB-820

Track your progress as you read

Finished sections get a check mark.

1 Chapter 1: Business Central Architecture & Platform Foundation

1.1 Business Central Architecture & Extensions Model 1.2 Customization Lifecycle: Cloud (SaaS) vs. On-Premises 1.3 Base Application, System Application & AppSource

2 Chapter 2: Development Environment & Configuration

2.1: Development Environment Setup: VS Code, AL: Go! Projects & Sandboxes 2.2: AL Configuration Files: app.json & launch.json Parameters 2.3: Multi-Root Workspaces & Project Dependencies

3 Chapter 3: Extension Lifecycle: Debugging, Deployment, Multilanguage & Maintenance

3.1 Debugging & Snapshot Debugging in Visual Studio Code 3.2 Extension Deployment & Schema Synchronization Modes 3.3 Multilanguage Development with XLIFF & Translation Files 3.4 Extension Maintenance, Deprecation & Breaking Changes

4 Chapter 4: Tables, Table Extensions & Data Modeling

4.1: Building Tables, Fields, Keys & Data Types 4.2: Table Extensions & Table Modifications 4.3: FlowFields, FlowFilters & Table Relations 4.4: Enums, Enum Extensions & Extensible Types

5 Chapter 5: Pages, Page Extensions & Role Centers

5.1: Page Types, Anatomy & Control Structure 5.2: Building Card, List & Document Pages 5.3: Page Extensions & Page Customizations 5.4: Role Centers, Headlines & Cue Data Modeling

6 Chapter 6: Reports & Document Generation

6.1 Report Architecture, DataItems & Dataset Design 6.2 Report Layouts: RDLC, Word, Excel & Multilanguage 6.3 Document Reports & Request Page Programming 6.4 Processing-Only Reports & Report Substitutions

7 Chapter 7: XMLports & Data Exchange

7.1 XMLport Architecture, Formats & Properties 7.2 XMLport Node Hierarchy, Triggers & Stream Manipulation

8 Chapter 8: Codeunits, Events, Triggers & Interfaces

8.1 Codeunit Types, Execution & SingleInstance Codeunits 8.2 Events, Publishers, Subscribers & Event Isolation 8.3 Interfaces, Polymorphism & Dynamic Codeunit Invocation 8.4 Installation & Upgrade Codeunits, Data Transfer & Archive

9 Chapter 9: Entitlements, Permissions & Queries

9.1 Permission Sets & Permission Set Extensions 9.2 Inherent Permissions, Inherent Entitlements & Security Scoping 9.3 Query Objects: Joins, Aggregation & Query as Report Data Source

10 Chapter 10: UI Customization, User Assistance & Onboarding

10.1 Profile Objects & Custom Page Views in AL 10.2 User Assistance: ToolTips, Teaching Tips & In-App Tours 10.3 Assisted Setup, Guided Experience & Onboarding Checklists

11 Chapter 11: Business Central Design Patterns & Data Process Model

11.1 Functional Table Types: Master Data, Supplemental & Setup Patterns 11.2 Document Standards: Header, Line, History & Journal Architectures 11.3 Data Process Model & Posting Routine Architecture

12 Chapter 12: AL Language Fundamentals, Data Types & Variables

12.1 AL Syntax, Variable Scope, Primitive & Complex Data Types 12.2 Expressions, Control Flow Statements & Built-in Functions 12.3 Access Modifiers (Public, Internal, Local) & Code Scoping

13 Chapter 13: Data Manipulation, Streams & Error Handling

13.1 Record Operations: Get, FindSet, ModifyAll & Filter Functions 13.2 Streams, File Management & TempBlob 13.3 Error Handling: ErrorInfo, TryFunctions & Collectible Errors

14 Chapter 14: Testing, Test Toolkit & Automation

14.1 Testing Architecture & the Test Toolkit 14.2 Authoring Test Codeunits & UI Handler Functions

15 Chapter 15: Telemetry, Performance Optimization & Analyzers

15.1 Telemetry Configuration & Azure Application Insights 15.2 Custom Telemetry Signals with Session.LogMessage & KQL 15.3 Performance Profiler, SetLoadFields & Query Optimization 15.4 AL Analyzers: CodeCop, AppSourceCop, UICop & PTECop

16 Chapter 16: REST Web Services & JSON in AL

16.1 HttpClient, HttpRequestMessage & REST API Consumption 16.2 JSON Processing: JsonObject, JsonArray, JsonValue & JsonToken

17 Chapter 17: API Pages, OData, Read Scale-Out & OAuth

17.1 API Pages (PageType=API), OData Web Services & REST Endpoints 17.2 Bound and Unbound OData Actions with [ServiceEnabled] 17.3 Read Scale-Out Architecture & DataAccessIntent Configuration 17.4 Microsoft Entra ID App Registrations & OAuth 2.0 Integration

2.3: Multi-Root Workspaces & Project Dependencies

Key Takeaways Explain This Topic AI

Visual Studio Code multi-root workspaces (.code-workspace) allow developers to manage, edit, and compile multiple interdependent AL extension projects within a single unified IDE window.

The AL Language extension resolves symbols across open workspace folders directly in memory before querying the .alpackages folder, providing real-time cross-project IntelliSense without manual symbol downloads.

Extension dependencies are declared in app.json using id, name, publisher, and version, establishing a minimum version constraint (>= declared version) and determining build order.

Circular dependencies between AL extensions are strictly prohibited and fail the build; they must be resolved by refactoring shared models and interfaces into a lower-tier Core extension.

Workspace-level settings such as al.packageCachePath centralize symbol storage to a single shared directory, eliminating redundant multi-gigabyte symbol downloads across projects.

Last updated: August 2026

2.3: Multi-Root Workspaces & Project Dependencies

Enterprise Business Central solutions rarely consist of a single monolithic extension. Instead, professional development architectures partition complex business domains into modular, layered applications—such as core frameworks, domain-specific modules, country localizations, and integration connectors. The MB-820 exam tests your mastery of Visual Studio Code multi-root workspaces , project dependency resolution, circular reference elimination, and symbol cache optimization across multi-app architectures.

1. Multi-Root Workspace Architecture ( .code-workspace )

A Visual Studio Code multi-root workspace enables developers to open and work on multiple distinct AL extension project folders simultaneously within a single IDE window. Each folder maintains its own independent app.json , launch.json , and source code tree, while sharing unified workspace settings. {

  • "folders": [
  • {
  • "name": "01 - Contoso Core Library",
  • "path": "./ContosoCore"
  • },
  • {
  • "name": "02 - Contoso Logistics Engine",
  • "path": "./ContosoLogistics"
  • },
  • {
  • "name": "03 - Contoso Shipping Connector",
  • "path": "./ContosoShipping"
  • }
  • ],
  • "settings": {
  • "al.packageCachePath": "./.shared-packages",
  • "al.enableCodeActions": true,
  • "al.incrementalBuild": true,
  • "al.codeAnalyzers": [
  • "${CodeCop}",
  • "${AppSourceCop}"
  • ],
  • "al.ruleSetPath": "./ruleset.json"
  • }
  • }
  • In-Memory Abstract Syntax Tree (AST) Symbol Resolution

The primary benefit of multi-root workspaces is real-time in-memory symbol resolution :

In a single-project setup, whenever an upstream dependency is modified, developers must recompile the upstream project ( Ctrl+Shift+B ), copy its generated .app package into the dependent project's .alpackages folder, and reload the window.

In a multi-root workspace , the AL Language extension inspects all open workspace folders. When Project B depends on Project A, the language server constructs an in-memory Abstract Syntax Tree (AST) of Project A directly from its raw source code.

Instant Cross-Project IntelliSense : If a developer adds a new public procedure or table field in ContosoCore , that procedure or field is immediately visible in ContosoLogistics and ContosoShipping via IntelliSense without compiling, packaging, or downloading symbols .

2. Project Dependencies & Dependency Graphs

Upstream dependencies are formally declared within the dependencies array of the downstream project's app.json : {

  • "id": "3d4e5f6a-7b8c-9d0e-1f2a-3b4c5d6e7f8a",
  • "name": "Contoso Logistics Engine",
  • "publisher": "Contoso",
  • "version": "2.0.0.0",
  • "dependencies": [
  • {
  • "id": "1a2b3c4d-5e6f-7a8b-9c0d-1e2f3a4b5c6d",
  • "name": "Contoso Core Library",
  • "publisher": "Contoso",
  • "version": "1.5.0.0"
  • }
  • ]
  • }
  • Key Dependency Rules for the MB-820 Exam

Exact Identification : A dependency entry requires four exact attributes: id (GUID), name , publisher , and version . The id is the primary matching key.

Minimum Version Semantics : The version specified in the dependency declaration represents the minimum compatible version . The target runtime environment must have a version installed that is greater than or equal to ( >= ) the declared version (e.g., 1.5.0.0 or higher).

Directed Acyclic Graph (DAG) Compilation Order : The AL compiler builds a dependency graph across all workspace folders. Compilation occurs strictly from the bottom up:

Level 0: Foundation / Core libraries (no dependencies).

Level 1: Domain modules (depend on Level 0).

Level 2: Composite integrations / UI customizations (depend on Level 1 and Level 0).

Breaking Changes Propagation : If a developer modifies a public method signature (e.g., adding a mandatory parameter) or removes a table field in a Level 0 project, all downstream projects will immediately display compiler errors in the Problems pane until updated.

3. Circular Dependencies & Decoupling Strategies

A circular dependency occurs when Extension A depends on Extension B, while Extension B simultaneously depends on Extension A (either directly or transitively through an intermediary Extension C). FATAL ARCHITECTURAL DEFECT (Circular Dependency):

  • +-----------------------+ +-----------------------+
  • | Extension A | -----------> | Extension B |
  • | (Contoso Logistics) | <----------- | (Contoso Billing) |
  • +-----------------------+ +-----------------------+

REFACTORED CLEAN ARCHITECTURE (Common Kernel / Interface Pattern):

  • +-----------------------+ +-----------------------+
  • | Extension A | | Extension B |
  • | (Contoso Logistics) | | (Contoso Billing) |
  • +-----------------------+ +-----------------------+
  • \ /
  • \ /
  • v v
  • +------------------------------+
  • | Extension C |
  • | (Contoso Core Interfaces) |
  • | - Shared Tables & Enums |
  • | - Business Event Publishers |
  • +------------------------------+
  • Circular Dependency Detection

The AL compiler strictly forbids circular references. If a circular loop exists in the dependency graph, symbol resolution fails and the compiler reports that a circular dependency was detected between the listed extensions.

Architectural Remediation Patterns

When two modules require mutual interaction, developers must decouple them using one of two proven design patterns:

Shared Kernel / Common Core Pattern :

Extract the shared tables, enums, interfaces, and integration event publishers into a third foundational extension (e.g., Contoso Core Interfaces ).

Configure both Extension A and Extension B to depend downward on the Core extension.

Event-Driven Decoupling (Publish/Subscribe) :

Instead of Extension A directly invoking a codeunit in Extension B, Extension A declares and raises an Integration Event Publisher .

Extension B subscribes to Extension A's event using [EventSubscriber] .

Extension A remains completely unaware of Extension B, eliminating the dependency from A to B.

Interface Polymorphism :

Declare an AL interface in the Core extension.

Implement the interface within concrete codeunits in Extension A and Extension B.

Use extensible enums to dynamically instantiate the desired implementation at runtime without direct project coupling.

4. Centralized Package Cache Optimization ( al.packageCachePath )

In enterprise multi-app workspaces containing multiple projects, each project by default maintains its own local .alpackages folder. Downloading identical multi-gigabyte symbol files ( Microsoft_Base Application.app , Microsoft_System.app ) for 5 to 10 distinct folders wastes gigabytes of disk space and saturates network bandwidth. {

  • "settings": {
  • "al.packageCachePath": "c:/AL/SharedSymbols"
  • }
  • }

Benefits of Centralized Package Caching:

Single Download : When AL: Download Symbols is executed in any project, symbols are downloaded to the centralized folder and immediately shared across all workspace projects.

Disk Footprint Reduction : Reduces workspace disk consumption from ~15 GB down to ~3 GB.

Fast CI/CD Builds : Build scripts can pre-populate the shared symbol directory once prior to executing parallel project builds.

Unified Cache Invalidation : Executing AL: Clear Object Cache flushes the single shared cache, preventing subtle version drift between projects.

Loading diagram... Multi-Root Workspace Architecture & Symbol Dependency Resolution