Adding the base for the currency system

This commit is contained in:
ION606
2022-04-14 21:49:11 -04:00
parent 4ca09e072a
commit 737d784c6e
8 changed files with 1546 additions and 0 deletions
+107
View File
@@ -0,0 +1,107 @@
const { Op } = require('sequelize');
const { Collection, Client, Formatters, Intents } = require('discord.js');
const { Users, CurrencyShop } = require('./dbObjects.js');
const client = new Client({ intents: [Intents.FLAGS.GUILDS, Intents.FLAGS.GUILD_MESSAGES] });
const currency = new Collection();
/*
* Make sure you are on at least version 5 of Sequelize! Version 4 as used in this guide will pose a security threat.
* You can read more about this issue On the [Sequelize issue tracker](https://github.com/sequelize/sequelize/issues/7310).
*/
Reflect.defineProperty(currency, 'add', {
value: async (id, amount) => {
const user = currency.get(id);
if (user) {
user.balance += Number(amount);
return user.save();
}
const newUser = await Users.create({ user_id: id, balance: amount });
currency.set(id, newUser);
return newUser;
},
});
Reflect.defineProperty(currency, 'getBalance', {
value: id => {
const user = currency.get(id);
return user ? user.balance : 0;
},
});
client.once('ready', async () => {
const storedBalances = await Users.findAll();
storedBalances.forEach(b => currency.set(b.user_id, b));
console.log(`Logged in as ${client.user.tag}!`);
});
client.on('messageCreate', async message => {
if (message.author.bot) return;
currency.add(message.author.id, 1);
});
client.on('interactionCreate', async interaction => {
if (!interaction.isCommand()) return;
const { commandName } = interaction;
if (commandName === 'balance') {
const target = interaction.options.getUser('user') || interaction.user;
return interaction.reply(`${target.tag} has ${currency.getBalance(target.id)}💰`);
} else if (commandName === 'inventory') {
const target = interaction.options.getUser('user') || interaction.user;
const user = await Users.findOne({ where: { user_id: target.id } });
const items = await user.getItems();
if (!items.length) return interaction.reply(`${target.tag} has nothing!`);
return interaction.reply(`${target.tag} currently has ${items.map(t => `${t.amount} ${t.item.name}`).join(', ')}`);
} else if (commandName === 'transfer') {
const currentAmount = currency.getBalance(interaction.user.id);
const transferAmount = interaction.options.getInteger('amount');
const transferTarget = interaction.options.getUser('user');
if (transferAmount > currentAmount) return interaction.reply(`Sorry ${interaction.user} you don't have that much.`);
if (transferAmount <= 0) return interaction.reply(`Please enter an amount greater than zero, ${interaction.user}`);
currency.add(interaction.user.id, -transferAmount);
currency.add(transferTarget.id, transferAmount);
return interaction.reply(`Successfully transferred ${transferAmount}💰 to ${transferTarget.tag}. Your current balance is ${currency.getBalance(interaction.user.id)}💰`);
} else if (commandName === 'buy') {
const itemName = interaction.options.getString('item');
const item = await CurrencyShop.findOne({ where: { name: { [Op.like]: itemName } } });
if (!item) return interaction.reply('That item doesn\'t exist.');
if (item.cost > currency.getBalance(interaction.user.id)) {
return interaction.reply(`You don't have enough currency, ${interaction.user}`);
}
const user = await Users.findOne({ where: { user_id: interaction.user.id } });
currency.add(interaction.user.id, -item.cost);
await user.addItem(item);
return interaction.reply(`You've bought a ${item.name}`);
} else if (commandName === 'shop') {
const items = await CurrencyShop.findAll();
return interaction.reply(Formatters.codeBlock(items.map(i => `${i.name}: ${i.cost}💰`).join('\n')));
} else if (commandName === 'leaderboard') {
return interaction.reply(
Formatters.codeBlock(
currency.sort((a, b) => b.balance - a.balance)
.filter(user => client.users.cache.has(user.user_id))
.first(10)
.map((user, position) => `(${position + 1}) ${(client.users.cache.get(user.user_id).tag)}: ${user.balance}💰`)
.join('\n'),
),
);
}
});
client.login('your-token-goes-here');
+32
View File
@@ -0,0 +1,32 @@
const Sequelize = require('sequelize');
/*
* Make sure you are on at least version 5 of Sequelize! Version 4 as used in this guide will pose a security threat.
* You can read more about this issue on the [Sequelize issue tracker](https://github.com/sequelize/sequelize/issues/7310).
*/
const sequelize = new Sequelize('database', 'username', 'password', {
host: 'localhost',
dialect: 'sqlite',
logging: false,
storage: 'database.sqlite',
});
const CurrencyShop = require('./models/CurrencyShop.js')(sequelize, Sequelize.DataTypes);
require('./models/Users.js')(sequelize, Sequelize.DataTypes);
require('./models/UserItems.js')(sequelize, Sequelize.DataTypes);
const force = process.argv.includes('--force') || process.argv.includes('-f');
sequelize.sync({ force }).then(async () => {
const shop = [
CurrencyShop.upsert({ name: 'Tea', cost: 1 }),
CurrencyShop.upsert({ name: 'Coffee', cost: 2 }),
CurrencyShop.upsert({ name: 'Cake', cost: 5 }),
];
await Promise.all(shop);
console.log('Database synced');
sequelize.close();
}).catch(console.error);
+47
View File
@@ -0,0 +1,47 @@
const Sequelize = require('sequelize');
/*
* Make sure you are on at least version 5 of Sequelize! Version 4 as used in this guide will pose a security threat.
* You can read more about this issue on the [Sequelize issue tracker](https://github.com/sequelize/sequelize/issues/7310).
*/
const sequelize = new Sequelize('database', 'username', 'password', {
host: 'localhost',
dialect: 'sqlite',
logging: false,
storage: 'database.sqlite',
});
const Users = require('./models/Users.js')(sequelize, Sequelize.DataTypes);
const CurrencyShop = require('./models/CurrencyShop.js')(sequelize, Sequelize.DataTypes);
const UserItems = require('./models/UserItems.js')(sequelize, Sequelize.DataTypes);
UserItems.belongsTo(CurrencyShop, { foreignKey: 'item_id', as: 'item' });
Reflect.defineProperty(Users.prototype, 'addItem', {
/* eslint-disable-next-line func-name-matching */
value: async function addItem(item) {
const userItem = await UserItems.findOne({
where: { user_id: this.user_id, item_id: item.id },
});
if (userItem) {
userItem.amount += 1;
return userItem.save();
}
return UserItems.create({ user_id: this.user_id, item_id: item.id, amount: 1 });
},
});
Reflect.defineProperty(Users.prototype, 'getItems', {
/* eslint-disable-next-line func-name-matching */
value: function getItems() {
return UserItems.findAll({
where: { user_id: this.user_id },
include: ['item'],
});
},
});
module.exports = { Users, CurrencyShop, UserItems };
+14
View File
@@ -0,0 +1,14 @@
module.exports = (sequelize, DataTypes) => {
return sequelize.define('currency_shop', {
name: {
type: DataTypes.STRING,
unique: true,
},
cost: {
type: DataTypes.INTEGER,
allowNull: false,
},
}, {
timestamps: false,
});
};
+13
View File
@@ -0,0 +1,13 @@
module.exports = (sequelize, DataTypes) => {
return sequelize.define('user_item', {
user_id: DataTypes.STRING,
item_id: DataTypes.INTEGER,
amount: {
type: DataTypes.INTEGER,
allowNull: false,
'default': 0,
},
}, {
timestamps: false,
});
};
+15
View File
@@ -0,0 +1,15 @@
module.exports = (sequelize, DataTypes) => {
return sequelize.define('users', {
user_id: {
type: DataTypes.STRING,
primaryKey: true,
},
balance: {
type: DataTypes.INTEGER,
defaultValue: 0,
allowNull: false,
},
}, {
timestamps: false,
});
};
+1316
View File
File diff suppressed because it is too large Load Diff
+2
View File
@@ -7,6 +7,8 @@
"ffmpeg": "^0.0.4",
"ffmpeg-static": "^5.0.0",
"node.js": "^0.0.1-security",
"sequelize": "^6.19.0",
"sqlite3": "^5.0.3",
"sudo": "^1.0.3"
},
"name": "selmerbot",