kopia lustrzana https://github.com/halcy/Mastodon.py
Merge branch 'master' of github.com:halcy/Mastodon.py
commit
137cf49435
|
@ -64,13 +64,14 @@ from .push import Mastodon as Push
|
|||
from .admin import Mastodon as Admin
|
||||
from .streaming_endpoints import Mastodon as Streaming
|
||||
|
||||
|
||||
###
|
||||
# The actual Mastodon class
|
||||
#
|
||||
# Almost all code is now imported from smaller files to make editing a bit more pleasant
|
||||
###
|
||||
class Mastodon(Utility, Authentication, Accounts, Instance, Timeline, Statuses, Polls, Notifications, Hashtags,
|
||||
Filters, Suggestions, Endorsements, Relationships, Lists, Trends, Search, Favourites, Reports,
|
||||
class Mastodon(Utility, Authentication, Accounts, Instance, Timeline, Statuses, Polls, Notifications, Hashtags,
|
||||
Filters, Suggestions, Endorsements, Relationships, Lists, Trends, Search, Favourites, Reports,
|
||||
Preferences, Push, Admin, Conversations, Media, Streaming):
|
||||
"""
|
||||
Thorough and easy to use Mastodon
|
||||
|
|
|
@ -9,6 +9,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
@api_version("2.7.0", "2.7.0", "3.4.0")
|
||||
def create_account(self, username, password, email, agreement=False, reason=None, locale="en", scopes=_DEFAULT_SCOPES, to_file=None, return_detailed_error=False):
|
||||
|
@ -16,8 +17,8 @@ class Mastodon(Internals):
|
|||
Creates a new user account with the given username, password and email. "agreement"
|
||||
must be set to true (after showing the user the instance's user agreement and having
|
||||
them agree to it), "locale" specifies the language for the confirmation email as an
|
||||
ISO 639-1 (two letter) or, if a language does not have one, 639-3 (three letter) language
|
||||
code. `reason` can be used to specify why a user would like to join if approved-registrations
|
||||
ISO 639-1 (two letter) or, if a language does not have one, 639-3 (three letter) language
|
||||
code. `reason` can be used to specify why a user would like to join if approved-registrations
|
||||
mode is on.
|
||||
|
||||
Does not require an access token, but does require a client grant.
|
||||
|
@ -30,11 +31,11 @@ class Mastodon(Internals):
|
|||
|
||||
By default, the function will throw if the account could not be created. Alternately,
|
||||
when `return_detailed_error` is passed, Mastodon.py will return the detailed error
|
||||
response that the API provides (Starting from version 3.4.0 - not checked here) as an dict with
|
||||
error details as the second return value and the token returned as `None` in case of error.
|
||||
The dict will contain a text `error` values as well as a `details` value which is a dict with
|
||||
one optional key for each potential field (`username`, `password`, `email` and `agreement`),
|
||||
each if present containing a dict with an `error` category and free text `description`.
|
||||
response that the API provides (Starting from version 3.4.0 - not checked here) as an dict with
|
||||
error details as the second return value and the token returned as `None` in case of error.
|
||||
The dict will contain a text `error` values as well as a `details` value which is a dict with
|
||||
one optional key for each potential field (`username`, `password`, `email` and `agreement`),
|
||||
each if present containing a dict with an `error` category and free text `description`.
|
||||
Valid error categories are:
|
||||
|
||||
* ERR_BLOCKED - When e-mail provider is not allowed
|
||||
|
@ -77,7 +78,7 @@ class Mastodon(Internals):
|
|||
raise MastodonIllegalArgumentError(f'Invalid request: {e}')
|
||||
self.access_token = response['access_token']
|
||||
self.__set_refresh_token(response.get('refresh_token'))
|
||||
self.__set_token_expired(int(response.get('expires_in', 0)))
|
||||
self.__set_token_expired(int(response.get('expires_in', 0)))
|
||||
except Exception as e:
|
||||
raise MastodonIllegalArgumentError('Invalid request')
|
||||
|
||||
|
@ -274,14 +275,14 @@ class Mastodon(Internals):
|
|||
def account_lookup(self, acct):
|
||||
"""
|
||||
Look up an account from user@instance form (@instance allowed but not required for
|
||||
local accounts). Will only return accounts that the instance already knows about,
|
||||
and not do any webfinger requests. Use `account_search` if you need to resolve users
|
||||
local accounts). Will only return accounts that the instance already knows about,
|
||||
and not do any webfinger requests. Use `account_search` if you need to resolve users
|
||||
through webfinger from remote.
|
||||
|
||||
Returns an :ref:`account dict <account dict>`.
|
||||
"""
|
||||
return self.__api_request('GET', '/api/v1/accounts/lookup', self.__generate_params(locals()))
|
||||
|
||||
|
||||
@api_version("3.5.0", "3.5.0", _DICT_VERSION_FAMILIAR_FOLLOWERS)
|
||||
def account_familiar_followers(self, id):
|
||||
"""
|
||||
|
@ -347,7 +348,6 @@ class Mastodon(Internals):
|
|||
"""
|
||||
id = self.__unpack_id(id)
|
||||
return self.__api_request('POST', f'/api/v1/accounts/{id}/remove_from_followers')
|
||||
|
||||
|
||||
@api_version("1.0.0", "1.4.0", _DICT_VERSION_RELATIONSHIP)
|
||||
def account_block(self, id):
|
||||
|
|
|
@ -7,12 +7,13 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Moderation API
|
||||
###
|
||||
@api_version("2.9.1", "4.0.0", _DICT_VERSION_ADMIN_ACCOUNT)
|
||||
def admin_accounts_v2(self, origin=None, by_domain=None, status=None, username=None, display_name=None, email=None, ip=None,
|
||||
def admin_accounts_v2(self, origin=None, by_domain=None, status=None, username=None, display_name=None, email=None, ip=None,
|
||||
permissions=None, invited_by=None, role_ids=None, max_id=None, min_id=None, since_id=None, limit=None):
|
||||
"""
|
||||
Fetches a list of accounts that match given criteria. By default, local accounts are returned.
|
||||
|
@ -65,8 +66,8 @@ class Mastodon(Internals):
|
|||
@api_version("2.9.1", "2.9.1", _DICT_VERSION_ADMIN_ACCOUNT)
|
||||
def admin_accounts(self, remote=False, by_domain=None, status='active', username=None, display_name=None, email=None, ip=None, staff_only=False, max_id=None, min_id=None, since_id=None, limit=None):
|
||||
"""
|
||||
Currently a synonym for admin_accounts_v1, now deprecated. You are strongly encouraged to use admin_accounts_v2 instead, since this one is kind of bad.
|
||||
|
||||
Currently a synonym for admin_accounts_v1, now deprecated. You are strongly encouraged to use admin_accounts_v2 instead, since this one is kind of bad.
|
||||
|
||||
!!!!! This function may be switched to calling the v2 API in the future. This is your warning. If you want to keep using v1, use it explicitly. !!!!!
|
||||
"""
|
||||
return self.admin_accounts_v1(
|
||||
|
@ -377,16 +378,16 @@ class Mastodon(Internals):
|
|||
id = self.__unpack_id(id)
|
||||
return self.__api_request('GET', f'/api/v1/admin/domain_blocks/{id}')
|
||||
else:
|
||||
params = self.__generate_params(locals(),['limit'])
|
||||
params = self.__generate_params(locals(), ['limit'])
|
||||
return self.__api_request('GET', '/api/v1/admin/domain_blocks/', params)
|
||||
|
||||
|
||||
@api_version("4.0.0", "4.0.0", _DICT_VERSION_ADMIN_DOMAIN_BLOCK)
|
||||
def admin_create_domain_block(self, domain:str, severity:str=None, reject_media:bool=None, reject_reports:bool=None, private_comment:str=None, public_comment:str=None, obfuscate:bool=None):
|
||||
"""
|
||||
Perform a moderation action on a domain. Requires scope `admin:write:domain_blocks`.
|
||||
|
||||
Valid severities are:
|
||||
* "silence" - hide all posts from federated timelines and do not show notifications to local users from the remote instance's users unless they are following the remote user.
|
||||
* "silence" - hide all posts from federated timelines and do not show notifications to local users from the remote instance's users unless they are following the remote user.
|
||||
* "suspend" - deny interactions with this instance going forward. This action is reversible.
|
||||
* "limit" - generally used with reject_media=true to force reject media from an instance without silencing or suspending..
|
||||
|
||||
|
@ -411,7 +412,7 @@ class Mastodon(Internals):
|
|||
Modify existing moderation action on a domain. Requires scope `admin:write:domain_blocks`.
|
||||
|
||||
Valid severities are:
|
||||
* "silence" - hide all posts from federated timelines and do not show notifications to local users from the remote instance's users unless they are following the remote user.
|
||||
* "silence" - hide all posts from federated timelines and do not show notifications to local users from the remote instance's users unless they are following the remote user.
|
||||
* "suspend" - deny interactions with this instance going forward. This action is reversible.
|
||||
* "limit" - generally used with reject_media=true to force reject media from an instance without silencing or suspending.
|
||||
|
||||
|
@ -481,7 +482,7 @@ class Mastodon(Internals):
|
|||
for key in ["active_users", "new_users", "interactions", "opened_reports", "resolved_reports"]:
|
||||
if params_init[key] == True:
|
||||
keys.append(key)
|
||||
|
||||
|
||||
params = {}
|
||||
for key in ["tag_accounts", "tag_uses", "tag_servers"]:
|
||||
if params_init[key] is not None:
|
||||
|
@ -498,7 +499,7 @@ class Mastodon(Internals):
|
|||
params["keys"] = keys
|
||||
params["start_at"] = self.__consistent_isoformat_utc(start_at)
|
||||
params["end_at"] = self.__consistent_isoformat_utc(end_at)
|
||||
|
||||
|
||||
return self.__api_request('POST', '/api/v1/admin/measures', params, use_json=True)
|
||||
|
||||
@api_version("3.5.0", "3.5.0", _DICT_VERSION_ADMIN_DIMENSION)
|
||||
|
@ -531,7 +532,7 @@ class Mastodon(Internals):
|
|||
for key in ["languages", "sources", "servers", "space_usage", "software_versions"]:
|
||||
if params_init[key] == True:
|
||||
keys.append(key)
|
||||
|
||||
|
||||
params = {}
|
||||
for key in ["tag_servers", "tag_languages"]:
|
||||
if params_init[key] is not None:
|
||||
|
@ -550,7 +551,7 @@ class Mastodon(Internals):
|
|||
params["limit"] = limit
|
||||
params["start_at"] = self.__consistent_isoformat_utc(start_at)
|
||||
params["end_at"] = self.__consistent_isoformat_utc(end_at)
|
||||
|
||||
|
||||
return self.__api_request('POST', '/api/v1/admin/dimensions', params, use_json=True)
|
||||
|
||||
@api_version("3.5.0", "3.5.0", _DICT_VERSION_ADMIN_RETENTION)
|
||||
|
@ -568,4 +569,4 @@ class Mastodon(Internals):
|
|||
"end_at": self.__consistent_isoformat_utc(end_at),
|
||||
"frequency": frequency
|
||||
}
|
||||
return self.__api_request('POST', '/api/v1/admin/retention', params)
|
||||
return self.__api_request('POST', '/api/v1/admin/retention', params)
|
||||
|
|
|
@ -14,6 +14,7 @@ from .utility import parse_version_string, api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Registering apps
|
||||
|
@ -45,7 +46,7 @@ class Mastodon(Internals):
|
|||
Returns `client_id` and `client_secret`, both as strings.
|
||||
"""
|
||||
if api_base_url is None:
|
||||
raise MastodonIllegalArgumentError("API base URL is required.")
|
||||
raise MastodonIllegalArgumentError("API base URL is required.")
|
||||
api_base_url = Mastodon.__protocolize(api_base_url)
|
||||
|
||||
request_data = {
|
||||
|
@ -91,9 +92,9 @@ class Mastodon(Internals):
|
|||
version_check_mode="created", session=None, feature_set="mainline", user_agent=_DEFAULT_USER_AGENT, lang=None):
|
||||
"""
|
||||
Create a new API wrapper instance based on the given `client_secret` and `client_id` on the
|
||||
instance given by `api_base_url`. If you give a `client_id` and it is not a file, you must
|
||||
instance given by `api_base_url`. If you give a `client_id` and it is not a file, you must
|
||||
also give a secret. If you specify an `access_token` then you don't need to specify a `client_id`.
|
||||
It is allowed to specify neither - in this case, you will be restricted to only using endpoints
|
||||
It is allowed to specify neither - in this case, you will be restricted to only using endpoints
|
||||
that do not require authentication. If a file is given as `client_id`, client ID, secret and
|
||||
base url are read from that file.
|
||||
|
||||
|
@ -221,7 +222,7 @@ class Mastodon(Internals):
|
|||
|
||||
# Verify we have a base URL, protocolize
|
||||
if self.api_base_url is None:
|
||||
raise MastodonIllegalArgumentError("API base URL is required.")
|
||||
raise MastodonIllegalArgumentError("API base URL is required.")
|
||||
self.api_base_url = Mastodon.__protocolize(self.api_base_url)
|
||||
|
||||
if not version_check_mode in ["created", "changed", "none"]:
|
||||
|
|
|
@ -5,7 +5,8 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
class Mastodon(Internals):
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Conversations
|
||||
###
|
||||
|
|
|
@ -62,4 +62,4 @@ _SCOPE_SETS = {
|
|||
}
|
||||
_VALID_SCOPES = ['read', 'write', 'follow', 'push', 'admin:read', 'admin:write'] + \
|
||||
_SCOPE_SETS['read'] + _SCOPE_SETS['write'] + \
|
||||
_SCOPE_SETS['admin:read'] + _SCOPE_SETS['admin:write']
|
||||
_SCOPE_SETS['admin:read'] + _SCOPE_SETS['admin:write']
|
||||
|
|
|
@ -5,7 +5,8 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
class Mastodon(Internals):
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Endorsements
|
||||
###
|
||||
|
|
|
@ -5,6 +5,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Favourites
|
||||
|
@ -59,4 +60,3 @@ class Mastodon(Internals):
|
|||
|
||||
params = self.__generate_params(locals())
|
||||
return self.__api_request('GET', '/api/v1/bookmarks', params)
|
||||
|
||||
|
|
|
@ -8,6 +8,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Keyword filters
|
||||
|
|
|
@ -5,6 +5,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Featured hashtags
|
||||
|
|
|
@ -7,6 +7,7 @@ from .compat import urlparse
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Instances
|
||||
|
|
|
@ -22,10 +22,11 @@ from .errors import MastodonNetworkError, MastodonIllegalArgumentError, Mastodon
|
|||
from .compat import urlparse, magic, PurePath
|
||||
from .defaults import _DEFAULT_STREAM_TIMEOUT, _DEFAULT_STREAM_RECONNECT_WAIT_SEC
|
||||
|
||||
|
||||
###
|
||||
# Internal helpers, dragons probably
|
||||
###
|
||||
class Mastodon():
|
||||
class Mastodon():
|
||||
def __datetime_to_epoch(self, date_time):
|
||||
"""
|
||||
Converts a python datetime to unix epoch, accounting for
|
||||
|
@ -37,7 +38,6 @@ class Mastodon():
|
|||
date_time = date_time.replace(tzinfo=datetime.timezone.utc)
|
||||
return date_time.timestamp()
|
||||
|
||||
|
||||
def __get_logged_in_id(self):
|
||||
"""
|
||||
Fetch the logged in user's ID, with caching. ID is reset on calls to log_in.
|
||||
|
@ -77,7 +77,7 @@ class Mastodon():
|
|||
mark_delete.append(k)
|
||||
# Two step process because otherwise python gets very upset
|
||||
for k in mark_delete:
|
||||
del json_object[k]
|
||||
del json_object[k]
|
||||
return json_object
|
||||
|
||||
@staticmethod
|
||||
|
@ -98,7 +98,7 @@ class Mastodon():
|
|||
"""
|
||||
Converts json string numerals to native python bignums.
|
||||
"""
|
||||
for key in ('id', 'week', 'in_reply_to_id', 'in_reply_to_account_id', 'logins', 'registrations', 'statuses',
|
||||
for key in ('id', 'week', 'in_reply_to_id', 'in_reply_to_account_id', 'logins', 'registrations', 'statuses',
|
||||
'day', 'last_read_id', 'value', 'frequency', 'rate', 'invited_by_account_id', 'count'):
|
||||
if (key in json_object and isinstance(json_object[key], six.text_type)):
|
||||
try:
|
||||
|
@ -131,14 +131,14 @@ class Mastodon():
|
|||
isotime = isotime[:-2] + ":" + isotime[-2:]
|
||||
return isotime
|
||||
|
||||
def __api_request(self, method, endpoint, params={}, files={}, headers={}, access_token_override=None, base_url_override=None,
|
||||
def __api_request(self, method, endpoint, params={}, files={}, headers={}, access_token_override=None, base_url_override=None,
|
||||
do_ratelimiting=True, use_json=False, parse=True, return_response_object=False, skip_error_check=False, lang_override=None):
|
||||
"""
|
||||
Internal API request helper.
|
||||
"""
|
||||
response = None
|
||||
remaining_wait = 0
|
||||
|
||||
|
||||
# Add language to params if not None
|
||||
lang = self.lang
|
||||
if lang_override is not None:
|
||||
|
@ -270,7 +270,7 @@ class Mastodon():
|
|||
time.sleep(to_next)
|
||||
request_complete = False
|
||||
continue
|
||||
|
||||
|
||||
if not skip_error_check:
|
||||
if response_object.status_code == 404:
|
||||
ex_type = MastodonNotFoundError
|
||||
|
@ -665,4 +665,4 @@ class Mastodon():
|
|||
return version_string.split("+")[1]
|
||||
except:
|
||||
# If this fails, assume that if there is a +, what is before that is the masto version (or that there is no +)
|
||||
return version_string.split("+")[0]
|
||||
return version_string.split("+")[0]
|
||||
|
|
|
@ -5,6 +5,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Lists
|
||||
|
|
|
@ -8,6 +8,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Media
|
||||
|
|
|
@ -6,6 +6,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Notifications
|
||||
|
@ -16,7 +17,7 @@ class Mastodon(Internals):
|
|||
Fetch notifications (mentions, favourites, reblogs, follows) for the logged-in
|
||||
user. Pass `account_id` to get only notifications originating from the given account.
|
||||
|
||||
There are different types of notifications:
|
||||
There are different types of notifications:
|
||||
* `follow` - A user followed the logged in user
|
||||
* `follow_request` - A user has requested to follow the logged in user (for locked accounts)
|
||||
* `favourite` - A user favourited a post by the logged in user
|
||||
|
@ -29,7 +30,7 @@ class Mastodon(Internals):
|
|||
* `admin.report` - For accounts with appropriate permissions (TODO: document which those are when adding the permission API): A new report has been received
|
||||
Parameters `exclude_types` and `types` are array of these types, specifying them will in- or exclude the
|
||||
types of notifications given. It is legal to give both parameters at the same tine, the result will then
|
||||
be the intersection of the results of both filters. Specifying `mentions_only` is a deprecated way to set
|
||||
be the intersection of the results of both filters. Specifying `mentions_only` is a deprecated way to set
|
||||
`exclude_types` to all but mentions.
|
||||
|
||||
Can be passed an `id` to fetch a single notification.
|
||||
|
|
|
@ -5,6 +5,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Polls
|
||||
|
@ -56,4 +57,4 @@ class Mastodon(Internals):
|
|||
"""
|
||||
poll_params = locals()
|
||||
del poll_params["self"]
|
||||
return poll_params
|
||||
return poll_params
|
||||
|
|
|
@ -8,6 +8,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Preferences
|
||||
|
@ -68,4 +69,3 @@ class Mastodon(Internals):
|
|||
params[timeline]["last_read_id"] = self.__unpack_id(last_read_id)
|
||||
|
||||
return self.__api_request('POST', '/api/v1/markers', params, use_json=True)
|
||||
|
|
@ -12,6 +12,7 @@ from .compat import IMPL_HAS_ECE, http_ece
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Webpush subscriptions
|
||||
|
@ -148,14 +149,14 @@ class Mastodon(Internals):
|
|||
|
||||
push_key_pair = ec.generate_private_key(ec.SECP256R1(), default_backend())
|
||||
push_key_priv = push_key_pair.private_numbers().private_value
|
||||
try:
|
||||
try:
|
||||
push_key_pub = push_key_pair.public_key().public_bytes(
|
||||
serialization.Encoding.X962,
|
||||
serialization.PublicFormat.UncompressedPoint,
|
||||
)
|
||||
except:
|
||||
push_key_pub = push_key_pair.public_key().public_numbers().encode_point()
|
||||
|
||||
|
||||
push_shared_secret = os.urandom(16)
|
||||
|
||||
priv_dict = {
|
||||
|
|
|
@ -5,6 +5,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Mutes and Blocks
|
||||
|
@ -131,4 +132,4 @@ class Mastodon(Internals):
|
|||
Remove a domain block for the logged-in user.
|
||||
"""
|
||||
params = self.__generate_params(locals())
|
||||
self.__api_request('DELETE', '/api/v1/domain_blocks', params)
|
||||
self.__api_request('DELETE', '/api/v1/domain_blocks', params)
|
||||
|
|
|
@ -7,6 +7,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Reports
|
||||
|
@ -59,4 +60,4 @@ class Mastodon(Internals):
|
|||
del params_initial['forward']
|
||||
|
||||
params = self.__generate_params(params_initial)
|
||||
return self.__api_request('POST', '/api/v1/reports/', params)
|
||||
return self.__api_request('POST', '/api/v1/reports/', params)
|
||||
|
|
|
@ -6,6 +6,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Searching
|
||||
|
|
|
@ -9,7 +9,8 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
class Mastodon(Internals):
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Statuses
|
||||
###
|
||||
|
@ -244,19 +245,19 @@ class Mastodon(Internals):
|
|||
|
||||
Returns a :ref:`status dict <status dict>` with the new status.
|
||||
"""
|
||||
return self.__status_internal(
|
||||
status,
|
||||
in_reply_to_id,
|
||||
media_ids,
|
||||
sensitive,
|
||||
visibility,
|
||||
spoiler_text,
|
||||
language,
|
||||
idempotency_key,
|
||||
content_type,
|
||||
scheduled_at,
|
||||
poll,
|
||||
quote_id,
|
||||
return self.__status_internal(
|
||||
status,
|
||||
in_reply_to_id,
|
||||
media_ids,
|
||||
sensitive,
|
||||
visibility,
|
||||
spoiler_text,
|
||||
language,
|
||||
idempotency_key,
|
||||
content_type,
|
||||
scheduled_at,
|
||||
poll,
|
||||
quote_id,
|
||||
edit=None
|
||||
)
|
||||
|
||||
|
@ -272,7 +273,7 @@ class Mastodon(Internals):
|
|||
return self.status_post(status)
|
||||
|
||||
@api_version("3.5.0", "3.5.0", _DICT_VERSION_STATUS)
|
||||
def status_update(self, id, status = None, spoiler_text = None, sensitive = None, media_ids = None, poll = None):
|
||||
def status_update(self, id, status=None, spoiler_text=None, sensitive=None, media_ids=None, poll=None):
|
||||
"""
|
||||
Edit a status. The meanings of the fields are largely the same as in :ref:`status_post() <status_post()>`,
|
||||
though not every field can be edited.
|
||||
|
@ -280,13 +281,13 @@ class Mastodon(Internals):
|
|||
Note that editing a poll will reset the votes.
|
||||
"""
|
||||
return self.__status_internal(
|
||||
status = status,
|
||||
media_ids = media_ids,
|
||||
sensitive = sensitive,
|
||||
spoiler_text = spoiler_text,
|
||||
poll = poll,
|
||||
edit = id
|
||||
)
|
||||
status=status,
|
||||
media_ids=media_ids,
|
||||
sensitive=sensitive,
|
||||
spoiler_text=spoiler_text,
|
||||
poll=poll,
|
||||
edit=id
|
||||
)
|
||||
|
||||
@api_version("3.5.0", "3.5.0", _DICT_VERSION_STATUS_EDIT)
|
||||
def status_history(self, id):
|
||||
|
@ -317,7 +318,7 @@ class Mastodon(Internals):
|
|||
scheduled_at=None, poll=None, untag=False):
|
||||
"""
|
||||
Helper function - acts like status_post, but prepends the name of all
|
||||
the users that are being replied to to the status text and retains
|
||||
the users that are being replied to the status text and retains
|
||||
CW and visibility if not explicitly overridden.
|
||||
|
||||
Note that `to_status` should be a :ref:`status dict <status dict>` and not an ID.
|
||||
|
|
|
@ -84,7 +84,7 @@ class StreamListener(object):
|
|||
contains the content of the unknown event.
|
||||
"""
|
||||
pass
|
||||
|
||||
|
||||
def handle_heartbeat(self):
|
||||
"""The server has sent us a keep-alive message. This callback may be
|
||||
useful to carry out periodic housekeeping tasks, or just to confirm
|
||||
|
@ -217,6 +217,7 @@ class StreamListener(object):
|
|||
else:
|
||||
handler(name, payload)
|
||||
|
||||
|
||||
class CallbackStreamListener(StreamListener):
|
||||
"""
|
||||
Simple callback stream handler class.
|
||||
|
@ -226,21 +227,20 @@ class CallbackStreamListener(StreamListener):
|
|||
for diagnostics.
|
||||
"""
|
||||
|
||||
def __init__(self,
|
||||
update_handler=None,
|
||||
local_update_handler=None,
|
||||
delete_handler=None,
|
||||
notification_handler=None,
|
||||
conversation_handler=None,
|
||||
unknown_event_handler=None,
|
||||
status_update_handler=None,
|
||||
filters_changed_handler=None,
|
||||
announcement_handler=None,
|
||||
announcement_reaction_handler=None,
|
||||
announcement_delete_handler=None,
|
||||
encryted_message_handler=None
|
||||
|
||||
):
|
||||
def __init__(self,
|
||||
update_handler=None,
|
||||
local_update_handler=None,
|
||||
delete_handler=None,
|
||||
notification_handler=None,
|
||||
conversation_handler=None,
|
||||
unknown_event_handler=None,
|
||||
status_update_handler=None,
|
||||
filters_changed_handler=None,
|
||||
announcement_handler=None,
|
||||
announcement_reaction_handler=None,
|
||||
announcement_delete_handler=None,
|
||||
encryted_message_handler=None
|
||||
):
|
||||
super(CallbackStreamListener, self).__init__()
|
||||
self.update_handler = update_handler
|
||||
self.local_update_handler = local_update_handler
|
||||
|
@ -306,4 +306,4 @@ class CallbackStreamListener(StreamListener):
|
|||
|
||||
def on_unknown_event(self, name, unknown_event=None):
|
||||
if self.unknown_event_handler is not None:
|
||||
self.unknown_event_handler(name, unknown_event)
|
||||
self.unknown_event_handler(name, unknown_event)
|
||||
|
|
|
@ -7,6 +7,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Streaming
|
||||
|
|
|
@ -5,6 +5,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Follow suggestions
|
||||
|
|
|
@ -6,6 +6,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Timelines
|
||||
|
@ -101,4 +102,3 @@ class Mastodon(Internals):
|
|||
"""
|
||||
id = self.__unpack_id(id)
|
||||
return self.timeline(f'list/{id}', max_id=max_id, min_id=min_id, since_id=since_id, limit=limit, only_media=only_media, local=local, remote=remote)
|
||||
|
||||
|
|
|
@ -5,6 +5,7 @@ from .utility import api_version
|
|||
|
||||
from .internals import Mastodon as Internals
|
||||
|
||||
|
||||
class Mastodon(Internals):
|
||||
###
|
||||
# Reading data: Trends
|
||||
|
@ -14,7 +15,7 @@ class Mastodon(Internals):
|
|||
"""
|
||||
Alias for :ref:`trending_tags() <trending_tags()>`
|
||||
"""
|
||||
return self.trending_tags(limit=limit)
|
||||
return self.trending_tags(limit=limit)
|
||||
|
||||
@api_version("3.5.0", "3.5.0", _DICT_VERSION_HASHTAG)
|
||||
def trending_tags(self, limit=None, lang=None):
|
||||
|
@ -27,7 +28,7 @@ class Mastodon(Internals):
|
|||
Does not require authentication unless locked down by the administrator.
|
||||
|
||||
Important versioning note: This endpoint does not exist for Mastodon versions
|
||||
between 2.8.0 (inclusive) and 3.0.0 (exclusive).
|
||||
between 2.8.0 (inclusive) and 3.0.0 (exclusive).
|
||||
|
||||
Pass `lang` to override the global locale parameter, which may affect trend ordering.
|
||||
|
||||
|
|
|
@ -24,10 +24,12 @@ def parse_version_string(version_string):
|
|||
)
|
||||
return version_parts
|
||||
|
||||
|
||||
def max_version(*version_strings):
|
||||
"""Returns the maximum version of all provided version strings."""
|
||||
return max(version_strings, key=parse_version_string)
|
||||
|
||||
|
||||
def api_version(created_ver, last_changed_ver, return_value_ver):
|
||||
"""Version check decorator. Currently only checks Bigger Than."""
|
||||
def api_min_version_decorator(function):
|
||||
|
@ -49,6 +51,7 @@ def api_version(created_ver, last_changed_ver, return_value_ver):
|
|||
return decorate(function, wrapper)
|
||||
return api_min_version_decorator
|
||||
|
||||
|
||||
###
|
||||
# Dict helper class.
|
||||
# Defined at top level so it can be pickled.
|
||||
|
@ -91,7 +94,7 @@ class Mastodon():
|
|||
not have one, 639-3 (three letter) language codes. This affects some error messages (those related to validation) and trends.
|
||||
"""
|
||||
self.lang = lang
|
||||
|
||||
|
||||
def retrieve_mastodon_version(self):
|
||||
"""
|
||||
Determine installed Mastodon version and set major, minor and patch (not including RC info) accordingly.
|
||||
|
@ -127,7 +130,7 @@ class Mastodon():
|
|||
elif major == self.mastodon_major and minor == self.mastodon_minor and patch > self.mastodon_patch:
|
||||
return False
|
||||
return True
|
||||
|
||||
|
||||
def get_approx_server_time(self):
|
||||
"""
|
||||
Retrieve the approximate server time
|
||||
|
|
|
@ -37,4 +37,4 @@ _DICT_VERSION_FAMILIAR_FOLLOWERS = max_version("3.5.0", _DICT_VERSION_ACCOUNT)
|
|||
_DICT_VERSION_ADMIN_DOMAIN_BLOCK = "4.0.0"
|
||||
_DICT_VERSION_ADMIN_MEASURE = "3.5.0"
|
||||
_DICT_VERSION_ADMIN_DIMENSION = "3.5.0"
|
||||
_DICT_VERSION_ADMIN_RETENTION = "3.5.0"
|
||||
_DICT_VERSION_ADMIN_RETENTION = "3.5.0"
|
||||
|
|
Ładowanie…
Reference in New Issue