Merge branch 'master' into artUpdate
This commit is contained in:
commit
b5daad6aa4
|
@ -245,12 +245,6 @@
|
||||||
license: The Apache Software License, Version 2.0
|
license: The Apache Software License, Version 2.0
|
||||||
licenseUrl: http://www.apache.org/licenses/LICENSE-2.0.txt
|
licenseUrl: http://www.apache.org/licenses/LICENSE-2.0.txt
|
||||||
url: https://developer.android.com/jetpack/androidx
|
url: https://developer.android.com/jetpack/androidx
|
||||||
- artifact: com.github.bumptech.glide:okhttp-integration:+
|
|
||||||
name: okhttp-integration
|
|
||||||
copyrightHolder: Google Inc.
|
|
||||||
license: Simplified BSD License
|
|
||||||
licenseUrl: http://www.opensource.org/licenses/bsd-license
|
|
||||||
url: https://github.com/bumptech/glide
|
|
||||||
- artifact: com.github.bumptech.glide:glide:+
|
- artifact: com.github.bumptech.glide:glide:+
|
||||||
name: glide
|
name: glide
|
||||||
copyrightHolder: Google Inc.
|
copyrightHolder: Google Inc.
|
||||||
|
@ -687,10 +681,6 @@
|
||||||
license: The Apache Software License, Version 2.0
|
license: The Apache Software License, Version 2.0
|
||||||
licenseUrl: https://www.apache.org/licenses/LICENSE-2.0.txt
|
licenseUrl: https://www.apache.org/licenses/LICENSE-2.0.txt
|
||||||
url: https://github.com/Kotlin/kotlinx.coroutines
|
url: https://github.com/Kotlin/kotlinx.coroutines
|
||||||
- artifact: com.squareup.okhttp:okhttp:+
|
|
||||||
name: okhttp
|
|
||||||
copyrightHolder: Square, Inc.
|
|
||||||
license: The Apache Software License, Version 2.0
|
|
||||||
- artifact: com.squareup.okio:okio:+
|
- artifact: com.squareup.okio:okio:+
|
||||||
name: okio
|
name: okio
|
||||||
copyrightHolder: Square, Inc.
|
copyrightHolder: Square, Inc.
|
||||||
|
@ -973,3 +963,9 @@
|
||||||
license: The 3-Clause BSD License
|
license: The 3-Clause BSD License
|
||||||
licenseUrl: https://opensource.org/licenses/BSD-3-Clause
|
licenseUrl: https://opensource.org/licenses/BSD-3-Clause
|
||||||
url: https://github.com/tanersener/smart-exception
|
url: https://github.com/tanersener/smart-exception
|
||||||
|
- artifact: com.github.bumptech.glide:okhttp3-integration:+
|
||||||
|
name: okhttp3-integration
|
||||||
|
copyrightHolder: Google Inc.
|
||||||
|
license: Simplified BSD License
|
||||||
|
licenseUrl: http://www.opensource.org/licenses/bsd-license
|
||||||
|
url: https://github.com/bumptech/glide
|
||||||
|
|
|
@ -27,8 +27,14 @@ import androidx.recyclerview.widget.LinearLayoutManager
|
||||||
import androidx.recyclerview.widget.RecyclerView
|
import androidx.recyclerview.widget.RecyclerView
|
||||||
import com.arthenica.ffmpegkit.FFmpegKitConfig
|
import com.arthenica.ffmpegkit.FFmpegKitConfig
|
||||||
import com.google.android.material.color.MaterialColors
|
import com.google.android.material.color.MaterialColors
|
||||||
|
import com.google.gson.JsonDeserializer
|
||||||
|
import com.google.gson.JsonElement
|
||||||
|
import com.google.gson.JsonPrimitive
|
||||||
|
import com.google.gson.JsonSerializer
|
||||||
import okhttp3.HttpUrl
|
import okhttp3.HttpUrl
|
||||||
import org.pixeldroid.app.R
|
import org.pixeldroid.app.R
|
||||||
|
import java.time.Instant
|
||||||
|
import java.time.format.DateTimeFormatter
|
||||||
import java.util.*
|
import java.util.*
|
||||||
import kotlin.properties.ReadWriteProperty
|
import kotlin.properties.ReadWriteProperty
|
||||||
import kotlin.reflect.KProperty
|
import kotlin.reflect.KProperty
|
||||||
|
@ -227,6 +233,17 @@ fun Context.themeActionBar(): Int {
|
||||||
@ColorInt
|
@ColorInt
|
||||||
fun Context.getColorFromAttr(@AttrRes attrColor: Int): Int = MaterialColors.getColor(this, attrColor, Color.BLACK)
|
fun Context.getColorFromAttr(@AttrRes attrColor: Int): Int = MaterialColors.getColor(this, attrColor, Color.BLACK)
|
||||||
|
|
||||||
|
|
||||||
|
val typeAdapterInstantDeserializer: JsonDeserializer<Instant> = JsonDeserializer { json: JsonElement, _, _ ->
|
||||||
|
DateTimeFormatter.ISO_OFFSET_DATE_TIME.parse(
|
||||||
|
json.asString, Instant::from
|
||||||
|
)
|
||||||
|
}
|
||||||
|
|
||||||
|
val typeAdapterInstantSerializer: JsonSerializer<Instant> = JsonSerializer { src: Instant, _, _ ->
|
||||||
|
JsonPrimitive(DateTimeFormatter.ISO_INSTANT.format(src))
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Delegated property to use in fragments to prevent memory leaks of bindings.
|
* Delegated property to use in fragments to prevent memory leaks of bindings.
|
||||||
* This makes it unnecessary to set binding to null in onDestroyView.
|
* This makes it unnecessary to set binding to null in onDestroyView.
|
||||||
|
|
|
@ -11,6 +11,8 @@ import org.pixeldroid.app.utils.db.AppDatabase
|
||||||
import org.pixeldroid.app.utils.db.entities.UserDatabaseEntity
|
import org.pixeldroid.app.utils.db.entities.UserDatabaseEntity
|
||||||
import org.pixeldroid.app.utils.di.PixelfedAPIHolder
|
import org.pixeldroid.app.utils.di.PixelfedAPIHolder
|
||||||
import org.pixeldroid.app.utils.di.TokenAuthenticator
|
import org.pixeldroid.app.utils.di.TokenAuthenticator
|
||||||
|
import org.pixeldroid.app.utils.typeAdapterInstantDeserializer
|
||||||
|
import org.pixeldroid.app.utils.typeAdapterInstantSerializer
|
||||||
import retrofit2.Response
|
import retrofit2.Response
|
||||||
import retrofit2.Retrofit
|
import retrofit2.Retrofit
|
||||||
import retrofit2.adapter.rxjava3.RxJava3CallAdapterFactory
|
import retrofit2.adapter.rxjava3.RxJava3CallAdapterFactory
|
||||||
|
@ -40,42 +42,31 @@ interface PixelfedAPI {
|
||||||
}
|
}
|
||||||
|
|
||||||
fun createFromUrl(baseUrl: String): PixelfedAPI {
|
fun createFromUrl(baseUrl: String): PixelfedAPI {
|
||||||
return Retrofit.Builder().client(
|
return Retrofit.Builder()
|
||||||
|
.baseUrl(baseUrl)
|
||||||
|
.addConverterFactory(GsonConverterFactory.create(gSonInstance))
|
||||||
|
.addCallAdapterFactory(RxJava3CallAdapterFactory.create())
|
||||||
|
.client(
|
||||||
OkHttpClient().newBuilder().addNetworkInterceptor(headerInterceptor)
|
OkHttpClient().newBuilder().addNetworkInterceptor(headerInterceptor)
|
||||||
// Only do secure-ish TLS connections (no HTTP or very old SSL/TLS)
|
// Only do secure-ish TLS connections (no HTTP or very old SSL/TLS)
|
||||||
.connectionSpecs(listOf(ConnectionSpec.MODERN_TLS)).build()
|
.connectionSpecs(listOf(ConnectionSpec.MODERN_TLS)).build()
|
||||||
)
|
)
|
||||||
.baseUrl(baseUrl)
|
|
||||||
.addConverterFactory(GsonConverterFactory.create(gSonInstance))
|
|
||||||
.addCallAdapterFactory(RxJava3CallAdapterFactory.create())
|
|
||||||
.build().create(PixelfedAPI::class.java)
|
.build().create(PixelfedAPI::class.java)
|
||||||
}
|
}
|
||||||
|
|
||||||
private var gSonInstance: Gson = GsonBuilder()
|
private val gSonInstance: Gson = GsonBuilder()
|
||||||
.registerTypeAdapter(
|
.registerTypeAdapter(Instant::class.java, typeAdapterInstantDeserializer)
|
||||||
Instant::class.java,
|
.registerTypeAdapter(Instant::class.java, typeAdapterInstantSerializer)
|
||||||
JsonDeserializer { json: JsonElement, _, _ ->
|
|
||||||
DateTimeFormatter.ISO_OFFSET_DATE_TIME.parse(
|
|
||||||
json.asString, Instant::from
|
|
||||||
)
|
|
||||||
} as JsonDeserializer<Instant>).registerTypeAdapter(
|
|
||||||
Instant::class.java,
|
|
||||||
JsonSerializer { src: Instant, _, _ ->
|
|
||||||
JsonPrimitive(DateTimeFormatter.ISO_INSTANT.format(src))
|
|
||||||
})
|
|
||||||
.create()
|
.create()
|
||||||
|
|
||||||
private val intermediate: Retrofit.Builder = Retrofit.Builder()
|
|
||||||
.addConverterFactory(GsonConverterFactory.create(gSonInstance))
|
|
||||||
.addCallAdapterFactory(RxJava3CallAdapterFactory.create())
|
|
||||||
|
|
||||||
|
|
||||||
fun apiForUser(
|
fun apiForUser(
|
||||||
user: UserDatabaseEntity,
|
user: UserDatabaseEntity,
|
||||||
db: AppDatabase,
|
db: AppDatabase,
|
||||||
pixelfedAPIHolder: PixelfedAPIHolder
|
pixelfedAPIHolder: PixelfedAPIHolder
|
||||||
): PixelfedAPI =
|
): PixelfedAPI =
|
||||||
intermediate
|
Retrofit.Builder()
|
||||||
|
.addConverterFactory(GsonConverterFactory.create(gSonInstance))
|
||||||
|
.addCallAdapterFactory(RxJava3CallAdapterFactory.create())
|
||||||
.baseUrl(user.instance_uri)
|
.baseUrl(user.instance_uri)
|
||||||
.client(
|
.client(
|
||||||
OkHttpClient().newBuilder().addNetworkInterceptor(headerInterceptor)
|
OkHttpClient().newBuilder().addNetworkInterceptor(headerInterceptor)
|
||||||
|
|
|
@ -229,4 +229,10 @@
|
||||||
<string name="color_choice_button">选择这个强调色</string>
|
<string name="color_choice_button">选择这个强调色</string>
|
||||||
<string name="color_chosen">已选择强调色</string>
|
<string name="color_chosen">已选择强调色</string>
|
||||||
<string name="accentColorTitle">强调色</string>
|
<string name="accentColorTitle">强调色</string>
|
||||||
|
<string name="error_editing">编辑时出错</string>
|
||||||
|
<string name="profile_error">无法加载个人资料</string>
|
||||||
|
<string name="from_other_domain">来自 %1$s</string>
|
||||||
|
<string name="add_images_error">添加图片时出错</string>
|
||||||
|
<string name="notification_thumbnail">此通知帖文中图片的缩略图</string>
|
||||||
|
<string name="post_preview">帖文预览</string>
|
||||||
</resources>
|
</resources>
|
|
@ -2,13 +2,26 @@ package org.pixeldroid.app
|
||||||
|
|
||||||
import com.github.tomakehurst.wiremock.client.WireMock.*
|
import com.github.tomakehurst.wiremock.client.WireMock.*
|
||||||
import com.github.tomakehurst.wiremock.junit.WireMockRule
|
import com.github.tomakehurst.wiremock.junit.WireMockRule
|
||||||
|
import com.google.gson.GsonBuilder
|
||||||
|
import com.google.gson.JsonDeserializer
|
||||||
|
import com.google.gson.JsonElement
|
||||||
|
import com.google.gson.JsonPrimitive
|
||||||
|
import com.google.gson.JsonSerializer
|
||||||
import org.pixeldroid.app.utils.api.PixelfedAPI
|
import org.pixeldroid.app.utils.api.PixelfedAPI
|
||||||
import org.pixeldroid.app.utils.api.objects.*
|
import org.pixeldroid.app.utils.api.objects.*
|
||||||
import kotlinx.coroutines.runBlocking
|
import kotlinx.coroutines.runBlocking
|
||||||
|
import okhttp3.ConnectionSpec
|
||||||
|
import okhttp3.OkHttpClient
|
||||||
import org.junit.Assert.assertEquals
|
import org.junit.Assert.assertEquals
|
||||||
import org.junit.Rule
|
import org.junit.Rule
|
||||||
import org.junit.Test
|
import org.junit.Test
|
||||||
|
import org.pixeldroid.app.utils.typeAdapterInstantDeserializer
|
||||||
|
import org.pixeldroid.app.utils.typeAdapterInstantSerializer
|
||||||
|
import retrofit2.Retrofit
|
||||||
|
import retrofit2.adapter.rxjava3.RxJava3CallAdapterFactory
|
||||||
|
import retrofit2.converter.gson.GsonConverterFactory
|
||||||
import java.time.Instant
|
import java.time.Instant
|
||||||
|
import java.time.format.DateTimeFormatter
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -20,6 +33,23 @@ class APIUnitTest {
|
||||||
@get:Rule
|
@get:Rule
|
||||||
var wireMockRule = WireMockRule(8089)
|
var wireMockRule = WireMockRule(8089)
|
||||||
|
|
||||||
|
|
||||||
|
// Same as in PixelfedAPI but allow cleartext
|
||||||
|
private val api: PixelfedAPI = Retrofit.Builder()
|
||||||
|
.baseUrl("http://localhost:8089")
|
||||||
|
.addConverterFactory(GsonConverterFactory.create(GsonBuilder()
|
||||||
|
.registerTypeAdapter(Instant::class.java, typeAdapterInstantDeserializer)
|
||||||
|
.registerTypeAdapter(Instant::class.java, typeAdapterInstantSerializer)
|
||||||
|
.create())
|
||||||
|
)
|
||||||
|
.addCallAdapterFactory(RxJava3CallAdapterFactory.create())
|
||||||
|
.client(
|
||||||
|
OkHttpClient().newBuilder().addNetworkInterceptor(PixelfedAPI.headerInterceptor)
|
||||||
|
// Allow cleartext
|
||||||
|
.connectionSpecs(listOf(ConnectionSpec.CLEARTEXT)).build()
|
||||||
|
)
|
||||||
|
.build().create(PixelfedAPI::class.java)
|
||||||
|
|
||||||
@Test
|
@Test
|
||||||
fun api_correctly_translated_data_class() {
|
fun api_correctly_translated_data_class() {
|
||||||
stubFor(
|
stubFor(
|
||||||
|
@ -44,9 +74,10 @@ class APIUnitTest {
|
||||||
val statusesHome: List<Status>
|
val statusesHome: List<Status>
|
||||||
|
|
||||||
runBlocking {
|
runBlocking {
|
||||||
statuses = PixelfedAPI.createFromUrl("http://localhost:8089")
|
|
||||||
|
statuses = api
|
||||||
.timelinePublic(null, null, null, null, null)
|
.timelinePublic(null, null, null, null, null)
|
||||||
statusesHome = PixelfedAPI.createFromUrl("http://localhost:8089")
|
statusesHome = api
|
||||||
.timelineHome(null, null, null, null, null)
|
.timelineHome(null, null, null, null, null)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -69,8 +100,7 @@ class APIUnitTest {
|
||||||
.withBody(""" {"id":3197,"name":"Pixeldroid","website":null,"redirect_uri":"urn:ietf:wg:oauth:2.0:oob","client_id":3197,"client_secret":"hhRwLupqUJPghKsZzpZtxNV67g5DBdPYCqW6XE3m","vapid_key":null}"""
|
.withBody(""" {"id":3197,"name":"Pixeldroid","website":null,"redirect_uri":"urn:ietf:wg:oauth:2.0:oob","client_id":3197,"client_secret":"hhRwLupqUJPghKsZzpZtxNV67g5DBdPYCqW6XE3m","vapid_key":null}"""
|
||||||
)))
|
)))
|
||||||
val application: Application = runBlocking {
|
val application: Application = runBlocking {
|
||||||
PixelfedAPI.createFromUrl("http://localhost:8089")
|
api.registerApplication("Pixeldroid", "urn:ietf:wg:oauth:2.0:oob", "read write follow")
|
||||||
.registerApplication("Pixeldroid", "urn:ietf:wg:oauth:2.0:oob", "read write follow")
|
|
||||||
}
|
}
|
||||||
|
|
||||||
assertEquals("3197", application.client_id)
|
assertEquals("3197", application.client_id)
|
||||||
|
@ -100,8 +130,7 @@ class APIUnitTest {
|
||||||
val PACKAGE_ID = "org.pixeldroid.app"
|
val PACKAGE_ID = "org.pixeldroid.app"
|
||||||
|
|
||||||
val token: Token = runBlocking {
|
val token: Token = runBlocking {
|
||||||
PixelfedAPI.createFromUrl("http://localhost:8089")
|
api.obtainToken(
|
||||||
.obtainToken(
|
|
||||||
"123", "ssqdfqsdfqds", "$OAUTH_SCHEME://$PACKAGE_ID", SCOPE, "abc",
|
"123", "ssqdfqsdfqds", "$OAUTH_SCHEME://$PACKAGE_ID", SCOPE, "abc",
|
||||||
"authorization_code"
|
"authorization_code"
|
||||||
)
|
)
|
||||||
|
|
File diff suppressed because it is too large
Load Diff
Loading…
Reference in New Issue