133 lines
4.2 KiB
C#
133 lines
4.2 KiB
C#
using MycroForge.CLI.CodeGen;
|
|
using MycroForge.CLI.Commands;
|
|
using MycroForge.Core;
|
|
|
|
namespace MycroForge.CLI.Features;
|
|
|
|
public sealed partial class Db : IFeature
|
|
{
|
|
#region Defaults
|
|
|
|
private static readonly string[] Settings =
|
|
[
|
|
"class DbSettings:",
|
|
"\tdef get_connectionstring() -> str:",
|
|
"\t\tconnectionstring = \"mysql+asyncmy://root:password@localhost:%db_port%/%app_name%\"",
|
|
"\t\treturn connectionstring",
|
|
];
|
|
|
|
private static readonly string[] AsyncSession =
|
|
[
|
|
"from sqlalchemy.ext.asyncio import create_async_engine, AsyncEngine, AsyncSession",
|
|
$"from {FeatureName}.settings import DbSettings",
|
|
"",
|
|
"async_engine: AsyncEngine = create_async_engine(DbSettings.get_connectionstring())",
|
|
"",
|
|
"def async_session() -> AsyncSession:",
|
|
"\treturn AsyncSession(async_engine, expire_on_commit=False)"
|
|
];
|
|
|
|
private static readonly string[] EntityBase =
|
|
[
|
|
"from sqlalchemy.orm import DeclarativeBase",
|
|
"",
|
|
"class EntityBase(DeclarativeBase):",
|
|
"\tpass"
|
|
];
|
|
|
|
private static readonly string[] DockerCompose =
|
|
[
|
|
"# Access the database UI at http://localhost:${DBU_PORT}.",
|
|
"# Login: username = root & password = password",
|
|
"",
|
|
"services:",
|
|
" %app_name%_mariadb:",
|
|
" image: 'mariadb:10.4'",
|
|
" container_name: '%app_name%_mariadb'",
|
|
" networks:",
|
|
" - default",
|
|
" ports:",
|
|
" - '${DBH_PORT}:3306'",
|
|
" environment:",
|
|
" MYSQL_ROOT_PASSWORD: 'password'",
|
|
" MYSQL_USER: 'root'",
|
|
" MYSQL_PASSWORD: 'password'",
|
|
" MYSQL_DATABASE: '%app_name%'",
|
|
" volumes:",
|
|
" - '%app_name%_mariadb:/var/lib/mysql'",
|
|
"",
|
|
" %app_name%_phpmyadmin:",
|
|
" image: %dbu_platform%/phpmyadmin",
|
|
" container_name: %app_name%_phpmyadmin",
|
|
" ports:",
|
|
" - '${DBU_PORT}:80'",
|
|
" networks:",
|
|
" - default",
|
|
" environment:",
|
|
" PMA_HOST: %app_name%_mariadb",
|
|
" PMA_PORT: 3306",
|
|
" PMA_ARBITRARY: 1",
|
|
" links:",
|
|
" - %app_name%_mariadb",
|
|
"",
|
|
"volumes:",
|
|
" %app_name%_mariadb:\n",
|
|
];
|
|
|
|
#endregion
|
|
|
|
public const string FeatureName = "db";
|
|
|
|
private readonly OptionsContainer _optionsContainer;
|
|
|
|
public string Name => FeatureName;
|
|
|
|
public Db(OptionsContainer optionsContainer)
|
|
{
|
|
_optionsContainer = optionsContainer;
|
|
}
|
|
|
|
public async Task ExecuteAsync(ProjectContext context)
|
|
{
|
|
var options = _optionsContainer.Get<Options>();
|
|
var config = await context.LoadConfig(create: true);
|
|
config.Db = new()
|
|
{
|
|
DbhPort = options.DbhPort ?? 5050,
|
|
DbuPort = options.DbuPort ?? 5051,
|
|
DbuPlatform = options.DbuPlatform
|
|
};
|
|
await context.SaveConfig(config);
|
|
|
|
var appName = context.AppName;
|
|
|
|
await context.Bash(
|
|
"source .venv/bin/activate",
|
|
"python3 -m pip install asyncmy sqlalchemy alembic",
|
|
"python3 -m pip freeze > requirements.txt",
|
|
$"alembic init -t async {FeatureName}"
|
|
);
|
|
|
|
var env = await context.ReadFile($"{FeatureName}/env.py");
|
|
env = new DbEnvInitializer(env).Rewrite();
|
|
await context.WriteFile($"{FeatureName}/env.py", env);
|
|
|
|
var settings = string.Join('\n', Settings)
|
|
.Replace("%app_name%", appName)
|
|
.Replace("%db_port%", config.Db.DbhPort.ToString())
|
|
;
|
|
|
|
await context.CreateFile($"{FeatureName}/settings.py", settings);
|
|
|
|
await context.CreateFile($"{FeatureName}/engine/async_session.py", AsyncSession);
|
|
|
|
await context.CreateFile($"{FeatureName}/entities/entity_base.py", EntityBase);
|
|
|
|
var dockerCompose = string.Join('\n', DockerCompose)
|
|
.Replace("%app_name%", appName)
|
|
.Replace("%dbu_platform%", options.DbuPlatform.ToString())
|
|
;
|
|
|
|
await context.CreateFile($"{FeatureName}.docker-compose.yml", dockerCompose);
|
|
}
|
|
} |