Compare commits

...

7 commits

66 changed files with 254 additions and 88839 deletions

View file

@ -90,21 +90,17 @@ public sealed class Bot : IBot
public IReadOnlyList<ulong> GetCurrentGuildIds() public IReadOnlyList<ulong> GetCurrentGuildIds()
=> Client.Guilds.Select(x => x.Id).ToList().AsReadOnly(); => Client.Guilds.Select(x => x.Id).ToList().AsReadOnly();
=> Client.Guilds.Select(x => x.Id).ToList().AsReadOnly();
private async Task AddServices()
private async Task AddServices() private async Task AddServices()
{ {
var startingGuildIdList = GetCurrentGuildIds().ToList(); var startingGuildIdList = GetCurrentGuildIds().ToList();
var startTime = Stopwatch.GetTimestamp(); var startTime = Stopwatch.GetTimestamp();
var bot = Client.CurrentUser; var bot = Client.CurrentUser;
await using (var uow = _db.GetDbContext())
await using (var uow = _db.GetDbContext()) await using (var uow = _db.GetDbContext())
{ {
AllGuildConfigs = await uow.GuildConfigs.GetAllGuildConfigs(startingGuildIdList); AllGuildConfigs = await uow.GuildConfigs.GetAllGuildConfigs(startingGuildIdList);
uow.EnsureUserCreated(bot.Id, bot.Username, bot.Discriminator, bot.AvatarId); uow.EnsureUserCreated(bot.Id, bot.Username, bot.Discriminator, bot.AvatarId);
AllGuildConfigs = await uow.GuildConfigs.GetAllGuildConfigs(startingGuildIdList);
} }
// var svcs = new StandardKernel(new NinjectSettings() // var svcs = new StandardKernel(new NinjectSettings()
@ -272,7 +268,6 @@ public sealed class Bot : IBot
try try
{ {
await AddServices(); await AddServices();
await AddServices();
} }
catch (Exception ex) catch (Exception ex)
{ {

View file

@ -690,6 +690,17 @@ public abstract class EllieContext : DbContext
}) })
.IsUnique()); .IsUnique());
modelBuilder.Entity<GreetSettings>(gs =>
{
gs
.Property(x => x.IsEnabled)
.HasDefaultValue(false);
gs
.Property(x => x.AutoDeleteTimer)
.HasDefaultValue(0);
});
#endregion #endregion
} }

View file

@ -44,8 +44,6 @@ public sealed class EllieDbService : DbService
case "postgres": case "postgres":
case "pgsql": case "pgsql":
return new PostgreSqlContext(connString); return new PostgreSqlContext(connString);
case "mysql":
return new MysqlContext(connString);
case "sqlite": case "sqlite":
return new SqliteContext(connString); return new SqliteContext(connString);
default: default:

View file

@ -1,38 +0,0 @@
using Microsoft.EntityFrameworkCore;
using EllieBot.Db.Models;
namespace EllieBot.Db;
public sealed class MysqlContext : EllieContext
{
private readonly string _connStr;
private readonly string _version;
protected override string CurrencyTransactionOtherIdDefaultValue
=> "NULL";
public MysqlContext(string connStr = "Server=localhost", string version = "8.0")
{
_connStr = connStr;
_version = version;
}
protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
{
base.OnConfiguring(optionsBuilder);
optionsBuilder
.UseLowerCaseNamingConvention()
.UseMySql(_connStr, ServerVersion.Parse(_version));
}
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
base.OnModelCreating(modelBuilder);
// mysql is case insensitive by default
// we can set binary collation to change that
modelBuilder.Entity<ClubInfo>()
.Property(x => x.Name)
.UseCollation("utf8mb4_bin");
}
}

View file

@ -91,7 +91,6 @@
<PackageReference Include="Microsoft.EntityFrameworkCore.Sqlite" Version="8.0.8" /> <PackageReference Include="Microsoft.EntityFrameworkCore.Sqlite" Version="8.0.8" />
<PackageReference Include="Npgsql.EntityFrameworkCore.PostgreSQL" Version="8.0.4" /> <PackageReference Include="Npgsql.EntityFrameworkCore.PostgreSQL" Version="8.0.4" />
<PackageReference Include="Pomelo.EntityFrameworkCore.MySql" Version="8.0.2" />
<PackageReference Include="EFCore.NamingConventions" Version="8.0.3" /> <PackageReference Include="EFCore.NamingConventions" Version="8.0.3" />

View file

