fix: movie_folder download preference not saving when unchecked

This commit is contained in:
2025-05-19 20:37:10 -05:00
parent c47b1fc23f
commit 70189b95e1
6 changed files with 126 additions and 11 deletions

View File

@@ -0,0 +1,13 @@
<?php
namespace App\User\Action\Command;
use OneToMany\RichBundle\Contract\CommandInterface;
/** @implements CommandInterface<SaveUserMediaPreferencesCommand> */
class SaveUserDownloadPreferencesCommand implements CommandInterface
{
public function __construct(
public string $movie_folder,
) {}
}

View File

@@ -0,0 +1,52 @@
<?php
namespace App\User\Action\Handler;
use App\User\Action\Command\SaveUserMediaPreferencesCommand;
use App\User\Action\Result\SaveUserDownloadPreferencesResult;
use App\User\Action\Result\SaveUserMediaPreferencesResult;
use App\User\Framework\Entity\User;
use App\User\Framework\Entity\UserPreference;
use App\User\Framework\Repository\PreferencesRepository;
use Doctrine\ORM\EntityManagerInterface;
use OneToMany\RichBundle\Contract\CommandInterface as C;
use OneToMany\RichBundle\Contract\HandlerInterface;
use OneToMany\RichBundle\Contract\ResultInterface as R;
use Symfony\Bundle\SecurityBundle\Security;
/** @implements HandlerInterface<SaveUserMediaPreferencesCommand> */
class SaveUserDownloadPreferencesHandler implements HandlerInterface
{
public function __construct(
private readonly EntityManagerInterface $entityManager,
private readonly PreferencesRepository $preferenceRepository,
private readonly Security $token,
) {}
public function handle(C $command): R
{
/** @var User $user */
$user = $this->token->getUser();
foreach ($command as $preference => $value) {
if ($user->hasUserPreference($preference)) {
$user->updateUserPreference($preference, $value);
$this->entityManager->flush();
continue;
}
$preference = $this->preferenceRepository->find($preference);
$user->addUserPreference(
(new UserPreference())
->setUser($user)
->setPreference($preference)
->setPreferenceValue($value)
);
}
$this->entityManager->flush();
return new SaveUserDownloadPreferencesResult($user->getDownloadPreferences());
}
}

View File

@@ -0,0 +1,28 @@
<?php
namespace App\User\Action\Input;
use App\User\Action\Command\SaveUserDownloadPreferencesCommand;
use OneToMany\RichBundle\Attribute\SourceRequest;
use OneToMany\RichBundle\Attribute\SourceSecurity;
use OneToMany\RichBundle\Contract\CommandInterface as C;
use OneToMany\RichBundle\Contract\InputInterface;
/** @implements InputInterface<SaveUserDownloadPreferencesInput, SaveUserDownloadPreferencesCommand> */
class SaveUserDownloadPreferencesInput implements InputInterface
{
public function __construct(
#[SourceSecurity]
public mixed $userId,
#[SourceRequest('movie_folder', nullify: true)]
public bool $movieFolder,
) {}
public function toCommand(): C
{
return new SaveUserDownloadPreferencesCommand(
$this->movieFolder,
);
}
}

View File

@@ -0,0 +1,14 @@
<?php
namespace App\User\Action\Result;
use Doctrine\Common\Collections\Collection;
use OneToMany\RichBundle\Contract\ResultInterface;
/** @implements ResultInterface */
class SaveUserDownloadPreferencesResult implements ResultInterface
{
public function __construct(
public array $downloadPreferences,
) {}
}

View File

