C# 无法确定是否存在具有指定格式名称的队列
我在执行以下代码时遇到异常。你知道怎么了吗C# 无法确定是否存在具有指定格式名称的队列,c#,exception,msmq,C#,Exception,Msmq,我在执行以下代码时遇到异常。你知道怎么了吗 string queueName = "FormatName:Direct=TCP:1.1.1.1\\Private$\\test"; MessageQueue queue; if (MessageQueue.Exists(queueName)) queue = new System.Messaging.MessageQueue(queueName); else queue = MessageQueue.Create(queueName);
string queueName = "FormatName:Direct=TCP:1.1.1.1\\Private$\\test";
MessageQueue queue;
if (MessageQueue.Exists(queueName))
queue = new System.Messaging.MessageQueue(queueName);
else queue = MessageQueue.Create(queueName);
queue.Send(sWriter.ToString());
编辑:
这是异常消息和stacktrace的第一行无法确定是否存在具有指定格式名称的队列 存在。
位于System.Messaging.MessageQueue.exists(字符串路径)
顺便说一句,它适用于本地队列。从您的示例中,看起来您正在尝试检查是否存在远程专用队列,但正如文档所述: 无法调用Exists来验证 存在远程专用队列 尝试这样做将产生一个
InvalidOperationException
如果您的工作流确实需要这些信息,您可以使用该方法并迭代结果以找到匹配项。如果你愿意,我建议你阅读,这篇文章对这种方法进行了深入的讨论 建议另一种选择:甚至不检查队列是否存在,“而是在队列不存在的情况下处理未传递的消息。”(您需要跟踪管理队列和/或死信队列,但您可能无论如何都应该这样做。)试试这个
public static bool IsQueueAvailable(string queueName)
{
var queue = new MessageQueue(queueName);
try
{
queue.Peek(new TimeSpan(0, 0, 5));
return true;
}
catch (MessageQueueException ex)
{
return ex.Message.StartsWith("Timeout");
}
}
如果队列不存在,或者运行应用程序的帐户没有足够的权限访问该队列,则异常消息会明确说明这一点
而且,这将同时适用于FormatName和常规队列路径。以上检查异常消息的答案确实适用于引发英语异常的系统。我的系统引发了荷兰例外。我得到“De timeout voor De gevraagde bewerking is verstreken.”所以这不是一个非常健壮的解决方案异常有一个属性MessageQueueErrorCode,应该用来检查是否发生了IOTimeout 所以最好使用
return (ex.MessageQueueErrorCode == MessageQueueErrorCode.IOTimeout);
而不是:
return ex.Message.StartsWith("Timeout");
无法在远程队列上使用Exists方法,因此必须模拟该远程计算机上的用户:
//usings
using System;
using System.Messaging;
using System.Runtime.InteropServices;
using System.Security;
using System.Security.Principal;
//Declaring the advapi32.dll
[DllImport("advapi32.dll", SetLastError = true)]
public static extern bool LogonUser(
string lpszUsername,
string lpszDomain,
string lpszPassword,
int dwLogonType,
int dwLogonProvider,
out IntPtr phToken);
private void IterateRemoteMQ()
{
IntPtr userToken = IntPtr.Zero;
bool success = LogonUser(
"REMOTE_USERNAME", //Username on the remote machine
".", //Domain, if not using AD, Leave it at "."
"PASSWORD", //Password for the username on the remote machine
9, //Means we're using new credentials, otherwise it will try to impersonate a local user
0,
out userToken);
if (!success)
{
throw new SecurityException("Logon user failed");
}
//Go through each queue to see if yours exists, or do some operation on that queue.
using (WindowsIdentity.Impersonate(userToken))
{
MessageQueue[] Queues = MessageQueue.GetPrivateQueuesByMachine("192.168.1.10");
foreach (MessageQueue mq in Queues)
{
string MSMQ_Name = mq.QueueName;
}
}
我最终得到了来自、和的答案。此外,我还检查了
ArgumentException
:
/// <summary>
/// Checks if a (remote) Microsoft Message Queue is available
/// </summary>
/// <param name="queueName">The name of the Message Queue.</param>
/// <returns>Returns true if the queue is available otherwise false.</returns>
public static bool IsQueueAvailable(string queueName)
{
MessageQueue queue;
try
{
queue = new MessageQueue(queueName);
queue.Peek(new TimeSpan(0, 0, 5)); // wait max. 5 sec. to recieve first message from queue (reduce if necessary)
return true;
}
catch (Exception ex)
{
if(ex is ArgumentException)
{ // the provided queue name is wrong.
return false;
}
else if (ex is MessageQueueException)
{ // if message queue exception occurs either the queue is avialable but without entries (check for peek timeout) or the queue does not exist or you don't have access.
return (((MessageQueueException)ex).MessageQueueErrorCode == MessageQueueErrorCode.IOTimeout);
}
// any other error occurred.
return false;
}
}
//
///检查(远程)Microsoft消息队列是否可用
///
///消息队列的名称。
///如果队列可用,则返回true;否则返回false。
公共静态bool IsQueueAvailable(字符串queueName)
{
消息队列;
尝试
{
队列=新消息队列(队列名称);
queue.Peek(新时间跨度(0,0,5));//最多等待5秒以接收来自队列的第一条消息(如有必要,减少)
返回true;
}
捕获(例外情况除外)
{
if(ex为异常)
{//提供的队列名称错误。
返回false;
}
else if(ex为MessageQueueException)
{//如果发生消息队列异常,则队列是可访问的,但没有条目(检查peek timeout),或者队列不存在,或者您没有访问权限。
返回(((MessageQueueException)ex.MessageQueueErrorCode==MessageQueueErrorCode.IOTimeout);
}
//发生任何其他错误。
返回false;
}
}
请提供异常消息测试时,我在队列为空时获得超时。@请检查我的组合答案: