在WebSphere MQ 6中,我想编写新队列的脚本。但是队列可能已经存在,我需要脚本是幂等的。
我可以使用命令documented here创建队列。例如:
DEFINE QREMOTE(%s) RNAME(%s) RQMNAME(%s) XMITQ(%s) DEFPSIST(YES) REPLACE
或
DEFINE QLOCAL(%s) DESCR(%s) DEFPSIST(YES) REPLACE
REPLACE
关键字可确保在队列已存在时创建不会失败。
我已经使用现有的非空队列对此进行了测试,似乎没有消息丢失。然而,这不足以证明这一点。我需要确定,如果我对现有队列运行DEFINE Q... REPLACE
命令,则不会丢失或损坏任何消息。现有队列甚至可能在当时参与交易。
任何人都可以确认或否认这种行为吗?
答案 0 :(得分:2)
如果对象处于打开状态,DEFINE
REPLACE
命令将失败。因此,您无法使用挂起的事务重新定义队列。 DEFINE
REPLACE
期间ALTER
期间保留队列中所有邮件的manual states,这意味着不会丢失邮件完整性。您可FORCE
具有DEFINE
选项的队列来更改当前打开的队列here。这也会在队列中保留消息而不会损失完整性。
FIFO
命令不会影响队列中的消息。您可能会注意到的唯一影响是,例如,如果您将队列从PRIORITY
更改为BIND(ONOPEN)
,反之亦然。这仅更改队列中 new 消息的索引和排序,并且不会影响现有消息。同样,更改影响句柄的队列属性仅在下次打开队列时生效。一个例子就是将BIND(NOTFIXED)
更改为DEFINE QLOCAL (APP.FUNCTION.SUBFUNCTION.QA) +
GET(DISABLED) +
PUT(DISABLED) +
NOTRIGGER +
NOREPLACE
ALTER QLOCAL (APP.FUNCTION.SUBFUNCTION.QA) +
DESCR('APP service queue for QA') +
DEFPSIST(NO) +
BOTHRESH(5) +
BOQNAME('APP.FUNCTION.BACKOUT.QA') +
CLUSTER('DIV_QA') +
CLUSNL(' ') +
DEFBIND(NOTFIXED)
。
我对WMQ集群recommending for a while的一个看法是将队列定义拆分为构建时和运行时属性。例如:
GET
在这种情况下,PUT
,TRIGGER
和NOREPLACE
属性被视为运行时属性,仅在首次定义队列时设置。这允许您在群集中定义新队列,并在准备好打开应用程序之前将其禁用。在后续的脚本运行中,这些属性永远不会更改,因为该语句使用GET
。因此,一旦在队列上启用PUT
和ALTER
,这些属性(以及应用程序的功能)就不会受到后续脚本运行的干扰。
GET(DISABLED)
然后处理所有被视为构建时的属性。例如,如果更改描述,则希望在下一个脚本运行中选择它。因为我们在上一步中定义了队列(或者因为队列存在而导致该步骤失败),所以我们知道ALTER会起作用。
群集成员资格等任何属性是构建时还是运行时由您自行决定。这只是一个例子,在很多情况下管理员通过重新运行MQSC脚本而无意中破坏了某些东西。
但要更多地回答你的问题,那些破坏的事情是因为某人重置了{{1}} 等运行时属性(这可能会导致正在进行的事务被撤消如果应用程序尝试在禁用获取后对该队列执行GET)而不是因为更改导致队列,消息或事务的完整性失败。