Coding standards & best practices
Guidelines and best practices for developing and maintaining extensions in this repository.
1. Modern Android & Java APIs
WebP image compression
Bitmap.CompressFormat.WEBP is deprecated on Android 11 (API 30+). Use version-gated WebP compression formats:
kotlin
val format = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
Bitmap.CompressFormat.WEBP_LOSSLESS // or WEBP_LOSSY
} else {
@Suppress("DEPRECATION")
Bitmap.CompressFormat.WEBP
}
bitmap.compress(format, quality, outputStream)Date and time parsing
Avoid legacy SimpleDateFormat and fragile string operations. Prefer java.time (DateTimeFormatter, LocalDate, Instant, ZonedDateTime) with safe parsing:
kotlin
private val dateFormatter by lazy {
DateTimeFormatter.ofPattern("yyyy-MM-dd", Locale.ENGLISH)
}
val date = try {
LocalDate.parse(dateStr, dateFormatter).atStartOfDay(ZoneOffset.UTC).toInstant().toEpochMilli()
} catch (_: Exception) {
0L
}Modern locale construction
Avoid deprecated Locale(language, country) constructors. Use Locale.of(...):
kotlin
val locale = Locale.of("en", "US")WebView settings
Do not enable deprecated WebSettings such as WebSettings.databaseEnabled. Keep WebView interceptors minimal and clean.
2. Kotlin Compiler Hygiene & Null Safety
Under modern Kotlin compilers (Kotlin 2.x+):
- Avoid redundant assertions (
!!): Do not assert non-null on types that are already non-null or smart-cast. - Avoid dead Elvis operators (
?:): Remove redundant fallback Elvis operators on non-null values. - Avoid unnecessary safe calls (
?.): Do not use?.on non-nullable receivers. - Exhaustive branching: Ensure
whenblocks handle all cases safely.
3. Extension Architecture (Keiyoushi 1.6)
- Extend
KeiSource: All new extensions must extendKeiSource(libVersion = "1.6"), not legacyHttpSource. - Metadata via Gradle DSL: Do not manually declare
name,lang,id, orbaseUrlin@Sourceclasses. Define them insource {}blocks withinbuild.gradle.kts. - DTO Models: Use regular
classinstead ofdata classfor@Serializablemodels to reduce APK bytecode overhead. - Shared Utilities: Use
keiyoushi.utils(response.parseAs<T>(),toJsonRequestBody()) instead of local JSON or client instances.
4. Code Formatting & Linting
Before committing:
bash
# Format code with Spotless
./gradlew spotlessApply
# Run release lint on your extension
./gradlew :src:<lang>:<extension>:lintRelease