Compartilhar via


Gerar códigos QR e imprimi-los em recibos para a Arábia Saudita

Nota

A funcionalidade descrita neste artigo destina-se a suportar os requisitos da Fase 1 da implementação da Faturação Eletrónica no Reino da Arábia Saudita. Para obter informações sobre as funcionalidades destinadas a suportar os requisitos da Fase 2 da implementação da Faturação Eletrónica no Reino da Arábia Saudita, consulte Gerar e submeter faturas eletrónicas simplificadas para a Arábia Saudita.

Isto artigo fornece uma visão geral da funcionalidade de impressão de códigos QR disponível para a Arábia Saudita Microsoft Dynamics 365 Commerce.

Em uma loja vinculada a uma entidade legal que tenha seu endereço principal na Arábia Saudita, os utilizadores podem imprimir um código QR no recibo de uma transação de venda de dinheiro e transporte ou ordem de cliente. O código QR contém as seguintes informações.

Sequência Campo Origem de dados
1 Nome da empresa O nome da entidade legal
2 Número de identificação para efeitos de IVA da empresa O número de registo fiscal da entidade legal
3 Data e hora da transação A data e a hora da transação da loja de retalho
4 Valor total do recebimento (incluindo o imposto sobre o valor acrescentado [IVA]) O valor total da transação da loja de retalho
5 Valor total do IVA incluído no recibo O valor total do imposto da transação da loja de retalho

Nota

Quando as transações de encomendas de clientes são criadas, o valor total do recebimento é calculado adicionando os valores totais de todas as linhas de transações que utilizam o modo de entrega de transporte.

O código QR é gerado através da aplicação da transformação base64 às informações de transação codificadas no formato Tag-Length-Value (TLV). Zakat, Autoridade Tributária e Aduaneira (ZATCA) fornece ferramentas que podem ser usadas para validar o código QR. Para obter mais informações sobre os requisitos de faturação eletrónica e os recursos de validação de código QR, consulte Portal de faturamento eletrônico da ZATCA.

Configurar códigos QR

Para gerar códigos QR e imprimi-los em recibos para a Arábia Saudita, você deve concluir as seguintes tarefas.

  1. Configure campos personalizados para que possam ser utilizados em formatos de recibo para recibos de venda.
  2. Configure formatos de recibo.
  3. Especifique dimensões de código QR em parâmetros do Commerce.
  4. Habilite as extensões de tempo de execução (CRT) do Commerce.

Configurar campos personalizados para que possam ser utilizados em formatos de recibo para recibos de venda

Pode configurar o idioma, o texto e os campos personalizados utilizados nos formatos de recibo do ponto de venda (POS). Na página de texto Idioma , adicione os seguintes registos para as etiquetas dos campos personalizados para esquemas de recibo. Observe que os valores ID deidioma, ID de texto e Texto mostrados na tabela são apenas exemplos. Você pode alterá-los para atender às suas necessidades. No entanto, os valores de ID de texto que você usa devem ser exclusivos e devem ser iguais ou superiores a 900001.

ID do idioma ID de texto Texto
pt-PT 900001 Código QR (SA)

Nota

A empresa padrão do utente que cria a configuração de recebimento deve ser a mesma entidade legal onde a configuração de texto de idioma é criada. Como alternativa, os mesmos textos de idioma devem ser criados na empresa padrão do utente e na entidade legal da loja para a qual a configuração foi criada.

Na página Campos personalizados, adicione os seguintes registos para os campos personalizados para esquemas de recibo. Observe que os valores de ID de texto de legenda devem corresponder aos valores de ID de texto especificados na página de texto Idioma .

Nome Tipo ID de texto de legenda
INVOICEQRCODE_SA Receção 900001

Configurar formatos de recibo

Para cada formato de recibo necessário, altere o valor do campo Comportamento de impressão para Sempre imprimir.

No designer de formato de recibo, adicione o seguinte campo personalizado à secção Rodapé do recibo. Observe que os nomes dos campos correspondem aos textos de idioma definidos na secção anterior.

  • Código QR (SA) – Isto campo imprime o código QR no recibo.

Para obter mais informações sobre como trabalhar com formatos de recibo, consulte Configurar e projetar formatos de recibo.

Especificar dimensões de código QR em parâmetros do Commerce

