Skip to content

Commit ae586d6

Browse files
committed
Merge branch 'master' into auto_transform
2 parents 978cc1b + dff55b6 commit ae586d6

File tree

41 files changed

+561
-117
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

41 files changed

+561
-117
lines changed

.github/workflows/version-check.yml

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
name: Version Check
2+
3+
on:
4+
workflow_dispatch:
5+
pull_request:
6+
branches:
7+
- 'releases/**'
8+
9+
jobs:
10+
version-check:
11+
runs-on: ubuntu-latest
12+
steps:
13+
- uses: actions/checkout@v3.5.3
14+
15+
- name: Build
16+
run: |
17+
./gradlew gmavenVersionCheck

README.md

Lines changed: 6 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -225,30 +225,21 @@ strategy](https://docs.gradle.org/current/dsl/org.gradle.api.artifacts.Resolutio
225225

226226
### Commands
227227

228-
The simplest way to publish a project and all its associated dependencies is to
229-
just publish all projects. The following command builds SNAPSHOT dependencies of
230-
all projects. All pom level dependencies within the published artifacts will
231-
also point to SNAPSHOT versions that are co-published.
228+
For more advanced use cases where developers wish to make changes to a project,
229+
but have transitive dependencies point to publicly released versions, individual
230+
projects may be published as follows.
232231

233232
```bash
234-
./gradlew publishAllToLocal
233+
# e.g. to publish Firestore and Functions
234+
./gradlew -PprojectsToPublish="firebase-firestore,firebase-functions" \
235+
publishReleasingLibrariesToMavenLocal
235236
```
236237

237238
Developers may take a dependency on these locally published versions by adding
238239
the `mavenLocal()` repository to your [repositories
239240
block](https://docs.gradle.org/current/userguide/declaring_repositories.html) in
240241
your app module's build.gradle.
241242

242-
For more advanced use cases where developers wish to make changes to a project,
243-
but have transitive dependencies point to publicly released versions, individual
244-
projects may be published as follows.
245-
246-
```bash
247-
# e.g. to publish Firestore and Functions
248-
./gradlew -PprojectsToPublish=":firebase-firestore,:firebase-functions" \
249-
publishProjectsToMavenLocal
250-
```
251-
252243
### Code Formatting
253244

254245
#### Java

buildSrc/README.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
## Build Source
22

3+
> [!NOTE]
4+
> Eventually, this will be merged with our [contributor documentation](https://firebase.github.io/firebase-android-sdk/).
5+
36
This file will be more organized as time progresses. Because a lot of our
47
plugins and systems require a moderate amount of cognitive overhead to understand,
58
I thought it best to provide documentation for such systems. You can find the

buildSrc/src/main/java/com/google/firebase/gradle/bomgenerator/RecipeVersionWriter.java

Lines changed: 0 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -173,18 +173,6 @@ public String generateVersionUpdate() {
173173
"Firebase Functions KTX",
174174
"functions-ktx-dependency",
175175
"com.google.firebase:firebase-functions-ktx"));
176-
outputBuilder.append(
177-
generateVersionVariable(
178-
depsByArtifactId,
179-
"Firebase Dynamic Links",
180-
"fdl-dependency",
181-
"com.google.firebase:firebase-dynamic-links"));
182-
outputBuilder.append(
183-
generateVersionVariable(
184-
depsByArtifactId,
185-
"Firebase Dynamic Links KTX",
186-
"fdl-ktx-dependency",
187-
"com.google.firebase:firebase-dynamic-links-ktx"));
188176
outputBuilder.append(
189177
generateVersionVariable(
190178
depsByArtifactId,

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

Lines changed: 8 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -56,11 +56,17 @@ class FirebaseJavaLibraryPlugin : BaseFirebaseLibraryPlugin() {
5656
setupStaticAnalysis(project, firebaseLibrary)
5757
setupApiInformationAnalysis(project)
5858
getIsPomValidTask(project, firebaseLibrary)
59-
getSemverTaskJar(project, firebaseLibrary)
59+
setupVersionCheckTasks(project, firebaseLibrary)
6060
configurePublishing(project, firebaseLibrary)
6161
}
6262

63-
private fun getSemverTaskJar(project: Project, firebaseLibrary: FirebaseLibraryExtension) {
63+
private fun setupVersionCheckTasks(project: Project, firebaseLibrary: FirebaseLibraryExtension) {
64+
project.tasks.register<GmavenVersionChecker>("gmavenVersionCheck") {
65+
groupId.value(firebaseLibrary.groupId.get())
66+
artifactId.value(firebaseLibrary.artifactId.get())
67+
version.value(firebaseLibrary.version)
68+
latestReleasedVersion.value(firebaseLibrary.latestReleasedVersion.orElseGet { "" })
69+
}
6470
project.mkdir("semver")
6571
project.tasks.register<GmavenCopier>("copyPreviousArtifacts") {
6672
dependsOn("jar")

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

Lines changed: 20 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -27,7 +27,6 @@ import java.io.File
2727
import org.gradle.api.JavaVersion
2828
import org.gradle.api.Project
2929
import org.gradle.api.attributes.Attribute
30-
import org.gradle.api.publish.tasks.GenerateModuleMetadata
3130
import org.gradle.api.tasks.Copy
3231
import org.gradle.kotlin.dsl.apply
3332
import org.gradle.kotlin.dsl.create
@@ -85,6 +84,7 @@ class FirebaseLibraryPlugin : BaseFirebaseLibraryPlugin() {
8584
android.testServer(FirebaseTestServer(project, firebaseLibrary.testLab, android))
8685
setupStaticAnalysis(project, firebaseLibrary)
8786
getIsPomValidTask(project, firebaseLibrary)
87+
<<<<<<< HEAD
8888
getSemverTaskAar(project, firebaseLibrary)
8989
getPackageTransform(project, firebaseLibrary)
9090
configurePublishing(project, firebaseLibrary, android)
@@ -99,7 +99,20 @@ class FirebaseLibraryPlugin : BaseFirebaseLibraryPlugin() {
9999
}
100100

101101
private fun getSemverTaskAar(project: Project, firebaseLibrary: FirebaseLibraryExtension) {
102+
=======
103+
setupVersionCheckTasks(project, firebaseLibrary)
104+
configurePublishing(project, firebaseLibrary, android)
105+
}
106+
107+
private fun setupVersionCheckTasks(project: Project, firebaseLibrary: FirebaseLibraryExtension) {
108+
project.tasks.register<GmavenVersionChecker>("gmavenVersionCheck") {
109+
groupId.value(firebaseLibrary.groupId.get())
110+
artifactId.value(firebaseLibrary.artifactId.get())
111+
version.value(firebaseLibrary.version)
112+
latestReleasedVersion.value(firebaseLibrary.latestReleasedVersion.orElseGet { "" })
113+
}
102114
project.mkdir("semver")
115+
project.mkdir("semver/previous-version")
103116
project.tasks.register<GmavenCopier>("copyPreviousArtifacts") {
104117
dependsOn("bundleReleaseAar")
105118
project.file("semver/previous.aar").delete()
@@ -120,7 +133,10 @@ class FirebaseLibraryPlugin : BaseFirebaseLibraryPlugin() {
120133

121134
project.tasks.register<Copy>("extractPreviousClasses") {
122135
dependsOn("copyPreviousArtifacts")
123-
if (project.file("semver/previous.aar").exists()) {
136+
if (
137+
GmavenHelper(firebaseLibrary.groupId.get(), firebaseLibrary.artifactId.get())
138+
.isPresentInGmaven()
139+
) {
124140
from(project.zipTree("semver/previous.aar"))
125141
into(project.file("semver/previous-version"))
126142
}
@@ -130,15 +146,15 @@ class FirebaseLibraryPlugin : BaseFirebaseLibraryPlugin() {
130146

131147
val previousJarFile = project.file("semver/previous-version/classes.jar").absolutePath
132148
project.tasks.register<ApiDiffer>("semverCheck") {
149+
dependsOn("extractCurrentClasses")
150+
dependsOn("extractPreviousClasses")
133151
currentJar.value(currentJarFile)
134152
previousJar.value(previousJarFile)
135153
version.value(firebaseLibrary.version)
136154
previousVersionString.value(
137155
GmavenHelper(firebaseLibrary.groupId.get(), firebaseLibrary.artifactId.get())
138156
.getLatestReleasedVersion()
139157
)
140-
dependsOn("extractCurrentClasses")
141-
dependsOn("extractPreviousClasses")
142158
}
143159
}
144160

@@ -178,7 +194,6 @@ class FirebaseLibraryPlugin : BaseFirebaseLibraryPlugin() {
178194
android: LibraryExtension
179195
) {
180196
android.publishing.singleVariant("release") { withSourcesJar() }
181-
project.tasks.withType<GenerateModuleMetadata> { isEnabled = false }
182197

183198
configurePublishing(project, firebaseLibrary)
184199
}

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

Lines changed: 35 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@
1515
package com.google.firebase.gradle.plugins
1616

1717
import java.io.FileNotFoundException
18+
import java.net.HttpURLConnection
1819
import java.net.URL
1920
import javax.xml.parsers.DocumentBuilder
2021
import javax.xml.parsers.DocumentBuilderFactory
@@ -30,24 +31,52 @@ class GmavenHelper(val groupId: String, val artifactId: String) {
3031
return "${GMAVEN_ROOT}/${groupIdAsPath}/${artifactId}/${version}/${pomFileName}"
3132
}
3233

34+
fun isPresentInGmaven(): Boolean {
35+
val groupIdAsPath = groupId.replace(".", "/")
36+
val u = URL("${GMAVEN_ROOT}/${groupIdAsPath}/${artifactId}/maven-metadata.xml")
37+
val huc: HttpURLConnection = u.openConnection() as HttpURLConnection
38+
huc.setRequestMethod("GET") // OR huc.setRequestMethod ("HEAD");
39+
huc.connect()
40+
val code: Int = huc.getResponseCode()
41+
return code == HttpURLConnection.HTTP_OK
42+
}
43+
3344
fun getArtifactForVersion(version: String, isJar: Boolean): String {
3445
val fileName =
3546
if (isJar == true) "${artifactId}-${version}.jar" else "${artifactId}-${version}.aar"
3647
val groupIdAsPath = groupId.replace(".", "/")
3748
return "${GMAVEN_ROOT}/${groupIdAsPath}/${artifactId}/${version}/${fileName}"
3849
}
3950

51+
fun hasReleasedVersion(version: String): Boolean {
52+
val doc: Document? = getMavenMetadata()
53+
if (doc != null) {
54+
val versions = doc.getElementsByTagName("version")
55+
for (i in 0..versions.length - 1) {
56+
if (versions.item(i).textContent == version) {
57+
return true
58+
}
59+
}
60+
}
61+
return false
62+
}
63+
4064
fun getLatestReleasedVersion(): String {
65+
val doc: Document? = getMavenMetadata()
66+
return doc?.getElementsByTagName("latest")?.item(0)?.getTextContent() ?: ""
67+
}
68+
69+
fun getMavenMetadata(): Document? {
70+
val groupIdAsPath = groupId.replace(".", "/")
71+
val mavenMetadataUrl = "${GMAVEN_ROOT}/${groupIdAsPath}/${artifactId}/maven-metadata.xml"
72+
val factory: DocumentBuilderFactory = DocumentBuilderFactory.newInstance()
73+
val builder: DocumentBuilder = factory.newDocumentBuilder()
4174
try {
42-
val groupIdAsPath = groupId.replace(".", "/")
43-
val mavenMetadataUrl = "${GMAVEN_ROOT}/${groupIdAsPath}/${artifactId}/maven-metadata.xml"
44-
val factory: DocumentBuilderFactory = DocumentBuilderFactory.newInstance()
45-
val builder: DocumentBuilder = factory.newDocumentBuilder()
4675
val doc: Document = builder.parse(URL(mavenMetadataUrl).openStream())
4776
doc.documentElement.normalize()
48-
return doc.getElementsByTagName("latest").item(0).getTextContent()
77+
return doc
4978
} catch (e: FileNotFoundException) {
50-
return ""
79+
return null
5180
}
5281
}
5382
}
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 org.gradle.api.DefaultTask
18+
import org.gradle.api.GradleException
19+
import org.gradle.api.provider.Property
20+
import org.gradle.api.tasks.Input
21+
import org.gradle.api.tasks.TaskAction
22+
23+
abstract class GmavenVersionChecker : DefaultTask() {
24+
25+
@get:Input abstract val groupId: Property<String>
26+
27+
@get:Input abstract val artifactId: Property<String>
28+
29+
@get:Input abstract val latestReleasedVersion: Property<String>
30+
31+
@get:Input abstract val version: Property<String>
32+
33+
@TaskAction
34+
fun run() {
35+
val mavenHelper = GmavenHelper(groupId.get(), artifactId.get())
36+
val latestMavenVersion = mavenHelper.getLatestReleasedVersion()
37+
val info =
38+
"\n latestReleasedVersion in gradle.properties should match the latest release on GMaven (${latestMavenVersion})" +
39+
"\n version in gradle.properties should be a version bump above this, following SemVer, and should not be released on GMaven"
40+
// Either the Maven metadata does not exist, or the library hasn't been released
41+
if (latestMavenVersion.isEmpty()) {
42+
return
43+
}
44+
// TODO(b/285892320): Remove condition when bug fixed
45+
if (artifactId.get() == "protolite-well-known-types") {
46+
return
47+
}
48+
if (version.get() == latestReleasedVersion.get()) {
49+
throw GradleException(
50+
"version and latestReleasedVersion from gradle.properties are the same (${version.get()})" +
51+
info
52+
)
53+
}
54+
if (latestMavenVersion == version.get()) {
55+
throw GradleException(
56+
"version from gradle.properties (${version.get()}) is already the latest release on GMaven" +
57+
info
58+
)
59+
} else if (mavenHelper.hasReleasedVersion(version.get())) {
60+
throw GradleException(
61+
"version from gradle.properties (${version.get()}) has already been released on GMaven" +
62+
info
63+
)
64+
}
65+
if (latestMavenVersion != latestReleasedVersion.get()) {
66+
if (mavenHelper.hasReleasedVersion(latestReleasedVersion.get())) {
67+
throw GradleException(
68+
"latestReleasedVersion from gradle.properties (${latestReleasedVersion.get()}) has been released but is not the latest release on GMaven (${latestMavenVersion})"
69+
)
70+
} else {
71+
throw GradleException(
72+
"latestReleasedVersion from gradle.properties (${latestReleasedVersion.get()}) has not been released on GMaven" +
73+
info
74+
)
75+
}
76+
}
77+
}
78+
}

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

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -191,9 +191,9 @@ abstract class PublishingPlugin : Plugin<Project> {
191191
allFirebaseLibraries: List<FirebaseLibraryExtension>
192192
): ReleaseMetadata? {
193193
val projectsToPublish = project.provideProperty<String>("projectsToPublish").orNull
194-
val releaseName = project.provideProperty<String>("releaseName").orNull
194+
val releaseName = project.provideProperty<String>("releaseName").orNull ?: "NO_NAME"
195195

196-
if (projectsToPublish == null || releaseName == null) return null
196+
if (projectsToPublish == null) return null
197197

198198
val projectNames = projectsToPublish.split(",")
199199
val librariesToRelease =
@@ -450,7 +450,6 @@ abstract class PublishingPlugin : Plugin<Project> {
450450
project.tasks.register(SEMVER_CHECK_TASK) {
451451
for (releasingProject in releasingProjects) {
452452
val semverCheckTask = releasingProject.tasks.named("semverCheck")
453-
454453
dependsOn(semverCheckTask)
455454
}
456455
}

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

Lines changed: 4 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -36,16 +36,14 @@ abstract class GmavenCopier : DefaultTask() {
3636
@TaskAction
3737
fun run() {
3838
val mavenHelper = GmavenHelper(groupId.get(), artifactId.get())
39+
if (!mavenHelper.isPresentInGmaven()) {
40+
return
41+
}
3942
val gMavenPath =
4043
mavenHelper.getArtifactForVersion(
4144
mavenHelper.getLatestReleasedVersion(),
4245
!aarAndroidFile.get()
4346
)
44-
try {
45-
URL(gMavenPath).openStream().use { Files.copy(it, Paths.get(filePath.get())) }
46-
} catch (_: java.io.FileNotFoundException) {
47-
// Gmaven Artifact doesn't exist.
48-
return
49-
}
47+
URL(gMavenPath).openStream().use { Files.copy(it, Paths.get(filePath.get())) }
5048
}
5149
}

0 commit comments

Comments
 (0)