Add functionality for sale end dates
This commit is contained in:
parent
e47c6b2f40
commit
0491d232be
@ -105,7 +105,7 @@ let getStoreItems (storeId : string) =
|
|||||||
|> Sql.connect
|
|> Sql.connect
|
||||||
|> Sql.parameters [ "sid", Sql.string storeId ]
|
|> Sql.parameters [ "sid", Sql.string storeId ]
|
||||||
|> Sql.query """
|
|> Sql.query """
|
||||||
SELECT store_id,stock,available,limit_stock,i.id,name,description,icon_url,image_url,category,require_role,require_invites,
|
SELECT store_id,stock,available,limit_stock,i.id,name,description,icon_url,image_url,category,require_role,require_invites,sale_end,
|
||||||
buy_price,sell_price,rate_limit,expiration,drop_chance,can_trade,can_consume,attack_power,defense_power,class_name,max_stack,mods
|
buy_price,sell_price,rate_limit,expiration,drop_chance,can_trade,can_consume,attack_power,defense_power,class_name,max_stack,mods
|
||||||
FROM store_item
|
FROM store_item
|
||||||
JOIN item i on store_item.item_id = i.id
|
JOIN item i on store_item.item_id = i.id
|
||||||
@ -116,6 +116,7 @@ let getStoreItems (storeId : string) =
|
|||||||
Stock = reader.int "stock"
|
Stock = reader.int "stock"
|
||||||
LimitStock = reader.bool "limit_stock"
|
LimitStock = reader.bool "limit_stock"
|
||||||
Available = reader.bool "available"
|
Available = reader.bool "available"
|
||||||
|
SaleEnd = reader.int64OrNone "sale_end"
|
||||||
TotalSold = None
|
TotalSold = None
|
||||||
RequiresInvites = reader.intOrNone "require_invites"
|
RequiresInvites = reader.intOrNone "require_invites"
|
||||||
RequiresRole = reader.stringOrNone "require_role" |> Option.map uint64
|
RequiresRole = reader.stringOrNone "require_role" |> Option.map uint64
|
||||||
@ -127,7 +128,7 @@ let getAllActiveStoreItems () =
|
|||||||
connStr
|
connStr
|
||||||
|> Sql.connect
|
|> Sql.connect
|
||||||
|> Sql.query """
|
|> Sql.query """
|
||||||
SELECT store_id,stock,available,limit_stock,i.id,name,description,icon_url,image_url,category,require_role,require_invites,
|
SELECT store_id,stock,available,limit_stock,i.id,name,description,icon_url,image_url,category,require_role,require_invites,sale_end,
|
||||||
buy_price,sell_price,rate_limit,expiration,drop_chance,can_trade,can_consume,attack_power,defense_power,class_name,max_stack,mods
|
buy_price,sell_price,rate_limit,expiration,drop_chance,can_trade,can_consume,attack_power,defense_power,class_name,max_stack,mods
|
||||||
FROM store_item
|
FROM store_item
|
||||||
JOIN item i on store_item.item_id = i.id
|
JOIN item i on store_item.item_id = i.id
|
||||||
@ -138,6 +139,7 @@ let getAllActiveStoreItems () =
|
|||||||
Stock = reader.int "stock"
|
Stock = reader.int "stock"
|
||||||
LimitStock = reader.bool "limit_stock"
|
LimitStock = reader.bool "limit_stock"
|
||||||
Available = reader.bool "available"
|
Available = reader.bool "available"
|
||||||
|
SaleEnd = reader.int64OrNone "sale_end"
|
||||||
TotalSold = None
|
TotalSold = None
|
||||||
RequiresInvites = reader.intOrNone "require_invites"
|
RequiresInvites = reader.intOrNone "require_invites"
|
||||||
RequiresRole = reader.stringOrNone "require_role" |> Option.map uint64
|
RequiresRole = reader.stringOrNone "require_role" |> Option.map uint64
|
||||||
@ -151,7 +153,7 @@ let getRafflesWithPurchases storeId =
|
|||||||
|> Sql.parameters [ "sid" , Sql.string storeId ]
|
|> Sql.parameters [ "sid" , Sql.string storeId ]
|
||||||
|> Sql.query """
|
|> Sql.query """
|
||||||
WITH raffles AS
|
WITH raffles AS
|
||||||
(SELECT store_id,stock,available,limit_stock,i.id AS raffle_id,name,description,icon_url,image_url,category,require_role,require_invites,
|
(SELECT store_id,stock,available,limit_stock,i.id AS raffle_id,name,description,icon_url,image_url,category,require_role,require_invites,sale_end,
|
||||||
buy_price,sell_price,rate_limit,expiration,drop_chance,can_trade,can_consume,attack_power,defense_power,class_name,max_stack,mods
|
buy_price,sell_price,rate_limit,expiration,drop_chance,can_trade,can_consume,attack_power,defense_power,class_name,max_stack,mods
|
||||||
FROM store_item
|
FROM store_item
|
||||||
JOIN item i on store_item.item_id = i.id
|
JOIN item i on store_item.item_id = i.id
|
||||||
@ -166,6 +168,7 @@ FULL JOIN (SELECT item_id, count(*) AS total FROM inventory_item
|
|||||||
Stock = reader.int "stock"
|
Stock = reader.int "stock"
|
||||||
LimitStock = reader.bool "limit_stock"
|
LimitStock = reader.bool "limit_stock"
|
||||||
Available = reader.bool "available"
|
Available = reader.bool "available"
|
||||||
|
SaleEnd = reader.int64OrNone "sale_end"
|
||||||
TotalSold = reader.intOrNone "total"
|
TotalSold = reader.intOrNone "total"
|
||||||
RequiresInvites = reader.intOrNone "require_invites"
|
RequiresInvites = reader.intOrNone "require_invites"
|
||||||
RequiresRole = reader.stringOrNone "require_role" |> Option.map uint64
|
RequiresRole = reader.stringOrNone "require_role" |> Option.map uint64
|
||||||
@ -178,7 +181,7 @@ let getStoreItemBySymbol (itemSymbol : string) =
|
|||||||
|> Sql.connect
|
|> Sql.connect
|
||||||
|> Sql.parameters [ "iid", Sql.string itemSymbol ]
|
|> Sql.parameters [ "iid", Sql.string itemSymbol ]
|
||||||
|> Sql.query """
|
|> Sql.query """
|
||||||
SELECT store_id,stock,available,limit_stock,i.id,name,description,icon_url,image_url,category,require_role,require_invites,
|
SELECT store_id,stock,available,limit_stock,i.id,name,description,icon_url,image_url,category,require_role,require_invites,sale_end,
|
||||||
buy_price,sell_price,rate_limit,expiration,drop_chance,can_trade,can_consume,attack_power,defense_power,class_name,max_stack,mods
|
buy_price,sell_price,rate_limit,expiration,drop_chance,can_trade,can_consume,attack_power,defense_power,class_name,max_stack,mods
|
||||||
FROM store_item
|
FROM store_item
|
||||||
JOIN item i on store_item.item_id = i.id
|
JOIN item i on store_item.item_id = i.id
|
||||||
@ -189,6 +192,7 @@ let getStoreItemBySymbol (itemSymbol : string) =
|
|||||||
Stock = reader.int "stock"
|
Stock = reader.int "stock"
|
||||||
LimitStock = reader.bool "limit_stock"
|
LimitStock = reader.bool "limit_stock"
|
||||||
Available = reader.bool "available"
|
Available = reader.bool "available"
|
||||||
|
SaleEnd = reader.int64OrNone "sale_end"
|
||||||
TotalSold = None
|
TotalSold = None
|
||||||
RequiresInvites = reader.intOrNone "require_invites"
|
RequiresInvites = reader.intOrNone "require_invites"
|
||||||
RequiresRole = reader.stringOrNone "require_role" |> Option.map uint64
|
RequiresRole = reader.stringOrNone "require_role" |> Option.map uint64
|
||||||
|
@ -142,6 +142,7 @@ type StoreItem = {
|
|||||||
LimitStock : bool
|
LimitStock : bool
|
||||||
Available : bool
|
Available : bool
|
||||||
TotalSold : int option
|
TotalSold : int option
|
||||||
|
SaleEnd : int64 option
|
||||||
RequiresRole : uint64 option
|
RequiresRole : uint64 option
|
||||||
RequiresInvites : int option
|
RequiresInvites : int option
|
||||||
Item : Item
|
Item : Item
|
||||||
|
@ -53,13 +53,20 @@ let checkDoesntExceedStackCap (item : Item) player =
|
|||||||
| _ , Some _ -> "You already own this item" |> embedWithError
|
| _ , Some _ -> "You already own this item" |> embedWithError
|
||||||
| _ -> Ok ()
|
| _ -> Ok ()
|
||||||
|
|
||||||
|
let checkItemSaleStillActive (item : StoreItem) =
|
||||||
|
match item.SaleEnd with
|
||||||
|
| Some time ->
|
||||||
|
let date = DateTimeOffset.FromUnixTimeSeconds(time).DateTime.ToUniversalTime()
|
||||||
|
if DateTime.UtcNow < date then Ok () else $"Sale for {item.Item.Name} has already ended!" |> embedWithError
|
||||||
|
| None -> Ok ()
|
||||||
|
|
||||||
let checkSoldItemAlready (item : Item) player =
|
let checkSoldItemAlready (item : Item) player =
|
||||||
if player.Inventory |> List.exists (fun i -> item.Id = i.Id)
|
if player.Inventory |> List.exists (fun i -> item.Id = i.Id)
|
||||||
then Ok ()
|
then Ok ()
|
||||||
else $"{item.Name} not found in your inventory! Looks like you sold it already."
|
else $"{item.Name} not found in your inventory! Looks like you sold it already."
|
||||||
|> embedWithError
|
|> embedWithError
|
||||||
|
|
||||||
let checkHasItemsInArsenal itemType items player =
|
let checkHasItemsInArsenal itemType items =
|
||||||
if List.isEmpty items |> not
|
if List.isEmpty items |> not
|
||||||
then Ok ()
|
then Ok ()
|
||||||
else $"You currently have no {itemType} in your arsenal to sell!"
|
else $"You currently have no {itemType} in your arsenal to sell!"
|
||||||
@ -125,6 +132,13 @@ let getItemEmbeds owned (items : StoreItem list) =
|
|||||||
| _ -> ())
|
| _ -> ())
|
||||||
// if item.Item.Type = ItemType.Whitelist then
|
// if item.Item.Type = ItemType.Whitelist then
|
||||||
// embed.AddField("Mint Allowance", (if item.Item.Id = "WHITEOG" then 2 else 1) |> string, true) |> ignore
|
// embed.AddField("Mint Allowance", (if item.Item.Id = "WHITEOG" then 2 else 1) |> string, true) |> ignore
|
||||||
|
item.SaleEnd |> Option.iter (fun time ->
|
||||||
|
let date = DateTimeOffset.FromUnixTimeSeconds(time).DateTime.ToUniversalTime()
|
||||||
|
if DateTime.UtcNow < date then
|
||||||
|
embed.AddField("⏰ Closes", $"<t:{time}:R>", true) |> ignore
|
||||||
|
else
|
||||||
|
embed.AddField("🚫 Closed", $"<t:{time}:R>", true) |> ignore)
|
||||||
|
|
||||||
item.TotalSold |> Option.iter (fun total -> embed.AddField("Total Sold", string total, true) |> ignore)
|
item.TotalSold |> Option.iter (fun total -> embed.AddField("Total Sold", string total, true) |> ignore)
|
||||||
embed.Color <- WeaponClass.getClassEmbedColor item.Item
|
embed.Color <- WeaponClass.getClassEmbedColor item.Item
|
||||||
embed.Title <- titleText
|
embed.Title <- titleText
|
||||||
@ -142,12 +156,19 @@ let getBuyItemsEmbed storeId player (storeInventory : StoreItem list) =
|
|||||||
storeInventory
|
storeInventory
|
||||||
|> List.map (fun item ->
|
|> List.map (fun item ->
|
||||||
let owned = player.Inventory |> List.exists (fun i -> i.Id = item.Item.Id)
|
let owned = player.Inventory |> List.exists (fun i -> i.Id = item.Item.Id)
|
||||||
|
let saleStillOngoing =
|
||||||
|
match item.SaleEnd with
|
||||||
|
| Some time ->
|
||||||
|
let date = DateTimeOffset.FromUnixTimeSeconds(time).DateTime.ToUniversalTime()
|
||||||
|
DateTime.UtcNow < date
|
||||||
|
| None -> true
|
||||||
let inStock = item.Available && (item.Stock > 0 || item.LimitStock = false)
|
let inStock = item.Available && (item.Stock > 0 || item.LimitStock = false)
|
||||||
match owned , inStock with
|
match owned , inStock , saleStillOngoing with
|
||||||
| _ , false ->
|
| _ , false , _ ->
|
||||||
let msg = if item.Available then "Out of Stock" else "Unavailable"
|
let msg = if item.Available then "Out of Stock" else "Unavailable"
|
||||||
DiscordButtonComponent(WeaponClass.getClassButtonColor item.Item, $"Buy-{item.Item.Id}-{storeId}", $"{item.Item.Name} ({msg})", true)
|
DiscordButtonComponent(WeaponClass.getClassButtonColor item.Item, $"Buy-{item.Item.Id}-{storeId}", $"{item.Item.Name} ({msg})", true)
|
||||||
| false , true -> DiscordButtonComponent(WeaponClass.getClassButtonColor item.Item, $"Buy-{item.Item.Id}-{storeId}", $"Buy {item.Item.Name}")
|
| false , true , true -> DiscordButtonComponent(WeaponClass.getClassButtonColor item.Item, $"Buy-{item.Item.Id}-{storeId}", $"Buy {item.Item.Name}")
|
||||||
|
| _ , _ , false -> DiscordButtonComponent(WeaponClass.getClassButtonColor item.Item, $"Buy-{item.Item.Id}-{storeId}", $"Closed {item.Item.Name}", true)
|
||||||
| _ ->
|
| _ ->
|
||||||
match checkDoesntExceedStackCap item.Item player with
|
match checkDoesntExceedStackCap item.Item player with
|
||||||
| Ok _ -> DiscordButtonComponent(WeaponClass.getClassButtonColor item.Item, $"Buy-{item.Item.Id}-{storeId}", $"Buy {item.Item.Name}")
|
| Ok _ -> DiscordButtonComponent(WeaponClass.getClassButtonColor item.Item, $"Buy-{item.Item.Id}-{storeId}", $"Buy {item.Item.Name}")
|
||||||
@ -261,7 +282,7 @@ let buyForPlayer storeId player (filterBy : ItemType option) (ctx : IDiscordCont
|
|||||||
let sell itemType getItems (ctx : IDiscordContext) =
|
let sell itemType getItems (ctx : IDiscordContext) =
|
||||||
executePlayerAction ctx (fun player -> async {
|
executePlayerAction ctx (fun player -> async {
|
||||||
let items = getItems player.Inventory
|
let items = getItems player.Inventory
|
||||||
match checkHasItemsInArsenal itemType items player with
|
match checkHasItemsInArsenal itemType items with
|
||||||
| Ok _ -> let itemStore = getSellEmbed items
|
| Ok _ -> let itemStore = getSellEmbed items
|
||||||
do! ctx.FollowUp(itemStore) |> Async.AwaitTask
|
do! ctx.FollowUp(itemStore) |> Async.AwaitTask
|
||||||
| Error e -> do! ctx.FollowUp e |> Async.AwaitTask
|
| Error e -> do! ctx.FollowUp e |> Async.AwaitTask
|
||||||
@ -335,6 +356,7 @@ let handleBuyItem (dispatch : IDiscordContext -> Task) (ctx : IDiscordContext) i
|
|||||||
let storeItem = storeInventory |> List.find (fun si -> si.Item.Id = itemId)
|
let storeItem = storeInventory |> List.find (fun si -> si.Item.Id = itemId)
|
||||||
do! checkHasSufficientFunds storeItem.Item player
|
do! checkHasSufficientFunds storeItem.Item player
|
||||||
do! checkHasStock storeItem
|
do! checkHasStock storeItem
|
||||||
|
do! checkItemSaleStillActive storeItem
|
||||||
do! checkDoesntExceedStackCap storeItem.Item player
|
do! checkDoesntExceedStackCap storeItem.Item player
|
||||||
do! checkHasRequiredRole storeItem (ctx.GetDiscordMember())
|
do! checkHasRequiredRole storeItem (ctx.GetDiscordMember())
|
||||||
do! checkHasRequiredInvites storeItem player
|
do! checkHasRequiredInvites storeItem player
|
||||||
|
@ -507,7 +507,6 @@ let submitAddress (address : string) (ctx : IDiscordContext) =
|
|||||||
do! user.GrantRoleAsync(role) |> Async.AwaitTask
|
do! user.GrantRoleAsync(role) |> Async.AwaitTask
|
||||||
let role = ctx.GetGuild().GetRole(GuildEnvironment.roleWhiteOGPending)
|
let role = ctx.GetGuild().GetRole(GuildEnvironment.roleWhiteOGPending)
|
||||||
do! user.RevokeRoleAsync(role) |> Async.AwaitTask
|
do! user.RevokeRoleAsync(role) |> Async.AwaitTask
|
||||||
|
|
||||||
|
|
||||||
do! Messaging.sendFollowUpMessage ctx $"""
|
do! Messaging.sendFollowUpMessage ctx $"""
|
||||||
🚀 __Mint Date:__ June 20th
|
🚀 __Mint Date:__ June 20th
|
||||||
|
Loading…
x
Reference in New Issue
Block a user