@ -7,16 +7,7 @@ public static class MigrationQueries
{ {
public static void MigrateRero(MigrationBuilder migrationBuilder) public static void MigrateRero(MigrationBuilder migrationBuilder)
{ {
if (migrationBuilder.IsMySql()) if (migrationBuilder.IsSqlite())
{
migrationBuilder.Sql(
@"INSERT IGNORE into reactionroles(guildid, channelid, messageid, emote, roleid, `group`, levelreq, dateadded)
select guildid, channelid, messageid, emotename, roleid, exclusive, 0, reactionrolemessage.dateadded
from reactionrole
left join reactionrolemessage on reactionrolemessage.id = reactionrole.reactionrolemessageid
left join guildconfigs on reactionrolemessage.guildconfigid = guildconfigs.id;");
}
else if (migrationBuilder.IsSqlite())
{ {
migrationBuilder.Sql( migrationBuilder.Sql(
@"insert or ignore into reactionroles(guildid, channelid, messageid, emote, roleid, 'group', levelreq, dateadded) @"insert or ignore into reactionroles(guildid, channelid, messageid, emote, roleid, 'group', levelreq, dateadded)
@ -27,7 +18,8 @@ left join guildconfigs on reactionrolemessage.guildconfigid = guildconfigs.id;")
} }
else if (migrationBuilder.IsNpgsql()) else if (migrationBuilder.IsNpgsql())
{ {
migrationBuilder.Sql(@"insert into reactionroles(guildid, channelid, messageid, emote, roleid, ""group"", levelreq, dateadded) migrationBuilder.Sql(
@"insert into reactionroles(guildid, channelid, messageid, emote, roleid, ""group"", levelreq, dateadded)
select guildid, channelid, messageid, emotename, roleid, exclusive::int, 0, reactionrolemessage.dateadded select guildid, channelid, messageid, emotename, roleid, exclusive::int, 0, reactionrolemessage.dateadded
from reactionrole from reactionrole
left join reactionrolemessage on reactionrolemessage.id = reactionrole.reactionrolemessageid left join reactionrolemessage on reactionrolemessage.id = reactionrole.reactionrolemessageid
@ -43,15 +35,34 @@ left join guildconfigs on reactionrolemessage.guildconfigid = guildconfigs.id;")
public static void GuildConfigCleanup(MigrationBuilder builder) public static void GuildConfigCleanup(MigrationBuilder builder)
{ {
builder.Sql($""" builder.Sql($"""
DELETE FROM "DelMsgOnCmdChannel" WHERE "GuildConfigId" is NULL;
DELETE FROM "WarningPunishment" WHERE "GuildConfigId" NOT IN (SELECT "Id" from "GuildConfigs");
DELETE FROM "StreamRoleBlacklistedUser" WHERE "StreamRoleSettingsId" is NULL; DELETE FROM "StreamRoleBlacklistedUser" WHERE "StreamRoleSettingsId" is NULL;
"""); """);
}
builder.Sql($""" public static void GreetSettingsCopy(MigrationBuilder builder)
DELETE FROM "DelMsgOnCmdChannel" WHERE "GuildConfigId" is NULL; {
""");
builder.Sql(""" builder.Sql("""
DELETE FROM "WarningPunishment" WHERE "GuildConfigId" NOT IN (SELECT "Id" from "GuildConfigs"); INSERT INTO GreetSettings (GuildId, GreetType, MessageText, IsEnabled, ChannelId, AutoDeleteTimer)
SELECT GuildId, 0, ChannelGreetMessageText, SendChannelGreetMessage, GreetMessageChannelId, AutoDeleteGreetMessagesTimer
FROM GuildConfigs
WHERE SendChannelGreetMessage = TRUE;
INSERT INTO GreetSettings (GuildId, GreetType, MessageText, IsEnabled, ChannelId, AutoDeleteTimer)
SELECT GuildId, 1, DmGreetMessageText, SendDmGreetMessage, GreetMessageChannelId, 0
FROM GuildConfigs
WHERE SendDmGreetMessage = TRUE;
INSERT INTO GreetSettings (GuildId, GreetType, MessageText, IsEnabled, ChannelId, AutoDeleteTimer)
SELECT GuildId, 2, ChannelByeMessageText, SendChannelByeMessage, ByeMessageChannelId, AutoDeleteByeMessagesTimer
FROM GuildConfigs
WHERE SendChannelByeMessage = TRUE;
INSERT INTO GreetSettings (GuildId, GreetType, MessageText, IsEnabled, ChannelId, AutoDeleteTimer)
SELECT GuildId, 3, BoostMessage, SendBoostMessage, BoostMessageChannelId, BoostMessageDeleteAfter
FROM GuildConfigs
WHERE SendBoostMessage = TRUE;
"""); """);
} }
} }

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -1,26 +0,0 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class stondel : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<bool>(
name: "deletestreamonlinemessage",
table: "guildconfigs",
type: "tinyint(1)",
nullable: false,
defaultValue: false);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "deletestreamonlinemessage",
table: "guildconfigs");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,41 +0,0 @@
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class bank : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateTable(
name: "bankusers",
columns: table => new
{
id = table.Column<int>(type: "int", nullable: false)
.Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn),
userid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
balance = table.Column<long>(type: "bigint", nullable: false),
dateadded = table.Column<DateTime>(type: "datetime(6)", nullable: true)
},
constraints: table =>
{
table.PrimaryKey("pk_bankusers", x => x.id);
})
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.CreateIndex(
name: "ix_bankusers_userid",
table: "bankusers",
column: "userid",
unique: true);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "bankusers");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,120 +0,0 @@
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class newrero : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateTable(
name: "reactionroles",
columns: table => new
{
id = table.Column<int>(type: "int", nullable: false)
.Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn),
guildid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
channelid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
messageid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
emote = table.Column<string>(type: "varchar(100)", maxLength: 100, nullable: true)
.Annotation("MySql:CharSet", "utf8mb4"),
roleid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
group = table.Column<int>(type: "int", nullable: false),
levelreq = table.Column<int>(type: "int", nullable: false),
dateadded = table.Column<DateTime>(type: "datetime(6)", nullable: true)
},
constraints: table =>
{
table.PrimaryKey("pk_reactionroles", x => x.id);
})
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.CreateIndex(
name: "ix_reactionroles_guildid",
table: "reactionroles",
column: "guildid");
migrationBuilder.CreateIndex(
name: "ix_reactionroles_messageid_emote",
table: "reactionroles",
columns: new[] { "messageid", "emote" },
unique: true);
MigrationQueries.MigrateRero(migrationBuilder);
migrationBuilder.DropTable(
name: "reactionrole");
migrationBuilder.DropTable(
name: "reactionrolemessage");
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "reactionroles");
migrationBuilder.CreateTable(
name: "reactionrolemessage",
columns: table => new
{
id = table.Column<int>(type: "int", nullable: false)
.Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn),
guildconfigid = table.Column<int>(type: "int", nullable: false),
channelid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
dateadded = table.Column<DateTime>(type: "datetime(6)", nullable: true),
exclusive = table.Column<bool>(type: "tinyint(1)", nullable: false),
index = table.Column<int>(type: "int", nullable: false),
messageid = table.Column<ulong>(type: "bigint unsigned", nullable: false)
},
constraints: table =>
{
table.PrimaryKey("pk_reactionrolemessage", x => x.id);
table.ForeignKey(
name: "fk_reactionrolemessage_guildconfigs_guildconfigid",
column: x => x.guildconfigid,
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
})
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.CreateTable(
name: "reactionrole",
columns: table => new
{
id = table.Column<int>(type: "int", nullable: false)
.Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn),
dateadded = table.Column<DateTime>(type: "datetime(6)", nullable: true),
emotename = table.Column<string>(type: "longtext", nullable: true)
.Annotation("MySql:CharSet", "utf8mb4"),
reactionrolemessageid = table.Column<int>(type: "int", nullable: true),
roleid = table.Column<ulong>(type: "bigint unsigned", nullable: false)
},
constraints: table =>
{
table.PrimaryKey("pk_reactionrole", x => x.id);
table.ForeignKey(
name: "fk_reactionrole_reactionrolemessage_reactionrolemessageid",
column: x => x.reactionrolemessageid,
principalTable: "reactionrolemessage",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
})
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.CreateIndex(
name: "ix_reactionrole_reactionrolemessageid",
table: "reactionrole",
column: "reactionrolemessageid");
migrationBuilder.CreateIndex(
name: "ix_reactionrolemessage_guildconfigid",
table: "reactionrolemessage",
column: "guildconfigid");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,175 +0,0 @@
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class patronagesystem : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.RenameColumn(
name: "patreonuserid",
table: "rewardedusers",
newName: "platformuserid");
migrationBuilder.RenameIndex(
name: "ix_rewardedusers_patreonuserid",
table: "rewardedusers",
newName: "ix_rewardedusers_platformuserid");
migrationBuilder.AlterColumn<long>(
name: "xp",
table: "userxpstats",
type: "bigint",
nullable: false,
oldClrType: typeof(int),
oldType: "int");
migrationBuilder.AlterColumn<long>(
name: "awardedxp",
table: "userxpstats",
type: "bigint",
nullable: false,
oldClrType: typeof(int),
oldType: "int");
migrationBuilder.AlterColumn<long>(
name: "amountrewardedthismonth",
table: "rewardedusers",
type: "bigint",
nullable: false,
oldClrType: typeof(int),
oldType: "int");
migrationBuilder.AlterColumn<bool>(
name: "verboseerrors",
table: "guildconfigs",
type: "tinyint(1)",
nullable: false,
defaultValue: true,
oldClrType: typeof(bool),
oldType: "tinyint(1)");
migrationBuilder.AlterColumn<long>(
name: "totalxp",
table: "discorduser",
type: "bigint",
nullable: false,
defaultValue: 0L,
oldClrType: typeof(int),
oldType: "int",
oldDefaultValue: 0);
migrationBuilder.CreateTable(
name: "patronquotas",
columns: table => new
{
userid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
featuretype = table.Column<int>(type: "int", nullable: false),
feature = table.Column<string>(type: "varchar(255)", nullable: false)
.Annotation("MySql:CharSet", "utf8mb4"),
hourlycount = table.Column<uint>(type: "int unsigned", nullable: false),
dailycount = table.Column<uint>(type: "int unsigned", nullable: false),
monthlycount = table.Column<uint>(type: "int unsigned", nullable: false)
},
constraints: table =>
{
table.PrimaryKey("pk_patronquotas", x => new { x.userid, x.featuretype, x.feature });
})
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.CreateTable(
name: "patrons",
columns: table => new
{
userid = table.Column<ulong>(type: "bigint unsigned", nullable: false)
.Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn),
uniqueplatformuserid = table.Column<string>(type: "varchar(255)", nullable: true)
.Annotation("MySql:CharSet", "utf8mb4"),
amountcents = table.Column<int>(type: "int", nullable: false),
lastcharge = table.Column<DateTime>(type: "datetime(6)", nullable: false),
validthru = table.Column<DateTime>(type: "datetime(6)", nullable: false)
},
constraints: table =>
{
table.PrimaryKey("pk_patrons", x => x.userid);
})
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.CreateIndex(
name: "ix_patronquotas_userid",
table: "patronquotas",
column: "userid");
migrationBuilder.CreateIndex(
name: "ix_patrons_uniqueplatformuserid",
table: "patrons",
column: "uniqueplatformuserid",
unique: true);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "patronquotas");
migrationBuilder.DropTable(
name: "patrons");
migrationBuilder.RenameColumn(
name: "platformuserid",
table: "rewardedusers",
newName: "patreonuserid");
migrationBuilder.RenameIndex(
name: "ix_rewardedusers_platformuserid",
table: "rewardedusers",
newName: "ix_rewardedusers_patreonuserid");
migrationBuilder.AlterColumn<int>(
name: "xp",
table: "userxpstats",
type: "int",
nullable: false,
oldClrType: typeof(long),
oldType: "bigint");
migrationBuilder.AlterColumn<int>(
name: "awardedxp",
table: "userxpstats",
type: "int",
nullable: false,
oldClrType: typeof(long),
oldType: "bigint");
migrationBuilder.AlterColumn<int>(
name: "amountrewardedthismonth",
table: "rewardedusers",
type: "int",
nullable: false,
oldClrType: typeof(long),
oldType: "bigint");
migrationBuilder.AlterColumn<bool>(
name: "verboseerrors",
table: "guildconfigs",
type: "tinyint(1)",
nullable: false,
oldClrType: typeof(bool),
oldType: "tinyint(1)",
oldDefaultValue: true);
migrationBuilder.AlterColumn<int>(
name: "totalxp",
table: "discorduser",
type: "int",
nullable: false,
defaultValue: 0,
oldClrType: typeof(long),
oldType: "bigint",
oldDefaultValue: 0L);
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,38 +0,0 @@
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class stondeldbcache : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateTable(
name: "streamonlinemessages",
columns: table => new
{
id = table.Column<int>(type: "int", nullable: false)
.Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn),
channelid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
messageid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
type = table.Column<int>(type: "int", nullable: false),
name = table.Column<string>(type: "longtext", nullable: true)
.Annotation("MySql:CharSet", "utf8mb4"),
dateadded = table.Column<DateTime>(type: "datetime(6)", nullable: true)
},
constraints: table =>
{
table.PrimaryKey("pk_streamonlinemessages", x => x.id);
})
.Annotation("MySql:CharSet", "utf8mb4");
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "streamonlinemessages");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,25 +0,0 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class logwarns : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<ulong>(
name: "logwarnsid",
table: "logsettings",
type: "bigint unsigned",
nullable: true);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "logwarnsid",
table: "logsettings");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,44 +0,0 @@
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class xpitemshop : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateTable(
name: "xpshopowneditem",
columns: table => new
{
id = table.Column<int>(type: "int", nullable: false)
.Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn),
userid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
itemtype = table.Column<int>(type: "int", nullable: false),
isusing = table.Column<bool>(type: "tinyint(1)", nullable: false),
itemkey = table.Column<string>(type: "varchar(255)", nullable: false)
.Annotation("MySql:CharSet", "utf8mb4"),
dateadded = table.Column<DateTime>(type: "datetime(6)", nullable: true)
},
constraints: table =>
{
table.PrimaryKey("pk_xpshopowneditem", x => x.id);
})
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.CreateIndex(
name: "ix_xpshopowneditem_userid_itemtype_itemkey",
table: "xpshopowneditem",
columns: new[] { "userid", "itemtype", "itemkey" },
unique: true);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "xpshopowneditem");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,26 +0,0 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class linkonlychannels : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<int>(
name: "type",
table: "imageonlychannels",
type: "int",
nullable: false,
defaultValue: 0);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "type",
table: "imageonlychannels");
}
}
}

View file

