-
Notifications
You must be signed in to change notification settings - Fork 903
[BWA-182] Add mTLS support for Glide image loading #6125
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
base: main
Are you sure you want to change the base?
Conversation
|
Great job! No new security vulnerabilities introduced in this pull request |
Codecov Report❌ Patch coverage is
Additional details and impacted files@@ Coverage Diff @@
## main #6125 +/- ##
==========================================
- Coverage 84.96% 84.94% -0.03%
==========================================
Files 724 725 +1
Lines 52758 52898 +140
Branches 7659 7681 +22
==========================================
+ Hits 44826 44934 +108
- Misses 5249 5281 +32
Partials 2683 2683 ☔ View full report in Codecov by Sentry. 🚀 New features to boost your workflow:
|
| private class OkHttpDataFetcher( | ||
| private val client: OkHttpClient, | ||
| private val url: GlideUrl, | ||
| ) : com.bumptech.glide.load.data.DataFetcher<InputStream> { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we add an import for this instead of having the full path here?
| private var call: Call? = null | ||
|
|
||
| override fun loadData( | ||
| priority: com.bumptech.glide.Priority, |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Same thing here
| * This wraps our CertificateProvider to handle client certificate selection during | ||
| * the TLS handshake. | ||
| */ | ||
| private fun createSslContext(certificateProvider: CertificateProvider): SSLContext = |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This exact logic already exists in the app. Can we pull it out as a common extension method on CertificateProvider and use it in multiple places. I think we can probably do that with a lot of this.
fun CertificateProvider.createSslContext(): SSLContext =
SSLContext.getInstance("TLS").apply {
init(
arrayOf(
CertificateProviderKeyManager(certificateProvider = certificateProvider),
),
createSslTrustManagers(),
null,
)
}
fun CertificateProvider.createMtlsOkHttpClient(): OkHttpClient {
val sslContext = createSslContext(certificateProvider)
val trustManagers = createSslTrustManagers()
return OkHttpClient.Builder()
.sslSocketFactory(
sslContext.socketFactory,
trustManagers.first() as X509TrustManager,
)
.build()
}
private fun createSslTrustManagers(): Array<TrustManager> =
TrustManagerFactory
.getInstance(TrustManagerFactory.getDefaultAlgorithm())
.apply { init(null as KeyStore?) }
.trustManagers
| import com.bumptech.glide.module.AppGlideModule | ||
| import org.junit.Assert.assertNotNull | ||
| import org.junit.Assert.assertTrue | ||
| import org.junit.Test |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we make sure these use Junit 5
| override fun getDataClass(): Class<InputStream> = InputStream::class.java | ||
|
|
||
| override fun getDataSource(): com.bumptech.glide.load.DataSource = | ||
| com.bumptech.glide.load.DataSource.REMOTE |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we just pull in the import for this?
| val sslContext = createSslContext() | ||
| val trustManagers = createSslTrustManagers() | ||
|
|
||
| return OkHttpClient.Builder() |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
👍
| width: Int, | ||
| height: Int, | ||
| options: Options, | ||
| ): ModelLoader.LoadData<InputStream>? { |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we make this return type nonnull.
| if (response?.isSuccessful == true) { | ||
| callback.onDataReady(response.body?.byteStream()) | ||
| } else { | ||
| callback.onLoadFailed(Exception("HTTP ${response?.code}: ${response?.message}")) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Can we simplify some of this.
- We can make a
localCallthat is nonnull to avoid weird nullability issues. - Move the try catch around only the function that can throw.
- We can also use the
HttpExceptionfrom Glide.
val localCall = client.newCall(request).also { call = it }
val response = try {
localCall.execute()
} catch (e: IOException) {
callback.onLoadFailed(e)
return
}
if (response.isSuccessful) {
callback.onDataReady(response.body.byteStream())
} else {
callback.onLoadFailed(HttpException(response.message, response.code))
}
🎟️ Tracking
https://bitwarden.atlassian.net/browse/BWA-182
📔 Objective
This PR adds mTLS (mutual TLS) support to Glide image loading.
This allows image requests to pass through Cloudflare's mTLS validation.
⏰ Reminders before review
🦮 Reviewer guidelines
:+1:) or similar for great changes:memo:) or ℹ️ (:information_source:) for notes or general info:question:) for questions:thinking:) or 💭 (:thought_balloon:) for more open inquiry that's not quite a confirmed issue and could potentially benefit from discussion:art:) for suggestions / improvements:x:) or:warning:) for more significant problems or concerns needing attention:seedling:) or ♻️ (:recycle:) for future improvements or indications of technical debt:pick:) for minor or nitpick changes