blob: 7fbe2d59ec1bb342f123e3ed1121103a52f26b70 [file] [log] [blame]
Tsu Chiang Chuang9a223d72011-04-27 17:19:46 -07001/*
2 * Copyright (C) 2008 The Android Open Source Project
3 *
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
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
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.
15 */
16
17package util.build;
18
Andreas Gampea16d71a2017-06-29 21:04:42 -070019import java.io.BufferedInputStream;
Tsu Chiang Chuang9a223d72011-04-27 17:19:46 -070020import java.io.File;
Andreas Gampea16d71a2017-06-29 21:04:42 -070021import java.io.FileInputStream;
22import java.io.FileOutputStream;
Tsu Chiang Chuang9a223d72011-04-27 17:19:46 -070023import java.io.IOException;
Andreas Gampea16d71a2017-06-29 21:04:42 -070024import java.nio.file.Files;
25import java.nio.file.Path;
26import java.nio.file.Paths;
27import java.util.jar.JarEntry;
28import java.util.jar.JarOutputStream;
Tsu Chiang Chuang9a223d72011-04-27 17:19:46 -070029
Andreas Gampea16d71a2017-06-29 21:04:42 -070030/**
31 * JarBuildStep takes a single input file and embeds it into a (new) jar file as a single entry.
32 */
Tsu Chiang Chuang9a223d72011-04-27 17:19:46 -070033public class JarBuildStep extends BuildStep {
34
Andreas Gampea16d71a2017-06-29 21:04:42 -070035 String outputJarEntryName;
Tsu Chiang Chuang9a223d72011-04-27 17:19:46 -070036 private final boolean deleteInputFileAfterBuild;
37
Andreas Gampea16d71a2017-06-29 21:04:42 -070038 public JarBuildStep(BuildFile inputFile, String outputJarEntryName,
39 BuildFile outputJarFile, boolean deleteInputFileAfterBuild) {
40 super(inputFile, outputJarFile);
41 this.outputJarEntryName = outputJarEntryName;
Tsu Chiang Chuang9a223d72011-04-27 17:19:46 -070042 this.deleteInputFileAfterBuild = deleteInputFileAfterBuild;
43 }
44
45 @Override
46 boolean build() {
47 if (super.build()) {
Andreas Gampea16d71a2017-06-29 21:04:42 -070048 File tempFile = new File(inputFile.folder, outputJarEntryName);
Tsu Chiang Chuang9a223d72011-04-27 17:19:46 -070049 try {
50 if (!inputFile.fileName.equals(tempFile)) {
51 copyFile(inputFile.fileName, tempFile);
52 } else {
53 tempFile = null;
54 }
55 } catch (IOException e) {
56 System.err.println("io exception:"+e.getMessage());
57 e.printStackTrace();
58 return false;
59 }
60
61 File outDir = outputFile.fileName.getParentFile();
62 if (!outDir.exists() && !outDir.mkdirs()) {
63 System.err.println("failed to create output dir: "
64 + outDir.getAbsolutePath());
65 return false;
66 }
Tsu Chiang Chuang9a223d72011-04-27 17:19:46 -070067
Andreas Gampea16d71a2017-06-29 21:04:42 -070068 // Find the input. We'll need to look into the input folder, but check with the
69 // (relative) destination filename (this is effectively removing the inputFile folder
70 // from the entry path in the jar file).
71 Path absoluteInputPath = Paths.get(inputFile.folder.getAbsolutePath())
72 .resolve(outputJarEntryName);
73 File absoluteInputFile = absoluteInputPath.toFile();
74 if (!absoluteInputFile.exists()) {
75 // Something went wrong.
76 throw new IllegalArgumentException(absoluteInputFile.getAbsolutePath());
Tsu Chiang Chuang9a223d72011-04-27 17:19:46 -070077 }
Andreas Gampea16d71a2017-06-29 21:04:42 -070078
79 // Use a JarOutputStream to create the output jar file.
80 File jarOutFile = outputFile.fileName;
81 try (JarOutputStream jarOut = new JarOutputStream(new FileOutputStream(jarOutFile))) {
82 // Create the JAR entry for the file. Use destFileName, and copy the timestamp
83 // from the input.
84 JarEntry entry = new JarEntry(outputJarEntryName);
85 entry.setTime(absoluteInputFile.lastModified());
86
87 // Push the entry. The stream will then be ready to accept content.
88 jarOut.putNextEntry(entry);
89
90 // Copy absoluteInputFile into the jar file.
91 Files.copy(absoluteInputPath, jarOut);
92
93 // Finish the entry.
94 jarOut.closeEntry();
95
96 // (Implicitly close the stream, finishing the jar file.)
97 } catch (Exception e) {
98 System.err.println("exception in JarBuildStep for " +
99 outputFile.fileName.getAbsolutePath() + ", " + outputJarEntryName);
100 e.printStackTrace(System.err);
101 jarOutFile.delete();
102 return false;
103 }
104
105 // Clean up.
106 if (tempFile != null) {
107 tempFile.delete();
108 }
109 if (deleteInputFileAfterBuild) {
110 inputFile.fileName.delete();
111 }
112
113 return true;
Tsu Chiang Chuang9a223d72011-04-27 17:19:46 -0700114 }
115 return false;
116 }
117
118 @Override
119 public int hashCode() {
120 return inputFile.hashCode() ^ outputFile.hashCode()
Andreas Gampea16d71a2017-06-29 21:04:42 -0700121 ^ outputJarEntryName.hashCode();
Tsu Chiang Chuang9a223d72011-04-27 17:19:46 -0700122 }
123
124 @Override
125 public boolean equals(Object obj) {
126 if (super.equals(obj)) {
127 JarBuildStep other = (JarBuildStep) obj;
128 return inputFile.equals(other.inputFile)
129 && outputFile.equals(other.outputFile)
Andreas Gampea16d71a2017-06-29 21:04:42 -0700130 && outputJarEntryName.equals(other.outputJarEntryName);
Tsu Chiang Chuang9a223d72011-04-27 17:19:46 -0700131
132 }
133 return false;
134 }
135
136}