IDEADEV-41034: Artifact: manifest.mf name recognition is case-sensitive
[fedora-idea.git] / java / compiler / impl / src / com / intellij / packaging / impl / elements / PackagingElementFactoryImpl.java
blob0ca24141838e25a550206f21544d57e675f79258
1 /*
2 * Copyright 2000-2009 JetBrains s.r.o.
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
8 * http://www.apache.org/licenses/LICENSE-2.0
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
16 package com.intellij.packaging.impl.elements;
18 import com.intellij.openapi.extensions.Extensions;
19 import com.intellij.openapi.module.Module;
20 import com.intellij.openapi.project.Project;
21 import com.intellij.openapi.roots.OrderRootType;
22 import com.intellij.openapi.roots.impl.libraries.LibraryImpl;
23 import com.intellij.openapi.roots.impl.libraries.LibraryTableImplUtil;
24 import com.intellij.openapi.roots.libraries.Library;
25 import com.intellij.openapi.roots.libraries.LibraryTable;
26 import com.intellij.openapi.util.io.FileUtil;
27 import com.intellij.openapi.util.text.StringUtil;
28 import com.intellij.openapi.vfs.VirtualFile;
29 import com.intellij.packaging.artifacts.Artifact;
30 import com.intellij.packaging.artifacts.ArtifactPointerManager;
31 import com.intellij.packaging.elements.*;
32 import com.intellij.packaging.ui.ArtifactEditorContext;
33 import com.intellij.util.ArrayUtil;
34 import com.intellij.util.PathUtil;
35 import org.jetbrains.annotations.NonNls;
36 import org.jetbrains.annotations.NotNull;
37 import org.jetbrains.annotations.Nullable;
39 import java.util.ArrayList;
40 import java.util.Collections;
41 import java.util.List;
43 /**
44 * @author nik
46 public class PackagingElementFactoryImpl extends PackagingElementFactory {
47 public static final PackagingElementType<DirectoryPackagingElement> DIRECTORY_ELEMENT_TYPE = new DirectoryElementType();
48 public static final PackagingElementType<ArchivePackagingElement> ARCHIVE_ELEMENT_TYPE = new ArchiveElementType();
49 public static final PackagingElementType<FileCopyPackagingElement> FILE_COPY_ELEMENT_TYPE = new FileCopyElementType();
50 public static final PackagingElementType<DirectoryCopyPackagingElement> DIRECTORY_COPY_ELEMENT_TYPE = new DirectoryCopyElementType();
51 public static final PackagingElementType<ArtifactRootElement<?>> ARTIFACT_ROOT_ELEMENT_TYPE = new ArtifactRootElementType();
52 private static final PackagingElementType[] STANDARD_TYPES = {
53 DIRECTORY_ELEMENT_TYPE, ARCHIVE_ELEMENT_TYPE,
54 LibraryElementType.LIBRARY_ELEMENT_TYPE, ModuleOutputElementType.MODULE_OUTPUT_ELEMENT_TYPE,
55 ArtifactElementType.ARTIFACT_ELEMENT_TYPE, FILE_COPY_ELEMENT_TYPE, DIRECTORY_COPY_ELEMENT_TYPE
58 @NotNull
59 @Override
60 public PackagingElementType<?>[] getNonCompositeElementTypes() {
61 final List<PackagingElementType> elementTypes = new ArrayList<PackagingElementType>();
62 for (PackagingElementType elementType : getAllElementTypes()) {
63 if (!(elementType instanceof CompositePackagingElementType)) {
64 elementTypes.add(elementType);
67 return elementTypes.toArray(new PackagingElementType[elementTypes.size()]);
70 @Override
71 @NotNull
72 public ComplexPackagingElementType<?>[] getComplexElementTypes() {
73 List<ComplexPackagingElementType<?>> types = new ArrayList<ComplexPackagingElementType<?>>();
74 for (PackagingElementType type : getAllElementTypes()) {
75 if (type instanceof ComplexPackagingElementType) {
76 types.add((ComplexPackagingElementType)type);
79 return types.toArray(new ComplexPackagingElementType[types.size()]);
82 @NotNull
83 @Override
84 public CompositePackagingElementType<?>[] getCompositeElementTypes() {
85 final List<CompositePackagingElementType> elementTypes = new ArrayList<CompositePackagingElementType>();
86 for (PackagingElementType elementType : getAllElementTypes()) {
87 if (elementType instanceof CompositePackagingElementType) {
88 elementTypes.add((CompositePackagingElementType)elementType);
91 return elementTypes.toArray(new CompositePackagingElementType[elementTypes.size()]);
94 @Override
95 public PackagingElementType<?> findElementType(String id) {
96 for (PackagingElementType elementType : getAllElementTypes()) {
97 if (elementType.getId().equals(id)) {
98 return elementType;
101 if (id.equals(ARTIFACT_ROOT_ELEMENT_TYPE.getId())) {
102 return ARTIFACT_ROOT_ELEMENT_TYPE;
104 throw new AssertionError(id + " not registered");
107 @NotNull
108 @Override
109 public PackagingElementType[] getAllElementTypes() {
110 final PackagingElementType[] types = Extensions.getExtensions(PackagingElementType.EP_NAME);
111 return ArrayUtil.mergeArrays(STANDARD_TYPES, types, PackagingElementType.class);
114 @NotNull
115 @Override
116 public PackagingElement<?> createArtifactElement(@NotNull Artifact artifact, @NotNull Project project) {
117 return new ArtifactPackagingElement(project, ArtifactPointerManager.getInstance(project).create(artifact));
120 @NotNull
121 public DirectoryPackagingElement createDirectory(@NotNull @NonNls String directoryName) {
122 return new DirectoryPackagingElement(directoryName);
125 @NotNull
126 @Override
127 public ArtifactRootElement<?> createArtifactRootElement() {
128 return new ArtifactRootElementImpl();
131 @Override
132 @NotNull
133 public CompositePackagingElement<?> getOrCreateDirectory(@NotNull CompositePackagingElement<?> parent, @NotNull String relativePath) {
134 return getOrCreateDirectoryOrArchive(parent, relativePath, true);
137 @NotNull
138 @Override
139 public CompositePackagingElement<?> getOrCreateArchive(@NotNull CompositePackagingElement<?> parent, @NotNull String relativePath) {
140 return getOrCreateDirectoryOrArchive(parent, relativePath, false);
143 @Override
144 public void addFileCopy(@NotNull CompositePackagingElement<?> root, @NotNull String outputDirectoryPath, @NotNull String sourceFilePath) {
145 addFileCopy(root, outputDirectoryPath, sourceFilePath, null);
148 @Override
149 public void addFileCopy(@NotNull CompositePackagingElement<?> root, @NotNull String outputDirectoryPath, @NotNull String sourceFilePath,
150 @Nullable String outputFileName) {
151 final String fileName = PathUtil.getFileName(sourceFilePath);
152 if (outputFileName != null && outputFileName.equals(fileName)) {
153 outputFileName = null;
155 getOrCreateDirectory(root, outputDirectoryPath).addOrFindChild(new FileCopyPackagingElement(sourceFilePath, outputFileName));
158 @NotNull
159 private CompositePackagingElement<?> getOrCreateDirectoryOrArchive(@NotNull CompositePackagingElement<?> root,
160 @NotNull @NonNls String path, final boolean directory) {
161 path = StringUtil.trimStart(StringUtil.trimEnd(path, "/"), "/");
162 if (path.length() == 0) {
163 return root;
165 int index = path.lastIndexOf('/');
166 String lastName = path.substring(index + 1);
167 String parentPath = index != -1 ? path.substring(0, index) : "";
169 final CompositePackagingElement<?> parent = getOrCreateDirectoryOrArchive(root, parentPath, true);
170 final CompositePackagingElement<?> last = directory ? createDirectory(lastName) : createArchive(lastName);
171 return parent.addOrFindChild(last);
174 @NotNull
175 public PackagingElement<?> createModuleOutput(@NotNull String moduleName, Project project) {
176 return new ModuleOutputPackagingElement(moduleName);
179 @NotNull
180 @Override
181 public PackagingElement<?> createModuleOutput(@NotNull Module module) {
182 return new ModuleOutputPackagingElement(module.getName());
185 @NotNull
186 @Override
187 public List<? extends PackagingElement<?>> createLibraryElements(@NotNull Library library) {
188 final LibraryTable table = library.getTable();
189 final String libraryName = library.getName();
190 if (table != null) {
191 return Collections.singletonList(createLibraryFiles(libraryName, table.getTableLevel(), null));
193 if (libraryName != null) {
194 final Module module = ((LibraryImpl)library).getModule();
195 if (module != null) {
196 return Collections.singletonList(createLibraryFiles(libraryName, LibraryTableImplUtil.MODULE_LEVEL, module.getName()));
199 final List<PackagingElement<?>> elements = new ArrayList<PackagingElement<?>>();
200 for (VirtualFile file : library.getFiles(OrderRootType.CLASSES)) {
201 final String path = FileUtil.toSystemIndependentName(PathUtil.getLocalPath(file));
202 elements.add(file.isDirectory() && file.isInLocalFileSystem() ? new DirectoryCopyPackagingElement(path) : new FileCopyPackagingElement(path));
204 return elements;
207 @NotNull
208 @Override
209 public PackagingElement<?> createLibraryFiles(@NotNull String libraryName, @NotNull String level, String moduleName) {
210 return new LibraryPackagingElement(level, libraryName, moduleName);
213 @NotNull
214 public CompositePackagingElement<?> createArchive(@NotNull @NonNls String archiveFileName) {
215 return new ArchivePackagingElement(archiveFileName);
218 @Nullable
219 private static PackagingElement<?> findArchiveOrDirectoryByName(@NotNull CompositePackagingElement<?> parent, @NotNull String name) {
220 for (PackagingElement<?> element : parent.getChildren()) {
221 if (element instanceof ArchivePackagingElement && ((ArchivePackagingElement)element).getArchiveFileName().equals(name) ||
222 element instanceof DirectoryPackagingElement && ((DirectoryPackagingElement)element).getDirectoryName().equals(name)) {
223 return element;
226 return null;
229 @NotNull
230 public static String suggestFileName(@NotNull CompositePackagingElement<?> parent, @NonNls @NotNull String prefix, @NonNls @NotNull String suffix) {
231 String name = prefix + suffix;
232 int i = 2;
233 while (findArchiveOrDirectoryByName(parent, name) != null) {
234 name = prefix + i++ + suffix;
236 return name;
239 @NotNull
240 @Override
241 public PackagingElement<?> createDirectoryCopyWithParentDirectories(@NotNull String filePath, @NotNull String relativeOutputPath) {
242 return createParentDirectories(relativeOutputPath, new DirectoryCopyPackagingElement(filePath));
245 @NotNull
246 @Override
247 public PackagingElement<?> createFileCopyWithParentDirectories(@NotNull String filePath, @NotNull String relativeOutputPath) {
248 return createFileCopyWithParentDirectories(filePath, relativeOutputPath, null);
251 @NotNull
252 @Override
253 public PackagingElement<?> createFileCopyWithParentDirectories(@NotNull String filePath,
254 @NotNull String relativeOutputPath,
255 @Nullable String outputFileName) {
256 final FileCopyPackagingElement file = new FileCopyPackagingElement(filePath, outputFileName);
257 return createParentDirectories(relativeOutputPath, file);
260 @NotNull
261 @Override
262 public PackagingElement<?> createParentDirectories(@NotNull String relativeOutputPath, @NotNull PackagingElement<?> element) {
263 return createParentDirectories(relativeOutputPath, Collections.singletonList(element)).get(0);
266 @NotNull
267 @Override
268 public List<? extends PackagingElement<?>> createParentDirectories(@NotNull String relativeOutputPath, @NotNull List<? extends PackagingElement<?>> elements) {
269 relativeOutputPath = StringUtil.trimStart(relativeOutputPath, "/");
270 if (relativeOutputPath.length() == 0) {
271 return elements;
273 int slash = relativeOutputPath.indexOf('/');
274 if (slash == -1) slash = relativeOutputPath.length();
275 String rootName = relativeOutputPath.substring(0, slash);
276 String pathTail = relativeOutputPath.substring(slash);
277 final DirectoryPackagingElement root = createDirectory(rootName);
278 final CompositePackagingElement<?> last = getOrCreateDirectory(root, pathTail);
279 last.addOrFindChildren(elements);
280 return Collections.singletonList(root);
283 public static PackagingElement<?> createDirectoryOrArchiveWithParents(@NotNull String path, final boolean archive) {
284 path = FileUtil.toSystemIndependentName(path);
285 final String parentPath = PathUtil.getParentPath(path);
286 final String fileName = PathUtil.getFileName(path);
287 final PackagingElement<?> element = archive ? new ArchivePackagingElement(fileName) : new DirectoryPackagingElement(fileName);
288 return getInstance().createParentDirectories(parentPath, element);
291 private static class ArtifactRootElementType extends PackagingElementType<ArtifactRootElement<?>> {
292 protected ArtifactRootElementType() {
293 super("root", "");
296 @Override
297 public boolean canCreate(@NotNull ArtifactEditorContext context, @NotNull Artifact artifact) {
298 return false;
301 @NotNull
302 public List<? extends ArtifactRootElement<?>> chooseAndCreate(@NotNull ArtifactEditorContext context, @NotNull Artifact artifact,
303 @NotNull CompositePackagingElement<?> parent) {
304 throw new UnsupportedOperationException("'create' not implemented in " + getClass().getName());
307 @NotNull
308 public ArtifactRootElement<?> createEmpty(@NotNull Project project) {
309 return new ArtifactRootElementImpl();