def test_dequeue_order(self): """ Test the order that frames are returned by dequeue() method. """ dest = '/queue/foo' frame1 = StompFrame('MESSAGE', headers={'message-id': 'id-1'}, body='message-1') self.store.enqueue(dest, frame1) frame2 = StompFrame('MESSAGE', headers={'message-id': 'id-2'}, body='message-2') self.store.enqueue(dest, frame2) frame3 = StompFrame('MESSAGE', headers={'message-id': 'id-3'}, body='message-3') self.store.enqueue(dest, frame3) assert self.store.has_frames(dest) == True assert self.store.size(dest) == 3 # Perform some updates to change the expected order. sess = meta.Session() sess.execute(model.frames_table.update().where(model.frames_table.c.message_id=='id-1').values(queued=datetime.datetime(2010, 01, 01))) sess.execute(model.frames_table.update().where(model.frames_table.c.message_id=='id-2').values(queued=datetime.datetime(2009, 01, 01))) sess.execute(model.frames_table.update().where(model.frames_table.c.message_id=='id-3').values(queued=datetime.datetime(2004, 01, 01))) sess.commit() rframe1 = self.store.dequeue(dest) assert frame3 == rframe1 rframe2 = self.store.dequeue(dest) assert frame2 == rframe2 rframe3 = self.store.dequeue(dest) assert frame1 == rframe3 assert self.store.has_frames(dest) == False assert self.store.size(dest) == 0
def destinations(self): """ Provides a list of destinations (queue "addresses") available. @return: A list of the detinations available. @rtype: C{set} """ session = meta.Session() sel = select([distinct(model.frames_table.c.destination)]) result = session.execute(sel) return set([r[0] for r in result.fetchall()])
def has_frames(self, destination): """ Whether specified queue has any frames. @param destination: The queue name (destinationination). @type destination: C{str} @return: Whether there are any frames in the specified queue. @rtype: C{bool} """ session = meta.Session() sel = select([model.frames_table.c.message_id ]).where(model.frames_table.c.destination == destination) result = session.execute(sel) first = result.fetchone() return first is not None
def enqueue(self, destination, frame): """ Store message (frame) for specified destinationination. @param destination: The destinationination queue name for this message (frame). @type destination: C{str} @param frame: The message (frame) to send to specified destinationination. @type frame: C{stompclient.frame.Frame} """ session = meta.Session() message_id = frame.headers.get('message-id') if not message_id: raise ValueError("Cannot queue a frame without message-id set.") ins = model.frames_table.insert().values(message_id=message_id, destination=destination, frame=frame) session.execute(ins) session.commit()
def size(self, destination): """ Size of the queue for specified destination. @param destination: The queue destination (e.g. /queue/foo) @type destination: C{str} @return: The number of frames in specified queue. @rtype: C{int} """ session = meta.Session() sel = select([func.count(model.frames_table.c.message_id) ]).where(model.frames_table.c.destination == destination) result = session.execute(sel) first = result.fetchone() if not first: return 0 else: return int(first[0])
def dequeue(self, destination): """ Removes and returns an item from the queue (or C{None} if no items in queue). @param destination: The queue name (destinationination). @type destination: C{str} @return: The first frame in the specified queue, or C{None} if there are none. @rtype: C{stompclient.frame.Frame} """ session = meta.Session() try: selstmt = select( [model.frames_table.c.message_id, model.frames_table.c.frame]) selstmt = selstmt.where( model.frames_table.c.destination == destination) selstmt = selstmt.order_by(model.frames_table.c.queued, model.frames_table.c.sequence) result = session.execute(selstmt) first = result.fetchone() if not first: return None delstmt = model.frames_table.delete().where( model.frames_table.c.message_id == first[ model.frames_table.c.message_id]) session.execute(delstmt) frame = first[model.frames_table.c.frame] except: session.rollback() raise else: session.commit() return frame