Injection

Working with manually handled Nabla SDK instances

If you use your own DI framework or if you just want to have control on the instance of the Nabla SDK used by UI components, you can provide your own instance.

Get your own Nabla instances

As the SDK relies on Android components, your NablaClient must be initialized at app startup (by overriding Application.onCreate or by using App Startup lib):

class MyApplication : Application() {

    override fun onCreate() {
        super.onCreate()

        NablaClient.initialize(
            modules = listOf(
                NablaMessagingModule(),
            ),
            configuration = Configuration(
                publicApiKey = "MY_API_KEY"
            ),
            name = "MyOwnNablaInstance",
        )
    }
}

Instead of relying on the NablaClient.getInstance() and NablaMessagingClient.getInstance() singleton, you can create your own instance and use it. Here's an example using Hilt:

@Module
@InstallIn(SingletonComponent::class)
object NablaModule {
    @Provides
    @Singleton
    fun provideNablaClient(
        @ApplicationContext context: Context,
    ): NablaClient = NablaClient.getInstance(name = "MyOwnNablaInstance")
}

📘

Make sure not to forget to also authenticate your patient before using the rest of the APIs. See Authentication for details about how to do it.

UI Component: Custom Views

Since views we provide are backed by view models, you can directly pass your own NablaMessagingClient instance to the view model factory, e.g. ConversationListViewModelFactory for ConversationsListView.

class MainActivity : AppCompatActivity() {
    private lateinit var binding: ActivityMainBinding

    @Inject
    lateinit var nablaMessagingClient: NablaMessagingClient

    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)

        binding = ActivityMainBinding.inflate(layoutInflater)
        setContentView(binding.root)

        // Pass your nabla instance to the factory
        val viewModel: ConversationListViewModel by viewModels {
            ConversationListViewModelFactory(
                owner = this,
                messagingClient = nablaMessagingClient,
            )
        }

        // Step 2 - Connect the View to the ViewModel
        // If you're using a Fragment, the lifecycleOwner is "viewLifecycleOwner"
        binding.conversationListView.bindViewModel(
            viewModel,
            onConversationClicked = { id: ConversationId ->
                // TODO handle click on a conversation
            },
        )
    }
}

UI Component: Activities & Fragments

To provide your own instance to a Nabla Activity or Fragment such us InboxFragment, ConversationFragment or ConversationActivity, you should pass to it the same client name you used during init.

For instance, if your NablaClient init looks like the following

class MyApplication : Application() {

    override fun onCreate() {
        super.onCreate()

        NablaClient.initialize(
            modules = listOf(
                NablaMessagingModule(),
            ),
            configuration = Configuration(
                publicApiKey = "MY_API_KEY"
            ),
            name = "MyOwnNablaInstance",
        )
    }
}

Then, your new Activity/Fragment call should specify the same name.

val myInboxFragment = InboxFragment.newInstance(sdkName = "MyOwnNablaInstance")

val myConversationFragment = ConversationFragment.newInstance(conversationId, sdkName = "MyOwnNablaInstance") {
    setFragment(MyConversationFragment())
}

val myConversationActivity = ConversationActivity.newIntent(requireContext(), conversationId, sdkName = "MyOwnNablaInstance")