001    /*
002     * Sonar, open source software quality management tool.
003     * Copyright (C) 2009 SonarSource SA
004     * mailto:contact AT sonarsource DOT com
005     *
006     * Sonar is free software; you can redistribute it and/or
007     * modify it under the terms of the GNU Lesser General Public
008     * License as published by the Free Software Foundation; either
009     * version 3 of the License, or (at your option) any later version.
010     *
011     * Sonar is distributed in the hope that it will be useful,
012     * but WITHOUT ANY WARRANTY; without even the implied warranty of
013     * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
014     * Lesser General Public License for more details.
015     *
016     * You should have received a copy of the GNU Lesser General Public
017     * License along with Sonar; if not, write to the Free Software
018     * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02
019     */
020    package org.sonar.api.resources;
021    
022    import java.util.List;
023    
024    import org.apache.commons.lang.StringUtils;
025    import org.apache.commons.lang.builder.ToStringBuilder;
026    import org.sonar.api.utils.WildcardPattern;
027    
028    /**
029     * This class is an implementation of a resource of type FILE
030     * 
031     * @since 1.10
032     */
033    public class File extends Resource<Directory> {
034    
035      private String directoryKey;
036      private String filename;
037      private Language language;
038      private Directory parent;
039      private String qualifier = Resource.QUALIFIER_FILE;
040    
041      /**
042       * File in project. Key is the path relative to project source directories. It is not the absolute path and it does not include the path
043       * to source directories. Example : <code>new File("org/sonar/foo.sql")</code>. The absolute path may be
044       * c:/myproject/src/main/sql/org/sonar/foo.sql. Project root is c:/myproject and source dir is src/main/sql.
045       */
046      public File(String key) {
047        if (key == null) {
048          throw new IllegalArgumentException("File key is null");
049        }
050        String realKey = parseKey(key);
051        if (realKey.indexOf(Directory.SEPARATOR) >= 0) {
052          this.directoryKey = Directory.parseKey(StringUtils.substringBeforeLast(key, Directory.SEPARATOR));
053          this.filename = StringUtils.substringAfterLast(realKey, Directory.SEPARATOR);
054          realKey = new StringBuilder().append(this.directoryKey).append(Directory.SEPARATOR).append(filename).toString();
055    
056        } else {
057          this.filename = key;
058        }
059        setKey(realKey);
060      }
061    
062      /**
063       * Creates a file from its containing directory and name
064       */
065      public File(String directory, String filename) {
066        this.filename = StringUtils.trim(filename);
067        if (StringUtils.isBlank(directory)) {
068          setKey(filename);
069    
070        } else {
071          this.directoryKey = Directory.parseKey(directory);
072          setKey(new StringBuilder().append(directoryKey).append(Directory.SEPARATOR).append(this.filename).toString());
073        }
074      }
075    
076      /**
077       * Creates a File from its language and its key
078       */
079      public File(Language language, String key) {
080        this(key);
081        this.language = language;
082      }
083    
084      /**
085       * Creates a File from language, directory and filename
086       */
087      public File(Language language, String directory, String filename) {
088        this(directory, filename);
089        this.language = language;
090      }
091    
092      /**
093       * {@inheritDoc}
094       * 
095       * @see Resource#getParent()
096       */
097      public Directory getParent() {
098        if (parent == null) {
099          parent = new Directory(directoryKey);
100        }
101        return parent;
102      }
103    
104      private static String parseKey(String key) {
105        if (StringUtils.isBlank(key)) {
106          return null;
107        }
108    
109        key = key.replace('\\', '/');
110        key = StringUtils.trim(key);
111        return key;
112      }
113    
114      /**
115       * {@inheritDoc}
116       * 
117       * @see Resource#matchFilePattern(String)
118       */
119      public boolean matchFilePattern(String antPattern) {
120        WildcardPattern matcher = WildcardPattern.create(antPattern, "/");
121        return matcher.match(getKey());
122      }
123    
124      /**
125       * Creates a File from an io.file and a list of sources directories
126       */
127      public static File fromIOFile(java.io.File file, List<java.io.File> sourceDirs) {
128        String relativePath = DefaultProjectFileSystem.getRelativePath(file, sourceDirs);
129        if (relativePath != null) {
130          return new File(relativePath);
131        }
132        return null;
133      }
134    
135      /**
136       * Creates a File from its name and a project
137       */
138      public static File fromIOFile(java.io.File file, Project project) {
139        return fromIOFile(file, project.getFileSystem().getSourceDirs());
140      }
141    
142      /**
143       * {@inheritDoc}
144       * 
145       * @see Resource#getName()
146       */
147      public String getName() {
148        return filename;
149      }
150    
151      /**
152       * {@inheritDoc}
153       * 
154       * @see Resource#getLongName()
155       */
156      public String getLongName() {
157        return getKey();
158      }
159    
160      /**
161       * {@inheritDoc}
162       * 
163       * @see Resource#getDescription()
164       */
165      public String getDescription() {
166        return null;
167      }
168    
169      /**
170       * {@inheritDoc}
171       * 
172       * @see Resource#getLanguage()
173       */
174      public Language getLanguage() {
175        return language;
176      }
177    
178      /**
179       * Sets the language of the file
180       */
181      public void setLanguage(Language language) {
182        this.language = language;
183      }
184    
185      /**
186       * @return SCOPE_ENTITY
187       */
188      public String getScope() {
189        return Resource.SCOPE_ENTITY;
190      }
191    
192      /**
193       * Returns the qualifier associated to this File. Should be QUALIFIER_FILE or
194       * 
195       * @return QUALIFIER_UNIT_TEST_CLASS
196       */
197      public String getQualifier() {
198        return qualifier;
199      }
200    
201      public void setQualifier(String qualifier) {
202        this.qualifier = qualifier;
203      }
204    
205      @Override
206      public String toString() {
207        return new ToStringBuilder(this)
208            .append("key", getKey())
209            .append("dir", directoryKey)
210            .append("filename", filename)
211            .append("language", language)
212            .toString();
213      }
214    }