Update phpMyAdmin to 4.9.2

This commit is contained in:
cytopia 2019-12-08 08:14:01 +01:00
parent 914f32bc14
commit d6818a1470
No known key found for this signature in database
GPG Key ID: 6D56EDB8695128A2
2689 changed files with 29704 additions and 24095 deletions

View File

@ -1,17 +0,0 @@
# EditorConfig.org
root = true
[*]
end_of_line = lf
insert_final_newline = true
trim_trailing_whitespace = true
charset = utf-8
[*.{js,php,twig,phtml,json,css}]
indent_style = space
indent_size = 4
[{*.sql,package.json,.travis.yml}]
indent_style = space
indent_size = 2

View File

@ -1,3 +0,0 @@
js/vendor/
tmp/
vendor/

View File

@ -1,42 +0,0 @@
{
"env": {
"browser": true,
"jquery": true
},
"rules": {
"array-bracket-spacing": "error",
"brace-style": "error",
"camelcase": "warn",
"comma-style": ["error", "last"],
"curly": "error",
"dot-notation": "error",
"eol-last": "error",
"eqeqeq": "error",
"indent": ["error", 4],
"keyword-spacing": "error",
"new-cap": "warn",
"no-array-constructor": "warn",
"no-eval": "warn",
"no-loop-func": "warn",
"no-mixed-spaces-and-tabs": "error",
"no-multiple-empty-lines": "error",
"no-new-func": "error",
"no-new-object": "error",
"no-param-reassign": "warn",
"no-trailing-spaces": "error",
"no-underscore-dangle": "warn",
"no-unneeded-ternary": "error",
"no-useless-escape": "warn",
"object-curly-spacing": ["error", "always"],
"one-var": ["error", "never"],
"padded-blocks": ["error", "never"],
"quotes": ["error", "single"],
"semi": "error",
"space-before-blocks": "error",
"space-before-function-paren": "error",
"space-in-parens": "error",
"space-infix-ops": "error",
"spaced-comment": ["error", "always"],
"wrap-iife": "error"
}
}

View File

@ -1,145 +0,0 @@
phpMyAdmin - ChangeLog
======================
4.8.4 (2018-12-11)
- issue #14452 Remove hash param in edit query URL
- issue #14295 Issue in Changing theme
- issue #13267 Ensure that database names with '.' are handled properly when DisableIS is true
- issue #14438 Invisible Icon "Show Full Queries"
- issue #14133 CSS issue in Designer
- issue #14447 Error while copying database (pma__column_info)
- issue #14571 "No database selected" - DROP a view
- issue #14636 Move operation causes SELECT * FROM `undefined`
- issue #14630 Enum '0' produces incorrect search SQL
- issue #14223 Fix TypeError in database designer
- issue #13621 QBE selenium tests broken since merge of #13342
- issue #14672 When logging with $cfg['AuthLog'] to syslog, successful login messages were not logged even if $cfg['AuthLogSuccess'] was true.
- issue #14339 Fix infinite loop when sorting table rows by key.
- issue #14658 Regression on multi table query functionality (foreign keys)
- issue #14617 Fix designer errors when database is empty
- issue #13032 Fix designer errors when database contains special chars
- issue #14352 Fix designer javascript errors
- issue #14764 Fix left/right icons hidden
- issue [security] Local file inclusion flaw in the Transformation feature (PMASA-2018-6)
- issue [security] Multiple CSRF/XSRF vulnerabilities (PMASA-2018-7)
- issue [security] XSS vulnerability in the navigation tree (PMASA-2018-8)
4.8.3 (2018-08-22)
- issue #14314 Error when naming a database '0'
- issue #14333 Fix NULL as default not shown
- issue #14229 Fixes issue with recent table list
- issue #14045 Fix slow performance on DB structure filtering
- issue #14327 Fix Editing server variable not showing save or cancel option
- issue #14377 Populate options for view create and edit
- issue #14171 2FA configuration fails if PHP doesn't have GD support
- issue #14390 Can't unhide tables
- issue #14382 "Visualize GIS data" icon missing
- issue #14435 Event scheduler status toggle doesn't work
- issue #14365 View not working on multiple servers
- issue #14207 Partition actions in table structure do not work
- issue #14375 Fixes ERR_BLOCKED_BY_XSS_AUDITOR on export table
- issue #14552 Blank message shown instead of MySQL error when adding trigger and other locations
- issue #14525 Fix PHP 7.3 warning: "continue" in "switch" is equal to "break"
- issue #14554 Icon missing when creating a new trigger, routine, and event
- issue #14422 Table comment not showing since 4.8.1
- issue #14426 Drop table doesn't work when you copy tables to another database
- issue #14581 Escaped HTML in 'Add a new server' setup
- issue #14548 [security] HTML injection in import warning messages, see PMASA-2018-5
4.8.2 (2018-06-21)
- issue #14370 WHERE 0 causes Fatal error
- issue #14225 Fix missing index icon
- issue [security] XSS vulnerability in Designer, see PMASA-2018-3
- issue [security] File inclusion and remote code execution vulnerability, see PMASA-2018-4
4.8.1 (2018-05-24)
- issue #12772 Fix case where the central columns attributes don't get filled in
- issue #14049 Fix case where the query builder doesn't work when selected column is *
- issue #14029 Revert "Browse" table CSS overflow
- issue #14241 Dropping indexes and foreign keys fail
- issue #14227 Relational linking broken
- issue #14246 Fixed error in configuration storage zero config
- issue #14128 Show 2FA Secret next to QR code
- issue #14212 XML Export from single table throws fatal error
- issue #14239 Line and some other charts ignore result set order of values chosen for the x-axis
- issue #14260 Fixed configuration for DefaultLang and Lang
- issue #14264 Linking for 'Distinct values' broken
- issue #13968 Fix MariaDB 10.2 current_timestamp()
- issue #14249 Fix for missing go button in view edit
- issue #14125 Fix for issues with spatial fields
- issue #14189 Remember table's sorting broken
- issue #14289 Fix multi-column sorting
- issue #14278 Fix central columns in-line edit bug
- issue #14066 Fix AUTO_INCREMENT error when only exporting table structure in database-level exports
- issue #13893 Simulating queries produces unexpected results
- issue #14309 Setup script icons missing
4.8.0.1 (2018-04-19)
- issue [security] Multiple CSRF vulnerabilities, See PMASA-2018-02
4.8.0 (2018-04-07)
- issue #12946 Allow to export JSON with unescaped unicode chars
- issue #12983 Disable login button without solved reCaptcha
- issue #12315 Allow to remove individual segments from pie charts
- issue Change label from "Improve table structure" to "Normalize" to match standard terminology
- issue #13087 Offer login as different user on access denied from MySQL
- issue #13110 Indicate when HTTPS is not properly reported on the server
- issue #13119 No database selected error when adding foreign key
- issue #12388 Improved database search to allow search for exact phrase match
- issue #13099 Report error when trying to copy database to same name
- issue #13167 Themes now have to contain metadata in theme.json
- issue #6363 phpMyAdmin no longer requires eval() in PHP
- issue #12386 The mbstring dependency is now optional
- issue #13269 Small refactoring in preparation to CSP
- issue #13384 Database link broken in Databases Page
- issue #13391 Configurable authentication logging using $cfg['AuthLog']
- issue #13086 Add support for Google Invisible Captcha
- issue #13058 Improved error reporting for reCAPTCHA
- issue #12899 Improved rendering of server variables table
- issue #12948 Fixed javascript editor for TIME values
- issue #13095 Fixed alignment of foreign keys editing
- issue #12944 Improved inline editor for JSON
- issue #13145 Improved layout of operations pages
- issue #13448 Add "format" query button in edit view form
- issue #6241 Implement Responsive Design/mobile interface
- issue Use a single location for classes under PhpMyAdmin namespace
- issue #12354 Indicate SSL status on main page
- issue #5666 Configuration directives for defaults of Transformation options
- issue #12261 Remove inline JavaScript
- issue #13408 Show MySQL warnings when executing SQL queries
- issue #5827 Allow Designer to show tables from other databases
- issue #13268 Replace Query-By-Example with multi-table query generator interface
- issue #13576 Add privileges export to per-database listing
- issue Consolidate functions into class files
- issue #13560 Add support for changing collation for all tables and columns in database
- issue #13303 Add support for creating fulltext index from table structure
- issue #13711 Lower default value for $cfg['MaxExactCount']
- issue #13722 DisableIS is not fully honored
- issue #6197 Added support for authentication using U2F and 2FA
- issue #13480 Avoid removing cookies on upgrade
- issue #13397 Remember state of navigation panel
- issue #11688 Reduced cookie usage
- issue #13466 Better utilization of user preferences
- issue #14042 Rename PMD to Designer
- issue #13940 Honor arg_separator in AJAX requests
- issue #14060 Can't edit rows in Internet Explorer
- issue #14096 Internet Explorer compatibility; fixes JavaScript error Object doesn't support property or method 'startsWith'
4.7.9 (2018-03-05)
- issue #13931 Fixed browsing tables with more results
- issue #13927 "Not an integer" when browsing a table
- issue #13887 "Input variables exceeded 1000" error relating to PHP's max_input_vars directive
4.7.8 (2018-02-20)
- issue #13914 Fixed resetting default setting values.
- issue #13758 Fixed fallback value for collation connection.
- issue #13938 Fixed error handling in PHP 7.2
- issue [security] Fix XSS in Central Columns Feature, See PMASA-2018-01
--- Older ChangeLogs can be found on our project website ---
https://www.phpmyadmin.net/old-stuff/ChangeLogs/
# vim: et ts=4 sw=4 sts=4
# vim: ft=changelog fenc=utf-8
# vim: fde=getline(v\:lnum-1)=~'^\\s*$'&&getline(v\:lnum)=~'\\S'?'>1'\:1&&v\:lnum>4&&getline(v\:lnum)!~'^#'
# vim: fdn=1 fdm=expr

View File

@ -1 +0,0 @@
Tue Dec 11 02:02:39 UTC 2018

View File

