I’ve been working on a custom currency system by Python for my Discord bot. It looks legit, but I don’t know if it is secure. It has anti-copying money so users earn fair and square. It works like this:
Whenever a user wants a money, he uses the /addcoin function to add money to his account. /addcoin requires a code, so he must mine for the code, which is the input of the SHA256 hash (shown in /coin). If it is correct, he gets a dollar and the system adds his ID to a file. After that, the system automatically renews the code, making the last code unusable. This means he can’t use it again. Don’t worry, the project is hosted locally by a computer, a raspberry pi, smth like that, so the files will be safe.
Here is the money part of my bot. Sorry if it’s too long!
@bot.tree.command(name="balance", description="Shows the user's current balance")
async def balance(interaction: discord.Interaction):
await interaction.response.defer()
"""Shows the user's current balance."""
ensure_file_exists(MONEY_FILE, default_content={})
user_id = str(interaction.user.id)
with open(MONEY_FILE, "r") as file:
money_data = json.load(file)
balance = money_data.get(user_id, 0)
await interaction.followup.send(f"Your balance is ${balance}")
@bot.tree.command(name="coin", description="Shows the SHA-256 hash of the money key")
async def coin(interaction: discord.Interaction):
await interaction.response.defer()
"""Shows the SHA-256 hash of the money key."""
if os.path.exists(SHA256_FILE):
with open(SHA256_FILE, "r") as file:
sha256_hash = file.read().strip()
await interaction.followup.send(f"SHA-256 Hash: {sha256_hash}")
else:
await interaction.followup.send("SHA-256 hash file does not exist.")
@bot.tree.command(name="addcoin", description="Decodes the given answer and updates balance if correct")
@app_commands.describe(answer="The answer to decode")
async def addcoin(interaction: discord.Interaction, answer: str):
await interaction.response.defer()
"""Decodes the given answer and updates balance if correct."""
ensure_file_exists(MONEY_FILE, default_content={})
ensure_file_exists(RECEIVED_FILE, default_content={})
user_id = str(interaction.user.id)
if os.path.exists(SHA256_FILE):
with open(SHA256_FILE, "r") as file:
correct_answer = file.read().strip()
hashed_answer = hashlib.sha256(answer.encode()).hexdigest()
if hashed_answer == correct_answer:
with open(RECEIVED_FILE, "r") as file:
received_data = json.load(file)
if user_id in received_data:
await interaction.followup.send("You have already claimed your reward.")
return
with open(MONEY_FILE, "r") as file:
money_data = json.load(file)
money_data[user_id] = money_data.get(user_id, 0) + 1
with open(MONEY_FILE, "w") as file:
json.dump(money_data, file)
received_data[user_id] = True
with open(RECEIVED_FILE, "w") as file:
json.dump(received_data, file)
await interaction.followup.send("Correct answer! $1 has been added to your balance.")
await newcoin(interaction)
else:
await interaction.followup.send("Incorrect answer. Please try again.")
else:
await interaction.followup.send("SHA-256 hash file does not exist.")
async def newcoin(interaction: discord.Interaction):
"""Renew the money key and update the SHA-256 hash."""
new_key = ''.join(random_.choices(string.ascii_letters + string.digits, k=32))
new_hash = hashlib.sha256(new_key.encode()).hexdigest()
with open(KEY_FILE, "w") as key_file:
key_file.write(new_key)
with open(SHA256_FILE, "w") as hash_file:
hash_file.write(new_hash)
if os.path.exists(RECEIVED_FILE):
os.remove(RECEIVED_FILE)
await interaction.followup.send("The money key has been renewed.")
@bot.tree.command(name="transfer", description="Transfer money to another user")
@app_commands.describe(recipient="The user to transfer money to", amount="The amount of money to transfer")
async def transfer(interaction: discord.Interaction, recipient: discord.User, amount: int):
await interaction.response.defer()
"""Transfer money to another user."""
ensure_file_exists(MONEY_FILE, default_content={})
user_id = str(interaction.user.id)
recipient_id = str(recipient.id)
if amount <= 0:
await interaction.followup.send("Invalid amount. Please enter a positive number.")
return
with open(MONEY_FILE, "r") as file:
money_data = json.load(file)
if money_data.get(user_id, 0) < amount:
await interaction.followup.send("You do not have enough balance to transfer that amount.")
return
money_data[user_id] -= amount
money_data[recipient_id] = money_data.get(recipient_id, 0) + amount
with open(MONEY_FILE, "w") as file:
json.dump(money_data, file)
await interaction.followup.send(f"Transferred ${amount} to {recipient.mention}.")
async def is_file_owner(user_id, file_name):
return file_name.startswith(f"{user_id}:")
async def get_file_path(interaction: discord.Interaction, file_name):
if not ":" in file_name:
file_name = str(interaction.user.id) + ":" + file_name
return os.path.join(FILES_DIRECTORY, file_name)