public IActionResult CreateDatabase([FromBody] NewDatabaseInstance newDatabase) { if (newDatabase == null) { return(BadRequest(new { EntityType = "Database", Message = $"Must supply database details in the request body." })); } if (!ModelState.IsValid) { return(BadRequest(ModelState)); } DatabaseServer targetServer = DocumentSession.GetDatabaseServerById(newDatabase.ServerId); if (targetServer == null) { return(NotFound(new { Id = newDatabase.ServerId, EntityType = "DatabaseServer", Message = $"No database server found for tenant with Id {newDatabase.ServerId}" })); } if (targetServer.Kind != DatabaseServerKind.SqlServer) { return(BadRequest(new { ServerId = targetServer.Id, ServerKind = targetServer.Kind, Reason = "NotImplemented", Message = $"Creation of databases in ${targetServer.Kind} servers is not supported yet." })); } if (targetServer.Status != ProvisioningStatus.Ready) { return(StatusCode(StatusCodes.Status409Conflict, new { Id = targetServer.Id, EntityType = "DatabaseServer", Action = targetServer.Action, Status = targetServer.Status, Message = $"Cannot create a database in server {targetServer.Id} because a server-level action is already in progress." })); } Tenant ownerTenant = DocumentSession.GetTenantById(targetServer.TenantId); if (ownerTenant == null) { return(NotFound(new { Id = targetServer.TenantId, EntityType = "Tenant", Message = $"Target server's owning tenant not found with Id {targetServer.TenantId}." })); } DatabaseInstance existingDatabase = DocumentSession.GetDatabaseInstanceByName(newDatabase.Name, targetServer.Id); if (existingDatabase != null) { return(StatusCode(StatusCodes.Status409Conflict, new { Id = existingDatabase.Id, Name = existingDatabase.Name, EntityType = "Database", Message = $"Database '{existingDatabase.Name}' already exists on server '{targetServer.Name}'." })); } var database = new DatabaseInstance { Name = newDatabase.Name, DatabaseUser = newDatabase.DatabaseUser, DatabasePassword = newDatabase.DatabasePassword, Storage = { SizeMB = newDatabase.SizeMB }, ServerId = targetServer.Id, TenantId = ownerTenant.Id, Action = ProvisioningAction.Provision, Status = ProvisioningStatus.Pending }; DocumentSession.Store(database); targetServer.DatabaseIds.Add(database.Id); var user = new DatabaseUser { Name = database.DatabaseUser, DatabaseId = database.Id, ServerId = database.ServerId, TenantId = database.TenantId, }; if (targetServer.Kind == DatabaseServerKind.SqlServer) { user.AddPassword(database.DatabasePassword); } // TODO: Request client certificate from Vault and store it as a user credential. DocumentSession.Store(user); DocumentSession.SaveChanges(); return(StatusCode(StatusCodes.Status202Accepted, new { Id = database.Id, Name = database.Name, Message = $"Database '{database.Name}' queued for creation on server '{targetServer.Name}'." })); }