@ -1,154 +0,0 @@
<?php
/* vim: set expandtab sw=4 ts=4 sts=4: */
/**
* phpMyAdmin sample configuration, you can use it as base for
* manual configuration. For easier setup you can use setup/
*
* All directives are explained in documentation in the doc/ folder
* or at <https://docs.phpmyadmin.net/>.
*
* @package PhpMyAdmin
*/
/**
* This is needed for cookie based authentication to encrypt password in
* cookie. Needs to be 32 chars long.
*/
$cfg['blowfish_secret'] = ''; /* YOU MUST FILL IN THIS FOR COOKIE AUTH! */
/**
* Servers configuration
*/
$i = 0;
/**
* First server
*/
$i++;
/* Authentication type */
$cfg['Servers'][$i]['auth_type'] = 'cookie';
/* Server parameters */
$cfg['Servers'][$i]['host'] = 'localhost';
$cfg['Servers'][$i]['compress'] = false;
$cfg['Servers'][$i]['AllowNoPassword'] = false;
/**
* phpMyAdmin configuration storage settings.
*/
/* User used to manipulate with storage */
// $cfg['Servers'][$i]['controlhost'] = '';
// $cfg['Servers'][$i]['controlport'] = '';
// $cfg['Servers'][$i]['controluser'] = 'pma';
// $cfg['Servers'][$i]['controlpass'] = 'pmapass';
/* Storage database and tables */
// $cfg['Servers'][$i]['pmadb'] = 'phpmyadmin';
// $cfg['Servers'][$i]['bookmarktable'] = 'pma__bookmark';
// $cfg['Servers'][$i]['relation'] = 'pma__relation';
// $cfg['Servers'][$i]['table_info'] = 'pma__table_info';
// $cfg['Servers'][$i]['table_coords'] = 'pma__table_coords';
// $cfg['Servers'][$i]['pdf_pages'] = 'pma__pdf_pages';
// $cfg['Servers'][$i]['column_info'] = 'pma__column_info';
// $cfg['Servers'][$i]['history'] = 'pma__history';
// $cfg['Servers'][$i]['table_uiprefs'] = 'pma__table_uiprefs';
// $cfg['Servers'][$i]['tracking'] = 'pma__tracking';
// $cfg['Servers'][$i]['userconfig'] = 'pma__userconfig';
// $cfg['Servers'][$i]['recent'] = 'pma__recent';
// $cfg['Servers'][$i]['favorite'] = 'pma__favorite';
// $cfg['Servers'][$i]['users'] = 'pma__users';
// $cfg['Servers'][$i]['usergroups'] = 'pma__usergroups';
// $cfg['Servers'][$i]['navigationhiding'] = 'pma__navigationhiding';
// $cfg['Servers'][$i]['savedsearches'] = 'pma__savedsearches';
// $cfg['Servers'][$i]['central_columns'] = 'pma__central_columns';
// $cfg['Servers'][$i]['designer_settings'] = 'pma__designer_settings';
// $cfg['Servers'][$i]['export_templates'] = 'pma__export_templates';
/**
* End of servers configuration
*/
/**
* Directories for saving/loading files from server
*/
$cfg['UploadDir'] = '';
$cfg['SaveDir'] = '';
/**
* Whether to display icons or text or both icons and text in table row
* action segment. Value can be either of 'icons', 'text' or 'both'.
* default = 'both'
*/
//$cfg['RowActionType'] = 'icons';
/**
* Defines whether a user should be displayed a "show all (records)"
* button in browse mode or not.
* default = false
*/
//$cfg['ShowAll'] = true;
/**
* Number of rows displayed when browsing a result set. If the result
* set contains more rows, "Previous" and "Next".
* Possible values: 25, 50, 100, 250, 500
* default = 25
*/
//$cfg['MaxRows'] = 50;
/**
* Disallow editing of binary fields
* valid values are:
* false allow editing
* 'blob' allow editing except for BLOB fields
* 'noblob' disallow editing except for BLOB fields
* 'all' disallow editing
* default = 'blob'
*/
//$cfg['ProtectBinary'] = false;
/**
* Default language to use, if not browser-defined or user-defined
* (you find all languages in the locale folder)
* uncomment the desired line:
* default = 'en'
*/
//$cfg['DefaultLang'] = 'en';
//$cfg['DefaultLang'] = 'de';
/**
* How many columns should be used for table display of a database?
* (a value larger than 1 results in some information being hidden)
* default = 1
*/
//$cfg['PropertiesNumColumns'] = 2;
/**
* Set to true if you want DB-based query history.If false, this utilizes
* JS-routines to display query history (lost by window close)
*
* This requires configuration storage enabled, see above.
* default = false
*/
//$cfg['QueryHistoryDB'] = true;
/**
* When using DB-based query history, how many entries should be kept?
* default = 25
*/
//$cfg['QueryHistoryMax'] = 100;
/**
* Whether or not to query the user before sending the error report to
* the phpMyAdmin team when a JavaScript error occurs
*
* Available options
* ('ask' | 'always' | 'never')
* default = 'ask'
*/
//$cfg['SendErrorReports'] = 'always';
/**
* You can find more configuration options in the documentation
* in the doc/ folder or at <https://docs.phpmyadmin.net/>.
*/

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -1,165 +0,0 @@
/*!
* JavaScript Cookie v2.2.0
* https://github.com/js-cookie/js-cookie
*
* Copyright 2006, 2015 Klaus Hartl & Fagner Brack
* Released under the MIT license
*/
;(function (factory) {
var registeredInModuleLoader = false;
if (typeof define === 'function' && define.amd) {
define(factory);
registeredInModuleLoader = true;
}
if (typeof exports === 'object') {
module.exports = factory();
registeredInModuleLoader = true;
}
if (!registeredInModuleLoader) {
var OldCookies = window.Cookies;
var api = window.Cookies = factory();
api.noConflict = function () {
window.Cookies = OldCookies;
return api;
};
}
}(function () {
function extend () {
var i = 0;
var result = {};
for (; i < arguments.length; i++) {
var attributes = arguments[ i ];
for (var key in attributes) {
result[key] = attributes[key];
}
}
return result;
}
function init (converter) {
function api (key, value, attributes) {
var result;
if (typeof document === 'undefined') {
return;
}
// Write
if (arguments.length > 1) {
attributes = extend({
path: '/'
}, api.defaults, attributes);
if (typeof attributes.expires === 'number') {
var expires = new Date();
expires.setMilliseconds(expires.getMilliseconds() + attributes.expires * 864e+5);
attributes.expires = expires;
}
// We're using "expires" because "max-age" is not supported by IE
attributes.expires = attributes.expires ? attributes.expires.toUTCString() : '';
try {
result = JSON.stringify(value);
if (/^[\{\[]/.test(result)) {
value = result;
}
} catch (e) {}
if (!converter.write) {
value = encodeURIComponent(String(value))
.replace(/%(23|24|26|2B|3A|3C|3E|3D|2F|3F|40|5B|5D|5E|60|7B|7D|7C)/g, decodeURIComponent);
} else {
value = converter.write(value, key);
}
key = encodeURIComponent(String(key));
key = key.replace(/%(23|24|26|2B|5E|60|7C)/g, decodeURIComponent);
key = key.replace(/[\(\)]/g, escape);
var stringifiedAttributes = '';
for (var attributeName in attributes) {
if (!attributes[attributeName]) {
continue;
}
stringifiedAttributes += '; ' + attributeName;
if (attributes[attributeName] === true) {
continue;
}
stringifiedAttributes += '=' + attributes[attributeName];
}
return (document.cookie = key + '=' + value + stringifiedAttributes);
}
// Read
if (!key) {
result = {};
}
// To prevent the for loop in the first place assign an empty array
// in case there are no cookies at all. Also prevents odd result when
// calling "get()"
var cookies = document.cookie ? document.cookie.split('; ') : [];
var rdecode = /(%[0-9A-Z]{2})+/g;
var i = 0;
for (; i < cookies.length; i++) {
var parts = cookies[i].split('=');
var cookie = parts.slice(1).join('=');
if (!this.json && cookie.charAt(0) === '"') {
cookie = cookie.slice(1, -1);
}
try {
var name = parts[0].replace(rdecode, decodeURIComponent);
cookie = converter.read ?
converter.read(cookie, name) : converter(cookie, name) ||
cookie.replace(rdecode, decodeURIComponent);
if (this.json) {
try {
cookie = JSON.parse(cookie);
} catch (e) {}
}
if (key === name) {
result = cookie;
break;
}
if (!key) {
result[name] = cookie;
}
} catch (e) {}
}
return result;
}
api.set = api;
api.get = function (key) {
return api.call(api, key);
};
api.getJSON = function () {
return api.apply({
json: true
}, [].slice.call(arguments));
};
api.defaults = {};
api.remove = function (key, attributes) {
api(key, '', extend(attributes, {
expires: -1
}));
};
api.withConverter = init;
return api;
}
return init(function () {});
}));

View File

@ -1,15 +0,0 @@
<?xml version="1.0"?>
<ruleset name="phpMyAdmin Coding Standard">
<rule ref="./vendor/phpmyadmin/coding-standard/PMAStandard/ruleset.xml"/>
<arg value="sp"/>
<arg name="colors"/>
<arg name="extensions" value="php"/>
<exclude-pattern>*/build/*</exclude-pattern>
<exclude-pattern>*/node_modules/*</exclude-pattern>
<exclude-pattern>*/tmp/*</exclude-pattern>
<exclude-pattern>*/vendor/*</exclude-pattern>
<file>.</file>
</ruleset>

View File

@ -1,65 +0,0 @@
<div id="layer_menu" class="hide">
<div class="center">
<a href="#" class="M_butt" target="_self" >
<img title="{% trans 'Hide/Show all' %}"
alt="v"
id="key_HS_all"
src="{{ theme.getImgPath('designer/downarrow1.png') }}"
data-down="{{ theme.getImgPath('designer/downarrow1.png') }}"
data-right="{{ theme.getImgPath('designer/rightarrow1.png') }}" />
</a>
<a href="#" class="M_butt" target="_self" >
<img alt="v"
id="key_HS"
title="{% trans 'Hide/Show tables with no relationship' %}"
src="{{ theme.getImgPath('designer/downarrow2.png') }}"
data-down="{{ theme.getImgPath('designer/downarrow2.png') }}"
data-right="{{ theme.getImgPath('designer/rightarrow2.png') }}" />
</a>
</div>
<div id="id_scroll_tab" class="scroll_tab">
<table width="100%" style="padding-left: 3px;">
{% for i in 0..table_names|length - 1 %}
<tr>
<td title="{% trans 'Structure' %}"
width="1px"
class="L_butt2_1">
<img alt=""
table_name="{{ table_names_small_url[i] }}"
class="scroll_tab_struct"
src="{{ theme.getImgPath('designer/exec.png') }}"/>
</td>
<td width="1px">
<input class="scroll_tab_checkbox"
title="{% trans 'Hide' %}"
id="check_vis_{{ table_names_url[i]|url_encode }}"
style="margin:0;"
type="checkbox"
value="{{ table_names_url[i]|url_encode }}"
{% if (tab_pos[table_names[i]] is defined
and tab_pos[table_names[i]]['H'])
or display_page == -1 -%}
checked="checked"
{%- endif %} />
</td>
<td class="designer_Tabs"
designer_url_table_name="{{ table_names_url[i]|url_encode }}">
{{ table_names_out[i]|raw }}
</td>
</tr>
{% endfor %}
</table>
</div>
{# end id_scroll_tab #}
<div class="center">
{% trans 'Number of tables:' %} {{ table_names|length }}
</div>
<div id="layer_menu_sizer">
<div class="floatleft">
<img class="icon"
data-right="{{ theme.getImgPath('designer/resizeright.png') }}"
src="{{ theme.getImgPath('designer/resize.png') }}"/>
</div>
</div>
</div>
{# end layer_menu #}

View File

@ -1,21 +0,0 @@
Copyright (c) 2016 Nils Adermann, Jordi Boggiano
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is furnished
to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
THE SOFTWARE.

View File

@ -1,29 +0,0 @@
Copyright 2014, Google Inc.
All rights reserved.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are
met:
* Redistributions of source code must retain the above copyright
notice, this list of conditions and the following disclaimer.
* Redistributions in binary form must reproduce the above
copyright notice, this list of conditions and the following disclaimer
in the documentation and/or other materials provided with the
distribution.
* Neither the name of Google Inc. nor the names of its
contributors may be used to endorse or promote products derived from
this software without specific prior written permission.
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
"AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.

View File

@ -1,42 +0,0 @@
<?php
/**
* This is a PHP library that handles calling reCAPTCHA.
*
* @copyright Copyright (c) 2015, Google Inc.
* @link https://www.google.com/recaptcha
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
namespace ReCaptcha;
/**
* Method used to send the request to the service.
*/
interface RequestMethod
{
/**
* Submit the request with the specified parameters.
*
* @param RequestParameters $params Request parameters
* @return string Body of the reCAPTCHA response
*/
public function submit(RequestParameters $params);
}

View File

@ -1,74 +0,0 @@
<?php
/**
* This is a PHP library that handles calling reCAPTCHA.
*
* @copyright Copyright (c) 2015, Google Inc.
* @link https://www.google.com/recaptcha
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
namespace ReCaptcha\RequestMethod;
/**
* Convenience wrapper around the cURL functions to allow mocking.
*/
class Curl
{
/**
* @see http://php.net/curl_init
* @param string $url
* @return resource cURL handle
*/
public function init($url = null)
{
return curl_init($url);
}
/**
* @see http://php.net/curl_setopt_array
* @param resource $ch
* @param array $options
* @return bool
*/
public function setoptArray($ch, array $options)
{
return curl_setopt_array($ch, $options);
}
/**
* @see http://php.net/curl_exec
* @param resource $ch
* @return mixed
*/
public function exec($ch)
{
return curl_exec($ch);
}
/**
* @see http://php.net/curl_close
* @param resource $ch
*/
public function close($ch)
{
curl_close($ch);
}
}

View File

@ -1,80 +0,0 @@
<?php
/**
* This is a PHP library that handles calling reCAPTCHA.
*
* @copyright Copyright (c) 2015, Google Inc.
* @link https://www.google.com/recaptcha
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
namespace ReCaptcha\RequestMethod;
use ReCaptcha\ReCaptcha;
use ReCaptcha\RequestMethod;
use ReCaptcha\RequestParameters;
/**
* Sends POST requests to the reCAPTCHA service.
*/
class Post implements RequestMethod
{
/**
* URL for reCAPTCHA sitevrerify API
* @var string
*/
private $siteVerifyUrl;
/**
* Only needed if you want to override the defaults
*
* @param string $siteVerifyUrl URL for reCAPTCHA sitevrerify API
*/
public function __construct($siteVerifyUrl = null)
{
$this->siteVerifyUrl = (is_null($siteVerifyUrl)) ? ReCaptcha::SITE_VERIFY_URL : $siteVerifyUrl;
}
/**
* Submit the POST request with the specified parameters.
*
* @param RequestParameters $params Request parameters
* @return string Body of the reCAPTCHA response
*/
public function submit(RequestParameters $params)
{
$options = array(
'http' => array(
'header' => "Content-type: application/x-www-form-urlencoded\r\n",
'method' => 'POST',
'content' => $params->toQueryString(),
// Force the peer to validate (not needed in 5.6.0+, but still works)
'verify_peer' => true,
),
);
$context = stream_context_create($options);
$response = file_get_contents($this->siteVerifyUrl, false, $context);
if ($response !== false) {
return $response;
}
return '{"success": false, "error-codes": ["'.ReCaptcha::E_CONNECTION_FAILED.'"]}';
}
}

View File

@ -1,40 +0,0 @@
<?php
/* An autoloader for ReCaptcha\Foo classes. This should be required()
* by the user before attempting to instantiate any of the ReCaptcha
* classes.
*/
spl_autoload_register(function ($class) {
if (substr($class, 0, 10) !== 'ReCaptcha\\') {
/* If the class does not lie under the "ReCaptcha" namespace,
* then we can exit immediately.
*/
return;
}
/* All of the classes have names like "ReCaptcha\Foo", so we need
* to replace the backslashes with frontslashes if we want the
* name to map directly to a location in the filesystem.
*/
$class = str_replace('\\', '/', $class);
/* First, check under the current directory. It is important that
* we look here first, so that we don't waste time searching for
* test classes in the common case.
*/
$path = dirname(__FILE__).'/'.$class.'.php';
if (is_readable($path)) {
require_once $path;
return;
}
/* If we didn't find what we're looking for already, maybe it's
* a test class?
*/
$path = dirname(__FILE__).'/../tests/'.$class.'.php';
if (is_readable($path)) {
require_once $path;
}
});

View File

@ -1,5 +0,0 @@
#!/usr/bin/env bash
basedir=$( dirname $( readlink -f ${BASH_SOURCE[0]} ) )
php -dphar.readonly=0 "$basedir/other/build_phar.php" $*

View File

@ -1,57 +0,0 @@
<?php
$dist = dirname(__DIR__).'/dist';
if (!is_dir($dist)) {
mkdir($dist, 0755);
}
if (file_exists($dist.'/random_compat.phar')) {
unlink($dist.'/random_compat.phar');
}
$phar = new Phar(
$dist.'/random_compat.phar',
FilesystemIterator::CURRENT_AS_FILEINFO | \FilesystemIterator::KEY_AS_FILENAME,
'random_compat.phar'
);
rename(
dirname(__DIR__).'/lib/random.php',
dirname(__DIR__).'/lib/index.php'
);
$phar->buildFromDirectory(dirname(__DIR__).'/lib');
rename(
dirname(__DIR__).'/lib/index.php',
dirname(__DIR__).'/lib/random.php'
);
/**
* If we pass an (optional) path to a private key as a second argument, we will
* sign the Phar with OpenSSL.
*
* If you leave this out, it will produce an unsigned .phar!
*/
if ($argc > 1) {
if (!@is_readable($argv[1])) {
echo 'Could not read the private key file:', $argv[1], "\n";
exit(255);
}
$pkeyFile = file_get_contents($argv[1]);
$private = openssl_get_privatekey($pkeyFile);
if ($private !== false) {
$pkey = '';
openssl_pkey_export($private, $pkey);
$phar->setSignatureAlgorithm(Phar::OPENSSL, $pkey);
/**
* Save the corresponding public key to the file
*/
if (!@is_readable($dist.'/random_compat.phar.pubkey')) {
$details = openssl_pkey_get_details($private);
file_put_contents(
$dist.'/random_compat.phar.pubkey',
$details['key']
);
}
} else {
echo 'An error occurred reading the private key from OpenSSL.', "\n";
exit(255);
}
}

View File

@ -1,9 +0,0 @@
<?php
require_once 'lib/byte_safe_strings.php';
require_once 'lib/cast_to_int.php';
require_once 'lib/error_polyfill.php';
require_once 'other/ide_stubs/libsodium.php';
require_once 'lib/random.php';
$int = random_int(0, 65536);

View File

@ -1,28 +0,0 @@
<?xml version="1.0"?>
<psalm
autoloader="psalm-autoload.php"
useDocblockTypes="true"
totallyTyped="true"
>
<projectFiles>
<directory name="lib" />
</projectFiles>
<issueHandlers>
<RedundantConditionGivenDocblockType errorLevel="info" />
<!-- We have to be explicit because PHP 5 lacks scalar types -->
<UnresolvableInclude errorLevel="info" />
<!-- Because we put the variants into their own subdirectory -->
<DuplicateClass errorLevel="info" />
<!-- Later versions of Psalm are only PHP 7 compatible, which
sees our redefinition of Error and TypeError as duplicate
class errors. -->
<UndefinedConstant errorLevel="info" />
<!-- The Mcrypt constants aren't defined in PHP 7.2 -->
<MissingReturnType errorLevel="info" />
<!-- False positive with some versions of (Psalm, PHP) -->
<InvalidReturnType errorLevel="info" />
<!-- The "last resort" function in lib/random.php -->
<MixedInferredReturnType errorLevel="suppress" />
<!-- Only used in totallyTyped mode -->
</issueHandlers>
</psalm>

View File

@ -1,102 +0,0 @@
<?php
/*
* This file is part of the Symfony package.
*
* (c) Fabien Potencier <fabien@symfony.com>
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
namespace Symfony\Polyfill\Util;
use PHPUnit\Framework\AssertionFailedError;
use PHPUnit\Framework\Test;
use PHPUnit\Framework\TestListener as TestListenerInterface;
use PHPUnit\Framework\TestSuite;
use PHPUnit\Framework\Warning;
use PHPUnit\Framework\WarningTestCase;
if (class_exists('PHPUnit_Runner_Version') && version_compare(\PHPUnit_Runner_Version::id(), '6.0.0', '<')) {
class_alias('Symfony\Polyfill\Util\LegacyTestListener', 'Symfony\Polyfill\Util\TestListener');
// Using an early return instead of a else does not work when using the PHPUnit phar due to some weird PHP behavior (the class
// gets defined without executing the code before it and so the definition is not properly conditional)
} else {
/**
* @author Nicolas Grekas <p@tchwork.com>
*/
class TestListener extends TestSuite implements TestListenerInterface
{
private $suite;
private $trait;
public function __construct(TestSuite $suite = null)
{
if ($suite) {
$this->suite = $suite;
$this->setName($suite->getName().' with polyfills enabled');
$this->addTest($suite);
}
$this->trait = new TestListenerTrait();
}
public function startTestSuite(TestSuite $suite)
{
$this->trait->startTestSuite($suite);
}
protected function setUp()
{
TestListenerTrait::$enabledPolyfills = $this->suite->getName();
}
protected function tearDown()
{
TestListenerTrait::$enabledPolyfills = false;
}
public function addError(Test $test, \Exception $e, $time)
{
$this->trait->addError($test, $e, $time);
}
public function addWarning(Test $test, Warning $e, $time)
{
}
public function addFailure(Test $test, AssertionFailedError $e, $time)
{
$this->trait->addError($test, $e, $time);
}
public function addIncompleteTest(Test $test, \Exception $e, $time)
{
}
public function addRiskyTest(Test $test, \Exception $e, $time)
{
}
public function addSkippedTest(Test $test, \Exception $e, $time)
{
}
public function endTestSuite(TestSuite $suite)
{
}
public function startTest(Test $test)
{
}
public function endTest(Test $test, $time)
{
}
public static function warning($message)
{
return parent::warning($message);
}
}
}

View File

@ -1,16 +0,0 @@
<?php
return PhpCsFixer\Config::create()
->setRules(array(
'@Symfony' => true,
'@Symfony:risky' => true,
'array_syntax' => array('syntax' => 'long'),
'php_unit_fqcn_annotation' => false,
'no_unreachable_default_argument_value' => false,
'braces' => array('allow_single_line_closure' => true),
'heredoc_to_nowdoc' => false,
'dir_constant' => false,
))
->setRiskyAllowed(true)
->setFinder(PhpCsFixer\Finder::create()->in(__DIR__))
;

View File

@ -1,54 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Twig_BaseNodeVisitor can be used to make node visitors compatible with Twig 1.x and 2.x.
*
* @author Fabien Potencier <fabien@symfony.com>
*/
abstract class Twig_BaseNodeVisitor implements Twig_NodeVisitorInterface
{
final public function enterNode(Twig_NodeInterface $node, Twig_Environment $env)
{
if (!$node instanceof Twig_Node) {
throw new LogicException('Twig_BaseNodeVisitor only supports Twig_Node instances.');
}
return $this->doEnterNode($node, $env);
}
final public function leaveNode(Twig_NodeInterface $node, Twig_Environment $env)
{
if (!$node instanceof Twig_Node) {
throw new LogicException('Twig_BaseNodeVisitor only supports Twig_Node instances.');
}
return $this->doLeaveNode($node, $env);
}
/**
* Called before child nodes are visited.
*
* @return Twig_Node The modified node
*/
abstract protected function doEnterNode(Twig_Node $node, Twig_Environment $env);
/**
* Called after child nodes are visited.
*
* @return Twig_Node|false The modified node or false if the node must be removed
*/
abstract protected function doLeaveNode(Twig_Node $node, Twig_Environment $env);
}
class_alias('Twig_BaseNodeVisitor', 'Twig\NodeVisitor\AbstractNodeVisitor', false);
class_exists('Twig_Environment');
class_exists('Twig_Node');

View File

@ -1,40 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Exception thrown when an error occurs during template loading.
*
* Automatic template information guessing is always turned off as
* if a template cannot be loaded, there is nothing to guess.
* However, when a template is loaded from another one, then, we need
* to find the current context and this is automatically done by
* Twig_Template::displayWithErrorHandling().
*
* This strategy makes Twig_Environment::resolveTemplate() much faster.
*
* @author Fabien Potencier <fabien@symfony.com>
*/
class Twig_Error_Loader extends Twig_Error
{
public function __construct($message, $lineno = -1, $source = null, Exception $previous = null)
{
if (PHP_VERSION_ID < 50300) {
$this->previous = $previous;
Exception::__construct('');
} else {
Exception::__construct('', 0, $previous);
}
$this->appendMessage($message);
$this->setTemplateLine(false);
}
}
class_alias('Twig_Error_Loader', 'Twig\Error\LoaderError', false);

View File

@ -1,744 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
* (c) Armin Ronacher
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Parses expressions.
*
* This parser implements a "Precedence climbing" algorithm.
*
* @see https://www.engr.mun.ca/~theo/Misc/exp_parsing.htm
* @see https://en.wikipedia.org/wiki/Operator-precedence_parser
*
* @author Fabien Potencier <fabien@symfony.com>
*
* @internal
*/
class Twig_ExpressionParser
{
const OPERATOR_LEFT = 1;
const OPERATOR_RIGHT = 2;
protected $parser;
protected $unaryOperators;
protected $binaryOperators;
private $env;
public function __construct(Twig_Parser $parser, $env = null)
{
$this->parser = $parser;
if ($env instanceof Twig_Environment) {
$this->env = $env;
$this->unaryOperators = $env->getUnaryOperators();
$this->binaryOperators = $env->getBinaryOperators();
} else {
@trigger_error('Passing the operators as constructor arguments to '.__METHOD__.' is deprecated since version 1.27. Pass the environment instead.', E_USER_DEPRECATED);
$this->env = $parser->getEnvironment();
$this->unaryOperators = func_get_arg(1);
$this->binaryOperators = func_get_arg(2);
}
}
public function parseExpression($precedence = 0)
{
$expr = $this->getPrimary();
$token = $this->parser->getCurrentToken();
while ($this->isBinary($token) && $this->binaryOperators[$token->getValue()]['precedence'] >= $precedence) {
$op = $this->binaryOperators[$token->getValue()];
$this->parser->getStream()->next();
if ('is not' === $token->getValue()) {
$expr = $this->parseNotTestExpression($expr);
} elseif ('is' === $token->getValue()) {
$expr = $this->parseTestExpression($expr);
} elseif (isset($op['callable'])) {
$expr = call_user_func($op['callable'], $this->parser, $expr);
} else {
$expr1 = $this->parseExpression(self::OPERATOR_LEFT === $op['associativity'] ? $op['precedence'] + 1 : $op['precedence']);
$class = $op['class'];
$expr = new $class($expr, $expr1, $token->getLine());
}
$token = $this->parser->getCurrentToken();
}
if (0 === $precedence) {
return $this->parseConditionalExpression($expr);
}
return $expr;
}
protected function getPrimary()
{
$token = $this->parser->getCurrentToken();
if ($this->isUnary($token)) {
$operator = $this->unaryOperators[$token->getValue()];
$this->parser->getStream()->next();
$expr = $this->parseExpression($operator['precedence']);
$class = $operator['class'];
return $this->parsePostfixExpression(new $class($expr, $token->getLine()));
} elseif ($token->test(Twig_Token::PUNCTUATION_TYPE, '(')) {
$this->parser->getStream()->next();
$expr = $this->parseExpression();
$this->parser->getStream()->expect(Twig_Token::PUNCTUATION_TYPE, ')', 'An opened parenthesis is not properly closed');
return $this->parsePostfixExpression($expr);
}
return $this->parsePrimaryExpression();
}
protected function parseConditionalExpression($expr)
{
while ($this->parser->getStream()->nextIf(Twig_Token::PUNCTUATION_TYPE, '?')) {
if (!$this->parser->getStream()->nextIf(Twig_Token::PUNCTUATION_TYPE, ':')) {
$expr2 = $this->parseExpression();
if ($this->parser->getStream()->nextIf(Twig_Token::PUNCTUATION_TYPE, ':')) {
$expr3 = $this->parseExpression();
} else {
$expr3 = new Twig_Node_Expression_Constant('', $this->parser->getCurrentToken()->getLine());
}
} else {
$expr2 = $expr;
$expr3 = $this->parseExpression();
}
$expr = new Twig_Node_Expression_Conditional($expr, $expr2, $expr3, $this->parser->getCurrentToken()->getLine());
}
return $expr;
}
protected function isUnary(Twig_Token $token)
{
return $token->test(Twig_Token::OPERATOR_TYPE) && isset($this->unaryOperators[$token->getValue()]);
}
protected function isBinary(Twig_Token $token)
{
return $token->test(Twig_Token::OPERATOR_TYPE) && isset($this->binaryOperators[$token->getValue()]);
}
public function parsePrimaryExpression()
{
$token = $this->parser->getCurrentToken();
switch ($token->getType()) {
case Twig_Token::NAME_TYPE:
$this->parser->getStream()->next();
switch ($token->getValue()) {
case 'true':
case 'TRUE':
$node = new Twig_Node_Expression_Constant(true, $token->getLine());
break;
case 'false':
case 'FALSE':
$node = new Twig_Node_Expression_Constant(false, $token->getLine());
break;
case 'none':
case 'NONE':
case 'null':
case 'NULL':
$node = new Twig_Node_Expression_Constant(null, $token->getLine());
break;
default:
if ('(' === $this->parser->getCurrentToken()->getValue()) {
$node = $this->getFunctionNode($token->getValue(), $token->getLine());
} else {
$node = new Twig_Node_Expression_Name($token->getValue(), $token->getLine());
}
}
break;
case Twig_Token::NUMBER_TYPE:
$this->parser->getStream()->next();
$node = new Twig_Node_Expression_Constant($token->getValue(), $token->getLine());
break;
case Twig_Token::STRING_TYPE:
case Twig_Token::INTERPOLATION_START_TYPE:
$node = $this->parseStringExpression();
break;
case Twig_Token::OPERATOR_TYPE:
if (preg_match(Twig_Lexer::REGEX_NAME, $token->getValue(), $matches) && $matches[0] == $token->getValue()) {
// in this context, string operators are variable names
$this->parser->getStream()->next();
$node = new Twig_Node_Expression_Name($token->getValue(), $token->getLine());
break;
} elseif (isset($this->unaryOperators[$token->getValue()])) {
$class = $this->unaryOperators[$token->getValue()]['class'];
$ref = new ReflectionClass($class);
$negClass = 'Twig_Node_Expression_Unary_Neg';
$posClass = 'Twig_Node_Expression_Unary_Pos';
if (!(in_array($ref->getName(), array($negClass, $posClass)) || $ref->isSubclassOf($negClass) || $ref->isSubclassOf($posClass))) {
throw new Twig_Error_Syntax(sprintf('Unexpected unary operator "%s".', $token->getValue()), $token->getLine(), $this->parser->getStream()->getSourceContext());
}
$this->parser->getStream()->next();
$expr = $this->parsePrimaryExpression();
$node = new $class($expr, $token->getLine());
break;
}
// no break
default:
if ($token->test(Twig_Token::PUNCTUATION_TYPE, '[')) {
$node = $this->parseArrayExpression();
} elseif ($token->test(Twig_Token::PUNCTUATION_TYPE, '{')) {
$node = $this->parseHashExpression();
} elseif ($token->test(Twig_Token::OPERATOR_TYPE, '=') && ('==' === $this->parser->getStream()->look(-1)->getValue() || '!=' === $this->parser->getStream()->look(-1)->getValue())) {
throw new Twig_Error_Syntax(sprintf('Unexpected operator of value "%s". Did you try to use "===" or "!==" for strict comparison? Use "is same as(value)" instead.', $token->getValue()), $token->getLine(), $this->parser->getStream()->getSourceContext());
} else {
throw new Twig_Error_Syntax(sprintf('Unexpected token "%s" of value "%s".', Twig_Token::typeToEnglish($token->getType()), $token->getValue()), $token->getLine(), $this->parser->getStream()->getSourceContext());
}
}
return $this->parsePostfixExpression($node);
}
public function parseStringExpression()
{
$stream = $this->parser->getStream();
$nodes = array();
// a string cannot be followed by another string in a single expression
$nextCanBeString = true;
while (true) {
if ($nextCanBeString && $token = $stream->nextIf(Twig_Token::STRING_TYPE)) {
$nodes[] = new Twig_Node_Expression_Constant($token->getValue(), $token->getLine());
$nextCanBeString = false;
} elseif ($stream->nextIf(Twig_Token::INTERPOLATION_START_TYPE)) {
$nodes[] = $this->parseExpression();
$stream->expect(Twig_Token::INTERPOLATION_END_TYPE);
$nextCanBeString = true;
} else {
break;
}
}
$expr = array_shift($nodes);
foreach ($nodes as $node) {
$expr = new Twig_Node_Expression_Binary_Concat($expr, $node, $node->getTemplateLine());
}
return $expr;
}
public function parseArrayExpression()
{
$stream = $this->parser->getStream();
$stream->expect(Twig_Token::PUNCTUATION_TYPE, '[', 'An array element was expected');
$node = new Twig_Node_Expression_Array(array(), $stream->getCurrent()->getLine());
$first = true;
while (!$stream->test(Twig_Token::PUNCTUATION_TYPE, ']')) {
if (!$first) {
$stream->expect(Twig_Token::PUNCTUATION_TYPE, ',', 'An array element must be followed by a comma');
// trailing ,?
if ($stream->test(Twig_Token::PUNCTUATION_TYPE, ']')) {
break;
}
}
$first = false;
$node->addElement($this->parseExpression());
}
$stream->expect(Twig_Token::PUNCTUATION_TYPE, ']', 'An opened array is not properly closed');
return $node;
}
public function parseHashExpression()
{
$stream = $this->parser->getStream();
$stream->expect(Twig_Token::PUNCTUATION_TYPE, '{', 'A hash element was expected');
$node = new Twig_Node_Expression_Array(array(), $stream->getCurrent()->getLine());
$first = true;
while (!$stream->test(Twig_Token::PUNCTUATION_TYPE, '}')) {
if (!$first) {
$stream->expect(Twig_Token::PUNCTUATION_TYPE, ',', 'A hash value must be followed by a comma');
// trailing ,?
if ($stream->test(Twig_Token::PUNCTUATION_TYPE, '}')) {
break;
}
}
$first = false;
// a hash key can be:
//
// * a number -- 12
// * a string -- 'a'
// * a name, which is equivalent to a string -- a
// * an expression, which must be enclosed in parentheses -- (1 + 2)
if (($token = $stream->nextIf(Twig_Token::STRING_TYPE)) || ($token = $stream->nextIf(Twig_Token::NAME_TYPE)) || $token = $stream->nextIf(Twig_Token::NUMBER_TYPE)) {
$key = new Twig_Node_Expression_Constant($token->getValue(), $token->getLine());
} elseif ($stream->test(Twig_Token::PUNCTUATION_TYPE, '(')) {
$key = $this->parseExpression();
} else {
$current = $stream->getCurrent();
throw new Twig_Error_Syntax(sprintf('A hash key must be a quoted string, a number, a name, or an expression enclosed in parentheses (unexpected token "%s" of value "%s".', Twig_Token::typeToEnglish($current->getType()), $current->getValue()), $current->getLine(), $stream->getSourceContext());
}
$stream->expect(Twig_Token::PUNCTUATION_TYPE, ':', 'A hash key must be followed by a colon (:)');
$value = $this->parseExpression();
$node->addElement($value, $key);
}
$stream->expect(Twig_Token::PUNCTUATION_TYPE, '}', 'An opened hash is not properly closed');
return $node;
}
public function parsePostfixExpression($node)
{
while (true) {
$token = $this->parser->getCurrentToken();
if (Twig_Token::PUNCTUATION_TYPE == $token->getType()) {
if ('.' == $token->getValue() || '[' == $token->getValue()) {
$node = $this->parseSubscriptExpression($node);
} elseif ('|' == $token->getValue()) {
$node = $this->parseFilterExpression($node);
} else {
break;
}
} else {
break;
}
}
return $node;
}
public function getFunctionNode($name, $line)
{
switch ($name) {
case 'parent':
$this->parseArguments();
if (!count($this->parser->getBlockStack())) {
throw new Twig_Error_Syntax('Calling "parent" outside a block is forbidden.', $line, $this->parser->getStream()->getSourceContext());
}
if (!$this->parser->getParent() && !$this->parser->hasTraits()) {
throw new Twig_Error_Syntax('Calling "parent" on a template that does not extend nor "use" another template is forbidden.', $line, $this->parser->getStream()->getSourceContext());
}
return new Twig_Node_Expression_Parent($this->parser->peekBlockStack(), $line);
case 'block':
$args = $this->parseArguments();
if (count($args) < 1) {
throw new Twig_Error_Syntax('The "block" function takes one argument (the block name).', $line, $this->parser->getStream()->getSourceContext());
}
return new Twig_Node_Expression_BlockReference($args->getNode(0), count($args) > 1 ? $args->getNode(1) : null, $line);
case 'attribute':
$args = $this->parseArguments();
if (count($args) < 2) {
throw new Twig_Error_Syntax('The "attribute" function takes at least two arguments (the variable and the attributes).', $line, $this->parser->getStream()->getSourceContext());
}
return new Twig_Node_Expression_GetAttr($args->getNode(0), $args->getNode(1), count($args) > 2 ? $args->getNode(2) : null, Twig_Template::ANY_CALL, $line);
default:
if (null !== $alias = $this->parser->getImportedSymbol('function', $name)) {
$arguments = new Twig_Node_Expression_Array(array(), $line);
foreach ($this->parseArguments() as $n) {
$arguments->addElement($n);
}
$node = new Twig_Node_Expression_MethodCall($alias['node'], $alias['name'], $arguments, $line);
$node->setAttribute('safe', true);
return $node;
}
$args = $this->parseArguments(true);
$class = $this->getFunctionNodeClass($name, $line);
return new $class($name, $args, $line);
}
}
public function parseSubscriptExpression($node)
{
$stream = $this->parser->getStream();
$token = $stream->next();
$lineno = $token->getLine();
$arguments = new Twig_Node_Expression_Array(array(), $lineno);
$type = Twig_Template::ANY_CALL;
if ('.' == $token->getValue()) {
$token = $stream->next();
if (
Twig_Token::NAME_TYPE == $token->getType()
||
Twig_Token::NUMBER_TYPE == $token->getType()
||
(Twig_Token::OPERATOR_TYPE == $token->getType() && preg_match(Twig_Lexer::REGEX_NAME, $token->getValue()))
) {
$arg = new Twig_Node_Expression_Constant($token->getValue(), $lineno);
if ($stream->test(Twig_Token::PUNCTUATION_TYPE, '(')) {
$type = Twig_Template::METHOD_CALL;
foreach ($this->parseArguments() as $n) {
$arguments->addElement($n);
}
}
} else {
throw new Twig_Error_Syntax('Expected name or number.', $lineno, $stream->getSourceContext());
}
if ($node instanceof Twig_Node_Expression_Name && null !== $this->parser->getImportedSymbol('template', $node->getAttribute('name'))) {
if (!$arg instanceof Twig_Node_Expression_Constant) {
throw new Twig_Error_Syntax(sprintf('Dynamic macro names are not supported (called on "%s").', $node->getAttribute('name')), $token->getLine(), $stream->getSourceContext());
}
$name = $arg->getAttribute('value');
if ($this->parser->isReservedMacroName($name)) {
throw new Twig_Error_Syntax(sprintf('"%s" cannot be called as macro as it is a reserved keyword.', $name), $token->getLine(), $stream->getSourceContext());
}
$node = new Twig_Node_Expression_MethodCall($node, 'get'.$name, $arguments, $lineno);
$node->setAttribute('safe', true);
return $node;
}
} else {
$type = Twig_Template::ARRAY_CALL;
// slice?
$slice = false;
if ($stream->test(Twig_Token::PUNCTUATION_TYPE, ':')) {
$slice = true;
$arg = new Twig_Node_Expression_Constant(0, $token->getLine());
} else {
$arg = $this->parseExpression();
}
if ($stream->nextIf(Twig_Token::PUNCTUATION_TYPE, ':')) {
$slice = true;
}
if ($slice) {
if ($stream->test(Twig_Token::PUNCTUATION_TYPE, ']')) {
$length = new Twig_Node_Expression_Constant(null, $token->getLine());
} else {
$length = $this->parseExpression();
}
$class = $this->getFilterNodeClass('slice', $token->getLine());
$arguments = new Twig_Node(array($arg, $length));
$filter = new $class($node, new Twig_Node_Expression_Constant('slice', $token->getLine()), $arguments, $token->getLine());
$stream->expect(Twig_Token::PUNCTUATION_TYPE, ']');
return $filter;
}
$stream->expect(Twig_Token::PUNCTUATION_TYPE, ']');
}
return new Twig_Node_Expression_GetAttr($node, $arg, $arguments, $type, $lineno);
}
public function parseFilterExpression($node)
{
$this->parser->getStream()->next();
return $this->parseFilterExpressionRaw($node);
}
public function parseFilterExpressionRaw($node, $tag = null)
{
while (true) {
$token = $this->parser->getStream()->expect(Twig_Token::NAME_TYPE);
$name = new Twig_Node_Expression_Constant($token->getValue(), $token->getLine());
if (!$this->parser->getStream()->test(Twig_Token::PUNCTUATION_TYPE, '(')) {
$arguments = new Twig_Node();
} else {
$arguments = $this->parseArguments(true);
}
$class = $this->getFilterNodeClass($name->getAttribute('value'), $token->getLine());
$node = new $class($node, $name, $arguments, $token->getLine(), $tag);
if (!$this->parser->getStream()->test(Twig_Token::PUNCTUATION_TYPE, '|')) {
break;
}
$this->parser->getStream()->next();
}
return $node;
}
/**
* Parses arguments.
*
* @param bool $namedArguments Whether to allow named arguments or not
* @param bool $definition Whether we are parsing arguments for a function definition
*
* @return Twig_Node
*
* @throws Twig_Error_Syntax
*/
public function parseArguments($namedArguments = false, $definition = false)
{
$args = array();
$stream = $this->parser->getStream();
$stream->expect(Twig_Token::PUNCTUATION_TYPE, '(', 'A list of arguments must begin with an opening parenthesis');
while (!$stream->test(Twig_Token::PUNCTUATION_TYPE, ')')) {
if (!empty($args)) {
$stream->expect(Twig_Token::PUNCTUATION_TYPE, ',', 'Arguments must be separated by a comma');
}
if ($definition) {
$token = $stream->expect(Twig_Token::NAME_TYPE, null, 'An argument must be a name');
$value = new Twig_Node_Expression_Name($token->getValue(), $this->parser->getCurrentToken()->getLine());
} else {
$value = $this->parseExpression();
}
$name = null;
if ($namedArguments && $token = $stream->nextIf(Twig_Token::OPERATOR_TYPE, '=')) {
if (!$value instanceof Twig_Node_Expression_Name) {
throw new Twig_Error_Syntax(sprintf('A parameter name must be a string, "%s" given.', get_class($value)), $token->getLine(), $stream->getSourceContext());
}
$name = $value->getAttribute('name');
if ($definition) {
$value = $this->parsePrimaryExpression();
if (!$this->checkConstantExpression($value)) {
throw new Twig_Error_Syntax(sprintf('A default value for an argument must be a constant (a boolean, a string, a number, or an array).'), $token->getLine(), $stream->getSourceContext());
}
} else {
$value = $this->parseExpression();
}
}
if ($definition) {
if (null === $name) {
$name = $value->getAttribute('name');
$value = new Twig_Node_Expression_Constant(null, $this->parser->getCurrentToken()->getLine());
}
$args[$name] = $value;
} else {
if (null === $name) {
$args[] = $value;
} else {
$args[$name] = $value;
}
}
}
$stream->expect(Twig_Token::PUNCTUATION_TYPE, ')', 'A list of arguments must be closed by a parenthesis');
return new Twig_Node($args);
}
public function parseAssignmentExpression()
{
$stream = $this->parser->getStream();
$targets = array();
while (true) {
$token = $stream->expect(Twig_Token::NAME_TYPE, null, 'Only variables can be assigned to');
$value = $token->getValue();
if (in_array(strtolower($value), array('true', 'false', 'none', 'null'))) {
throw new Twig_Error_Syntax(sprintf('You cannot assign a value to "%s".', $value), $token->getLine(), $stream->getSourceContext());
}
$targets[] = new Twig_Node_Expression_AssignName($value, $token->getLine());
if (!$stream->nextIf(Twig_Token::PUNCTUATION_TYPE, ',')) {
break;
}
}
return new Twig_Node($targets);
}
public function parseMultitargetExpression()
{
$targets = array();
while (true) {
$targets[] = $this->parseExpression();
if (!$this->parser->getStream()->nextIf(Twig_Token::PUNCTUATION_TYPE, ',')) {
break;
}
}
return new Twig_Node($targets);
}
private function parseNotTestExpression(Twig_NodeInterface $node)
{
return new Twig_Node_Expression_Unary_Not($this->parseTestExpression($node), $this->parser->getCurrentToken()->getLine());
}
private function parseTestExpression(Twig_NodeInterface $node)
{
$stream = $this->parser->getStream();
list($name, $test) = $this->getTest($node->getTemplateLine());
$class = $this->getTestNodeClass($test);
$arguments = null;
if ($stream->test(Twig_Token::PUNCTUATION_TYPE, '(')) {
$arguments = $this->parser->getExpressionParser()->parseArguments(true);
}
return new $class($node, $name, $arguments, $this->parser->getCurrentToken()->getLine());
}
private function getTest($line)
{
$stream = $this->parser->getStream();
$name = $stream->expect(Twig_Token::NAME_TYPE)->getValue();
if ($test = $this->env->getTest($name)) {
return array($name, $test);
}
if ($stream->test(Twig_Token::NAME_TYPE)) {
// try 2-words tests
$name = $name.' '.$this->parser->getCurrentToken()->getValue();
if ($test = $this->env->getTest($name)) {
$stream->next();
return array($name, $test);
}
}
$e = new Twig_Error_Syntax(sprintf('Unknown "%s" test.', $name), $line, $stream->getSourceContext());
$e->addSuggestions($name, array_keys($this->env->getTests()));
throw $e;
}
private function getTestNodeClass($test)
{
if ($test instanceof Twig_SimpleTest && $test->isDeprecated()) {
$stream = $this->parser->getStream();
$message = sprintf('Twig Test "%s" is deprecated', $test->getName());
if (!is_bool($test->getDeprecatedVersion())) {
$message .= sprintf(' since version %s', $test->getDeprecatedVersion());
}
if ($test->getAlternative()) {
$message .= sprintf('. Use "%s" instead', $test->getAlternative());
}
$src = $stream->getSourceContext();
$message .= sprintf(' in %s at line %d.', $src->getPath() ? $src->getPath() : $src->getName(), $stream->getCurrent()->getLine());
@trigger_error($message, E_USER_DEPRECATED);
}
if ($test instanceof Twig_SimpleTest) {
return $test->getNodeClass();
}
return $test instanceof Twig_Test_Node ? $test->getClass() : 'Twig_Node_Expression_Test';
}
protected function getFunctionNodeClass($name, $line)
{
if (false === $function = $this->env->getFunction($name)) {
$e = new Twig_Error_Syntax(sprintf('Unknown "%s" function.', $name), $line, $this->parser->getStream()->getSourceContext());
$e->addSuggestions($name, array_keys($this->env->getFunctions()));
throw $e;
}
if ($function instanceof Twig_SimpleFunction && $function->isDeprecated()) {
$message = sprintf('Twig Function "%s" is deprecated', $function->getName());
if (!is_bool($function->getDeprecatedVersion())) {
$message .= sprintf(' since version %s', $function->getDeprecatedVersion());
}
if ($function->getAlternative()) {
$message .= sprintf('. Use "%s" instead', $function->getAlternative());
}
$src = $this->parser->getStream()->getSourceContext();
$message .= sprintf(' in %s at line %d.', $src->getPath() ? $src->getPath() : $src->getName(), $line);
@trigger_error($message, E_USER_DEPRECATED);
}
if ($function instanceof Twig_SimpleFunction) {
return $function->getNodeClass();
}
return $function instanceof Twig_Function_Node ? $function->getClass() : 'Twig_Node_Expression_Function';
}
protected function getFilterNodeClass($name, $line)
{
if (false === $filter = $this->env->getFilter($name)) {
$e = new Twig_Error_Syntax(sprintf('Unknown "%s" filter.', $name), $line, $this->parser->getStream()->getSourceContext());
$e->addSuggestions($name, array_keys($this->env->getFilters()));
throw $e;
}
if ($filter instanceof Twig_SimpleFilter && $filter->isDeprecated()) {
$message = sprintf('Twig Filter "%s" is deprecated', $filter->getName());
if (!is_bool($filter->getDeprecatedVersion())) {
$message .= sprintf(' since version %s', $filter->getDeprecatedVersion());
}
if ($filter->getAlternative()) {
$message .= sprintf('. Use "%s" instead', $filter->getAlternative());
}
$src = $this->parser->getStream()->getSourceContext();
$message .= sprintf(' in %s at line %d.', $src->getPath() ? $src->getPath() : $src->getName(), $line);
@trigger_error($message, E_USER_DEPRECATED);
}
if ($filter instanceof Twig_SimpleFilter) {
return $filter->getNodeClass();
}
return $filter instanceof Twig_Filter_Node ? $filter->getClass() : 'Twig_Node_Expression_Filter';
}
// checks that the node only contains "constant" elements
protected function checkConstantExpression(Twig_NodeInterface $node)
{
if (!($node instanceof Twig_Node_Expression_Constant || $node instanceof Twig_Node_Expression_Array
|| $node instanceof Twig_Node_Expression_Unary_Neg || $node instanceof Twig_Node_Expression_Unary_Pos
)) {
return false;
}
foreach ($node as $n) {
if (!$this->checkConstantExpression($n)) {
return false;
}
}
return true;
}
}
class_alias('Twig_ExpressionParser', 'Twig\ExpressionParser', false);

View File

@ -1,47 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* @final
*/
class Twig_Extension_StringLoader extends Twig_Extension
{
public function getFunctions()
{
return array(
new Twig_SimpleFunction('template_from_string', 'twig_template_from_string', array('needs_environment' => true)),
);
}
public function getName()
{
return 'string_loader';
}
}
/**
* Loads a template from a string.
*
* <pre>
* {{ include(template_from_string("Hello {{ name }}")) }}
* </pre>
*
* @param Twig_Environment $env A Twig_Environment instance
* @param string $template A template as a string or object implementing __toString()
*
* @return Twig_Template
*/
function twig_template_from_string(Twig_Environment $env, $template)
{
return $env->createTemplate((string) $template);
}
class_alias('Twig_Extension_StringLoader', 'Twig\Extension\StringLoaderExtension', false);

View File

@ -1,19 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
class Twig_Node_Expression_Binary_GreaterEqual extends Twig_Node_Expression_Binary
{
public function operator(Twig_Compiler $compiler)
{
return $compiler->raw('>=');
}
}
class_alias('Twig_Node_Expression_Binary_GreaterEqual', 'Twig\Node\Expression\Binary\GreaterEqualBinary', false);

View File

@ -1,19 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
class Twig_Node_Expression_Binary_LessEqual extends Twig_Node_Expression_Binary
{
public function operator(Twig_Compiler $compiler)
{
return $compiler->raw('<=');
}
}
class_alias('Twig_Node_Expression_Binary_LessEqual', 'Twig\Node\Expression\Binary\LessEqualBinary', false);

View File

@ -1,45 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Returns the value or the default value when it is undefined or empty.
*
* <pre>
* {{ var.foo|default('foo item on var is not defined') }}
* </pre>
*
* @author Fabien Potencier <fabien@symfony.com>
*/
class Twig_Node_Expression_Filter_Default extends Twig_Node_Expression_Filter
{
public function __construct(Twig_NodeInterface $node, Twig_Node_Expression_Constant $filterName, Twig_NodeInterface $arguments, $lineno, $tag = null)
{
$default = new Twig_Node_Expression_Filter($node, new Twig_Node_Expression_Constant('default', $node->getTemplateLine()), $arguments, $node->getTemplateLine());
if ('default' === $filterName->getAttribute('value') && ($node instanceof Twig_Node_Expression_Name || $node instanceof Twig_Node_Expression_GetAttr)) {
$test = new Twig_Node_Expression_Test_Defined(clone $node, 'defined', new Twig_Node(), $node->getTemplateLine());
$false = count($arguments) ? $arguments->getNode(0) : new Twig_Node_Expression_Constant('', $node->getTemplateLine());
$node = new Twig_Node_Expression_Conditional($test, $default, $false, $node->getTemplateLine());
} else {
$node = $default;
}
parent::__construct($node, $filterName, $arguments, $lineno, $tag);
}
public function compile(Twig_Compiler $compiler)
{
$compiler->subcompile($this->getNode('node'));
}
}
class_alias('Twig_Node_Expression_Filter_Default', 'Twig\Node\Expression\Filter\DefaultFilter', false);

View File

@ -1,48 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
class Twig_Node_Expression_NullCoalesce extends Twig_Node_Expression_Conditional
{
public function __construct(Twig_NodeInterface $left, Twig_NodeInterface $right, $lineno)
{
$test = new Twig_Node_Expression_Binary_And(
new Twig_Node_Expression_Test_Defined(clone $left, 'defined', new Twig_Node(), $left->getTemplateLine()),
new Twig_Node_Expression_Unary_Not(new Twig_Node_Expression_Test_Null($left, 'null', new Twig_Node(), $left->getTemplateLine()), $left->getTemplateLine()),
$left->getTemplateLine()
);
parent::__construct($test, $left, $right, $lineno);
}
public function compile(Twig_Compiler $compiler)
{
/*
* This optimizes only one case. PHP 7 also supports more complex expressions
* that can return null. So, for instance, if log is defined, log("foo") ?? "..." works,
* but log($a["foo"]) ?? "..." does not if $a["foo"] is not defined. More advanced
* cases might be implemented as an optimizer node visitor, but has not been done
* as benefits are probably not worth the added complexity.
*/
if (PHP_VERSION_ID >= 70000 && $this->getNode('expr2') instanceof Twig_Node_Expression_Name) {
$this->getNode('expr2')->setAttribute('always_defined', true);
$compiler
->raw('((')
->subcompile($this->getNode('expr2'))
->raw(') ?? (')
->subcompile($this->getNode('expr3'))
->raw('))')
;
} else {
parent::compile($compiler);
}
}
}
class_alias('Twig_Node_Expression_NullCoalesce', 'Twig\Node\Expression\NullCoalesceExpression', false);

View File

@ -1,61 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Checks if a variable is defined in the current context.
*
* <pre>
* {# defined works with variable names and variable attributes #}
* {% if foo is defined %}
* {# ... #}
* {% endif %}
* </pre>
*
* @author Fabien Potencier <fabien@symfony.com>
*/
class Twig_Node_Expression_Test_Defined extends Twig_Node_Expression_Test
{
public function __construct(Twig_NodeInterface $node, $name, Twig_NodeInterface $arguments = null, $lineno)
{
if ($node instanceof Twig_Node_Expression_Name) {
$node->setAttribute('is_defined_test', true);
} elseif ($node instanceof Twig_Node_Expression_GetAttr) {
$node->setAttribute('is_defined_test', true);
$this->changeIgnoreStrictCheck($node);
} elseif ($node instanceof Twig_Node_Expression_BlockReference) {
$node->setAttribute('is_defined_test', true);
} elseif ($node instanceof Twig_Node_Expression_Function && 'constant' === $node->getAttribute('name')) {
$node->setAttribute('is_defined_test', true);
} elseif ($node instanceof Twig_Node_Expression_Constant || $node instanceof Twig_Node_Expression_Array) {
$node = new Twig_Node_Expression_Constant(true, $node->getTemplateLine());
} else {
throw new Twig_Error_Syntax('The "defined" test only works with simple variables.', $this->getTemplateLine());
}
parent::__construct($node, $name, $arguments, $lineno);
}
protected function changeIgnoreStrictCheck(Twig_Node_Expression_GetAttr $node)
{
$node->setAttribute('ignore_strict_check', true);
if ($node->getNode('node') instanceof Twig_Node_Expression_GetAttr) {
$this->changeIgnoreStrictCheck($node->getNode('node'));
}
}
public function compile(Twig_Compiler $compiler)
{
$compiler->subcompile($this->getNode('node'));
}
}
class_alias('Twig_Node_Expression_Test_Defined', 'Twig\Node\Expression\Test\DefinedTest', false);

View File

@ -1,29 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
* (c) Armin Ronacher
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
abstract class Twig_Node_Expression_Unary extends Twig_Node_Expression
{
public function __construct(Twig_NodeInterface $node, $lineno)
{
parent::__construct(array('node' => $node), array(), $lineno);
}
public function compile(Twig_Compiler $compiler)
{
$compiler->raw(' ');
$this->operator($compiler);
$compiler->subcompile($this->getNode('node'));
}
abstract public function operator(Twig_Compiler $compiler);
}
class_alias('Twig_Node_Expression_Unary', 'Twig\Node\Expression\Unary\AbstractUnary', false);

View File

@ -1,90 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
* (c) Armin Ronacher
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Represents an include node.
*
* @author Fabien Potencier <fabien@symfony.com>
*/
class Twig_Node_Include extends Twig_Node implements Twig_NodeOutputInterface
{
public function __construct(Twig_Node_Expression $expr, Twig_Node_Expression $variables = null, $only = false, $ignoreMissing = false, $lineno, $tag = null)
{
$nodes = array('expr' => $expr);
if (null !== $variables) {
$nodes['variables'] = $variables;
}
parent::__construct($nodes, array('only' => (bool) $only, 'ignore_missing' => (bool) $ignoreMissing), $lineno, $tag);
}
public function compile(Twig_Compiler $compiler)
{
$compiler->addDebugInfo($this);
if ($this->getAttribute('ignore_missing')) {
$compiler
->write("try {\n")
->indent()
;
}
$this->addGetTemplate($compiler);
$compiler->raw('->display(');
$this->addTemplateArguments($compiler);
$compiler->raw(");\n");
if ($this->getAttribute('ignore_missing')) {
$compiler
->outdent()
->write("} catch (Twig_Error_Loader \$e) {\n")
->indent()
->write("// ignore missing template\n")
->outdent()
->write("}\n\n")
;
}
}
protected function addGetTemplate(Twig_Compiler $compiler)
{
$compiler
->write('$this->loadTemplate(')
->subcompile($this->getNode('expr'))
->raw(', ')
->repr($this->getTemplateName())
->raw(', ')
->repr($this->getTemplateLine())
->raw(')')
;
}
protected function addTemplateArguments(Twig_Compiler $compiler)
{
if (!$this->hasNode('variables')) {
$compiler->raw(false === $this->getAttribute('only') ? '$context' : 'array()');
} elseif (false === $this->getAttribute('only')) {
$compiler
->raw('array_merge($context, ')
->subcompile($this->getNode('variables'))
->raw(')')
;
} else {
$compiler->subcompile($this->getNode('variables'));
}
}
}
class_alias('Twig_Node_Include', 'Twig\Node\IncludeNode', false);

View File

@ -1,51 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Twig_Node_SandboxedPrint adds a check for the __toString() method
* when the variable is an object and the sandbox is activated.
*
* When there is a simple Print statement, like {{ article }},
* and if the sandbox is enabled, we need to check that the __toString()
* method is allowed if 'article' is an object.
*
* @author Fabien Potencier <fabien@symfony.com>
*/
class Twig_Node_SandboxedPrint extends Twig_Node_Print
{
public function compile(Twig_Compiler $compiler)
{
$compiler
->addDebugInfo($this)
->write('echo $this->env->getExtension(\'Twig_Extension_Sandbox\')->ensureToStringAllowed(')
->subcompile($this->getNode('expr'))
->raw(");\n")
;
}
/**
* Removes node filters.
*
* This is mostly needed when another visitor adds filters (like the escaper one).
*
* @return Twig_Node
*/
protected function removeNodeFilter(Twig_Node $node)
{
if ($node instanceof Twig_Node_Expression_Filter) {
return $this->removeNodeFilter($node->getNode('node'));
}
return $node;
}
}
class_alias('Twig_Node_SandboxedPrint', 'Twig\Node\SandboxedPrintNode', false);

View File

@ -1,37 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Represents a spaceless node.
*
* It removes spaces between HTML tags.
*
* @author Fabien Potencier <fabien@symfony.com>
*/
class Twig_Node_Spaceless extends Twig_Node
{
public function __construct(Twig_NodeInterface $body, $lineno, $tag = 'spaceless')
{
parent::__construct(array('body' => $body), array(), $lineno, $tag);
}
public function compile(Twig_Compiler $compiler)
{
$compiler
->addDebugInfo($this)
->write("ob_start();\n")
->subcompile($this->getNode('body'))
->write("echo trim(preg_replace('/>\s+</', '><', ob_get_clean()));\n")
;
}
}
class_alias('Twig_Node_Spaceless', 'Twig\Node\SpacelessNode', false);

View File

@ -1,154 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Twig_NodeVisitor_Escaper implements output escaping.
*
* @final
*
* @author Fabien Potencier <fabien@symfony.com>
*/
class Twig_NodeVisitor_Escaper extends Twig_BaseNodeVisitor
{
protected $statusStack = array();
protected $blocks = array();
protected $safeAnalysis;
protected $traverser;
protected $defaultStrategy = false;
protected $safeVars = array();
public function __construct()
{
$this->safeAnalysis = new Twig_NodeVisitor_SafeAnalysis();
}
protected function doEnterNode(Twig_Node $node, Twig_Environment $env)
{
if ($node instanceof Twig_Node_Module) {
if ($env->hasExtension('Twig_Extension_Escaper') && $defaultStrategy = $env->getExtension('Twig_Extension_Escaper')->getDefaultStrategy($node->getTemplateName())) {
$this->defaultStrategy = $defaultStrategy;
}
$this->safeVars = array();
$this->blocks = array();
} elseif ($node instanceof Twig_Node_AutoEscape) {
$this->statusStack[] = $node->getAttribute('value');
} elseif ($node instanceof Twig_Node_Block) {
$this->statusStack[] = isset($this->blocks[$node->getAttribute('name')]) ? $this->blocks[$node->getAttribute('name')] : $this->needEscaping($env);
} elseif ($node instanceof Twig_Node_Import) {
$this->safeVars[] = $node->getNode('var')->getAttribute('name');
}
return $node;
}
protected function doLeaveNode(Twig_Node $node, Twig_Environment $env)
{
if ($node instanceof Twig_Node_Module) {
$this->defaultStrategy = false;
$this->safeVars = array();
$this->blocks = array();
} elseif ($node instanceof Twig_Node_Expression_Filter) {
return $this->preEscapeFilterNode($node, $env);
} elseif ($node instanceof Twig_Node_Print) {
return $this->escapePrintNode($node, $env, $this->needEscaping($env));
}
if ($node instanceof Twig_Node_AutoEscape || $node instanceof Twig_Node_Block) {
array_pop($this->statusStack);
} elseif ($node instanceof Twig_Node_BlockReference) {
$this->blocks[$node->getAttribute('name')] = $this->needEscaping($env);
}
return $node;
}
protected function escapePrintNode(Twig_Node_Print $node, Twig_Environment $env, $type)
{
if (false === $type) {
return $node;
}
$expression = $node->getNode('expr');
if ($this->isSafeFor($type, $expression, $env)) {
return $node;
}
$class = get_class($node);
return new $class(
$this->getEscaperFilter($type, $expression),
$node->getTemplateLine()
);
}
protected function preEscapeFilterNode(Twig_Node_Expression_Filter $filter, Twig_Environment $env)
{
$name = $filter->getNode('filter')->getAttribute('value');
$type = $env->getFilter($name)->getPreEscape();
if (null === $type) {
return $filter;
}
$node = $filter->getNode('node');
if ($this->isSafeFor($type, $node, $env)) {
return $filter;
}
$filter->setNode('node', $this->getEscaperFilter($type, $node));
return $filter;
}
protected function isSafeFor($type, Twig_NodeInterface $expression, $env)
{
$safe = $this->safeAnalysis->getSafe($expression);
if (null === $safe) {
if (null === $this->traverser) {
$this->traverser = new Twig_NodeTraverser($env, array($this->safeAnalysis));
}
$this->safeAnalysis->setSafeVars($this->safeVars);
$this->traverser->traverse($expression);
$safe = $this->safeAnalysis->getSafe($expression);
}
return in_array($type, $safe) || in_array('all', $safe);
}
protected function needEscaping(Twig_Environment $env)
{
if (count($this->statusStack)) {
return $this->statusStack[count($this->statusStack) - 1];
}
return $this->defaultStrategy ? $this->defaultStrategy : false;
}
protected function getEscaperFilter($type, Twig_NodeInterface $node)
{
$line = $node->getTemplateLine();
$name = new Twig_Node_Expression_Constant('escape', $line);
$args = new Twig_Node(array(new Twig_Node_Expression_Constant((string) $type, $line), new Twig_Node_Expression_Constant(null, $line), new Twig_Node_Expression_Constant(true, $line)));
return new Twig_Node_Expression_Filter($node, $name, $args, $line);
}
public function getPriority()
{
return 0;
}
}
class_alias('Twig_NodeVisitor_Escaper', 'Twig\NodeVisitor\EscaperNodeVisitor', false);

View File

@ -1,82 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Twig_NodeVisitor_Sandbox implements sandboxing.
*
* @final
*
* @author Fabien Potencier <fabien@symfony.com>
*/
class Twig_NodeVisitor_Sandbox extends Twig_BaseNodeVisitor
{
protected $inAModule = false;
protected $tags;
protected $filters;
protected $functions;
protected function doEnterNode(Twig_Node $node, Twig_Environment $env)
{
if ($node instanceof Twig_Node_Module) {
$this->inAModule = true;
$this->tags = array();
$this->filters = array();
$this->functions = array();
return $node;
} elseif ($this->inAModule) {
// look for tags
if ($node->getNodeTag() && !isset($this->tags[$node->getNodeTag()])) {
$this->tags[$node->getNodeTag()] = $node;
}
// look for filters
if ($node instanceof Twig_Node_Expression_Filter && !isset($this->filters[$node->getNode('filter')->getAttribute('value')])) {
$this->filters[$node->getNode('filter')->getAttribute('value')] = $node;
}
// look for functions
if ($node instanceof Twig_Node_Expression_Function && !isset($this->functions[$node->getAttribute('name')])) {
$this->functions[$node->getAttribute('name')] = $node;
}
// the .. operator is equivalent to the range() function
if ($node instanceof Twig_Node_Expression_Binary_Range && !isset($this->functions['range'])) {
$this->functions['range'] = $node;
}
// wrap print to check __toString() calls
if ($node instanceof Twig_Node_Print) {
return new Twig_Node_SandboxedPrint($node->getNode('expr'), $node->getTemplateLine(), $node->getNodeTag());
}
}
return $node;
}
protected function doLeaveNode(Twig_Node $node, Twig_Environment $env)
{
if ($node instanceof Twig_Node_Module) {
$this->inAModule = false;
$node->setNode('display_start', new Twig_Node(array(new Twig_Node_CheckSecurity($this->filters, $this->tags, $this->functions), $node->getNode('display_start'))));
}
return $node;
}
public function getPriority()
{
return 0;
}
}
class_alias('Twig_NodeVisitor_Sandbox', 'Twig\NodeVisitor\SandboxNodeVisitor', false);

View File

@ -1,45 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Twig_NodeVisitorInterface is the interface the all node visitor classes must implement.
*
* @author Fabien Potencier <fabien@symfony.com>
*/
interface Twig_NodeVisitorInterface
{
/**
* Called before child nodes are visited.
*
* @return Twig_NodeInterface The modified node
*/
public function enterNode(Twig_NodeInterface $node, Twig_Environment $env);
/**
* Called after child nodes are visited.
*
* @return Twig_NodeInterface|false The modified node or false if the node must be removed
*/
public function leaveNode(Twig_NodeInterface $node, Twig_Environment $env);
/**
* Returns the priority for this visitor.
*
* Priority should be between -10 and 10 (0 is the default).
*
* @return int The priority level
*/
public function getPriority();
}
class_alias('Twig_NodeVisitorInterface', 'Twig\NodeVisitor\NodeVisitorInterface', false);
class_exists('Twig_Environment');
class_exists('Twig_Node');

View File

@ -1,67 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* @author Fabien Potencier <fabien@symfony.com>
*
* @final
*/
class Twig_Profiler_NodeVisitor_Profiler extends Twig_BaseNodeVisitor
{
private $extensionName;
public function __construct($extensionName)
{
$this->extensionName = $extensionName;
}
protected function doEnterNode(Twig_Node $node, Twig_Environment $env)
{
return $node;
}
protected function doLeaveNode(Twig_Node $node, Twig_Environment $env)
{
if ($node instanceof Twig_Node_Module) {
$varName = $this->getVarName();
$node->setNode('display_start', new Twig_Node(array(new Twig_Profiler_Node_EnterProfile($this->extensionName, Twig_Profiler_Profile::TEMPLATE, $node->getTemplateName(), $varName), $node->getNode('display_start'))));
$node->setNode('display_end', new Twig_Node(array(new Twig_Profiler_Node_LeaveProfile($varName), $node->getNode('display_end'))));
} elseif ($node instanceof Twig_Node_Block) {
$varName = $this->getVarName();
$node->setNode('body', new Twig_Node_Body(array(
new Twig_Profiler_Node_EnterProfile($this->extensionName, Twig_Profiler_Profile::BLOCK, $node->getAttribute('name'), $varName),
$node->getNode('body'),
new Twig_Profiler_Node_LeaveProfile($varName),
)));
} elseif ($node instanceof Twig_Node_Macro) {
$varName = $this->getVarName();
$node->setNode('body', new Twig_Node_Body(array(
new Twig_Profiler_Node_EnterProfile($this->extensionName, Twig_Profiler_Profile::MACRO, $node->getAttribute('name'), $varName),
$node->getNode('body'),
new Twig_Profiler_Node_LeaveProfile($varName),
)));
}
return $node;
}
private function getVarName()
{
return sprintf('__internal_%s', hash('sha256', $this->extensionName));
}
public function getPriority()
{
return 0;
}
}
class_alias('Twig_Profiler_NodeVisitor_Profiler', 'Twig\Profiler\NodeVisitor\ProfilerNodeVisitor', false);

View File

@ -1,83 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Marks a section of a template to be escaped or not.
*
* <pre>
* {% autoescape true %}
* Everything will be automatically escaped in this block
* {% endautoescape %}
*
* {% autoescape false %}
* Everything will be outputed as is in this block
* {% endautoescape %}
*
* {% autoescape true js %}
* Everything will be automatically escaped in this block
* using the js escaping strategy
* {% endautoescape %}
* </pre>
*
* @final
*/
class Twig_TokenParser_AutoEscape extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$lineno = $token->getLine();
$stream = $this->parser->getStream();
if ($stream->test(Twig_Token::BLOCK_END_TYPE)) {
$value = 'html';
} else {
$expr = $this->parser->getExpressionParser()->parseExpression();
if (!$expr instanceof Twig_Node_Expression_Constant) {
throw new Twig_Error_Syntax('An escaping strategy must be a string or a bool.', $stream->getCurrent()->getLine(), $stream->getSourceContext());
}
$value = $expr->getAttribute('value');
$compat = true === $value || false === $value;
if (true === $value) {
$value = 'html';
}
if ($compat && $stream->test(Twig_Token::NAME_TYPE)) {
@trigger_error('Using the autoescape tag with "true" or "false" before the strategy name is deprecated since version 1.21.', E_USER_DEPRECATED);
if (false === $value) {
throw new Twig_Error_Syntax('Unexpected escaping strategy as you set autoescaping to false.', $stream->getCurrent()->getLine(), $stream->getSourceContext());
}
$value = $stream->next()->getValue();
}
}
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$body = $this->parser->subparse(array($this, 'decideBlockEnd'), true);
$stream->expect(Twig_Token::BLOCK_END_TYPE);
return new Twig_Node_AutoEscape($value, $body, $lineno, $this->getTag());
}
public function decideBlockEnd(Twig_Token $token)
{
return $token->test('endautoescape');
}
public function getTag()
{
return 'autoescape';
}
}
class_alias('Twig_TokenParser_AutoEscape', 'Twig\TokenParser\AutoEscapeTokenParser', false);

View File

@ -1,73 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
* (c) Armin Ronacher
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Marks a section of a template as being reusable.
*
* <pre>
* {% block head %}
* <link rel="stylesheet" href="style.css" />
* <title>{% block title %}{% endblock %} - My Webpage</title>
* {% endblock %}
* </pre>
*
* @final
*/
class Twig_TokenParser_Block extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$lineno = $token->getLine();
$stream = $this->parser->getStream();
$name = $stream->expect(Twig_Token::NAME_TYPE)->getValue();
if ($this->parser->hasBlock($name)) {
throw new Twig_Error_Syntax(sprintf("The block '%s' has already been defined line %d.", $name, $this->parser->getBlock($name)->getTemplateLine()), $stream->getCurrent()->getLine(), $stream->getSourceContext());
}
$this->parser->setBlock($name, $block = new Twig_Node_Block($name, new Twig_Node(array()), $lineno));
$this->parser->pushLocalScope();
$this->parser->pushBlockStack($name);
if ($stream->nextIf(Twig_Token::BLOCK_END_TYPE)) {
$body = $this->parser->subparse(array($this, 'decideBlockEnd'), true);
if ($token = $stream->nextIf(Twig_Token::NAME_TYPE)) {
$value = $token->getValue();
if ($value != $name) {
throw new Twig_Error_Syntax(sprintf('Expected endblock for block "%s" (but "%s" given).', $name, $value), $stream->getCurrent()->getLine(), $stream->getSourceContext());
}
}
} else {
$body = new Twig_Node(array(
new Twig_Node_Print($this->parser->getExpressionParser()->parseExpression(), $lineno),
));
}
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$block->setNode('body', $body);
$this->parser->popBlockStack();
$this->parser->popLocalScope();
return new Twig_Node_BlockReference($name, $lineno, $this->getTag());
}
public function decideBlockEnd(Twig_Token $token)
{
return $token->test('endblock');
}
public function getTag()
{
return 'block';
}
}
class_alias('Twig_TokenParser_Block', 'Twig\TokenParser\BlockTokenParser', false);

