Merge branch 'master' into develop

This commit is contained in:
Dane Everitt 2019-12-28 11:49:08 -08:00
commit 51defae917
No known key found for this signature in database
GPG Key ID: EEA66103B3D71F53
15 changed files with 140 additions and 21 deletions

View File

@ -3,6 +3,18 @@ This file is a running track of new features and fixes to each version of the pa
This project follows [Semantic Versioning](http://semver.org) guidelines.
## v0.7.16 (Derelict Dermodactylus)
### Fixed
* Fixed the /api/application/servers endpoint erroring when including subusers or egg
* Fixed bug in migration files causing failures when using MySQL 8.
* Fixed missing redirect return when an error occurs while modifying database information.
* Fixes bug in login attempt tracking.
* Fixes a bug where certain URL encoded files would not be editable in the file manager.
### Added
* The application API now includes the egg's name in the egg model's response.
* The /api/application/servers endpoint can now include server's databases and subusers.
## v0.7.15 (Derelict Dermodactylus)
### Fixed
* Fixes support for PHP 7.3 when running `composer install` commands due to a dependency that needed updating.

View File

@ -165,7 +165,7 @@ class DatabaseController extends Controller
$this->alert->danger(
sprintf('There was an error while trying to connect to the host or while executing a query: "%s"', $exception->getMessage())
)->flash();
$redirect->withInput($request->normalize());
return $redirect->withInput($request->normalize());
} else {
throw $exception;
}

View File

@ -203,11 +203,11 @@ class Server extends Validable
/**
* Gets the subusers associated with a server.
*
* @return \Illuminate\Database\Eloquent\Relations\HasManyThrough
* @return \Illuminate\Database\Eloquent\Relations\HasMany
*/
public function subusers()
{
return $this->hasManyThrough(User::class, Subuser::class, 'server_id', 'id', 'id', 'user_id');
return $this->hasMany(Subuser::class, 'server_id', 'id');
}
/**

View File

@ -51,7 +51,7 @@ class NestDeletionService
{
$count = $this->serverRepository->findCountWhere([['nest_id', '=', $nest]]);
if ($count > 0) {
throw new HasActiveServersException(trans('exceptions.service.delete_has_servers'));
throw new HasActiveServersException(trans('exceptions.nest.delete_has_servers'));
}
return $this->repository->delete($nest);

View File

@ -41,6 +41,7 @@ class EggTransformer extends BaseTransformer
return [
'id' => $model->id,
'uuid' => $model->uuid,
'name' => $model->name,
'nest' => $model->nest_id,
'author' => $model->author,
'description' => $model->description,

View File

@ -28,6 +28,7 @@ class ServerTransformer extends BaseTransformer
'variables',
'location',
'node',
'databases',
];
/**
@ -131,7 +132,7 @@ class ServerTransformer extends BaseTransformer
$server->loadMissing('subusers');
return $this->collection($server->getRelation('subusers'), $this->makeTransformer(UserTransformer::class), 'user');
return $this->collection($server->getRelation('subusers'), $this->makeTransformer(SubuserTransformer::class), 'subuser');
}
/**
@ -195,14 +196,14 @@ class ServerTransformer extends BaseTransformer
}
/**
* Return a generic array with service option information for this server.
* Return a generic array with egg information for this server.
*
* @param \Pterodactyl\Models\Server $server
* @return \League\Fractal\Resource\Item|\League\Fractal\Resource\NullResource
*
* @throws \Pterodactyl\Exceptions\Transformer\InvalidTransformerLevelException
*/
public function includeOption(Server $server)
public function includeEgg(Server $server)
{
if (! $this->authorize(AdminAcl::RESOURCE_EGGS)) {
return $this->null();
@ -210,7 +211,7 @@ class ServerTransformer extends BaseTransformer
$server->loadMissing('egg');
return $this->item($server->getRelation('egg'), $this->makeTransformer(EggVariableTransformer::class), 'egg');
return $this->item($server->getRelation('egg'), $this->makeTransformer(EggTransformer::class), 'egg');
}
/**
@ -269,4 +270,23 @@ class ServerTransformer extends BaseTransformer
return $this->item($server->getRelation('node'), $this->makeTransformer(NodeTransformer::class), 'node');
}
/**
* Return a generic array with database information for this server.
*
* @param \Pterodactyl\Models\Server $server
* @return \League\Fractal\Resource\Collection|\League\Fractal\Resource\NullResource
*
* @throws \Pterodactyl\Exceptions\Transformer\InvalidTransformerLevelException
*/
public function includeDatabases(Server $server)
{
if (! $this->authorize(AdminAcl::RESOURCE_SERVER_DATABASES)) {
return $this->null();
}
$server->loadMissing('databases');
return $this->collection($server->getRelation('databases'), $this->makeTransformer(ServerDatabaseTransformer::class), 'databases');
}
}