@ -1,48 +0,0 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class removeobsoletexpcolumns : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "lastlevelup",
table: "userxpstats");
migrationBuilder.DropColumn(
name: "lastlevelup",
table: "discorduser");
migrationBuilder.DropColumn(
name: "lastxpgain",
table: "discorduser");
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<DateTime>(
name: "lastlevelup",
table: "userxpstats",
type: "datetime(6)",
nullable: false,
defaultValueSql: "(UTC_TIMESTAMP)");
migrationBuilder.AddColumn<DateTime>(
name: "lastlevelup",
table: "discorduser",
type: "datetime(6)",
nullable: false,
defaultValueSql: "(UTC_TIMESTAMP)");
migrationBuilder.AddColumn<DateTime>(
name: "lastxpgain",
table: "discorduser",
type: "datetime(6)",
nullable: false,
defaultValueSql: "(UTC_TIMESTAMP - INTERVAL 1 year)");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,25 +0,0 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class banprune : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<int>(
name: "prunedays",
table: "bantemplates",
type: "int",
nullable: true);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "prunedays",
table: "bantemplates");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,25 +0,0 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class shoprolereq : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<ulong>(
name: "rolerequirement",
table: "shopentry",
type: "bigint unsigned",
nullable: true);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "rolerequirement",
table: "shopentry");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,41 +0,0 @@
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class autopub : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateTable(
name: "autopublishchannel",
columns: table => new
{
id = table.Column<int>(type: "int", nullable: false)
.Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn),
guildid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
channelid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
dateadded = table.Column<DateTime>(type: "datetime(6)", nullable: true)
},
constraints: table =>
{
table.PrimaryKey("pk_autopublishchannel", x => x.id);
})
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.CreateIndex(
name: "ix_autopublishchannel_guildid",
table: "autopublishchannel",
column: "guildid",
unique: true);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "autopublishchannel");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,43 +0,0 @@
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class gamblingstats : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateTable(
name: "gamblingstats",
columns: table => new
{
id = table.Column<int>(type: "int", nullable: false)
.Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn),
feature = table.Column<string>(type: "varchar(255)", nullable: true)
.Annotation("MySql:CharSet", "utf8mb4"),
bet = table.Column<decimal>(type: "decimal(65,30)", nullable: false),
paidout = table.Column<decimal>(type: "decimal(65,30)", nullable: false),
dateadded = table.Column<DateTime>(type: "datetime(6)", nullable: true)
},
constraints: table =>
{
table.PrimaryKey("pk_gamblingstats", x => x.id);
})
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.CreateIndex(
name: "ix_gamblingstats_feature",
table: "gamblingstats",
column: "feature",
unique: true);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "gamblingstats");
}
}
}

View file

@ -1,26 +0,0 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class toggleglobalexpressions : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<bool>(
name: "disableglobalexpressions",
table: "guildconfigs",
type: "tinyint(1)",
nullable: false,
defaultValue: false);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "disableglobalexpressions",
table: "guildconfigs");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,35 +0,0 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class logthread : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<ulong>(
name: "threadcreatedid",
table: "logsettings",
type: "bigint unsigned",
nullable: true);
migrationBuilder.AddColumn<ulong>(
name: "threaddeletedid",
table: "logsettings",
type: "bigint unsigned",
nullable: true);
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "threadcreatedid",
table: "logsettings");
migrationBuilder.DropColumn(
name: "threaddeletedid",
table: "logsettings");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,26 +0,0 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
public partial class feedtext : Migration
{
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.AddColumn<string>(
name: "message",
table: "feedsub",
type: "longtext",
nullable: true)
.Annotation("MySql:CharSet", "utf8mb4");
}
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "message",
table: "feedsub");
}
}
}

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

File diff suppressed because it is too large Load diff

View file