View File

@ -1,67 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Embeds a template.
*
* @final
*/
class Twig_TokenParser_Embed extends Twig_TokenParser_Include
{
public function parse(Twig_Token $token)
{
$stream = $this->parser->getStream();
$parent = $this->parser->getExpressionParser()->parseExpression();
list($variables, $only, $ignoreMissing) = $this->parseArguments();
$parentToken = $fakeParentToken = new Twig_Token(Twig_Token::STRING_TYPE, '__parent__', $token->getLine());
if ($parent instanceof Twig_Node_Expression_Constant) {
$parentToken = new Twig_Token(Twig_Token::STRING_TYPE, $parent->getAttribute('value'), $token->getLine());
} elseif ($parent instanceof Twig_Node_Expression_Name) {
$parentToken = new Twig_Token(Twig_Token::NAME_TYPE, $parent->getAttribute('name'), $token->getLine());
}
// inject a fake parent to make the parent() function work
$stream->injectTokens(array(
new Twig_Token(Twig_Token::BLOCK_START_TYPE, '', $token->getLine()),
new Twig_Token(Twig_Token::NAME_TYPE, 'extends', $token->getLine()),
$parentToken,
new Twig_Token(Twig_Token::BLOCK_END_TYPE, '', $token->getLine()),
));
$module = $this->parser->parse($stream, array($this, 'decideBlockEnd'), true);
// override the parent with the correct one
if ($fakeParentToken === $parentToken) {
$module->setNode('parent', $parent);
}
$this->parser->embedTemplate($module);
$stream->expect(Twig_Token::BLOCK_END_TYPE);
return new Twig_Node_Embed($module->getTemplateName(), $module->getAttribute('index'), $variables, $only, $ignoreMissing, $token->getLine(), $this->getTag());
}
public function decideBlockEnd(Twig_Token $token)
{
return $token->test('endembed');
}
public function getTag()
{
return 'embed';
}
}
class_alias('Twig_TokenParser_Embed', 'Twig\TokenParser\EmbedTokenParser', false);

