Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

ENH Rendering scalars in ArrayList in templates #11238

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion src/View/SSViewer_DataPresenter.php
Original file line number Diff line number Diff line change
Expand Up @@ -376,7 +376,7 @@ protected function getValueSource($property)

// Check if the method to-be-called exists on the target object - if so, don't check any further
// injection locations
$on = $this->itemIterator ? $this->itemIterator->current() : $this->item;
$on = $this->getItem();
if (is_object($on) && (isset($on->$property) || method_exists($on, $property ?? ''))) {
return [];
}
Expand Down
27 changes: 23 additions & 4 deletions src/View/SSViewer_Scope.php
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,11 @@
use ArrayIterator;
use Countable;
use Iterator;
use SilverStripe\ORM\FieldType\DBBoolean;
use SilverStripe\ORM\FieldType\DBText;
use SilverStripe\ORM\FieldType\DBFloat;
use SilverStripe\ORM\FieldType\DBInt;
use SilverStripe\ORM\FieldType\DBField;

/**
* This tracks the current scope for an SSViewer instance. It has three goals:
Expand Down Expand Up @@ -121,7 +126,11 @@ public function __construct($item, SSViewer_Scope $inheritedScope = null)
*/
public function getItem()
{
return $this->itemIterator ? $this->itemIterator->current() : $this->item;
$item = $this->itemIterator ? $this->itemIterator->current() : $this->item;
if (is_scalar($item)) {
$item = $this->convertScalarToDBField($item);
}
return $item;
}

/**
Expand Down Expand Up @@ -176,7 +185,7 @@ public function resetLocalScope()
*/
public function getObj($name, $arguments = [], $cache = false, $cacheName = null)
{
$on = $this->itemIterator ? $this->itemIterator->current() : $this->item;
$on = $this->getItem();
return $on->obj($name, $arguments, $cache, $cacheName);
}

Expand Down Expand Up @@ -240,7 +249,7 @@ public function obj($name, $arguments = [], $cache = false, $cacheName = null)
*/
public function self()
{
$result = $this->itemIterator ? $this->itemIterator->current() : $this->item;
$result = $this->getItem();
$this->resetLocalScope();

return $result;
Expand Down Expand Up @@ -338,7 +347,7 @@ public function next()
*/
public function __call($name, $arguments)
{
$on = $this->itemIterator ? $this->itemIterator->current() : $this->item;
$on = $this->getItem();
$retval = $on ? $on->$name(...$arguments) : null;

$this->resetLocalScope();
Expand Down Expand Up @@ -368,4 +377,14 @@ protected function getUpIndex()
{
return $this->upIndex;
}

private function convertScalarToDBField(bool|string|float|int $value): DBField
{
return match (gettype($value)) {
'boolean' => DBBoolean::create()->setValue($value),
'string' => DBText::create()->setValue($value),
'double' => DBFloat::create()->setValue($value),
'integer' => DBInt::create()->setValue($value),
};
}
}
12 changes: 12 additions & 0 deletions tests/php/View/SSViewerTest.php
Original file line number Diff line number Diff line change
Expand Up @@ -2218,4 +2218,16 @@ public function testFromStringCaching()
$this->assertTrue(file_exists($cacheFile ?? ''), 'Cache file wasn\'t created when it was meant to');
unlink($cacheFile ?? '');
}

public function testPrimitivesConvertedToDBFields()
{
$data = new ArrayData([
// null value should not be rendered, though should also not throw exception
'Foo' => new ArrayList(['hello', true, 456, 7.89, null])
]);
$this->assertEqualIgnoringWhitespace(
'hello 1 456 7.89',
$this->render('<% loop $Foo %>$Me<% end_loop %>', $data)
);
}
}
Loading