@ -1,702 +0,0 @@
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
/// <inheritdoc />
public partial class guidlconfigcleanup : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropForeignKey(
name: "fk_antiraidsetting_guildconfigs_guildconfigid",
table: "antiraidsetting");
migrationBuilder.DropForeignKey(
name: "fk_antispamignore_antispamsetting_antispamsettingid",
table: "antispamignore");
migrationBuilder.DropForeignKey(
name: "fk_antispamsetting_guildconfigs_guildconfigid",
table: "antispamsetting");
migrationBuilder.DropForeignKey(
name: "fk_commandalias_guildconfigs_guildconfigid",
table: "commandalias");
migrationBuilder.DropForeignKey(
name: "fk_commandcooldown_guildconfigs_guildconfigid",
table: "commandcooldown");
migrationBuilder.DropForeignKey(
name: "fk_delmsgoncmdchannel_guildconfigs_guildconfigid",
table: "delmsgoncmdchannel");
migrationBuilder.DropForeignKey(
name: "fk_excludeditem_xpsettings_xpsettingsid",
table: "excludeditem");
migrationBuilder.DropForeignKey(
name: "fk_filterchannelid_guildconfigs_guildconfigid",
table: "filterchannelid");
migrationBuilder.DropForeignKey(
name: "fk_filteredword_guildconfigs_guildconfigid",
table: "filteredword");
migrationBuilder.DropForeignKey(
name: "fk_filterlinkschannelid_guildconfigs_guildconfigid",
table: "filterlinkschannelid");
migrationBuilder.DropForeignKey(
name: "fk_filterwordschannelid_guildconfigs_guildconfigid",
table: "filterwordschannelid");
migrationBuilder.DropForeignKey(
name: "fk_followedstream_guildconfigs_guildconfigid",
table: "followedstream");
migrationBuilder.DropForeignKey(
name: "fk_gcchannelid_guildconfigs_guildconfigid",
table: "gcchannelid");
migrationBuilder.DropForeignKey(
name: "fk_muteduserid_guildconfigs_guildconfigid",
table: "muteduserid");
migrationBuilder.DropForeignKey(
name: "fk_permissions_guildconfigs_guildconfigid",
table: "permissions");
migrationBuilder.DropForeignKey(
name: "fk_shopentry_guildconfigs_guildconfigid",
table: "shopentry");
migrationBuilder.DropForeignKey(
name: "fk_shopentryitem_shopentry_shopentryid",
table: "shopentryitem");
migrationBuilder.DropForeignKey(
name: "fk_slowmodeignoredrole_guildconfigs_guildconfigid",
table: "slowmodeignoredrole");
migrationBuilder.DropForeignKey(
name: "fk_slowmodeignoreduser_guildconfigs_guildconfigid",
table: "slowmodeignoreduser");
migrationBuilder.DropForeignKey(
name: "fk_streamroleblacklisteduser_streamrolesettings_streamrolesetti~",
table: "streamroleblacklisteduser");
migrationBuilder.DropForeignKey(
name: "fk_streamrolewhitelisteduser_streamrolesettings_streamrolesetti~",
table: "streamrolewhitelisteduser");
migrationBuilder.DropForeignKey(
name: "fk_unbantimer_guildconfigs_guildconfigid",
table: "unbantimer");
migrationBuilder.DropForeignKey(
name: "fk_unmutetimer_guildconfigs_guildconfigid",
table: "unmutetimer");
migrationBuilder.DropForeignKey(
name: "fk_unroletimer_guildconfigs_guildconfigid",
table: "unroletimer");
migrationBuilder.DropForeignKey(
name: "fk_vcroleinfo_guildconfigs_guildconfigid",
table: "vcroleinfo");
migrationBuilder.DropForeignKey(
name: "fk_warningpunishment_guildconfigs_guildconfigid",
table: "warningpunishment");
migrationBuilder.DropTable(
name: "ignoredvoicepresencechannels");
migrationBuilder.AlterColumn<int>(
name: "streamrolesettingsid",
table: "streamrolewhitelisteduser",
type: "int",
nullable: false,
defaultValue: 0,
oldClrType: typeof(int),
oldType: "int",
oldNullable: true);
migrationBuilder.AlterColumn<int>(
name: "streamrolesettingsid",
table: "streamroleblacklisteduser",
type: "int",
nullable: false,
defaultValue: 0,
oldClrType: typeof(int),
oldType: "int",
oldNullable: true);
migrationBuilder.AlterColumn<int>(
name: "guildconfigid",
table: "delmsgoncmdchannel",
type: "int",
nullable: false,
defaultValue: 0,
oldClrType: typeof(int),
oldType: "int",
oldNullable: true);
migrationBuilder.AddForeignKey(
name: "fk_antiraidsetting_guildconfigs_guildconfigid",
table: "antiraidsetting",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_antispamignore_antispamsetting_antispamsettingid",
table: "antispamignore",
column: "antispamsettingid",
principalTable: "antispamsetting",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_antispamsetting_guildconfigs_guildconfigid",
table: "antispamsetting",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_commandalias_guildconfigs_guildconfigid",
table: "commandalias",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_commandcooldown_guildconfigs_guildconfigid",
table: "commandcooldown",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_delmsgoncmdchannel_guildconfigs_guildconfigid",
table: "delmsgoncmdchannel",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_excludeditem_xpsettings_xpsettingsid",
table: "excludeditem",
column: "xpsettingsid",
principalTable: "xpsettings",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_filterchannelid_guildconfigs_guildconfigid",
table: "filterchannelid",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_filteredword_guildconfigs_guildconfigid",
table: "filteredword",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_filterlinkschannelid_guildconfigs_guildconfigid",
table: "filterlinkschannelid",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_filterwordschannelid_guildconfigs_guildconfigid",
table: "filterwordschannelid",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_followedstream_guildconfigs_guildconfigid",
table: "followedstream",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_gcchannelid_guildconfigs_guildconfigid",
table: "gcchannelid",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_muteduserid_guildconfigs_guildconfigid",
table: "muteduserid",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_permissions_guildconfigs_guildconfigid",
table: "permissions",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_shopentry_guildconfigs_guildconfigid",
table: "shopentry",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_shopentryitem_shopentry_shopentryid",
table: "shopentryitem",
column: "shopentryid",
principalTable: "shopentry",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_slowmodeignoredrole_guildconfigs_guildconfigid",
table: "slowmodeignoredrole",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_slowmodeignoreduser_guildconfigs_guildconfigid",
table: "slowmodeignoreduser",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_streamroleblacklisteduser_streamrolesettings_streamrolesetti~",
table: "streamroleblacklisteduser",
column: "streamrolesettingsid",
principalTable: "streamrolesettings",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_streamrolewhitelisteduser_streamrolesettings_streamrolesetti~",
table: "streamrolewhitelisteduser",
column: "streamrolesettingsid",
principalTable: "streamrolesettings",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_unbantimer_guildconfigs_guildconfigid",
table: "unbantimer",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_unmutetimer_guildconfigs_guildconfigid",
table: "unmutetimer",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_unroletimer_guildconfigs_guildconfigid",
table: "unroletimer",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_vcroleinfo_guildconfigs_guildconfigid",
table: "vcroleinfo",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_warningpunishment_guildconfigs_guildconfigid",
table: "warningpunishment",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropForeignKey(
name: "fk_antiraidsetting_guildconfigs_guildconfigid",
table: "antiraidsetting");
migrationBuilder.DropForeignKey(
name: "fk_antispamignore_antispamsetting_antispamsettingid",
table: "antispamignore");
migrationBuilder.DropForeignKey(
name: "fk_antispamsetting_guildconfigs_guildconfigid",
table: "antispamsetting");
migrationBuilder.DropForeignKey(
name: "fk_commandalias_guildconfigs_guildconfigid",
table: "commandalias");
migrationBuilder.DropForeignKey(
name: "fk_commandcooldown_guildconfigs_guildconfigid",
table: "commandcooldown");
migrationBuilder.DropForeignKey(
name: "fk_delmsgoncmdchannel_guildconfigs_guildconfigid",
table: "delmsgoncmdchannel");
migrationBuilder.DropForeignKey(
name: "fk_excludeditem_xpsettings_xpsettingsid",
table: "excludeditem");
migrationBuilder.DropForeignKey(
name: "fk_filterchannelid_guildconfigs_guildconfigid",
table: "filterchannelid");
migrationBuilder.DropForeignKey(
name: "fk_filteredword_guildconfigs_guildconfigid",
table: "filteredword");
migrationBuilder.DropForeignKey(
name: "fk_filterlinkschannelid_guildconfigs_guildconfigid",
table: "filterlinkschannelid");
migrationBuilder.DropForeignKey(
name: "fk_filterwordschannelid_guildconfigs_guildconfigid",
table: "filterwordschannelid");
migrationBuilder.DropForeignKey(
name: "fk_followedstream_guildconfigs_guildconfigid",
table: "followedstream");
migrationBuilder.DropForeignKey(
name: "fk_gcchannelid_guildconfigs_guildconfigid",
table: "gcchannelid");
migrationBuilder.DropForeignKey(
name: "fk_muteduserid_guildconfigs_guildconfigid",
table: "muteduserid");
migrationBuilder.DropForeignKey(
name: "fk_permissions_guildconfigs_guildconfigid",
table: "permissions");
migrationBuilder.DropForeignKey(
name: "fk_shopentry_guildconfigs_guildconfigid",
table: "shopentry");
migrationBuilder.DropForeignKey(
name: "fk_shopentryitem_shopentry_shopentryid",
table: "shopentryitem");
migrationBuilder.DropForeignKey(
name: "fk_slowmodeignoredrole_guildconfigs_guildconfigid",
table: "slowmodeignoredrole");
migrationBuilder.DropForeignKey(
name: "fk_slowmodeignoreduser_guildconfigs_guildconfigid",
table: "slowmodeignoreduser");
migrationBuilder.DropForeignKey(
name: "fk_streamroleblacklisteduser_streamrolesettings_streamrolesetti~",
table: "streamroleblacklisteduser");
migrationBuilder.DropForeignKey(
name: "fk_streamrolewhitelisteduser_streamrolesettings_streamrolesetti~",
table: "streamrolewhitelisteduser");
migrationBuilder.DropForeignKey(
name: "fk_unbantimer_guildconfigs_guildconfigid",
table: "unbantimer");
migrationBuilder.DropForeignKey(
name: "fk_unmutetimer_guildconfigs_guildconfigid",
table: "unmutetimer");
migrationBuilder.DropForeignKey(
name: "fk_unroletimer_guildconfigs_guildconfigid",
table: "unroletimer");
migrationBuilder.DropForeignKey(
name: "fk_vcroleinfo_guildconfigs_guildconfigid",
table: "vcroleinfo");
migrationBuilder.DropForeignKey(
name: "fk_warningpunishment_guildconfigs_guildconfigid",
table: "warningpunishment");
migrationBuilder.AlterColumn<int>(
name: "streamrolesettingsid",
table: "streamrolewhitelisteduser",
type: "int",
nullable: true,
oldClrType: typeof(int),
oldType: "int");
migrationBuilder.AlterColumn<int>(
name: "streamrolesettingsid",
table: "streamroleblacklisteduser",
type: "int",
nullable: true,
oldClrType: typeof(int),
oldType: "int");
migrationBuilder.AlterColumn<int>(
name: "guildconfigid",
table: "delmsgoncmdchannel",
type: "int",
nullable: true,
oldClrType: typeof(int),
oldType: "int");
migrationBuilder.CreateTable(
name: "ignoredvoicepresencechannels",
columns: table => new
{
id = table.Column<int>(type: "int", nullable: false)
.Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn),
logsettingid = table.Column<int>(type: "int", nullable: true),
channelid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
dateadded = table.Column<DateTime>(type: "datetime(6)", nullable: true)
},
constraints: table =>
{
table.PrimaryKey("pk_ignoredvoicepresencechannels", x => x.id);
table.ForeignKey(
name: "fk_ignoredvoicepresencechannels_logsettings_logsettingid",
column: x => x.logsettingid,
principalTable: "logsettings",
principalColumn: "id");
})
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.CreateIndex(
name: "ix_ignoredvoicepresencechannels_logsettingid",
table: "ignoredvoicepresencechannels",
column: "logsettingid");
migrationBuilder.AddForeignKey(
name: "fk_antiraidsetting_guildconfigs_guildconfigid",
table: "antiraidsetting",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_antispamignore_antispamsetting_antispamsettingid",
table: "antispamignore",
column: "antispamsettingid",
principalTable: "antispamsetting",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_antispamsetting_guildconfigs_guildconfigid",
table: "antispamsetting",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id",
onDelete: ReferentialAction.Cascade);
migrationBuilder.AddForeignKey(
name: "fk_commandalias_guildconfigs_guildconfigid",
table: "commandalias",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_commandcooldown_guildconfigs_guildconfigid",
table: "commandcooldown",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_delmsgoncmdchannel_guildconfigs_guildconfigid",
table: "delmsgoncmdchannel",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_excludeditem_xpsettings_xpsettingsid",
table: "excludeditem",
column: "xpsettingsid",
principalTable: "xpsettings",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_filterchannelid_guildconfigs_guildconfigid",
table: "filterchannelid",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_filteredword_guildconfigs_guildconfigid",
table: "filteredword",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_filterlinkschannelid_guildconfigs_guildconfigid",
table: "filterlinkschannelid",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_filterwordschannelid_guildconfigs_guildconfigid",
table: "filterwordschannelid",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_followedstream_guildconfigs_guildconfigid",
table: "followedstream",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_gcchannelid_guildconfigs_guildconfigid",
table: "gcchannelid",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_muteduserid_guildconfigs_guildconfigid",
table: "muteduserid",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_permissions_guildconfigs_guildconfigid",
table: "permissions",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_shopentry_guildconfigs_guildconfigid",
table: "shopentry",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_shopentryitem_shopentry_shopentryid",
table: "shopentryitem",
column: "shopentryid",
principalTable: "shopentry",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_slowmodeignoredrole_guildconfigs_guildconfigid",
table: "slowmodeignoredrole",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_slowmodeignoreduser_guildconfigs_guildconfigid",
table: "slowmodeignoreduser",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_streamroleblacklisteduser_streamrolesettings_streamrolesetti~",
table: "streamroleblacklisteduser",
column: "streamrolesettingsid",
principalTable: "streamrolesettings",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_streamrolewhitelisteduser_streamrolesettings_streamrolesetti~",
table: "streamrolewhitelisteduser",
column: "streamrolesettingsid",
principalTable: "streamrolesettings",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_unbantimer_guildconfigs_guildconfigid",
table: "unbantimer",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_unmutetimer_guildconfigs_guildconfigid",
table: "unmutetimer",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_unroletimer_guildconfigs_guildconfigid",
table: "unroletimer",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_vcroleinfo_guildconfigs_guildconfigid",
table: "vcroleinfo",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
migrationBuilder.AddForeignKey(
name: "fk_warningpunishment_guildconfigs_guildconfigid",
table: "warningpunishment",
column: "guildconfigid",
principalTable: "guildconfigs",
principalColumn: "id");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,44 +0,0 @@
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
/// <inheritdoc />
public partial class removepatronlimits : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "patronquotas");
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateTable(
name: "patronquotas",
columns: table => new
{
userid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
featuretype = table.Column<int>(type: "int", nullable: false),
feature = table.Column<string>(type: "varchar(255)", nullable: false)
.Annotation("MySql:CharSet", "utf8mb4"),
dailycount = table.Column<uint>(type: "int unsigned", nullable: false),
hourlycount = table.Column<uint>(type: "int unsigned", nullable: false),
monthlycount = table.Column<uint>(type: "int unsigned", nullable: false)
},
constraints: table =>
{
table.PrimaryKey("pk_patronquotas", x => new { x.userid, x.featuretype, x.feature });
})
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.CreateIndex(
name: "ix_patronquotas_userid",
table: "patronquotas",
column: "userid");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,36 +0,0 @@
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
/// <inheritdoc />
public partial class honeypot : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.CreateTable(
name: "honeypotchannels",
columns: table => new
{
guildid = table.Column<ulong>(type: "bigint unsigned", nullable: false)
.Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn),
channelid = table.Column<ulong>(type: "bigint unsigned", nullable: false)
},
constraints: table =>
{
table.PrimaryKey("pk_honeypotchannels", x => x.guildid);
})
.Annotation("MySql:CharSet", "utf8mb4");
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "honeypotchannels");
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -1,202 +0,0 @@
using Microsoft.EntityFrameworkCore.Metadata;
using Microsoft.EntityFrameworkCore.Migrations;
#nullable disable
namespace EllieBot.Migrations.Mysql
{
/// <inheritdoc />
public partial class greetsettings : Migration
{
/// <inheritdoc />
protected override void Up(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropColumn(
name: "autodeletebyemessagestimer",
table: "guildconfigs");
migrationBuilder.DropColumn(
name: "autodeletegreetmessagestimer",
table: "guildconfigs");
migrationBuilder.DropColumn(
name: "boostmessage",
table: "guildconfigs");
migrationBuilder.DropColumn(
name: "boostmessagechannelid",
table: "guildconfigs");
migrationBuilder.DropColumn(
name: "boostmessagedeleteafter",
table: "guildconfigs");
migrationBuilder.DropColumn(
name: "byemessagechannelid",
table: "guildconfigs");
migrationBuilder.DropColumn(
name: "channelbyemessagetext",
table: "guildconfigs");
migrationBuilder.DropColumn(
name: "channelgreetmessagetext",
table: "guildconfigs");
migrationBuilder.DropColumn(
name: "dmgreetmessagetext",
table: "guildconfigs");
migrationBuilder.DropColumn(
name: "greetmessagechannelid",
table: "guildconfigs");
migrationBuilder.DropColumn(
name: "sendboostmessage",
table: "guildconfigs");
migrationBuilder.DropColumn(
name: "sendchannelbyemessage",
table: "guildconfigs");
migrationBuilder.DropColumn(
name: "sendchannelgreetmessage",
table: "guildconfigs");
migrationBuilder.DropColumn(
name: "senddmgreetmessage",
table: "guildconfigs");
migrationBuilder.CreateTable(
name: "greetsettings",
columns: table => new
{
id = table.Column<int>(type: "int", nullable: false)
.Annotation("MySql:ValueGenerationStrategy", MySqlValueGenerationStrategy.IdentityColumn),
guildid = table.Column<ulong>(type: "bigint unsigned", nullable: false),
greettype = table.Column<int>(type: "int", nullable: false),
messagetext = table.Column<string>(type: "longtext", nullable: true)
.Annotation("MySql:CharSet", "utf8mb4"),
isenabled = table.Column<bool>(type: "tinyint(1)", nullable: false),
channelid = table.Column<ulong>(type: "bigint unsigned", nullable: true),
autodeletetimer = table.Column<int>(type: "int", nullable: false)
},
constraints: table =>
{
table.PrimaryKey("pk_greetsettings", x => x.id);
})
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.CreateIndex(
name: "ix_greetsettings_guildid_greettype",
table: "greetsettings",
columns: new[] { "guildid", "greettype" },
unique: true);
}
/// <inheritdoc />
protected override void Down(MigrationBuilder migrationBuilder)
{
migrationBuilder.DropTable(
name: "greetsettings");
migrationBuilder.AddColumn<int>(
name: "autodeletebyemessagestimer",
table: "guildconfigs",
type: "int",
nullable: false,
defaultValue: 0);
migrationBuilder.AddColumn<int>(
name: "autodeletegreetmessagestimer",
table: "guildconfigs",
type: "int",
nullable: false,
defaultValue: 0);
migrationBuilder.AddColumn<string>(
name: "boostmessage",
table: "guildconfigs",
type: "longtext",
nullable: true)
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.AddColumn<ulong>(
name: "boostmessagechannelid",
table: "guildconfigs",
type: "bigint unsigned",
nullable: false,
defaultValue: 0ul);
migrationBuilder.AddColumn<int>(
name: "boostmessagedeleteafter",
table: "guildconfigs",
type: "int",
nullable: false,
defaultValue: 0);
migrationBuilder.AddColumn<ulong>(
name: "byemessagechannelid",
table: "guildconfigs",
type: "bigint unsigned",
nullable: false,
defaultValue: 0ul);
migrationBuilder.AddColumn<string>(
name: "channelbyemessagetext",
table: "guildconfigs",
type: "longtext",
nullable: true)
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.AddColumn<string>(
name: "channelgreetmessagetext",
table: "guildconfigs",
type: "longtext",
nullable: true)
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.AddColumn<string>(
name: "dmgreetmessagetext",
table: "guildconfigs",
type: "longtext",
nullable: true)
.Annotation("MySql:CharSet", "utf8mb4");
migrationBuilder.AddColumn<ulong>(
name: "greetmessagechannelid",
table: "guildconfigs",
type: "bigint unsigned",
nullable: false,
defaultValue: 0ul);
migrationBuilder.AddColumn<bool>(
name: "sendboostmessage",
table: "guildconfigs",
type: "tinyint(1)",
nullable: false,
defaultValue: false);
migrationBuilder.AddColumn<bool>(
name: "sendchannelbyemessage",
table: "guildconfigs",
type: "tinyint(1)",
nullable: false,
defaultValue: false);
migrationBuilder.AddColumn<bool>(
name: "sendchannelgreetmessage",
table: "guildconfigs",
type: "tinyint(1)",
nullable: false,
defaultValue: false);
migrationBuilder.AddColumn<bool>(
name: "senddmgreetmessage",
table: "guildconfigs",
type: "tinyint(1)",
nullable: false,
defaultValue: false);
}
}
}