View File

@ -1,46 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
* (c) Armin Ronacher
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Extends a template by another one.
*
* <pre>
* {% extends "base.html" %}
* </pre>
*
* @final
*/
class Twig_TokenParser_Extends extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$stream = $this->parser->getStream();
if (!$this->parser->isMainScope()) {
throw new Twig_Error_Syntax('Cannot extend from a block.', $token->getLine(), $stream->getSourceContext());
}
if (null !== $this->parser->getParent()) {
throw new Twig_Error_Syntax('Multiple extends tags are forbidden.', $token->getLine(), $stream->getSourceContext());
}
$this->parser->setParent($this->parser->getExpressionParser()->parseExpression());
$stream->expect(Twig_Token::BLOCK_END_TYPE);
}
public function getTag()
{
return 'extends';
}
}
class_alias('Twig_TokenParser_Extends', 'Twig\TokenParser\ExtendsTokenParser', false);

View File

@ -1,53 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Filters a section of a template by applying filters.
*
* <pre>
* {% filter upper %}
* This text becomes uppercase
* {% endfilter %}
* </pre>
*
* @final
*/
class Twig_TokenParser_Filter extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$name = $this->parser->getVarName();
$ref = new Twig_Node_Expression_BlockReference(new Twig_Node_Expression_Constant($name, $token->getLine()), null, $token->getLine(), $this->getTag());
$filter = $this->parser->getExpressionParser()->parseFilterExpressionRaw($ref, $this->getTag());
$this->parser->getStream()->expect(Twig_Token::BLOCK_END_TYPE);
$body = $this->parser->subparse(array($this, 'decideBlockEnd'), true);
$this->parser->getStream()->expect(Twig_Token::BLOCK_END_TYPE);
$block = new Twig_Node_Block($name, $body, $token->getLine());
$this->parser->setBlock($name, $block);
return new Twig_Node_Print($filter, $token->getLine(), $this->getTag());
}
public function decideBlockEnd(Twig_Token $token)
{
return $token->test('endfilter');
}
public function getTag()
{
return 'filter';
}
}
class_alias('Twig_TokenParser_Filter', 'Twig\TokenParser\FilterTokenParser', false);

