796 lines
28 KiB
PHP
796 lines
28 KiB
PHP
<?php
|
|
|
|
namespace App\Game\Service;
|
|
|
|
use App\Game\Enum\DecodeMessage;
|
|
use App\Game\Enum\SessionSettingType;
|
|
use App\Game\Entity\Player;
|
|
use App\Game\Entity\SessionSetting;
|
|
use App\Game\Repository\SessionSettingRepository;
|
|
use App\Tech\Entity\User;
|
|
use Doctrine\ORM\EntityManagerInterface;
|
|
use Symfony\Bundle\SecurityBundle\Security;
|
|
use Symfony\Component\Mercure\HubInterface;
|
|
use Symfony\Component\Mercure\Update;
|
|
|
|
class GameResponseService
|
|
{
|
|
public function __construct(
|
|
private Security $security,
|
|
private PlayerService $playerService,
|
|
private SessionSettingRepository $sessionSettingRepository,
|
|
private HubInterface $hub,
|
|
private EntityManagerInterface $entityManager,
|
|
) {
|
|
}
|
|
|
|
public function getGameResponse(string $raw) : array
|
|
{
|
|
$info = json_decode($raw, true);
|
|
|
|
$message = $info['message'] ?? '';
|
|
$ts = $info['ts'] ?? '';
|
|
|
|
if(!is_string($message))
|
|
return ['error' => 'Invalid message.'];
|
|
|
|
$user = $this->security->getUser();
|
|
|
|
if(!$user instanceof User)
|
|
return ['error' => 'You are not logged in.'];
|
|
|
|
$player = $this->playerService->GetCurrentlyActiveAsPlayer($user);
|
|
|
|
if(!$player)
|
|
return ['error' => 'You are not in a game.'];
|
|
|
|
// TODO: Here i need to add a message handler to save the message in a big log.
|
|
|
|
$data = [];
|
|
|
|
if(str_starts_with($message, '/')) {
|
|
$data = $this->checkGameCommando($message, $player);
|
|
} else {
|
|
$data = $this->checkConsoleCommando($message, $player);
|
|
}
|
|
|
|
return $data;
|
|
}
|
|
|
|
private function getRechten(Player $player): array
|
|
{
|
|
$settingName = SessionSettingType::tryFrom('RightsForPlayer' . $player->getScreen());
|
|
|
|
if (!$settingName) {
|
|
return [];
|
|
}
|
|
|
|
$setting = $this->sessionSettingRepository->getSetting($player->getSession(), $settingName, $player);
|
|
if (!$setting || !$setting->getValue()) {
|
|
return [];
|
|
}
|
|
|
|
return json_decode($setting->getValue(), true) ?? [];
|
|
}
|
|
|
|
private function checkGameCommando(string $message, Player $player) : array
|
|
{
|
|
$messagePart = explode(' ', $message);
|
|
|
|
$rechten = $this->getRechten($player);
|
|
|
|
switch($messagePart[0]) {
|
|
case '/chat':
|
|
if(!in_array('chat', $rechten))
|
|
return ['result' => ['Unknown command']];
|
|
|
|
if($this->handleChatMessage($message, $player))
|
|
return ['result' => ['succesfully send']];
|
|
else
|
|
return ['result' => ['Error sending']];
|
|
case '/help':
|
|
return ['result' => $this->getHelpCommand($rechten)];
|
|
case '/decode':
|
|
if(!in_array('decode', $rechten))
|
|
return ['result' => ['Unknown command']];
|
|
|
|
return ['result' => [$this->handleDecodeMessage($messagePart[1], $player)]];
|
|
case '/verify':
|
|
if(!in_array('verify', $rechten))
|
|
return ['result' => ['Unknown command']];
|
|
|
|
$result = $this->handleVerifyMessage($message, $player);
|
|
return ['result' => [$result]];
|
|
default:
|
|
return ['result' => ['Unknown command']];
|
|
}
|
|
}
|
|
|
|
private function checkConsoleCommando(string $message, Player $player, bool $sudo = false) : array
|
|
{
|
|
$messagePart = explode(' ', $message);
|
|
$rechten = $this->getRechten($player);
|
|
switch($messagePart[0]) {
|
|
case 'help':
|
|
return ['result' => $this->getHelpCommand($rechten)];
|
|
case 'ls':
|
|
if(!in_array('ls', $rechten))
|
|
return ['result' => ['Unknown command']];
|
|
|
|
$files = $this->getAllCurrentFilesInDirectory($player);
|
|
return ['result' => $files];
|
|
case 'cd':
|
|
if(!in_array('cd', $rechten))
|
|
return ['result' => ['Unknown command']];
|
|
|
|
$pwd = $this->playerService->getCurrentPwdOfPlayer($player);
|
|
if(!$pwd)
|
|
return ['result' => ['Unknown command']];
|
|
$newLocation = $this->goToNewDir($pwd, $messagePart[1], $player);
|
|
|
|
if($newLocation === false)
|
|
return ['result' => ['Unknown path']];
|
|
|
|
$this->playerService->saveCurrentPwdOfPlayer($player, $newLocation);
|
|
return ['result' => ['Path: ' . $newLocation]];
|
|
case 'pwd':
|
|
if(!in_array('pwd', $rechten))
|
|
return ['result' => ['Unknown command']];
|
|
|
|
$pwd = $this->playerService->getCurrentPwdOfPlayer($player);
|
|
return ['result' => ['Path: ' . $pwd]];
|
|
case 'rm':
|
|
if(!in_array('rm', $rechten))
|
|
return ['result' => ['Unknown command']];
|
|
|
|
$pwd = $this->playerService->getCurrentPwdOfPlayer($player);
|
|
if(!$pwd)
|
|
return ['result' => ['Unknown command']];
|
|
|
|
if (!isset($messagePart[1])) {
|
|
return ['result' => ['Usage: rm {filename}']];
|
|
}
|
|
|
|
$filename = $messagePart[1];
|
|
$fullPath = ($pwd === '/' ? '' : $pwd) . '/' . $filename;
|
|
|
|
if(!$this->isAllowedToRemove($fullPath, $player, $sudo))
|
|
return ['result' => ['You are not allowed to remove this file.']];
|
|
|
|
$this->playerService->addDeletedFileToSession($player, $fullPath);
|
|
return ['result' => ['File removed: ' . $filename]];
|
|
case 'sudo':
|
|
if(!in_array('sudo', $rechten))
|
|
return ['result' => ['Unknown command']];
|
|
|
|
$sudo = array_shift($messagePart);
|
|
$message = implode(' ', $messagePart);
|
|
|
|
return $this->checkConsoleCommando($message, $player, true);
|
|
default:
|
|
return ['result' => ['Unknown command']];
|
|
}
|
|
}
|
|
|
|
private function getHelpCommand(mixed $rechten) : array
|
|
{
|
|
$messages = [];
|
|
|
|
foreach($rechten as $recht) {
|
|
switch($recht) {
|
|
case 'chat':
|
|
$messages[] = '/chat';
|
|
$messages[] = ' Use /chat {message} to send the message to the other agents.';
|
|
$messages[] = ' If you want to send a message specifically to one other agent, use the id of the agent after /chat, like /chat 6 {message}';
|
|
$messages[] = ' This will send the message only to agent with id 6.';
|
|
$messages[] = ' USAGE: /chat {message}';
|
|
$messages[] = ' USAGE: /chat 6 {message}';
|
|
$messages[] = '';
|
|
break;
|
|
case 'help':
|
|
$messages[] = '/help';
|
|
$messages[] = ' This shows this help.';
|
|
$messages[] = ' USAGE: /help';
|
|
$messages[] = '';
|
|
break;
|
|
case 'decode':
|
|
$messages[] = '/decode';
|
|
$messages[] = ' This message will decode the message followed by it.';
|
|
$messages[] = ' Every agent has a different way to decode messages. This is a security measure. The AI Virus has no access to all decoders.';
|
|
$messages[] = ' USAGE: /decode {message}';
|
|
$messages[] = '';
|
|
break;
|
|
case 'pwd':
|
|
$messages[] = 'pwd';
|
|
$messages[] = ' This message will let you know what your current location is.';
|
|
$messages[] = ' It will show you the folder you are in so you can continue navigating the server.';
|
|
$messages[] = ' USAGE: pwd';
|
|
$messages[] = '';
|
|
break;
|
|
case 'cat':
|
|
$messages[] = 'cat';
|
|
$messages[] = ' To read a file, use cat {filename}.';
|
|
$messages[] = ' This will print the full content of the file on the screen.';
|
|
$messages[] = ' USAGE: cat {filename}';
|
|
$messages[] = '';
|
|
break;
|
|
case 'ls':
|
|
$messages[] = 'ls';
|
|
$messages[] = ' To show all the files in the current directory, use ls.';
|
|
$messages[] = ' This will print the full list of directories and files of the current location on your screen.';
|
|
$messages[] = ' USAGE: ls';
|
|
$messages[] = '';
|
|
break;
|
|
case 'rm':
|
|
$messages[] = 'rm';
|
|
$messages[] = ' Use rm to delete a file.';
|
|
$messages[] = ' Be careful with this command. It can not be undone and we do not want to lose any valuable data.';
|
|
$messages[] = ' USAGE: rm {filename}';
|
|
$messages[] = '';
|
|
break;
|
|
case 'cd':
|
|
$messages[] = 'cd';
|
|
$messages[] = ' Use cd to move to a different directory.';
|
|
$messages[] = ' You can go into a folder by using cd {foldername}, or a folder up by using "cd ..".';
|
|
$messages[] = ' Using cd / moves you to the root directory.';
|
|
$messages[] = ' USAGE: cd {directory}';
|
|
$messages[] = '';
|
|
break;
|
|
case 'sudo':
|
|
$messages[] = 'sudo';
|
|
$messages[] = ' If you do not have enough rights to execute a command, you can use sudo to execute it as root.';
|
|
$messages[] = ' This is only possible for verified users. To verify yourself, use the /verify command.';
|
|
$messages[] = ' USAGE: sudo {command}';
|
|
$messages[] = '';
|
|
break;
|
|
case 'verify':
|
|
$messages[] = '/verify';
|
|
$messages[] = ' You can verify yourself by using this command.';
|
|
$messages[] = ' Use this command and follow instructions to verify yourself.';
|
|
$messages[] = ' USAGE: /verify';
|
|
$messages[] = '';
|
|
break;
|
|
}
|
|
}
|
|
|
|
return $messages;
|
|
}
|
|
|
|
private function handleChatMessage(string $message, Player $player) : bool
|
|
{
|
|
$messageParts = explode(' ', $message);
|
|
$toSingle = false;
|
|
|
|
if (isset($messageParts[1]) &&
|
|
is_numeric($messageParts[1]) &&
|
|
$messageParts[1] >= 1 &&
|
|
$messageParts[1] <= $player->getSession()->getGame()->getNumberOfPlayers()) {
|
|
|
|
$toSingle = true;
|
|
}
|
|
|
|
$chatMessage = array_shift($messageParts);
|
|
$sendTo = 0;
|
|
|
|
if ($toSingle) {
|
|
$sendTo = array_shift($messageParts);
|
|
$chatMessage = array_shift($messageParts);
|
|
}
|
|
|
|
$message = $player->getUser()->getUsername() . ': ' . $chatMessage . ' ';
|
|
foreach($messageParts as $messagePart) {
|
|
$message .= $messagePart . ' ';
|
|
}
|
|
|
|
$message = trim($message);
|
|
|
|
$activeGame = $player->getSession()?->getId();
|
|
|
|
if(is_null($activeGame))
|
|
return false;
|
|
|
|
$topic = $_ENV['MERCURE_TOPIC_BASE'] . '/game/hub-' . $activeGame;
|
|
$this->hub->publish(new Update($topic, json_encode([$sendTo, $message])));
|
|
|
|
$this->updateChatTracking($player, (int)$sendTo);
|
|
|
|
$this->checkAndRegenerateVerifyCodes($player, $chatMessage . ' ' . implode(' ', $messageParts));
|
|
|
|
return true;
|
|
}
|
|
|
|
private function checkAndRegenerateVerifyCodes(Player $player, string $messageContent): void
|
|
{
|
|
$screen = $player->getScreen();
|
|
$session = $player->getSession();
|
|
|
|
$verifyCodesSettingName = SessionSettingType::tryFrom('VerifyCodesForPlayer' . $screen);
|
|
|
|
if (!$verifyCodesSettingName) {
|
|
return;
|
|
}
|
|
|
|
$setting = $this->sessionSettingRepository->getSetting($session, $verifyCodesSettingName, $player);
|
|
if (!$setting) {
|
|
return;
|
|
}
|
|
|
|
$codes = json_decode($setting->getValue() ?? '[]', true) ?? [];
|
|
$regenerated = false;
|
|
|
|
foreach ($codes as $targetPlayerScreen => $code) {
|
|
if (str_contains($messageContent, (string)$code)) {
|
|
$codes[$targetPlayerScreen] = bin2hex(random_bytes(3));
|
|
$regenerated = true;
|
|
}
|
|
}
|
|
|
|
if ($regenerated) {
|
|
$setting->setValue(json_encode($codes));
|
|
$this->entityManager->persist($setting);
|
|
$this->entityManager->flush();
|
|
|
|
// Notify the player that their codes have changed
|
|
$topic = $_ENV['MERCURE_TOPIC_BASE'] . '/game/hub-' . $session->getId();
|
|
$notification = "Security Alert: One of your verify codes was shared and has been regenerated.";
|
|
// We send it only to this player (screen)
|
|
$this->hub->publish(new Update($topic, json_encode([$screen, $notification])));
|
|
}
|
|
}
|
|
|
|
private function updateChatTracking(Player $player, int $sendTo): void
|
|
{
|
|
$rights = $this->getRechten($player);
|
|
if(in_array('verify', $rights))
|
|
return;
|
|
|
|
$trackingSettingName = SessionSettingType::tryFrom('ChatTrackingForPlayer' . $player->getScreen());
|
|
|
|
if (!$trackingSettingName) {
|
|
return;
|
|
}
|
|
|
|
$setting = $this->sessionSettingRepository->getSetting($player->getSession(), $trackingSettingName, $player);
|
|
if (!$setting) {
|
|
$setting = new SessionSetting();
|
|
$setting->setSession($player->getSession());
|
|
$setting->setPlayer($player);
|
|
$setting->setName($trackingSettingName);
|
|
$setting->setValue(json_encode([]));
|
|
}
|
|
|
|
$tracking = json_decode($setting->getValue() ?? '[]', true) ?? [];
|
|
if (!in_array($sendTo, $tracking)) {
|
|
$tracking[] = $sendTo;
|
|
$setting->setValue(json_encode($tracking));
|
|
$this->entityManager->persist($setting);
|
|
$this->entityManager->flush();
|
|
|
|
$this->checkAndGrantVerifyRight($player, $tracking);
|
|
}
|
|
}
|
|
|
|
private function checkAndGrantVerifyRight(Player $player, array $tracking): void
|
|
{
|
|
$screen = $player->getScreen();
|
|
$requiredTargets = [0]; // Everyone
|
|
$numPlayers = $player->getSession()->getGame()->getNumberOfPlayers();
|
|
for ($i = 1; $i <= $numPlayers; $i++) {
|
|
if ($i !== $screen) {
|
|
$requiredTargets[] = $i;
|
|
}
|
|
}
|
|
|
|
// Check if all required targets are in tracking
|
|
foreach ($requiredTargets as $target) {
|
|
if (!in_array($target, $tracking)) {
|
|
return;
|
|
}
|
|
}
|
|
|
|
// Grant verify right
|
|
$rightsSettingName = SessionSettingType::tryFrom('RightsForPlayer' . $screen);
|
|
|
|
if (!$rightsSettingName) {
|
|
return;
|
|
}
|
|
|
|
$setting = $this->sessionSettingRepository->getSetting($player->getSession(), $rightsSettingName, $player);
|
|
if (!$setting) {
|
|
return; // Should have been initialized
|
|
}
|
|
|
|
$rights = json_decode($setting->getValue() ?? '[]', true) ?? [];
|
|
$newRights = ['verify', 'cat'];
|
|
|
|
$updated = false;
|
|
foreach ($newRights as $newRight) {
|
|
if (!in_array($newRight, $rights)) {
|
|
$rights[] = $newRight;
|
|
$updated = true;
|
|
}
|
|
}
|
|
|
|
if ($updated) {
|
|
$setting->setValue(json_encode($rights));
|
|
$this->entityManager->persist($setting);
|
|
$this->entityManager->flush();
|
|
}
|
|
}
|
|
|
|
private function handleDecodeMessage(string $message, Player $player)
|
|
{
|
|
$userNumber = $player->getScreen();
|
|
|
|
preg_match('/\d+/', $message, $matches);
|
|
$num = $matches[0] ?? null;
|
|
$randomString = $this->generateRandomString(250, 500);
|
|
|
|
if(is_null($num) || $num != $userNumber)
|
|
return $randomString;
|
|
|
|
foreach (DecodeMessage::cases() as $decodeMessage) {
|
|
if ($decodeMessage->name === $message) {
|
|
return $decodeMessage->value;
|
|
}
|
|
}
|
|
|
|
return $randomString;
|
|
}
|
|
|
|
private function generateRandomString(int $min, int $max): string
|
|
{
|
|
$characters = '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ ';
|
|
$charactersLength = strlen($characters);
|
|
$randomString = '';
|
|
$length = random_int($min, $max);
|
|
for ($i = 0; $i < $length; $i++) {
|
|
$randomString .= $characters[random_int(0, $charactersLength - 1)];
|
|
}
|
|
return $randomString;
|
|
}
|
|
|
|
private function handleVerifyMessage(string $message, Player $player) : string
|
|
{
|
|
$messageParts = explode(' ', $message);
|
|
if (count($messageParts) < 2) {
|
|
return 'Usage: /verify {code}';
|
|
}
|
|
|
|
$code = $messageParts[1];
|
|
$screen = $player->getScreen();
|
|
$session = $player->getSession();
|
|
|
|
$progressSettingName = SessionSettingType::tryFrom('VerificationProgressForPlayer' . $screen);
|
|
|
|
if (!$progressSettingName) {
|
|
return 'Error: Invalid player screen.';
|
|
}
|
|
|
|
$progressSetting = $this->sessionSettingRepository->getSetting($session, $progressSettingName, $player);
|
|
if (!$progressSetting) {
|
|
return 'Error: Verification progress setting not found.';
|
|
}
|
|
|
|
$progress = json_decode($progressSetting->getValue() ?? '[]', true) ?? [];
|
|
|
|
$verifiedBy = null;
|
|
foreach ($session->getPlayers() as $otherPlayer) {
|
|
if ($otherPlayer->getId() === $player->getId()) {
|
|
continue;
|
|
}
|
|
|
|
$otherScreen = $otherPlayer->getScreen();
|
|
$codesSettingName = SessionSettingType::tryFrom('VerifyCodesForPlayer' . $otherScreen);
|
|
|
|
if (!$codesSettingName) {
|
|
continue;
|
|
}
|
|
|
|
$codesSetting = $this->sessionSettingRepository->getSetting($session, $codesSettingName, $otherPlayer);
|
|
if (!$codesSetting) {
|
|
continue;
|
|
}
|
|
|
|
$codes = json_decode($codesSetting->getValue() ?? '[]', true) ?? [];
|
|
if (isset($codes[$screen]) && $codes[$screen] === $code) {
|
|
$verifiedBy = $otherScreen;
|
|
break;
|
|
}
|
|
}
|
|
|
|
if ($verifiedBy !== null) {
|
|
if (!in_array($verifiedBy, $progress)) {
|
|
$progress[] = $verifiedBy;
|
|
$progressSetting->setValue(json_encode($progress));
|
|
$this->entityManager->persist($progressSetting);
|
|
$this->entityManager->flush();
|
|
|
|
$response = 'You have been successfully verified by Agent ' . $verifiedBy . '.';
|
|
|
|
if (count($progress) >= 2) {
|
|
$this->grantVerificationRights($player);
|
|
$response .= ' You have received additional rights!';
|
|
}
|
|
|
|
return $response;
|
|
} else {
|
|
return 'You were already verified by Agent ' . $verifiedBy . '.';
|
|
}
|
|
}
|
|
|
|
return 'Invalid verification code.';
|
|
}
|
|
|
|
private function grantVerificationRights(Player $player): void
|
|
{
|
|
$screen = $player->getScreen();
|
|
$rightsSettingName = SessionSettingType::tryFrom('RightsForPlayer' . $screen);
|
|
|
|
if (!$rightsSettingName) {
|
|
return;
|
|
}
|
|
|
|
$setting = $this->sessionSettingRepository->getSetting($player->getSession(), $rightsSettingName, $player);
|
|
if (!$setting) {
|
|
return;
|
|
}
|
|
|
|
$rights = json_decode($setting->getValue() ?? '[]', true) ?? [];
|
|
$newRights = ['cd', 'decode'];
|
|
|
|
$updated = false;
|
|
foreach ($newRights as $newRight) {
|
|
if (!in_array($newRight, $rights)) {
|
|
$rights[] = $newRight;
|
|
$updated = true;
|
|
}
|
|
}
|
|
|
|
if ($updated) {
|
|
$setting->setValue(json_encode($rights));
|
|
$this->entityManager->persist($setting);
|
|
$this->entityManager->flush();
|
|
|
|
$this->checkIfAllPlayersVerified($player);
|
|
}
|
|
}
|
|
|
|
private function checkIfAllPlayersVerified(Player $player): void
|
|
{
|
|
$session = $player->getSession();
|
|
$everyoneVerifiedSetting = $this->sessionSettingRepository->getSetting($session, SessionSettingType::EVERYONE_VERIFIED, $player);
|
|
|
|
if ($everyoneVerifiedSetting && $everyoneVerifiedSetting->getValue() === 'true') {
|
|
return;
|
|
}
|
|
|
|
$allVerified = true;
|
|
foreach ($session->getPlayers() as $otherPlayer) {
|
|
$otherScreen = $otherPlayer->getScreen();
|
|
$progressSettingName = SessionSettingType::tryFrom('VerificationProgressForPlayer' . $otherScreen);
|
|
|
|
if (!$progressSettingName) {
|
|
continue;
|
|
}
|
|
|
|
$progressSetting = $this->sessionSettingRepository->getSetting($session, $progressSettingName, $otherPlayer);
|
|
$progress = json_decode($progressSetting?->getValue() ?? '[]', true) ?? [];
|
|
|
|
if (count($progress) < $session->getGame()->getNumberOfPlayers() - 1) {
|
|
$allVerified = false;
|
|
break;
|
|
}
|
|
}
|
|
|
|
if ($allVerified) {
|
|
if (!$everyoneVerifiedSetting) {
|
|
$everyoneVerifiedSetting = new SessionSetting();
|
|
$everyoneVerifiedSetting->setSession($session);
|
|
$everyoneVerifiedSetting->setPlayer($player);
|
|
$everyoneVerifiedSetting->setName(SessionSettingType::EVERYONE_VERIFIED);
|
|
}
|
|
$everyoneVerifiedSetting->setValue('true');
|
|
$this->entityManager->persist($everyoneVerifiedSetting);
|
|
$this->entityManager->flush();
|
|
|
|
$topic = $_ENV['MERCURE_TOPIC_BASE'] . '/game/hub-' . $session->getId();
|
|
$message = "Mainframe Help Modus: Agents Doyle, Vega and Lennox rapports have been updated with coded messages.";
|
|
$this->hub->publish(new Update($topic, json_encode([0, $message])));
|
|
}
|
|
}
|
|
|
|
private function goToNewDir(string $pwd, string $newPwd, Player $player) : string|bool
|
|
{
|
|
$allPossiblePaths = $this->getAllPossiblePaths($player);
|
|
|
|
$dirParts = explode('/', $newPwd);
|
|
|
|
$int = count($dirParts);
|
|
|
|
if($dirParts[0] == '') {
|
|
$newDir = '';
|
|
$startPart = 1;
|
|
} else {
|
|
$newDir = $pwd;
|
|
$startPart = 0;
|
|
}
|
|
|
|
for($i = $startPart; $i < $int; $i++) {
|
|
if($dirParts[$i] == '..')
|
|
$newDir = $this->getPrevPath($newDir);
|
|
else
|
|
$newDir .= '/' . $dirParts[$i];
|
|
|
|
if(!in_array($newDir, $allPossiblePaths))
|
|
return false;
|
|
}
|
|
|
|
return $newDir;
|
|
}
|
|
|
|
private function getPrevPath(string $pwd) : string
|
|
{
|
|
$pwdParts = explode('/', $pwd);
|
|
array_pop($pwdParts);
|
|
$pwd = implode('/', $pwdParts);
|
|
return $pwd;
|
|
}
|
|
|
|
private function getAllPossiblePaths(Player $player) : array
|
|
{
|
|
$paths = [];
|
|
|
|
$paths[] = '/';
|
|
$paths[] = '/var';
|
|
$paths[] = '/var/arrest';
|
|
$paths[] = '/var/www';
|
|
$paths[] = '/var/marriage';
|
|
$paths[] = '/var/rapports';
|
|
$paths[] = '/var/linking';
|
|
|
|
$paths[] = '/etc';
|
|
$paths[] = '/etc/short';
|
|
$paths[] = '/etc/long';
|
|
$paths[] = '/etc/arrest';
|
|
$paths[] = '/etc/power';
|
|
$paths[] = '/etc/break';
|
|
$paths[] = '/etc/handle';
|
|
$paths[] = '/etc/freak';
|
|
$paths[] = '/etc/host';
|
|
|
|
$paths[] = '/home';
|
|
|
|
$playerNames = ['root', 'Luke', 'Charles', 'William', 'Peter'];
|
|
|
|
$players = $player->getSession()->getPlayers();
|
|
|
|
foreach($players as $player) {
|
|
$playerNames[] = $player->getUser()->getUsername();
|
|
}
|
|
|
|
$playerNames = array_unique($playerNames);
|
|
|
|
foreach($playerNames as $name) {
|
|
$paths[] = '/home/' . $name;
|
|
}
|
|
|
|
return $paths;
|
|
}
|
|
|
|
private function isAllowedToRemove(string $file, Player $player, bool $sudo) : bool
|
|
{
|
|
if(!$this->fileExists($file, $player))
|
|
return false;
|
|
|
|
if(str_starts_with($file, '/var/rapports/'))
|
|
return false;
|
|
|
|
$rights = $this->getRechten($player);
|
|
|
|
if(in_array('sudo', $rights) || $sudo)
|
|
return true;
|
|
|
|
$sudoFiles = [
|
|
'/var/arrest/handle.sh',
|
|
'/var/arrest/cell.sh',
|
|
'/var/marriage/divorce.sh',
|
|
];
|
|
|
|
return !in_array($file, $sudoFiles);
|
|
}
|
|
|
|
private function fileExists(string $file, Player $player) : bool
|
|
{
|
|
$files = $this->getAllPossibleFiles($player);
|
|
|
|
if(in_array($file, $files))
|
|
return true;
|
|
|
|
return false;
|
|
}
|
|
|
|
private function getAllPossibleFiles(Player $player = null) : array
|
|
{
|
|
$files = [];
|
|
|
|
$files[] = '/var/arrest/handle.sh';
|
|
$files[] = '/var/arrest/bars.sh';
|
|
$files[] = '/var/arrest/cell.sh';
|
|
$files[] = '/var/marriage/share.sh';
|
|
$files[] = '/var/marriage/divorce.sh';
|
|
$files[] = '/var/rapports/095_07-14.txt';
|
|
$files[] = '/var/rapports/007_19-52.txt';
|
|
$files[] = '/var/rapports/083_25-39.txt';
|
|
$files[] = '/var/rapports/019_31-11.txt';
|
|
$files[] = '/var/rapports/075_46-77.txt';
|
|
$files[] = '/var/rapports/031_53-28.txt';
|
|
$files[] = '/var/rapports/072_61-05.txt';
|
|
$files[] = '/var/rapports/064_72-90.txt';
|
|
$files[] = '/var/rapports/091_81-33.txt';
|
|
$files[] = '/var/rapports/079_89-47.txt';
|
|
$files[] = '/var/rapports/098_92-14.txt';
|
|
$files[] = '/var/rapports/012_94-31.txt';
|
|
$files[] = '/var/rapports/016_98-07.txt';
|
|
$files[] = '/var/rapports/087_102-45.txt';
|
|
$files[] = '/var/rapports/094_110-19.txt';
|
|
$files[] = '/var/rapports/063_117-56.txt';
|
|
$files[] = '/var/rapports/017_123-88.txt';
|
|
$files[] = '/var/rapports/093_138-24.txt';
|
|
$files[] = '/var/rapports/001_145-93.txt';
|
|
$files[] = '/var/rapports/index.txt';
|
|
|
|
$players = $player->getSession()->getPlayers();
|
|
|
|
foreach($players as $player) {
|
|
$files[] = '/var/home/' . $player->getUser()->getUsername() . '/verifyCodes.txt';
|
|
}
|
|
|
|
return $files;
|
|
}
|
|
|
|
private function getAllCurrentFilesInDirectory(Player $player) : array
|
|
{
|
|
$pwd = $this->playerService->getCurrentPwdOfPlayer($player);
|
|
if (!$pwd) {
|
|
return [];
|
|
}
|
|
|
|
$allPaths = $this->getAllPossiblePaths($player);
|
|
$allFiles = $this->getAllPossibleFiles();
|
|
$deletedFiles = $this->playerService->getDeletedFilesOfSession($player);
|
|
|
|
$entries = [];
|
|
|
|
// Find directories in current pwd
|
|
foreach ($allPaths as $path) {
|
|
if ($path === $pwd) {
|
|
continue;
|
|
}
|
|
|
|
// Check if $path is a direct child of $pwd
|
|
$parent = $this->getPrevPath($path);
|
|
if ($parent === $pwd) {
|
|
$parts = explode('/', $path);
|
|
$entries[] = [end($parts) . '/', 'dir'];
|
|
}
|
|
}
|
|
|
|
// Find files in current pwd
|
|
foreach ($allFiles as $file) {
|
|
if (in_array($file, $deletedFiles)) {
|
|
continue;
|
|
}
|
|
|
|
$parent = $this->getPrevPath($file);
|
|
if ($parent === $pwd) {
|
|
$parts = explode('/', $file);
|
|
$entries[] = [end($parts), 'file'];
|
|
}
|
|
}
|
|
|
|
sort($entries);
|
|
return $entries;
|
|
}
|
|
}
|