Rozszerzalność synchronizacji danych z DataService

Dodawanie i aktualizacja danych

Czynność po stronie Altum

W bazie Altum istnieje procedura POS.ExportCustomObjects. Należy ją nadpisać, tak by pobierała z bazy dane, które mają trafić do danego POS-a, i zwracała je w formacie XML.

Do procedury są przekazywane parametry pozwalające ograniczyć i dostosować zestaw danych wysyłanych do konkretnego POS-a:

  • @rowVersion (bigint) – Wartość pozwalająca przeprowadzać synchronizację różnicową. Jest to wartość znajdująca się w XML wygenerowanym przez tę procedurę podczas ostatniej pomyślnej synchronizacji (w atrybucie RowVersion).
  • @companyUnitId (int) – Id centrum, w którym zdefiniowano POS-a (CompanyStructure.CompanyUnits)
  • @pointOfSaleId (int) – Id POS-a (Synchronization.PointsOfSales)
  • @languageId (int) – Id języka danych (Dictionaries.Languages)

Przy eksporcie danych z kolumn typu bit i datetime należy korzystać z funkcji POS.GetBitStringPOS.GetDatetimeString.

Czynność po stronie POS

W bazie POS-a istnieje procedura Synchronization.ImportCustomObjects. Należy ją nadpisać, tak by aktualizowała w bazie POS-a tabele na podstawie otrzymanych od Altum danych w formacie XML – tych wygenerowanych przez procedurę POS.ExportCustomObjects.

Przykład

Przykład pokazuje synchronizację różnicową danych z dwóch tabel – eksport z bazy Altum i import do bazy POS-a:

  • SecDictionaries.Dic_PaymentForms -> Configuration.CustomPaymentForms
  • dbo.Dic_Country -> Configuration
a)    Procedura eksportująca
ALTER PROCEDURE [POS].[ExportCustomObjects]
    @rowVersion bigint,
    @companyUnitId int,
    @pointOfSaleId int,
    @languageId int
AS
BEG+IN
                                    SET NOCOUNT ON;
    declare @dbts bigint = cast(@@DBTS as bigint)
        
    select
            @dbts as [@RowVersion],

        (select
            pf.Id			as [@Id],
            pf.Name		as [@Name],
            pf.CategoryId		as [@Type],
            POS.GetBitString(pf.Active)
                        as [@IsActive]
        from SecDictionaries.Dic_PaymentForms pf
        where pf.Timestamp > @rowVersion		
        for xml path('PaymentForm'), type),
        (select
                        c.Id		as [@Id],
            c.Code		as [@Code],
            c.Name		as [@Name],
            POS.GetBitString(c.Active)
                    as [@IsActive]
        from dbo.Dic_Country c
        where c.Timestamp > @rowVersion
        
        for xml path('Country'), type)
    for xml path('CustomObjects')
END
b)    Procedura importująca
ALTER PROCEDURE [Synchronization].[ImportCustomObjects]
    @XML xml
AS
BEGIN
    SET NOCOUNT ON;
    
    -- Countries --
    select
        doc.col.value('@Id', 'int') Id,
        doc.col.value('@Code', 'nvarchar(50)') Code,
        doc.col.value('@Name', 'nvarchar(100)') Name,
        doc.col.value('@IsActive', 'bit') IsActive
    into #Countries
    from @XML.nodes('/DataFromERP/CustomObjects/Country') doc(col)

update pos
    set
        Code = erp.Code,
        Name = erp.Name,
        IsActive = erp.IsActive
    from Configuration.CustomCountries pos
        join #Countries erp on erp.Id = pos.Id

    insert into Configuration.CustomCountries
    (
        Id,
        Code,
        Name,
        IsActive
    )
    select
        Id,
        Code,
        Name,
        IsActive
    from #Countries erp
    where not exists (select 1 from Configuration.CustomCountries where Id = erp.Id)

    -- Payment forms --
    select
        doc.col.value('@Id', 'int') Id,
        doc.col.value('@Name', 'nvarchar(50)') Name,
        doc.col.value('@Type', 'tinyint') [Type],
        doc.col.value('@IsActive', 'bit') IsActive
    into #PaymentForms
    from @XML.nodes('/DataFromERP/CustomObjects/PaymentForm')  doc(col)

    update pos
    set
        Name = erp.Name,
        Type = erp.Type,
        IsActive = erp.IsActive
    from Configuration.CustomPaymentForms pos
        join #PaymentForms erp on erp.Id = pos.Id

    insert into Configuration.CustomPaymentForms
    (
        Id,
        Name,
        Type,
        IsActive
    )
    select
        Id,
        Name,
        Type,
        IsActive
    from #PaymentForms erp
    where not exists (select 1 from Configuration.CustomPaymentForms where Id = erp.Id)
    
END

Obsługa słowników uniwersalnych

Aktualizacja procedury eksportującej

W procedurze POS.ExportGenericDirectories, w klauzuli WHERE należy uwzględnić InternalName słownika, który tez ma być synchronizowany.

W procedurze POS.ExportGenericDirectoryValues, w klauzuli WHERE należy uwzględnić InternalName słownika, który też ma być synchronizowany.

Klucze obce do schematu Altum

Dla tabel synchronizowanych

