Skip to content

Commit

Permalink
Misc foundry renames and documentation updates (#1005)
Browse files Browse the repository at this point in the history
<!--
  ⬆ Put your description above this! ⬆

  Please be descriptive and detailed.
  
Please read our [Contributing
Guidelines](https://github.com/tinyspeck/foundry/blob/main/.github/CONTRIBUTING.md)
and [Code of Conduct](https://slackhq.github.io/code-of-conduct).

Don't worry about deleting this, it's not visible in the PR!
-->
  • Loading branch information
ZacSweers authored Oct 2, 2024
1 parent 3fbd389 commit f0eb0fa
Show file tree
Hide file tree
Showing 43 changed files with 308 additions and 396 deletions.
33 changes: 33 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,39 @@ Changelog
**Unreleased**
--------------

### Project Restructuring

We've restructured this project! Since its early days as a simple Gradle convention plugin it's expanded into IntelliJ plugins, CLIs, CI tooling, and more. To better capture this, we've renamed the project to *Foundry*, restructured its artifacts into a more cohesive setup, moved kotlin-cli-util into this repo, and will likely split out some more artifacts down the line.

#### Migration Guide

- Any **gradle properties** prefixed with `slack.` or `sgp.` have now moved to `foundry.`. `slack.gradle.` prefix have also removed the `gradle.` (i.e. `slack.gradle.foo` would now be `foundry.foo`).
- Package names have all aligned to `foundry.*`. In most cases it should be simple enough to replace `import com.slack.*` with `import foundry.*`.
- Gradle coordinates group have moved to the `com.slack.foundry` group name.

| Old Artifact ID | New Artifact ID |
|---------------------|-----------------|
| sgp | gradle-plugin |
| sgp-agp-handler-api | agp-handler-api |
| sgp-common | foundry-common |
| sgp-tracing | tracing |
| skippy | skippy |

- The former `kotlin-cli-util` APIs have moved to the `com.slack.foundry:cli` artifact.
- Platform-specific plugins now live under the `platforms/` directory.
- All other tools now live under the `tools/` directory.
- Most top-level `Slack`-prefixed APIs are now prefixed with `Foundry`.
- The primary gradle entry points are now `foundry {}`, but the previous `slack {}` entry points are left with deprecation `ReplaceWith` options.
- Gradle plugin IDs have migrated to `foundry.*` names.

| Old | New |
|-------------------------------|--------------------------|
| `slack.gradle.root` | `foundry.root` |
| `slack.gradle.base` | `foundry.base` |
| `slack.gradle.apk-versioning` | `foundry.apk-versioning` |

- Introduce new required `foundry.android.defaultNamespacePrefix` property for android projects. This is necessary for projects that don't define an `android.namespace` explicitly.

0.19.6
------

Expand Down
57 changes: 0 additions & 57 deletions build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -131,69 +131,12 @@ allprojects {
}
}

/**
* These are magic shared versions that are used in both buildSrc's build file and
* SlackDependencies. These are copied as a source into the main source set and templated for
* replacement.
*/
data class KotlinBuildConfig(val kotlin: String) {
private val kotlinVersion by lazy {
val (major, minor, patch) = kotlin.substringBefore("-").split('.').map { it.toInt() }
KotlinVersion(major, minor, patch)
}

// Left as a toe-hold for any future needs
private val extraArgs = arrayOf<String>()

/**
* See more information about these in
* - CommonCompilerArguments.kt
* - K2JVMCompilerArguments.kt
*/
val kotlinCompilerArgs: List<String> =
listOf(
// Enhance not null annotated type parameter's types to definitely not null types (@NotNull T
// => T & Any)
"-Xenhance-type-parameter-types-to-def-not-null",
// Use fast implementation on Jar FS. This may speed up compilation time, but currently it's
// an experimental mode
// TODO toe-hold but we can't use it yet because it emits a warning that fails with -Werror
// https://youtrack.jetbrains.com/issue/KT-54928
// "-Xuse-fast-jar-file-system",
// Support inferring type arguments based on only self upper bounds of the corresponding type
// parameters
"-Xself-upper-bound-inference",
) + extraArgs

/**
* See more information about these in
* - CommonCompilerArguments.kt
* - K2JVMCompilerArguments.kt
*/
val kotlinJvmCompilerArgs: List<String> =
listOf(
"-Xjsr305=strict",
// Match JVM assertion behavior:
// https://publicobject.com/2019/11/18/kotlins-assert-is-not-like-javas-assert/
"-Xassertions=jvm",
// Potentially useful for static analysis tools or annotation processors.
"-Xemit-jvm-type-annotations",
// Enable new jvm-default behavior
// https://blog.jetbrains.com/kotlin/2020/07/kotlin-1-4-m3-generating-default-methods-in-interfaces/
"-Xjvm-default=all",
"-Xtype-enhancement-improvements-strict-mode",
// https://kotlinlang.org/docs/whatsnew1520.html#support-for-jspecify-nullness-annotations
"-Xjspecify-annotations=strict",
)
}

tasks.dokkaHtmlMultiModule {
outputDirectory.set(rootDir.resolve("docs/api/0.x"))
includes.from(project.layout.projectDirectory.file("README.md"))
}

val kotlinVersion = libs.versions.kotlin.get()
val kotlinBuildConfig = KotlinBuildConfig(kotlinVersion)

val jvmTargetVersion = libs.versions.jvmTarget.map(JvmTarget::fromTarget)

Expand Down
6 changes: 3 additions & 3 deletions config/git/hooks/pre-commit
Original file line number Diff line number Diff line change
Expand Up @@ -2,8 +2,8 @@

######## FORMAT HOOK START ########

if [[ "$SLACK_COMMIT_HOOK_OPT_OUT" == "true" ]]; then
echo 'Warning: Skipping pre-commit hook because SLACK_COMMIT_HOOK_OPT_OUT is true'
if [[ "$FOUNDRY_COMMIT_HOOK_OPT_OUT" == "true" ]]; then
echo 'Warning: Skipping pre-commit hook because FOUNDRY_COMMIT_HOOK_OPT_OUT is true'
exit
fi

Expand Down Expand Up @@ -65,7 +65,7 @@ original_partially_staged_filenames=$(echo "$original_partially_staged_chksum" |

#### Sort Dependencies section
# Get a list of staged build.gradle.kts files
kts_files_list="$(git diff --cached --name-only --diff-filter=ACMR "-G.*" | grep -Ei "build\.gradle\.kts$" | grep -v -x -F "tooling/slack-platform/build.gradle.kts")"
kts_files_list="$(git diff --cached --name-only --diff-filter=ACMR "-G.*" | grep -Ei "build\.gradle\.kts$" )"
if [[ ! -z ${kts_files_list} ]]; then
# We have some build files! Join them to a string delimited on space. We'll pass these to sortDependencies
kts_files_list="$(echo ${kts_files_list} | paste -sd " " -)"
Expand Down
5 changes: 0 additions & 5 deletions config/lint/lint.xml
Original file line number Diff line number Diff line change
Expand Up @@ -19,11 +19,6 @@
<ignore path="build" />
</issue>

<!-- <issue id="ComposeCompositionLocalUsage">-->
<!-- <option name="allowed-composition-locals"-->
<!-- value="LocalComposeDarkModeHelper,LocalImageLoader,LocalSKImageLoader,LocalSlackColors,LocalTypography,LocalTraceContext,LocalSKPalettes,LocalSKColorSet,LocalSKThemeColorSet,LocalSKUserThemeEmitter,LocalSlackCompositionLocalsState" />-->
<!-- </issue>-->

<issue id="ComposeNamingUppercase,ComposeNamingLowercase">
<option name="allowed-composable-function-names" value=".*Presenter"/>
</issue>
Expand Down
18 changes: 9 additions & 9 deletions docs/architecture.md
Original file line number Diff line number Diff line change
@@ -1,33 +1,33 @@
Architecture
============

SGP consists of three Gradle plugins and some associated helper artifacts.
Foundry contains three Gradle plugins and some associated helper artifacts.

## `SlackRootPlugin`
## `FoundryRootPlugin`

This is the root plugin that is applied to the root project of a multi-project build.

```kotlin
plugins {
id("com.slack.gradle.root")
id("foundry.root")
}
```

Its responsibilities include:

- Registering the `SlackTools` build service.
- Registering the `FoundryTools` build service.
- Setting up global configuration (i.e. global lifecycle tasks, download tasks, etc).
- Validating the JDK matches the expected JDK defined in `libs.versions.toml`.
- Configure git (hooks, ignored revisions, etc).
- (If running on macOS) Validating the build isn't running in Rosetta mode.

## `SlackBasePlugin`
## `FoundryBasePlugin`

This is the base plugin that is applied to _all_ projects (including the root project).

```kotlin
plugins {
id("com.slack.gradle.base")
id("foundry.base")
}
```

Expand All @@ -45,7 +45,7 @@ Its responsibilities include:

This class warrants special mention as it is responsible for the bulk of the configuration applied to projects SGP manages.

- Creates and exposes the [`slack` extension DSL](/dsl).
- Creates and exposes the [`foundry` extension DSL](/dsl).
- Applies common configurations.
- This largely just sets up the dependency sorter plugin.
- Applies common JVM configurations.
Expand Down Expand Up @@ -74,7 +74,7 @@ Java projects are fairly simple. Note that these are applied on all projects tha
- Gradle toolchains are used to manage the JDK used for `JavaCompile` tasks in non-android projects to ensure consistency.
- All `JavaCompile` tasks have `-parameters` added to `options.compilerArgs` for better static analysis and annotation processing support.
- If opted-in, error-prone and nullaway are applied and set up with the project with common configurations (configured checks, ignoring build dirs, etc).
- SGP supports Error-Prone's auto-patching mode via enabling the `slack.epAutoPatch` property.
- Foundry supports Error-Prone's auto-patching mode via enabling the `foundry.epAutoPatch` property.

##### Android

Expand Down Expand Up @@ -147,7 +147,7 @@ This also adds a `generateVersionProperties` task that is more or less only rele

## AGP Handlers

SGP is designed to work with multiple versions of AGP at a time, albeit only for forward compatibility and testing reasons. Generally SGP will only be tested against the latest stable version of AGP. To support multiple beta/canary versions of upcoming AGP versions, SGP has an API called `AgpHandler`, which is intended to be an AGP-agnostic common interface for configuring AGP projects across breaking API (source or binary) changes. When a new such change is introduced, we create an `AgpHandler{version}` artifact and implementation with that AGP version as its minimum. At runtime, SGP loads the relevant `AgpHandler` instance for the AGP version it is running against and relevant APIs use this instance via `SlackTools` to interact with them in a version-agnostic way. These aren't always needed so there may be times when there are no implementations needed for the current suite of AGP versions.
SGP is designed to work with multiple versions of AGP at a time, albeit only for forward compatibility and testing reasons. Generally SGP will only be tested against the latest stable version of AGP. To support multiple beta/canary versions of upcoming AGP versions, SGP has an API called `AgpHandler`, which is intended to be an AGP-agnostic common interface for configuring AGP projects across breaking API (source or binary) changes. When a new such change is introduced, we create an `AgpHandler{version}` artifact and implementation with that AGP version as its minimum. At runtime, SGP loads the relevant `AgpHandler` instance for the AGP version it is running against and relevant APIs use this instance via `FoundryTools` to interact with them in a version-agnostic way. These aren't always needed so there may be times when there are no implementations needed for the current suite of AGP versions.

An example handler for AGP 8.0 looks like this.

Expand Down
2 changes: 1 addition & 1 deletion docs/dependency-rake.md
Original file line number Diff line number Diff line change
Expand Up @@ -41,7 +41,7 @@ The core implementation of DR lives in `DependencyRake.kt`.
To run dependency rake in a project, use the below command

```bash
$ ./gradlew rakeDependencies -Pslack.gradle.config.enableAnalysisPlugin=true --no-configuration-cache
$ ./gradlew rakeDependencies -Pfoundry.config.enableAnalysisPlugin=true --no-configuration-cache
```

This will run all `rakeDependencies` tasks in the project. This task exists on all subprojects as well, but it
Expand Down
2 changes: 1 addition & 1 deletion docs/dsl.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,7 @@ Some examples of this include Dagger, Moshi code gen, Robolectric, and more.
The primary entry point is the `slack` extension in the build file, which is backed by the `SlackExtension` interface.

```kotlin
slack {
foundry {
features {
dagger(...)
moshi(...)
Expand Down
2 changes: 1 addition & 1 deletion docs/formatters-and-analysis.md
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ The core set of analysis tools supported in SGP are:

SGP ships with a standard set of git hooks (pre-commit, etc) that it can bootstrap in projects by running `./gradlew installCommitHooks`. These hooks rely on checking in relevant binaries for each formatter/checker, it's strongly recommended to use git-lfs for these. These files should be edited as needed to best serve the project they're running in.

SGP can configure these hooks in the project automatically during bootstrap if you add the `slack.git.hooksPath` gradle property and point it at the hooks directory that the above command output to, or wherever the host project opts to store them.
SGP can configure these hooks in the project automatically during bootstrap if you add the `foundry.git.hooksPath` gradle property and point it at the hooks directory that the above command output to, or wherever the host project opts to store them.

Note that Detekt is not yet supported in git hooks as these require extra parameters for baselines.

Expand Down
42 changes: 19 additions & 23 deletions docs/index.md
Original file line number Diff line number Diff line change
@@ -1,22 +1,18 @@
foundry
===================

This repository contains the core Gradle plugin and associated logic used for Slack's Android app.
This repository contains much of Slack's Android/Kotlin/JVM tooling for Gradle, IntelliJ, CLIs, and more.

This repo is effectively _read-only_ and does not publish artifacts to Maven Central. We [develop
This repo is effectively for Slack's own used but publishes to Maven Central. We [develop
these in the open](https://slack.engineering/developing-in-the-open/) to knowledge-share with the community.

As such, our issue tracker is closed and we don't normally accept external PRs, but we welcome your
questions in the discussions section of the project!

We may later publish some of these components. If you're interested in this, feel free to raise in
a discussions post or vote for existing suggestions.
As such, we don't normally accept external PRs, but we welcome your questions in the discussions section of the project!

## Highlights

### Common project configuration

The `slack.base` plugin offers common configuration for all projects implementing it, covering a
The `foundry.base` plugin offers common configuration for all projects implementing it, covering a
wide spectrum of Android, Kotlin, and Java configurations.

This includes a whole host of things!
Expand All @@ -25,7 +21,7 @@ This includes a whole host of things!
- Common Kotlin configuration (freeCompilerArgs, JVM target, etc).
- Common Java configuration (toolchains, release versions, etc).
- Common annotation processors.
- SlackExtension (see next section).
- `FoundryExtension` (see next section).
- Formatting (via Spotless).
- Platforms and BOM dependencies (see "Platform plugins" section below).
- Common lint checks (both on Android and plain JVM projects).
Expand All @@ -34,12 +30,12 @@ Full docs can be found in the [architecture](architecture) docs.

### Feature DSL

To ease use and configuration of common features in projects, we expose a `slack` DSL in projects
To ease use and configuration of common features in projects, we expose a `foundry` DSL in projects
that allows for configuration of these in a semantically easy and boilerplate-free way. This is
controlled via `SlackExtension`.
controlled via `FoundryExtension`.

```kotlin
slack {
foundry {
features {
dagger()
moshi(codegen = true)
Expand Down Expand Up @@ -88,7 +84,7 @@ its advice to a project to automatically optimize it and _rake_ dependencies.
As a part of our modularization efforts, we developed a scoring mechanism for modules that we could
use as a measure of their "modularization". This includes a number of metrics and weighs them in a
formula to compute a score. This includes LoC, language mixtures, and build graph centrality. This
logic is under the `slack.stats` package.
logic is under the `foundry.stats` package.

### Robolectric Jars Management

Expand Down Expand Up @@ -166,25 +162,25 @@ There are a _ton_ of miscellaneous tools, utilities, and glue code for Gradle (a
SGP expects there to be a `libs` version catalog.

The following versions are required to be set the above catalog.
Their docs can be found in `SlackVersions.kt`.
Their docs can be found in `FoundryVersions.kt`.

For Android projects, some extra definitions need to be defined

- `libs.versions.toml` libraries
- `google-coreLibraryDesugaring` - the core library desugaring libraries to use with L8.
- `gradle.properties` properties
- `slack.compileSdkVersion`
- `slack.targetSdkVersion`
- `slack.minSdkVersion`
- `foundry.compileSdkVersion`
- `foundry.targetSdkVersion`
- `foundry.minSdkVersion`

The following plugins are applied by default but can be disabled if you don't need them.

- Gradle's test retry – `slack.auto-apply.test-retry`
- By default, this uses the [Gradle test-retry plugin](https://github.com/gradle/test-retry-gradle-plugin), but can be configured to use the Gradle Enterprise plugin's implementation instead by setting the `slack.test.retry.pluginType` property to `GE`.
- Spotless – `slack.auto-apply.spotless`
- Detekt – `slack.auto-apply.detekt`
- NullAway – `slack.auto-apply.nullaway`
- Android Cache Fix – `slack.auto-apply.cache-fix`
- Gradle's test retry – `foundry.auto-apply.test-retry`
- By default, this uses the [Gradle test-retry plugin](https://github.com/gradle/test-retry-gradle-plugin), but can be configured to use the Gradle Enterprise plugin's implementation instead by setting the `foundry.test.retry.pluginType` property to `GE`.
- Spotless – `foundry.auto-apply.spotless`
- Detekt – `foundry.auto-apply.detekt`
- NullAway – `foundry.auto-apply.nullaway`
- Android Cache Fix – `foundry.auto-apply.cache-fix`

## Commit hooks

Expand Down
2 changes: 1 addition & 1 deletion docs/utilities.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ will just show stub files instead.

To work mitigate this, we will _patch_ the SDK by putting a copy of the previous version's sources in the location of
the new SDK. This allows most sources to still index properly during the beta period. Then, once the new sources are
available, the consuming repo needs only to update the `slack.latestCompileSdkWithSources` gradle property to that new
available, the consuming repo needs only to update the `foundry.latestCompileSdkWithSources` gradle property to that new
SDK version and the patcher will clear out that copy and let AGP download the real ones.

This runs automatically in the root plugin.
Expand Down
4 changes: 2 additions & 2 deletions mkdocs.yml
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,11 @@
site_name: foundry
repo_name: foundry
repo_url: https://github.com/slackhq/foundry
site_description: "Gradle and IntelliJ build tooling used in Slack's Android repo"
site_description: "Gradle and IntelliJ build tooling used in Slack's Android projects"
site_author: Slack
remote_branch: gh-pages

copyright: 'Copyright &copy; 2023 Slack Technologies, LLC'
copyright: 'Copyright &copy; 2024 Slack Technologies, LLC'

theme:
name: 'material'
Expand Down
6 changes: 3 additions & 3 deletions platforms/gradle/foundry-gradle-plugin/build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -27,15 +27,15 @@ plugins {

gradlePlugin {
plugins.create("foundry-root") {
id = "foundry.gradle.root"
id = "foundry.root"
implementationClass = "foundry.gradle.FoundryRootPlugin"
}
plugins.create("foundry-base") {
id = "foundry.gradle.base"
id = "foundry.base"
implementationClass = "foundry.gradle.FoundryBasePlugin"
}
plugins.create("apkVersioning") {
id = "foundry.gradle.apk-versioning"
id = "foundry.apk-versioning"
implementationClass = "foundry.gradle.ApkVersioningPlugin"
}
}
Expand Down
Loading

0 comments on commit f0eb0fa

Please sign in to comment.