jdaugherty commented on code in PR #16551:
URL: https://github.com/apache/grails-core/pull/16551#discussion_r4210768192


##########
grails-gsp/core/src/main/groovy/org/grails/gsp/compiler/LogicLineTrimmer.java:
##########
@@ -0,0 +1,94 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *    https://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ */
+package org.grails.gsp.compiler;
+
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+/**
+ * Removes the lines of a page that hold only template logic, for a page 
declaring
+ * {@code trimLogicLines="true"}: a line holding nothing but page directives, 
scriptlets and comments,
+ * besides spaces and tabs, writes neither its indentation nor its line break. 
A line holding text, an
+ * expression or a tag is left as it is.
+ *
+ * <p>The line break of a removed line is moved inside the line's last 
construct, just after its
+ * opening delimiter, rather than dropped, so that every line of the page 
keeps its number in the
+ * compiled page and in the errors reported against it.</p>
+ */
+final class LogicLineTrimmer {
+
+    private static final String CONSTRUCT = "(?:" +
+            "<%--(?:(?!--%>).)*--%>" +          // <%-- comment --%>
+            "|%\\{--(?:(?!--\\}%).)*--\\}%" +   // %{-- comment --}%
+            "|<%@(?:(?!%>).)*%>" +              // <%@ directive %>
+            "|<%(?![=@]|--)(?:(?!%>).)*%>" +    // <% scriptlet %>

Review Comment:
   Fixed in 651f2cde15. A declaration (`<%!`) is no longer read as a scriptlet: 
its line is left as it is, so the page reports that declarations are not 
supported, the same as without `trimLogicLines`. Covered by "a declaration on 
its own line is rejected as it is with trimming" in `GspTrimLogicLinesSpec`, 
which failed with a `MissingMethodException` before the fix.



##########
grails-gsp/core/src/main/groovy/org/grails/gsp/compiler/LogicLineTrimmer.java:
##########
@@ -0,0 +1,94 @@
+/*
+ *  Licensed to the Apache Software Foundation (ASF) under one
+ *  or more contributor license agreements.  See the NOTICE file
+ *  distributed with this work for additional information
+ *  regarding copyright ownership.  The ASF licenses this file
+ *  to you under the Apache License, Version 2.0 (the
+ *  "License"); you may not use this file except in compliance
+ *  with the License.  You may obtain a copy of the License at
+ *
+ *    https://www.apache.org/licenses/LICENSE-2.0
+ *
+ *  Unless required by applicable law or agreed to in writing,
+ *  software distributed under the License is distributed on an
+ *  "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ *  KIND, either express or implied.  See the License for the
+ *  specific language governing permissions and limitations
+ *  under the License.
+ */
+package org.grails.gsp.compiler;
+
+import java.util.regex.Matcher;
+import java.util.regex.Pattern;
+
+/**
+ * Removes the lines of a page that hold only template logic, for a page 
declaring
+ * {@code trimLogicLines="true"}: a line holding nothing but page directives, 
scriptlets and comments,
+ * besides spaces and tabs, writes neither its indentation nor its line break. 
A line holding text, an
+ * expression or a tag is left as it is.
+ *
+ * <p>The line break of a removed line is moved inside the line's last 
construct, just after its
+ * opening delimiter, rather than dropped, so that every line of the page 
keeps its number in the
+ * compiled page and in the errors reported against it.</p>
+ */
+final class LogicLineTrimmer {
+
+    private static final String CONSTRUCT = "(?:" +
+            "<%--(?:(?!--%>).)*--%>" +          // <%-- comment --%>
+            "|%\\{--(?:(?!--\\}%).)*--\\}%" +   // %{-- comment --}%
+            "|<%@(?:(?!%>).)*%>" +              // <%@ directive %>
+            "|<%(?![=@]|--)(?:(?!%>).)*%>" +    // <% scriptlet %>
+            "|%\\{(?!--)(?:(?!\\}%).)*\\}%" +   // %{ scriptlet }%
+            ")";
+
+    private static final Pattern CONSTRUCT_PATTERN = 
Pattern.compile(CONSTRUCT, Pattern.DOTALL);
+
+    private static final Pattern LOGIC_LINE_PATTERN = Pattern.compile(
+            "^[ \\t]*(" + CONSTRUCT + "(?:[ \\t]*" + CONSTRUCT + ")*)[ 
\\t]*(\\r?\\n|\\z)",
+            Pattern.MULTILINE | Pattern.DOTALL);
+
+    private LogicLineTrimmer() {
+    }
+
+    static String trim(String gspSource) {
+        Matcher line = LOGIC_LINE_PATTERN.matcher(gspSource);

Review Comment:
   Fixed in 651f2cde15. `LogicLineTrimmer` no longer runs a regex over the 
whole page. It walks the page the way `GroovyPageScanner` reads it (expressions 
through `GroovyPageExpressionParser`, tag attributes, scriptlets, comments), so 
a logic line can only start in the page's text. Text inside an expression, a 
tag, a scriptlet or a comment is never trimmed. New specs cover a multi-line 
`${}` string, a scriptlet string and a tag-attribute expression, and all three 
failed before the fix. The trimmed output of all 62 Forge GSPs is 
byte-identical before and after.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]

Reply via email to