2018-02-14 12:06:26 -06:00
using System.Linq ;
using System.Threading ;
using Microsoft.EntityFrameworkCore ;
2018-02-10 06:05:13 -06:00
2018-02-14 12:06:26 -06:00
using log4net ;
using Microsoft.EntityFrameworkCore.Infrastructure ;
using Microsoft.EntityFrameworkCore.Storage ;
using ACE.Database.Models.Auth ;
2017-02-19 02:30:22 -05:00
using ACE.Entity.Enum ;
2019-03-31 04:52:09 -05:00
using System.Collections.Generic ;
using System ;
2019-07-06 16:12:24 -05:00
using System.Net ;
2017-02-16 19:54:23 -06:00
2017-02-07 00:34:00 -05:00
namespace ACE.Database
{
2018-02-14 12:06:26 -06:00
public class AuthenticationDatabase
2017-02-07 00:34:00 -05:00
{
2018-02-14 12:06:26 -06:00
private static readonly ILog log = LogManager . GetLogger ( System . Reflection . MethodBase . GetCurrentMethod ( ) . DeclaringType ) ;
public bool Exists ( bool retryUntilFound )
2017-02-07 00:34:00 -05:00
{
2018-02-14 12:06:26 -06:00
var config = Common . ConfigManager . Config . MySql . Authentication ;
2017-02-07 00:34:00 -05:00
2018-02-14 12:06:26 -06:00
for ( ; ; )
{
using ( var context = new AuthDbContext ( ) )
{
if ( ( ( RelationalDatabaseCreator ) context . Database . GetService < IDatabaseCreator > ( ) ) . Exists ( ) )
{
2025-08-23 13:32:35 -04:00
log . InfoFormat ( "[DATABASE] Successfully connected to {0} database on {1}:{2}." , config . Database , config . Host , config . Port ) ;
2018-02-14 12:06:26 -06:00
return true ;
}
}
2017-02-07 00:34:00 -05:00
2025-08-23 13:32:35 -04:00
log . Error ( $"[DATABASE] Attempting to reconnect to {config.Database} database on {config.Host}:{config.Port} in 5 seconds..." ) ;
2018-01-28 06:46:15 -06:00
2018-02-14 12:06:26 -06:00
if ( retryUntilFound )
Thread . Sleep ( 5000 ) ;
else
return false ;
}
2017-02-07 00:34:00 -05:00
}
2018-02-14 12:06:26 -06:00
2018-12-02 13:41:16 -06:00
public int GetAccountCount ( )
{
using ( var context = new AuthDbContext ( ) )
return context . Account . Count ( ) ;
}
2018-02-14 12:06:26 -06:00
/// <exception cref="MySqlException">Account with name already exists.</exception>
2019-07-06 16:12:24 -05:00
public Account CreateAccount ( string name , string password , AccessLevel accessLevel , IPAddress address )
2017-02-07 00:34:00 -05:00
{
2018-02-14 12:06:26 -06:00
var account = new Account ( ) ;
account . AccountName = name ;
account . SetPassword ( password ) ;
2019-03-08 14:41:23 -05:00
account . SetSaltForBCrypt ( ) ;
2018-02-14 12:06:26 -06:00
account . AccessLevel = ( uint ) accessLevel ;
2019-07-06 16:12:24 -05:00
account . CreateTime = DateTime . UtcNow ;
account . CreateIP = address . GetAddressBytes ( ) ;
2018-02-14 12:06:26 -06:00
using ( var context = new AuthDbContext ( ) )
{
context . Account . Add ( account ) ;
context . SaveChanges ( ) ;
}
return account ;
2017-10-21 13:32:06 -04:00
}
2017-02-07 00:34:00 -05:00
2018-02-14 12:06:26 -06:00
/// <summary>
/// Will return null if the accountId was not found.
/// </summary>
2017-10-21 13:32:06 -04:00
public Account GetAccountById ( uint accountId )
{
2018-02-14 12:06:26 -06:00
using ( var context = new AuthDbContext ( ) )
2018-08-01 08:32:28 -05:00
{
return context . Account
. AsNoTracking ( )
. FirstOrDefault ( r = > r . AccountId = = accountId ) ;
}
2017-10-21 13:32:06 -04:00
}
2017-02-07 00:34:00 -05:00
2018-02-14 12:06:26 -06:00
/// <summary>
/// Will return null if the accountName was not found.
/// </summary>
2017-10-21 13:32:06 -04:00
public Account GetAccountByName ( string accountName )
{
2018-02-14 12:06:26 -06:00
using ( var context = new AuthDbContext ( ) )
2018-08-01 08:32:28 -05:00
{
return context . Account
. AsNoTracking ( )
. FirstOrDefault ( r = > r . AccountName = = accountName ) ;
}
2018-02-14 12:06:26 -06:00
}
2017-10-21 13:32:06 -04:00
2018-02-14 12:06:26 -06:00
/// <summary>
/// id will be 0 if the accountName was not found.
/// </summary>
public uint GetAccountIdByName ( string accountName )
{
using ( var context = new AuthDbContext ( ) )
{
2018-08-01 08:32:28 -05:00
var result = context . Account
. AsNoTracking ( )
. FirstOrDefault ( r = > r . AccountName = = accountName ) ;
2017-02-19 02:30:22 -05:00
2018-02-14 12:06:26 -06:00
return ( result ! = null ) ? result . AccountId : 0 ;
}
2017-10-21 13:32:06 -04:00
}
2018-01-28 06:46:15 -06:00
2018-02-14 12:06:26 -06:00
public void UpdateAccount ( Account account )
2017-10-21 13:32:06 -04:00
{
2018-02-14 12:06:26 -06:00
using ( var context = new AuthDbContext ( ) )
{
context . Entry ( account ) . State = EntityState . Modified ;
context . SaveChanges ( ) ;
}
2017-02-19 02:30:22 -05:00
}
2018-01-28 06:46:15 -06:00
2018-02-14 12:06:26 -06:00
public bool UpdateAccountAccessLevel ( uint accountId , AccessLevel accessLevel )
2018-01-28 06:46:15 -06:00
{
2018-02-14 12:06:26 -06:00
using ( var context = new AuthDbContext ( ) )
{
2018-08-01 08:32:28 -05:00
var account = context . Account
. First ( r = > r . AccountId = = accountId ) ;
2018-02-14 12:06:26 -06:00
if ( account = = null )
return false ;
account . AccessLevel = ( uint ) accessLevel ;
context . SaveChanges ( ) ;
}
return true ;
2018-01-28 06:46:15 -06:00
}
2019-03-31 04:52:09 -05:00
public List < string > GetListofAccountsByAccessLevel ( AccessLevel accessLevel )
{
using ( var context = new AuthDbContext ( ) )
{
var results = context . Account
. AsNoTracking ( )
. Where ( r = > r . AccessLevel = = Convert . ToUInt32 ( accessLevel ) ) . ToList ( ) ;
var result = new List < string > ( ) ;
foreach ( var account in results )
result . Add ( account . AccountName ) ;
return result ;
}
}
2020-04-12 18:47:17 -04:00
public List < string > GetListofBannedAccounts ( )
{
using ( var context = new AuthDbContext ( ) )
{
var results = context . Account
. AsNoTracking ( )
. Where ( r = > r . BanExpireTime > DateTime . UtcNow ) . ToList ( ) ;
var result = new List < string > ( ) ;
foreach ( var account in results )
{
var bannedbyAccount = account . BannedByAccountId . Value > 0 ? $"account {GetAccountById(account.BannedByAccountId.Value).AccountName}" : "CONSOLE" ;
result . Add ( $"{account.AccountName} -- banned by {bannedbyAccount} until server time {account.BanExpireTime.Value.ToLocalTime():MMM dd yyyy h:mmtt}{(!string.IsNullOrWhiteSpace(account.BanReason) ? $" - - Reason : { account . BanReason } " : " ")}" ) ;
}
return result ;
}
}
2017-02-07 00:34:00 -05:00
}
}