Question

L'un de nos produits implémente la structure de service Web unidirectionnelle suivante:

Server <--------------------- Middleware <---------------- Client
        SOAP over JMS (queue)              SOAP over HTTP

Dans ce modèle, les clients envoient des messages SOAP via HTTP à notre middleware (Progress SonicMQ). Les messages sont poussés dans les files d'attente JMS par SonicMQ et notre serveur les récupère à partir de là. Cependant, comme vous pouvez le constater, le serveur n'envoie pas de réponse au client (JMS asynchrone).

Nous aimerions implémenter un canal de réponse pour ce modèle. La solution souvent suggérée consiste à créer une file d'attente replyTo temporaire (à la volée) dans le middleware, ce qui permet au serveur d'envoyer une réponse à cette file d'attente. Ensuite, le client peut extraire la réponse et la file d'attente replyTo est fermée. Cela semble assez pratique, mais malheureusement, nos clients fonctionnent sur HTTP simple et non sur JMS, de sorte que leurs clients ne peuvent pas facilement configurer les files d'attente replyTo.

Une approche pour obtenir un canal de réponse dans un tel modèle hybride SOAP HTTP / JMS consiste à configurer le middleware pour qu'il ouvre la file d'attente replyTo à chaque réception SOAP réussie, ajoute les informations replyTo-queue et l'expéditeur au message SOAP et envoie le message message à la file d'attente, où il serait récupéré par le serveur. Après avoir reçu et traité le message, le serveur pourrait envoyer une réponse à la file d'attente replyTo indiquée dans le middleware. Enfin, le middleware renverrait la réponse (SOAP) via HTTP au client d'origine en utilisant les données du message SOAP (les données qui y étaient insérées dans les procédures du middleware lors de la première réception de la demande).

Bien que cela soit probablement possible, cela ressemble à un hacky. La question est donc la suivante: existe-t-il des moyens plus propres de réaliser un tel modèle de demande / réponse dans notre cas? La fin du serveur a été implémentée en Java.

La solution:

Progression SonicMQ prend en charge " réponse au contenu Envoi " HTTP Acceptor, qui permet d’envoyer facilement une réponse JMS. L’accepteur d’envoi de réponse au contenu fonctionne de la manière suivante:

  • Acceptor reçoit le message HTTP envoyé par un client
  • Acceptor crée une file d'attente JMS temporaire
  • Acceptor construit un message JMS contenant le corps HTTP et ajoute l'identification de la file d'attente temporaire au nouveau message JMS créé
  • Acceptor place le message JMS dans la file d'attente de destination (pas la file d'attente temporaire)
  • Acceptor commence à utiliser la file d'attente de réponses temporaire
  • Lorsque le client extrait le message de la file d'attente de destination d'origine, il contient l'identifiant défini de la file d'attente de réponses-À
  • Le client consomme le message
  • Le client envoie une réponse à la file d'attente Reply-To
  • L'accepteur reçoit un message de la file d'attente
  • Acceptor envoie un message en tant que HTTP au client qui a envoyé le message HTTP à l'origine

Si le consommateur (" serveur " dans notre cas) échoue et n'envoie pas de réponse, le HTTP Acceptor envoie un message HTTP au client indiquant le délai. Ceci est une fonctionnalité très standard de SonicMQ. Je suppose que cela existe également dans d’autres produits.

Ceci permet d’utiliser SOAP standard sur JMS (voir la réponse de skaffman) dans le & serveur & "; end évite toute programmation personnalisée dans le middleware.

Je vois toujours quelques problèmes dans le modèle JMS, mais il s’agit bien d’une amélioration.

Mise à jour 2009-11-05:

Après plus de recherches sur ce problème, mes soupçons contre HTTP < - > middleware < - > JMS ont été pertinents.

Il y a quelques problèmes critiques dans ce modèle. Le modèle synchrone-asynchrone avec middleware n'est tout simplement pas pratique. Soit les deux extrémités implémentent la connexion JMS (qui devrait basculer), soit avec HTTP aux deux extrémités. Les mélanger ne provoque que des maux de tête. SOAP sur HTTP est plus simple et mieux pris en charge que SOAP sur JMS.

Encore une fois: si vous concevez ce type de système ... NE LE FAITES PAS.

Était-ce utile?

La solution

Je ne pense pas que votre solution suggérée soit un bidouillage, je pense que c'est la bonne solution. Vous avez la couche intermédiaire client avec un protocole synchrone, puis la couche intermédiaire du serveur utilisant une couche asynchrone, à laquelle vous devez ajouter un chemin de réponse afin de satisfaire la sémantique synchrone. C'est à ça que sert le middleware. N'oubliez pas que JMS fournit une prise en charge explicite des files d'attente de réponses temporaires. Vous n'aurez donc pas besoin de manipuler la charge utile.

Une possibilité plus à gauche réside dans le fait que SOAP 1.2 a été conçu avec JMS en tête. Vous pouvez donc utiliser la couche de service Web entre la couche middleware et la couche serveur qui gère SOAP sur JMS. Cela signifie que vous pouvez conserver SOAP de bout en bout, le middleware ne modifiant que le transport.

À ma connaissance, la seule pile de services Web prenant en charge le transport JMS est Spring Web. Services , dont le processus et le développement sont documenté ici . Cela vous donnerait également l’opportunité de porter votre couche SOAP sur Spring-WS, ce qui donne un coup de pied au cul:)

Autres conseils

Pourquoi ne pas ajouter un lien vers une page permettant aux utilisateurs de vérifier le moment où une réponse est prête, par exemple un identifiant de traqueur Fed Ex? Indiquez l'ID de suivi à vos utilisateurs lorsqu'ils envoient la demande.

Cela entrerait dans l'idiome requête / réponse HTTP et vos utilisateurs sauraient toujours que la demande est & "feu et oublie &";.

.
Licencié sous: CC-BY-SA avec attribution
Non affilié à StackOverflow
scroll top