bcquality/microsoft/knowledge/upgrade/no-changecompany-in-upgrade.good.al
Jesper Schulz-Wedde 488ce50775
knowledge(upgrade): upgrade code must not use ChangeCompany (#210)
* knowledge(upgrade): upgrade code must not use ChangeCompany

Addresses ADO bug 651092. Upgrade and feature data update code must run in the
context of the company being upgraded; ChangeCompany leaves triggers, events and
upgrade tags in the calling company and races the target company's own upgrade.

Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>

* Address review: self-contained samples, fixture registration, scoped feature routing

- Declare the sample table in both companions so each compiles on its own.
- Register no-changecompany-in-upgrade and changecompany-runs-triggers-in-the-calling-company in review-fixtures.json.
- Limit the Feature Data Update rule to UpdateData/AfterUpdate and their reachable helpers; read-only IsDataUpdateRequired/ReviewData preflight is permitted and shown as a clean control.
- Add feature data update execution to al-upgrade-review applicability and not-applicable scope.

Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>

* Clarify cross-company upgrade sequencing without race claims

Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>

---------

Co-authored-by: Jesper Schulz-Wedde <jesper.schulzwedde@microsoft.com>
Co-authored-by: Copilot App <223556219+Copilot@users.noreply.github.com>
2026-10-02 11:35:11 +02:00

96 lines
2.9 KiB
AL

table 50262 "Sales Order Ext"
{
DataClassification = CustomerContent;
fields
{
field(1; "No."; Code[20]) { }
field(2; "Shipping Agent Code"; Code[10]) { TableRelation = "Shipping Agent"; }
field(3; "Legacy Carrier Code"; Code[10]) { }
}
keys
{
key(PK; "No.") { Clustered = true; }
}
}
codeunit 50260 "Upgrade Current Company"
{
Subtype = Upgrade;
// The platform runs this trigger once per company, in that company's own session.
trigger OnUpgradePerCompany()
begin
UpgradeShippingAgentCodes();
end;
local procedure UpgradeShippingAgentCodes()
var
SalesOrderExt: Record "Sales Order Ext";
UpgradeTag: Codeunit "Upgrade Tag";
begin
if UpgradeTag.HasUpgradeTag(ShippingAgentUpgradeTag()) then
exit;
// Only the current company's rows; triggers, events, and the tag all apply here.
SalesOrderExt.SetRange("Shipping Agent Code", '');
if SalesOrderExt.FindSet(true) then
repeat
SalesOrderExt.Validate("Shipping Agent Code", SalesOrderExt."Legacy Carrier Code");
SalesOrderExt.Modify(true);
until SalesOrderExt.Next() = 0;
UpgradeTag.SetUpgradeTag(ShippingAgentUpgradeTag());
end;
local procedure ShippingAgentUpgradeTag(): Code[250]
begin
exit('CONTOSO-1001-ShippingAgentCode-20260101');
end;
}
codeunit 50264 "Shipping Agent Feat. Data Upd." implements "Feature Data Update"
{
// Read-only preflight: counting rows across companies to report scope is allowed.
procedure IsDataUpdateRequired(): Boolean
var
Company: Record Company;
SalesOrderExt: Record "Sales Order Ext";
begin
if Company.FindSet() then
repeat
SalesOrderExt.ChangeCompany(Company.Name);
SalesOrderExt.SetRange("Shipping Agent Code", '');
if not SalesOrderExt.IsEmpty() then
exit(true);
until Company.Next() = 0;
exit(false);
end;
procedure ReviewData()
begin
end;
// Feature Management runs this once per company, in that company.
procedure UpdateData(FeatureDataUpdateStatus: Record "Feature Data Update Status")
var
SalesOrderExt: Record "Sales Order Ext";
begin
SalesOrderExt.SetRange("Shipping Agent Code", '');
if SalesOrderExt.FindSet(true) then
repeat
SalesOrderExt.Validate("Shipping Agent Code", SalesOrderExt."Legacy Carrier Code");
SalesOrderExt.Modify(true);
until SalesOrderExt.Next() = 0;
end;
procedure AfterUpdate(FeatureDataUpdateStatus: Record "Feature Data Update Status")
begin
end;
procedure GetTaskDescription(): Text
begin
exit('Copies legacy carrier codes to the shipping agent code.');
end;
}