Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Lottery revert #94

Merged
merged 2 commits into from
Dec 1, 2023
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions bot-commands.js
Original file line number Diff line number Diff line change
Expand Up @@ -741,6 +741,7 @@ async function Dispatch(discordMessage) {
'!prez': HandlePrezCommand,
'!veep': HandleVeepCommand,
'!indict': Ban.HandleBanCommand,
'!lottery': yen.DoLottery,
'!money': yen.HandleYenCommand,
'!nick': HandleNickCommand,
'!overflow': HandleOverflowCommand,
Expand Down
61 changes: 59 additions & 2 deletions yen.js
Original file line number Diff line number Diff line change
Expand Up @@ -131,6 +131,44 @@ async function CalculateInactivityTaxBase() {
return tax;
}

async function ChooseRandomInactiveUserWeightedByYen() {
let totalTaxBase = 0;
const inactiveUsers = [];
await UserCache.ForEach((user) => {
if (!user.yen) {
// Users with no yen can't pay tax.
return;
}
if (!user.last_seen) {
// Users that have never been seen for whatever reason don't pay tax.
return;
}
const lastSeen = moment(user.last_seen);
const gracePeriodEnd = lastSeen.add(90, 'days');
const currentTime = moment();
if (gracePeriodEnd.isAfter(currentTime)) {
// Recently active users don't pay tax. Only inactive ones.
return;
}
inactiveUsers.push(user);
totalTaxBase += user.yen;
});
if (totalTaxBase === 0) {
return null;
}
inactiveUsers.sort((a, b) => (a.commissar_id - b.commissar_id));
const r = Math.random() * totalTaxBase;
let cumulativeTax = 0;
for (const user of inactiveUsers) {
cumulativeTax += user.yen;
if (cumulativeTax >= r) {
return user;
}
}
// Shouldn't get here.
return null;
}

async function UpdateTaxChannel() {
const guild = await DiscordUtil.GetMainDiscordGuild();
const taxChannelId = '1012023632312156311';
Expand Down Expand Up @@ -185,7 +223,7 @@ async function UpdateTaxChannel() {
setTimeout(async () => {
await UpdateTaxChannel();
}, 60 * 1000);
// Lottery once per hour, which also triggers an update of the tax and yen channels.
// Lottery once an hour.
setInterval(async () => {
await DoLottery();
}, 3600 * 1000);
Expand Down Expand Up @@ -323,14 +361,17 @@ async function DoLottery() {
for (const i in taxBase) {
totalTaxBase += taxBase[i];
}
console.log('totalTaxBase', totalTaxBase);
const maxPrizeYen = 10;
const targetPrize = Math.floor(0.1 * totalTaxBase);
console.log('targetPrize', targetPrize);
const prizeYen = Math.min(targetPrize, maxPrizeYen);
const plan = await CalculateTaxPlan(prizeYen);
if (!plan) {
console.log('Could not raise enough tax revenue for lottery.');
return;
}
console.log('Tax Plan', plan);
const membersInVoiceChat = [];
const guild = await DiscordUtil.GetMainDiscordGuild();
for (const [channelId, channel] of guild.channels.cache) {
Expand All @@ -342,17 +383,20 @@ async function DoLottery() {
}
}
const n = membersInVoiceChat.length;
console.log(n, 'people in voice chat');
if (n < 2) {
console.log('Not enough people in voice chat for lottery.');
return;
}
const randomIndex = Math.floor(Math.random() * n);
const winnerId = membersInVoiceChat[randomIndex];
console.log('winnerId', winnerId);
const recipient = await UserCache.GetCachedUserByDiscordId(winnerId);
if (!recipient) {
console.log('Error. Invalid lottery winner.');
return;
}
console.log('Implementing lottery tax plan');
await ImplementTaxPlan(plan, recipient);
await UpdateYenChannel();
await UpdateTaxChannel();
Expand All @@ -378,14 +422,24 @@ async function UpdateYenChannel() {
const lines = [];
let savedMessage;
let totalYen = 0;
let activeYen = 0;
for (let i = 0; i < n; i++) {
const user = users[i];
const name = user.getNicknameOrTitleWithInsignia();
const rank = i + 1;
const line = `${rank}. ¥ ${user.yen} ${name}`;
lines.push(line);
totalYen += user.yen;
if (user.last_seen) {
const lastSeen = moment(user.last_seen);
const gracePeriodEnd = lastSeen.add(90, 'days');
const currentTime = moment();
if (gracePeriodEnd.isAfter(currentTime)) {
activeYen += user.yen;
}
}
}
const inactiveYen = totalYen - activeYen;
const guild = await DiscordUtil.GetMainDiscordGuild();
const yenChannelId = '1007017809492070522';
const channel = await guild.channels.resolve(yenChannelId);
Expand All @@ -394,10 +448,13 @@ async function UpdateYenChannel() {
const jeffSteamInventoryValue = 121462;
const reserveRatio = jeffSteamInventoryValue / totalYen;
const formattedReserveRatio = parseInt(reserveRatio * 100);
const formattedActiveYenPercent = parseInt(100 * activeYen / totalYen);
let message = '';
message += `Total yen in circulation: ¥ ${totalYen}\n`;
message += `Liquidation value of Jeff's Rust skins (August 2023): ¥ ${jeffSteamInventoryValue}\n`;
message += `Liquidation value of Jeff's Rust skins (Nov 2023): ¥ ${jeffSteamInventoryValue}\n`;
message += `Reserve ratio: ${formattedReserveRatio}%\n`;
message += `All recently active members (90d): ¥ ${activeYen} (${formattedActiveYenPercent}%)\n`;
message += `Inactive members: ¥ ${inactiveYen}\n`;
await channel.send(threeTicks + message + threeTicks);
}

Expand Down
Loading