001    /**
002     * Copyright (c) 2000-2012 Liferay, Inc. All rights reserved.
003     *
004     * This library is free software; you can redistribute it and/or modify it under
005     * the terms of the GNU Lesser General Public License as published by the Free
006     * Software Foundation; either version 2.1 of the License, or (at your option)
007     * any later version.
008     *
009     * This library is distributed in the hope that it will be useful, but WITHOUT
010     * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
011     * FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
012     * details.
013     */
014    
015    package com.liferay.portal.tools;
016    
017    import com.liferay.portal.kernel.io.unsync.UnsyncBufferedReader;
018    import com.liferay.portal.kernel.io.unsync.UnsyncStringReader;
019    import com.liferay.portal.kernel.util.ArrayUtil;
020    import com.liferay.portal.kernel.util.CharPool;
021    import com.liferay.portal.kernel.util.ClassUtil;
022    import com.liferay.portal.kernel.util.GetterUtil;
023    import com.liferay.portal.kernel.util.ListUtil;
024    import com.liferay.portal.kernel.util.PropertiesUtil;
025    import com.liferay.portal.kernel.util.PropsKeys;
026    import com.liferay.portal.kernel.util.StringBundler;
027    import com.liferay.portal.kernel.util.StringPool;
028    import com.liferay.portal.kernel.util.StringUtil;
029    import com.liferay.portal.kernel.util.TextFormatter;
030    import com.liferay.portal.kernel.util.Tuple;
031    import com.liferay.portal.kernel.util.Validator;
032    import com.liferay.portal.kernel.xml.Document;
033    import com.liferay.portal.kernel.xml.DocumentException;
034    import com.liferay.portal.kernel.xml.Element;
035    import com.liferay.portal.util.FileImpl;
036    import com.liferay.portal.xml.SAXReaderImpl;
037    import com.liferay.util.ContentUtil;
038    
039    import java.io.File;
040    import java.io.FileInputStream;
041    import java.io.FileNotFoundException;
042    import java.io.IOException;
043    import java.io.InputStream;
044    
045    import java.net.URL;
046    
047    import java.util.ArrayList;
048    import java.util.Arrays;
049    import java.util.Collection;
050    import java.util.Collections;
051    import java.util.HashMap;
052    import java.util.HashSet;
053    import java.util.List;
054    import java.util.Map;
055    import java.util.Properties;
056    import java.util.Set;
057    import java.util.TreeSet;
058    import java.util.regex.Matcher;
059    import java.util.regex.Pattern;
060    
061    import org.apache.tools.ant.DirectoryScanner;
062    
063    /**
064     * @author Brian Wing Shun Chan
065     * @author Igor Spasic
066     * @author Wesley Gong
067     * @author Hugo Huijser
068     */
069    public class SourceFormatter {
070    
071            public static void main(String[] args) {
072                    try {
073                            _excludes = StringUtil.split(
074                                    GetterUtil.getString(
075                                            System.getProperty("source.formatter.excludes")));
076    
077                            _portalSource = _isPortalSource();
078    
079                            _sourceFormatterHelper = new SourceFormatterHelper(false);
080    
081                            _sourceFormatterHelper.init();
082    
083                            Thread thread1 = new Thread () {
084    
085                                    @Override
086                                    public void run() {
087                                            try {
088                                                    _formatJSP();
089                                                    _formatAntXML();
090                                                    _formatDDLStructuresXML();
091                                                    _formatFriendlyURLRoutesXML();
092                                                    _formatFTL();
093                                                    _formatJS();
094                                                    _formatPortalProperties();
095                                                    _formatPortletXML();
096                                                    _formatServiceXML();
097                                                    _formatSH();
098                                                    _formatSQL();
099                                                    _formatStrutsConfigXML();
100                                                    _formatTilesDefsXML();
101                                                    _formatTLD();
102                                                    _formatWebXML();
103                                            }
104                                            catch (Exception e) {
105                                                    e.printStackTrace();
106                                            }
107                                    }
108    
109                            };
110    
111                            Thread thread2 = new Thread () {
112    
113                                    @Override
114                                    public void run() {
115                                            try {
116                                                    _formatJava();
117                                            }
118                                            catch (Exception e) {
119                                                    e.printStackTrace();
120                                            }
121                                    }
122    
123                            };
124    
125                            thread1.start();
126                            thread2.start();
127    
128                            thread1.join();
129                            thread2.join();
130    
131                            _sourceFormatterHelper.close();
132                    }
133                    catch (Exception e) {
134                            e.printStackTrace();
135                    }
136            }
137    
138            public static String stripJavaImports(
139                            String content, String packageDir, String className)
140                    throws IOException {
141    
142                    Matcher matcher = _javaImportPattern.matcher(content);
143    
144                    if (!matcher.find()) {
145                            return content;
146                    }
147    
148                    String imports = matcher.group();
149    
150                    Set<String> classes = ClassUtil.getClasses(
151                            new UnsyncStringReader(content), className);
152    
153                    StringBundler sb = new StringBundler();
154    
155                    UnsyncBufferedReader unsyncBufferedReader = new UnsyncBufferedReader(
156                            new UnsyncStringReader(imports));
157    
158                    String line = null;
159    
160                    while ((line = unsyncBufferedReader.readLine()) != null) {
161                            if (line.contains("import ")) {
162                                    int importX = line.indexOf(" ");
163                                    int importY = line.lastIndexOf(".");
164    
165                                    String importPackage = line.substring(importX + 1, importY);
166                                    String importClass = line.substring(
167                                            importY + 1, line.length() - 1);
168    
169                                    if (!packageDir.equals(importPackage)) {
170                                            if (!importClass.equals("*")) {
171                                                    if (classes.contains(importClass)) {
172                                                            sb.append(line);
173                                                            sb.append("\n");
174                                                    }
175                                            }
176                                            else {
177                                                    sb.append(line);
178                                                    sb.append("\n");
179                                            }
180                                    }
181                            }
182                    }
183    
184                    imports = _formatImports(sb.toString(), 7);
185    
186                    content =
187                            content.substring(0, matcher.start()) + imports +
188                                    content.substring(matcher.end());
189    
190                    // Ensure a blank line exists between the package and the first import
191    
192                    content = content.replaceFirst(
193                            "(?m)^[ \t]*(package .*;)\\s*^[ \t]*import", "$1\n\nimport");
194    
195                    // Ensure a blank line exists between the last import (or package if
196                    // there are no imports) and the class comment
197    
198                    content = content.replaceFirst(
199                            "(?m)^[ \t]*((?:package|import) .*;)\\s*^[ \t]*/\\*\\*",
200                            "$1\n\n/**");
201    
202                    return content;
203            }
204    
205            private static void _addJSPIncludeFileNames(
206                    String fileName, Set<String> includeFileNames) {
207    
208                    String content = _jspContents.get(fileName);
209    
210                    if (Validator.isNull(content)) {
211                            return;
212                    }
213    
214                    for (int x = 0;;) {
215                            x = content.indexOf("<%@ include file=", x);
216    
217                            if (x == -1) {
218                                    break;
219                            }
220    
221                            x = content.indexOf(StringPool.QUOTE, x);
222    
223                            if (x == -1) {
224                                    break;
225                            }
226    
227                            int y = content.indexOf(StringPool.QUOTE, x + 1);
228    
229                            if (y == -1) {
230                                    break;
231                            }
232    
233                            String includeFileName = content.substring(x + 1, y);
234    
235                            Matcher matcher = _jspIncludeFilePattern.matcher(includeFileName);
236    
237                            if (!matcher.find()) {
238                                    throw new RuntimeException(
239                                            "Invalid include " + includeFileName);
240                            }
241    
242                            String docrootPath = fileName.substring(
243                                    0, fileName.indexOf("docroot") + 7);
244    
245                            includeFileName = docrootPath + includeFileName;
246    
247                            if ((includeFileName.endsWith("jsp") ||
248                                     includeFileName.endsWith("jspf")) &&
249                                    !includeFileName.endsWith("html/portlet/init.jsp") &&
250                                    !includeFileName.endsWith("html/taglib/init.jsp") &&
251                                    !includeFileNames.contains(includeFileName)) {
252    
253                                    includeFileNames.add(includeFileName);
254                            }
255    
256                            x = y;
257                    }
258            }
259    
260            private static void _addJSPReferenceFileNames(
261                    String fileName, Set<String> includeFileNames) {
262    
263                    for (Map.Entry<String, String> entry : _jspContents.entrySet()) {
264                            String referenceFileName = entry.getKey();
265                            String content = entry.getValue();
266    
267                            if (content.contains("<%@ include file=\"" + fileName) &&
268                                    !includeFileNames.contains(referenceFileName)) {
269    
270                                    includeFileNames.add(referenceFileName);
271                            }
272                    }
273            }
274    
275            private static void _addJSPUnusedImports(
276                    String fileName, List<String> importLines,
277                    List<String> unneededImports) {
278    
279                    for (String importLine : importLines) {
280                            Set<String> includeFileNames = new HashSet<String>();
281    
282                            includeFileNames.add(fileName);
283    
284                            Set<String> checkedFileNames = new HashSet<String>();
285    
286                            int x = importLine.indexOf(StringPool.QUOTE);
287                            int y = importLine.indexOf(StringPool.QUOTE, x + 1);
288    
289                            if ((x == -1) || (y == -1)) {
290                                    continue;
291                            }
292    
293                            String className = importLine.substring(x + 1, y);
294    
295                            className = className.substring(
296                                    className.lastIndexOf(StringPool.PERIOD) + 1);
297    
298                            if (!_isJSPImportRequired(
299                                            fileName, className, includeFileNames, checkedFileNames)) {
300    
301                                    unneededImports.add(importLine);
302                            }
303                    }
304            }
305    
306            private static List<String> _addParameterTypes(
307                    String line, List<String> parameterTypes) {
308    
309                    int x = line.indexOf(StringPool.OPEN_PARENTHESIS);
310    
311                    if (x != -1) {
312                            line = line.substring(x + 1);
313    
314                            if (Validator.isNull(line) ||
315                                    line.startsWith(StringPool.CLOSE_PARENTHESIS)) {
316    
317                                    return parameterTypes;
318                            }
319                    }
320    
321                    for (x = 0;;) {
322                            x = line.indexOf(StringPool.SPACE);
323    
324                            if (x == -1) {
325                                    return parameterTypes;
326                            }
327    
328                            String parameterType = line.substring(0, x);
329    
330                            if (parameterType.equals("throws")) {
331                                    return parameterTypes;
332                            }
333    
334                            if (parameterType.endsWith("...")) {
335                                    parameterType = StringUtil.replaceLast(
336                                            parameterType, "...", StringPool.BLANK);
337                            }
338    
339                            parameterTypes.add(parameterType);
340    
341                            int y = line.indexOf(StringPool.COMMA);
342                            int z = line.indexOf(StringPool.CLOSE_PARENTHESIS);
343    
344                            if ((y == -1) || ((z != -1) && (z < y))) {
345                                    return parameterTypes;
346                            }
347    
348                            line = line.substring(y + 1);
349                            line = line.trim();
350                    }
351            }
352    
353            private static void _checkIfClause(
354                    String ifClause, String fileName, int lineCount) {
355    
356                    int quoteCount = StringUtil.count(ifClause, StringPool.QUOTE);
357    
358                    if ((quoteCount % 2) == 1) {
359                            return;
360                    }
361    
362                    ifClause = _stripQuotes(ifClause);
363    
364                    if (ifClause.contains(StringPool.DOUBLE_SLASH) ||
365                            ifClause.contains("/*") || ifClause.contains("*/")) {
366    
367                            return;
368                    }
369    
370                    ifClause = _stripRedundantParentheses(ifClause);
371    
372                    ifClause = StringUtil.replace(
373                            ifClause, new String[] {"'('", "')'"},
374                            new String[] {StringPool.BLANK, StringPool.BLANK});
375    
376                    int level = 0;
377                    int max = StringUtil.count(ifClause, StringPool.OPEN_PARENTHESIS);
378                    int previousParenthesisPos = -1;
379    
380                    int[] levels = new int[max];
381    
382                    for (int i = 0; i < ifClause.length(); i++) {
383                            char c = ifClause.charAt(i);
384    
385                            if ((c == CharPool.OPEN_PARENTHESIS) ||
386                                    (c == CharPool.CLOSE_PARENTHESIS)) {
387    
388                                    if (previousParenthesisPos != -1) {
389                                            String s = ifClause.substring(
390                                                    previousParenthesisPos + 1, i);
391    
392                                            _checkMissingParentheses(s, fileName, lineCount);
393                                    }
394    
395                                    previousParenthesisPos = i;
396    
397                                    if (c == CharPool.OPEN_PARENTHESIS) {
398                                            levels[level] = i;
399    
400                                            level += 1;
401                                    }
402                                    else {
403                                            int posOpenParenthesis = levels[level - 1];
404    
405                                            if (level > 1) {
406                                                    char nextChar = ifClause.charAt(i + 1);
407                                                    char previousChar = ifClause.charAt(
408                                                            posOpenParenthesis - 1);
409    
410                                                    if (!Character.isLetterOrDigit(nextChar) &&
411                                                            (nextChar != CharPool.PERIOD) &&
412                                                            !Character.isLetterOrDigit(previousChar)) {
413    
414                                                            String s = ifClause.substring(
415                                                                    posOpenParenthesis + 1, i);
416    
417                                                            if (Validator.isNotNull(s) &&
418                                                                    !s.contains(StringPool.SPACE)) {
419    
420                                                                    _sourceFormatterHelper.printError(
421                                                                            fileName,
422                                                                            "redundant parentheses: " + fileName + " " +
423                                                                                    lineCount);
424                                                            }
425                                                    }
426    
427                                                    if ((previousChar == CharPool.OPEN_PARENTHESIS) &&
428                                                            (nextChar == CharPool.CLOSE_PARENTHESIS)) {
429    
430                                                            _sourceFormatterHelper.printError(
431                                                                    fileName,
432                                                                    "redundant parentheses: " + fileName + " " +
433                                                                            lineCount);
434                                                    }
435                                            }
436    
437                                            level -= 1;
438                                    }
439                            }
440                    }
441            }
442    
443            private static void _checkLanguageKeys(
444                            String fileName, String content, Pattern pattern)
445                    throws IOException {
446    
447                    String fileExtension = _fileUtil.getExtension(fileName);
448    
449                    if (!_portalSource || fileExtension.equals("vm")) {
450                            return;
451                    }
452    
453                    if (_portalLanguageKeysProperties == null) {
454                            _portalLanguageKeysProperties = new Properties();
455    
456                            ClassLoader classLoader = SourceFormatter.class.getClassLoader();
457    
458                            InputStream inputStream = classLoader.getResourceAsStream(
459                                    "content/Language.properties");
460    
461                            _portalLanguageKeysProperties.load(inputStream);
462                    }
463    
464                    Matcher matcher = pattern.matcher(content);
465    
466                    while (matcher.find()) {
467                            String[] languageKeys = _getLanguageKeys(matcher);
468    
469                            for (String languageKey : languageKeys) {
470                                    if (Validator.isNumber(languageKey) ||
471                                            languageKey.endsWith(StringPool.DASH) ||
472                                            languageKey.endsWith(StringPool.PERIOD) ||
473                                            languageKey.endsWith(StringPool.UNDERLINE) ||
474                                            languageKey.startsWith(StringPool.DASH) ||
475                                            languageKey.startsWith(StringPool.PERIOD) ||
476                                            languageKey.startsWith(StringPool.UNDERLINE)) {
477    
478                                            continue;
479                                    }
480    
481                                    if (!_portalLanguageKeysProperties.containsKey(languageKey)) {
482                                            _sourceFormatterHelper.printError(
483                                                    fileName,
484                                                    "missing language key: " + languageKey +
485                                                            StringPool.SPACE + fileName);
486                                    }
487                            }
488                    }
489            }
490    
491            private static void _checkMissingParentheses(
492                    String s, String fileName, int lineCount) {
493    
494                    if (Validator.isNull(s)) {
495                            return;
496                    }
497    
498                    boolean containsAndOrOperator = (s.contains("&&") || s.contains("||"));
499    
500                    boolean containsCompareOperator =
501                            (s.contains(" == ") || s.contains(" != ") || s.contains(" < ") ||
502                             s.contains(" > ") || s.contains(" =< ") || s.contains(" => ") ||
503                             s.contains(" <= ") || s.contains(" >= "));
504    
505                    boolean containsMathOperator =
506                            (s.contains(" = ") || s.contains(" - ") || s.contains(" + ") ||
507                             s.contains(" & ") || s.contains(" % ") || s.contains(" * ") ||
508                             s.contains(" / "));
509    
510                    if (containsCompareOperator &&
511                            (containsAndOrOperator ||
512                             (containsMathOperator && !s.contains(StringPool.OPEN_BRACKET)))) {
513    
514                            _sourceFormatterHelper.printError(
515                                    fileName, "missing parentheses: " + fileName + " " + lineCount);
516                    }
517            }
518    
519            private static boolean _checkTaglibVulnerability(
520                    String jspContent, String vulnerability) {
521    
522                    int pos1 = -1;
523    
524                    do {
525                            pos1 = jspContent.indexOf(vulnerability, pos1 + 1);
526    
527                            if (pos1 != -1) {
528                                    int pos2 = jspContent.lastIndexOf(CharPool.LESS_THAN, pos1);
529    
530                                    while ((pos2 > 0) &&
531                                               (jspContent.charAt(pos2 + 1) == CharPool.PERCENT)) {
532    
533                                            pos2 = jspContent.lastIndexOf(CharPool.LESS_THAN, pos2 - 1);
534                                    }
535    
536                                    String tagContent = jspContent.substring(pos2, pos1);
537    
538                                    if (!tagContent.startsWith("<aui:") &&
539                                            !tagContent.startsWith("<liferay-portlet:") &&
540                                            !tagContent.startsWith("<liferay-util:") &&
541                                            !tagContent.startsWith("<portlet:")) {
542    
543                                            return true;
544                                    }
545                            }
546                    }
547                    while (pos1 != -1);
548    
549                    return false;
550            }
551    
552            private static void _checkXSS(String fileName, String jspContent) {
553                    Matcher matcher = _xssPattern.matcher(jspContent);
554    
555                    while (matcher.find()) {
556                            boolean xssVulnerable = false;
557    
558                            String jspVariable = matcher.group(1);
559    
560                            String anchorVulnerability = " href=\"<%= " + jspVariable + " %>";
561    
562                            if (_checkTaglibVulnerability(jspContent, anchorVulnerability)) {
563                                    xssVulnerable = true;
564                            }
565    
566                            String inputVulnerability = " value=\"<%= " + jspVariable + " %>";
567    
568                            if (_checkTaglibVulnerability(jspContent, inputVulnerability)) {
569                                    xssVulnerable = true;
570                            }
571    
572                            String inlineStringVulnerability1 = "'<%= " + jspVariable + " %>";
573    
574                            if (jspContent.contains(inlineStringVulnerability1)) {
575                                    xssVulnerable = true;
576                            }
577    
578                            String inlineStringVulnerability2 = "(\"<%= " + jspVariable + " %>";
579    
580                            if (jspContent.contains(inlineStringVulnerability2)) {
581                                    xssVulnerable = true;
582                            }
583    
584                            String inlineStringVulnerability3 = " \"<%= " + jspVariable + " %>";
585    
586                            if (jspContent.contains(inlineStringVulnerability3)) {
587                                    xssVulnerable = true;
588                            }
589    
590                            String documentIdVulnerability = ".<%= " + jspVariable + " %>";
591    
592                            if (jspContent.contains(documentIdVulnerability)) {
593                                    xssVulnerable = true;
594                            }
595    
596                            if (xssVulnerable) {
597                                    _sourceFormatterHelper.printError(
598                                            fileName, "(xss): " + fileName + " (" + jspVariable + ")");
599                            }
600                    }
601            }
602    
603            private static String _fixAntXMLProjectName(
604                            String basedir, String fileName, String content)
605                    throws IOException {
606    
607                    int x = 0;
608    
609                    if (fileName.endsWith("-ext/build.xml")) {
610                            x = fileName.indexOf("ext/");
611    
612                            if (x == -1) {
613                                    x = 0;
614                            }
615                            else {
616                                    x = x + 4;
617                            }
618                    }
619                    else if (fileName.endsWith("-hook/build.xml")) {
620                            x = fileName.indexOf("hooks/");
621    
622                            if (x == -1) {
623                                    x = 0;
624                            }
625                            else {
626                                    x = x + 6;
627                            }
628                    }
629                    else if (fileName.endsWith("-layouttpl/build.xml")) {
630                            x = fileName.indexOf("layouttpl/");
631    
632                            if (x == -1) {
633                                    x = 0;
634                            }
635                            else {
636                                    x = x + 10;
637                            }
638                    }
639                    else if (fileName.endsWith("-portlet/build.xml")) {
640                            x = fileName.indexOf("portlets/");
641    
642                            if (x == -1) {
643                                    x = 0;
644                            }
645                            else {
646                                    x = x + 9;
647                            }
648                    }
649                    else if (fileName.endsWith("-theme/build.xml")) {
650                            x = fileName.indexOf("themes/");
651    
652                            if (x == -1) {
653                                    x = 0;
654                            }
655                            else {
656                                    x = x + 7;
657                            }
658                    }
659                    else if (fileName.endsWith("-web/build.xml") &&
660                                     !fileName.endsWith("/ext-web/build.xml")) {
661    
662                            x = fileName.indexOf("webs/");
663    
664                            if (x == -1) {
665                                    x = 0;
666                            }
667                            else {
668                                    x = x + 5;
669                            }
670                    }
671                    else {
672                            return content;
673                    }
674    
675                    int y = fileName.indexOf("/", x);
676    
677                    String correctProjectElementText =
678                            "<project name=\"" + fileName.substring(x, y) + "\"";
679    
680                    if (!content.contains(correctProjectElementText)) {
681                            x = content.indexOf("<project name=\"");
682    
683                            y = content.indexOf("\"", x) + 1;
684                            y = content.indexOf("\"", y) + 1;
685    
686                            content =
687                                    content.substring(0, x) + correctProjectElementText +
688                                            content.substring(y);
689    
690                            _sourceFormatterHelper.printError(
691                                    fileName, fileName + " has an incorrect project name");
692    
693                            _fileUtil.write(basedir + fileName, content);
694                    }
695    
696                    return content;
697            }
698    
699            private static String _fixDataAccessConnection(
700                    String className, String content) {
701    
702                    int x = content.indexOf("package ");
703    
704                    int y = content.indexOf(CharPool.SEMICOLON, x);
705    
706                    if ((x == -1) || (y == -1)) {
707                            return content;
708                    }
709    
710                    String packageName = content.substring(x + 8, y);
711    
712                    if (!packageName.startsWith("com.liferay.portal.kernel.upgrade") &&
713                            !packageName.startsWith("com.liferay.portal.kernel.verify") &&
714                            !packageName.startsWith("com.liferay.portal.upgrade") &&
715                            !packageName.startsWith("com.liferay.portal.verify")) {
716    
717                            return content;
718                    }
719    
720                    content = StringUtil.replace(
721                            content, "DataAccess.getConnection",
722                            "DataAccess.getUpgradeOptimizedConnection");
723    
724                    return content;
725            }
726    
727            private static String _fixSessionKey(
728                    String fileName, String content, Pattern pattern) {
729    
730                    Matcher matcher = pattern.matcher(content);
731    
732                    if (!matcher.find()) {
733                            return content;
734                    }
735    
736                    String newContent = content;
737    
738                    do {
739                            String match = matcher.group();
740    
741                            int x = -1;
742    
743                            if (pattern.equals(_sessionKeyPattern)) {
744                                    x = match.indexOf(StringPool.COMMA);
745                            }
746                            else if (pattern.equals(_taglibSessionKeyPattern)) {
747                                    x = match.indexOf("key=");
748                            }
749    
750                            String substring = match.substring(x + 1).trim();
751    
752                            String quote = StringPool.BLANK;
753    
754                            if (substring.startsWith(StringPool.APOSTROPHE)) {
755                                    quote = StringPool.APOSTROPHE;
756                            }
757                            else if (substring.startsWith(StringPool.QUOTE)) {
758                                    quote = StringPool.QUOTE;
759                            }
760                            else {
761                                    continue;
762                            }
763    
764                            int y = match.indexOf(quote, x + 1);
765                            int z = match.indexOf(quote, y + 1);
766    
767                            if ((x == -1) || (y == -1) || (z == -1)) {
768                                    continue;
769                            }
770    
771                            String prefix = match.substring(0, y + 1);
772                            String suffix = match.substring(z);
773                            String oldKey = match.substring(y + 1, z);
774    
775                            for (char c : oldKey.toCharArray()) {
776                                    if (!Validator.isChar(c) || !Validator.isDigit(c) ||
777                                            (c != CharPool.DASH) || (c != CharPool.UNDERLINE)) {
778    
779                                            continue;
780                                    }
781                            }
782    
783                            String newKey = TextFormatter.format(oldKey, TextFormatter.O);
784    
785                            newKey = TextFormatter.format(newKey, TextFormatter.M);
786    
787                            if (newKey.equals(oldKey)) {
788                                    continue;
789                            }
790    
791                            String oldSub = prefix.concat(oldKey).concat(suffix);
792                            String newSub = prefix.concat(newKey).concat(suffix);
793    
794                            newContent = StringUtil.replaceFirst(newContent, oldSub, newSub);
795                    }
796                    while (matcher.find());
797    
798                    return newContent;
799            }
800    
801            private static void _formatAntXML() throws DocumentException, IOException {
802                    String basedir = "./";
803    
804                    DirectoryScanner directoryScanner = new DirectoryScanner();
805    
806                    directoryScanner.setBasedir(basedir);
807                    directoryScanner.setIncludes(new String[] {"**\\b*.xml"});
808                    directoryScanner.setExcludes(new String[] {"**\\tools\\**"});
809    
810                    List<String> fileNames = _sourceFormatterHelper.scanForFiles(
811                            directoryScanner);
812    
813                    for (String fileName : fileNames) {
814                            File file = new File(basedir + fileName);
815    
816                            String content = _fileUtil.read(file);
817    
818                            String newContent = _trimContent(content);
819    
820                            newContent = _fixAntXMLProjectName(basedir, fileName, newContent);
821    
822                            Document document = _saxReaderUtil.read(newContent);
823    
824                            Element rootElement = document.getRootElement();
825    
826                            String previousName = StringPool.BLANK;
827    
828                            List<Element> targetElements = rootElement.elements("target");
829    
830                            for (Element targetElement : targetElements) {
831                                    String name = targetElement.attributeValue("name");
832    
833                                    if (name.equals("Test")) {
834                                            name = name.toLowerCase();
835                                    }
836    
837                                    if (name.compareTo(previousName) < -1) {
838                                            _sourceFormatterHelper.printError(
839                                                    fileName,
840                                                    fileName + " has an unordered target " + name);
841    
842                                            break;
843                                    }
844    
845                                    previousName = name;
846                            }
847    
848                            if ((newContent != null) && !content.equals(newContent)) {
849                                    _fileUtil.write(file, newContent);
850    
851                                    _sourceFormatterHelper.printError(fileName, file);
852                            }
853                    }
854            }
855    
856            private static void _formatDDLStructuresXML()
857                    throws DocumentException, IOException {
858    
859                    String basedir =
860                            "./portal-impl/src/com/liferay/portal/events/dependencies/";
861    
862                    if (!_fileUtil.exists(basedir)) {
863                            return;
864                    }
865    
866                    DirectoryScanner directoryScanner = new DirectoryScanner();
867    
868                    directoryScanner.setBasedir(basedir);
869                    directoryScanner.setIncludes(new String[] {"**\\*structures.xml"});
870    
871                    List<String> fileNames = _sourceFormatterHelper.scanForFiles(
872                            directoryScanner);
873    
874                    for (String fileName : fileNames) {
875                            File file = new File(basedir + fileName);
876    
877                            String content = _fileUtil.read(file);
878    
879                            String newContent = _trimContent(content);
880    
881                            newContent = _formatDDLStructuresXML(content);
882    
883                            if ((newContent != null) && !content.equals(newContent)) {
884                                    _fileUtil.write(file, newContent);
885    
886                                    _sourceFormatterHelper.printError(fileName, file);
887                            }
888                    }
889            }
890    
891            private static String _formatDDLStructuresXML(String content)
892                    throws DocumentException, IOException {
893    
894                    Document document = _saxReaderUtil.read(content);
895    
896                    Element rootElement = document.getRootElement();
897    
898                    rootElement.sortAttributes(true);
899    
900                    rootElement.sortElementsByChildElement("structure", "name");
901    
902                    List<Element> structureElements = rootElement.elements("structure");
903    
904                    for (Element structureElement : structureElements) {
905                            Element structureRootElement = structureElement.element("root");
906    
907                            structureRootElement.sortElementsByAttribute(
908                                    "dynamic-element", "name");
909    
910                            List<Element> dynamicElementElements =
911                                    structureRootElement.elements("dynamic-element");
912    
913                            for (Element dynamicElementElement : dynamicElementElements) {
914                                    Element metaDataElement = dynamicElementElement.element(
915                                            "meta-data");
916    
917                                    metaDataElement.sortElementsByAttribute("entry", "name");
918                            }
919                    }
920    
921                    return document.formattedString();
922            }
923    
924            private static void _formatFriendlyURLRoutesXML()
925                    throws DocumentException, IOException {
926    
927                    String basedir = "./";
928    
929                    DirectoryScanner directoryScanner = new DirectoryScanner();
930    
931                    directoryScanner.setBasedir(basedir);
932                    directoryScanner.setIncludes(new String[] {"**\\*routes.xml"});
933                    directoryScanner.setExcludes(
934                            new String[] {"**\\classes\\**", "**\\bin\\**"});
935    
936                    List<String> fileNames = _sourceFormatterHelper.scanForFiles(
937                            directoryScanner);
938    
939                    for (String fileName : fileNames) {
940                            File file = new File(basedir + fileName);
941    
942                            String content = _fileUtil.read(file);
943    
944                            if (content.contains("<!-- SourceFormatter.Ignore -->")) {
945                                    continue;
946                            }
947    
948                            String newContent = _trimContent(content);
949    
950                            newContent = _formatFriendlyURLRoutesXML(content);
951    
952                            if ((newContent != null) && !content.equals(newContent)) {
953                                    _fileUtil.write(file, newContent);
954    
955                                    _sourceFormatterHelper.printError(fileName, file);
956                            }
957                    }
958            }
959    
960            private static String _formatFriendlyURLRoutesXML(String content)
961                    throws DocumentException {
962    
963                    Document document = _saxReaderUtil.read(content);
964    
965                    Element rootElement = document.getRootElement();
966    
967                    List<ComparableRoute> comparableRoutes =
968                            new ArrayList<ComparableRoute>();
969    
970                    for (Element routeElement : rootElement.elements("route")) {
971                            String pattern = routeElement.elementText("pattern");
972    
973                            ComparableRoute comparableRoute = new ComparableRoute(pattern);
974    
975                            for (Element generatedParameterElement :
976                                            routeElement.elements("generated-parameter")) {
977    
978                                    String name = generatedParameterElement.attributeValue("name");
979                                    String value = generatedParameterElement.getText();
980    
981                                    comparableRoute.addGeneratedParameter(name, value);
982                            }
983    
984                            for (Element ignoredParameterElement :
985                                            routeElement.elements("ignored-parameter")) {
986    
987                                    String name = ignoredParameterElement.attributeValue("name");
988    
989                                    comparableRoute.addIgnoredParameter(name);
990                            }
991    
992                            for (Element implicitParameterElement :
993                                            routeElement.elements("implicit-parameter")) {
994    
995                                    String name = implicitParameterElement.attributeValue("name");
996                                    String value = implicitParameterElement.getText();
997    
998                                    comparableRoute.addImplicitParameter(name, value);
999                            }
1000    
1001                            for (Element overriddenParameterElement :
1002                                            routeElement.elements("overridden-parameter")) {
1003    
1004                                    String name = overriddenParameterElement.attributeValue("name");
1005                                    String value = overriddenParameterElement.getText();
1006    
1007                                    comparableRoute.addOverriddenParameter(name, value);
1008                            }
1009    
1010                            comparableRoutes.add(comparableRoute);
1011                    }
1012    
1013                    Collections.sort(comparableRoutes);
1014    
1015                    StringBundler sb = new StringBundler();
1016    
1017                    sb.append("<?xml version=\"1.0\"?>\n");
1018                    sb.append("<!DOCTYPE routes PUBLIC \"-//Liferay//DTD Friendly URL ");
1019                    sb.append("Routes 6.2.0//EN\" \"http://www.liferay.com/dtd/");
1020                    sb.append("liferay-friendly-url-routes_6_2_0.dtd\">\n\n<routes>\n");
1021    
1022                    for (ComparableRoute comparableRoute : comparableRoutes) {
1023                            sb.append("\t<route>\n");
1024                            sb.append("\t\t<pattern>");
1025                            sb.append(comparableRoute.getPattern());
1026                            sb.append("</pattern>\n");
1027    
1028                            Map<String, String> generatedParameters =
1029                                    comparableRoute.getGeneratedParameters();
1030    
1031                            for (Map.Entry<String, String> entry :
1032                                            generatedParameters.entrySet()) {
1033    
1034                                    sb.append("\t\t<generated-parameter name=\"");
1035                                    sb.append(entry.getKey());
1036                                    sb.append("\">");
1037                                    sb.append(entry.getValue());
1038                                    sb.append("</generated-parameter>\n");
1039                            }
1040    
1041                            Set<String> ignoredParameters =
1042                                    comparableRoute.getIgnoredParameters();
1043    
1044                            for (String entry : ignoredParameters) {
1045                                    sb.append("\t\t<ignored-parameter name=\"");
1046                                    sb.append(entry);
1047                                    sb.append("\" />\n");
1048                            }
1049    
1050                            Map<String, String> implicitParameters =
1051                                    comparableRoute.getImplicitParameters();
1052    
1053                            for (Map.Entry<String, String> entry :
1054                                            implicitParameters.entrySet()) {
1055    
1056                                    sb.append("\t\t<implicit-parameter name=\"");
1057                                    sb.append(entry.getKey());
1058                                    sb.append("\">");
1059                                    sb.append(entry.getValue());
1060                                    sb.append("</implicit-parameter>\n");
1061                            }
1062    
1063                            Map<String, String> overriddenParameters =
1064                                    comparableRoute.getOverriddenParameters();
1065    
1066                            for (Map.Entry<String, String> entry :
1067                                            overriddenParameters.entrySet()) {
1068    
1069                                    sb.append("\t\t<overridden-parameter name=\"");
1070                                    sb.append(entry.getKey());
1071                                    sb.append("\">");
1072                                    sb.append(entry.getValue());
1073                                    sb.append("</overridden-parameter>\n");
1074                            }
1075    
1076                            sb.append("\t</route>\n");
1077                    }
1078    
1079                    sb.append("</routes>");
1080    
1081                    return sb.toString();
1082            }
1083    
1084            private static void _formatFTL() throws IOException {
1085                    String basedir = "./";
1086    
1087                    DirectoryScanner directoryScanner = new DirectoryScanner();
1088    
1089                    directoryScanner.setBasedir(basedir);
1090                    directoryScanner.setIncludes(new String[] {"**\\*.ftl"});
1091                    directoryScanner.setExcludes(
1092                            new String[] {
1093                                    "**\\journal\\dependencies\\template.ftl",
1094                                    "**\\servicebuilder\\dependencies\\props.ftl"
1095                            });
1096    
1097                    List<String> fileNames = _sourceFormatterHelper.scanForFiles(
1098                            directoryScanner);
1099    
1100                    for (String fileName : fileNames) {
1101                            File file = new File(basedir + fileName);
1102    
1103                            String content = _fileUtil.read(file);
1104    
1105                            String newContent = _trimContent(content);
1106    
1107                            if ((newContent != null) && !content.equals(newContent)) {
1108                                    _fileUtil.write(file, newContent);
1109    
1110                                    _sourceFormatterHelper.printError(fileName, file);
1111                            }
1112                    }
1113            }
1114    
1115            private static String _formatImports(String imports, int classStartPos)
1116                    throws IOException {
1117    
1118                    if (imports.contains("/*") || imports.contains("*/") ||
1119                            imports.contains("//")) {
1120    
1121                            return imports + "\n";
1122                    }
1123    
1124                    List<String> importsList = new ArrayList<String>();
1125    
1126                    UnsyncBufferedReader unsyncBufferedReader = new UnsyncBufferedReader(
1127                            new UnsyncStringReader(imports));
1128    
1129                    String line = null;
1130    
1131                    while ((line = unsyncBufferedReader.readLine()) != null) {
1132                            if ((line.contains("import=") || line.contains("import ")) &&
1133                                    !importsList.contains(line)) {
1134    
1135                                    importsList.add(line);
1136                            }
1137                    }
1138    
1139                    importsList = ListUtil.sort(importsList);
1140    
1141                    StringBundler sb = new StringBundler();
1142    
1143                    String temp = null;
1144    
1145                    for (int i = 0; i < importsList.size(); i++) {
1146                            String s = importsList.get(i);
1147    
1148                            int pos = s.indexOf(".");
1149    
1150                            pos = s.indexOf(".", pos + 1);
1151    
1152                            if (pos == -1) {
1153                                    pos = s.indexOf(".");
1154                            }
1155    
1156                            String packageLevel = s.substring(classStartPos, pos);
1157    
1158                            if ((i != 0) && !packageLevel.equals(temp)) {
1159                                    sb.append("\n");
1160                            }
1161    
1162                            temp = packageLevel;
1163    
1164                            sb.append(s);
1165                            sb.append("\n");
1166                    }
1167    
1168                    return sb.toString();
1169            }
1170    
1171            private static void _formatJava() throws IOException {
1172                    String copyright = _getCopyright();
1173                    String oldCopyright = _getOldCopyright();
1174    
1175                    boolean portalJavaFiles = true;
1176    
1177                    Collection<String> fileNames = null;
1178    
1179                    if (_portalSource) {
1180                            fileNames = _getPortalJavaFiles();
1181    
1182                            _javaTermSortExclusions = _getPortalExclusionsProperties(
1183                                    "source_formatter_javaterm_sort_exclusions.properties");
1184                            _lineLengthExclusions = _getPortalExclusionsProperties(
1185                                    "source_formatter_line_length_exclusions.properties");
1186                    }
1187                    else {
1188                            portalJavaFiles = false;
1189    
1190                            fileNames = _getPluginJavaFiles();
1191    
1192                            _javaTermSortExclusions = _getPluginExclusionsProperties(
1193                                    "source_formatter_javaterm_sort_exclusions.properties");
1194                            _lineLengthExclusions = _getPluginExclusionsProperties(
1195                                    "source_formatter_line_length_exclusions.properties");
1196                    }
1197    
1198                    for (String fileName : fileNames) {
1199                            File file = new File(fileName);
1200    
1201                            String content = _fileUtil.read(file);
1202    
1203                            if (_isGenerated(content)) {
1204                                    continue;
1205                            }
1206    
1207                            String className = file.getName();
1208    
1209                            className = className.substring(0, className.length() - 5);
1210    
1211                            String packagePath = fileName;
1212    
1213                            int packagePathX = packagePath.indexOf(
1214                                    File.separator + "src" + File.separator);
1215                            int packagePathY = packagePath.lastIndexOf(File.separator);
1216    
1217                            if ((packagePathX + 5) >= packagePathY) {
1218                                    packagePath = StringPool.BLANK;
1219                            }
1220                            else {
1221                                    packagePath = packagePath.substring(
1222                                            packagePathX + 5, packagePathY);
1223                            }
1224    
1225                            packagePath = StringUtil.replace(
1226                                    packagePath, File.separator, StringPool.PERIOD);
1227    
1228                            if (packagePath.endsWith(".model")) {
1229                                    if (content.contains("extends " + className + "Model")) {
1230                                            continue;
1231                                    }
1232                            }
1233    
1234                            String newContent = content;
1235    
1236                            if (newContent.contains("$\n */")) {
1237                                    _sourceFormatterHelper.printError(fileName, "*: " + fileName);
1238    
1239                                    newContent = StringUtil.replace(
1240                                            newContent, "$\n */", "$\n *\n */");
1241                            }
1242    
1243                            if ((oldCopyright != null) && newContent.contains(oldCopyright)) {
1244                                    newContent = StringUtil.replace(
1245                                            newContent, oldCopyright, copyright);
1246    
1247                                    _sourceFormatterHelper.printError(
1248                                            fileName, "old (c): " + fileName);
1249                            }
1250    
1251                            if (!newContent.contains(copyright)) {
1252                                    String customCopyright = _getCustomCopyright(file);
1253    
1254                                    if (Validator.isNull(customCopyright) ||
1255                                            !newContent.contains(customCopyright)) {
1256    
1257                                            _sourceFormatterHelper.printError(
1258                                                    fileName, "(c): " + fileName);
1259                                    }
1260                            }
1261    
1262                            if (newContent.contains(className + ".java.html")) {
1263                                    _sourceFormatterHelper.printError(
1264                                            fileName, "Java2HTML: " + fileName);
1265                            }
1266    
1267                            if (newContent.contains(" * @author Raymond Aug") &&
1268                                    !newContent.contains(" * @author Raymond Aug\u00e9")) {
1269    
1270                                    newContent = newContent.replaceFirst(
1271                                            "Raymond Aug.++", "Raymond Aug\u00e9");
1272    
1273                                    _sourceFormatterHelper.printError(
1274                                            fileName, "UTF-8: " + fileName);
1275                            }
1276    
1277                            newContent = _fixDataAccessConnection(className, newContent);
1278                            newContent = _fixSessionKey(
1279                                    fileName, newContent, _sessionKeyPattern);
1280    
1281                            newContent = StringUtil.replace(
1282                                    newContent,
1283                                    new String[] {
1284                                            "com.liferay.portal.PortalException",
1285                                            "com.liferay.portal.SystemException",
1286                                            "com.liferay.util.LocalizationUtil",
1287                                            "private static final Log _log"
1288                                    },
1289                                    new String[] {
1290                                            "com.liferay.portal.kernel.exception.PortalException",
1291                                            "com.liferay.portal.kernel.exception.SystemException",
1292                                            "com.liferay.portal.kernel.util.LocalizationUtil",
1293                                            "private static Log _log"
1294                                    });
1295    
1296                            newContent = stripJavaImports(newContent, packagePath, className);
1297    
1298                            newContent = StringUtil.replace(
1299                                    newContent,
1300                                    new String[] {
1301                                            ";\n/**", "\t/*\n\t *", "catch(", "else{", "if(", "for(",
1302                                            "while(", "List <", "){\n", "]{\n", "\n\n\n"
1303                                    },
1304                                    new String[] {
1305                                            ";\n\n/**", "\t/**\n\t *", "catch (", "else {", "if (",
1306                                            "for (", "while (", "List<", ") {\n", "] {\n", "\n\n"
1307                                    });
1308    
1309                            if (newContent.contains("*/\npackage ")) {
1310                                    _sourceFormatterHelper.printError(
1311                                            fileName, "package: " + fileName);
1312                            }
1313    
1314                            if (!newContent.endsWith("\n\n}") && !newContent.endsWith("{\n}")) {
1315                                    _sourceFormatterHelper.printError(fileName, "}: " + fileName);
1316                            }
1317    
1318                            if (portalJavaFiles && !className.equals("BaseServiceImpl") &&
1319                                    className.endsWith("ServiceImpl") &&
1320                                    newContent.contains("ServiceUtil.")) {
1321    
1322                                    _sourceFormatterHelper.printError(
1323                                            fileName, "ServiceUtil: " + fileName);
1324                            }
1325    
1326                            if (!className.equals("DeepNamedValueScanner") &&
1327                                    !className.equals("ProxyUtil") &&
1328                                    newContent.contains("import java.lang.reflect.Proxy;")) {
1329    
1330                                    _sourceFormatterHelper.printError(
1331                                            fileName, "Proxy: " + fileName);
1332                            }
1333    
1334                            // LPS-28266
1335    
1336                            for (int pos1 = -1;;) {
1337                                    pos1 = newContent.indexOf(StringPool.TAB + "try {", pos1 + 1);
1338    
1339                                    if (pos1 == -1) {
1340                                            break;
1341                                    }
1342    
1343                                    int pos2 = newContent.indexOf(
1344                                            StringPool.TAB + "try {", pos1 + 1);
1345                                    int pos3 = newContent.indexOf("\"select count(", pos1);
1346    
1347                                    if ((pos2 != -1) && (pos3 != -1) && (pos2 < pos3)) {
1348                                            continue;
1349                                    }
1350    
1351                                    int pos4 = newContent.indexOf("rs.getLong(1)", pos1);
1352                                    int pos5 = newContent.indexOf(
1353                                            StringPool.TAB + "finally {", pos1);
1354    
1355                                    if ((pos3 == -1) || (pos4 == -1) || (pos5 == -1)) {
1356                                            break;
1357                                    }
1358    
1359                                    if ((pos3 < pos4) && (pos4 < pos5)) {
1360                                            _sourceFormatterHelper.printError(
1361                                                    fileName, "Use getInt(1) for count: " + fileName);
1362                                    }
1363                            }
1364    
1365                            _checkLanguageKeys(fileName, newContent, _languageKeyPattern);
1366    
1367                            String oldContent = newContent;
1368    
1369                            for (;;) {
1370                                    newContent = _formatJava(fileName, oldContent);
1371    
1372                                    if (oldContent.equals(newContent)) {
1373                                            break;
1374                                    }
1375    
1376                                    oldContent = newContent;
1377                            }
1378    
1379                            if ((newContent != null) && !content.equals(newContent)) {
1380                                    _fileUtil.write(file, newContent);
1381    
1382                                    _sourceFormatterHelper.printError(fileName, file);
1383                            }
1384                    }
1385            }
1386    
1387            private static String _formatJava(String fileName, String content)
1388                    throws IOException {
1389    
1390                    StringBundler sb = new StringBundler();
1391    
1392                    UnsyncBufferedReader unsyncBufferedReader = new UnsyncBufferedReader(
1393                            new UnsyncStringReader(content));
1394    
1395                    int index = 0;
1396                    int lineCount = 0;
1397    
1398                    String line = null;
1399    
1400                    String previousLine = StringPool.BLANK;
1401    
1402                    int lineToSkipIfEmpty = 0;
1403    
1404                    String javaTermName = null;
1405                    int javaTermPos = -1;
1406                    int javaTermType = 0;
1407    
1408                    int nextJavaTermPos = -1;
1409                    int nextJavaTermType = 0;
1410    
1411                    String previousJavaTermName = null;
1412                    int previousJavaTermPos = -1;
1413                    int previousJavaTermType = 0;
1414    
1415                    List<String> parameterTypes = new ArrayList<String>();
1416                    List<String> previousParameterTypes = null;
1417    
1418                    int lastCommentOrAnnotationPos = -1;
1419    
1420                    boolean hasSameConstructorOrMethodName = false;
1421                    boolean readParameterTypes = false;
1422    
1423                    boolean hasUnsortedJavaTerms = false;
1424    
1425                    String ifClause = StringPool.BLANK;
1426    
1427                    String packageName = StringPool.BLANK;
1428    
1429                    while ((line = unsyncBufferedReader.readLine()) != null) {
1430                            lineCount++;
1431    
1432                            line = _trimLine(line);
1433    
1434                            if (Validator.isNull(line)) {
1435                                    lastCommentOrAnnotationPos = -1;
1436                            }
1437    
1438                            line = StringUtil.replace(
1439                                    line,
1440                                    new String[] {
1441                                            "* Copyright (c) 2000-2011 Liferay, Inc."
1442                                    },
1443                                    new String[] {
1444                                            "* Copyright (c) 2000-2012 Liferay, Inc."
1445                                    });
1446    
1447                            if (line.startsWith("package ")) {
1448                                    packageName = line.substring(8, line.length() - 1);
1449                            }
1450    
1451                            if (line.startsWith("import ")) {
1452                                    int pos = line.lastIndexOf(StringPool.PERIOD);
1453    
1454                                    if (pos != -1) {
1455                                            String importPackageName = line.substring(7, pos);
1456    
1457                                            if (importPackageName.equals(packageName)) {
1458                                                    continue;
1459                                            }
1460                                    }
1461                            }
1462    
1463                            if (line.contains(StringPool.TAB + "for (") && line.contains(":") &&
1464                                    !line.contains(" :")) {
1465    
1466                                    line = StringUtil.replace(line, ":" , " :");
1467                            }
1468    
1469                            line = _replacePrimitiveWrapperInstantiation(
1470                                    fileName, line, lineCount);
1471    
1472                            String trimmedLine = StringUtil.trimLeading(line);
1473    
1474                            if (trimmedLine.startsWith(StringPool.EQUAL)) {
1475                                    _sourceFormatterHelper.printError(
1476                                            fileName, "equal: " + fileName + " " + lineCount);
1477                            }
1478    
1479                            if (!trimmedLine.equals("{") && line.endsWith("{") &&
1480                                    !line.endsWith(" {")) {
1481    
1482                                    line = StringUtil.replaceLast(line, "{", " {");
1483                            }
1484    
1485                            line = _sortExceptions(line);
1486    
1487                            if (trimmedLine.startsWith("if (") ||
1488                                    trimmedLine.startsWith("else if (") ||
1489                                    trimmedLine.startsWith("while (") ||
1490                                    Validator.isNotNull(ifClause)) {
1491    
1492                                    if (Validator.isNull(ifClause) ||
1493                                            ifClause.endsWith(StringPool.OPEN_PARENTHESIS)) {
1494    
1495                                            ifClause = ifClause + trimmedLine;
1496                                    }
1497                                    else {
1498                                            ifClause = ifClause + StringPool.SPACE + trimmedLine;
1499                                    }
1500    
1501                                    if (ifClause.endsWith(") {")) {
1502                                            _checkIfClause(ifClause, fileName, lineCount);
1503    
1504                                            ifClause = StringPool.BLANK;
1505                                    }
1506                            }
1507    
1508                            String excluded = null;
1509    
1510                            String fileNameWithForwardSlashes = StringUtil.replace(
1511                                    fileName, "\\", "/");
1512    
1513                            if (line.startsWith(StringPool.TAB + "private ") ||
1514                                    line.startsWith(StringPool.TAB + "protected ") ||
1515                                    line.startsWith(StringPool.TAB + "public ")) {
1516    
1517                                    Tuple tuple = _getJavaTermTuple(line);
1518    
1519                                    if (hasUnsortedJavaTerms) {
1520                                            if (nextJavaTermPos == -1) {
1521                                                    if (lastCommentOrAnnotationPos == -1) {
1522                                                            nextJavaTermPos = index;
1523                                                    }
1524                                                    else {
1525                                                            nextJavaTermPos = lastCommentOrAnnotationPos;
1526                                                    }
1527    
1528                                                    if (tuple != null) {
1529                                                            nextJavaTermType = (Integer)tuple.getObject(1);
1530                                                    }
1531                                            }
1532                                    }
1533                                    else {
1534                                            hasSameConstructorOrMethodName = false;
1535    
1536                                            if (tuple != null) {
1537                                                    javaTermName = (String)tuple.getObject(0);
1538    
1539                                                    if (lastCommentOrAnnotationPos == -1) {
1540                                                            javaTermPos = index;
1541                                                    }
1542                                                    else {
1543                                                            javaTermPos = lastCommentOrAnnotationPos;
1544                                                    }
1545    
1546                                                    if (Validator.isNotNull(javaTermName)) {
1547                                                            javaTermType = (Integer)tuple.getObject(1);
1548    
1549                                                            boolean isConstructorOrMethod =
1550                                                                    _isInJavaTermTypeGroup(
1551                                                                            javaTermType, _TYPE_CONSTRUCTOR) ||
1552                                                                    _isInJavaTermTypeGroup(
1553                                                                            javaTermType, _TYPE_METHOD);
1554    
1555                                                            if (isConstructorOrMethod) {
1556                                                                    readParameterTypes = true;
1557                                                            }
1558    
1559                                                            if (_javaTermSortExclusions != null) {
1560                                                                    excluded = _javaTermSortExclusions.getProperty(
1561                                                                            fileNameWithForwardSlashes + StringPool.AT +
1562                                                                                    lineCount);
1563    
1564                                                                    if (excluded == null) {
1565                                                                            excluded =
1566                                                                                    _javaTermSortExclusions.getProperty(
1567                                                                                            fileNameWithForwardSlashes +
1568                                                                                                    StringPool.AT + javaTermName);
1569                                                                    }
1570    
1571                                                                    if (excluded == null) {
1572                                                                            excluded = 
1573                                                                                    _javaTermSortExclusions.getProperty(
1574                                                                                            fileNameWithForwardSlashes);
1575                                                                    }
1576                                                            }
1577    
1578                                                            if (excluded == null) {
1579                                                                    if (_isInJavaTermTypeGroup(
1580                                                                                    javaTermType,
1581                                                                                    _TYPE_VARIABLE_NOT_FINAL)) {
1582    
1583                                                                            char firstChar = javaTermName.charAt(0);
1584    
1585                                                                            if (firstChar == CharPool.UNDERLINE) {
1586                                                                                    firstChar = javaTermName.charAt(1);
1587                                                                            }
1588    
1589                                                                            if (Character.isUpperCase(firstChar)) {
1590                                                                                    _sourceFormatterHelper.printError(
1591                                                                                            fileName,
1592                                                                                            "final: " + fileName + " " +
1593                                                                                                    lineCount);
1594                                                                            }
1595                                                                    }
1596    
1597                                                                    if (Validator.isNotNull(previousJavaTermName)) {
1598                                                                            if (previousJavaTermType > javaTermType) {
1599                                                                                    hasUnsortedJavaTerms = true;
1600                                                                            }
1601                                                                            else if (previousJavaTermType ==
1602                                                                                                    javaTermType) {
1603    
1604                                                                                    if (isConstructorOrMethod &&
1605                                                                                            previousJavaTermName.equals(
1606                                                                                                    javaTermName)) {
1607    
1608                                                                                            hasSameConstructorOrMethodName =
1609                                                                                                    true;
1610                                                                                    }
1611                                                                                    else if (_hasUnsortedJavaTerms(
1612                                                                                                            fileName,
1613                                                                                                            previousJavaTermName,
1614                                                                                                            javaTermName,
1615                                                                                                            javaTermType)) {
1616    
1617                                                                                            hasUnsortedJavaTerms = true;
1618                                                                                    }
1619                                                                            }
1620                                                                    }
1621                                                            }
1622    
1623                                                            if (!hasUnsortedJavaTerms && !readParameterTypes) {
1624                                                                    previousJavaTermName = javaTermName;
1625                                                                    previousJavaTermPos = javaTermPos;
1626                                                                    previousJavaTermType = javaTermType;
1627                                                            }
1628                                                    }
1629                                            }
1630                                    }
1631                            }
1632                            else if (line.startsWith(StringPool.TAB + "/**") ||
1633                                             line.startsWith(StringPool.TAB + "@")) {
1634    
1635                                    if (lastCommentOrAnnotationPos == -1) {
1636                                            lastCommentOrAnnotationPos = index;
1637                                    }
1638                            }
1639    
1640                            if (readParameterTypes) {
1641                                    parameterTypes = _addParameterTypes(
1642                                            trimmedLine, parameterTypes);
1643    
1644                                    if (trimmedLine.contains(StringPool.CLOSE_PARENTHESIS)) {
1645                                            if (hasSameConstructorOrMethodName) {
1646                                                    if (_hasUnsortedConstructorsOrMethods(
1647                                                                    previousParameterTypes, parameterTypes)) {
1648    
1649                                                            hasUnsortedJavaTerms = true;
1650                                                    }
1651                                            }
1652    
1653                                            readParameterTypes = false;
1654    
1655                                            previousParameterTypes = ListUtil.copy(parameterTypes);
1656    
1657                                            parameterTypes.clear();
1658    
1659                                            if (!hasUnsortedJavaTerms) {
1660                                                    previousJavaTermName = javaTermName;
1661                                                    previousJavaTermPos = javaTermPos;
1662                                                    previousJavaTermType = javaTermType;
1663                                            }
1664                                    }
1665                            }
1666    
1667                            if (!trimmedLine.contains(StringPool.DOUBLE_SLASH) &&
1668                                    !trimmedLine.startsWith(StringPool.STAR)) {
1669    
1670                                    while (trimmedLine.contains(StringPool.TAB)) {
1671                                            line = StringUtil.replaceLast(
1672                                                    line, StringPool.TAB, StringPool.SPACE);
1673    
1674                                            trimmedLine = StringUtil.replaceLast(
1675                                                    trimmedLine, StringPool.TAB, StringPool.SPACE);
1676                                    }
1677    
1678                                    if (line.contains(StringPool.TAB + StringPool.SPACE) &&
1679                                            !previousLine.endsWith("&&") &&
1680                                            !previousLine.endsWith("||") &&
1681                                            !previousLine.contains(StringPool.TAB + "((") &&
1682                                            !previousLine.contains(StringPool.TAB + StringPool.SPACE) &&
1683                                            !previousLine.contains(StringPool.TAB + "implements ") &&
1684                                            !previousLine.contains(StringPool.TAB + "throws ")) {
1685    
1686                                            line = StringUtil.replace(
1687                                                    line, StringPool.TAB + StringPool.SPACE,
1688                                                    StringPool.TAB);
1689                                    }
1690    
1691                                    while (trimmedLine.contains(StringPool.DOUBLE_SPACE) &&
1692                                               !trimmedLine.contains(
1693                                                       StringPool.QUOTE + StringPool.DOUBLE_SPACE) &&
1694                                               !fileName.contains("Test")) {
1695    
1696                                            line = StringUtil.replaceLast(
1697                                                    line, StringPool.DOUBLE_SPACE, StringPool.SPACE);
1698    
1699                                            trimmedLine = StringUtil.replaceLast(
1700                                                    trimmedLine, StringPool.DOUBLE_SPACE, StringPool.SPACE);
1701                                    }
1702    
1703                                    if (!line.contains(StringPool.QUOTE)) {
1704                                            if ((trimmedLine.startsWith("private ") ||
1705                                                     trimmedLine.startsWith("protected ") ||
1706                                                     trimmedLine.startsWith("public ")) &&
1707                                                    line.contains(" (")) {
1708    
1709                                                    line = StringUtil.replace(line, " (", "(");
1710                                            }
1711    
1712                                            if (line.contains(" [")) {
1713                                                    line = StringUtil.replace(line, " [", "[");
1714                                            }
1715    
1716                                            for (int x = -1;;) {
1717                                                    int posComma = line.indexOf(StringPool.COMMA, x + 1);
1718                                                    int posSemicolon = line.indexOf(
1719                                                            StringPool.SEMICOLON, x + 1);
1720    
1721                                                    if ((posComma == -1) && (posSemicolon == -1)) {
1722                                                            break;
1723                                                    }
1724    
1725                                                    x = Math.min(posComma, posSemicolon);
1726    
1727                                                    if (x == -1) {
1728                                                            x = Math.max(posComma, posSemicolon);
1729                                                    }
1730    
1731                                                    if (line.length() > (x + 1)) {
1732                                                            char nextChar = line.charAt(x + 1);
1733    
1734                                                            if ((nextChar != CharPool.APOSTROPHE) &&
1735                                                                    (nextChar != CharPool.CLOSE_PARENTHESIS) &&
1736                                                                    (nextChar != CharPool.SPACE) &&
1737                                                                    (nextChar != CharPool.STAR)) {
1738    
1739                                                                    line = StringUtil.insert(
1740                                                                            line, StringPool.SPACE, x + 1);
1741                                                            }
1742                                                    }
1743    
1744                                                    if (x > 0) {
1745                                                            char previousChar = line.charAt(x - 1);
1746    
1747                                                            if (previousChar == CharPool.SPACE) {
1748                                                                    line = line.substring(0, x - 1).concat(
1749                                                                            line.substring(x));
1750                                                            }
1751                                                    }
1752                                            }
1753                                    }
1754                            }
1755    
1756                            if ((line.contains(" && ") || line.contains(" || ")) &&
1757                                    line.endsWith(StringPool.OPEN_PARENTHESIS)) {
1758    
1759                                    _sourceFormatterHelper.printError(
1760                                            fileName, "line break: " + fileName + " " + lineCount);
1761                            }
1762    
1763                            if (line.contains(StringPool.COMMA) &&
1764                                    !line.contains(StringPool.CLOSE_PARENTHESIS) &&
1765                                    !line.contains(StringPool.GREATER_THAN) &&
1766                                    !line.contains(StringPool.QUOTE) &&
1767                                    line.endsWith(StringPool.OPEN_PARENTHESIS)) {
1768    
1769                                    _sourceFormatterHelper.printError(
1770                                            fileName, "line break: " + fileName + " " + lineCount);
1771                            }
1772    
1773                            if (line.endsWith(" +") || line.endsWith(" -") ||
1774                                    line.endsWith(" *") || line.endsWith(" /")) {
1775    
1776                                    int x = line.indexOf(" = ");
1777    
1778                                    if (x != -1) {
1779                                            int y = line.indexOf(StringPool.QUOTE);
1780    
1781                                            if ((y == -1) || (x < y)) {
1782                                                    _sourceFormatterHelper.printError(
1783                                                            fileName,
1784                                                            "line break: " + fileName + " " + lineCount);
1785                                            }
1786                                    }
1787                            }
1788    
1789                            if (line.contains("    ") && !line.matches("\\s*\\*.*")) {
1790                                    if (!fileName.endsWith("StringPool.java")) {
1791                                            _sourceFormatterHelper.printError(
1792                                                    fileName, "tab: " + fileName + " " + lineCount);
1793                                    }
1794                            }
1795    
1796                            if (line.contains("  {") && !line.matches("\\s*\\*.*")) {
1797                                    _sourceFormatterHelper.printError(
1798                                            fileName, "{:" + fileName + " " + lineCount);
1799                            }
1800    
1801                            excluded = null;
1802    
1803                            if (_lineLengthExclusions != null) {
1804                                    excluded = _lineLengthExclusions.getProperty(
1805                                            fileNameWithForwardSlashes + StringPool.AT + lineCount);
1806    
1807                                    if (excluded == null) {
1808                                            excluded = _lineLengthExclusions.getProperty(
1809                                                    fileNameWithForwardSlashes);
1810                                    }
1811                            }
1812    
1813                            Tuple combinedLines = null;
1814                            int lineLength = _getLineLength(line);
1815    
1816                            if ((excluded == null) &&
1817                                    !line.startsWith("import ") && !line.startsWith("package ") &&
1818                                    !line.matches("\\s*\\*.*")) {
1819    
1820                                    if (fileName.endsWith("Table.java") &&
1821                                            line.contains("String TABLE_SQL_CREATE = ")) {
1822                                    }
1823                                    else if (fileName.endsWith("Table.java") &&
1824                                                     line.contains("String TABLE_SQL_DROP = ")) {
1825                                    }
1826                                    else if (fileName.endsWith("Table.java") &&
1827                                                     line.contains(" index IX_")) {
1828                                    }
1829                                    else {
1830                                            if (lineLength > 80) {
1831                                                    _sourceFormatterHelper.printError(
1832                                                            fileName, "> 80: " + fileName + " " + lineCount);
1833                                            }
1834                                            else {
1835                                                    int lineTabCount = StringUtil.count(
1836                                                            line, StringPool.TAB);
1837                                                    int previousLineTabCount = StringUtil.count(
1838                                                            previousLine, StringPool.TAB);
1839    
1840                                                    if (previousLine.endsWith(StringPool.COMMA) &&
1841                                                            previousLine.contains(
1842                                                                    StringPool.OPEN_PARENTHESIS) &&
1843                                                            !previousLine.contains("for (") &&
1844                                                            (lineTabCount > previousLineTabCount)) {
1845    
1846                                                            _sourceFormatterHelper.printError(
1847                                                                    fileName,
1848                                                                    "line break: " + fileName + " " + lineCount);
1849                                                    }
1850    
1851                                                    if (Validator.isNotNull(trimmedLine) &&
1852                                                            ((previousLine.endsWith(StringPool.COLON) &&
1853                                                              previousLine.contains(StringPool.TAB + "for ")) ||
1854                                                             (previousLine.endsWith(
1855                                                                     StringPool.OPEN_PARENTHESIS) &&
1856                                                              previousLine.contains(StringPool.TAB + "if "))) &&
1857                                                            ((previousLineTabCount + 2) != lineTabCount)) {
1858    
1859                                                            _sourceFormatterHelper.printError(
1860                                                                    fileName,
1861                                                                    "line break: " + fileName + " " + lineCount);
1862                                                    }
1863    
1864                                                    if (previousLine.endsWith(StringPool.PERIOD)) {
1865                                                            int x = trimmedLine.indexOf(
1866                                                                    StringPool.OPEN_PARENTHESIS);
1867    
1868                                                            if ((x != -1) &&
1869                                                                    ((_getLineLength(previousLine) + x) < 80) &&
1870                                                                    (trimmedLine.endsWith(
1871                                                                            StringPool.OPEN_PARENTHESIS) ||
1872                                                                     (trimmedLine.charAt(x + 1) !=
1873                                                                             CharPool.CLOSE_PARENTHESIS))) {
1874    
1875                                                                    _sourceFormatterHelper.printError(
1876                                                                            fileName,
1877                                                                            "line break: " + fileName + " " +
1878                                                                                    lineCount);
1879                                                            }
1880                                                    }
1881    
1882                                                    combinedLines = _getCombinedLines(
1883                                                            trimmedLine, previousLine, lineTabCount,
1884                                                            previousLineTabCount);
1885                                            }
1886                                    }
1887                            }
1888    
1889                            if (combinedLines != null) {
1890                                    previousLine = (String)combinedLines.getObject(0);
1891    
1892                                    if (combinedLines.getSize() > 1) {
1893                                            String linePart = (String)combinedLines.getObject(1);
1894                                            boolean addToPreviousLine =
1895                                                    (Boolean)combinedLines.getObject(2);
1896    
1897                                            if (addToPreviousLine) {
1898                                                    previousLine = previousLine + linePart;
1899                                                    line = StringUtil.replaceFirst(
1900                                                            line, linePart, StringPool.BLANK);
1901                                            }
1902                                            else {
1903                                                    if (((linePart.length() + lineLength) <= 80) &&
1904                                                            (line.endsWith(StringPool.OPEN_CURLY_BRACE) ||
1905                                                             line.endsWith(StringPool.SEMICOLON))) {
1906    
1907                                                            previousLine = StringUtil.replaceLast(
1908                                                                    previousLine, linePart, StringPool.BLANK);
1909    
1910                                                            line = StringUtil.replaceLast(
1911                                                                    line, StringPool.TAB,
1912                                                                    StringPool.TAB + linePart);
1913                                                    }
1914                                                    else {
1915                                                            _sourceFormatterHelper.printError(
1916                                                                    fileName,
1917                                                                    "line break: " + fileName + " " + lineCount);
1918                                                    }
1919                                            }
1920    
1921                                            sb.append(previousLine);
1922                                            sb.append("\n");
1923    
1924                                            previousLine = line;
1925                                    }
1926                                    else if (line.endsWith(StringPool.OPEN_CURLY_BRACE) &&
1927                                                     !previousLine.contains(" class ")) {
1928    
1929                                            lineToSkipIfEmpty = lineCount + 1;
1930                                    }
1931                            }
1932                            else {
1933                                    if ((lineCount > 1) &&
1934                                            (Validator.isNotNull(previousLine) ||
1935                                             (lineToSkipIfEmpty != (lineCount - 1)))) {
1936    
1937                                            sb.append(previousLine);
1938    
1939                                            if (Validator.isNotNull(previousLine) &&
1940                                                    Validator.isNotNull(trimmedLine) &&
1941                                                    !previousLine.contains("/*")) {
1942    
1943                                                    String trimmedPreviousLine = StringUtil.trimLeading(
1944                                                            previousLine);
1945    
1946                                                    if ((trimmedPreviousLine.startsWith("// ") &&
1947                                                             !trimmedLine.startsWith("// ")) ||
1948                                                            (!trimmedPreviousLine.startsWith("// ") &&
1949                                                             trimmedLine.startsWith("// "))) {
1950    
1951                                                            sb.append("\n");
1952                                                    }
1953                                                    else if (previousLine.endsWith(
1954                                                                            StringPool.TAB +
1955                                                                                    StringPool.CLOSE_CURLY_BRACE) &&
1956                                                                     !trimmedLine.startsWith(
1957                                                                             StringPool.CLOSE_CURLY_BRACE) &&
1958                                                                     !trimmedLine.startsWith(
1959                                                                             StringPool.CLOSE_PARENTHESIS) &&
1960                                                                     !trimmedLine.startsWith(
1961                                                                             StringPool.DOUBLE_SLASH) &&
1962                                                                     !trimmedLine.startsWith("catch ") &&
1963                                                                     !trimmedLine.startsWith("else ") &&
1964                                                                     !trimmedLine.startsWith("finally ") &&
1965                                                                     !trimmedLine.startsWith("while ")) {
1966    
1967                                                            sb.append("\n");
1968                                                    }
1969                                            }
1970    
1971                                            sb.append("\n");
1972                                    }
1973    
1974                                    previousLine = line;
1975                            }
1976    
1977                            index = index + line.length() + 1;
1978                    }
1979    
1980                    sb.append(previousLine);
1981    
1982                    unsyncBufferedReader.close();
1983    
1984                    String newContent = sb.toString();
1985    
1986                    if (newContent.endsWith("\n")) {
1987                            newContent = newContent.substring(0, newContent.length() - 1);
1988                    }
1989    
1990                    if (hasUnsortedJavaTerms && content.equals(newContent)) {
1991                            if (nextJavaTermPos == -1) {
1992                                    nextJavaTermPos = newContent.length() - 2;
1993                            }
1994    
1995                            String javaTerm1 = newContent.substring(
1996                                    previousJavaTermPos, javaTermPos);
1997    
1998                            if (!newContent.contains("\n\n" + javaTerm1)) {
1999                                    newContent = StringUtil.replace(
2000                                            newContent, javaTerm1, "\n" + javaTerm1);
2001                            }
2002    
2003                            javaTerm1 = javaTerm1.trim();
2004    
2005                            String javaTerm2 = newContent.substring(
2006                                    javaTermPos, nextJavaTermPos);
2007    
2008                            javaTerm2 = javaTerm2.trim();
2009    
2010                            newContent = StringUtil.replaceFirst(
2011                                    newContent, javaTerm1, javaTerm2);
2012                            newContent = StringUtil.replaceLast(
2013                                    newContent, javaTerm2, javaTerm1);
2014    
2015                            if ((previousJavaTermType == nextJavaTermType) &&
2016                                    _isInJavaTermTypeGroup(
2017                                            previousJavaTermType, _TYPE_VARIABLE_NOT_STATIC)) {
2018    
2019                                    newContent = StringUtil.replace(
2020                                            newContent, javaTerm1 + "\n\n", javaTerm1 + "\n");
2021                            }
2022                    }
2023    
2024                    return newContent;
2025            }
2026    
2027            private static void _formatJS() throws IOException {
2028                    String basedir = "./";
2029    
2030                    DirectoryScanner directoryScanner = new DirectoryScanner();
2031    
2032                    directoryScanner.setBasedir(basedir);
2033    
2034                    String[] excludes = {
2035                            "**\\js\\aui\\**", "**\\js\\editor\\**", "**\\js\\misc\\**",
2036                            "**\\tools\\**", "**\\VAADIN\\**"
2037                    };
2038    
2039                    excludes = ArrayUtil.append(excludes, _excludes);
2040    
2041                    directoryScanner.setExcludes(excludes);
2042    
2043                    directoryScanner.setIncludes(new String[] {"**\\*.js"});
2044    
2045                    List<String> fileNames = _sourceFormatterHelper.scanForFiles(
2046                            directoryScanner);
2047    
2048                    for (String fileName : fileNames) {
2049                            File file = new File(basedir + fileName);
2050    
2051                            String content = _fileUtil.read(file);
2052    
2053                            String newContent = _trimContent(content);
2054    
2055                            newContent = StringUtil.replace(
2056                                    newContent,
2057                                    new String[] {
2058                                            "else{", "for(", "function (", "if(", "while(", "){\n",
2059                                            "= new Array();", "= new Object();"
2060                                    },
2061                                    new String[] {
2062                                            "else {", "for (", "function(", "if (", "while (", ") {\n",
2063                                            "= [];", "= {};"
2064                                    });
2065    
2066                            Pattern pattern = Pattern.compile("\t+var \\w+\\, ");
2067    
2068                            for (;;) {
2069                                    Matcher matcher = pattern.matcher(newContent);
2070    
2071                                    if (!matcher.find()) {
2072                                            break;
2073                                    }
2074    
2075                                    String match = newContent.substring(
2076                                            matcher.start(), matcher.end());
2077    
2078                                    int pos = match.indexOf("var ");
2079    
2080                                    StringBundler sb = new StringBundler(4);
2081    
2082                                    sb.append(match.substring(0, match.length() - 2));
2083                                    sb.append(StringPool.SEMICOLON);
2084                                    sb.append("\n");
2085                                    sb.append(match.substring(0, pos + 4));
2086    
2087                                    newContent = StringUtil.replace(
2088                                            newContent, match, sb.toString());
2089                            }
2090    
2091                            if (newContent.endsWith("\n")) {
2092                                    newContent = newContent.substring(0, newContent.length() - 1);
2093                            }
2094    
2095                            _checkLanguageKeys(fileName, newContent, _languageKeyPattern);
2096    
2097                            if ((newContent != null) && !content.equals(newContent)) {
2098                                    _fileUtil.write(file, newContent);
2099    
2100                                    _sourceFormatterHelper.printError(fileName, file);
2101                            }
2102                    }
2103            }
2104    
2105            private static void _formatJSP() throws IOException {
2106                    String basedir = "./";
2107    
2108                    String copyright = _getCopyright();
2109                    String oldCopyright = _getOldCopyright();
2110    
2111                    DirectoryScanner directoryScanner = new DirectoryScanner();
2112    
2113                    directoryScanner.setBasedir(basedir);
2114    
2115                    String[] excludes = {
2116                            "**\\portal\\aui\\**", "**\\bin\\**", "**\\null.jsp", "**\\tmp\\**",
2117                            "**\\tools\\**"
2118                    };
2119    
2120                    excludes = ArrayUtil.append(excludes, _excludes);
2121    
2122                    directoryScanner.setExcludes(excludes);
2123    
2124                    directoryScanner.setIncludes(
2125                            new String[] {"**\\*.jsp", "**\\*.jspf", "**\\*.vm"});
2126    
2127                    List<String> fileNames = _sourceFormatterHelper.scanForFiles(
2128                            directoryScanner);
2129    
2130                    for (String fileName : fileNames) {
2131                            File file = new File(basedir + fileName);
2132    
2133                            String content = _fileUtil.read(file);
2134    
2135                            fileName = fileName.replace(
2136                                    CharPool.BACK_SLASH, CharPool.FORWARD_SLASH);
2137    
2138                            _jspContents.put(fileName, content);
2139                    }
2140    
2141                    boolean stripJSPImports = true;
2142    
2143                    for (String fileName : fileNames) {
2144                            File file = new File(basedir + fileName);
2145    
2146                            String content = _fileUtil.read(file);
2147    
2148                            String oldContent = content;
2149                            String newContent = StringPool.BLANK;
2150    
2151                            for (;;) {
2152                                    newContent = _formatJSP(fileName, oldContent);
2153    
2154                                    if (oldContent.equals(newContent)) {
2155                                            break;
2156                                    }
2157    
2158                                    oldContent = newContent;
2159                            }
2160    
2161                            newContent = StringUtil.replace(
2162                                    newContent,
2163                                    new String[] {
2164                                            "<br/>", "\"/>", "\" >", "@page import", "\"%>", ")%>",
2165                                            "javascript: "
2166                                    },
2167                                    new String[] {
2168                                            "<br />", "\" />", "\">", "@ page import", "\" %>", ") %>",
2169                                            "javascript:"
2170                                    });
2171    
2172                            if (stripJSPImports) {
2173                                    try {
2174                                            newContent = _stripJSPImports(fileName, newContent);
2175                                    }
2176                                    catch (RuntimeException re) {
2177                                            stripJSPImports = false;
2178                                    }
2179                            }
2180    
2181                            newContent = StringUtil.replace(
2182                                    newContent,
2183                                    new String[] {
2184                                            "* Copyright (c) 2000-2011 Liferay, Inc."
2185                                    },
2186                                    new String[] {
2187                                            "* Copyright (c) 2000-2012 Liferay, Inc."
2188                                    });
2189    
2190                            if (fileName.endsWith(".jsp") || fileName.endsWith(".jspf")) {
2191                                    if ((oldCopyright != null) &&
2192                                            newContent.contains(oldCopyright)) {
2193    
2194                                            newContent = StringUtil.replace(
2195                                                    newContent, oldCopyright, copyright);
2196    
2197                                            _sourceFormatterHelper.printError(
2198                                                    fileName, "old (c): " + fileName);
2199                                    }
2200    
2201                                    if (!newContent.contains(copyright)) {
2202                                            String customCopyright = _getCustomCopyright(file);
2203    
2204                                            if (Validator.isNull(customCopyright) ||
2205                                                    !newContent.contains(customCopyright)) {
2206    
2207                                                    _sourceFormatterHelper.printError(
2208                                                            fileName, "(c): " + fileName);
2209                                            }
2210                                            else {
2211                                                    newContent = StringUtil.replace(
2212                                                            newContent, "<%\n" + customCopyright + "\n%>",
2213                                                            "<%--\n" + customCopyright + "\n--%>");
2214                                            }
2215                                    }
2216                                    else {
2217                                            newContent = StringUtil.replace(
2218                                                    newContent, "<%\n" + copyright + "\n%>",
2219                                                    "<%--\n" + copyright + "\n--%>");
2220                                    }
2221                            }
2222    
2223                            newContent = StringUtil.replace(
2224                                    newContent,
2225                                    new String[] {
2226                                            "alert('<%= LanguageUtil.",
2227                                            "alert(\"<%= LanguageUtil.", "confirm('<%= LanguageUtil.",
2228                                            "confirm(\"<%= LanguageUtil."
2229                                    },
2230                                    new String[] {
2231                                            "alert('<%= UnicodeLanguageUtil.",
2232                                            "alert(\"<%= UnicodeLanguageUtil.",
2233                                            "confirm('<%= UnicodeLanguageUtil.",
2234                                            "confirm(\"<%= UnicodeLanguageUtil."
2235                                    });
2236    
2237                            if (newContent.contains("    ")) {
2238                                    if (!fileName.matches(".*template.*\\.vm$")) {
2239                                            _sourceFormatterHelper.printError(
2240                                                    fileName, "tab: " + fileName);
2241                                    }
2242                            }
2243    
2244                            if (fileName.endsWith("init.jsp")) {
2245                                    int x = newContent.indexOf("<%@ page import=");
2246    
2247                                    int y = newContent.lastIndexOf("<%@ page import=");
2248    
2249                                    y = newContent.indexOf("%>", y);
2250    
2251                                    if ((x != -1) && (y != -1) && (y > x)) {
2252    
2253                                            // Set compressImports to false to decompress imports
2254    
2255                                            boolean compressImports = true;
2256    
2257                                            if (compressImports) {
2258                                                    String imports = newContent.substring(x, y);
2259    
2260                                                    imports = StringUtil.replace(
2261                                                            imports, new String[] {"%>\r\n<%@ ", "%>\n<%@ "},
2262                                                            new String[] {"%><%@\r\n", "%><%@\n"});
2263    
2264                                                    newContent =
2265                                                            newContent.substring(0, x) + imports +
2266                                                                    newContent.substring(y);
2267                                            }
2268                                    }
2269                            }
2270    
2271                            newContent = _fixSessionKey(
2272                                    fileName, newContent, _sessionKeyPattern);
2273                            newContent = _fixSessionKey(
2274                                    fileName, newContent, _taglibSessionKeyPattern);
2275    
2276                            _checkLanguageKeys(fileName, newContent, _languageKeyPattern);
2277                            _checkLanguageKeys(fileName, newContent, _taglibLanguageKeyPattern);
2278                            _checkXSS(fileName, newContent);
2279    
2280                            if ((newContent != null) && !content.equals(newContent)) {
2281                                    _fileUtil.write(file, newContent);
2282    
2283                                    _sourceFormatterHelper.printError(fileName, file);
2284                            }
2285                    }
2286            }
2287    
2288            private static String _formatJSP(String fileName, String content)
2289                    throws IOException {
2290    
2291                    StringBundler sb = new StringBundler();
2292    
2293                    UnsyncBufferedReader unsyncBufferedReader = new UnsyncBufferedReader(
2294                            new UnsyncStringReader(content));
2295    
2296                    int lineCount = 0;
2297    
2298                    String line = null;
2299    
2300                    String previousLine = StringPool.BLANK;
2301    
2302                    String currentAttributeAndValue = null;
2303                    String previousAttribute = null;
2304                    String previousAttributeAndValue = null;
2305    
2306                    boolean readAttributes = false;
2307    
2308                    String currentException = null;
2309                    String previousException = null;
2310    
2311                    boolean hasUnsortedExceptions = false;
2312    
2313                    while ((line = unsyncBufferedReader.readLine()) != null) {
2314                            lineCount++;
2315    
2316                            if (!fileName.contains("jsonw") ||
2317                                    !fileName.endsWith("action.jsp")) {
2318    
2319                                    line = _trimLine(line);
2320                            }
2321    
2322                            if (line.contains("<aui:button ") &&
2323                                    line.contains("type=\"button\"")) {
2324    
2325                                    _sourceFormatterHelper.printError(
2326                                            fileName, "aui:button " + fileName + " " + lineCount);
2327                            }
2328    
2329                            String trimmedLine = StringUtil.trimLeading(line);
2330                            String trimmedPreviousLine = StringUtil.trimLeading(previousLine);
2331    
2332                            if (!trimmedLine.equals("%>") && line.contains("%>") &&
2333                                    !line.contains("--%>") && !line.contains(" %>")) {
2334    
2335                                    line = StringUtil.replace(line, "%>", " %>");
2336                            }
2337    
2338                            if (line.contains("<%=") && !line.contains("<%= ")) {
2339                                    line = StringUtil.replace(line, "<%=", "<%= ");
2340                            }
2341    
2342                            if (trimmedPreviousLine.equals("%>") && Validator.isNotNull(line) &&
2343                                    !trimmedLine.equals("-->")) {
2344    
2345                                    sb.append("\n");
2346                            }
2347                            else if (Validator.isNotNull(previousLine) &&
2348                                             !trimmedPreviousLine.equals("<!--") &&
2349                                             trimmedLine.equals("<%")) {
2350    
2351                                    sb.append("\n");
2352                            }
2353                            else if (trimmedPreviousLine.equals("<%") &&
2354                                             Validator.isNull(line)) {
2355    
2356                                    continue;
2357                            }
2358                            else if (trimmedPreviousLine.equals("<%") &&
2359                                             trimmedLine.startsWith("//")) {
2360    
2361                                    sb.append("\n");
2362                            }
2363                            else if (Validator.isNull(previousLine) &&
2364                                             trimmedLine.equals("%>") && (sb.index() > 2)) {
2365    
2366                                    String lineBeforePreviousLine = sb.stringAt(sb.index() - 3);
2367    
2368                                    if (!lineBeforePreviousLine.startsWith("//")) {
2369                                            sb.setIndex(sb.index() - 1);
2370                                    }
2371                            }
2372    
2373                            if ((trimmedLine.startsWith("if (") ||
2374                                     trimmedLine.startsWith("else if (") ||
2375                                     trimmedLine.startsWith("while (")) &&
2376                                    trimmedLine.endsWith(") {")) {
2377    
2378                                    _checkIfClause(trimmedLine, fileName, lineCount);
2379                            }
2380    
2381                            if (readAttributes) {
2382                                    if (!trimmedLine.startsWith(StringPool.FORWARD_SLASH) &&
2383                                            !trimmedLine.startsWith(StringPool.GREATER_THAN)) {
2384    
2385                                            int pos = trimmedLine.indexOf(StringPool.EQUAL);
2386    
2387                                            if (pos != -1) {
2388                                                    String attribute = trimmedLine.substring(0, pos);
2389    
2390                                                    if (!trimmedLine.endsWith(StringPool.QUOTE) &&
2391                                                            !trimmedLine.endsWith(StringPool.APOSTROPHE)) {
2392    
2393                                                            _sourceFormatterHelper.printError(
2394                                                                    fileName,
2395                                                                    "attribute: " + fileName + " " + lineCount);
2396    
2397                                                            readAttributes = false;
2398                                                    }
2399                                                    else if (Validator.isNotNull(previousAttribute)) {
2400                                                            if (!_isJSPAttributName(attribute)) {
2401                                                                    _sourceFormatterHelper.printError(
2402                                                                            fileName,
2403                                                                            "attribute: " + fileName + " " + lineCount);
2404    
2405                                                                    readAttributes = false;
2406                                                            }
2407                                                            else if (Validator.isNull(
2408                                                                                    previousAttributeAndValue) &&
2409                                                                             (previousAttribute.compareTo(
2410                                                                                     attribute) > 0)) {
2411    
2412                                                                    previousAttributeAndValue = previousLine;
2413                                                                    currentAttributeAndValue = line;
2414                                                            }
2415                                                    }
2416    
2417                                                    if (!readAttributes) {
2418                                                            previousAttribute = null;
2419                                                            previousAttributeAndValue = null;
2420                                                    }
2421                                                    else {
2422                                                            previousAttribute = attribute;
2423                                                    }
2424                                            }
2425                                    }
2426                                    else {
2427                                            previousAttribute = null;
2428    
2429                                            readAttributes = false;
2430                                    }
2431                            }
2432    
2433                            if (!hasUnsortedExceptions) {
2434                                    int i = line.indexOf("<liferay-ui:error exception=\"<%=");
2435    
2436                                    if (i != -1) {
2437                                            currentException = line.substring(i + 33);
2438    
2439                                            if (Validator.isNotNull(previousException) &&
2440                                                    (previousException.compareTo(currentException) > 0)) {
2441    
2442                                                    hasUnsortedExceptions = true;
2443                                            }
2444                                    }
2445    
2446                                    if (!hasUnsortedExceptions) {
2447                                            previousException = currentException;
2448                                            currentException = null;
2449                                    }
2450                            }
2451    
2452                            if (trimmedLine.startsWith(StringPool.LESS_THAN) &&
2453                                    !trimmedLine.startsWith("<%") &&
2454                                    !trimmedLine.startsWith("<!")) {
2455    
2456                                    if (!trimmedLine.contains(StringPool.GREATER_THAN) &&
2457                                            !trimmedLine.contains(StringPool.SPACE)) {
2458    
2459                                            readAttributes = true;
2460                                    }
2461                                    else {
2462                                            line = _sortJSPAttributes(fileName, line, lineCount);
2463                                    }
2464                            }
2465    
2466                            if (!trimmedLine.contains(StringPool.DOUBLE_SLASH) &&
2467                                    !trimmedLine.startsWith(StringPool.STAR)) {
2468    
2469                                    while (trimmedLine.contains(StringPool.TAB)) {
2470                                            line = StringUtil.replaceLast(
2471                                                    line, StringPool.TAB, StringPool.SPACE);
2472    
2473                                            trimmedLine = StringUtil.replaceLast(
2474                                                    trimmedLine, StringPool.TAB, StringPool.SPACE);
2475                                    }
2476    
2477                                    while (trimmedLine.contains(StringPool.DOUBLE_SPACE) &&
2478                                               !trimmedLine.contains(
2479                                                       StringPool.QUOTE + StringPool.DOUBLE_SPACE) &&
2480                                               !fileName.endsWith(".vm")) {
2481    
2482                                            line = StringUtil.replaceLast(
2483                                                    line, StringPool.DOUBLE_SPACE, StringPool.SPACE);
2484    
2485                                            trimmedLine = StringUtil.replaceLast(
2486                                                    trimmedLine, StringPool.DOUBLE_SPACE, StringPool.SPACE);
2487                                    }
2488                            }
2489    
2490                            int x = line.indexOf("<%@ include file");
2491    
2492                            if (x != -1) {
2493                                    x = line.indexOf(StringPool.QUOTE, x);
2494    
2495                                    int y = line.indexOf(StringPool.QUOTE, x + 1);
2496    
2497                                    if (y != -1) {
2498                                            String includeFileName = line.substring(x + 1, y);
2499    
2500                                            Matcher matcher = _jspIncludeFilePattern.matcher(
2501                                                    includeFileName);
2502    
2503                                            if (!matcher.find()) {
2504                                                    _sourceFormatterHelper.printError(
2505                                                            fileName, "include: " + fileName + " " + lineCount);
2506                                            }
2507                                    }
2508                            }
2509    
2510                            line = _replacePrimitiveWrapperInstantiation(
2511                                    fileName, line, lineCount);
2512    
2513                            previousLine = line;
2514    
2515                            sb.append(line);
2516                            sb.append("\n");
2517                    }
2518    
2519                    unsyncBufferedReader.close();
2520    
2521                    content = sb.toString();
2522    
2523                    if (content.endsWith("\n")) {
2524                            content = content.substring(0, content.length() - 1);
2525                    }
2526    
2527                    content = _formatTaglibQuotes(fileName, content, StringPool.QUOTE);
2528                    content = _formatTaglibQuotes(fileName, content, StringPool.APOSTROPHE);
2529    
2530                    if (Validator.isNotNull(previousAttributeAndValue)) {
2531                            content = StringUtil.replaceFirst(
2532                                    content,
2533                                    previousAttributeAndValue + "\n" + currentAttributeAndValue,
2534                                    currentAttributeAndValue + "\n" + previousAttributeAndValue);
2535                    }
2536    
2537                    if (hasUnsortedExceptions) {
2538                            if ((StringUtil.count(content, currentException) > 1) ||
2539                                    (StringUtil.count(content, previousException) > 1)) {
2540    
2541                                    _sourceFormatterHelper.printError(
2542                                            fileName, "unsorted exceptions: " + fileName);
2543                            }
2544                            else {
2545                                    content = StringUtil.replaceFirst(
2546                                            content, previousException, currentException);
2547    
2548                                    content = StringUtil.replaceLast(
2549                                            content, currentException, previousException);
2550                            }
2551                    }
2552    
2553                    return content;
2554            }
2555    
2556            private static void _formatPortalProperties() throws IOException {
2557                    String basedir = "./";
2558    
2559                    String portalPortalProperties = null;
2560    
2561                    if (_portalSource) {
2562                            File portalPortalPropertiesFile = new File(
2563                                    basedir + "portal-impl/src/portal.properties");
2564    
2565                            portalPortalProperties = _fileUtil.read(portalPortalPropertiesFile);
2566                    }
2567                    else {
2568                            portalPortalProperties = ContentUtil.get("portal.properties");
2569                    }
2570    
2571                    DirectoryScanner directoryScanner = new DirectoryScanner();
2572    
2573                    directoryScanner.setBasedir(basedir);
2574    
2575                    if (_portalSource) {
2576                            directoryScanner.setExcludes(
2577                                    new String[] {"**\\classes\\**", "**\\bin\\**"});
2578                            directoryScanner.setIncludes(
2579                                    new String[] {
2580                                            "**\\portal-ext.properties",
2581                                            "**\\portal-legacy-*.properties",
2582                                    });
2583                    }
2584                    else {
2585                            directoryScanner.setIncludes(
2586                                    new String[] {
2587                                            "**\\portal.properties", "**\\portal-ext.properties"
2588                                    });
2589                    }
2590    
2591                    List<String> fileNames = _sourceFormatterHelper.scanForFiles(
2592                            directoryScanner);
2593    
2594                    for (String fileName : fileNames) {
2595                            File file = new File(basedir + fileName);
2596    
2597                            String content = _fileUtil.read(file);
2598    
2599                            _formatPortalProperties(fileName, content, portalPortalProperties);
2600                    }
2601            }
2602    
2603            private static void _formatPortalProperties(
2604                            String fileName, String content, String portalPortalProperties)
2605                    throws IOException {
2606    
2607                    UnsyncBufferedReader unsyncBufferedReader = new UnsyncBufferedReader(
2608                            new UnsyncStringReader(content));
2609    
2610                    int lineCount = 0;
2611    
2612                    String line = null;
2613    
2614                    int previousPos = -1;
2615    
2616                    while ((line = unsyncBufferedReader.readLine()) != null) {
2617                            lineCount++;
2618    
2619                            int pos = line.indexOf(StringPool.EQUAL);
2620    
2621                            if (pos == -1) {
2622                                    continue;
2623                            }
2624    
2625                            String property = line.substring(0, pos + 1);
2626    
2627                            property = property.trim();
2628    
2629                            pos = portalPortalProperties.indexOf(
2630                                    StringPool.FOUR_SPACES + property);
2631    
2632                            if (pos == -1) {
2633                                    continue;
2634                            }
2635    
2636                            if (pos < previousPos) {
2637                                    _sourceFormatterHelper.printError(
2638                                            fileName, "sort " + fileName + " " + lineCount);
2639                            }
2640    
2641                            previousPos = pos;
2642                    }
2643            }
2644    
2645            private static void _formatPortletXML()
2646                    throws DocumentException, IOException {
2647    
2648                    String basedir = "./";
2649    
2650                    if (_portalSource) {
2651                            File file = new File(
2652                                    basedir + "portal-web/docroot/WEB-INF/portlet-custom.xml");
2653    
2654                            String content = _fileUtil.read(file);
2655    
2656                            String newContent = _formatPortletXML(content);
2657    
2658                            if ((newContent != null) && !content.equals(newContent)) {
2659                                    _fileUtil.write(file, newContent);
2660    
2661                                    _sourceFormatterHelper.printError(file.toString(), file);
2662                            }
2663                    }
2664                    else {
2665                            DirectoryScanner directoryScanner = new DirectoryScanner();
2666    
2667                            directoryScanner.setBasedir(basedir);
2668                            directoryScanner.setIncludes(new String[] {"**\\portlet.xml"});
2669    
2670                            List<String> fileNames = _sourceFormatterHelper.scanForFiles(
2671                                    directoryScanner);
2672    
2673                            for (String fileName : fileNames) {
2674                                    File file = new File(basedir + fileName);
2675    
2676                                    String content = _fileUtil.read(file);
2677    
2678                                    String newContent = _trimContent(content);
2679    
2680                                    newContent = _formatPortletXML(content);
2681    
2682                                    if ((newContent != null) && !content.equals(newContent)) {
2683                                            _fileUtil.write(file, newContent);
2684    
2685                                            _sourceFormatterHelper.printError(fileName, file);
2686                                    }
2687                            }
2688                    }
2689            }
2690    
2691            private static String _formatPortletXML(String content)
2692                    throws DocumentException, IOException {
2693    
2694                    Document document = _saxReaderUtil.read(content);
2695    
2696                    Element rootElement = document.getRootElement();
2697    
2698                    rootElement.sortAttributes(true);
2699    
2700                    List<Element> portletElements = rootElement.elements("portlet");
2701    
2702                    for (Element portletElement : portletElements) {
2703                            portletElement.sortElementsByChildElement("init-param", "name");
2704    
2705                            Element portletPreferencesElement = portletElement.element(
2706                                    "portlet-preferences");
2707    
2708                            if (portletPreferencesElement != null) {
2709                                    portletPreferencesElement.sortElementsByChildElement(
2710                                            "preference", "name");
2711                            }
2712                    }
2713    
2714                    return document.formattedString();
2715            }
2716    
2717            private static void _formatServiceXML()
2718                    throws DocumentException, IOException {
2719    
2720                    String basedir = "./";
2721    
2722                    DirectoryScanner directoryScanner = new DirectoryScanner();
2723    
2724                    directoryScanner.setBasedir(basedir);
2725                    directoryScanner.setIncludes(new String[] {"**\\service.xml"});
2726    
2727                    List<String> fileNames = _sourceFormatterHelper.scanForFiles(
2728                            directoryScanner);
2729    
2730                    for (String fileName : fileNames) {
2731                            File file = new File(basedir + fileName);
2732    
2733                            String content = _fileUtil.read(file);
2734    
2735                            String newContent = _trimContent(content);
2736    
2737                            _formatServiceXML(fileName, content);
2738    
2739                            if ((newContent != null) && !content.equals(newContent)) {
2740                                    _fileUtil.write(file, newContent);
2741    
2742                                    _sourceFormatterHelper.printError(fileName, file);
2743                            }
2744                    }
2745            }
2746    
2747            private static void _formatServiceXML(String fileName, String content)
2748                    throws DocumentException {
2749    
2750                    Document document = _saxReaderUtil.read(content);
2751    
2752                    Element rootElement = document.getRootElement();
2753    
2754                    List<Element> entityElements = rootElement.elements("entity");
2755    
2756                    String previousEntityName = StringPool.BLANK;
2757    
2758                    for (Element entityElement : entityElements) {
2759                            String entityName = entityElement.attributeValue("name");
2760    
2761                            if (Validator.isNotNull(previousEntityName) &&
2762                                    (previousEntityName.compareToIgnoreCase(entityName) > 0)) {
2763    
2764                                    _sourceFormatterHelper.printError(
2765                                            fileName, "sort: " + fileName + " " + entityName);
2766                            }
2767    
2768                            String previousReferenceEntity = StringPool.BLANK;
2769                            String previousReferencePackagePath = StringPool.BLANK;
2770    
2771                            List<Element> referenceElements = entityElement.elements(
2772                                    "reference");
2773    
2774                            for (Element referenceElement : referenceElements) {
2775                                    String referenceEntity = referenceElement.attributeValue(
2776                                            "entity");
2777                                    String referencePackagePath = referenceElement.attributeValue(
2778                                            "package-path");
2779    
2780    
2781                                    if (Validator.isNotNull(previousReferencePackagePath)) {
2782                                            if ((previousReferencePackagePath.compareToIgnoreCase(
2783                                                            referencePackagePath) > 0) ||
2784                                                    (previousReferencePackagePath.equals(
2785                                                            referencePackagePath) &&
2786                                                     (previousReferenceEntity.compareToIgnoreCase(
2787                                                             referenceEntity) > 0))) {
2788    
2789                                                    _sourceFormatterHelper.printError(
2790                                                            fileName,
2791                                                            "sort: " + fileName + " " + referencePackagePath);
2792                                            }
2793                                    }
2794    
2795                                    previousReferenceEntity = referenceEntity;
2796                                    previousReferencePackagePath = referencePackagePath;
2797                            }
2798    
2799                            previousEntityName = entityName;
2800                    }
2801    
2802                    Element exceptionsElement = rootElement.element("exceptions");
2803    
2804                    if (exceptionsElement == null) {
2805                            return;
2806                    }
2807    
2808                    List<Element> exceptionElements = exceptionsElement.elements(
2809                            "exception");
2810    
2811                    String previousException = StringPool.BLANK;
2812    
2813                    for (Element exceptionElement : exceptionElements) {
2814                            String exception = exceptionElement.getStringValue();
2815    
2816                            if (Validator.isNotNull(previousException) &&
2817                                    (previousException.compareToIgnoreCase(exception) > 0)) {
2818    
2819                                    _sourceFormatterHelper.printError(
2820                                            fileName, "sort: " + fileName + " " + exception);
2821                            }
2822    
2823                            previousException = exception;
2824                    }
2825            }
2826    
2827            private static void _formatSH() throws IOException {
2828                    _formatSH("ext/create.sh");
2829                    _formatSH("hooks/create.sh");
2830                    _formatSH("layouttpl/create.sh");
2831                    _formatSH("portlets/create.sh");
2832                    _formatSH("themes/create.sh");
2833            }
2834    
2835            private static void _formatSH(String fileName) throws IOException {
2836                    File file = new File(fileName);
2837    
2838                    if (!file.exists()) {
2839                            return;
2840                    }
2841    
2842                    String content = _fileUtil.read(new File(fileName), true);
2843    
2844                    if (content.contains("\r")) {
2845                            _sourceFormatterHelper.printError(
2846                                    fileName, "Invalid new line character");
2847    
2848                            content = StringUtil.replace(content, "\r", "");
2849    
2850                            _fileUtil.write(fileName, content);
2851                    }
2852            }
2853    
2854            private static void _formatSQL() throws IOException {
2855                    String basedir = "./";
2856    
2857                    DirectoryScanner directoryScanner = new DirectoryScanner();
2858    
2859                    directoryScanner.setBasedir(basedir);
2860                    directoryScanner.setIncludes(new String[] {"**\\sql\\*.sql"});
2861    
2862                    List<String> fileNames = _sourceFormatterHelper.scanForFiles(
2863                            directoryScanner);
2864    
2865                    for (String fileName : fileNames) {
2866                            File file = new File(basedir + fileName);
2867    
2868                            String content = _fileUtil.read(file);
2869    
2870                            String newContent = _formatSQL(content);
2871    
2872                            if ((newContent != null) && !content.equals(newContent)) {
2873                                    _fileUtil.write(file, newContent);
2874    
2875                                    _sourceFormatterHelper.printError(fileName, file);
2876                            }
2877                    }
2878            }
2879    
2880            private static String _formatSQL(String content) throws IOException {
2881                    StringBundler sb = new StringBundler();
2882    
2883                    UnsyncBufferedReader unsyncBufferedReader = new UnsyncBufferedReader(
2884                            new UnsyncStringReader(content));
2885    
2886                    String line = null;
2887    
2888                    String previousLineSqlCommand = StringPool.BLANK;
2889    
2890                    while ((line = unsyncBufferedReader.readLine()) != null) {
2891                            line = _trimLine(line);
2892    
2893                            if (Validator.isNotNull(line) && !line.startsWith(StringPool.TAB)) {
2894                                    String sqlCommand = StringUtil.split(line, CharPool.SPACE)[0];
2895    
2896                                    if (Validator.isNotNull(previousLineSqlCommand) &&
2897                                            !previousLineSqlCommand.equals(sqlCommand)) {
2898    
2899                                            sb.append("\n");
2900                                    }
2901    
2902                                    previousLineSqlCommand = sqlCommand;
2903                            }
2904                            else {
2905                                    previousLineSqlCommand = StringPool.BLANK;
2906                            }
2907    
2908                            sb.append(line);
2909                            sb.append("\n");
2910                    }
2911    
2912                    unsyncBufferedReader.close();
2913    
2914                    content = sb.toString();
2915    
2916                    if (content.endsWith("\n")) {
2917                            content = content.substring(0, content.length() - 1);
2918                    }
2919    
2920                    return content;
2921            }
2922    
2923            private static void _formatStrutsConfigXML()
2924                    throws DocumentException, IOException {
2925    
2926                    String basedir = "./";
2927    
2928                    if (!_portalSource) {
2929                            return;
2930                    }
2931    
2932                    String fileName = "portal-web/docroot/WEB-INF/struts-config.xml";
2933    
2934                    File file = new File(basedir + fileName);
2935    
2936                    String content = _fileUtil.read(file);
2937    
2938                    String newContent = _trimContent(content);
2939    
2940                    Document document = _saxReaderUtil.read(newContent);
2941    
2942                    Element rootElement = document.getRootElement();
2943    
2944                    Element actionMappingsElement = rootElement.element("action-mappings");
2945    
2946                    List<Element> actionElements = actionMappingsElement.elements("action");
2947    
2948                    String previousPath = StringPool.BLANK;
2949    
2950                    for (Element actionElement : actionElements) {
2951                            String path = actionElement.attributeValue("path");
2952    
2953                            if (Validator.isNotNull(previousPath) &&
2954                                    (previousPath.compareTo(path) > 0) &&
2955                                    (!previousPath.startsWith("/portal/") ||
2956                                     path.startsWith("/portal/"))) {
2957    
2958                                    _sourceFormatterHelper.printError(
2959                                            fileName, "sort: " + fileName + " " + path);
2960                            }
2961    
2962                            previousPath = path;
2963                    }
2964    
2965                    if ((newContent != null) && !content.equals(newContent)) {
2966                            _fileUtil.write(file, newContent);
2967    
2968                            _sourceFormatterHelper.printError(fileName, file);
2969                    }
2970            }
2971    
2972            private static String _formatTaglibQuotes(
2973                    String fileName, String content, String quoteType) {
2974    
2975                    String quoteFix = StringPool.APOSTROPHE;
2976    
2977                    if (quoteFix.equals(quoteType)) {
2978                            quoteFix = StringPool.QUOTE;
2979                    }
2980    
2981                    Pattern pattern = Pattern.compile(_getTaglibRegex(quoteType));
2982    
2983                    Matcher matcher = pattern.matcher(content);
2984    
2985                    while (matcher.find()) {
2986                            int x = content.indexOf(quoteType + "<%=", matcher.start());
2987                            int y = content.indexOf("%>" + quoteType, x);
2988    
2989                            while ((x != -1) && (y != -1)) {
2990                                    String result = content.substring(x + 1, y + 2);
2991    
2992                                    if (result.contains(quoteType)) {
2993                                            int lineCount = 1;
2994    
2995                                            char[] contentCharArray = content.toCharArray();
2996    
2997                                            for (int i = 0; i < x; i++) {
2998                                                    if (contentCharArray[i] == CharPool.NEW_LINE) {
2999                                                            lineCount++;
3000                                                    }
3001                                            }
3002    
3003                                            if (!result.contains(quoteFix)) {
3004                                                    StringBundler sb = new StringBundler(5);
3005    
3006                                                    sb.append(content.substring(0, x));
3007                                                    sb.append(quoteFix);
3008                                                    sb.append(result);
3009                                                    sb.append(quoteFix);
3010                                                    sb.append(content.substring(y + 3, content.length()));
3011    
3012                                                    content = sb.toString();
3013                                            }
3014                                            else {
3015                                                    _sourceFormatterHelper.printError(
3016                                                            fileName, "taglib: " + fileName + " " + lineCount);
3017                                            }
3018                                    }
3019    
3020                                    x = content.indexOf(quoteType + "<%=", y);
3021    
3022                                    if (x > matcher.end()) {
3023                                            break;
3024                                    }
3025    
3026                                    y = content.indexOf("%>" + quoteType, x);
3027                            }
3028                    }
3029    
3030                    return content;
3031            }
3032    
3033            private static void _formatTilesDefsXML()
3034                    throws DocumentException, IOException {
3035    
3036                    String basedir = "./";
3037    
3038                    if (!_portalSource) {
3039                            return;
3040                    }
3041    
3042                    String fileName = "portal-web/docroot/WEB-INF/tiles-defs.xml";
3043    
3044                    File file = new File(basedir + fileName);
3045    
3046                    String content = _fileUtil.read(file);
3047    
3048                    String newContent = _trimContent(content);
3049    
3050                    Document document = _saxReaderUtil.read(newContent);
3051    
3052                    Element rootElement = document.getRootElement();
3053    
3054                    List<Element> definitionElements = rootElement.elements("definition");
3055    
3056                    String previousName = StringPool.BLANK;
3057    
3058                    for (Element definitionElement : definitionElements) {
3059                            String name = definitionElement.attributeValue("name");
3060    
3061                            if (Validator.isNotNull(previousName) &&
3062                                    (previousName.compareTo(name) > 0) &&
3063                                    !previousName.equals("portlet")) {
3064    
3065                                    _sourceFormatterHelper.printError(
3066                                            fileName, "sort: " + fileName + " " + name);
3067    
3068                            }
3069    
3070                            previousName = name;
3071                    }
3072    
3073                    if ((newContent != null) && !content.equals(newContent)) {
3074                            _fileUtil.write(file, newContent);
3075    
3076                            _sourceFormatterHelper.printError(fileName, file);
3077                    }
3078            }
3079    
3080            private static void _formatTLD() throws IOException {
3081                    String basedir = "./";
3082    
3083                    DirectoryScanner directoryScanner = new DirectoryScanner();
3084    
3085                    directoryScanner.setBasedir(basedir);
3086                    directoryScanner.setIncludes(new String[] {"**\\*.tld"});
3087                    directoryScanner.setExcludes(
3088                            new String[] {
3089                                    "**\\classes\\**", "**\\bin\\**", "**\\WEB-INF\\tld\\**"
3090                            });
3091    
3092                    List<String> fileNames = _sourceFormatterHelper.scanForFiles(
3093                            directoryScanner);
3094    
3095                    for (String fileName : fileNames) {
3096                            File file = new File(basedir + fileName);
3097    
3098                            String content = _fileUtil.read(file);
3099    
3100                            String newContent = _trimContent(content);
3101    
3102                            if ((newContent != null) && !content.equals(newContent)) {
3103                                    _fileUtil.write(file, newContent);
3104    
3105                                    _sourceFormatterHelper.printError(fileName, file);
3106                            }
3107                    }
3108            }
3109    
3110            private static void _formatWebXML() throws IOException {
3111                    String basedir = "./";
3112    
3113                    if (_portalSource) {
3114                            Properties properties = new Properties();
3115    
3116                            String propertiesContent = _fileUtil.read(
3117                                    basedir + "portal-impl/src/portal.properties");
3118    
3119                            PropertiesUtil.load(properties, propertiesContent);
3120    
3121                            String[] locales = StringUtil.split(
3122                                    properties.getProperty(PropsKeys.LOCALES));
3123    
3124                            Arrays.sort(locales);
3125    
3126                            Set<String> urlPatterns = new TreeSet<String>();
3127    
3128                            for (String locale : locales) {
3129                                    int pos = locale.indexOf(StringPool.UNDERLINE);
3130    
3131                                    String languageCode = locale.substring(0, pos);
3132    
3133                                    urlPatterns.add(languageCode);
3134                                    urlPatterns.add(locale);
3135                            }
3136    
3137                            StringBundler sb = new StringBundler();
3138    
3139                            for (String urlPattern : urlPatterns) {
3140                                    sb.append("\t<servlet-mapping>\n");
3141                                    sb.append("\t\t<servlet-name>I18n Servlet</servlet-name>\n");
3142                                    sb.append(
3143                                            "\t\t<url-pattern>/" + urlPattern +"/*</url-pattern>\n");
3144                                    sb.append("\t</servlet-mapping>\n");
3145                            }
3146    
3147                            File file = new File(
3148                                    basedir + "portal-web/docroot/WEB-INF/web.xml");
3149    
3150                            String content = _fileUtil.read(file);
3151    
3152                            String newContent = _trimContent(content);
3153    
3154                            int x = newContent.indexOf("<servlet-mapping>");
3155    
3156                            x = newContent.indexOf(
3157                                    "<servlet-name>I18n Servlet</servlet-name>", x);
3158    
3159                            x = newContent.lastIndexOf("<servlet-mapping>", x) - 1;
3160    
3161                            int y = newContent.lastIndexOf(
3162                                    "<servlet-name>I18n Servlet</servlet-name>");
3163    
3164                            y = newContent.indexOf("</servlet-mapping>", y) + 19;
3165    
3166                            newContent =
3167                                    newContent.substring(0, x) + sb.toString() +
3168                                            newContent.substring(y);
3169    
3170                            x = newContent.indexOf("<security-constraint>");
3171    
3172                            x = newContent.indexOf(
3173                                    "<web-resource-name>/c/portal/protected</web-resource-name>",
3174                                    x);
3175    
3176                            x = newContent.indexOf("<url-pattern>", x) - 3;
3177    
3178                            y = newContent.indexOf("<http-method>", x);
3179    
3180                            y = newContent.lastIndexOf("</url-pattern>", y) + 15;
3181    
3182                            sb = new StringBundler();
3183    
3184                            sb.append("\t\t\t<url-pattern>/c/portal/protected</url-pattern>\n");
3185    
3186                            for (String urlPattern : urlPatterns) {
3187                                    sb.append(
3188                                            "\t\t\t<url-pattern>/" + urlPattern +
3189                                                    "/c/portal/protected</url-pattern>\n");
3190                            }
3191    
3192                            newContent =
3193                                    newContent.substring(0, x) + sb.toString() +
3194                                            newContent.substring(y);
3195    
3196                            if ((newContent != null) && !content.equals(newContent)) {
3197                                    _fileUtil.write(file, newContent);
3198    
3199                                    System.out.println(file);
3200                            }
3201                    }
3202                    else {
3203                            String webXML = ContentUtil.get(
3204                                    "com/liferay/portal/deploy/dependencies/web.xml");
3205    
3206                            DirectoryScanner directoryScanner = new DirectoryScanner();
3207    
3208                            directoryScanner.setBasedir(basedir);
3209                            directoryScanner.setIncludes(new String[] {"**\\web.xml"});
3210    
3211                            List<String> fileNames = _sourceFormatterHelper.scanForFiles(
3212                                    directoryScanner);
3213    
3214                            for (String fileName : fileNames) {
3215                                    String content = _fileUtil.read(basedir + fileName);
3216    
3217                                    if (content.equals(webXML)) {
3218                                            _sourceFormatterHelper.printError(fileName, fileName);
3219                                    }
3220                            }
3221                    }
3222            }
3223    
3224            private static String _getClassName(String line) {
3225                    int pos = line.indexOf(" implements ");
3226    
3227                    if (pos == -1) {
3228                            pos = line.indexOf(" extends ");
3229                    }
3230    
3231                    if (pos == -1) {
3232                            pos = line.indexOf(StringPool.OPEN_CURLY_BRACE);
3233                    }
3234    
3235                    if (pos != -1) {
3236                            line = line.substring(0, pos);
3237                    }
3238    
3239                    line = line.trim();
3240    
3241                    pos = line.lastIndexOf(StringPool.SPACE);
3242    
3243                    return line.substring(pos + 1);
3244            }
3245    
3246            private static Tuple _getCombinedLines(
3247                    String line, String previousLine, int lineTabCount,
3248                    int previousLineTabCount) {
3249    
3250                    if (Validator.isNull(line) || Validator.isNull(previousLine)) {
3251                            return null;
3252                    }
3253    
3254                    String trimmedPreviousLine = StringUtil.trimLeading(previousLine);
3255    
3256                    if (line.startsWith("// ") || trimmedPreviousLine.startsWith("// ")) {
3257                            return null;
3258                    }
3259    
3260                    if (line.startsWith("+ ") || line.startsWith("- ") ||
3261                            line.startsWith("|| ") || line.startsWith("&& ")) {
3262    
3263                            int pos = line.indexOf(StringPool.SPACE);
3264    
3265                            String linePart = line.substring(0, pos);
3266    
3267                            return new Tuple(previousLine + StringPool.SPACE, linePart, true);
3268                    }
3269    
3270                    int previousLineLength = _getLineLength(previousLine);
3271    
3272                    if ((line.length() + previousLineLength) < 80) {
3273                            if (trimmedPreviousLine.startsWith("for ") &&
3274                                    previousLine.endsWith(StringPool.COLON) &&
3275                                    line.endsWith(StringPool.OPEN_CURLY_BRACE)) {
3276    
3277                                    return new Tuple(previousLine + StringPool.SPACE + line);
3278                            }
3279    
3280                            if ((previousLine.endsWith(StringPool.EQUAL) ||
3281                                     previousLine.endsWith(StringPool.PERIOD) ||
3282                                     trimmedPreviousLine.equals("return")) &&
3283                                    line.endsWith(StringPool.SEMICOLON)) {
3284    
3285                                    return new Tuple(previousLine + StringPool.SPACE + line);
3286                            }
3287    
3288                            if ((trimmedPreviousLine.startsWith("if ") ||
3289                                     trimmedPreviousLine.startsWith("else ")) &&
3290                                    (previousLine.endsWith("||") || previousLine.endsWith("&&")) &&
3291                                    line.endsWith(StringPool.OPEN_CURLY_BRACE)) {
3292    
3293                                    return new Tuple(previousLine + StringPool.SPACE + line);
3294                            }
3295    
3296                            if ((line.startsWith("extends ") ||
3297                                     line.startsWith("implements ") ||
3298                                     line.startsWith("throws")) &&
3299                                    line.endsWith(StringPool.OPEN_CURLY_BRACE) &&
3300                                    (lineTabCount == (previousLineTabCount + 1))) {
3301    
3302                                    return new Tuple(previousLine + StringPool.SPACE + line);
3303                            }
3304                    }
3305    
3306                    if (previousLine.endsWith(StringPool.EQUAL) &&
3307                            line.endsWith(StringPool.SEMICOLON)) {
3308    
3309                            String tempLine = line;
3310    
3311                            for (int pos = 0;;) {
3312                                    pos = tempLine.indexOf(StringPool.DASH);
3313    
3314                                    if (pos == -1) {
3315                                            pos = tempLine.indexOf(StringPool.PLUS);
3316                                    }
3317    
3318                                    if (pos == -1) {
3319                                            pos = tempLine.indexOf(StringPool.SLASH);
3320                                    }
3321    
3322                                    if (pos == -1) {
3323                                            pos = tempLine.indexOf(StringPool.STAR);
3324                                    }
3325    
3326                                    if (pos == -1) {
3327                                            break;
3328                                    }
3329    
3330                                    String linePart = tempLine.substring(0, pos);
3331    
3332                                    int openParenthesisCount = StringUtil.count(
3333                                            linePart, StringPool.OPEN_PARENTHESIS);
3334                                    int closeParenthesisCount = StringUtil.count(
3335                                            linePart, StringPool.CLOSE_PARENTHESIS);
3336    
3337                                    if (openParenthesisCount == closeParenthesisCount) {
3338                                            return null;
3339                                    }
3340    
3341                                    tempLine =
3342                                            tempLine.substring(0, pos) + tempLine.substring(pos + 1);
3343                            }
3344    
3345                            int x = line.indexOf(StringPool.OPEN_PARENTHESIS);
3346    
3347                            if (x == 0) {
3348                                    x = line.indexOf(StringPool.OPEN_PARENTHESIS, 1);
3349                            }
3350    
3351                            if (x != -1) {
3352                                    int y = line.indexOf(StringPool.CLOSE_PARENTHESIS, x);
3353                                    int z = line.indexOf(StringPool.QUOTE);
3354    
3355                                    if (((x + 1) != y) && ((z == -1) || (z > x))) {
3356                                            char previousChar = line.charAt(x - 1);
3357    
3358                                            if ((previousChar != CharPool.CLOSE_PARENTHESIS) &&
3359                                                    (previousChar != CharPool.OPEN_PARENTHESIS) &&
3360                                                    (previousChar != CharPool.SPACE) &&
3361                                                    (previousLineLength + 1 + x) < 80) {
3362    
3363                                                    String linePart = line.substring(0, x + 1);
3364    
3365                                                    if (linePart.contains(StringPool.SPACE) ||
3366                                                            (linePart.startsWith(StringPool.OPEN_PARENTHESIS) &&
3367                                                             !linePart.contains(
3368                                                                     StringPool.CLOSE_PARENTHESIS))) {
3369    
3370                                                            return null;
3371                                                    }
3372    
3373                                                    return new Tuple(
3374                                                            previousLine + StringPool.SPACE, linePart, true);
3375                                            }
3376                                    }
3377                            }
3378                    }
3379    
3380                    if (previousLine.endsWith(StringPool.COMMA) &&
3381                            (previousLineTabCount == lineTabCount) &&
3382                            !previousLine.contains(StringPool.CLOSE_CURLY_BRACE)) {
3383    
3384                            int x = line.indexOf(StringPool.COMMA);
3385    
3386                            if (x != -1) {
3387                                    while ((previousLineLength + 1 + x) < 80) {
3388                                            String linePart = line.substring(0, x + 1);
3389    
3390                                            if (_isValidJavaParameter(linePart)) {
3391                                                    if (line.equals(linePart)) {
3392                                                            return new Tuple(
3393                                                                    previousLine + StringPool.SPACE + linePart);
3394                                                    }
3395                                                    else {
3396                                                            return new Tuple(
3397                                                                    previousLine + StringPool.SPACE,
3398                                                                    linePart + StringPool.SPACE, true);
3399                                                    }
3400                                            }
3401    
3402                                            String partAfterComma = line.substring(x + 1);
3403    
3404                                            int pos = partAfterComma.indexOf(StringPool.COMMA);
3405    
3406                                            if (pos == -1) {
3407                                                    break;
3408                                            }
3409    
3410                                            x = x + pos + 1;
3411                                    }
3412                            }
3413                            else if (!line.endsWith(StringPool.OPEN_PARENTHESIS) &&
3414                                             !line.endsWith(StringPool.PLUS) &&
3415                                             !line.endsWith(StringPool.PERIOD) &&
3416                                             (!line.startsWith("new ") ||
3417                                              !line.endsWith(StringPool.OPEN_CURLY_BRACE)) &&
3418                                             ((line.length() + previousLineLength) < 80)) {
3419    
3420                                    return new Tuple(previousLine + StringPool.SPACE + line);
3421                            }
3422                    }
3423    
3424                    if (!previousLine.endsWith(StringPool.OPEN_PARENTHESIS)) {
3425                            return null;
3426                    }
3427    
3428                    if (StringUtil.count(previousLine, StringPool.OPEN_PARENTHESIS) > 1) {
3429                            int pos = trimmedPreviousLine.lastIndexOf(
3430                                    StringPool.OPEN_PARENTHESIS, trimmedPreviousLine.length() - 2);
3431    
3432                            if ((pos > 0) &&
3433                                    Character.isLetterOrDigit(
3434                                            trimmedPreviousLine.charAt(pos -1 ))) {
3435    
3436                                    String filePart = trimmedPreviousLine.substring(pos + 1);
3437    
3438                                    if (!filePart.contains(StringPool.CLOSE_PARENTHESIS) &&
3439                                            !filePart.contains(StringPool.QUOTE)) {
3440    
3441                                            return new Tuple(previousLine, filePart, false);
3442                                    }
3443                            }
3444                    }
3445    
3446                    if ((line.length() + previousLineLength) > 80) {
3447                            return null;
3448                    }
3449    
3450                    if (line.endsWith(StringPool.SEMICOLON)) {
3451                            return new Tuple(previousLine + line);
3452                    }
3453    
3454                    if (((line.endsWith(StringPool.OPEN_CURLY_BRACE) &&
3455                              !line.startsWith("new ")) ||
3456                             line.endsWith(StringPool.CLOSE_PARENTHESIS)) &&
3457                            (trimmedPreviousLine.startsWith("else ") ||
3458                             trimmedPreviousLine.startsWith("if ") ||
3459                             trimmedPreviousLine.startsWith("private ") ||
3460                             trimmedPreviousLine.startsWith("protected ") ||
3461                             trimmedPreviousLine.startsWith("public "))) {
3462    
3463                            return new Tuple(previousLine + line);
3464                    }
3465    
3466                    return null;
3467            }
3468    
3469            private static String _getConstructorOrMethodName(String line, int pos) {
3470                    line = line.substring(0, pos);
3471    
3472                    int x = line.lastIndexOf(StringPool.SPACE);
3473    
3474                    return line.substring(x + 1);
3475            }
3476    
3477            private static String _getCopyright() throws IOException {
3478                    String copyright = _fileUtil.read("copyright.txt");
3479    
3480                    if (Validator.isNull(copyright)) {
3481                            copyright = _fileUtil.read("../copyright.txt");
3482                    }
3483    
3484                    if (Validator.isNull(copyright)) {
3485                            copyright = _fileUtil.read("../../copyright.txt");
3486                    }
3487    
3488                    return copyright;
3489            }
3490    
3491            private static String _getCustomCopyright(File file) throws IOException {
3492                    String absolutePath = _fileUtil.getAbsolutePath(file);
3493    
3494                    for (int x = absolutePath.length();;) {
3495                            x = absolutePath.lastIndexOf(StringPool.SLASH, x);
3496    
3497                            if (x == -1) {
3498                                    break;
3499                            }
3500    
3501                            String copyright = _fileUtil.read(
3502                                    absolutePath.substring(0, x + 1) + "copyright.txt");
3503    
3504                            if (Validator.isNotNull(copyright)) {
3505                                    return copyright;
3506                            }
3507    
3508                            x = x - 1;
3509                    }
3510    
3511                    return null;
3512            }
3513    
3514            private static Tuple _getJavaTermTuple(String line) {
3515                    int pos = line.indexOf(StringPool.OPEN_PARENTHESIS);
3516    
3517                    if (line.startsWith(StringPool.TAB + "public static final ") &&
3518                            (line.contains(StringPool.EQUAL) ||
3519                            (line.endsWith(StringPool.SEMICOLON) && (pos == -1)))) {
3520    
3521                            return new Tuple(
3522                                    _getVariableName(line), _TYPE_VARIABLE_PUBLIC_STATIC_FINAL);
3523                    }
3524                    else if (line.startsWith(StringPool.TAB + "public static ")) {
3525                            if (line.contains(StringPool.EQUAL) ||
3526                                    (line.endsWith(StringPool.SEMICOLON) && (pos == -1))) {
3527    
3528                                    return new Tuple(
3529                                            _getVariableName(line), _TYPE_VARIABLE_PUBLIC_STATIC);
3530                            }
3531    
3532                            if (pos != -1) {
3533                                    return new Tuple(
3534                                            _getConstructorOrMethodName(line, pos),
3535                                            _TYPE_METHOD_PUBLIC_STATIC);
3536                            }
3537    
3538                            if (line.startsWith(StringPool.TAB + "public static class ")) {
3539                                    return new Tuple(
3540                                            _getClassName(line), _TYPE_CLASS_PUBLIC_STATIC);
3541                            }
3542                    }
3543                    else if (line.startsWith(StringPool.TAB + "public ")) {
3544                            if (line.contains(StringPool.EQUAL) ||
3545                                    (line.endsWith(StringPool.SEMICOLON) && (pos == -1))) {
3546    
3547                                    return new Tuple(_getVariableName(line), _TYPE_VARIABLE_PUBLIC);
3548                            }
3549    
3550                            if (pos != -1) {
3551                                    int spaceCount = StringUtil.count(
3552                                            line.substring(0, pos), StringPool.SPACE);
3553    
3554                                    if (spaceCount == 1) {
3555                                            return new Tuple(
3556                                                    _getConstructorOrMethodName(line, pos),
3557                                                    _TYPE_CONSTRUCTOR_PUBLIC);
3558                                    }
3559    
3560                                    if (spaceCount > 1) {
3561                                            return new Tuple(
3562                                                    _getConstructorOrMethodName(line, pos),
3563                                                    _TYPE_METHOD_PUBLIC);
3564                                    }
3565                            }
3566                            else if (line.startsWith(StringPool.TAB + "public class ")) {
3567                                    return new Tuple(_getClassName(line), _TYPE_CLASS_PUBLIC);
3568                            }
3569                    }
3570                    else if (line.startsWith(StringPool.TAB + "protected static final ")) {
3571                            if (line.contains(StringPool.EQUAL) ||
3572                                    (line.endsWith(StringPool.SEMICOLON) && (pos == -1))) {
3573    
3574                                    return new Tuple(
3575                                            _getVariableName(line),
3576                                            _TYPE_VARIABLE_PROTECTED_STATIC_FINAL);
3577                            }
3578                    }
3579                    else if (line.startsWith(StringPool.TAB + "protected static ")) {
3580                            if (line.contains(StringPool.EQUAL) ||
3581                                    (line.endsWith(StringPool.SEMICOLON) && (pos == -1))) {
3582    
3583                                    return new Tuple(
3584                                            _getVariableName(line), _TYPE_VARIABLE_PROTECTED_STATIC);
3585                            }
3586    
3587                            if (pos != -1) {
3588                                    return new Tuple(
3589                                            _getConstructorOrMethodName(line, pos),
3590                                            _TYPE_METHOD_PROTECTED_STATIC);
3591                            }
3592    
3593                            if (line.startsWith(StringPool.TAB + "protected static class ")) {
3594                                    return new Tuple(
3595                                            _getClassName(line), _TYPE_CLASS_PROTECTED_STATIC);
3596                            }
3597                    }
3598                    else if (line.startsWith(StringPool.TAB + "protected ")) {
3599                            if (pos != -1) {
3600                                    if (!line.contains(StringPool.EQUAL)) {
3601                                            int spaceCount = StringUtil.count(
3602                                                    line.substring(0, pos), StringPool.SPACE);
3603    
3604                                            if (spaceCount == 1) {
3605                                                    return new Tuple(
3606                                                            _getConstructorOrMethodName(line, pos),
3607                                                            _TYPE_CONSTRUCTOR_PROTECTED);
3608                                            }
3609    
3610                                            if (spaceCount > 1) {
3611                                                    return new Tuple(
3612                                                            _getConstructorOrMethodName(line, pos),
3613                                                            _TYPE_METHOD_PROTECTED);
3614                                            }
3615                                    }
3616                            }
3617                            else if (line.startsWith(StringPool.TAB + "protected class ")) {
3618                                    return new Tuple(_getClassName(line), _TYPE_CLASS_PROTECTED);
3619                            }
3620    
3621                            return new Tuple(_getVariableName(line), _TYPE_VARIABLE_PROTECTED);
3622                    }
3623                    else if (line.startsWith(StringPool.TAB + "private static final ")) {
3624                            if (line.contains(StringPool.EQUAL) ||
3625                                    (line.endsWith(StringPool.SEMICOLON) && (pos == -1))) {
3626    
3627                                    return new Tuple(
3628                                            _getVariableName(line),
3629                                            _TYPE_VARIABLE_PRIVATE_STATIC_FINAL);
3630                            }
3631                    }
3632                    else if (line.startsWith(StringPool.TAB + "private static ")) {
3633                            if (line.contains(StringPool.EQUAL) ||
3634                                    (line.endsWith(StringPool.SEMICOLON) && (pos == -1))) {
3635    
3636                                    return new Tuple(
3637                                            _getVariableName(line), _TYPE_VARIABLE_PRIVATE_STATIC);
3638                            }
3639    
3640                            if (pos != -1) {
3641                                    return new Tuple(
3642                                            _getConstructorOrMethodName(line, pos),
3643                                            _TYPE_METHOD_PRIVATE_STATIC);
3644                            }
3645    
3646                            if (line.startsWith(StringPool.TAB + "private static class ")) {
3647                                    return new Tuple(
3648                                            _getClassName(line), _TYPE_CLASS_PRIVATE_STATIC);
3649                            }
3650                    }
3651                    else if (line.startsWith(StringPool.TAB + "private ")) {
3652                            if (line.contains(StringPool.EQUAL) ||
3653                                    (line.endsWith(StringPool.SEMICOLON) && (pos == -1))) {
3654    
3655                                    return new Tuple(
3656                                            _getVariableName(line), _TYPE_VARIABLE_PRIVATE);
3657                            }
3658    
3659                            if (pos != -1) {
3660                                    int spaceCount = StringUtil.count(
3661                                            line.substring(0, pos), StringPool.SPACE);
3662    
3663                                    if (spaceCount == 1) {
3664                                            return new Tuple(
3665                                                    _getConstructorOrMethodName(line, pos),
3666                                                    _TYPE_CONSTRUCTOR_PRIVATE);
3667                                    }
3668    
3669                                    if (spaceCount > 1) {
3670                                            return new Tuple(
3671                                                    _getConstructorOrMethodName(line, pos),
3672                                                    _TYPE_METHOD_PRIVATE);
3673                                    }
3674                            }
3675                            else if (line.startsWith(StringPool.TAB + "private class ")) {
3676                                    return new Tuple(_getClassName(line), _TYPE_CLASS_PRIVATE);
3677                            }
3678                    }
3679    
3680                    return null;
3681            }
3682    
3683            private static List<String> _getJSPDuplicateImports(
3684                    String fileName, String content, List<String> importLines) {
3685    
3686                    List<String> duplicateImports = new ArrayList<String>();
3687    
3688                    for (String importLine : importLines) {
3689                            int x = content.indexOf("<%@ include file=");
3690    
3691                            if (x == -1) {
3692                                    continue;
3693                            }
3694    
3695                            int y = content.indexOf("<%@ page import=");
3696    
3697                            if (y == -1) {
3698                                    continue;
3699                            }
3700    
3701                            if ((x < y) && _isJSPDuplicateImport(fileName, importLine, false)) {
3702                                    duplicateImports.add(importLine);
3703                            }
3704                    }
3705    
3706                    return duplicateImports;
3707            }
3708    
3709            private static String[] _getLanguageKeys(Matcher matcher) {
3710                    if (matcher.groupCount() > 0) {
3711                            String languageKey = matcher.group(1);
3712    
3713                            if (Validator.isNotNull(languageKey)) {
3714                                    return new String[] {languageKey};
3715                            }
3716                    }
3717    
3718                    StringBundler sb = new StringBundler();
3719    
3720                    String match = matcher.group();
3721    
3722                    int count = 0;
3723    
3724                    for (int i = 0; i < match.length(); i++) {
3725                            char c = match.charAt(i);
3726    
3727                            switch (c) {
3728                                    case CharPool.CLOSE_PARENTHESIS:
3729                                            if (count <= 1) {
3730                                                    return new String[0];
3731                                            }
3732    
3733                                            count--;
3734    
3735                                            break;
3736    
3737                                    case CharPool.OPEN_PARENTHESIS:
3738                                            count++;
3739    
3740                                            break;
3741    
3742                                    case CharPool.QUOTE:
3743                                            if (count > 1) {
3744                                                    break;
3745                                            }
3746    
3747                                            while (i < match.length()) {
3748                                                    i++;
3749    
3750                                                    if (match.charAt(i) == CharPool.QUOTE) {
3751                                                            String languageKey = sb.toString();
3752    
3753                                                            if (match.startsWith("names")) {
3754                                                                    return StringUtil.split(languageKey);
3755                                                            }
3756                                                            else {
3757                                                                    return new String[] {languageKey};
3758                                                            }
3759    
3760                                                    }
3761    
3762                                                    sb.append(match.charAt(i));
3763                                            }
3764                            }
3765                    }
3766    
3767                    return new String[0];
3768            }
3769    
3770            private static int _getLineLength(String line) {
3771                    int lineLength = 0;
3772    
3773                    int tabLength = 4;
3774    
3775                    for (char c : line.toCharArray()) {
3776                            if (c == CharPool.TAB) {
3777                                    for (int i = 0; i < tabLength; i++) {
3778                                            lineLength++;
3779                                    }
3780    
3781                                    tabLength = 4;
3782                            }
3783                            else {
3784                                    lineLength++;
3785    
3786                                    tabLength--;
3787    
3788                                    if (tabLength <= 0) {
3789                                            tabLength = 4;
3790                                    }
3791                            }
3792                    }
3793    
3794                    return lineLength;
3795            }
3796    
3797            private static String _getOldCopyright() throws IOException {
3798                    String copyright = _fileUtil.read("old-copyright.txt");
3799    
3800                    if (Validator.isNull(copyright)) {
3801                            copyright = _fileUtil.read("../old-copyright.txt");
3802                    }
3803    
3804                    if (Validator.isNull(copyright)) {
3805                            copyright = _fileUtil.read("../../old-copyright.txt");
3806                    }
3807    
3808                    return copyright;
3809            }
3810    
3811            private static Properties _getPluginExclusionsProperties(String fileName)
3812                    throws IOException {
3813    
3814                    FileInputStream fileInputStream = null;
3815    
3816                    int level = 0;
3817    
3818                    try {
3819                            fileInputStream = new FileInputStream(fileName);
3820                    }
3821                    catch (FileNotFoundException fnfe) {
3822                    }
3823    
3824                    if (fileInputStream == null) {
3825                            try {
3826                                    fileInputStream = new FileInputStream("../" + fileName);
3827    
3828                                    level = 1;
3829                            }
3830                            catch (FileNotFoundException fnfe) {
3831                            }
3832                    }
3833    
3834                    if (fileInputStream == null) {
3835                            try {
3836                                    fileInputStream = new FileInputStream("../../" + fileName);
3837    
3838                                    level = 2;
3839                            }
3840                            catch (FileNotFoundException fnfe) {
3841                                    return null;
3842                            }
3843                    }
3844    
3845                    Properties properties = new Properties();
3846    
3847                    properties.load(fileInputStream);
3848    
3849                    if (level > 0) {
3850                            properties = _stripTopLevelDirectories(properties, level);
3851                    }
3852    
3853                    return properties;
3854            }
3855    
3856            private static Collection<String> _getPluginJavaFiles() {
3857                    String basedir = "./";
3858    
3859                    Collection<String> fileNames = new TreeSet<String>();
3860    
3861                    DirectoryScanner directoryScanner = new DirectoryScanner();
3862    
3863                    directoryScanner.setBasedir(basedir);
3864    
3865                    String[] excludes = {
3866                            "**\\bin\\**", "**\\model\\*Clp.java",
3867                            "**\\model\\impl\\*BaseImpl.java", "**\\model\\impl\\*Model.java",
3868                            "**\\model\\impl\\*ModelImpl.java",
3869                            "**\\service\\**\\model\\*Model.java",
3870                            "**\\service\\**\\model\\*Soap.java",
3871                            "**\\service\\**\\model\\*Wrapper.java",
3872                            "**\\service\\**\\service\\*Service.java",
3873                            "**\\service\\**\\service\\*ServiceClp.java",
3874                            "**\\service\\**\\service\\*ServiceFactory.java",
3875                            "**\\service\\**\\service\\*ServiceUtil.java",
3876                            "**\\service\\**\\service\\*ServiceWrapper.java",
3877                            "**\\service\\**\\service\\ClpSerializer.java",
3878                            "**\\service\\**\\service\\messaging\\*ClpMessageListener.java",
3879                            "**\\service\\**\\service\\persistence\\*Finder.java",
3880                            "**\\service\\**\\service\\persistence\\*Persistence.java",
3881                            "**\\service\\**\\service\\persistence\\*Util.java",
3882                            "**\\service\\base\\*ServiceBaseImpl.java",
3883                            "**\\service\\base\\*ServiceClpInvoker.java",
3884                            "**\\service\\http\\*JSONSerializer.java",
3885                            "**\\service\\http\\*ServiceHttp.java",
3886                            "**\\service\\http\\*ServiceJSON.java",
3887                            "**\\service\\http\\*ServiceSoap.java",
3888                            "**\\service\\persistence\\*PersistenceImpl.java", "**\\tmp\\**"
3889                    };
3890    
3891                    excludes = ArrayUtil.append(excludes, _excludes);
3892    
3893                    directoryScanner.setExcludes(excludes);
3894    
3895                    directoryScanner.setIncludes(new String[] {"**\\*.java"});
3896    
3897                    fileNames.addAll(_sourceFormatterHelper.scanForFiles(directoryScanner));
3898    
3899                    return fileNames;
3900            }
3901    
3902            private static Properties _getPortalExclusionsProperties(String fileName)
3903                    throws IOException {
3904    
3905                    Properties properties = new Properties();
3906    
3907                    ClassLoader classLoader = SourceFormatter.class.getClassLoader();
3908    
3909                    String sourceFormatterExclusions = System.getProperty(
3910                            "source-formatter-exclusions",
3911                            "com/liferay/portal/tools/dependencies/" + fileName);
3912    
3913                    URL url = classLoader.getResource(sourceFormatterExclusions);
3914    
3915                    if (url == null) {
3916                            return null;
3917                    }
3918    
3919                    InputStream inputStream = url.openStream();
3920    
3921                    properties.load(inputStream);
3922    
3923                    inputStream.close();
3924    
3925                    return properties;
3926            }
3927    
3928            private static Collection<String> _getPortalJavaFiles() {
3929                    String basedir = "./";
3930    
3931                    Collection<String> fileNames = new TreeSet<String>();
3932    
3933                    DirectoryScanner directoryScanner = new DirectoryScanner();
3934    
3935                    directoryScanner.setBasedir(basedir);
3936    
3937                    String[] excludes = {
3938                            "**\\*_IW.java", "**\\PropsValues.java", "**\\bin\\**",
3939                            "**\\classes\\*", "**\\counter\\service\\**", "**\\jsp\\*",
3940                            "**\\model\\impl\\*BaseImpl.java", "**\\model\\impl\\*Model.java",
3941                            "**\\model\\impl\\*ModelImpl.java", "**\\portal\\service\\**",
3942                            "**\\portal-client\\**",
3943                            "**\\portal-service\\**\\model\\*Model.java",
3944                            "**\\portal-service\\**\\model\\*Soap.java",
3945                            "**\\portal-service\\**\\model\\*Wrapper.java",
3946                            "**\\portal-web\\classes\\**\\*.java",
3947                            "**\\portal-web\\test\\**\\*Test.java",
3948                            "**\\portal-web\\test\\**\\*Tests.java",
3949                            "**\\portlet\\**\\service\\**", "**\\tmp\\**", "**\\tools\\tck\\**"
3950                    };
3951    
3952                    excludes = ArrayUtil.append(excludes, _excludes);
3953    
3954                    directoryScanner.setExcludes(excludes);
3955    
3956                    directoryScanner.setIncludes(new String[] {"**\\*.java"});
3957    
3958                    fileNames.addAll(_sourceFormatterHelper.scanForFiles(directoryScanner));
3959    
3960                    directoryScanner = new DirectoryScanner();
3961    
3962                    directoryScanner.setBasedir(basedir);
3963    
3964                    excludes = new String[] {
3965                            "**\\bin\\**", "**\\portal-client\\**", "**\\tools\\ext_tmpl\\**",
3966                            "**\\*_IW.java", "**\\test\\**\\*PersistenceTest.java"
3967                    };
3968    
3969                    excludes = ArrayUtil.append(excludes, _excludes);
3970    
3971                    directoryScanner.setExcludes(excludes);
3972    
3973                    directoryScanner.setIncludes(
3974                            new String[] {
3975                                    "**\\com\\liferay\\portal\\service\\ServiceContext*.java",
3976                                    "**\\model\\BaseModel.java",
3977                                    "**\\model\\impl\\BaseModelImpl.java",
3978                                    "**\\service\\Base*.java",
3979                                    "**\\service\\PersistedModelLocalService*.java",
3980                                    "**\\service\\base\\PrincipalBean.java",
3981                                    "**\\service\\http\\*HttpTest.java",
3982                                    "**\\service\\http\\*SoapTest.java",
3983                                    "**\\service\\http\\TunnelUtil.java",
3984                                    "**\\service\\impl\\*.java", "**\\service\\jms\\*.java",
3985                                    "**\\service\\permission\\*.java",
3986                                    "**\\service\\persistence\\BasePersistence.java",
3987                                    "**\\service\\persistence\\BatchSession*.java",
3988                                    "**\\service\\persistence\\*FinderImpl.java",
3989                                    "**\\service\\persistence\\*Query.java",
3990                                    "**\\service\\persistence\\impl\\BasePersistenceImpl.java",
3991                                    "**\\portal-impl\\test\\**\\*.java",
3992                                    "**\\portal-service\\**\\liferay\\documentlibrary\\**.java",
3993                                    "**\\portal-service\\**\\liferay\\lock\\**.java",
3994                                    "**\\portal-service\\**\\liferay\\mail\\**.java",
3995                                    "**\\util-bridges\\**\\*.java"
3996                            });
3997    
3998                    fileNames.addAll(_sourceFormatterHelper.scanForFiles(directoryScanner));
3999    
4000                    return fileNames;
4001            }
4002    
4003            private static String _getTaglibRegex(String quoteType) {
4004                    StringBuilder sb = new StringBuilder();
4005    
4006                    sb.append("<(");
4007    
4008                    for (int i = 0; i < _TAG_LIBRARIES.length; i++) {
4009                            sb.append(_TAG_LIBRARIES[i]);
4010                            sb.append(StringPool.PIPE);
4011                    }
4012    
4013                    sb.deleteCharAt(sb.length() - 1);
4014                    sb.append("):([^>]|%>)*");
4015                    sb.append(quoteType);
4016                    sb.append("<%=.*");
4017                    sb.append(quoteType);
4018                    sb.append(".*%>");
4019                    sb.append(quoteType);
4020                    sb.append("([^>]|%>)*>");
4021    
4022                    return sb.toString();
4023            }
4024    
4025            private static String _getVariableName(String line) {
4026                    int x = line.indexOf(StringPool.EQUAL);
4027                    int y = line.lastIndexOf(StringPool.SPACE);
4028    
4029                    if (x != -1) {
4030                            line = line.substring(0, x);
4031                            line = StringUtil.trim(line);
4032    
4033                            y = line.lastIndexOf(StringPool.SPACE);
4034    
4035                            return line.substring(y + 1);
4036                    }
4037    
4038                    if (line.endsWith(StringPool.SEMICOLON)) {
4039                            return line.substring(y + 1, line.length() - 1);
4040                    }
4041    
4042                    return StringPool.BLANK;
4043            }
4044    
4045            private static boolean _hasUnsortedConstructorsOrMethods(
4046                    List<String> previousMethodParameterTypes,
4047                    List<String> methodParameterTypes) {
4048    
4049                    if (methodParameterTypes.isEmpty()) {
4050                            return true;
4051                    }
4052    
4053                    for (int i = 0; i < previousMethodParameterTypes.size(); i++) {
4054                            if (methodParameterTypes.size() < (i + 1)) {
4055                                    return true;
4056                            }
4057    
4058                            String previousParameterType = previousMethodParameterTypes.get(i);
4059    
4060                            if (previousParameterType.endsWith("...")) {
4061                                    previousParameterType = StringUtil.replaceLast(
4062                                            previousParameterType, "...", StringPool.BLANK);
4063                            }
4064    
4065                            String parameterType = methodParameterTypes.get(i);
4066    
4067                            if (previousParameterType.compareToIgnoreCase(parameterType) < 0) {
4068                                    return false;
4069                            }
4070    
4071                            if (previousParameterType.compareToIgnoreCase(parameterType) > 0) {
4072                                    return true;
4073                            }
4074    
4075                            if (previousParameterType.compareTo(parameterType) > 0) {
4076                                    return false;
4077                            }
4078    
4079                            if (previousParameterType.compareTo(parameterType) < 0) {
4080                                    return true;
4081                            }
4082                    }
4083    
4084                    return false;
4085            }
4086    
4087            private static boolean _hasUnsortedJavaTerms(
4088                    String fileName, String previousJavaTermName, String javaTermName,
4089                    int javaTermType) {
4090    
4091                    if (Validator.isNull(previousJavaTermName) ||
4092                            Validator.isNull(javaTermName)) {
4093    
4094                            return false;
4095                    }
4096    
4097                    if (javaTermType == _TYPE_VARIABLE_PRIVATE_STATIC) {
4098                            if (javaTermName.equals("_log")) {
4099                                    return true;
4100                            }
4101    
4102                            if (previousJavaTermName.equals("_instance") ||
4103                                    previousJavaTermName.equals("_log")) {
4104    
4105                                    return false;
4106                            }
4107    
4108                            if (javaTermName.equals("_instance")) {
4109                                    return true;
4110                            }
4111                    }
4112    
4113                    String javaTermNameLowerCase = javaTermName.toLowerCase();
4114                    String previousJavaTermNameLowerCase =
4115                            previousJavaTermName.toLowerCase();
4116    
4117                    if (fileName.contains("persistence") &&
4118                            ((previousJavaTermName.startsWith("doCount") &&
4119                              javaTermName.startsWith("doCount")) ||
4120                             (previousJavaTermName.startsWith("doFind") &&
4121                              javaTermName.startsWith("doFind")) ||
4122                             (previousJavaTermNameLowerCase.startsWith("count") &&
4123                              javaTermNameLowerCase.startsWith("count")) ||
4124                             (previousJavaTermNameLowerCase.startsWith("filter") &&
4125                              javaTermNameLowerCase.startsWith("filter")) ||
4126                             (previousJavaTermNameLowerCase.startsWith("find") &&
4127                              javaTermNameLowerCase.startsWith("find")) ||
4128                             (previousJavaTermNameLowerCase.startsWith("join") &&
4129                              javaTermNameLowerCase.startsWith("join")))) {
4130    
4131                            return false;
4132                    }
4133    
4134                    if (previousJavaTermName.compareToIgnoreCase(javaTermName) <= 0) {
4135                            return false;
4136                    }
4137    
4138                    return true;
4139            }
4140    
4141            private static boolean _isGenerated(String content) {
4142                    if (content.contains("* @generated") || content.contains("$ANTLR")) {
4143                            return true;
4144                    }
4145                    else {
4146                            return false;
4147                    }
4148            }
4149    
4150            private static boolean _isInJavaTermTypeGroup(
4151                    int javaTermType, int[] javaTermTypeGroup) {
4152    
4153                    for (int type : javaTermTypeGroup) {
4154                            if (javaTermType == type) {
4155                                    return true;
4156                            }
4157                    }
4158    
4159                    return false;
4160            }
4161    
4162            private static boolean _isJSPAttributName(String attributeName) {
4163                    if (Validator.isNull(attributeName)) {
4164                            return false;
4165                    }
4166    
4167                    Matcher matcher = _jspAttributeNamePattern.matcher(attributeName);
4168    
4169                    return matcher.matches();
4170            }
4171    
4172            private static boolean _isJSPDuplicateImport(
4173                    String fileName, String importLine, boolean checkFile) {
4174    
4175                    String content = _jspContents.get(fileName);
4176    
4177                    if (Validator.isNull(content)) {
4178                            return false;
4179                    }
4180    
4181                    int x = importLine.indexOf("page");
4182    
4183                    if (x == -1) {
4184                            return false;
4185                    }
4186    
4187                    if (checkFile && content.contains(importLine.substring(x))) {
4188                            return true;
4189                    }
4190    
4191                    int y = content.indexOf("<%@ include file=");
4192    
4193                    if (y == -1) {
4194                            return false;
4195                    }
4196    
4197                    y = content.indexOf(StringPool.QUOTE, y);
4198    
4199                    if (y == -1) {
4200                            return false;
4201                    }
4202    
4203                    int z = content.indexOf(StringPool.QUOTE, y + 1);
4204    
4205                    if (z == -1) {
4206                            return false;
4207                    }
4208    
4209                    String includeFileName = content.substring(y + 1, z);
4210    
4211                    String docrootPath = fileName.substring(
4212                            0, fileName.indexOf("docroot") + 7);
4213    
4214                    includeFileName = docrootPath + includeFileName;
4215    
4216                    return _isJSPDuplicateImport(includeFileName, importLine, true);
4217            }
4218    
4219            private static boolean _isJSPImportRequired(
4220                    String fileName, String className, Set<String> includeFileNames,
4221                    Set<String> checkedFileNames) {
4222    
4223                    if (checkedFileNames.contains(fileName)) {
4224                            return false;
4225                    }
4226    
4227                    checkedFileNames.add(fileName);
4228    
4229                    String content = _jspContents.get(fileName);
4230    
4231                    if (Validator.isNull(content)) {
4232                            return false;
4233                    }
4234    
4235                    Pattern pattern = Pattern.compile(
4236                            "[^A-Za-z0-9_]" + className + "[^A-Za-z0-9_\"]");
4237    
4238                    Matcher matcher = pattern.matcher(content);
4239    
4240                    if (matcher.find()) {
4241                            return true;
4242                    }
4243    
4244                    _addJSPIncludeFileNames(fileName, includeFileNames);
4245    
4246                    String docrootPath = fileName.substring(
4247                            0, fileName.indexOf("docroot") + 7);
4248    
4249                    fileName = fileName.replaceFirst(docrootPath, StringPool.BLANK);
4250    
4251                    if (fileName.endsWith("init.jsp") ||
4252                            fileName.contains("init-ext.jsp")) {
4253    
4254                            _addJSPReferenceFileNames(fileName, includeFileNames);
4255                    }
4256    
4257                    String[] includeFileNamesArray = includeFileNames.toArray(
4258                            new String[includeFileNames.size()]);
4259    
4260                    for (String includeFileName : includeFileNamesArray) {
4261                            if (!checkedFileNames.contains(includeFileName) &&
4262                                    _isJSPImportRequired(
4263                                            includeFileName, className, includeFileNames,
4264                                            checkedFileNames)) {
4265    
4266                                    return true;
4267                            }
4268                    }
4269    
4270                    return false;
4271            }
4272    
4273            private static boolean _isPortalSource() {
4274                    String basedir = "./";
4275    
4276                    if (_fileUtil.exists(basedir + "portal-impl")) {
4277                            return true;
4278                    }
4279                    else {
4280                            return false;
4281                    }
4282            }
4283    
4284            private static boolean _isValidJavaParameter(String javaParameter) {
4285                    int quoteCount = StringUtil.count(javaParameter, StringPool.QUOTE);
4286    
4287                    if ((quoteCount % 2) == 1) {
4288                            return false;
4289                    }
4290    
4291                    javaParameter = _stripQuotes(javaParameter);
4292    
4293                    int openParenthesisCount = StringUtil.count(
4294                            javaParameter, StringPool.OPEN_PARENTHESIS);
4295                    int closeParenthesisCount = StringUtil.count(
4296                            javaParameter, StringPool.CLOSE_PARENTHESIS);
4297                    int lessThanCount = StringUtil.count(
4298                            javaParameter, StringPool.LESS_THAN);
4299                    int greaterThanCount = StringUtil.count(
4300                            javaParameter, StringPool.GREATER_THAN);
4301                    int openCurlyBraceCount = StringUtil.count(
4302                            javaParameter, StringPool.OPEN_CURLY_BRACE);
4303                    int closeCurlyBraceCount = StringUtil.count(
4304                            javaParameter, StringPool.CLOSE_CURLY_BRACE);
4305    
4306                    if ((openParenthesisCount == closeParenthesisCount) &&
4307                            (lessThanCount == greaterThanCount) &&
4308                            (openCurlyBraceCount == closeCurlyBraceCount)) {
4309    
4310                            return true;
4311                    }
4312    
4313                    return false;
4314            }
4315    
4316            private static String _replacePrimitiveWrapperInstantiation(
4317                    String fileName, String line, int lineCount) {
4318    
4319                    if (true) {
4320                            return line;
4321                    }
4322    
4323                    String newLine = StringUtil.replace(
4324                            line,
4325                            new String[] {
4326                                    "new Boolean(", "new Byte(", "new Character(", "new Integer(",
4327                                    "new Long(", "new Short("
4328                            },
4329                            new String[] {
4330                                    "Boolean.valueOf(", "Byte.valueOf(", "Character.valueOf(",
4331                                    "Integer.valueOf(", "Long.valueOf(", "Short.valueOf("
4332                            });
4333    
4334                    if (!line.equals(newLine)) {
4335                            _sourceFormatterHelper.printError(
4336                                    fileName, "> new Primitive(: " + fileName + " " + lineCount);
4337                    }
4338    
4339                    return newLine;
4340            }
4341    
4342            private static String _sortExceptions(String line) {
4343                    if (!line.endsWith(StringPool.OPEN_CURLY_BRACE) &&
4344                            !line.endsWith(StringPool.SEMICOLON)) {
4345    
4346                            return line;
4347                    }
4348    
4349                    int x = line.indexOf("throws ");
4350    
4351                    if (x == -1) {
4352                            return line;
4353                    }
4354    
4355                    String previousException = StringPool.BLANK;
4356    
4357                    String[] exceptions = StringUtil.split(
4358                            line.substring(x), CharPool.SPACE);
4359    
4360                    for (int i = 1; i < exceptions.length; i++) {
4361                            String exception = exceptions[i];
4362    
4363                            if (exception.equals(StringPool.OPEN_CURLY_BRACE)) {
4364                                    break;
4365                            }
4366    
4367                            if (exception.endsWith(StringPool.COMMA) ||
4368                                    exception.endsWith(StringPool.SEMICOLON)) {
4369    
4370                                    exception = exception.substring(0, exception.length() - 1);
4371                            }
4372    
4373                            if (Validator.isNotNull(previousException) &&
4374                                    (previousException.compareToIgnoreCase(exception) > 0)) {
4375    
4376                                    return StringUtil.replace(
4377                                            line, previousException + ", " + exception,
4378                                            exception + ", " + previousException);
4379                            }
4380    
4381                            previousException = exception;
4382                    }
4383    
4384                    return line;
4385            }
4386    
4387            private static String _sortJSPAttributes(
4388                    String fileName, String line, int lineCount) {
4389    
4390                    String s = line;
4391    
4392                    int x = s.indexOf(StringPool.SPACE);
4393    
4394                    if (x == -1) {
4395                            return line;
4396                    }
4397    
4398                    s = s.substring(x + 1);
4399    
4400                    String previousAttribute = null;
4401                    String previousAttributeAndValue = null;
4402    
4403                    boolean wrongOrder = false;
4404    
4405                    for (x = 0;;) {
4406                            x = s.indexOf(StringPool.EQUAL);
4407    
4408                            if ((x == -1) || (s.length() <= (x + 1))) {
4409                                    return line;
4410                            }
4411    
4412                            String attribute = s.substring(0, x);
4413    
4414                            if (!_isJSPAttributName(attribute)) {
4415                                    return line;
4416                            }
4417    
4418                            if (Validator.isNotNull(previousAttribute) &&
4419                                    (previousAttribute.compareTo(attribute) > 0)) {
4420    
4421                                    wrongOrder = true;
4422                            }
4423    
4424                            s = s.substring(x + 1);
4425    
4426                            char delimeter = s.charAt(0);
4427    
4428                            if ((delimeter != CharPool.APOSTROPHE) &&
4429                                    (delimeter != CharPool.QUOTE)) {
4430    
4431                                    _sourceFormatterHelper.printError(
4432                                            fileName, "delimeter: " + fileName + " " + lineCount);
4433    
4434                                    return line;
4435                            }
4436    
4437                            s = s.substring(1);
4438    
4439                            int y = s.indexOf(delimeter);
4440    
4441                            if ((y == -1) || (s.length() <= (y + 1))) {
4442                                    return line;
4443                            }
4444    
4445                            String value = s.substring(0, y);
4446    
4447                            if ((delimeter == CharPool.APOSTROPHE) &&
4448                                    !value.contains(StringPool.QUOTE)) {
4449    
4450                                    return StringUtil.replace(
4451                                            line, StringPool.APOSTROPHE + value + StringPool.APOSTROPHE,
4452                                            StringPool.QUOTE + value + StringPool.QUOTE);
4453                            }
4454    
4455                            if (value.contains("<%") && !value.contains("%>")) {
4456                                    int z = s.indexOf("%>");
4457    
4458                                    if (z == -1) {
4459                                            return line;
4460                                    }
4461    
4462                                    y = s.substring(z).indexOf(delimeter);
4463    
4464                                    value = s.substring(0, y + z);
4465                            }
4466    
4467                            StringBundler sb = new StringBundler(5);
4468    
4469                            sb.append(attribute);
4470                            sb.append(StringPool.EQUAL);
4471                            sb.append(delimeter);
4472                            sb.append(value);
4473                            sb.append(delimeter);
4474    
4475                            String currentAttributeAndValue = sb.toString();
4476    
4477                            if (wrongOrder) {
4478                                    if (line.contains(currentAttributeAndValue) &&
4479                                            line.contains(previousAttributeAndValue)) {
4480    
4481                                            line = StringUtil.replaceFirst(
4482                                                    line, previousAttributeAndValue,
4483                                                    currentAttributeAndValue);
4484    
4485                                            line = StringUtil.replaceLast(
4486                                                    line, currentAttributeAndValue,
4487                                                    previousAttributeAndValue);
4488                                    }
4489    
4490                                    return line;
4491                            }
4492    
4493                            s = s.substring(y + 1);
4494    
4495                            s = StringUtil.trimLeading(s);
4496    
4497                            previousAttribute = attribute;
4498                            previousAttributeAndValue = currentAttributeAndValue;
4499                    }
4500            }
4501    
4502            private static String _stripJSPImports(String fileName, String content)
4503                    throws IOException {
4504    
4505                    fileName = fileName.replace(
4506                            CharPool.BACK_SLASH, CharPool.FORWARD_SLASH);
4507    
4508                    if (!fileName.contains("docroot") ||
4509                            fileName.endsWith("init-ext.jsp")) {
4510    
4511                            return content;
4512                    }
4513    
4514                    Matcher matcher = _jspImportPattern.matcher(content);
4515    
4516                    if (!matcher.find()) {
4517                            return content;
4518                    }
4519    
4520                    String imports = matcher.group();
4521    
4522                    imports = StringUtil.replace(
4523                            imports, new String[] {"%><%@\r\n", "%><%@\n"},
4524                            new String[] {"%>\r\n<%@ ", "%>\n<%@ "});
4525    
4526                    if (!fileName.endsWith("html/common/init.jsp") &&
4527                            !fileName.endsWith("html/portal/init.jsp")) {
4528    
4529                            List<String> importLines = new ArrayList<String>();
4530    
4531                            UnsyncBufferedReader unsyncBufferedReader =
4532                                    new UnsyncBufferedReader(new UnsyncStringReader(imports));
4533    
4534                            String line = null;
4535    
4536                            while ((line = unsyncBufferedReader.readLine()) != null) {
4537                                    if (line.contains("import=")) {
4538                                            importLines.add(line);
4539                                    }
4540                            }
4541    
4542                            List<String> unneededImports = _getJSPDuplicateImports(
4543                                    fileName, content, importLines);
4544    
4545                            _addJSPUnusedImports(fileName, importLines, unneededImports);
4546    
4547                            for (String unneededImport : unneededImports) {
4548                                    imports = StringUtil.replace(
4549                                            imports, unneededImport, StringPool.BLANK);
4550                            }
4551                    }
4552    
4553                    imports = _formatImports(imports, 17);
4554    
4555                    String beforeImports = content.substring(0, matcher.start());
4556    
4557                    if (Validator.isNull(imports)) {
4558                            beforeImports = StringUtil.replaceLast(
4559                                    beforeImports, "\n", StringPool.BLANK);
4560                    }
4561    
4562                    String afterImports = content.substring(matcher.end());
4563    
4564                    if (Validator.isNull(afterImports)) {
4565                            imports = StringUtil.replaceLast(imports, "\n", StringPool.BLANK);
4566    
4567                            content = beforeImports + imports;
4568    
4569                            return content;
4570                    }
4571    
4572                    content = beforeImports + imports + "\n" + afterImports;
4573    
4574                    return content;
4575            }
4576    
4577            private static String _stripQuotes(String s) {
4578                    String[] parts = StringUtil.split(s, CharPool.QUOTE);
4579    
4580                    int i = 1;
4581    
4582                    while (i < parts.length) {
4583                            s = StringUtil.replaceFirst(
4584                                    s, StringPool.QUOTE + parts[i] + StringPool.QUOTE,
4585                                    StringPool.BLANK);
4586    
4587                            i = i + 2;
4588                    }
4589    
4590                    return s;
4591            }
4592    
4593            private static String _stripRedundantParentheses(String s) {
4594                    for (int x = 0;;) {
4595                            x = s.indexOf(StringPool.OPEN_PARENTHESIS, x + 1);
4596                            int y = s.indexOf(StringPool.CLOSE_PARENTHESIS, x);
4597    
4598                            if ((x == -1) || (y == -1)) {
4599                                    return s;
4600                            }
4601    
4602                            String linePart = s.substring(x + 1, y);
4603    
4604                            linePart = StringUtil.replace(
4605                                    linePart, StringPool.COMMA, StringPool.BLANK);
4606    
4607                            if (Validator.isAlphanumericName(linePart) ||
4608                                    Validator.isNull(linePart)) {
4609    
4610                                    s = s.substring(0, x) + s.substring(y + 1);
4611                            }
4612                    }
4613            }
4614    
4615            private static Properties _stripTopLevelDirectories(
4616                            Properties properties, int level)
4617                    throws IOException {
4618    
4619                    File dir = new File(".");
4620    
4621                    String dirName = dir.getCanonicalPath();
4622    
4623                    dirName = StringUtil.replace(
4624                            dirName, StringPool.BACK_SLASH, StringPool.SLASH);
4625    
4626                    int pos = dirName.length();
4627    
4628                    for (int i = 0; i < level; i++) {
4629                            pos = dirName.lastIndexOf(StringPool.SLASH, pos - 1);
4630                    }
4631    
4632                    String topLevelDirNames = dirName.substring(pos + 1) + StringPool.SLASH;
4633    
4634                    Properties newProperties = new Properties();
4635    
4636                    for (Map.Entry<Object, Object> entry : properties.entrySet()) {
4637                            String key = (String)entry.getKey();
4638    
4639                            if (!key.startsWith(topLevelDirNames)) {
4640                                    continue;
4641                            }
4642    
4643                            key = StringUtil.replaceFirst(
4644                                    key, topLevelDirNames, StringPool.BLANK);
4645    
4646                            String value = (String)entry.getValue();
4647    
4648                            newProperties.setProperty(key, value);
4649                    }
4650    
4651                    return newProperties;
4652            }
4653    
4654            private static String _trimContent(String content) throws IOException {
4655                    StringBundler sb = new StringBundler();
4656    
4657                    UnsyncBufferedReader unsyncBufferedReader = new UnsyncBufferedReader(
4658                            new UnsyncStringReader(content));
4659    
4660                    String line = null;
4661    
4662                    while ((line = unsyncBufferedReader.readLine()) != null) {
4663                            sb.append(_trimLine(line));
4664                            sb.append("\n");
4665                    }
4666    
4667                    unsyncBufferedReader.close();
4668    
4669                    content = sb.toString();
4670    
4671                    if (content.endsWith("\n")) {
4672                            content = content.substring(0, content.length() - 1);
4673                    }
4674    
4675                    return content;
4676            }
4677    
4678            private static String _trimLine(String line) {
4679                    if (line.trim().length() == 0) {
4680                            return StringPool.BLANK;
4681                    }
4682    
4683                    line = StringUtil.trimTrailing(line);
4684    
4685                    if (!line.startsWith(StringPool.SPACE) || line.startsWith(" *")) {
4686                            return line;
4687                    }
4688    
4689                    if (!line.startsWith(StringPool.FOUR_SPACES)) {
4690                            while (line.startsWith(StringPool.SPACE)) {
4691                                    line = StringUtil.replaceFirst(
4692                                            line, StringPool.SPACE, StringPool.BLANK);
4693                            }
4694                    }
4695                    else {
4696                            int pos = 0;
4697    
4698                            String temp = line;
4699    
4700                            while (temp.startsWith(StringPool.FOUR_SPACES)) {
4701                                    line = StringUtil.replaceFirst(
4702                                            line, StringPool.FOUR_SPACES, StringPool.TAB);
4703    
4704                                    pos++;
4705    
4706                                    temp = line.substring(pos);
4707                            }
4708                    }
4709    
4710                    return line;
4711            }
4712    
4713            private static final String[] _TAG_LIBRARIES = new String[] {
4714                    "aui", "c", "html", "jsp", "liferay-portlet", "liferay-security",
4715                    "liferay-theme", "liferay-ui", "liferay-util", "portlet", "struts",
4716                    "tiles"
4717            };
4718    
4719            private static final int _TYPE_CLASS_PRIVATE = 24;
4720    
4721            private static final int _TYPE_CLASS_PRIVATE_STATIC = 23;
4722    
4723            private static final int _TYPE_CLASS_PROTECTED = 16;
4724    
4725            private static final int _TYPE_CLASS_PROTECTED_STATIC = 15;
4726    
4727            private static final int _TYPE_CLASS_PUBLIC = 8;
4728    
4729            private static final int _TYPE_CLASS_PUBLIC_STATIC = 7;
4730    
4731            private static final int[] _TYPE_CONSTRUCTOR = {
4732                    SourceFormatter._TYPE_CONSTRUCTOR_PRIVATE,
4733                    SourceFormatter._TYPE_CONSTRUCTOR_PROTECTED,
4734                    SourceFormatter._TYPE_CONSTRUCTOR_PUBLIC
4735            };
4736    
4737            private static final int _TYPE_CONSTRUCTOR_PRIVATE = 18;
4738    
4739            private static final int _TYPE_CONSTRUCTOR_PROTECTED = 10;
4740    
4741            private static final int _TYPE_CONSTRUCTOR_PUBLIC = 4;
4742    
4743            private static final int[] _TYPE_METHOD = {
4744                    SourceFormatter._TYPE_METHOD_PRIVATE,
4745                    SourceFormatter._TYPE_METHOD_PRIVATE_STATIC,
4746                    SourceFormatter._TYPE_METHOD_PROTECTED,
4747                    SourceFormatter._TYPE_METHOD_PROTECTED_STATIC,
4748                    SourceFormatter._TYPE_METHOD_PUBLIC,
4749                    SourceFormatter._TYPE_METHOD_PUBLIC_STATIC
4750            };
4751    
4752            private static final int _TYPE_METHOD_PRIVATE = 19;
4753    
4754            private static final int _TYPE_METHOD_PRIVATE_STATIC = 17;
4755    
4756            private static final int _TYPE_METHOD_PROTECTED = 11;
4757    
4758            private static final int _TYPE_METHOD_PROTECTED_STATIC = 9;
4759    
4760            private static final int _TYPE_METHOD_PUBLIC = 5;
4761    
4762            private static final int _TYPE_METHOD_PUBLIC_STATIC = 3;
4763    
4764            private static final int[] _TYPE_VARIABLE_NOT_FINAL = {
4765                    SourceFormatter._TYPE_VARIABLE_PRIVATE,
4766                    SourceFormatter._TYPE_VARIABLE_PRIVATE_STATIC,
4767                    SourceFormatter._TYPE_VARIABLE_PROTECTED,
4768                    SourceFormatter._TYPE_VARIABLE_PROTECTED_STATIC,
4769                    SourceFormatter._TYPE_VARIABLE_PUBLIC,
4770                    SourceFormatter._TYPE_VARIABLE_PUBLIC_STATIC
4771            };
4772    
4773            private static final int[] _TYPE_VARIABLE_NOT_STATIC = {
4774                    SourceFormatter._TYPE_VARIABLE_PRIVATE,
4775                    SourceFormatter._TYPE_VARIABLE_PROTECTED,
4776                    SourceFormatter._TYPE_VARIABLE_PUBLIC
4777            };
4778    
4779            private static final int _TYPE_VARIABLE_PRIVATE = 22;
4780    
4781            private static final int _TYPE_VARIABLE_PRIVATE_STATIC = 21;
4782    
4783            private static final int _TYPE_VARIABLE_PRIVATE_STATIC_FINAL = 20;
4784    
4785            private static final int _TYPE_VARIABLE_PROTECTED = 14;
4786    
4787            private static final int _TYPE_VARIABLE_PROTECTED_STATIC = 13;
4788    
4789            private static final int _TYPE_VARIABLE_PROTECTED_STATIC_FINAL = 12;
4790    
4791            private static final int _TYPE_VARIABLE_PUBLIC = 6;
4792    
4793            private static final int _TYPE_VARIABLE_PUBLIC_STATIC = 2;
4794    
4795            private static final int _TYPE_VARIABLE_PUBLIC_STATIC_FINAL = 1;
4796    
4797            private static String[] _excludes;
4798            private static FileImpl _fileUtil = FileImpl.getInstance();
4799            private static Pattern _javaImportPattern = Pattern.compile(
4800                    "(^[ \t]*import\\s+.*;\n+)+", Pattern.MULTILINE);
4801            private static Properties _javaTermSortExclusions;
4802            private static Pattern _jspAttributeNamePattern = Pattern.compile(
4803                    "[a-z]+[-_a-zA-Z0-9]*");
4804            private static Map<String, String> _jspContents =
4805                    new HashMap<String, String>();
4806            private static Pattern _jspImportPattern = Pattern.compile(
4807                    "(<.*\n*page.import=\".*>\n*)+", Pattern.MULTILINE);
4808            private static Pattern _jspIncludeFilePattern = Pattern.compile(
4809                    "/.*[.]jsp[f]?");
4810            private static Pattern _languageKeyPattern = Pattern.compile(
4811                    "LanguageUtil.(?:get|format)\\([^;%]+|Liferay.Language.get\\('([^']+)");
4812            private static Properties _lineLengthExclusions;
4813            private static Properties _portalLanguageKeysProperties;
4814            private static boolean _portalSource;
4815            private static SAXReaderImpl _saxReaderUtil = SAXReaderImpl.getInstance();
4816            private static Pattern _sessionKeyPattern = Pattern.compile(
4817                    "SessionErrors.(?:add|contains|get)\\([^;%&|!]+|".concat(
4818                            "SessionMessages.(?:add|contains|get)\\([^;%&|!]+"),
4819                    Pattern.MULTILINE);
4820            private static SourceFormatterHelper _sourceFormatterHelper;
4821            private static Pattern _taglibLanguageKeyPattern = Pattern.compile(
4822                    "(?:confirmation|label|(?:M|m)essage|message key|names|title)=\"[^A-Z" +
4823                            "<=%\\[\\s]+\"");
4824            private static Pattern _taglibSessionKeyPattern = Pattern.compile(
4825                    "<liferay-ui:error [^>]+>|<liferay-ui:success [^>]+>",
4826                    Pattern.MULTILINE);
4827            private static Pattern _xssPattern = Pattern.compile(
4828                    "String\\s+([^\\s]+)\\s*=\\s*(Bean)?ParamUtil\\.getString\\(");
4829    
4830    }