packages/deriver/tests/Unit/Deriver/Evaluator/Predicate/ControlsTest.php

1<?php
2
3declare(strict_types=1);
4
5namespace Tests\Unit\Deriver\Evaluator\Predicate;
6
7use Deriver\Deriver\BranchEvaluators;
8use Deriver\Deriver\Evaluator\Call\Evaluators;
9use Deriver\Deriver\Evaluator\Enumeration\Choices;
10use Deriver\Deriver\Evaluator\Evaluator;
11use Deriver\Deriver\Evaluator\EvaluatorConfig;
12use Deriver\Deriver\Evaluator\Index\DefinitionIndex;
13use Deriver\Deriver\Evaluator\Request\Budget;
14use Deriver\Deriver\Evaluator\Scope\Context;
15use Deriver\Deriver\Evaluator\Scope\Frame;
16use Deriver\Deriver\Evaluator\Term;
17use Deriver\Deriver\Lowerer\Declaration\Index;
18use Deriver\Deriver\MicroEvaluatorConversion;
19use Deriver\Deriver\Parser\Parser;
20use Deriver\Deriver\Parser\ParserConfig;
21use Deriver\Deriver\Resolver\Resolver;
22use Deriver\Deriver\Sources\Source;
23use PHPUnit\Framework\Attributes\CoversNothing;
24use PHPUnit\Framework\TestCase;
25
26#[CoversNothing]
27final class ControlsTest extends TestCase
28{
29    public function testApplySharesConditionsWithoutSharingTheObservedValue(): void
30    {
31        $source = 'function subject($x){if($x)return 1;return 2;}';
32        $tree = (new Resolver())->resolve((new Parser(new ParserConfig('8.3')))->parse(new Source('a.php', '<?php ' . $source)));
33        $index = new DefinitionIndex(new Index('s', [$tree]));
34        $config = new EvaluatorConfig(evaluators: array_map((new MicroEvaluatorConversion())->convert(...), BranchEvaluators::truth()));
35        $engine = new Evaluator(new Context($index, $config, new Evaluators($config->target), new Budget()));
36        $graph = $index->graph('subject');
37        self::assertNotNull($graph);
38        $frame = new Frame($graph, 'source:subject');
39        $block = $graph->returns()[0][0];
40        $controls = new \Deriver\Deriver\Evaluator\Predicate\Controls($engine);
41        $first = $controls->apply($frame, $block, Term::constant(7), 32);
42        $work = $engine->context->workUnits;
43        $second = $controls->apply($frame, $block, Term::constant(9), 32);
44        self::assertSame($work, $engine->context->workUnits);
45        self::assertSame([7], array_map(static fn (array $row) => $row[0]->native(), iterator_to_array((new Choices())->alternatives($first))));
46        self::assertSame([9], array_map(static fn (array $row) => $row[0]->native(), iterator_to_array((new Choices())->alternatives($second))));
47    }
48}
49