Come usare le code del bus di servizio con PHPHow to use Service Bus queues with PHP

Questa guida illustra come usare le code del bus di servizio.This guide shows you how to use Service Bus queues. Gli esempi sono scritti in PHP e usano Azure SDK per PHP.The samples are written in PHP and use the Azure SDK for PHP. Gli scenari presentati includono la creazione di code, l'invio e la ricezione di messaggi e l'eliminazione di code.The scenarios covered include creating queues, sending and receiving messages, and deleting queues.

Informazioni sulle code del bus di servizioWhat are Service Bus queues?

Le code del bus di servizio supportano un modello di comunicazione con messaggistica negoziata .Service Bus queues support a brokered messaging communication model. Quando si usano le code, i componenti di un'applicazione distribuita non comunicano direttamente l'uno con l'altro, ma scambiano messaggi tramite una coda, che agisce da intermediario (broker).When using queues, components of a distributed application do not communicate directly with each other; instead they exchange messages via a queue, which acts as an intermediary (broker). Un producer di messaggi (mittente) invia un messaggio alla coda e quindi prosegue con la relativa elaborazione.A message producer (sender) hands off a message to the queue and then continues its processing. In modo asincrono, il consumer di messaggi (ricevitore) recupera il messaggio dalla coda e lo elabora.Asynchronously, a message consumer (receiver) pulls the message from the queue and processes it. Il producer non deve attendere la risposta del consumer per continuare a elaborare e inviare ulteriori messaggi.The producer does not have to wait for a reply from the consumer in order to continue to process and send further messages. Le code consentono un recapito dei messaggi di tipo FIFO (First In, First Out) a uno o più consumer concorrenti.Queues offer First In, First Out (FIFO) message delivery to one or more competing consumers. In base a questo metodo, in genere i messaggi vengono ricevuti ed elaborati nell'ordine temporale in cui sono stati aggiunti alla coda e ogni messaggio viene ricevuto ed elaborato da un solo consumer.That is, messages are typically received and processed by the receivers in the order in which they were added to the queue, and each message is received and processed by only one message consumer.

Concetti relativi alle code

Le code del bus di servizio sono una tecnologia di carattere generale che può essere usata in numerosi scenari:Service Bus queues are a general-purpose technology that can be used for a wide variety of scenarios:

  • Comunicazione tra ruoli Web e di lavoro in un'applicazione Azure multilivello.Communication between web and worker roles in a multi-tier Azure application.
  • Comunicazione tra app locali e app ospitate in Azure in una soluzione ibrida.Communication between on-premises apps and Azure-hosted apps in a hybrid solution.
  • Comunicazione tra componenti di un'applicazione distribuita in esecuzione in locale in organizzazioni diverse o in reparti diversi della stessa organizzazione.Communication between components of a distributed application running on-premises in different organizations or departments of an organization.

L'uso delle code consente la scalabilità delle applicazioni e garantisce maggiore resilienza all'architettura.Using queues enables you to scale your applications more easily, and enable more resiliency to your architecture.

Creare un'applicazione PHPCreate a PHP application

Per creare un'applicazione PHP che acceda al servizio BLOB di Azure, è sufficiente fare riferimento alle classi in Azure SDK per PHP dall'interno del codice.The only requirement for creating a PHP application that accesses the Azure Blob service is the referencing of classes in the Azure SDK for PHP from within your code. Per creare l'applicazione, è possibile usare qualsiasi strumento di sviluppo o il Blocco note.You can use any development tools to create your application, or Notepad.

Nota

L'installazione di PHP deve avere anche l'estensione OpenSSL installata e abilitata.Your PHP installation must also have the OpenSSL extension installed and enabled.

In questa guida si useranno le funzionalità del servizio che possono essere chiamate da un'applicazione PHP in locale o nel codice in esecuzione in un ruolo Web, in un ruolo di lavoro o in un sito Web di Azure.In this guide, you will use service features which can be called from within a PHP application locally, or in code running within an Azure web role, worker role, or website.

Acquisire le librerie client di AzureGet the Azure client libraries