View File

@ -1,34 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Flushes the output to the client.
*
* @see flush()
*
* @final
*/
class Twig_TokenParser_Flush extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$this->parser->getStream()->expect(Twig_Token::BLOCK_END_TYPE);
return new Twig_Node_Flush($token->getLine(), $this->getTag());
}
public function getTag()
{
return 'flush';
}
}
class_alias('Twig_TokenParser_Flush', 'Twig\TokenParser\FlushTokenParser', false);

View File

@ -1,127 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
* (c) Armin Ronacher
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Loops over each item of a sequence.
*
* <pre>
* <ul>
* {% for user in users %}
* <li>{{ user.username|e }}</li>
* {% endfor %}
* </ul>
* </pre>
*
* @final
*/
class Twig_TokenParser_For extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$lineno = $token->getLine();
$stream = $this->parser->getStream();
$targets = $this->parser->getExpressionParser()->parseAssignmentExpression();
$stream->expect(Twig_Token::OPERATOR_TYPE, 'in');
$seq = $this->parser->getExpressionParser()->parseExpression();
$ifexpr = null;
if ($stream->nextIf(Twig_Token::NAME_TYPE, 'if')) {
$ifexpr = $this->parser->getExpressionParser()->parseExpression();
}
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$body = $this->parser->subparse(array($this, 'decideForFork'));
if ('else' == $stream->next()->getValue()) {
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$else = $this->parser->subparse(array($this, 'decideForEnd'), true);
} else {
$else = null;
}
$stream->expect(Twig_Token::BLOCK_END_TYPE);
if (count($targets) > 1) {
$keyTarget = $targets->getNode(0);
$keyTarget = new Twig_Node_Expression_AssignName($keyTarget->getAttribute('name'), $keyTarget->getTemplateLine());
$valueTarget = $targets->getNode(1);
$valueTarget = new Twig_Node_Expression_AssignName($valueTarget->getAttribute('name'), $valueTarget->getTemplateLine());
} else {
$keyTarget = new Twig_Node_Expression_AssignName('_key', $lineno);
$valueTarget = $targets->getNode(0);
$valueTarget = new Twig_Node_Expression_AssignName($valueTarget->getAttribute('name'), $valueTarget->getTemplateLine());
}
if ($ifexpr) {
$this->checkLoopUsageCondition($stream, $ifexpr);
$this->checkLoopUsageBody($stream, $body);
}
return new Twig_Node_For($keyTarget, $valueTarget, $seq, $ifexpr, $body, $else, $lineno, $this->getTag());
}
public function decideForFork(Twig_Token $token)
{
return $token->test(array('else', 'endfor'));
}
public function decideForEnd(Twig_Token $token)
{
return $token->test('endfor');
}
// the loop variable cannot be used in the condition
protected function checkLoopUsageCondition(Twig_TokenStream $stream, Twig_NodeInterface $node)
{
if ($node instanceof Twig_Node_Expression_GetAttr && $node->getNode('node') instanceof Twig_Node_Expression_Name && 'loop' == $node->getNode('node')->getAttribute('name')) {
throw new Twig_Error_Syntax('The "loop" variable cannot be used in a looping condition.', $node->getTemplateLine(), $stream->getSourceContext());
}
foreach ($node as $n) {
if (!$n) {
continue;
}
$this->checkLoopUsageCondition($stream, $n);
}
}
// check usage of non-defined loop-items
// it does not catch all problems (for instance when a for is included into another or when the variable is used in an include)
protected function checkLoopUsageBody(Twig_TokenStream $stream, Twig_NodeInterface $node)
{
if ($node instanceof Twig_Node_Expression_GetAttr && $node->getNode('node') instanceof Twig_Node_Expression_Name && 'loop' == $node->getNode('node')->getAttribute('name')) {
$attribute = $node->getNode('attribute');
if ($attribute instanceof Twig_Node_Expression_Constant && in_array($attribute->getAttribute('value'), array('length', 'revindex0', 'revindex', 'last'))) {
throw new Twig_Error_Syntax(sprintf('The "loop.%s" variable is not defined when looping with a condition.', $attribute->getAttribute('value')), $node->getTemplateLine(), $stream->getSourceContext());
}
}
// should check for parent.loop.XXX usage
if ($node instanceof Twig_Node_For) {
return;
}
foreach ($node as $n) {
if (!$n) {
continue;
}
$this->checkLoopUsageBody($stream, $n);
}
}
public function getTag()
{
return 'for';
}
}
class_alias('Twig_TokenParser_For', 'Twig\TokenParser\ForTokenParser', false);

