Unofficial 🐘 client written in 🎯

Overview

mastodon_dart

The official Dart library for accessing the Mastodon API. Optionally use in conjunction with mastodon_flutter to build a Flutter Mastodon app.

Mastodon API documentation: https://docs.joinmastodon.org/api

Status

This package is in development. Use in production at your own risk. That said, development is active and most Mastodon features are currently supported.

Mocking

This library includes a powerful mocking sub-library that lets you quickly build out Mastodon apps using fake data. Once you're ready to use real data, simply switch from the mock library to the real one.

Contributing

Create an issue, back it with a PR, and tag an active contributor.

Example

Updated example code coming soon

Comments
  • Package is discontinued until Mastodon provides an OpenAPI spec

    Package is discontinued until Mastodon provides an OpenAPI spec

    After some internal discussions we decided that we are no longer willing to support mastodon_dart. The reason is because keeping up with the Mastodon API is too much work without them having an official OpenAPI spec. If the Mastodon team decides to make an OpenAPI spec available we will reconsider supporting mastodon_dart.

    Related: https://github.com/tootsuite/mastodon/issues/1404

    opened by lukepighetti 9
  • Handle malformed Card#authorUrl parsing

    Handle malformed Card#authorUrl parsing

    I ran across https://mastodon.social/@GIbiz/109626791400616879 which returns a malformed author_url value.

    "author_url": "[\"https://www.gamesindustry.biz/authors/brendan-sinclair\", \"https://twitter.com/BrendanSinclair\"]",
    
    opened by abraham 6
  • TimelineBloc does not like Poll entities

    TimelineBloc does not like Poll entities

    Steps to reproduce:

    1. Check out the add_missing_entity_data branch
    2. Run the mastodon_flutter example app while depending on mastodon_dart from path
    3. The below stack trace will appear in the console

    Stack trace:

    E/flutter ( 1696): [ERROR:flutter/lib/ui/ui_dart_state.cc(157)] Unhandled Exception: type 'List<dynamic>' is not a subtype of type 'Map<String, dynamic>' in type cast
    E/flutter ( 1696): #0      _$PollFromJson (package:mastodon_dart/src/data/poll.g.dart:21:31)
    E/flutter ( 1696): #1      new Poll.fromJson (package:mastodon_dart/src/data/poll.dart:69:55)
    E/flutter ( 1696): #2      _$StatusFromJson (package:mastodon_dart/src/data/status.g.dart:55:16)
    E/flutter ( 1696): #3      new Status.fromJson (package:mastodon_dart/src/data/status.dart:170:57)
    E/flutter ( 1696): #4      Timelines.publicTimeline.<anonymous closure> (package:mastodon_dart/src/endpoints/timelines.dart:92:55)
    E/flutter ( 1696): #5      MappedListIterable.elementAt (dart:_internal/iterable.dart:417:31)
    E/flutter ( 1696): #6      ListIterator.moveNext (dart:_internal/iterable.dart:346:26)
    E/flutter ( 1696): #7      new List.from (dart:core-patch/array_patch.dart:54:19)
    E/flutter ( 1696): #8      Timelines.publicTimeline (package:mastodon_dart/src/endpoints/timelines.dart:91:12)
    E/flutter ( 1696): <asynchronous suspension>
    E/flutter ( 1696): #9      _LocalTimelineState.updateTimelineBloc.<anonymous closure> (package:jiminy_for_mastodon/screens/timelines/local_timeline.dart:61:49)
    E/flutter ( 1696): #10     TimelineBloc._handleRequest (package:mastodon_dart/src/bloc/timeline.dart:40:42)
    E/flutter ( 1696): #11     _rootRunUnary (dart:async/zone.dart:1192:38)
    E/flutter ( 1696): #12     _CustomZone.runUnary (dart:async/zone.dart:1085:19)
    E/flutter ( 1696): #13     _CustomZone.runUnaryGuarded (dart:async/zone.dart:987:7)
    E/flutter ( 1696): #14     _BufferingStreamSubscription._sendData (dart:async/stream_impl.dart:339:11)
    E/flutter ( 1696): #15     _BufferingStreamSubscription._add (dart:async/stream_impl.dart:266:7)
    E/flutter ( 1696): #16     _SyncStreamControllerDispatch._sendData (dart:async/stream_controller.dart:779:19)
    E/flutter ( 1696): #17     _StreamController._add (dart:async/stream_controller.dart:655:7)
    E/flutter ( 1696): #18     _StreamController.add (dart:async/stream_controller.dart:597:5)
    E/flutter ( 1696): #19     BackpressureStreamTransformer._buildTransformer.<anonymous closure>.<anonymous closure>.<anonymous closure> (package:rxdart/src/transformers/backpressure/backpressure.dart:99:53)
    E/flutter ( 1696): #20     BackpressureStreamTransformer._buildTransformer.<anonymous closure>.<anonymous closure>.<anonymous closure> (package:rxdart/src/transformers/backpressure/backpressure.dart:214:39)
    E/flutter ( 1696): #21     BackpressureStreamTransformer._buildTransformer.<anonymous closure>.<anonymous closure>.<anonymous closure> (package:rxdart/src/transformers/backpressure/backpressure.dart:249:32)
    E/flutter ( 1696): #22     _rootRunUnary (dart:async/zone.dart:1192:38)
    E/flutter ( 1696): #23     _CustomZone.runUnary (dart:async/zone.dart:1085:19)
    E/flutter ( 1696): #24     _CustomZone.runUnaryGuarded (dart:async/zone.dart:987:7)
    E/flutter ( 1696): #25     _BufferingStreamSubscription._sendData (dart:async/stream_impl.dart:339:11)
    E/flutter ( 1696): #26     _BufferingStreamSubscription._add (dart:async/stream_impl.dart:266:7)
    E/flutter ( 1696): #27     _ForwardingStreamSubscription._add (dart:async/stream_pipe.dart:134:11)
    E/flutter ( 1696): #28     _WhereStream._handleData (dart:async/stream_pipe.dart:209:12)
    E/flutter ( 1696): #29     _ForwardingStreamSubscription._handleData (dart:async/stream_pipe.dart:166:13)
    E/flutter ( 1696): #30     _rootRunUnary (dart:async/zone.dart:1192:38)
    E/flutter ( 1696): #31     _CustomZone.runUnary (dart:async/zone.dart:1085:19)
    E/flutter ( 1696): #32     _CustomZone.runUnaryGuarded (dart:async/zone.dart:987:7)
    E/flutter ( 1696): #33     _BufferingStreamSubscription._sendData (dart:async/stream_impl.dart:339:11)
    E/flutter ( 1696): #34     _DelayedData.perform (dart:async/stream_impl.dart:594:14)
    E/flutter ( 1696): #35     _StreamImplEvents.handleNext (dart:async/stream_impl.dart:710:11)
    E/flutter ( 1696): #36     _PendingEvents.schedule.<anonymous closure> (dart:async/stream_impl.dart:670:7)
    E/flutter ( 1696): #37     _rootRun (dart:async/zone.dart:1180:38)
    E/flutter ( 1696): #38     _CustomZone.run (dart:async/zone.dart:1077:19)
    E/flutter ( 1696): #39     _CustomZone.runGuarded (dart:async/zone.dart:979:7)
    E/flutter ( 1696): #40     _CustomZone.bindCallbackGuarded.<anonymous closure> (dart:async/zone.dart:1019:23)
    E/flutter ( 1696): #41     _rootRun (dart:async/zone.dart:1184:13)
    E/flutter ( 1696): #42     _CustomZone.run (dart:async/zone.dart:1077:19)
    E/flutter ( 1696): #43     _CustomZone.runGuarded (dart:async/zone.dart:979:7)
    E/flutter ( 1696): #44     _CustomZone.bindCallbackGuarded.<anonymous closure> (dart:async/zone.dart:1019:23)
    E/flutter ( 1696): #45     _microtaskLoop (dart:async/schedule_microtask.dart:43:21)
    E/flutter ( 1696): #46     _startMicrotaskLoop (dart:async/schedule_microtask.dart:52:5)
    E/flutter ( 1696): 
    
    bug 
    opened by GroovinChip 4
  • Add admin entities/functionality

    Add admin entities/functionality

    Relates to #14

    DISCUSSION: Currently we have zero support for admin related things. @lukepighetti do you think we should add admin support to existing entities or make them separate?

    todo:

    • [ ] Add admin endpoints, regular and mock https://docs.joinmastodon.org/methods/admin/
    • [ ] Resolve discussion about whether to add admin support to existing entities or to make separate admin entities
    enhancement 
    opened by GroovinChip 4
  • When building my app on a new machine, I get the following error after copying my token and returning to the app

    When building my app on a new machine, I get the following error after copying my token and returning to the app

    E/flutter (21006): [ERROR:flutter/shell/common/shell.cc(186)] Dart Error: Unhandled exception:
    E/flutter (21006): Unsupported operation: Cannot modify an unmodifiable Map
    E/flutter (21006): #0      _ImmutableMap.removeWhere (dart:core/runtime/libimmutable_map.dart:118:5)
    E/flutter (21006): #1      __Base&Authentication&Utilities.request (package:mastodon/src/utilities.dart:23:31)
    E/flutter (21006): <asynchronous suspension>
    E/flutter (21006): #2      _Mastodon&_Base&Accounts.verifyCredentials (package:mastodon/src/endpoints/accounts.dart:57:28)
    E/flutter (21006): <asynchronous suspension>
    E/flutter (21006): #3      AuthBloc._handleToken (package:mastodon/src/bloc/auth.dart:131:38)
    E/flutter (21006): <asynchronous suspension>
    E/flutter (21006): #4      _RootZone.runUnaryGuarded (dart:async/zone.dart:1314:10)
    E/flutter (21006): #5      _BufferingStreamSubscription._sendData (dart:async/stream_impl.dart:336:11)
    E/flutter (21006): #6      _DelayedData.perform (dart:async/stream_impl.dart:591:14)
    E/flutter (21006): #7      _StreamImplEvents.handleNext (dart:async/stream_impl.dart:707:11)
    E/flutter (21006): #8      _PendingEvents.schedule.<anonymous closure> (dart:async/stream_impl.dart:667:7)
    E/flutter (21006): #9      _microtaskLoop (dart:async/schedule_microtask.dart:41:21)
    E/flutter (21006): #10     _startMicrotaskLoop (dart:async/schedule_microtask.dart:50:5)```
    opened by GroovinChip 3
  • Implement Timelines.listTimeline()

    Implement Timelines.listTimeline()

    https://docs.joinmastodon.org/methods/timelines/lists/

    https://github.com/lukepighetti/mastodon-dart/blob/76cc1dd6917d0bcc14757cdf99f83d7d781c9d76/lib/src/endpoints/timelines.dart#L130-L146

    good first issue 
    opened by lukepighetti 2
  • Update Marker to use JsonSerializable

    Update Marker to use JsonSerializable

    Builds on https://github.com/lukepighetti/mastodon_dart/pull/53

    • Switch them to JsonSerializable
    • Rename Marker to Markers
    • Rename Position to Marker
    • Update Marker attribute types
    opened by abraham 1
  • Add rest constructor

    Add rest constructor

    Adds named constructor to instantiate without websocket.

    Mastodon.rest(Uri.parse('https://mastodon.social'));
    

    Alternative to https://github.com/lukepighetti/mastodon_dart/pull/45

    opened by abraham 1
  • null safety

    null safety

    This PR

    • removes BLoCs (this repo is going 100% stateless)
    • removes mocks
    • migrates to null safety
    • updates all deps
    • removes unused deps
    • removes library.dart
    • renames src/data to src/models
    • removes dead example
    opened by lukepighetti 1
  • Add blurhash to media model

    Add blurhash to media model

    https://docs.joinmastodon.org/methods/statuses/media/

    {
      "id": "22348641",
      "type": "image",
      "url": "https://files.mastodon.social/media_attachments/files/022/348/641/original/cebc6d51be03e509.jpeg",
      "preview_url": "https://files.mastodon.social/media_attachments/files/022/348/641/small/cebc6d51be03e509.jpeg",
      "remote_url": null,
      "text_url": "https://mastodon.social/media/4Zj6ewxzzzDi0g8JnZQ",
      "meta": {
        "focus": {
          "x": -0.69,
          "y": 0.42
        },
        "original": {
          "width": 640,
          "height": 480,
          "size": "640x480",
          "aspect": 1.3333333333333333
        },
        "small": {
          "width": 461,
          "height": 346,
          "size": "461x346",
          "aspect": 1.3323699421965318
        }
      },
      "description": "test uploaded via api",
      "blurhash": "UFBWY:8_0Jxv4mx]t8t64.%M-:IUWGWAt6M}" //////////////////////////////////
    }
    

    context https://github.com/woltapp/blurhash https://blurha.sh

    opened by lukepighetti 1
  • Add error entity?

    Add error entity?

    Related to #14

    Is this needed? I've seen this error get printed in the console, I don't know that we need this as its own entity.

    What do you think @lukepighetti

    opened by GroovinChip 1
  • Handle parsing exceptions

    Handle parsing exceptions

    I expect API response formats to become more divergent and buggy as more servers and forks of Mastodon popup. Currently if you request a timeline and one posts triggers a parsing exception (like #51) the entire response is lost. I'd like to see a way to get all the successful statuses and a list of exceptions for the failed statuses. This way users can be shown most of the content and the option to report parse issues to developers.

    I'm noodling something similar to the following. What do you think?

    class StatusException {
      final Exception exception;
      final String unparsed;
      final String? id;
      final Uri? uri;
      final String? attribute;
    
      StatusException({
        required this.exception,
        required this.unparsed,
        this.id,
        this.uri,
        this.attribute,
      });
    }
    
    class Response {
      final List<Status> statuses;
      final List<StatusException> exceptions;
    
      Response({
        required this.statuses,
        this.exceptions = const [],
      });
    }
    
    client.partialReponse = true; // some way of enabling partial responses
    final Response response = await client.timeline();
    
    opened by abraham 1
Owner
Luke Pighetti
Mobile engineer
Luke Pighetti
Vrchat mobile client - VRChat Unofficial Mobile Client For Flutter

VRChatMC VRChatの非公式なAPIを利用したVRChatのモバイルクライアント Flutterで作成されたシンプルなUIが特徴的です iosビルドは

ふぁ 8 Sep 28, 2022
unofficial windows client for smotreshka.tv

smotreshka Rebuild models flutter pub run build_runner build --delete-conflicting-outputs Getting Started This project is a starting point for a Flut

null 0 Dec 3, 2021
An open-source unofficial GitHub mobile client, that aims to deliver the ultimate GitHub experience on mobile devices.

DioHub for Github Summary Features Roadmap Support Screenshots Build Instructions Summary DioHub is an open-source unofficial GitHub mobile client, th

Naman Shergill 401 Jan 4, 2023
Flathub-desktop - Unofficial Desktop Client for Flathub

Flathub Desktop Unofficial Desktop Client for Flathub How to build and run: You

Jean3219 2 Sep 19, 2022
An unofficial, platform independent, client for accessing different AI models developed by OpenAI

The OpenAI API can be applied to virtually any task that involves understanding or generating natural language or code. They offer a spectrum of model

Francesco Coppola 14 Dec 30, 2022
An unofficial wrapper for the kdecole api

This is an UNOFFICIAL wrapper for the kdecole api How to use ? Login First, you need to create a Client() object : LOGIN AND PASSWORD ARE NOT YOUR ENT

null 5 Nov 2, 2022
The unofficial flutter plugin for Freshchat

?? Flutter Freshchat A Flutter plugin for integrating Freshchat in your mobile app. Setup Android Add this to your AndroidManifest.xml <provider a

Fayeed Pawaskar 31 Jun 2, 2022
Unofficial delivery app for Rapidinho made with Flutter

Rapidinho Unofficial delivery app for Rapidinho made with Flutter Getting Started Gradle version: 4.6 Flutter version: 0.8.3 Install Flutter Clone thi

GDG Luanda 190 Dec 26, 2022
Unofficial Turkish Dictionary app of TDK (Turkish Language Association) developing with Flutter

Turkish Dictionary Unofficial Turkish Dictionary app of TDK (Turkish Language Association) developing with Flutter Design Feyza Nur Demirci Şahin Abut

Flutter Turkey 80 Oct 20, 2022
Unofficial wrapper for using Rapid7 insightOps logs (former LogEntries) with Dart.

An unofficial wrapper for using Rapid7 insightOps logs (former LogEntries) with Dart. This package is using logging package to do the actual logging,

Kirill Bubochkin 2 Mar 3, 2021
Flutter & Dart Unofficial Flat Data API

Flutter & Dart Unofficial Flat Data API Flat Dataset for different helpful Flutter APIs Flutter Releases Currently does a daily snapshot of the Flutte

Leo Farias 21 Dec 26, 2022
An unofficial Flutter plugin that wraps pusher-websocket-java on Android and pusher-websocket-swift on iOS

Pusher Flutter Client An unofficial Flutter plugin that wraps pusher-websocket-java on Android and pusher-websocket-swift on iOS. Get it from pub. How

HomeX 31 Oct 21, 2022
Unofficial KronoX app for Android and iOS

School Schedule Unofficial KronoX app for Android and iOS made using Flutter Supported Platforms The app is available on Google Play. It's not availab

kraxie 8 Oct 31, 2022
VerificaC19-flutter - Unofficial EU DGC validation package for Flutter

VerificaC19 package for Flutter About This package allows to decode and validate

Federico Mastrini 13 Oct 21, 2022
Flutter list view - An unofficial list view for flutter

Flutter List View I don't like official list view. There are some features don't

null 24 Dec 15, 2022
Federico 1 Feb 3, 2022
An unofficial nhentai app.

Eros-N English | 简体中文 Introduction An unofficial Nhentai app. Features Front page User login Favorites View gallery Gallery tags More view settings Do

null 131 Jan 9, 2023
A streaming client for the Komga self-hosted comics/manga/BD server targeting Android/iOS written in Dart/Flutter

Klutter A streaming client for the Komga self-hosted comics/manga/BD server targeting Android/iOS written in Dart/Flutter Background This is a project

Mark Winckle 58 Dec 7, 2022
a project-m36 websocket client written by flutter/dart

project_m36_websocket_client A Flutter web websocket client for Project-M36. It's also an attempt to bring algebraic datatypes into the Dart land. Pro

null 1 Jan 8, 2022