Installazione tramite ComposerInstall via Composer

  1. Creare un file denominato composer.json nella radice del progetto, quindi aggiungere nel file il codice seguente:Create a file named composer.json in the root of your project and add the following code to it:

    {
      "require": {
        "microsoft/azure-storage": "*"
      }
    }
    
  2. Scaricare composer.phar nella radice del progetto.Download composer.phar in your project root.
  3. Aprire un prompt dei comandi ed eseguire il comando seguente nella radice del progettoOpen a command prompt and execute the following command in your project root

    php composer.phar install
    

In alternativa andare alla libreria client PHP di Archiviazione di Microsoft Azure su GitHub per clonare il codice sorgente.Alternatively go to the Azure Storage PHP Client Library on GitHub to clone the source code.

Configurare l'applicazione per l'uso del bus di servizioConfigure your application to use Service Bus

Per usare le API delle code del bus di servizio, procedere come segue:To use the Service Bus queue APIs, do the following:

  1. Fare riferimento al file autoloader mediante l'istruzione require_once.Reference the autoloader file using the require_once statement.
  2. Fare riferimento a tutte le eventuali classi utilizzabili.Reference any classes you might use.

Nell'esempio seguente viene indicato come includere il file autoloader e fare riferimento alla classe ServicesBuilder.The following example shows how to include the autoloader file and reference the ServicesBuilder class.

Nota

Questo esempio (e in altri esempi in questo articolo) presuppone che siano state installate le librerie client PHP per Azure tramite Composer.This example (and other examples in this article) assumes you have installed the PHP Client Libraries for Azure via Composer. Se le librerie sono state installate manualmente o come pacchetto PEAR, è necessario fare riferimento al file autoloader WindowsAzure.php.If you installed the libraries manually or as a PEAR package, you must reference the WindowsAzure.php autoloader file.

require_once 'vendor/autoload.php';
use WindowsAzure\Common\ServicesBuilder;

Nei seguenti esempi l'istruzione require_once verrà sempre visualizzata, ma si fa riferimento solo alle classi necessarie per eseguire l'esempio.In the examples below, the require_once statement will always be shown, but only the classes necessary for the example to execute are referenced.

Configurare una stringa di connessione per il bus di servizioSet up a Service Bus connection

Per creare un'istanza di un client del bus di servizio, è necessario innanzitutto disporre di una stringa di connessione valida nel seguente formato:To instantiate a Service Bus client, you must first have a valid connection string in this format:

Endpoint=[yourEndpoint];SharedAccessKeyName=RootManageSharedAccessKey;SharedAccessKey=[Primary Key]

Dove Endpoint è in genere nel formato [yourNamespace].servicebus.windows.net.Where Endpoint is typically of the format [yourNamespace].servicebus.windows.net.

Per creare un client del servizio Azure, è necessario usare la classe ServicesBuilder.To create any Azure service client you must use the ServicesBuilder class. È possibile:You can:

  • Passare la stringa di connessione direttamente.Pass the connection string directly to it.
  • utilizzare CloudConfigurationManager (CCM) per cercare la stringa di connessione in più origini esterne:Use the CloudConfigurationManager (CCM) to check multiple external sources for the connection string:
    • Per impostazione predefinita viene fornito con il supporto per un'origine esterna, ovvero le variabili ambientaliBy default it comes with support for one external source - environmental variables
    • È possibile aggiungere nuove origini estendendo la classe ConnectionStringSourceYou can add new sources by extending the ConnectionStringSource class

Per gli esempi illustrati in questo articolo, la stringa di connessione viene passata direttamente.For the examples outlined here, the connection string is passed directly.

require_once 'vendor/autoload.php';

use WindowsAzure\Common\ServicesBuilder;

$connectionString = "Endpoint=[yourEndpoint];SharedAccessKeyName=RootManageSharedAccessKey;SharedAccessKey=[Primary Key]";

$serviceBusRestProxy = ServicesBuilder::getInstance()->createServiceBusService($connectionString);

Creare una codaCreate a queue

