diff --git a/.idea/compiler.xml b/.idea/compiler.xml
index aaa7ffdad..7b2ca4a83 100644
--- a/.idea/compiler.xml
+++ b/.idea/compiler.xml
@@ -116,6 +116,7 @@
+
@@ -272,6 +273,7 @@
+
diff --git a/.idea/kotlinc.xml b/.idea/kotlinc.xml
index 8d81632f8..148fdd246 100644
--- a/.idea/kotlinc.xml
+++ b/.idea/kotlinc.xml
@@ -1,6 +1,6 @@
-
+
\ No newline at end of file
diff --git a/build.gradle.kts b/build.gradle.kts
index e8d4749f4..d7aca97f3 100755
--- a/build.gradle.kts
+++ b/build.gradle.kts
@@ -42,7 +42,6 @@ buildscript {
dependencies {
classpath(libs.kotlin.gradle.plugin)
classpath(libs.nav.safe.args.gradle.plugin)
- classpath(libs.realm.gradle.plugin)
}
}
diff --git a/core/app/build.gradle.kts b/core/app/build.gradle.kts
index 9f3fc46b5..7028cdac9 100755
--- a/core/app/build.gradle.kts
+++ b/core/app/build.gradle.kts
@@ -28,7 +28,6 @@ plugins {
id("kotlin-android")
id("kotlin-kapt")
id("kotlin-parcelize")
- id("realm-android")
id("androidx.navigation.safeargs.kotlin")
id("com.itsaky.androidide.desugaring")
}
diff --git a/core/app/src/main/java/com/itsaky/androidide/app/IDEApplication.kt b/core/app/src/main/java/com/itsaky/androidide/app/IDEApplication.kt
index 57f32048e..46789db4f 100755
--- a/core/app/src/main/java/com/itsaky/androidide/app/IDEApplication.kt
+++ b/core/app/src/main/java/com/itsaky/androidide/app/IDEApplication.kt
@@ -58,7 +58,6 @@ import com.itsaky.androidide.utils.flashError
import com.termux.app.TermuxApplication
import com.termux.shared.reflection.ReflectionUtils
import io.github.rosemoe.sora.widget.schemes.EditorColorScheme
-import io.realm.Realm
import kotlinx.coroutines.DelicateCoroutinesApi
import kotlinx.coroutines.GlobalScope
import kotlinx.coroutines.launch
@@ -110,8 +109,6 @@ class IDEApplication : TermuxApplication() {
EventBus.getDefault().register(this)
- Realm.init(this)
-
AppCompatDelegate.setDefaultNightMode(GeneralPreferences.uiMode)
if (IThemeManager.getInstance().getCurrentTheme() == IDETheme.MATERIAL_YOU) {
diff --git a/core/database/.gitignore b/core/database/.gitignore
deleted file mode 100644
index 42afabfd2..000000000
--- a/core/database/.gitignore
+++ /dev/null
@@ -1 +0,0 @@
-/build
\ No newline at end of file
diff --git a/core/database/build.gradle.kts b/core/database/build.gradle.kts
deleted file mode 100644
index 969171f1f..000000000
--- a/core/database/build.gradle.kts
+++ /dev/null
@@ -1,41 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-
-import com.itsaky.androidide.build.config.BuildConfig
-
-plugins {
- id("com.android.library")
- id("kotlin-android")
- id("kotlin-kapt")
- id("realm-android")
-}
-
-
-
-android {
- namespace = "${BuildConfig.packageName}.database"
-}
-
-dependencies {
- kapt(libs.google.auto.service)
- implementation(libs.google.auto.service.annotations)
-
- implementation(projects.core.common)
- implementation(projects.logging.logger)
- implementation(projects.utilities.shared)
-}
\ No newline at end of file
diff --git a/core/database/consumer-rules.pro b/core/database/consumer-rules.pro
deleted file mode 100644
index e69de29bb..000000000
diff --git a/core/database/proguard-rules.pro b/core/database/proguard-rules.pro
deleted file mode 100644
index 481bb4348..000000000
--- a/core/database/proguard-rules.pro
+++ /dev/null
@@ -1,21 +0,0 @@
-# Add project specific ProGuard rules here.
-# You can control the set of applied configuration files using the
-# proguardFiles setting in build.gradle.
-#
-# For more details, see
-# http://developer.android.com/guide/developing/tools/proguard.html
-
-# If your project uses WebView with JS, uncomment the following
-# and specify the fully qualified class name to the JavaScript interface
-# class:
-#-keepclassmembers class fqcn.of.javascript.interface.for.webview {
-# public *;
-#}
-
-# Uncomment this to preserve the line number information for
-# debugging stack traces.
-#-keepattributes SourceFile,LineNumberTable
-
-# If you keep the line number information, uncomment this to
-# hide the original source file name.
-#-renamesourcefileattribute SourceFile
\ No newline at end of file
diff --git a/core/database/src/main/java/com/itsaky/androidide/db/IRealmProvider.kt b/core/database/src/main/java/com/itsaky/androidide/db/IRealmProvider.kt
deleted file mode 100644
index 2bf6ec341..000000000
--- a/core/database/src/main/java/com/itsaky/androidide/db/IRealmProvider.kt
+++ /dev/null
@@ -1,91 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.db
-
-import com.itsaky.androidide.utils.ServiceLoader
-import io.realm.Realm
-import io.realm.RealmConfiguration
-
-/**
- * An [IRealmProvider] provides the instance of [Realm].
- *
- * @author Akash Yadav
- */
-interface IRealmProvider {
-
- /**
- * Get the [Realm] instance.
- *
- * @param path The path of the database.
- */
- fun get(path: String): Realm {
- return get(path, null)
- }
-
- /**
- * Get the [Realm] instance.
- *
- * @param path The path of the database.
- * @param config An optional function to configure the [RealmConfiguration] builder.
- */
- fun get(path: String, config: (RealmConfiguration.Builder.() -> Unit)?): Realm
-
- companion object {
-
- private lateinit var sInstance: IRealmProvider
-
- /**
- * The separator used to separate segments in an index path.
- */
- const val PATH_SEPARATOR = '/'
-
- /**
- * Create the path for the given segments.
- *
- * @param first The first (root) path segment.
- * @param rest The rest of the path segments.
- * @return The created path string.
- */
- @JvmStatic
- fun createPath(first: String, vararg rest: String): String {
-
- val sb = StringBuilder()
- sb.append(PATH_SEPARATOR)
- sb.append(first)
-
- for (segment in rest) {
- sb.append(PATH_SEPARATOR)
- sb.append(segment)
- }
-
- return sb.toString()
- }
-
- /**
- * Get the [IRealmProvider] instance, finding the implementation if necessary.
- */
- @JvmStatic
- fun instance(): IRealmProvider {
- if (!Companion::sInstance.isInitialized) {
- val clazz = IRealmProvider::class.java
- sInstance = ServiceLoader.load(clazz, clazz.classLoader).findFirstOrThrow()
- }
- return sInstance
- }
- }
-}
\ No newline at end of file
diff --git a/core/database/src/main/java/com/itsaky/androidide/db/internal/DatabaseEntity.kt b/core/database/src/main/java/com/itsaky/androidide/db/internal/DatabaseEntity.kt
deleted file mode 100644
index 0974859f5..000000000
--- a/core/database/src/main/java/com/itsaky/androidide/db/internal/DatabaseEntity.kt
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.db.internal
-
-import io.realm.RealmObject
-import io.realm.annotations.PrimaryKey
-import io.realm.annotations.RealmField
-import io.realm.annotations.Required
-
-/**
- * An entity to store information about all registered box stores.
- *
- * @author Akash Yadav
- */
-open class DatabaseEntity(
- @Required
- @PrimaryKey
- @RealmField("path")
- var path: String = "",
-
- @Required
- @RealmField("name")
- var name: String = "",
-
- @Required
- @RealmField("directory")
- var directory: String = "",
-) : RealmObject() {
-
- override fun equals(other: Any?): Boolean {
- if (this === other) return true
- if (other !is DatabaseEntity) return false
-
- if (path != other.path) return false
- if (name != other.name) return false
- if (directory != other.directory) return false
-
- return true
- }
-
- override fun hashCode(): Int {
- var result = path.hashCode()
- result = 31 * result + name.hashCode()
- result = 31 * result + directory.hashCode()
- return result
- }
-
- override fun toString(): String {
- return "DatabaseEntity(path='$path', name='$name', directory='$directory')"
- }
-}
\ No newline at end of file
diff --git a/core/database/src/main/java/com/itsaky/androidide/db/internal/InternalDBRealmModule.kt b/core/database/src/main/java/com/itsaky/androidide/db/internal/InternalDBRealmModule.kt
deleted file mode 100644
index 4c5a9a7dd..000000000
--- a/core/database/src/main/java/com/itsaky/androidide/db/internal/InternalDBRealmModule.kt
+++ /dev/null
@@ -1,28 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.db.internal
-
-import io.realm.annotations.RealmModule
-
-/**
- * [RealmModule] for the internal database entitites.
- *
- * @author Akash Yadav
- */
-@RealmModule(library = true, classes = [DatabaseEntity::class])
-internal class InternalDBRealmModule
\ No newline at end of file
diff --git a/core/database/src/main/java/com/itsaky/androidide/db/internal/RealmProviderImpl.kt b/core/database/src/main/java/com/itsaky/androidide/db/internal/RealmProviderImpl.kt
deleted file mode 100644
index b7bb28974..000000000
--- a/core/database/src/main/java/com/itsaky/androidide/db/internal/RealmProviderImpl.kt
+++ /dev/null
@@ -1,115 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.db.internal
-
-import com.google.auto.service.AutoService
-import com.itsaky.androidide.db.IRealmProvider
-import com.itsaky.androidide.utils.Environment
-import io.realm.Realm
-import io.realm.RealmConfiguration
-import org.slf4j.LoggerFactory
-
-/**
- * Default implementation of [IRealmProvider].
- *
- * @author Akash Yadav
- */
-@AutoService(IRealmProvider::class)
-@Suppress("unused")
-internal class RealmProviderImpl : IRealmProvider {
-
- companion object {
- private val log = LoggerFactory.getLogger(RealmProviderImpl::class.java)
-
- // must be a relative path, with no special characters except '_' '-' and '/' (path sep)
- private val dbNameRegex = Regex("^[a-zA-Z0-9_\\-/]+$")
- private const val MASTER_DB_NAME = "master"
- private const val MASTER_DB_PATH = "/$MASTER_DB_NAME"
- }
-
- private val masterDb: Realm by lazy {
- createDb(MASTER_DB_PATH) {
- modules(InternalDBRealmModule())
- }
- }
-
- override fun get(path: String, config: (RealmConfiguration.Builder.() -> Unit)?): Realm {
- require(path != MASTER_DB_PATH) {
- "Master DB is internal to AndroidIDE"
- }
-
- return createDb(path, config)
- }
-
- private fun createDb(path: String, confFunc: (RealmConfiguration.Builder.() -> Unit)?): Realm {
- val (parentPath, name) = validateDbPath(path)
-
- val configBuilder = RealmConfiguration.Builder()
- confFunc?.also { configure -> configBuilder.configure() }
-
- var dbDir = Environment.REALM_DB_DIR
- if (parentPath.isNotEmpty()) {
- dbDir = dbDir.resolve(parentPath)
- }
-
- val dbName = "${name}.realm"
- val config = configBuilder
- .name(dbName)
- .directory(dbDir)
- .allowQueriesOnUiThread(false)
- .allowWritesOnUiThread(false)
- .compactOnLaunch()
- .build()
-
- log.info("Creating DB at $dbDir/$dbName")
-
- if (parentPath.isEmpty() && name != MASTER_DB_NAME) {
- masterDb.executeTransactionAsync { realm ->
- realm.insertOrUpdate(DatabaseEntity(name = name, path = path, directory = dbDir.absolutePath))
- }
- }
-
- return Realm.getInstance(config)
- }
-
- private fun validateDbPath(path: String): Pair {
- val idx = path.indexOfLast { it == IRealmProvider.PATH_SEPARATOR }
- require(
- path.matches(dbNameRegex)
- && path[0] == IRealmProvider.PATH_SEPARATOR
- && idx >= 0
- && path.indexOf("//") == -1
- ) {
- "Invalid DB path: $path"
- }
-
- val parentPath = if (idx > 1) {
- path.substring(1, idx)
- } else ""
-
- val name = path.substring(idx + 1)
-
- if (name == MASTER_DB_NAME) {
- require(parentPath.isEmpty()) {
- "Master DB must not have any parent path"
- }
- }
-
- return parentPath to name
- }
-}
\ No newline at end of file
diff --git a/core/database/src/main/java/com/itsaky/androidide/db/utils/realmDictionaryExts.kt b/core/database/src/main/java/com/itsaky/androidide/db/utils/realmDictionaryExts.kt
deleted file mode 100644
index 4408fc98d..000000000
--- a/core/database/src/main/java/com/itsaky/androidide/db/utils/realmDictionaryExts.kt
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.db.utils
-
-import io.realm.RealmDictionary
-
-/**
- * Check if two RealmDictionaries are equal.
- */
-fun RealmDictionary?.isEqualTo(other: Any?): Boolean {
- // implementation taken from java/util/AbstractMap from JDK 21
- if (other == this) return true
- if (other == null || this == null) return false
- if (other !is RealmDictionary<*>) return false
- if (this.size != other.size) return false
-
- try {
- for (entry in this.entries) {
- val key = entry.key
- val value = entry.value
- if (value == null) {
- if (!(other[key] == null && other.containsKey(key))) {
- return false
- }
- } else {
- if (value != other[key]) {
- return false
- }
- }
- }
- } catch (e: ClassCastException) {
- return false
- } catch (e: NullPointerException) {
- return false
- }
-
- return true
-}
-
-/**
- * Generate the hash code for a RealmDictionary.
- */
-fun RealmDictionary.hash(): Int {
- return this.entries.sumOf { it.hashCode() }
-}
\ No newline at end of file
diff --git a/core/indexing-api/build.gradle.kts b/core/indexing-api/build.gradle.kts
index c9bad0810..6af9850cf 100644
--- a/core/indexing-api/build.gradle.kts
+++ b/core/indexing-api/build.gradle.kts
@@ -22,11 +22,8 @@ plugins {
id("com.android.library")
id("kotlin-android")
id("kotlin-kapt")
- id("realm-android")
}
-
-
android {
namespace = "${BuildConfig.packageName}.indexing.api"
}
@@ -36,7 +33,6 @@ dependencies {
implementation(libs.google.auto.service.annotations)
api(projects.core.common)
- api(projects.core.database)
api(projects.core.projects)
api(projects.logging.logger)
api(projects.utilities.shared)
diff --git a/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/AbstractDBIndex.kt b/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/AbstractDBIndex.kt
deleted file mode 100644
index cb13321fb..000000000
--- a/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/AbstractDBIndex.kt
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.indexing
-
-import io.realm.Realm
-
-/**
- * Abstract implementation of [IIndex] for indexing data in the database.
- *
- * @property params The index parameters.
- * @author Akash Yadav
- */
-abstract class AbstractDBIndex(
- protected val params: IIndexParams?
-) : IDatabaseIndex {
-
- protected abstract val realm: Realm
-
- override fun index(symbol: T) {
- realm.executeTransaction {
- it.insertOrUpdate(symbol)
- }
- }
-
- override fun indexAsync(symbol: T) {
- realm.executeTransactionAsync {
- it.insertOrUpdate(symbol)
- }
- }
-
- override fun indexAll(symbols: Collection) {
- realm.executeTransaction {
- it.insertOrUpdate(symbols)
- }
- }
-
- override fun indexAllAsync(symbols: Collection) {
- realm.executeTransactionAsync { it.insertOrUpdate(symbols) }
- }
-
- override fun delete() {
- realm.deleteAll()
- }
-}
\ No newline at end of file
diff --git a/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/IDatabaseIndex.kt b/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/IDatabaseIndex.kt
deleted file mode 100644
index 76dc71bac..000000000
--- a/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/IDatabaseIndex.kt
+++ /dev/null
@@ -1,33 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.indexing
-
-import io.realm.RealmQuery
-
-/**
- * An index which is stored in the database.
- *
- * @author Akash Yadav
- */
-interface IDatabaseIndex : IIndex {
-
- /**
- * Perform a query on the Realm database.
- */
- fun query(): RealmQuery
-}
\ No newline at end of file
diff --git a/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/IIndex.kt b/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/IIndex.kt
index e8d92968d..7d96be5d4 100644
--- a/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/IIndex.kt
+++ b/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/IIndex.kt
@@ -17,8 +17,6 @@
package com.itsaky.androidide.indexing
-import com.itsaky.androidide.db.IRealmProvider
-
/**
* An index of symbols of type [IndexableT].
*
@@ -28,6 +26,8 @@ interface IIndex {
companion object {
+ const val PATH_SEPARATOR = '/'
+
/**
* The default batch size for indexing.
*/
@@ -44,7 +44,7 @@ interface IIndex {
* Create an index path.
*/
fun createIndexPath(parentPath: String, name: String): String =
- "${parentPath}${IRealmProvider.PATH_SEPARATOR}${name}"
+ "${parentPath}${PATH_SEPARATOR}${name}"
}
/**
diff --git a/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/IIndexable.kt b/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/IIndexable.kt
index 667667471..c037b92ea 100644
--- a/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/IIndexable.kt
+++ b/core/indexing-api/src/main/java/com/itsaky/androidide/indexing/IIndexable.kt
@@ -17,11 +17,9 @@
package com.itsaky.androidide.indexing
-import io.realm.RealmModel
-
/**
* An indexable object.
*
* @author Akash Yadav
*/
-interface IIndexable : RealmModel
\ No newline at end of file
+interface IIndexable
\ No newline at end of file
diff --git a/core/indexing-core/build.gradle.kts b/core/indexing-core/build.gradle.kts
index d063b16b5..b29249e8d 100644
--- a/core/indexing-core/build.gradle.kts
+++ b/core/indexing-core/build.gradle.kts
@@ -22,11 +22,8 @@ plugins {
id("com.android.library")
id("kotlin-android")
id("kotlin-kapt")
- id("realm-android")
}
-
-
android {
namespace = "${BuildConfig.packageName}.indexing.core"
}
diff --git a/core/indexing-core/src/main/java/com/itsaky/androidide/indexing/core/IndexingCoreRealmModule.kt b/core/indexing-core/src/main/java/com/itsaky/androidide/indexing/core/IndexingCoreRealmModule.kt
deleted file mode 100644
index 08f2f1b13..000000000
--- a/core/indexing-core/src/main/java/com/itsaky/androidide/indexing/core/IndexingCoreRealmModule.kt
+++ /dev/null
@@ -1,26 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.indexing.core
-
-import io.realm.annotations.RealmModule
-
-/**
- * @author Akash Yadav
- */
-@RealmModule(classes = [])
-class IndexingCoreRealmModule
\ No newline at end of file
diff --git a/editor/impl/src/main/java/com/itsaky/androidide/editor/adapters/CompletionListAdapter.kt b/editor/impl/src/main/java/com/itsaky/androidide/editor/adapters/CompletionListAdapter.kt
index 282b6940a..f5860688d 100755
--- a/editor/impl/src/main/java/com/itsaky/androidide/editor/adapters/CompletionListAdapter.kt
+++ b/editor/impl/src/main/java/com/itsaky/androidide/editor/adapters/CompletionListAdapter.kt
@@ -27,7 +27,7 @@ import android.widget.TextView
import com.itsaky.androidide.editor.R
import com.itsaky.androidide.editor.databinding.LayoutCompletionItemBinding
import com.itsaky.androidide.lookup.Lookup
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaType
+import com.itsaky.androidide.lsp.java.utils.JavaType
import com.itsaky.androidide.lsp.models.ClassCompletionData
import com.itsaky.androidide.lsp.models.CompletionItemKind.CLASS
import com.itsaky.androidide.lsp.models.CompletionItemKind.CONSTRUCTOR
diff --git a/gradle/libs.versions.toml b/gradle/libs.versions.toml
index e7b3d424a..11a73e790 100644
--- a/gradle/libs.versions.toml
+++ b/gradle/libs.versions.toml
@@ -161,8 +161,6 @@ tooling-builderModel = { module = "com.android.tools.build:builder-model", versi
tooling-gradleApi = { module = "com.itsaky.androidide.gradle:gradle-tooling-api", version.ref = "gradle-tooling" }
tooling-slf4j = { module = "org.slf4j:slf4j-api", version = "2.0.12" }
-realm-gradle-plugin = { module = "io.realm:realm-gradle-plugin", version.ref = "realm" }
-
# Classpaths
android-gradle-plugin = { module = "com.android.tools.build:gradle", version.ref = "agp" }
kotlin-gradle-plugin = { module = "org.jetbrains.kotlin:kotlin-gradle-plugin", version.ref = "kotlin" }
diff --git a/java/lsp/build.gradle.kts b/java/lsp/build.gradle.kts
index e17747a5b..0a25dc30a 100644
--- a/java/lsp/build.gradle.kts
+++ b/java/lsp/build.gradle.kts
@@ -22,11 +22,8 @@ plugins {
id("com.android.library")
id("kotlin-android")
id("kotlin-kapt")
- id("realm-android")
}
-
-
android {
namespace = "${BuildConfig.packageName}.lsp.java"
diff --git a/java/lsp/src/androidTest/java/com/itsaky/androidide/lsp/java/indexing/JavaClassCRUDTest.kt b/java/lsp/src/androidTest/java/com/itsaky/androidide/lsp/java/indexing/JavaClassCRUDTest.kt
index 458ee380b..5760cb225 100644
--- a/java/lsp/src/androidTest/java/com/itsaky/androidide/lsp/java/indexing/JavaClassCRUDTest.kt
+++ b/java/lsp/src/androidTest/java/com/itsaky/androidide/lsp/java/indexing/JavaClassCRUDTest.kt
@@ -20,7 +20,7 @@ package com.itsaky.androidide.lsp.java.indexing
import androidx.test.ext.junit.runners.AndroidJUnit4
import com.google.common.truth.Truth.assertThat
import com.itsaky.androidide.lsp.java.indexing.classfile.JavaClass
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaType
+import com.itsaky.androidide.lsp.java.utils.JavaType
import com.itsaky.androidide.testing.android.rules.RealmDBTestRule
import io.realm.RealmList
import io.realm.RealmObject
diff --git a/java/lsp/src/androidTest/java/com/itsaky/androidide/lsp/java/indexing/ModelBuilderTestUtil.kt b/java/lsp/src/androidTest/java/com/itsaky/androidide/lsp/java/indexing/ModelBuilderTestUtil.kt
index 1493097ba..0977c25ea 100644
--- a/java/lsp/src/androidTest/java/com/itsaky/androidide/lsp/java/indexing/ModelBuilderTestUtil.kt
+++ b/java/lsp/src/androidTest/java/com/itsaky/androidide/lsp/java/indexing/ModelBuilderTestUtil.kt
@@ -20,7 +20,7 @@ package com.itsaky.androidide.lsp.java.indexing
import com.itsaky.androidide.lsp.java.indexing.classfile.JavaClass
import com.itsaky.androidide.lsp.java.indexing.classfile.JavaField
import com.itsaky.androidide.lsp.java.indexing.classfile.JavaMethod
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaType
+import com.itsaky.androidide.lsp.java.utils.JavaType
import io.realm.RealmList
import openjdk.tools.classfile.AccessFlags
diff --git a/java/lsp/src/androidTest/java/com/itsaky/androidide/lsp/java/indexing/SharedModelCRUDTest.kt b/java/lsp/src/androidTest/java/com/itsaky/androidide/lsp/java/indexing/SharedModelCRUDTest.kt
index 30d8c59e8..889c4601d 100644
--- a/java/lsp/src/androidTest/java/com/itsaky/androidide/lsp/java/indexing/SharedModelCRUDTest.kt
+++ b/java/lsp/src/androidTest/java/com/itsaky/androidide/lsp/java/indexing/SharedModelCRUDTest.kt
@@ -25,7 +25,7 @@ import com.itsaky.androidide.lsp.java.indexing.classfile.ClassAnnotationElementV
import com.itsaky.androidide.lsp.java.indexing.classfile.EnumAnnotationElementValue
import com.itsaky.androidide.lsp.java.indexing.classfile.IAnnotationElementValue
import com.itsaky.androidide.lsp.java.indexing.classfile.JavaConstant
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaType
+import com.itsaky.androidide.lsp.java.utils.JavaType
import com.itsaky.androidide.lsp.java.indexing.classfile.PrimitiveAnnotationElementValue
import com.itsaky.androidide.testing.android.rules.RealmDBTestRule
import io.realm.RealmAny
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/IJavaIndexable.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/IJavaIndexable.kt
deleted file mode 100644
index 30b0dbef5..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/IJavaIndexable.kt
+++ /dev/null
@@ -1,25 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing
-
-import com.itsaky.androidide.indexing.IIndexable
-
-/**
- * @author Akash Yadav
- */
-interface IJavaIndexable : IIndexable
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/IJavaSymbol.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/IJavaSymbol.kt
deleted file mode 100644
index 07ebb9f2e..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/IJavaSymbol.kt
+++ /dev/null
@@ -1,29 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing
-
-/**
- * A java symbol.
- *
- * @property accessFlags Access flags of the symbol.
- * @property apiInfo Info about the APIs in which this symbol was added, deprecated or removed in.
- * @author Akash Yadav
- */
-interface IJavaSymbol : IJavaIndexable {
- var accessFlags: Int
-}
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/IJavaType.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/IJavaType.kt
deleted file mode 100644
index fccc6db64..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/IJavaType.kt
+++ /dev/null
@@ -1,73 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing
-
-import io.realm.RealmList
-import io.realm.annotations.Required
-
-/**
- * A Java user type. May be a class, interface, enum, or annotation. Qualified name of a type or a
- * package name is always represented in the (partially) internal form. For example, the fully qualified
- * of `java.lang.Object` is `java/lang/Object` and the package name is `java/lang`.
- *
- * @property fqn The fully qualified name of the type.
- * @property name The simple name of the type.
- * @property packageName The package name of the type.
- * @property superInterfacesFqn The fully qualified names of the interfaces implemented by the type.
- * @property fields The fields of the type.
- * @property methods The methods of the type.
- * @property isClass Whether the type is a class.
- * @property isInterface Whether the type is an interface.
- * @property isAnnotation Whether the type is an annotation.
- * @property isEnum Whether the type is an enum.
- * @author Akash Yadav
- */
-interface IJavaType : IJavaSymbol {
- var fqn: String?
- var name: String?
- var packageName: String?
- var isInner: Boolean
-
- /**
- * The fully qualified name of the superclass of the type.
- *
- * Info about fields and methods are availabe in the class file itself. Hhowever, a class may
- * extend a class (or implement an interface) which may be defined in other jar files. As a result,
- * we only store the fully qualifed names of the classes and interfaces then add an index based on
- * these fully qualifed names in the database.
- *
- * This property is not [Required] because we also index `java/lang/Object`, which does not have
- * a superclass.
- */
- var superClassFqn: String?
- var superInterfacesFqn: RealmList?
- var fields: RealmList?
- var methods: RealmList?
-
- val isClass: Boolean
- get() = false
-
- val isInterface: Boolean
- get() = false
-
- val isAnnotation: Boolean
- get() = false
-
- val isEnum: Boolean
- get() = false
-}
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/ISharedJavaIndexable.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/ISharedJavaIndexable.kt
deleted file mode 100644
index fd89363a5..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/ISharedJavaIndexable.kt
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing
-
-/**
- * An [IJavaIndexable] model which is shared between other models.
- *
- * @author Akash Yadav
- */
-interface ISharedJavaIndexable : IJavaIndexable {
-
- /**
- * A unique ID for the indexable.
- */
- var id: Int?
-
- /**
- * Compute and update the ID of this indexable.
- */
- fun computeId()
-}
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/JavaIndexingRealmModule.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/JavaIndexingRealmModule.kt
deleted file mode 100644
index 14f5b8931..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/JavaIndexingRealmModule.kt
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing
-
-import com.itsaky.androidide.lsp.java.indexing.classfile.AnnotationAnnotationElementValue
-import com.itsaky.androidide.lsp.java.indexing.classfile.AnnotationElement
-import com.itsaky.androidide.lsp.java.indexing.classfile.ArrayAnnotationElementValue
-import com.itsaky.androidide.lsp.java.indexing.classfile.ClassAnnotationElementValue
-import com.itsaky.androidide.lsp.java.indexing.classfile.EnumAnnotationElementValue
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaAnnotation
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaClass
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaConstant
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaEnum
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaField
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaInterface
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaMethod
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaType
-import com.itsaky.androidide.lsp.java.indexing.classfile.PrimitiveAnnotationElementValue
-import io.realm.annotations.RealmModule
-
-/**
- * [RealmModule] for the indexing databased for Java.
- *
- * @author Akash Yadav
- */
-@RealmModule(
- library = true, classes = [
- AnnotationElement::class,
- AnnotationAnnotationElementValue::class,
- ArrayAnnotationElementValue::class,
- ClassAnnotationElementValue::class,
- EnumAnnotationElementValue::class,
- PrimitiveAnnotationElementValue::class,
- JavaAnnotation::class,
- JavaClass::class,
- JavaConstant::class,
- JavaEnum::class,
- JavaField::class,
- JavaInterface::class,
- JavaMethod::class,
- JavaType::class,
- ]
-)
-internal class JavaIndexingRealmModule
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/JavaJarModelBuilder.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/JavaJarModelBuilder.kt
deleted file mode 100644
index a70038026..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/JavaJarModelBuilder.kt
+++ /dev/null
@@ -1,424 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing
-
-import androidx.annotation.VisibleForTesting
-import com.itsaky.androidide.lsp.java.indexing.classfile.AnnotationAnnotationElementValue
-import com.itsaky.androidide.lsp.java.indexing.classfile.AnnotationElement
-import com.itsaky.androidide.lsp.java.indexing.classfile.AnnotationElement.Companion.newAnnotationElement
-import com.itsaky.androidide.lsp.java.indexing.classfile.ArrayAnnotationElementValue
-import com.itsaky.androidide.lsp.java.indexing.classfile.ClassAnnotationElementValue
-import com.itsaky.androidide.lsp.java.indexing.classfile.EnumAnnotationElementValue
-import com.itsaky.androidide.lsp.java.indexing.classfile.IAnnotationElementValue
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaAnnotation
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaClass
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaConstant
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaEnum
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaField
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaInterface
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaMethod
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaType
-import com.itsaky.androidide.lsp.java.indexing.classfile.PrimitiveAnnotationElementValue
-import com.itsaky.androidide.lsp.java.utils.DescriptorUtils
-import io.realm.RealmAny
-import io.realm.RealmDictionary
-import io.realm.RealmList
-import openjdk.tools.classfile.AccessFlags
-import openjdk.tools.classfile.Annotation.Annotation_element_value
-import openjdk.tools.classfile.Annotation.Array_element_value
-import openjdk.tools.classfile.Annotation.Class_element_value
-import openjdk.tools.classfile.Annotation.Enum_element_value
-import openjdk.tools.classfile.Annotation.Primitive_element_value
-import openjdk.tools.classfile.Annotation.element_value
-import openjdk.tools.classfile.AnnotationDefault_attribute
-import openjdk.tools.classfile.Attribute
-import openjdk.tools.classfile.ClassFile
-import openjdk.tools.classfile.ConstantPool
-import openjdk.tools.classfile.ConstantPool.CONSTANT_Double_info
-import openjdk.tools.classfile.ConstantPool.CONSTANT_Float_info
-import openjdk.tools.classfile.ConstantPool.CONSTANT_Integer_info
-import openjdk.tools.classfile.ConstantPool.CONSTANT_Long_info
-import openjdk.tools.classfile.ConstantPool.CONSTANT_String_info
-import openjdk.tools.classfile.ConstantPool.CONSTANT_Utf8_info
-import openjdk.tools.classfile.ConstantPool.CPInfo
-import openjdk.tools.classfile.ConstantValue_attribute
-import java.io.File
-import java.util.zip.ZipFile
-
-/**
- * [JavaJarModelBuilder] builds models for Java classes in a JAR file.
- *
- * @author Akash Yadav
- */
-class JavaJarModelBuilder(private val jar: File) {
-
- // for testing purposes
- // prefer using consumeTypes(Function)
- @VisibleForTesting(otherwise = VisibleForTesting.PRIVATE)
- fun buildTypes(): List> {
- val types = mutableListOf>()
- consumeTypes { types.add(it) }
- return types
- }
-
- fun consumeTypes(consumer: (IJavaType<*, *>) -> Unit) {
- ZipFile(jar).use { jar ->
- jar.entries().asSequence().filter { it.name.endsWith(".class") }.forEach { entry ->
- jar.getInputStream(entry).buffered().use { inputStream ->
- val classFile = ClassFile.read(inputStream)!!
-
- // build model only if the class is not an anonymous or local class
- if (classFile.getAttribute(Attribute.EnclosingMethod) == null) {
- val type = buildType(classFile)
- consumer(type)
- }
- }
- }
- }
- }
-
- private fun buildType(classFile: ClassFile): IJavaType<*, *> {
- val classInfo = classFile.constant_pool.getClassInfo(classFile.this_class)
- val fqn = classInfo.baseName
- val (pck, name, isInner) = splitFqn(fqn)
- return buildType(fqn, pck, name, isInner, classFile)
- }
-
- /**
- * Split the given fully qualified name of a class and return the package name and the simple name
- * of the class, along with whether the class is an inner class.
- */
- private fun splitFqn(fqn: String): Triple {
- val dolIdx = fqn.lastIndexOf('$')
-
- // start looking for '/' from the index of the last '$'
- // a '/' will always appear before a '$'
- val slaIdx = fqn.lastIndexOf('/', startIndex = if (dolIdx == -1) fqn.lastIndex else dolIdx - 1)
-
- if (slaIdx == -1 && dolIdx != -1) {
- // fqn == SomeClass$InnerClass (inner class of a class in the root package)
- // pck is empty, but fqn is not the class's simple name
- return Triple("", fqn.substring(dolIdx + 1), true)
- }
-
- if (slaIdx == -1) {
- // fqn == SomeClass (class in the root package)
- // pck is empty and fqn is class's simple name
- return Triple("", fqn, false)
- }
-
- if (dolIdx == -1) {
- // fqn == com/example/SomeClass
- return Triple(fqn.substring(0, slaIdx), fqn.substring(slaIdx + 1), false)
- }
-
- // fqn == com/example/SomeClass$InnerClass
- return Triple(fqn.substring(0, slaIdx), fqn.substring(dolIdx + 1), true)
- }
-
- private fun buildType(
- fqn: String,
- pck: String,
- name: String,
- isInner: Boolean,
- classFile: ClassFile
- ): IJavaType<*, *> {
- return when {
- classFile.access_flags.`is`(AccessFlags.ACC_ENUM) -> buildEnum(fqn, name, pck, classFile)
- classFile.access_flags.`is`(AccessFlags.ACC_ANNOTATION) -> buildAnnotation(
- fqn,
- name,
- pck,
- classFile
- )
-
- classFile.access_flags.`is`(AccessFlags.ACC_INTERFACE) -> buildInterface(
- fqn,
- name,
- pck,
- classFile
- )
-
- else -> buildClass(fqn, name, pck, classFile)
- }.also {
- it.isInner = isInner
- }
- }
-
- private fun buildClass(fqn: String, name: String, pck: String, classFile: ClassFile): JavaClass {
- return JavaClass.newInstance(fqn, name, pck, classFile.access_flags.flags).apply {
- setSuperClass(classFile)
- setSuperInterfaces(classFile)
- setFields(classFile)
- setMethods(classFile)
- }
- }
-
- private fun buildInterface(
- fqn: String, name: String, pck: String, classFile: ClassFile
- ): JavaInterface {
- return JavaInterface.newInstance(fqn, name, pck, classFile.access_flags.flags).apply {
- setSuperClass(classFile)
- setSuperInterfaces(classFile)
- setFields(classFile)
- setMethods(classFile)
- }
- }
-
- private fun buildAnnotation(
- fqn: String, name: String, pck: String, classFile: ClassFile
- ): JavaAnnotation {
- return JavaAnnotation.newInstance(fqn, name, pck, classFile.access_flags.flags).apply {
- setSuperClass(classFile)
- setSuperInterfaces(classFile)
- setFields(classFile)
- setAnnotationElements(classFile)
- }
- }
-
- private fun buildEnum(fqn: String, name: String, pck: String, classFile: ClassFile): JavaEnum {
- return JavaEnum.newInstance(fqn, name, pck, classFile.access_flags.flags).apply {
- setSuperClass(classFile)
- setSuperInterfaces(classFile)
- setFields(classFile)
- setMethods(classFile)
- }
- }
-
- private fun IJavaType<*, *>.setSuperInterfaces(classFile: ClassFile) {
- val interfaces = RealmList()
- for (iface in classFile.interfaces) {
- val ifaceInfo = classFile.constant_pool.getClassInfo(iface)
- interfaces.add(ifaceInfo.baseName!!)
- }
-
- superInterfacesFqn = interfaces
- }
-
- private fun IJavaType<*, *>.setSuperClass(classFile: ClassFile) {
- if (classFile.super_class == 0) {
- // From https://docs.oracle.com/javase/specs/jvms/se21/html/jvms-4.html#jvms-4.5
- // If the value of the super_class field is 0, then this class represents the java/lang/Object class itself
- // and hence, doesn't have a super class.
- return
- }
-
- val superclassInfo = classFile.constant_pool.getClassInfo(classFile.super_class)
- superClassFqn = superclassInfo.baseName!!
- }
-
- private fun IJavaType<*, JavaMethod>.setMethods(classFile: ClassFile) {
- methods = RealmList().apply {
- classFile.methods.forEach { method ->
- val descriptor = classFile.constant_pool.getUTF8Value(method.descriptor.index)
- val methodName = method.getName(classFile.constant_pool)
- val methodType = DescriptorUtils.returnType(descriptor)
- val paramTypes = RealmList().apply {
- addAll(DescriptorUtils.paramTypes(descriptor))
- }
-
- add(JavaMethod.newInstance(methodName, paramTypes, methodType, method.access_flags.flags))
- }
- }
- }
-
- private fun IJavaType.setFields(classFile: ClassFile) {
- fields = RealmList().apply {
- classFile.fields.forEach { field ->
- val descriptor = classFile.constant_pool.getUTF8Value(field.descriptor.index)
- val fieldName = field.getName(classFile.constant_pool)
- val fieldType = DescriptorUtils.type(descriptor)
-
- add(JavaField.newField(fieldName, fieldType, field.access_flags.flags).apply {
- field.attributes.get(Attribute.ConstantValue)?.also { constAttr ->
- val constantValue = constAttr as ConstantValue_attribute
- val constant = classFile.constant_pool.get(constantValue.constantvalue_index)
- val isStringType = fieldType.isStringType()
- val javaConstant = if (fieldType.isPrimitive() || isStringType) {
- toJavaConstant(fieldType.kind, constant, if (isStringType) 's' else null)
- } else {
- throw IllegalArgumentException("Invalid field type for constant value: $fieldType")
- }
-
- this.constantValue = javaConstant
- }
- })
- }
- }
- }
-
- private fun JavaAnnotation.setAnnotationElements(classFile: ClassFile) {
- methods = RealmList().apply {
- classFile.methods.forEach { method ->
- val descriptor = classFile.constant_pool.getUTF8Value(method.descriptor.index)
- val methodName = method.getName(classFile.constant_pool)
- val methodType = DescriptorUtils.returnType(descriptor)
-
- add(
- newAnnotationElement(
- methodName, methodType, method.access_flags.flags
- ).apply {
- val annotationDefault =
- method.attributes.get(Attribute.AnnotationDefault) as? AnnotationDefault_attribute?
- if (annotationDefault != null) {
- val defaultValue = annotationDefault.default_value
- val value = toAnnotationElementValue(defaultValue, classFile)
- this.defaultValue = value.let(RealmAny::valueOf) ?: RealmAny.nullValue()
- }
- })
- }
- }
- }
-
- private fun toAnnotationElementValue(
- defaultValue: element_value, classFile: ClassFile
- ): IAnnotationElementValue {
- val char = defaultValue.tag.toChar()
- var kind = JavaType.kindForType(char)
- if (char == 's') {
- kind = JavaType.KIND_REF
- }
-
- var value: IAnnotationElementValue? = when (kind) {
- JavaType.KIND_BOOLEAN,
- JavaType.KIND_BYTE,
- JavaType.KIND_CHAR,
- JavaType.KIND_SHORT,
- JavaType.KIND_INT,
- JavaType.KIND_LONG,
- JavaType.KIND_FLOAT,
- JavaType.KIND_DOUBLE -> PrimitiveAnnotationElementValue.newInstance(
- // annotation value kinds are same as JavaType.KIND_*
- kind = kind,
- value = toPrimitiveConstant(
- classFile.constant_pool, kind, char, defaultValue as Primitive_element_value
- )
- )
-
- else -> null
- }
-
- if (value == null) {
- value = when (char) {
- 's' -> PrimitiveAnnotationElementValue.newInstance(
- kind = IAnnotationElementValue.KIND_STRING,
- value = toPrimitiveConstant(
- classFile.constant_pool,
- JavaType.KIND_REF,
- char,
- defaultValue as Primitive_element_value
- )
- )
-
- 'e' -> {
- val enum = defaultValue as Enum_element_value
- EnumAnnotationElementValue.newInstance(
- name = classFile.constant_pool.getUTF8Value(enum.const_name_index),
- type = DescriptorUtils.type(classFile.constant_pool.getUTF8Value(enum.type_name_index))
- )
- }
-
- 'c' -> {
- // even though the name is given as "class_info_index", the constant at that index
- // is actually a CONSTANT_Utf8_info representing a return type descriptor (JLS $4.3.3)
- // this has been clearly mentioned in the Java Language Specification
- ClassAnnotationElementValue.newInstance(
- DescriptorUtils.type(
- classFile.constant_pool.getUTF8Value(
- (defaultValue as Class_element_value).class_info_index
- )
- )
- )
- }
-
- '@' -> {
- val annotation = (defaultValue as Annotation_element_value).annotation_value
- AnnotationAnnotationElementValue.newInstance(type = DescriptorUtils.type(
- classFile.constant_pool.getUTF8Value(
- annotation.type_index
- )
- ),
- values = RealmDictionary().apply {
- for (pair in annotation.element_value_pairs) {
- this[classFile.constant_pool.getUTF8Value(pair.element_name_index)] =
- toAnnotationElementValue(pair.value, classFile).let { elementValue ->
- RealmAny.valueOf(elementValue)
- }
- }
- })
- }
-
- '[' -> {
- ArrayAnnotationElementValue.newInstance(values = RealmList().apply {
- (defaultValue as Array_element_value).values.forEach { element ->
- add(toAnnotationElementValue(element, classFile).let { elementValue ->
- RealmAny.valueOf(elementValue)
- })
- }
- })
- }
-
- else -> throw IllegalArgumentException("Unknown value tag: ${defaultValue.tag}")
- }
- }
- return value
- }
-
- private fun toPrimitiveConstant(
- constantPool: ConstantPool, kind: Int, char: Char, prim: Primitive_element_value
- ): JavaConstant {
- if (kind == JavaType.KIND_REF && char != 's') {
- throw IllegalArgumentException("Unknown value tag: $char")
- }
-
- val constant = constantPool.get(prim.const_value_index)
- return toJavaConstant(kind, constant, char)
- }
-
- private fun toJavaConstant(
- kind: Int, constant: CPInfo, char: Char?
- ): JavaConstant {
- val realmAny = when (kind) {
- JavaType.KIND_BOOLEAN,
- JavaType.KIND_BYTE,
- JavaType.KIND_CHAR,
- JavaType.KIND_SHORT,
- JavaType.KIND_INT -> (constant as CONSTANT_Integer_info).value.let {
- RealmAny.valueOf(it)
- }
-
- JavaType.KIND_LONG -> (constant as CONSTANT_Long_info).value.let { RealmAny.valueOf(it) }
- JavaType.KIND_FLOAT -> (constant as CONSTANT_Float_info).value.let { RealmAny.valueOf(it) }
- JavaType.KIND_DOUBLE -> (constant as CONSTANT_Double_info).value.let { RealmAny.valueOf(it) }
- else -> if (char == 's') {
- if (constant is CONSTANT_String_info) {
- constant.string
- } else {
- (constant as CONSTANT_Utf8_info).value
- }.let { RealmAny.valueOf(it) }
- } else {
- throw IllegalArgumentException("Unknown value tag: $char")
- }
- }
-
- return JavaConstant.newInstance(
- kind = kind,
- value = realmAny
- )
- }
-}
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/AnnotationElement.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/AnnotationElement.kt
deleted file mode 100644
index f0fe17bdc..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/AnnotationElement.kt
+++ /dev/null
@@ -1,91 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing.classfile
-
-import com.itsaky.androidide.lsp.java.indexing.IJavaSymbol
-import io.realm.RealmAny
-import io.realm.RealmResults
-import io.realm.annotations.Index
-import io.realm.annotations.LinkingObjects
-import io.realm.annotations.RealmClass
-import io.realm.annotations.RealmField
-import io.realm.annotations.Required
-
-/**
- * A method defined in an annotation type.
- *
- * @property defaultValue The default value of the annotation element.
- * @author Akash Yadav
- */
-@RealmClass(embedded = true)
-open class AnnotationElement : IJavaSymbol {
-
- @Index
- @Required
- @RealmField("name")
- var name: String? = null
-
- @RealmField("type")
- var type: JavaType? = null
-
- @RealmField("accessFlags")
- override var accessFlags: Int = 0
-
- @LinkingObjects("methods")
- val ofClass: RealmResults? = null
-
- /**
- * The default value of the annotation element. One of the following:
- * - [PrimitiveAnnotationElementValue]
- * - [EnumAnnotationElementValue]
- * - [ArrayAnnotationElementValue]
- * - [ClassAnnotationElementValue]
- * - [AnnotationAnnotationElementValue]
- */
- @RealmField("defaultValue")
- var defaultValue: RealmAny? = null
-
- /**
- * Returns the signature of the method.
- */
- fun signature(): String {
- val sb = StringBuilder()
- sb.append(name)
- sb.append("(")
- sb.append(")")
- sb.append(type?.internalForm())
- return sb.toString()
- }
-
- companion object {
- @JvmStatic
- fun newAnnotationElement(
- name: String,
- type: JavaType,
- accessFlags: Int,
- defaultValue: RealmAny? = null
- ): AnnotationElement {
- return AnnotationElement().apply {
- this.name = name
- this.type = type
- this.accessFlags = accessFlags
- this.defaultValue = defaultValue
- }
- }
- }
-}
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaAnnotation.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaAnnotation.kt
deleted file mode 100644
index 4a3a7d4a2..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaAnnotation.kt
+++ /dev/null
@@ -1,105 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing.classfile
-
-import com.itsaky.androidide.lsp.java.indexing.IJavaType
-import io.realm.RealmList
-import io.realm.annotations.Index
-import io.realm.annotations.PrimaryKey
-import io.realm.annotations.RealmClass
-import io.realm.annotations.RealmField
-import io.realm.annotations.Required
-
-/**
- * A Java annotation type.
- *
- * Implementation note:
- * An annotation type is a Java interface, and hence, it inherits from [JavaInterface] instead of
- * [IJavaType]. Also, [IJavaType.isInterface] and [IJavaType.isAnnotation] both
- * return `true` for annotation types.
- *
- * @author Akash Yadav
- */
-
-@RealmClass
-open class JavaAnnotation : IJavaType {
-
- @Index
- @PrimaryKey
- @Required
- @RealmField("fqn")
- override var fqn: String? = null
-
- @Required
- @RealmField("name")
- override var name: String? = null
-
- @Required
- @RealmField("pck")
- override var packageName: String? = null
-
- @RealmField("isInner")
- override var isInner: Boolean = false
-
- @RealmField("superClassFqn")
- override var superClassFqn: String? = null
-
- @RealmField("superInterfacesFqn")
- override var superInterfacesFqn: RealmList? = null
-
- @RealmField("accessFlags")
- override var accessFlags: Int = 0
-
- @RealmField("fields")
- override var fields: RealmList? = null
-
- @RealmField("methods")
- override var methods: RealmList? = null
-
- override val isInterface: Boolean
- get() = true
-
- override val isAnnotation: Boolean
- get() = true
-
- companion object {
- @JvmStatic
- fun newInstance(
- fqn: String,
- name: String,
- packageName: String,
- accessFlags: Int,
- isInner: Boolean = false,
- superInterfacesFqn: RealmList? = null,
- fields: RealmList? = null,
- methods: RealmList? = null
- ): JavaAnnotation {
- return JavaAnnotation().apply {
- this.fqn = fqn
- this.name = name
- this.packageName = packageName
- this.isInner = isInner
- this.superClassFqn = superClassFqn
- this.superInterfacesFqn = superInterfacesFqn
- this.accessFlags = accessFlags
- this.fields = fields
- this.methods = methods
- }
- }
- }
-}
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaClass.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaClass.kt
deleted file mode 100644
index 8fcde79eb..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaClass.kt
+++ /dev/null
@@ -1,98 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing.classfile
-
-import com.itsaky.androidide.lsp.java.indexing.IJavaType
-import io.realm.RealmList
-import io.realm.annotations.Index
-import io.realm.annotations.PrimaryKey
-import io.realm.annotations.RealmClass
-import io.realm.annotations.RealmField
-import io.realm.annotations.Required
-
-/**
- * A Java class type.
- *
- * @author Akash Yadav
- */
-
-@RealmClass
-open class JavaClass : IJavaType {
-
- @Index
- @PrimaryKey
- @Required
- @RealmField("fqn")
- override var fqn: String? = null
-
- @Required
- @RealmField("name")
- override var name: String? = null
-
- @Required
- @RealmField("pck")
- override var packageName: String? = null
-
- @RealmField("isInner")
- override var isInner: Boolean = false
-
- @RealmField("superClassFqn")
- override var superClassFqn: String? = null
-
- @RealmField("superInterfacesFqn")
- override var superInterfacesFqn: RealmList? = null
-
- @RealmField("accessFlags")
- override var accessFlags: Int = 0
-
- @RealmField("fields")
- override var fields: RealmList? = null
-
- @RealmField("methods")
- override var methods: RealmList? = null
-
- override val isClass: Boolean
- get() = true
-
- companion object {
- @JvmStatic
- fun newInstance(
- fqn: String,
- name: String,
- packageName: String,
- accessFlags: Int,
- isInner: Boolean = false,
- superClassFqn: String? = null,
- superInterfacesFqn: RealmList? = null,
- fields: RealmList? = null,
- methods: RealmList? = null
- ): JavaClass {
- return JavaClass().apply {
- this.fqn = fqn
- this.name = name
- this.packageName = packageName
- this.isInner = isInner
- this.superClassFqn = superClassFqn
- this.superInterfacesFqn = superInterfacesFqn
- this.accessFlags = accessFlags
- this.fields = fields
- this.methods = methods
- }
- }
- }
-}
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaConstant.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaConstant.kt
deleted file mode 100644
index 7a042f55a..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaConstant.kt
+++ /dev/null
@@ -1,152 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing.classfile
-
-import com.google.common.base.Objects
-import com.itsaky.androidide.lsp.java.indexing.ISharedJavaIndexable
-import io.realm.RealmAny
-import io.realm.annotations.PrimaryKey
-import io.realm.annotations.RealmClass
-import io.realm.annotations.RealmField
-
-/**
- * A constant value in Java.
- *
- * A unique ID is used as the primary key in order to ensure that a constant is not stored multiple
- * times in the database. Also, a string constant always has type [JavaType.KIND_REF]. A constant
- * is never of type [JavaType.KIND_VOID].
- *
- * @property id A unique ID which is generated for the constant.
- * @property kind The kind of contant. See [JavaType] for a list of kinds.
- * @property value The value of the constant. Cast this value based on the value of [kind].
- * @author Akash Yadav
- */
-@RealmClass
-open class JavaConstant : ISharedJavaIndexable {
-
- @PrimaryKey
- @RealmField("id")
- override var id: Int? = null
-
- @RealmField("kind")
- var kind: Int = JavaType.KIND_UNKNOWN
- private set
-
- @RealmField("value")
- var value: RealmAny? = null
- private set
-
- companion object {
- fun newInstance(kind: Int, value: RealmAny): JavaConstant {
- return JavaConstant().apply {
- this.kind = kind
- this.value = value
- this.computeId()
- }
- }
- }
-
- fun update(kind: Int = this.kind, value: RealmAny? = this.value) {
- this.kind = kind
- this.value = value
- this.computeId()
- }
-
- fun update(src: JavaConstant) {
- this.kind = src.kind
- this.value = src.value
- this.computeId()
- }
-
-
- override fun computeId() {
- this.id = Objects.hashCode(this.kind, this.kind, this.value)
- }
-
- // boolean, byte, short, int are stored as int in the bytecode
-
- fun asBoolean(): Boolean? {
- return safeCast(JavaType.KIND_BOOLEAN) { asInteger() == 1 }
- }
-
- fun asByte(): Byte? {
- return safeCast(JavaType.KIND_BYTE) { asInteger()?.toByte() }
- }
-
- fun asShort(): Short? {
- return safeCast(JavaType.KIND_SHORT) { asInteger()?.toShort() }
- }
-
- fun asInt(): Int? {
- return safeCast(JavaType.KIND_INT) { asInteger() }
- }
-
- fun asLong(): Long? {
- return safeCast(JavaType.KIND_LONG) { asLong() }
- }
-
- fun asFloat(): Float? {
- return safeCast(JavaType.KIND_FLOAT) { asFloat() }
- }
-
- fun asDouble(): Double? {
- return safeCast(JavaType.KIND_DOUBLE) { asDouble() }
- }
-
- fun asString(): String? {
- return safeCast(JavaType.KIND_REF) { asString() }
- }
-
- fun asChar(): Char? {
- return safeCast(JavaType.KIND_CHAR) { asInteger()?.toChar() }
- }
-
- private inline fun safeCast(kind: Int, action: RealmAny.() -> R): R? {
- return value?.let {
- if (this.kind == kind) {
- try {
- it.action()
- } catch (ex: ClassCastException) {
- throw IllegalStateException("Kind == $kind but safeCast failed", ex)
- }
- } else null
- }
- }
-
- override fun equals(other: Any?): Boolean {
- if (this === other) return true
- if (other !is JavaConstant) return false
-
- if (id != other.id) return false
- if (kind != other.kind) return false
- if (value != other.value) return false
-
- return true
- }
-
- override fun hashCode(): Int {
- var result = id ?: 0
- result = 31 * result + kind
- result = 31 * result + (value?.hashCode() ?: 0)
- return result
- }
-
- override fun toString(): String {
- return "JavaConstant(id=$id, kind=$kind, value=$value)"
- }
-}
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaEnum.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaEnum.kt
deleted file mode 100644
index 78d9ca644..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaEnum.kt
+++ /dev/null
@@ -1,97 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing.classfile
-
-import com.itsaky.androidide.lsp.java.indexing.IJavaType
-import io.realm.RealmList
-import io.realm.annotations.Index
-import io.realm.annotations.PrimaryKey
-import io.realm.annotations.RealmClass
-import io.realm.annotations.RealmField
-import io.realm.annotations.Required
-
-/**
- * A Java enum type.
- *
- * @author Akash Yadav
- */
-@RealmClass
-open class JavaEnum : IJavaType {
-
- @Index
- @PrimaryKey
- @Required
- @RealmField("fqn")
- override var fqn: String? = null
-
- @Required
- @RealmField("name")
- override var name: String? = null
-
- @Required
- @RealmField("pck")
- override var packageName: String? = null
-
- @RealmField("isInner")
- override var isInner: Boolean = false
-
- @RealmField("superClassFqn")
- override var superClassFqn: String? = null
-
- @RealmField("superInterfacesFqn")
- override var superInterfacesFqn: RealmList? = null
-
- @RealmField("accessFlags")
- override var accessFlags: Int = 0
-
- @RealmField("fields")
- override var fields: RealmList? = null
-
- @RealmField("methods")
- override var methods: RealmList? = null
-
- override val isEnum: Boolean
- get() = true
-
- companion object {
- @JvmStatic
- fun newInstance(
- fqn: String,
- name: String,
- packageName: String,
- accessFlags: Int,
- isInner: Boolean = false,
- superClassFqn: String? = null,
- superInterfacesFqn: RealmList? = null,
- fields: RealmList? = null,
- methods: RealmList? = null
- ): JavaEnum {
- return JavaEnum().apply {
- this.fqn = fqn
- this.name = name
- this.packageName = packageName
- this.isInner = isInner
- this.superClassFqn = superClassFqn
- this.superInterfacesFqn = superInterfacesFqn
- this.accessFlags = accessFlags
- this.fields = fields
- this.methods = methods
- }
- }
- }
-}
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaField.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaField.kt
deleted file mode 100644
index b1b809ffa..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaField.kt
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing.classfile
-
-import com.itsaky.androidide.lsp.java.indexing.IJavaSymbol
-import io.realm.RealmResults
-import io.realm.annotations.Index
-import io.realm.annotations.LinkingObjects
-import io.realm.annotations.RealmClass
-import io.realm.annotations.RealmField
-
-/**
- * @author Akash Yadav
- */
-@RealmClass(embedded = true)
-open class JavaField : IJavaSymbol {
-
- @Index
- @RealmField("name")
- var name: String? = null
-
- @RealmField("type")
- var type: JavaType? = null
-
- @RealmField("accessFlags")
- override var accessFlags: Int = 0
-
- @RealmField("constantValue")
- var constantValue: JavaConstant? = null
-
- @LinkingObjects("fields")
- val ofClass: RealmResults? = null
-
- companion object {
- @JvmStatic
- fun newField(
- name: String,
- type: JavaType,
- accessFlags: Int,
- constantValue: JavaConstant? = null
- ): JavaField {
- return JavaField().apply {
- this.name = name
- this.type = type
- this.accessFlags = accessFlags
- this.constantValue = constantValue
- }
- }
- }
-}
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaInterface.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaInterface.kt
deleted file mode 100644
index 130e055cf..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaInterface.kt
+++ /dev/null
@@ -1,96 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing.classfile
-
-import com.itsaky.androidide.lsp.java.indexing.IJavaType
-import io.realm.RealmList
-import io.realm.annotations.Index
-import io.realm.annotations.PrimaryKey
-import io.realm.annotations.RealmClass
-import io.realm.annotations.RealmField
-import io.realm.annotations.Required
-
-/**
- * A Java interface type.
- *
- * @author Akash Yadav
- */
-
-@RealmClass
-open class JavaInterface : IJavaType {
-
- @Index
- @PrimaryKey
- @Required
- @RealmField("fqn")
- override var fqn: String? = null
-
- @Required
- @RealmField("name")
- override var name: String? = null
-
- @Required
- @RealmField("pck")
- override var packageName: String? = null
-
- @RealmField("isInner")
- override var isInner: Boolean = false
-
- @RealmField("superClassFqn")
- override var superClassFqn: String? = null
-
- @RealmField("superInterfacesFqn")
- override var superInterfacesFqn: RealmList? = null
-
- @RealmField("accessFlags")
- override var accessFlags: Int = 0
-
- @RealmField("fields")
- override var fields: RealmList? = null
-
- @RealmField("methods")
- override var methods: RealmList? = null
-
- override val isInterface: Boolean
- get() = true
-
- companion object {
- @JvmStatic
- fun newInstance(
- fqn: String,
- name: String,
- packageName: String,
- accessFlags: Int,
- isInner: Boolean = false,
- superInterfacesFqn: RealmList? = null,
- fields: RealmList? = null,
- methods: RealmList? = null
- ): JavaInterface {
- return JavaInterface().apply {
- this.fqn = fqn
- this.name = name
- this.packageName = packageName
- this.isInner = isInner
- this.superInterfacesFqn = superInterfacesFqn
- this.accessFlags = accessFlags
- this.fields = fields
- this.methods = methods
- }
- }
- }
-}
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaMethod.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaMethod.kt
deleted file mode 100644
index 69635b067..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaMethod.kt
+++ /dev/null
@@ -1,83 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing.classfile
-
-import com.itsaky.androidide.lsp.java.indexing.IJavaSymbol
-import io.realm.RealmList
-import io.realm.RealmResults
-import io.realm.annotations.Index
-import io.realm.annotations.LinkingObjects
-import io.realm.annotations.RealmClass
-import io.realm.annotations.RealmField
-import io.realm.annotations.Required
-
-/**
- * @author Akash Yadav
- */
-
-@RealmClass(embedded = true)
-open class JavaMethod : IJavaSymbol {
- @Index
- @Required
- @RealmField("name")
- var name: String? = null
-
- @RealmField("paramTypes")
- var paramsTypes: RealmList? = null
-
- @RealmField("returnType")
- var returnType: JavaType? = null
-
- @RealmField("accessFlags")
- override var accessFlags: Int = 0
-
- @LinkingObjects("methods")
- val ofClass: RealmResults? = null
-
- /**
- * Returns the signature of the method.
- */
- fun signature(): String {
- val sb = StringBuilder()
- sb.append(name)
- sb.append("(")
- paramsTypes?.forEach {
- sb.append(it.internalForm())
- }
- sb.append(")")
- sb.append(returnType?.internalForm())
- return sb.toString()
- }
-
- companion object {
- @JvmStatic
- fun newInstance(
- name: String,
- paramsTypes: RealmList,
- returnType: JavaType,
- accessFlags: Int,
- ): JavaMethod {
- return JavaMethod().apply {
- this.name = name
- this.paramsTypes = paramsTypes
- this.returnType = returnType
- this.accessFlags = accessFlags
- }
- }
- }
-}
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/annotationElementValues.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/annotationElementValues.kt
deleted file mode 100644
index 743352a7a..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/annotationElementValues.kt
+++ /dev/null
@@ -1,340 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing.classfile
-
-import com.google.common.base.Objects
-import com.itsaky.androidide.db.utils.hash
-import com.itsaky.androidide.db.utils.isEqualTo
-import com.itsaky.androidide.lsp.java.indexing.ISharedJavaIndexable
-import io.realm.RealmAny
-import io.realm.RealmDictionary
-import io.realm.RealmList
-import io.realm.annotations.PrimaryKey
-import io.realm.annotations.RealmClass
-import io.realm.annotations.RealmField
-import io.realm.annotations.Required
-
-sealed interface IAnnotationElementValue : ISharedJavaIndexable {
- var kind: Int
-
- companion object {
- const val KIND_UNKNOWN = JavaType.KIND_UNKNOWN
- const val KIND_BOOLEAN = JavaType.KIND_BOOLEAN
- const val KIND_BYTE = JavaType.KIND_BYTE
- const val KIND_CHAR = JavaType.KIND_CHAR
- const val KIND_DOUBLE = JavaType.KIND_DOUBLE
- const val KIND_FLOAT = JavaType.KIND_FLOAT
- const val KIND_INT = JavaType.KIND_INT
- const val KIND_LONG = JavaType.KIND_LONG
- const val KIND_SHORT = JavaType.KIND_SHORT
-
- const val KIND_STRING = JavaType.__KIND_STRING
- const val KIND_CLASS = JavaType.__KIND_CLASS
- const val KIND_ENUM = JavaType.__KIND_ENUM
- const val KIND_ANNOTATION = JavaType.__KIND_ANNOTATION
- const val KIND_ARRAY = JavaType.__KIND_ARRAY
- }
-}
-
-
-@RealmClass
-open class PrimitiveAnnotationElementValue : IAnnotationElementValue {
-
- @PrimaryKey
- @Required
- @RealmField("id")
- override var id: Int? = null
-
- @RealmField("kind")
- override var kind: Int = 0
-
- @RealmField("value")
- var value: JavaConstant? = null
-
- override fun computeId() {
- this.id = Objects.hashCode(this.kind, this.value)
- }
-
- override fun equals(other: Any?): Boolean {
- if (this === other) return true
- if (other !is PrimitiveAnnotationElementValue) return false
-
- if (id != other.id) return false
- if (kind != other.kind) return false
- if (value != other.value) return false
-
- return true
- }
-
- override fun hashCode(): Int {
- var result = id ?: 0
- result = 31 * result + kind
- result = 31 * result + (value?.hashCode() ?: 0)
- return result
- }
-
- override fun toString(): String {
- return "PrimitiveAnnotationElementValue(id=$id, kind=$kind, value=$value)"
- }
-
- companion object {
- @JvmStatic
- fun newInstance(kind: Int, value: JavaConstant): PrimitiveAnnotationElementValue {
- return PrimitiveAnnotationElementValue().apply {
- this.kind = kind
- this.value = value
- this.computeId()
- }
- }
- }
-}
-
-
-@RealmClass
-open class EnumAnnotationElementValue : IAnnotationElementValue {
- @PrimaryKey
- @Required
- @RealmField("id")
- override var id: Int? = null
-
- @RealmField("kind")
- override var kind: Int = IAnnotationElementValue.KIND_ENUM
-
- @RealmField("name")
- var name: String? = null
-
- @RealmField("type")
- var type: JavaType? = null
-
- override fun computeId() {
- this.id = Objects.hashCode(this.kind, this.name, this.type)
- }
-
- override fun equals(other: Any?): Boolean {
- if (this === other) return true
- if (other !is EnumAnnotationElementValue) return false
-
- if (id != other.id) return false
- if (kind != other.kind) return false
- if (name != other.name) return false
- if (type != other.type) return false
-
- return true
- }
-
- override fun hashCode(): Int {
- var result = id ?: 0
- result = 31 * result + kind
- result = 31 * result + (name?.hashCode() ?: 0)
- result = 31 * result + (type?.hashCode() ?: 0)
- return result
- }
-
- override fun toString(): String {
- return "EnumAnnotationElementValue(id=$id, kind=$kind, name=$name, type=$type)"
- }
-
- companion object {
- @JvmStatic
- fun newInstance(name: String, type: JavaType): EnumAnnotationElementValue {
- return EnumAnnotationElementValue().apply {
- this.name = name
- this.type = type
- this.computeId()
- }
- }
- }
-}
-
-
-@RealmClass
-open class ArrayAnnotationElementValue : IAnnotationElementValue {
-
- @PrimaryKey
- @Required
- @RealmField("id")
- override var id: Int? = null
-
- @RealmField("kind")
- override var kind: Int = IAnnotationElementValue.KIND_ARRAY
-
- @RealmField("numValues")
- var numValues: Int = 0
-
- /**
- * The elements of the array element value. Always of type [IAnnotationElementValue].
- */
- @RealmField("values")
- var values: RealmList? = null
-
- override fun computeId() {
- this.id = Objects.hashCode(this.kind, this.numValues, this.values)
- }
-
- override fun equals(other: Any?): Boolean {
- if (this === other) return true
- if (other !is ArrayAnnotationElementValue) return false
-
- if (id != other.id) return false
- if (kind != other.kind) return false
- if (numValues != other.numValues) return false
- if (values != other.values) return false
-
- return true
- }
-
- override fun hashCode(): Int {
- var result = id ?: 0
- result = 31 * result + kind
- result = 31 * result + numValues
- result = 31 * result + (values?.hashCode() ?: 0)
- return result
- }
-
- override fun toString(): String {
- return "ArrayAnnotationElementValue(id=$id, kind=$kind, numValues=$numValues, values=$values)"
- }
-
- companion object {
- @JvmStatic
- fun newInstance(values: RealmList): ArrayAnnotationElementValue {
- return ArrayAnnotationElementValue().apply {
- this.numValues = values.size
- this.values = values
- this.computeId()
- }
- }
- }
-}
-
-
-@RealmClass
-open class ClassAnnotationElementValue : IAnnotationElementValue {
-
- @PrimaryKey
- @Required
- @RealmField("id")
- override var id: Int? = null
-
- @RealmField("kind")
- override var kind: Int = IAnnotationElementValue.KIND_CLASS
-
- @RealmField("type")
- var type: JavaType? = null
-
- override fun computeId() {
- this.id = Objects.hashCode(this.kind, this.type)
- }
-
- override fun equals(other: Any?): Boolean {
- if (this === other) return true
- if (other !is ClassAnnotationElementValue) return false
-
- if (id != other.id) return false
- if (kind != other.kind) return false
- if (type != other.type) return false
-
- return true
- }
-
- override fun hashCode(): Int {
- var result = id ?: 0
- result = 31 * result + kind
- result = 31 * result + (type?.hashCode() ?: 0)
- return result
- }
-
- override fun toString(): String {
- return "ClassAnnotationElementValue(id=$id, kind=$kind, type=$type)"
- }
-
- companion object {
- @JvmStatic
- fun newInstance(type: JavaType): ClassAnnotationElementValue {
- return ClassAnnotationElementValue().apply {
- this.type = type
- this.computeId()
- }
- }
- }
-}
-
-
-@RealmClass
-open class AnnotationAnnotationElementValue : IAnnotationElementValue {
-
- @PrimaryKey
- @Required
- @RealmField("id")
- override var id: Int? = null
-
- @RealmField("kind")
- override var kind: Int = IAnnotationElementValue.KIND_ANNOTATION
-
- @RealmField("type")
- var type: JavaType? = null
-
- /**
- * The named elements of the annotation element value. Always of type [IAnnotationElementValue].
- */
- @RealmField("values")
- var values: RealmDictionary? = null
-
- override fun computeId() {
- // RealmDictionary seems to not override hashCode()
- this.id = Objects.hashCode(this.kind, this.type, this.values?.hash())
- }
-
- override fun equals(other: Any?): Boolean {
- if (this === other) return true
- if (other !is AnnotationAnnotationElementValue) return false
-
- if (id != other.id) return false
- if (kind != other.kind) return false
- if (type != other.type) return false
- if (!values.isEqualTo(other)) return false
-
- return true
- }
-
- override fun hashCode(): Int {
- var result = id ?: 0
- result = 31 * result + kind
- result = 31 * result + (type?.hashCode() ?: 0)
- result = 31 * result + (values?.hashCode() ?: 0)
- return result
- }
-
- override fun toString(): String {
- return "AnnotationAnnotationElementValue(id=$id, kind=$kind, type=$type, values=$values)"
- }
-
- companion object {
- @JvmStatic
- fun newInstance(
- type: JavaType,
- values: RealmDictionary
- ): AnnotationAnnotationElementValue {
- return AnnotationAnnotationElementValue().apply {
- this.type = type
- this.values = values
- this.computeId()
- }
- }
- }
-}
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/internal/JavaIndexServiceImpl.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/internal/JavaIndexServiceImpl.kt
deleted file mode 100644
index 34b69d377..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/internal/JavaIndexServiceImpl.kt
+++ /dev/null
@@ -1,43 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing.internal
-
-import com.google.auto.service.AutoService
-import com.itsaky.androidide.indexing.IIndexService
-import com.itsaky.androidide.projects.IWorkspace
-import java.io.File
-
-/**
- * @author Akash Yadav
- */
-@AutoService(IIndexService::class)
-internal class JavaIndexServiceImpl : IIndexService {
-
- override val displayName: String
- get() = "Java LSP Indexing Service"
-
- override fun scanFiles(workspace: IWorkspace): Collection {
- return emptySet()
- }
-
- override suspend fun indexFiles(
- workspace: IWorkspace,
- files: Collection
- ) {
- }
-}
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/utils/DescriptorUtils.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/utils/DescriptorUtils.kt
deleted file mode 100644
index f6f2e8781..000000000
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/utils/DescriptorUtils.kt
+++ /dev/null
@@ -1,232 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.utils
-
-import com.itsaky.androidide.lsp.java.indexing.IJavaType
-import com.itsaky.androidide.lsp.java.indexing.classfile.AnnotationElement
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaField
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaMethod
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaType
-import java.util.Objects
-
-/**
- * @author Akash Yadav
- */
-object DescriptorUtils {
-
- /**
- * Create a method ID for the given method.
- */
- fun createMethodId(
- klass: IJavaType<*, *>,
- method: JavaMethod
- ): Int {
- return Objects.hash(klass.fqn, method.name, method.paramsTypes, method.returnType)
- }
-
- /**
- * Create a method ID for the given method.
- */
- fun createMethodId(
- klass: IJavaType<*, *>,
- element: AnnotationElement
- ): Int {
- return Objects.hash(klass.fqn, element.name, element.type)
- }
-
- /**
- * Create a field ID for the given field. The string representation is similar to how fields
- * are represented in Smali.
- *
- * ```
- * Lcom/example/Foo;->bar:I
- * ```
- */
- fun createFieldId(
- klass: IJavaType<*, *>,
- field: JavaField
- ): Int {
- return Objects.hash(klass.fqn, field.name, field.type)
- }
-
- /**
- * Parse the return type of a method descriptor.
- *
- * @param descriptor The method descriptor.
- */
- fun returnType(descriptor: String): JavaType {
- val idx = descriptor.indexOfLast { it == ')' }
- if (descriptor[0] != '(' || idx == -1) {
- throw IllegalArgumentException("Invalid method descriptor: $descriptor")
- }
-
- return type(descriptor.substring(idx + 1))
- }
-
- /**
- * Parse the parameter types of a method descriptor.
- *
- * @param descriptor The method descriptor.
- */
- fun paramTypes(descriptor: String): List {
- val idx = descriptor.indexOfLast { it == ')' }
- if (descriptor[0] != '(' || idx == -1) {
- throw IllegalArgumentException("Invalid method descriptor: $descriptor")
- }
-
- val types = mutableListOf()
- val params = descriptor.substring(1, idx)
- var i = 0
- while (i < params.length) {
- types.add(
- when (params[i]) {
- 'L' -> {
- val end = params.indexOf(';', startIndex = i + 1)
- referenceType(params, fromIndex = i, toIndex = end).also {
- i = end + 1
- }
- }
-
- '[' -> arrayType(params, fromIndex = i).also {
- // number of '['
- // + length of type (I or java/lang/String)
- // + 2 if kind is ref (because refs have 'L' and ';')
- i += it.arrayDims + it.name!!.length + (if (it.kind == JavaType.KIND_REF) 2 else 0)
- }
-
- else -> primitive(params[i].toString()).also {
- ++i
- }
- }
- )
- }
-
- return types
- }
-
- /**
- * Parse a type descriptor. A type descriptor can be any of :
- * - a primitive type descriptor
- * - a reference type descriptor
- * - an array type descriptor
- *
- * @param descriptor The type descriptor.
- */
- fun type(descriptor: String): JavaType {
- if (descriptor.startsWith("L")) {
- return referenceType(descriptor)
- }
-
- if (descriptor.startsWith("[")) {
- return arrayType(descriptor)
- }
-
- if (descriptor.length != 1) {
- throw IllegalArgumentException("Invalid type descriptor: $descriptor")
- }
-
- return primitive(descriptor)
- }
-
- /**
- * Parse a primitive type descriptor.
- *
- * @param descriptor The primitive type descriptor.
- */
- fun primitive(descriptor: String): JavaType = primitive(descriptor[0])
-
- /**
- * Parse a primitive type descriptor.
- *
- * @param char The primitive type.
- */
- fun primitive(char: Char): JavaType {
- val primitive = JavaType.primitiveFor(char)
- return requireNotNull(primitive) {
- "Invalid type descriptor: $char"
- }
- }
-
- /**
- * Parse a reference type descriptor.
- *
- * Format:
- * ```
- * Lcom/example/Foo;
- * ```
- *
- * @param descriptor The descriptor of a reference type
- * @param fromIndex The index of the first character of the reference type name.
- * @param toIndex The index of the last character of the reference type name (inclusive).
- */
- fun referenceType(
- descriptor: String, fromIndex: Int = 0, toIndex: Int = descriptor.length - 1
- ): JavaType {
- if (descriptor[fromIndex] != 'L' || descriptor[toIndex] != ';') {
- throw IllegalArgumentException("Invalid reference type descriptor: $descriptor, fromIndex: $fromIndex, toIndex: $toIndex")
- }
-
- return when (descriptor) {
- "Ljava/lang/String;" -> JavaType.STRING
- "Ljava/lang/Object;" -> JavaType.OBJECT
- "Ljava/lang/Class;" -> JavaType.CLASS
- else -> {
- // remove leading 'L' and trailing ';'
- val name = descriptor.substring(fromIndex + 1, toIndex)
- JavaType.newInstance(name = name, kind = JavaType.KIND_REF)
- }
- }
- }
-
-
- /**
- * Parse an array type descriptor.
- *
- * Format:
- * ```
- * [I
- * [[I
- * [[Lcom/example/Foo;
- * ```
- *
- * @param descriptor The array type descriptor.
- * @param fromIndex The index of the first character of the array type descriptor.
- */
- fun arrayType(descriptor: String, fromIndex: Int = 0): JavaType {
- if (descriptor[fromIndex] != '[') {
- throw IllegalArgumentException("Invalid array type descriptor: $descriptor, fromIndex: $fromIndex")
- }
-
- var idx = fromIndex + 1
- var dims = 1
- while (descriptor[idx] == '[') {
- idx++
- dims++
- }
-
- val type = if (descriptor[idx] == 'L') {
- referenceType(
- descriptor, fromIndex = idx, toIndex = descriptor.indexOf(';', startIndex = idx + 1)
- )
- } else {
- primitive(descriptor[idx])
- }
-
- return JavaType.newInstance(name = type.name, kind = type.kind, arrayDims = dims)
- }
-}
\ No newline at end of file
diff --git a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaType.kt b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/utils/JavaType.kt
similarity index 79%
rename from java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaType.kt
rename to java/lsp/src/main/java/com/itsaky/androidide/lsp/java/utils/JavaType.kt
index 206529d25..e812d76ea 100644
--- a/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/indexing/classfile/JavaType.kt
+++ b/java/lsp/src/main/java/com/itsaky/androidide/lsp/java/utils/JavaType.kt
@@ -15,38 +15,17 @@
* along with AndroidIDE. If not, see .
*/
-package com.itsaky.androidide.lsp.java.indexing.classfile
-
-import com.google.common.base.Objects
-import com.itsaky.androidide.lsp.java.indexing.ISharedJavaIndexable
-import com.itsaky.androidide.models.ICloneable
-import io.realm.annotations.Index
-import io.realm.annotations.PrimaryKey
-import io.realm.annotations.RealmClass
-import io.realm.annotations.RealmField
-import io.realm.annotations.Required
+package com.itsaky.androidide.lsp.java.utils
/**
* @author Akash Yadav
*/
+open class JavaType {
-@RealmClass
-open class JavaType : ISharedJavaIndexable, ICloneable {
-
- @Required
- @PrimaryKey
- @RealmField("id")
- override var id: Int? = null
-
- @Index
- @Required
- @RealmField("name")
var name: String? = null
- @RealmField("kind")
var kind: Int = KIND_UNKNOWN
- @RealmField("arrayDims")
var arrayDims: Int = 0
/**
@@ -76,14 +55,7 @@ open class JavaType : ISharedJavaIndexable, ICloneable {
*/
fun isPrimitive(): Boolean {
return when (kind) {
- KIND_BOOLEAN,
- KIND_BYTE,
- KIND_CHAR,
- KIND_DOUBLE,
- KIND_FLOAT,
- KIND_INT,
- KIND_LONG,
- KIND_SHORT -> true
+ KIND_BOOLEAN, KIND_BYTE, KIND_CHAR, KIND_DOUBLE, KIND_FLOAT, KIND_INT, KIND_LONG, KIND_SHORT -> true
else -> false
}
@@ -117,14 +89,6 @@ open class JavaType : ISharedJavaIndexable, ICloneable {
return name == CLASS.name
}
- override fun clone(): JavaType {
- return newInstance(name = name, kind = kind, arrayDims = arrayDims)
- }
-
- override fun computeId() {
- this.id = Objects.hashCode(this.kind, this.name, this.arrayDims)
- }
-
override fun equals(other: Any?): Boolean {
if (this === other) return true
if (other !is JavaType) return false
@@ -144,7 +108,7 @@ open class JavaType : ISharedJavaIndexable, ICloneable {
}
override fun toString(): String {
- return "JavaType(id=$id, name=$name, kind=$kind, arrayDims=$arrayDims)"
+ return "JavaType(name=$name, kind=$kind, arrayDims=$arrayDims)"
}
companion object {
@@ -160,14 +124,6 @@ open class JavaType : ISharedJavaIndexable, ICloneable {
const val KIND_VOID = 8
const val KIND_REF = 9
- // kind values used in IAnnotationElementValue
- // defined here for convenience
- internal const val __KIND_STRING = 10
- internal const val __KIND_CLASS = 11
- internal const val __KIND_ENUM = 12
- internal const val __KIND_ANNOTATION = 13
- internal const val __KIND_ARRAY = 14
-
const val TYPE_BOOLEAN = 'Z'
const val TYPE_BYTE = 'B'
const val TYPE_CHAR = 'C'
@@ -264,7 +220,6 @@ open class JavaType : ISharedJavaIndexable, ICloneable {
this.name = name
this.kind = kind
this.arrayDims = arrayDims
- this.computeId()
}
}
diff --git a/java/lsp/src/test/java/com/itsaky/androidide/lsp/java/indexing/AndroidJarModelingRule.kt b/java/lsp/src/test/java/com/itsaky/androidide/lsp/java/indexing/AndroidJarModelingRule.kt
deleted file mode 100644
index 3d4ae0dd2..000000000
--- a/java/lsp/src/test/java/com/itsaky/androidide/lsp/java/indexing/AndroidJarModelingRule.kt
+++ /dev/null
@@ -1,65 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing
-
-import com.google.common.truth.Truth.assertThat
-import com.itsaky.androidide.utils.FileProvider
-import org.junit.rules.TestRule
-import org.junit.runner.Description
-import org.junit.runners.model.Statement
-import java.io.File
-
-/**
- * @author Akash Yadav
- */
-class AndroidJarModelingRule : TestRule {
-
- private val androidJar: File by lazy {
- FileProvider.projectRoot()
- .resolve("utilities")
- .resolve("framework-stubs")
- .resolve("libs")
- .resolve("android.jar")
- .toFile().also {
- check(it.exists()) {
- "android.jar file could not be found"
- }
- }
- }
-
- private val androidJarIndexer: JavaJarModelBuilder by lazy {
- assertThat(androidJar.exists()).isTrue()
- JavaJarModelBuilder(androidJar)
- }
-
- val types: List> by lazy {
- androidJarIndexer.buildTypes()
- }
-
- override fun apply(base: Statement?, description: Description?): Statement {
-
- // call 'types' to build the type models
- types
-
- base?.evaluate()
-
- return object : Statement() {
- override fun evaluate() {}
- }
- }
-}
\ No newline at end of file
diff --git a/java/lsp/src/test/java/com/itsaky/androidide/lsp/java/indexing/DescriptorUtilsTest.kt b/java/lsp/src/test/java/com/itsaky/androidide/lsp/java/indexing/DescriptorUtilsTest.kt
deleted file mode 100644
index 55de3e392..000000000
--- a/java/lsp/src/test/java/com/itsaky/androidide/lsp/java/indexing/DescriptorUtilsTest.kt
+++ /dev/null
@@ -1,121 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing
-
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaType
-import com.itsaky.androidide.lsp.java.utils.DescriptorUtils
-import org.junit.Assert.assertEquals
-import org.junit.Test
-import org.junit.runner.RunWith
-import org.robolectric.RobolectricTestRunner
-
-/**
- * @author Akash Yadav
- */
-@RunWith(RobolectricTestRunner::class)
-class DescriptorUtilsTest {
-
- @Test
- fun testReturnType() {
- val descriptor1 = "(I)V"
- val expected1 = JavaType.newInstance(name = "V", kind = JavaType.KIND_VOID)
- assertEquals(expected1, DescriptorUtils.returnType(descriptor1))
-
- val descriptor2 = "(Ljava/lang/String;)I"
- val expected2 = JavaType.newInstance(name = "I", kind = JavaType.KIND_INT)
- assertEquals(expected2, DescriptorUtils.returnType(descriptor2))
-
- val descriptor3 = "(I[Ljava/lang/String;)V"
- val expected3 = JavaType.newInstance(name = "V", kind = JavaType.KIND_VOID)
- assertEquals(expected3, DescriptorUtils.returnType(descriptor3))
- }
-
- @Test(expected = IllegalArgumentException::class)
- fun testReturnTypeInvalidDescriptor() {
- DescriptorUtils.returnType("Ljava/lang/String;I")
- }
-
- @Test
- fun testParamTypes() {
- val descriptor1 = "(I)V"
- val expected1 = listOf(JavaType.newInstance(name = "I", kind = JavaType.KIND_INT))
- assertEquals(expected1, DescriptorUtils.paramTypes(descriptor1))
-
- val descriptor2 = "(Ljava/lang/String;I)V"
- val expected2 = listOf(
- JavaType.newInstance(name = "java/lang/String", kind = JavaType.KIND_REF),
- JavaType.newInstance(name = "I", kind = JavaType.KIND_INT)
- )
- assertEquals(expected2, DescriptorUtils.paramTypes(descriptor2))
-
- val descriptor3 = "([I[Ljava/lang/String;)V"
- val expected3 = listOf(
- JavaType.newInstance(name = "I", kind = JavaType.KIND_INT, arrayDims = 1),
- JavaType.newInstance(name = "java/lang/String", kind = JavaType.KIND_REF, arrayDims = 1)
- )
- assertEquals(expected3, DescriptorUtils.paramTypes(descriptor3))
- }
-
- @Test(expected = IllegalArgumentException::class)
- fun testParamTypesInvalidDescriptor() {
- DescriptorUtils.paramTypes("Ljava/lang/String;I")
- }
-
- @Test
- fun testPrimitive() {
- val booleanType = JavaType.newInstance(name = "Z", kind = JavaType.KIND_BOOLEAN)
- assertEquals(booleanType, DescriptorUtils.primitive('Z'))
-
- val intType = JavaType.newInstance(name = "I", kind = JavaType.KIND_INT)
- assertEquals(intType, DescriptorUtils.primitive('I'))
- }
-
- @Test(expected = IllegalArgumentException::class)
- fun testPrimitiveInvalidType() {
- DescriptorUtils.primitive('X')
- }
-
- @Test
- fun testReferenceType() {
- val descriptor = "Ljava/lang/String;"
- val expected = JavaType.newInstance(name = "java/lang/String", kind = JavaType.KIND_REF)
- assertEquals(expected, DescriptorUtils.referenceType(descriptor))
- }
-
- @Test(expected = IllegalArgumentException::class)
- fun testReferenceTypeInvalidDescriptor() {
- DescriptorUtils.referenceType("Ljava/lang/String")
- }
-
- @Test
- fun testArrayType() {
- val descriptor1 = "[I"
- val expected1 = JavaType.newInstance(name = "I", kind = JavaType.KIND_INT, arrayDims = 1)
- assertEquals(expected1, DescriptorUtils.arrayType(descriptor1))
-
- val descriptor2 = "[[Ljava/lang/String;"
- val expected2 =
- JavaType.newInstance(name = "java/lang/String", kind = JavaType.KIND_REF, arrayDims = 2)
- assertEquals(expected2, DescriptorUtils.arrayType(descriptor2))
- }
-
- @Test(expected = IllegalArgumentException::class)
- fun testArrayTypeInvalidDescriptor() {
- DescriptorUtils.arrayType("Ljava/lang/String;")
- }
-}
\ No newline at end of file
diff --git a/java/lsp/src/test/java/com/itsaky/androidide/lsp/java/indexing/JavaIndexWorkerTest.kt b/java/lsp/src/test/java/com/itsaky/androidide/lsp/java/indexing/JavaIndexWorkerTest.kt
deleted file mode 100644
index 8b770846a..000000000
--- a/java/lsp/src/test/java/com/itsaky/androidide/lsp/java/indexing/JavaIndexWorkerTest.kt
+++ /dev/null
@@ -1,524 +0,0 @@
-/*
- * This file is part of AndroidIDE.
- *
- * AndroidIDE is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * AndroidIDE is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with AndroidIDE. If not, see .
- */
-
-package com.itsaky.androidide.lsp.java.indexing
-
-import android.view.View
-import com.google.common.truth.Truth.assertThat
-import com.itsaky.androidide.lsp.java.indexing.classfile.AnnotationElement
-import com.itsaky.androidide.lsp.java.indexing.classfile.IAnnotationElementValue
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaAnnotation
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaClass
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaEnum
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaField
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaInterface
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaMethod
-import com.itsaky.androidide.lsp.java.indexing.classfile.JavaType
-import com.itsaky.androidide.lsp.java.indexing.classfile.PrimitiveAnnotationElementValue
-import io.realm.RealmAny
-import openjdk.tools.classfile.AccessFlags
-import org.junit.Rule
-import org.junit.Test
-import org.junit.runner.RunWith
-import org.robolectric.RobolectricTestRunner
-import java.lang.reflect.Modifier
-
-/**
- * @author Akash Yadav
- */
-@RunWith(RobolectricTestRunner::class)
-class JavaJarModelBuilderTest {
-
- @Rule
- @JvmField
- val indexRule = AndroidJarModelingRule()
-
- private val types: List>
- get() = indexRule.types
-
- @Test
- fun `test JavaClass properties`() {
- val sampleClass = types.firstOrNull { it.fqn == "java/lang/String" }
-
- assertThat(sampleClass).isNotNull()
- sampleClass?.let {
- assertThat(it.fqn).isEqualTo("java/lang/String")
- assertThat(it.name).isEqualTo("String")
- assertThat(it.packageName).isEqualTo("java/lang")
- assertThat(it.superClassFqn).isEqualTo("java/lang/Object")
- assertThat(it.superInterfacesFqn).containsAtLeast(
- "java/io/Serializable",
- "java/lang/Comparable",
- "java/lang/CharSequence"
- )
- }
- }
-
- @Test
- fun `test JavaField properties`() {
- val sampleClass = types.firstOrNull { it.fqn == "java/lang/String" }
- val fields = sampleClass?.fields
-
- assertThat(fields).isNotEmpty()
- fields?.forEach { f ->
- val field = f as JavaField
- assertThat(field.name).isNotEmpty()
- assertThat(field.accessFlags).isGreaterThan(0)
- assertThat(field.type).isNotNull()
- }
-
- // java.lang.String in Android only has a single public field
- assertThat(fields?.size).isEqualTo(1)
-
- val field = fields?.firstOrNull() as JavaField?
- assertThat(field).isNotNull()
- assertThat(field?.name).isEqualTo("CASE_INSENSITIVE_ORDER")
- assertThat(field?.type?.name).isEqualTo("java/util/Comparator")
- assertThat(field?.type?.internalForm()).isEqualTo("Ljava/util/Comparator;")
- assertThat(field?.type?.kind).isEqualTo(JavaType.KIND_REF)
- assertThat(Modifier.isPublic(field?.accessFlags ?: 0)).isTrue()
- assertThat(Modifier.isStatic(field?.accessFlags ?: 0)).isTrue()
- assertThat(Modifier.isFinal(field?.accessFlags ?: 0)).isTrue()
- }
-
- @Test
- fun `test JavaMethod properties`() {
- val sampleClass = types.firstOrNull { it.fqn == "java/lang/String" }
- val methods = sampleClass?.methods
-
- assertThat(methods).isNotEmpty()
- methods?.forEach { mth ->
- val method = mth as JavaMethod
- assertThat(method.name).isNotEmpty()
- assertThat(method.accessFlags).isGreaterThan(0)
- assertThat(method.paramsTypes).isNotNull()
- assertThat(method.returnType).isNotNull()
- }
-
- assertThat(methods?.size).isAtLeast(1)
-
- val method = (methods as List?)?.firstOrNull { it.name == "compareTo" }
- assertThat(method).isNotNull()
- assertThat(method?.name).isEqualTo("compareTo")
- assertThat(method?.paramsTypes?.size).isEqualTo(1)
- assertThat(method?.returnType?.name).isEqualTo("I")
- assertThat(Modifier.isPublic(method?.accessFlags ?: 0)).isTrue()
- assertThat(Modifier.isStatic(method?.accessFlags ?: 0)).isFalse()
- assertThat(Modifier.isFinal(method?.accessFlags ?: 0)).isFalse()
-
- val param = method?.paramsTypes?.firstOrNull()
- assertThat(param).isNotNull()
- assertThat(param?.name).isEqualTo("java/lang/String")
- assertThat(param?.internalForm()).isEqualTo("Ljava/lang/String;")
- assertThat(param?.kind).isEqualTo(JavaType.KIND_REF)
- assertThat(param?.arrayDims).isEqualTo(0)
- }
-
- @Test
- fun `test JavaType properties`() {
- val sampleClass = types.firstOrNull { it.fqn == "java/lang/String" }
- val fields = sampleClass?.fields
- val methods = sampleClass?.methods
-
- fields?.forEach { f ->
- val field = f as JavaField
- assertThat(field.type?.name).isNotEmpty()
- assertThat(field.type?.kind).isNotEqualTo(JavaType.KIND_UNKNOWN)
- }
-
- methods?.forEach { mth ->
- val method = mth as JavaMethod
- method.paramsTypes?.forEach { paramType ->
- assertThat(paramType.name).isNotEmpty()
- assertThat(paramType.kind).isNotEqualTo(JavaType.KIND_UNKNOWN)
- }
- assertThat(method.returnType?.name).isNotEmpty()
- assertThat(method.returnType?.kind).isNotEqualTo(JavaType.KIND_UNKNOWN)
- }
- }
-
- @Test
- fun `test integer constant field values`() {
- val viewClass: IJavaType =
- types.first { it.fqn == "android/view/View" } as IJavaType
- assertThat(viewClass.fields).isNotEmpty()
-
- val fields = viewClass.fields!!
- val visible = fields.firstOrNull { it.name == "VISIBLE" }
- assertThat(visible).isNotNull()
- assertThat(visible?.type).isEqualTo(JavaType.INT)
-
- val constantValue = visible?.constantValue
- assertThat(constantValue).isNotNull()
- assertThat(constantValue?.kind).isEqualTo(JavaType.KIND_INT)
- assertThat(constantValue?.value?.type).isEqualTo(RealmAny.Type.INTEGER)
- assertThat(constantValue?.asInt()).isNotNull()
- assertThat(constantValue?.asInt()).isEqualTo(View.VISIBLE)
- }
-
- @Test
- fun `test object type`() {
- val obj = types.firstOrNull { it.fqn == "java/lang/Object" }
- assertThat(obj).isNotNull()
- assertThat(obj?.name).isEqualTo("Object")
- assertThat(obj?.superClassFqn).isNull()
- assertThat(obj?.superInterfacesFqn).isEmpty()
- assertThat(obj?.fields).isEmpty()
- assertThat(obj?.methods).isNotEmpty()
- assertThat(obj?.isAnnotation).isFalse()
- assertThat(obj?.isInterface).isFalse()
- assertThat(obj?.isEnum).isFalse()
- assertThat(obj?.isClass).isTrue()
- assertThat(obj).isInstanceOf(JavaClass::class.java)
- assertThat(obj?.packageName).isEqualTo("java/lang")
-
- val access = AccessFlags(obj!!.accessFlags)
- assertThat(access.`is`(AccessFlags.ACC_PUBLIC)).isTrue()
- assertThat(access.`is`(AccessFlags.ACC_STATIC)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_INTERFACE)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_ANNOTATION)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_ENUM)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_ABSTRACT)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_FINAL)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_NATIVE)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_NATIVE)).isFalse()
- }
-
- @Test
- fun `test class simple name`() {
- val obj = types.firstOrNull { it.fqn == "android/view/View" }
- assertThat(obj).isNotNull()
- assertThat(obj?.name).isEqualTo("View")
- assertThat(obj?.packageName).isEqualTo("android/view")
- assertThat(obj?.superClassFqn).isEqualTo("java/lang/Object")
- assertThat(obj?.superInterfacesFqn).isNotEmpty()
- assertThat(obj?.fields).isNotEmpty()
- assertThat(obj?.methods).isNotEmpty()
- assertThat(obj?.isAnnotation).isFalse()
- assertThat(obj?.isInterface).isFalse()
- assertThat(obj?.isEnum).isFalse()
- assertThat(obj?.isClass).isTrue()
- assertThat(obj).isInstanceOf(JavaClass::class.java)
-
- val access = AccessFlags(obj!!.accessFlags)
- assertThat(access.`is`(AccessFlags.ACC_PUBLIC)).isTrue()
- assertThat(access.`is`(AccessFlags.ACC_STATIC)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_INTERFACE)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_ANNOTATION)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_ENUM)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_ABSTRACT)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_FINAL)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_NATIVE)).isFalse()
- assertThat(access.`is`(AccessFlags.ACC_NATIVE)).isFalse()
- }
-
- @Test
- fun `test class superclass name`() {
- types.firstOrNull { it.fqn == "android/view/View" }.also {
- assertThat(it).isNotNull()
- assertThat(it?.superClassFqn).isEqualTo("java/lang/Object")
- }
- }
-
- @Test
- fun `test class super interface names`() {
- types.firstOrNull { it.fqn == "android/view/View" }.also {
- assertThat(it).isNotNull()
- assertThat(it?.superInterfacesFqn).containsExactly(
- "android/graphics/drawable/Drawable\$Callback",
- "android/view/KeyEvent\$Callback",
- "android/view/accessibility/AccessibilityEventSource"
- )
- }
- }
-
- @Test
- fun `test interface super interface names`() {
- types.firstOrNull { it.fqn == "java/io/Closeable" }.also {
- assertThat(it).isNotNull()
- assertThat(it?.superInterfacesFqn).containsExactly("java/lang/AutoCloseable")
- }
- }
-
- @Test
- fun `test class fields`() {
- types.firstOrNull { it.fqn == "android/view/View" }.also { view ->
- assertThat(view).isNotNull()
- assertThat(view?.fields?.map { field -> (field as JavaField).name }).containsAtLeast(
- "VISIBLE",
- "INVISIBLE",
- "GONE",
- "FOCUS_DOWN",
- "FOCUS_UP",
- "FOCUS_LEFT",
- "FOCUS_RIGHT",
- "FOCUS_BACKWARD",
- "FOCUS_FORWARD",
- )
- }
-
- types.firstOrNull { it.fqn == "android/view/ViewGroup\$LayoutParams" }.also { view ->
- assertThat(view).isNotNull()
- assertThat(view?.fields?.map { field -> (field as JavaField).name }).containsAtLeast(
- "WRAP_CONTENT",
- "MATCH_PARENT",
- "FILL_PARENT",
- )
- }
- }
-
- @Test
- fun `test interface fields`() {
- types.firstOrNull { it.fqn == "android/provider/CalendarContract\$CalendarSyncColumns" }
- .also { view ->
- assertThat(view).isNotNull()
- assertThat(view?.fields?.map { field -> (field as JavaField).name }).containsAtLeast(
- "CAL_SYNC1",
- "CAL_SYNC2",
- "CAL_SYNC3",
- "CAL_SYNC4",
- "CAL_SYNC5",
- "CAL_SYNC6",
- "CAL_SYNC7",
- "CAL_SYNC8",
- "CAL_SYNC9",
- "CAL_SYNC10",
- )
- }
- }
-
- @Test
- fun `test mandatory enum fields`() {
- types.filterIsInstance().forEach { enum ->
- assertThat(enum.fields?.map { it.name }).contains("\$VALUES")
- }
- }
-
- @Test
- fun `test enum fields`() {
- types.firstOrNull { it.fqn == "android/net/wifi/SupplicantState" }.also { enum ->
- assertThat(enum?.fields?.map { (it as JavaField).name })
- .containsAtLeast(
- "DISCONNECTED",
- "INTERFACE_DISABLED",
- "INACTIVE",
- "SCANNING",
- "AUTHENTICATING",
- "ASSOCIATING",
- "ASSOCIATED",
- "FOUR_WAY_HANDSHAKE",
- "COMPLETED",
- "GROUP_HANDSHAKE",
- "DORMANT",
- "UNINITIALIZED",
- "INVALID"
- )
- }
- }
-
- @Test
- fun `test annotation fields`() {
- // android.jar doesn't seem to contain annotation classes with some fields
- // TODO: add test for verifying how annotation fields are handled
- }
-
- @Test
- fun `test class methods`() {
- types.firstOrNull { it.fqn == "android/view/View" }.also { view ->
- assertThat(view).isNotNull()
- assertThat(view?.methods?.map { field -> (field as JavaMethod).signature() }).containsAtLeast(
- "setId(I)V",
- "getId()I",
- "setOnClickListener(Landroid/view/View\$OnClickListener;)V",
- "hasOnClickListeners()Z",
- "hasOnLongClickListeners()Z",
- "setAccessibilityDelegate(Landroid/view/View\$AccessibilityDelegate;)V",
- "getAccessibilityDelegate()Landroid/view/View\$AccessibilityDelegate;",
- "setAccessibilityLiveRegion(I)V",
- "getAccessibilityLiveRegion()I",
- "setAccessibilityHeading(Z)V",
- "isAccessibilityHeading()Z",
- "setPadding(IIII)V",
- "setPaddingRelative(IIII)V",
- )
- }
- }
-
- @Test
- fun `test interface methods`() {
- types.firstOrNull { it.fqn == "android/view/View\$OnClickListener" }.also { view ->
- assertThat(view).isNotNull()
- assertThat(view?.methods?.map { field -> (field as JavaMethod).signature() })
- .contains("onClick(Landroid/view/View;)V")
- }
- types.firstOrNull { it.fqn == "android/view/View\$OnLongClickListener" }.also { view ->
- assertThat(view).isNotNull()
- assertThat(view?.methods?.map { field -> (field as JavaMethod).signature() })
- .containsAtLeast(
- "onLongClick(Landroid/view/View;)Z",
- "onLongClickUseDefaultHapticFeedback(Landroid/view/View;)Z"
- )
- }
- }
-
- @Test
- fun `test mandatory enum methods`() {
- types.filterIsInstance().forEach { enum ->
- assertThat(enum.methods?.map { it.signature() }).containsAtLeast(
- "values()[L${enum.fqn};",
- "\$values()[L${enum.fqn};",
- "valueOf(Ljava/lang/String;)L${enum.fqn};",
- "()V"
- )
- }
- }
-
- @Test
- fun `test enum methods`() {
- types.firstOrNull { it.fqn == "android/icu/text/DisplayContext" }.also { enum ->
- assertThat(enum?.methods?.map { (it as JavaMethod).signature() }).contains(
- "type()Landroid/icu/text/DisplayContext\$Type;"
- )
- }
- }
-
- @Test
- fun `test annotation methods`() {
- types.firstOrNull { it.fqn == "android/annotation/TargetApi" }.also { annotation ->
- assertThat(annotation?.methods?.map { (it as AnnotationElement).signature() }).containsExactly(
- "value()I"
- )
- }
- }
-
- @Test
- fun `test annotation methods with default values`() {
- types.firstOrNull { it.fqn == "java/lang/Deprecated" }.also { annotation ->
- assertThat(annotation?.methods).isNotEmpty()
-
- val since =
- annotation?.methods?.find { (it as AnnotationElement).name == "since" } as AnnotationElement
- assertThat(since.type).isEqualTo(JavaType.STRING)
-
- var defValue = since.defaultValue
- assertThat(defValue).isNotNull()
- assertThat(defValue?.valueClass).isEqualTo(PrimitiveAnnotationElementValue::class.java)
-
- var defVal = defValue?.asRealmModel(PrimitiveAnnotationElementValue::class.java)
- assertThat(defVal).isNotNull()
- assertThat(defVal?.kind).isEqualTo(IAnnotationElementValue.KIND_STRING)
- assertThat(defVal?.value).isNotNull()
- assertThat(defVal?.value?.kind).isEqualTo(JavaType.KIND_REF)
- assertThat(defVal?.value?.asString()).isEqualTo("")
- assertThat(defVal?.value?.asBoolean()).isNull()
- assertThat(defVal?.value?.asByte()).isNull()
- assertThat(defVal?.value?.asShort()).isNull()
- assertThat(defVal?.value?.asChar()).isNull()
- assertThat(defVal?.value?.asInt()).isNull()
- assertThat(defVal?.value?.asLong()).isNull()
- assertThat(defVal?.value?.asFloat()).isNull()
- assertThat(defVal?.value?.asDouble()).isNull()
-
- val forRemoval =
- annotation.methods?.find { (it as AnnotationElement).name == "forRemoval" } as AnnotationElement
- assertThat(forRemoval.type).isEqualTo(JavaType.BOOLEAN)
-
- defValue = forRemoval.defaultValue
- assertThat(defValue).isNotNull()
- assertThat(defValue?.valueClass).isEqualTo(PrimitiveAnnotationElementValue::class.java)
-
- defVal = defValue?.asRealmModel(PrimitiveAnnotationElementValue::class.java)
- assertThat(defVal).isNotNull()
- assertThat(defVal?.kind).isEqualTo(IAnnotationElementValue.KIND_BOOLEAN)
- assertThat(defVal?.value).isNotNull()
- assertThat(defVal?.value?.kind).isEqualTo(JavaType.KIND_BOOLEAN)
- assertThat(defVal?.value?.asBoolean()).isEqualTo(false)
- assertThat(defVal?.value?.asByte()).isNull()
- assertThat(defVal?.value?.asShort()).isNull()
- assertThat(defVal?.value?.asChar()).isNull()
- assertThat(defVal?.value?.asInt()).isNull()
- assertThat(defVal?.value?.asLong()).isNull()
- assertThat(defVal?.value?.asFloat()).isNull()
- assertThat(defVal?.value?.asDouble()).isNull()
- assertThat(defVal?.value?.asString()).isNull()
- }
- }
-
- @Test
- fun `test annotation methods with array value`() {
- types.firstOrNull { it.fqn == "java/lang/SuppressWarnings" }.also { annotation ->
- assertThat(annotation?.methods).isNotEmpty()
-
- val value =
- annotation?.methods?.find { (it as AnnotationElement).name == "value" } as AnnotationElement
- assertThat(value.type?.kind).isEqualTo(JavaType.KIND_REF)
- assertThat(value.type?.name).isEqualTo("java/lang/String")
- assertThat(value.type?.arrayDims).isEqualTo(1)
-
- val defValue = value.defaultValue
- assertThat(defValue).isNull()
- }
- }
-
- @Test
- fun `test class type classification`() {
- types.firstOrNull { it.fqn == "android/view/View" }.also {
- assertThat(it).isNotNull()
- assertThat(it?.isClass).isTrue()
- assertThat(it?.isInterface).isFalse()
- assertThat(it?.isAnnotation).isFalse()
- assertThat(it?.isEnum).isFalse()
- assertThat(it).isInstanceOf(JavaClass::class.java)
- }
- }
-
- @Test
- fun `test interface type classification`() {
- types.firstOrNull { it.fqn == "android/view/View\$OnClickListener" }.also {
- assertThat(it).isNotNull()
- assertThat(it?.isClass).isFalse()
- assertThat(it?.isInterface).isTrue()
- assertThat(it?.isAnnotation).isFalse()
- assertThat(it?.isEnum).isFalse()
- assertThat(it).isInstanceOf(JavaInterface::class.java)
- }
- }
-
- @Test
- fun `test annotation type classification`() {
- types.firstOrNull { it.fqn == "java/lang/Deprecated" }.also {
- assertThat(it).isNotNull()
- assertThat(it?.isClass).isFalse()
- assertThat(it?.isInterface).isTrue()
- assertThat(it?.isAnnotation).isTrue()
- assertThat(it?.isEnum).isFalse()
- assertThat(it).isInstanceOf(JavaAnnotation::class.java)
- }
- }
-
- @Test
- fun `test enum type classification`() {
- types.firstOrNull { it.fqn == "android/icu/text/DisplayContext" }.also {
- assertThat(it).isNotNull()
- assertThat(it?.isClass).isFalse()
- assertThat(it?.isInterface).isFalse()
- assertThat(it?.isAnnotation).isFalse()
- assertThat(it?.isEnum).isTrue()
- assertThat(it).isInstanceOf(JavaEnum::class.java)
- }
- }
-}
diff --git a/settings.gradle.kts b/settings.gradle.kts
index 798ed9681..752cb21bd 100644
--- a/settings.gradle.kts
+++ b/settings.gradle.kts
@@ -126,7 +126,6 @@ include(
":core:actions",
":core:app",
":core:common",
- ":core:database",
":core:indexing-api",
":core:indexing-core",
":core:lsp-api",
diff --git a/testing/androidTest/build.gradle.kts b/testing/androidTest/build.gradle.kts
index bbada5339..b3b9b776f 100644
--- a/testing/androidTest/build.gradle.kts
+++ b/testing/androidTest/build.gradle.kts
@@ -42,11 +42,6 @@ configurations.api {
dependencies {
- // compileOnly so that we can provide the APIs for the related test rules
- // if a module needs to use those APIs, it needs to explicitly add the database module as a
- // dependency
- compileOnly(projects.core.database)
-
api(libs.google.protobuf)
api(libs.tests.androidx.espresso.core)
api(libs.tests.androidx.espresso.contrib)
diff --git a/testing/benchmarks/build.gradle.kts b/testing/benchmarks/build.gradle.kts
index 723f4947b..c5ad72998 100644
--- a/testing/benchmarks/build.gradle.kts
+++ b/testing/benchmarks/build.gradle.kts
@@ -66,7 +66,6 @@ dependencies {
androidTestImplementation(libs.androidx.benchmark.junit4)
androidTestImplementation(projects.core.common)
- androidTestImplementation(projects.core.database)
androidTestImplementation(projects.core.indexingApi)
androidTestImplementation(projects.java.lsp)
androidTestImplementation(projects.utilities.shared)