Skip to content

Commit

Permalink
LegalDocuments: Add dpro footer links for anonymous user
Browse files Browse the repository at this point in the history
  • Loading branch information
lscharmer authored and mjansenDatabay committed Dec 3, 2024
1 parent 5dab698 commit 1f63785
Show file tree
Hide file tree
Showing 7 changed files with 119 additions and 31 deletions.
14 changes: 10 additions & 4 deletions Services/DataProtection/classes/Consumer.php
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@

namespace ILIAS\DataProtection;

use ilLink;
use ILIAS\Data\URI;
use ILIAS\LegalDocuments\ConsumerToolbox\UI;
use ILIAS\LegalDocuments\ConsumerToolbox\User;
use ilDBConstants;
Expand Down Expand Up @@ -85,7 +87,7 @@ public function uses(UseSlot $slot, LazyProvide $provide): UseSlot
} else {
$slot = $slot->canWithdraw($blocks->slot()->withdrawProcess($user, $global_settings, $this->userHasWithdrawn(...)))
->hasAgreement($agreement, self::GOTO_NAME)
->showInFooter($blocks->slot()->modifyFooter($user))
->showInFooter($blocks->slot()->modifyFooter($user, self::GOTO_NAME))
->onSelfRegistration($blocks->slot()->selfRegistration($user, $build_user))
->hasOnlineStatusFilter($blocks->slot()->onlineStatusFilter($this->usersWhoDidntAgree($this->container->database())))
->hasUserManagementFields($blocks->userManagementAgreeDateField($build_user, 'dpro_agree_date', 'dpro'))
Expand All @@ -98,15 +100,19 @@ public function uses(UseSlot $slot, LazyProvide $provide): UseSlot

private function showMatchingDocument(User $user, UI $ui, Provide $legal_documents): Closure
{
return function ($footer) use ($user, $ui, $legal_documents) {
return function (Closure $footer) use ($user, $ui, $legal_documents) {
$in_footer = fn($v) => $footer('usr_agreement', $ui->txt('usr_agreement'), $v);
if (!$user->isLoggedIn()) {
return $in_footer(new URI(ilLink::_getLink(null, 'usr', [], self::GOTO_NAME)));
}
if ($user->cannotAgree()) {
return $footer;
}

$render = fn(Document $document): Footer => $footer->withAdditionalModalAndTrigger($ui->create()->modal()->roundtrip(
$render = fn(Document $document): Closure => $in_footer($ui->create()->modal()->roundtrip(
$document->content()->title(),
[$legal_documents->document()->contentAsComponent($document->content())]
), $ui->create()->button()->shy($ui->txt('usr_agreement'), ''));
));

return $user->matchingDocument()
->map($render)
Expand Down
36 changes: 35 additions & 1 deletion Services/LegalDocuments/classes/Conductor.php
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@

namespace ILIAS\LegalDocuments;

use ILIAS\UI\Component\Modal\Modal;
use ILIAS\LegalDocuments\PageFragment;
use ILIAS\DI\Container;
use ILIAS\LegalDocuments\ConsumerSlots\SelfRegistration;
Expand Down Expand Up @@ -102,7 +103,7 @@ public function logoutText(): string

public function modifyFooter(Footer $footer): Footer
{
return array_reduce($this->internal->all('footer'), fn($footer, Closure $proc) => $proc($footer), $footer);
return $this->footerBridge($footer, array_reduce($this->internal->all('footer'), fn(Closure $footer, Closure $proc) => $proc($footer), $this->collectFooterItems([]))());
}

public function agree(string $gui, string $cmd): void
Expand Down Expand Up @@ -274,4 +275,37 @@ private function createInternal(): Internal
$action
)));
}

private function footerBridge(Footer $footer, array $collection): Footer
{
$new_links = [];
$add_item = function (string $id, string $title, object $obj) use (&$footer, &$new_links): void {
if ($obj instanceof Modal) {
$footer = $footer->withAdditionalModalAndTrigger($obj, $this->container->ui()->factory()->button()->shy($title, ''));
} else {
$new_links[] = $this->container->ui()->factory()->link()->standard($title, (string) $obj);
}
};

foreach ($collection as $args) {
$add_item(...$args);
}

$old_links = $footer->getLinks();
$modals = $footer->getModals();
$new_footer = $this->container->ui()->factory()->mainControls()->footer(array_merge($old_links, $new_links), $footer->getText());
$new_footer = $footer->getPermanentURL() ? $new_footer->withPermanentURL($footer->getPermanentURL()) : $new_footer;

return array_reduce($modals, static fn(Footer $f, array $m) => $f->withAdditionalModalAndTrigger(...$m), $new_footer);
}

