Initial Commit of Files
PufferPanel v0.9 (Laravel) is now Pterodactyl 1.0
This commit is contained in:
commit
1489f7a694
154 changed files with 10159 additions and 0 deletions
83
app/Http/Controllers/API/UserController.php
Normal file
83
app/Http/Controllers/API/UserController.php
Normal file
|
@ -0,0 +1,83 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Controllers\API;
|
||||
|
||||
use Gate;
|
||||
use Log;
|
||||
use Debugbar;
|
||||
use Pterodactyl\Models\API;
|
||||
use Pterodactyl\Models\User;
|
||||
|
||||
use Pterodactyl\Http\Controllers\Controller;
|
||||
use Illuminate\Http\Request;
|
||||
|
||||
class UserController extends Controller
|
||||
{
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
$this->middleware('api');
|
||||
}
|
||||
|
||||
public function getAllUsers(Request $request)
|
||||
{
|
||||
|
||||
// Policies don't work if the user isn't logged in for whatever reason in Laravel...
|
||||
if(!API::checkPermission($request->header('X-Authorization'), 'get-users')) {
|
||||
return API::noPermissionError();
|
||||
}
|
||||
|
||||
return response()->json([
|
||||
'users' => User::all()
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns JSON response about a user given their ID.
|
||||
* If fields are provided only those fields are returned.
|
||||
*
|
||||
* Does not return protected fields (i.e. password & totp_secret)
|
||||
*
|
||||
* @param Request $request
|
||||
* @param int $id
|
||||
* @param string $fields
|
||||
* @return Response
|
||||
*/
|
||||
public function getUser(Request $request, $id, $fields = null)
|
||||
{
|
||||
|
||||
// Policies don't work if the user isn't logged in for whatever reason in Laravel...
|
||||
if(!API::checkPermission($request->header('X-Authorization'), 'get-users')) {
|
||||
return API::noPermissionError();
|
||||
}
|
||||
|
||||
if (is_null($fields)) {
|
||||
return response()->json(User::find($id));
|
||||
}
|
||||
|
||||
$query = User::where('id', $id);
|
||||
$explode = explode(',', $fields);
|
||||
|
||||
foreach($explode as &$exploded) {
|
||||
if(!empty($exploded)) {
|
||||
$query->addSelect($exploded);
|
||||
}
|
||||
}
|
||||
|
||||
try {
|
||||
return response()->json($query->get());
|
||||
} catch (\Exception $e) {
|
||||
if ($e instanceof \Illuminate\Database\QueryException) {
|
||||
return response()->json([
|
||||
'error' => 'One of the fields provided in your argument list is invalid.'
|
||||
], 500);
|
||||
}
|
||||
throw $e;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
43
app/Http/Controllers/Admin/AccountsController.php
Normal file
43
app/Http/Controllers/Admin/AccountsController.php
Normal file
|
@ -0,0 +1,43 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Controllers\Admin;
|
||||
|
||||
use Debugbar;
|
||||
use Pterodactyl\Models\User;
|
||||
|
||||
use Pterodactyl\Http\Controllers\Controller;
|
||||
use Illuminate\Http\Request;
|
||||
|
||||
class AccountsController extends Controller
|
||||
{
|
||||
|
||||
/**
|
||||
* Controller Constructor
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
|
||||
// All routes in this controller are protected by the authentication middleware.
|
||||
$this->middleware('auth');
|
||||
$this->middleware('admin');
|
||||
|
||||
}
|
||||
|
||||
public function getIndex(Request $request)
|
||||
{
|
||||
return view('admin.accounts.index', [
|
||||
'users' => User::paginate(20)
|
||||
]);
|
||||
}
|
||||
|
||||
public function getNew(Request $request)
|
||||
{
|
||||
//
|
||||
}
|
||||
|
||||
public function getView(Request $request, $id)
|
||||
{
|
||||
//
|
||||
}
|
||||
|
||||
}
|
30
app/Http/Controllers/Admin/BaseController.php
Normal file
30
app/Http/Controllers/Admin/BaseController.php
Normal file
|
@ -0,0 +1,30 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Controllers\Admin;
|
||||
|
||||
use Debugbar;
|
||||
|
||||
use Pterodactyl\Http\Controllers\Controller;
|
||||
use Illuminate\Http\Request;
|
||||
|
||||
class BaseController extends Controller
|
||||
{
|
||||
|
||||
/**
|
||||
* Controller Constructor
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
|
||||
// All routes in this controller are protected by the authentication middleware.
|
||||
$this->middleware('auth');
|
||||
$this->middleware('admin');
|
||||
|
||||
}
|
||||
|
||||
public function getIndex(Request $request)
|
||||
{
|
||||
return view('admin.index');
|
||||
}
|
||||
|
||||
}
|
47
app/Http/Controllers/Admin/ServersController.php
Normal file
47
app/Http/Controllers/Admin/ServersController.php
Normal file
|
@ -0,0 +1,47 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Controllers\Admin;
|
||||
|
||||
use Debugbar;
|
||||
use Pterodactyl\Models\Server;
|
||||
use Pterodactyl\Models\Node;
|
||||
|
||||
use Pterodactyl\Http\Controllers\Controller;
|
||||
use Illuminate\Http\Request;
|
||||
|
||||
class ServersController extends Controller
|
||||
{
|
||||
|
||||
/**
|
||||
* Controller Constructor
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
|
||||
// All routes in this controller are protected by the authentication middleware.
|
||||
$this->middleware('auth');
|
||||
$this->middleware('admin');
|
||||
|
||||
}
|
||||
|
||||
public function getIndex(Request $request)
|
||||
{
|
||||
return view('admin.servers.index', [
|
||||
'servers' => Server::select('servers.*', 'nodes.name as a_nodeName', 'users.email as a_ownerEmail')
|
||||
->join('nodes', 'servers.node', '=', 'nodes.id')
|
||||
->join('users', 'servers.owner', '=', 'users.id')
|
||||
->paginate(20),
|
||||
]);
|
||||
}
|
||||
|
||||
public function getNew(Request $request)
|
||||
{
|
||||
//
|
||||
}
|
||||
|
||||
public function getView(Request $request, $id)
|
||||
{
|
||||
//
|
||||
}
|
||||
|
||||
}
|
97
app/Http/Controllers/Auth/AuthController.php
Normal file
97
app/Http/Controllers/Auth/AuthController.php
Normal file
|
@ -0,0 +1,97 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Controllers\Auth;
|
||||
|
||||
use Pterodactyl\Models\User;
|
||||
|
||||
use Validator;
|
||||
use Auth;
|
||||
|
||||
use Pterodactyl\Http\Controllers\Controller;
|
||||
use Illuminate\Http\Request;
|
||||
use Illuminate\Foundation\Auth\ThrottlesLogins;
|
||||
use Illuminate\Foundation\Auth\AuthenticatesAndRegistersUsers;
|
||||
|
||||
class AuthController extends Controller
|
||||
{
|
||||
/*
|
||||
|--------------------------------------------------------------------------
|
||||
| Registration & Login Controller
|
||||
|--------------------------------------------------------------------------
|
||||
|
|
||||
| This controller handles the registration of new users, as well as the
|
||||
| authentication of existing users. By default, this controller uses
|
||||
| a simple trait to add these behaviors. Why don't you explore it?
|
||||
|
|
||||
*/
|
||||
|
||||
use AuthenticatesAndRegistersUsers, ThrottlesLogins;
|
||||
|
||||
/**
|
||||
* Post-Authentication redirect location.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
protected $redirectPath = '/';
|
||||
|
||||
/**
|
||||
* Failed post-authentication redirect location.
|
||||
*
|
||||
* @var string
|
||||
*/
|
||||
protected $loginPath = '/auth/login';
|
||||
|
||||
/**
|
||||
* Lockout time for failed login requests.
|
||||
*
|
||||
* @var integer
|
||||
*/
|
||||
protected $lockoutTime = 120;
|
||||
|
||||
/**
|
||||
* After how many attempts should logins be throttled and locked.
|
||||
*
|
||||
* @var integer
|
||||
*/
|
||||
protected $maxLoginAttempts = 5;
|
||||
|
||||
/**
|
||||
* Create a new authentication controller instance.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
$this->middleware('guest', ['except' => 'getLogout']);
|
||||
}
|
||||
|
||||
/**
|
||||
* Get a validator for an incoming registration request.
|
||||
*
|
||||
* @param array $data
|
||||
* @return \Illuminate\Contracts\Validation\Validator
|
||||
*/
|
||||
protected function validator(array $data)
|
||||
{
|
||||
return Validator::make($data, [
|
||||
'email' => 'required|email|max:255|unique:users',
|
||||
'password' => 'required|confirmed|min:8',
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Create a new user instance after a valid registration.
|
||||
*
|
||||
* @param array $data
|
||||
* @return User
|
||||
*/
|
||||
protected function create(array $data)
|
||||
{
|
||||
return User::create([
|
||||
'name' => $data['name'],
|
||||
'email' => $data['email'],
|
||||
'password' => password_hash($data['password']),
|
||||
]);
|
||||
}
|
||||
|
||||
}
|
32
app/Http/Controllers/Auth/PasswordController.php
Normal file
32
app/Http/Controllers/Auth/PasswordController.php
Normal file
|
@ -0,0 +1,32 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Controllers\Auth;
|
||||
|
||||
use Pterodactyl\Http\Controllers\Controller;
|
||||
use Illuminate\Foundation\Auth\ResetsPasswords;
|
||||
|
||||
class PasswordController extends Controller
|
||||
{
|
||||
/*
|
||||
|--------------------------------------------------------------------------
|
||||
| Password Reset Controller
|
||||
|--------------------------------------------------------------------------
|
||||
|
|
||||
| This controller is responsible for handling password reset requests
|
||||
| and uses a simple trait to include this behavior. You're free to
|
||||
| explore this trait and override any methods you wish to tweak.
|
||||
|
|
||||
*/
|
||||
|
||||
use ResetsPasswords;
|
||||
|
||||
/**
|
||||
* Create a new password controller instance.
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
$this->middleware('guest');
|
||||
}
|
||||
}
|
222
app/Http/Controllers/Base/IndexController.php
Normal file
222
app/Http/Controllers/Base/IndexController.php
Normal file
|
@ -0,0 +1,222 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Controllers\Base;
|
||||
|
||||
use Auth;
|
||||
use Debugbar;
|
||||
use Google2FA;
|
||||
use Log;
|
||||
use Alert;
|
||||
use Pterodactyl\Exceptions\AccountNotFoundException;
|
||||
use Pterodactyl\Exceptions\DisplayException;
|
||||
use Pterodactyl\Models\User;
|
||||
use Pterodactyl\Models\Server;
|
||||
|
||||
use Pterodactyl\Http\Controllers\Controller;
|
||||
use Illuminate\Http\Request;
|
||||
|
||||
class IndexController extends Controller
|
||||
{
|
||||
|
||||
/**
|
||||
* Controller Constructor
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
|
||||
// All routes in this controller are protected by the authentication middleware.
|
||||
$this->middleware('auth');
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns listing of user's servers.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return \Illuminate\Contracts\View\View
|
||||
*/
|
||||
public function getIndex(Request $request)
|
||||
{
|
||||
return view('base.index', [
|
||||
'servers' => Server::getUserServers(),
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns TOTP Management Page.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return \Illuminate\Contracts\View\View
|
||||
*/
|
||||
public function getAccountTotp(Request $request)
|
||||
{
|
||||
return view('base.totp');
|
||||
}
|
||||
|
||||
/**
|
||||
* Generates TOTP Secret and returns popup data for user to verify
|
||||
* that they can generate a valid response.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return \Illuminate\Contracts\View\View
|
||||
*/
|
||||
public function putAccountTotp(Request $request)
|
||||
{
|
||||
|
||||
try {
|
||||
$totpSecret = User::setTotpSecret(Auth::user()->id);
|
||||
} catch (\Exception $e) {
|
||||
if ($e instanceof AccountNotFoundException) {
|
||||
return response($e->getMessage(), 500);
|
||||
}
|
||||
throw $e;
|
||||
}
|
||||
|
||||
return response()->json([
|
||||
'qrImage' => Google2FA::getQRCodeGoogleUrl(
|
||||
'Pterodactyl',
|
||||
Auth::user()->email,
|
||||
$totpSecret
|
||||
),
|
||||
'secret' => $totpSecret
|
||||
]);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Verifies that 2FA token recieved is valid and will work on the account.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function postAccountTotp(Request $request)
|
||||
{
|
||||
|
||||
if (!$request->has('token')) {
|
||||
return response('No input \'token\' defined.', 500);
|
||||
}
|
||||
|
||||
try {
|
||||
if(User::toggleTotp(Auth::user()->id, $request->input('token'))) {
|
||||
return response('true');
|
||||
}
|
||||
return response('false');
|
||||
} catch (\Exception $e) {
|
||||
if ($e instanceof AccountNotFoundException) {
|
||||
return response($e->getMessage(), 500);
|
||||
}
|
||||
throw $e;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Disables TOTP on an account.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function deleteAccountTotp(Request $request)
|
||||
{
|
||||
|
||||
if (!$request->has('token')) {
|
||||
Alert::danger('Missing required `token` field in request.')->flash();
|
||||
return redirect()->route('account.totp');
|
||||
}
|
||||
|
||||
try {
|
||||
if(User::toggleTotp(Auth::user()->id, $request->input('token'))) {
|
||||
return redirect()->route('account.totp');
|
||||
}
|
||||
|
||||
Alert::danger('Unable to disable TOTP on this account, was the token correct?')->flash();
|
||||
return redirect()->route('account.totp');
|
||||
} catch (\Exception $e) {
|
||||
if ($e instanceof AccountNotFoundException) {
|
||||
Alert::danger('An error occured while attempting to perform this action.')->flash();
|
||||
return redirect()->route('account.totp');
|
||||
}
|
||||
throw $e;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Display base account information page.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return \Illuminate\Contracts\View\View
|
||||
*/
|
||||
public function getAccount(Request $request)
|
||||
{
|
||||
return view('base.account');
|
||||
}
|
||||
|
||||
/**
|
||||
* Update an account email.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function postAccountEmail(Request $request)
|
||||
{
|
||||
|
||||
$this->validate($request, [
|
||||
'new_email' => 'required|email',
|
||||
'password' => 'required'
|
||||
]);
|
||||
|
||||
if (!password_verify($request->input('password'), Auth::user()->password)) {
|
||||
Alert::danger('The password provided was not valid for this account.')->flash();
|
||||
return redirect()->route('account');
|
||||
}
|
||||
|
||||
// Met Validation, lets roll out.
|
||||
try {
|
||||
User::setEmail(Auth::user()->id, $request->input('new_email'));
|
||||
Alert::success('Your email address has successfully been updated.')->flash();
|
||||
return redirect()->route('account');
|
||||
} catch (\Exception $e) {
|
||||
if ($e instanceof AccountNotFoundException || $e instanceof DisplayException) {
|
||||
Alert::danger($e->getMessage())->flash();
|
||||
return redirect()->route('account');
|
||||
}
|
||||
throw $e;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Update an account password.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function postAccountPassword(Request $request)
|
||||
{
|
||||
|
||||
$this->validate($request, [
|
||||
'current_password' => 'required',
|
||||
'new_password' => 'required|confirmed|different:current_password|regex:((?=.*\d)(?=.*[a-z])(?=.*[A-Z]).{8,})',
|
||||
'new_password_confirmation' => 'required'
|
||||
]);
|
||||
|
||||
if (!password_verify($request->input('current_password'), Auth::user()->password)) {
|
||||
Alert::danger('The password provided was not valid for this account.')->flash();
|
||||
return redirect()->route('account');
|
||||
}
|
||||
|
||||
// Met Validation, lets roll out.
|
||||
try {
|
||||
User::setPassword(Auth::user()->id, $request->input('new_password'));
|
||||
Alert::success('Your password has successfully been updated.')->flash();
|
||||
return redirect()->route('account');
|
||||
} catch (\Exception $e) {
|
||||
if ($e instanceof AccountNotFoundException || $e instanceof DisplayException) {
|
||||
Alert::danger($e->getMessage())->flash();
|
||||
return redirect()->route('account');
|
||||
}
|
||||
throw $e;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
13
app/Http/Controllers/Controller.php
Normal file
13
app/Http/Controllers/Controller.php
Normal file
|
@ -0,0 +1,13 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Controllers;
|
||||
|
||||
use Illuminate\Foundation\Bus\DispatchesJobs;
|
||||
use Illuminate\Routing\Controller as BaseController;
|
||||
use Illuminate\Foundation\Validation\ValidatesRequests;
|
||||
use Illuminate\Foundation\Auth\Access\AuthorizesRequests;
|
||||
|
||||
abstract class Controller extends BaseController
|
||||
{
|
||||
use AuthorizesRequests, DispatchesJobs, ValidatesRequests;
|
||||
}
|
193
app/Http/Controllers/Scales/FileController.php
Normal file
193
app/Http/Controllers/Scales/FileController.php
Normal file
|
@ -0,0 +1,193 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Controllers\Scales;
|
||||
|
||||
use \Exception;
|
||||
use Log;
|
||||
use Debugbar;
|
||||
use Pterodactyl\Models\Server;
|
||||
use Pterodactyl\Models\Node;
|
||||
|
||||
use Pterodactyl\Exceptions\DisplayException;
|
||||
use Pterodactyl\Http\Helpers;
|
||||
use Pterodactyl\Http\Controllers\Controller;
|
||||
|
||||
use GuzzleHttp\Client;
|
||||
use GuzzleHttp\Exception\RequestException;
|
||||
|
||||
class FileController extends Controller
|
||||
{
|
||||
|
||||
/**
|
||||
* The Eloquent Model associated with the requested server.
|
||||
*
|
||||
* @var \Illuminate\Database\Eloquent\Model
|
||||
*/
|
||||
protected $server;
|
||||
|
||||
/**
|
||||
* The Eloquent Model for the node corresponding with the requested server.
|
||||
*
|
||||
* @var \Illuminate\Database\Eloquent\Model
|
||||
*/
|
||||
protected $node;
|
||||
|
||||
/**
|
||||
* The Guzzle Client associated with the requested server and node.
|
||||
*
|
||||
* @var \GuzzleHttp\Client
|
||||
*/
|
||||
protected $client;
|
||||
|
||||
/**
|
||||
* The Guzzle Client headers associated with the requested server and node.
|
||||
* (non-administrative headers)
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $headers;
|
||||
|
||||
/**
|
||||
* Constructor
|
||||
*
|
||||
* @param string $server The server Short UUID
|
||||
*/
|
||||
public function __construct($uuid)
|
||||
{
|
||||
|
||||
$this->server = Server::getByUUID($uuid);
|
||||
$this->node = Node::getByID($this->server->node);
|
||||
$this->client = Node::guzzleRequest($this->server->node);
|
||||
$this->headers = Server::getGuzzleHeaders($uuid);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Get the contents of a requested file for the server.
|
||||
*
|
||||
* @param string $file
|
||||
* @return string
|
||||
*/
|
||||
public function returnFileContents($file)
|
||||
{
|
||||
|
||||
if (empty($file)) {
|
||||
throw new Exception('Not all parameters were properly passed to the function.');
|
||||
}
|
||||
|
||||
$file = (object) pathinfo($file);
|
||||
if (!in_array($file->extension, Helpers::editableFiles())) {
|
||||
throw new DisplayException('You do not have permission to edit this type of file.');
|
||||
}
|
||||
|
||||
$file->dirname = (in_array($file->dirname, ['.', './', '/'])) ? null : trim($file->dirname, '/') . '/';
|
||||
|
||||
$res = $this->client->request('GET', '/server/file/' . rawurlencode($file->dirname.$file->basename), [
|
||||
'headers' => $this->headers
|
||||
]);
|
||||
|
||||
$json = json_decode($res->getBody());
|
||||
if($res->getStatusCode() !== 200 || !isset($json->contents)) {
|
||||
throw new DisplayException('Scales provided a non-200 error code: HTTP\\' . $res->getStatusCode());
|
||||
}
|
||||
|
||||
return $json;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Save the contents of a requested file on the Scales instance.
|
||||
*
|
||||
* @param string $file
|
||||
* @param string $content
|
||||
* @return boolean
|
||||
*/
|
||||
public function saveFileContents($file, $content)
|
||||
{
|
||||
|
||||
if (empty($file)) {
|
||||
throw new Exception('A valid file and path must be specified to save a file.');
|
||||
}
|
||||
|
||||
$file = (object) pathinfo($file);
|
||||
|
||||
if(!in_array($file->extension, Helpers::editableFiles())) {
|
||||
throw new DisplayException('You do not have permission to edit this type of file.');
|
||||
}
|
||||
|
||||
$file->dirname = (in_array($file->dirname, ['.', './', '/'])) ? null : trim($file->dirname, '/') . '/';
|
||||
|
||||
$res = $this->client->request('PUT', '/server/file/' . rawurlencode($file->dirname.$file->basename), [
|
||||
'headers' => $this->headers,
|
||||
'form_params' => [
|
||||
'contents' => $content
|
||||
]
|
||||
]);
|
||||
|
||||
if ($res->getStatusCode() !== 204) {
|
||||
throw new DisplayException('An error occured while attempting to save this file. Scales said: ' . $res->getBody());
|
||||
}
|
||||
|
||||
return true;
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a listing of all files and folders within a specified Scales directory.
|
||||
*
|
||||
* @param string $directory
|
||||
* @return object
|
||||
*/
|
||||
public function returnDirectoryListing($directory)
|
||||
{
|
||||
|
||||
if (empty($directory)) {
|
||||
throw new Exception('A valid directory must be specified in order to list its contents.');
|
||||
}
|
||||
|
||||
$res = $this->client->request('GET', '/server/directory/' . $directory, [
|
||||
'headers' => $this->headers
|
||||
]);
|
||||
|
||||
$json = json_decode($res->getBody());
|
||||
if($res->getStatusCode() !== 200) {
|
||||
throw new DisplayException('An error occured while attempting to save this file. Scales said: ' . $res->getBody());
|
||||
}
|
||||
|
||||
// Iterate through results
|
||||
$files = [];
|
||||
$folders = [];
|
||||
foreach($json as &$value) {
|
||||
|
||||
if ($value->file !== true) {
|
||||
|
||||
// @TODO Handle Symlinks
|
||||
$folders = array_merge($folders, [[
|
||||
'entry' => $value->name,
|
||||
'directory' => trim($directory, '/'),
|
||||
'size' => null,
|
||||
'date' => strtotime($value->modified)
|
||||
]]);
|
||||
|
||||
} else {
|
||||
|
||||
$files = array_merge($files, [[
|
||||
'entry' => $value->name,
|
||||
'directory' => trim($directory, '/'),
|
||||
'extension' => pathinfo($value->name, PATHINFO_EXTENSION),
|
||||
'size' => Helpers::bytesToHuman($value->size),
|
||||
'date' => strtotime($value->modified)
|
||||
]]);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
return (object) [
|
||||
'files' => $files,
|
||||
'folders' => $folders,
|
||||
];
|
||||
|
||||
}
|
||||
|
||||
}
|
182
app/Http/Controllers/Server/AjaxController.php
Normal file
182
app/Http/Controllers/Server/AjaxController.php
Normal file
|
@ -0,0 +1,182 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Controllers\Server;
|
||||
|
||||
use Log;
|
||||
use Debugbar;
|
||||
use Pterodactyl\Models\Server;
|
||||
use Pterodactyl\Models\Node;
|
||||
use Pterodactyl\Http\Helpers;
|
||||
|
||||
use Pterodactyl\Exceptions\DisplayException;
|
||||
use Pterodactyl\Http\Controllers\Scales\FileController;
|
||||
use Pterodactyl\Http\Controllers\Controller;
|
||||
use Illuminate\Http\Request;
|
||||
|
||||
use GuzzleHttp\Client;
|
||||
use GuzzleHttp\Exception\RequestException;
|
||||
|
||||
class AjaxController extends Controller
|
||||
{
|
||||
|
||||
/**
|
||||
* @var array
|
||||
*/
|
||||
protected $files = [];
|
||||
|
||||
/**
|
||||
* @var array
|
||||
*/
|
||||
protected $folders = [];
|
||||
|
||||
/**
|
||||
* @var string
|
||||
*/
|
||||
protected $directory;
|
||||
|
||||
/**
|
||||
* Controller Constructor
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
|
||||
// All routes in this controller are protected by the authentication middleware.
|
||||
$this->middleware('auth');
|
||||
|
||||
// Routes in this file are also checked aganist the server middleware. If the user
|
||||
// does not have permission to view the server it will not load.
|
||||
$this->middleware('server');
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true or false depending on the power status of the requested server.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param string $uuid
|
||||
* @return \Illuminate\Contracts\View\View
|
||||
*/
|
||||
public function getStatus(Request $request, $uuid)
|
||||
{
|
||||
|
||||
$server = Server::getByUUID($uuid);
|
||||
$client = Node::guzzleRequest($server->node);
|
||||
|
||||
try {
|
||||
|
||||
$res = $client->request('GET', '/server', [
|
||||
'headers' => Server::getGuzzleHeaders($uuid)
|
||||
]);
|
||||
|
||||
if($res->getStatusCode() === 200) {
|
||||
|
||||
$json = json_decode($res->getBody());
|
||||
|
||||
if (isset($json->status) && $json->status === 1) {
|
||||
return 'true';
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
} catch (RequestException $e) {
|
||||
Debugbar::error($e->getMessage());
|
||||
Log::notice('An exception was raised while attempting to contact a Scales instance to get server status information.', [
|
||||
'exception' => $e->getMessage(),
|
||||
'path' => $request->path()
|
||||
]);
|
||||
}
|
||||
|
||||
return 'false';
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns a listing of files in a given directory for a server.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param string $uuid`
|
||||
* @return \Illuminate\Contracts\View\View
|
||||
*/
|
||||
public function postDirectoryList(Request $request, $uuid)
|
||||
{
|
||||
|
||||
$server = Server::getByUUID($uuid);
|
||||
$this->directory = '/' . trim(urldecode($request->input('directory', '/')), '/');
|
||||
$this->authorize('list-files', $server);
|
||||
|
||||
$prevDir = [
|
||||
'header' => ($this->directory !== '/') ? $this->directory : ''
|
||||
];
|
||||
if ($this->directory !== '/') {
|
||||
$prevDir['first'] = true;
|
||||
}
|
||||
|
||||
// Determine if we should show back links in the file browser.
|
||||
// This code is strange, and could probably be rewritten much better.
|
||||
$goBack = explode('/', rtrim($this->directory, '/'));
|
||||
if (isset($goBack[2]) && !empty($goBack[2])) {
|
||||
$prevDir['show'] = true;
|
||||
$prevDir['link'] = '/' . trim(str_replace(end($goBack), '', $this->directory), '/');
|
||||
$prevDir['link_show'] = trim($prevDir['link'], '/');
|
||||
}
|
||||
|
||||
$controller = new FileController($uuid);
|
||||
|
||||
try {
|
||||
$directoryContents = $controller->returnDirectoryListing($this->directory);
|
||||
} catch (\Exception $e) {
|
||||
|
||||
Debugbar::addException($e);
|
||||
$exception = 'An error occured while attempting to load the requested directory, please try again.';
|
||||
|
||||
if ($e instanceof DisplayException) {
|
||||
$exception = $e->getMessage();
|
||||
}
|
||||
|
||||
return response($exception, 500);
|
||||
|
||||
}
|
||||
|
||||
return view('server.files.list', [
|
||||
'server' => $server,
|
||||
'files' => $directoryContents->files,
|
||||
'folders' => $directoryContents->folders,
|
||||
'extensions' => Helpers::editableFiles(),
|
||||
'directory' => $prevDir
|
||||
]);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles a POST request to save a file.
|
||||
*
|
||||
* @param Request $request
|
||||
* @param string $uuid
|
||||
* @return \Illuminate\Http\Response
|
||||
*/
|
||||
public function postSaveFile(Request $request, $uuid)
|
||||
{
|
||||
|
||||
$server = Server::getByUUID($uuid);
|
||||
$this->authorize('save-files', $server);
|
||||
|
||||
$controller = new FileController($uuid);
|
||||
|
||||
try {
|
||||
$controller->saveFileContents($request->input('file'), $request->input('contents'));
|
||||
return response(null, 204);
|
||||
} catch (\Exception $e) {
|
||||
|
||||
Debugbar::addException($e);
|
||||
$exception = 'An error occured while attempting to save that file, please try again.';
|
||||
|
||||
if ($e instanceof DisplayException) {
|
||||
$exception = $e->getMessage();
|
||||
}
|
||||
|
||||
return response($exception, 500);
|
||||
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
}
|
162
app/Http/Controllers/Server/ServerController.php
Normal file
162
app/Http/Controllers/Server/ServerController.php
Normal file
|
@ -0,0 +1,162 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Controllers\Server;
|
||||
|
||||
use Auth;
|
||||
use Pterodactyl\Models\Server;
|
||||
use Pterodactyl\Models\Node;
|
||||
use Pterodactyl\Models\Download;
|
||||
use Debugbar;
|
||||
use Uuid;
|
||||
use Alert;
|
||||
|
||||
use Pterodactyl\Exceptions\DisplayException;
|
||||
use Pterodactyl\Http\Controllers\Scales\FileController;
|
||||
use Pterodactyl\Http\Controllers\Controller;
|
||||
use Illuminate\Http\Request;
|
||||
|
||||
class ServerController extends Controller
|
||||
{
|
||||
|
||||
/**
|
||||
* Controller Constructor
|
||||
*
|
||||
* @return void
|
||||
*/
|
||||
public function __construct()
|
||||
{
|
||||
|
||||
// All routes in this controller are protected by the authentication middleware.
|
||||
$this->middleware('auth');
|
||||
|
||||
// Routes in this file are also checked aganist the server middleware. If the user
|
||||
// does not have permission to view the server it will not load.
|
||||
$this->middleware('server');
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders server index page for specified server.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @return \Illuminate\Contracts\View\View
|
||||
*/
|
||||
public function getIndex(Request $request)
|
||||
{
|
||||
$server = Server::getByUUID($request->route()->server);
|
||||
return view('server.index', [
|
||||
'server' => $server,
|
||||
'node' => Node::find($server->node)
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders file overview page.
|
||||
*
|
||||
* @param Request $request
|
||||
* @return \Illuminate\Contracts\View\View
|
||||
*/
|
||||
public function getFiles(Request $request)
|
||||
{
|
||||
|
||||
$server = Server::getByUUID($request->route()->server);
|
||||
$this->authorize('list-files', $server);
|
||||
|
||||
return view('server.files.index', [
|
||||
'server' => $server,
|
||||
'node' => Node::find($server->node)
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders add file page.
|
||||
*
|
||||
* @param Request $request
|
||||
* @return \Illuminate\Contracts\View\View
|
||||
*/
|
||||
public function getAddFile(Request $request)
|
||||
{
|
||||
|
||||
$server = Server::getByUUID($request->route()->server);
|
||||
$this->authorize('add-files', $server);
|
||||
|
||||
return view('server.files.add', [
|
||||
'server' => $server,
|
||||
'node' => Node::find($server->node),
|
||||
'directory' => (in_array($request->get('dir'), [null, '/', ''])) ? '' : trim($request->get('dir'), '/') . '/'
|
||||
]);
|
||||
}
|
||||
|
||||
/**
|
||||
* Renders edit file page for a given file.
|
||||
*
|
||||
* @param Request $request
|
||||
* @param string $uuid
|
||||
* @param string $file
|
||||
* @return \Illuminate\Contracts\View\View
|
||||
*/
|
||||
public function getEditFile(Request $request, $uuid, $file)
|
||||
{
|
||||
|
||||
$server = Server::getByUUID($uuid);
|
||||
$this->authorize('edit-files', $server);
|
||||
|
||||
$fileInfo = (object) pathinfo($file);
|
||||
$controller = new FileController($uuid);
|
||||
|
||||
try {
|
||||
$fileContent = $controller->returnFileContents($file);
|
||||
} catch (\Exception $e) {
|
||||
|
||||
Debugbar::addException($e);
|
||||
$exception = 'An error occured while attempting to load the requested file for editing, please try again.';
|
||||
|
||||
if ($e instanceof DisplayException) {
|
||||
$exception = $e->getMessage();
|
||||
}
|
||||
|
||||
Alert::danger($exception)->flash();
|
||||
return redirect()->route('files.index', $uuid);
|
||||
|
||||
}
|
||||
|
||||
return view('server.files.edit', [
|
||||
'server' => $server,
|
||||
'node' => Node::find($server->node),
|
||||
'file' => $file,
|
||||
'contents' => $fileContent->contents,
|
||||
'directory' => (in_array($fileInfo->dirname, ['.', './', '/'])) ? '/' : trim($fileInfo->dirname, '/') . '/',
|
||||
'extension' => $fileInfo->extension
|
||||
]);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* Handles downloading a file for the user.
|
||||
*
|
||||
* @param Request $request
|
||||
* @param string $uuid
|
||||
* @param string $file
|
||||
* @return \Illuminate\Contracts\View\View
|
||||
*/
|
||||
public function getDownloadFile(Request $request, $uuid, $file)
|
||||
{
|
||||
|
||||
$server = Server::getByUUID($uuid);
|
||||
$node = Node::find($server->node);
|
||||
|
||||
$this->authorize('download-files', $server);
|
||||
|
||||
$download = new Download;
|
||||
|
||||
$download->token = Uuid::generate(4);
|
||||
$download->server = $server->id;
|
||||
$download->path = str_replace('../', '', $file);
|
||||
|
||||
$download->save();
|
||||
|
||||
return redirect('https://' . $node->fqdn . ':' . $node->daemonListen . '/server/download/' . $download->token);
|
||||
|
||||
}
|
||||
|
||||
}
|
58
app/Http/Helpers.php
Normal file
58
app/Http/Helpers.php
Normal file
|
@ -0,0 +1,58 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http;
|
||||
|
||||
class Helpers {
|
||||
|
||||
/**
|
||||
* Listing of editable files in the control panel.
|
||||
* @var array
|
||||
*/
|
||||
protected static $editable = [
|
||||
'txt',
|
||||
'yml',
|
||||
'yaml',
|
||||
'log',
|
||||
'conf',
|
||||
'config',
|
||||
'html',
|
||||
'json',
|
||||
'properties',
|
||||
'props',
|
||||
'cfg',
|
||||
'lang',
|
||||
'ini',
|
||||
'cmd',
|
||||
'sh',
|
||||
'lua',
|
||||
'0' // Supports BungeeCord Files
|
||||
];
|
||||
|
||||
public function __construct()
|
||||
{
|
||||
//
|
||||
}
|
||||
|
||||
/**
|
||||
* Converts from bytes to the largest possible size that is still readable.
|
||||
*
|
||||
* @param int $bytes
|
||||
* @param int $decimals
|
||||
* @return string
|
||||
*/
|
||||
public static function bytesToHuman($bytes, $decimals = 2)
|
||||
{
|
||||
|
||||
$sz = explode(',', 'B,KB,MB,GB');
|
||||
$factor = floor((strlen($bytes) - 1) / 3);
|
||||
|
||||
return sprintf("%.{$decimals}f", $bytes / pow(1024, $factor)).' '.$sz[$factor];
|
||||
|
||||
}
|
||||
|
||||
public static function editableFiles()
|
||||
{
|
||||
return self::$editable;
|
||||
}
|
||||
|
||||
}
|
36
app/Http/Kernel.php
Normal file
36
app/Http/Kernel.php
Normal file
|
@ -0,0 +1,36 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http;
|
||||
|
||||
use Illuminate\Foundation\Http\Kernel as HttpKernel;
|
||||
|
||||
class Kernel extends HttpKernel
|
||||
{
|
||||
/**
|
||||
* The application's global HTTP middleware stack.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $middleware = [
|
||||
\Illuminate\Foundation\Http\Middleware\CheckForMaintenanceMode::class,
|
||||
\Pterodactyl\Http\Middleware\EncryptCookies::class,
|
||||
\Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse::class,
|
||||
\Illuminate\Session\Middleware\StartSession::class,
|
||||
\Illuminate\View\Middleware\ShareErrorsFromSession::class,
|
||||
\Pterodactyl\Http\Middleware\VerifyCsrfToken::class,
|
||||
];
|
||||
|
||||
/**
|
||||
* The application's route middleware.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $routeMiddleware = [
|
||||
'auth' => \Pterodactyl\Http\Middleware\Authenticate::class,
|
||||
'auth.basic' => \Illuminate\Auth\Middleware\AuthenticateWithBasicAuth::class,
|
||||
'guest' => \Pterodactyl\Http\Middleware\RedirectIfAuthenticated::class,
|
||||
'server' => \Pterodactyl\Http\MiddleWare\CheckServer::class,
|
||||
'api' => \Pterodactyl\Http\MiddleWare\APIAuthenticate::class,
|
||||
'admin' => \Pterodactyl\Http\Middleware\AdminAuthenticate::class,
|
||||
];
|
||||
}
|
46
app/Http/Middleware/APIAuthenticate.php
Normal file
46
app/Http/Middleware/APIAuthenticate.php
Normal file
|
@ -0,0 +1,46 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Middleware;
|
||||
|
||||
use Closure;
|
||||
use Debugbar;
|
||||
|
||||
use Pterodactyl\Models\API;
|
||||
|
||||
class APIAuthenticate
|
||||
{
|
||||
/**
|
||||
* Handle an incoming request.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param \Closure $next
|
||||
* @return mixed
|
||||
*/
|
||||
public function handle($request, Closure $next)
|
||||
{
|
||||
|
||||
if(!$request->header('X-Authorization')) {
|
||||
return response()->json([
|
||||
'error' => 'Authorization header was missing with this request. Please pass the \'X-Authorization\' header with your request.'
|
||||
], 403);
|
||||
}
|
||||
|
||||
$api = API::where('key', $request->header('X-Authorization'))->first();
|
||||
if (!$api) {
|
||||
return response()->json([
|
||||
'error' => 'Invalid API key was provided in the request.'
|
||||
], 403);
|
||||
}
|
||||
|
||||
if (!is_null($api->allowed_ips)) {
|
||||
if (!in_array($request->ip(), json_decode($api->allowed_ips, true))) {
|
||||
return response()->json([
|
||||
'error' => 'This IP (' . $request->ip() . ') is not permitted to access the API with that token.'
|
||||
], 403);
|
||||
}
|
||||
}
|
||||
|
||||
return $next($request);
|
||||
|
||||
}
|
||||
}
|
51
app/Http/Middleware/AdminAuthenticate.php
Normal file
51
app/Http/Middleware/AdminAuthenticate.php
Normal file
|
@ -0,0 +1,51 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Middleware;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Contracts\Auth\Guard;
|
||||
|
||||
class AdminAuthenticate
|
||||
{
|
||||
/**
|
||||
* The Guard implementation.
|
||||
*
|
||||
* @var Guard
|
||||
*/
|
||||
protected $auth;
|
||||
|
||||
/**
|
||||
* Create a new filter instance.
|
||||
*
|
||||
* @param Guard $auth
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(Guard $auth)
|
||||
{
|
||||
$this->auth = $auth;
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle an incoming request.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param \Closure $next
|
||||
* @return mixed
|
||||
*/
|
||||
public function handle($request, Closure $next)
|
||||
{
|
||||
if ($this->auth->guest()) {
|
||||
if ($request->ajax()) {
|
||||
return response('Unauthorized.', 401);
|
||||
} else {
|
||||
return redirect()->guest('auth/login');
|
||||
}
|
||||
}
|
||||
|
||||
if($this->auth->user()->root_admin !== 1) {
|
||||
return abort(403);
|
||||
}
|
||||
|
||||
return $next($request);
|
||||
}
|
||||
}
|
47
app/Http/Middleware/Authenticate.php
Normal file
47
app/Http/Middleware/Authenticate.php
Normal file
|
@ -0,0 +1,47 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Middleware;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Contracts\Auth\Guard;
|
||||
|
||||
class Authenticate
|
||||
{
|
||||
/**
|
||||
* The Guard implementation.
|
||||
*
|
||||
* @var Guard
|
||||
*/
|
||||
protected $auth;
|
||||
|
||||
/**
|
||||
* Create a new filter instance.
|
||||
*
|
||||
* @param Guard $auth
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(Guard $auth)
|
||||
{
|
||||
$this->auth = $auth;
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle an incoming request.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param \Closure $next
|
||||
* @return mixed
|
||||
*/
|
||||
public function handle($request, Closure $next)
|
||||
{
|
||||
if ($this->auth->guest()) {
|
||||
if ($request->ajax()) {
|
||||
return response('Unauthorized.', 401);
|
||||
} else {
|
||||
return redirect()->guest('auth/login');
|
||||
}
|
||||
}
|
||||
|
||||
return $next($request);
|
||||
}
|
||||
}
|
33
app/Http/Middleware/CheckServer.php
Normal file
33
app/Http/Middleware/CheckServer.php
Normal file
|
@ -0,0 +1,33 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Middleware;
|
||||
|
||||
use Closure;
|
||||
use Auth;
|
||||
use Pterodactyl\Models\Server;
|
||||
use Debugbar;
|
||||
|
||||
class CheckServer
|
||||
{
|
||||
/**
|
||||
* Handle an incoming request.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param \Closure $next
|
||||
* @return mixed
|
||||
*/
|
||||
public function handle($request, Closure $next)
|
||||
{
|
||||
|
||||
if (!Auth::user()) {
|
||||
return redirect()->guest('auth/login');
|
||||
}
|
||||
|
||||
if (!Server::getByUUID($request->route()->server)) {
|
||||
return redirect('/');
|
||||
}
|
||||
|
||||
return $next($request);
|
||||
|
||||
}
|
||||
}
|
17
app/Http/Middleware/EncryptCookies.php
Normal file
17
app/Http/Middleware/EncryptCookies.php
Normal file
|
@ -0,0 +1,17 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Middleware;
|
||||
|
||||
use Illuminate\Cookie\Middleware\EncryptCookies as BaseEncrypter;
|
||||
|
||||
class EncryptCookies extends BaseEncrypter
|
||||
{
|
||||
/**
|
||||
* The names of the cookies that should not be encrypted.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $except = [
|
||||
//
|
||||
];
|
||||
}
|
43
app/Http/Middleware/RedirectIfAuthenticated.php
Normal file
43
app/Http/Middleware/RedirectIfAuthenticated.php
Normal file
|
@ -0,0 +1,43 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Middleware;
|
||||
|
||||
use Closure;
|
||||
use Illuminate\Contracts\Auth\Guard;
|
||||
|
||||
class RedirectIfAuthenticated
|
||||
{
|
||||
/**
|
||||
* The Guard implementation.
|
||||
*
|
||||
* @var Guard
|
||||
*/
|
||||
protected $auth;
|
||||
|
||||
/**
|
||||
* Create a new filter instance.
|
||||
*
|
||||
* @param Guard $auth
|
||||
* @return void
|
||||
*/
|
||||
public function __construct(Guard $auth)
|
||||
{
|
||||
$this->auth = $auth;
|
||||
}
|
||||
|
||||
/**
|
||||
* Handle an incoming request.
|
||||
*
|
||||
* @param \Illuminate\Http\Request $request
|
||||
* @param \Closure $next
|
||||
* @return mixed
|
||||
*/
|
||||
public function handle($request, Closure $next)
|
||||
{
|
||||
if ($this->auth->check()) {
|
||||
return redirect('/home');
|
||||
}
|
||||
|
||||
return $next($request);
|
||||
}
|
||||
}
|
17
app/Http/Middleware/VerifyCsrfToken.php
Normal file
17
app/Http/Middleware/VerifyCsrfToken.php
Normal file
|
@ -0,0 +1,17 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Middleware;
|
||||
|
||||
use Illuminate\Foundation\Http\Middleware\VerifyCsrfToken as BaseVerifier;
|
||||
|
||||
class VerifyCsrfToken extends BaseVerifier
|
||||
{
|
||||
/**
|
||||
* The URIs that should be excluded from CSRF verification.
|
||||
*
|
||||
* @var array
|
||||
*/
|
||||
protected $except = [
|
||||
//
|
||||
];
|
||||
}
|
10
app/Http/Requests/Request.php
Normal file
10
app/Http/Requests/Request.php
Normal file
|
@ -0,0 +1,10 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Requests;
|
||||
|
||||
use Illuminate\Foundation\Http\FormRequest;
|
||||
|
||||
abstract class Request extends FormRequest
|
||||
{
|
||||
//
|
||||
}
|
30
app/Http/Routes/AdminRoutes.php
Normal file
30
app/Http/Routes/AdminRoutes.php
Normal file
|
@ -0,0 +1,30 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Routes;
|
||||
|
||||
use Illuminate\Routing\Router;
|
||||
|
||||
class AdminRoutes {
|
||||
|
||||
public function map(Router $router) {
|
||||
$router->group(['prefix' => 'admin'], function ($server) use ($router) {
|
||||
$router->get('/', [ 'as' => 'admin.index', 'uses' => 'Admin\BaseController@getIndex' ]);
|
||||
|
||||
// Account Routes
|
||||
$router->group(['prefix' => 'accounts'], function ($server) use ($router) {
|
||||
$router->get('/', [ 'as' => 'admin.accounts', 'uses' => 'Admin\AccountsController@getIndex' ]);
|
||||
$router->get('/new', [ 'as' => 'admin.accounts.new', 'uses' => 'Admin\AccountsController@getNew' ]);
|
||||
$router->get('/view/{id}', [ 'as' => 'admin.accounts.view', 'uses' => 'Admin\AccountsController@getView' ]);
|
||||
});
|
||||
|
||||
// Server Routes
|
||||
$router->group(['prefix' => 'servers'], function ($server) use ($router) {
|
||||
$router->get('/', [ 'as' => 'admin.servers', 'uses' => 'Admin\ServersController@getIndex' ]);
|
||||
$router->get('/new', [ 'as' => 'admin.servers.new', 'uses' => 'Admin\ServersController@getNew' ]);
|
||||
$router->get('/view/{id}', [ 'as' => 'admin.servers.view', 'uses' => 'Admin\ServersController@getView' ]);
|
||||
});
|
||||
|
||||
});
|
||||
}
|
||||
|
||||
}
|
18
app/Http/Routes/AuthRoutes.php
Normal file
18
app/Http/Routes/AuthRoutes.php
Normal file
|
@ -0,0 +1,18 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Routes;
|
||||
|
||||
use Illuminate\Routing\Router;
|
||||
|
||||
class AuthRoutes {
|
||||
|
||||
public function map(Router $router) {
|
||||
$router->group(['prefix' => 'auth'], function () use ($router) {
|
||||
$router->get('login', [ 'as' => 'auth.login', 'uses' => 'Auth\AuthController@getLogin' ]);
|
||||
$router->post('login', [ 'as' => 'auth.login.submit', 'uses' => 'Auth\AuthController@postLogin' ]);
|
||||
|
||||
$router->get('logout', [ 'as' => 'auth.logout', 'uses' => 'Auth\AuthController@getLogout' ]);
|
||||
});
|
||||
}
|
||||
|
||||
}
|
30
app/Http/Routes/BaseRoutes.php
Normal file
30
app/Http/Routes/BaseRoutes.php
Normal file
|
@ -0,0 +1,30 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Routes;
|
||||
|
||||
use Illuminate\Routing\Router;
|
||||
|
||||
class BaseRoutes {
|
||||
|
||||
public function map(Router $router) {
|
||||
|
||||
// Handle Index. Redirect /index to /
|
||||
$router->get('/', [ 'as' => 'index', 'uses' => 'Base\IndexController@getIndex' ]);
|
||||
$router->get('/index', function () {
|
||||
return redirect()->route('index');
|
||||
});
|
||||
|
||||
// Account Routes
|
||||
$router->get('/account', [ 'as' => 'account', 'uses' => 'Base\IndexController@getAccount' ]);
|
||||
$router->post('/account/password', [ 'uses' => 'Base\IndexController@postAccountPassword' ]);
|
||||
$router->post('/account/email', [ 'uses' => 'Base\IndexController@postAccountEmail' ]);
|
||||
|
||||
// TOTP Routes
|
||||
$router->get('/account/totp', [ 'as' => 'account.totp', 'uses' => 'Base\IndexController@getAccountTotp' ]);
|
||||
$router->put('/account/totp', [ 'uses' => 'Base\IndexController@putAccountTotp' ]);
|
||||
$router->post('/account/totp', [ 'uses' => 'Base\IndexController@postAccountTotp' ]);
|
||||
$router->delete('/account/totp', [ 'uses' => 'Base\IndexController@deleteAccountTotp' ]);
|
||||
|
||||
}
|
||||
|
||||
}
|
22
app/Http/Routes/RestRoutes.php
Normal file
22
app/Http/Routes/RestRoutes.php
Normal file
|
@ -0,0 +1,22 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Routes;
|
||||
|
||||
use Illuminate\Routing\Router;
|
||||
|
||||
class RestRoutes {
|
||||
|
||||
public function map(Router $router) {
|
||||
$router->group(['prefix' => 'api/v1'], function ($server) use ($router) {
|
||||
|
||||
$router->group(['prefix' => 'users'], function ($server) use ($router) {
|
||||
|
||||
$router->get('/', [ 'uses' => 'API\UserController@getAllUsers' ]);
|
||||
$router->get('/{id}/{fields?}', [ 'uses' => 'API\UserController@getUser' ])->where('id', '[0-9]+');
|
||||
|
||||
});
|
||||
|
||||
});
|
||||
}
|
||||
|
||||
}
|
27
app/Http/Routes/ServerRoutes.php
Normal file
27
app/Http/Routes/ServerRoutes.php
Normal file
|
@ -0,0 +1,27 @@
|
|||
<?php
|
||||
|
||||
namespace Pterodactyl\Http\Routes;
|
||||
|
||||
use Illuminate\Routing\Router;
|
||||
|
||||
class ServerRoutes {
|
||||
|
||||
public function map(Router $router) {
|
||||
$router->group(['prefix' => 'server/{server}'], function ($server) use ($router) {
|
||||
|
||||
$router->get('/', [ 'as' => 'server.index', 'uses' => 'Server\ServerController@getIndex' ]);
|
||||
$router->get('/files', [ 'as' => 'files.index', 'uses' => 'Server\ServerController@getFiles' ]);
|
||||
$router->get('/files/edit/{file}', [ 'as' => 'files.edit', 'uses' => 'Server\ServerController@getEditFile' ])->where('file', '.*');
|
||||
$router->get('/files/download/{file}', [ 'as' => 'files.download', 'uses' => 'Server\ServerController@getDownloadFile' ])->where('file', '.*');
|
||||
$router->get('/files/add', [ 'as' => 'files.add', 'uses' => 'Server\ServerController@getAddFile' ]);
|
||||
|
||||
// Ajax Routes
|
||||
$router->group(['prefix' => 'ajax'], function ($server) use ($router) {
|
||||
$router->get('status', [ 'uses' => 'Server\AjaxController@getStatus' ]);
|
||||
$router->post('files/directory-list', [ 'uses' => 'Server\AjaxController@postDirectoryList' ]);
|
||||
$router->post('files/save', [ 'uses' => 'Server\AjaxController@postSaveFile' ]);
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
}
|
Loading…
Add table
Add a link
Reference in a new issue