An open API service indexing awesome lists of open source software.

https://github.com/mv-gh/lemmybackwardscompatibleapi

Kotlin multiplatform Backward compatible Lemmy API
https://github.com/mv-gh/lemmybackwardscompatibleapi

api api-client kotlin kotlin-library kotlin-multiplatform lemmy

Last synced: 16 days ago
JSON representation

Kotlin multiplatform Backward compatible Lemmy API

Awesome Lists containing this project

README

        

![Sonatype Nexus (Snapshots)](https://img.shields.io/nexus/s/it.vercruysse.lemmyapi/lemmy-api?server=https%3A%2F%2Fs01.oss.sonatype.org)
![badge][badge-js]
![badge][badge-jvm]
![badge][badge-android]
![badge][badge-linux]
![badge][badge-windows]
![badge][badge-mac]
![badge][badge-ios]
![badge][badge-watchos]
![badge][badge-tvos]
![example workflow](https://github.com//mv-gh/lemmybackwardsCompatibleAPi/actions/workflows/ci.yml/badge.svg)
[![License: AGPL v3](https://img.shields.io/badge/License-AGPL_v3-blue.svg)](https://www.gnu.org/licenses/agpl-3.0)
![GitHub stars](https://img.shields.io/github/stars/mv-gh/lemmybackwardsCompatibleAPi?style=social)

# LemmyBackwardsCompatibleAPI

A backwards compatible API for Lemmy made with Kotlin Multiplatform. Supports Lemmy 0.18+

## Usage

```kotlin
val api = LemmyApi.getLemmyApi("voyager.lemmy.ml", auth)

api.getSite()

// Some features are version dependent, so we can check if they are supported
if(api.FF.instanceBlock()) {
api.instanceBlock()
}

// These enums can be different depending on the version of the API
api.getSupportedEntries()

```

## Installation

```kts
implementation("it.vercruysse.lemmyapi:lemmy-api:VERSION")
```
It is currently in beta, so only snapshots are available.

Add the following repository
```kts
maven { url = uri("https://s01.oss.sonatype.org/content/repositories/snapshots") }
```

## Goals

The intention is to provide an easy-to-use API that supports a wide range of Lemmy instances.
The backwards compatibility is achieved by transforming the requests and responses to a "universal" type.
And by allowing you to check if a feature is supported by the instance.
That way you can change the behavior of your app depending on the instance's version.

It is a non-goal to provide a stable API. The API can change with every iteration without warning nor deprecation.

## Extra features

- JVM datatypes implement `Serializable`
- Android datatypes implement `Parcelable` and `Serializable`

## Backwards Compatibility Strategy

The API is backwards compatible by using the following strategy:
- API route gets added.
Add a function that returns if this feature is supported.
Older versions implement this route by throwing an error (nonSupported).
- API route gets removed.
newer versions implement this route by throwing an error (nonSupported).
Is added to the `oldRoutes` interface
- API routes its request/response changes.
For this, we transform response/requests to a "universal" type.
Concrete this means, it will usually be the modified latest datatypes.
So that the response will be the same regardless of which version.
Here are some examples from how this will look concrete:
- [Move admin flag from person to local_user](https://github.com/LemmyNet/lemmy/pull/3403), pre 0.19 version APIs will map their datatype to the latest datatype by moving that field from person to local_user
- ... TODO: add more examples
- Enum entries keep an added/removed version.
Using get `getSupportedEntries` we can retrieve the supported entries for a given enum.
This is useful, for example, for sorting, where the sorting options can change between versions.

## AutoGenerated Code

To minimize the maintenance burden, many aspects have been automated.

This is done through kotlinscripts which are located in the `GeneratorScripts` submodule

There is 3 main scripts:
- `GenTypes`: This script updates the datatypes for the set package version (ex: v0x19).
It does this by downloading the TS types from [lemmy-js-client](https://github.com/LemmyNet/lemmy-js-client).
And applying the transformations (see [here](./docs/types_transformations.md)) to the types. This script does require that you have downloaded [dukat](https://github.com/Kotlin/dukat)
- `GenRoutes`: This script generates templates for the routes, LemmyApiService and its implementation. It will output it to `temp/` and you can copy what you need.
It does this by extracting the routes from [lemmy_openapi_spec](https://github.com/MV-GH/lemmy_openapi_spec)
- `GenMapperRoutes`: This script is a bit more complex. To prevent having to manually write all the basic transformations between datatypes of different versions.
We can automatically generate them with [Konvert](https://github.com/mcarleio/konvert).
This is done by having a definition file, in this case it is just a Interface `MapperGenerator`. Uncomment the annotations and build the project.
The mappings will be generated in the build folder. Then you can copy them to the appropriate Transformer class.
Now to prevent having to manually write the definition file, we can generate it with `GenMapperRoutes`. This will output them to the `temp/` folder.
And these are generated by comparing the datatypes from the given source package version and the given target package version.
Datatypes, which exist in both, will have a mapping generated.

[badge-android]: http://img.shields.io/badge/-android-6EDB8D.svg?style=flat
[badge-android-native]: http://img.shields.io/badge/support-[AndroidNative]-6EDB8D.svg?style=flat
[badge-wearos]: http://img.shields.io/badge/-wearos-8ECDA0.svg?style=flat
[badge-jvm]: http://img.shields.io/badge/-jvm-DB413D.svg?style=flat
[badge-js]: http://img.shields.io/badge/-js-F8DB5D.svg?style=flat
[badge-js-ir]: https://img.shields.io/badge/support-[IR]-AAC4E0.svg?style=flat
[badge-nodejs]: https://img.shields.io/badge/-nodejs-68a063.svg?style=flat
[badge-linux]: http://img.shields.io/badge/-linux-2D3F6C.svg?style=flat
[badge-windows]: http://img.shields.io/badge/-windows-4D76CD.svg?style=flat
[badge-wasm]: https://img.shields.io/badge/-wasm-624FE8.svg?style=flat
[badge-apple-silicon]: http://img.shields.io/badge/support-[AppleSilicon]-43BBFF.svg?style=flat
[badge-ios]: http://img.shields.io/badge/-ios-CDCDCD.svg?style=flat
[badge-mac]: http://img.shields.io/badge/-macos-111111.svg?style=flat
[badge-watchos]: http://img.shields.io/badge/-watchos-C0C0C0.svg?style=flat
[badge-tvos]: http://img.shields.io/badge/-tvos-808080.svg?style=flat