View File

@ -1,66 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Imports macros.
*
* <pre>
* {% from 'forms.html' import forms %}
* </pre>
*
* @final
*/
class Twig_TokenParser_From extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$macro = $this->parser->getExpressionParser()->parseExpression();
$stream = $this->parser->getStream();
$stream->expect('import');
$targets = array();
do {
$name = $stream->expect(Twig_Token::NAME_TYPE)->getValue();
$alias = $name;
if ($stream->nextIf('as')) {
$alias = $stream->expect(Twig_Token::NAME_TYPE)->getValue();
}
$targets[$name] = $alias;
if (!$stream->nextIf(Twig_Token::PUNCTUATION_TYPE, ',')) {
break;
}
} while (true);
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$node = new Twig_Node_Import($macro, new Twig_Node_Expression_AssignName($this->parser->getVarName(), $token->getLine()), $token->getLine(), $this->getTag());
foreach ($targets as $name => $alias) {
if ($this->parser->isReservedMacroName($name)) {
throw new Twig_Error_Syntax(sprintf('"%s" cannot be an imported macro as it is a reserved keyword.', $name), $token->getLine(), $stream->getSourceContext());
}
$this->parser->addImportedSymbol('function', $alias, 'get'.$name, $node->getNode('var'));
}
return $node;
}
public function getTag()
{
return 'from';
}
}
class_alias('Twig_TokenParser_From', 'Twig\TokenParser\FromTokenParser', false);