private function collectFooterItems(array $items): Closure
{
return function (...$args) use ($items) {
if ($args === []) {
return $items;
}
return $this->collectFooterItems(array_merge($items, [$args]));
};
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,7 @@

namespace ILIAS\LegalDocuments\ConsumerToolbox\ConsumerSlots;

use ilLink;
use ILIAS\LegalDocuments\Value\DocumentContent;
use ILIAS\UI\Component\Component;
use ILIAS\UI\Component\MainControls\Footer;
Expand All @@ -30,6 +31,7 @@
use ILIAS\LegalDocuments\Provide;
use ilTemplate;
use Closure;
use ILIAS\UI\Component\Modal\Modal;

final class ModifyFooter
{
Expand All @@ -42,28 +44,33 @@ public function __construct(
private readonly User $user,
private readonly Provide $legal_documents,
private readonly Closure $render,
private readonly Closure $create_template
private readonly Closure $create_template,
private readonly ?Closure $goto_link,
) {
}

public function __invoke(Footer $footer): Footer
public function __invoke(Closure $footer): Closure
{
return $this->user->acceptedVersion()->map(
$this->renderModal($footer)
fn($document) => $this->footer($footer, $this->renderModal($document))
)->except(
fn() => new Ok($footer)
fn() => new Ok(
!$this->goto_link || $this->user->isLoggedIn() ?
$footer :
$this->footer($footer, ($this->goto_link)())
)
)->value();
}

public function renderModal(Footer $footer): Closure
public function renderModal(DocumentContent $content): Modal
{
return fn(DocumentContent $content): Footer => $footer->withAdditionalModalAndTrigger($this->ui->create()->modal()->roundtrip($content->title(), [
return $this->ui->create()->modal()->roundtrip($content->title(), [
$this->ui->create()->legacy($this->ui->txt('usr_agreement_footer_intro')),
$this->ui->create()->divider()->horizontal(),
$this->legal_documents->document()->contentAsComponent($content),
$this->ui->create()->divider()->horizontal(),
$this->withdrawalButton(),
]), $this->ui->create()->button()->shy($this->ui->txt('usr_agreement'), ''));
]);
}

public function withdrawalButton(): Component
Expand All @@ -80,4 +87,12 @@ public function withdrawalButton(): Component

return $this->ui->create()->legacy($template->get());
}

/**
* @param URI|Modal $value
*/
private function footer(Closure $footer, object $value): Closure
{
return $footer($this->legal_documents->id(), $this->ui->txt('usr_agreement'), $value);
}
}
7 changes: 5 additions & 2 deletions Services/LegalDocuments/classes/ConsumerToolbox/Slot.php
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@

namespace ILIAS\LegalDocuments\ConsumerToolbox;

use ILIAS\Data\URI;
use ilLink;
use ILIAS\Refinery\Constraint;
use ILIAS\LegalDocuments\ConsumerToolbox\ConsumerSlots\OnlineStatusFilter;
use ILIAS\LegalDocuments\ConsumerToolbox\ConsumerSlots\SelfRegistration;
Expand Down Expand Up @@ -69,9 +71,10 @@ public function agreement(User $user, Settings $settings): Agreement
return new Agreement($user, $settings, $this->blocks->ui(), $this->blocks->routing(), $this->blocks->withRequest(...));
}

public function modifyFooter(User $user): ModifyFooter
public function modifyFooter(User $user, ?string $goto_target = null): ModifyFooter
{
return new ModifyFooter($this->blocks->ui(), $user, $this->provide, fn($arg) => $this->container->ui()->renderer()->render($arg), $this->template(...));
$link = $goto_target ? static fn() => new URI(ilLink::_getLink(null, 'usr', [], $goto_target)) : null;
return new ModifyFooter($this->blocks->ui(), $user, $this->provide, fn($arg) => $this->container->ui()->renderer()->render($arg), $this->template(...), $link);
}

