Skip to content

Commit 990f27f

Browse files
VinayGuthalrlazo
andauthored
add check to diff pom files and see if any dependency is downgraded (firebase#4719)
* add check to diff pom files and see if any dependency is downgraded * update revert * add copyright * update * Update buildSrc/src/main/java/com/google/firebase/gradle/plugins/GmavenHelper.kt Co-authored-by: Rodrigo Lazo <rlazo@users.noreply.github.com> * Update buildSrc/src/main/java/com/google/firebase/gradle/plugins/GmavenHelper.kt Co-authored-by: Rodrigo Lazo <rlazo@users.noreply.github.com> * Update buildSrc/src/main/java/com/google/firebase/gradle/plugins/GmavenHelper.kt Co-authored-by: Rodrigo Lazo <rlazo@users.noreply.github.com> * update * Update buildSrc/src/main/java/com/google/firebase/gradle/plugins/PomValidator.kt Co-authored-by: Rodrigo Lazo <rlazo@users.noreply.github.com> * update --------- Co-authored-by: Rodrigo Lazo <rlazo@users.noreply.github.com>
1 parent f7ced5b commit 990f27f

File tree

7 files changed

+156
-0
lines changed

7 files changed

+156
-0
lines changed
Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
name: Validate Artifact Dependencies
2+
3+
on:
4+
workflow_dispatch:
5+
pull_request:
6+
branches:
7+
- 'releases/**'
8+
9+
jobs:
10+
build-artifacts:
11+
runs-on: ubuntu-latest
12+
steps:
13+
- uses: actions/checkout@v3
14+
15+
- name: Perform gradle build
16+
run: |
17+
./gradlew validatePomForRelease -PpublishConfigFilePath=release.cfg -PpublishMode=RELEASE -PincludeFireEscapeArtifacts=true

buildSrc/src/main/java/com/google/firebase/gradle/plugins/BaseFirebaseLibraryPlugin.kt

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -72,6 +72,15 @@ abstract class BaseFirebaseLibraryPlugin : Plugin<Project> {
7272
return apiInfo
7373
}
7474

75+
protected fun getIsPomValidTask(project: Project, firebaseLibrary: FirebaseLibraryExtension) {
76+
project.tasks.register<PomValidator>("isPomDependencyValid") {
77+
pomFilePath.value(project.file("build/publications/mavenAar/pom-default.xml"))
78+
groupId.value(firebaseLibrary.groupId.get())
79+
artifactId.value(firebaseLibrary.artifactId.get())
80+
dependsOn("generatePomFileForMavenAarPublication")
81+
}
82+
}
83+
7584
protected fun getGenerateApiTxt(project: Project, srcDirs: Set<File>) =
7685
project.tasks.register<GenerateApiTxtTask>("generateApiTxtFile") {
7786
sources.value(project.provider { srcDirs })

buildSrc/src/main/java/com/google/firebase/gradle/plugins/FirebaseJavaLibraryPlugin.kt

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@ class FirebaseJavaLibraryPlugin : BaseFirebaseLibraryPlugin() {
4747

4848
setupStaticAnalysis(project, firebaseLibrary)
4949
setupApiInformationAnalysis(project)
50+
getIsPomValidTask(project, firebaseLibrary)
5051
configurePublishing(project, firebaseLibrary)
5152
}
5253

@@ -55,6 +56,7 @@ class FirebaseJavaLibraryPlugin : BaseFirebaseLibraryPlugin() {
5556
project.convention.getPlugin<JavaPluginConvention>().sourceSets.getByName("main").java.srcDirs
5657

5758
val apiInfo = getApiInfo(project, srcDirs)
59+
5860
val generateApiTxt = getGenerateApiTxt(project, srcDirs)
5961
val docStubs = getDocStubs(project, srcDirs)
6062

buildSrc/src/main/java/com/google/firebase/gradle/plugins/FirebaseLibraryPlugin.kt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -79,6 +79,7 @@ class FirebaseLibraryPlugin : BaseFirebaseLibraryPlugin() {
7979
setupApiInformationAnalysis(project, android)
8080
android.testServer(FirebaseTestServer(project, firebaseLibrary.testLab, android))
8181
setupStaticAnalysis(project, firebaseLibrary)
82+
getIsPomValidTask(project, firebaseLibrary)
8283
configurePublishing(project, firebaseLibrary, android)
8384
}
8485

Lines changed: 40 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,40 @@
1+
// Copyright 2023 Google LLC
2+
//
3+
// Licensed under the Apache License, Version 2.0 (the "License");
4+
// you may not use this file except in compliance with the License.
5+
// You may obtain a copy of the License at
6+
//
7+
// http://www.apache.org/licenses/LICENSE-2.0
8+
//
9+
// Unless required by applicable law or agreed to in writing, software
10+
// distributed under the License is distributed on an "AS IS" BASIS,
11+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
// See the License for the specific language governing permissions and
13+
// limitations under the License.
14+
15+
package com.google.firebase.gradle.plugins
16+
17+
import java.net.URL
18+
import javax.xml.parsers.DocumentBuilder
19+
import javax.xml.parsers.DocumentBuilderFactory
20+
import org.w3c.dom.Document
21+
22+
class GmavenHelper(val groupId: String, val artifactId: String) {
23+
val GMAVEN_ROOT = "https://dl.google.com/dl/android/maven2"
24+
25+
fun getPomFileForVersion(version: String): String {
26+
val pomFileName = "${artifactId}-${version}.pom"
27+
val groupIdAsPath = groupId.replace(".", "/")
28+
return "${GMAVEN_ROOT}/${groupIdAsPath}/${artifactId}/${version}/${pomFileName}"
29+
}
30+
31+
fun getLatestReleasedVersion(): String {
32+
val groupIdAsPath = groupId.replace(".", "/")
33+
val mavenMetadataUrl = "${GMAVEN_ROOT}/${groupIdAsPath}/${artifactId}/maven-metadata.xml"
34+
val factory: DocumentBuilderFactory = DocumentBuilderFactory.newInstance()
35+
val builder: DocumentBuilder = factory.newDocumentBuilder()
36+
val doc: Document = builder.parse(URL(mavenMetadataUrl).openStream())
37+
doc.documentElement.normalize()
38+
return doc.getElementsByTagName("latest").item(0).getTextContent()
39+
}
40+
}
Lines changed: 78 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,78 @@
1+
// Copyright 2023 Google LLC
2+
//
3+
// Licensed under the Apache License, Version 2.0 (the "License");
4+
// you may not use this file except in compliance with the License.
5+
// You may obtain a copy of the License at
6+
//
7+
// http://www.apache.org/licenses/LICENSE-2.0
8+
//
9+
// Unless required by applicable law or agreed to in writing, software
10+
// distributed under the License is distributed on an "AS IS" BASIS,
11+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
// See the License for the specific language governing permissions and
13+
// limitations under the License.
14+
15+
package com.google.firebase.gradle.plugins
16+
17+
import java.io.File
18+
import java.net.URL
19+
import javax.xml.parsers.DocumentBuilder
20+
import javax.xml.parsers.DocumentBuilderFactory
21+
import org.gradle.api.DefaultTask
22+
import org.gradle.api.GradleException
23+
import org.gradle.api.provider.Property
24+
import org.gradle.api.tasks.Input
25+
import org.gradle.api.tasks.InputFile
26+
import org.gradle.api.tasks.TaskAction
27+
import org.w3c.dom.Document
28+
import org.w3c.dom.Element
29+
import org.w3c.dom.Node
30+
import org.w3c.dom.NodeList
31+
32+
abstract class PomValidator : DefaultTask() {
33+
@get:InputFile abstract val pomFilePath: Property<File>
34+
@get:Input abstract val artifactId: Property<String>
35+
@get:Input abstract val groupId: Property<String>
36+
37+
@TaskAction
38+
fun run() {
39+
val gMavenHelper = GmavenHelper(groupId.get(), artifactId.get())
40+
val latestReleasedVersion = gMavenHelper.getLatestReleasedVersion()
41+
val releasedVersionPomUrl = gMavenHelper.getPomFileForVersion(latestReleasedVersion)
42+
var output: String = diffWithPomFileUrl(releasedVersionPomUrl).trim()
43+
if (output.isNotEmpty()) {
44+
throw GradleException("${output}\nPlease fix the above errors")
45+
}
46+
}
47+
48+
fun getMapFromXml(pomNodeList: NodeList): Map<String, String> {
49+
val pomMap = mutableMapOf<String, String>()
50+
for (i in 0..pomNodeList.length - 1) {
51+
val node: Node = pomNodeList.item(i)
52+
if (node.getNodeType() == Node.ELEMENT_NODE) {
53+
val element = node as Element
54+
val artifact = element.getElementsByTagName("artifactId").item(0).getTextContent()
55+
val version = element.getElementsByTagName("version").item(0).getTextContent()
56+
pomMap[artifact] = version
57+
}
58+
}
59+
return pomMap
60+
}
61+
62+
fun diffWithPomFileUrl(pomUrl: String): String {
63+
val factory: DocumentBuilderFactory = DocumentBuilderFactory.newInstance()
64+
val oldPomBuilder: DocumentBuilder = factory.newDocumentBuilder()
65+
val oldPomDoc: Document = oldPomBuilder.parse(URL(pomUrl).openStream())
66+
val currentPomBuilder: DocumentBuilder = factory.newDocumentBuilder()
67+
val currentPomDoc: Document = currentPomBuilder.parse(pomFilePath.get())
68+
val oldPomMap = getMapFromXml(oldPomDoc.getElementsByTagName("dependency"))
69+
val currentPomMap = getMapFromXml(currentPomDoc.getElementsByTagName("dependency"))
70+
71+
return currentPomMap
72+
.filter {
73+
(oldPomMap.get(it.key) != null) && (oldPomMap.get(it.key)!!.trim()) > it.value.trim()
74+
}
75+
.map { "Artifacts ${it.key} has been degraded to ${it.value} from ${oldPomMap.get(it.key)}" }
76+
.joinToString("\n")
77+
}
78+
}

buildSrc/src/main/java/com/google/firebase/gradle/plugins/publish/PublishingPlugin.java

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -134,6 +134,15 @@ public void apply(Project project) {
134134
.set("projectsToPublish", projectsToPublish);
135135

136136
Publisher publisher = new Publisher(publishMode, projectsToPublish);
137+
project
138+
.getTasks()
139+
.create(
140+
"validatePomForRelease",
141+
t -> {
142+
for (FirebaseLibraryExtension toPublish : projectsToPublish) {
143+
t.dependsOn(toPublish.getPath() + ":isPomDependencyValid");
144+
}
145+
});
137146
project.subprojects(
138147
sub -> {
139148
FirebaseLibraryExtension firebaseLibrary =

0 commit comments

Comments
 (0)