def test_ItemDrop_model(self): # ItemDrops just use string-times # This item is for BRD and CLR, and is droppable with min_dkp 3 itemdrop = models.ItemDrop("Ochre Tessera", "Bob", "Mon Aug 17 07:15:39 2020") self.assertEqual("BRD, CLR", itemdrop.classes()) self.assertEqual("Yes", itemdrop.droppable()) self.assertEqual(config.MIN_DKP, itemdrop.min_dkp()) # This item is for BRD only and is NODROP itemdrop = models.ItemDrop("Light Woolen Mask", "Bob", "Mon Aug 17 07:15:39 2020") self.assertEqual("BRD", itemdrop.classes()) self.assertEqual("NO", itemdrop.droppable()) # This item should have the case fixed itemdrop = models.ItemDrop("light WOOLEN Mask", "Bob", "Mon Aug 17 07:15:39 2020") self.assertEqual("Light Woolen Mask", itemdrop.name) # Should be JSON Encodable itemdrop_json = json.dumps(itemdrop, cls=utils.JSONEncoder) # Should be JSON Decodable loaded_itemdrop = json.loads(itemdrop_json, cls=utils.JSONDecoder) self.assertEqual(itemdrop, loaded_itemdrop)
def test_DKPAuction_model_bid_text(self): item_name = 'Copper Disc' itemdrop = models.ItemDrop(item_name, "Jim", "timestamp") auc = models.DKPAuction(itemdrop, 'VCR', min_dkp=3) # No bids config.PRIMARY_BID_CHANNEL = 'auc' self.assertEqual( "/AUC ~[Copper Disc] (DRU, SHD) - BID IN /AUC, MIN 3 DKP. " "You MUST include the item name in your bid! Closing in {}. ". format(auc.time_remaining_text()), auc.bid_text()) # Valid bid result = auc.add(3, 'Peter') self.assertTrue(result) self.assertListEqual([('Peter', 3)], auc.highest()) # Bid exists config.PRIMARY_BID_CHANNEL = 'shout' self.assertEqual( "/SHOUT ~[Copper Disc] (DRU, SHD) - BID IN /SHOUT. " "You MUST include the item name in your bid! Currently: " "`Peter` with 3 DKP - Closing in {}! ".format( auc.time_remaining_text()), auc.bid_text()) item_name = 'Golden Jasper Earring' itemdrop = models.ItemDrop(item_name, "Jim", "timestamp") auc = models.DKPAuction(itemdrop, 'VCR', min_dkp=3) # No bids config.PRIMARY_BID_CHANNEL = 'gu' self.assertEqual( "/GU ~[Golden Jasper Earring] - BID IN /GU, MIN 3 DKP. " "You MUST include the item name in your bid! Closing in {}. ". format(auc.time_remaining_text()), auc.bid_text())
def test_handle_gratss(self, mock_post_event, mock_store_state): config.PENDING_AUCTIONS.clear() config.ACTIVE_AUCTIONS.clear() # Set up a historical auction with bids jerkin_1 = models.ItemDrop('Shiverback-hide Jerkin', 'Jim', 'Sun Aug 16 22:47:31 2020') config.PENDING_AUCTIONS.append(jerkin_1) auction1 = utils.start_auction_dkp(jerkin_1, 'VCR') self.assertEqual(config.ACTIVE_AUCTIONS.get(auction1.item.uuid), auction1) bid_line = ("[Sun Aug 16 22:47:31 2020] Toald tells the guild, " "'Shiverback-hide Jerkin 1 main'") config.RESTRICT_BIDS = False bid_match = config.MATCH_BID_GU.match(bid_line) message_handlers.handle_bid(bid_match, 'window') config.HISTORICAL_AUCTIONS[auction1.item.uuid] = ( config.ACTIVE_AUCTIONS.pop(auction1.item.uuid)) # Set up a historical auction without bids (rot) disc_1 = models.ItemDrop('Copper Disc', 'Jim', 'Sun Aug 16 22:47:31 2020') config.PENDING_AUCTIONS.append(disc_1) auction2 = utils.start_auction_dkp(disc_1, 'VCR') self.assertEqual(config.ACTIVE_AUCTIONS.get(auction2.item.uuid), auction2) config.HISTORICAL_AUCTIONS[auction2.item.uuid] = ( config.ACTIVE_AUCTIONS.pop(auction2.item.uuid)) # A gratss message from auction history should not register (bids) line = ("[Sun Aug 16 22:47:31 2020] Jim tells the guild, " "'~Gratss Toald on [Shiverback-hide Jerkin] (1 DKP)!'") match = config.MATCH_GRATSS.match(line) self.assertFalse(message_handlers.handle_gratss(match, 'window')) # A gratss message from auction history should not register (no bids) line = ("[Sun Aug 16 22:47:31 2020] Jim tells the guild, " "'~Gratss ROT on [Copper Disc] (0 DKP)!'") match = config.MATCH_GRATSS.match(line) self.assertFalse(message_handlers.handle_gratss(match, 'window')) # A gratss message that doesn't match auction history SHOULD register line = ("[Sun Aug 16 22:47:31 2020] Jim tells the guild, " "'~Gratss Jim on [Bladestopper] (100 DKP)!'") match = config.MATCH_GRATSS.match(line) self.assertTrue(message_handlers.handle_gratss(match, 'window')) # A gratss message direct to /tell should register (no tell windows) line = ("[Sun Aug 16 22:47:31 2020] Jim tells you, " "'~Gratss Jim on [Bladestopper] (100 DKP)!'") match = config.MATCH_GRATSS.match(line) self.assertTrue(message_handlers.handle_gratss(match, 'window')) # A gratss message direct to /tell should register (tell windows) line = ("[Sun Aug 16 22:47:31 2020] Jim -> You, " "'~Gratss Jim on [Bladestopper] (100 DKP)!'") match = config.MATCH_GRATSS.match(line) self.assertTrue(message_handlers.handle_gratss(match, 'window'))
def add_sample_data(): copper_disc = models.ItemDrop('Copper Disc', 'Bob', 'Mon Aug 17 07:15:39 2020') platinum_disc1 = models.ItemDrop('Platinum Disc', 'Jim', 'Mon Aug 17 07:16:05 2020') platinum_disc2 = models.ItemDrop('Platinum Disc', 'Bill', 'Mon Aug 17 07:16:05 2020') config.PENDING_AUCTIONS.append(copper_disc) config.PENDING_AUCTIONS.append(platinum_disc1) config.PENDING_AUCTIONS.append(platinum_disc2)
def handle_drop(match: re.Match, window: wx.Frame, skip_store=False) -> list: timestamp = match.group("time") name = match.group("name") text = match.group("text") guild = config.LAST_WHO_SNAPSHOT.get(name, models.Player(name)).guild if text.lower().startswith("looted"): LOG.info("Ignoring drop message starting with 'looted'") return list() if AWARD_MESSAGE_MATCHER.match(text): LOG.info("Ignoring drop message that matches Gratss") return list() if NUMBER_MATCHER.match(text): # line contains a number, it's probably a bid, ignore it LOG.info("Ignoring drop message with a number, probably a bid") return list() if config.RESTRICT_BIDS and guild and guild not in config.ALLIANCE_MAP: # Some other guild is talking, discard line LOG.info("Ignoring ooc from guild %s", guild) return list() # Handle text to return a list of items linked found_items = utils.get_items_from_text(text) used_found_items = [] now = datetime.datetime.now() skip = False for item in found_items: if item.lower() in utils.get_active_item_names(): LOG.debug("Skipping drop %s because it is already up for auction.") continue for pending in config.PENDING_AUCTIONS: pending_time = dateutil.parser.parse(pending.timestamp) if (item.lower() == pending.name.lower() and (now - pending_time).seconds < config.DROP_COOLDOWN): skip = True LOG.debug("Skipping drop %s because of DROP_COOLDOWN config.", item) break if skip: skip = False continue drop = models.ItemDrop(item, name, timestamp) if (config.NODROP_ONLY and item in extra_data.EXTRA_ITEM_DATA and not extra_data.EXTRA_ITEM_DATA[item].get('nodrop', True)): config.IGNORED_AUCTIONS.append(drop) LOG.info("Added droppable item to IGNORED AUCTIONS: %s", drop) else: config.PENDING_AUCTIONS.append(drop) LOG.info("Added item to PENDING AUCTIONS: %s", drop) used_found_items.append(item) if not found_items: return list() if used_found_items: wx.PostEvent(window, models.DropEvent()) utils.alert_message( "New Drops Detected", '\n'.join(["\u00A0\u2022 %s" % drop for drop in used_found_items])) utils.alert_sound(config.NEW_DROP_SOUND) if not skip_store: utils.store_state() return found_items
def test_RandomAuction_model_bid_text(self): item_name = 'Copper Disc' itemdrop = models.ItemDrop(item_name, "Jim", "timestamp") config.NUMBERS = ['12345'] auc = models.RandomAuction(itemdrop) config.PRIMARY_BID_CHANNEL = 'auc' self.assertEqual("/AUC ~[Copper Disc] (DRU, SHD) ROLL 12345 NOW!", auc.bid_text()) item_name = 'Golden Jasper Earring' itemdrop = models.ItemDrop(item_name, "Jim", "timestamp") auc = models.RandomAuction(itemdrop) config.PRIMARY_BID_CHANNEL = 'gu' self.assertEqual("/GU ~[Golden Jasper Earring] ROLL 12345 NOW!", auc.bid_text())
def test_Auction_base_model(self): item_name = 'Copper Disc' itemdrop = models.ItemDrop(item_name, "Jim", "timestamp") auc = models.Auction(itemdrop) self.assertRaises(NotImplementedError, auc.add, 1, 'Jim') self.assertRaises(NotImplementedError, auc.highest) # Should be JSON Encodable auc_json = json.dumps(auc, cls=utils.JSONEncoder) # Should be JSON Decodable loaded_auc = json.loads(auc_json, cls=utils.JSONDecoder) self.assertEqual(auc, loaded_auc)
def test_RandomAuction_model_add(self): item_name = 'Copper Disc' itemdrop = models.ItemDrop(item_name, "Jim", "timestamp") auc = models.RandomAuction(itemdrop) self.assertListEqual([], auc.highest()) # First roll, valid result = auc.add(10, 'Peter') self.assertTrue(result) self.assertListEqual([('Peter', 10)], auc.highest()) # Second roll, lower than first roll result = auc.add(8, 'Paul') self.assertTrue(result) self.assertListEqual([('Peter', 10)], auc.highest()) # Third roll, higher than first roll result = auc.add(12, 'Mary') self.assertTrue(result) self.assertListEqual([('Mary', 12)], auc.highest()) # Fifth roll, player rolls a second time result = auc.add(18, 'Paul') self.assertFalse(result) self.assertListEqual([('Mary', 12)], auc.highest()) # Fifth roll, tied with highest roll result = auc.add(12, 'Dan') self.assertTrue(result) self.assertEqual(2, len(tuple(auc.highest()))) self.assertIn(('Mary', 12), tuple(auc.highest())) self.assertIn(('Dan', 12), tuple(auc.highest())) # Invalid roll result = auc.add(None, 'Fred') self.assertFalse(result) # All rolls should be tracked self.assertDictEqual({ 'Dan': 12, 'Mary': 12, 'Paul': 8, 'Peter': 10 }, auc.rolls) # Should be JSON Encodable auc_json = json.dumps(auc, cls=utils.JSONEncoder) # Should be JSON Decodable loaded_auc = json.loads(auc_json, cls=utils.JSONDecoder) self.assertEqual(auc, loaded_auc)
def test_start_auction_dkp(self): pending = utils.config.PENDING_AUCTIONS active = utils.config.ACTIVE_AUCTIONS pending.clear() active.clear() copper_disc = models.ItemDrop('Copper Disc', 'Jim', 'timestamp') pending.append(copper_disc) utils.start_auction_dkp(copper_disc, 'VCR') self.assertListEqual([], pending) self.assertIn(copper_disc.uuid, active) self.assertIsInstance(active[copper_disc.uuid], models.DKPAuction)
def test_RandomAuction_model_win_text(self): item_name = 'Copper Disc' itemdrop = models.ItemDrop(item_name, "Jim", "timestamp") config.NUMBERS = ['12345'] auc = models.RandomAuction(itemdrop) config.PRIMARY_BID_CHANNEL = 'auc' auc.add(10, "Bill") auc.add(20, "Tom") auc.add(5, "James") self.assertEqual("/AUC ~Gratss Tom on [Copper Disc] with 20 / 12345!", auc.win_text())
def test_handle_bid_all_matchers(self, mock_post_event, mock_store_state): item_name = 'Copper Disc' itemdrop = models.ItemDrop(item_name, "Jim", "timestamp") disc_auction = models.DKPAuction(itemdrop, 'VCR') config.ACTIVE_AUCTIONS = {itemdrop.uuid: disc_auction} # Check SAY line = ("[Sun Aug 16 22:47:31 2020] Jim says, " "'Copper Disc 10 DKP'") match = config.MATCH_BID_SAY.match(line) result = message_handlers.handle_bid(match, 'window') self.assertTrue(result) # Check OOC line = ("[Sun Aug 16 22:47:31 2020] Jim says out of character, " "'Copper Disc 11 DKP'") match = config.MATCH_BID_OOC.match(line) result = message_handlers.handle_bid(match, 'window') self.assertTrue(result) # Check AUC line = ("[Sun Aug 16 22:47:31 2020] Jim auctions, " "'Copper Disc 12 DKP'") match = config.MATCH_BID_AUC.match(line) result = message_handlers.handle_bid(match, 'window') self.assertTrue(result) # Check SHOUT line = ("[Sun Aug 16 22:47:31 2020] Jim shouts, " "'Copper Disc 13 DKP'") match = config.MATCH_BID_SHOUT.match(line) result = message_handlers.handle_bid(match, 'window') self.assertTrue(result) # Check GU line = ("[Sun Aug 16 22:47:31 2020] Jim tells the guild, " "'Copper Disc 14 DKP'") match = config.MATCH_BID_GU.match(line) result = message_handlers.handle_bid(match, 'window') self.assertTrue(result) config.ACTIVE_AUCTIONS.clear()
def test_DKPAuction_model_add(self): item_name = 'Copper Disc' itemdrop = models.ItemDrop(item_name, "Jim", "timestamp") auc = models.DKPAuction(itemdrop, 'VCR', min_dkp=3) self.assertListEqual([], auc.highest()) # Bid too low result = auc.add(2, 'Peter') self.assertFalse(result) self.assertListEqual([], auc.highest()) # First bid, valid result = auc.add(10, 'Peter') self.assertTrue(result) self.assertListEqual([('Peter', 10)], auc.highest()) # Second bid, lower than first bid result = auc.add(8, 'Paul') self.assertFalse(result) self.assertListEqual([('Peter', 10)], auc.highest()) # Third bid, higher than first bid result = auc.add(12, 'Mary') self.assertTrue(result) self.assertListEqual([('Mary', 12)], auc.highest()) # Fourth bid, tied with highest bid result = auc.add(12, 'Dan') self.assertFalse(result) self.assertListEqual([('Mary', 12)], auc.highest()) # Invalid bid result = auc.add(None, 'Fred') self.assertFalse(result) # Should be JSON Encodable auc_json = json.dumps(auc, cls=utils.JSONEncoder) # Should be JSON Decodable loaded_auc = json.loads(auc_json, cls=utils.JSONDecoder) self.assertEqual(auc, loaded_auc)
def test_handle_bid(self, mock_post_event, mock_store_state): config.LAST_WHO_SNAPSHOT = { 'Jim': models.Player('Jim', None, None, 'Venerate'), 'Pim': models.Player('Pim', None, None, 'Castle'), 'Tim': models.Player('Tim', None, None, 'Kingdom'), 'Dan': models.Player('Dan', None, None, 'Dial a Daniel'), } item_name = 'Copper Disc' itemdrop = models.ItemDrop(item_name, "Jim", "timestamp") disc_auction = models.DKPAuction(itemdrop, 'VCR') config.ACTIVE_AUCTIONS = {itemdrop.uuid: disc_auction} # FILTER ON - Someone in the alliance bids on an inactive item config.RESTRICT_BIDS = True line = ("[Sun Aug 16 22:47:31 2020] Jim auctions, " "'Platinum Disc 10 DKP'") match = config.MATCH_BID[1].match(line) result = message_handlers.handle_bid(match, 'window') self.assertFalse(result) self.assertListEqual([], disc_auction.highest()) self.assertEqual(1, len(config.ACTIVE_AUCTIONS)) mock_post_event.assert_not_called() # FILTER ON - Someone outside the alliance bids on an active item line = ("[Sun Aug 16 22:47:31 2020] Dan auctions, " "'Copper Disc 10 DKP'") match = config.MATCH_BID[1].match(line) result = message_handlers.handle_bid(match, 'window') self.assertFalse(result) self.assertEqual([], disc_auction.highest()) mock_post_event.assert_not_called() # FILTER OFF - Someone in the alliance bids on an inactive item config.RESTRICT_BIDS = False line = ("[Sun Aug 16 22:47:31 2020] Jim auctions, " "'Platinum Disc 10 DKP'") match = config.MATCH_BID[1].match(line) result = message_handlers.handle_bid(match, 'window') self.assertFalse(result) self.assertListEqual([], disc_auction.highest()) self.assertEqual(1, len(config.ACTIVE_AUCTIONS)) mock_post_event.assert_not_called() # FILTER ON - Someone outside the alliance bids on an active item config.RESTRICT_BIDS = True line = ("[Sun Aug 16 22:47:31 2020] Dan auctions, " "'Copper Disc 10 DKP'") match = config.MATCH_BID[1].match(line) result = message_handlers.handle_bid(match, 'window') self.assertFalse(result) self.assertEqual([], disc_auction.highest()) mock_post_event.assert_not_called() # Someone in the alliance says random stuff with a number line = ("[Sun Aug 16 22:47:31 2020] Tim auctions, " "'I am 12 and what channel is this'") match = config.MATCH_BID[1].match(line) result = message_handlers.handle_bid(match, 'window') self.assertFalse(result) self.assertListEqual([], disc_auction.highest()) mock_post_event.assert_not_called() # Someone in the alliance bids on two items at once line = ("[Sun Aug 16 22:47:31 2020] Jim auctions, " "'Copper Disc 10 DKP Platinum Disc'") match = config.MATCH_BID[1].match(line) result = message_handlers.handle_bid(match, 'window') self.assertFalse(result) self.assertListEqual([], disc_auction.highest()) mock_post_event.assert_not_called() # Someone we haven't seen bids on an active item line = ("[Sun Aug 16 22:47:31 2020] Paul auctions, " "'Copper Disc 5 DKP'") match = config.MATCH_BID[1].match(line) result = message_handlers.handle_bid(match, 'window') self.assertTrue(result) self.assertListEqual([('Paul', 5)], disc_auction.highest()) mock_post_event.assert_called_once_with('window', models.BidEvent(disc_auction)) mock_post_event.reset_mock() # Someone in the alliance bids on an active item line = ("[Sun Aug 16 22:47:31 2020] Jim auctions, " "'Copper Disc 10 DKP'") match = config.MATCH_BID[1].match(line) result = message_handlers.handle_bid(match, 'window') self.assertTrue(result) self.assertIn(('Jim', 10), disc_auction.highest()) mock_post_event.assert_called_once_with('window', models.BidEvent(disc_auction)) mock_post_event.reset_mock() # Someone in the alliance bids on an active item with wrong case line = ("[Sun Aug 16 22:47:31 2020] Pim auctions, " "'copper DISC 11 DKP'") match = config.MATCH_BID[1].match(line) result = message_handlers.handle_bid(match, 'window') self.assertTrue(result) self.assertIn(('Pim', 11), disc_auction.highest()) mock_post_event.assert_called_once_with('window', models.BidEvent(disc_auction)) mock_post_event.reset_mock() # Someone in the alliance bids on an active item for their 2nd main # This would trigger a bug with "2nd" being read as "2 DKP" line = ("[Sun Aug 16 22:47:31 2020] Jim auctions, " "'Copper Disc 2nd main 12dkp'") match = config.MATCH_BID[1].match(line) result = message_handlers.handle_bid(match, 'window') self.assertTrue(result) self.assertIn(('Jim', 12), disc_auction.highest()) mock_post_event.assert_called_once_with('window', models.BidEvent(disc_auction)) mock_post_event.reset_mock() # Someone in the alliance avoids bidding using ~ line = ("[Sun Aug 16 22:47:31 2020] Jim auctions, " "'~Copper Disc 14 DKP'") match = config.MATCH_BID[1].match(line) result = message_handlers.handle_bid(match, 'window') self.assertFalse(result) self.assertListEqual([('Jim', 12)], disc_auction.highest()) mock_post_event.assert_not_called() config.ACTIVE_AUCTIONS.clear()
def test_handle_drop(self, mock_post_event, mock_store_state): config.LAST_WHO_SNAPSHOT = { 'Jim': models.Player('Jim', None, None, 'Force of Will'), 'James': models.Player('James', None, None, 'Kingdom'), 'Dan': models.Player('Dan', None, None, 'Dial a Daniel'), } config.PENDING_AUCTIONS = list() config.ACTIVE_AUCTIONS = {} # # FILTER OFF - Item linked by a non-federation guild member # config.RESTRICT_BIDS = False # line = ("[Sun Aug 16 22:47:31 2020] Dan says out of character, " # "'Belt of Iniquity'") # match = config.MATCH_DROP.match(line) # items = message_handlers.handle_drop(match, 'window') # self.assertEqual(1, len(items)) # self.assertEqual(1, len(config.PENDING_AUCTIONS)) # mock_post_event.assert_called_once_with( # 'window', models.DropEvent()) # mock_post_event.reset_mock() # config.PENDING_AUCTIONS = list() # # FILTER ON - Item linked by a non-federation guild member # config.RESTRICT_BIDS = True # line = ("[Sun Aug 16 22:47:31 2020] Dan says out of character, " # "'Belt of Iniquity'") # match = config.MATCH_DROP.match(line) # items = message_handlers.handle_drop(match, 'window') # self.assertEqual(0, len(items)) # self.assertEqual(0, len(config.PENDING_AUCTIONS)) # mock_post_event.assert_not_called() # Item linked by a federation guild member # NODROP filter on, droppable item config.NODROP_ONLY = True line = ("[Sun Aug 16 22:47:31 2020] Jim says out of character, " "'Copper Disc'") jim_disc_1_uuid = "jim_disc_1_uuid" jim_disc_1 = models.ItemDrop('Copper Disc', 'Jim', 'Sun Aug 16 22:47:31 2020', uuid=jim_disc_1_uuid) match = config.MATCH_DROP_OOC.match(line) items = list(message_handlers.handle_drop(match, 'window')) self.assertEqual(1, len(items)) self.assertIn('Copper Disc', items) self.assertEqual(0, len(config.PENDING_AUCTIONS)) mock_post_event.assert_not_called() mock_post_event.reset_mock() self.mock_playsound.assert_not_called() self.mock_playsound.reset_mock() # NODROP filter on, NODROP item line = ("[Sun Aug 16 22:47:31 2020] Jim says, " "'Belt of Iniquity'") jim_belt_1_uuid = "jim_belt_1_uuid" jim_belt_1 = models.ItemDrop('Belt of Iniquity', 'Jim', 'Sun Aug 16 22:47:31 2020', uuid=jim_belt_1_uuid) match = config.MATCH_DROP_SAY.match(line) with mock.patch('uuid.uuid4') as mock_uuid4: mock_uuid4.return_value = jim_belt_1_uuid items = list(message_handlers.handle_drop(match, 'window')) self.assertEqual(1, len(items)) self.assertIn('Belt of Iniquity', items) self.assertEqual(1, len(config.PENDING_AUCTIONS)) self.assertListEqual([jim_belt_1], config.PENDING_AUCTIONS) mock_post_event.assert_called_once_with('window', models.DropEvent()) mock_post_event.reset_mock() self.mock_playsound.assert_called_once() self.mock_playsound.reset_mock() # NODROP filter off, droppable item config.NODROP_ONLY = False line = ("[Sun Aug 16 22:47:31 2020] Jim tells the guild, " "'Copper Disc'") match = config.MATCH_DROP_GU.match(line) with mock.patch('uuid.uuid4') as mock_uuid4: mock_uuid4.return_value = jim_disc_1_uuid items = list(message_handlers.handle_drop(match, 'window')) self.assertEqual(1, len(items)) self.assertIn('Copper Disc', items) self.assertEqual(2, len(config.PENDING_AUCTIONS)) self.assertListEqual([jim_belt_1, jim_disc_1], config.PENDING_AUCTIONS) mock_post_event.assert_called_once_with('window', models.DropEvent()) mock_post_event.reset_mock() self.mock_playsound.assert_called_once() self.mock_playsound.reset_mock() # Two items linked by a federation guild member, plus chat line = ("[Sun Aug 16 22:47:41 2020] James tells the guild, " "'Platinum Disc and Golden Amber Earring woo'") james_disc_uuid = "james_disc_uuid" james_earring_uuid = "james_earring_uuid" james_disc = models.ItemDrop('Platinum Disc', 'James', 'Sun Aug 16 22:47:41 2020', uuid=james_disc_uuid) james_earring = models.ItemDrop('Golden Amber Earring', 'James', 'Sun Aug 16 22:47:41 2020', uuid=james_earring_uuid) match = config.MATCH_DROP_GU.match(line) with mock.patch('uuid.uuid4') as mock_uuid4: mock_uuid4.side_effect = [james_disc_uuid, james_earring_uuid] items = list(message_handlers.handle_drop(match, 'window')) self.assertEqual(2, len(items)) self.assertListEqual(['Platinum Disc', 'Golden Amber Earring'], items) self.assertListEqual( [jim_belt_1, jim_disc_1, james_disc, james_earring], config.PENDING_AUCTIONS) mock_post_event.assert_called_once_with('window', models.DropEvent()) mock_post_event.reset_mock() self.mock_playsound.assert_called_once() self.mock_playsound.reset_mock() # Random chatter by federation guild member line = ("[Sun Aug 16 22:47:31 2020] Jim tells the guild, " "'four score and seven years ago, we wanted pixels'") match = config.MATCH_DROP_GU.match(line) items = list(message_handlers.handle_drop(match, 'window')) self.assertEqual(0, len(items)) self.assertListEqual( [jim_belt_1, jim_disc_1, james_disc, james_earring], config.PENDING_AUCTIONS) mock_post_event.assert_not_called() self.mock_playsound.assert_not_called() # Someone reports they looted an item line = ("[Sun Aug 16 22:47:31 2020] Jim tells the guild, " "'looted Belt of Iniquity'") match = config.MATCH_DROP_GU.match(line) items = list(message_handlers.handle_drop(match, 'window')) self.assertEqual(0, len(items)) self.assertListEqual( [jim_belt_1, jim_disc_1, james_disc, james_earring], config.PENDING_AUCTIONS) mock_post_event.assert_not_called() self.mock_playsound.assert_not_called() # Bid message doesn't register as a drop config.ACTIVE_AUCTIONS.clear() jerkin_1 = models.ItemDrop('Shiverback-hide Jerkin', 'Jim', 'Sun Aug 16 22:47:31 2020') config.PENDING_AUCTIONS.append(jerkin_1) auction1 = utils.start_auction_dkp(jerkin_1, 'VCR') self.assertEqual(config.ACTIVE_AUCTIONS.get(auction1.item.uuid), auction1) config.PENDING_AUCTIONS.clear() line = ("[Sun Aug 16 22:47:31 2020] Jim tells the guild, " "'Shiverback-hide Jerkin'") match = config.MATCH_DROP_GU.match(line) items = list(message_handlers.handle_drop(match, 'window')) # One item should be found self.assertListEqual(['Shiverback-hide Jerkin'], items) self.assertListEqual([], config.PENDING_AUCTIONS) mock_post_event.assert_not_called() self.mock_playsound.assert_not_called() # A gratss message from another app should not register as a drop bid_line = ("[Sun Aug 16 22:47:31 2020] Toald tells the guild, " "'Shiverback-hide Jerkin 1 main'") config.RESTRICT_BIDS = False bid_match = config.MATCH_BID_GU.match(bid_line) message_handlers.handle_bid(bid_match, 'window') config.HISTORICAL_AUCTIONS[auction1.item.uuid] = ( config.ACTIVE_AUCTIONS.pop(auction1.item.uuid)) line = ("[Sun Aug 16 22:47:31 2020] Jim tells the guild, " "'~Gratss Toald on [Shiverback-hide Jerkin] (1 DKP)!'") match = config.MATCH_DROP_GU.match(line) items = list(message_handlers.handle_drop(match, 'window')) self.assertListEqual([], items) # Ignore items if a number is present, it's probably a bid match = config.MATCH_DROP_GU.match(bid_line) items = list(message_handlers.handle_drop(match, 'window')) self.assertListEqual([], items) # second same drop shouldn't record if it is within cooldown time jerkin_2 = models.ItemDrop( 'Shiverback-hide Jerkin', 'Jim', utils.datetime_to_eq_format(datetime.datetime.now())) config.PENDING_AUCTIONS.append(jerkin_2) line = ("[{}] Jim tells the guild, 'Shiverback-hide Jerkin'".format( utils.datetime_to_eq_format(datetime.datetime.now()))) match = config.MATCH_DROP_GU.match(line) self.assertEqual([jerkin_2], config.PENDING_AUCTIONS) items = list(message_handlers.handle_drop(match, 'window')) self.assertListEqual([jerkin_2.name], items) self.assertEqual([jerkin_2], config.PENDING_AUCTIONS) # second same drop should record if it is past cooldown time jerkin_2.timestamp = utils.datetime_to_eq_format( datetime.datetime.now() - datetime.timedelta(seconds=config.DROP_COOLDOWN)) self.assertEqual(1, len(config.PENDING_AUCTIONS)) items = list(message_handlers.handle_drop(match, 'window')) self.assertListEqual([jerkin_2.name], items) self.assertEqual(2, len(config.PENDING_AUCTIONS))