/**
Expand Down
11 changes: 7 additions & 4 deletions Services/LegalDocuments/test/ConductorTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -50,6 +50,7 @@
use ilObjUser;
use ILIAS\LegalDocuments\ConsumerToolbox\Routing;
use ILIAS\Data\Result\Error;
use Closure;

require_once __DIR__ . '/ContainerMock.php';

Expand Down Expand Up @@ -140,18 +141,20 @@ public function testLogoutText(): void
public function testModifyFooter(): void
{
$footer = $this->mock(Footer::class);
$new_footer = $this->mock(Footer::class);

$modify_footer = function (Footer $f) use ($footer) {
$this->assertSame($footer, $f);
$modify_footer = function ($f) {
$this->assertInstanceOf(Closure::class, $f);
return $f;
};

$instance = new Conductor($this->mock(Container::class), $this->mockMethod(Internal::class, 'all', ['footer'], [
$container = $this->mockTree(Container::class, ['ui' => ['factory' => ['mainControls' => ['footer' => $new_footer]]]]);
$instance = new Conductor($container, $this->mockMethod(Internal::class, 'all', ['footer'], [
$modify_footer,
$modify_footer,
]), $this->mock(Routing::class));

$this->assertSame($footer, $instance->modifyFooter($footer));
$this->assertSame($new_footer, $instance->modifyFooter($footer));
}

/**
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -20,6 +20,8 @@

namespace ILIAS\LegalDocuments\ConsumerToolbox\ConsumerSlots;

use ILIAS\Data\URI;
use ILIAS\Data\Result\Error;
use ILIAS\UI\Component\Component;
use ILIAS\LegalDocuments\Value\DocumentContent;
use ilTemplate;
Expand All @@ -32,6 +34,7 @@
use ILIAS\LegalDocuments\ConsumerToolbox\ConsumerSlots\ModifyFooter;
use PHPUnit\Framework\TestCase;
use Closure;
use ILIAS\UI\Component\Modal\Modal;

require_once __DIR__ . '/../../ContainerMock.php';

Expand All @@ -46,41 +49,64 @@ public function testConstruct(): void
$this->mock(User::class),
$this->mock(Provide::class),
$this->fail(...),
$this->fail(...)
$this->fail(...),
null,
));
}

public function testInvoke(): void
{
$footer = $this->mock(Footer::class);
$footer->expects(self::once())->method('withAdditionalModalAndTrigger')->willReturn($footer);
$return = fn() => null;
$footer = fn() => $return;

$instance = new ModifyFooter(
$this->mock(UI::class),
$this->mockTree(User::class, ['acceptedVersion' => new Ok($this->mock(DocumentContent::class))]),
$this->mock(Provide::class),
fn() => 'rendered',
fn() => $this->mock(ilTemplate::class)
fn() => $this->mock(ilTemplate::class),
null,
);

$this->assertSame($footer, $instance($footer));
$this->assertSame($return, $instance($footer));
}

public function testRenderModal(): void
public function testInvokeWithGotoLink(): void
{
$footer = $this->mock(Footer::class);
$footer->expects(self::once())->method('withAdditionalModalAndTrigger')->willReturn($footer);
$dummy_uri = $this->mock(URI::class);
$return = fn() => null;
$footer = function ($id, $title, $uri) use ($dummy_uri, $return) {
$this->assertSame('foo', $id);
$this->assertSame('translated', $title);
$this->assertSame($dummy_uri, $uri);
return $return;
};

$instance = new ModifyFooter(
$this->mockTree(UI::class, ['txt' => 'translated']),
$this->mockTree(User::class, ['acceptedVersion' => new Error('Not found.'), 'isLoggedIn' => false]),
$this->mockTree(Provide::class, ['id' => 'foo']),
fn() => 'rendered',
fn() => $this->mock(ilTemplate::class),
fn() => $dummy_uri,
);

$this->assertSame($return, $instance($footer));
}

public function testRenderModal(): void
{
$instance = new ModifyFooter(
$this->mock(UI::class),
$this->mock(User::class),
$this->mock(Provide::class),
fn() => 'rendered',
fn() => $this->mock(ilTemplate::class)
fn() => $this->mock(ilTemplate::class),
null
);

$proc = $instance->renderModal($footer);
$this->assertSame($footer, $proc($this->mock(DocumentContent::class)));
$modal = $instance->renderModal($this->mock(DocumentContent::class));
$this->assertInstanceOf(Modal::class, $modal);
}

public function testWithdrawalButton(): void
Expand All @@ -94,7 +120,8 @@ public function testWithdrawalButton(): void
$this->mock(User::class),
$this->mock(Provide::class),
fn() => 'rendered',
fn() => $template
fn() => $template,
null
);

$this->assertInstanceOf(Component::class, $instance->withdrawalButton());
Expand Down
2 changes: 1 addition & 1 deletion Services/TermsOfService/classes/Consumer.php
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,7 @@ public function uses(UseSlot $slot, LazyProvide $provide): UseSlot

return $slot->canWithdraw($blocks->slot()->withdrawProcess($user, $global_settings, $this->userHasWithdrawn(...)))
->hasAgreement($blocks->slot()->agreement($user, $global_settings), self::GOTO_NAME)
->showInFooter($blocks->slot()->modifyFooter($user))
->showInFooter($blocks->slot()->modifyFooter($user, self::GOTO_NAME))
->showOnLoginPage($blocks->slot()->showOnLoginPage())
->onSelfRegistration($blocks->slot()->selfRegistration($user, $build_user))
->hasOnlineStatusFilter($blocks->slot()->onlineStatusFilter($this->usersWhoDidntAgree($this->container->database())))
Expand Down

0 comments on commit 1f63785

Please sign in to comment.