Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
pterodactyl
GitHub Repository: pterodactyl/panel
Path: blob/1.0-develop/app/Http/Controllers/Admin/ServersController.php
10279 views
1
<?php
2
3
namespace Pterodactyl\Http\Controllers\Admin;
4
5
use Illuminate\Http\Request;
6
use Pterodactyl\Models\User;
7
use Illuminate\Http\Response;
8
use Pterodactyl\Models\Mount;
9
use Pterodactyl\Models\Server;
10
use Pterodactyl\Models\Database;
11
use Pterodactyl\Models\MountServer;
12
use Illuminate\Http\RedirectResponse;
13
use Prologue\Alerts\AlertsMessageBag;
14
use Pterodactyl\Exceptions\DisplayException;
15
use Pterodactyl\Http\Controllers\Controller;
16
use Illuminate\Validation\ValidationException;
17
use Pterodactyl\Services\Servers\SuspensionService;
18
use Pterodactyl\Repositories\Eloquent\MountRepository;
19
use Pterodactyl\Services\Servers\ServerDeletionService;
20
use Pterodactyl\Services\Servers\ReinstallServerService;
21
use Pterodactyl\Exceptions\Model\DataValidationException;
22
use Pterodactyl\Repositories\Wings\DaemonServerRepository;
23
use Pterodactyl\Services\Servers\BuildModificationService;
24
use Pterodactyl\Services\Databases\DatabasePasswordService;
25
use Pterodactyl\Services\Servers\DetailsModificationService;
26
use Pterodactyl\Services\Servers\StartupModificationService;
27
use Pterodactyl\Contracts\Repository\NestRepositoryInterface;
28
use Pterodactyl\Repositories\Eloquent\DatabaseHostRepository;
29
use Pterodactyl\Services\Databases\DatabaseManagementService;
30
use Illuminate\Contracts\Config\Repository as ConfigRepository;
31
use Pterodactyl\Contracts\Repository\ServerRepositoryInterface;
32
use Pterodactyl\Contracts\Repository\DatabaseRepositoryInterface;
33
use Pterodactyl\Contracts\Repository\AllocationRepositoryInterface;
34
use Pterodactyl\Services\Servers\ServerConfigurationStructureService;
35
use Pterodactyl\Http\Requests\Admin\Servers\Databases\StoreServerDatabaseRequest;
36
37
class ServersController extends Controller
38
{
39
/**
40
* ServersController constructor.
41
*/
42
public function __construct(
43
protected AlertsMessageBag $alert,
44
protected AllocationRepositoryInterface $allocationRepository,
45
protected BuildModificationService $buildModificationService,
46
protected ConfigRepository $config,
47
protected DaemonServerRepository $daemonServerRepository,
48
protected DatabaseManagementService $databaseManagementService,
49
protected DatabasePasswordService $databasePasswordService,
50
protected DatabaseRepositoryInterface $databaseRepository,
51
protected DatabaseHostRepository $databaseHostRepository,
52
protected ServerDeletionService $deletionService,
53
protected DetailsModificationService $detailsModificationService,
54
protected ReinstallServerService $reinstallService,
55
protected ServerRepositoryInterface $repository,
56
protected MountRepository $mountRepository,
57
protected NestRepositoryInterface $nestRepository,
58
protected ServerConfigurationStructureService $serverConfigurationStructureService,
59
protected StartupModificationService $startupModificationService,
60
protected SuspensionService $suspensionService,
61
) {
62
}
63
64
/**
65
* Update the details for a server.
66
*
67
* @throws DataValidationException
68
* @throws \Pterodactyl\Exceptions\Repository\RecordNotFoundException
69
*/
70
public function setDetails(Request $request, Server $server): RedirectResponse
71
{
72
$this->detailsModificationService->handle($server, $request->only([
73
'owner_id', 'external_id', 'name', 'description',
74
]));
75
76
$this->alert->success(trans('admin/server.alerts.details_updated'))->flash();
77
78
return redirect()->route('admin.servers.view.details', $server->id);
79
}
80
81
/**
82
* Toggles the installation status for a server.
83
*
84
* @throws DisplayException
85
* @throws DataValidationException
86
* @throws \Pterodactyl\Exceptions\Repository\RecordNotFoundException
87
*/
88
public function toggleInstall(Server $server): RedirectResponse
89
{
90
if ($server->status === Server::STATUS_INSTALL_FAILED) {
91
throw new DisplayException(trans('admin/server.exceptions.marked_as_failed'));
92
}
93
94
$this->repository->update($server->id, [
95
'status' => $server->isInstalled() ? Server::STATUS_INSTALLING : null,
96
], true, true);
97
98
$this->alert->success(trans('admin/server.alerts.install_toggled'))->flash();
99
100
return redirect()->route('admin.servers.view.manage', $server->id);
101
}
102
103
/**
104
* Reinstalls the server with the currently assigned service.
105
*
106
* @throws DisplayException
107
* @throws DataValidationException
108
* @throws \Pterodactyl\Exceptions\Repository\RecordNotFoundException
109
*/
110
public function reinstallServer(Server $server): RedirectResponse
111
{
112
$this->reinstallService->handle($server);
113
$this->alert->success(trans('admin/server.alerts.server_reinstalled'))->flash();
114
115
return redirect()->route('admin.servers.view.manage', $server->id);
116
}
117
118
/**
119
* Manage the suspension status for a server.
120
*
121
* @throws DisplayException
122
* @throws DataValidationException
123
* @throws \Pterodactyl\Exceptions\Repository\RecordNotFoundException
124
*/
125
public function manageSuspension(Request $request, Server $server): RedirectResponse
126
{
127
$this->suspensionService->toggle($server, $request->input('action'));
128
$this->alert->success(trans('admin/server.alerts.suspension_toggled', [
129
'status' => $request->input('action') . 'ed',
130
]))->flash();
131
132
return redirect()->route('admin.servers.view.manage', $server->id);
133
}
134
135
/**
136
* Update the build configuration for a server.
137
*
138
* @throws DisplayException
139
* @throws \Pterodactyl\Exceptions\Repository\RecordNotFoundException
140
* @throws ValidationException
141
*/
142
public function updateBuild(Request $request, Server $server): RedirectResponse
143
{
144
try {
145
$this->buildModificationService->handle($server, $request->only([
146
'allocation_id', 'add_allocations', 'remove_allocations',
147
'memory', 'swap', 'io', 'cpu', 'threads', 'disk',
148
'database_limit', 'allocation_limit', 'backup_limit', 'oom_disabled',
149
]));
150
} catch (DataValidationException $exception) {
151
throw new ValidationException($exception->getValidator());
152
}
153
154
$this->alert->success(trans('admin/server.alerts.build_updated'))->flash();
155
156
return redirect()->route('admin.servers.view.build', $server->id);
157
}
158
159
/**
160
* Start the server deletion process.
161
*
162
* @throws DisplayException
163
* @throws \Throwable
164
*/
165
public function delete(Request $request, Server $server): RedirectResponse
166
{
167
$this->deletionService->withForce($request->filled('force_delete'))->handle($server);
168
$this->alert->success(trans('admin/server.alerts.server_deleted'))->flash();
169
170
return redirect()->route('admin.servers');
171
}
172
173
/**
174
* Update the startup command as well as variables.
175
*
176
* @throws ValidationException
177
*/
178
public function saveStartup(Request $request, Server $server): RedirectResponse
179
{
180
$data = $request->except('_token');
181
if (!empty($data['custom_docker_image'])) {
182
$data['docker_image'] = $data['custom_docker_image'];
183
unset($data['custom_docker_image']);
184
}
185
186
try {
187
$this->startupModificationService
188
->setUserLevel(User::USER_LEVEL_ADMIN)
189
->handle($server, $data);
190
} catch (DataValidationException $exception) {
191
throw new ValidationException($exception->getValidator());
192
}
193
194
$this->alert->success(trans('admin/server.alerts.startup_changed'))->flash();
195
196
return redirect()->route('admin.servers.view.startup', $server->id);
197
}
198
199
/**
200
* Creates a new database assigned to a specific server.
201
*
202
* @throws \Throwable
203
*/
204
public function newDatabase(StoreServerDatabaseRequest $request, Server $server): RedirectResponse
205
{
206
$this->databaseManagementService->create($server, [
207
'database' => DatabaseManagementService::generateUniqueDatabaseName($request->input('database'), $server->id),
208
'remote' => $request->input('remote'),
209
'database_host_id' => $request->input('database_host_id'),
210
'max_connections' => $request->input('max_connections'),
211
]);
212
213
return redirect()->route('admin.servers.view.database', $server->id)->withInput();
214
}
215
216
/**
217
* Resets the database password for a specific database on this server.
218
*
219
* @throws \Throwable
220
*/
221
public function resetDatabasePassword(Request $request, Server $server): Response
222
{
223
/** @var Database $database */
224
$database = $server->databases()->findOrFail($request->input('database'));
225
226
$this->databasePasswordService->handle($database);
227
228
return response('', 204);
229
}
230
231
/**
232
* Deletes a database from a server.
233
*
234
* @throws \Exception
235
*/
236
public function deleteDatabase(Server $server, Database $database): Response
237
{
238
$this->databaseManagementService->delete($database);
239
240
return response('', 204);
241
}
242
243
/**
244
* Add a mount to a server.
245
*
246
* @throws \Throwable
247
*/
248
public function addMount(Request $request, Server $server): RedirectResponse
249
{
250
$mountServer = (new MountServer())->forceFill([
251
'mount_id' => $request->input('mount_id'),
252
'server_id' => $server->id,
253
]);
254
255
$mountServer->saveOrFail();
256
257
$this->alert->success('Mount was added successfully.')->flash();
258
259
return redirect()->route('admin.servers.view.mounts', $server->id);
260
}
261
262
/**
263
* Remove a mount from a server.
264
*/
265
public function deleteMount(Server $server, Mount $mount): RedirectResponse
266
{
267
MountServer::where('mount_id', $mount->id)->where('server_id', $server->id)->delete();
268
269
$this->alert->success('Mount was removed successfully.')->flash();
270
271
return redirect()->route('admin.servers.view.mounts', $server->id);
272
}
273
}
274
275