From a33d0d407cb904c531a4d4f7881f26c0cb2467aa Mon Sep 17 00:00:00 2001 From: Aleksey Rostovskiy Date: Fri, 16 Nov 2018 18:45:46 +0300 Subject: [PATCH] IDEA-CR-40021 Generate links to third-party libraries in JSON format (IDEA-202226) JSON file is needed for proper showing on the website --- .../intellij/build/ProductProperties.groovy | 2 +- .../build/impl/DistributionJARsBuilder.groovy | 18 +++-- .../build/impl/LibraryLicenseData.groovy | 19 +++++ .../impl/LibraryLicensesListGenerator.groovy | 70 ++++++++++++++----- 4 files changed, 85 insertions(+), 24 deletions(-) create mode 100644 platform/build-scripts/groovy/org/jetbrains/intellij/build/impl/LibraryLicenseData.groovy diff --git a/platform/build-scripts/groovy/org/jetbrains/intellij/build/ProductProperties.groovy b/platform/build-scripts/groovy/org/jetbrains/intellij/build/ProductProperties.groovy index 3d92c4c09192..e36ae776c312 100644 --- a/platform/build-scripts/groovy/org/jetbrains/intellij/build/ProductProperties.groovy +++ b/platform/build-scripts/groovy/org/jetbrains/intellij/build/ProductProperties.groovy @@ -73,7 +73,7 @@ abstract class ProductProperties { /** * Now file containing information about third-party libraries is bundled and shown inside IDE. - * If {@code true} html file of third-party libraries will be placed alongside with build artifacts. + * If {@code true} html & json files of third-party libraries will be placed alongside with build artifacts. */ boolean generateLibrariesLicensesTable = true diff --git a/platform/build-scripts/groovy/org/jetbrains/intellij/build/impl/DistributionJARsBuilder.groovy b/platform/build-scripts/groovy/org/jetbrains/intellij/build/impl/DistributionJARsBuilder.groovy index 4dd1e75388ab..6e520cd13c45 100644 --- a/platform/build-scripts/groovy/org/jetbrains/intellij/build/impl/DistributionJARsBuilder.groovy +++ b/platform/build-scripts/groovy/org/jetbrains/intellij/build/impl/DistributionJARsBuilder.groovy @@ -231,8 +231,10 @@ class DistributionJARsBuilder { if (productProperties.generateLibrariesLicensesTable) { String artifactNamePrefix = productProperties.getBaseArtifactName(buildContext.applicationInfo, buildContext.buildNumber) - buildContext.ant.copy(file: getThirdPartyLibrariesFilePath(), + buildContext.ant.copy(file: getThirdPartyLibrariesHtmlFilePath(), tofile: "$buildContext.paths.artifacts/$artifactNamePrefix-third-party-libraries.html") + buildContext.ant.copy(file: getThirdPartyLibrariesJsonFilePath(), + tofile: "$buildContext.paths.artifacts/$artifactNamePrefix-third-party-libraries.json") } if (productProperties.scrambleMainJar) { @@ -251,15 +253,23 @@ class DistributionJARsBuilder { private void buildThirdPartyLibrariesList() { buildContext.messages.block("Generate table of licenses for used third-party libraries") { - def generator = new LibraryLicensesListGenerator(buildContext.messages, buildContext.project, buildContext.productProperties.allLibraryLicenses) - generator.generateLicensesTable(getThirdPartyLibrariesFilePath(), usedModules) + def generator = LibraryLicensesListGenerator.create(buildContext.messages, + buildContext.project, + buildContext.productProperties.allLibraryLicenses, + usedModules) + generator.generateHtml(getThirdPartyLibrariesHtmlFilePath()) + generator.generateJson(getThirdPartyLibrariesJsonFilePath()) } } - private String getThirdPartyLibrariesFilePath() { + private String getThirdPartyLibrariesHtmlFilePath() { "$buildContext.paths.distAll/$THIRD_PARTY_LIBRARIES_FILE_PATH" } + private String getThirdPartyLibrariesJsonFilePath() { + "$buildContext.paths.temp/third-party-libraries.json" + } + private void buildLib() { def ant = buildContext.ant def layoutBuilder = createLayoutBuilder() diff --git a/platform/build-scripts/groovy/org/jetbrains/intellij/build/impl/LibraryLicenseData.groovy b/platform/build-scripts/groovy/org/jetbrains/intellij/build/impl/LibraryLicenseData.groovy new file mode 100644 index 000000000000..30f4cb586839 --- /dev/null +++ b/platform/build-scripts/groovy/org/jetbrains/intellij/build/impl/LibraryLicenseData.groovy @@ -0,0 +1,19 @@ +// Copyright 2000-2018 JetBrains s.r.o. Use of this source code is governed by the Apache 2.0 license that can be found in the LICENSE file. +package org.jetbrains.intellij.build.impl + +import groovy.transform.CompileStatic +import groovy.transform.Immutable + +/** + * Describes library entry format in third-party libraries JSON file. + * This file is used by external tools, so class properties shouldn't be changed. + */ +@Immutable +@CompileStatic +class LibraryLicenseData { + String name + String url + String version + String license + String licenseUrl +} diff --git a/platform/build-scripts/groovy/org/jetbrains/intellij/build/impl/LibraryLicensesListGenerator.groovy b/platform/build-scripts/groovy/org/jetbrains/intellij/build/impl/LibraryLicensesListGenerator.groovy index 06f26eafb216..372bde4c487f 100644 --- a/platform/build-scripts/groovy/org/jetbrains/intellij/build/impl/LibraryLicensesListGenerator.groovy +++ b/platform/build-scripts/groovy/org/jetbrains/intellij/build/impl/LibraryLicensesListGenerator.groovy @@ -15,6 +15,7 @@ */ package org.jetbrains.intellij.build.impl +import com.google.gson.GsonBuilder import com.intellij.util.containers.ContainerUtil import groovy.text.SimpleTemplateEngine import groovy.transform.CompileStatic @@ -32,24 +33,27 @@ import org.jetbrains.jps.model.module.JpsModule @CompileStatic class LibraryLicensesListGenerator { private final BuildMessages messages - private final JpsProject project - private final List licensesList + private Map licensesInModules - LibraryLicensesListGenerator(BuildMessages messages, JpsProject project, List licensesList) { + private LibraryLicensesListGenerator(BuildMessages messages, + Map licensesInModules) { this.messages = messages - this.project = project - this.licensesList = licensesList + this.licensesInModules = licensesInModules } - static List getLibraryNames(JpsLibrary lib) { - def name = lib.name - if (name.startsWith("#")) { - return ContainerUtil.map(lib.getFiles(JpsOrderRootType.COMPILED), {f->f.getName()}) - } - return Collections.singletonList(name) + static LibraryLicensesListGenerator create(BuildMessages messages, + JpsProject project, + List licensesList, + Set usedModulesNames) { + Map licences = generateLicenses(messages, project, licensesList, usedModulesNames) + return new LibraryLicensesListGenerator(messages, licences) } - void generateLicensesTable(String filePath, Set usedModulesNames) { + private static Map generateLicenses(BuildMessages messages, + JpsProject project, + List licensesList, + Set usedModulesNames) { + Map licenses = [:] messages.debug("Generating licenses table") messages.debug("Used modules: $usedModulesNames") Set usedModules = project.modules.findAll { usedModulesNames.contains(it.name) } as Set @@ -62,8 +66,7 @@ class LibraryLicensesListGenerator { } } - Map licenses = [:] - licensesList.findAll {it.license != LibraryLicense.JETBRAINS_OWN}.each { LibraryLicense lib -> + licensesList.findAll { it.license != LibraryLicense.JETBRAINS_OWN }.each { LibraryLicense lib -> if (usedModulesNames.contains(lib.attachedTo)) { licenses[lib] = lib.attachedTo } @@ -76,7 +79,18 @@ class LibraryLicensesListGenerator { } } } + return licenses + } + static List getLibraryNames(JpsLibrary lib) { + def name = lib.name + if (name.startsWith("#")) { + return ContainerUtil.map(lib.getFiles(JpsOrderRootType.COMPILED), {f->f.getName()}) + } + return Collections.singletonList(name) + } + + void generateHtml(String filePath) { messages.debug("Used libraries:") List lines = [] @@ -93,7 +107,7 @@ class LibraryLicensesListGenerator { '''.trim() def engine = new SimpleTemplateEngine() - licenses.entrySet().each { + licensesInModules.entrySet().each { LibraryLicense lib = it.key String moduleName = it.value @@ -108,10 +122,6 @@ class LibraryLicensesListGenerator { messages.debug(" $lib.name (in module $moduleName)") lines << engine.createTemplate(line).make(["name": name, "libVersion": lib.version ?: "", "license": license]).toString() } - //projectBuilder.info("Unused libraries:") - //licensesList.findAll {!licenses.containsKey(it)}.each {LibraryLicense lib -> - // projectBuilder.info(" $lib.name") - //} lines.sort(true, String.CASE_INSENSITIVE_ORDER) File file = new File(filePath) @@ -171,5 +181,27 @@ class LibraryLicensesListGenerator { out.close() } } + + void generateJson(String filePath) { + List entries = [] + + licensesInModules.keySet().sort( {it.name} ).each { + entries.add( + new LibraryLicenseData( + name: it.name, + url: it.url, + version: it.version, + license: it.license, + licenseUrl: it.libraryLicenseUrl + ) + ) + } + + File file = new File(filePath) + file.parentFile.mkdirs() + file.withWriter { + new GsonBuilder().setPrettyPrinting().create().toJson(entries, it) + } + } }