Na guia Parâmetros de configuração da página Parâmetros do Commerce, adicione os seguintes parâmetros de configuração:

  • QrCodeWidth - A largura da imagem do código QR, em pixels. Especifique um valor apropriado para o parâmetro.
  • QrCodeHeight - A altura da imagem do código QR, em pixels. Especifique um valor apropriado para o parâmetro.

Nota

É obrigatório especificar os valores destes parâmetros de configuração para imprimir códigos QR nos recibos. O suporte para valores padrão dos parâmetros pode ser adicionado em atualizações futuras.

Ativar CRT extensões

Aviso

Essa funcionalidade de localização não pode ser usada com o novo modelo independente de empacotamento e extensão e o kit de desenvolvimento de software (SDK) do Commerce. Você deve usar a versão anterior do Retail SDK em uma máquina virtual (VM) de desenvolvedor em Microsoft Dynamics Lifecycle Services (LCS). Para obter informações sobre os recursos de localização para a Arábia Saudita disponíveis no Commerce SDK, consulte Gerar e enviar faturas eletrônicas simplificadas para a Arábia Saudita

Ambiente de desenvolvimento

Siga estas etapas para configurar um ambiente de desenvolvimento para que você possa testar e estender a funcionalidade de localização.

  1. Encontre o ficheiro de configuração de extensão para CRT:

    • Retail Server: O ficheiro é chamado commerceruntime.ext.config e pode ser encontrado na pasta bin\ext no local do site Serviços de Informação Internet (IIS) Retail Server.
    • Local CRT no Modern POS: O ficheiro é chamado CommerceRuntime.MPOSOffline.Ext.config e pode ser encontrado no local do broker do cliente local CRT .
  2. Registre a CRT alteração no ficheiro de configuração da extensão, conforme mostrado no exemplo a seguir.

    <add source="assembly" value="Microsoft.Dynamics.Commerce.Runtime.ReceiptsSaudiArabia" />
    <add source="assembly" value="Microsoft.Dynamics.Commerce.Runtime.ElectronicReporting" />
    

Ambiente de produção

Siga estas etapas para criar pacotes implantáveis que contenham componentes do Commerce e para aplicá-los em um ambiente de produção.

  1. Nos ficheiros de configuração do pacote commerceruntime.ext.config e CommerceRuntime.MPOSOffline.Ext.config na pasta RetailSdk\Assets , adicione as seguintes linhas à secção de composição .

    <add source="assembly" value="Microsoft.Dynamics.Commerce.Runtime.ReceiptsSaudiArabia" />
    <add source="assembly" value="Microsoft.Dynamics.Commerce.Runtime.ElectronicReporting" />
    
  2. Abra o prompt de comando do MSBuild para Visual Studio o utilitário e execute o msbuild na pasta Retail SDK para criar pacotes implantáveis.

  3. Aplique os pacotes via LCS ou manualmente. Para obter mais informações, consulte Criar pacotes implantáveis.

Quando utiliza uma impressora OPOS (Object Linking and Embedding for Retail POS), poderá ter de implementar personalizações adicionais para suportar requisitos específicos da impressora para a imagem de código QR. Por exemplo, poderá ter de converter a imagem do código QR do formato PNG para o formato BMP. Esta secção mostra um exemplo desse tipo de personalização.

Nota

Isto exemplo de personalização foi testado utilizando a impressora EPSON TM-T88V OPOS. Poderá ter de ser modificado para suportar diferentes marcas ou modelos de impressoras.

