Créer l’objet de codeunit Gestion de l’extension Récompenses client
Le codeunit Gestion de l’extension Récompenses client encapsule la plupart de la logique et des fonctionnalités requises pour l’extension Récompenses client. Ce codeunit comporte des exemples d’utilisation des événements afin de réagir à des actions ou des comportements spécifiques qui se produisent dans l’extension.
Cette extension inclut l’obligation d’effectuer un appel vers un service externe ou une API pour valider les codes d’activation que les utilisateurs ont saisis. En général, vous pouvez terminer cette vérification en définissant des procédures qui prennent le code d’activation, puis passent des appels à l’API. Au lieu d’utiliser cette approche, vous pouvez utiliser des événements dans AL.
Pour créer un codeunit dans votre projet, créez un fichier nommé CustomerRewardsExtMgt.Codeunit.al.
Ajoutez ensuite le code suivant au codeunit :
codeunit 50101 "Customer Rewards Ext. Mgt"
{
EventSubscriberInstance = StaticAutomatic;
// Determines if the extension is activated
procedure IsCustomerRewardsActivated(): Boolean;
var
ActivationCodeInformation: Record "Activation Code Information";
begin
if not ActivationCodeInformation.FindFirst() then
exit(false);
if (ActivationCodeInformation."Date Activated" <= Today) and (Today <= ActivationCodeInformation."Expiration Date") then
exit(true);
exit(false);
end;
// Opens the Customer Rewards Assisted Setup Guide
procedure OpenCustomerRewardsWizard();
var
CustomerRewardsWizard: Page "Customer Rewards Wizard";
begin
CustomerRewardsWizard.RunModal();
end;
// Opens the Reward Level page
procedure OpenRewardsLevelPage();
var
RewardsLevelList: Page "Rewards Level List";
begin
RewardsLevelList.Run();
end;
// Determines the corresponding reward level and returns it
procedure GetRewardLevel(RewardPoints: Integer) RewardLevelTxt: Text;
var
RewardLevel: Record "Reward Level";
MinRewardLevelPoints: Integer;
begin
RewardLevelTxt := NoRewardlevelTxt;
if RewardLevel.IsEmpty() then
exit;
RewardLevel.SetRange("Minimum Reward Points", 0, RewardPoints);
RewardLevel.SetCurrentKey("Minimum Reward Points"); // sorted in ascending order
if not RewardLevel.FindFirst() then
exit;
MinRewardLevelPoints := RewardLevel."Minimum Reward Points";
if RewardPoints >= MinRewardLevelPoints then begin
RewardLevel.Reset();
RewardLevel.SetRange("Minimum Reward Points", MinRewardLevelPoints, RewardPoints);
RewardLevel.SetCurrentKey("Minimum Reward Points"); // sorted in ascending order
RewardLevel.FindLast();
RewardLevelTxt := RewardLevel.Level;
end;
end;
// Activates Customer Rewards if activation code is validated successfully
procedure ActivateCustomerRewards(ActivationCode: Text): Boolean;
var
ActivationCodeInformation: Record "Activation Code Information";
begin
// raise event
OnGetActivationCodeStatusFromServer(ActivationCode);
exit(ActivationCodeInformation.Get(ActivationCode));
end;
// publishes event
[IntegrationEvent(false, false)]
procedure OnGetActivationCodeStatusFromServer(ActivationCode: Text);
begin
end;
// Subscribes to OnGetActivationCodeStatusFromServer event and handles it when the event is raised
[EventSubscriber(ObjectType::Codeunit, Codeunit::"Customer Rewards Ext Mgt", 'OnGetActivationCodeStatusFromServer', '', false, false)]
local procedure OnGetActivationCodeStatusFromServerSubscriber(ActivationCode: Text);
var
ActivationCodeInfo: Record "Activation Code Information";
ResponseText: Text;
Result: JsonToken;
JsonRepsonse: JsonToken;
begin
if not CanHandle() then
exit; // use the mock
// Get response from external service and update activation code information if successful
if (GetHttpResponse(ActivationCode, ResponseText)) then begin
JsonRepsonse.ReadFrom(ResponseText);
if (JsonRepsonse.SelectToken('ActivationResponse', Result)) then
if (Result.AsValue().AsText() = 'Success') then begin
if (ActivationCodeInfo.FindFirst()) then
ActivationCodeInfo.Delete();
ActivationCodeInfo.Init();
ActivationCodeInfo.ActivationCode := ActivationCode;
ActivationCodeInfo."Date Activated" := Today;
ActivationCodeInfo."Expiration Date" := CALCDATE('<1Y>', Today);
ActivationCodeInfo.Insert();
end;
end;
end;
// Helper method to make calls to a service to validate activation code
local procedure GetHttpResponse(ActivationCode: Text; var ResponseText: Text): Boolean;
begin
// You will typically make external calls / http requests to your service to validate the activation code
// here but for the sample extension we simply return a successful dummy response
if ActivationCode = '' then
exit(false);
ResponseText := DummySuccessResponseTxt;
exit(true);
end;
// Subscribes to the OnAfterReleaseSalesDoc event and increases reward points for the sell to customer in posted sales order
[EventSubscriber(ObjectType::Codeunit, Codeunit::"Release Sales Document", 'OnAfterReleaseSalesDoc', '', false, false)]
local procedure OnAfterReleaseSalesDocSubscriber(VAR SalesHeader: Record "Sales Header"; PreviewMode: Boolean; LinesWereModified: Boolean);
var
Customer: Record Customer;
begin
if SalesHeader.Status <> SalesHeader.Status::Released then
exit;
Customer.Get(SalesHeader."Sell-to Customer No.");
Customer.RewardPoints += 1; // Add a point for each new sales order
Customer.Modify();
end;
// Checks if the current codeunit is allowed to handle Customer Rewards Activation requests rather than a mock.
local procedure CanHandle(): Boolean;
var
CustomerRewardsMgtSetup: Record "Customer Rewards Mgt Setup";
begin
if CustomerRewardsMgtSetup.Get() then
exit(CustomerRewardsMgtSetup."Cust. Rew. Ext. Mgt. Cod. ID" = CODEUNIT::"Customer Rewards Ext Mgt");
exit(false);
end;
var
DummySuccessResponseTxt: Label '{"ActivationResponse": "Success"}', Locked = true;
NoRewardlevelTxt: TextConst ENU = 'NONE';
}
Les sections suivantes examinent le code du codeunit, étape par étape.
La propriété EventSubscriberInstance spécifie comment les méthodes d’abonné aux événements d’un codeunit sont liées à l’instance du codeunit et aux événements auxquels elles s’abonnent. Pour cet exemple, la propriété a été définie sur StaticAutomatic, ce qui signifie que les abonnés sont liés statiquement aux événements et que les instances de codeunit sont contrôlées par le système. Il s’agit de la valeur par défaut.
codeunit 50101 "Customer Rewards Ext Mgt"
{
EventSubscriberInstance = StaticAutomatic;
La méthode de l’éditeur d’événements OnGetActivationCodeStatusFromServer a été définie pour accepter le code d’activation entré par l’utilisateur en tant que paramètre. De plus, la méthode d’abonné OnGetActivationCodeStatusFromServerSubscriber a été définie pour écouter et gérer l’événement.
// publishes event
[IntegrationEvent(false, false)]
procedure OnGetActivationCodeStatusFromServer(ActivationCode: Text);
begin
end;
al-languageCopy
// Subscribes to OnGetActivationCodeStatusFromServer event and handles it when the event is raised
[EventSubscriber(ObjectType::Codeunit, Codeunit::"Customer Rewards Ext Mgt", 'OnGetActivationCodeStatusFromServer', '', false, false)]
local procedure OnGetActivationCodeStatusFromServerSubscriber(ActivationCode: Text);
var
ActivationCodeInfo: Record "Activation Code Information";
ResponseText: Text;
Result: JsonToken;
JsonRepsonse: JsonToken;
begin
if not CanHandle() then
exit; // use the mock
// Get response from external service and update activation code information if successful
if (GetHttpResponse(ActivationCode, ResponseText)) then begin
JsonRepsonse.ReadFrom(ResponseText);
if (JsonRepsonse.SelectToken('ActivationResponse', Result)) then
if (Result.AsValue().AsText() = 'Success') then begin
if (ActivationCodeInfo.FindFirst()) then
ActivationCodeInfo.Delete();
ActivationCodeInfo.Init();
ActivationCodeInfo.ActivationCode := ActivationCode;
ActivationCodeInfo."Date Activated" := Today;
ActivationCodeInfo."Expiration Date" := CALCDATE('<1Y>', Today);
ActivationCodeInfo.Insert();
end;
end;
end;
Quand la procédure ActivateCustomerRewards est exécutée, l’événement OnGetActivationCodeStatusFromServer est déclenché.
// Activates Customer Rewards if activation code is validated successfully
procedure ActivateCustomerRewards(ActivationCode: Text): Boolean;
var
ActivationCodeInformation: Record "Activation Code Information";
begin
// raise event
OnGetActivationCodeStatusFromServer(ActivationCode);
exit(ActivationCodeInformation.Get(ActivationCode));
end;
Comme la propriété EventSubscriberInstance du codeunit est définie sur Static-Automatic par défaut, la procédure OnGetActivationCodeStatusFromServerSubscriber est appelée.
Dans cette procédure, vous gérez l’événement déclenché en vérifiant d’abord si le codeunit actuel a été défini pour gérer cet événement.
if not CanHandle() then
exit; // use the mock
al-languageCopy
// Checks if the current codeunit is allowed to handle Customer Rewards Activation requests rather than a mock.
local procedure CanHandle(): Boolean;
var
CustomerRewardsMgtSetup: Record "Customer Rewards Mgt Setup";
begin
if CustomerRewardsMgtSetup.Get() then
exit(CustomerRewardsMgtSetup."Cust. Rew. Ext. Mgt. Cod. ID" = CODEUNIT::"Customer Rewards Ext Mgt");
exit(false);
end;
Si le codeunit peut gérer l’événement, la procédure d’assistance GetHttpResponse est appelée pour valider le code d’activation. Selon la réponse, Récompenses client est activé ou non.
// Get response from external service and update activation code information if successful
if (GetHttpResponse(ActivationCode, ResponseText)) then begin
JsonRepsonse.ReadFrom(ResponseText);
// Helper method to make calls to a service to validate activation code
local procedure GetHttpResponse(ActivationCode: Text; var ResponseText: Text): Boolean;
begin
// You will typically make external calls / http requests to your service to validate the activation code
// here but for the sample extension we simply return a successful dummy response
if ActivationCode = '' then
exit(false);
ResponseText := DummySuccessResponseTxt;
exit(true);
end;
En utilisant des événements lorsque l’extension passe des appels externes à un service, vous pouvez simuler le comportement de ce qui se passe lorsque des événements sont déclenchés.
La procédure IsCustomerRewardsActivated recherche un code d’activation dans la table Informations sur le code d’activation et vérifie également si ce code est actif ou expiré.
// Determines if the extension is activated
procedure IsCustomerRewardsActivated(): Boolean;
var
ActivationCodeInformation: Record "Activation Code Information";
begin
if not ActivationCodeInformation.FindFirst() then
exit(false);
if (ActivationCodeInformation."Date Activated" <= Today) and (Today <= ActivationCodeInformation."Expiration Date") then
exit(true);
exit(false);
end;
Cette procédure est référencée dans la page Liste des niveaux de récompenses et dans l’extension de page Ext. Liste des clients.
La procédure OpenCustomerRewardsWizard exécute la page Assistant Récompenses client :
// Opens the Customer Rewards Assisted Setup Guide
procedure OpenCustomerRewardsWizard();
var
CustomerRewardsWizard: Page "Customer Rewards Wizard";
begin
CustomerRewardsWizard.RunModal();
end;
Cette page est créée dans un module ultérieur, donc pour l’instant, elle ne se compile pas. Vous pouvez commenter la procédure et supprimer les commentaires après avoir testé l’extension.
La procédure OpenRewardsLevelPage ouvre la page Liste des niveaux de récompense.
// Opens the Reward Level page
procedure OpenRewardsLevelPage();
var
RewardsLevelList: Page "Rewards Level List";
begin
RewardsLevelList.Run();
end;
Cette procédure est référencée à partir des objets suivants :
Extension de page Extension Liste des clients
Page Assistant Récompenses client
La procédure GetRewardLevel détermine le niveau de récompense correspondant, puis le renvoie.
// Determines the corresponding reward level and returns it
procedure GetRewardLevel(RewardPoints: Integer) RewardLevelTxt: Text;
var
RewardLevel: Record "Reward Level";
MinRewardLevelPoints: Integer;
begin
RewardLevelTxt := NoRewardlevelTxt;
if RewardLevel.IsEmpty() then
exit;
RewardLevel.SetRange("Minimum Reward Points", 0, RewardPoints);
RewardLevel.SetCurrentKey("Minimum Reward Points"); // sorted in ascending order
if not RewardLevel.FindFirst() then
exit;
MinRewardLevelPoints := RewardLevel."Minimum Reward Points";
if RewardPoints >= MinRewardLevelPoints then begin
RewardLevel.Reset();
RewardLevel.SetRange("Minimum Reward Points", MinRewardLevelPoints, RewardPoints);
RewardLevel.SetCurrentKey("Minimum Reward Points"); // sorted in ascending order
RewardLevel.FindLast();
RewardLevelTxt := RewardLevel.Level;
end;
end;
Cette procédure est référencée à partir de l’extension de page Extension Fiche client.
Enfin, la procédure OnAfterReleaseSalesDocSubscriber s’exécute.
// Subscribes to the OnAfterReleaseSalesDoc event and increases reward points for the sell to customer in posted sales order
[EventSubscriber(ObjectType::Codeunit, Codeunit::"Release Sales Document", 'OnAfterReleaseSalesDoc', '', false, false)]
local procedure OnAfterReleaseSalesDocSubscriber(VAR SalesHeader: Record "Sales Header"; PreviewMode: Boolean; LinesWereModified: Boolean);
var
Customer: Record Customer;
begin
if SalesHeader.Status <> SalesHeader.Status::Released then
exit;
Customer.Get(SalesHeader."Sell-to Customer No.");
Customer.RewardPoints += 1; // Add a point for each new sales order
Customer.Modify();
end;
La procédure est exécutée chaque fois qu’un document de vente est lancé, car la procédure est abonnée à l’événement OnAfterReleaseSalesDoc dans le codeunit Lancer le document de vente.
La procédure ajoute un point de récompense à un client pour chaque nouvelle commande vente. Elle augmente les points de récompense pour chaque vente à un client pour chaque commande vente validée.