mirror of
https://git.sr.ht/~tsileo/microblog.pub
synced 2024-11-15 03:04:28 +00:00
Rename the ActivityType enum
This commit is contained in:
parent
12feb38a8f
commit
7a8621e72e
2 changed files with 66 additions and 66 deletions
115
activitypub.py
115
activitypub.py
|
@ -24,12 +24,11 @@ from typing import TypeVar
|
||||||
|
|
||||||
logger = logging.getLogger(__name__)
|
logger = logging.getLogger(__name__)
|
||||||
|
|
||||||
A = TypeVar('A', bound='BaseActivity')
|
|
||||||
ObjectType = Dict[str, Any]
|
ObjectType = Dict[str, Any]
|
||||||
ObjectOrIDType = Union[str, ObjectType]
|
ObjectOrIDType = Union[str, ObjectType]
|
||||||
|
|
||||||
|
|
||||||
class ActivityTypes(Enum):
|
class ActivityType(Enum):
|
||||||
ANNOUNCE = 'Announce'
|
ANNOUNCE = 'Announce'
|
||||||
BLOCK = 'Block'
|
BLOCK = 'Block'
|
||||||
LIKE = 'Like'
|
LIKE = 'Like'
|
||||||
|
@ -84,8 +83,8 @@ def _get_actor_id(actor: ObjectOrIDType) -> str:
|
||||||
|
|
||||||
|
|
||||||
class BaseActivity(object):
|
class BaseActivity(object):
|
||||||
ACTIVITY_TYPE: Optional[ActivityTypes] = None
|
ACTIVITY_TYPE: Optional[ActivityType] = None
|
||||||
ALLOWED_OBJECT_TYPES: List[ActivityTypes] = []
|
ALLOWED_OBJECT_TYPES: List[ActivityType] = []
|
||||||
|
|
||||||
def __init__(self, **kwargs) -> None:
|
def __init__(self, **kwargs) -> None:
|
||||||
if not self.ACTIVITY_TYPE:
|
if not self.ACTIVITY_TYPE:
|
||||||
|
@ -99,7 +98,7 @@ class BaseActivity(object):
|
||||||
if 'id' in kwargs:
|
if 'id' in kwargs:
|
||||||
self._data['id'] = kwargs.pop('id')
|
self._data['id'] = kwargs.pop('id')
|
||||||
|
|
||||||
if self.ACTIVITY_TYPE != ActivityTypes.PERSON:
|
if self.ACTIVITY_TYPE != ActivityType.PERSON:
|
||||||
actor = kwargs.get('actor')
|
actor = kwargs.get('actor')
|
||||||
if actor:
|
if actor:
|
||||||
kwargs.pop('actor')
|
kwargs.pop('actor')
|
||||||
|
@ -117,9 +116,9 @@ class BaseActivity(object):
|
||||||
else:
|
else:
|
||||||
if not self.ALLOWED_OBJECT_TYPES:
|
if not self.ALLOWED_OBJECT_TYPES:
|
||||||
raise ValueError('unexpected object')
|
raise ValueError('unexpected object')
|
||||||
if 'type' not in obj or (self.ACTIVITY_TYPE != ActivityTypes.CREATE and 'id' not in obj):
|
if 'type' not in obj or (self.ACTIVITY_TYPE != ActivityType.CREATE and 'id' not in obj):
|
||||||
raise ValueError('invalid object')
|
raise ValueError('invalid object')
|
||||||
if ActivityTypes(obj['type']) not in self.ALLOWED_OBJECT_TYPES:
|
if ActivityType(obj['type']) not in self.ALLOWED_OBJECT_TYPES:
|
||||||
print(self, kwargs)
|
print(self, kwargs)
|
||||||
raise ValueError(f'unexpected object type {obj["type"]} (allowed={self.ALLOWED_OBJECT_TYPES})')
|
raise ValueError(f'unexpected object type {obj["type"]} (allowed={self.ALLOWED_OBJECT_TYPES})')
|
||||||
self._data['object'] = obj
|
self._data['object'] = obj
|
||||||
|
@ -185,8 +184,8 @@ class BaseActivity(object):
|
||||||
return self._data.get(name)
|
return self._data.get(name)
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def type_enum(self) -> ActivityTypes:
|
def type_enum(self) -> ActivityType:
|
||||||
return ActivityTypes(self.type)
|
return ActivityType(self.type)
|
||||||
|
|
||||||
def _set_id(self, uri: str, obj_id: str) -> None:
|
def _set_id(self, uri: str, obj_id: str) -> None:
|
||||||
raise NotImplementedError
|
raise NotImplementedError
|
||||||
|
@ -199,7 +198,7 @@ class BaseActivity(object):
|
||||||
pass
|
pass
|
||||||
|
|
||||||
def _actor_id(self, obj: ObjectOrIDType) -> str:
|
def _actor_id(self, obj: ObjectOrIDType) -> str:
|
||||||
if isinstance(obj, dict) and obj['type'] == ActivityTypes.PERSON.value:
|
if isinstance(obj, dict) and obj['type'] == ActivityType.PERSON.value:
|
||||||
obj_id = obj.get('id')
|
obj_id = obj.get('id')
|
||||||
if not obj_id:
|
if not obj_id:
|
||||||
raise ValueError('missing object id')
|
raise ValueError('missing object id')
|
||||||
|
@ -223,11 +222,11 @@ class BaseActivity(object):
|
||||||
if isinstance(self._data['object'], dict):
|
if isinstance(self._data['object'], dict):
|
||||||
p = parse_activity(self._data['object'])
|
p = parse_activity(self._data['object'])
|
||||||
else:
|
else:
|
||||||
if self.ACTIVITY_TYPE == ActivityTypes.FOLLOW:
|
if self.ACTIVITY_TYPE == ActivityType.FOLLOW:
|
||||||
p = Person(**ACTOR_SERVICE.get(self._data['object']))
|
p = Person(**ACTOR_SERVICE.get(self._data['object']))
|
||||||
else:
|
else:
|
||||||
obj = OBJECT_SERVICE.get(self._data['object'])
|
obj = OBJECT_SERVICE.get(self._data['object'])
|
||||||
if ActivityTypes(obj.get('type')) not in self.ALLOWED_OBJECT_TYPES:
|
if ActivityType(obj.get('type')) not in self.ALLOWED_OBJECT_TYPES:
|
||||||
raise ValueError('invalid object type')
|
raise ValueError('invalid object type')
|
||||||
|
|
||||||
p = parse_activity(obj)
|
p = parse_activity(obj)
|
||||||
|
@ -249,7 +248,7 @@ class BaseActivity(object):
|
||||||
def get_actor(self) -> 'BaseActivity':
|
def get_actor(self) -> 'BaseActivity':
|
||||||
actor = self._data.get('actor')
|
actor = self._data.get('actor')
|
||||||
if not actor:
|
if not actor:
|
||||||
if self.type_enum == ActivityTypes.NOTE:
|
if self.type_enum == ActivityType.NOTE:
|
||||||
actor = str(self._data.get('attributedTo'))
|
actor = str(self._data.get('attributedTo'))
|
||||||
else:
|
else:
|
||||||
raise ValueError('failed to fetch actor')
|
raise ValueError('failed to fetch actor')
|
||||||
|
@ -279,7 +278,7 @@ class BaseActivity(object):
|
||||||
self.verify()
|
self.verify()
|
||||||
actor = self.get_actor()
|
actor = self.get_actor()
|
||||||
|
|
||||||
if DB.outbox.find_one({'type': ActivityTypes.BLOCK.value,
|
if DB.outbox.find_one({'type': ActivityType.BLOCK.value,
|
||||||
'activity.object': actor.id,
|
'activity.object': actor.id,
|
||||||
'meta.undo': False}):
|
'meta.undo': False}):
|
||||||
print('actor is blocked, drop activity')
|
print('actor is blocked, drop activity')
|
||||||
|
@ -357,8 +356,8 @@ class BaseActivity(object):
|
||||||
actor = Person(**ACTOR_SERVICE.get(recipient))
|
actor = Person(**ACTOR_SERVICE.get(recipient))
|
||||||
except NotAnActorError as error:
|
except NotAnActorError as error:
|
||||||
# Is the activity a `Collection`/`OrderedCollection`?
|
# Is the activity a `Collection`/`OrderedCollection`?
|
||||||
if error.activity and error.activity['type'] in [ActivityTypes.COLLECTION.value,
|
if error.activity and error.activity['type'] in [ActivityType.COLLECTION.value,
|
||||||
ActivityTypes.ORDERED_COLLECTION.value]:
|
ActivityType.ORDERED_COLLECTION.value]:
|
||||||
for item in parse_collection(error.activity):
|
for item in parse_collection(error.activity):
|
||||||
if item in [ME, AS_PUBLIC]:
|
if item in [ME, AS_PUBLIC]:
|
||||||
continue
|
continue
|
||||||
|
@ -393,7 +392,7 @@ class BaseActivity(object):
|
||||||
|
|
||||||
|
|
||||||
class Person(BaseActivity):
|
class Person(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.PERSON
|
ACTIVITY_TYPE = ActivityType.PERSON
|
||||||
|
|
||||||
def _init(self, **kwargs):
|
def _init(self, **kwargs):
|
||||||
# if 'icon' in kwargs:
|
# if 'icon' in kwargs:
|
||||||
|
@ -410,15 +409,15 @@ class Person(BaseActivity):
|
||||||
|
|
||||||
|
|
||||||
class Block(BaseActivity):
|
class Block(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.BLOCK
|
ACTIVITY_TYPE = ActivityType.BLOCK
|
||||||
|
|
||||||
|
|
||||||
class Collection(BaseActivity):
|
class Collection(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.COLLECTION
|
ACTIVITY_TYPE = ActivityType.COLLECTION
|
||||||
|
|
||||||
|
|
||||||
class Image(BaseActivity):
|
class Image(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.IMAGE
|
ACTIVITY_TYPE = ActivityType.IMAGE
|
||||||
NO_CONTEXT = True
|
NO_CONTEXT = True
|
||||||
|
|
||||||
def _init(self, **kwargs):
|
def _init(self, **kwargs):
|
||||||
|
@ -431,11 +430,11 @@ class Image(BaseActivity):
|
||||||
|
|
||||||
|
|
||||||
class Follow(BaseActivity):
|
class Follow(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.FOLLOW
|
ACTIVITY_TYPE = ActivityType.FOLLOW
|
||||||
ALLOWED_OBJECT_TYPES = [ActivityTypes.PERSON]
|
ALLOWED_OBJECT_TYPES = [ActivityType.PERSON]
|
||||||
|
|
||||||
def _build_reply(self, reply_type: ActivityTypes) -> BaseActivity:
|
def _build_reply(self, reply_type: ActivityType) -> BaseActivity:
|
||||||
if reply_type == ActivityTypes.ACCEPT:
|
if reply_type == ActivityType.ACCEPT:
|
||||||
return Accept(
|
return Accept(
|
||||||
object=self.to_dict(embed=True),
|
object=self.to_dict(embed=True),
|
||||||
)
|
)
|
||||||
|
@ -461,7 +460,7 @@ class Follow(BaseActivity):
|
||||||
DB.following.delete_one({'remote_actor': self.get_object().id})
|
DB.following.delete_one({'remote_actor': self.get_object().id})
|
||||||
|
|
||||||
def build_accept(self) -> BaseActivity:
|
def build_accept(self) -> BaseActivity:
|
||||||
return self._build_reply(ActivityTypes.ACCEPT)
|
return self._build_reply(ActivityType.ACCEPT)
|
||||||
|
|
||||||
def build_undo(self) -> BaseActivity:
|
def build_undo(self) -> BaseActivity:
|
||||||
return Undo(object=self.to_dict(embed=True))
|
return Undo(object=self.to_dict(embed=True))
|
||||||
|
@ -472,8 +471,8 @@ class Follow(BaseActivity):
|
||||||
|
|
||||||
|
|
||||||
class Accept(BaseActivity):
|
class Accept(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.ACCEPT
|
ACTIVITY_TYPE = ActivityType.ACCEPT
|
||||||
ALLOWED_OBJECT_TYPES = [ActivityTypes.FOLLOW]
|
ALLOWED_OBJECT_TYPES = [ActivityType.FOLLOW]
|
||||||
|
|
||||||
def _recipients(self) -> List[str]:
|
def _recipients(self) -> List[str]:
|
||||||
return [self.get_object().get_actor().id]
|
return [self.get_object().get_actor().id]
|
||||||
|
@ -490,12 +489,12 @@ class Accept(BaseActivity):
|
||||||
|
|
||||||
|
|
||||||
class Undo(BaseActivity):
|
class Undo(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.UNDO
|
ACTIVITY_TYPE = ActivityType.UNDO
|
||||||
ALLOWED_OBJECT_TYPES = [ActivityTypes.FOLLOW, ActivityTypes.LIKE, ActivityTypes.ANNOUNCE]
|
ALLOWED_OBJECT_TYPES = [ActivityType.FOLLOW, ActivityType.LIKE, ActivityType.ANNOUNCE]
|
||||||
|
|
||||||
def _recipients(self) -> List[str]:
|
def _recipients(self) -> List[str]:
|
||||||
obj = self.get_object()
|
obj = self.get_object()
|
||||||
if obj.type_enum == ActivityTypes.FOLLOW:
|
if obj.type_enum == ActivityType.FOLLOW:
|
||||||
return [obj.get_object().id]
|
return [obj.get_object().id]
|
||||||
else:
|
else:
|
||||||
return [obj.get_object().get_actor().id]
|
return [obj.get_object().get_actor().id]
|
||||||
|
@ -538,8 +537,8 @@ class Undo(BaseActivity):
|
||||||
|
|
||||||
|
|
||||||
class Like(BaseActivity):
|
class Like(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.LIKE
|
ACTIVITY_TYPE = ActivityType.LIKE
|
||||||
ALLOWED_OBJECT_TYPES = [ActivityTypes.NOTE]
|
ALLOWED_OBJECT_TYPES = [ActivityType.NOTE]
|
||||||
|
|
||||||
def _recipients(self) -> List[str]:
|
def _recipients(self) -> List[str]:
|
||||||
return [self.get_object().get_actor().id]
|
return [self.get_object().get_actor().id]
|
||||||
|
@ -577,8 +576,8 @@ class Like(BaseActivity):
|
||||||
|
|
||||||
|
|
||||||
class Announce(BaseActivity):
|
class Announce(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.ANNOUNCE
|
ACTIVITY_TYPE = ActivityType.ANNOUNCE
|
||||||
ALLOWED_OBJECT_TYPES = [ActivityTypes.NOTE]
|
ALLOWED_OBJECT_TYPES = [ActivityType.NOTE]
|
||||||
|
|
||||||
def _recipients(self) -> List[str]:
|
def _recipients(self) -> List[str]:
|
||||||
recipients = []
|
recipients = []
|
||||||
|
@ -638,8 +637,8 @@ class Announce(BaseActivity):
|
||||||
|
|
||||||
|
|
||||||
class Delete(BaseActivity):
|
class Delete(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.DELETE
|
ACTIVITY_TYPE = ActivityType.DELETE
|
||||||
ALLOWED_OBJECT_TYPES = [ActivityTypes.NOTE, ActivityTypes.TOMBSTONE]
|
ALLOWED_OBJECT_TYPES = [ActivityType.NOTE, ActivityType.TOMBSTONE]
|
||||||
|
|
||||||
def _recipients(self) -> List[str]:
|
def _recipients(self) -> List[str]:
|
||||||
return self.get_object().recipients()
|
return self.get_object().recipients()
|
||||||
|
@ -654,15 +653,15 @@ class Delete(BaseActivity):
|
||||||
|
|
||||||
|
|
||||||
class Update(BaseActivity):
|
class Update(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.UPDATE
|
ACTIVITY_TYPE = ActivityType.UPDATE
|
||||||
ALLOWED_OBJECT_TYPES = [ActivityTypes.NOTE, ActivityTypes.PERSON]
|
ALLOWED_OBJECT_TYPES = [ActivityType.NOTE, ActivityType.PERSON]
|
||||||
|
|
||||||
# TODO(tsileo): ensure the actor updating is the same as the orinial activity
|
# TODO(tsileo): ensure the actor updating is the same as the orinial activity
|
||||||
# (ensuring that the Update and its object are of same origin)
|
# (ensuring that the Update and its object are of same origin)
|
||||||
|
|
||||||
def _process_from_inbox(self):
|
def _process_from_inbox(self):
|
||||||
obj = self.get_object()
|
obj = self.get_object()
|
||||||
if obj.type_enum == ActivityTypes.NOTE:
|
if obj.type_enum == ActivityType.NOTE:
|
||||||
DB.inbox.update_one({'activity.object.id': obj.id}, {'$set': {'activity.object': obj.to_dict()}})
|
DB.inbox.update_one({'activity.object.id': obj.id}, {'$set': {'activity.object': obj.to_dict()}})
|
||||||
return
|
return
|
||||||
|
|
||||||
|
@ -694,8 +693,8 @@ class Update(BaseActivity):
|
||||||
|
|
||||||
|
|
||||||
class Create(BaseActivity):
|
class Create(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.CREATE
|
ACTIVITY_TYPE = ActivityType.CREATE
|
||||||
ALLOWED_OBJECT_TYPES = [ActivityTypes.NOTE]
|
ALLOWED_OBJECT_TYPES = [ActivityType.NOTE]
|
||||||
|
|
||||||
def _set_id(self, uri: str, obj_id: str) -> None:
|
def _set_id(self, uri: str, obj_id: str) -> None:
|
||||||
self._data['object']['id'] = uri + '/activity'
|
self._data['object']['id'] = uri + '/activity'
|
||||||
|
@ -768,11 +767,11 @@ class Create(BaseActivity):
|
||||||
|
|
||||||
|
|
||||||
class Tombstone(BaseActivity):
|
class Tombstone(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.TOMBSTONE
|
ACTIVITY_TYPE = ActivityType.TOMBSTONE
|
||||||
|
|
||||||
|
|
||||||
class Note(BaseActivity):
|
class Note(BaseActivity):
|
||||||
ACTIVITY_TYPE = ActivityTypes.NOTE
|
ACTIVITY_TYPE = ActivityType.NOTE
|
||||||
|
|
||||||
def _init(self, **kwargs):
|
def _init(self, **kwargs):
|
||||||
print(self._data)
|
print(self._data)
|
||||||
|
@ -831,25 +830,25 @@ class Note(BaseActivity):
|
||||||
|
|
||||||
|
|
||||||
_ACTIVITY_TYPE_TO_CLS = {
|
_ACTIVITY_TYPE_TO_CLS = {
|
||||||
ActivityTypes.IMAGE: Image,
|
ActivityType.IMAGE: Image,
|
||||||
ActivityTypes.PERSON: Person,
|
ActivityType.PERSON: Person,
|
||||||
ActivityTypes.FOLLOW: Follow,
|
ActivityType.FOLLOW: Follow,
|
||||||
ActivityTypes.ACCEPT: Accept,
|
ActivityType.ACCEPT: Accept,
|
||||||
ActivityTypes.UNDO: Undo,
|
ActivityType.UNDO: Undo,
|
||||||
ActivityTypes.LIKE: Like,
|
ActivityType.LIKE: Like,
|
||||||
ActivityTypes.ANNOUNCE: Announce,
|
ActivityType.ANNOUNCE: Announce,
|
||||||
ActivityTypes.UPDATE: Update,
|
ActivityType.UPDATE: Update,
|
||||||
ActivityTypes.DELETE: Delete,
|
ActivityType.DELETE: Delete,
|
||||||
ActivityTypes.CREATE: Create,
|
ActivityType.CREATE: Create,
|
||||||
ActivityTypes.NOTE: Note,
|
ActivityType.NOTE: Note,
|
||||||
ActivityTypes.BLOCK: Block,
|
ActivityType.BLOCK: Block,
|
||||||
ActivityTypes.COLLECTION: Collection,
|
ActivityType.COLLECTION: Collection,
|
||||||
ActivityTypes.TOMBSTONE: Tombstone,
|
ActivityType.TOMBSTONE: Tombstone,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
def parse_activity(payload: ObjectType) -> BaseActivity:
|
def parse_activity(payload: ObjectType) -> BaseActivity:
|
||||||
t = ActivityTypes(payload['type'])
|
t = ActivityType(payload['type'])
|
||||||
if t not in _ACTIVITY_TYPE_TO_CLS:
|
if t not in _ACTIVITY_TYPE_TO_CLS:
|
||||||
raise ValueError('unsupported activity type')
|
raise ValueError('unsupported activity type')
|
||||||
|
|
||||||
|
|
17
app.py
17
app.py
|
@ -33,7 +33,7 @@ from werkzeug.utils import secure_filename
|
||||||
|
|
||||||
import activitypub
|
import activitypub
|
||||||
import config
|
import config
|
||||||
from activitypub import ActivityTypes
|
from activitypub import ActivityType
|
||||||
from activitypub import clean_activity
|
from activitypub import clean_activity
|
||||||
from utils.content_helper import parse_markdown
|
from utils.content_helper import parse_markdown
|
||||||
from config import KEY
|
from config import KEY
|
||||||
|
@ -444,7 +444,7 @@ def outbox():
|
||||||
# FIXME(tsileo): filter deleted, add query support for build_ordered_collection
|
# FIXME(tsileo): filter deleted, add query support for build_ordered_collection
|
||||||
q = {
|
q = {
|
||||||
'meta.deleted': False,
|
'meta.deleted': False,
|
||||||
'type': {'$in': [ActivityTypes.CREATE.value, ActivityTypes.ANNOUNCE.value]},
|
'type': {'$in': [ActivityType.CREATE.value, ActivityType.ANNOUNCE.value]},
|
||||||
}
|
}
|
||||||
return jsonify(**activitypub.build_ordered_collection(
|
return jsonify(**activitypub.build_ordered_collection(
|
||||||
DB.outbox,
|
DB.outbox,
|
||||||
|
@ -463,7 +463,7 @@ def outbox():
|
||||||
print(data)
|
print(data)
|
||||||
activity = activitypub.parse_activity(data)
|
activity = activitypub.parse_activity(data)
|
||||||
|
|
||||||
if activity.type_enum == ActivityTypes.NOTE:
|
if activity.type_enum == ActivityType.NOTE:
|
||||||
activity = activity.build_create()
|
activity = activity.build_create()
|
||||||
|
|
||||||
activity.post_to_outbox()
|
activity.post_to_outbox()
|
||||||
|
@ -486,7 +486,7 @@ def outbox_activity(item_id):
|
||||||
if not data:
|
if not data:
|
||||||
abort(404)
|
abort(404)
|
||||||
obj = data['activity']
|
obj = data['activity']
|
||||||
if obj['type'] != ActivityTypes.CREATE.value:
|
if obj['type'] != ActivityType.CREATE.value:
|
||||||
abort(404)
|
abort(404)
|
||||||
return jsonify(**clean_activity(obj['object']))
|
return jsonify(**clean_activity(obj['object']))
|
||||||
|
|
||||||
|
@ -496,7 +496,7 @@ def admin():
|
||||||
q = {
|
q = {
|
||||||
'meta.deleted': False,
|
'meta.deleted': False,
|
||||||
'meta.undo': False,
|
'meta.undo': False,
|
||||||
'type': ActivityTypes.LIKE.value,
|
'type': ActivityType.LIKE.value,
|
||||||
}
|
}
|
||||||
col_liked = DB.outbox.count(q)
|
col_liked = DB.outbox.count(q)
|
||||||
|
|
||||||
|
@ -801,7 +801,7 @@ def api_new_note():
|
||||||
note = activitypub.Note(
|
note = activitypub.Note(
|
||||||
cc=cc,
|
cc=cc,
|
||||||
to=[to if to else config.AS_PUBLIC],
|
to=[to if to else config.AS_PUBLIC],
|
||||||
content=content, # TODO(tsileo): handle markdown
|
content=content,
|
||||||
tag=tags,
|
tag=tags,
|
||||||
source={'mediaType': 'text/markdown', 'content': source},
|
source={'mediaType': 'text/markdown', 'content': source},
|
||||||
)
|
)
|
||||||
|
@ -810,6 +810,7 @@ def api_new_note():
|
||||||
return Response(
|
return Response(
|
||||||
status=201,
|
status=201,
|
||||||
response='OK',
|
response='OK',
|
||||||
|
headers={'Microblogpub-Created-Activity': created.id},
|
||||||
)
|
)
|
||||||
|
|
||||||
@app.route('/api/stream')
|
@app.route('/api/stream')
|
||||||
|
@ -895,7 +896,7 @@ def tags(tag):
|
||||||
q = {
|
q = {
|
||||||
'meta.deleted': False,
|
'meta.deleted': False,
|
||||||
'meta.undo': False,
|
'meta.undo': False,
|
||||||
'type': ActivityTypes.CREATE.value,
|
'type': ActivityType.CREATE.value,
|
||||||
'activity.object.tag.type': 'Hashtag',
|
'activity.object.tag.type': 'Hashtag',
|
||||||
'activity.object.tag.name': '#'+tag,
|
'activity.object.tag.name': '#'+tag,
|
||||||
}
|
}
|
||||||
|
@ -915,7 +916,7 @@ def liked():
|
||||||
q = {
|
q = {
|
||||||
'meta.deleted': False,
|
'meta.deleted': False,
|
||||||
'meta.undo': False,
|
'meta.undo': False,
|
||||||
'type': ActivityTypes.LIKE.value,
|
'type': ActivityType.LIKE.value,
|
||||||
}
|
}
|
||||||
return jsonify(**activitypub.build_ordered_collection(
|
return jsonify(**activitypub.build_ordered_collection(
|
||||||
DB.outbox,
|
DB.outbox,
|
||||||
|
|
Loading…
Reference in a new issue