È possibile eseguire operazioni di gestione per le code del bus di servizio usando la classe ServiceBusRestProxy.You can perform management operations for Service Bus queues via the ServiceBusRestProxy class. Un oggetto ServiceBusRestProxy è costruito tramite il metodo factory ServicesBuilder::createServiceBusService con una stringa di connessione appropriata che incapsula le autorizzazioni di token per gestirlo.A ServiceBusRestProxy object is constructed via the ServicesBuilder::createServiceBusService factory method with an appropriate connection string that encapsulates the token permissions to manage it.

L'esempio seguente mostra come creare un'istanza di ServiceBusRestProxy e chiamare il metodo ServiceBusRestProxy->createQueue per creare una coda denominata myqueue in uno spazio dei nomi del servizio MySBNamespace:The following example shows how to instantiate a ServiceBusRestProxy and call ServiceBusRestProxy->createQueue to create a queue named myqueue within a MySBNamespace service namespace:

require_once 'vendor/autoload.php';

use WindowsAzure\Common\ServicesBuilder;
use WindowsAzure\Common\ServiceException;
use WindowsAzure\ServiceBus\Models\QueueInfo;

// Create Service Bus REST proxy.
$serviceBusRestProxy = ServicesBuilder::getInstance()->createServiceBusService($connectionString);

try    {
    $queueInfo = new QueueInfo("myqueue");

    // Create queue.
    $serviceBusRestProxy->createQueue($queueInfo);
}
catch(ServiceException $e){
    // Handle exception based on error codes and messages.
    // Error codes and messages are here: 
    // https://docs.microsoft.com/rest/api/storageservices/Common-REST-API-Error-Codes
    $code = $e->getCode();
    $error_message = $e->getMessage();
    echo $code.": ".$error_message."<br />";
}

Nota

È possibile usare il metodo listQueues negli oggetti ServiceBusRestProxy per verificare se in uno spazio dei nomi esiste già una coda con il nome specificato.You can use the listQueues method on ServiceBusRestProxy objects to check if a queue with a specified name already exists within a namespace.

Inviare messaggi a una codaSend messages to a queue

Per inviare un messaggio a una coda del bus di servizio, l'applicazione chiama il metodo ServiceBusRestProxy->sendQueueMessage.To send a message to a Service Bus queue, your application calls the ServiceBusRestProxy->sendQueueMessage method. Il seguente codice illustra come inviare un messaggio alla coda myqueue creata in precedenza all'interno dello spazio dei nomi del servizio MySBNamespace.The following code shows how to send a message to the myqueue queue previously created within the MySBNamespace service namespace.

require_once 'vendor/autoload.php';

use WindowsAzure\Common\ServicesBuilder;
use WindowsAzure\Common\ServiceException;
use WindowsAzure\ServiceBus\Models\BrokeredMessage;

// Create Service Bus REST proxy.
$serviceBusRestProxy = ServicesBuilder::getInstance()->createServiceBusService($connectionString);

try    {
    // Create message.
    $message = new BrokeredMessage();
    $message->setBody("my message");

    // Send message.
    $serviceBusRestProxy->sendQueueMessage("myqueue", $message);
}
catch(ServiceException $e){
    // Handle exception based on error codes and messages.
    // Error codes and messages are here: 
    // https://docs.microsoft.com/rest/api/storageservices/Common-REST-API-Error-Codes
    $code = $e->getCode();
    $error_message = $e->getMessage();
    echo $code.": ".$error_message."<br />";
}

I messaggi inviati e ricevuti dalle code del bus di servizio sono istanze della classe BrokeredMessage.Messages sent to (and received from ) Service Bus queues are instances of the BrokeredMessage class. Gli oggetti BrokeredMessage includono un set di proprietà e metodi standard usati per contenere le proprietà personalizzate specifiche dell'applicazione e un corpo di dati arbitrari dell'applicazione.BrokeredMessage objects have a set of standard methods and properties that are used to hold custom application-specific properties, and a body of arbitrary application data.

