mirror of
https://github.com/mangosfour/server.git
synced 2025-12-14 16:37:01 +00:00
[11704] Resolve possible crash in auction code for paiment pending state.
Source of crash in sharing item object for sent mail to new owner and in same time use it in still existed auction for show pending paiment. Crash possible if new onwer get mail in less hour delay and will drop item at receive. Solution: Added fields in memory auction object and table `auction` for store item stack size and random property id. This let not use auction item except points where item send to owner at expire and new owner at buyout/timeout auction with bid.
This commit is contained in:
parent
0daf12a348
commit
0f0fa22607
7 changed files with 129 additions and 103 deletions
|
|
@ -21,7 +21,7 @@
|
|||
|
||||
DROP TABLE IF EXISTS `character_db_version`;
|
||||
CREATE TABLE `character_db_version` (
|
||||
`required_11620_01_characters_character_equipmentsets` bit(1) default NULL
|
||||
`required_11704_01_characters_auction` bit(1) default NULL
|
||||
) ENGINE=MyISAM DEFAULT CHARSET=utf8 ROW_FORMAT=FIXED COMMENT='Last applied sql update to DB';
|
||||
|
||||
--
|
||||
|
|
@ -144,6 +144,8 @@ CREATE TABLE `auction` (
|
|||
`houseid` int(11) unsigned NOT NULL default '0',
|
||||
`itemguid` int(11) unsigned NOT NULL default '0',
|
||||
`item_template` int(11) unsigned NOT NULL default '0' COMMENT 'Item Identifier',
|
||||
`item_count` int(11) unsigned NOT NULL default '0',
|
||||
`item_randompropertyid` int(11) NOT NULL default '0',
|
||||
`itemowner` int(11) unsigned NOT NULL default '0',
|
||||
`buyoutprice` int(11) NOT NULL default '0',
|
||||
`time` bigint(40) NOT NULL default '0',
|
||||
|
|
@ -152,8 +154,7 @@ CREATE TABLE `auction` (
|
|||
`lastbid` int(11) NOT NULL default '0',
|
||||
`startbid` int(11) NOT NULL default '0',
|
||||
`deposit` int(11) NOT NULL default '0',
|
||||
PRIMARY KEY (`id`),
|
||||
UNIQUE KEY `item_guid` (`itemguid`)
|
||||
PRIMARY KEY (`id`)
|
||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
|
||||
|
||||
--
|
||||
|
|
|
|||
10
sql/updates/11704_01_characters_auction.sql
Normal file
10
sql/updates/11704_01_characters_auction.sql
Normal file
|
|
@ -0,0 +1,10 @@
|
|||
ALTER TABLE character_db_version CHANGE COLUMN required_11620_01_characters_character_equipmentsets required_11704_01_characters_auction bit;
|
||||
|
||||
ALTER TABLE `auction`
|
||||
DROP KEY `item_guid`,
|
||||
ADD COLUMN `item_count` int(11) unsigned NOT NULL default '0' AFTER `item_template`,
|
||||
ADD COLUMN `item_randompropertyid` int(11) NOT NULL default '0' AFTER `item_count`;
|
||||
|
||||
UPDATE auction, item_instance
|
||||
SET auction.item_count = SUBSTRING_INDEX(SUBSTRING_INDEX(item_instance.data, ' ', 14 + 1), ' ', -1)
|
||||
WHERE auction.itemguid = item_instance.guid;
|
||||
|
|
@ -107,11 +107,7 @@ void WorldSession::SendAuctionBidderNotification(AuctionEntry* auction)
|
|||
data << uint32(auction->moneyDeliveryTime ? 0 : auction->bid);
|
||||
data << uint32(auction->GetAuctionOutBid()); // AuctionOutBid?
|
||||
data << uint32(auction->itemTemplate);
|
||||
|
||||
Item *item = sAuctionMgr.GetAItem(auction->itemGuidLow);
|
||||
uint32 randomId = item ? item->GetItemRandomPropertyId() : 0;
|
||||
|
||||
data << uint32(randomId); // random property (value > 0) or suffix (value < 0)
|
||||
data << int32(auction->itemRandomPropertyId);
|
||||
|
||||
SendPacket(&data);
|
||||
}
|
||||
|
|
@ -131,11 +127,7 @@ void WorldSession::SendAuctionOwnerNotification(AuctionEntry* auction)
|
|||
// if guid!=0, client updates auctions with new bid, outbid and bidderGuid, else it shows error messages as described above
|
||||
data << guid; // bidder guid
|
||||
data << uint32(auction->itemTemplate); // item entry
|
||||
|
||||
Item *item = sAuctionMgr.GetAItem(auction->itemGuidLow);
|
||||
uint32 randomId = item ? item->GetItemRandomPropertyId() : 0;
|
||||
|
||||
data << uint32(randomId); // random property (value > 0) or suffix (value < 0)
|
||||
data << uint32(auction->itemRandomPropertyId);
|
||||
|
||||
float timeLeft = float(auction->moneyDeliveryTime - time(NULL)) / float(DAY);
|
||||
|
||||
|
|
@ -150,11 +142,7 @@ void WorldSession::SendAuctionRemovedNotification(AuctionEntry* auction)
|
|||
WorldPacket data(SMSG_AUCTION_REMOVED_NOTIFICATION, (3*4));
|
||||
data << uint32(auction->Id);
|
||||
data << uint32(auction->itemTemplate);
|
||||
|
||||
Item *item = sAuctionMgr.GetAItem(auction->itemGuidLow);
|
||||
uint32 randomId = item ? item->GetItemRandomPropertyId() : 0;
|
||||
|
||||
data << uint32(randomId); // random property (value > 0) or suffix (value < 0)
|
||||
data << uint32(auction->itemRandomPropertyId);
|
||||
|
||||
SendPacket(&data);
|
||||
}
|
||||
|
|
@ -471,6 +459,8 @@ void WorldSession::HandleAuctionPlaceBid(WorldPacket & recv_data)
|
|||
auction->bidder = pl->GetGUIDLow();
|
||||
auction->bid = price;
|
||||
|
||||
SendAuctionCommandResult(auction, AUCTION_BID_PLACED, AUCTION_OK);
|
||||
|
||||
if (auction_owner)
|
||||
auction_owner->GetSession()->SendAuctionOwnerNotification(auction);
|
||||
|
||||
|
|
@ -478,8 +468,6 @@ void WorldSession::HandleAuctionPlaceBid(WorldPacket & recv_data)
|
|||
|
||||
// after this update we should save player's money ...
|
||||
CharacterDatabase.PExecute("UPDATE auction SET buyguid = '%u', lastbid = '%u' WHERE id = '%u'", auction->bidder, auction->bid, auction->Id);
|
||||
|
||||
SendAuctionCommandResult(auction, AUCTION_BID_PLACED, AUCTION_OK);
|
||||
}
|
||||
else // buyout
|
||||
{
|
||||
|
|
@ -497,15 +485,11 @@ void WorldSession::HandleAuctionPlaceBid(WorldPacket & recv_data)
|
|||
auction->bidder = pl->GetGUIDLow();
|
||||
auction->bid = auction->buyout;
|
||||
|
||||
GetPlayer()->GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_HIGHEST_AUCTION_BID, auction->buyout);
|
||||
|
||||
auction->moneyDeliveryTime = time(NULL) + HOUR;
|
||||
|
||||
sAuctionMgr.SendAuctionWonMail(auction);
|
||||
|
||||
SendAuctionCommandResult(auction, AUCTION_BID_PLACED, AUCTION_OK);
|
||||
|
||||
CharacterDatabase.PExecute("UPDATE auction SET moneyTime = '" UI64FMTD "', buyguid = '%u', lastbid = '%u' WHERE id = '%u'", (uint64)auction->moneyDeliveryTime, auction->bidder, auction->bid, auction->Id);
|
||||
auction->AuctionBidWinning();
|
||||
|
||||
GetPlayer()->GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_HIGHEST_AUCTION_BID, auction->buyout);
|
||||
}
|
||||
CharacterDatabase.BeginTransaction();
|
||||
pl->SaveInventoryAndGoldToDB();
|
||||
|
|
|
|||
|
|
@ -124,8 +124,8 @@ void AuctionHouseMgr::SendAuctionWonMail(AuctionEntry *auction)
|
|||
|
||||
uint32 owner_accid = ownerGuid ? sObjectMgr.GetPlayerAccountIdByGUID(ownerGuid) : 0;
|
||||
|
||||
sLog.outCommand(bidder_accId,"GM %s (Account: %u) won item in auction: %s (Entry: %u Count: %u) and pay money: %u. Original owner %s (Account: %u)",
|
||||
bidder_name.c_str(), bidder_accId, pItem->GetProto()->Name1, pItem->GetEntry(), pItem->GetCount(), auction->bid, owner_name.c_str(), owner_accid);
|
||||
sLog.outCommand(bidder_accId,"GM %s (Account: %u) won item in auction (Entry: %u Count: %u) and pay money: %u. Original owner %s (Account: %u)",
|
||||
bidder_name.c_str(), bidder_accId, auction->itemTemplate, auction->itemCount, auction->bid, owner_name.c_str(), owner_accid);
|
||||
}
|
||||
}
|
||||
else if (!bidder)
|
||||
|
|
@ -148,8 +148,7 @@ void AuctionHouseMgr::SendAuctionWonMail(AuctionEntry *auction)
|
|||
|
||||
// set owner to bidder (to prevent delete item with sender char deleting)
|
||||
// owner in `data` will set at mail receive and item extracting
|
||||
CharacterDatabase.PExecute("UPDATE item_instance SET owner_guid = '%u' WHERE guid='%u'",auction->bidder,pItem->GetGUIDLow());
|
||||
CharacterDatabase.CommitTransaction();
|
||||
CharacterDatabase.PExecute("UPDATE item_instance SET owner_guid = '%u' WHERE guid='%u'", auction->bidder, auction->itemGuidLow);
|
||||
|
||||
if (bidder)
|
||||
{
|
||||
|
|
@ -157,8 +156,10 @@ void AuctionHouseMgr::SendAuctionWonMail(AuctionEntry *auction)
|
|||
// FIXME: for offline player need also
|
||||
bidder->GetAchievementMgr().UpdateAchievementCriteria(ACHIEVEMENT_CRITERIA_TYPE_WON_AUCTIONS, 1);
|
||||
}
|
||||
else
|
||||
RemoveAItem(pItem->GetGUIDLow()); // we have to remove the item, before we delete it !!
|
||||
|
||||
RemoveAItem(auction->itemGuidLow); // we have to remove the item, before we delete it !!
|
||||
auction->itemGuidLow = 0; // pending list will not use guid data
|
||||
|
||||
|
||||
// will delete item or place to receiver mail list
|
||||
MailDraft(msgAuctionWonSubject.str(), msgAuctionWonBody.str())
|
||||
|
|
@ -168,8 +169,9 @@ void AuctionHouseMgr::SendAuctionWonMail(AuctionEntry *auction)
|
|||
// receiver not exist
|
||||
else
|
||||
{
|
||||
CharacterDatabase.PExecute("DELETE FROM item_instance WHERE guid='%u'", pItem->GetGUIDLow());
|
||||
RemoveAItem(pItem->GetGUIDLow()); // we have to remove the item, before we delete it !!
|
||||
CharacterDatabase.PExecute("DELETE FROM item_instance WHERE guid='%u'", auction->itemGuidLow);
|
||||
RemoveAItem(auction->itemGuidLow); // we have to remove the item, before we delete it !!
|
||||
auction->itemGuidLow = 0;
|
||||
delete pItem;
|
||||
}
|
||||
}
|
||||
|
|
@ -269,8 +271,9 @@ void AuctionHouseMgr::SendAuctionExpiredMail(AuctionEntry * auction)
|
|||
|
||||
if (owner)
|
||||
owner->GetSession()->SendAuctionOwnerNotification(auction);
|
||||
else
|
||||
RemoveAItem(pItem->GetGUIDLow()); // we have to remove the item, before we delete it !!
|
||||
|
||||
RemoveAItem(auction->itemGuidLow); // we have to remove the item, before we delete it !!
|
||||
auction->itemGuidLow = 0;
|
||||
|
||||
// will delete item or place to receiver mail list
|
||||
MailDraft(subject.str(), "") // TODO: fix body
|
||||
|
|
@ -280,8 +283,9 @@ void AuctionHouseMgr::SendAuctionExpiredMail(AuctionEntry * auction)
|
|||
// owner not found
|
||||
else
|
||||
{
|
||||
CharacterDatabase.PExecute("DELETE FROM item_instance WHERE guid='%u'",pItem->GetGUIDLow());
|
||||
RemoveAItem(pItem->GetGUIDLow()); // we have to remove the item, before we delete it !!
|
||||
CharacterDatabase.PExecute("DELETE FROM item_instance WHERE guid='%u'", auction->itemGuidLow);
|
||||
RemoveAItem(auction->itemGuidLow); // we have to remove the item, before we delete it !!
|
||||
auction->itemGuidLow = 0;
|
||||
delete pItem;
|
||||
}
|
||||
}
|
||||
|
|
@ -364,7 +368,7 @@ void AuctionHouseMgr::LoadAuctions()
|
|||
return;
|
||||
}
|
||||
|
||||
result = CharacterDatabase.Query("SELECT id,houseid,itemguid,item_template,itemowner,buyoutprice,time,moneyTime,buyguid,lastbid,startbid,deposit FROM auction");
|
||||
result = CharacterDatabase.Query("SELECT id,houseid,itemguid,item_template,item_count,item_randompropertyid,itemowner,buyoutprice,time,moneyTime,buyguid,lastbid,startbid,deposit FROM auction");
|
||||
if (!result)
|
||||
{
|
||||
BarGoLink bar(1);
|
||||
|
|
@ -390,7 +394,10 @@ void AuctionHouseMgr::LoadAuctions()
|
|||
uint32 houseid = fields[1].GetUInt32();
|
||||
auction->itemGuidLow = fields[2].GetUInt32();
|
||||
auction->itemTemplate = fields[3].GetUInt32();
|
||||
auction->owner = fields[4].GetUInt32();
|
||||
auction->itemCount = fields[4].GetUInt32();
|
||||
auction->itemRandomPropertyId = fields[5].GetUInt32();
|
||||
|
||||
auction->owner = fields[6].GetUInt32();
|
||||
|
||||
if (auction->owner)
|
||||
{
|
||||
|
|
@ -407,24 +414,43 @@ void AuctionHouseMgr::LoadAuctions()
|
|||
auction->ownerName = plWName;
|
||||
}
|
||||
|
||||
auction->buyout = fields[5].GetUInt32();
|
||||
auction->expireTime = fields[6].GetUInt32();
|
||||
auction->moneyDeliveryTime = fields[7].GetUInt32();
|
||||
auction->bidder = fields[8].GetUInt32();
|
||||
auction->bid = fields[9].GetUInt32();
|
||||
auction->startbid = fields[10].GetUInt32();
|
||||
auction->deposit = fields[11].GetUInt32();
|
||||
auction->buyout = fields[7].GetUInt32();
|
||||
auction->expireTime = fields[8].GetUInt32();
|
||||
auction->moneyDeliveryTime = fields[9].GetUInt32();
|
||||
auction->bidder = fields[10].GetUInt32();
|
||||
auction->bid = fields[11].GetUInt32();
|
||||
auction->startbid = fields[12].GetUInt32();
|
||||
auction->deposit = fields[13].GetUInt32();
|
||||
auction->auctionHouseEntry = NULL; // init later
|
||||
|
||||
// check if sold item exists for guid
|
||||
// and item_template in fact (GetAItem will fail if problematic in result check in AuctionHouseMgr::LoadAuctionItems)
|
||||
Item* pItem = GetAItem(auction->itemGuidLow);
|
||||
if (!pItem)
|
||||
if (auction->moneyDeliveryTime)
|
||||
auction->itemGuidLow = 0; // must be 0 if auction delivery pending
|
||||
else
|
||||
{
|
||||
auction->DeleteFromDB();
|
||||
sLog.outError("Auction %u has not a existing item : %u, deleted", auction->Id, auction->itemGuidLow);
|
||||
delete auction;
|
||||
continue;
|
||||
// check if sold item exists for guid
|
||||
// and item_template in fact (GetAItem will fail if problematic in result check in AuctionHouseMgr::LoadAuctionItems)
|
||||
Item* pItem = GetAItem(auction->itemGuidLow);
|
||||
if (!pItem)
|
||||
{
|
||||
auction->DeleteFromDB();
|
||||
sLog.outError("Auction %u has not a existing item : %u, deleted", auction->Id, auction->itemGuidLow);
|
||||
delete auction;
|
||||
continue;
|
||||
}
|
||||
|
||||
// overwrite by real item data
|
||||
if ((auction->itemTemplate != pItem->GetEntry()) ||
|
||||
(auction->itemCount != pItem->GetCount()) ||
|
||||
(auction->itemRandomPropertyId != pItem->GetItemRandomPropertyId()))
|
||||
{
|
||||
auction->itemTemplate = pItem->GetEntry();
|
||||
auction->itemCount = pItem->GetCount();
|
||||
auction->itemRandomPropertyId = pItem->GetItemRandomPropertyId();
|
||||
|
||||
//No SQL injection (no strings)
|
||||
CharacterDatabase.PExecute("UPDATE auction SET item_template = %u, item_count = %u, item_randompropertyid = %i WHERE itemguid = %u",
|
||||
auction->itemTemplate, auction->itemCount, auction->itemRandomPropertyId, auction->itemGuidLow);
|
||||
}
|
||||
}
|
||||
|
||||
auction->auctionHouseEntry = sAuctionHouseStore.LookupEntry(houseid);
|
||||
|
|
@ -438,12 +464,19 @@ void AuctionHouseMgr::LoadAuctions()
|
|||
std::ostringstream msgAuctionCanceledOwner;
|
||||
msgAuctionCanceledOwner << auction->itemTemplate << ":0:" << AUCTION_CANCELED << ":0:0";
|
||||
|
||||
// item will deleted or added to received mail list
|
||||
MailDraft(msgAuctionCanceledOwner.str(), "") // TODO: fix body
|
||||
.AddItem(pItem)
|
||||
.SendMailTo(MailReceiver(ObjectGuid(HIGHGUID_PLAYER, auction->owner)), auction, MAIL_CHECK_MASK_COPIED);
|
||||
if (auction->itemGuidLow)
|
||||
{
|
||||
Item* pItem = GetAItem(auction->itemGuidLow);
|
||||
|
||||
RemoveAItem(auction->itemGuidLow);
|
||||
auction->itemGuidLow = 0;
|
||||
|
||||
// item will deleted or added to received mail list
|
||||
MailDraft(msgAuctionCanceledOwner.str(), "") // TODO: fix body
|
||||
.AddItem(pItem)
|
||||
.SendMailTo(MailReceiver(ObjectGuid(HIGHGUID_PLAYER, auction->owner)), auction, MAIL_CHECK_MASK_COPIED);
|
||||
}
|
||||
|
||||
RemoveAItem(auction->itemGuidLow);
|
||||
auction->DeleteFromDB();
|
||||
delete auction;
|
||||
|
||||
|
|
@ -578,7 +611,7 @@ void AuctionHouseObject::Update()
|
|||
sAuctionMgr.SendAuctionSuccessfulMail(itr->second);
|
||||
|
||||
itr->second->DeleteFromDB();
|
||||
sAuctionMgr.RemoveAItem(itr->second->itemGuidLow);
|
||||
MANGOS_ASSERT(!itr->second->itemGuidLow); // already removed or send in mail at won
|
||||
delete itr->second;
|
||||
RemoveAuction(itr->first);
|
||||
}
|
||||
|
|
@ -587,22 +620,17 @@ void AuctionHouseObject::Update()
|
|||
{
|
||||
if (curTime > itr->second->expireTime)
|
||||
{
|
||||
///- Either cancel the auction if there was no bidder
|
||||
if (itr->second->bidder == 0)
|
||||
///- perform the transaction if there was bidder
|
||||
if (itr->second->bidder)
|
||||
{
|
||||
sAuctionMgr.SendAuctionExpiredMail(itr->second);
|
||||
}
|
||||
///- Or perform the transaction
|
||||
else
|
||||
{
|
||||
itr->second->moneyDeliveryTime = time(NULL) + HOUR;
|
||||
sAuctionMgr.SendAuctionWonMail(itr->second);
|
||||
itr->second->AuctionBidWinning();
|
||||
continue;
|
||||
}
|
||||
|
||||
///- In any case clear the auction
|
||||
///- cancel the auction if there was no bidder
|
||||
sAuctionMgr.SendAuctionExpiredMail(itr->second);
|
||||
|
||||
itr->second->DeleteFromDB();
|
||||
sAuctionMgr.RemoveAItem(itr->second->itemGuidLow);
|
||||
delete itr->second;
|
||||
RemoveAuction(itr->first);
|
||||
}
|
||||
|
|
@ -648,25 +676,25 @@ int AuctionEntry::CompareAuctionEntry(uint32 column, const AuctionEntry *auc, Pl
|
|||
{
|
||||
case 0: // level = 0
|
||||
{
|
||||
Item *item1 = sAuctionMgr.GetAItem(itemGuidLow);
|
||||
Item *item2 = sAuctionMgr.GetAItem(auc->itemGuidLow);
|
||||
if (!item1 || !item2)
|
||||
ItemPrototype const* itemProto1 = ObjectMgr::GetItemPrototype(itemTemplate);
|
||||
ItemPrototype const* itemProto2 = ObjectMgr::GetItemPrototype(auc->itemTemplate);
|
||||
if (!itemProto2 || !itemProto1)
|
||||
return 0;
|
||||
if (item1->GetProto()->RequiredLevel < item2->GetProto()->RequiredLevel)
|
||||
if (itemProto1->RequiredLevel < itemProto2->RequiredLevel)
|
||||
return -1;
|
||||
else if (item1->GetProto()->RequiredLevel > item2->GetProto()->RequiredLevel)
|
||||
else if (itemProto1->RequiredLevel > itemProto2->RequiredLevel)
|
||||
return +1;
|
||||
break;
|
||||
}
|
||||
case 1: // quality = 1
|
||||
{
|
||||
Item *item1 = sAuctionMgr.GetAItem(itemGuidLow);
|
||||
Item *item2 = sAuctionMgr.GetAItem(auc->itemGuidLow);
|
||||
if (!item1 || !item2)
|
||||
ItemPrototype const* itemProto1 = ObjectMgr::GetItemPrototype(itemTemplate);
|
||||
ItemPrototype const* itemProto2 = ObjectMgr::GetItemPrototype(auc->itemTemplate);
|
||||
if (!itemProto2 || !itemProto1)
|
||||
return 0;
|
||||
if (item1->GetProto()->Quality < item2->GetProto()->Quality)
|
||||
if (itemProto1->Quality < itemProto2->Quality)
|
||||
return -1;
|
||||
else if (item1->GetProto()->Quality > item2->GetProto()->Quality)
|
||||
else if (itemProto1->Quality > itemProto2->Quality)
|
||||
return +1;
|
||||
break;
|
||||
}
|
||||
|
|
@ -765,13 +793,9 @@ int AuctionEntry::CompareAuctionEntry(uint32 column, const AuctionEntry *auc, Pl
|
|||
break;
|
||||
case 9: // quantity = 9
|
||||
{
|
||||
Item *item1 = sAuctionMgr.GetAItem(itemGuidLow);
|
||||
Item *item2 = sAuctionMgr.GetAItem(auc->itemGuidLow);
|
||||
if (!item1 || !item2)
|
||||
return 0;
|
||||
if (item1->GetCount() < item2->GetCount())
|
||||
if (itemCount < auc->itemCount)
|
||||
return -1;
|
||||
else if (item1->GetCount() > item2->GetCount())
|
||||
else if (itemCount > auc->itemCount)
|
||||
return +1;
|
||||
break;
|
||||
}
|
||||
|
|
@ -889,15 +913,8 @@ void AuctionHouseObject::BuildListPendingSales(WorldPacket& data, Player* player
|
|||
continue;
|
||||
if (Aentry && Aentry->owner == player->GetGUIDLow())
|
||||
{
|
||||
Item *pItem = sAuctionMgr.GetAItem(Aentry->itemGuidLow);
|
||||
if (!pItem)
|
||||
{
|
||||
sLog.outError("Auction: item with guid %u doesn't exist!", Aentry->itemGuidLow);
|
||||
continue;
|
||||
}
|
||||
|
||||
std::ostringstream str1;
|
||||
str1 << Aentry->itemTemplate << ":" << pItem->GetItemRandomPropertyId() << ":" << AUCTION_SUCCESSFUL << ":" << Aentry->Id << ":" << pItem->GetCount();
|
||||
str1 << Aentry->itemTemplate << ":" << Aentry->itemRandomPropertyId << ":" << AUCTION_SUCCESSFUL << ":" << Aentry->Id << ":" << Aentry->itemCount;
|
||||
|
||||
std::ostringstream str2;
|
||||
str2.width(16);
|
||||
|
|
@ -923,6 +940,8 @@ AuctionEntry* AuctionHouseObject::AddAuction(AuctionHouseEntry const* auctionHou
|
|||
AH->Id = sObjectMgr.GenerateAuctionID();
|
||||
AH->itemGuidLow = newItem->GetObjectGuid().GetCounter();
|
||||
AH->itemTemplate = newItem->GetEntry();
|
||||
AH->itemCount = newItem->GetCount();
|
||||
AH->itemRandomPropertyId = newItem->GetItemRandomPropertyId();
|
||||
AH->owner = pl ? pl->GetGUIDLow() : 0;
|
||||
|
||||
if (pl)
|
||||
|
|
@ -1009,7 +1028,15 @@ void AuctionEntry::DeleteFromDB() const
|
|||
void AuctionEntry::SaveToDB() const
|
||||
{
|
||||
//No SQL injection (no strings)
|
||||
CharacterDatabase.PExecute("INSERT INTO auction (id,houseid,itemguid,item_template,itemowner,buyoutprice,time,moneyTime,buyguid,lastbid,startbid,deposit) "
|
||||
"VALUES ('%u', '%u', '%u', '%u', '%u', '%u', '" UI64FMTD "', '" UI64FMTD "', '%u', '%u', '%u', '%u')",
|
||||
Id, auctionHouseEntry->houseId, itemGuidLow, itemTemplate, owner, buyout, (uint64)expireTime, (uint64)moneyDeliveryTime, bidder, bid, startbid, deposit);
|
||||
CharacterDatabase.PExecute("INSERT INTO auction (id,houseid,itemguid,item_template,item_count,item_randompropertyid,itemowner,buyoutprice,time,moneyTime,buyguid,lastbid,startbid,deposit) "
|
||||
"VALUES ('%u', '%u', '%u', '%u', '%u', '%i', '%u', '%u', '" UI64FMTD "', '" UI64FMTD "', '%u', '%u', '%u', '%u')",
|
||||
Id, auctionHouseEntry->houseId, itemGuidLow, itemTemplate, itemCount, itemRandomPropertyId, owner, buyout, (uint64)expireTime, (uint64)moneyDeliveryTime, bidder, bid, startbid, deposit);
|
||||
}
|
||||
|
||||
void AuctionEntry::AuctionBidWinning()
|
||||
{
|
||||
moneyDeliveryTime = time(NULL) + HOUR;
|
||||
CharacterDatabase.PExecute("UPDATE auction SET itemguid = 0, moneyTime = '" UI64FMTD "', buyguid = '%u', lastbid = '%u' WHERE id = '%u'", (uint64)moneyDeliveryTime, bidder, bid, Id);
|
||||
|
||||
sAuctionMgr.SendAuctionWonMail(this);
|
||||
}
|
||||
|
|
|
|||
|
|
@ -56,8 +56,10 @@ enum AuctionAction
|
|||
struct AuctionEntry
|
||||
{
|
||||
uint32 Id;
|
||||
uint32 itemGuidLow;
|
||||
uint32 itemGuidLow; // can be 0 after send won mail with item
|
||||
uint32 itemTemplate;
|
||||
uint32 itemCount;
|
||||
int32 itemRandomPropertyId;
|
||||
uint32 owner; // player low guid, can be 0 for server generated auction
|
||||
std::wstring ownerName; // cache name for sorting
|
||||
uint32 startbid; // maybe useless
|
||||
|
|
@ -77,6 +79,8 @@ struct AuctionEntry
|
|||
bool BuildAuctionInfo(WorldPacket & data) const;
|
||||
void DeleteFromDB() const;
|
||||
void SaveToDB() const;
|
||||
void AuctionBidWinning();
|
||||
|
||||
|
||||
// -1,0,+1 order result
|
||||
int CompareAuctionEntry(uint32 column, const AuctionEntry *auc, Player* viewPlayer) const;
|
||||
|
|
|
|||
|
|
@ -1,4 +1,4 @@
|
|||
#ifndef __REVISION_NR_H__
|
||||
#define __REVISION_NR_H__
|
||||
#define REVISION_NR "11703"
|
||||
#define REVISION_NR "11704"
|
||||
#endif // __REVISION_NR_H__
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
#ifndef __REVISION_SQL_H__
|
||||
#define __REVISION_SQL_H__
|
||||
#define REVISION_DB_CHARACTERS "required_11620_01_characters_character_equipmentsets"
|
||||
#define REVISION_DB_CHARACTERS "required_11704_01_characters_auction"
|
||||
#define REVISION_DB_MANGOS "required_11701_01_mangos_command"
|
||||
#define REVISION_DB_REALMD "required_10008_01_realmd_realmd_db_version"
|
||||
#endif // __REVISION_SQL_H__
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue