profile
viewpoint
If you are wondering where the data of this site comes from, please visit https://api.github.com/users/fo2rist/events. GitMemory does not store any data, but only uses NGINX to cache data for a period of time. The idea behind GitMemory is simply to give users a better reading experience.
Dmitry Sitnikov fo2rist Distillery Santa Monica fo2rist.com

fo2rist/cadabra 3

A/B testing library for Java/Kotlin/Android

fo2rist/garmin-vehicle-keyfob 3

Garmin app that allow to Lock/Unlock a car from watch

fo2rist/android-drawable-scale-test 1

Test how Android scales drawables for different resolutions

fo2rist/apiai-python-webhook 1

Test webhook for AI API slack-bot

fo2rist/droidcon-kotlin-scope-extension-functions 1

Demo repository with example of good and bad scope functions usage

fo2rist/livejournal-archiver 1

Archives posts from LiveJournal account to local storage

fo2rist/saynohi 1

Slack app that prevents no topic conversations

fo2rist/dagger-sample-test 0

Set of tests that reveal how different dagger dependencies are resolved

fo2rist/formula-history-mobile 0

Formula 1 History & Stats for mobile

startedAppTelemetry/SwiftClient

started time in a day

pull request commentgoogle/iosched

Implement App Startup

@manuelvicnt Thank you for taking valuable time on this, those are really great findings and should give insights to developers in tests! I also played around a bit with Startup but unfortunately kept getting errors. Hope @tikurahul will rescue us 🤞

nuhkoca

comment created time in 2 days

pull request commentgoogle/iosched

Implement App Startup

Hi @nuhkoca ! Tried locally and yes, the tests keep failing but for a different reason now. EarlyEntryPoints fixes the problem when accessing the graph in tests.

As initializers run automatically, by the time AnalyticsHelperInitializer run and tries to access the context, there's no context because the test hasn't even started yet. And that throws the following runtime exception.

androidx.startup.StartupException: java.lang.IllegalStateException: No instrumentation registered! Must run under a registering instrumentation.

I thought about removing the automatic initialization for tests and then activating them manually in MainTestApplication, but I couldn't get it to work. Following the [App Startup documentation], I added a new AndroidManifest.xml file in the androidTest folder and added:

<application>
    <provider
        android:name="androidx.startup.InitializationProvider"
        android:authorities="${applicationId}.androidx-startup"
        android:exported="false"
        tools:node="remove"/>
</application>

But that does NOT work either! Because ${applicationId} = com.google.samples.apps.iosched.test and the authority in the main app is com.google.samples.apps.iosched. And if you try to hardcode com.google.samples.apps.iosched in there doesn't work as the provider is not the same. It gives a The application could not be installed: INSTALL_FAILED_CONFLICTING_PROVIDER compilation error.

@tikurahul can you help here? Not wanting to run initializers during integration tests seems to be a common use case the community can face.

nuhkoca

comment created time in 2 days

pull request commentgoogle/iosched

Implement App Startup

Let me take a look tomorrow. No need to push your changes with EarlyEntryPoint though :D

nuhkoca

comment created time in 3 days

Pull request review commentgoogle/iosched

Implement App Startup