Dostępność obiektów, uprawnienia itp. mogą, na poziomie wiersza w danej tabeli, wpływać na to, które dane są synchronizowane. Przykładem mogą być Kontrahenci, grupy kontrahentów, magazyny, rejestry, formy płatności itd.

Aby uniknąć wielokrotnej ewaluacji, które dane należy synchronizować w tabelach pochodnych (na podstawie FK) należy posiłkować się tabelą POS.SentObjects.

Przykład: Eksport definicji podatków powiązanych z kontrahentem

(select
        ven.Id as [@Id],
        ven.ActivityId as [@ActivityId],
        ven.VendorId as [@VendorId]
        from Implementations.VendorActivityConnectionsEcoTax ven
        inner join Implementations.ActivityEcoTax ac on ven.ActivityId = ac.Id
        inner join Implementations.SettingsEcoTax sett on ac.Id = sett.CompanyActivityId and sett.CompanyId = @companyUnitId 
        inner join POS.SentObjects so on so.ObjectId = ven.VendorId and so.SyncTypeId = 14 and so.POSId = @pointOfSaleId
        where ven.Timestamp > @rowVersion 
                        for xml path('VendorActivityConnectionsEcoTax'), type)

wartość typu synchronizowanego obiektu można znaleźć w tabeli POS.SyncTypes.

Dla tabel niesynchronizowanych

Należy samodzielnie zaimplementować proces synchronizacji, tak jakby tabela pochodziła z doróbki.

Usuwanie danych

Czynności po stronie Altum

a) Do tabeli DeletionTypes dodać wpis z Id >= 1000 oraz unikatową nazwą typu usuwanych obiektów.
b) W triggerze AFTER DELETE tabeli, z której usuwanie danych ma być synchronizowane do POS, dodawać do tabeli POS.DeletedObjects wpisy o usuniętych obiektach. Kolumny do wypełnienia:

  • DeletionTypeId – identyfikator typu zdefiniowanego w pkcie a)
  • Ident – identyfikator usuniętego obiektu. Może to być liczba (int), GUID (uniqueidentifier), nvarchar lub zbiór wartości rozdzielonych znakiem „|”, np. „3428|654”. Patrz też punkt dot. czynności po stronie POS (kolumny IdentColumnName, IdentColumnType).
  • POSId – identyfikator POS-a (Synchronization.PointsOfSales) – należy go wypełnić, jeśli obiekt powinien zostać usunięty tylko z konkretnego stanowiska POS, albo pozostawić NULL, jeśli powinien zostać usunięty na wszystkich stanowiskach.

Czynności po stronie POS

Do tabeli Synchronization.DeletionTypes dodać wiersz definiujący sposób obsługi przez mechanizm synchronizacji informacji o usunięciu obiektów przychodzący z ERP-a.

Dostępne są dwa tryby usuwania: automatyczny i niestandardowy.

  • W trybie automatycznym mechanizm synchronizacji będzie automatycznie usuwał dane z podanej tabeli, identyfikując wiersze na podstawie podanych nazw kolumn (muszą być uzupełnione wartości w kolumnach TableName, IdentColumnName, IdentColumnType, a także NULL w kolumnie CustomProcName). Stosowany do usuwania na POS-ie niemal wszystkich typów obiektów usuwalnych w ERP-ie (patrz standardowe wpisy w tabeli Synchronization.DeletionTypes).
  • Tryb niestandardowy natomiast wymaga podania procedury obsługującej usuwanie obiektów danego typu (musi być wypełniona kolumna CustomProcName). Używany jest, gdy warunek usunięcia jest bardziej skomplikowany i nie da się zastosować mechanizmu automatycznego lub gdy przy usuwaniu należy wykonać dodatkowe operacje.

Tabela Synchronization.DeletionTypes zawiera następujące kolumny:

  • DelType – nazwa taka, jak w bazie Altum w tabeli DeletionTypes.
  • Order – liczba wyznaczająca kolejność usuwania typów obiektów.
  • TableName [tylko tryb automatyczny] – nazwa tabeli, z której obiekty mają być automatycznie usuwane w ramach danego typu DelType.
  • IdentColumnName [tylko tryb automatyczny] – nazwy kolumn (rozdzielonych znakiem „|”), wg których ma się odbywać automatyczna identyfikacja usuwanych wierszy, np. „Id”, „GUID”, „PriceTypeId|CustomerGroupId”. Ich liczba i kolejność musi się zgadzać z wartością wpisywaną w bazie Altum do kolumny POS.DeletedObjects.Ident.
  • IdentColumnType [tylko tryb automatyczny] – typy kolumn zdefiniowanych jako IdentColumnName, w tej samej liczbie i kolejności, np. „int”, „uniqueidentifier”, „int|int”. W przypadku typu nvarchar(x) wpisujemy „nvarchar”.
  • CustomProcName [tylko tryb niestandardowy] – nazwa procedury odpowiadającej za usunięcie obiektów danego typu. Powinna korzystać z danych z tabeli tymczasowej #DeletedObjects. Patrz istniejące procedury Synchronization.DeleteCustomerPriceTypes, Synchronization.DeleteWarehouseDocuments.

 

Czy ten artykuł był pomocny?