View File

@ -0,0 +1,85 @@
<?php
namespace Pterodactyl\Transformers\Api\Application;
use Pterodactyl\Models\Subuser;
use Pterodactyl\Models\Permission;
use Pterodactyl\Services\Acl\Api\AdminAcl;
class SubuserTransformer extends BaseTransformer
{
/**
* List of resources that can be included.
*
* @var array
*/
protected $availableIncludes = ['user', 'server'];
/**
* Return the resource name for the JSONAPI output.
*
* @return string
*/
public function getResourceName(): string
{
return Subuser::RESOURCE_NAME;
}
/**
* Return a transformed Subuser model that can be consumed by external services.
*
* @param \Pterodactyl\Models\Subuser $subuser
* @return array
*/
public function transform(Subuser $subuser): array
{
return [
'id' => $subuser->id,
'user_id' => $subuser->user_id,
'server_id' => $subuser->server_id,
'permissions' => $subuser->permissions->map(function (Permission $permission) {
return $permission->permission;
}),
'created_at' => $this->formatTimestamp($subuser->created_at),
'updated_at' => $this->formatTimestamp($subuser->updated_at),
];
}
/**
* Return a generic item of user for this subuser.
*
* @param \Pterodactyl\Models\Subuser $subuser
* @return \League\Fractal\Resource\Item|\League\Fractal\Resource\NullResource
*
* @throws \Pterodactyl\Exceptions\Transformer\InvalidTransformerLevelException
*/
public function includeUser(Subuser $subuser)
{
if (! $this->authorize(AdminAcl::RESOURCE_USERS)) {
return $this->null();
}
$subuser->loadMissing('user');
return $this->item($subuser->getRelation('user'), $this->makeTransformer(UserTransformer::class), 'user');
}
/**
* Return a generic item of server for this subuser.
*
* @param \Pterodactyl\Models\Subuser $subuser
* @return \League\Fractal\Resource\Item|\League\Fractal\Resource\NullResource
*
* @throws \Pterodactyl\Exceptions\Transformer\InvalidTransformerLevelException
*/
public function includeServer(Subuser $subuser)
{
if (! $this->authorize(AdminAcl::RESOURCE_SERVERS)) {
return $this->null();
}
$subuser->loadMissing('server');
return $this->item($subuser->getRelation('server'), $this->makeTransformer(ServerTransformer::class), 'server');
}
}

View File

