| name | bc-cds-page-generator |
| description | Automatically generate AL list page objects for CDS (Dataverse) tables following the BCS CDS Countries page structure. Creates list pages with proper field layouts, CRM integration actions, coupling procedures, and initialization triggers. Use when user requests to create, generate, or build a list page for a CDS/Dataverse table, or mentions creating UI for Dataverse entities. Trigger phrases include "create page for CDS table", "generate list page for [entity]", "build Dataverse page", or when working with CDS integration tables that need user interfaces. |
Business Central CDS Page Generator
Overview
Generates AL list page objects for CDS (Common Data Service/Dataverse) tables following established patterns from the BCS CDS Countries page. Creates properly structured pages with field layouts, CRM integration actions, coupling procedures, and initialization triggers.
Quick Start
Basic usage:
// Create a list page for a CDS table
// Pattern: "BCS CDS [EntityName]" for page name
// Pattern: "Dataverse [EntityName]" for caption
Example request:
- "Create a list page for the BCS CDS bcs_country table"
- "Generate a Dataverse page for the account CDS table"
- "Build a list page for the contact CDS entity"
Prerequisites
- CDS table already exists (TableType = CDS)
- Knowledge of which fields should be visible by default
- Available page ID (use Object ID Ninja or manual allocation)
- Understanding of CDS/CRM integration requirements
Core Page Structure
1. Page Properties
Standard properties for CDS list pages:
page [ID] "BCS CDS [EntityName]"
{
ApplicationArea = All;
Caption = 'Dataverse [EntityName]';
PageType = List;
SourceTable = "BCS CDS [tablename]";
UsageCategory = Lists;
Editable = false;
RefreshOnActivate = true;
}
Key properties:
- PageType: Always
List for entity lists
- Editable: Set to
false (CDS tables are typically read-only from BC)
- RefreshOnActivate: Set to
true to refresh data from Dataverse
- UsageCategory:
Lists to make it searchable
2. Layout Pattern
Field organization follows this structure:
layout
{
area(Content)
{
repeater(General)
{
// 1. Primary identification fields (visible)
field(primaryfield; Rec.primaryfield)
{
ApplicationArea = All;
ToolTip = 'Specifies...';
Caption = '...';
}
// 2. Important business fields (visible)
field(businessfield; Rec.businessfield)
{
ApplicationArea = All;
ToolTip = 'Specifies...';
Caption = '...';
}
// 3. Additional fields (Visible = false)
field(additionalfield; Rec.additionalfield)
{
ApplicationArea = All;
ToolTip = 'Specifies...';
Caption = '...';
Visible = false;
}
// 4. System fields (Visible = false)
field(CreatedOn; Rec.CreatedOn)
{
ApplicationArea = All;
ToolTip = 'Specifies the value of the Created On field.';
Visible = false;
}
field(ModifiedOn; Rec.ModifiedOn)
{
ApplicationArea = All;
ToolTip = 'Specifies the value of the Modified On field.';
Visible = false;
}
field(statecode; Rec.statecode)
{
ApplicationArea = All;
ToolTip = 'Specifies the value of the Status field.';
Visible = false;
}
field(statuscode; Rec.statuscode)
{
ApplicationArea = All;
ToolTip = 'Specifies the value of the Status Reason field.';
Visible = false;
}
field(SystemId; Rec.SystemId)
{
ApplicationArea = All;
ToolTip = 'Specifies the value of the SystemId field.';
Visible = false;
}
}
}
}
Field organization principles:
- Show primary identification fields first (code, name, number)
- Show important business fields
- Hide technical/administrative fields (set Visible = false)
- Always include system fields (CreatedOn, ModifiedOn, statecode, statuscode, SystemId)
- Always provide meaningful ToolTips
3. Actions Pattern
Standard CDS integration action:
actions
{
area(processing)
{
action(CreateFromCDS)
{
ApplicationArea = All;
Caption = 'Create in Business Central';
Promoted = true;
PromotedCategory = Process;
ToolTip = 'Generate the record from the coupled Microsoft Dataverse [entity].';
trigger OnAction()
var
CDSEntity: Record "BCS CDS [tablename]";
CRMIntegrationManagement: Codeunit "CRM Integration Management";
begin
CurrPage.SetSelectionFilter(CDSEntity);
CRMIntegrationManagement.CreateNewRecordsFromCRM(CDSEntity);
end;
}
}
}
Action purpose:
- Allows users to create BC records from selected Dataverse records
- Uses standard CRM Integration Management codeunit
- Applies to selected records via SetSelectionFilter
4. Triggers Pattern
Initialization trigger:
trigger OnInit()
begin
Codeunit.Run(Codeunit::"CRM Integration Management");
end;
Trigger purpose:
- Ensures CRM integration is initialized when page opens
- Required for proper CDS synchronization
5. Procedures Pattern
Coupling helper procedure:
/// <summary>
/// Sets the currently coupled [entity] record in the lookup page.
/// </summary>
/// <param name="[Entity]">The [entity] record that is currently coupled.</param>
procedure SetCurrentlyCoupled[Entity]([Entity]: Record "BCS CDS [tablename]")
begin
CurrentlyCoupled[Entity] := [Entity];
end;
var
CurrentlyCoupled[Entity]: Record "BCS CDS [tablename]";
Procedure purpose:
- Used when page is opened as a lookup for coupling
- Tracks the currently coupled record
- Helpful for CRM integration scenarios
Generation Workflow
Step 1: Identify CDS Table
Determine the source CDS table:
- Table name: e.g., "BCS CDS bcs_country"
- Entity name: e.g., "Country", "Account", "Contact"
- Primary fields: code/number, name, key identifiers
Step 2: Determine Page ID
Find next available page ID:
Get-ChildItem "src/Page/*.al" |
ForEach-Object {
$content = Get-Content $_.FullName -Raw
if ($content -match 'page\s+(\d+)') {
[int]$matches[1]
}
} |
Sort-Object |
Select-Object -Last 1
# Next ID = Last ID + 1
Step 3: Generate Page Structure
Create page file following the pattern:
- File name:
BCSCDS[EntityName].Page.al
- Page object:
page [ID] "BCS CDS [EntityName]"
- Caption:
'Dataverse [EntityName]'
- SourceTable: Reference to CDS table
Step 4: Add Field Layout
Organize fields by importance:
- Add primary identification fields (visible)
- Add key business fields (visible)
- Add supplementary fields (Visible = false)
- Add standard system fields (all hidden)
Field template:
field(fieldname; Rec.fieldname)
{
ApplicationArea = All;
ToolTip = 'Specifies [description from table field].';
Caption = '[Field Caption]';
Visible = false; // for non-primary fields
}
Step 5: Add Standard Components
- CreateFromCDS action: Copy from template, update entity name
- OnInit trigger: Copy as-is
- SetCurrentlyCoupled procedure: Update entity name and record variable
Step 6: Validate and Test
- Verify all field names match table definition
- Check ToolTip descriptions are meaningful
- Ensure page compiles without errors
- Test page opens and displays data from Dataverse
Template Example
Based on BCS CDS Countries page:
page 70004 "BCS CDS Countries"
{
ApplicationArea = All;
Caption = 'Dataverse Countries';
PageType = List;
SourceTable = "BCS CDS bcs_country";
UsageCategory = Lists;
Editable = false;
RefreshOnActivate = true;
layout
{
area(Content)
{
repeater(General)
{
// Primary visible fields
field(bcs_countrycode; Rec.bcs_countrycode)
{
ApplicationArea = All;
ToolTip = 'Specifies the two-letter country code.';
Caption = 'Code';
}
field(bcs_countryname; Rec.bcs_countryname)
{
ApplicationArea = All;
ToolTip = 'Specifies the name of the country.';
Caption = 'Name';
}
// Additional business fields with visibility control
// ... (see full page for complete structure)
// System fields (always hidden)
field(CreatedOn; Rec.CreatedOn)
{
ApplicationArea = All;
ToolTip = 'Specifies the value of the Created On field.';
Visible = false;
}
// ... other system fields
}
}
}
actions
{
area(processing)
{
action(CreateFromCDS)
{
ApplicationArea = All;
Caption = 'Create in Business Central';
Promoted = true;
PromotedCategory = Process;
ToolTip = 'Generate the record from the coupled Microsoft Dataverse country.';
trigger OnAction()
var
CDSCountry: Record "BCS CDS bcs_country";
CRMIntegrationManagement: Codeunit "CRM Integration Management";
begin
CurrPage.SetSelectionFilter(CDSCountry);
CRMIntegrationManagement.CreateNewRecordsFromCRM(CDSCountry);
end;
}
}
}
trigger OnInit()
begin
Codeunit.Run(Codeunit::"CRM Integration Management");
end;
procedure SetCurrentlyCoupledCountry(Country: Record "BCS CDS bcs_country")
begin
CurrentlyCoupledAccount := Country;
end;
var
CurrentlyCoupledAccount: Record "BCS CDS bcs_country";
}
Best Practices
-
Naming Conventions
- Page name:
"BCS CDS [EntityName]" (plural for lists)
- Page caption:
'Dataverse [EntityName]'
- File name:
BCSCDS[EntityName].Page.al
-
Field Visibility
- Show 3-5 most important fields by default
- Hide technical fields (IDs, timestamps, status codes)
- Make system fields accessible but not visible
-
ToolTips
- Always provide meaningful ToolTips
- Use descriptions from table field definitions
- Format: "Specifies [description]."
-
Actions
- Include CreateFromCDS action for all CDS pages
- Use proper naming in variables (CDSEntity pattern)
- Leverage CRM Integration Management codeunit
-
Documentation
- Add XML comments to procedures
- Explain purpose of coupling procedures
- Document any custom actions
Integration with Other Skills
Works with bc-dataverse-entity-generator:
- First generate CDS table
- Then create list page for that table
Works with bc-tooltip-manager:
- Generate page with basic tooltips
- Enhance tooltips using tooltip manager
Complements dataverse-schema-generator:
- Use schema documentation to identify important fields
- Reference field descriptions for tooltips
Common Patterns
Standard Entity Pages
For common entities (Account, Contact, Lead):
- Show primary identifier (Number, Code)
- Show name
- Show key classification fields
- Hide audit fields
Master Data Pages
For reference data (Country, Currency):
- Show code
- Show name/description
- Show key attributes (ISO codes, etc.)
- Group related fields
Transaction Pages
For transactional entities:
- Show document number
- Show date
- Show customer/vendor
- Show amount fields
- Show status
Troubleshooting
Issue: Fields not found
- Solution: Verify field names match CDS table exactly (case-sensitive)
Issue: Page doesn't display data
- Solution: Check RefreshOnActivate = true and OnInit trigger is present
Issue: CreateFromCDS action fails
- Solution: Verify CRM Integration Management codeunit is available and CDS connection is configured
Issue: Compilation errors on CreateFromCDS
- Solution: Update variable names to match entity (CDSCountry, CDSAccount, etc.)
Additional Resources
- Template page:
src/Page/BCSCDSCountries.Page.al
- EXAMPLES.md: Detailed generation examples for various entities
- README.md: Quick reference guide
This skill follows AL development best practices and CDS integration patterns.