+/*+ * Copyright 2021 Google LLC+ *+ * Licensed under the Apache License, Version 2.0 (the "License");+ * you may not use this file except in compliance with the License.+ * You may obtain a copy of the License at+ *+ *     https://www.apache.org/licenses/LICENSE-2.0+ *+ * Unless required by applicable law or agreed to in writing, software+ * distributed under the License is distributed on an "AS IS" BASIS,+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.+ * See the License for the specific language governing permissions and+ * limitations under the License.+ */++package com.google.samples.apps.iosched.util.initializers++import android.content.Context+import androidx.startup.Initializer+import com.google.samples.apps.iosched.di.InitializerEntryPoint+import com.google.samples.apps.iosched.shared.analytics.AnalyticsHelper+import javax.inject.Inject++class AnalyticsHelperInitializer : Initializer<Unit> {++    @Inject+    lateinit var analyticsHelper: AnalyticsHelper++    override fun create(context: Context) {+        InitializerEntryPoint.resolve(context).inject(this)

Yeah, sorry, meant analyticsHelper = InitializerEntryPoint.resolve(context). analyticsHelper() instead

nuhkoca

comment created time in 3 days

Pull request review commentgoogle/iosched

Implement App Startup

+/*+ * Copyright 2021 Google LLC+ *+ * Licensed under the Apache License, Version 2.0 (the "License");+ * you may not use this file except in compliance with the License.+ * You may obtain a copy of the License at+ *+ *     https://www.apache.org/licenses/LICENSE-2.0+ *+ * Unless required by applicable law or agreed to in writing, software+ * distributed under the License is distributed on an "AS IS" BASIS,+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.+ * See the License for the specific language governing permissions and+ * limitations under the License.+ */++package com.google.samples.apps.iosched.di++import android.content.Context+import com.google.samples.apps.iosched.util.initializers.AnalyticsHelperInitializer+import dagger.hilt.EntryPoint+import dagger.hilt.InstallIn+import dagger.hilt.android.EntryPointAccessors+import dagger.hilt.components.SingletonComponent++@EntryPoint+@InstallIn(SingletonComponent::class)+interface InitializerEntryPoint {++    companion object {+        fun resolve(context: Context): InitializerEntryPoint {+            return EntryPointAccessors.fromApplication(+                context,+                InitializerEntryPoint::class.java+            )+        }+    }++    fun inject(initializer: AnalyticsHelperInitializer)

Yes, sorry! I meant to say analyticsHelper instead :) thank you!

nuhkoca

comment created time in 3 days

pull request commentgoogle/iosched

Implement App Startup

@manuelvicnt Thanks a lot for your review. I did the same what you and documentation mentioned but tests still fail. So I need your help here :D Shall I push changes?

nuhkoca

comment created time in 3 days

Pull request review commentgoogle/iosched

Implement App Startup

+/*+ * Copyright 2021 Google LLC+ *+ * Licensed under the Apache License, Version 2.0 (the "License");+ * you may not use this file except in compliance with the License.+ * You may obtain a copy of the License at+ *+ *     https://www.apache.org/licenses/LICENSE-2.0+ *+ * Unless required by applicable law or agreed to in writing, software+ * distributed under the License is distributed on an "AS IS" BASIS,+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.+ * See the License for the specific language governing permissions and+ * limitations under the License.+ */++package com.google.samples.apps.iosched.util.initializers++import android.content.Context+import androidx.startup.Initializer+import com.google.samples.apps.iosched.di.InitializerEntryPoint+import com.google.samples.apps.iosched.shared.analytics.AnalyticsHelper+import javax.inject.Inject++class AnalyticsHelperInitializer : Initializer<Unit> {++    @Inject+    lateinit var analyticsHelper: AnalyticsHelper++    override fun create(context: Context) {+        InitializerEntryPoint.resolve(context).inject(this)

Sorry, I didn't get this, why EntryPoint returns initializer instance instead of dependency which is AnalyticsHelper in this class?

nuhkoca

comment created time in 3 days

Pull request review commentgoogle/iosched

Implement App Startup

+/*+ * Copyright 2021 Google LLC+ *+ * Licensed under the Apache License, Version 2.0 (the "License");+ * you may not use this file except in compliance with the License.+ * You may obtain a copy of the License at+ *+ *     https://www.apache.org/licenses/LICENSE-2.0+ *+ * Unless required by applicable law or agreed to in writing, software+ * distributed under the License is distributed on an "AS IS" BASIS,+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.+ * See the License for the specific language governing permissions and+ * limitations under the License.+ */++package com.google.samples.apps.iosched.di++import android.content.Context+import com.google.samples.apps.iosched.util.initializers.AnalyticsHelperInitializer+import dagger.hilt.EntryPoint+import dagger.hilt.InstallIn+import dagger.hilt.android.EntryPointAccessors+import dagger.hilt.components.SingletonComponent++@EntryPoint+@InstallIn(SingletonComponent::class)+interface InitializerEntryPoint {++    companion object {+        fun resolve(context: Context): InitializerEntryPoint {+            return EntryPointAccessors.fromApplication(+                context,+                InitializerEntryPoint::class.java+            )+        }+    }++    fun inject(initializer: AnalyticsHelperInitializer)

I think analyticsHelperInitializer should be analyticsHelper instead, right? Cause we have an instance of AnalyticsHelper from the graph.

nuhkoca

comment created time in 3 days

pull request commentgoogle/iosched

Implement App Startup

Hi @nuhkoca ! The problem with the tests are due to EntryPoints being used. In tests, Hilt's SingletonComponent is scoped to the lifetime of the test case instead of the lifetime of the Application.

To get this fixed, you need to use @EarlyEntryPoints instead of @EntryPoints in the different initializers.

More info here: https://dagger.dev/hilt/early-entry-point.html

Let me know if you need more help :D thank you!

nuhkoca

comment created time in 3 days

Pull request review commentgoogle/iosched

Implement App Startup

+/*+ * Copyright 2021 Google LLC+ *+ * Licensed under the Apache License, Version 2.0 (the "License");+ * you may not use this file except in compliance with the License.+ * You may obtain a copy of the License at+ *+ *     https://www.apache.org/licenses/LICENSE-2.0+ *+ * Unless required by applicable law or agreed to in writing, software+ * distributed under the License is distributed on an "AS IS" BASIS,+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.+ * See the License for the specific language governing permissions and+ * limitations under the License.+ */++package com.google.samples.apps.iosched.util.initializers++import android.content.Context+import androidx.startup.Initializer+import com.google.samples.apps.iosched.di.InitializerEntryPoint+import com.google.samples.apps.iosched.shared.analytics.AnalyticsHelper+import javax.inject.Inject++class AnalyticsHelperInitializer : Initializer<Unit> {++    @Inject+    lateinit var analyticsHelper: AnalyticsHelper++    override fun create(context: Context) {+        InitializerEntryPoint.resolve(context).inject(this)
        analyticsHelperInitializer = InitializerEntryPoint.resolve(context). analyticsHelperInitializer()

As commented above, I'd rather not have entry points behave like Dagger components. Also, the @Inject from analyticsHelper can be removed and can be made private.

Thanks!

nuhkoca

comment created time in 3 days

Pull request review commentgoogle/iosched

Implement App Startup

+/*+ * Copyright 2021 Google LLC+ *+ * Licensed under the Apache License, Version 2.0 (the "License");+ * you may not use this file except in compliance with the License.+ * You may obtain a copy of the License at+ *+ *     https://www.apache.org/licenses/LICENSE-2.0+ *+ * Unless required by applicable law or agreed to in writing, software+ * distributed under the License is distributed on an "AS IS" BASIS,+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.+ * See the License for the specific language governing permissions and+ * limitations under the License.+ */++package com.google.samples.apps.iosched.di++import android.content.Context+import com.google.samples.apps.iosched.util.initializers.AnalyticsHelperInitializer+import dagger.hilt.EntryPoint+import dagger.hilt.InstallIn+import dagger.hilt.android.EntryPointAccessors+import dagger.hilt.components.SingletonComponent++@EntryPoint+@InstallIn(SingletonComponent::class)+interface InitializerEntryPoint {++    companion object {+        fun resolve(context: Context): InitializerEntryPoint {+            return EntryPointAccessors.fromApplication(+                context,+                InitializerEntryPoint::class.java+            )+        }+    }++    fun inject(initializer: AnalyticsHelperInitializer)
    fun analyticsHelperInitializer(): AnalyticsHelperInitializer

I understand this works as you expect and is nice to read. However, an entry point's responsibility is not injecting classes, entry points expose instances from the graph.

nuhkoca

comment created time in 3 days

pull request commentgoogle/iosched

Implement App Startup

@JoseAlcerreca can you help me for UI tests? After moving AnalyticsHelper out of application and inject it in the Initializer class, UI tests have start to fail and I don't know how to get it to working with Hilt.

nuhkoca

comment created time in 3 days

Pull request review commentgoogle/iosched

Implement App Startup

 dependencies {     implementation(fileTree(mapOf("dir" to "libs", "include" to listOf("*.jar"))))      implementation(Libs.CORE_KTX)+    implementation(Libs.APP_STARTUP)

Right of course!

nuhkoca

comment created time in 3 days

release cashapp/quickjs-java

0.9.0

released time in 5 days

Pull request review commentgoogle/iosched

Implement App Startup

 import javax.inject.Inject class MainApplication : Application() {      // Even if the var isn't used, needs to be initialized at application startup.-    @Inject lateinit var analyticsHelper: AnalyticsHelper--    override fun onCreate() {-        // ThreeTenBP for times and dates, called before super to be available for objects-        AndroidThreeTen.init(this)--        // Enable strict mode before Dagger creates graph-        if (BuildConfig.DEBUG) {-            enableStrictMode()-        }-        super.onCreate()--        if (BuildConfig.DEBUG) {-            Timber.plant(Timber.DebugTree())-        } else {-            Timber.plant(CrashlyticsTree())-        }-    }--    private fun enableStrictMode() {-        StrictMode.setThreadPolicy(-            Builder()-                .detectDiskReads()-                .detectDiskWrites()-                .detectNetwork()-                .penaltyLog()-                .build()-        )-    }+    @Inject+    lateinit var analyticsHelper: AnalyticsHelper

Sure let me blend AppStartup with Hilt :)

nuhkoca

comment created time in 6 days

Pull request review commentgoogle/iosched

Implement App Startup

 dependencies {     implementation(fileTree(mapOf("dir" to "libs", "include" to listOf("*.jar"))))      implementation(Libs.CORE_KTX)+    implementation(Libs.APP_STARTUP)

Hmm won't it fail in release app? Please note this is not Startup Macrobenchmark library. I believe, we need AppStartup for release variant, as well, no?

nuhkoca

comment created time in 6 days

Pull request review commentgoogle/iosched

Implement App Startup

          </activity>          <activity-            android:name=".ui.MainActivity" />+            android:name=".ui.MainActivity" >+            <intent-filter>+                <action android:name="com.google.samples.apps.iosched.STARTUP_ACTIVITY" />

This is not related to AppStartup rather Startup Macrobenchmark library. So I measured MainActivity.

nuhkoca

comment created time in 6 days

Pull request review commentgoogle/iosched

Implement App Startup

 import javax.inject.Inject class MainApplication : Application() {      // Even if the var isn't used, needs to be initialized at application startup.-    @Inject lateinit var analyticsHelper: AnalyticsHelper--    override fun onCreate() {-        // ThreeTenBP for times and dates, called before super to be available for objects-        AndroidThreeTen.init(this)--        // Enable strict mode before Dagger creates graph-        if (BuildConfig.DEBUG) {-            enableStrictMode()-        }-        super.onCreate()--        if (BuildConfig.DEBUG) {-            Timber.plant(Timber.DebugTree())-        } else {-            Timber.plant(CrashlyticsTree())-        }-    }--    private fun enableStrictMode() {-        StrictMode.setThreadPolicy(-            Builder()-                .detectDiskReads()-                .detectDiskWrites()-                .detectNetwork()-                .penaltyLog()-                .build()-        )-    }+    @Inject+    lateinit var analyticsHelper: AnalyticsHelper

Can this have its own initializer?

nuhkoca

comment created time in 6 days

Pull request review commentgoogle/iosched

Implement App Startup

 dependencies {     implementation(fileTree(mapOf("dir" to "libs", "include" to listOf("*.jar"))))      implementation(Libs.CORE_KTX)+    implementation(Libs.APP_STARTUP)

can this be debugImplementation?

nuhkoca

comment created time in 6 days

Pull request review commentgoogle/iosched

Implement App Startup

          </activity>          <activity-            android:name=".ui.MainActivity" />+            android:name=".ui.MainActivity" >+            <intent-filter>+                <action android:name="com.google.samples.apps.iosched.STARTUP_ACTIVITY" />

I have 0 experience with AppStartup, but, can this be applied to the LauncherActivity to take its performance loss into account?

nuhkoca

comment created time in 6 days

delete branch cljla/code

delete branch : update-readme

delete time in 9 days

push eventcljla/code

Nate Jones

commit sha d5117d2cb5a2dabe0fe9fc8c1c5b59fdfc50c271

Update README for June 2021

view details

push time in 9 days

push eventcljla/code

Nate Jones

commit sha d5117d2cb5a2dabe0fe9fc8c1c5b59fdfc50c271

Update README for June 2021

view details

push time in 9 days

push eventcljla/code

Nate Jones

commit sha 6a357b6ed78686a7ae4c3f7c3cd8ba2bab75884e

update

view details

push time in 9 days

create barnchcljla/code

branch : update-readme

created branch time in 9 days

pull request commentgoogle/iosched

Implement App Startup

cc @JoseAlcerreca I think this can be merged, right?

nuhkoca

comment created time in 10 days

push eventcljla/code

Nate Jones

commit sha 88feee42c0f1fe7d6d295994d85e90c01e57e85e

June works!

view details

push time in 10 days

push eventcljla/code

Nate Jones

commit sha 1c9caff70f87e6128804ce7deca4df0d8a5f5aa6

Prepare for June 2021

view details

push time in 10 days

Pull request review commentgoogle/iosched

Implement App Startup

 androidComponents { }  dependencies {-    //noinspection GradleDependency-    implementation "org.jetbrains.kotlin:kotlin-stdlib:1.5.0"-    implementation 'androidx.test.ext:junit:1.1.2'-    implementation 'androidx.test.espresso:espresso-core:3.3.0'-    implementation 'androidx.test.uiautomator:uiautomator:2.2.0'-    implementation 'androidx.benchmark:benchmark-macro-junit4:1.1.0-SNAPSHOT'+    api platform(project(":depconstraints"))

To be consistent with other modules, moved all dependencies to depconstraints module.

nuhkoca

comment created time in 10 days