• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1// Script used to build ADT plugins, IDE and monitor
2// There are 2 major tasks done by this plugin:
3//    copydeps: copies tools/base, tools/swt and prebuilt jars into plugins' libs folder
4//    buildEclipse: builds Eclipse by running Tycho from the commandline
5//
6// Usage: $ ANDROID_SRC/tools/gradlew -i -b /path/to/this/build.gradle copydeps|buildEclipse
7
8// get tools/base version
9apply from: "../../tools/buildSrc/base/version.gradle"
10
11ext.outPath = System.env.OUT_DIR
12if (outPath != null) {
13    ext.outFile = new File(outPath)
14} else {
15    outPath = '../../out'
16    ext.outFile = new File(projectDir, outPath)
17}
18
19repositories {
20    maven { url '../../prebuilts/tools/common/m2/repository' }
21    maven { url outPath + '/repo' }
22}
23
24ext {
25    // list of plugins whose manifest should be examined to identify dependencies
26    adtPlugins = new File(projectDir, 'plugins').listFiles().findAll { it.name.startsWith("com.android") }
27
28    //
29    def eclipseBuildDeps = new File(projectDir, "../../prebuilts/eclipse-build-deps").getCanonicalFile()
30    targetComponents = [
31            "platform": new File(eclipseBuildDeps, "platform/org.eclipse.platform-4.2.2.zip"),
32            "cdt"     : new File(eclipseBuildDeps, "cdt/cdt-master-8.0.2.zip"),
33            "emf"     : new File(eclipseBuildDeps, "emf/emf-xsd-Update-2.9.1.zip"),
34            "jdt"     : new File(eclipseBuildDeps, "jdt/org.eclipse.jdt.source-4.2.2.zip"),
35            "wtp"     : new File(eclipseBuildDeps, "wtp/wtp-repo-R-3.3.2-20120210195245.zip"),
36            "gef"     : new File(eclipseBuildDeps, "gef/GEF-Update-3.9.1.zip"),
37            "pde"     : new File(eclipseBuildDeps, "pde/org.eclipse.pde-3.8.zip"),
38            "egit"    : new File(eclipseBuildDeps, "egit/org.eclipse.egit.repository-2.2.0.201212191850-r.zip"),
39    ]
40
41    buildNumber = System.getenv("BUILD_NUMBER")
42    if (buildNumber == null) {
43        buildNumber = "SNAPSHOT"
44    }
45}
46
47// a mapping from the library names as used inside the plugin's MANIFEST.MF to the Maven artifact id
48def artifacts = [
49        // tools/base and tools/swt dependencies
50        'manifest-merger'     : "com.android.tools.build:manifest-merger:$ext.baseVersion",
51        'ddmlib'              : "com.android.tools.ddms:ddmlib:$ext.baseVersion",
52        'ddmuilib'            : "com.android.tools.ddms:ddmuilib:$ext.baseVersion",
53        'layoutlib-api'       : "com.android.tools.layoutlib:layoutlib-api:$ext.baseVersion",
54        'lint-api'            : "com.android.tools.lint:lint-api:$ext.baseVersion",
55        'lint-checks'         : "com.android.tools.lint:lint-checks:$ext.baseVersion",
56        'asset-studio'        : "com.android.tools:asset-studio:$ext.baseVersion",
57        'annotations'         : "com.android.tools:annotations:$ext.baseVersion",
58        'common'              : "com.android.tools:common:$ext.baseVersion",
59        'dvlib'               : "com.android.tools:dvlib:$ext.baseVersion",
60        'hierarchyviewer2lib' : "com.android.tools:hierarchyviewer2lib:$ext.baseVersion",
61        'ninepatch'           : "com.android.tools:ninepatch:$ext.baseVersion",
62        'rule-api'            : "com.android.tools:rule-api:$ext.baseVersion",
63        'sdk-common'          : "com.android.tools:sdk-common:$ext.baseVersion",
64        'sdklib'              : "com.android.tools:sdklib:$ext.baseVersion",
65        'sdkstats'            : "com.android.tools:sdkstats:$ext.baseVersion",
66        'sdkuilib'            : "com.android.tools:sdkuilib:$ext.baseVersion",
67        'swtmenubar'          : "com.android.tools:swtmenubar:$ext.baseVersion",
68        'testutils'           : "com.android.tools:testutils:$ext.baseVersion",
69        'traceview'           : "com.android.tools:traceview:$ext.baseVersion",
70        'uiautomatorviewer'   : "com.android.tools:uiautomatorviewer:$ext.baseVersion",
71
72        // prebuilts
73        'ant-glob'                         : 'com.android.tools.external:ant-glob:1.0',
74        'asm-5.0.3'                        : 'org.ow2.asm:asm:5.0.3',
75        'asm-analysis-5.0.3'               : 'org.ow2.asm:asm-analysis:5.0.3',
76        'asm-tree-5.0.3'                   : 'org.ow2.asm:asm-tree:5.0.3',
77        'commons-codec-1.4'                : 'commons-codec:commons-codec:1.4',
78        'commons-compress-1.0'             : 'org.apache.commons:commons-compress:1.8.1',
79        'commons-logging-1.1.1'            : 'commons-logging:commons-logging:1.1.1',
80        'easymock'                         : 'org.easymock:easymock:3.3',
81        'freemarker-2.3.20'                : 'org.freemarker:freemarker:2.3.20',
82        'guava-17.0'                       : 'com.google.guava:guava:17.0',
83        'host-libprotobuf-java-2.3.0-lite' : 'com.android.tools.external:libprotobuf-java-lite:2.3.0',
84        'httpclient-4.1.1'                 : 'org.apache.httpcomponents:httpclient:4.1.1',
85        'httpcore-4.1'                     : 'org.apache.httpcomponents:httpcore:4.1',
86        'httpmime-4.1'                     : 'org.apache.httpcomponents:httpmime:4.1',
87        'jcommon-1.0.12'                   : 'jfree:jcommon:1.0.12',
88        'jfreechart-1.0.9'                 : 'jfree:jfreechart:1.0.9',
89        'jfreechart-swt-1.0.9'             : 'jfree:jfreechart-swt:1.0.9',
90        'kxml2-2.3.0'                      : 'net.sf.kxml:kxml2:2.3.0',
91        'liblzf-1.0'                       : 'com.android.tools.external:liblzf:1.0',
92        'lombok-ast-0.2.3'                 : 'com.android.tools.external.lombok:lombok-ast:0.2.3',
93        'propertysheet'                    : 'com.android.tools.external:propertysheet:1.0',
94]
95
96configurations {
97    compile
98}
99
100dependencies {
101    compile artifacts.values()
102}
103
104task copydeps << {
105    // get the resolved dependencies from the compile configuration
106    def resolvedDependencies = configurations.compile.resolvedConfiguration.firstLevelModuleDependencies
107
108    // generate a map from "xy.jar" -> "/path/to/xy-1.0.jar"
109    def artifactMap = [:]
110    resolvedDependencies.each { dependency ->
111        def dependencyId = dependency.getName()
112        def artifactName = artifacts.find{ it.value == dependencyId}?.key
113
114        // get the jar file corresponding to the dependency
115        def artifact = getArtifact(dependency)
116        artifactMap.put(artifactName + ".jar", artifact)
117    }
118
119    project.adtPlugins.each { File pluginFile ->
120        def manifestDeps = getManifestDependencies(new File(pluginFile, "META-INF/MANIFEST.MF"))
121        logger.info("Dependencies for " + pluginFile.toString() + ": " + manifestDeps.join(","))
122
123        File dest = new File(pluginFile, "libs")
124        if (!manifestDeps.isEmpty() && !dest.isDirectory()) {
125            dest.mkdirs()
126        }
127
128        manifestDeps.each {
129            if (!artifactMap.containsKey(it)) {
130                throw new RuntimeException("No resolved artifact for: " + it + ", required for: "
131                        + pluginFile.getPath())
132            }
133
134            String destName = artifactMap.get(it)
135            logger.info("\tCopying " + destName + " to " + dest)
136            ant.copy(file: destName, tofile: new File(dest, it))
137        }
138    }
139}
140
141// unzip eclipse prebuilts into the out folder to create a target platform for the build
142task unzipTargetPlatform << {
143    File targetDir = new File(outFile, "/host/maven/target").getCanonicalFile()
144    targetDir.mkdirs()
145
146    project.targetComponents.each { String k, File v ->
147        File d = new File(targetDir, k)
148        logger.info("Unzipping " + v.getPath() + " into: " + d.getPath())
149        ant.unzip(src: v, dest: d)
150    }
151}
152
153task buildEclipse(type: Exec, dependsOn: unzipTargetPlatform) {
154    def maven = new File(projectDir, "../../prebuilts/eclipse/maven/apache-maven-3.2.1/bin/mvn").getCanonicalFile()
155    def androidOut = outFile.getCanonicalPath()
156    environment("M2_HOME", maven.getParentFile().getParentFile().getCanonicalPath())
157    workingDir projectDir
158    commandLine maven.getCanonicalPath(), "-s", "settings.xml", "-DforceContextQualifier=$project.buildNumber", "-DANDROID_OUT=$androidOut", "package"
159}
160
161private File getArtifact(ResolvedDependency dependency) {
162    if (dependency.moduleArtifacts.size() != 1) {
163        String msg = String.format("Each dependency is expected to map to a single jar file, " +
164                "but %s maps to the following artifacts: %s",
165                dependency,
166                dependency.moduleArtifacts.collect { it.file })
167        throw new RuntimeException(msg);
168    }
169
170    return dependency.moduleArtifacts.iterator().next().file
171}
172
173// parse a plugin's manifest file and return the list of jar dependencies expected to be
174// bundled inside
175private List<String> getManifestDependencies(File manifest) {
176    if (manifest == null || !manifest.exists()) {
177        return []
178    }
179
180    def entries = []
181
182    def fis = new FileInputStream(manifest)
183    try {
184        java.util.jar.Manifest m = new java.util.jar.Manifest(fis)
185        def classPath = m.getMainAttributes().getValue("Bundle-ClassPath")
186        if (classPath == null) {
187            return []
188        }
189
190        classPath.split(',').each {
191            if (!it.equals(".")) {
192                if (!it.startsWith("libs/") || !it.endsWith(".jar")) {
193                    throw new RuntimeException(
194                            "Unexpected classpath entry: " + it + " in file: " + manifest)
195                }
196
197                entries.add(it.substring("libs/".length()))
198            }
199        }
200    } finally {
201        fis.close()
202    }
203
204    return entries
205}
206