Tout le monde ici a fait un travail fantastique à fournir des solutions, et juste après avoir fini moi-même aux prises avec ce problème, je voulais jeter mon propre 2c et montrer la solution Je suis arrivé avec ça fonctionne très bien.
Tout d'abord lorsque la file d'attente est créée, je fais que j'ouvrir les autorisations comme si (je ne suis pas préoccupé par la sécurité de file d'attente dans le contexte de notre application ... ceci est une décision calculée):
queue.SetPermissions("Everyone", MessageQueueAccessRights.FullControl, AccessControlEntryType.Set);
Sans cette ligne, je recevrais toutes sortes d'erreurs inaccessibles et ne pouvais même pas parcourir la file d'attente à partir de l'écran de gestion de l'ordinateur.Soit dit en passant, si cela vous arrive et vous vous demandez comment tuer la file d'attente que vous n'avez pas accès à tout:
- Arrêtez le service « Message Queuing »
- Aller à « C: \ Windows \ System32 \ MSMQ \ storage \ lqs »
- Ouvrir chaque fichier dans le bloc-notes et recherchez votre nom de file d'attente (il sera très probablement le fichier qui a été le plus récemment modifié)
- Supprimer ce fichier et redémarrez le service de messagerie
Créer une classe de base f ou vos éléments de message de file d'attente et marquez-le [Serializable]. Le cache de charge de l'application d'une liste de tous vos types de messages en utilisant quelque chose comme ceci:
var types = typeof(QueueItemBase).Assembly
.GetTypes()
.Where(t => typeof(QueueItemBase).IsAssignableFrom(t) && t.IsAbstract == false)
.ToArray();
...
// Create and cache a message formatter instance
_messageFormatter = new XmlMessageFormatter(types);
Maintenant, vous êtes prêt à recevoir des messages. Mon premier instinct était de rechercher des messages, mais l'API n'aime pas vraiment travailler de cette façon. Donc, je crée un thread d'arrière-plan et appelle la méthode de blocage Receive sur la file d'attente qui reviendra une fois qu'un message est disponible. De là, le décodage message est aussi simple que:
var message = queue.Receive();
if (message == null)
continue;
// Tell the message about our formatter containing all our message types before we
// try and deserialise
message.Formatter = _messageFormatter;
var item = message.Body as QueueItemBase;
Et cela devrait être tout ce que vous avez besoin pour bien mis en œuvre, l'intégration typesafe MSMQ!
Parfait! Juste ce que je voulais. – NLV