{"id":30144144,"url":"https://github.com/icerockdev/moko-errors","last_synced_at":"2025-09-25T19:48:55.139Z","repository":{"id":43376822,"uuid":"278276239","full_name":"icerockdev/moko-errors","owner":"icerockdev","description":"Automated exceptions handler for mobile (android \u0026 ios) Kotlin Multiplatform development.","archived":false,"fork":false,"pushed_at":"2024-09-30T04:47:02.000Z","size":302,"stargazers_count":53,"open_issues_count":7,"forks_count":6,"subscribers_count":7,"default_branch":"master","last_synced_at":"2025-05-07T05:04:01.019Z","etag":null,"topics":["android","coroutines","error-handling","ios","kotlin","kotlin-multiplatform","kotlin-native","moko"],"latest_commit_sha":null,"homepage":"https://moko.icerock.dev/","language":"Kotlin","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/icerockdev.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE.md","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2020-07-09T05:57:34.000Z","updated_at":"2024-10-09T15:03:06.000Z","dependencies_parsed_at":"2022-09-26T22:01:49.085Z","dependency_job_id":null,"html_url":"https://github.com/icerockdev/moko-errors","commit_stats":null,"previous_names":[],"tags_count":11,"template":false,"template_full_name":null,"purl":"pkg:github/icerockdev/moko-errors","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/icerockdev%2Fmoko-errors","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/icerockdev%2Fmoko-errors/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/icerockdev%2Fmoko-errors/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/icerockdev%2Fmoko-errors/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/icerockdev","download_url":"https://codeload.github.com/icerockdev/moko-errors/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/icerockdev%2Fmoko-errors/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":269849592,"owners_count":24485153,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","status":"online","status_checked_at":"2025-08-11T02:00:10.019Z","response_time":75,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["android","coroutines","error-handling","ios","kotlin","kotlin-multiplatform","kotlin-native","moko"],"created_at":"2025-08-11T07:38:13.665Z","updated_at":"2025-09-25T19:48:50.098Z","avatar_url":"https://github.com/icerockdev.png","language":"Kotlin","readme":"![moko-errors](img/logo.png)\n\n[![GitHub license](https://img.shields.io/badge/license-Apache%20License%202.0-blue.svg?style=flat)](http://www.apache.org/licenses/LICENSE-2.0) [![Download](https://img.shields.io/maven-central/v/dev.icerock.moko/errors) ](https://repo1.maven.org/maven2/dev/icerock/moko/errors) ![kotlin-version](https://kotlin-version.aws.icerock.dev/kotlin-version?group=dev.icerock.moko\u0026name=errors)\n# Mobile Kotlin errors\nThis is a Kotlin MultiPlatform library that provides automatic exception handling and\nautomatic error displaying to a screen.\n\n## Table of Contents\n- [Features](#features)\n- [Requirements](#requirements)\n- [Installation](#installation)\n- [Usage](#usage)\n- [Samples](#samples)\n- [Set Up Locally](#set-up-locally)\n- [Contributing](#contributing)\n- [License](#license)\n\n## Features\n- **ExceptionHandler** implements safe code execution and automatic exception display using **ErrorPresenter**.\n- **ExceptionMappersStorage** singleton object, storage that stores a set of exception converters\nto error classes required for **ErrorPresenter** objects.\n- **ErrorPresenter** classes implements a strategy for displaying exceptions in a user-friendly form\non the platforms. Converts the exception class to an error object to display. There are several\n`ErrorPresenter` implementations: `AlertErrorPresenter` - displays errors text in alert dialogs,\n`ToastErrorPresenter` - displays errors text in toasts for Android and in alert dialog for iOS,\n`SnackBarErrorPresenter` - displays errors text in snackbar for Android and in alert dialog for iOS,\n`SelectorErrorPresenter` - for selecting error presenter by some custom condition.\n\n## Requirements\n- Kotlin 1.9.0\n- Gradle version 6.8+\n- Android API 16+\n- iOS version 11.0+\n\n## Installation\nroot build.gradle  \n```groovy\nallprojects {\n    repositories {\n        mavenCentral()\n    }\n}\n```\n\nproject build.gradle\n```groovy\ndependencies {\n    commonMainApi(\"dev.icerock.moko:errors:0.8.0\")\n}\n```\n\n## Usage\n\n#### ExceptionMappersStorage\n\nRegistration of simple custom exceptions mapper in the singleton storage:\n\n```kotlin\nExceptionMappersStorage\n    .register\u003cIllegalArgumentException, StringDesc\u003e {   // Will map all IllegalArgumentException instances to StringDesc\n        \"Illegal argument was passed!\".desc()\n    }\n    .register\u003cHttpException, Int\u003e {                     // Will map all HttpException instances to Int\n        it.code\n    }\n```\n\nRegistration of custom exception mapper with condition:\n\n```kotlin\nExceptionMappersStorage.condition\u003cStringDesc\u003e(              // Registers exception mapper Throwable -\u003e StringDesc\n    condition = { it is CustomException \u0026\u0026 it.code == 10 }, // Condition that maps Throwable -\u003e Boolean\n    mapper = { \"Custom error happened!\".desc() }            // Mapper for Throwable that matches to the condition\n)\n```\n\nFor every error type you should to set fallback (default) value using method `setFallbackValue`  \n(except `StringDesc` class which already has default value).\n\n```kotlin\nExceptionMappersStorage\n    .setFallbackValue\u003cInt\u003e(520) // Sets for Int error type default value as 520\n\n// Creates new mapper that for any unregistered exception will return the fallback value - 520\nval throwableToIntMapper: (Throwable) -\u003e Int = ExceptionMappersStorage.throwableMapper()\n```\n\nUsing factory method `throwableMapper` you can create exception mappers automaticlly:\n\n```kotlin\nval throwableToIntMapper: (Throwable) -\u003e Int = ExceptionMappersStorage.throwableMapper()\n```\n\nIf a default value is not found when creating a mapper using factory method `throwableMapper`, an \nexception will be thrown `FallbackValueNotFoundException`   \n\nThe registration can be done in the form of an endless chain:\n\n```kotlin\nExceptionMappersStorage\n    .condition\u003cStringDesc\u003e(\n        condition = { it is CustomException \u0026\u0026 it.code == 10 },\n        mapper = { \"Custom error happened!\".desc() }\n    )\n    .register\u003cIllegalArgumentException, StringDesc\u003e {\n        \"Illegal argument was passed!\".desc()\n    }\n    .register\u003cHttpException, Int\u003e {\n        it.code\n    }\n    .setFallbackValue\u003cInt\u003e(520)\n```\n\n#### ExceptionHandler\n\nE.g. declare `ExceptionHandler` property in some `ViewModel` class:\n\n```kotlin\nclass SimpleViewModel(\n    val exceptionHandler: ExceptionHandler\n) : ViewModel() {\n    // ...\n}\n```\n\nBind `ExceptionHandler` in the platform code.\n\nOn Android in an `Activity` of `Fragment`: \n\n```kotlin\nviewModel.exceptionHandler.bind(\n    lifecycleOwner = this,\n    activity = this\n)\n```\n\nOn iOS in a `ViewController`:\n\n```swift\nviewModel.exceptionHandler.bind(viewController: self)\n```\n\nCreating instances of `ExceptionHandler` class which uses `(Throwable) -\u003e StringDesc` mappers:\n\n```kotlin\nExceptionHandler\u003cStringDesc\u003e(\n    errorPresenter = errorsPresenterInstance,                    // Concrete ErrorPresenter implementation\n    exceptionMapper = ExceptionMappersStorage.throwableMapper(), // Create mapper (Throwable) -\u003e StringDesc from ExceptionMappersStorage\n    onCatch = {                                                  // Optional global catcher\n        println(\"Got exception: $it\")                            // E.g. here we can log all exceptions that are handled by ExceptionHandler\n    }\n)\n```\n\nAnd use it to safe requests in `ViewModel`:\n\n```kotlin\nfun onSendRequest() {\n    viewModelScope.launch {\n        exceptionHandler.handle {\n            serverRequest()     // Some dangerous code that can throw an exception\n        }.finally {             // Optional finally block\n            // Some code        \n        }.execute()             // Starts code execution in `handle` lambda\n    }\n}\n```\n\nAlso you can add some custom `catch` handlers for `ExceptionHandler` that work as a catch in the\ntry/catch operator:\n\n```kotlin\nfun onSendRequest() {\n    viewModelScope.launch {\n        exceptionHandler.handle {\n            serverRequest()\n        }.catch\u003cIllegalArgumentException\u003e {     // Specifying exception class\n            // Some custom handler code\n            false                               // true - cancels ErrorPresenter; false - allows execution of ErrorsPresenter\n        }.execute()                             // Starts code execution in `handle` lambda\n    }\n}\n```\n\n#### ErrorPresenter\n\nThere are `ErrorPresenter` interface implementations:\n* `AlertErrorPresenter` - displays errors text in alert dialogs;\n* `ToastErrorPresenter` - displays errors text in toasts for Android (for iOS shows alert dialog);\n* `SnackBarErrorPresenter` - displays errors text in snackbar for Android (for iOS shows alert dialog);\n* `SelectorErrorPresenter` - for selecting error presenter by some custom condition.\n\nYou need to pass some `ErrorPresenter` to `ErrorHandler` instance. E.g. creation of error presenters\nin common code:\n\n```kotlin\nval alertErrorPresenter = AlertErrorPresenter(\n    alertTitle = \"Error\".desc(),\n    positiveButtonText = \"OK\".desc()\n)\nval toastErrorPresenter = ToastErrorPresenter(\n    duration = ToastDuration.LONG\n)\n```\n\n`SelectorErrorPresenter` - special presenter that select some error presenter by custom condition lambda \nwhich should return some `ErrorPresenter` to be used for showing errors:\n\n```kotlin\nval selectorErrorPresenter = SelectorErrorPresenter { throwable -\u003e\n    when (throwable) {\n        is CustomException -\u003e alertErrorPresenter\n        else -\u003e toastErrorPresenter\n    }\n}\n```\n\nAnd pass some `ErrorPresenter` to `ErrorHandler`:\n\n```kotlin\nval exceptionHandler = ExceptionHandler(\n    errorPresenter = selectorErrorPresenter,\n    exceptionMapper = ExceptionMappersStorage.throwableMapper()\n)\n```\n\n## Samples\nPlease see more examples in the [sample directory](sample).\n\n## Set Up Locally \n- The [errors directory](errors) contains the `errors` library;\n- The [sample directory](sample) contains sample apps for Android and iOS; plus the mpp-library connected to the apps.\n\n## Contributing\nAll development (both new features and bug fixes) is performed in the `develop` branch. This way `master` always contains the sources of the most recently released version. Please send PRs with bug fixes to the `develop` branch. Documentation fixes in the markdown files are an exception to this rule. They are updated directly in `master`.\n\nThe `develop` branch is pushed to `master` on release.\n\nFor more details on contributing please see the [contributing guide](CONTRIBUTING.md).\n\n## License\n        \n    Copyright 2020 IceRock MAG Inc.\n    \n    Licensed under the Apache License, Version 2.0 (the \"License\");\n    you may not use this file except in compliance with the License.\n    You may obtain a copy of the License at\n    \n       http://www.apache.org/licenses/LICENSE-2.0\n    \n    Unless required by applicable law or agreed to in writing, software\n    distributed under the License is distributed on an \"AS IS\" BASIS,\n    WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n    See the License for the specific language governing permissions and\n    limitations under the License.\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ficerockdev%2Fmoko-errors","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Ficerockdev%2Fmoko-errors","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Ficerockdev%2Fmoko-errors/lists"}