View File

@ -1,86 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
* (c) Armin Ronacher
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Tests a condition.
*
* <pre>
* {% if users %}
* <ul>
* {% for user in users %}
* <li>{{ user.username|e }}</li>
* {% endfor %}
* </ul>
* {% endif %}
* </pre>
*
* @final
*/
class Twig_TokenParser_If extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$lineno = $token->getLine();
$expr = $this->parser->getExpressionParser()->parseExpression();
$stream = $this->parser->getStream();
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$body = $this->parser->subparse(array($this, 'decideIfFork'));
$tests = array($expr, $body);
$else = null;
$end = false;
while (!$end) {
switch ($stream->next()->getValue()) {
case 'else':
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$else = $this->parser->subparse(array($this, 'decideIfEnd'));
break;
case 'elseif':
$expr = $this->parser->getExpressionParser()->parseExpression();
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$body = $this->parser->subparse(array($this, 'decideIfFork'));
$tests[] = $expr;
$tests[] = $body;
break;
case 'endif':
$end = true;
break;
default:
throw new Twig_Error_Syntax(sprintf('Unexpected end of template. Twig was looking for the following tags "else", "elseif", or "endif" to close the "if" block started at line %d).', $lineno), $stream->getCurrent()->getLine(), $stream->getSourceContext());
}
}
$stream->expect(Twig_Token::BLOCK_END_TYPE);
return new Twig_Node_If(new Twig_Node($tests), $else, $lineno, $this->getTag());
}
public function decideIfFork(Twig_Token $token)
{
return $token->test(array('elseif', 'else', 'endif'));
}
public function decideIfEnd(Twig_Token $token)
{
return $token->test(array('endif'));
}
public function getTag()
{
return 'if';
}
}
class_alias('Twig_TokenParser_If', 'Twig\TokenParser\IfTokenParser', false);

View File

@ -1,41 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Imports macros.
*
* <pre>
* {% import 'forms.html' as forms %}
* </pre>
*
* @final
*/
class Twig_TokenParser_Import extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$macro = $this->parser->getExpressionParser()->parseExpression();
$this->parser->getStream()->expect('as');
$var = new Twig_Node_Expression_AssignName($this->parser->getStream()->expect(Twig_Token::NAME_TYPE)->getValue(), $token->getLine());
$this->parser->getStream()->expect(Twig_Token::BLOCK_END_TYPE);
$this->parser->addImportedSymbol('template', $var->getAttribute('name'));
return new Twig_Node_Import($macro, $var, $token->getLine(), $this->getTag());
}
public function getTag()
{
return 'import';
}
}
class_alias('Twig_TokenParser_Import', 'Twig\TokenParser\ImportTokenParser', false);