Le code del bus di servizio supportano messaggi di dimensioni massime pari a 256 KB nel livello Standard e pari a 1 MB nel livello Premium.Service Bus queues support a maximum message size of 256 KB in the Standard tier and 1 MB in the Premium tier. Le dimensioni massime dell'intestazione, che include le proprietà standard e personalizzate dell'applicazione, non possono superare 64 KB.The header, which includes the standard and custom application properties, can have a maximum size of 64 KB. Non esiste alcun limite al numero di messaggi mantenuti in una coda, mentre è prevista una limitazione alla dimensione totale dei messaggi di una coda.There is no limit on the number of messages held in a queue but there is a cap on the total size of the messages held by a queue. Il limite massimo della dimensione di una coda è di 5 GB.This upper limit on queue size is 5 GB.

Ricevere messaggi da una codaReceive messages from a queue

Il modo ideale per ricevere i messaggi da una coda prevede l'uso di un metodo ServiceBusRestProxy->receiveQueueMessage.The best way to receive messages from a queue is to use a ServiceBusRestProxy->receiveQueueMessage method. È possibile ricevere i messaggi in due modi diversi: ReceiveAndDelete e PeekLock.Messages can be received in two different modes: ReceiveAndDelete and PeekLock. PeekLock è la modalità predefinita.PeekLock is the default.

Quando si usa la modalità ReceiveAndDelete, l'operazione di ricezione viene eseguita in un'unica fase. Quando infatti il bus di servizio riceve una richiesta di lettura per un messaggio in una coda, lo contrassegna come utilizzato e lo restituisce all'applicazione.When using ReceiveAndDelete mode, receive is a single-shot operation; that is, when Service Bus receives a read request for a message in a queue, it marks the message as being consumed and returns it to the application. La modalità ReceiveAndDelete costituisce il modello più semplice ed è adatta per scenari in cui un'applicazione può tollerare la mancata elaborazione di un messaggio in caso di errore.ReceiveAndDelete mode is the simplest model and works best for scenarios in which an application can tolerate not processing a message in the event of a failure. Per comprendere meglio questo meccanismo, si consideri uno scenario in cui il consumer invia la richiesta di ricezione e viene arrestato in modo anomalo prima dell'elaborazione.To understand this, consider a scenario in which the consumer issues the receive request and then crashes before processing it. Poiché il bus di servizio contrassegna il messaggio come utilizzato, quando l'applicazione viene riavviata e inizia a utilizzare nuovamente i messaggi, il messaggio utilizzato prima dell'arresto anomalo risulterà perso.Because Service Bus will have marked the message as being consumed, then when the application restarts and begins consuming messages again, it will have missed the message that was consumed prior to the crash.

Nella modalità PeekLock predefinita l'operazione di ricezione viene suddivisa in due fasi, in modo da consentire il supporto di applicazioni che non possono tollerare messaggi mancanti.In the default PeekLock mode, receiving a message becomes a two stage operation, which makes it possible to support applications that cannot tolerate missing messages. Quando il bus di servizio riceve una richiesta, individua il messaggio successivo da utilizzare, lo blocca per impedirne la ricezione da parte di altri consumer e quindi lo restituisce all'applicazione.When Service Bus receives a request, it finds the next message to be consumed, locks it to prevent other consumers from receiving it, and then returns it to the application. Dopo aver elaborato il messaggio, o averlo archiviato in modo affidabile per una successiva elaborazione, l'applicazione completa la seconda fase del processo di ricezione passando il messaggio ricevuto a ServiceBusRestProxy->deleteMessage.After the application finishes processing the message (or stores it reliably for future processing), it completes the second stage of the receive process by passing the received message to ServiceBusRestProxy->deleteMessage. Quando il bus di servizio vede la chiamata deleteMessage, contrassegna il messaggio come utilizzato e lo rimuove dalla coda.When Service Bus sees the deleteMessage call, it will mark the message as being consumed and remove it from the queue.

L'esempio seguente illustra come ricevere ed elaborare un messaggio usando la modalità PeekLock (predefinita).The following example shows how to receive and process a message using PeekLock mode (the default mode).

require_once 'vendor/autoload.php';

use WindowsAzure\Common\ServicesBuilder;
use WindowsAzure\Common\ServiceException;
use WindowsAzure\ServiceBus\Models\ReceiveMessageOptions;

