From 01857d176a2a9a2e3816b9cbf32da0c58f6aac3d Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Thu, 19 Sep 2013 14:42:54 +1000 Subject: [PATCH 01/26] focus on quick reply textarea --- js/quick-reply.js | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/js/quick-reply.js b/js/quick-reply.js index 91c35222..d60a3a82 100644 --- a/js/quick-reply.js +++ b/js/quick-reply.js @@ -365,13 +365,19 @@ if ($(this).width() <= 800) return; show_quick_reply(); - $('#quick-reply textarea').focus(); if (with_link) { - $(window).ready(function() { + $(document).ready(function() { if ($('#' + id).length) { highlightReply(id); - $(window).scrollTop($('#' + id).offset().top); + $(document).scrollTop($('#' + id).offset().top); } + + // Honestly, I'm not sure why we need setTimeout() here, but it seems to work. + // Same for the "tmp" variable stuff you see inside here: + setTimeout(function() { + var tmp = $('#quick-reply textarea').val(); + $('#quick-reply textarea').val('').focus().val(tmp); + }, 1); }); } }); From 9c48084f3b5064d580a5c88a6fe9170599cf8879 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Thu, 19 Sep 2013 16:08:25 +1000 Subject: [PATCH 02/26] upgrade twig library --- inc/lib/Twig/Autoloader.php | 0 inc/lib/Twig/Compiler.php | 5 +- inc/lib/Twig/CompilerInterface.php | 0 inc/lib/Twig/Environment.php | 14 +++- inc/lib/Twig/Error.php | 6 +- inc/lib/Twig/Error/Loader.php | 0 inc/lib/Twig/Error/Runtime.php | 0 inc/lib/Twig/Error/Syntax.php | 0 inc/lib/Twig/ExistsLoaderInterface.php | 0 inc/lib/Twig/ExpressionParser.php | 83 +++++++++++-------- inc/lib/Twig/Extension.php | 0 inc/lib/Twig/Extension/Core.php | 22 ++--- inc/lib/Twig/Extension/Debug.php | 0 inc/lib/Twig/Extension/Escaper.php | 0 inc/lib/Twig/Extension/Optimizer.php | 0 inc/lib/Twig/Extension/Sandbox.php | 0 inc/lib/Twig/Extension/Staging.php | 0 inc/lib/Twig/Extension/StringLoader.php | 12 +-- inc/lib/Twig/ExtensionInterface.php | 0 inc/lib/Twig/Filter.php | 0 inc/lib/Twig/Filter/Function.php | 0 inc/lib/Twig/Filter/Method.php | 0 inc/lib/Twig/Filter/Node.php | 0 inc/lib/Twig/FilterCallableInterface.php | 0 inc/lib/Twig/FilterInterface.php | 0 inc/lib/Twig/Function.php | 0 inc/lib/Twig/Function/Function.php | 0 inc/lib/Twig/Function/Method.php | 0 inc/lib/Twig/Function/Node.php | 0 inc/lib/Twig/FunctionCallableInterface.php | 0 inc/lib/Twig/FunctionInterface.php | 0 inc/lib/Twig/Lexer.php | 0 inc/lib/Twig/LexerInterface.php | 0 inc/lib/Twig/Loader/Array.php | 7 +- inc/lib/Twig/Loader/Chain.php | 3 +- inc/lib/Twig/Loader/Filesystem.php | 27 +++--- inc/lib/Twig/Loader/String.php | 0 inc/lib/Twig/LoaderInterface.php | 0 inc/lib/Twig/Markup.php | 0 inc/lib/Twig/Node.php | 0 inc/lib/Twig/Node/AutoEscape.php | 0 inc/lib/Twig/Node/Block.php | 0 inc/lib/Twig/Node/BlockReference.php | 0 inc/lib/Twig/Node/Body.php | 0 inc/lib/Twig/Node/Do.php | 0 inc/lib/Twig/Node/Embed.php | 0 inc/lib/Twig/Node/Expression.php | 0 inc/lib/Twig/Node/Expression/Array.php | 0 inc/lib/Twig/Node/Expression/AssignName.php | 0 inc/lib/Twig/Node/Expression/Binary.php | 0 inc/lib/Twig/Node/Expression/Binary/Add.php | 0 inc/lib/Twig/Node/Expression/Binary/And.php | 0 .../Node/Expression/Binary/BitwiseAnd.php | 0 .../Twig/Node/Expression/Binary/BitwiseOr.php | 0 .../Node/Expression/Binary/BitwiseXor.php | 0 .../Twig/Node/Expression/Binary/Concat.php | 0 inc/lib/Twig/Node/Expression/Binary/Div.php | 0 inc/lib/Twig/Node/Expression/Binary/Equal.php | 0 .../Twig/Node/Expression/Binary/FloorDiv.php | 0 .../Twig/Node/Expression/Binary/Greater.php | 0 .../Node/Expression/Binary/GreaterEqual.php | 0 inc/lib/Twig/Node/Expression/Binary/In.php | 0 inc/lib/Twig/Node/Expression/Binary/Less.php | 0 .../Twig/Node/Expression/Binary/LessEqual.php | 0 inc/lib/Twig/Node/Expression/Binary/Mod.php | 0 inc/lib/Twig/Node/Expression/Binary/Mul.php | 0 .../Twig/Node/Expression/Binary/NotEqual.php | 0 inc/lib/Twig/Node/Expression/Binary/NotIn.php | 0 inc/lib/Twig/Node/Expression/Binary/Or.php | 0 inc/lib/Twig/Node/Expression/Binary/Power.php | 0 inc/lib/Twig/Node/Expression/Binary/Range.php | 0 inc/lib/Twig/Node/Expression/Binary/Sub.php | 0 .../Twig/Node/Expression/BlockReference.php | 0 inc/lib/Twig/Node/Expression/Call.php | 6 +- inc/lib/Twig/Node/Expression/Conditional.php | 0 inc/lib/Twig/Node/Expression/Constant.php | 0 .../Node/Expression/ExtensionReference.php | 0 inc/lib/Twig/Node/Expression/Filter.php | 0 .../Twig/Node/Expression/Filter/Default.php | 0 inc/lib/Twig/Node/Expression/Function.php | 0 inc/lib/Twig/Node/Expression/GetAttr.php | 4 +- inc/lib/Twig/Node/Expression/MacroCall.php | 60 ++++++++++++++ inc/lib/Twig/Node/Expression/MethodCall.php | 0 inc/lib/Twig/Node/Expression/Name.php | 0 inc/lib/Twig/Node/Expression/Parent.php | 0 inc/lib/Twig/Node/Expression/TempName.php | 0 inc/lib/Twig/Node/Expression/Test.php | 0 .../Twig/Node/Expression/Test/Constant.php | 0 inc/lib/Twig/Node/Expression/Test/Defined.php | 0 .../Twig/Node/Expression/Test/Divisibleby.php | 0 inc/lib/Twig/Node/Expression/Test/Even.php | 0 inc/lib/Twig/Node/Expression/Test/Null.php | 0 inc/lib/Twig/Node/Expression/Test/Odd.php | 0 inc/lib/Twig/Node/Expression/Test/Sameas.php | 0 inc/lib/Twig/Node/Expression/Unary.php | 0 inc/lib/Twig/Node/Expression/Unary/Neg.php | 0 inc/lib/Twig/Node/Expression/Unary/Not.php | 0 inc/lib/Twig/Node/Expression/Unary/Pos.php | 0 inc/lib/Twig/Node/Flush.php | 0 inc/lib/Twig/Node/For.php | 0 inc/lib/Twig/Node/ForLoop.php | 0 inc/lib/Twig/Node/If.php | 0 inc/lib/Twig/Node/Import.php | 0 inc/lib/Twig/Node/Include.php | 0 inc/lib/Twig/Node/Macro.php | 4 +- inc/lib/Twig/Node/Module.php | 36 +++++++- inc/lib/Twig/Node/Print.php | 0 inc/lib/Twig/Node/Sandbox.php | 0 inc/lib/Twig/Node/SandboxedModule.php | 0 inc/lib/Twig/Node/SandboxedPrint.php | 0 inc/lib/Twig/Node/Set.php | 0 inc/lib/Twig/Node/SetTemp.php | 0 inc/lib/Twig/Node/Spaceless.php | 0 inc/lib/Twig/Node/Text.php | 0 inc/lib/Twig/NodeInterface.php | 0 inc/lib/Twig/NodeOutputInterface.php | 0 inc/lib/Twig/NodeTraverser.php | 0 inc/lib/Twig/NodeVisitor/Escaper.php | 0 inc/lib/Twig/NodeVisitor/Optimizer.php | 0 inc/lib/Twig/NodeVisitor/SafeAnalysis.php | 2 + inc/lib/Twig/NodeVisitor/Sandbox.php | 0 inc/lib/Twig/NodeVisitorInterface.php | 0 inc/lib/Twig/Parser.php | 2 +- inc/lib/Twig/ParserInterface.php | 0 inc/lib/Twig/Sandbox/SecurityError.php | 0 inc/lib/Twig/Sandbox/SecurityPolicy.php | 0 .../Twig/Sandbox/SecurityPolicyInterface.php | 0 inc/lib/Twig/SimpleFilter.php | 0 inc/lib/Twig/SimpleFunction.php | 0 inc/lib/Twig/SimpleTest.php | 0 inc/lib/Twig/Template.php | 74 +++++++++++++++-- inc/lib/Twig/TemplateInterface.php | 0 inc/lib/Twig/Test.php | 0 inc/lib/Twig/Test/Function.php | 0 inc/lib/Twig/Test/IntegrationTestCase.php | 0 inc/lib/Twig/Test/Method.php | 0 inc/lib/Twig/Test/Node.php | 0 inc/lib/Twig/Test/NodeTestCase.php | 0 inc/lib/Twig/TestCallableInterface.php | 0 inc/lib/Twig/TestInterface.php | 0 inc/lib/Twig/Token.php | 0 inc/lib/Twig/TokenParser.php | 0 inc/lib/Twig/TokenParser/AutoEscape.php | 0 inc/lib/Twig/TokenParser/Block.php | 0 inc/lib/Twig/TokenParser/Do.php | 0 inc/lib/Twig/TokenParser/Embed.php | 0 inc/lib/Twig/TokenParser/Extends.php | 0 inc/lib/Twig/TokenParser/Filter.php | 0 inc/lib/Twig/TokenParser/Flush.php | 0 inc/lib/Twig/TokenParser/For.php | 0 inc/lib/Twig/TokenParser/From.php | 2 +- inc/lib/Twig/TokenParser/If.php | 0 inc/lib/Twig/TokenParser/Import.php | 0 inc/lib/Twig/TokenParser/Include.php | 0 inc/lib/Twig/TokenParser/Macro.php | 0 inc/lib/Twig/TokenParser/Sandbox.php | 0 inc/lib/Twig/TokenParser/Set.php | 0 inc/lib/Twig/TokenParser/Spaceless.php | 0 inc/lib/Twig/TokenParser/Use.php | 0 inc/lib/Twig/TokenParserBroker.php | 0 inc/lib/Twig/TokenParserBrokerInterface.php | 0 inc/lib/Twig/TokenParserInterface.php | 0 inc/lib/Twig/TokenStream.php | 0 163 files changed, 275 insertions(+), 94 deletions(-) mode change 100644 => 100755 inc/lib/Twig/Autoloader.php mode change 100644 => 100755 inc/lib/Twig/Compiler.php mode change 100644 => 100755 inc/lib/Twig/CompilerInterface.php mode change 100644 => 100755 inc/lib/Twig/Environment.php mode change 100644 => 100755 inc/lib/Twig/Error.php mode change 100644 => 100755 inc/lib/Twig/Error/Loader.php mode change 100644 => 100755 inc/lib/Twig/Error/Runtime.php mode change 100644 => 100755 inc/lib/Twig/Error/Syntax.php mode change 100644 => 100755 inc/lib/Twig/ExistsLoaderInterface.php mode change 100644 => 100755 inc/lib/Twig/ExpressionParser.php mode change 100644 => 100755 inc/lib/Twig/Extension.php mode change 100644 => 100755 inc/lib/Twig/Extension/Core.php mode change 100644 => 100755 inc/lib/Twig/Extension/Debug.php mode change 100644 => 100755 inc/lib/Twig/Extension/Escaper.php mode change 100644 => 100755 inc/lib/Twig/Extension/Optimizer.php mode change 100644 => 100755 inc/lib/Twig/Extension/Sandbox.php mode change 100644 => 100755 inc/lib/Twig/Extension/Staging.php mode change 100644 => 100755 inc/lib/Twig/Extension/StringLoader.php mode change 100644 => 100755 inc/lib/Twig/ExtensionInterface.php mode change 100644 => 100755 inc/lib/Twig/Filter.php mode change 100644 => 100755 inc/lib/Twig/Filter/Function.php mode change 100644 => 100755 inc/lib/Twig/Filter/Method.php mode change 100644 => 100755 inc/lib/Twig/Filter/Node.php mode change 100644 => 100755 inc/lib/Twig/FilterCallableInterface.php mode change 100644 => 100755 inc/lib/Twig/FilterInterface.php mode change 100644 => 100755 inc/lib/Twig/Function.php mode change 100644 => 100755 inc/lib/Twig/Function/Function.php mode change 100644 => 100755 inc/lib/Twig/Function/Method.php mode change 100644 => 100755 inc/lib/Twig/Function/Node.php mode change 100644 => 100755 inc/lib/Twig/FunctionCallableInterface.php mode change 100644 => 100755 inc/lib/Twig/FunctionInterface.php mode change 100644 => 100755 inc/lib/Twig/Lexer.php mode change 100644 => 100755 inc/lib/Twig/LexerInterface.php mode change 100644 => 100755 inc/lib/Twig/Loader/Array.php mode change 100644 => 100755 inc/lib/Twig/Loader/Chain.php mode change 100644 => 100755 inc/lib/Twig/Loader/Filesystem.php mode change 100644 => 100755 inc/lib/Twig/Loader/String.php mode change 100644 => 100755 inc/lib/Twig/LoaderInterface.php mode change 100644 => 100755 inc/lib/Twig/Markup.php mode change 100644 => 100755 inc/lib/Twig/Node.php mode change 100644 => 100755 inc/lib/Twig/Node/AutoEscape.php mode change 100644 => 100755 inc/lib/Twig/Node/Block.php mode change 100644 => 100755 inc/lib/Twig/Node/BlockReference.php mode change 100644 => 100755 inc/lib/Twig/Node/Body.php mode change 100644 => 100755 inc/lib/Twig/Node/Do.php mode change 100644 => 100755 inc/lib/Twig/Node/Embed.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Array.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/AssignName.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/Add.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/And.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/BitwiseAnd.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/BitwiseOr.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/BitwiseXor.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/Concat.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/Div.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/Equal.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/FloorDiv.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/Greater.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/GreaterEqual.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/In.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/Less.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/LessEqual.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/Mod.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/Mul.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/NotEqual.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/NotIn.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/Or.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/Power.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/Range.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Binary/Sub.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/BlockReference.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Call.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Conditional.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Constant.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/ExtensionReference.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Filter.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Filter/Default.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Function.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/GetAttr.php create mode 100755 inc/lib/Twig/Node/Expression/MacroCall.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/MethodCall.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Name.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Parent.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/TempName.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Test.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Test/Constant.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Test/Defined.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Test/Divisibleby.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Test/Even.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Test/Null.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Test/Odd.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Test/Sameas.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Unary.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Unary/Neg.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Unary/Not.php mode change 100644 => 100755 inc/lib/Twig/Node/Expression/Unary/Pos.php mode change 100644 => 100755 inc/lib/Twig/Node/Flush.php mode change 100644 => 100755 inc/lib/Twig/Node/For.php mode change 100644 => 100755 inc/lib/Twig/Node/ForLoop.php mode change 100644 => 100755 inc/lib/Twig/Node/If.php mode change 100644 => 100755 inc/lib/Twig/Node/Import.php mode change 100644 => 100755 inc/lib/Twig/Node/Include.php mode change 100644 => 100755 inc/lib/Twig/Node/Macro.php mode change 100644 => 100755 inc/lib/Twig/Node/Module.php mode change 100644 => 100755 inc/lib/Twig/Node/Print.php mode change 100644 => 100755 inc/lib/Twig/Node/Sandbox.php mode change 100644 => 100755 inc/lib/Twig/Node/SandboxedModule.php mode change 100644 => 100755 inc/lib/Twig/Node/SandboxedPrint.php mode change 100644 => 100755 inc/lib/Twig/Node/Set.php mode change 100644 => 100755 inc/lib/Twig/Node/SetTemp.php mode change 100644 => 100755 inc/lib/Twig/Node/Spaceless.php mode change 100644 => 100755 inc/lib/Twig/Node/Text.php mode change 100644 => 100755 inc/lib/Twig/NodeInterface.php mode change 100644 => 100755 inc/lib/Twig/NodeOutputInterface.php mode change 100644 => 100755 inc/lib/Twig/NodeTraverser.php mode change 100644 => 100755 inc/lib/Twig/NodeVisitor/Escaper.php mode change 100644 => 100755 inc/lib/Twig/NodeVisitor/Optimizer.php mode change 100644 => 100755 inc/lib/Twig/NodeVisitor/SafeAnalysis.php mode change 100644 => 100755 inc/lib/Twig/NodeVisitor/Sandbox.php mode change 100644 => 100755 inc/lib/Twig/NodeVisitorInterface.php mode change 100644 => 100755 inc/lib/Twig/Parser.php mode change 100644 => 100755 inc/lib/Twig/ParserInterface.php mode change 100644 => 100755 inc/lib/Twig/Sandbox/SecurityError.php mode change 100644 => 100755 inc/lib/Twig/Sandbox/SecurityPolicy.php mode change 100644 => 100755 inc/lib/Twig/Sandbox/SecurityPolicyInterface.php mode change 100644 => 100755 inc/lib/Twig/SimpleFilter.php mode change 100644 => 100755 inc/lib/Twig/SimpleFunction.php mode change 100644 => 100755 inc/lib/Twig/SimpleTest.php mode change 100644 => 100755 inc/lib/Twig/Template.php mode change 100644 => 100755 inc/lib/Twig/TemplateInterface.php mode change 100644 => 100755 inc/lib/Twig/Test.php mode change 100644 => 100755 inc/lib/Twig/Test/Function.php mode change 100644 => 100755 inc/lib/Twig/Test/IntegrationTestCase.php mode change 100644 => 100755 inc/lib/Twig/Test/Method.php mode change 100644 => 100755 inc/lib/Twig/Test/Node.php mode change 100644 => 100755 inc/lib/Twig/Test/NodeTestCase.php mode change 100644 => 100755 inc/lib/Twig/TestCallableInterface.php mode change 100644 => 100755 inc/lib/Twig/TestInterface.php mode change 100644 => 100755 inc/lib/Twig/Token.php mode change 100644 => 100755 inc/lib/Twig/TokenParser.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/AutoEscape.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/Block.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/Do.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/Embed.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/Extends.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/Filter.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/Flush.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/For.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/From.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/If.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/Import.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/Include.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/Macro.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/Sandbox.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/Set.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/Spaceless.php mode change 100644 => 100755 inc/lib/Twig/TokenParser/Use.php mode change 100644 => 100755 inc/lib/Twig/TokenParserBroker.php mode change 100644 => 100755 inc/lib/Twig/TokenParserBrokerInterface.php mode change 100644 => 100755 inc/lib/Twig/TokenParserInterface.php mode change 100644 => 100755 inc/lib/Twig/TokenStream.php diff --git a/inc/lib/Twig/Autoloader.php b/inc/lib/Twig/Autoloader.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Compiler.php b/inc/lib/Twig/Compiler.php old mode 100644 new mode 100755 index 99aecbcc..b80210b1 --- a/inc/lib/Twig/Compiler.php +++ b/inc/lib/Twig/Compiler.php @@ -180,11 +180,12 @@ class Twig_Compiler implements Twig_CompilerInterface $this->raw($value ? 'true' : 'false'); } elseif (is_array($value)) { $this->raw('array('); - $i = 0; + $first = true; foreach ($value as $key => $value) { - if ($i++) { + if (!$first) { $this->raw(', '); } + $first = false; $this->repr($key); $this->raw(' => '); $this->repr($value); diff --git a/inc/lib/Twig/CompilerInterface.php b/inc/lib/Twig/CompilerInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Environment.php b/inc/lib/Twig/Environment.php old mode 100644 new mode 100755 index 3afa73d6..09ea4a25 --- a/inc/lib/Twig/Environment.php +++ b/inc/lib/Twig/Environment.php @@ -16,7 +16,7 @@ */ class Twig_Environment { - const VERSION = '1.13.1'; + const VERSION = '1.14.0-DEV'; protected $charset; protected $loader; @@ -44,6 +44,7 @@ class Twig_Environment protected $functionCallbacks; protected $filterCallbacks; protected $staging; + protected $templateClasses; /** * Constructor. @@ -107,6 +108,7 @@ class Twig_Environment $this->setCache($options['cache']); $this->functionCallbacks = array(); $this->filterCallbacks = array(); + $this->templateClasses = array(); $this->addExtension(new Twig_Extension_Core()); $this->addExtension(new Twig_Extension_Escaper($options['autoescape'])); @@ -262,7 +264,13 @@ class Twig_Environment */ public function getTemplateClass($name, $index = null) { - return $this->templateClassPrefix.md5($this->getLoader()->getCacheKey($name)).(null === $index ? '' : '_'.$index); + $suffix = null === $index ? '' : '_'.$index; + $cls = $name.$suffix; + if (isset($this->templateClasses[$cls])) { + return $this->templateClasses[$cls]; + } + + return $this->templateClasses[$cls] = $this->templateClassPrefix.hash('sha256', $this->getLoader()->getCacheKey($name)).$suffix; } /** @@ -728,7 +736,7 @@ class Twig_Environment public function addNodeVisitor(Twig_NodeVisitorInterface $visitor) { if ($this->extensionInitialized) { - throw new LogicException('Unable to add a node visitor as extensions have already been initialized.', $extension->getName()); + throw new LogicException('Unable to add a node visitor as extensions have already been initialized.'); } $this->staging->addNodeVisitor($visitor); diff --git a/inc/lib/Twig/Error.php b/inc/lib/Twig/Error.php old mode 100644 new mode 100755 index 72d91a98..61a4cfa0 --- a/inc/lib/Twig/Error.php +++ b/inc/lib/Twig/Error.php @@ -186,6 +186,7 @@ class Twig_Error extends Exception protected function guessTemplateInfo() { $template = null; + $templateClass = null; if (version_compare(phpversion(), '5.3.6', '>=')) { $backtrace = debug_backtrace(DEBUG_BACKTRACE_IGNORE_ARGS | DEBUG_BACKTRACE_PROVIDE_OBJECT); @@ -195,8 +196,11 @@ class Twig_Error extends Exception foreach ($backtrace as $trace) { if (isset($trace['object']) && $trace['object'] instanceof Twig_Template && 'Twig_Template' !== get_class($trace['object'])) { - if (null === $this->filename || $this->filename == $trace['object']->getTemplateName()) { + $currentClass = get_class($trace['object']); + $isEmbedContainer = 0 === strpos($templateClass, $currentClass); + if (null === $this->filename || ($this->filename == $trace['object']->getTemplateName() && !$isEmbedContainer)) { $template = $trace['object']; + $templateClass = get_class($trace['object']); } } } diff --git a/inc/lib/Twig/Error/Loader.php b/inc/lib/Twig/Error/Loader.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Error/Runtime.php b/inc/lib/Twig/Error/Runtime.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Error/Syntax.php b/inc/lib/Twig/Error/Syntax.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/ExistsLoaderInterface.php b/inc/lib/Twig/ExistsLoaderInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/ExpressionParser.php b/inc/lib/Twig/ExpressionParser.php old mode 100644 new mode 100755 index 9cf19344..9deab09c --- a/inc/lib/Twig/ExpressionParser.php +++ b/inc/lib/Twig/ExpressionParser.php @@ -316,22 +316,22 @@ class Twig_ExpressionParser throw new Twig_Error_Syntax('The "attribute" function takes at least two arguments (the variable and the attributes)', $line, $this->parser->getFilename()); } - return new Twig_Node_Expression_GetAttr($args->getNode(0), $args->getNode(1), count($args) > 2 ? $args->getNode(2) : new Twig_Node_Expression_Array(array(), $line), Twig_TemplateInterface::ANY_CALL, $line); + return new Twig_Node_Expression_GetAttr($args->getNode(0), $args->getNode(1), count($args) > 2 ? $args->getNode(2) : new Twig_Node_Expression_Array(array(), $line), 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); + if (null !== $alias = $this->parser->getImportedSymbol('macro', $name)) { + return new Twig_Node_Expression_MacroCall($alias['node'], $alias['name'], $this->createArrayFromArguments($args), $line); } - $args = $this->parseArguments(true); - $class = $this->getFunctionNodeClass($name, $line); + try { + $class = $this->getFunctionNodeClass($name, $line); + } catch (Twig_Error_Syntax $e) { + if (!$this->parser->hasMacro($name)) { + throw $e; + } + + return new Twig_Node_Expression_MacroCall(new Twig_Node_Expression_Name('_self', $line), $name, $this->createArrayFromArguments($args), $line); + } return new $class($name, $args, $line); } @@ -343,7 +343,7 @@ class Twig_ExpressionParser $token = $stream->next(); $lineno = $token->getLine(); $arguments = new Twig_Node_Expression_Array(array(), $lineno); - $type = Twig_TemplateInterface::ANY_CALL; + $type = Twig_Template::ANY_CALL; if ($token->getValue() == '.') { $token = $stream->next(); if ( @@ -354,13 +354,6 @@ class Twig_ExpressionParser ($token->getType() == Twig_Token::OPERATOR_TYPE && 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_TemplateInterface::METHOD_CALL; - foreach ($this->parseArguments() as $n) { - $arguments->addElement($n); - } - } } else { throw new Twig_Error_Syntax('Expected name or number', $lineno, $this->parser->getFilename()); } @@ -370,13 +363,17 @@ class Twig_ExpressionParser throw new Twig_Error_Syntax(sprintf('Dynamic macro names are not supported (called on "%s")', $node->getAttribute('name')), $token->getLine(), $this->parser->getFilename()); } - $node = new Twig_Node_Expression_MethodCall($node, 'get'.$arg->getAttribute('value'), $arguments, $lineno); - $node->setAttribute('safe', true); + $arguments = $this->createArrayFromArguments($this->parseArguments(true)); - return $node; + return new Twig_Node_Expression_MacroCall($node, $arg->getAttribute('value'), $arguments, $lineno); + } + + if ($stream->test(Twig_Token::PUNCTUATION_TYPE, '(')) { + $type = Twig_Template::METHOD_CALL; + $arguments = $this->createArrayFromArguments($this->parseArguments()); } } else { - $type = Twig_TemplateInterface::ARRAY_CALL; + $type = Twig_Template::ARRAY_CALL; // slice? $slice = false; @@ -452,6 +449,8 @@ class Twig_ExpressionParser * * @param Boolean $namedArguments Whether to allow named arguments or not * @param Boolean $definition Whether we are parsing arguments for a function definition + * + * @return Twig_Node */ public function parseArguments($namedArguments = false, $definition = false) { @@ -483,25 +482,26 @@ class Twig_ExpressionParser $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(), $this->parser->getFilename()); + throw new Twig_Error_Syntax('A default value for an argument must be a constant (a boolean, a string, a number, or an array).', $token->getLine(), $this->parser->getFilename()); } } 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; + if ($definition && null === $name) { + $name = $value->getAttribute('name'); + $value = new Twig_Node_Expression_Constant(null, $this->parser->getCurrentToken()->getLine()); + } + + if (null === $name) { + $args[] = $value; } else { - if (null === $name) { - $args[] = $value; - } else { - $args[$name] = $value; + if ($definition && isset($args[$name])) { + throw new Twig_Error_Syntax(sprintf('Arguments cannot contain the same argument name more than once ("%s" is defined twice).', $name), $token->getLine(), $this->parser->getFilename()); } + + $args[$name] = $value; } } $stream->expect(Twig_Token::PUNCTUATION_TYPE, ')', 'A list of arguments must be closed by a parenthesis'); @@ -597,4 +597,15 @@ class Twig_ExpressionParser return true; } + + private function createArrayFromArguments(Twig_Node $arguments, $line = null) + { + $line = null === $line ? $arguments->getLine() : $line; + $array = new Twig_Node_Expression_Array(array(), $line); + foreach ($arguments as $key => $value) { + $array->addElement($value, new Twig_Node_Expression_Constant($key, $value->getLine())); + } + + return $array; + } } diff --git a/inc/lib/Twig/Extension.php b/inc/lib/Twig/Extension.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Extension/Core.php b/inc/lib/Twig/Extension/Core.php old mode 100644 new mode 100755 index e68687b4..60fe1936 --- a/inc/lib/Twig/Extension/Core.php +++ b/inc/lib/Twig/Extension/Core.php @@ -348,7 +348,7 @@ function twig_random(Twig_Environment $env, $values = null) return $values < 0 ? mt_rand($values, 0) : mt_rand(0, $values); } - if ($values instanceof Traversable) { + if (is_object($values) && $values instanceof Traversable) { $values = iterator_to_array($values); } elseif (is_string($values)) { if ('' === $values) { @@ -620,7 +620,7 @@ function twig_array_merge($arr1, $arr2) */ function twig_slice(Twig_Environment $env, $item, $start, $length = null, $preserveKeys = false) { - if ($item instanceof Traversable) { + if (is_object($item) && $item instanceof Traversable) { $item = iterator_to_array($item, false); } @@ -687,7 +687,7 @@ function twig_last(Twig_Environment $env, $item) */ function twig_join_filter($value, $glue = '') { - if ($value instanceof Traversable) { + if (is_object($value) && $value instanceof Traversable) { $value = iterator_to_array($value, false); } @@ -829,7 +829,7 @@ function twig_in_filter($value, $compare) } return false !== strpos($compare, (string) $value); - } elseif ($compare instanceof Traversable) { + } elseif (is_object($compare) && $compare instanceof Traversable) { return in_array($value, iterator_to_array($compare, false), is_object($value)); } @@ -1329,13 +1329,13 @@ function twig_constant($constant, $object = null) * * @param array $items An array of items * @param integer $size The size of the batch - * @param string $fill A string to fill missing items + * @param mixed $fill A value used to fill missing items * * @return array */ function twig_array_batch($items, $size, $fill = null) { - if ($items instanceof Traversable) { + if (is_object($items) && $items instanceof Traversable) { $items = iterator_to_array($items, false); } @@ -1345,10 +1345,12 @@ function twig_array_batch($items, $size, $fill = null) if (null !== $fill) { $last = count($result) - 1; - $result[$last] = array_merge( - $result[$last], - array_fill(0, $size - count($result[$last]), $fill) - ); + if ($fillCount = $size - count($result[$last])) { + $result[$last] = array_merge( + $result[$last], + array_fill(0, $fillCount, $fill) + ); + } } return $result; diff --git a/inc/lib/Twig/Extension/Debug.php b/inc/lib/Twig/Extension/Debug.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Extension/Escaper.php b/inc/lib/Twig/Extension/Escaper.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Extension/Optimizer.php b/inc/lib/Twig/Extension/Optimizer.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Extension/Sandbox.php b/inc/lib/Twig/Extension/Sandbox.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Extension/Staging.php b/inc/lib/Twig/Extension/Staging.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Extension/StringLoader.php b/inc/lib/Twig/Extension/StringLoader.php old mode 100644 new mode 100755 index 20f3f994..5e1a60d0 --- a/inc/lib/Twig/Extension/StringLoader.php +++ b/inc/lib/Twig/Extension/StringLoader.php @@ -43,16 +43,16 @@ class Twig_Extension_StringLoader extends Twig_Extension */ function twig_template_from_string(Twig_Environment $env, $template) { - static $loader; + $name = sprintf('__string_template__%s', hash('sha256', uniqid(mt_rand(), true), false)); - if (null === $loader) { - $loader = new Twig_Loader_String(); - } + $loader = new Twig_Loader_Chain(array( + new Twig_Loader_Array(array($name => $template)), + $current = $env->getLoader(), + )); - $current = $env->getLoader(); $env->setLoader($loader); try { - $template = $env->loadTemplate($template); + $template = $env->loadTemplate($name); } catch (Exception $e) { $env->setLoader($current); diff --git a/inc/lib/Twig/ExtensionInterface.php b/inc/lib/Twig/ExtensionInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Filter.php b/inc/lib/Twig/Filter.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Filter/Function.php b/inc/lib/Twig/Filter/Function.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Filter/Method.php b/inc/lib/Twig/Filter/Method.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Filter/Node.php b/inc/lib/Twig/Filter/Node.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/FilterCallableInterface.php b/inc/lib/Twig/FilterCallableInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/FilterInterface.php b/inc/lib/Twig/FilterInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Function.php b/inc/lib/Twig/Function.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Function/Function.php b/inc/lib/Twig/Function/Function.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Function/Method.php b/inc/lib/Twig/Function/Method.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Function/Node.php b/inc/lib/Twig/Function/Node.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/FunctionCallableInterface.php b/inc/lib/Twig/FunctionCallableInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/FunctionInterface.php b/inc/lib/Twig/FunctionInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Lexer.php b/inc/lib/Twig/Lexer.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/LexerInterface.php b/inc/lib/Twig/LexerInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Loader/Array.php b/inc/lib/Twig/Loader/Array.php old mode 100644 new mode 100755 index 89087aea..ac561048 --- a/inc/lib/Twig/Loader/Array.php +++ b/inc/lib/Twig/Loader/Array.php @@ -21,7 +21,7 @@ */ class Twig_Loader_Array implements Twig_LoaderInterface, Twig_ExistsLoaderInterface { - protected $templates; + protected $templates = array(); /** * Constructor. @@ -32,10 +32,7 @@ class Twig_Loader_Array implements Twig_LoaderInterface, Twig_ExistsLoaderInterf */ public function __construct(array $templates) { - $this->templates = array(); - foreach ($templates as $name => $template) { - $this->templates[$name] = $template; - } + $this->templates = $templates; } /** diff --git a/inc/lib/Twig/Loader/Chain.php b/inc/lib/Twig/Loader/Chain.php old mode 100644 new mode 100755 index 1f1cf065..7919eda6 --- a/inc/lib/Twig/Loader/Chain.php +++ b/inc/lib/Twig/Loader/Chain.php @@ -17,7 +17,7 @@ class Twig_Loader_Chain implements Twig_LoaderInterface, Twig_ExistsLoaderInterface { private $hasSourceCache = array(); - protected $loaders; + protected $loaders = array(); /** * Constructor. @@ -26,7 +26,6 @@ class Twig_Loader_Chain implements Twig_LoaderInterface, Twig_ExistsLoaderInterf */ public function __construct(array $loaders = array()) { - $this->loaders = array(); foreach ($loaders as $loader) { $this->addLoader($loader); } diff --git a/inc/lib/Twig/Loader/Filesystem.php b/inc/lib/Twig/Loader/Filesystem.php old mode 100644 new mode 100755 index f9211cbd..23bac47d --- a/inc/lib/Twig/Loader/Filesystem.php +++ b/inc/lib/Twig/Loader/Filesystem.php @@ -16,8 +16,11 @@ */ class Twig_Loader_Filesystem implements Twig_LoaderInterface, Twig_ExistsLoaderInterface { - protected $paths; - protected $cache; + /** Identifier of the main namespace. */ + const MAIN_NAMESPACE = '__main__'; + + protected $paths = array(); + protected $cache = array(); /** * Constructor. @@ -38,7 +41,7 @@ class Twig_Loader_Filesystem implements Twig_LoaderInterface, Twig_ExistsLoaderI * * @return array The array of paths where to look for templates */ - public function getPaths($namespace = '__main__') + public function getPaths($namespace = self::MAIN_NAMESPACE) { return isset($this->paths[$namespace]) ? $this->paths[$namespace] : array(); } @@ -46,7 +49,7 @@ class Twig_Loader_Filesystem implements Twig_LoaderInterface, Twig_ExistsLoaderI /** * Returns the path namespaces. * - * The "__main__" namespace is always defined. + * The main namespace is always defined. * * @return array The array of defined namespaces */ @@ -61,7 +64,7 @@ class Twig_Loader_Filesystem implements Twig_LoaderInterface, Twig_ExistsLoaderI * @param string|array $paths A path or an array of paths where to look for templates * @param string $namespace A path namespace */ - public function setPaths($paths, $namespace = '__main__') + public function setPaths($paths, $namespace = self::MAIN_NAMESPACE) { if (!is_array($paths)) { $paths = array($paths); @@ -81,7 +84,7 @@ class Twig_Loader_Filesystem implements Twig_LoaderInterface, Twig_ExistsLoaderI * * @throws Twig_Error_Loader */ - public function addPath($path, $namespace = '__main__') + public function addPath($path, $namespace = self::MAIN_NAMESPACE) { // invalidate the cache $this->cache = array(); @@ -101,7 +104,7 @@ class Twig_Loader_Filesystem implements Twig_LoaderInterface, Twig_ExistsLoaderI * * @throws Twig_Error_Loader */ - public function prependPath($path, $namespace = '__main__') + public function prependPath($path, $namespace = self::MAIN_NAMESPACE) { // invalidate the cache $this->cache = array(); @@ -175,15 +178,15 @@ class Twig_Loader_Filesystem implements Twig_LoaderInterface, Twig_ExistsLoaderI $this->validateName($name); - $namespace = '__main__'; + $namespace = self::MAIN_NAMESPACE; + $shortname = $name; if (isset($name[0]) && '@' == $name[0]) { if (false === $pos = strpos($name, '/')) { throw new Twig_Error_Loader(sprintf('Malformed namespaced template name "%s" (expecting "@namespace/template_name").', $name)); } $namespace = substr($name, 1, $pos - 1); - - $name = substr($name, $pos + 1); + $shortname = substr($name, $pos + 1); } if (!isset($this->paths[$namespace])) { @@ -191,8 +194,8 @@ class Twig_Loader_Filesystem implements Twig_LoaderInterface, Twig_ExistsLoaderI } foreach ($this->paths[$namespace] as $path) { - if (is_file($path.'/'.$name)) { - return $this->cache[$name] = $path.'/'.$name; + if (is_file($path.'/'.$shortname)) { + return $this->cache[$name] = $path.'/'.$shortname; } } diff --git a/inc/lib/Twig/Loader/String.php b/inc/lib/Twig/Loader/String.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/LoaderInterface.php b/inc/lib/Twig/LoaderInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Markup.php b/inc/lib/Twig/Markup.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node.php b/inc/lib/Twig/Node.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/AutoEscape.php b/inc/lib/Twig/Node/AutoEscape.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Block.php b/inc/lib/Twig/Node/Block.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/BlockReference.php b/inc/lib/Twig/Node/BlockReference.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Body.php b/inc/lib/Twig/Node/Body.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Do.php b/inc/lib/Twig/Node/Do.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Embed.php b/inc/lib/Twig/Node/Embed.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression.php b/inc/lib/Twig/Node/Expression.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Array.php b/inc/lib/Twig/Node/Expression/Array.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/AssignName.php b/inc/lib/Twig/Node/Expression/AssignName.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary.php b/inc/lib/Twig/Node/Expression/Binary.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/Add.php b/inc/lib/Twig/Node/Expression/Binary/Add.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/And.php b/inc/lib/Twig/Node/Expression/Binary/And.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/BitwiseAnd.php b/inc/lib/Twig/Node/Expression/Binary/BitwiseAnd.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/BitwiseOr.php b/inc/lib/Twig/Node/Expression/Binary/BitwiseOr.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/BitwiseXor.php b/inc/lib/Twig/Node/Expression/Binary/BitwiseXor.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/Concat.php b/inc/lib/Twig/Node/Expression/Binary/Concat.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/Div.php b/inc/lib/Twig/Node/Expression/Binary/Div.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/Equal.php b/inc/lib/Twig/Node/Expression/Binary/Equal.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/FloorDiv.php b/inc/lib/Twig/Node/Expression/Binary/FloorDiv.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/Greater.php b/inc/lib/Twig/Node/Expression/Binary/Greater.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/GreaterEqual.php b/inc/lib/Twig/Node/Expression/Binary/GreaterEqual.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/In.php b/inc/lib/Twig/Node/Expression/Binary/In.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/Less.php b/inc/lib/Twig/Node/Expression/Binary/Less.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/LessEqual.php b/inc/lib/Twig/Node/Expression/Binary/LessEqual.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/Mod.php b/inc/lib/Twig/Node/Expression/Binary/Mod.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/Mul.php b/inc/lib/Twig/Node/Expression/Binary/Mul.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/NotEqual.php b/inc/lib/Twig/Node/Expression/Binary/NotEqual.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/NotIn.php b/inc/lib/Twig/Node/Expression/Binary/NotIn.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/Or.php b/inc/lib/Twig/Node/Expression/Binary/Or.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/Power.php b/inc/lib/Twig/Node/Expression/Binary/Power.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/Range.php b/inc/lib/Twig/Node/Expression/Binary/Range.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Binary/Sub.php b/inc/lib/Twig/Node/Expression/Binary/Sub.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/BlockReference.php b/inc/lib/Twig/Node/Expression/BlockReference.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Call.php b/inc/lib/Twig/Node/Expression/Call.php old mode 100644 new mode 100755 index 87b62deb..dba9b0e6 --- a/inc/lib/Twig/Node/Expression/Call.php +++ b/inc/lib/Twig/Node/Expression/Call.php @@ -146,7 +146,7 @@ abstract class Twig_Node_Expression_Call extends Twig_Node_Expression if (array_key_exists($name, $parameters)) { if (array_key_exists($pos, $parameters)) { - throw new Twig_Error_Syntax(sprintf('Arguments "%s" is defined twice for %s "%s".', $name, $this->getAttribute('type'), $this->getAttribute('name'))); + throw new Twig_Error_Syntax(sprintf('Argument "%s" is defined twice for %s "%s".', $name, $this->getAttribute('type'), $this->getAttribute('name'))); } $arguments[] = $parameters[$name]; @@ -164,8 +164,8 @@ abstract class Twig_Node_Expression_Call extends Twig_Node_Expression } } - foreach (array_keys($parameters) as $name) { - throw new Twig_Error_Syntax(sprintf('Unknown argument "%s" for %s "%s".', $name, $this->getAttribute('type'), $this->getAttribute('name'))); + if (!empty($parameters)) { + throw new Twig_Error_Syntax(sprintf('Unknown argument%s "%s" for %s "%s".', count($parameters) > 1 ? 's' : '' , implode('", "', array_keys($parameters)), $this->getAttribute('type'), $this->getAttribute('name'))); } return $arguments; diff --git a/inc/lib/Twig/Node/Expression/Conditional.php b/inc/lib/Twig/Node/Expression/Conditional.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Constant.php b/inc/lib/Twig/Node/Expression/Constant.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/ExtensionReference.php b/inc/lib/Twig/Node/Expression/ExtensionReference.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Filter.php b/inc/lib/Twig/Node/Expression/Filter.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Filter/Default.php b/inc/lib/Twig/Node/Expression/Filter/Default.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Function.php b/inc/lib/Twig/Node/Expression/Function.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/GetAttr.php b/inc/lib/Twig/Node/Expression/GetAttr.php old mode 100644 new mode 100755 index 81a9b137..55d9fcc3 --- a/inc/lib/Twig/Node/Expression/GetAttr.php +++ b/inc/lib/Twig/Node/Expression/GetAttr.php @@ -32,10 +32,10 @@ class Twig_Node_Expression_GetAttr extends Twig_Node_Expression $compiler->raw(', ')->subcompile($this->getNode('attribute')); - if (count($this->getNode('arguments')) || Twig_TemplateInterface::ANY_CALL !== $this->getAttribute('type') || $this->getAttribute('is_defined_test') || $this->getAttribute('ignore_strict_check')) { + if (count($this->getNode('arguments')) || Twig_Template::ANY_CALL !== $this->getAttribute('type') || $this->getAttribute('is_defined_test') || $this->getAttribute('ignore_strict_check')) { $compiler->raw(', ')->subcompile($this->getNode('arguments')); - if (Twig_TemplateInterface::ANY_CALL !== $this->getAttribute('type') || $this->getAttribute('is_defined_test') || $this->getAttribute('ignore_strict_check')) { + if (Twig_Template::ANY_CALL !== $this->getAttribute('type') || $this->getAttribute('is_defined_test') || $this->getAttribute('ignore_strict_check')) { $compiler->raw(', ')->repr($this->getAttribute('type')); } diff --git a/inc/lib/Twig/Node/Expression/MacroCall.php b/inc/lib/Twig/Node/Expression/MacroCall.php new file mode 100755 index 00000000..3e6b8c12 --- /dev/null +++ b/inc/lib/Twig/Node/Expression/MacroCall.php @@ -0,0 +1,60 @@ + + */ +class Twig_Node_Expression_MacroCall extends Twig_Node_Expression +{ + public function __construct(Twig_Node_Expression $template, $name, Twig_Node_Expression_Array $arguments, $lineno) + { + parent::__construct(array('template' => $template, 'arguments' => $arguments), array('name' => $name), $lineno); + } + + public function compile(Twig_Compiler $compiler) + { + $namedNames = array(); + $namedCount = 0; + $positionalCount = 0; + foreach ($this->getNode('arguments')->getKeyValuePairs() as $pair) { + $name = $pair['key']->getAttribute('value'); + if (!is_int($name)) { + $namedCount++; + $namedNames[$name] = 1; + } elseif ($namedCount > 0) { + throw new Twig_Error_Syntax(sprintf('Positional arguments cannot be used after named arguments for macro "%s".', $this->getAttribute('name')), $this->lineno); + } else { + $positionalCount++; + } + } + + $compiler + ->raw('$this->callMacro(') + ->subcompile($this->getNode('template')) + ->raw(', ')->repr($this->getAttribute('name')) + ->raw(', ')->subcompile($this->getNode('arguments')) + ; + + if ($namedCount > 0) { + $compiler + ->raw(', ')->repr($namedNames) + ->raw(', ')->repr($namedCount) + ->raw(', ')->repr($positionalCount) + ; + } + + $compiler + ->raw(')') + ; + } +} diff --git a/inc/lib/Twig/Node/Expression/MethodCall.php b/inc/lib/Twig/Node/Expression/MethodCall.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Name.php b/inc/lib/Twig/Node/Expression/Name.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Parent.php b/inc/lib/Twig/Node/Expression/Parent.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/TempName.php b/inc/lib/Twig/Node/Expression/TempName.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Test.php b/inc/lib/Twig/Node/Expression/Test.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Test/Constant.php b/inc/lib/Twig/Node/Expression/Test/Constant.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Test/Defined.php b/inc/lib/Twig/Node/Expression/Test/Defined.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Test/Divisibleby.php b/inc/lib/Twig/Node/Expression/Test/Divisibleby.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Test/Even.php b/inc/lib/Twig/Node/Expression/Test/Even.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Test/Null.php b/inc/lib/Twig/Node/Expression/Test/Null.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Test/Odd.php b/inc/lib/Twig/Node/Expression/Test/Odd.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Test/Sameas.php b/inc/lib/Twig/Node/Expression/Test/Sameas.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Unary.php b/inc/lib/Twig/Node/Expression/Unary.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Unary/Neg.php b/inc/lib/Twig/Node/Expression/Unary/Neg.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Unary/Not.php b/inc/lib/Twig/Node/Expression/Unary/Not.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Expression/Unary/Pos.php b/inc/lib/Twig/Node/Expression/Unary/Pos.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Flush.php b/inc/lib/Twig/Node/Flush.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/For.php b/inc/lib/Twig/Node/For.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/ForLoop.php b/inc/lib/Twig/Node/ForLoop.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/If.php b/inc/lib/Twig/Node/If.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Import.php b/inc/lib/Twig/Node/Import.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Include.php b/inc/lib/Twig/Node/Include.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Macro.php b/inc/lib/Twig/Node/Macro.php old mode 100644 new mode 100755 index 89910618..43c75e5c --- a/inc/lib/Twig/Node/Macro.php +++ b/inc/lib/Twig/Node/Macro.php @@ -18,7 +18,7 @@ class Twig_Node_Macro extends Twig_Node { public function __construct($name, Twig_NodeInterface $body, Twig_NodeInterface $arguments, $lineno, $tag = null) { - parent::__construct(array('body' => $body, 'arguments' => $arguments), array('name' => $name), $lineno, $tag); + parent::__construct(array('body' => $body, 'arguments' => $arguments), array('name' => $name, 'method' => 'get'.ucfirst($name)), $lineno, $tag); } /** @@ -30,7 +30,7 @@ class Twig_Node_Macro extends Twig_Node { $compiler ->addDebugInfo($this) - ->write(sprintf("public function get%s(", $this->getAttribute('name'))) + ->write(sprintf("public function %s(", $this->getAttribute('method'))) ; $count = count($this->getNode('arguments')); diff --git a/inc/lib/Twig/Node/Module.php b/inc/lib/Twig/Node/Module.php old mode 100644 new mode 100755 index 585048b8..224410a2 --- a/inc/lib/Twig/Node/Module.php +++ b/inc/lib/Twig/Node/Module.php @@ -235,9 +235,41 @@ class Twig_Node_Module extends Twig_Node $compiler ->outdent() - ->write(");\n") + ->write(");\n\n") + ; + + // macro information + $compiler + ->write("\$this->macros = array(\n") + ->indent() + ; + + foreach ($this->getNode('macros') as $name => $node) { + $compiler + ->addIndentation()->repr($name)->raw(" => array(\n") + ->indent() + ->write("'method' => ")->repr($node->getAttribute('method'))->raw(",\n") + ->write("'arguments' => array(\n") + ->indent() + ; + foreach ($node->getNode('arguments') as $argument => $value) { + $compiler->addIndentation()->repr($argument)->raw (' => ')->subcompile($value)->raw(",\n"); + } + $compiler + ->outdent() + ->write("),\n") + ->outdent() + ->write("),\n") + ; + } + $compiler ->outdent() - ->write("}\n\n"); + ->write(");\n") + ; + + $compiler + ->outdent() + ->write("}\n\n") ; } diff --git a/inc/lib/Twig/Node/Print.php b/inc/lib/Twig/Node/Print.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Sandbox.php b/inc/lib/Twig/Node/Sandbox.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/SandboxedModule.php b/inc/lib/Twig/Node/SandboxedModule.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/SandboxedPrint.php b/inc/lib/Twig/Node/SandboxedPrint.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Set.php b/inc/lib/Twig/Node/Set.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/SetTemp.php b/inc/lib/Twig/Node/SetTemp.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Spaceless.php b/inc/lib/Twig/Node/Spaceless.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Node/Text.php b/inc/lib/Twig/Node/Text.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/NodeInterface.php b/inc/lib/Twig/NodeInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/NodeOutputInterface.php b/inc/lib/Twig/NodeOutputInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/NodeTraverser.php b/inc/lib/Twig/NodeTraverser.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/NodeVisitor/Escaper.php b/inc/lib/Twig/NodeVisitor/Escaper.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/NodeVisitor/Optimizer.php b/inc/lib/Twig/NodeVisitor/Optimizer.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/NodeVisitor/SafeAnalysis.php b/inc/lib/Twig/NodeVisitor/SafeAnalysis.php old mode 100644 new mode 100755 index c4bbd812..b0c658cd --- a/inc/lib/Twig/NodeVisitor/SafeAnalysis.php +++ b/inc/lib/Twig/NodeVisitor/SafeAnalysis.php @@ -89,6 +89,8 @@ class Twig_NodeVisitor_SafeAnalysis implements Twig_NodeVisitorInterface } else { $this->setSafe($node, array()); } + } elseif ($node instanceof Twig_Node_Expression_MacroCall) { + $this->setSafe($node, array('all')); } elseif ($node instanceof Twig_Node_Expression_GetAttr && $node->getNode('node') instanceof Twig_Node_Expression_Name) { $name = $node->getNode('node')->getAttribute('name'); // attributes on template instances are safe diff --git a/inc/lib/Twig/NodeVisitor/Sandbox.php b/inc/lib/Twig/NodeVisitor/Sandbox.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/NodeVisitorInterface.php b/inc/lib/Twig/NodeVisitorInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Parser.php b/inc/lib/Twig/Parser.php old mode 100644 new mode 100755 index 958e46b3..bebdd9bb --- a/inc/lib/Twig/Parser.php +++ b/inc/lib/Twig/Parser.php @@ -49,7 +49,7 @@ class Twig_Parser implements Twig_ParserInterface public function getVarName() { - return sprintf('__internal_%s', hash('sha1', uniqid(mt_rand(), true), false)); + return sprintf('__internal_%s', hash('sha256', uniqid(mt_rand(), true), false)); } public function getFilename() diff --git a/inc/lib/Twig/ParserInterface.php b/inc/lib/Twig/ParserInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Sandbox/SecurityError.php b/inc/lib/Twig/Sandbox/SecurityError.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Sandbox/SecurityPolicy.php b/inc/lib/Twig/Sandbox/SecurityPolicy.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Sandbox/SecurityPolicyInterface.php b/inc/lib/Twig/Sandbox/SecurityPolicyInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/SimpleFilter.php b/inc/lib/Twig/SimpleFilter.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/SimpleFunction.php b/inc/lib/Twig/SimpleFunction.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/SimpleTest.php b/inc/lib/Twig/SimpleTest.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Template.php b/inc/lib/Twig/Template.php old mode 100644 new mode 100755 index a001ca03..a42fab28 --- a/inc/lib/Twig/Template.php +++ b/inc/lib/Twig/Template.php @@ -24,6 +24,7 @@ abstract class Twig_Template implements Twig_TemplateInterface protected $env; protected $blocks; protected $traits; + protected $macros; /** * Constructor. @@ -35,6 +36,7 @@ abstract class Twig_Template implements Twig_TemplateInterface $this->env = $env; $this->blocks = array(); $this->traits = array(); + $this->macros = array(); } /** @@ -326,7 +328,7 @@ abstract class Twig_Template implements Twig_TemplateInterface * @param mixed $object The object or array from where to get the item * @param mixed $item The item to get from the array or object * @param array $arguments An array of arguments to pass if the item is an object method - * @param string $type The type of attribute (@see Twig_TemplateInterface) + * @param string $type The type of attribute (@see Twig_Template constants) * @param Boolean $isDefinedTest Whether this is only a defined check * @param Boolean $ignoreStrictCheck Whether to ignore the strict attribute check or not * @@ -334,10 +336,10 @@ abstract class Twig_Template implements Twig_TemplateInterface * * @throws Twig_Error_Runtime if the attribute does not exist and Twig is running in strict mode and $isDefinedTest is false */ - protected function getAttribute($object, $item, array $arguments = array(), $type = Twig_TemplateInterface::ANY_CALL, $isDefinedTest = false, $ignoreStrictCheck = false) + protected function getAttribute($object, $item, array $arguments = array(), $type = Twig_Template::ANY_CALL, $isDefinedTest = false, $ignoreStrictCheck = false) { // array - if (Twig_TemplateInterface::METHOD_CALL !== $type) { + if (Twig_Template::METHOD_CALL !== $type) { $arrayItem = is_bool($item) || is_float($item) ? (int) $item : $item; if ((is_array($object) && array_key_exists($arrayItem, $object)) @@ -350,7 +352,7 @@ abstract class Twig_Template implements Twig_TemplateInterface return $object[$arrayItem]; } - if (Twig_TemplateInterface::ARRAY_CALL === $type || !is_object($object)) { + if (Twig_Template::ARRAY_CALL === $type || !is_object($object)) { if ($isDefinedTest) { return false; } @@ -363,7 +365,7 @@ abstract class Twig_Template implements Twig_TemplateInterface throw new Twig_Error_Runtime(sprintf('Key "%s" in object (with ArrayAccess) of type "%s" does not exist', $arrayItem, get_class($object)), -1, $this->getTemplateName()); } elseif (is_array($object)) { throw new Twig_Error_Runtime(sprintf('Key "%s" for array with keys "%s" does not exist', $arrayItem, implode(', ', array_keys($object))), -1, $this->getTemplateName()); - } elseif (Twig_TemplateInterface::ARRAY_CALL === $type) { + } elseif (Twig_Template::ARRAY_CALL === $type) { throw new Twig_Error_Runtime(sprintf('Impossible to access a key ("%s") on a %s variable ("%s")', $item, gettype($object), $object), -1, $this->getTemplateName()); } else { throw new Twig_Error_Runtime(sprintf('Impossible to access an attribute ("%s") on a %s variable ("%s")', $item, gettype($object), $object), -1, $this->getTemplateName()); @@ -386,7 +388,7 @@ abstract class Twig_Template implements Twig_TemplateInterface $class = get_class($object); // object property - if (Twig_TemplateInterface::METHOD_CALL !== $type) { + if (Twig_Template::METHOD_CALL !== $type) { if (isset($object->$item) || array_key_exists((string) $item, $object)) { if ($isDefinedTest) { return true; @@ -445,6 +447,66 @@ abstract class Twig_Template implements Twig_TemplateInterface return $ret; } + /** + * Calls macro in a template. + * + * @param Twig_Template $template The template + * @param string $macro The name of macro + * @param array $arguments The arguments of macro + * @param array $namedNames An array of names of arguments as keys + * @param integer $namedCount The count of named arguments + * @param integer $positionalCount The count of positional arguments + * + * @return string The content of a macro + * + * @throws Twig_Error_Runtime if the macro is not defined + * @throws Twig_Error_Runtime if the argument is defined twice + * @throws Twig_Error_Runtime if the argument is unknown + */ + protected function callMacro(Twig_Template $template, $macro, array $arguments, array $namedNames = array(), $namedCount = 0, $positionalCount = -1) + { + if (!isset($template->macros[$macro]['reflection'])) { + if (!isset($template->macros[$macro])) { + throw new Twig_Error_Runtime(sprintf('Macro "%s" is not defined in the template "%s".', $macro, $template->getTemplateName())); + } + + $template->macros[$macro]['reflection'] = new ReflectionMethod($template, $template->macros[$macro]['method']); + } + + if ($namedCount < 1) { + return $template->macros[$macro]['reflection']->invokeArgs($template, $arguments); + } + + $i = 0; + $args = array(); + foreach ($template->macros[$macro]['arguments'] as $name => $value) { + if (isset($namedNames[$name])) { + if ($i < $positionalCount) { + throw new Twig_Error_Runtime(sprintf('Argument "%s" is defined twice for macro "%s" defined in the template "%s".', $name, $macro, $template->getTemplateName())); + } + + $args[] = $arguments[$name]; + if (--$namedCount < 1) { + break; + } + } elseif ($i < $positionalCount) { + $args[] = $arguments[$i]; + } else { + $args[] = $value; + } + + $i++; + } + + if ($namedCount > 0) { + $parameters = array_keys(array_diff_key($namedNames, $template->macros[$macro]['arguments'])); + + throw new Twig_Error_Runtime(sprintf('Unknown argument%s "%s" for macro "%s" defined in the template "%s".', count($parameters) > 1 ? 's' : '' , implode('", "', $parameters), $macro, $template->getTemplateName())); + } + + return $template->macros[$macro]['reflection']->invokeArgs($template, $args); + } + /** * This method is only useful when testing Twig. Do not use it. */ diff --git a/inc/lib/Twig/TemplateInterface.php b/inc/lib/Twig/TemplateInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Test.php b/inc/lib/Twig/Test.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Test/Function.php b/inc/lib/Twig/Test/Function.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Test/IntegrationTestCase.php b/inc/lib/Twig/Test/IntegrationTestCase.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Test/Method.php b/inc/lib/Twig/Test/Method.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Test/Node.php b/inc/lib/Twig/Test/Node.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Test/NodeTestCase.php b/inc/lib/Twig/Test/NodeTestCase.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TestCallableInterface.php b/inc/lib/Twig/TestCallableInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TestInterface.php b/inc/lib/Twig/TestInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/Token.php b/inc/lib/Twig/Token.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser.php b/inc/lib/Twig/TokenParser.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/AutoEscape.php b/inc/lib/Twig/TokenParser/AutoEscape.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/Block.php b/inc/lib/Twig/TokenParser/Block.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/Do.php b/inc/lib/Twig/TokenParser/Do.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/Embed.php b/inc/lib/Twig/TokenParser/Embed.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/Extends.php b/inc/lib/Twig/TokenParser/Extends.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/Filter.php b/inc/lib/Twig/TokenParser/Filter.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/Flush.php b/inc/lib/Twig/TokenParser/Flush.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/For.php b/inc/lib/Twig/TokenParser/For.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/From.php b/inc/lib/Twig/TokenParser/From.php old mode 100644 new mode 100755 index a54054db..ff6e5756 --- a/inc/lib/Twig/TokenParser/From.php +++ b/inc/lib/Twig/TokenParser/From.php @@ -56,7 +56,7 @@ class Twig_TokenParser_From extends Twig_TokenParser $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) { - $this->parser->addImportedSymbol('function', $alias, 'get'.$name, $node->getNode('var')); + $this->parser->addImportedSymbol('macro', $alias, $name, $node->getNode('var')); } return $node; diff --git a/inc/lib/Twig/TokenParser/If.php b/inc/lib/Twig/TokenParser/If.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/Import.php b/inc/lib/Twig/TokenParser/Import.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/Include.php b/inc/lib/Twig/TokenParser/Include.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/Macro.php b/inc/lib/Twig/TokenParser/Macro.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/Sandbox.php b/inc/lib/Twig/TokenParser/Sandbox.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/Set.php b/inc/lib/Twig/TokenParser/Set.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/Spaceless.php b/inc/lib/Twig/TokenParser/Spaceless.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParser/Use.php b/inc/lib/Twig/TokenParser/Use.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParserBroker.php b/inc/lib/Twig/TokenParserBroker.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParserBrokerInterface.php b/inc/lib/Twig/TokenParserBrokerInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenParserInterface.php b/inc/lib/Twig/TokenParserInterface.php old mode 100644 new mode 100755 diff --git a/inc/lib/Twig/TokenStream.php b/inc/lib/Twig/TokenStream.php old mode 100644 new mode 100755 From df143c6b50efa82548417c6c782069064c634e0c Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Thu, 19 Sep 2013 16:09:35 +1000 Subject: [PATCH 03/26] fix Twig permissions --- inc/lib/Twig/Autoloader.php | 0 inc/lib/Twig/Compiler.php | 0 inc/lib/Twig/CompilerInterface.php | 0 inc/lib/Twig/Environment.php | 0 inc/lib/Twig/Error.php | 0 inc/lib/Twig/Error/Loader.php | 0 inc/lib/Twig/Error/Runtime.php | 0 inc/lib/Twig/Error/Syntax.php | 0 inc/lib/Twig/ExistsLoaderInterface.php | 0 inc/lib/Twig/ExpressionParser.php | 0 inc/lib/Twig/Extension.php | 0 inc/lib/Twig/Extension/Core.php | 0 inc/lib/Twig/Extension/Debug.php | 0 inc/lib/Twig/Extension/Escaper.php | 0 inc/lib/Twig/Extension/Optimizer.php | 0 inc/lib/Twig/Extension/Sandbox.php | 0 inc/lib/Twig/Extension/Staging.php | 0 inc/lib/Twig/Extension/StringLoader.php | 0 inc/lib/Twig/ExtensionInterface.php | 0 inc/lib/Twig/Filter.php | 0 inc/lib/Twig/Filter/Function.php | 0 inc/lib/Twig/Filter/Method.php | 0 inc/lib/Twig/Filter/Node.php | 0 inc/lib/Twig/FilterCallableInterface.php | 0 inc/lib/Twig/FilterInterface.php | 0 inc/lib/Twig/Function.php | 0 inc/lib/Twig/Function/Function.php | 0 inc/lib/Twig/Function/Method.php | 0 inc/lib/Twig/Function/Node.php | 0 inc/lib/Twig/FunctionCallableInterface.php | 0 inc/lib/Twig/FunctionInterface.php | 0 inc/lib/Twig/Lexer.php | 0 inc/lib/Twig/LexerInterface.php | 0 inc/lib/Twig/Loader/Array.php | 0 inc/lib/Twig/Loader/Chain.php | 0 inc/lib/Twig/Loader/Filesystem.php | 0 inc/lib/Twig/Loader/String.php | 0 inc/lib/Twig/LoaderInterface.php | 0 inc/lib/Twig/Markup.php | 0 inc/lib/Twig/Node.php | 0 inc/lib/Twig/Node/AutoEscape.php | 0 inc/lib/Twig/Node/Block.php | 0 inc/lib/Twig/Node/BlockReference.php | 0 inc/lib/Twig/Node/Body.php | 0 inc/lib/Twig/Node/Do.php | 0 inc/lib/Twig/Node/Embed.php | 0 inc/lib/Twig/Node/Expression.php | 0 inc/lib/Twig/Node/Expression/Array.php | 0 inc/lib/Twig/Node/Expression/AssignName.php | 0 inc/lib/Twig/Node/Expression/Binary.php | 0 inc/lib/Twig/Node/Expression/Binary/Add.php | 0 inc/lib/Twig/Node/Expression/Binary/And.php | 0 inc/lib/Twig/Node/Expression/Binary/BitwiseAnd.php | 0 inc/lib/Twig/Node/Expression/Binary/BitwiseOr.php | 0 inc/lib/Twig/Node/Expression/Binary/BitwiseXor.php | 0 inc/lib/Twig/Node/Expression/Binary/Concat.php | 0 inc/lib/Twig/Node/Expression/Binary/Div.php | 0 inc/lib/Twig/Node/Expression/Binary/Equal.php | 0 inc/lib/Twig/Node/Expression/Binary/FloorDiv.php | 0 inc/lib/Twig/Node/Expression/Binary/Greater.php | 0 inc/lib/Twig/Node/Expression/Binary/GreaterEqual.php | 0 inc/lib/Twig/Node/Expression/Binary/In.php | 0 inc/lib/Twig/Node/Expression/Binary/Less.php | 0 inc/lib/Twig/Node/Expression/Binary/LessEqual.php | 0 inc/lib/Twig/Node/Expression/Binary/Mod.php | 0 inc/lib/Twig/Node/Expression/Binary/Mul.php | 0 inc/lib/Twig/Node/Expression/Binary/NotEqual.php | 0 inc/lib/Twig/Node/Expression/Binary/NotIn.php | 0 inc/lib/Twig/Node/Expression/Binary/Or.php | 0 inc/lib/Twig/Node/Expression/Binary/Power.php | 0 inc/lib/Twig/Node/Expression/Binary/Range.php | 0 inc/lib/Twig/Node/Expression/Binary/Sub.php | 0 inc/lib/Twig/Node/Expression/BlockReference.php | 0 inc/lib/Twig/Node/Expression/Call.php | 0 inc/lib/Twig/Node/Expression/Conditional.php | 0 inc/lib/Twig/Node/Expression/Constant.php | 0 inc/lib/Twig/Node/Expression/ExtensionReference.php | 0 inc/lib/Twig/Node/Expression/Filter.php | 0 inc/lib/Twig/Node/Expression/Filter/Default.php | 0 inc/lib/Twig/Node/Expression/Function.php | 0 inc/lib/Twig/Node/Expression/GetAttr.php | 0 inc/lib/Twig/Node/Expression/MacroCall.php | 0 inc/lib/Twig/Node/Expression/MethodCall.php | 0 inc/lib/Twig/Node/Expression/Name.php | 0 inc/lib/Twig/Node/Expression/Parent.php | 0 inc/lib/Twig/Node/Expression/TempName.php | 0 inc/lib/Twig/Node/Expression/Test.php | 0 inc/lib/Twig/Node/Expression/Test/Constant.php | 0 inc/lib/Twig/Node/Expression/Test/Defined.php | 0 inc/lib/Twig/Node/Expression/Test/Divisibleby.php | 0 inc/lib/Twig/Node/Expression/Test/Even.php | 0 inc/lib/Twig/Node/Expression/Test/Null.php | 0 inc/lib/Twig/Node/Expression/Test/Odd.php | 0 inc/lib/Twig/Node/Expression/Test/Sameas.php | 0 inc/lib/Twig/Node/Expression/Unary.php | 0 inc/lib/Twig/Node/Expression/Unary/Neg.php | 0 inc/lib/Twig/Node/Expression/Unary/Not.php | 0 inc/lib/Twig/Node/Expression/Unary/Pos.php | 0 inc/lib/Twig/Node/Flush.php | 0 inc/lib/Twig/Node/For.php | 0 inc/lib/Twig/Node/ForLoop.php | 0 inc/lib/Twig/Node/If.php | 0 inc/lib/Twig/Node/Import.php | 0 inc/lib/Twig/Node/Include.php | 0 inc/lib/Twig/Node/Macro.php | 0 inc/lib/Twig/Node/Module.php | 0 inc/lib/Twig/Node/Print.php | 0 inc/lib/Twig/Node/Sandbox.php | 0 inc/lib/Twig/Node/SandboxedModule.php | 0 inc/lib/Twig/Node/SandboxedPrint.php | 0 inc/lib/Twig/Node/Set.php | 0 inc/lib/Twig/Node/SetTemp.php | 0 inc/lib/Twig/Node/Spaceless.php | 0 inc/lib/Twig/Node/Text.php | 0 inc/lib/Twig/NodeInterface.php | 0 inc/lib/Twig/NodeOutputInterface.php | 0 inc/lib/Twig/NodeTraverser.php | 0 inc/lib/Twig/NodeVisitor/Escaper.php | 0 inc/lib/Twig/NodeVisitor/Optimizer.php | 0 inc/lib/Twig/NodeVisitor/SafeAnalysis.php | 0 inc/lib/Twig/NodeVisitor/Sandbox.php | 0 inc/lib/Twig/NodeVisitorInterface.php | 0 inc/lib/Twig/Parser.php | 0 inc/lib/Twig/ParserInterface.php | 0 inc/lib/Twig/Sandbox/SecurityError.php | 0 inc/lib/Twig/Sandbox/SecurityPolicy.php | 0 inc/lib/Twig/Sandbox/SecurityPolicyInterface.php | 0 inc/lib/Twig/SimpleFilter.php | 0 inc/lib/Twig/SimpleFunction.php | 0 inc/lib/Twig/SimpleTest.php | 0 inc/lib/Twig/Template.php | 0 inc/lib/Twig/TemplateInterface.php | 0 inc/lib/Twig/Test.php | 0 inc/lib/Twig/Test/Function.php | 0 inc/lib/Twig/Test/IntegrationTestCase.php | 0 inc/lib/Twig/Test/Method.php | 0 inc/lib/Twig/Test/Node.php | 0 inc/lib/Twig/Test/NodeTestCase.php | 0 inc/lib/Twig/TestCallableInterface.php | 0 inc/lib/Twig/TestInterface.php | 0 inc/lib/Twig/Token.php | 0 inc/lib/Twig/TokenParser.php | 0 inc/lib/Twig/TokenParser/AutoEscape.php | 0 inc/lib/Twig/TokenParser/Block.php | 0 inc/lib/Twig/TokenParser/Do.php | 0 inc/lib/Twig/TokenParser/Embed.php | 0 inc/lib/Twig/TokenParser/Extends.php | 0 inc/lib/Twig/TokenParser/Filter.php | 0 inc/lib/Twig/TokenParser/Flush.php | 0 inc/lib/Twig/TokenParser/For.php | 0 inc/lib/Twig/TokenParser/From.php | 0 inc/lib/Twig/TokenParser/If.php | 0 inc/lib/Twig/TokenParser/Import.php | 0 inc/lib/Twig/TokenParser/Include.php | 0 inc/lib/Twig/TokenParser/Macro.php | 0 inc/lib/Twig/TokenParser/Sandbox.php | 0 inc/lib/Twig/TokenParser/Set.php | 0 inc/lib/Twig/TokenParser/Spaceless.php | 0 inc/lib/Twig/TokenParser/Use.php | 0 inc/lib/Twig/TokenParserBroker.php | 0 inc/lib/Twig/TokenParserBrokerInterface.php | 0 inc/lib/Twig/TokenParserInterface.php | 0 inc/lib/Twig/TokenStream.php | 0 163 files changed, 0 insertions(+), 0 deletions(-) mode change 100755 => 100644 inc/lib/Twig/Autoloader.php mode change 100755 => 100644 inc/lib/Twig/Compiler.php mode change 100755 => 100644 inc/lib/Twig/CompilerInterface.php mode change 100755 => 100644 inc/lib/Twig/Environment.php mode change 100755 => 100644 inc/lib/Twig/Error.php mode change 100755 => 100644 inc/lib/Twig/Error/Loader.php mode change 100755 => 100644 inc/lib/Twig/Error/Runtime.php mode change 100755 => 100644 inc/lib/Twig/Error/Syntax.php mode change 100755 => 100644 inc/lib/Twig/ExistsLoaderInterface.php mode change 100755 => 100644 inc/lib/Twig/ExpressionParser.php mode change 100755 => 100644 inc/lib/Twig/Extension.php mode change 100755 => 100644 inc/lib/Twig/Extension/Core.php mode change 100755 => 100644 inc/lib/Twig/Extension/Debug.php mode change 100755 => 100644 inc/lib/Twig/Extension/Escaper.php mode change 100755 => 100644 inc/lib/Twig/Extension/Optimizer.php mode change 100755 => 100644 inc/lib/Twig/Extension/Sandbox.php mode change 100755 => 100644 inc/lib/Twig/Extension/Staging.php mode change 100755 => 100644 inc/lib/Twig/Extension/StringLoader.php mode change 100755 => 100644 inc/lib/Twig/ExtensionInterface.php mode change 100755 => 100644 inc/lib/Twig/Filter.php mode change 100755 => 100644 inc/lib/Twig/Filter/Function.php mode change 100755 => 100644 inc/lib/Twig/Filter/Method.php mode change 100755 => 100644 inc/lib/Twig/Filter/Node.php mode change 100755 => 100644 inc/lib/Twig/FilterCallableInterface.php mode change 100755 => 100644 inc/lib/Twig/FilterInterface.php mode change 100755 => 100644 inc/lib/Twig/Function.php mode change 100755 => 100644 inc/lib/Twig/Function/Function.php mode change 100755 => 100644 inc/lib/Twig/Function/Method.php mode change 100755 => 100644 inc/lib/Twig/Function/Node.php mode change 100755 => 100644 inc/lib/Twig/FunctionCallableInterface.php mode change 100755 => 100644 inc/lib/Twig/FunctionInterface.php mode change 100755 => 100644 inc/lib/Twig/Lexer.php mode change 100755 => 100644 inc/lib/Twig/LexerInterface.php mode change 100755 => 100644 inc/lib/Twig/Loader/Array.php mode change 100755 => 100644 inc/lib/Twig/Loader/Chain.php mode change 100755 => 100644 inc/lib/Twig/Loader/Filesystem.php mode change 100755 => 100644 inc/lib/Twig/Loader/String.php mode change 100755 => 100644 inc/lib/Twig/LoaderInterface.php mode change 100755 => 100644 inc/lib/Twig/Markup.php mode change 100755 => 100644 inc/lib/Twig/Node.php mode change 100755 => 100644 inc/lib/Twig/Node/AutoEscape.php mode change 100755 => 100644 inc/lib/Twig/Node/Block.php mode change 100755 => 100644 inc/lib/Twig/Node/BlockReference.php mode change 100755 => 100644 inc/lib/Twig/Node/Body.php mode change 100755 => 100644 inc/lib/Twig/Node/Do.php mode change 100755 => 100644 inc/lib/Twig/Node/Embed.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Array.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/AssignName.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/Add.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/And.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/BitwiseAnd.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/BitwiseOr.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/BitwiseXor.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/Concat.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/Div.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/Equal.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/FloorDiv.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/Greater.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/GreaterEqual.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/In.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/Less.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/LessEqual.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/Mod.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/Mul.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/NotEqual.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/NotIn.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/Or.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/Power.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/Range.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Binary/Sub.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/BlockReference.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Call.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Conditional.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Constant.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/ExtensionReference.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Filter.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Filter/Default.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Function.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/GetAttr.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/MacroCall.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/MethodCall.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Name.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Parent.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/TempName.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Test.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Test/Constant.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Test/Defined.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Test/Divisibleby.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Test/Even.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Test/Null.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Test/Odd.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Test/Sameas.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Unary.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Unary/Neg.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Unary/Not.php mode change 100755 => 100644 inc/lib/Twig/Node/Expression/Unary/Pos.php mode change 100755 => 100644 inc/lib/Twig/Node/Flush.php mode change 100755 => 100644 inc/lib/Twig/Node/For.php mode change 100755 => 100644 inc/lib/Twig/Node/ForLoop.php mode change 100755 => 100644 inc/lib/Twig/Node/If.php mode change 100755 => 100644 inc/lib/Twig/Node/Import.php mode change 100755 => 100644 inc/lib/Twig/Node/Include.php mode change 100755 => 100644 inc/lib/Twig/Node/Macro.php mode change 100755 => 100644 inc/lib/Twig/Node/Module.php mode change 100755 => 100644 inc/lib/Twig/Node/Print.php mode change 100755 => 100644 inc/lib/Twig/Node/Sandbox.php mode change 100755 => 100644 inc/lib/Twig/Node/SandboxedModule.php mode change 100755 => 100644 inc/lib/Twig/Node/SandboxedPrint.php mode change 100755 => 100644 inc/lib/Twig/Node/Set.php mode change 100755 => 100644 inc/lib/Twig/Node/SetTemp.php mode change 100755 => 100644 inc/lib/Twig/Node/Spaceless.php mode change 100755 => 100644 inc/lib/Twig/Node/Text.php mode change 100755 => 100644 inc/lib/Twig/NodeInterface.php mode change 100755 => 100644 inc/lib/Twig/NodeOutputInterface.php mode change 100755 => 100644 inc/lib/Twig/NodeTraverser.php mode change 100755 => 100644 inc/lib/Twig/NodeVisitor/Escaper.php mode change 100755 => 100644 inc/lib/Twig/NodeVisitor/Optimizer.php mode change 100755 => 100644 inc/lib/Twig/NodeVisitor/SafeAnalysis.php mode change 100755 => 100644 inc/lib/Twig/NodeVisitor/Sandbox.php mode change 100755 => 100644 inc/lib/Twig/NodeVisitorInterface.php mode change 100755 => 100644 inc/lib/Twig/Parser.php mode change 100755 => 100644 inc/lib/Twig/ParserInterface.php mode change 100755 => 100644 inc/lib/Twig/Sandbox/SecurityError.php mode change 100755 => 100644 inc/lib/Twig/Sandbox/SecurityPolicy.php mode change 100755 => 100644 inc/lib/Twig/Sandbox/SecurityPolicyInterface.php mode change 100755 => 100644 inc/lib/Twig/SimpleFilter.php mode change 100755 => 100644 inc/lib/Twig/SimpleFunction.php mode change 100755 => 100644 inc/lib/Twig/SimpleTest.php mode change 100755 => 100644 inc/lib/Twig/Template.php mode change 100755 => 100644 inc/lib/Twig/TemplateInterface.php mode change 100755 => 100644 inc/lib/Twig/Test.php mode change 100755 => 100644 inc/lib/Twig/Test/Function.php mode change 100755 => 100644 inc/lib/Twig/Test/IntegrationTestCase.php mode change 100755 => 100644 inc/lib/Twig/Test/Method.php mode change 100755 => 100644 inc/lib/Twig/Test/Node.php mode change 100755 => 100644 inc/lib/Twig/Test/NodeTestCase.php mode change 100755 => 100644 inc/lib/Twig/TestCallableInterface.php mode change 100755 => 100644 inc/lib/Twig/TestInterface.php mode change 100755 => 100644 inc/lib/Twig/Token.php mode change 100755 => 100644 inc/lib/Twig/TokenParser.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/AutoEscape.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/Block.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/Do.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/Embed.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/Extends.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/Filter.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/Flush.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/For.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/From.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/If.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/Import.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/Include.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/Macro.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/Sandbox.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/Set.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/Spaceless.php mode change 100755 => 100644 inc/lib/Twig/TokenParser/Use.php mode change 100755 => 100644 inc/lib/Twig/TokenParserBroker.php mode change 100755 => 100644 inc/lib/Twig/TokenParserBrokerInterface.php mode change 100755 => 100644 inc/lib/Twig/TokenParserInterface.php mode change 100755 => 100644 inc/lib/Twig/TokenStream.php diff --git a/inc/lib/Twig/Autoloader.php b/inc/lib/Twig/Autoloader.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Compiler.php b/inc/lib/Twig/Compiler.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/CompilerInterface.php b/inc/lib/Twig/CompilerInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Environment.php b/inc/lib/Twig/Environment.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Error.php b/inc/lib/Twig/Error.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Error/Loader.php b/inc/lib/Twig/Error/Loader.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Error/Runtime.php b/inc/lib/Twig/Error/Runtime.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Error/Syntax.php b/inc/lib/Twig/Error/Syntax.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/ExistsLoaderInterface.php b/inc/lib/Twig/ExistsLoaderInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/ExpressionParser.php b/inc/lib/Twig/ExpressionParser.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Extension.php b/inc/lib/Twig/Extension.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Extension/Core.php b/inc/lib/Twig/Extension/Core.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Extension/Debug.php b/inc/lib/Twig/Extension/Debug.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Extension/Escaper.php b/inc/lib/Twig/Extension/Escaper.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Extension/Optimizer.php b/inc/lib/Twig/Extension/Optimizer.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Extension/Sandbox.php b/inc/lib/Twig/Extension/Sandbox.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Extension/Staging.php b/inc/lib/Twig/Extension/Staging.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Extension/StringLoader.php b/inc/lib/Twig/Extension/StringLoader.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/ExtensionInterface.php b/inc/lib/Twig/ExtensionInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Filter.php b/inc/lib/Twig/Filter.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Filter/Function.php b/inc/lib/Twig/Filter/Function.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Filter/Method.php b/inc/lib/Twig/Filter/Method.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Filter/Node.php b/inc/lib/Twig/Filter/Node.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/FilterCallableInterface.php b/inc/lib/Twig/FilterCallableInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/FilterInterface.php b/inc/lib/Twig/FilterInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Function.php b/inc/lib/Twig/Function.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Function/Function.php b/inc/lib/Twig/Function/Function.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Function/Method.php b/inc/lib/Twig/Function/Method.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Function/Node.php b/inc/lib/Twig/Function/Node.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/FunctionCallableInterface.php b/inc/lib/Twig/FunctionCallableInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/FunctionInterface.php b/inc/lib/Twig/FunctionInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Lexer.php b/inc/lib/Twig/Lexer.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/LexerInterface.php b/inc/lib/Twig/LexerInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Loader/Array.php b/inc/lib/Twig/Loader/Array.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Loader/Chain.php b/inc/lib/Twig/Loader/Chain.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Loader/Filesystem.php b/inc/lib/Twig/Loader/Filesystem.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Loader/String.php b/inc/lib/Twig/Loader/String.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/LoaderInterface.php b/inc/lib/Twig/LoaderInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Markup.php b/inc/lib/Twig/Markup.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node.php b/inc/lib/Twig/Node.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/AutoEscape.php b/inc/lib/Twig/Node/AutoEscape.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Block.php b/inc/lib/Twig/Node/Block.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/BlockReference.php b/inc/lib/Twig/Node/BlockReference.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Body.php b/inc/lib/Twig/Node/Body.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Do.php b/inc/lib/Twig/Node/Do.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Embed.php b/inc/lib/Twig/Node/Embed.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression.php b/inc/lib/Twig/Node/Expression.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Array.php b/inc/lib/Twig/Node/Expression/Array.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/AssignName.php b/inc/lib/Twig/Node/Expression/AssignName.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary.php b/inc/lib/Twig/Node/Expression/Binary.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/Add.php b/inc/lib/Twig/Node/Expression/Binary/Add.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/And.php b/inc/lib/Twig/Node/Expression/Binary/And.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/BitwiseAnd.php b/inc/lib/Twig/Node/Expression/Binary/BitwiseAnd.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/BitwiseOr.php b/inc/lib/Twig/Node/Expression/Binary/BitwiseOr.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/BitwiseXor.php b/inc/lib/Twig/Node/Expression/Binary/BitwiseXor.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/Concat.php b/inc/lib/Twig/Node/Expression/Binary/Concat.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/Div.php b/inc/lib/Twig/Node/Expression/Binary/Div.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/Equal.php b/inc/lib/Twig/Node/Expression/Binary/Equal.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/FloorDiv.php b/inc/lib/Twig/Node/Expression/Binary/FloorDiv.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/Greater.php b/inc/lib/Twig/Node/Expression/Binary/Greater.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/GreaterEqual.php b/inc/lib/Twig/Node/Expression/Binary/GreaterEqual.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/In.php b/inc/lib/Twig/Node/Expression/Binary/In.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/Less.php b/inc/lib/Twig/Node/Expression/Binary/Less.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/LessEqual.php b/inc/lib/Twig/Node/Expression/Binary/LessEqual.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/Mod.php b/inc/lib/Twig/Node/Expression/Binary/Mod.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/Mul.php b/inc/lib/Twig/Node/Expression/Binary/Mul.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/NotEqual.php b/inc/lib/Twig/Node/Expression/Binary/NotEqual.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/NotIn.php b/inc/lib/Twig/Node/Expression/Binary/NotIn.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/Or.php b/inc/lib/Twig/Node/Expression/Binary/Or.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/Power.php b/inc/lib/Twig/Node/Expression/Binary/Power.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/Range.php b/inc/lib/Twig/Node/Expression/Binary/Range.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Binary/Sub.php b/inc/lib/Twig/Node/Expression/Binary/Sub.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/BlockReference.php b/inc/lib/Twig/Node/Expression/BlockReference.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Call.php b/inc/lib/Twig/Node/Expression/Call.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Conditional.php b/inc/lib/Twig/Node/Expression/Conditional.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Constant.php b/inc/lib/Twig/Node/Expression/Constant.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/ExtensionReference.php b/inc/lib/Twig/Node/Expression/ExtensionReference.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Filter.php b/inc/lib/Twig/Node/Expression/Filter.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Filter/Default.php b/inc/lib/Twig/Node/Expression/Filter/Default.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Function.php b/inc/lib/Twig/Node/Expression/Function.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/GetAttr.php b/inc/lib/Twig/Node/Expression/GetAttr.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/MacroCall.php b/inc/lib/Twig/Node/Expression/MacroCall.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/MethodCall.php b/inc/lib/Twig/Node/Expression/MethodCall.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Name.php b/inc/lib/Twig/Node/Expression/Name.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Parent.php b/inc/lib/Twig/Node/Expression/Parent.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/TempName.php b/inc/lib/Twig/Node/Expression/TempName.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Test.php b/inc/lib/Twig/Node/Expression/Test.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Test/Constant.php b/inc/lib/Twig/Node/Expression/Test/Constant.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Test/Defined.php b/inc/lib/Twig/Node/Expression/Test/Defined.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Test/Divisibleby.php b/inc/lib/Twig/Node/Expression/Test/Divisibleby.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Test/Even.php b/inc/lib/Twig/Node/Expression/Test/Even.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Test/Null.php b/inc/lib/Twig/Node/Expression/Test/Null.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Test/Odd.php b/inc/lib/Twig/Node/Expression/Test/Odd.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Test/Sameas.php b/inc/lib/Twig/Node/Expression/Test/Sameas.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Unary.php b/inc/lib/Twig/Node/Expression/Unary.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Unary/Neg.php b/inc/lib/Twig/Node/Expression/Unary/Neg.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Unary/Not.php b/inc/lib/Twig/Node/Expression/Unary/Not.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Expression/Unary/Pos.php b/inc/lib/Twig/Node/Expression/Unary/Pos.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Flush.php b/inc/lib/Twig/Node/Flush.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/For.php b/inc/lib/Twig/Node/For.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/ForLoop.php b/inc/lib/Twig/Node/ForLoop.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/If.php b/inc/lib/Twig/Node/If.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Import.php b/inc/lib/Twig/Node/Import.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Include.php b/inc/lib/Twig/Node/Include.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Macro.php b/inc/lib/Twig/Node/Macro.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Module.php b/inc/lib/Twig/Node/Module.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Print.php b/inc/lib/Twig/Node/Print.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Sandbox.php b/inc/lib/Twig/Node/Sandbox.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/SandboxedModule.php b/inc/lib/Twig/Node/SandboxedModule.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/SandboxedPrint.php b/inc/lib/Twig/Node/SandboxedPrint.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Set.php b/inc/lib/Twig/Node/Set.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/SetTemp.php b/inc/lib/Twig/Node/SetTemp.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Spaceless.php b/inc/lib/Twig/Node/Spaceless.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Node/Text.php b/inc/lib/Twig/Node/Text.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/NodeInterface.php b/inc/lib/Twig/NodeInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/NodeOutputInterface.php b/inc/lib/Twig/NodeOutputInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/NodeTraverser.php b/inc/lib/Twig/NodeTraverser.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/NodeVisitor/Escaper.php b/inc/lib/Twig/NodeVisitor/Escaper.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/NodeVisitor/Optimizer.php b/inc/lib/Twig/NodeVisitor/Optimizer.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/NodeVisitor/SafeAnalysis.php b/inc/lib/Twig/NodeVisitor/SafeAnalysis.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/NodeVisitor/Sandbox.php b/inc/lib/Twig/NodeVisitor/Sandbox.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/NodeVisitorInterface.php b/inc/lib/Twig/NodeVisitorInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Parser.php b/inc/lib/Twig/Parser.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/ParserInterface.php b/inc/lib/Twig/ParserInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Sandbox/SecurityError.php b/inc/lib/Twig/Sandbox/SecurityError.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Sandbox/SecurityPolicy.php b/inc/lib/Twig/Sandbox/SecurityPolicy.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Sandbox/SecurityPolicyInterface.php b/inc/lib/Twig/Sandbox/SecurityPolicyInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/SimpleFilter.php b/inc/lib/Twig/SimpleFilter.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/SimpleFunction.php b/inc/lib/Twig/SimpleFunction.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/SimpleTest.php b/inc/lib/Twig/SimpleTest.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Template.php b/inc/lib/Twig/Template.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TemplateInterface.php b/inc/lib/Twig/TemplateInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Test.php b/inc/lib/Twig/Test.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Test/Function.php b/inc/lib/Twig/Test/Function.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Test/IntegrationTestCase.php b/inc/lib/Twig/Test/IntegrationTestCase.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Test/Method.php b/inc/lib/Twig/Test/Method.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Test/Node.php b/inc/lib/Twig/Test/Node.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Test/NodeTestCase.php b/inc/lib/Twig/Test/NodeTestCase.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TestCallableInterface.php b/inc/lib/Twig/TestCallableInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TestInterface.php b/inc/lib/Twig/TestInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/Token.php b/inc/lib/Twig/Token.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser.php b/inc/lib/Twig/TokenParser.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/AutoEscape.php b/inc/lib/Twig/TokenParser/AutoEscape.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/Block.php b/inc/lib/Twig/TokenParser/Block.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/Do.php b/inc/lib/Twig/TokenParser/Do.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/Embed.php b/inc/lib/Twig/TokenParser/Embed.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/Extends.php b/inc/lib/Twig/TokenParser/Extends.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/Filter.php b/inc/lib/Twig/TokenParser/Filter.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/Flush.php b/inc/lib/Twig/TokenParser/Flush.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/For.php b/inc/lib/Twig/TokenParser/For.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/From.php b/inc/lib/Twig/TokenParser/From.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/If.php b/inc/lib/Twig/TokenParser/If.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/Import.php b/inc/lib/Twig/TokenParser/Import.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/Include.php b/inc/lib/Twig/TokenParser/Include.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/Macro.php b/inc/lib/Twig/TokenParser/Macro.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/Sandbox.php b/inc/lib/Twig/TokenParser/Sandbox.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/Set.php b/inc/lib/Twig/TokenParser/Set.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/Spaceless.php b/inc/lib/Twig/TokenParser/Spaceless.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParser/Use.php b/inc/lib/Twig/TokenParser/Use.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParserBroker.php b/inc/lib/Twig/TokenParserBroker.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParserBrokerInterface.php b/inc/lib/Twig/TokenParserBrokerInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenParserInterface.php b/inc/lib/Twig/TokenParserInterface.php old mode 100755 new mode 100644 diff --git a/inc/lib/Twig/TokenStream.php b/inc/lib/Twig/TokenStream.php old mode 100755 new mode 100644 From a9b7f9b1bc88b196a165ebb1bb74d01081d1e6fd Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Sat, 21 Sep 2013 12:51:23 +1000 Subject: [PATCH 04/26] begin implementation of in-built ban appealing --- inc/config.php | 33 +++++++--- inc/functions.php | 34 ++++++++-- inc/mod/pages.php | 110 +++++++++++++++++++-------------- mod.php | 1 + post.php | 41 ++++++++++++ stylesheets/style.css | 6 ++ templates/banned.html | 56 +++++++++++++++-- templates/mod/ban_appeals.html | 106 +++++++++++++++++++++++++++++++ templates/mod/dashboard.html | 3 + 9 files changed, 324 insertions(+), 66 deletions(-) create mode 100644 templates/mod/ban_appeals.html diff --git a/inc/config.php b/inc/config.php index 84de9cfb..2bdd3131 100644 --- a/inc/config.php +++ b/inc/config.php @@ -523,9 +523,31 @@ // pure-PHP geolocation library. $config['country_flags'] = false; +/* +* ==================== +* Ban settings +* ==================== +*/ + // Require users to see the ban page at least once for a ban even if it has since expired. $config['require_ban_view'] = true; + // Show the post the user was banned for on the "You are banned" page. + $config['ban_show_post'] = false; + + // Optional HTML to append to "You are banned" pages. For example, you could include instructions and/or + // a link to an email address or IRC chat room to appeal the ban. + $config['ban_page_extra'] = ''; + + // Allow users to appeal bans through Tinyboard. + $config['ban_appeals'] = false; + + // Do not allow users to appeal bans that are shorter than this length (in seconds). + $config['ban_appeals_min_length'] = 60 * 60 * 6; // 6 hours + + // How many ban appeals can be made for a single ban? + $config['ban_appeals_max'] = 1; + /* * ==================== * Markup settings @@ -821,13 +843,6 @@ // Automatically remove unnecessary whitespace when compiling HTML files from templates. $config['minify_html'] = true; - // Show the post the user was banned for on the "You are banned" page. - $config['ban_show_post'] = false; - - // Optional HTML to append to "You are banned" pages. For example, you could include instructions and/or - // a link to an email address or IRC chat room to appeal the ban. - $config['ban_page_extra'] = ''; - // Display flags (when available). This config option has no effect unless poster flags are enabled (see // $config['country_flags']). Disable this if you want all previously-assigned flags to be hidden. $config['display_flags'] = true; @@ -1322,6 +1337,10 @@ $config['mod']['debug_sql'] = DISABLED; // Edit the current configuration (via web interface) $config['mod']['edit_config'] = ADMIN; + // View ban appeals + $config['mod']['view_ban_appeals'] = MOD; + // Accept and deny ban appeals + $config['mod']['ban_appeals'] = MOD; // Config editor permissions $config['mod']['config'] = array(); diff --git a/inc/functions.php b/inc/functions.php index cfde4640..078911ea 100644 --- a/inc/functions.php +++ b/inc/functions.php @@ -625,11 +625,16 @@ function displayBan($ban) { $ban['ip'] = $_SERVER['REMOTE_ADDR']; if ($ban['post'] && isset($ban['post']['board'], $ban['post']['id'])) { - openBoard($ban['post']['board']); - - $query = query(sprintf("SELECT `thumb`, `file` FROM ``posts_%s`` WHERE `id` = " . (int)$ban['post']['id'], $board['uri'])); - if ($_post = $query->fetch(PDO::FETCH_ASSOC)) { - $ban['post'] = array_merge($ban['post'], $_post); + if (openBoard($ban['post']['board'])) { + + $query = query(sprintf("SELECT `thumb`, `file` FROM ``posts_%s`` WHERE `id` = " . + (int)$ban['post']['id'], $board['uri'])); + if ($_post = $query->fetch(PDO::FETCH_ASSOC)) { + $ban['post'] = array_merge($ban['post'], $_post); + } else { + $ban['post']['file'] = 'deleted'; + $ban['post']['thumb'] = false; + } } else { $ban['post']['file'] = 'deleted'; $ban['post']['thumb'] = false; @@ -641,6 +646,21 @@ function displayBan($ban) { $post = new Thread($ban['post'], null, false, false); } } + + $denied_appeals = array(); + $pending_appeal = false; + + if ($config['ban_appeals']) { + $query = query("SELECT `time`, `denied` FROM `ban_appeals` WHERE `ban_id` = " . (int)$ban['id']) or error(db_error()); + while ($ban_appeal = $query->fetch(PDO::FETCH_ASSOC)) { + if ($ban_appeal['denied']) { + $denied_appeals[] = $ban_appeal['time']; + } else { + $pending_appeal = $ban_appeal['time']; + } + } + } + // Show banned page and exit die( Element('page.html', array( @@ -651,7 +671,9 @@ function displayBan($ban) { 'config' => $config, 'ban' => $ban, 'board' => $board, - 'post' => isset($post) ? $post->build(true) : false + 'post' => isset($post) ? $post->build(true) : false, + 'denied_appeals' => $denied_appeals, + 'pending_appeal' => $pending_appeal ) )) )); diff --git a/inc/mod/pages.php b/inc/mod/pages.php index 525a3d16..bae00a0f 100644 --- a/inc/mod/pages.php +++ b/inc/mod/pages.php @@ -197,37 +197,7 @@ function mod_search($type, $search_query_escaped, $page_no = 1) { // Form a series of LIKE clauses for the query. // This gets a little complicated. - // Escape "escape" character - $query = str_replace('!', '!!', $query); - - // Escape SQL wildcard - $query = str_replace('%', '!%', $query); - - // Use asterisk as wildcard instead - $query = str_replace('*', '%', $query); - - $query = str_replace('`', '!`', $query); - - // Array of phrases to match - $match = array(); - - // Exact phrases ("like this") - if (preg_match_all('/"(.+?)"/', $query, $exact_phrases)) { - $exact_phrases = $exact_phrases[1]; - foreach ($exact_phrases as $phrase) { - $query = str_replace("\"{$phrase}\"", '', $query); - $match[] = $pdo->quote($phrase); - } - } - - // Non-exact phrases (ie. plain keywords) - $keywords = explode(' ', $query); - foreach ($keywords as $word) { - if (empty($word)) - continue; - $match[] = $pdo->quote($word); - } - + // Which `field` to search? if ($type == 'posts') $sql_field = array('body_nomarkup', 'filename', 'subject', 'filehash', 'ip', 'name', 'trip'); @@ -238,22 +208,6 @@ function mod_search($type, $search_query_escaped, $page_no = 1) { if ($type == 'log') $sql_field = 'text'; - // Build the "LIKE 'this' AND LIKE 'that'" etc. part of the SQL query - $sql_like = ''; - foreach ($match as $phrase) { - if (!empty($sql_like)) - $sql_like .= ' AND '; - $phrase = preg_replace('/^\'(.+)\'$/', '\'%$1%\'', $phrase); - if (is_array($sql_field)) { - foreach ($sql_field as $field) { - $sql_like .= '`' . $field . '` LIKE ' . $phrase . ' ESCAPE \'!\' OR'; - } - $sql_like = preg_replace('/ OR$/', '', $sql_like); - } else { - $sql_like .= '`' . $sql_field . '` LIKE ' . $phrase . ' ESCAPE \'!\''; - } - } - // Compile SQL query @@ -884,6 +838,68 @@ function mod_bans($page_no = 1) { mod_page(_('Ban list'), 'mod/ban_list.html', array('bans' => $bans, 'count' => Bans::count())); } +function mod_ban_appeals() { + global $config, $board; + + if (!hasPermission($config['mod']['view_ban_appeals'])) + error($config['error']['noaccess']); + + // Remove stale ban appeals + query("DELETE FROM ``ban_appeals`` WHERE NOT EXISTS (SELECT 1 FROM ``bans`` WHERE `ban_id` = ``bans``.`id`)") + or error(db_error()); + + if (isset($_POST['appeal_id']) && (isset($_POST['unban']) || isset($_POST['deny']))) { + if (!hasPermission($config['mod']['ban_appeals'])) + error($config['error']['noaccess']); + if (isset($_POST['unban'])) { + $query = query("SELECT `ban_id` FROM ``ban_appeals`` WHERE `id` = " . + (int)$_POST['appeal_id']) or error(db_error()); + if ($ban_id = $query->fetchColumn()) { + Bans::delete($ban_id); + query("DELETE FROM ``ban_appeals`` WHERE `id` = " . (int)$_POST['appeal_id']) or error(db_error()); + } + } else { + query("UPDATE ``ban_appeals`` SET `denied` = 1 WHERE `id` = " . (int)$_POST['appeal_id']) or error(db_error()); + } + + header('Location: ?/ban-appeals', true, $config['redirect_http']); + return; + } + + $query = query("SELECT *, ``ban_appeals``.`id` AS `id` FROM ``ban_appeals`` + LEFT JOIN ``bans`` ON `ban_id` = ``bans``.`id` + WHERE `denied` != 1 ORDER BY `time`") or error(db_error()); + $ban_appeals = $query->fetchAll(PDO::FETCH_ASSOC); + foreach ($ban_appeals as &$ban) { + if ($ban['post']) + $ban['post'] = json_decode($ban['post'], true); + $ban['mask'] = Bans::range_to_string(array($ban['ipstart'], $ban['ipend'])); + + if ($ban['post'] && isset($ban['post']['board'], $ban['post']['id'])) { + if (openBoard($ban['post']['board'])) { + $query = query(sprintf("SELECT `thumb`, `file` FROM ``posts_%s`` WHERE `id` = " . + (int)$ban['post']['id'], $board['uri'])); + if ($_post = $query->fetch(PDO::FETCH_ASSOC)) { + $ban['post'] = array_merge($ban['post'], $_post); + } else { + $ban['post']['file'] = 'deleted'; + $ban['post']['thumb'] = false; + } + } else { + $ban['post']['file'] = 'deleted'; + $ban['post']['thumb'] = false; + } + + if ($ban['post']['thread']) { + $ban['post'] = new Post($ban['post']); + } else { + $ban['post'] = new Thread($ban['post'], null, false, false); + } + } + } + + mod_page(_('Ban appeals'), 'mod/ban_appeals.html', array('ban_appeals' => $ban_appeals)); +} function mod_lock($board, $unlock, $post) { global $config; diff --git a/mod.php b/mod.php index 6ef4644d..ca6d971e 100644 --- a/mod.php +++ b/mod.php @@ -59,6 +59,7 @@ $pages = array( '/IP/([\w.:]+)/remove_note/(\d+)' => 'ip_remove_note', // remove note from ip address '/bans' => 'bans', // ban list '/bans/(\d+)' => 'bans', // ban list + '/ban-appeals' => 'ban_appeals', // view ban appeals '/search' => 'search_redirect', // search '/search/(posts|IP_notes|bans|log)/(.+)/(\d+)' => 'search', // search diff --git a/post.php b/post.php index 1328bed3..b1528870 100644 --- a/post.php +++ b/post.php @@ -763,6 +763,47 @@ if (isset($_POST['delete'])) { 'id' => $id )); } +} elseif (isset($_POST['appeal'])) { + if (!isset($_POST['ban_id'])) + error($config['error']['bot']); + + $ban_id = (int)$_POST['ban_id']; + + $bans = Bans::find($_SERVER['REMOTE_ADDR']); + foreach ($bans as $_ban) { + if ($_ban['id'] == $ban_id) { + $ban = $_ban; + break; + } + } + + if (!isset($ban)) { + error(_("That ban doesn't exist or is not for you.")); + } + + if ($ban['expires'] && $ban['expires'] - $ban['created'] <= $config['ban_appeals_min_length']) { + error(_("You cannot appeal a ban of this length.")); + } + + $query = query("SELECT `denied` FROM ``ban_appeals`` WHERE `ban_id` = $ban_id") or error(db_error()); + $ban_appeals = $query->fetchAll(PDO::FETCH_COLUMN); + + if (count($ban_appeals) >= $config['ban_appeals_max']) { + error(_("You cannot appeal this ban again.")); + } + + foreach ($ban_appeals as $is_denied) { + if (!$is_denied) + error(_("There is already a pending appeal for this ban.")); + } + + $query = prepare("INSERT INTO ``ban_appeals`` VALUES (NULL, :ban_id, :time, :message, 0)"); + $query->bindValue(':ban_id', $ban_id, PDO::PARAM_INT); + $query->bindValue(':time', time(), PDO::PARAM_INT); + $query->bindValue(':message', $_POST['appeal']); + $query->execute() or error(db_error($query)); + + displayBan($ban); } else { if (!file_exists($config['has_installed'])) { header('Location: install.php', true, $config['redirect_http']); diff --git a/stylesheets/style.css b/stylesheets/style.css index ef12a5f5..31b866ef 100644 --- a/stylesheets/style.css +++ b/stylesheets/style.css @@ -424,4 +424,10 @@ table.mod.config-editor input[type="text"] { p.intro.thread-hidden { margin: 0px; padding: 0px; +} +form.ban-appeal { + margin: 9px 20px; +} +form.ban-appeal textarea { + display: block; } \ No newline at end of file diff --git a/templates/banned.html b/templates/banned.html index 79648156..666521a4 100644 --- a/templates/banned.html +++ b/templates/banned.html @@ -77,16 +77,60 @@

{% trans %}Your IP address is{% endtrans %} {{ ban.ip }}.

- {% if post %} + {% if config.ban_page_extra %} +

{{ config.ban_page_extra }}

+ {% endif %} + + {% if post and config.ban_show_post %}
-

You were banned for the following post on {{ board.url }}:

+

{% trans %}You were banned for the following post on {% endtrans %}{{ board.url }}:

{{ post }}
{% endif %} - {% if config.ban_page_extra %} -

{{ config.ban_page_extra }}

+ {% if config.ban_appeals %} +
+ {% if pending_appeal %} +

+ {% trans %}You submitted an appeal for this ban on{% endtrans %} + {{ pending_appeal|date(config.ban_date) }}. {% trans %}It is still pending{% endtrans %}. +

+ {% elseif denied_appeals|length >= config.ban_appeals_max %} + {% if denied_appeals|length == 1 %} +

+ {% trans %}You appealed this ban on{% endtrans %} + {{ denied_appeals[0]|date(config.ban_date) }} + {% trans %}and it was denied. You may not appeal this ban again.{% endtrans %} +

+ {% else %} +

{% trans %}You have submitted the maximum number of ban appeals allowed. You may not appeal this ban again.{% endtrans %}

+ {% endif %} + {% else %} + {% if denied_appeals|length %} + {% if denied_appeals|length == 1 %} +

+ {% trans %}You appealed this ban on{% endtrans %} + {{ denied_appeals[0]|date(config.ban_date) }} + {% trans %}and it was denied.{% endtrans %} +

+

{% trans %}You may appeal this ban again. Please enter your reasoning below.{% endtrans %}

+ {% else %} +

+ {% trans %}You last appealed this ban on{% endtrans %} + {{ denied_appeals[denied_appeals|length - 1]|date(config.ban_date) }} + {% trans %}and it was denied.{% endtrans %} +

+

{% trans %}You may appeal this ban again. Please enter your reasoning below.{% endtrans %}

+ {% endif %} + {% else %} +

{% trans %}You may appeal this ban. Please enter your reasoning below.{% endtrans %}

+ {% endif %} +
+ + + +
+ {% endif %} {% endif %} -{% endfilter %} - +{% endfilter %} \ No newline at end of file diff --git a/templates/mod/ban_appeals.html b/templates/mod/ban_appeals.html new file mode 100644 index 00000000..f43b7db5 --- /dev/null +++ b/templates/mod/ban_appeals.html @@ -0,0 +1,106 @@ +{% for ban in ban_appeals %} + +
+ + + + + + {% if mod|hasPermission(config.mod.show_ip, board.uri) %} + + + + + {% endif %} + + + + + + + + + + + + + + + + + + + + + + + + +
{% trans 'Status' %} + {% if config.mod.view_banexpired and ban.expires != 0 and ban.expires < time() %} + {% trans 'Expired' %} + {% else %} + {% trans 'Active' %} + {% endif %} +
{% trans 'IP' %}{{ ban.mask }}
{% trans 'Reason' %} + {% if ban.reason %} + {{ ban.reason }} + {% else %} + {% trans 'no reason' %} + {% endif %} +
{% trans 'Board' %} + {% if ban.board %} + {{ config.board_abbreviation|sprintf(ban.board) }} + {% else %} + {% trans 'all boards' %} + {% endif %} +
{% trans 'Set' %}{{ ban.created|date(config.post_date) }}
{% trans 'Expires' %} + {% if ban.expires %} + {{ ban.expires|date(config.post_date) }} + {% else %} + {% trans 'never' %} + {% endif %} +
{% trans 'Seen' %} + {% if ban.seen %} + {% trans 'Yes' %} + {% else %} + {% trans 'No' %} + {% endif %} +
{% trans 'Staff' %} + {% if ban.username %} + {{ ban.username|e }} + {% else %} + {% trans 'deleted?' %} + {% endif %} +
+ + + + + + + + + + + {% if mod|hasPermission(config.mod.ban_appeals, board.uri) %} + + + + + {% endif %} +
{% trans 'Appeal time' %}{{ ban.time|date(config.post_date) }}
{% trans 'Appeal reason' %}{{ ban.message|e }}
{% trans 'Action' %} + + + +
+ + {% if ban.post %} +
+ {{ ban.post.build(true) }} +
+ {% endif %} +
+
+ +{% endfor %} \ No newline at end of file diff --git a/templates/mod/dashboard.html b/templates/mod/dashboard.html index e2f7507d..916f0c03 100644 --- a/templates/mod/dashboard.html +++ b/templates/mod/dashboard.html @@ -86,6 +86,9 @@ {% if mod|hasPermission(config.mod.view_banlist) %}
  • {% trans 'Ban list' %}
  • {% endif %} + {% if config.ban_appeals and mod|hasPermission(config.mod.view_ban_appeals) %} +
  • {% trans 'Ban appeals' %}
  • + {% endif %} {% if mod|hasPermission(config.mod.manageusers) %}
  • {% trans 'Manage users' %}
  • {% elseif mod|hasPermission(config.mod.change_password) %} From 902da76433fbcedc083971f60c4e4fbd7a100b6e Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Sat, 21 Sep 2013 12:58:12 +1000 Subject: [PATCH 05/26] don't show ban appeal for short bans --- templates/banned.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/templates/banned.html b/templates/banned.html index 666521a4..1a9a3915 100644 --- a/templates/banned.html +++ b/templates/banned.html @@ -88,7 +88,7 @@
    {% endif %} - {% if config.ban_appeals %} + {% if config.ban_appeals and (not ban.expires or ban.expires - ban.created > config.ban_appeals_min_length )%}
    {% if pending_appeal %}

    From e36cce7903210153c6d02d0dca1be967d73c6561 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Sat, 21 Sep 2013 13:01:30 +1000 Subject: [PATCH 06/26] schema for ban appeals --- install.php | 12 +++++++++++- install.sql | 16 ++++++++++++++++ 2 files changed, 27 insertions(+), 1 deletion(-) diff --git a/install.php b/install.php index c39f62dd..5b72f51b 100644 --- a/install.php +++ b/install.php @@ -413,7 +413,7 @@ if (file_exists($config['has_installed'])) { query("UPDATE ``mods`` SET `type` = 30 WHERE `type` = 2") or error(db_error()); query("ALTER TABLE ``mods`` CHANGE `type` `type` smallint(1) NOT NULL") or error(db_error()); case 'v0.9.6-dev-20': - query("CREATE TABLE IF NOT EXISTS `bans_new_temp` ( + __query("CREATE TABLE IF NOT EXISTS `bans_new_temp` ( `id` int(10) unsigned NOT NULL AUTO_INCREMENT, `ipstart` varbinary(16) NOT NULL, `ipend` varbinary(16) DEFAULT NULL, @@ -472,6 +472,16 @@ if (file_exists($config['has_installed'])) { query("DROP TABLE ``bans``") or error(db_error()); // Replace with new table query("RENAME TABLE ``bans_new_temp`` TO ``bans``") or error(db_error()); + case 'v0.9.6-dev-21': + __query("CREATE TABLE IF NOT EXISTS ``ban_appeals`` ( + `id` int(10) unsigned NOT NULL AUTO_INCREMENT, + `ban_id` int(10) unsigned NOT NULL, + `time` int(10) unsigned NOT NULL, + `message` text NOT NULL, + `denied` tinyint(1) NOT NULL, + PRIMARY KEY (`id`), + KEY `ban_id` (`ban_id`) + ) ENGINE=MyISAM DEFAULT CHARSET=utf8mb4 AUTO_INCREMENT=1 ;") or error(db_error()); case false: // Update version number file_write($config['has_installed'], VERSION); diff --git a/install.sql b/install.sql index 462cd2f0..dcfce8f7 100644 --- a/install.sql +++ b/install.sql @@ -268,6 +268,22 @@ CREATE TABLE IF NOT EXISTS `flood` ( KEY `time` (`time`) ) ENGINE=MyISAM DEFAULT CHARSET=ascii COLLATE=ascii_bin AUTO_INCREMENT=1 ; +-- -------------------------------------------------------- + +-- +-- Table structure for table `ban_appeals` +-- + +CREATE TABLE IF NOT EXISTS `ban_appeals` ( + `id` int(10) unsigned NOT NULL AUTO_INCREMENT, + `ban_id` int(10) unsigned NOT NULL, + `time` int(10) unsigned NOT NULL, + `message` text NOT NULL, + `denied` tinyint(1) NOT NULL, + PRIMARY KEY (`id`), + KEY `ban_id` (`ban_id`) +) ENGINE=MyISAM DEFAULT CHARSET=utf8mb4 AUTO_INCREMENT=1 ; + /*!40101 SET CHARACTER_SET_CLIENT=@OLD_CHARACTER_SET_CLIENT */; /*!40101 SET CHARACTER_SET_RESULTS=@OLD_CHARACTER_SET_RESULTS */; /*!40101 SET COLLATION_CONNECTION=@OLD_COLLATION_CONNECTION */; From 0f777519e306af50d576adc9b4967aeeba1440dc Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Sat, 21 Sep 2013 13:02:44 +1000 Subject: [PATCH 07/26] forgot to increment version number --- install.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/install.php b/install.php index 5b72f51b..2aac065c 100644 --- a/install.php +++ b/install.php @@ -1,7 +1,7 @@ Date: Sat, 21 Sep 2013 21:47:44 +1000 Subject: [PATCH 08/26] "Post looks automated" bug --- js/quick-reply.js | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/js/quick-reply.js b/js/quick-reply.js index d60a3a82..6ef6815d 100644 --- a/js/quick-reply.js +++ b/js/quick-reply.js @@ -375,8 +375,8 @@ // Honestly, I'm not sure why we need setTimeout() here, but it seems to work. // Same for the "tmp" variable stuff you see inside here: setTimeout(function() { - var tmp = $('#quick-reply textarea').val(); - $('#quick-reply textarea').val('').focus().val(tmp); + var tmp = $('#quick-reply textarea[name="body"]').val(); + $('#quick-reply textarea[name="body"]').val('').focus().val(tmp); }, 1); }); } From ff4352d914f7fbedbbfd7068c4df5407b3ce1648 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Sun, 22 Sep 2013 08:13:19 +1000 Subject: [PATCH 09/26] Fixed automatic $config['root'] detection with mod.php --- inc/config.php | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-) diff --git a/inc/config.php b/inc/config.php index 2bdd3131..5105c25f 100644 --- a/inc/config.php +++ b/inc/config.php @@ -1000,9 +1000,14 @@ // The root directory, including the trailing slash, for Tinyboard. // Examples: '/', 'http://boards.chan.org/', '/chan/'. - if (isset($_SERVER['REQUEST_URI'])) - $config['root'] = str_replace('\\', '/', dirname($_SERVER['REQUEST_URI'])) == '/' ? '/' : str_replace('\\', '/', dirname($_SERVER['REQUEST_URI'])) . '/'; - else + if (isset($_SERVER['REQUEST_URI'])) { + $request_uri = $_SERVER['REQUEST_URI']; + if (isset($_SERVER['QUERY_STRING']) && $_SERVER['QUERY_STRING'] !== '') + $request_uri = substr($request_uri, 0, - 1 - strlen($_SERVER['QUERY_STRING'])); + $config['root'] = str_replace('\\', '/', dirname($request_uri)) == '/' + ? '/' : str_replace('\\', '/', dirname($request_uri)) . '/'; + unset($request_uri); + } else $config['root'] = '/'; // CLI mode // The scheme and domain. This is used to get the site's absolute URL (eg. for image identification links). From 39be89ba4945238f6311454283a66930b94577be Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 23 Sep 2013 10:11:16 +1000 Subject: [PATCH 10/26] ?/debug/apc --- inc/config.php | 2 ++ inc/mod/pages.php | 13 +++++++++++++ mod.php | 1 + templates/mod/debug/apc.html | 23 +++++++++++++++++++++++ 4 files changed, 39 insertions(+) create mode 100644 templates/mod/debug/apc.html diff --git a/inc/config.php b/inc/config.php index 5105c25f..9ca4cfeb 100644 --- a/inc/config.php +++ b/inc/config.php @@ -1340,6 +1340,8 @@ $config['mod']['news_delete'] = ADMIN; // Execute un-filtered SQL queries on the database (?/debug/sql) $config['mod']['debug_sql'] = DISABLED; + // Look through all cache values for debugging when APC is enabled (?/debug/apc) + $config['mod']['debug_apc'] = ADMIN; // Edit the current configuration (via web interface) $config['mod']['edit_config'] = ADMIN; // View ban appeals diff --git a/inc/mod/pages.php b/inc/mod/pages.php index bae00a0f..4346cf94 100644 --- a/inc/mod/pages.php +++ b/inc/mod/pages.php @@ -2354,3 +2354,16 @@ function mod_debug_sql() { mod_page(_('Debug: SQL'), 'mod/debug/sql.html', $args); } +function mod_debug_apc() { + global $config; + + if (!hasPermission($config['mod']['debug_apc'])) + error($config['error']['noaccess']); + + if ($config['cache']['enabled'] != 'apc') + error('APC is not enabled.'); + + $cached_vars = new APCIterator('user', '/^' . $config['cache']['prefix'] . '/'); + + mod_page(_('Debug: APC'), 'mod/debug/apc.html', array('cached_vars' => $cached_vars)); +} diff --git a/mod.php b/mod.php index ca6d971e..cf6423ed 100644 --- a/mod.php +++ b/mod.php @@ -89,6 +89,7 @@ $pages = array( // these pages aren't listed in the dashboard without $config['debug'] '/debug/antispam' => 'debug_antispam', '/debug/recent' => 'debug_recent_posts', + '/debug/apc' => 'debug_apc', '/debug/sql' => 'secure_POST debug_sql', // This should always be at the end: diff --git a/templates/mod/debug/apc.html b/templates/mod/debug/apc.html new file mode 100644 index 00000000..53f59eb0 --- /dev/null +++ b/templates/mod/debug/apc.html @@ -0,0 +1,23 @@ + + + + + + + + + + {% for var in cached_vars %} + + + + + + + + + {% endfor %} +
    KeyHitsCreatedExpiresSizeValue
    {{ var.key }}{{ var.num_hits }}{{ var.creation_time|ago }} ago{{ (var.creation_time + var.ttl)|until }} (ttl: {{ var.ttl }}s){{ var.mem_size }} bytes + {% set value = var.value|json_encode %} + {{ value[:80]|e('html') }}{% if value|length > 80 %}…{% endif %} +
    \ No newline at end of file From fcbc21131431725e4cb4cafde0fd907e9c607fa1 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 23 Sep 2013 10:21:18 +1000 Subject: [PATCH 11/26] Fixed weird bug with ?/debug/sql trying to allocate a few GB on some instances. Assuming bug with APCu. --- inc/mod/pages.php | 8 +++++++- templates/mod/debug/apc.html | 9 ++------- 2 files changed, 9 insertions(+), 8 deletions(-) diff --git a/inc/mod/pages.php b/inc/mod/pages.php index 4346cf94..b240db55 100644 --- a/inc/mod/pages.php +++ b/inc/mod/pages.php @@ -2363,7 +2363,13 @@ function mod_debug_apc() { if ($config['cache']['enabled'] != 'apc') error('APC is not enabled.'); - $cached_vars = new APCIterator('user', '/^' . $config['cache']['prefix'] . '/'); + $cache_info = apc_cache_info('user'); + // $cached_vars = new APCIterator('user', '/^' . $config['cache']['prefix'] . '/'); + $cached_vars = array(); + foreach ($cache_info['cache_list'] as $var) { + $cached_vars[] = $var; + } + mod_page(_('Debug: APC'), 'mod/debug/apc.html', array('cached_vars' => $cached_vars)); } diff --git a/templates/mod/debug/apc.html b/templates/mod/debug/apc.html index 53f59eb0..0aa05e9f 100644 --- a/templates/mod/debug/apc.html +++ b/templates/mod/debug/apc.html @@ -5,19 +5,14 @@ Created Expires Size - Value {% for var in cached_vars %} - {{ var.key }} + {% if var.key %}{{ var.key }}{% else %}{{ var.info }}{% endif %} {{ var.num_hits }} {{ var.creation_time|ago }} ago - {{ (var.creation_time + var.ttl)|until }} (ttl: {{ var.ttl }}s) + {{ (var.creation_time + var.ttl)|until }} (ttl: {{ (time() + var.ttl)|until }}) {{ var.mem_size }} bytes - - {% set value = var.value|json_encode %} - {{ value[:80]|e('html') }}{% if value|length > 80 %}…{% endif %} - {% endfor %} \ No newline at end of file From 4ce6218ba05fa4fbef02d35438fce9e7e2c928c7 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 23 Sep 2013 10:24:29 +1000 Subject: [PATCH 12/26] Some APC libraries/versions do stuff differently. --- templates/mod/debug/apc.html | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/templates/mod/debug/apc.html b/templates/mod/debug/apc.html index 0aa05e9f..f3c0bde7 100644 --- a/templates/mod/debug/apc.html +++ b/templates/mod/debug/apc.html @@ -8,10 +8,10 @@ {% for var in cached_vars %} - {% if var.key %}{{ var.key }}{% else %}{{ var.info }}{% endif %} - {{ var.num_hits }} - {{ var.creation_time|ago }} ago - {{ (var.creation_time + var.ttl)|until }} (ttl: {{ (time() + var.ttl)|until }}) + {{ var.key ? var.key : var.info }} + {{ var.nhits ? var.nhits : var.num_hits }} + {{ (var.ctime ? var.ctime : var.creation_time)|ago }} ago + {{ ((var.ctime ? var.ctime : var.creation_time) + var.ttl)|until }} (ttl: {{ (time() + var.ttl)|until }}) {{ var.mem_size }} bytes {% endfor %} From 6eefc5ea2a450d868ecb18465eafea7e8bdb9693 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 23 Sep 2013 10:26:13 +1000 Subject: [PATCH 13/26] . --- templates/mod/debug/apc.html | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/templates/mod/debug/apc.html b/templates/mod/debug/apc.html index f3c0bde7..fde0979b 100644 --- a/templates/mod/debug/apc.html +++ b/templates/mod/debug/apc.html @@ -8,10 +8,10 @@ {% for var in cached_vars %} - {{ var.key ? var.key : var.info }} - {{ var.nhits ? var.nhits : var.num_hits }} - {{ (var.ctime ? var.ctime : var.creation_time)|ago }} ago - {{ ((var.ctime ? var.ctime : var.creation_time) + var.ttl)|until }} (ttl: {{ (time() + var.ttl)|until }}) + {{ var.key is defined ? var.key : var.info }} + {{ var.nhits is defined ? var.nhits : var.num_hits }} + {{ (var.ctime is defined ? var.ctime : var.creation_time)|ago }} ago + {{ ((var.ctime is defined ? var.ctime : var.creation_time) + var.ttl)|until }} (ttl: {{ (time() + var.ttl)|until }}) {{ var.mem_size }} bytes {% endfor %} From 04cfeaf01c5ea830b1caa1a442a864019a02ce39 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 23 Sep 2013 10:38:06 +1000 Subject: [PATCH 14/26] hide expired cache shit --- templates/mod/debug/apc.html | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/templates/mod/debug/apc.html b/templates/mod/debug/apc.html index fde0979b..e8733af8 100644 --- a/templates/mod/debug/apc.html +++ b/templates/mod/debug/apc.html @@ -6,7 +6,7 @@ Expires Size - {% for var in cached_vars %} + {% for var in cached_vars if (var.ctime is defined ? var.ctime : var.creation_time) + var.ttl > time() %} {{ var.key is defined ? var.key : var.info }} {{ var.nhits is defined ? var.nhits : var.num_hits }} From d234c014f06955974e10a25b1199f22c226e7808 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 23 Sep 2013 10:41:47 +1000 Subject: [PATCH 15/26] ?/debug/apc with cache prefixes --- inc/mod/pages.php | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/inc/mod/pages.php b/inc/mod/pages.php index b240db55..e47289b4 100644 --- a/inc/mod/pages.php +++ b/inc/mod/pages.php @@ -2368,8 +2368,10 @@ function mod_debug_apc() { // $cached_vars = new APCIterator('user', '/^' . $config['cache']['prefix'] . '/'); $cached_vars = array(); foreach ($cache_info['cache_list'] as $var) { + if ($config['cache']['prefix'] != '' && strpos(isset($var['key']) ? $var['key'] : $var['info'], $config['cache']['prefix']) !== 0) + continue; $cached_vars[] = $var; } - + mod_page(_('Debug: APC'), 'mod/debug/apc.html', array('cached_vars' => $cached_vars)); } From 699279d84aab16594505aa394fc4c9ed22cbba11 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 23 Sep 2013 12:41:27 +1000 Subject: [PATCH 16/26] Hardened secure tripcode? --- inc/functions.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/inc/functions.php b/inc/functions.php index 078911ea..02665952 100644 --- a/inc/functions.php +++ b/inc/functions.php @@ -1973,7 +1973,7 @@ function generate_tripcode($name) { if (isset($config['custom_tripcode']["##{$trip}"])) $trip = $config['custom_tripcode']["##{$trip}"]; else - $trip = '!!' . substr(crypt($trip, $config['secure_trip_salt']), -10); + $trip = '!!' . substr(crypt($trip, $salt . $config['secure_trip_salt']), -10); } else { if (isset($config['custom_tripcode']["#{$trip}"])) $trip = $config['custom_tripcode']["#{$trip}"]; From 9cf6814776a989cca12cf1249460268b50ae25b2 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 23 Sep 2013 12:53:44 +1000 Subject: [PATCH 17/26] Fix secure tripcode hardening --- inc/functions.php | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/inc/functions.php b/inc/functions.php index 02665952..3448e7db 100644 --- a/inc/functions.php +++ b/inc/functions.php @@ -1973,14 +1973,13 @@ function generate_tripcode($name) { if (isset($config['custom_tripcode']["##{$trip}"])) $trip = $config['custom_tripcode']["##{$trip}"]; else - $trip = '!!' . substr(crypt($trip, $salt . $config['secure_trip_salt']), -10); + $trip = '!!' . substr(crypt($trip, substr(base64_encode(sha1($trip . $config['secure_trip_salt'], true)), 0, 9)), -10); } else { if (isset($config['custom_tripcode']["#{$trip}"])) $trip = $config['custom_tripcode']["#{$trip}"]; else $trip = '!' . substr(crypt($trip, $salt), -10); } - return array($name, $trip); } From 299b0e3f2f0bae47c2739071c7e604f5d97a5065 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 23 Sep 2013 14:00:04 +1000 Subject: [PATCH 18/26] filehash filter condition --- inc/filters.php | 2 ++ 1 file changed, 2 insertions(+) diff --git a/inc/filters.php b/inc/filters.php index f06154ba..f694d2b1 100644 --- a/inc/filters.php +++ b/inc/filters.php @@ -91,6 +91,8 @@ class Filter { return preg_match($match, $post['subject']); case 'body': return preg_match($match, $post['body_nomarkup']); + case 'filehash': + return $match === $post['filehash']; case 'filename': if (!$post['has_file']) return false; From 964bb83300a75095a19768d3e426a429d77c4d6a Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 23 Sep 2013 14:23:42 +1000 Subject: [PATCH 19/26] OK, now it is secure. --- inc/functions.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/inc/functions.php b/inc/functions.php index 3448e7db..7c6d3df3 100644 --- a/inc/functions.php +++ b/inc/functions.php @@ -1973,13 +1973,14 @@ function generate_tripcode($name) { if (isset($config['custom_tripcode']["##{$trip}"])) $trip = $config['custom_tripcode']["##{$trip}"]; else - $trip = '!!' . substr(crypt($trip, substr(base64_encode(sha1($trip . $config['secure_trip_salt'], true)), 0, 9)), -10); + $trip = '!!' . substr(crypt($trip, '_..A.' . substr(base64_encode(sha1($trip . $config['secure_trip_salt'], true)), 0, 4)), -10); } else { if (isset($config['custom_tripcode']["#{$trip}"])) $trip = $config['custom_tripcode']["#{$trip}"]; else $trip = '!' . substr(crypt($trip, $salt), -10); } + return array($name, $trip); } From de70fb6253446f86913562bc4ce0932562a753ce Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 23 Sep 2013 15:52:45 +1000 Subject: [PATCH 20/26] $config['error']['lurk'] was last used in 2010 I think --- inc/config.php | 1 - 1 file changed, 1 deletion(-) diff --git a/inc/config.php b/inc/config.php index 9ca4cfeb..a9ed2069 100644 --- a/inc/config.php +++ b/inc/config.php @@ -936,7 +936,6 @@ */ // Error messages - $config['error']['lurk'] = _('Lurk some more before posting.'); $config['error']['bot'] = _('You look like a bot.'); $config['error']['referer'] = _('Your browser sent an invalid or no HTTP referer.'); $config['error']['toolong'] = _('The %s field was too long.'); From 00f4da3b82afda892906578ec1bd3c766fe0cd45 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 23 Sep 2013 15:52:59 +1000 Subject: [PATCH 21/26] $config['referer_match'] = false to disable --- post.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/post.php b/post.php index b1528870..a8ba8dba 100644 --- a/post.php +++ b/post.php @@ -181,7 +181,8 @@ if (isset($_POST['delete'])) { error($config['error']['bot']); // Check the referrer - if (!isset($_SERVER['HTTP_REFERER']) || !preg_match($config['referer_match'], urldecode($_SERVER['HTTP_REFERER']))) + if ($config['referer_match'] !== false && + (!isset($_SERVER['HTTP_REFERER']) || !preg_match($config['referer_match'], urldecode($_SERVER['HTTP_REFERER'])))) error($config['error']['referer']); checkDNSBL(); From c8062fbf767100a46e32a81ed34d8d8eaf5c45e7 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 23 Sep 2013 16:48:56 +1000 Subject: [PATCH 22/26] CSRF more mod pages --- inc/mod/pages.php | 124 +++++++++++++++++++++------ mod.php | 86 ++++++++++--------- templates/mod/ban_appeals.html | 1 + templates/mod/ban_list.html | 3 +- templates/mod/board.html | 1 + templates/mod/config-editor-php.html | 1 + templates/mod/config-editor.html | 1 + templates/mod/dashboard.html | 2 +- templates/mod/new_pm.html | 1 + templates/mod/news.html | 3 +- templates/mod/noticeboard.html | 5 +- templates/mod/rebuild.html | 1 + templates/mod/report.html | 4 +- templates/mod/theme_config.html | 1 + templates/mod/themes.html | 4 +- templates/mod/user.html | 1 + templates/mod/users.html | 4 +- templates/mod/view_ip.html | 2 + 18 files changed, 166 insertions(+), 79 deletions(-) diff --git a/inc/mod/pages.php b/inc/mod/pages.php index e47289b4..58cd5c26 100644 --- a/inc/mod/pages.php +++ b/inc/mod/pages.php @@ -156,7 +156,9 @@ function mod_dashboard() { if ($latest) $args['newer_release'] = $latest; } - + + $args['logout_token'] = make_secure_link_token('logout'); + mod_page(_('Dashboard'), 'mod/dashboard.html', $args); } @@ -389,7 +391,10 @@ function mod_edit_board($boardName) { header('Location: ?/', true, $config['redirect_http']); } else { - mod_page(sprintf('%s: ' . $config['board_abbreviation'], _('Edit board'), $board['uri']), 'mod/board.html', array('board' => $board)); + mod_page(sprintf('%s: ' . $config['board_abbreviation'], _('Edit board'), $board['uri']), 'mod/board.html', array( + 'board' => $board, + 'token' => make_secure_link_token('edit/' . $board['uri']) + )); } } @@ -459,7 +464,7 @@ function mod_new_board() { header('Location: ?/' . $board['uri'] . '/' . $config['file_index'], true, $config['redirect_http']); } - mod_page(_('New board'), 'mod/board.html', array('new' => true)); + mod_page(_('New board'), 'mod/board.html', array('new' => true, 'token' => make_secure_link_token('new-board'))); } function mod_noticeboard($page_no = 1) { @@ -502,11 +507,19 @@ function mod_noticeboard($page_no = 1) { if (empty($noticeboard) && $page_no > 1) error($config['error']['404']); + foreach ($noticeboard as &$entry) { + $entry['delete_token'] = make_secure_link_token('noticeboard/delete/' . $entry['id']); + } + $query = prepare("SELECT COUNT(*) FROM ``noticeboard``"); $query->execute() or error(db_error($query)); $count = $query->fetchColumn(); - mod_page(_('Noticeboard'), 'mod/noticeboard.html', array('noticeboard' => $noticeboard, 'count' => $count)); + mod_page(_('Noticeboard'), 'mod/noticeboard.html', array( + 'noticeboard' => $noticeboard, + 'count' => $count, + 'token' => make_secure_link_token('noticeboard') + )); } function mod_noticeboard_delete($id) { @@ -563,11 +576,15 @@ function mod_news($page_no = 1) { if (empty($news) && $page_no > 1) error($config['error']['404']); + foreach ($news as &$entry) { + $entry['delete_token'] = make_secure_link_token('news/delete/' . $entry['id']); + } + $query = prepare("SELECT COUNT(*) FROM ``news``"); $query->execute() or error(db_error($query)); $count = $query->fetchColumn(); - mod_page(_('News'), 'mod/news.html', array('news' => $news, 'count' => $count)); + mod_page(_('News'), 'mod/news.html', array('news' => $news, 'count' => $count, 'token' => make_secure_link_token('news'))); } function mod_news_delete($id) { @@ -773,6 +790,8 @@ function mod_page_ip($ip) { $args['logs'] = array(); } + $args['security_token'] = make_secure_link_token('IP/' . $ip); + mod_page(sprintf('%s: %s', _('IP'), $ip), 'mod/view_ip.html', $args, $args['hostname']); } @@ -835,7 +854,11 @@ function mod_bans($page_no = 1) { $ban['single_addr'] = true; } - mod_page(_('Ban list'), 'mod/ban_list.html', array('bans' => $bans, 'count' => Bans::count())); + mod_page(_('Ban list'), 'mod/ban_list.html', array( + 'bans' => $bans, + 'count' => Bans::count(), + 'token' => make_secure_link_token('bans') + )); } function mod_ban_appeals() { @@ -851,15 +874,23 @@ function mod_ban_appeals() { if (isset($_POST['appeal_id']) && (isset($_POST['unban']) || isset($_POST['deny']))) { if (!hasPermission($config['mod']['ban_appeals'])) error($config['error']['noaccess']); + + $query = query("SELECT *, ``ban_appeals``.`id` AS `id` FROM ``ban_appeals`` + LEFT JOIN ``bans`` ON `ban_id` = ``bans``.`id` + WHERE ``ban_appeals``.`id` = " . (int)$_POST['appeal_id']) or error(db_error()); + if (!$ban = $query->fetch(PDO::FETCH_ASSOC)) { + error(_('Ban appeal not found!')); + } + + $ban['mask'] = Bans::range_to_string(array($ban['ipstart'], $ban['ipend'])); + if (isset($_POST['unban'])) { - $query = query("SELECT `ban_id` FROM ``ban_appeals`` WHERE `id` = " . - (int)$_POST['appeal_id']) or error(db_error()); - if ($ban_id = $query->fetchColumn()) { - Bans::delete($ban_id); - query("DELETE FROM ``ban_appeals`` WHERE `id` = " . (int)$_POST['appeal_id']) or error(db_error()); - } + modLog('Accepted ban appeal #' . $ban['id'] . ' for ' . $ban['mask']); + Bans::delete($ban['ban_id'], true); + query("DELETE FROM ``ban_appeals`` WHERE `id` = " . $ban['id']) or error(db_error()); } else { - query("UPDATE ``ban_appeals`` SET `denied` = 1 WHERE `id` = " . (int)$_POST['appeal_id']) or error(db_error()); + modLog('Denied ban appeal #' . $ban['id'] . ' for ' . $ban['mask']); + query("UPDATE ``ban_appeals`` SET `denied` = 1 WHERE `id` = " . $ban['id']) or error(db_error()); } header('Location: ?/ban-appeals', true, $config['redirect_http']); @@ -898,7 +929,10 @@ function mod_ban_appeals() { } } - mod_page(_('Ban appeals'), 'mod/ban_appeals.html', array('ban_appeals' => $ban_appeals)); + mod_page(_('Ban appeals'), 'mod/ban_appeals.html', array( + 'ban_appeals' => $ban_appeals, + 'token' => make_secure_link_token('ban-appeals') + )); } function mod_lock($board, $unlock, $post) { @@ -1583,7 +1617,12 @@ function mod_user($uid) { $user['boards'] = explode(',', $user['boards']); - mod_page(_('Edit user'), 'mod/user.html', array('user' => $user, 'logs' => $log, 'boards' => listBoards())); + mod_page(_('Edit user'), 'mod/user.html', array( + 'user' => $user, + 'logs' => $log, + 'boards' => listBoards(), + 'token' => make_secure_link_token('users/' . $user['id']) + )); } function mod_user_new() { @@ -1636,7 +1675,7 @@ function mod_user_new() { return; } - mod_page(_('Edit user'), 'mod/user.html', array('new' => true, 'boards' => listBoards())); + mod_page(_('New user'), 'mod/user.html', array('new' => true, 'boards' => listBoards(), 'token' => make_secure_link_token('users/new'))); } @@ -1646,9 +1685,18 @@ function mod_users() { if (!hasPermission($config['mod']['manageusers'])) error($config['error']['noaccess']); - $query = query("SELECT *, (SELECT `time` FROM ``modlogs`` WHERE `mod` = `id` ORDER BY `time` DESC LIMIT 1) AS `last`, (SELECT `text` FROM ``modlogs`` WHERE `mod` = `id` ORDER BY `time` DESC LIMIT 1) AS `action` FROM ``mods`` ORDER BY `type` DESC,`id`") or error(db_error()); + $query = query("SELECT + *, + (SELECT `time` FROM ``modlogs`` WHERE `mod` = `id` ORDER BY `time` DESC LIMIT 1) AS `last`, + (SELECT `text` FROM ``modlogs`` WHERE `mod` = `id` ORDER BY `time` DESC LIMIT 1) AS `action` + FROM ``mods`` ORDER BY `type` DESC,`id`") or error(db_error()); $users = $query->fetchAll(PDO::FETCH_ASSOC); + foreach ($users as &$user) { + $user['promote_token'] = make_secure_link_token("users/{$user['id']}/promote"); + $user['demote_token'] = make_secure_link_token("users/{$user['id']}/demote"); + } + mod_page(sprintf('%s (%d)', _('Manage users'), count($users)), 'mod/users.html', array('users' => $users)); } @@ -1740,7 +1788,10 @@ function mod_pm($id, $reply = false) { error($config['error']['404']); // deleted? mod_page(sprintf('%s %s', _('New PM for'), $pm['to_username']), 'mod/new_pm.html', array( - 'username' => $pm['username'], 'id' => $pm['sender'], 'message' => quote($pm['message']) + 'username' => $pm['username'], + 'id' => $pm['sender'], + 'message' => quote($pm['message']), + 'token' => make_secure_link_token('new_PM/' . $pm['username']) )); } else { mod_page(sprintf('%s – #%d', _('Private message'), $id), 'mod/pm.html', $pm); @@ -1812,7 +1863,11 @@ function mod_new_pm($username) { header('Location: ?/', true, $config['redirect_http']); } - mod_page(sprintf('%s %s', _('New PM for'), $username), 'mod/new_pm.html', array('username' => $username, 'id' => $id)); + mod_page(sprintf('%s %s', _('New PM for'), $username), 'mod/new_pm.html', array( + 'username' => $username, + 'id' => $id, + 'token' => make_secure_link_token('new_PM/' . $username) + )); } function mod_rebuild() { @@ -1881,7 +1936,10 @@ function mod_rebuild() { return; } - mod_page(_('Rebuild'), 'mod/rebuild.html', array('boards' => listBoards())); + mod_page(_('Rebuild'), 'mod/rebuild.html', array( + 'boards' => listBoards(), + 'token' => make_secure_link_token('rebuild') + )); } function mod_reports() { @@ -1936,7 +1994,13 @@ function mod_reports() { } // a little messy and inefficient - $append_html = Element('mod/report.html', array('report' => $report, 'config' => $config, 'mod' => $mod)); + $append_html = Element('mod/report.html', array( + 'report' => $report, + 'config' => $config, + 'mod' => $mod, + 'token' => make_secure_link_token('reports/' . $report['id'] . '/dismiss'), + 'token_all' => make_secure_link_token('reports/' . $report['id'] . '/dismissall') + )); // Bug fix for https://github.com/savetheinternet/Tinyboard/issues/21 $po->body = truncate($po->body, $po->link(), $config['body_truncate'] - substr_count($append_html, '
    ')); @@ -2030,7 +2094,8 @@ function mod_config($board_config = false) { 'readonly' => $readonly, 'boards' => listBoards(), 'board' => $board_config, - 'file' => $config_file + 'file' => $config_file, + 'token' => make_secure_link_token('config' . ($board_config ? '/' . $board_config : '')) )); return; } @@ -2113,17 +2178,18 @@ function mod_config($board_config = false) { } } - header('Location: ?/config', true, $config['redirect_http']); + header('Location: ?/config' . ($board_config ? '/' . $board_config : ''), true, $config['redirect_http']); exit; } - + mod_page(_('Config editor') . ($board_config ? ': ' . sprintf($config['board_abbreviation'], $board_config) : ''), 'mod/config-editor.html', array( 'boards' => listBoards(), 'board' => $board_config, 'conf' => $conf, - 'file' => $config_file + 'file' => $config_file, + 'token' => make_secure_link_token('config' . ($board_config ? '/' . $board_config : '')) )); } @@ -2149,6 +2215,11 @@ function mod_themes_list() { } } closedir($dir); + + foreach ($themes as $theme_name => &$theme) { + $theme['rebuild_token'] = make_secure_link_token('themes/' . $theme_name . '/rebuild'); + $theme['uninstall_token'] = make_secure_link_token('themes/' . $theme_name . '/uninstall'); + } mod_page(_('Manage themes'), 'mod/themes.html', array( 'themes' => $themes, @@ -2219,7 +2290,7 @@ function mod_theme_configure($theme_name) { 'theme_name' => $theme_name, 'theme' => $theme, 'result' => $result, - 'message' => $message, + 'message' => $message )); return; } @@ -2230,6 +2301,7 @@ function mod_theme_configure($theme_name) { 'theme_name' => $theme_name, 'theme' => $theme, 'settings' => $settings, + 'token' => make_secure_link_token('themes/' . $theme_name) )); } diff --git a/mod.php b/mod.php index cf6423ed..f6a4aa0c 100644 --- a/mod.php +++ b/mod.php @@ -24,49 +24,51 @@ if (get_magic_quotes_gpc()) { $query = isset($_SERVER['QUERY_STRING']) ? rawurldecode($_SERVER['QUERY_STRING']) : ''; $pages = array( - '' => ':?/', // redirect to dashboard - '/' => 'dashboard', // dashboard - '/confirm/(.+)' => 'confirm', // confirm action (if javascript didn't work) - '/logout' => 'logout', // logout + '' => ':?/', // redirect to dashboard + '/' => 'dashboard', // dashboard + '/confirm/(.+)' => 'confirm', // confirm action (if javascript didn't work) + '/logout' => 'secure logout', // logout - '/users' => 'users', // manage users - '/users/(\d+)' => 'user', // edit user - '/users/(\d+)/(promote|demote)' => 'user_promote', // prmote/demote user - '/users/new' => 'user_new', // create a new user - '/new_PM/([^/]+)' => 'new_pm', // create a new pm - '/PM/(\d+)(/reply)?' => 'pm', // read a pm - '/inbox' => 'inbox', // pm inbox + '/users' => 'users', // manage users + '/users/(\d+)/(promote|demote)' => 'secure user_promote', // prmote/demote user + '/users/(\d+)' => 'secure_POST user', // edit user + '/users/new' => 'secure_POST user_new', // create a new user - '/noticeboard' => 'noticeboard', // view noticeboard - '/noticeboard/(\d+)' => 'noticeboard', // view noticeboard - '/noticeboard/delete/(\d+)' => 'noticeboard_delete', // delete from noticeboard - '/log' => 'log', // modlog - '/log/(\d+)' => 'log', // modlog - '/log:([^/]+)' => 'user_log', // modlog - '/log:([^/]+)/(\d+)' => 'user_log', // modlog - '/news' => 'news', // view news - '/news/(\d+)' => 'news', // view news - '/news/delete/(\d+)' => 'news_delete', // delete from news + '/new_PM/([^/]+)' => 'secure_POST new_pm', // create a new pm + '/PM/(\d+)(/reply)?' => 'pm', // read a pm + '/inbox' => 'inbox', // pm inbox - '/edit/(\%b)' => 'edit_board', // edit board details - '/new-board' => 'new_board', // create a new board + '/log' => 'log', // modlog + '/log/(\d+)' => 'log', // modlog + '/log:([^/]+)' => 'user_log', // modlog + '/log:([^/]+)/(\d+)' => 'user_log', // modlog + '/news' => 'secure_POST news', // view news + '/news/(\d+)' => 'secure_POST news', // view news + '/news/delete/(\d+)' => 'secure news_delete', // delete from news - '/rebuild' => 'rebuild', // rebuild static files - '/reports' => 'reports', // report queue - '/reports/(\d+)/dismiss(all)?' => 'report_dismiss', // dismiss a report + '/noticeboard' => 'secure_POST noticeboard', // view noticeboard + '/noticeboard/(\d+)' => 'secure_POST noticeboard', // view noticeboard + '/noticeboard/delete/(\d+)' => 'secure noticeboard_delete', // delete from noticeboard - '/IP/([\w.:]+)' => 'ip', // view ip address - '/IP/([\w.:]+)/remove_note/(\d+)' => 'ip_remove_note', // remove note from ip address - '/bans' => 'bans', // ban list - '/bans/(\d+)' => 'bans', // ban list - '/ban-appeals' => 'ban_appeals', // view ban appeals + '/edit/(\%b)' => 'secure_POST edit_board', // edit board details + '/new-board' => 'secure_POST new_board', // create a new board + + '/rebuild' => 'secure_POST rebuild', // rebuild static files + '/reports' => 'reports', // report queue + '/reports/(\d+)/dismiss(all)?' => 'secure report_dismiss', // dismiss a report + + '/IP/([\w.:]+)' => 'secure_POST ip', // view ip address + '/IP/([\w.:]+)/remove_note/(\d+)' => 'secure ip_remove_note', // remove note from ip address - '/search' => 'search_redirect', // search - '/search/(posts|IP_notes|bans|log)/(.+)/(\d+)' => 'search', // search - '/search/(posts|IP_notes|bans|log)/(.+)' => 'search', // search - - // CSRF-protected moderator actions '/ban' => 'secure_POST ban', // new ban + '/bans' => 'secure_POST bans', // ban list + '/bans/(\d+)' => 'secure_POST bans', // ban list + '/ban-appeals' => 'secure_POST ban_appeals', // view ban appeals + + '/search' => 'search_redirect', // search + '/search/(posts|IP_notes|bans|log)/(.+)/(\d+)' => 'search', // search + '/search/(posts|IP_notes|bans|log)/(.+)' => 'search', // search + '/(\%b)/ban(&delete)?/(\d+)' => 'secure_POST ban_post', // ban poster '/(\%b)/move/(\d+)' => 'secure_POST move', // move thread '/(\%b)/edit(_raw)?/(\d+)' => 'secure_POST edit_post', // edit post @@ -78,13 +80,13 @@ $pages = array( '/(\%b)/(un)?sticky/(\d+)' => 'secure sticky', // sticky thread '/(\%b)/bump(un)?lock/(\d+)' => 'secure bumplock', // "bumplock" thread - '/themes' => 'themes_list', // manage themes - '/themes/(\w+)' => 'theme_configure', // configure/reconfigure theme - '/themes/(\w+)/rebuild' => 'theme_rebuild', // rebuild theme - '/themes/(\w+)/uninstall' => 'theme_uninstall', // uninstall theme + '/themes' => 'themes_list', // manage themes + '/themes/(\w+)' => 'secure_POST theme_configure', // configure/reconfigure theme + '/themes/(\w+)/rebuild' => 'secure theme_rebuild', // rebuild theme + '/themes/(\w+)/uninstall' => 'secure theme_uninstall', // uninstall theme - '/config' => 'config', // config editor - '/config/(\%b)' => 'config', // config editor + '/config' => 'secure_POST config', // config editor + '/config/(\%b)' => 'secure_POST config', // config editor // these pages aren't listed in the dashboard without $config['debug'] '/debug/antispam' => 'debug_antispam', diff --git a/templates/mod/ban_appeals.html b/templates/mod/ban_appeals.html index f43b7db5..23eced12 100644 --- a/templates/mod/ban_appeals.html +++ b/templates/mod/ban_appeals.html @@ -1,6 +1,7 @@ {% for ban in ban_appeals %}

    + diff --git a/templates/mod/ban_list.html b/templates/mod/ban_list.html index b41cef28..97c02029 100644 --- a/templates/mod/ban_list.html +++ b/templates/mod/ban_list.html @@ -1,7 +1,8 @@ {% if bans|count == 0 %}

    ({% trans 'There are no active bans.' %})

    {% else %} - + +
    {% trans 'Status' %}
    diff --git a/templates/mod/board.html b/templates/mod/board.html index 0775e421..4da597a7 100644 --- a/templates/mod/board.html +++ b/templates/mod/board.html @@ -5,6 +5,7 @@ {% endif %} +
    {% trans 'IP address/mask' %}
    diff --git a/templates/mod/config-editor-php.html b/templates/mod/config-editor-php.html index 4f76b5dd..0c1a3a09 100644 --- a/templates/mod/config-editor-php.html +++ b/templates/mod/config-editor-php.html @@ -21,6 +21,7 @@ {% if not readonly %}{% endif %} + diff --git a/templates/mod/config-editor.html b/templates/mod/config-editor.html index 4f4cba93..411d55e6 100644 --- a/templates/mod/config-editor.html +++ b/templates/mod/config-editor.html @@ -14,6 +14,7 @@ {% endif %} +
    {% trans 'URI' %}
    diff --git a/templates/mod/dashboard.html b/templates/mod/dashboard.html index 916f0c03..7b907533 100644 --- a/templates/mod/dashboard.html +++ b/templates/mod/dashboard.html @@ -164,7 +164,7 @@ {% trans 'User account' %} diff --git a/templates/mod/new_pm.html b/templates/mod/new_pm.html index 3fd78ac6..605b0973 100644 --- a/templates/mod/new_pm.html +++ b/templates/mod/new_pm.html @@ -1,4 +1,5 @@ +
    {% trans 'Name' %}
    diff --git a/templates/mod/news.html b/templates/mod/news.html index b0335e0a..510d60ce 100644 --- a/templates/mod/news.html +++ b/templates/mod/news.html @@ -2,6 +2,7 @@
    {% trans 'New post' %} +
    To
    @@ -39,7 +40,7 @@
    {% if mod|hasPermission(config.mod.news_delete) %} - [{% trans 'delete' %}] + [{% trans 'delete' %}] {% endif %}

    diff --git a/templates/mod/noticeboard.html b/templates/mod/noticeboard.html index 463b8430..fc2e0aef 100644 --- a/templates/mod/noticeboard.html +++ b/templates/mod/noticeboard.html @@ -1,7 +1,8 @@ {% if mod|hasPermission(config.mod.noticeboard_post) %}
    {% trans 'New post' %} - + + @@ -27,7 +28,7 @@
    {% if mod|hasPermission(config.mod.noticeboard_delete) %} - [{% trans 'delete' %}] + [{% trans 'delete' %}] {% endif %}

    diff --git a/templates/mod/rebuild.html b/templates/mod/rebuild.html index 7c6b28ba..81d1ead3 100644 --- a/templates/mod/rebuild.html +++ b/templates/mod/rebuild.html @@ -1,4 +1,5 @@ +
    • diff --git a/templates/mod/report.html b/templates/mod/report.html index 9c8463ed..b5392d5b 100644 --- a/templates/mod/report.html +++ b/templates/mod/report.html @@ -13,13 +13,13 @@ {% if mod|hasPermission(config.mod.report_dismiss, report.board) or mod|hasPermission(config.mod.report_dismiss_ip, report.board) %}
      {% if mod|hasPermission(config.mod.report_dismiss, report.board) %} - Dismiss + Dismiss {% endif %} {% if mod|hasPermission(config.mod.report_dismiss_ip, report.board) %} {% if mod|hasPermission(config.mod.report_dismiss, report.board) %} | {% endif %} - Dismiss+ + Dismiss+ {% endif %} {% endif %}

    diff --git a/templates/mod/theme_config.html b/templates/mod/theme_config.html index d85b5df1..d82a1f14 100644 --- a/templates/mod/theme_config.html +++ b/templates/mod/theme_config.html @@ -1,4 +1,5 @@ + {% if not config %}

    (No configuration required.)

    {% else %} diff --git a/templates/mod/themes.html b/templates/mod/themes.html index b596826d..b230bc48 100644 --- a/templates/mod/themes.html +++ b/templates/mod/themes.html @@ -28,8 +28,8 @@ {% if theme_name in themes_in_use %}{% trans 'Reconfigure' %}{% else %}{% trans 'Install' %}{% endif %} {% if theme_name in themes_in_use %} -
  • {% trans 'Rebuild' %}
  • -
  • {% trans 'Uninstall' %}
  • +
  • {% trans 'Rebuild' %}
  • +
  • {% trans 'Uninstall' %}
  • {% endif %} diff --git a/templates/mod/user.html b/templates/mod/user.html index 89240824..08598fe5 100644 --- a/templates/mod/user.html +++ b/templates/mod/user.html @@ -5,6 +5,7 @@ {% endif %} +
    {% trans 'Name' %}
    diff --git a/templates/mod/users.html b/templates/mod/users.html index b4c666e1..6f42ce2a 100644 --- a/templates/mod/users.html +++ b/templates/mod/users.html @@ -48,10 +48,10 @@ {% endif %}
    {% trans 'Username' %} {% if mod|hasPermission(config.mod.promoteusers) and user.type < constant(config.mod.groups[0:-1]|last) %} - + {% endif %} {% if mod|hasPermission(config.mod.promoteusers) and user.type > constant(config.mod.groups|first) %} - + {% endif %} {% if mod|hasPermission(config.mod.modlog) %} [{% trans 'log' %}] diff --git a/templates/mod/view_ip.html b/templates/mod/view_ip.html index f73c5d5a..1c1c7fa6 100644 --- a/templates/mod/view_ip.html +++ b/templates/mod/view_ip.html @@ -57,6 +57,7 @@ {% if mod|hasPermission(config.mod.create_notes) %} + @@ -87,6 +88,7 @@ {% for ban in bans %} +
    {% trans 'Staff' %}
    From a3c3ef6068a8d81e66f0fb96eddee261678640c4 Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Tue, 24 Sep 2013 09:53:20 +1000 Subject: [PATCH 23/26] Required PHP version is now 5.3. Deal with it, nerds. Fuck everyone who still hasn't upgraded. --- README.md | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-) diff --git a/README.md b/README.md index 3a1583df..9d3a7058 100644 --- a/README.md +++ b/README.md @@ -8,7 +8,7 @@ imageboard software package. It is written in PHP and has few dependencies. Requirements ------------ -1. PHP >= 5.2.5 +1. PHP >= 5.3 2. MySQL server 3. [mbstring](http://www.php.net/manual/en/mbstring.installation.php) 4. [PHP GD](http://www.php.net/manual/en/intro.image.php) @@ -19,10 +19,9 @@ operating systems. Tinyboard does not include an Apache ```.htaccess``` file nor it need one. ### Recommended -1. PHP >= 5.3 -2. MySQL server >= 5.5.3 -3. ImageMagick (command-line ImageMagick or GraphicsMagick preferred). -4. [APC (Alternative PHP Cache)](http://php.net/manual/en/book.apc.php), [XCache](http://xcache.lighttpd.net/) or [Memcached](http://www.php.net/manual/en/intro.memcached.php) +1. MySQL server >= 5.5.3 +2. ImageMagick (command-line ImageMagick or GraphicsMagick preferred). +3. [APC (Alternative PHP Cache)](http://php.net/manual/en/book.apc.php), [XCache](http://xcache.lighttpd.net/) or [Memcached](http://www.php.net/manual/en/intro.memcached.php) Contributing ------------ From a665f16aed57e23262eaf2dd9ef88dc149431e04 Mon Sep 17 00:00:00 2001 From: Desuneko Date: Fri, 27 Sep 2013 20:17:21 +0200 Subject: [PATCH 24/26] install.php: fixed a typo --- install.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/install.php b/install.php index 2aac065c..5b65823c 100644 --- a/install.php +++ b/install.php @@ -13,7 +13,7 @@ $page = array( 'nojavascript' => true ); -// this breaks the dispaly of licenses if enabled +// this breaks the display of licenses if enabled $config['minify_html'] = false; if (file_exists($config['has_installed'])) { From f5422cad65e5cafd7d53da87d62a6fc247da3b1b Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Mon, 30 Sep 2013 12:18:56 +1000 Subject: [PATCH 25/26] Um. I accidentally deleted this code for some reason. --- inc/mod/pages.php | 54 ++++++++++++++++++++++++++++++++++++++++++----- 1 file changed, 49 insertions(+), 5 deletions(-) diff --git a/inc/mod/pages.php b/inc/mod/pages.php index 58cd5c26..c091263e 100644 --- a/inc/mod/pages.php +++ b/inc/mod/pages.php @@ -199,27 +199,71 @@ function mod_search($type, $search_query_escaped, $page_no = 1) { // Form a series of LIKE clauses for the query. // This gets a little complicated. - + // Escape "escape" character + $query = str_replace('!', '!!', $query); + + // Escape SQL wildcard + $query = str_replace('%', '!%', $query); + + // Use asterisk as wildcard instead + $query = str_replace('*', '%', $query); + + $query = str_replace('`', '!`', $query); + + // Array of phrases to match + $match = array(); + + // Exact phrases ("like this") + if (preg_match_all('/"(.+?)"/', $query, $exact_phrases)) { + $exact_phrases = $exact_phrases[1]; + foreach ($exact_phrases as $phrase) { + $query = str_replace("\"{$phrase}\"", '', $query); + $match[] = $pdo->quote($phrase); + } + } + + // Non-exact phrases (ie. plain keywords) + $keywords = explode(' ', $query); + foreach ($keywords as $word) { + if (empty($word)) + continue; + $match[] = $pdo->quote($word); + } + // Which `field` to search? if ($type == 'posts') - $sql_field = array('body_nomarkup', 'filename', 'subject', 'filehash', 'ip', 'name', 'trip'); + $sql_field = array('body_nomarkup', 'filename', 'file', 'subject', 'filehash', 'ip', 'name', 'trip'); if ($type == 'IP_notes') $sql_field = 'body'; if ($type == 'bans') $sql_field = 'reason'; if ($type == 'log') $sql_field = 'text'; - + + // Build the "LIKE 'this' AND LIKE 'that'" etc. part of the SQL query + $sql_like = ''; + foreach ($match as $phrase) { + if (!empty($sql_like)) + $sql_like .= ' AND '; + $phrase = preg_replace('/^\'(.+)\'$/', '\'%$1%\'', $phrase); + if (is_array($sql_field)) { + foreach ($sql_field as $field) { + $sql_like .= '`' . $field . '` LIKE ' . $phrase . ' ESCAPE \'!\' OR'; + } + $sql_like = preg_replace('/ OR$/', '', $sql_like); + } else { + $sql_like .= '`' . $sql_field . '` LIKE ' . $phrase . ' ESCAPE \'!\''; + } + } // Compile SQL query if ($type == 'posts') { $query = ''; - $boards = listBoards(); if (empty($boards)) error(_('There are no boards to search!')); - + foreach ($boards as $board) { openBoard($board['uri']); if (!hasPermission($config['mod']['search_posts'], $board['uri'])) From 9fb63b053fbb552a2a8bbde1e230a8b73296fb6d Mon Sep 17 00:00:00 2001 From: Michael Foster Date: Fri, 4 Oct 2013 20:13:58 +1000 Subject: [PATCH 26/26] new event: markup-url --- inc/functions.php | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/inc/functions.php b/inc/functions.php index 7c6d3df3..f6a217a5 100644 --- a/inc/functions.php +++ b/inc/functions.php @@ -1538,7 +1538,25 @@ function markup_url($matches) { $markup_urls[] = $url; - return '' . $url . '' . $after; + $link = (object) array( + 'href' => $url, + 'text' => $url, + 'rel' => 'nofollow', + 'target' => '_blank', + ); + + event('markup-url', $link); + $link = (array)$link; + + $parts = array(); + foreach ($link as $attr => $value) { + if ($attr == 'text' || $attr == 'after') + continue; + $parts[] = $attr . '="' . htmlspecialchars($value) . '"'; + } + if (isset($link['after'])) + $after = $link['after'] . $after; + return '' . utf8tohtml($link['text']) . '' . $after; } function unicodify($body) {
    {% trans 'Status' %}