View File

@ -1,60 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Defines a macro.
*
* <pre>
* {% macro input(name, value, type, size) %}
* <input type="{{ type|default('text') }}" name="{{ name }}" value="{{ value|e }}" size="{{ size|default(20) }}" />
* {% endmacro %}
* </pre>
*
* @final
*/
class Twig_TokenParser_Macro extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$lineno = $token->getLine();
$stream = $this->parser->getStream();
$name = $stream->expect(Twig_Token::NAME_TYPE)->getValue();
$arguments = $this->parser->getExpressionParser()->parseArguments(true, true);
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$this->parser->pushLocalScope();
$body = $this->parser->subparse(array($this, 'decideBlockEnd'), true);
if ($token = $stream->nextIf(Twig_Token::NAME_TYPE)) {
$value = $token->getValue();
if ($value != $name) {
throw new Twig_Error_Syntax(sprintf('Expected endmacro for macro "%s" (but "%s" given).', $name, $value), $stream->getCurrent()->getLine(), $stream->getSourceContext());
}
}
$this->parser->popLocalScope();
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$this->parser->setMacro($name, new Twig_Node_Macro($name, new Twig_Node_Body(array($body)), $arguments, $lineno, $this->getTag()));
}
public function decideBlockEnd(Twig_Token $token)
{
return $token->test('endmacro');
}
public function getTag()
{
return 'macro';
}
}
class_alias('Twig_TokenParser_Macro', 'Twig\TokenParser\MacroTokenParser', false);

View File

@ -1,61 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Marks a section of a template as untrusted code that must be evaluated in the sandbox mode.
*
* <pre>
* {% sandbox %}
* {% include 'user.html' %}
* {% endsandbox %}
* </pre>
*
* @see https://twig.symfony.com/doc/api.html#sandbox-extension for details
*
* @final
*/
class Twig_TokenParser_Sandbox extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$stream = $this->parser->getStream();
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$body = $this->parser->subparse(array($this, 'decideBlockEnd'), true);
$stream->expect(Twig_Token::BLOCK_END_TYPE);
// in a sandbox tag, only include tags are allowed
if (!$body instanceof Twig_Node_Include) {
foreach ($body as $node) {
if ($node instanceof Twig_Node_Text && ctype_space($node->getAttribute('data'))) {
continue;
}
if (!$node instanceof Twig_Node_Include) {
throw new Twig_Error_Syntax('Only "include" tags are allowed within a "sandbox" section.', $node->getTemplateLine(), $stream->getSourceContext());
}
}
}
return new Twig_Node_Sandbox($body, $token->getLine(), $this->getTag());
}
public function decideBlockEnd(Twig_Token $token)
{
return $token->test('endsandbox');
}
public function getTag()
{
return 'sandbox';
}
}
class_alias('Twig_TokenParser_Sandbox', 'Twig\TokenParser\SandboxTokenParser', false);

View File

@ -1,75 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Defines a variable.
*
* <pre>
* {% set foo = 'foo' %}
*
* {% set foo = [1, 2] %}
*
* {% set foo = {'foo': 'bar'} %}
*
* {% set foo = 'foo' ~ 'bar' %}
*
* {% set foo, bar = 'foo', 'bar' %}
*
* {% set foo %}Some content{% endset %}
* </pre>
*
* @final
*/
class Twig_TokenParser_Set extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$lineno = $token->getLine();
$stream = $this->parser->getStream();
$names = $this->parser->getExpressionParser()->parseAssignmentExpression();
$capture = false;
if ($stream->nextIf(Twig_Token::OPERATOR_TYPE, '=')) {
$values = $this->parser->getExpressionParser()->parseMultitargetExpression();
$stream->expect(Twig_Token::BLOCK_END_TYPE);
if (count($names) !== count($values)) {
throw new Twig_Error_Syntax('When using set, you must have the same number of variables and assignments.', $stream->getCurrent()->getLine(), $stream->getSourceContext());
}
} else {
$capture = true;
if (count($names) > 1) {
throw new Twig_Error_Syntax('When using set with a block, you cannot have a multi-target.', $stream->getCurrent()->getLine(), $stream->getSourceContext());
}
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$values = $this->parser->subparse(array($this, 'decideBlockEnd'), true);
$stream->expect(Twig_Token::BLOCK_END_TYPE);
}
return new Twig_Node_Set($capture, $names, $values, $lineno, $this->getTag());
}
public function decideBlockEnd(Twig_Token $token)
{
return $token->test('endset');
}
public function getTag()
{
return 'set';
}
}
class_alias('Twig_TokenParser_Set', 'Twig\TokenParser\SetTokenParser', false);

View File

@ -1,51 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Remove whitespaces between HTML tags.
*
* <pre>
* {% spaceless %}
* <div>
* <strong>foo</strong>
* </div>
* {% endspaceless %}
*
* {# output will be <div><strong>foo</strong></div> #}
* </pre>
*
* @final
*/
class Twig_TokenParser_Spaceless extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$lineno = $token->getLine();
$this->parser->getStream()->expect(Twig_Token::BLOCK_END_TYPE);
$body = $this->parser->subparse(array($this, 'decideSpacelessEnd'), true);
$this->parser->getStream()->expect(Twig_Token::BLOCK_END_TYPE);
return new Twig_Node_Spaceless($body, $lineno, $this->getTag());
}
public function decideSpacelessEnd(Twig_Token $token)
{
return $token->test('endspaceless');
}
public function getTag()
{
return 'spaceless';
}
}
class_alias('Twig_TokenParser_Spaceless', 'Twig\TokenParser\SpacelessTokenParser', false);

View File

@ -1,70 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Imports blocks defined in another template into the current template.
*
* <pre>
* {% extends "base.html" %}
*
* {% use "blocks.html" %}
*
* {% block title %}{% endblock %}
* {% block content %}{% endblock %}
* </pre>
*
* @see https://twig.symfony.com/doc/templates.html#horizontal-reuse for details.
*
* @final
*/
class Twig_TokenParser_Use extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$template = $this->parser->getExpressionParser()->parseExpression();
$stream = $this->parser->getStream();
if (!$template instanceof Twig_Node_Expression_Constant) {
throw new Twig_Error_Syntax('The template references in a "use" statement must be a string.', $stream->getCurrent()->getLine(), $stream->getSourceContext());
}
$targets = array();
if ($stream->nextIf('with')) {
do {
$name = $stream->expect(Twig_Token::NAME_TYPE)->getValue();
$alias = $name;
if ($stream->nextIf('as')) {
$alias = $stream->expect(Twig_Token::NAME_TYPE)->getValue();
}
$targets[$name] = new Twig_Node_Expression_Constant($alias, -1);
if (!$stream->nextIf(Twig_Token::PUNCTUATION_TYPE, ',')) {
break;
}
} while (true);
}
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$this->parser->addTrait(new Twig_Node(array('template' => $template, 'targets' => new Twig_Node($targets))));
return new Twig_Node();
}
public function getTag()
{
return 'use';
}
}
class_alias('Twig_TokenParser_Use', 'Twig\TokenParser\UseTokenParser', false);

View File

@ -1,52 +0,0 @@
<?php
/*
* This file is part of Twig.
*
* (c) Fabien Potencier
*
* For the full copyright and license information, please view the LICENSE
* file that was distributed with this source code.
*/
/**
* Creates a nested scope.
*
* @author Fabien Potencier <fabien@symfony.com>
*
* @final
*/
class Twig_TokenParser_With extends Twig_TokenParser
{
public function parse(Twig_Token $token)
{
$stream = $this->parser->getStream();
$variables = null;
$only = false;
if (!$stream->test(Twig_Token::BLOCK_END_TYPE)) {
$variables = $this->parser->getExpressionParser()->parseExpression();
$only = $stream->nextIf(Twig_Token::NAME_TYPE, 'only');
}
$stream->expect(Twig_Token::BLOCK_END_TYPE);
$body = $this->parser->subparse(array($this, 'decideWithEnd'), true);
$stream->expect(Twig_Token::BLOCK_END_TYPE);
return new Twig_Node_With($body, $variables, $only, $token->getLine(), $this->getTag());
}
public function decideWithEnd(Twig_Token $token)
{
return $token->test('endwith');
}
public function getTag()
{
return 'with';
}
}
class_alias('Twig_TokenParser_With', 'Twig\TokenParser\WithTokenParser', false);

View File

@ -1,33 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<phpunit backupGlobals="false"
backupStaticAttributes="false"
colors="true"
convertErrorsToExceptions="true"
convertNoticesToExceptions="true"
convertWarningsToExceptions="true"
processIsolation="false"
stopOnFailure="false"
syntaxCheck="false"
bootstrap="vendor/autoload.php"
>
<testsuites>
<testsuite name="Twig Test Suite">
<directory>./test/Twig/</directory>
</testsuite>
</testsuites>
<php>
<ini name="error_reporting" value="-1" />
</php>
<listeners>
<listener class="Symfony\Bridge\PhpUnit\SymfonyTestsListener" />
</listeners>
<filter>
<whitelist>
<directory suffix=".php">./lib/Twig/</directory>
</whitelist>
</filter>
</phpunit>

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Cache;
class_exists('Twig_CacheInterface');
if (\false) {
interface CacheInterface extends \Twig_CacheInterface
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Cache;
class_exists('Twig_Cache_Filesystem');
if (\false) {
class FilesystemCache extends \Twig_Cache_Filesystem
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Cache;
class_exists('Twig_Cache_Null');
if (\false) {
class NullCache extends \Twig_Cache_Null
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig;
class_exists('Twig_Compiler');
if (\false) {
class Compiler extends \Twig_Compiler
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig;
class_exists('Twig_Environment');
if (\false) {
class Environment extends \Twig_Environment
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Error;
class_exists('Twig_Error');
if (\false) {
class Error extends \Twig_Error
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Error;
class_exists('Twig_Error_Loader');
if (\false) {
class LoaderError extends \Twig_Error_Loader
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Error;
class_exists('Twig_Error_Runtime');
if (\false) {
class RuntimeError extends \Twig_Error_Runtime
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Error;
class_exists('Twig_Error_Syntax');
if (\false) {
class SyntaxError extends \Twig_Error_Syntax
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig;
class_exists('Twig_ExpressionParser');
if (\false) {
class ExpressionParser extends \Twig_ExpressionParser
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Extension;
class_exists('Twig_Extension');
if (\false) {
class AbstractExtension extends \Twig_Extension
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Extension;
class_exists('Twig_Extension_Core');
if (\false) {
class CoreExtension extends \Twig_Extension_Core
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Extension;
class_exists('Twig_Extension_Debug');
if (\false) {
class DebugExtension extends \Twig_Extension_Debug
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Extension;
class_exists('Twig_Extension_Escaper');
if (\false) {
class EscaperExtension extends \Twig_Extension_Escaper
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Extension;
class_exists('Twig_ExtensionInterface');
if (\false) {
interface ExtensionInterface extends \Twig_ExtensionInterface
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Extension;
class_exists('Twig_Extension_GlobalsInterface');
if (\false) {
interface GlobalsInterface extends \Twig_Extension_ExtensionInterface
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Extension;
class_exists('Twig_Extension_InitRuntimeInterface');
if (\false) {
interface InitRuntimeInterface extends \Twig_Extension_InitRuntimeInterface
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Extension;
class_exists('Twig_Extension_Optimizer');
if (\false) {
class OptimizerExtension extends \Twig_Extension_Optimizer
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Extension;
class_exists('Twig_Extension_Profiler');
if (\false) {
class ProfilerExtension extends \Twig_Extension_Profiler
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Extension;
class_exists('Twig_Extension_Sandbox');
if (\false) {
class SandboxExtension extends \Twig_Extension_Sandbox
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Extension;
class_exists('Twig_Extension_Staging');
if (\false) {
class StagingExtension extends \Twig_Extension_Staging
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Extension;
class_exists('Twig_Extension_StringLoader');
if (\false) {
class StringLoaderExtension extends \Twig_Extension_StringLoader
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig;
class_exists('Twig_FileExtensionEscapingStrategy');
if (\false) {
class FileExtensionEscapingStrategy extends \Twig_FileExtensionEscapingStrategy
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig;
class_exists('Twig_Lexer');
if (\false) {
class Lexer extends \Twig_Lexer
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Loader;
class_exists('Twig_Loader_Array');
if (\false) {
class ArrayLoader extends \Twig_Loader_Array
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Loader;
class_exists('Twig_Loader_Chain');
if (\false) {
class ChainLoader extends \Twig_Loader_Chain
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Loader;
class_exists('Twig_ExistsLoaderInterface');
if (\false) {
interface ExistsLoaderInterface extends \Twig_ExistsLoaderInterface
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Loader;
class_exists('Twig_Loader_Filesystem');
if (\false) {
class FilesystemLoader extends \Twig_Loader_Filesystem
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Loader;
class_exists('Twig_LoaderInterface');
if (\false) {
interface LoaderInterface extends \Twig_LoaderInterface
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Loader;
class_exists('Twig_SourceContextLoaderInterface');
if (\false) {
interface SourceContextLoaderInterface extends \Twig_SourceContextLoaderInterface
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig;
class_exists('Twig_Markup');
if (\false) {
class Markup extends \Twig_Markup
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Node;
class_exists('Twig_Node_AutoEscape');
if (\false) {
class AutoEscapeNode extends \Twig_Node_AutoEscape
{
}
}

View File

@ -1,11 +0,0 @@
<?php
namespace Twig\Node;
class_exists('Twig_Node_Block');
if (\false) {
class BlockNode extends \Twig_Node_Block
{
}
}

Some files were not shown because too many files have changed in this diff Show More