@@ -5,7 +5,9 @@ declare(strict_types=1);
namespace App\User\Framework\Controller\Web; namespace App\User\Framework\Controller\Web;
use Aimeos\Map; use Aimeos\Map;
use App\User\Action\Handler\SaveUserDownloadPreferencesHandler;
use App\User\Action\Handler\SaveUserMediaPreferencesHandler; use App\User\Action\Handler\SaveUserMediaPreferencesHandler;
use App\User\Action\Input\SaveUserDownloadPreferencesInput;
use App\User\Action\Input\SaveUserMediaPreferencesInput; use App\User\Action\Input\SaveUserMediaPreferencesInput;
use App\User\Framework\Entity\User; use App\User\Framework\Entity\User;
use App\User\Framework\Entity\UserPreference; use App\User\Framework\Entity\UserPreference;
@@ -27,6 +29,7 @@ class PreferencesController extends AbstractController
private readonly PreferencesRepository $preferencesRepository, private readonly PreferencesRepository $preferencesRepository,
private readonly SaveUserMediaPreferencesHandler $saveUserMediaPreferencesHandler, private readonly SaveUserMediaPreferencesHandler $saveUserMediaPreferencesHandler,
private readonly HubInterface $hub, private readonly HubInterface $hub,
private readonly SaveUserDownloadPreferencesHandler $saveUserDownloadPreferencesHandler,
) {} ) {}
#[Route('/user/preferences', 'app_user_preferences', methods: ['GET'])] #[Route('/user/preferences', 'app_user_preferences', methods: ['GET'])]
public function mediaPreferences(): Response public function mediaPreferences(): Response
@@ -54,8 +57,9 @@ class PreferencesController extends AbstractController
SaveUserMediaPreferencesInput $input, SaveUserMediaPreferencesInput $input,
): Response ): Response
{ {
$userPreferences = $this->saveUserMediaPreferencesHandler->handle($input->toCommand())->userPreferences; $this->saveUserMediaPreferencesHandler->handle($input->toCommand());
$userPreferences = Map::from($userPreferences)->rekey(fn($preference) => $preference->getPreference()->getId()); $mediaPreferences = $this->getUser()->getMediaPreferences();
$downloadPreferences = $this->getUser()->getDownloadPreferences();
$languages = CountryLanguages::$languages; $languages = CountryLanguages::$languages;
sort($languages); sort($languages);
@@ -75,7 +79,8 @@ class PreferencesController extends AbstractController
'preferences' => $this->preferencesRepository->findEnabled(), 'preferences' => $this->preferencesRepository->findEnabled(),
'languages' => $languages, 'languages' => $languages,
'providers' => ProviderList::$providers, 'providers' => ProviderList::$providers,
'userPreferences' => $userPreferences->toArray(), 'mediaPreferences' => $mediaPreferences,
'downloadPreferences' => $downloadPreferences,
] ]
); );
} }
@@ -83,11 +88,11 @@ class PreferencesController extends AbstractController
#[Route('/user/preferences/download', 'app_save_download_preferences', methods: ['POST'])] #[Route('/user/preferences/download', 'app_save_download_preferences', methods: ['POST'])]
public function saveDownloadPreferences( public function saveDownloadPreferences(
Request $request, Request $request,
SaveUserMediaPreferencesInput $input, SaveUserDownloadPreferencesInput $input,
): Response ): Response
{ {
$userPreferences = $this->saveUserMediaPreferencesHandler->handle($input->toCommand())->userPreferences; $downloadPreferences = $this->saveUserDownloadPreferencesHandler->handle($input->toCommand())->downloadPreferences;
$userPreferences = Map::from($userPreferences)->rekey(fn($preference) => $preference->getPreference()->getId()); $mediaPreferences = $this->getUser()->getMediaPreferences();
$languages = CountryLanguages::$languages; $languages = CountryLanguages::$languages;
sort($languages); sort($languages);
@@ -97,7 +102,7 @@ class PreferencesController extends AbstractController
$this->renderView('broadcast/Alert.stream.html.twig', [ $this->renderView('broadcast/Alert.stream.html.twig', [
'alert_id' => uniqid(), 'alert_id' => uniqid(),
'title' => 'Success', 'title' => 'Success',
'message' => 'Your media preferences have been saved.', 'message' => 'Your download preferences have been saved.',
]) ])
)); ));
@@ -107,7 +112,8 @@ class PreferencesController extends AbstractController
'preferences' => $this->preferencesRepository->findEnabled(), 'preferences' => $this->preferencesRepository->findEnabled(),
'languages' => $languages, 'languages' => $languages,
'providers' => ProviderList::$providers, 'providers' => ProviderList::$providers,
'userPreferences' => $userPreferences->toArray(), 'mediaPreferences' => $mediaPreferences,
'downloadPreferences' => $downloadPreferences,
] ]
); );
} }

View File

@@ -69,11 +69,13 @@
<twig:Card title="Download Preferences" class="w-full"> <twig:Card title="Download Preferences" class="w-full">
<p class="text-gray-50 mb-2">Change how your downloads are stored.</p> <p class="text-gray-50 mb-2">Change how your downloads are stored.</p>
<form id="media_preferences" class="flex flex-col" name="media_preferences" method="post" action="{{ path('app_save_download_preferences') }}"> <form id="download_preferences" class="flex flex-col" name="download_preferences" method="post" action="{{ path('app_save_download_preferences') }}">
<div class="flex flex-row gap-2"> <div class="flex flex-row gap-2 mb-2">
<input type="checkbox" name="movie_folder" id="movie_folder" {{ downloadPreferences['movie_folder'].getPreferenceValue() == true ? 'checked' }} /> <input type="hidden" name="movie_folder" id="movie_folder_hidden" value="0" />
<input type="checkbox" name="movie_folder" id="movie_folder" value="1" {{ downloadPreferences['movie_folder'].getPreferenceValue() == true ? 'checked' }} />
<label class="text-gray-50" for="movie_folder">Store movies in a new directory?</label> <label class="text-gray-50" for="movie_folder">Store movies in a new directory?</label>
</div> </div>
<button class="px-1.5 py-1 max-w-20 rounded-md bg-green-600 text-white" type="submit">Submit</button>
</form> </form>
</twig:Card> </twig:Card>
</div> </div>