You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

FilePattern.java 4.2KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131
  1. /*
  2. * Sonar Runner - Batch
  3. * Copyright (C) 2011 SonarSource
  4. * dev@sonar.codehaus.org
  5. *
  6. * This program is free software; you can redistribute it and/or
  7. * modify it under the terms of the GNU Lesser General Public
  8. * License as published by the Free Software Foundation; either
  9. * version 3 of the License, or (at your option) any later version.
  10. *
  11. * This program is distributed in the hope that it will be useful,
  12. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  14. * Lesser General Public License for more details.
  15. *
  16. * You should have received a copy of the GNU Lesser General Public
  17. * License along with this program; if not, write to the Free Software
  18. * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02
  19. */
  20. package org.sonar.runner.batch;
  21. import com.google.common.base.Joiner;
  22. import com.google.common.collect.Lists;
  23. import org.apache.commons.io.FileUtils;
  24. import org.apache.commons.io.FilenameUtils;
  25. import org.apache.commons.io.filefilter.AndFileFilter;
  26. import org.apache.commons.io.filefilter.FileFileFilter;
  27. import org.apache.commons.io.filefilter.IOFileFilter;
  28. import org.apache.commons.io.filefilter.TrueFileFilter;
  29. import org.apache.commons.lang.StringUtils;
  30. import org.sonar.api.utils.WildcardPattern;
  31. import java.io.File;
  32. import java.util.Collection;
  33. import java.util.Collections;
  34. import java.util.List;
  35. class FilePattern {
  36. Collection<File> listFiles(File basedir, String pattern) {
  37. File absoluteBasedir = absoluteBasedir(pattern);
  38. IOFileFilter filter;
  39. if (absoluteBasedir != null) {
  40. filter = new AbsolutePathFilter(WildcardPattern.create(pattern, "/"));
  41. basedir = absoluteBasedir.isFile() ? absoluteBasedir.getParentFile() : absoluteBasedir;
  42. } else {
  43. filter = new RelativePathFilter(basedir, WildcardPattern.create(pattern, "/"));
  44. }
  45. if (basedir.isDirectory() && basedir.exists()) {
  46. return FileUtils.listFiles(basedir, new AndFileFilter(FileFileFilter.FILE, filter), TrueFileFilter.TRUE);
  47. }
  48. return Collections.emptyList();
  49. }
  50. private File absoluteBasedir(String pattern) {
  51. File absoluteBasedir = null;
  52. int wildcard = StringUtils.indexOfAny(pattern, new char[]{'*', '?'});
  53. if (wildcard == 0) {
  54. // relative path
  55. } else if (wildcard == -1) {
  56. absoluteBasedir = new File(pattern);
  57. } else {
  58. int lastSlashBeforeWildcard = pattern.substring(0, wildcard).lastIndexOf("/");
  59. if (lastSlashBeforeWildcard >= 0) {
  60. String path = pattern.substring(0, lastSlashBeforeWildcard);
  61. absoluteBasedir = new File(path);
  62. }
  63. }
  64. if (absoluteBasedir != null && !absoluteBasedir.isAbsolute()) {
  65. absoluteBasedir = null;
  66. }
  67. return absoluteBasedir;
  68. }
  69. private static class RelativePathFilter implements IOFileFilter {
  70. private final File basedir;
  71. private final WildcardPattern pattern;
  72. private RelativePathFilter(File basedir, WildcardPattern pattern) {
  73. this.basedir = basedir;
  74. this.pattern = pattern;
  75. }
  76. public boolean accept(File file) {
  77. return pattern.match(relativePath(file));
  78. }
  79. public boolean accept(File file, String filename) {
  80. return true;
  81. }
  82. String relativePath(File file) {
  83. List<String> stack = Lists.newArrayList();
  84. String path = FilenameUtils.normalize(file.getAbsolutePath());
  85. File cursor = new File(path);
  86. while (cursor != null) {
  87. if (containsFile(cursor)) {
  88. return Joiner.on("/").join(stack);
  89. }
  90. stack.add(0, cursor.getName());
  91. cursor = cursor.getParentFile();
  92. }
  93. return null;
  94. }
  95. private boolean containsFile(File cursor) {
  96. return FilenameUtils.equalsNormalizedOnSystem(basedir.getAbsolutePath(), cursor.getAbsolutePath());
  97. }
  98. }
  99. private static class AbsolutePathFilter implements IOFileFilter {
  100. private final WildcardPattern pattern;
  101. private AbsolutePathFilter(WildcardPattern pattern) {
  102. this.pattern = pattern;
  103. }
  104. public boolean accept(File file) {
  105. return pattern.match(FilenameUtils.separatorsToUnix(file.getAbsolutePath()));
  106. }
  107. public boolean accept(File file, String filename) {
  108. return true;
  109. }
  110. }
  111. }