File diff suppressed because it is too large Load diff

View file

@ -5,6 +5,99 @@ public partial class Administration
[Group] [Group]
public partial class GreetCommands : EllieModule<GreetService> public partial class GreetCommands : EllieModule<GreetService>
{ {
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task Boost()
=> Toggle(GreetType.Boost);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task BoostDel(int timer = 30)
=> SetDel(GreetType.Boost, timer);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task BoostMsg([Leftover] string? text = null)
=> SetMsg(GreetType.Boost, text);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task Greet()
=> Toggle(GreetType.Greet);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task GreetDel(int timer = 30)
=> SetDel(GreetType.Greet, timer);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task GreetMsg([Leftover] string? text = null)
=> SetMsg(GreetType.Greet, text);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task GreetDm()
=> Toggle(GreetType.GreetDm);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task GreetDmMsg([Leftover] string? text = null)
=> SetMsg(GreetType.GreetDm, text);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task Bye()
=> Toggle(GreetType.Bye);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task ByeDel(int timer = 30)
=> SetDel(GreetType.Bye, timer);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task ByeMsg([Leftover] string? text = null)
=> SetMsg(GreetType.Bye, text);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task GreetTest([Leftover] IGuildUser? user = null)
=> Test(GreetType.Greet, user);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task GreetDmTest([Leftover] IGuildUser? user = null)
=> Test(GreetType.GreetDm, user);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
[Ratelimit(5)]
public Task ByeTest([Leftover] IGuildUser? user = null)
=> Test(GreetType.Bye, user);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
[Ratelimit(5)]
public Task BoostTest([Leftover] IGuildUser? user = null)
=> Test(GreetType.Boost, user);
public async Task Toggle(GreetType type) public async Task Toggle(GreetType type)
{ {
var enabled = await _service.SetGreet(ctx.Guild.Id, ctx.Channel.Id, type); var enabled = await _service.SetGreet(ctx.Guild.Id, ctx.Channel.Id, type);
@ -75,17 +168,16 @@ public partial class Administration
{ {
if (string.IsNullOrWhiteSpace(text)) if (string.IsNullOrWhiteSpace(text))
{ {
await _service.SetMessage(ctx.Guild.Id, type, null);
var conf = await _service.GetGreetSettingsAsync(ctx.Guild.Id, type); var conf = await _service.GetGreetSettingsAsync(ctx.Guild.Id, type);
var msg = conf?.MessageText ?? "No message set."; var msg = conf?.MessageText ?? GreetService.GetDefaultGreet(type);
await Response() await Response()
.Confirm( .Confirm(
type switch type switch
{ {
GreetType.Boost => strs.boostmsg_cur(msg.SanitizeMentions()), GreetType.Boost => strs.boostmsg_cur(msg),
GreetType.Greet => strs.greetmsg_cur(msg.SanitizeMentions()), GreetType.Greet => strs.greetmsg_cur(msg),
GreetType.Bye => strs.byemsg_cur(msg.SanitizeMentions()), GreetType.Bye => strs.byemsg_cur(msg),
GreetType.GreetDm => strs.greetdmmsg_cur(msg.SanitizeMentions()), GreetType.GreetDm => strs.greetdmmsg_cur(msg),
_ => strs.error _ => strs.error
}) })
.SendAsync(); .SendAsync();
@ -121,100 +213,6 @@ public partial class Administration
} }
} }
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task Boost()
=> Toggle(GreetType.Boost);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task BoostDel(int timer = 30)
=> SetDel(GreetType.Boost, timer);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task BoostMsg([Leftover] string? text = null)
=> SetMsg(GreetType.Boost, text);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task Greet()
=> Toggle(GreetType.Greet);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task GreetDel(int timer = 30)
=> SetDel(GreetType.Greet, timer);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task GreetMsg([Leftover] string? text = null)
=> SetMsg(GreetType.Greet, text);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task GreetDm()
=> Toggle(GreetType.GreetDm);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task GreetDmMsg([Leftover] string? text = null)
=> SetMsg(GreetType.GreetDm, text);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task Bye()
=> Toggle(GreetType.Bye);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task ByeDel(int timer = 30)
=> SetDel(GreetType.Bye, timer);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
public Task ByeMsg([Leftover] string? text = null)
=> SetMsg(GreetType.Bye, text);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
[Ratelimit(5)]
public Task GreetTest([Leftover] IGuildUser? user = null)
=> Test(GreetType.Greet, user);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
[Ratelimit(5)]
public Task GreetDmTest([Leftover] IGuildUser? user = null)
=> Test(GreetType.GreetDm, user);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
[Ratelimit(5)]
public Task ByeTest([Leftover] IGuildUser? user = null)
=> Test(GreetType.Bye, user);
[Cmd]
[RequireContext(ContextType.Guild)]
[UserPerm(GuildPerm.ManageGuild)]
[Ratelimit(5)]
public Task BoostTest([Leftover] IGuildUser? user = null)
=> Test(GreetType.Boost, user);
public async Task Test(GreetType type, IGuildUser? user = null) public async Task Test(GreetType type, IGuildUser? user = null)
{ {
user ??= (IGuildUser)ctx.User; user ??= (IGuildUser)ctx.User;

View file

@ -14,7 +14,6 @@ public class GreetService : IEService, IReadyExecutor
private readonly DiscordSocketClient _client; private readonly DiscordSocketClient _client;
private readonly BotConfigService _bss;
private readonly IReplacementService _repSvc; private readonly IReplacementService _repSvc;
private readonly IBotCache _cache; private readonly IBotCache _cache;
private readonly IMessageSenderService _sender; private readonly IMessageSenderService _sender;
@ -29,7 +28,6 @@ public class GreetService : IEService, IReadyExecutor
public GreetService( public GreetService(
DiscordSocketClient client, DiscordSocketClient client,
DbService db, DbService db,
BotConfigService bss,
IMessageSenderService sender, IMessageSenderService sender,
IReplacementService repSvc, IReplacementService repSvc,
IBotCache cache IBotCache cache
@ -37,10 +35,15 @@ public class GreetService : IEService, IReadyExecutor
{ {
_db = db; _db = db;
_client = client; _client = client;
_bss = bss;
_repSvc = repSvc; _repSvc = repSvc;
_cache = cache; _cache = cache;
_sender = sender; _sender = sender;
foreach (var type in Enum.GetValues<GreetType>())
{
_enabled[type] = new();
}
} }
public async Task OnReadyAsync() public async Task OnReadyAsync()
@ -52,11 +55,17 @@ public class GreetService : IEService, IReadyExecutor
var enabled = await uow.GetTable<GreetSettings>() var enabled = await uow.GetTable<GreetSettings>()
.Where(x => x.GuildId.In(guilds)) .Where(x => x.GuildId.In(guilds))
.Where(x => x.IsEnabled) .Where(x => x.IsEnabled)
.Select(x => new
{
x.GuildId,
x.GreetType
})
.ToListAsync(); .ToListAsync();
_enabled = enabled.GroupBy(x => x.GreetType, v => v.GuildId) foreach (var e in enabled)
.ToDictionary(x => x.Key, x => x.ToHashSet().ToConcurrentSet()) {
.ToConcurrent(); _enabled[e.GreetType].Add(e.GuildId);
}
} }
_client.UserJoined += OnUserJoined; _client.UserJoined += OnUserJoined;
@ -146,7 +155,7 @@ public class GreetService : IEService, IReadyExecutor
return Task.CompletedTask; return Task.CompletedTask;
} }
private readonly TypedKey<GreetSettings?> _greetSettingsKey = new(); private readonly TypedKey<GreetSettings?> _greetSettingsKey = new("greet_settings");
public async Task<GreetSettings?> GetGreetSettingsAsync(ulong gid, GreetType type) public async Task<GreetSettings?> GetGreetSettingsAsync(ulong gid, GreetType type)
=> await _cache.GetOrAddAsync<GreetSettings?>(_greetSettingsKey, => await _cache.GetOrAddAsync<GreetSettings?>(_greetSettingsKey,
@ -160,6 +169,9 @@ public class GreetService : IEService, IReadyExecutor
.Where(x => x.GuildId == gid && x.GreetType == type) .Where(x => x.GuildId == gid && x.GreetType == type)
.FirstOrDefaultAsync(); .FirstOrDefaultAsync();
if (res is not null)
res.MessageText ??= GetDefaultGreet(type);
return res; return res;
} }
@ -324,12 +336,12 @@ public class GreetService : IEService, IReadyExecutor
} }
private static string GetDefaultGreet(GreetType greetType) public static string GetDefaultGreet(GreetType greetType)
=> greetType switch => greetType switch
{ {
GreetType.Boost => "%user.name% has boosted the server!", GreetType.Boost => "%user.mention% has boosted the server!",
GreetType.Greet => "%user.name% has joined the server!", GreetType.Greet => "%user.mention% has joined the server!",
GreetType.Bye => "%user.name has left the server!", GreetType.Bye => "%user.name% has left the server!",
GreetType.GreetDm => "Welcome to the server %user.name%", GreetType.GreetDm => "Welcome to the server %user.name%",
_ => "%user.name% did something new!" _ => "%user.name% did something new!"
}; };
@ -343,16 +355,16 @@ public class GreetService : IEService, IReadyExecutor
await using var uow = _db.GetDbContext(); await using var uow = _db.GetDbContext();
var q = uow.GetTable<GreetSettings>(); var q = uow.GetTable<GreetSettings>();
if (value is null)
value = !_enabled[greetType].Contains(guildId);
if (value is { } v) if (value is { } v)
{ {
var defaultGreet = GetDefaultGreet(greetType);
await q await q
.InsertOrUpdateAsync(() => new() .InsertOrUpdateAsync(() => new()
{ {
GuildId = guildId, GuildId = guildId,
GreetType = greetType, GreetType = greetType,
MessageText = defaultGreet,
IsEnabled = v, IsEnabled = v,
ChannelId = channelId, ChannelId = channelId,
}, },
@ -367,40 +379,20 @@ public class GreetService : IEService, IReadyExecutor
GreetType = greetType, GreetType = greetType,
}); });
} }
else
{
var result = await q
.Where(x => x.GuildId == guildId && x.GreetType == greetType)
.UpdateWithOutputAsync((old) => new()
{
IsEnabled = !old.IsEnabled
},
(o, n) => n.IsEnabled);
if (result.Length > 0)
value = result[0];
}
if (value is true) if (value is true)
{ {
_enabled[greetType].Add(guildId); _enabled[greetType].Add(guildId);
} return true;
else
{
_enabled[greetType].TryRemove(guildId);
} }
return true; _enabled[greetType].TryRemove(guildId);
return false;
} }
public async Task<bool> SetMessage(ulong guildId, GreetType greetType, string? message) public async Task<bool> SetMessage(ulong guildId, GreetType greetType, string? message)
{ {
message = message?.SanitizeMentions();
if (string.IsNullOrWhiteSpace(message))
message = GetDefaultGreet(greetType);
await using (var uow = _db.GetDbContext()) await using (var uow = _db.GetDbContext())
{ {
await uow.GetTable<GreetSettings>() await uow.GetTable<GreetSettings>()
@ -475,6 +467,7 @@ public class GreetService : IEService, IReadyExecutor
{ {
if (conf.GreetType == GreetType.GreetDm) if (conf.GreetType == GreetType.GreetDm)
{ {
await _greetQueue.Writer.WriteAsync((conf, user, channel as ITextChannel));
return await GreetDmUser(conf, user); return await GreetDmUser(conf, user);
} }

View file

@ -20,9 +20,14 @@ public partial class Administration
[Cmd] [Cmd]
[OwnerOnly] [OwnerOnly]
public async Task AddPlaying(ActivityType t, [Leftover] string status) public Task AddPlaying([Leftover] string status)
=> AddPlaying(ActivityType.CustomStatus, status);
[Cmd]
[OwnerOnly]
public async Task AddPlaying(ActivityType statusType, [Leftover] string status)
{ {
await _service.AddPlaying(t, status); await _service.AddPlaying(statusType, status);
await Response().Confirm(strs.ropl_added).SendAsync(); await Response().Confirm(strs.ropl_added).SendAsync();
} }

View file

@ -57,14 +57,14 @@ public partial class EllieExpressions : EllieModule<EllieExpressionsService>
[Cmd] [Cmd]
[UserPerm(GuildPerm.Administrator)] [UserPerm(GuildPerm.Administrator)]
public async Task ExprAddServer(string key, [Leftover] string message) public async Task ExprAddServer(string trigger, [Leftover] string response)
{ {
if (string.IsNullOrWhiteSpace(message) || string.IsNullOrWhiteSpace(key)) if (string.IsNullOrWhiteSpace(response) || string.IsNullOrWhiteSpace(trigger))
{ {
return; return;
} }
await ExprAddInternalAsync(key, message); await ExprAddInternalAsync(trigger, response);
} }

View file

@ -175,8 +175,6 @@ public sealed partial class Help : EllieModule<HelpService>
return strs.module_description_gambling; return strs.module_description_gambling;
case "music": case "music":
return strs.module_description_music; return strs.module_description_music;
case "nsfw":
return strs.module_description_nsfw;
case "permissions": case "permissions":
return strs.module_description_permissions; return strs.module_description_permissions;
case "xp": case "xp":
@ -211,8 +209,6 @@ public sealed partial class Help : EllieModule<HelpService>
return "💰"; return "💰";
case "music": case "music":
return "🎶"; return "🎶";
case "nsfw":
return "😳";
case "permissions": case "permissions":
return "🚓"; return "🚓";
case "xp": case "xp":

View file

@ -72,7 +72,7 @@ public partial class Searches
} }
[Cmd] [Cmd]
public async Task Image([Leftover] string? query = null) public async Task Image([Leftover] string? query)
{ {
query = query?.Trim(); query = query?.Trim();

View file

@ -12,7 +12,7 @@ namespace EllieBot.Common.Configs;
public sealed partial class BotConfig : ICloneable<BotConfig> public sealed partial class BotConfig : ICloneable<BotConfig>
{ {
[Comment("""DO NOT CHANGE""")] [Comment("""DO NOT CHANGE""")]
public int Version { get; set; } = 7; public int Version { get; set; } = 8;
[Comment(""" [Comment("""
Most commands, when executed, have a small colored line Most commands, when executed, have a small colored line

View file

@ -61,6 +61,18 @@ public sealed partial class ReplacementPatternStore
private void WithUsers() private void WithUsers()
{ {
Register("%user%", static (IUser user) => user.Mention);
Register("%user.mention%", static (IUser user) => user.Mention);
Register("%user.fullname%", static (IUser user) => user.ToString()!);
Register("%user.name%", static (IUser user) => user.Username);
Register("%user.discrim%", static (IUser user) => user.Discriminator);
Register("%user.avatar%", static (IUser user) => user.RealAvatarUrl().ToString());
Register("%user.id%", static (IUser user) => user.Id.ToString());
Register("%user.created_time%", static (IUser user) => user.CreatedAt.ToString("HH:mm"));
Register("%user.created_date%", static (IUser user) => user.CreatedAt.ToString("dd.MM.yyyy"));
Register("%user.joined_time%", static (IGuildUser user) => user.JoinedAt?.ToString("HH:mm"));
Register("%user.joined_date%", static (IGuildUser user) => user.JoinedAt?.ToString("dd.MM.yyyy"));
Register("%user%", Register("%user%",
static (IUser[] users) => string.Join(" ", users.Select(user => user.Mention))); static (IUser[] users) => string.Join(" ", users.Select(user => user.Mention)));
Register("%user.mention%", Register("%user.mention%",

View file

@ -9,8 +9,8 @@ public sealed partial class Replacer
private readonly IEnumerable<RegexReplacementInfo> _regexReps; private readonly IEnumerable<RegexReplacementInfo> _regexReps;
private readonly object[] _inputData; private readonly object[] _inputData;
[GeneratedRegex(@"\%[\p{L}\p{N}\._]*[\p{L}\p{N}]+[\p{L}\p{N}\._]*\%")] // [GeneratedRegex(@"\%[\p{L}\p{N}\._]*[\p{L}\p{N}]+[\p{L}\p{N}\._]*\%")]
private static partial Regex TokenExtractionRegex(); // private static partial Regex TokenExtractionRegex();
public Replacer(IEnumerable<ReplacementInfo> reps, IEnumerable<RegexReplacementInfo> regexReps, object[] inputData) public Replacer(IEnumerable<ReplacementInfo> reps, IEnumerable<RegexReplacementInfo> regexReps, object[] inputData)
{ {
@ -24,10 +24,10 @@ public sealed partial class Replacer
if (string.IsNullOrWhiteSpace(input)) if (string.IsNullOrWhiteSpace(input))
return input; return input;
var matches = TokenExtractionRegex().IsMatch(input); // var matches = TokenExtractionRegex().IsMatch(input);
if (matches) // if (matches)
{ // {
foreach (var rep in _reps) foreach (var rep in _reps)
{ {
if (input.Contains(rep.Token, StringComparison.InvariantCulture)) if (input.Contains(rep.Token, StringComparison.InvariantCulture))
@ -36,7 +36,7 @@ public sealed partial class Replacer
input = input.Replace(rep.Token, await rep.GetValueAsync(objs), StringComparison.InvariantCulture); input = input.Replace(rep.Token, await rep.GetValueAsync(objs), StringComparison.InvariantCulture);
} }
} }
} // }
foreach (var rep in _regexReps) foreach (var rep in _regexReps)
{ {
@ -93,14 +93,16 @@ public sealed partial class Replacer
Embeds = await embedArr.Embeds.Map(async e => await ReplaceAsync(e) with Embeds = await embedArr.Embeds.Map(async e => await ReplaceAsync(e) with
{ {
Color = e.Color Color = e.Color
}).WhenAll(), })
.WhenAll(),
Content = await ReplaceAsync(embedArr.Content) Content = await ReplaceAsync(embedArr.Content)
}; };
private async ValueTask<SmartPlainText> ReplaceAsync(SmartPlainText plain) private async ValueTask<SmartPlainText> ReplaceAsync(SmartPlainText plain)
=> await ReplaceAsync(plain.Text); => await ReplaceAsync(plain.Text);
private async Task<T> ReplaceAsync<T>(T embedData) where T : SmartEmbedTextBase, new() private async Task<T> ReplaceAsync<T>(T embedData)
where T : SmartEmbedTextBase, new()
{ {
var newEmbedData = new T var newEmbedData = new T
{ {
@ -123,7 +125,8 @@ public sealed partial class Replacer
Name = await ReplaceAsync(f.Name), Name = await ReplaceAsync(f.Name),
Value = await ReplaceAsync(f.Value), Value = await ReplaceAsync(f.Value),
Inline = f.Inline Inline = f.Inline
}) ?? []), })
?? []),
Footer = embedData.Footer is null Footer = embedData.Footer is null
? null ? null
: new() : new()

View file

@ -69,5 +69,11 @@ public sealed class BotConfigService : ConfigServiceBase<BotConfig>
c.Version = 7; c.Version = 7;
c.IgnoreOtherBots = true; c.IgnoreOtherBots = true;
}); });
if (data.Version < 8)
ModifyConfig(c =>
{
c.Version = 8;
});
} }
} }

View file

@ -80,7 +80,6 @@ db:
# Database connection string. # Database connection string.
# You MUST change this if you're not using "sqlite" type. # You MUST change this if you're not using "sqlite" type.
# Default is "Data Source=data/EllieBot.db" # Default is "Data Source=data/EllieBot.db"
# Example for mysql: "Server=localhost;Port=3306;Uid=root;Pwd=my_super_secret_mysql_password;Database=ellie"
# Example for postgresql: "Server=localhost;Port=5432;User Id=postgres;Password=my_super_secret_postgres_password;Database=ellie;" # Example for postgresql: "Server=localhost;Port=5432;User Id=postgres;Password=my_super_secret_postgres_password;Database=ellie;"
connectionString: Data Source=data/EllieBot.db connectionString: Data Source=data/EllieBot.db
# Address and port of the coordinator endpoint. Leave empty for default. # Address and port of the coordinator endpoint. Leave empty for default.

View file

@ -1,5 +1,5 @@
# DO NOT CHANGE # DO NOT CHANGE
version: 7 version: 8
# Most commands, when executed, have a small colored line # Most commands, when executed, have a small colored line
# next to the response. The color depends whether the command # next to the response. The color depends whether the command
# is completed, errored or in progress (pending) # is completed, errored or in progress (pending)
@ -80,16 +80,6 @@ blocked:
modules: [] modules: []
# Which string will be used to recognize the commands # Which string will be used to recognize the commands
prefix: . prefix: .
# Toggles whether your bot will group greet/bye messages into a single message every 5 seconds.
# 1st user who joins will get greeted immediately
# If more users join within the next 5 seconds, they will be greeted in groups of 5.
# This will cause %user.mention% and other placeholders to be replaced with multiple users.
# Keep in mind this might break some of your embeds - for example if you have %user.avatar% in the thumbnail,
# it will become invalid, as it will resolve to a list of avatars of grouped users.
# note: This setting is primarily used if you're afraid of raids, or you're running medium/large bots where some
# servers might get hundreds of people join at once. This is used to prevent the bot from getting ratelimited,
# and (slightly) reduce the greet spam in those servers.
groupGreets: false
# Whether the bot will rotate through all specified statuses. # Whether the bot will rotate through all specified statuses.
# This setting can be changed via .ropl command. # This setting can be changed via .ropl command.
# See RotatingStatuses submodule in Administration. # See RotatingStatuses submodule in Administration.

View file

@ -140,13 +140,13 @@
imageUrl: https://cdn.nadeko.bot/flags/gt-flag.gif imageUrl: https://cdn.nadeko.bot/flags/gt-flag.gif
- word: Guinea - word: Guinea
imageUrl: https://cdn.nadeko.bot/flags/gv-flag.gif imageUrl: https://cdn.nadeko.bot/flags/gv-flag.gif
- word: Guinea-Bissau - word: Guinea Bissau
imageUrl: https://cdn.nadeko.bot/flags/pu-flag.gif imageUrl: https://cdn.nadeko.bot/flags/pu-flag.gif
- word: Guyana - word: Guyana
imageUrl: https://cdn.nadeko.bot/flags/gy-flag.gif imageUrl: https://cdn.nadeko.bot/flags/gy-flag.gif
- word: Haiti - word: Haiti
imageUrl: https://cdn.nadeko.bot/flags/ha-flag.gif imageUrl: https://cdn.nadeko.bot/flags/ha-flag.gif
- word: Holy See - word: Vatican
imageUrl: https://cdn.nadeko.bot/flags/vt-flag.gif imageUrl: https://cdn.nadeko.bot/flags/vt-flag.gif
- word: Honduras - word: Honduras
imageUrl: https://cdn.nadeko.bot/flags/ho-flag.gif imageUrl: https://cdn.nadeko.bot/flags/ho-flag.gif
@ -184,7 +184,7 @@
imageUrl: https://cdn.nadeko.bot/flags/ku-flag.gif imageUrl: https://cdn.nadeko.bot/flags/ku-flag.gif
- word: Kyrgyzstan - word: Kyrgyzstan
imageUrl: https://cdn.nadeko.bot/flags/kg-flag.gif imageUrl: https://cdn.nadeko.bot/flags/kg-flag.gif
- word: Laos - word: Lao People's Democratic Republic
imageUrl: https://cdn.nadeko.bot/flags/la-flag.gif imageUrl: https://cdn.nadeko.bot/flags/la-flag.gif
- word: Latvia - word: Latvia
imageUrl: https://cdn.nadeko.bot/flags/lg-flag.gif imageUrl: https://cdn.nadeko.bot/flags/lg-flag.gif
@ -282,7 +282,7 @@
imageUrl: https://cdn.nadeko.bot/flags/qa-flag.gif imageUrl: https://cdn.nadeko.bot/flags/qa-flag.gif
- word: Romania - word: Romania
imageUrl: https://cdn.nadeko.bot/flags/ro-flag.gif imageUrl: https://cdn.nadeko.bot/flags/ro-flag.gif
- word: Russia - word: Russian Federation
imageUrl: https://cdn.nadeko.bot/flags/rs-flag.gif imageUrl: https://cdn.nadeko.bot/flags/rs-flag.gif
- word: Rwanda - word: Rwanda
imageUrl: https://cdn.nadeko.bot/flags/rw-flag.gif imageUrl: https://cdn.nadeko.bot/flags/rw-flag.gif
@ -318,7 +318,7 @@
imageUrl: https://cdn.nadeko.bot/flags/so-flag.gif imageUrl: https://cdn.nadeko.bot/flags/so-flag.gif
- word: South Africa - word: South Africa
imageUrl: https://cdn.nadeko.bot/flags/sf-flag.gif imageUrl: https://cdn.nadeko.bot/flags/sf-flag.gif
- word: South Korea - word: Republic of Korea
imageUrl: https://cdn.nadeko.bot/flags/ks-flag.gif imageUrl: https://cdn.nadeko.bot/flags/ks-flag.gif
- word: South Sudan - word: South Sudan
imageUrl: https://cdn.nadeko.bot/flags/od-flag.gif imageUrl: https://cdn.nadeko.bot/flags/od-flag.gif
@ -326,9 +326,9 @@
imageUrl: https://cdn.nadeko.bot/flags/sp-flag.gif imageUrl: https://cdn.nadeko.bot/flags/sp-flag.gif
- word: Sri Lanka - word: Sri Lanka
imageUrl: https://cdn.nadeko.bot/flags/ce-flag.gif imageUrl: https://cdn.nadeko.bot/flags/ce-flag.gif
- word: St. Vincent Grenadines - word: Saint Vincent and the Grenadines
imageUrl: https://cdn.nadeko.bot/flags/vc-flag.gif imageUrl: https://cdn.nadeko.bot/flags/vc-flag.gif
- word: State of Palestine - word: Palestine
imageUrl: https://cdn.nadeko.bot/flags/palestine-flag.gif imageUrl: https://cdn.nadeko.bot/flags/palestine-flag.gif
- word: Sudan - word: Sudan
imageUrl: https://cdn.nadeko.bot/flags/su-flag.gif imageUrl: https://cdn.nadeko.bot/flags/su-flag.gif
@ -338,11 +338,11 @@
imageUrl: https://cdn.nadeko.bot/flags/sw-flag.gif imageUrl: https://cdn.nadeko.bot/flags/sw-flag.gif
- word: Switzerland - word: Switzerland
imageUrl: https://cdn.nadeko.bot/flags/sz-flag.gif imageUrl: https://cdn.nadeko.bot/flags/sz-flag.gif
- word: Syria - word: Syrian Arab Republic
imageUrl: https://cdn.nadeko.bot/flags/sy-flag.gif imageUrl: https://cdn.nadeko.bot/flags/sy-flag.gif
- word: Tajikistan - word: Tajikistan
imageUrl: https://cdn.nadeko.bot/flags/ti-flag.gif imageUrl: https://cdn.nadeko.bot/flags/ti-flag.gif
- word: Tanzania - word: United Republic of Tanzania
imageUrl: https://cdn.nadeko.bot/flags/tz-flag.gif imageUrl: https://cdn.nadeko.bot/flags/tz-flag.gif
- word: Thailand - word: Thailand
imageUrl: https://cdn.nadeko.bot/flags/th-flag.gif imageUrl: https://cdn.nadeko.bot/flags/th-flag.gif
@ -380,7 +380,7 @@
imageUrl: https://cdn.nadeko.bot/flags/nh-flag.gif imageUrl: https://cdn.nadeko.bot/flags/nh-flag.gif
- word: Venezuela - word: Venezuela
imageUrl: https://cdn.nadeko.bot/flags/ve-flag.gif imageUrl: https://cdn.nadeko.bot/flags/ve-flag.gif
- word: Vietnam - word: Viet Nam
imageUrl: https://cdn.nadeko.bot/flags/vm-flag.gif imageUrl: https://cdn.nadeko.bot/flags/vm-flag.gif
- word: Yemen - word: Yemen
imageUrl: https://cdn.nadeko.bot/flags/ym-flag.gif imageUrl: https://cdn.nadeko.bot/flags/ym-flag.gif

View file

@ -175,9 +175,9 @@ logignore:
params: params:
- { } - { }
- target: - target:
desc: "The channel to ignore or show the list of ignored channels for." desc: "The channel to ignore."
- target: - target:
desc: "The user or channel being targeted for logging ignore or inclusion." desc: "The user to ignore."
repeatlist: repeatlist:
desc: Lists currently repeating messages and their indexes. desc: Lists currently repeating messages and their indexes.
ex: ex:
@ -283,10 +283,12 @@ addplaying:
- Playing with you - Playing with you
- Watching you sleep - Watching you sleep
params: params:
- t: - statusType:
desc: "The type of status, allowed values are `Playing`, `Watching`, or `Listening`." desc: "The type of status, allowed values are `Playing`, `Watching`, or `Listening`."
status: status:
desc: "The status text." desc: "The status text."
- status:
desc: "The status text."
listplaying: listplaying:
desc: Lists all playing statuses and their indexes. desc: Lists all playing statuses and their indexes.
ex: ex:
@ -387,18 +389,18 @@ expradd:
- '"hello" Hi there %user.mention%' - '"hello" Hi there %user.mention%'
params: params:
- trigger: - trigger:
desc: "The trigger word or phrase for the bot to respond to users typing." desc: "The trigger word or phrase (phrase must be in quotes)."
response: response:
desc: "The text of the message that shows up when a user types the trigger word." desc: "The text of the message that shows up when a user types the trigger word or phrase."
expraddserver: expraddserver:
desc: 'Add an expression with a trigger and a response in this server. Bot will post a response whenever someone types the trigger word. This command is useful if you want to lower the permission requirement for managing expressions by using `{0}dpo`. Guide [here](<https://docs.elliebot.net/ellie/features/expressions/>).' desc: 'Add an expression with a trigger and a response in this server. Bot will post a response whenever someone types the trigger word. This command is useful if you want to lower the permission requirement for managing expressions by using `{0}dpo`. Guide [here](<https://docs.elliebot.net/ellie/features/expressions/>).'
ex: ex:
- '"hello" Hi there %user.mention%' - '"hello" Hi there %user.mention%'
params: params:
- key: - trigger:
desc: "The trigger word or phrase for the bot to respond to users typing." desc: "The trigger word or phrase (phrase must be in quotes)."
message: response:
desc: "The text of the message that shows up when a user types the trigger word." desc: "The text of the message that shows up when a user types the trigger word or phrase."
exprlist: exprlist:
desc: |- desc: |-
Lists global or server expressions (20 expressions per page). Lists global or server expressions (20 expressions per page).
@ -496,21 +498,21 @@ delmsgoncmd:
- list - list
params: params:
- _: - _:
desc: "The list of channels or servers where the automatic deletion is enabled, disabled, or inherited." desc: "The word 'list'"
- _: - _:
desc: "The server where the command is being executed or monitored for chat flood prevention." desc: "The word 'server'"
- _: - _:
desc: "The channel where the automatic deletion of successful command messages should be toggled." desc: "The word 'channel'"
s: s:
desc: "The state of whether automatic deletion is enabled or disabled for a specific channel." desc: "The state to set. One of 'enable', 'disable', or 'inherit'."
ch: ch:
desc: "The channel where the automatic deletion of successful command messages should be toggled for." desc: "Channel in which to set"
- _: - _:
desc: "The channel where the automatic deletion of successful command messages should be toggled." desc: "The word 'channel'"
s: s:
desc: "The state of whether automatic deletion is enabled or disabled for a specific channel." desc: "The state to set. One of 'enable', 'disable', or 'inherit'."
chId: chId:
desc: "The ID of a channel where the automatic deletion should be toggled or inherited." desc: "Optional channel id. If omitted, defaults to the current channel."
restart: restart:
desc: Restarts the bot. Might not work. desc: Restarts the bot. Might not work.
ex: ex:
@ -1623,7 +1625,7 @@ gencurlist:
- page: - page:
desc: "The current page number for pagination." desc: "The current page number for pagination."
choose: choose:
desc: Chooses a thing from a list of things. Seperate items with a semicolon ; desc: Chooses a thing from a list of things. Separate items with a semicolon ;
ex: ex:
- Get up;Sleep;Sleep more - Get up;Sleep;Sleep more
params: params:
@ -3341,7 +3343,7 @@ globalcommand:
globalmodule: globalmodule:
desc: Toggles whether a module can be used on any server. desc: Toggles whether a module can be used on any server.
ex: ex:
- nsfw - 'Gambling'
params: params:
- module: - module:
desc: "The type of module or configuration information being toggled." desc: "The type of module or configuration information being toggled."
@ -4564,3 +4566,5 @@ leaveunkeptservers:
params: params:
- shardId: - shardId:
desc: "Shard id from which to start leaving unkept servers." desc: "Shard id from which to start leaving unkept servers."
- delay:
desc: "Delay in miliseconds between leaves"

View file

@ -991,7 +991,6 @@
"module_description_help": "Get command help, descriptions and usage examples", "module_description_help": "Get command help, descriptions and usage examples",
"module_description_gambling": "Bet on dice rolls, blackjack, slots, coinflips and others", "module_description_gambling": "Bet on dice rolls, blackjack, slots, coinflips and others",
"module_description_games": "Play trivia, nunchi, hangman, connect4 and other games", "module_description_games": "Play trivia, nunchi, hangman, connect4 and other games",
"module_description_nsfw": "NSFW commands.",
"module_description_music": "Play music from youtube, local files and radio streams", "module_description_music": "Play music from youtube, local files and radio streams",
"module_description_utility": "Manage custom quotes, repeating messages and check facts about the server", "module_description_utility": "Manage custom quotes, repeating messages and check facts about the server",
"module_description_administration": "Moderation, punish users, setup self assignable roles and greet messages", "module_description_administration": "Moderation, punish users, setup self assignable roles and greet messages",