Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: android target #2

Merged
merged 3 commits into from
Feb 17, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
19 changes: 19 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,8 @@ On Mac OS X : ```/Users/<Account>/Library/Application Support/<AppName>```
On Windows XP : ```C:\Documents and Settings\<Account>\Application Data\Local Settings\<AppAuthor>\<AppName>```
On Windows 7 : ```C:\Users\<Account>\AppData\<AppAuthor>\<AppName>```
On Unix/Linux : ```/home/<account>/.local/share/<AppName>```
On Android (internal) : ```/data/user/<uid>/<packageName>```
On Android (external) : ```/storage/emulated/<storageId>/Android/data/<packageName>```

With __Kotlin Multiplatform AppDirs__, you can get the path depending on the runtime platform with the following code.

Expand Down Expand Up @@ -130,6 +132,23 @@ Shared dir: /srv/myapp/1.2.3
- _appAuthor_ parameter is not used on Unix/Linux.
- _roaming_ parameter has no effect on Unix/Linux.

### Output on Android (packageName = ca.gosyer.appdirsm, uid = 0)
```
User data dir: /data/user/0/ca.gosyer.appdirsm/app_data/1.2.3
User data dir (roaming): /data/user/0/ca.gosyer.appdirsm/app_data/1.2.3
User config dir: /data/user/0/ca.gosyer.appdirsm/app_config/1.2.3
User config dir (roaming): /data/user/0/ca.gosyer.appdirsm/app_config/1.2.3
User cache dir: /data/user/0/ca.gosyer.appdirsm/cache/1.2.3
User log dir: /data/user/0/ca.gosyer.appdirsm/app_logs/1.2.3
Site data dir: /storage/emulated/0/Android/data/ca.gosyer.appdirsm/files/data/1.2.3
Site data dir (multi path): /storage/emulated/0/Android/data/ca.gosyer.appdirsm/files/data/1.2.3
Site config dir: /storage/emulated/0/Android/data/ca.gosyer.appdirsm/files/config/1.2.3
Site config dir (multi path): /storage/emulated/0/Android/data/ca.gosyer.appdirsm/files/config/1.2.3
Shared dir: /storage/emulated/0/Android/data/ca.gosyer.appdirsm/files/shared/1.2.3
```

- __AppDirs__ respects [Scoped storage](https://source.android.com/docs/core/storage/scoped) and only accesses the application private directory.

## Bug report, feature request, question

Please create an issue on the [tracker](https://github.com/Syer10/Kotlin-Multiplatform-AppDirs/issues).
Expand Down
38 changes: 33 additions & 5 deletions build.gradle.kts
Original file line number Diff line number Diff line change
Expand Up @@ -3,15 +3,12 @@ import java.util.Properties
plugins {
kotlin("multiplatform") version "1.9.21"
id("com.vanniktech.maven.publish") version "0.25.1"
id("com.android.library") version "8.2.1"
}

group = "ca.gosyer"
version = "1.1.0"

repositories {
mavenCentral()
}

kotlin {
jvm {
compilations.all {
Expand All @@ -28,6 +25,14 @@ kotlin {
linuxArm64()
mingwX64()

androidTarget {
publishLibraryVariants("release")
Copy link
Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

By the way, the reason for adding this line is a bug from gradle-maven-publish-plugin


compilations.all {
kotlinOptions.jvmTarget = "1.8"
}
}

@OptIn(org.jetbrains.kotlin.gradle.ExperimentalKotlinGradlePluginApi::class)
applyHierarchyTemplate {
common {
Expand Down Expand Up @@ -129,6 +134,18 @@ kotlin {
dependsOn(nativeTest)
dependsOn(windowsTest)
}

// android
val androidMain by getting {
dependsOn(commonMain)
}
val androidInstrumentedTest by getting {
dependencies {
implementation("androidx.test.ext:junit-ktx:1.1.5")
implementation("androidx.test.espresso:espresso-core:3.5.1")
implementation("androidx.test:runner:1.5.2")
}
}
}
}

Expand All @@ -149,4 +166,15 @@ if (signingPropsFile.exists()) {
project.ext.set(key, value)
}
}
}
}

android {
namespace = "ca.gosyer"

sourceSets["main"].manifest.srcFile("src/androidMain/AndroidManifest.xml")

defaultConfig {
compileSdk = 34
minSdk = 21
}
}
3 changes: 3 additions & 0 deletions gradle.properties
Original file line number Diff line number Diff line change
Expand Up @@ -29,3 +29,6 @@ SONATYPE_HOST=S01
RELEASE_SIGNING_ENABLED=true

kotlin.native.cacheKind.macosArm64=none

android.useAndroidX=true
android.enableJetifier=true
16 changes: 15 additions & 1 deletion settings.gradle.kts
Original file line number Diff line number Diff line change
@@ -1,2 +1,16 @@
rootProject.name = "Kotlin-Multiplatform-AppDirs"
dependencyResolutionManagement {
repositories {
mavenCentral()
google()
}
}

pluginManagement {
repositories {
mavenCentral()
google()
gradlePluginPortal()
}
}

rootProject.name = "Kotlin-Multiplatform-AppDirs"
13 changes: 13 additions & 0 deletions src/androidMain/kotlin/ca/gosyer/appdirs/AppDirs.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
package ca.gosyer.appdirs

import ca.gosyer.appdirs.impl.AndroidAppDirs
import ca.gosyer.appdirs.impl.ContextRef

actual fun AppDirs(
appName: String?,
appAuthor: String?,
vararg extra: String
): AppDirs = AndroidAppDirs(
context = ContextRef,
extra = extra,
)
44 changes: 44 additions & 0 deletions src/androidMain/kotlin/ca/gosyer/appdirs/impl/AndroidAppDirs.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
package ca.gosyer.appdirs.impl

import android.content.Context
import ca.gosyer.appdirs.AppDirs
import java.io.File

class AndroidAppDirs(
private val context: Context,
vararg extra: String,
): AppDirs {
private val extras = extra.joinToString(pathSeparator())

override fun getUserDataDir(roaming: Boolean): String {
return getUserDir("data")
}

override fun getUserCacheDir(): String {
return File(context.cacheDir, extras).canonicalPath
}

override fun getUserConfigDir(roaming: Boolean): String {
return getUserDir("config")
}

override fun getUserLogDir(): String {
return getUserDir("logs")
}

private fun getUserDir(type: String, mode: Int = Context.MODE_PRIVATE): String {
return File(context.getDir(type, mode), extras).canonicalPath
}

override fun getSiteDataDir(multiPath: Boolean): String {
return context.getExternalFilesDir("data")!!.canonicalPath
}

override fun getSiteConfigDir(multiPath: Boolean): String {
return context.getExternalFilesDir("config")!!.canonicalPath
}

override fun getSharedDir(): String {
return context.getExternalFilesDir("shared")!!.canonicalPath
}
}
23 changes: 23 additions & 0 deletions src/androidMain/kotlin/ca/gosyer/appdirs/impl/AndroidUtil.kt
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
package ca.gosyer.appdirs.impl

import android.app.Application
import android.content.Context
import ca.gosyer.appdirs.AppDirsException
import java.lang.ref.WeakReference

internal actual fun home(): String {
throw UnsupportedOperationException()
}

internal actual fun pathSeparator(): String = "/"

internal actual fun fileSeparator(): String = ":"

private var _Context: WeakReference<Context>? = null
internal val ContextRef: Context get() {
return _Context?.get() ?: throw AppDirsException("In android target, please call Application#attachAppDirs() first!")
}

fun Application.attachAppDirs() {
_Context = WeakReference(this)
}
Loading