Siga estas etapas para criar uma nova extensão e adicioná-la ao seu ambiente.

  1. Instale o Retail SDK. Para obter mais informações, consulte Retail Software Development Kit (SDK).

  2. No Retail SDK, use o código a seguir, com base em sua versão do Commerce, para criar um projeto C# sob a solução CommerceRuntimeSamples.sln em RetailSdk\SampleExtensions\CommerceRuntime.

    <Project Sdk="Microsoft.NET.Sdk">
        <Import Project="..\..\..\BuildTools\Microsoft.Dynamics.RetailSdk.Build.props" />
        <Import Project="..\..\..\BuildTools\Common.props" />
        <Import Project="..\..\..\BuildTools\Microsoft.Dynamics.RetailSdk.Build.settings" />
    
        <PropertyGroup>
            <TargetFramework>netstandard2.0</TargetFramework>
            <AssemblyName>$(AssemblyNamePrefix).Commerce.Runtime.QrCodeExtension</AssemblyName>
            <RootNamespace>Contoso.Commerce.Runtime.QrCodeExtension</RootNamespace>
            <AutoGenerateBindingRedirects>true</AutoGenerateBindingRedirects>
        </PropertyGroup>
    
        <Import Project="..\..\..\BuildTools\Microsoft.Dynamics.RetailSdk.Build.targets" />
    
        <ItemGroup>
            <PackageReference Include="Microsoft.Dynamics.Commerce.Runtime.Framework" Version="$(FrameworkRepoPackagesVersion)" />
            <PackageReference Include="Microsoft.Dynamics.Commerce.Runtime.Services.Messages" Version="$(ChannelRepoPackagesVersion)" />
            <PackageReference Include="System.Drawing.Common" Version="4.7.0" />
        </ItemGroup>
    
        <ItemGroup>
            <Reference Include="Microsoft.Dynamics.Commerce.Runtime.ElectronicReporting">
                <HintPath>..\..\..\..\..\nuget packages\microsoft.dynamics.commerce.runtime.electronicreporting.9.35.21321.4\lib\netstandard2.0\Microsoft.Dynamics.Commerce.Runtime.ElectronicReporting.dll</HintPath>
            </Reference>
        </ItemGroup>
    
        <ItemGroup>
            <Folder Include="Properties\" />
        </ItemGroup>
    </Project>
    

    Você também deve alterar o valor do elemento HintPath para fazer referência a Microsoft.Dynamics.Commerce.Runtime.ElectronicReporting.DLL biblioteca sob o local do site do IIS Retail Server.

  3. Use o código a seguir, com base em sua versão do Commerce, para criar uma classe de extensão.

    /**
     * SAMPLE CODE NOTICE
     * 
     * THIS SAMPLE CODE IS MADE AVAILABLE AS IS. MICROSOFT MAKES NO WARRANTIES, WHETHER EXPRESS OR IMPLIED,
     * OF FITNESS FOR A PARTICULAR PURPOSE, OF ACCURACY OR COMPLETENESS OF RESPONSES, OF RESULTS, OR CONDITIONS OF MERCHANTABILITY.
     * THE ENTIRE RISK OF THE USE OR THE RESULTS FROM THE USE OF THIS SAMPLE CODE REMAINS WITH THE USER.
     * NO TECHNICAL SUPPORT IS PROVIDED. YOU MAY NOT DISTRIBUTE THIS CODE UNLESS YOU HAVE A LICENSE AGREEMENT WITH MICROSOFT THAT ALLOWS YOU TO DO SO.
     */
    
    using System.Drawing;
    using System.Drawing.Imaging;
    using System.IO;
    
    namespace Contoso
    {
        namespace Commerce.Runtime.QrCodeExtension
        {
            using System;
            using System.Collections.Generic;
            using System.Threading.Tasks;
            using Microsoft.Dynamics.Commerce.Runtime;
            using Microsoft.Dynamics.Commerce.Runtime.Messages;
            using Microsoft.Dynamics.Commerce.Runtime.Services.Messages;
    
            /// <summary>
            /// The extension for QR code printing.
            /// </summary>
            internal class QrCodeServiceExtension : IRequestHandlerAsync
            {
                /// <summary>
                /// Printer horizontal resolution for image.
                /// </summary>
                private const float PrinterXDpi = 60f;
    
                /// <summary>
                /// Printer vertical resolution for image.
                /// </summary>
                private const float PrinterYDpi = 90f;
    
                /// <summary>
                /// Printer pixel format for image.
                /// </summary>
                private const PixelFormat PrinterPixelFormat = PixelFormat.Format8bppIndexed;
    
                /// <summary>
                /// Gets the collection of supported request types by this service.
                /// </summary>
                public IEnumerable<Type> SupportedRequestTypes
                {
                    get => new[] {typeof(EncodeQrCodeServiceRequest)};
                }
    
                /// <summary>
                /// Processes the request.
                /// </summary>
                /// <param name="request">The request.</param>
                /// <returns>The response.</returns>
                public async Task<Response> Execute(Request request)
                {
                    ThrowIf.Null(request, nameof(request));
    
                    switch (request)
                    {
                        case EncodeQrCodeServiceRequest encodeQrCodeServiceRequest:
                        {
                            EncodeQrCodeServiceResponse nextResponse = await this.ExecuteNextAsync<EncodeQrCodeServiceResponse>(encodeQrCodeServiceRequest).ConfigureAwait(false);
    
                            if (nextResponse != null)
                            {
                                var qrCodeBmp = string.IsNullOrWhiteSpace(nextResponse.QRcode) ? nextResponse.QRcode : ConvertToGenericCompatibilityImage(nextResponse.QRcode);
                                return new EncodeQrCodeServiceResponse(qrCodeBmp);
                            }
    
                            return nextResponse;
                        }
                    }
    
                    return new NotHandledResponse();
                }
    
                /// <summary>
                /// Converts QR code image from any format to compatible with printer.
                /// </summary>
                /// <param name="base64data">Base64 image.</param>
                /// <returns>Image that Compatible with printer.</returns>
                private static string ConvertToGenericCompatibilityImage(string base64data)
                {
                    string convertedQrCode = base64data;
                    byte[] imageBytes = Convert.FromBase64String(convertedQrCode);
                    using (MemoryStream msOriginal = new MemoryStream(imageBytes))
                    using (MemoryStream msConverted = new MemoryStream())
                    {
                        var bitmapOriginal = new Bitmap(msOriginal);
                        if (!IsFormatCompatible(bitmapOriginal) || !AreResolutionAndPixelFormatCompatible(bitmapOriginal))
                        {
                            var bitmapConverted = bitmapOriginal;
    
                            if (!AreResolutionAndPixelFormatCompatible(bitmapOriginal))
                            {
                                var rectangle = new Rectangle(0, 0, bitmapOriginal.Width, bitmapOriginal.Height);
                                bitmapConverted = bitmapOriginal.Clone(rectangle, PrinterPixelFormat);
                                bitmapConverted.SetResolution(PrinterXDpi, PrinterYDpi);
                            }
    
                            bitmapConverted.Save(msConverted, ImageFormat.Bmp);
                        }
    
                        convertedQrCode = Convert.ToBase64String(msConverted.ToArray());
                    }
    
                    return convertedQrCode;
                }
    
                /// <summary>
                /// Verifies if the resolution and pixel format of bitmap are compatible with printer requirements.
                /// </summary>
                /// <param name="source">Bitmap.</param>
                /// <returns>True if compatible; otherwise false.</returns>
                private static bool AreResolutionAndPixelFormatCompatible(Bitmap source)
                {
                    return source.VerticalResolution == PrinterYDpi &&
                           source.HorizontalResolution == PrinterXDpi &&
                           source.PixelFormat == PrinterPixelFormat;
                }
    
                /// <summary>
                /// Verifies if the format of bitmap is compatible with printer requirements.
                /// </summary>
                /// <param name="source">Bitmap.</param>
                /// <returns>True if compatible; otherwise false.</returns>
                private static bool IsFormatCompatible(Bitmap source)
                {
                    return source.RawFormat.Equals(ImageFormat.Bmp);
                }
            }
        }
    }
    
  4. Nos ficheiros de configuração commerceruntime.ext.config e CommerceRuntime.MPOSOffline.Ext.config na pasta RetailSdk\Assets , adicione as seguintes linhas à secção de composição .

    <add source="assembly" value="Contoso.Commerce.Runtime.QrCodeExtension" />
    <add source="assembly" value="Microsoft.Dynamics.Commerce.Runtime.ReceiptsSaudiArabia" />
    <add source="assembly" value="Microsoft.Dynamics.Commerce.Runtime.ElectronicReporting" />
    
  5. No ficheiro de configuração de personalização do pacote Customization.settings na pasta BuildTools , adicione as seguintes linhas para incluir as CRT extensões nos pacotes implantáveis.

    <ISV_CommerceRuntime_CustomizableFile Include="$(SdkReferencesPath)\Contoso.Commerce.Runtime.QrCodeExtension.dll" />
    
  6. Inicie o MSBuild Command Prompt para Visual Studio utilitário e execute msbuild na pasta Retail SDK para criar pacotes implantáveis.

  7. Aplique os pacotes via LCS ou manualmente. Para obter mais informações, consulte Criar pacotes implantáveis.