{"id":23305636,"url":"https://github.com/nidomiro/kdataloader","last_synced_at":"2025-08-22T09:32:35.986Z","repository":{"id":46136207,"uuid":"222715395","full_name":"nidomiro/KDataLoader","owner":"nidomiro","description":"A Kotlin implementation of dataloader","archived":false,"fork":false,"pushed_at":"2022-07-18T09:57:51.000Z","size":271,"stargazers_count":8,"open_issues_count":0,"forks_count":2,"subscribers_count":1,"default_branch":"master","last_synced_at":"2024-12-20T12:13:21.704Z","etag":null,"topics":["coroutines","dataloader","kotlin","kotlin-coroutines","kotlin-dsl","kotlin-library"],"latest_commit_sha":null,"homepage":"https://github.com/nidomiro/KDataLoader#readme","language":"Kotlin","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/nidomiro.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":".github/FUNDING.yml","license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null},"funding":{"github":["nidomiro"]}},"created_at":"2019-11-19T14:29:40.000Z","updated_at":"2024-04-08T12:59:02.000Z","dependencies_parsed_at":"2022-07-20T15:49:52.910Z","dependency_job_id":null,"html_url":"https://github.com/nidomiro/KDataLoader","commit_stats":null,"previous_names":[],"tags_count":12,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nidomiro%2FKDataLoader","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nidomiro%2FKDataLoader/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nidomiro%2FKDataLoader/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/nidomiro%2FKDataLoader/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/nidomiro","download_url":"https://codeload.github.com/nidomiro/KDataLoader/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":230582885,"owners_count":18248672,"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","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":["coroutines","dataloader","kotlin","kotlin-coroutines","kotlin-dsl","kotlin-library"],"created_at":"2024-12-20T12:13:23.626Z","updated_at":"2024-12-20T12:13:25.100Z","avatar_url":"https://github.com/nidomiro.png","language":"Kotlin","funding_links":["https://github.com/sponsors/nidomiro"],"categories":[],"sub_categories":[],"readme":"[ ![Download](https://img.shields.io/badge/License-MIT-yellow.svg) ](https://opensource.org/licenses/MIT)\n[![Maven Central](https://maven-badges.herokuapp.com/maven-central/de.nidomiro/KDataLoader/badge.svg)](https://maven-badges.herokuapp.com/maven-central/de.nidomiro/KDataLoader)\n\n\n# KDataLoader\n\nA pure, multiplatform (js and jvm) Kotlin implementation of [DataLoader](https://github.com/graphql/dataloader).\nThis library is using [Kotlin Coroutines](https://kotlinlang.org/docs/reference/coroutines-overview.html).\n\n\n## What is a DataLoader?\n\nA DataLoader is a mechanism to optimize data-fetching.\nInstead of issuing multiple calls one after the other, the DataLoader will collect all calls and execute them together as one.\nThis alone has the huge benefit of fewer calls to your db/api, therefore reducing load.\nThe second optimization is to eliminate duplicate calls.\n\n### Example\n\nAssumption: You want to fetch a list of Projects with their members.\nThe relation between Project and Person is m:n, therefore a Person can work in multiple projects.\n\nThe data:\n```json\n{\n   \"projects\":[\n      {\n         \"name\":\"Project A\",\n         \"members\":[\n            {\n               \"id\":1,\n               \"name\":\"John\"\n            },\n            {\n               \"id\":2,\n               \"name\":\"Anne\"\n            }\n         ]\n      },\n      {\n         \"name\":\"Project B\",\n         \"members\":[\n            {\n               \"id\":2,\n               \"name\":\"Anne\"\n            }\n         ]\n      },\n      {\n         \"name\":\"Project C\",\n         \"members\":[\n            {\n               \"id\":1,\n               \"name\":\"John\"\n            },\n            {\n               \"id\":3,\n               \"name\":\"Peter\"\n            }\n         ]\n      }\n   ]\n}\n```\n\nIn a **naive** approach you will need **6 requests** to get all your data:\n\n1. fetch all Projects\n2. fetch John\n3. fetch Anne\n4. fetch Anne\n5. fetch John\n6. fetch Peter\n\nThe same scenario can be optimized to **2 requests** with a **DataLoader**:\n\n1. fetch all Projects\n2. fetch John, Anne and Peter in batch\n\n\nHow does it work?\n\nIf you want to load the Person with id 1, you simply call `dataLoader.loadAsync(1)`.\nYou won't get the result immediately, but you'll get a `Deferred`, which is an equivalent of a `Future` or `Promise` in other languages.\n\nIn the example above the calls will be:\n\n1. `dataLoader.loadAsync(1)`\n2. `dataLoader.loadAsync(2)`\n3. `dataLoader.loadAsync(2)`\n4. `dataLoader.loadAsync(1)`\n5. `dataLoader.loadAsync(3)`\n\nBy now no call to actually fetch the data has been made.\nThe actual fetch happens when you call `dataLoader.dispatch()`.\nIn this case the ids 1,2 and 3 will be fetched in one call.\nSince calling `dataLoader.loadAsync()` with the same id will result in the same `Deffered` being returned, no id is fetched more than once.\n\n\n\n## Install\n\n### Kotlin Multiplatform Project\nCurrently, only `jvm` and `js` is supported.\n\n```kotlin\nrepositories {\n    mavenCentral()\n}\n\nkotlin {\n    sourceSets {\n        val commonMain by getting {\n            dependencies {\n                implementation(\"de.nidomiro:KDataLoader:0.5.1\")\n            }\n        }\n    }\n}\n```\n\nFor JVM-only or js only use the following instead of `de.nidomiro:KDataLoader`:\n* JVM: `de.nidomiro:KDataLoader-jvm`\n* JS: `de.nidomiro:KDataLoader-js`\n\n### Maven\n \n```xml\n\u003cdependency\u003e\n    \u003cgroupId\u003ede.nidomiro\u003c/groupId\u003e\n    \u003cartifactId\u003eKDataLoader-jvm\u003c/artifactId\u003e\n    \u003cversion\u003e0.5.1\u003c/version\u003e\n\u003c/dependency\u003e\n```\n\n## Usage\n\nSince this library uses [Kotlin Coroutines](https://kotlinlang.org/docs/reference/coroutines-overview.html) every example assumes you are in a coroutine.\n\n```kotlin\nval batchLoader: BatchLoader\u003cInt, Int\u003e =\n    { keys -\u003e keys.map { ExecutionResult.Success(it) } }\n\nval dataLoader = dataLoader(batchLoader) {\n\n    configure {\n        // all default-values\n        cache = DefaultCacheImpl()\n        cacheEnabled = true\n        cacheExceptions = true\n        batchLoadEnabled = true\n        batchSize = Int.MAX_VALUE\n    }\n\n    prime(1 to 1) // prime the cache\n}\n\nval value1 = dataLoader.loadAsync(1)\nval value2 = dataLoader.loadAsync(2)\ndataLoader.dispatch() // actually fetch the data\n\nprintln(\"1 -\u003e ${value1.await()}\") // from cache\nprintln(\"2 -\u003e ${value2.await()}\") // loaded via BatchLoader\n```\n\n\n## Versioning\n\nThis Library uses [Semantic Versioning](https://semver.org/).\n\n## License\n\nThis Library is Licensed under the [MIT License](https://opensource.org/licenses/MIT).\n\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnidomiro%2Fkdataloader","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fnidomiro%2Fkdataloader","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fnidomiro%2Fkdataloader/lists"}