// Create Service Bus REST proxy.
$serviceBusRestProxy = ServicesBuilder::getInstance()->createServiceBusService($connectionString);

try    {
    // Set the receive mode to PeekLock (default is ReceiveAndDelete).
    $options = new ReceiveMessageOptions();
    $options->setPeekLock();

    // Receive message.
    $message = $serviceBusRestProxy->receiveQueueMessage("myqueue", $options);
    echo "Body: ".$message->getBody()."<br />";
    echo "MessageID: ".$message->getMessageId()."<br />";

    /*---------------------------
        Process message here.
    ----------------------------*/

    // Delete message. Not necessary if peek lock is not set.
    echo "Message deleted.<br />";
    $serviceBusRestProxy->deleteMessage($message);
}
catch(ServiceException $e){
    // Handle exception based on error codes and messages.
    // Error codes and messages are here:
    // https://docs.microsoft.com/rest/api/storageservices/Common-REST-API-Error-Codes
    $code = $e->getCode();
    $error_message = $e->getMessage();
    echo $code.": ".$error_message."<br />";
}

Come gestire arresti anomali e messaggi illeggibili dell'applicazioneHow to handle application crashes and unreadable messages

Il bus di servizio fornisce funzionalità per il ripristino gestito automaticamente in caso di errori nell'applicazione o di problemi di elaborazione di un messaggio.Service Bus provides functionality to help you gracefully recover from errors in your application or difficulties processing a message. Se un'applicazione ricevente non è in grado di elaborare il messaggio per un qualsiasi motivo, può chiamare il metodo unlockMessage anziché deleteMessage sul messaggio ricevuto.If a receiver application is unable to process the message for some reason, then it can call the unlockMessage method on the received message (instead of the deleteMessage method). In questo modo, il bus di servizio sbloccherà il messaggio nella coda rendendolo nuovamente disponibile per la ricezione da parte della stessa o da un'altra applicazione consumer.This will cause Service Bus to unlock the message within the queue and make it available to be received again, either by the same consuming application or by another consuming application.

Al messaggio bloccato nella coda è inoltre associato un timeout. Se l'applicazione non riesce a elaborare il messaggio prima della scadenza del timeout, ad esempio a causa di un arresto anomalo, il bus di servizio sbloccherà automaticamente il messaggio rendendolo nuovamente disponibile per la ricezione.There is also a timeout associated with a message locked within the queue, and if the application fails to process the message before the lock timeout expires (for example, if the application crashes), then Service Bus will unlock the message automatically and make it available to be received again.

In caso di arresto anomalo dell'applicazione dopo l'elaborazione del messaggio, ma prima dell'invio della richiesta deleteMessage, il messaggio verrà nuovamente recapitato all'applicazione al riavvio del sistema.In the event that the application crashes after processing the message but before the deleteMessage request is issued, then the message will be redelivered to the application when it restarts. Questo processo di elaborazione viene spesso definito di tipo At-Least-Once, per indicare che ogni messaggio verrà elaborato almeno una volta, ma che in determinate situazioni potrà essere recapitato una seconda volta.This is often called At Least Once processing; that is, each message is processed at least once but in certain situations the same message may be redelivered. Se lo scenario non tollera la doppia elaborazione,è consigliabile aggiungere logica aggiuntiva alle applicazioni per gestire il secondo recapito del messaggio.If the scenario cannot tolerate duplicate processing, then adding additional logic to applications to handle duplicate message delivery is recommended. A tale scopo viene spesso usato il metodo getMessageId del messaggio, che rimane costante in tutti i tentativi di recapito.This is often achieved using the getMessageId method of the message, which remains constant across delivery attempts.

Passaggi successiviNext steps

A questo punto, dopo aver appreso le nozioni di base delle code del bus di servizio, vedere Code, argomenti e sottoscrizioni per altre informazioni.Now that you've learned the basics of Service Bus queues, see Queues, topics, and subscriptions for more information.

Per altre informazioni, vedere anche il Centro per sviluppatori PHP.For more information, also visit the PHP Developer Center.