Passed
Push — master ( e78c48...210134 )
by Damian
14:57 queued 06:02
created

ViewableDataTest::testThemeDir()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 12
Code Lines 8

Duplication

Lines 0
Ratio 0 %

Importance

Changes 0
Metric Value
cc 1
eloc 8
c 0
b 0
f 0
nc 1
nop 0
dl 0
loc 12
rs 9.4285
1
<?php
2
3
namespace SilverStripe\View\Tests;
4
5
use SilverStripe\ORM\FieldType\DBField;
6
use SilverStripe\Dev\SapphireTest;
7
use SilverStripe\View\ArrayData;
8
use SilverStripe\View\SSViewer;
9
use SilverStripe\View\ViewableData;
10
11
/**
12
 * See {@link SSViewerTest->testCastingHelpers()} for more tests related to casting and ViewableData behaviour,
13
 * from a template-parsing perspective.
14
 */
15
class ViewableDataTest extends SapphireTest
16
{
17
18
    public function testCasting()
19
    {
20
        $htmlString = "&quot;";
21
        $textString = '"';
22
23
        $htmlField = DBField::create_field('HTMLFragment', $textString);
24
25
        $this->assertEquals($textString, $htmlField->forTemplate());
26
        $this->assertEquals($htmlString, $htmlField->obj('HTMLATT')->forTemplate());
27
        $this->assertEquals('%22', $htmlField->obj('URLATT')->forTemplate());
28
        $this->assertEquals('%22', $htmlField->obj('RAWURLATT')->forTemplate());
29
        $this->assertEquals($htmlString, $htmlField->obj('ATT')->forTemplate());
30
        $this->assertEquals($textString, $htmlField->obj('RAW')->forTemplate());
31
        $this->assertEquals('\"', $htmlField->obj('JS')->forTemplate());
32
        $this->assertEquals($htmlString, $htmlField->obj('HTML')->forTemplate());
33
        $this->assertEquals($htmlString, $htmlField->obj('XML')->forTemplate());
34
35
        $textField = DBField::create_field('Text', $textString);
36
        $this->assertEquals($htmlString, $textField->forTemplate());
37
        $this->assertEquals($htmlString, $textField->obj('HTMLATT')->forTemplate());
38
        $this->assertEquals('%22', $textField->obj('URLATT')->forTemplate());
39
        $this->assertEquals('%22', $textField->obj('RAWURLATT')->forTemplate());
40
        $this->assertEquals($htmlString, $textField->obj('ATT')->forTemplate());
41
        $this->assertEquals($textString, $textField->obj('RAW')->forTemplate());
42
        $this->assertEquals('\"', $textField->obj('JS')->forTemplate());
43
        $this->assertEquals($htmlString, $textField->obj('HTML')->forTemplate());
44
        $this->assertEquals($htmlString, $textField->obj('XML')->forTemplate());
45
    }
46
47
    public function testRequiresCasting()
48
    {
49
        $caster = new ViewableDataTest\Castable();
50
51
        $this->assertInstanceOf(ViewableDataTest\RequiresCasting::class, $caster->obj('alwaysCasted'));
52
        $this->assertInstanceOf(ViewableDataTest\Caster::class, $caster->obj('noCastingInformation'));
53
    }
54
55
    public function testFailoverRequiresCasting()
56
    {
57
        $caster = new ViewableDataTest\Castable();
58
        $container = new ViewableDataTest\Container();
59
        $container->setFailover($caster);
60
61
        $this->assertInstanceOf(ViewableDataTest\RequiresCasting::class, $container->obj('alwaysCasted'));
62
        $this->assertInstanceOf(ViewableDataTest\RequiresCasting::class, $caster->obj('alwaysCasted'));
63
64
        $this->assertInstanceOf(ViewableDataTest\Caster::class, $container->obj('noCastingInformation'));
65
        $this->assertInstanceOf(ViewableDataTest\Caster::class, $caster->obj('noCastingInformation'));
66
    }
67
68
    public function testCastingXMLVal()
69
    {
70
        $caster = new ViewableDataTest\Castable();
71
72
        $this->assertEquals('casted', $caster->XML_val('alwaysCasted'));
73
        $this->assertEquals('casted', $caster->XML_val('noCastingInformation'));
74
75
        // Test automatic escaping is applied even to fields with no 'casting'
76
        $this->assertEquals('casted', $caster->XML_val('unsafeXML'));
77
        $this->assertEquals('&lt;foo&gt;', $caster->XML_val('castedUnsafeXML'));
78
    }
79
80
    public function testArrayCustomise()
81
    {
82
        $viewableData    = new ViewableDataTest\Castable();
83
        $newViewableData = $viewableData->customise(
84
            array (
85
            'test'         => 'overwritten',
86
            'alwaysCasted' => 'overwritten'
87
            )
88
        );
89
90
        $this->assertEquals('test', $viewableData->XML_val('test'));
91
        $this->assertEquals('casted', $viewableData->XML_val('alwaysCasted'));
92
93
        $this->assertEquals('overwritten', $newViewableData->XML_val('test'));
94
        $this->assertEquals('overwritten', $newViewableData->XML_val('alwaysCasted'));
95
96
        $this->assertEquals('castable', $viewableData->forTemplate());
97
        $this->assertEquals('castable', $newViewableData->forTemplate());
0 ignored issues
show
Bug introduced by
The method forTemplate() does not exist on SilverStripe\View\ViewableData_Customised. Since you implemented __call, consider adding a @method annotation. ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-call  annotation

97
        $this->assertEquals('castable', $newViewableData->/** @scrutinizer ignore-call */ forTemplate());
Loading history...
98
    }
99
100
    public function testObjectCustomise()
101
    {
102
        $viewableData    = new ViewableDataTest\Castable();
103
        $newViewableData = $viewableData->customise(new ViewableDataTest\RequiresCasting());
104
105
        $this->assertEquals('test', $viewableData->XML_val('test'));
106
        $this->assertEquals('casted', $viewableData->XML_val('alwaysCasted'));
107
108
        $this->assertEquals('overwritten', $newViewableData->XML_val('test'));
109
        $this->assertEquals('casted', $newViewableData->XML_val('alwaysCasted'));
110
111
        $this->assertEquals('castable', $viewableData->forTemplate());
112
        $this->assertEquals('casted', $newViewableData->forTemplate());
113
    }
114
115
    public function testDefaultValueWrapping()
116
    {
117
        $data = new ArrayData(array('Title' => 'SomeTitleValue'));
118
        // this results in a cached raw string in ViewableData:
119
        $this->assertTrue($data->hasValue('Title'));
120
        $this->assertFalse($data->hasValue('SomethingElse'));
121
        // this should cast the raw string to a StringField since we are
122
        // passing true as the third argument:
123
        $obj = $data->obj('Title', null, true);
124
        $this->assertTrue(is_object($obj));
125
        // and the string field should have the value of the raw string:
126
        $this->assertEquals('SomeTitleValue', $obj->forTemplate());
127
    }
128
129
    public function testCastingClass()
130
    {
131
        $expected = array(
132
            //'NonExistant'   => null,
0 ignored issues
show
Unused Code Comprehensibility introduced by
50% of this comment could be valid code. Did you maybe forget this after debugging?

Sometimes obsolete code just ends up commented out instead of removed. In this case it is better to remove the code once you have checked you do not need it.

The code might also have been commented out for debugging purposes. In this case it is vital that someone uncomments it again or your project may behave in very unexpected ways in production.

This check looks for comments that seem to be mostly valid code and reports them.

Loading history...
133
            'Field'         => 'CastingType',
134
            'Argument'      => 'ArgumentType',
135
            'ArrayArgument' => 'ArrayArgumentType'
136
        );
137
        $obj = new ViewableDataTest\CastingClass();
138
139
        foreach ($expected as $field => $class) {
140
            $this->assertEquals(
141
                $class,
142
                $obj->castingClass($field),
143
                "castingClass() returns correct results for ::\$$field"
144
            );
145
        }
146
    }
147
148
    public function testObjWithCachedStringValueReturnsValidObject()
149
    {
150
        $obj = new ViewableDataTest\NoCastingInformation();
151
152
        // Save a literal string into cache
153
        $cache = true;
154
        $uncastedData = $obj->obj('noCastingInformation', null, false, $cache);
0 ignored issues
show
Bug introduced by
$cache of type true is incompatible with the type string expected by parameter $cacheName of SilverStripe\View\ViewableData::obj(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

154
        $uncastedData = $obj->obj('noCastingInformation', null, false, /** @scrutinizer ignore-type */ $cache);
Loading history...
155
156
        // Fetch the cached string as an object
157
        $forceReturnedObject = true;
158
        $castedData = $obj->obj('noCastingInformation', null, $forceReturnedObject);
159
160
        // Uncasted data should always be the nonempty string
161
        $this->assertNotEmpty($uncastedData, 'Uncasted data was empty.');
162
        //$this->assertTrue(is_string($uncastedData), 'Uncasted data should be a string.');
0 ignored issues
show
Unused Code Comprehensibility introduced by
77% of this comment could be valid code. Did you maybe forget this after debugging?

Sometimes obsolete code just ends up commented out instead of removed. In this case it is better to remove the code once you have checked you do not need it.

The code might also have been commented out for debugging purposes. In this case it is vital that someone uncomments it again or your project may behave in very unexpected ways in production.

This check looks for comments that seem to be mostly valid code and reports them.

Loading history...
163
164
        // Casted data should be the string wrapped in a DBField-object.
165
        $this->assertNotEmpty($castedData, 'Casted data was empty.');
166
        $this->assertInstanceOf(DBField::class, $castedData, 'Casted data should be instance of DBField.');
167
168
        $this->assertEquals($uncastedData, $castedData->getValue(), 'Casted and uncasted strings are not equal.');
169
    }
170
171
    public function testCaching()
172
    {
173
        $objCached = new ViewableDataTest\Cached();
174
        $objNotCached = new ViewableDataTest\NotCached();
175
176
        $objCached->Test = 'AAA';
177
        $objNotCached->Test = 'AAA';
178
179
        $this->assertEquals('AAA', $objCached->obj('Test', null, true, true));
0 ignored issues
show
Bug introduced by
true of type true is incompatible with the type string expected by parameter $cacheName of SilverStripe\View\ViewableData::obj(). ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-type  annotation

179
        $this->assertEquals('AAA', $objCached->obj('Test', null, true, /** @scrutinizer ignore-type */ true));
Loading history...
180
        $this->assertEquals('AAA', $objNotCached->obj('Test', null, true, true));
181
182
        $objCached->Test = 'BBB';
183
        $objNotCached->Test = 'BBB';
184
185
        // Cached data must be always the same
186
        $this->assertEquals('AAA', $objCached->obj('Test', null, true, true));
187
        $this->assertEquals('BBB', $objNotCached->obj('Test', null, true, true));
188
    }
189
190
    public function testSetFailover()
191
    {
192
        $failover = new ViewableData();
193
        $container = new ViewableDataTest\Container();
194
        $container->setFailover($failover);
195
196
        $this->assertSame($failover, $container->getFailover(), 'getFailover() returned a different object');
197
        $this->assertFalse($container->hasMethod('testMethod'), 'testMethod() is already defined when it shouldn’t be');
198
199
        // Ensure that defined methods detected from the failover aren't cached when setting a new failover
200
        $container->setFailover(new ViewableDataTest\Failover);
201
        $this->assertTrue($container->hasMethod('testMethod'));
202
203
        // Test the reverse - that defined methods previously detected in a failover are removed if they no longer exist
204
        $container->setFailover($failover);
205
        $this->assertSame($failover, $container->getFailover(), 'getFailover() returned a different object');
206
        $this->assertFalse($container->hasMethod('testMethod'), 'testMethod() incorrectly reported as existing');
207
    }
208
209
    public function testThemeDir()
210
    {
211
        $themes = [
212
            "silverstripe/framework:/tests/php/View/ViewableDataTest/testtheme",
213
            SSViewer::DEFAULT_THEME
214
        ];
215
        SSViewer::set_themes($themes);
216
217
        $data = new ViewableData();
218
        $this->assertContains(
219
            'tests/php/View/ViewableDataTest/testtheme',
220
            $data->ThemeDir()
0 ignored issues
show
Deprecated Code introduced by
The function SilverStripe\View\ViewableData::ThemeDir() has been deprecated: 4.0.0..5.0.0 Use $resourcePath or $resourceURL template helpers instead ( Ignorable by Annotation )

If this is a false-positive, you can also ignore this issue in your code via the ignore-deprecated  annotation

220
            /** @scrutinizer ignore-deprecated */ $data->ThemeDir()

This function has been deprecated. The supplier of the function has supplied an explanatory message.

The explanatory message should give you some clue as to whether and when the function will be removed and what other function to use instead.

Loading history...
221
        );
222
    }
223
}
224