Skip to content

Commit

Permalink
KSP support (#1244)
Browse files Browse the repository at this point in the history
* Update to xprocessing

* ksp sample module

* Tests

* fix lint

* add back ksp impl

* optimize default method lookup

* fix test and bump to beta2
  • Loading branch information
elihart authored Nov 3, 2021
1 parent 74e5f0d commit 687c845
Show file tree
Hide file tree
Showing 330 changed files with 45,598 additions and 3,923 deletions.
13 changes: 13 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
@@ -1,3 +1,16 @@
# 5.0.0
This adds support for Kotlin Symbol Processing, while maintaining backwards compatibility with java annotation processing via the xprocessing library from Room.

This includes a major version bump to 5.0.0 because there may be slight behavior differences with KSP, especially for generic types in generated code. For example, if you previously had an epoxy attribute in java source code with a raw type it may now appear in the generated code with a wildcard type, which may require tweaking the type that is passed to the model.

Additionally, some type checking was improved, for example more accurate validation of proper equals and hashcode implementations.

To use Epoxy with KSP, simply apply it with the ksp gradle plugin instead of kapt (https://github.com/google/ksp/blob/main/docs/quickstart.md). See the new epoxy-kspsample module for an example.

Note that unfortunately the databinding processor does NOT support KSP, simply because Android databinding itself uses KAPT and KSP cannot currently depend on KAPT sources. The code changes are in place to enable KSP with databinding once the databinding plugin from Android supports KSP (although this is unlikely) - alternatively it may be possible to configure the KSP plugin to run after KAPT and depend on its outputs (you're on your own if you want to try that).

Also, parallel processing support was removed because it is not compatible with KSP.

# 4.6.4 (September 23, 2021)
- Clean up dependency for the experimental epoxy module

Expand Down
18 changes: 14 additions & 4 deletions blessedDeps.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -47,13 +47,16 @@ rootProject.ext.KOTLIN_COROUTINES_VERSION = "1.3.9"
rootProject.ext.KOTLINX_METADATA = "0.3.0"
rootProject.ext.LOTTIE_VERSION = "2.8.0"
rootProject.ext.MOCKITO_VERSION = "3.7.7"
rootProject.ext.PARIS_VERSION = "1.7.3"
rootProject.ext.PARIS_VERSION = "2.0.1"
rootProject.ext.ROBOLECTRIC_VERSION = "4.5.1"
rootProject.ext.SQUARE_JAVAPOET_VERSION = "1.13.0"
rootProject.ext.SQUARE_KOTLINPOET_VERSION = "1.8.0"
rootProject.ext.COMPOSE_VERSION = "1.0.0-beta07"
rootProject.ext.COMPOSE_ACTIVITY_VERSION = "1.3.0-alpha07"
rootProject.ext.SQUARE_KOTLINPOET_VERSION = "1.10.2"
rootProject.ext.COMPOSE_VERSION = "1.0.4"
rootProject.ext.COMPOSE_ACTIVITY_VERSION = "1.3.1"
rootProject.ext.KOTLINX_LIFECYCLE_RUNTIME_VERSION = "2.3.0"
rootProject.ext.KSP_VERSION = "1.5.31-1.0.0"
rootProject.ext.XPROCESSING_VERSION = "2.4.0-beta01"
rootProject.ext.KOTLIN_TESTING_COMPILE_VERSION = '1.4.5'

rootProject.ext.deps = [
activityCompose : "androidx.activity:activity-compose:$COMPOSE_ACTIVITY_VERSION",
Expand Down Expand Up @@ -97,5 +100,12 @@ rootProject.ext.deps = [
robolectric : "org.robolectric:robolectric:$ROBOLECTRIC_VERSION",
squareJavaPoet : "com.squareup:javapoet:$SQUARE_JAVAPOET_VERSION",
squareKotlinPoet : "com.squareup:kotlinpoet:$SQUARE_KOTLINPOET_VERSION",
kotlinPoetJavaInterop : "com.squareup:kotlinpoet-javapoet:$SQUARE_KOTLINPOET_VERSION",
kotlinPoetKspInterop : "com.squareup:kotlinpoet-ksp:$SQUARE_KOTLINPOET_VERSION",
versionedParcelable : "androidx.versionedparcelable:versionedparcelable:$ANDROIDX_VERSIONED_PARCELABLE",
ksp : "com.google.devtools.ksp:symbol-processing-api:$KSP_VERSION",
kspImpl : "com.google.devtools.ksp:symbol-processing:$KSP_VERSION",
xProcessing : "androidx.room:room-compiler-processing:$XPROCESSING_VERSION",
xProcessingTesting : "androidx.room:room-compiler-processing-testing:$XPROCESSING_VERSION",
kotlinCompileTesting : "com.github.tschuchortdev:kotlin-compile-testing-ksp:$KOTLIN_TESTING_COMPILE_VERSION",
]
7 changes: 5 additions & 2 deletions build.gradle
Original file line number Diff line number Diff line change
@@ -1,12 +1,14 @@
// Top-level build file where you can add configuration options common to all sub-projects/modules.
buildscript {

ext.KOTLIN_VERSION = "1.4.32"
ext.ANDROID_PLUGIN_VERSION = '7.0.0'
ext.KOTLIN_VERSION = "1.5.31"
ext.ANDROID_PLUGIN_VERSION = '7.0.3'
ext.KSP_VERSION = '1.5.31-1.0.0'

repositories {
google()
mavenCentral()
gradlePluginPortal()
jcenter()
}
dependencies {
Expand All @@ -22,6 +24,7 @@ buildscript {

plugins {
id 'com.github.ben-manes.versions' version '0.38.0'
id "com.google.devtools.ksp" version "$KSP_VERSION"
}

allprojects {
Expand Down
1 change: 1 addition & 0 deletions epoxy-adapter/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ dependencies {
api project(':epoxy-annotations')

kapt project(':epoxy-processor')
kaptTest project(':epoxy-processor')

testImplementation rootProject.deps.junit
testImplementation rootProject.deps.robolectric
Expand Down
4 changes: 3 additions & 1 deletion epoxy-compose/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -27,11 +27,13 @@ android {
}
kotlinOptions {
jvmTarget = '1.8'
useIR = true
}
buildFeatures {
compose true
}
composeOptions {
kotlinCompilerExtensionVersion COMPOSE_VERSION
}
}

dependencies {
Expand Down
3 changes: 1 addition & 2 deletions epoxy-compose/gradle.properties
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
POM_NAME=Epoxy Compose Interop
POM_ARTIFACT_ID=epoxy-compose
POM_PACKAGING=jar
VERSION_NAME=4.6.4-alpha01
POM_PACKAGING=jar
1 change: 0 additions & 1 deletion epoxy-composeinterop-maverickssample/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,6 @@ android {
}
kotlinOptions {
jvmTarget = '1.8'
useIR = true
}
buildFeatures {
dataBinding true
Expand Down
1 change: 0 additions & 1 deletion epoxy-composesample/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,6 @@ android {
}
kotlinOptions {
jvmTarget = '1.8'
useIR = true
}
buildFeatures {
compose true
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,14 +8,15 @@ import androidx.appcompat.app.AppCompatActivity
class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)

setContentView(R.layout.activity_main)
}

fun onComposableInteropClicked(view: View) {
startActivity(Intent(this, ComposableInteropActivity::class.java))
}
findViewById<View>(R.id.button).setOnClickListener {
startActivity(Intent(this, ComposableInteropActivity::class.java))
}

fun onEpoxyInteropClicked(view: View) {
startActivity(Intent(this, EpoxyInteropActivity::class.java))
findViewById<View>(R.id.button2).setOnClickListener {
startActivity(Intent(this, EpoxyInteropActivity::class.java))
}
}
}
2 changes: 0 additions & 2 deletions epoxy-composesample/src/main/res/layout/activity_main.xml
Original file line number Diff line number Diff line change
Expand Up @@ -13,15 +13,13 @@
app:layout_constraintBottom_toTopOf="@+id/button2"
app:layout_constraintEnd_toEndOf="parent"
app:layout_constraintStart_toStartOf="parent"
android:onClick="onComposableInteropClicked"
app:layout_constraintTop_toTopOf="parent" />

<Button
android:id="@+id/button2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="Epoxy interop"
android:onClick="onEpoxyInteropClicked"
app:layout_constraintBottom_toBottomOf="parent"
app:layout_constraintEnd_toEndOf="@+id/button"
app:layout_constraintStart_toStartOf="@+id/button"
Expand Down
1 change: 1 addition & 0 deletions epoxy-kspsample/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
/build
59 changes: 59 additions & 0 deletions epoxy-kspsample/build.gradle
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
plugins {
id 'com.android.application'
id 'kotlin-android'
}
//apply plugin: 'com.google.devtools.ksp'
apply plugin: 'kotlin-kapt'

android {
compileSdkVersion rootProject.COMPILE_SDK_VERSION

defaultConfig {
applicationId "com.airbnb.epoxy.compose.sample"
minSdkVersion rootProject.COMPOSE_MIN_SDK_VERSION
targetSdkVersion rootProject.TARGET_SDK_VERSION
versionCode 1
versionName "1.0"
}

buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
}
}
compileOptions {
sourceCompatibility JavaVersion.VERSION_1_8
targetCompatibility JavaVersion.VERSION_1_8
}
kotlinOptions {
jvmTarget = '1.8'
}
}

project.android.buildTypes.all { buildType ->
buildType.javaCompileOptions.annotationProcessorOptions.arguments =
[
validateEpoxyModelUsage: "true",
logEpoxyTimings : "true",
]
}

//ksp {
// arg("logEpoxyTimings", "true")
// arg("validateEpoxyModelUsage", "true")
//}

dependencies {
implementation project(':epoxy-adapter')
implementation project(':epoxy-annotations')
// ksp project(':epoxy-processor')

This comment has been minimized.

Copy link
@chrisjenx

chrisjenx Nov 11, 2021

Not sure if this is intentional, but if you have been testing using this project, you realize ksp isnt processing right?

// ksp rootProject.deps.parisProcessor
kapt project(':epoxy-processor')
kapt rootProject.deps.parisProcessor

implementation rootProject.deps.androidAppcompat
implementation rootProject.deps.androidDesignLibrary
implementation rootProject.deps.paris
implementation rootProject.deps.androidCoreKtx
}
19 changes: 19 additions & 0 deletions epoxy-kspsample/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
<?xml version="1.0" encoding="utf-8"?>
<manifest package="com.airbnb.epoxy.ksp.sample"
xmlns:android="http://schemas.android.com/apk/res/android">

<application android:label="@string/app_name">
<activity
android:name="com.airbnb.epoxy.ksp.sample.MainActivity"
android:exported="true"
android:label="@string/app_name"
android:theme="@style/Theme.AppCompat.Light.NoActionBar">
<intent-filter>
<action android:name="android.intent.action.MAIN" />

<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
</application>

</manifest>
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
package com.airbnb.epoxy.ksp.sample

import android.os.Bundle
import androidx.appcompat.app.AppCompatActivity
import com.airbnb.epoxy.EpoxyRecyclerView
import com.airbnb.epoxy.ksp.sample.epoxyviews.headerView

class MainActivity : AppCompatActivity() {
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)

findViewById<EpoxyRecyclerView>(R.id.epoxy_recycler_view).withModels {
headerView {
id("header")
title("Hello World")
}
}
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
package com.airbnb.epoxy.ksp.sample.epoxyviews

import com.airbnb.epoxy.ksp.sample.R
import com.airbnb.paris.annotations.ParisConfig

@ParisConfig(rClass = R::class)
object EpoxyConfig
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
package com.airbnb.epoxy.ksp.sample.epoxyviews

import android.content.Context
import android.view.View
import android.view.ViewGroup
import android.widget.ImageView
import android.widget.LinearLayout
import android.widget.TextView
import com.airbnb.epoxy.ModelProp
import com.airbnb.epoxy.ModelView
import com.airbnb.epoxy.TextProp
import com.airbnb.epoxy.ksp.sample.R
import com.airbnb.paris.annotations.Style
import com.airbnb.paris.annotations.Styleable
import com.airbnb.paris.extensions.headerViewStyle
import com.airbnb.paris.extensions.layoutHeight
import com.airbnb.paris.extensions.layoutWidth

@Styleable // Dynamic styling via the Paris library
@ModelView
class HeaderView(context: Context?) : LinearLayout(context) {
private var title: TextView? = null
private var caption: TextView? = null
private var image: ImageView? = null

init {
orientation = VERTICAL
inflate(getContext(), R.layout.header_view, this)

title = findViewById(R.id.title_text)
caption = findViewById(R.id.caption_text)
image = findViewById(R.id.image)
}

@TextProp(defaultRes = R.string.app_name)
fun setTitle(title: CharSequence?) {
this.title?.text = title
}

@TextProp
fun setCaption(caption: CharSequence?) {
this.caption?.text = caption
}

@JvmOverloads
@ModelProp
fun setShowImage(isVisible: Boolean = false) {
image?.visibility = if (isVisible) View.VISIBLE else View.GONE
}

companion object {
@Style(isDefault = true)
val headerStyle: com.airbnb.paris.styles.Style = headerViewStyle {
layoutWidth(ViewGroup.LayoutParams.MATCH_PARENT)
layoutHeight(ViewGroup.LayoutParams.MATCH_PARENT)
}
}
}
7 changes: 7 additions & 0 deletions epoxy-kspsample/src/main/res/layout/activity_main.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
<?xml version="1.0" encoding="utf-8"?>
<com.airbnb.epoxy.EpoxyRecyclerView xmlns:android="http://schemas.android.com/apk/res/android"
android:id="@+id/epoxy_recycler_view"
android:layout_width="match_parent"
android:layout_height="match_parent">
</com.airbnb.epoxy.EpoxyRecyclerView>

37 changes: 37 additions & 0 deletions epoxy-kspsample/src/main/res/layout/header_view.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical">

<ImageView
android:layout_gravity="center"
android:id="@+id/image"
android:layout_width="200dp"
android:layout_height="200dp"
android:visibility="gone" />

<TextView
android:id="@+id/title_text"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="center"
android:gravity="center"
android:lineSpacingMultiplier="0.8"
android:paddingTop="8dp"
android:textColor="#000000"
android:textSize="16sp" />

<TextView
android:id="@+id/caption_text"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_marginTop="8dp"
android:gravity="center"
android:textColor="#000000"
android:textSize="20sp"
tools:text="caption" />


</LinearLayout>
3 changes: 3 additions & 0 deletions epoxy-kspsample/src/main/res/values/strings.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
<resources>
<string name="app_name">Epoxy KSP Sample</string>
</resources>
4 changes: 4 additions & 0 deletions epoxy-modelfactorytest/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -49,9 +49,13 @@ dependencies {

// Need to include the processors directly since we create an instance of it in code for testing
testImplementation project(':epoxy-processor')
testImplementation rootProject.deps.ksp
testImplementation rootProject.deps.parisProcessor

testImplementation project(':epoxy-processortest')
testImplementation "io.github.java-diff-utils:java-diff-utils:4.5"
testImplementation rootProject.deps.kotlinCompileTesting
testImplementation "io.strikt:strikt-core:0.31.0"
testImplementation rootProject.deps.googleTestingCompile
testImplementation rootProject.deps.junit
testImplementation rootProject.deps.robolectric
Expand Down
Loading

0 comments on commit 687c845

Please sign in to comment.