@ -12,7 +12,7 @@ return [
|
*/
'lockout' => [
'time' => 120,
'time' => 2,
'attempts' => 3,
],

View File

@ -16,7 +16,7 @@ class AddForeignKeysServers extends Migration
MODIFY COLUMN owner INT(10) UNSIGNED NOT NULL,
MODIFY COLUMN allocation INT(10) UNSIGNED NOT NULL,
MODIFY COLUMN service INT(10) UNSIGNED NOT NULL,
MODIFY COLUMN servers.option INT(10) UNSIGNED NOT NULL
MODIFY COLUMN `option` INT(10) UNSIGNED NOT NULL
');
Schema::table('servers', function (Blueprint $table) {
@ -55,7 +55,7 @@ class AddForeignKeysServers extends Migration
MODIFY COLUMN owner MEDIUMINT(8) UNSIGNED NOT NULL,
MODIFY COLUMN allocation MEDIUMINT(8) UNSIGNED NOT NULL,
MODIFY COLUMN service MEDIUMINT(8) UNSIGNED NOT NULL,
MODIFY COLUMN servers.option MEDIUMINT(8) UNSIGNED NOT NULL
MODIFY COLUMN `option` MEDIUMINT(8) UNSIGNED NOT NULL
');
}
}

View File

@ -6,15 +6,16 @@
@extends('layouts.admin')
@section('title')
Nests &rarr; Egg: {{ $egg->name }} &rarr; Scripts
Nests &rarr; Egg: {{ $egg->name }} &rarr; Install Script
@endsection
@section('content-header')
<h1>{{ $egg->name }}<small>Manage install and upgrade scripts for this Egg.</small></h1>
<h1>{{ $egg->name }}<small>Manage the install script for this Egg.</small></h1>
<ol class="breadcrumb">
<li><a href="{{ route('admin.index') }}">Admin</a></li>
<li><a href="{{ route('admin.nests') }}">Service</a></li>
<li><a href="{{ route('admin.nests') }}">Nests</a></li>
<li><a href="{{ route('admin.nests.view', $egg->nest->id) }}">{{ $egg->nest->name }}</a></li>
<li><a href="{{ route('admin.nests.egg.view', $egg->id) }}">{{ $egg->name }}</a></li>
<li class="active">{{ $egg->name }}</li>
</ol>
@endsection
@ -26,7 +27,7 @@
<ul class="nav nav-tabs">
<li><a href="{{ route('admin.nests.egg.view', $egg->id) }}">Configuration</a></li>
<li><a href="{{ route('admin.nests.egg.variables', $egg->id) }}">Variables</a></li>
<li class="active"><a href="{{ route('admin.nests.egg.scripts', $egg->id) }}">Scripts</a></li>
<li class="active"><a href="{{ route('admin.nests.egg.scripts', $egg->id) }}">Install Script</a></li>
</ul>
</div>
</div>

View File

@ -27,7 +27,7 @@
<ul class="nav nav-tabs">
<li><a href="{{ route('admin.nests.egg.view', $egg->id) }}">Configuration</a></li>
<li class="active"><a href="{{ route('admin.nests.egg.variables', $egg->id) }}">Variables</a></li>
<li><a href="{{ route('admin.nests.egg.scripts', $egg->id) }}">Scripts</a></li>
<li><a href="{{ route('admin.nests.egg.scripts', $egg->id) }}">Install Script</a></li>
</ul>
</div>
</div>

View File

@ -26,7 +26,7 @@
<ul class="nav nav-tabs">
<li class="active"><a href="{{ route('admin.nests.egg.view', $egg->id) }}">Configuration</a></li>
<li><a href="{{ route('admin.nests.egg.variables', $egg->id) }}">Variables</a></li>
<li><a href="{{ route('admin.nests.egg.scripts', $egg->id) }}">Scripts</a></li>
<li><a href="{{ route('admin.nests.egg.scripts', $egg->id) }}">Install Script</a></li>
</ul>
</div>
</div>

View File

@ -106,7 +106,7 @@
</div>
<div class="box-body">
<div class="row">
<div class="form-group col-xs-12">
<div class="form-group col-md-6">
<label for="pDaemonBase" class="form-label">Daemon Server File Directory</label>
<input type="text" name="daemonBase" id="pDaemonBase" class="form-control" value="/srv/daemon-data" />
<p class="text-muted small">Enter the directory where server files should be stored. <strong>If you use OVH you should check your partition scheme. You may need to use <code>/home/daemon-data</code> to have enough space.</strong></p>
@ -177,4 +177,4 @@
<script>
$('#pLocationId').select2();
</script>
@endsection
@endsection

View File

@ -60,7 +60,7 @@ class DatabasePasswordServiceTest extends TestCase
$this->dynamic->shouldReceive('set')->with('dynamic', $model->database_host_id)->once()->andReturnNull();
$this->encrypter->expects('encrypt')->with(m::on(function ($string) {
preg_match_all('/[!@+=^-]/', $string, $matches, PREG_SET_ORDER);
preg_match_all('/[!@+=.^-]/', $string, $matches, PREG_SET_ORDER);
$this->assertTrue(count($matches) >= 2 && count($matches) <= 6, "Failed asserting that [{$string}] contains 2 to 6 special characters.");
$this->assertTrue(strlen($string) === 24, "Failed asserting that [{$string}] is 24 characters in length.");

View File

@ -73,7 +73,7 @@ class NestDeletionServiceTest extends TestCase
$this->service->handle(1);
} catch (PterodactylException $exception) {
$this->assertInstanceOf(HasActiveServersException::class, $exception);
$this->assertEquals(trans('exceptions.service.delete_has_servers'), $exception->getMessage());
$this->assertEquals(trans('exceptions.nest.delete_has_servers'), $exception->getMessage());
}
}