diff --git a/bookwyrm/activitypub/__init__.py b/bookwyrm/activitypub/__init__.py index d363fbd5..bfb22fa3 100644 --- a/bookwyrm/activitypub/__init__.py +++ b/bookwyrm/activitypub/__init__.py @@ -27,5 +27,5 @@ activity_objects = {c[0]: c[1] for c in cls_members if hasattr(c[1], "to_model") def parse(activity_json): - """ figure out what activity this is and parse it """ + """figure out what activity this is and parse it""" return naive_parse(activity_objects, activity_json) diff --git a/bookwyrm/activitypub/base_activity.py b/bookwyrm/activitypub/base_activity.py index dd2795bb..5349e1dd 100644 --- a/bookwyrm/activitypub/base_activity.py +++ b/bookwyrm/activitypub/base_activity.py @@ -10,11 +10,11 @@ from bookwyrm.tasks import app class ActivitySerializerError(ValueError): - """ routine problems serializing activitypub json """ + """routine problems serializing activitypub json""" class ActivityEncoder(JSONEncoder): - """ used to convert an Activity object into json """ + """used to convert an Activity object into json""" def default(self, o): return o.__dict__ @@ -22,7 +22,7 @@ class ActivityEncoder(JSONEncoder): @dataclass class Link: - """ for tagging a book in a status """ + """for tagging a book in a status""" href: str name: str @@ -31,14 +31,14 @@ class Link: @dataclass class Mention(Link): - """ a subtype of Link for mentioning an actor """ + """a subtype of Link for mentioning an actor""" type: str = "Mention" @dataclass class Signature: - """ public key block """ + """public key block""" creator: str created: str @@ -47,7 +47,7 @@ class Signature: def naive_parse(activity_objects, activity_json, serializer=None): - """ this navigates circular import issues """ + """this navigates circular import issues""" if not serializer: if activity_json.get("publicKeyPem"): # ugh @@ -67,7 +67,7 @@ def naive_parse(activity_objects, activity_json, serializer=None): @dataclass(init=False) class ActivityObject: - """ actor activitypub json """ + """actor activitypub json""" id: str type: str @@ -106,7 +106,7 @@ class ActivityObject: setattr(self, field.name, value) def to_model(self, model=None, instance=None, allow_create=True, save=True): - """ convert from an activity to a model instance """ + """convert from an activity to a model instance""" model = model or get_model_from_type(self.type) # only reject statuses if we're potentially creating them @@ -181,7 +181,7 @@ class ActivityObject: return instance def serialize(self): - """ convert to dictionary with context attr """ + """convert to dictionary with context attr""" data = self.__dict__.copy() # recursively serialize for (k, v) in data.items(): @@ -200,7 +200,7 @@ class ActivityObject: def set_related_field( model_name, origin_model_name, related_field_name, related_remote_id, data ): - """ load reverse related fields (editions, attachments) without blocking """ + """load reverse related fields (editions, attachments) without blocking""" model = apps.get_model("bookwyrm.%s" % model_name, require_ready=True) origin_model = apps.get_model("bookwyrm.%s" % origin_model_name, require_ready=True) @@ -236,7 +236,7 @@ def set_related_field( def get_model_from_type(activity_type): - """ given the activity, what type of model """ + """given the activity, what type of model""" models = apps.get_models() model = [ m @@ -255,7 +255,7 @@ def get_model_from_type(activity_type): def resolve_remote_id( remote_id, model=None, refresh=False, save=True, get_activity=False ): - """ take a remote_id and return an instance, creating if necessary """ + """take a remote_id and return an instance, creating if necessary""" if model: # a bonus check we can do if we already know the model result = model.find_existing_by_remote_id(remote_id) if result and not refresh: diff --git a/bookwyrm/activitypub/book.py b/bookwyrm/activitypub/book.py index c5b896e3..f6ebf913 100644 --- a/bookwyrm/activitypub/book.py +++ b/bookwyrm/activitypub/book.py @@ -8,7 +8,7 @@ from .image import Document @dataclass(init=False) class Book(ActivityObject): - """ serializes an edition or work, abstract """ + """serializes an edition or work, abstract""" title: str lastEditedBy: str = None @@ -35,7 +35,7 @@ class Book(ActivityObject): @dataclass(init=False) class Edition(Book): - """ Edition instance of a book object """ + """Edition instance of a book object""" work: str isbn10: str = "" @@ -52,7 +52,7 @@ class Edition(Book): @dataclass(init=False) class Work(Book): - """ work instance of a book object """ + """work instance of a book object""" lccn: str = "" defaultEdition: str = "" @@ -62,7 +62,7 @@ class Work(Book): @dataclass(init=False) class Author(ActivityObject): - """ author of a book """ + """author of a book""" name: str lastEditedBy: str = None diff --git a/bookwyrm/activitypub/image.py b/bookwyrm/activitypub/image.py index a7120ce4..7950faaf 100644 --- a/bookwyrm/activitypub/image.py +++ b/bookwyrm/activitypub/image.py @@ -5,7 +5,7 @@ from .base_activity import ActivityObject @dataclass(init=False) class Document(ActivityObject): - """ a document """ + """a document""" url: str name: str = "" @@ -15,6 +15,6 @@ class Document(ActivityObject): @dataclass(init=False) class Image(Document): - """ an image """ + """an image""" type: str = "Image" diff --git a/bookwyrm/activitypub/note.py b/bookwyrm/activitypub/note.py index e1a42958..b501c3d6 100644 --- a/bookwyrm/activitypub/note.py +++ b/bookwyrm/activitypub/note.py @@ -9,19 +9,19 @@ from .image import Document @dataclass(init=False) class Tombstone(ActivityObject): - """ the placeholder for a deleted status """ + """the placeholder for a deleted status""" type: str = "Tombstone" def to_model(self, *args, **kwargs): # pylint: disable=unused-argument - """ this should never really get serialized, just searched for """ + """this should never really get serialized, just searched for""" model = apps.get_model("bookwyrm.Status") return model.find_existing_by_remote_id(self.id) @dataclass(init=False) class Note(ActivityObject): - """ Note activity """ + """Note activity""" published: str attributedTo: str @@ -39,7 +39,7 @@ class Note(ActivityObject): @dataclass(init=False) class Article(Note): - """ what's an article except a note with more fields """ + """what's an article except a note with more fields""" name: str type: str = "Article" @@ -47,14 +47,14 @@ class Article(Note): @dataclass(init=False) class GeneratedNote(Note): - """ just a re-typed note """ + """just a re-typed note""" type: str = "GeneratedNote" @dataclass(init=False) class Comment(Note): - """ like a note but with a book """ + """like a note but with a book""" inReplyToBook: str type: str = "Comment" @@ -62,7 +62,7 @@ class Comment(Note): @dataclass(init=False) class Quotation(Comment): - """ a quote and commentary on a book """ + """a quote and commentary on a book""" quote: str type: str = "Quotation" @@ -70,7 +70,7 @@ class Quotation(Comment): @dataclass(init=False) class Review(Comment): - """ a full book review """ + """a full book review""" name: str = None rating: int = None @@ -79,7 +79,7 @@ class Review(Comment): @dataclass(init=False) class Rating(Comment): - """ just a star rating """ + """just a star rating""" rating: int content: str = None diff --git a/bookwyrm/activitypub/ordered_collection.py b/bookwyrm/activitypub/ordered_collection.py index 650f6a40..e3a83be8 100644 --- a/bookwyrm/activitypub/ordered_collection.py +++ b/bookwyrm/activitypub/ordered_collection.py @@ -7,7 +7,7 @@ from .base_activity import ActivityObject @dataclass(init=False) class OrderedCollection(ActivityObject): - """ structure of an ordered collection activity """ + """structure of an ordered collection activity""" totalItems: int first: str @@ -19,7 +19,7 @@ class OrderedCollection(ActivityObject): @dataclass(init=False) class OrderedCollectionPrivate(OrderedCollection): - """ an ordered collection with privacy settings """ + """an ordered collection with privacy settings""" to: List[str] = field(default_factory=lambda: []) cc: List[str] = field(default_factory=lambda: []) @@ -27,14 +27,14 @@ class OrderedCollectionPrivate(OrderedCollection): @dataclass(init=False) class Shelf(OrderedCollectionPrivate): - """ structure of an ordered collection activity """ + """structure of an ordered collection activity""" type: str = "Shelf" @dataclass(init=False) class BookList(OrderedCollectionPrivate): - """ structure of an ordered collection activity """ + """structure of an ordered collection activity""" summary: str = None curation: str = "closed" @@ -43,7 +43,7 @@ class BookList(OrderedCollectionPrivate): @dataclass(init=False) class OrderedCollectionPage(ActivityObject): - """ structure of an ordered collection activity """ + """structure of an ordered collection activity""" partOf: str orderedItems: List @@ -54,7 +54,7 @@ class OrderedCollectionPage(ActivityObject): @dataclass(init=False) class CollectionItem(ActivityObject): - """ an item in a collection """ + """an item in a collection""" actor: str type: str = "CollectionItem" @@ -62,7 +62,7 @@ class CollectionItem(ActivityObject): @dataclass(init=False) class ListItem(CollectionItem): - """ a book on a list """ + """a book on a list""" book: str notes: str = None @@ -73,7 +73,7 @@ class ListItem(CollectionItem): @dataclass(init=False) class ShelfItem(CollectionItem): - """ a book on a list """ + """a book on a list""" book: str type: str = "ShelfItem" diff --git a/bookwyrm/activitypub/person.py b/bookwyrm/activitypub/person.py index 9231bd95..d5f37946 100644 --- a/bookwyrm/activitypub/person.py +++ b/bookwyrm/activitypub/person.py @@ -8,7 +8,7 @@ from .image import Image @dataclass(init=False) class PublicKey(ActivityObject): - """ public key block """ + """public key block""" owner: str publicKeyPem: str @@ -17,7 +17,7 @@ class PublicKey(ActivityObject): @dataclass(init=False) class Person(ActivityObject): - """ actor activitypub json """ + """actor activitypub json""" preferredUsername: str inbox: str diff --git a/bookwyrm/activitypub/verbs.py b/bookwyrm/activitypub/verbs.py index 090beea5..f26936d7 100644 --- a/bookwyrm/activitypub/verbs.py +++ b/bookwyrm/activitypub/verbs.py @@ -9,13 +9,13 @@ from .ordered_collection import CollectionItem @dataclass(init=False) class Verb(ActivityObject): - """generic fields for activities """ + """generic fields for activities""" actor: str object: ActivityObject def action(self): - """ usually we just want to update and save """ + """usually we just want to update and save""" # self.object may return None if the object is invalid in an expected way # ie, Question type if self.object: @@ -24,7 +24,7 @@ class Verb(ActivityObject): @dataclass(init=False) class Create(Verb): - """ Create activity """ + """Create activity""" to: List[str] cc: List[str] = field(default_factory=lambda: []) @@ -34,14 +34,14 @@ class Create(Verb): @dataclass(init=False) class Delete(Verb): - """ Create activity """ + """Create activity""" to: List[str] cc: List[str] = field(default_factory=lambda: []) type: str = "Delete" def action(self): - """ find and delete the activity object """ + """find and delete the activity object""" if not self.object: return @@ -59,25 +59,25 @@ class Delete(Verb): @dataclass(init=False) class Update(Verb): - """ Update activity """ + """Update activity""" to: List[str] type: str = "Update" def action(self): - """ update a model instance from the dataclass """ + """update a model instance from the dataclass""" if self.object: self.object.to_model(allow_create=False) @dataclass(init=False) class Undo(Verb): - """ Undo an activity """ + """Undo an activity""" type: str = "Undo" def action(self): - """ find and remove the activity object """ + """find and remove the activity object""" if isinstance(self.object, str): # it may be that sometihng should be done with these, but idk what # this seems just to be coming from pleroma @@ -103,64 +103,64 @@ class Undo(Verb): @dataclass(init=False) class Follow(Verb): - """ Follow activity """ + """Follow activity""" object: str type: str = "Follow" def action(self): - """ relationship save """ + """relationship save""" self.to_model() @dataclass(init=False) class Block(Verb): - """ Block activity """ + """Block activity""" object: str type: str = "Block" def action(self): - """ relationship save """ + """relationship save""" self.to_model() @dataclass(init=False) class Accept(Verb): - """ Accept activity """ + """Accept activity""" object: Follow type: str = "Accept" def action(self): - """ find and remove the activity object """ + """find and remove the activity object""" obj = self.object.to_model(save=False, allow_create=False) obj.accept() @dataclass(init=False) class Reject(Verb): - """ Reject activity """ + """Reject activity""" object: Follow type: str = "Reject" def action(self): - """ find and remove the activity object """ + """find and remove the activity object""" obj = self.object.to_model(save=False, allow_create=False) obj.reject() @dataclass(init=False) class Add(Verb): - """Add activity """ + """Add activity""" target: ActivityObject object: CollectionItem type: str = "Add" def action(self): - """ figure out the target to assign the item to a collection """ + """figure out the target to assign the item to a collection""" target = resolve_remote_id(self.target) item = self.object.to_model(save=False) setattr(item, item.collection_field, target) @@ -169,12 +169,12 @@ class Add(Verb): @dataclass(init=False) class Remove(Add): - """Remove activity """ + """Remove activity""" type: str = "Remove" def action(self): - """ find and remove the activity object """ + """find and remove the activity object""" obj = self.object.to_model(save=False, allow_create=False) if obj: obj.delete() @@ -182,19 +182,19 @@ class Remove(Add): @dataclass(init=False) class Like(Verb): - """ a user faving an object """ + """a user faving an object""" object: str type: str = "Like" def action(self): - """ like """ + """like""" self.to_model() @dataclass(init=False) class Announce(Verb): - """ boosting a status """ + """boosting a status""" published: str to: List[str] = field(default_factory=lambda: []) @@ -203,5 +203,5 @@ class Announce(Verb): type: str = "Announce" def action(self): - """ boost """ + """boost""" self.to_model() diff --git a/bookwyrm/activitystreams.py b/bookwyrm/activitystreams.py index 949ae9da..86321cd8 100644 --- a/bookwyrm/activitystreams.py +++ b/bookwyrm/activitystreams.py @@ -8,22 +8,22 @@ from bookwyrm.views.helpers import privacy_filter class ActivityStream(RedisStore): - """ a category of activity stream (like home, local, federated) """ + """a category of activity stream (like home, local, federated)""" def stream_id(self, user): - """ the redis key for this user's instance of this stream """ + """the redis key for this user's instance of this stream""" return "{}-{}".format(user.id, self.key) def unread_id(self, user): - """ the redis key for this user's unread count for this stream """ + """the redis key for this user's unread count for this stream""" return "{}-unread".format(self.stream_id(user)) def get_rank(self, obj): # pylint: disable=no-self-use - """ statuses are sorted by date published """ + """statuses are sorted by date published""" return obj.published_date.timestamp() def add_status(self, status): - """ add a status to users' feeds """ + """add a status to users' feeds""" # the pipeline contains all the add-to-stream activities pipeline = self.add_object_to_related_stores(status, execute=False) @@ -35,19 +35,19 @@ class ActivityStream(RedisStore): pipeline.execute() def add_user_statuses(self, viewer, user): - """ add a user's statuses to another user's feed """ + """add a user's statuses to another user's feed""" # only add the statuses that the viewer should be able to see (ie, not dms) statuses = privacy_filter(viewer, user.status_set.all()) self.bulk_add_objects_to_store(statuses, self.stream_id(viewer)) def remove_user_statuses(self, viewer, user): - """ remove a user's status from another user's feed """ + """remove a user's status from another user's feed""" # remove all so that followers only statuses are removed statuses = user.status_set.all() self.bulk_remove_objects_from_store(statuses, self.stream_id(viewer)) def get_activity_stream(self, user): - """ load the statuses to be displayed """ + """load the statuses to be displayed""" # clear unreads for this feed r.set(self.unread_id(user), 0) @@ -59,15 +59,15 @@ class ActivityStream(RedisStore): ) def get_unread_count(self, user): - """ get the unread status count for this user's feed """ + """get the unread status count for this user's feed""" return int(r.get(self.unread_id(user)) or 0) def populate_streams(self, user): - """ go from zero to a timeline """ + """go from zero to a timeline""" self.populate_store(self.stream_id(user)) def get_audience(self, status): # pylint: disable=no-self-use - """ given a status, what users should see it """ + """given a status, what users should see it""" # direct messages don't appeard in feeds, direct comments/reviews/etc do if status.privacy == "direct" and status.status_type == "Note": return [] @@ -98,7 +98,7 @@ class ActivityStream(RedisStore): return [self.stream_id(u) for u in self.get_audience(obj)] def get_statuses_for_user(self, user): # pylint: disable=no-self-use - """ given a user, what statuses should they see on this stream """ + """given a user, what statuses should they see on this stream""" return privacy_filter( user, models.Status.objects.select_subclasses(), @@ -111,7 +111,7 @@ class ActivityStream(RedisStore): class HomeStream(ActivityStream): - """ users you follow """ + """users you follow""" key = "home" @@ -134,7 +134,7 @@ class HomeStream(ActivityStream): class LocalStream(ActivityStream): - """ users you follow """ + """users you follow""" key = "local" @@ -154,7 +154,7 @@ class LocalStream(ActivityStream): class FederatedStream(ActivityStream): - """ users you follow """ + """users you follow""" key = "federated" @@ -182,7 +182,7 @@ streams = { @receiver(signals.post_save) # pylint: disable=unused-argument def add_status_on_create(sender, instance, created, *args, **kwargs): - """ add newly created statuses to activity feeds """ + """add newly created statuses to activity feeds""" # we're only interested in new statuses if not issubclass(sender, models.Status): return @@ -203,7 +203,7 @@ def add_status_on_create(sender, instance, created, *args, **kwargs): @receiver(signals.post_delete, sender=models.Boost) # pylint: disable=unused-argument def remove_boost_on_delete(sender, instance, *args, **kwargs): - """ boosts are deleted """ + """boosts are deleted""" # we're only interested in new statuses for stream in streams.values(): stream.remove_object_from_related_stores(instance) @@ -212,7 +212,7 @@ def remove_boost_on_delete(sender, instance, *args, **kwargs): @receiver(signals.post_save, sender=models.UserFollows) # pylint: disable=unused-argument def add_statuses_on_follow(sender, instance, created, *args, **kwargs): - """ add a newly followed user's statuses to feeds """ + """add a newly followed user's statuses to feeds""" if not created or not instance.user_subject.local: return HomeStream().add_user_statuses(instance.user_subject, instance.user_object) @@ -221,7 +221,7 @@ def add_statuses_on_follow(sender, instance, created, *args, **kwargs): @receiver(signals.post_delete, sender=models.UserFollows) # pylint: disable=unused-argument def remove_statuses_on_unfollow(sender, instance, *args, **kwargs): - """ remove statuses from a feed on unfollow """ + """remove statuses from a feed on unfollow""" if not instance.user_subject.local: return HomeStream().remove_user_statuses(instance.user_subject, instance.user_object) @@ -230,7 +230,7 @@ def remove_statuses_on_unfollow(sender, instance, *args, **kwargs): @receiver(signals.post_save, sender=models.UserBlocks) # pylint: disable=unused-argument def remove_statuses_on_block(sender, instance, *args, **kwargs): - """ remove statuses from all feeds on block """ + """remove statuses from all feeds on block""" # blocks apply ot all feeds if instance.user_subject.local: for stream in streams.values(): @@ -245,7 +245,7 @@ def remove_statuses_on_block(sender, instance, *args, **kwargs): @receiver(signals.post_delete, sender=models.UserBlocks) # pylint: disable=unused-argument def add_statuses_on_unblock(sender, instance, *args, **kwargs): - """ remove statuses from all feeds on block """ + """remove statuses from all feeds on block""" public_streams = [LocalStream(), FederatedStream()] # add statuses back to streams with statuses from anyone if instance.user_subject.local: @@ -261,7 +261,7 @@ def add_statuses_on_unblock(sender, instance, *args, **kwargs): @receiver(signals.post_save, sender=models.User) # pylint: disable=unused-argument def populate_streams_on_account_create(sender, instance, created, *args, **kwargs): - """ build a user's feeds when they join """ + """build a user's feeds when they join""" if not created or not instance.local: return diff --git a/bookwyrm/connectors/abstract_connector.py b/bookwyrm/connectors/abstract_connector.py index 2fe5d825..264b5a38 100644 --- a/bookwyrm/connectors/abstract_connector.py +++ b/bookwyrm/connectors/abstract_connector.py @@ -16,7 +16,7 @@ logger = logging.getLogger(__name__) class AbstractMinimalConnector(ABC): - """ just the bare bones, for other bookwyrm instances """ + """just the bare bones, for other bookwyrm instances""" def __init__(self, identifier): # load connector settings @@ -39,7 +39,7 @@ class AbstractMinimalConnector(ABC): setattr(self, field, getattr(info, field)) def search(self, query, min_confidence=None): - """ free text search """ + """free text search""" params = {} if min_confidence: params["min_confidence"] = min_confidence @@ -55,7 +55,7 @@ class AbstractMinimalConnector(ABC): return results def isbn_search(self, query): - """ isbn search """ + """isbn search""" params = {} data = get_data( "%s%s" % (self.isbn_search_url, query), @@ -70,27 +70,27 @@ class AbstractMinimalConnector(ABC): @abstractmethod def get_or_create_book(self, remote_id): - """ pull up a book record by whatever means possible """ + """pull up a book record by whatever means possible""" @abstractmethod def parse_search_data(self, data): - """ turn the result json from a search into a list """ + """turn the result json from a search into a list""" @abstractmethod def format_search_result(self, search_result): - """ create a SearchResult obj from json """ + """create a SearchResult obj from json""" @abstractmethod def parse_isbn_search_data(self, data): - """ turn the result json from a search into a list """ + """turn the result json from a search into a list""" @abstractmethod def format_isbn_search_result(self, search_result): - """ create a SearchResult obj from json """ + """create a SearchResult obj from json""" class AbstractConnector(AbstractMinimalConnector): - """ generic book data connector """ + """generic book data connector""" def __init__(self, identifier): super().__init__(identifier) @@ -99,14 +99,14 @@ class AbstractConnector(AbstractMinimalConnector): self.book_mappings = [] def is_available(self): - """ check if you're allowed to use this connector """ + """check if you're allowed to use this connector""" if self.max_query_count is not None: if self.connector.query_count >= self.max_query_count: return False return True def get_or_create_book(self, remote_id): - """ translate arbitrary json into an Activitypub dataclass """ + """translate arbitrary json into an Activitypub dataclass""" # first, check if we have the origin_id saved existing = models.Edition.find_existing_by_remote_id( remote_id @@ -151,7 +151,7 @@ class AbstractConnector(AbstractMinimalConnector): return edition def create_edition_from_data(self, work, edition_data): - """ if we already have the work, we're ready """ + """if we already have the work, we're ready""" mapped_data = dict_from_mappings(edition_data, self.book_mappings) mapped_data["work"] = work.remote_id edition_activity = activitypub.Edition(**mapped_data) @@ -171,7 +171,7 @@ class AbstractConnector(AbstractMinimalConnector): return edition def get_or_create_author(self, remote_id): - """ load that author """ + """load that author""" existing = models.Author.find_existing_by_remote_id(remote_id) if existing: return existing @@ -189,23 +189,23 @@ class AbstractConnector(AbstractMinimalConnector): @abstractmethod def is_work_data(self, data): - """ differentiate works and editions """ + """differentiate works and editions""" @abstractmethod def get_edition_from_work_data(self, data): - """ every work needs at least one edition """ + """every work needs at least one edition""" @abstractmethod def get_work_from_edition_data(self, data): - """ every edition needs a work """ + """every edition needs a work""" @abstractmethod def get_authors_from_data(self, data): - """ load author data """ + """load author data""" @abstractmethod def expand_book_data(self, book): - """ get more info on a book """ + """get more info on a book""" def dict_from_mappings(data, mappings): @@ -218,7 +218,7 @@ def dict_from_mappings(data, mappings): def get_data(url, params=None): - """ wrapper for request.get """ + """wrapper for request.get""" # check if the url is blocked if models.FederatedServer.is_blocked(url): raise ConnectorException( @@ -250,7 +250,7 @@ def get_data(url, params=None): def get_image(url): - """ wrapper for requesting an image """ + """wrapper for requesting an image""" try: resp = requests.get( url, @@ -268,7 +268,7 @@ def get_image(url): @dataclass class SearchResult: - """ standardized search result object """ + """standardized search result object""" title: str key: str @@ -284,14 +284,14 @@ class SearchResult: ) def json(self): - """ serialize a connector for json response """ + """serialize a connector for json response""" serialized = asdict(self) del serialized["connector"] return serialized class Mapping: - """ associate a local database field with a field in an external dataset """ + """associate a local database field with a field in an external dataset""" def __init__(self, local_field, remote_field=None, formatter=None): noop = lambda x: x @@ -301,7 +301,7 @@ class Mapping: self.formatter = formatter or noop def get_value(self, data): - """ pull a field from incoming json and return the formatted version """ + """pull a field from incoming json and return the formatted version""" value = data.get(self.remote_field) if not value: return None diff --git a/bookwyrm/connectors/bookwyrm_connector.py b/bookwyrm/connectors/bookwyrm_connector.py index f7869d55..640a0bca 100644 --- a/bookwyrm/connectors/bookwyrm_connector.py +++ b/bookwyrm/connectors/bookwyrm_connector.py @@ -4,7 +4,7 @@ from .abstract_connector import AbstractMinimalConnector, SearchResult class Connector(AbstractMinimalConnector): - """ this is basically just for search """ + """this is basically just for search""" def get_or_create_book(self, remote_id): edition = activitypub.resolve_remote_id(remote_id, model=models.Edition) diff --git a/bookwyrm/connectors/connector_manager.py b/bookwyrm/connectors/connector_manager.py index 53198c0a..20d273e0 100644 --- a/bookwyrm/connectors/connector_manager.py +++ b/bookwyrm/connectors/connector_manager.py @@ -16,11 +16,11 @@ logger = logging.getLogger(__name__) class ConnectorException(HTTPError): - """ when the connector can't do what was asked """ + """when the connector can't do what was asked""" def search(query, min_confidence=0.1): - """ find books based on arbitary keywords """ + """find books based on arbitary keywords""" if not query: return [] results = [] @@ -68,19 +68,19 @@ def search(query, min_confidence=0.1): def local_search(query, min_confidence=0.1, raw=False): - """ only look at local search results """ + """only look at local search results""" connector = load_connector(models.Connector.objects.get(local=True)) return connector.search(query, min_confidence=min_confidence, raw=raw) def isbn_local_search(query, raw=False): - """ only look at local search results """ + """only look at local search results""" connector = load_connector(models.Connector.objects.get(local=True)) return connector.isbn_search(query, raw=raw) def first_search_result(query, min_confidence=0.1): - """ search until you find a result that fits """ + """search until you find a result that fits""" for connector in get_connectors(): result = connector.search(query, min_confidence=min_confidence) if result: @@ -89,13 +89,13 @@ def first_search_result(query, min_confidence=0.1): def get_connectors(): - """ load all connectors """ + """load all connectors""" for info in models.Connector.objects.order_by("priority").all(): yield load_connector(info) def get_or_create_connector(remote_id): - """ get the connector related to the object's server """ + """get the connector related to the object's server""" url = urlparse(remote_id) identifier = url.netloc if not identifier: @@ -119,7 +119,7 @@ def get_or_create_connector(remote_id): @app.task def load_more_data(connector_id, book_id): - """ background the work of getting all 10,000 editions of LoTR """ + """background the work of getting all 10,000 editions of LoTR""" connector_info = models.Connector.objects.get(id=connector_id) connector = load_connector(connector_info) book = models.Book.objects.select_subclasses().get(id=book_id) @@ -127,7 +127,7 @@ def load_more_data(connector_id, book_id): def load_connector(connector_info): - """ instantiate the connector class """ + """instantiate the connector class""" connector = importlib.import_module( "bookwyrm.connectors.%s" % connector_info.connector_file ) @@ -137,6 +137,6 @@ def load_connector(connector_info): @receiver(signals.post_save, sender="bookwyrm.FederatedServer") # pylint: disable=unused-argument def create_connector(sender, instance, created, *args, **kwargs): - """ create a connector to an external bookwyrm server """ + """create a connector to an external bookwyrm server""" if instance.application_type == "bookwyrm": get_or_create_connector("https://{:s}".format(instance.server_name)) diff --git a/bookwyrm/connectors/openlibrary.py b/bookwyrm/connectors/openlibrary.py index 8ee738eb..a7c30b66 100644 --- a/bookwyrm/connectors/openlibrary.py +++ b/bookwyrm/connectors/openlibrary.py @@ -9,7 +9,7 @@ from .openlibrary_languages import languages class Connector(AbstractConnector): - """ instantiate a connector for OL """ + """instantiate a connector for OL""" def __init__(self, identifier): super().__init__(identifier) @@ -59,7 +59,7 @@ class Connector(AbstractConnector): ] def get_remote_id_from_data(self, data): - """ format a url from an openlibrary id field """ + """format a url from an openlibrary id field""" try: key = data["key"] except KeyError: @@ -87,7 +87,7 @@ class Connector(AbstractConnector): return get_data(url) def get_authors_from_data(self, data): - """ parse author json and load or create authors """ + """parse author json and load or create authors""" for author_blob in data.get("authors", []): author_blob = author_blob.get("author", author_blob) # this id is "/authors/OL1234567A" @@ -99,7 +99,7 @@ class Connector(AbstractConnector): yield author def get_cover_url(self, cover_blob, size="L"): - """ ask openlibrary for the cover """ + """ask openlibrary for the cover""" if not cover_blob: return None cover_id = cover_blob[0] @@ -141,7 +141,7 @@ class Connector(AbstractConnector): ) def load_edition_data(self, olkey): - """ query openlibrary for editions of a work """ + """query openlibrary for editions of a work""" url = "%s/works/%s/editions" % (self.books_url, olkey) return get_data(url) @@ -166,7 +166,7 @@ class Connector(AbstractConnector): def ignore_edition(edition_data): - """ don't load a million editions that have no metadata """ + """don't load a million editions that have no metadata""" # an isbn, we love to see it if edition_data.get("isbn_13") or edition_data.get("isbn_10"): return False @@ -185,19 +185,19 @@ def ignore_edition(edition_data): def get_description(description_blob): - """ descriptions can be a string or a dict """ + """descriptions can be a string or a dict""" if isinstance(description_blob, dict): return description_blob.get("value") return description_blob def get_openlibrary_key(key): - """ convert /books/OL27320736M into OL27320736M """ + """convert /books/OL27320736M into OL27320736M""" return key.split("/")[-1] def get_languages(language_blob): - """ /language/eng -> English """ + """/language/eng -> English""" langs = [] for lang in language_blob: langs.append(languages.get(lang.get("key", ""), None)) @@ -205,7 +205,7 @@ def get_languages(language_blob): def pick_default_edition(options): - """ favor physical copies with covers in english """ + """favor physical copies with covers in english""" if not options: return None if len(options) == 1: diff --git a/bookwyrm/connectors/self_connector.py b/bookwyrm/connectors/self_connector.py index 500ffd74..22835941 100644 --- a/bookwyrm/connectors/self_connector.py +++ b/bookwyrm/connectors/self_connector.py @@ -10,11 +10,11 @@ from .abstract_connector import AbstractConnector, SearchResult class Connector(AbstractConnector): - """ instantiate a connector """ + """instantiate a connector""" # pylint: disable=arguments-differ def search(self, query, min_confidence=0.1, raw=False): - """ search your local database """ + """search your local database""" if not query: return [] # first, try searching unqiue identifiers @@ -35,7 +35,7 @@ class Connector(AbstractConnector): return search_results def isbn_search(self, query, raw=False): - """ search your local database """ + """search your local database""" if not query: return [] @@ -87,11 +87,11 @@ class Connector(AbstractConnector): return None def parse_isbn_search_data(self, data): - """ it's already in the right format, don't even worry about it """ + """it's already in the right format, don't even worry about it""" return data def parse_search_data(self, data): - """ it's already in the right format, don't even worry about it """ + """it's already in the right format, don't even worry about it""" return data def expand_book_data(self, book): @@ -99,7 +99,7 @@ class Connector(AbstractConnector): def search_identifiers(query): - """ tries remote_id, isbn; defined as dedupe fields on the model """ + """tries remote_id, isbn; defined as dedupe fields on the model""" filters = [ {f.name: query} for f in models.Edition._meta.get_fields() @@ -115,7 +115,7 @@ def search_identifiers(query): def search_title_author(query, min_confidence): - """ searches for title and author """ + """searches for title and author""" vector = ( SearchVector("title", weight="A") + SearchVector("subtitle", weight="B") diff --git a/bookwyrm/context_processors.py b/bookwyrm/context_processors.py index 8f79a652..f5f25186 100644 --- a/bookwyrm/context_processors.py +++ b/bookwyrm/context_processors.py @@ -3,5 +3,5 @@ from bookwyrm import models def site_settings(request): # pylint: disable=unused-argument - """ include the custom info about the site """ + """include the custom info about the site""" return {"site": models.SiteSettings.objects.get()} diff --git a/bookwyrm/emailing.py b/bookwyrm/emailing.py index 1804254b..657310b0 100644 --- a/bookwyrm/emailing.py +++ b/bookwyrm/emailing.py @@ -8,7 +8,7 @@ from bookwyrm.settings import DOMAIN def email_data(): - """ fields every email needs """ + """fields every email needs""" site = models.SiteSettings.objects.get() if site.logo_small: logo_path = "/images/{}".format(site.logo_small.url) @@ -24,14 +24,14 @@ def email_data(): def invite_email(invite_request): - """ send out an invite code """ + """send out an invite code""" data = email_data() data["invite_link"] = invite_request.invite.link send_email.delay(invite_request.email, *format_email("invite", data)) def password_reset_email(reset_code): - """ generate a password reset email """ + """generate a password reset email""" data = email_data() data["reset_link"] = reset_code.link data["user"] = reset_code.user.display_name @@ -39,7 +39,7 @@ def password_reset_email(reset_code): def format_email(email_name, data): - """ render the email templates """ + """render the email templates""" subject = ( get_template("email/{}/subject.html".format(email_name)).render(data).strip() ) @@ -58,7 +58,7 @@ def format_email(email_name, data): @app.task def send_email(recipient, subject, html_content, text_content): - """ use a task to send the email """ + """use a task to send the email""" email = EmailMultiAlternatives( subject, text_content, settings.DEFAULT_FROM_EMAIL, [recipient] ) diff --git a/bookwyrm/forms.py b/bookwyrm/forms.py index df68334e..b6197f33 100644 --- a/bookwyrm/forms.py +++ b/bookwyrm/forms.py @@ -12,7 +12,7 @@ from bookwyrm import models class CustomForm(ModelForm): - """ add css classes to the forms """ + """add css classes to the forms""" def __init__(self, *args, **kwargs): css_classes = defaultdict(lambda: "") @@ -198,7 +198,7 @@ class ImportForm(forms.Form): class ExpiryWidget(widgets.Select): def value_from_datadict(self, data, files, name): - """ human-readable exiration time buckets """ + """human-readable exiration time buckets""" selected_string = super().value_from_datadict(data, files, name) if selected_string == "day": @@ -217,7 +217,7 @@ class ExpiryWidget(widgets.Select): class InviteRequestForm(CustomForm): def clean(self): - """ make sure the email isn't in use by a registered user """ + """make sure the email isn't in use by a registered user""" cleaned_data = super().clean() email = cleaned_data.get("email") if email and models.User.objects.filter(email=email).exists(): diff --git a/bookwyrm/importers/goodreads_import.py b/bookwyrm/importers/goodreads_import.py index 0b126c14..7b577ea8 100644 --- a/bookwyrm/importers/goodreads_import.py +++ b/bookwyrm/importers/goodreads_import.py @@ -9,7 +9,7 @@ class GoodreadsImporter(Importer): service = "GoodReads" def parse_fields(self, entry): - """ handle the specific fields in goodreads csvs """ + """handle the specific fields in goodreads csvs""" entry.update({"import_source": self.service}) # add missing 'Date Started' field entry.update({"Date Started": None}) diff --git a/bookwyrm/importers/importer.py b/bookwyrm/importers/importer.py index ddbfa304..c1e41897 100644 --- a/bookwyrm/importers/importer.py +++ b/bookwyrm/importers/importer.py @@ -10,7 +10,7 @@ logger = logging.getLogger(__name__) class Importer: - """ Generic class for csv data import from an outside service """ + """Generic class for csv data import from an outside service""" service = "Unknown" delimiter = "," @@ -18,7 +18,7 @@ class Importer: mandatory_fields = ["Title", "Author"] def create_job(self, user, csv_file, include_reviews, privacy): - """ check over a csv and creates a database entry for the job""" + """check over a csv and creates a database entry for the job""" job = ImportJob.objects.create( user=user, include_reviews=include_reviews, privacy=privacy ) @@ -32,16 +32,16 @@ class Importer: return job def save_item(self, job, index, data): # pylint: disable=no-self-use - """ creates and saves an import item """ + """creates and saves an import item""" ImportItem(job=job, index=index, data=data).save() def parse_fields(self, entry): - """ updates csv data with additional info """ + """updates csv data with additional info""" entry.update({"import_source": self.service}) return entry def create_retry_job(self, user, original_job, items): - """ retry items that didn't import """ + """retry items that didn't import""" job = ImportJob.objects.create( user=user, include_reviews=original_job.include_reviews, @@ -53,7 +53,7 @@ class Importer: return job def start_import(self, job): - """ initalizes a csv import job """ + """initalizes a csv import job""" result = import_data.delay(self.service, job.id) job.task_id = result.id job.save() @@ -61,7 +61,7 @@ class Importer: @app.task def import_data(source, job_id): - """ does the actual lookup work in a celery task """ + """does the actual lookup work in a celery task""" job = ImportJob.objects.get(id=job_id) try: for item in job.items.all(): @@ -89,7 +89,7 @@ def import_data(source, job_id): def handle_imported_book(source, user, item, include_reviews, privacy): - """ process a csv and then post about it """ + """process a csv and then post about it""" if isinstance(item.book, models.Work): item.book = item.book.default_edition if not item.book: diff --git a/bookwyrm/importers/librarything_import.py b/bookwyrm/importers/librarything_import.py index 3755cb1a..b3175a82 100644 --- a/bookwyrm/importers/librarything_import.py +++ b/bookwyrm/importers/librarything_import.py @@ -6,7 +6,7 @@ from . import Importer class LibrarythingImporter(Importer): - """ csv downloads from librarything """ + """csv downloads from librarything""" service = "LibraryThing" delimiter = "\t" @@ -15,7 +15,7 @@ class LibrarythingImporter(Importer): mandatory_fields = ["Title", "Primary Author"] def parse_fields(self, entry): - """ custom parsing for librarything """ + """custom parsing for librarything""" data = {} data["import_source"] = self.service data["Book Id"] = entry["Book Id"] diff --git a/bookwyrm/management/commands/deduplicate_book_data.py b/bookwyrm/management/commands/deduplicate_book_data.py index edd91a71..ed01a784 100644 --- a/bookwyrm/management/commands/deduplicate_book_data.py +++ b/bookwyrm/management/commands/deduplicate_book_data.py @@ -6,7 +6,7 @@ from bookwyrm import models def update_related(canonical, obj): - """ update all the models with fk to the object being removed """ + """update all the models with fk to the object being removed""" # move related models to canonical related_models = [ (r.remote_field.name, r.related_model) for r in canonical._meta.related_objects @@ -24,7 +24,7 @@ def update_related(canonical, obj): def copy_data(canonical, obj): - """ try to get the most data possible """ + """try to get the most data possible""" for data_field in obj._meta.get_fields(): if not hasattr(data_field, "activitypub_field"): continue @@ -38,7 +38,7 @@ def copy_data(canonical, obj): def dedupe_model(model): - """ combine duplicate editions and update related models """ + """combine duplicate editions and update related models""" fields = model._meta.get_fields() dedupe_fields = [ f for f in fields if hasattr(f, "deduplication_field") and f.deduplication_field @@ -68,12 +68,12 @@ def dedupe_model(model): class Command(BaseCommand): - """ dedplucate allllll the book data models """ + """dedplucate allllll the book data models""" help = "merges duplicate book data" # pylint: disable=no-self-use,unused-argument def handle(self, *args, **options): - """ run deudplications """ + """run deudplications""" dedupe_model(models.Edition) dedupe_model(models.Work) dedupe_model(models.Author) diff --git a/bookwyrm/management/commands/erase_streams.py b/bookwyrm/management/commands/erase_streams.py index 042e857f..1d34b1bb 100644 --- a/bookwyrm/management/commands/erase_streams.py +++ b/bookwyrm/management/commands/erase_streams.py @@ -10,15 +10,15 @@ r = redis.Redis( def erase_streams(): - """ throw the whole redis away """ + """throw the whole redis away""" r.flushall() class Command(BaseCommand): - """ delete activity streams for all users """ + """delete activity streams for all users""" help = "Delete all the user streams" # pylint: disable=no-self-use,unused-argument def handle(self, *args, **options): - """ flush all, baby """ + """flush all, baby""" erase_streams() diff --git a/bookwyrm/management/commands/initdb.py b/bookwyrm/management/commands/initdb.py index a86a1652..0c0cc61f 100644 --- a/bookwyrm/management/commands/initdb.py +++ b/bookwyrm/management/commands/initdb.py @@ -108,7 +108,7 @@ def init_connectors(): def init_federated_servers(): - """ big no to nazis """ + """big no to nazis""" built_in_blocks = ["gab.ai", "gab.com"] for server in built_in_blocks: FederatedServer.objects.create( diff --git a/bookwyrm/management/commands/populate_streams.py b/bookwyrm/management/commands/populate_streams.py index 4cd2036a..04f6bf6e 100644 --- a/bookwyrm/management/commands/populate_streams.py +++ b/bookwyrm/management/commands/populate_streams.py @@ -10,7 +10,7 @@ r = redis.Redis( def populate_streams(): - """ build all the streams for all the users """ + """build all the streams for all the users""" users = models.User.objects.filter( local=True, is_active=True, @@ -21,10 +21,10 @@ def populate_streams(): class Command(BaseCommand): - """ start all over with user streams """ + """start all over with user streams""" help = "Populate streams for all users" # pylint: disable=no-self-use,unused-argument def handle(self, *args, **options): - """ run feed builder """ + """run feed builder""" populate_streams() diff --git a/bookwyrm/management/commands/remove_editions.py b/bookwyrm/management/commands/remove_editions.py index 6829c6d1..9eb9b7da 100644 --- a/bookwyrm/management/commands/remove_editions.py +++ b/bookwyrm/management/commands/remove_editions.py @@ -5,7 +5,7 @@ from bookwyrm import models def remove_editions(): - """ combine duplicate editions and update related models """ + """combine duplicate editions and update related models""" # not in use filters = { "%s__isnull" % r.name: True for r in models.Edition._meta.related_objects @@ -33,10 +33,10 @@ def remove_editions(): class Command(BaseCommand): - """ dedplucate allllll the book data models """ + """dedplucate allllll the book data models""" help = "merges duplicate book data" # pylint: disable=no-self-use,unused-argument def handle(self, *args, **options): - """ run deudplications """ + """run deudplications""" remove_editions() diff --git a/bookwyrm/migrations/0046_reviewrating.py b/bookwyrm/migrations/0046_reviewrating.py index 8d149004..26f6f36a 100644 --- a/bookwyrm/migrations/0046_reviewrating.py +++ b/bookwyrm/migrations/0046_reviewrating.py @@ -8,7 +8,7 @@ from psycopg2.extras import execute_values def convert_review_rating(app_registry, schema_editor): - """ take rating type Reviews and convert them to ReviewRatings """ + """take rating type Reviews and convert them to ReviewRatings""" db_alias = schema_editor.connection.alias reviews = ( @@ -29,7 +29,7 @@ VALUES %s""", def unconvert_review_rating(app_registry, schema_editor): - """ undo the conversion from ratings back to reviews""" + """undo the conversion from ratings back to reviews""" # All we need to do to revert this is drop the table, which Django will do # on its own, as long as we have a valid reverse function. So, this is a # no-op function so Django will do its thing diff --git a/bookwyrm/models/activitypub_mixin.py b/bookwyrm/models/activitypub_mixin.py index 02cfafc0..83b4c0ab 100644 --- a/bookwyrm/models/activitypub_mixin.py +++ b/bookwyrm/models/activitypub_mixin.py @@ -31,18 +31,18 @@ PropertyField = namedtuple("PropertyField", ("set_activity_from_field")) def set_activity_from_property_field(activity, obj, field): - """ assign a model property value to the activity json """ + """assign a model property value to the activity json""" activity[field[1]] = getattr(obj, field[0]) class ActivitypubMixin: - """ add this mixin for models that are AP serializable """ + """add this mixin for models that are AP serializable""" activity_serializer = lambda: {} reverse_unfurl = False def __init__(self, *args, **kwargs): - """ collect some info on model fields """ + """collect some info on model fields""" self.image_fields = [] self.many_to_many_fields = [] self.simple_fields = [] # "simple" @@ -85,7 +85,7 @@ class ActivitypubMixin: @classmethod def find_existing_by_remote_id(cls, remote_id): - """ look up a remote id in the db """ + """look up a remote id in the db""" return cls.find_existing({"id": remote_id}) @classmethod @@ -126,7 +126,7 @@ class ActivitypubMixin: return match.first() def broadcast(self, activity, sender, software=None): - """ send out an activity """ + """send out an activity""" broadcast_task.delay( sender.id, json.dumps(activity, cls=activitypub.ActivityEncoder), @@ -134,7 +134,7 @@ class ActivitypubMixin: ) def get_recipients(self, software=None): - """ figure out which inbox urls to post to """ + """figure out which inbox urls to post to""" # first we have to figure out who should receive this activity privacy = self.privacy if hasattr(self, "privacy") else "public" # is this activity owned by a user (statuses, lists, shelves), or is it @@ -182,20 +182,20 @@ class ActivitypubMixin: return list(set(recipients)) def to_activity_dataclass(self): - """ convert from a model to an activity """ + """convert from a model to an activity""" activity = generate_activity(self) return self.activity_serializer(**activity) def to_activity(self, **kwargs): # pylint: disable=unused-argument - """ convert from a model to a json activity """ + """convert from a model to a json activity""" return self.to_activity_dataclass().serialize() class ObjectMixin(ActivitypubMixin): - """ add this mixin for object models that are AP serializable """ + """add this mixin for object models that are AP serializable""" def save(self, *args, created=None, **kwargs): - """ broadcast created/updated/deleted objects as appropriate """ + """broadcast created/updated/deleted objects as appropriate""" broadcast = kwargs.get("broadcast", True) # this bonus kwarg would cause an error in the base save method if "broadcast" in kwargs: @@ -254,7 +254,7 @@ class ObjectMixin(ActivitypubMixin): self.broadcast(activity, user) def to_create_activity(self, user, **kwargs): - """ returns the object wrapped in a Create activity """ + """returns the object wrapped in a Create activity""" activity_object = self.to_activity_dataclass(**kwargs) signature = None @@ -280,7 +280,7 @@ class ObjectMixin(ActivitypubMixin): ).serialize() def to_delete_activity(self, user): - """ notice of deletion """ + """notice of deletion""" return activitypub.Delete( id=self.remote_id + "/activity", actor=user.remote_id, @@ -290,7 +290,7 @@ class ObjectMixin(ActivitypubMixin): ).serialize() def to_update_activity(self, user): - """ wrapper for Updates to an activity """ + """wrapper for Updates to an activity""" activity_id = "%s#update/%s" % (self.remote_id, uuid4()) return activitypub.Update( id=activity_id, @@ -306,13 +306,13 @@ class OrderedCollectionPageMixin(ObjectMixin): @property def collection_remote_id(self): - """ this can be overriden if there's a special remote id, ie outbox """ + """this can be overriden if there's a special remote id, ie outbox""" return self.remote_id def to_ordered_collection( self, queryset, remote_id=None, page=False, collection_only=False, **kwargs ): - """ an ordered collection of whatevers """ + """an ordered collection of whatevers""" if not queryset.ordered: raise RuntimeError("queryset must be ordered") @@ -341,11 +341,11 @@ class OrderedCollectionPageMixin(ObjectMixin): class OrderedCollectionMixin(OrderedCollectionPageMixin): - """ extends activitypub models to work as ordered collections """ + """extends activitypub models to work as ordered collections""" @property def collection_queryset(self): - """ usually an ordered collection model aggregates a different model """ + """usually an ordered collection model aggregates a different model""" raise NotImplementedError("Model must define collection_queryset") activity_serializer = activitypub.OrderedCollection @@ -354,24 +354,24 @@ class OrderedCollectionMixin(OrderedCollectionPageMixin): return self.to_ordered_collection(self.collection_queryset, **kwargs) def to_activity(self, **kwargs): - """ an ordered collection of the specified model queryset """ + """an ordered collection of the specified model queryset""" return self.to_ordered_collection( self.collection_queryset, **kwargs ).serialize() class CollectionItemMixin(ActivitypubMixin): - """ for items that are part of an (Ordered)Collection """ + """for items that are part of an (Ordered)Collection""" activity_serializer = activitypub.CollectionItem def broadcast(self, activity, sender, software="bookwyrm"): - """ only send book collection updates to other bookwyrm instances """ + """only send book collection updates to other bookwyrm instances""" super().broadcast(activity, sender, software=software) @property def privacy(self): - """ inherit the privacy of the list, or direct if pending """ + """inherit the privacy of the list, or direct if pending""" collection_field = getattr(self, self.collection_field) if self.approved: return collection_field.privacy @@ -379,7 +379,7 @@ class CollectionItemMixin(ActivitypubMixin): @property def recipients(self): - """ the owner of the list is a direct recipient """ + """the owner of the list is a direct recipient""" collection_field = getattr(self, self.collection_field) if collection_field.user.local: # don't broadcast to yourself @@ -387,7 +387,7 @@ class CollectionItemMixin(ActivitypubMixin): return [collection_field.user] def save(self, *args, broadcast=True, **kwargs): - """ broadcast updated """ + """broadcast updated""" # first off, we want to save normally no matter what super().save(*args, **kwargs) @@ -400,14 +400,14 @@ class CollectionItemMixin(ActivitypubMixin): self.broadcast(activity, self.user) def delete(self, *args, broadcast=True, **kwargs): - """ broadcast a remove activity """ + """broadcast a remove activity""" activity = self.to_remove_activity(self.user) super().delete(*args, **kwargs) if self.user.local and broadcast: self.broadcast(activity, self.user) def to_add_activity(self, user): - """ AP for shelving a book""" + """AP for shelving a book""" collection_field = getattr(self, self.collection_field) return activitypub.Add( id="{:s}#add".format(collection_field.remote_id), @@ -417,7 +417,7 @@ class CollectionItemMixin(ActivitypubMixin): ).serialize() def to_remove_activity(self, user): - """ AP for un-shelving a book""" + """AP for un-shelving a book""" collection_field = getattr(self, self.collection_field) return activitypub.Remove( id="{:s}#remove".format(collection_field.remote_id), @@ -428,24 +428,24 @@ class CollectionItemMixin(ActivitypubMixin): class ActivityMixin(ActivitypubMixin): - """ add this mixin for models that are AP serializable """ + """add this mixin for models that are AP serializable""" def save(self, *args, broadcast=True, **kwargs): - """ broadcast activity """ + """broadcast activity""" super().save(*args, **kwargs) user = self.user if hasattr(self, "user") else self.user_subject if broadcast and user.local: self.broadcast(self.to_activity(), user) def delete(self, *args, broadcast=True, **kwargs): - """ nevermind, undo that activity """ + """nevermind, undo that activity""" user = self.user if hasattr(self, "user") else self.user_subject if broadcast and user.local: self.broadcast(self.to_undo_activity(), user) super().delete(*args, **kwargs) def to_undo_activity(self): - """ undo an action """ + """undo an action""" user = self.user if hasattr(self, "user") else self.user_subject return activitypub.Undo( id="%s#undo" % self.remote_id, @@ -455,7 +455,7 @@ class ActivityMixin(ActivitypubMixin): def generate_activity(obj): - """ go through the fields on an object """ + """go through the fields on an object""" activity = {} for field in obj.activity_fields: field.set_activity_from_field(activity, obj) @@ -478,7 +478,7 @@ def generate_activity(obj): def unfurl_related_field(related_field, sort_field=None): - """ load reverse lookups (like public key owner or Status attachment """ + """load reverse lookups (like public key owner or Status attachment""" if sort_field and hasattr(related_field, "all"): return [ unfurl_related_field(i) for i in related_field.order_by(sort_field).all() @@ -494,7 +494,7 @@ def unfurl_related_field(related_field, sort_field=None): @app.task def broadcast_task(sender_id, activity, recipients): - """ the celery task for broadcast """ + """the celery task for broadcast""" user_model = apps.get_model("bookwyrm.User", require_ready=True) sender = user_model.objects.get(id=sender_id) for recipient in recipients: @@ -505,7 +505,7 @@ def broadcast_task(sender_id, activity, recipients): def sign_and_send(sender, data, destination): - """ crpyto whatever and http junk """ + """crpyto whatever and http junk""" now = http_date() if not sender.key_pair.private_key: @@ -534,7 +534,7 @@ def sign_and_send(sender, data, destination): def to_ordered_collection_page( queryset, remote_id, id_only=False, page=1, pure=False, **kwargs ): - """ serialize and pagiante a queryset """ + """serialize and pagiante a queryset""" paginated = Paginator(queryset, PAGE_LENGTH) activity_page = paginated.get_page(page) diff --git a/bookwyrm/models/attachment.py b/bookwyrm/models/attachment.py index eaeca11e..c8b2e51c 100644 --- a/bookwyrm/models/attachment.py +++ b/bookwyrm/models/attachment.py @@ -8,7 +8,7 @@ from . import fields class Attachment(ActivitypubMixin, BookWyrmModel): - """ an image (or, in the future, video etc) associated with a status """ + """an image (or, in the future, video etc) associated with a status""" status = models.ForeignKey( "Status", on_delete=models.CASCADE, related_name="attachments", null=True @@ -16,13 +16,13 @@ class Attachment(ActivitypubMixin, BookWyrmModel): reverse_unfurl = True class Meta: - """ one day we'll have other types of attachments besides images """ + """one day we'll have other types of attachments besides images""" abstract = True class Image(Attachment): - """ an image attachment """ + """an image attachment""" image = fields.ImageField( upload_to="status/", diff --git a/bookwyrm/models/author.py b/bookwyrm/models/author.py index 4c5fe6c8..b9a4b146 100644 --- a/bookwyrm/models/author.py +++ b/bookwyrm/models/author.py @@ -9,7 +9,7 @@ from . import fields class Author(BookDataModel): - """ basic biographic info """ + """basic biographic info""" wikipedia_link = fields.CharField( max_length=255, blank=True, null=True, deduplication_field=True @@ -24,7 +24,7 @@ class Author(BookDataModel): bio = fields.HtmlField(null=True, blank=True) def get_remote_id(self): - """ editions and works both use "book" instead of model_name """ + """editions and works both use "book" instead of model_name""" return "https://%s/author/%s" % (DOMAIN, self.id) activity_serializer = activitypub.Author diff --git a/bookwyrm/models/base_model.py b/bookwyrm/models/base_model.py index 261c9686..e85ff733 100644 --- a/bookwyrm/models/base_model.py +++ b/bookwyrm/models/base_model.py @@ -7,14 +7,14 @@ from .fields import RemoteIdField class BookWyrmModel(models.Model): - """ shared fields """ + """shared fields""" created_date = models.DateTimeField(auto_now_add=True) updated_date = models.DateTimeField(auto_now=True) remote_id = RemoteIdField(null=True, activitypub_field="id") def get_remote_id(self): - """ generate a url that resolves to the local object """ + """generate a url that resolves to the local object""" base_path = "https://%s" % DOMAIN if hasattr(self, "user"): base_path = "%s%s" % (base_path, self.user.local_path) @@ -22,17 +22,17 @@ class BookWyrmModel(models.Model): return "%s/%s/%d" % (base_path, model_name, self.id) class Meta: - """ this is just here to provide default fields for other models """ + """this is just here to provide default fields for other models""" abstract = True @property def local_path(self): - """ how to link to this object in the local app """ + """how to link to this object in the local app""" return self.get_remote_id().replace("https://%s" % DOMAIN, "") def visible_to_user(self, viewer): - """ is a user authorized to view an object? """ + """is a user authorized to view an object?""" # make sure this is an object with privacy owned by a user if not hasattr(self, "user") or not hasattr(self, "privacy"): return None @@ -65,7 +65,7 @@ class BookWyrmModel(models.Model): @receiver(models.signals.post_save) # pylint: disable=unused-argument def set_remote_id(sender, instance, created, *args, **kwargs): - """ set the remote_id after save (when the id is available) """ + """set the remote_id after save (when the id is available)""" if not created or not hasattr(instance, "get_remote_id"): return if not instance.remote_id: diff --git a/bookwyrm/models/book.py b/bookwyrm/models/book.py index 5280c7aa..dd098e56 100644 --- a/bookwyrm/models/book.py +++ b/bookwyrm/models/book.py @@ -13,7 +13,7 @@ from . import fields class BookDataModel(ObjectMixin, BookWyrmModel): - """ fields shared between editable book data (books, works, authors) """ + """fields shared between editable book data (books, works, authors)""" origin_id = models.CharField(max_length=255, null=True, blank=True) openlibrary_key = fields.CharField( @@ -33,12 +33,12 @@ class BookDataModel(ObjectMixin, BookWyrmModel): ) class Meta: - """ can't initialize this model, that wouldn't make sense """ + """can't initialize this model, that wouldn't make sense""" abstract = True def save(self, *args, **kwargs): - """ ensure that the remote_id is within this instance """ + """ensure that the remote_id is within this instance""" if self.id: self.remote_id = self.get_remote_id() else: @@ -47,12 +47,12 @@ class BookDataModel(ObjectMixin, BookWyrmModel): return super().save(*args, **kwargs) def broadcast(self, activity, sender, software="bookwyrm"): - """ only send book data updates to other bookwyrm instances """ + """only send book data updates to other bookwyrm instances""" super().broadcast(activity, sender, software=software) class Book(BookDataModel): - """ a generic book, which can mean either an edition or a work """ + """a generic book, which can mean either an edition or a work""" connector = models.ForeignKey("Connector", on_delete=models.PROTECT, null=True) @@ -83,17 +83,17 @@ class Book(BookDataModel): @property def author_text(self): - """ format a list of authors """ + """format a list of authors""" return ", ".join(a.name for a in self.authors.all()) @property def latest_readthrough(self): - """ most recent readthrough activity """ + """most recent readthrough activity""" return self.readthrough_set.order_by("-updated_date").first() @property def edition_info(self): - """ properties of this edition, as a string """ + """properties of this edition, as a string""" items = [ self.physical_format if hasattr(self, "physical_format") else None, self.languages[0] + " language" @@ -106,20 +106,20 @@ class Book(BookDataModel): @property def alt_text(self): - """ image alt test """ + """image alt test""" text = "%s" % self.title if self.edition_info: text += " (%s)" % self.edition_info return text def save(self, *args, **kwargs): - """ can't be abstract for query reasons, but you shouldn't USE it """ + """can't be abstract for query reasons, but you shouldn't USE it""" if not isinstance(self, Edition) and not isinstance(self, Work): raise ValueError("Books should be added as Editions or Works") return super().save(*args, **kwargs) def get_remote_id(self): - """ editions and works both use "book" instead of model_name """ + """editions and works both use "book" instead of model_name""" return "https://%s/book/%d" % (DOMAIN, self.id) def __repr__(self): @@ -131,7 +131,7 @@ class Book(BookDataModel): class Work(OrderedCollectionPageMixin, Book): - """ a work (an abstract concept of a book that manifests in an edition) """ + """a work (an abstract concept of a book that manifests in an edition)""" # library of congress catalog control number lccn = fields.CharField( @@ -143,19 +143,19 @@ class Work(OrderedCollectionPageMixin, Book): ) def save(self, *args, **kwargs): - """ set some fields on the edition object """ + """set some fields on the edition object""" # set rank for edition in self.editions.all(): edition.save() return super().save(*args, **kwargs) def get_default_edition(self): - """ in case the default edition is not set """ + """in case the default edition is not set""" return self.default_edition or self.editions.order_by("-edition_rank").first() @transaction.atomic() def reset_default_edition(self): - """ sets a new default edition based on computed rank """ + """sets a new default edition based on computed rank""" self.default_edition = None # editions are re-ranked implicitly self.save() @@ -163,11 +163,11 @@ class Work(OrderedCollectionPageMixin, Book): self.save() def to_edition_list(self, **kwargs): - """ an ordered collection of editions """ + """an ordered collection of editions""" return self.to_ordered_collection( self.editions.order_by("-edition_rank").all(), remote_id="%s/editions" % self.remote_id, - **kwargs + **kwargs, ) activity_serializer = activitypub.Work @@ -176,7 +176,7 @@ class Work(OrderedCollectionPageMixin, Book): class Edition(Book): - """ an edition of a book """ + """an edition of a book""" # these identifiers only apply to editions, not works isbn_10 = fields.CharField( @@ -215,7 +215,7 @@ class Edition(Book): name_field = "title" def get_rank(self, ignore_default=False): - """ calculate how complete the data is on this edition """ + """calculate how complete the data is on this edition""" if ( not ignore_default and self.parent_work @@ -235,7 +235,7 @@ class Edition(Book): return rank def save(self, *args, **kwargs): - """ set some fields on the edition object """ + """set some fields on the edition object""" # calculate isbn 10/13 if self.isbn_13 and self.isbn_13[:3] == "978" and not self.isbn_10: self.isbn_10 = isbn_13_to_10(self.isbn_13) @@ -249,7 +249,7 @@ class Edition(Book): def isbn_10_to_13(isbn_10): - """ convert an isbn 10 into an isbn 13 """ + """convert an isbn 10 into an isbn 13""" isbn_10 = re.sub(r"[^0-9X]", "", isbn_10) # drop the last character of the isbn 10 number (the original checkdigit) converted = isbn_10[:9] @@ -271,7 +271,7 @@ def isbn_10_to_13(isbn_10): def isbn_13_to_10(isbn_13): - """ convert isbn 13 to 10, if possible """ + """convert isbn 13 to 10, if possible""" if isbn_13[:3] != "978": return None diff --git a/bookwyrm/models/connector.py b/bookwyrm/models/connector.py index 11bdbee2..6043fc02 100644 --- a/bookwyrm/models/connector.py +++ b/bookwyrm/models/connector.py @@ -9,7 +9,7 @@ ConnectorFiles = models.TextChoices("ConnectorFiles", CONNECTORS) class Connector(BookWyrmModel): - """ book data source connectors """ + """book data source connectors""" identifier = models.CharField(max_length=255, unique=True) priority = models.IntegerField(default=2) @@ -32,7 +32,7 @@ class Connector(BookWyrmModel): query_count_expiry = models.DateTimeField(auto_now_add=True, blank=True) class Meta: - """ check that there's code to actually use this connector """ + """check that there's code to actually use this connector""" constraints = [ models.CheckConstraint( diff --git a/bookwyrm/models/favorite.py b/bookwyrm/models/favorite.py index 7b72d175..c4518119 100644 --- a/bookwyrm/models/favorite.py +++ b/bookwyrm/models/favorite.py @@ -11,7 +11,7 @@ from .status import Status class Favorite(ActivityMixin, BookWyrmModel): - """ fav'ing a post """ + """fav'ing a post""" user = fields.ForeignKey( "User", on_delete=models.PROTECT, activitypub_field="actor" @@ -24,11 +24,11 @@ class Favorite(ActivityMixin, BookWyrmModel): @classmethod def ignore_activity(cls, activity): - """ don't bother with incoming favs of unknown statuses """ + """don't bother with incoming favs of unknown statuses""" return not Status.objects.filter(remote_id=activity.object).exists() def save(self, *args, **kwargs): - """ update user active time """ + """update user active time""" self.user.last_active_date = timezone.now() self.user.save(broadcast=False) super().save(*args, **kwargs) @@ -45,7 +45,7 @@ class Favorite(ActivityMixin, BookWyrmModel): ) def delete(self, *args, **kwargs): - """ delete and delete notifications """ + """delete and delete notifications""" # check for notification if self.status.user.local: notification_model = apps.get_model( @@ -62,6 +62,6 @@ class Favorite(ActivityMixin, BookWyrmModel): super().delete(*args, **kwargs) class Meta: - """ can't fav things twice """ + """can't fav things twice""" unique_together = ("user", "status") diff --git a/bookwyrm/models/federated_server.py b/bookwyrm/models/federated_server.py index aa2b2f6a..7d446ca0 100644 --- a/bookwyrm/models/federated_server.py +++ b/bookwyrm/models/federated_server.py @@ -13,7 +13,7 @@ FederationStatus = models.TextChoices( class FederatedServer(BookWyrmModel): - """ store which servers we federate with """ + """store which servers we federate with""" server_name = models.CharField(max_length=255, unique=True) status = models.CharField( @@ -25,7 +25,7 @@ class FederatedServer(BookWyrmModel): notes = models.TextField(null=True, blank=True) def block(self): - """ block a server """ + """block a server""" self.status = "blocked" self.save() @@ -35,7 +35,7 @@ class FederatedServer(BookWyrmModel): ) def unblock(self): - """ unblock a server """ + """unblock a server""" self.status = "federated" self.save() @@ -45,7 +45,7 @@ class FederatedServer(BookWyrmModel): @classmethod def is_blocked(cls, url): - """ look up if a domain is blocked """ + """look up if a domain is blocked""" url = urlparse(url) domain = url.netloc return cls.objects.filter(server_name=domain, status="blocked").exists() diff --git a/bookwyrm/models/fields.py b/bookwyrm/models/fields.py index a1b2035b..123b3efa 100644 --- a/bookwyrm/models/fields.py +++ b/bookwyrm/models/fields.py @@ -18,7 +18,7 @@ from bookwyrm.settings import DOMAIN def validate_remote_id(value): - """ make sure the remote_id looks like a url """ + """make sure the remote_id looks like a url""" if not value or not re.match(r"^http.?:\/\/[^\s]+$", value): raise ValidationError( _("%(value)s is not a valid remote_id"), @@ -27,7 +27,7 @@ def validate_remote_id(value): def validate_localname(value): - """ make sure localnames look okay """ + """make sure localnames look okay""" if not re.match(r"^[A-Za-z\-_\.0-9]+$", value): raise ValidationError( _("%(value)s is not a valid username"), @@ -36,7 +36,7 @@ def validate_localname(value): def validate_username(value): - """ make sure usernames look okay """ + """make sure usernames look okay""" if not re.match(r"^[A-Za-z\-_\.0-9]+@[A-Za-z\-_\.0-9]+\.[a-z]{2,}$", value): raise ValidationError( _("%(value)s is not a valid username"), @@ -45,7 +45,7 @@ def validate_username(value): class ActivitypubFieldMixin: - """ make a database field serializable """ + """make a database field serializable""" def __init__( self, @@ -64,7 +64,7 @@ class ActivitypubFieldMixin: super().__init__(*args, **kwargs) def set_field_from_activity(self, instance, data): - """ helper function for assinging a value to the field """ + """helper function for assinging a value to the field""" try: value = getattr(data, self.get_activitypub_field()) except AttributeError: @@ -78,7 +78,7 @@ class ActivitypubFieldMixin: setattr(instance, self.name, formatted) def set_activity_from_field(self, activity, instance): - """ update the json object """ + """update the json object""" value = getattr(instance, self.name) formatted = self.field_to_activity(value) if formatted is None: @@ -94,19 +94,19 @@ class ActivitypubFieldMixin: activity[key] = formatted def field_to_activity(self, value): - """ formatter to convert a model value into activitypub """ + """formatter to convert a model value into activitypub""" if hasattr(self, "activitypub_wrapper"): return {self.activitypub_wrapper: value} return value def field_from_activity(self, value): - """ formatter to convert activitypub into a model value """ + """formatter to convert activitypub into a model value""" if value and hasattr(self, "activitypub_wrapper"): value = value.get(self.activitypub_wrapper) return value def get_activitypub_field(self): - """ model_field_name to activitypubFieldName """ + """model_field_name to activitypubFieldName""" if self.activitypub_field: return self.activitypub_field name = self.name.split(".")[-1] @@ -115,7 +115,7 @@ class ActivitypubFieldMixin: class ActivitypubRelatedFieldMixin(ActivitypubFieldMixin): - """ default (de)serialization for foreign key and one to one """ + """default (de)serialization for foreign key and one to one""" def __init__(self, *args, load_remote=True, **kwargs): self.load_remote = load_remote @@ -146,7 +146,7 @@ class ActivitypubRelatedFieldMixin(ActivitypubFieldMixin): class RemoteIdField(ActivitypubFieldMixin, models.CharField): - """ a url that serves as a unique identifier """ + """a url that serves as a unique identifier""" def __init__(self, *args, max_length=255, validators=None, **kwargs): validators = validators or [validate_remote_id] @@ -156,7 +156,7 @@ class RemoteIdField(ActivitypubFieldMixin, models.CharField): class UsernameField(ActivitypubFieldMixin, models.CharField): - """ activitypub-aware username field """ + """activitypub-aware username field""" def __init__(self, activitypub_field="preferredUsername", **kwargs): self.activitypub_field = activitypub_field @@ -172,7 +172,7 @@ class UsernameField(ActivitypubFieldMixin, models.CharField): ) def deconstruct(self): - """ implementation of models.Field deconstruct """ + """implementation of models.Field deconstruct""" name, path, args, kwargs = super().deconstruct() del kwargs["verbose_name"] del kwargs["max_length"] @@ -191,7 +191,7 @@ PrivacyLevels = models.TextChoices( class PrivacyField(ActivitypubFieldMixin, models.CharField): - """ this maps to two differente activitypub fields """ + """this maps to two differente activitypub fields""" public = "https://www.w3.org/ns/activitystreams#Public" @@ -236,7 +236,7 @@ class PrivacyField(ActivitypubFieldMixin, models.CharField): class ForeignKey(ActivitypubRelatedFieldMixin, models.ForeignKey): - """ activitypub-aware foreign key field """ + """activitypub-aware foreign key field""" def field_to_activity(self, value): if not value: @@ -245,7 +245,7 @@ class ForeignKey(ActivitypubRelatedFieldMixin, models.ForeignKey): class OneToOneField(ActivitypubRelatedFieldMixin, models.OneToOneField): - """ activitypub-aware foreign key field """ + """activitypub-aware foreign key field""" def field_to_activity(self, value): if not value: @@ -254,14 +254,14 @@ class OneToOneField(ActivitypubRelatedFieldMixin, models.OneToOneField): class ManyToManyField(ActivitypubFieldMixin, models.ManyToManyField): - """ activitypub-aware many to many field """ + """activitypub-aware many to many field""" def __init__(self, *args, link_only=False, **kwargs): self.link_only = link_only super().__init__(*args, **kwargs) def set_field_from_activity(self, instance, data): - """ helper function for assinging a value to the field """ + """helper function for assinging a value to the field""" value = getattr(data, self.get_activitypub_field()) formatted = self.field_from_activity(value) if formatted is None or formatted is MISSING: @@ -293,7 +293,7 @@ class ManyToManyField(ActivitypubFieldMixin, models.ManyToManyField): class TagField(ManyToManyField): - """ special case of many to many that uses Tags """ + """special case of many to many that uses Tags""" def __init__(self, *args, **kwargs): super().__init__(*args, **kwargs) @@ -333,7 +333,7 @@ class TagField(ManyToManyField): def image_serializer(value, alt): - """ helper for serializing images """ + """helper for serializing images""" if value and hasattr(value, "url"): url = value.url else: @@ -343,7 +343,7 @@ def image_serializer(value, alt): class ImageField(ActivitypubFieldMixin, models.ImageField): - """ activitypub-aware image field """ + """activitypub-aware image field""" def __init__(self, *args, alt_field=None, **kwargs): self.alt_field = alt_field @@ -351,7 +351,7 @@ class ImageField(ActivitypubFieldMixin, models.ImageField): # pylint: disable=arguments-differ def set_field_from_activity(self, instance, data, save=True): - """ helper function for assinging a value to the field """ + """helper function for assinging a value to the field""" value = getattr(data, self.get_activitypub_field()) formatted = self.field_from_activity(value) if formatted is None or formatted is MISSING: @@ -397,7 +397,7 @@ class ImageField(ActivitypubFieldMixin, models.ImageField): class DateTimeField(ActivitypubFieldMixin, models.DateTimeField): - """ activitypub-aware datetime field """ + """activitypub-aware datetime field""" def field_to_activity(self, value): if not value: @@ -416,7 +416,7 @@ class DateTimeField(ActivitypubFieldMixin, models.DateTimeField): class HtmlField(ActivitypubFieldMixin, models.TextField): - """ a text field for storing html """ + """a text field for storing html""" def field_from_activity(self, value): if not value or value == MISSING: @@ -427,30 +427,30 @@ class HtmlField(ActivitypubFieldMixin, models.TextField): class ArrayField(ActivitypubFieldMixin, DjangoArrayField): - """ activitypub-aware array field """ + """activitypub-aware array field""" def field_to_activity(self, value): return [str(i) for i in value] class CharField(ActivitypubFieldMixin, models.CharField): - """ activitypub-aware char field """ + """activitypub-aware char field""" class TextField(ActivitypubFieldMixin, models.TextField): - """ activitypub-aware text field """ + """activitypub-aware text field""" class BooleanField(ActivitypubFieldMixin, models.BooleanField): - """ activitypub-aware boolean field """ + """activitypub-aware boolean field""" class IntegerField(ActivitypubFieldMixin, models.IntegerField): - """ activitypub-aware boolean field """ + """activitypub-aware boolean field""" class DecimalField(ActivitypubFieldMixin, models.DecimalField): - """ activitypub-aware boolean field """ + """activitypub-aware boolean field""" def field_to_activity(self, value): if not value: diff --git a/bookwyrm/models/import_job.py b/bookwyrm/models/import_job.py index 026cf7cd..1b1152ab 100644 --- a/bookwyrm/models/import_job.py +++ b/bookwyrm/models/import_job.py @@ -20,7 +20,7 @@ GOODREADS_SHELVES = { def unquote_string(text): - """ resolve csv quote weirdness """ + """resolve csv quote weirdness""" match = re.match(r'="([^"]*)"', text) if match: return match.group(1) @@ -28,7 +28,7 @@ def unquote_string(text): def construct_search_term(title, author): - """ formulate a query for the data connector """ + """formulate a query for the data connector""" # Strip brackets (usually series title from search term) title = re.sub(r"\s*\([^)]*\)\s*", "", title) # Open library doesn't like including author initials in search term. @@ -38,7 +38,7 @@ def construct_search_term(title, author): class ImportJob(models.Model): - """ entry for a specific request for book data import """ + """entry for a specific request for book data import""" user = models.ForeignKey(User, on_delete=models.CASCADE) created_date = models.DateTimeField(default=timezone.now) @@ -51,7 +51,7 @@ class ImportJob(models.Model): retry = models.BooleanField(default=False) def save(self, *args, **kwargs): - """ save and notify """ + """save and notify""" super().save(*args, **kwargs) if self.complete: notification_model = apps.get_model( @@ -65,7 +65,7 @@ class ImportJob(models.Model): class ImportItem(models.Model): - """ a single line of a csv being imported """ + """a single line of a csv being imported""" job = models.ForeignKey(ImportJob, on_delete=models.CASCADE, related_name="items") index = models.IntegerField() @@ -74,11 +74,11 @@ class ImportItem(models.Model): fail_reason = models.TextField(null=True) def resolve(self): - """ try various ways to lookup a book """ + """try various ways to lookup a book""" self.book = self.get_book_from_isbn() or self.get_book_from_title_author() def get_book_from_isbn(self): - """ search by isbn """ + """search by isbn""" search_result = connector_manager.first_search_result( self.isbn, min_confidence=0.999 ) @@ -88,7 +88,7 @@ class ImportItem(models.Model): return None def get_book_from_title_author(self): - """ search by title and author """ + """search by title and author""" search_term = construct_search_term(self.title, self.author) search_result = connector_manager.first_search_result( search_term, min_confidence=0.999 @@ -100,60 +100,60 @@ class ImportItem(models.Model): @property def title(self): - """ get the book title """ + """get the book title""" return self.data["Title"] @property def author(self): - """ get the book title """ + """get the book title""" return self.data["Author"] @property def isbn(self): - """ pulls out the isbn13 field from the csv line data """ + """pulls out the isbn13 field from the csv line data""" return unquote_string(self.data["ISBN13"]) @property def shelf(self): - """ the goodreads shelf field """ + """the goodreads shelf field""" if self.data["Exclusive Shelf"]: return GOODREADS_SHELVES.get(self.data["Exclusive Shelf"]) return None @property def review(self): - """ a user-written review, to be imported with the book data """ + """a user-written review, to be imported with the book data""" return self.data["My Review"] @property def rating(self): - """ x/5 star rating for a book """ + """x/5 star rating for a book""" return int(self.data["My Rating"]) @property def date_added(self): - """ when the book was added to this dataset """ + """when the book was added to this dataset""" if self.data["Date Added"]: return timezone.make_aware(dateutil.parser.parse(self.data["Date Added"])) return None @property def date_started(self): - """ when the book was started """ + """when the book was started""" if "Date Started" in self.data and self.data["Date Started"]: return timezone.make_aware(dateutil.parser.parse(self.data["Date Started"])) return None @property def date_read(self): - """ the date a book was completed """ + """the date a book was completed""" if self.data["Date Read"]: return timezone.make_aware(dateutil.parser.parse(self.data["Date Read"])) return None @property def reads(self): - """ formats a read through dataset for the book in this line """ + """formats a read through dataset for the book in this line""" start_date = self.date_started # Goodreads special case (no 'date started' field) diff --git a/bookwyrm/models/list.py b/bookwyrm/models/list.py index 639f8402..2a5c3382 100644 --- a/bookwyrm/models/list.py +++ b/bookwyrm/models/list.py @@ -21,7 +21,7 @@ CurationType = models.TextChoices( class List(OrderedCollectionMixin, BookWyrmModel): - """ a list of books """ + """a list of books""" name = fields.CharField(max_length=100) user = fields.ForeignKey( @@ -41,22 +41,22 @@ class List(OrderedCollectionMixin, BookWyrmModel): activity_serializer = activitypub.BookList def get_remote_id(self): - """ don't want the user to be in there in this case """ + """don't want the user to be in there in this case""" return "https://%s/list/%d" % (DOMAIN, self.id) @property def collection_queryset(self): - """ list of books for this shelf, overrides OrderedCollectionMixin """ + """list of books for this shelf, overrides OrderedCollectionMixin""" return self.books.filter(listitem__approved=True).order_by("listitem") class Meta: - """ default sorting """ + """default sorting""" ordering = ("-updated_date",) class ListItem(CollectionItemMixin, BookWyrmModel): - """ ok """ + """ok""" book = fields.ForeignKey( "Edition", on_delete=models.PROTECT, activitypub_field="book" @@ -74,7 +74,7 @@ class ListItem(CollectionItemMixin, BookWyrmModel): collection_field = "book_list" def save(self, *args, **kwargs): - """ create a notification too """ + """create a notification too""" created = not bool(self.id) super().save(*args, **kwargs) # tick the updated date on the parent list diff --git a/bookwyrm/models/notification.py b/bookwyrm/models/notification.py index 233d635b..ff0b4e5a 100644 --- a/bookwyrm/models/notification.py +++ b/bookwyrm/models/notification.py @@ -10,7 +10,7 @@ NotificationType = models.TextChoices( class Notification(BookWyrmModel): - """ you've been tagged, liked, followed, etc """ + """you've been tagged, liked, followed, etc""" user = models.ForeignKey("User", on_delete=models.CASCADE) related_book = models.ForeignKey("Edition", on_delete=models.CASCADE, null=True) @@ -29,7 +29,7 @@ class Notification(BookWyrmModel): ) def save(self, *args, **kwargs): - """ save, but don't make dupes """ + """save, but don't make dupes""" # there's probably a better way to do this if self.__class__.objects.filter( user=self.user, @@ -45,7 +45,7 @@ class Notification(BookWyrmModel): super().save(*args, **kwargs) class Meta: - """ checks if notifcation is in enum list for valid types """ + """checks if notifcation is in enum list for valid types""" constraints = [ models.CheckConstraint( diff --git a/bookwyrm/models/readthrough.py b/bookwyrm/models/readthrough.py index 1a5fcb0d..664daa13 100644 --- a/bookwyrm/models/readthrough.py +++ b/bookwyrm/models/readthrough.py @@ -7,14 +7,14 @@ from .base_model import BookWyrmModel class ProgressMode(models.TextChoices): - """ types of prgress available """ + """types of prgress available""" PAGE = "PG", "page" PERCENT = "PCT", "percent" class ReadThrough(BookWyrmModel): - """ Store a read through a book in the database. """ + """Store a read through a book in the database.""" user = models.ForeignKey("User", on_delete=models.PROTECT) book = models.ForeignKey("Edition", on_delete=models.PROTECT) @@ -28,13 +28,13 @@ class ReadThrough(BookWyrmModel): finish_date = models.DateTimeField(blank=True, null=True) def save(self, *args, **kwargs): - """ update user active time """ + """update user active time""" self.user.last_active_date = timezone.now() self.user.save(broadcast=False) super().save(*args, **kwargs) def create_update(self): - """ add update to the readthrough """ + """add update to the readthrough""" if self.progress: return self.progressupdate_set.create( user=self.user, progress=self.progress, mode=self.progress_mode @@ -43,7 +43,7 @@ class ReadThrough(BookWyrmModel): class ProgressUpdate(BookWyrmModel): - """ Store progress through a book in the database. """ + """Store progress through a book in the database.""" user = models.ForeignKey("User", on_delete=models.PROTECT) readthrough = models.ForeignKey("ReadThrough", on_delete=models.CASCADE) @@ -53,7 +53,7 @@ class ProgressUpdate(BookWyrmModel): ) def save(self, *args, **kwargs): - """ update user active time """ + """update user active time""" self.user.last_active_date = timezone.now() self.user.save(broadcast=False) super().save(*args, **kwargs) diff --git a/bookwyrm/models/relationship.py b/bookwyrm/models/relationship.py index 3f849597..12f4c51a 100644 --- a/bookwyrm/models/relationship.py +++ b/bookwyrm/models/relationship.py @@ -11,7 +11,7 @@ from . import fields class UserRelationship(BookWyrmModel): - """ many-to-many through table for followers """ + """many-to-many through table for followers""" user_subject = fields.ForeignKey( "User", @@ -28,16 +28,16 @@ class UserRelationship(BookWyrmModel): @property def privacy(self): - """ all relationships are handled directly with the participants """ + """all relationships are handled directly with the participants""" return "direct" @property def recipients(self): - """ the remote user needs to recieve direct broadcasts """ + """the remote user needs to recieve direct broadcasts""" return [u for u in [self.user_subject, self.user_object] if not u.local] class Meta: - """ relationships should be unique """ + """relationships should be unique""" abstract = True constraints = [ @@ -51,22 +51,22 @@ class UserRelationship(BookWyrmModel): ] def get_remote_id(self): - """ use shelf identifier in remote_id """ + """use shelf identifier in remote_id""" base_path = self.user_subject.remote_id return "%s#follows/%d" % (base_path, self.id) class UserFollows(ActivityMixin, UserRelationship): - """ Following a user """ + """Following a user""" status = "follows" def to_activity(self): # pylint: disable=arguments-differ - """ overrides default to manually set serializer """ + """overrides default to manually set serializer""" return activitypub.Follow(**generate_activity(self)) def save(self, *args, **kwargs): - """ really really don't let a user follow someone who blocked them """ + """really really don't let a user follow someone who blocked them""" # blocking in either direction is a no-go if UserBlocks.objects.filter( Q( @@ -85,7 +85,7 @@ class UserFollows(ActivityMixin, UserRelationship): @classmethod def from_request(cls, follow_request): - """ converts a follow request into a follow relationship """ + """converts a follow request into a follow relationship""" return cls.objects.create( user_subject=follow_request.user_subject, user_object=follow_request.user_object, @@ -94,13 +94,13 @@ class UserFollows(ActivityMixin, UserRelationship): class UserFollowRequest(ActivitypubMixin, UserRelationship): - """ following a user requires manual or automatic confirmation """ + """following a user requires manual or automatic confirmation""" status = "follow_request" activity_serializer = activitypub.Follow def save(self, *args, broadcast=True, **kwargs): - """ make sure the follow or block relationship doesn't already exist """ + """make sure the follow or block relationship doesn't already exist""" # if there's a request for a follow that already exists, accept it # without changing the local database state if UserFollows.objects.filter( @@ -141,13 +141,13 @@ class UserFollowRequest(ActivitypubMixin, UserRelationship): ) def get_accept_reject_id(self, status): - """ get id for sending an accept or reject of a local user """ + """get id for sending an accept or reject of a local user""" base_path = self.user_object.remote_id return "%s#%s/%d" % (base_path, status, self.id or 0) def accept(self, broadcast_only=False): - """ turn this request into the real deal""" + """turn this request into the real deal""" user = self.user_object if not self.user_subject.local: activity = activitypub.Accept( @@ -164,7 +164,7 @@ class UserFollowRequest(ActivitypubMixin, UserRelationship): self.delete() def reject(self): - """ generate a Reject for this follow request """ + """generate a Reject for this follow request""" if self.user_object.local: activity = activitypub.Reject( id=self.get_accept_reject_id(status="rejects"), @@ -177,13 +177,13 @@ class UserFollowRequest(ActivitypubMixin, UserRelationship): class UserBlocks(ActivityMixin, UserRelationship): - """ prevent another user from following you and seeing your posts """ + """prevent another user from following you and seeing your posts""" status = "blocks" activity_serializer = activitypub.Block def save(self, *args, **kwargs): - """ remove follow or follow request rels after a block is created """ + """remove follow or follow request rels after a block is created""" super().save(*args, **kwargs) UserFollows.objects.filter( diff --git a/bookwyrm/models/report.py b/bookwyrm/models/report.py index f9e8905b..7ff4c909 100644 --- a/bookwyrm/models/report.py +++ b/bookwyrm/models/report.py @@ -6,7 +6,7 @@ from .base_model import BookWyrmModel class Report(BookWyrmModel): - """ reported status or user """ + """reported status or user""" reporter = models.ForeignKey( "User", related_name="reporter", on_delete=models.PROTECT @@ -17,7 +17,7 @@ class Report(BookWyrmModel): resolved = models.BooleanField(default=False) def save(self, *args, **kwargs): - """ notify admins when a report is created """ + """notify admins when a report is created""" super().save(*args, **kwargs) user_model = apps.get_model("bookwyrm.User", require_ready=True) # moderators and superusers should be notified @@ -34,7 +34,7 @@ class Report(BookWyrmModel): ) class Meta: - """ don't let users report themselves """ + """don't let users report themselves""" constraints = [ models.CheckConstraint(check=~Q(reporter=F("user")), name="self_report") @@ -43,13 +43,13 @@ class Report(BookWyrmModel): class ReportComment(BookWyrmModel): - """ updates on a report """ + """updates on a report""" user = models.ForeignKey("User", on_delete=models.PROTECT) note = models.TextField() report = models.ForeignKey(Report, on_delete=models.PROTECT) class Meta: - """ sort comments """ + """sort comments""" ordering = ("-created_date",) diff --git a/bookwyrm/models/shelf.py b/bookwyrm/models/shelf.py index d37668dd..4110ae8d 100644 --- a/bookwyrm/models/shelf.py +++ b/bookwyrm/models/shelf.py @@ -9,7 +9,7 @@ from . import fields class Shelf(OrderedCollectionMixin, BookWyrmModel): - """ a list of books owned by a user """ + """a list of books owned by a user""" TO_READ = "to-read" READING = "reading" @@ -34,36 +34,36 @@ class Shelf(OrderedCollectionMixin, BookWyrmModel): activity_serializer = activitypub.Shelf def save(self, *args, **kwargs): - """ set the identifier """ + """set the identifier""" super().save(*args, **kwargs) if not self.identifier: self.identifier = self.get_identifier() super().save(*args, **kwargs, broadcast=False) def get_identifier(self): - """ custom-shelf-123 for the url """ + """custom-shelf-123 for the url""" slug = re.sub(r"[^\w]", "", self.name).lower() return "{:s}-{:d}".format(slug, self.id) @property def collection_queryset(self): - """ list of books for this shelf, overrides OrderedCollectionMixin """ + """list of books for this shelf, overrides OrderedCollectionMixin""" return self.books.order_by("shelfbook") def get_remote_id(self): - """ shelf identifier instead of id """ + """shelf identifier instead of id""" base_path = self.user.remote_id identifier = self.identifier or self.get_identifier() return "%s/books/%s" % (base_path, identifier) class Meta: - """ user/shelf unqiueness """ + """user/shelf unqiueness""" unique_together = ("user", "identifier") class ShelfBook(CollectionItemMixin, BookWyrmModel): - """ many to many join table for books and shelves """ + """many to many join table for books and shelves""" book = fields.ForeignKey( "Edition", on_delete=models.PROTECT, activitypub_field="book" diff --git a/bookwyrm/models/site.py b/bookwyrm/models/site.py index 1eb31869..193cffb7 100644 --- a/bookwyrm/models/site.py +++ b/bookwyrm/models/site.py @@ -12,7 +12,7 @@ from .user import User class SiteSettings(models.Model): - """ customized settings for this instance """ + """customized settings for this instance""" name = models.CharField(default="BookWyrm", max_length=100) instance_tagline = models.CharField( @@ -35,7 +35,7 @@ class SiteSettings(models.Model): @classmethod def get(cls): - """ gets the site settings db entry or defaults """ + """gets the site settings db entry or defaults""" try: return cls.objects.get(id=1) except cls.DoesNotExist: @@ -45,12 +45,12 @@ class SiteSettings(models.Model): def new_access_code(): - """ the identifier for a user invite """ + """the identifier for a user invite""" return base64.b32encode(Random.get_random_bytes(5)).decode("ascii") class SiteInvite(models.Model): - """ gives someone access to create an account on the instance """ + """gives someone access to create an account on the instance""" created_date = models.DateTimeField(auto_now_add=True) code = models.CharField(max_length=32, default=new_access_code) @@ -61,19 +61,19 @@ class SiteInvite(models.Model): invitees = models.ManyToManyField(User, related_name="invitees") def valid(self): - """ make sure it hasn't expired or been used """ + """make sure it hasn't expired or been used""" return (self.expiry is None or self.expiry > timezone.now()) and ( self.use_limit is None or self.times_used < self.use_limit ) @property def link(self): - """ formats the invite link """ + """formats the invite link""" return "https://{}/invite/{}".format(DOMAIN, self.code) class InviteRequest(BookWyrmModel): - """ prospective users can request an invite """ + """prospective users can request an invite""" email = models.EmailField(max_length=255, unique=True) invite = models.ForeignKey( @@ -83,30 +83,30 @@ class InviteRequest(BookWyrmModel): ignored = models.BooleanField(default=False) def save(self, *args, **kwargs): - """ don't create a request for a registered email """ + """don't create a request for a registered email""" if not self.id and User.objects.filter(email=self.email).exists(): raise IntegrityError() super().save(*args, **kwargs) def get_passowrd_reset_expiry(): - """ give people a limited time to use the link """ + """give people a limited time to use the link""" now = timezone.now() return now + datetime.timedelta(days=1) class PasswordReset(models.Model): - """ gives someone access to create an account on the instance """ + """gives someone access to create an account on the instance""" code = models.CharField(max_length=32, default=new_access_code) expiry = models.DateTimeField(default=get_passowrd_reset_expiry) user = models.OneToOneField(User, on_delete=models.CASCADE) def valid(self): - """ make sure it hasn't expired or been used """ + """make sure it hasn't expired or been used""" return self.expiry > timezone.now() @property def link(self): - """ formats the invite link """ + """formats the invite link""" return "https://{}/password-reset/{}".format(DOMAIN, self.code) diff --git a/bookwyrm/models/status.py b/bookwyrm/models/status.py index 0dee0b75..bd21ec56 100644 --- a/bookwyrm/models/status.py +++ b/bookwyrm/models/status.py @@ -19,7 +19,7 @@ from . import fields class Status(OrderedCollectionPageMixin, BookWyrmModel): - """ any post, like a reply to a review, etc """ + """any post, like a reply to a review, etc""" user = fields.ForeignKey( "User", on_delete=models.PROTECT, activitypub_field="attributedTo" @@ -59,12 +59,12 @@ class Status(OrderedCollectionPageMixin, BookWyrmModel): deserialize_reverse_fields = [("attachments", "attachment")] class Meta: - """ default sorting """ + """default sorting""" ordering = ("-published_date",) def save(self, *args, **kwargs): - """ save and notify """ + """save and notify""" super().save(*args, **kwargs) notification_model = apps.get_model("bookwyrm.Notification", require_ready=True) @@ -98,7 +98,7 @@ class Status(OrderedCollectionPageMixin, BookWyrmModel): ) def delete(self, *args, **kwargs): # pylint: disable=unused-argument - """ "delete" a status """ + """ "delete" a status""" if hasattr(self, "boosted_status"): # okay but if it's a boost really delete it super().delete(*args, **kwargs) @@ -109,7 +109,7 @@ class Status(OrderedCollectionPageMixin, BookWyrmModel): @property def recipients(self): - """ tagged users who definitely need to get this status in broadcast """ + """tagged users who definitely need to get this status in broadcast""" mentions = [u for u in self.mention_users.all() if not u.local] if ( hasattr(self, "reply_parent") @@ -121,7 +121,7 @@ class Status(OrderedCollectionPageMixin, BookWyrmModel): @classmethod def ignore_activity(cls, activity): # pylint: disable=too-many-return-statements - """ keep notes if they are replies to existing statuses """ + """keep notes if they are replies to existing statuses""" if activity.type == "Announce": try: boosted = activitypub.resolve_remote_id( @@ -163,16 +163,16 @@ class Status(OrderedCollectionPageMixin, BookWyrmModel): @property def status_type(self): - """ expose the type of status for the ui using activity type """ + """expose the type of status for the ui using activity type""" return self.activity_serializer.__name__ @property def boostable(self): - """ you can't boost dms """ + """you can't boost dms""" return self.privacy in ["unlisted", "public"] def to_replies(self, **kwargs): - """ helper function for loading AP serialized replies to a status """ + """helper function for loading AP serialized replies to a status""" return self.to_ordered_collection( self.replies(self), remote_id="%s/replies" % self.remote_id, @@ -181,7 +181,7 @@ class Status(OrderedCollectionPageMixin, BookWyrmModel): ).serialize() def to_activity_dataclass(self, pure=False): # pylint: disable=arguments-differ - """ return tombstone if the status is deleted """ + """return tombstone if the status is deleted""" if self.deleted: return activitypub.Tombstone( id=self.remote_id, @@ -210,16 +210,16 @@ class Status(OrderedCollectionPageMixin, BookWyrmModel): return activity def to_activity(self, pure=False): # pylint: disable=arguments-differ - """ json serialized activitypub class """ + """json serialized activitypub class""" return self.to_activity_dataclass(pure=pure).serialize() class GeneratedNote(Status): - """ these are app-generated messages about user activity """ + """these are app-generated messages about user activity""" @property def pure_content(self): - """ indicate the book in question for mastodon (or w/e) users """ + """indicate the book in question for mastodon (or w/e) users""" message = self.content books = ", ".join( '"%s"' % (book.remote_id, book.title) @@ -232,7 +232,7 @@ class GeneratedNote(Status): class Comment(Status): - """ like a review but without a rating and transient """ + """like a review but without a rating and transient""" book = fields.ForeignKey( "Edition", on_delete=models.PROTECT, activitypub_field="inReplyToBook" @@ -253,7 +253,7 @@ class Comment(Status): @property def pure_content(self): - """ indicate the book in question for mastodon (or w/e) users """ + """indicate the book in question for mastodon (or w/e) users""" return '%s

(comment on "%s")

' % ( self.content, self.book.remote_id, @@ -265,7 +265,7 @@ class Comment(Status): class Quotation(Status): - """ like a review but without a rating and transient """ + """like a review but without a rating and transient""" quote = fields.HtmlField() book = fields.ForeignKey( @@ -274,7 +274,7 @@ class Quotation(Status): @property def pure_content(self): - """ indicate the book in question for mastodon (or w/e) users """ + """indicate the book in question for mastodon (or w/e) users""" quote = re.sub(r"^

", '

"', self.quote) quote = re.sub(r"

$", '"

', quote) return '%s

-- "%s"

%s' % ( @@ -289,7 +289,7 @@ class Quotation(Status): class Review(Status): - """ a book review """ + """a book review""" name = fields.CharField(max_length=255, null=True) book = fields.ForeignKey( @@ -306,7 +306,7 @@ class Review(Status): @property def pure_name(self): - """ clarify review names for mastodon serialization """ + """clarify review names for mastodon serialization""" template = get_template("snippets/generated_status/review_pure_name.html") return template.render( {"book": self.book, "rating": self.rating, "name": self.name} @@ -314,7 +314,7 @@ class Review(Status): @property def pure_content(self): - """ indicate the book in question for mastodon (or w/e) users """ + """indicate the book in question for mastodon (or w/e) users""" return self.content activity_serializer = activitypub.Review @@ -322,7 +322,7 @@ class Review(Status): class ReviewRating(Review): - """ a subtype of review that only contains a rating """ + """a subtype of review that only contains a rating""" def save(self, *args, **kwargs): if not self.rating: @@ -339,7 +339,7 @@ class ReviewRating(Review): class Boost(ActivityMixin, Status): - """ boost'ing a post """ + """boost'ing a post""" boosted_status = fields.ForeignKey( "Status", @@ -350,7 +350,7 @@ class Boost(ActivityMixin, Status): activity_serializer = activitypub.Announce def save(self, *args, **kwargs): - """ save and notify """ + """save and notify""" # This constraint can't work as it would cross tables. # class Meta: # unique_together = ('user', 'boosted_status') @@ -374,7 +374,7 @@ class Boost(ActivityMixin, Status): ) def delete(self, *args, **kwargs): - """ delete and un-notify """ + """delete and un-notify""" notification_model = apps.get_model("bookwyrm.Notification", require_ready=True) notification_model.objects.filter( user=self.boosted_status.user, @@ -385,7 +385,7 @@ class Boost(ActivityMixin, Status): super().delete(*args, **kwargs) def __init__(self, *args, **kwargs): - """ the user field is "actor" here instead of "attributedTo" """ + """the user field is "actor" here instead of "attributedTo" """ super().__init__(*args, **kwargs) reserve_fields = ["user", "boosted_status", "published_date", "privacy"] diff --git a/bookwyrm/models/user.py b/bookwyrm/models/user.py index 0f98c82d..3efbd6ac 100644 --- a/bookwyrm/models/user.py +++ b/bookwyrm/models/user.py @@ -35,7 +35,7 @@ DeactivationReason = models.TextChoices( class User(OrderedCollectionPageMixin, AbstractUser): - """ a user who wants to read books """ + """a user who wants to read books""" username = fields.UsernameField() email = models.EmailField(unique=True, null=True) @@ -130,38 +130,38 @@ class User(OrderedCollectionPageMixin, AbstractUser): @property def following_link(self): - """ just how to find out the following info """ + """just how to find out the following info""" return "{:s}/following".format(self.remote_id) @property def alt_text(self): - """ alt text with username """ + """alt text with username""" return "avatar for %s" % (self.localname or self.username) @property def display_name(self): - """ show the cleanest version of the user's name possible """ + """show the cleanest version of the user's name possible""" if self.name and self.name != "": return self.name return self.localname or self.username @property def deleted(self): - """ for consistent naming """ + """for consistent naming""" return not self.is_active activity_serializer = activitypub.Person @classmethod def viewer_aware_objects(cls, viewer): - """ the user queryset filtered for the context of the logged in user """ + """the user queryset filtered for the context of the logged in user""" queryset = cls.objects.filter(is_active=True) if viewer and viewer.is_authenticated: queryset = queryset.exclude(blocks=viewer) return queryset def to_outbox(self, filter_type=None, **kwargs): - """ an ordered collection of statuses """ + """an ordered collection of statuses""" if filter_type: filter_class = apps.get_model( "bookwyrm.%s" % filter_type, require_ready=True @@ -188,7 +188,7 @@ class User(OrderedCollectionPageMixin, AbstractUser): ).serialize() def to_following_activity(self, **kwargs): - """ activitypub following list """ + """activitypub following list""" remote_id = "%s/following" % self.remote_id return self.to_ordered_collection( self.following.order_by("-updated_date").all(), @@ -198,7 +198,7 @@ class User(OrderedCollectionPageMixin, AbstractUser): ) def to_followers_activity(self, **kwargs): - """ activitypub followers list """ + """activitypub followers list""" remote_id = "%s/followers" % self.remote_id return self.to_ordered_collection( self.followers.order_by("-updated_date").all(), @@ -227,7 +227,7 @@ class User(OrderedCollectionPageMixin, AbstractUser): return activity_object def save(self, *args, **kwargs): - """ populate fields for new local users """ + """populate fields for new local users""" created = not bool(self.id) if not self.local and not re.match(regex.full_username, self.username): # generate a username that uses the domain (webfinger format) @@ -292,19 +292,19 @@ class User(OrderedCollectionPageMixin, AbstractUser): ).save(broadcast=False) def delete(self, *args, **kwargs): - """ deactivate rather than delete a user """ + """deactivate rather than delete a user""" self.is_active = False # skip the logic in this class's save() super().save(*args, **kwargs) @property def local_path(self): - """ this model doesn't inherit bookwyrm model, so here we are """ + """this model doesn't inherit bookwyrm model, so here we are""" return "/user/%s" % (self.localname or self.username) class KeyPair(ActivitypubMixin, BookWyrmModel): - """ public and private keys for a user """ + """public and private keys for a user""" private_key = models.TextField(blank=True, null=True) public_key = fields.TextField( @@ -319,7 +319,7 @@ class KeyPair(ActivitypubMixin, BookWyrmModel): return "%s/#main-key" % self.owner.remote_id def save(self, *args, **kwargs): - """ create a key pair """ + """create a key pair""" # no broadcasting happening here if "broadcast" in kwargs: del kwargs["broadcast"] @@ -337,7 +337,7 @@ class KeyPair(ActivitypubMixin, BookWyrmModel): class AnnualGoal(BookWyrmModel): - """ set a goal for how many books you read in a year """ + """set a goal for how many books you read in a year""" user = models.ForeignKey("User", on_delete=models.PROTECT) goal = models.IntegerField(validators=[MinValueValidator(1)]) @@ -347,17 +347,17 @@ class AnnualGoal(BookWyrmModel): ) class Meta: - """ unqiueness constraint """ + """unqiueness constraint""" unique_together = ("user", "year") def get_remote_id(self): - """ put the year in the path """ + """put the year in the path""" return "%s/goal/%d" % (self.user.remote_id, self.year) @property def books(self): - """ the books you've read this year """ + """the books you've read this year""" return ( self.user.readthrough_set.filter(finish_date__year__gte=self.year) .order_by("-finish_date") @@ -366,7 +366,7 @@ class AnnualGoal(BookWyrmModel): @property def ratings(self): - """ ratings for books read this year """ + """ratings for books read this year""" book_ids = [r.book.id for r in self.books] reviews = Review.objects.filter( user=self.user, @@ -376,12 +376,12 @@ class AnnualGoal(BookWyrmModel): @property def progress_percent(self): - """ how close to your goal, in percent form """ + """how close to your goal, in percent form""" return int(float(self.book_count / self.goal) * 100) @property def book_count(self): - """ how many books you've read this year """ + """how many books you've read this year""" return self.user.readthrough_set.filter( finish_date__year__gte=self.year ).count() @@ -389,7 +389,7 @@ class AnnualGoal(BookWyrmModel): @app.task def set_remote_server(user_id): - """ figure out the user's remote server in the background """ + """figure out the user's remote server in the background""" user = User.objects.get(id=user_id) actor_parts = urlparse(user.remote_id) user.federated_server = get_or_create_remote_server(actor_parts.netloc) @@ -399,7 +399,7 @@ def set_remote_server(user_id): def get_or_create_remote_server(domain): - """ get info on a remote server """ + """get info on a remote server""" try: return FederatedServer.objects.get(server_name=domain) except FederatedServer.DoesNotExist: @@ -428,7 +428,7 @@ def get_or_create_remote_server(domain): @app.task def get_remote_reviews(outbox): - """ ingest reviews by a new remote bookwyrm user """ + """ingest reviews by a new remote bookwyrm user""" outbox_page = outbox + "?page=true&type=Review" data = get_data(outbox_page) diff --git a/bookwyrm/redis_store.py b/bookwyrm/redis_store.py index 4236d6df..259bc4fd 100644 --- a/bookwyrm/redis_store.py +++ b/bookwyrm/redis_store.py @@ -10,16 +10,16 @@ r = redis.Redis( class RedisStore(ABC): - """ sets of ranked, related objects, like statuses for a user's feed """ + """sets of ranked, related objects, like statuses for a user's feed""" max_length = settings.MAX_STREAM_LENGTH def get_value(self, obj): - """ the object and rank """ + """the object and rank""" return {obj.id: self.get_rank(obj)} def add_object_to_related_stores(self, obj, execute=True): - """ add an object to all suitable stores """ + """add an object to all suitable stores""" value = self.get_value(obj) # we want to do this as a bulk operation, hence "pipeline" pipeline = r.pipeline() @@ -34,14 +34,14 @@ class RedisStore(ABC): return pipeline.execute() def remove_object_from_related_stores(self, obj): - """ remove an object from all stores """ + """remove an object from all stores""" pipeline = r.pipeline() for store in self.get_stores_for_object(obj): pipeline.zrem(store, -1, obj.id) pipeline.execute() def bulk_add_objects_to_store(self, objs, store): - """ add a list of objects to a given store """ + """add a list of objects to a given store""" pipeline = r.pipeline() for obj in objs[: self.max_length]: pipeline.zadd(store, self.get_value(obj)) @@ -50,18 +50,18 @@ class RedisStore(ABC): pipeline.execute() def bulk_remove_objects_from_store(self, objs, store): - """ remoev a list of objects from a given store """ + """remoev a list of objects from a given store""" pipeline = r.pipeline() for obj in objs[: self.max_length]: pipeline.zrem(store, -1, obj.id) pipeline.execute() def get_store(self, store): # pylint: disable=no-self-use - """ load the values in a store """ + """load the values in a store""" return r.zrevrange(store, 0, -1) def populate_store(self, store): - """ go from zero to a store """ + """go from zero to a store""" pipeline = r.pipeline() queryset = self.get_objects_for_store(store) @@ -75,12 +75,12 @@ class RedisStore(ABC): @abstractmethod def get_objects_for_store(self, store): - """ a queryset of what should go in a store, used for populating it """ + """a queryset of what should go in a store, used for populating it""" @abstractmethod def get_stores_for_object(self, obj): - """ the stores that an object belongs in """ + """the stores that an object belongs in""" @abstractmethod def get_rank(self, obj): - """ how to rank an object """ + """how to rank an object""" diff --git a/bookwyrm/sanitize_html.py b/bookwyrm/sanitize_html.py index 2a630f83..0be64c58 100644 --- a/bookwyrm/sanitize_html.py +++ b/bookwyrm/sanitize_html.py @@ -3,7 +3,7 @@ from html.parser import HTMLParser class InputHtmlParser(HTMLParser): # pylint: disable=abstract-method - """ Removes any html that isn't allowed_tagsed from a block """ + """Removes any html that isn't allowed_tagsed from a block""" def __init__(self): HTMLParser.__init__(self) @@ -28,7 +28,7 @@ class InputHtmlParser(HTMLParser): # pylint: disable=abstract-method self.allow_html = True def handle_starttag(self, tag, attrs): - """ check if the tag is valid """ + """check if the tag is valid""" if self.allow_html and tag in self.allowed_tags: self.output.append(("tag", self.get_starttag_text())) self.tag_stack.append(tag) @@ -36,7 +36,7 @@ class InputHtmlParser(HTMLParser): # pylint: disable=abstract-method self.output.append(("data", "")) def handle_endtag(self, tag): - """ keep the close tag """ + """keep the close tag""" if not self.allow_html or tag not in self.allowed_tags: self.output.append(("data", "")) return @@ -51,11 +51,11 @@ class InputHtmlParser(HTMLParser): # pylint: disable=abstract-method self.output.append(("tag", "" % tag)) def handle_data(self, data): - """ extract the answer, if we're in an answer tag """ + """extract the answer, if we're in an answer tag""" self.output.append(("data", data)) def get_output(self): - """ convert the output from a list of tuples to a string """ + """convert the output from a list of tuples to a string""" if self.tag_stack: self.allow_html = False if not self.allow_html: diff --git a/bookwyrm/signatures.py b/bookwyrm/signatures.py index 80cbfdc7..5488cf9b 100644 --- a/bookwyrm/signatures.py +++ b/bookwyrm/signatures.py @@ -13,7 +13,7 @@ MAX_SIGNATURE_AGE = 300 def create_key_pair(): - """ a new public/private key pair, used for creating new users """ + """a new public/private key pair, used for creating new users""" random_generator = Random.new().read key = RSA.generate(1024, random_generator) private_key = key.export_key().decode("utf8") @@ -23,7 +23,7 @@ def create_key_pair(): def make_signature(sender, destination, date, digest): - """ uses a private key to sign an outgoing message """ + """uses a private key to sign an outgoing message""" inbox_parts = urlparse(destination) signature_headers = [ "(request-target): post %s" % inbox_parts.path, @@ -44,14 +44,14 @@ def make_signature(sender, destination, date, digest): def make_digest(data): - """ creates a message digest for signing """ + """creates a message digest for signing""" return "SHA-256=" + b64encode(hashlib.sha256(data.encode("utf-8")).digest()).decode( "utf-8" ) def verify_digest(request): - """ checks if a digest is syntactically valid and matches the message """ + """checks if a digest is syntactically valid and matches the message""" algorithm, digest = request.headers["digest"].split("=", 1) if algorithm == "SHA-256": hash_function = hashlib.sha256 @@ -66,7 +66,7 @@ def verify_digest(request): class Signature: - """ read and validate incoming signatures """ + """read and validate incoming signatures""" def __init__(self, key_id, headers, signature): self.key_id = key_id @@ -75,7 +75,7 @@ class Signature: @classmethod def parse(cls, request): - """ extract and parse a signature from an http request """ + """extract and parse a signature from an http request""" signature_dict = {} for pair in request.headers["Signature"].split(","): k, v = pair.split("=", 1) @@ -92,7 +92,7 @@ class Signature: return cls(key_id, headers, signature) def verify(self, public_key, request): - """ verify rsa signature """ + """verify rsa signature""" if http_date_age(request.headers["date"]) > MAX_SIGNATURE_AGE: raise ValueError("Request too old: %s" % (request.headers["date"],)) public_key = RSA.import_key(public_key) @@ -118,7 +118,7 @@ class Signature: def http_date_age(datestr): - """ age of a signature in seconds """ + """age of a signature in seconds""" parsed = datetime.datetime.strptime(datestr, "%a, %d %b %Y %H:%M:%S GMT") delta = datetime.datetime.utcnow() - parsed return delta.total_seconds() diff --git a/bookwyrm/status.py b/bookwyrm/status.py index 793bd742..09fbdc06 100644 --- a/bookwyrm/status.py +++ b/bookwyrm/status.py @@ -6,7 +6,7 @@ from bookwyrm.sanitize_html import InputHtmlParser def create_generated_note(user, content, mention_books=None, privacy="public"): - """ a note created by the app about user activity """ + """a note created by the app about user activity""" # sanitize input html parser = InputHtmlParser() parser.feed(content) diff --git a/bookwyrm/templatetags/bookwyrm_tags.py b/bookwyrm/templatetags/bookwyrm_tags.py index bd14a410..2ed0cbc2 100644 --- a/bookwyrm/templatetags/bookwyrm_tags.py +++ b/bookwyrm/templatetags/bookwyrm_tags.py @@ -13,13 +13,13 @@ register = template.Library() @register.filter(name="dict_key") def dict_key(d, k): - """ Returns the given key from a dictionary. """ + """Returns the given key from a dictionary.""" return d.get(k) or 0 @register.filter(name="rating") def get_rating(book, user): - """ get the overall rating of a book """ + """get the overall rating of a book""" queryset = views.helpers.privacy_filter( user, models.Review.objects.filter(book=book) ) @@ -28,7 +28,7 @@ def get_rating(book, user): @register.filter(name="user_rating") def get_user_rating(book, user): - """ get a user's rating of a book """ + """get a user's rating of a book""" rating = ( models.Review.objects.filter( user=user, @@ -45,19 +45,19 @@ def get_user_rating(book, user): @register.filter(name="username") def get_user_identifier(user): - """ use localname for local users, username for remote """ + """use localname for local users, username for remote""" return user.localname if user.localname else user.username @register.filter(name="notification_count") def get_notification_count(user): - """ how many UNREAD notifications are there """ + """how many UNREAD notifications are there""" return user.notification_set.filter(read=False).count() @register.filter(name="replies") def get_replies(status): - """ get all direct replies to a status """ + """get all direct replies to a status""" # TODO: this limit could cause problems return models.Status.objects.filter( reply_parent=status, @@ -67,7 +67,7 @@ def get_replies(status): @register.filter(name="parent") def get_parent(status): - """ get the reply parent for a status """ + """get the reply parent for a status""" return ( models.Status.objects.filter(id=status.reply_parent_id) .select_subclasses() @@ -77,7 +77,7 @@ def get_parent(status): @register.filter(name="liked") def get_user_liked(user, status): - """ did the given user fav a status? """ + """did the given user fav a status?""" try: models.Favorite.objects.get(user=user, status=status) return True @@ -87,13 +87,13 @@ def get_user_liked(user, status): @register.filter(name="boosted") def get_user_boosted(user, status): - """ did the given user fav a status? """ + """did the given user fav a status?""" return user.id in status.boosters.all().values_list("user", flat=True) @register.filter(name="follow_request_exists") def follow_request_exists(user, requester): - """ see if there is a pending follow request for a user """ + """see if there is a pending follow request for a user""" try: models.UserFollowRequest.objects.filter( user_subject=requester, @@ -106,7 +106,7 @@ def follow_request_exists(user, requester): @register.filter(name="boosted_status") def get_boosted(boost): - """ load a boosted status. have to do this or it wont get foregin keys """ + """load a boosted status. have to do this or it wont get foregin keys""" return ( models.Status.objects.select_subclasses() .filter(id=boost.boosted_status.id) @@ -116,19 +116,19 @@ def get_boosted(boost): @register.filter(name="book_description") def get_book_description(book): - """ use the work's text if the book doesn't have it """ + """use the work's text if the book doesn't have it""" return book.description or book.parent_work.description @register.filter(name="uuid") def get_uuid(identifier): - """ for avoiding clashing ids when there are many forms """ + """for avoiding clashing ids when there are many forms""" return "%s%s" % (identifier, uuid4()) @register.filter(name="to_markdown") def get_markdown(content): - """ convert markdown to html """ + """convert markdown to html""" if content: return to_markdown(content) return None @@ -136,7 +136,7 @@ def get_markdown(content): @register.filter(name="mentions") def get_mentions(status, user): - """ people to @ in a reply: the parent and all mentions """ + """people to @ in a reply: the parent and all mentions""" mentions = set([status.user] + list(status.mention_users.all())) return ( " ".join("@" + get_user_identifier(m) for m in mentions if not m == user) + " " @@ -145,7 +145,7 @@ def get_mentions(status, user): @register.filter(name="status_preview_name") def get_status_preview_name(obj): - """ text snippet with book context for a status """ + """text snippet with book context for a status""" name = obj.__class__.__name__.lower() if name == "review": return "%s of %s" % (name, obj.book.title) @@ -158,7 +158,7 @@ def get_status_preview_name(obj): @register.filter(name="next_shelf") def get_next_shelf(current_shelf): - """ shelf you'd use to update reading progress """ + """shelf you'd use to update reading progress""" if current_shelf == "to-read": return "reading" if current_shelf == "reading": @@ -170,7 +170,7 @@ def get_next_shelf(current_shelf): @register.filter(name="title") def get_title(book): - """ display the subtitle if the title is short """ + """display the subtitle if the title is short""" if not book: return "" title = book.title @@ -181,7 +181,7 @@ def get_title(book): @register.simple_tag(takes_context=False) def related_status(notification): - """ for notifications """ + """for notifications""" if not notification.related_status: return None if hasattr(notification.related_status, "quotation"): @@ -195,7 +195,7 @@ def related_status(notification): @register.simple_tag(takes_context=True) def active_shelf(context, book): - """ check what shelf a user has a book on, if any """ + """check what shelf a user has a book on, if any""" shelf = models.ShelfBook.objects.filter( shelf__user=context["request"].user, book__in=book.parent_work.editions.all() ).first() @@ -204,7 +204,7 @@ def active_shelf(context, book): @register.simple_tag(takes_context=False) def latest_read_through(book, user): - """ the most recent read activity """ + """the most recent read activity""" return ( models.ReadThrough.objects.filter(user=user, book=book) .order_by("-start_date") @@ -214,7 +214,7 @@ def latest_read_through(book, user): @register.simple_tag(takes_context=False) def active_read_through(book, user): - """ the most recent read activity """ + """the most recent read activity""" return ( models.ReadThrough.objects.filter( user=user, book=book, finish_date__isnull=True @@ -226,12 +226,12 @@ def active_read_through(book, user): @register.simple_tag(takes_context=False) def comparison_bool(str1, str2): - """ idk why I need to write a tag for this, it reutrns a bool """ + """idk why I need to write a tag for this, it reutrns a bool""" return str1 == str2 @register.simple_tag(takes_context=False) def get_lang(): - """ get current language, strip to the first two letters """ + """get current language, strip to the first two letters""" language = utils.translation.get_language() return language[0 : language.find("-")] diff --git a/bookwyrm/tests/activitypub/test_base_activity.py b/bookwyrm/tests/activitypub/test_base_activity.py index 8ec0b703..77844a22 100644 --- a/bookwyrm/tests/activitypub/test_base_activity.py +++ b/bookwyrm/tests/activitypub/test_base_activity.py @@ -21,10 +21,10 @@ from bookwyrm import models @patch("bookwyrm.activitystreams.ActivityStream.add_status") class BaseActivity(TestCase): - """ the super class for model-linked activitypub dataclasses """ + """the super class for model-linked activitypub dataclasses""" def setUp(self): - """ we're probably going to re-use this so why copy/paste """ + """we're probably going to re-use this so why copy/paste""" self.user = models.User.objects.create_user( "mouse", "mouse@mouse.mouse", "mouseword", local=True, localname="mouse" ) @@ -45,28 +45,28 @@ class BaseActivity(TestCase): self.image_data = output.getvalue() def test_init(self, _): - """ simple successfuly init """ + """simple successfuly init""" instance = ActivityObject(id="a", type="b") self.assertTrue(hasattr(instance, "id")) self.assertTrue(hasattr(instance, "type")) def test_init_missing(self, _): - """ init with missing required params """ + """init with missing required params""" with self.assertRaises(ActivitySerializerError): ActivityObject() def test_init_extra_fields(self, _): - """ init ignoring additional fields """ + """init ignoring additional fields""" instance = ActivityObject(id="a", type="b", fish="c") self.assertTrue(hasattr(instance, "id")) self.assertTrue(hasattr(instance, "type")) def test_init_default_field(self, _): - """ replace an existing required field with a default field """ + """replace an existing required field with a default field""" @dataclass(init=False) class TestClass(ActivityObject): - """ test class with default field """ + """test class with default field""" type: str = "TestObject" @@ -75,7 +75,7 @@ class BaseActivity(TestCase): self.assertEqual(instance.type, "TestObject") def test_serialize(self, _): - """ simple function for converting dataclass to dict """ + """simple function for converting dataclass to dict""" instance = ActivityObject(id="a", type="b") serialized = instance.serialize() self.assertIsInstance(serialized, dict) @@ -84,7 +84,7 @@ class BaseActivity(TestCase): @responses.activate def test_resolve_remote_id(self, _): - """ look up or load remote data """ + """look up or load remote data""" # existing item result = resolve_remote_id("http://example.com/a/b", model=models.User) self.assertEqual(result, self.user) @@ -106,14 +106,14 @@ class BaseActivity(TestCase): self.assertEqual(result.name, "MOUSE?? MOUSE!!") def test_to_model_invalid_model(self, _): - """ catch mismatch between activity type and model type """ + """catch mismatch between activity type and model type""" instance = ActivityObject(id="a", type="b") with self.assertRaises(ActivitySerializerError): instance.to_model(model=models.User) @responses.activate def test_to_model_image(self, _): - """ update an image field """ + """update an image field""" activity = activitypub.Person( id=self.user.remote_id, name="New Name", @@ -146,7 +146,7 @@ class BaseActivity(TestCase): self.assertEqual(self.user.key_pair.public_key, "hi") def test_to_model_many_to_many(self, _): - """ annoying that these all need special handling """ + """annoying that these all need special handling""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): status = models.Status.objects.create( content="test status", @@ -216,7 +216,7 @@ class BaseActivity(TestCase): @responses.activate def test_set_related_field(self, _): - """ celery task to add back-references to created objects """ + """celery task to add back-references to created objects""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): status = models.Status.objects.create( content="test status", diff --git a/bookwyrm/tests/activitypub/test_quotation.py b/bookwyrm/tests/activitypub/test_quotation.py index 1f429dd2..c90348bc 100644 --- a/bookwyrm/tests/activitypub/test_quotation.py +++ b/bookwyrm/tests/activitypub/test_quotation.py @@ -8,10 +8,10 @@ from bookwyrm import activitypub, models class Quotation(TestCase): - """ we have hecka ways to create statuses """ + """we have hecka ways to create statuses""" def setUp(self): - """ model objects we'll need """ + """model objects we'll need""" with patch("bookwyrm.models.user.set_remote_server.delay"): self.user = models.User.objects.create_user( "mouse", @@ -30,7 +30,7 @@ class Quotation(TestCase): self.status_data = json.loads(datafile.read_bytes()) def test_quotation_activity(self): - """ create a Quoteation ap object from json """ + """create a Quoteation ap object from json""" quotation = activitypub.Quotation(**self.status_data) self.assertEqual(quotation.type, "Quotation") @@ -41,7 +41,7 @@ class Quotation(TestCase): self.assertEqual(quotation.published, "2020-05-10T02:38:31.150343+00:00") def test_activity_to_model(self): - """ create a model instance from an activity object """ + """create a model instance from an activity object""" activity = activitypub.Quotation(**self.status_data) quotation = activity.to_model(model=models.Quotation) diff --git a/bookwyrm/tests/connectors/test_abstract_connector.py b/bookwyrm/tests/connectors/test_abstract_connector.py index 97190c16..4497b4e5 100644 --- a/bookwyrm/tests/connectors/test_abstract_connector.py +++ b/bookwyrm/tests/connectors/test_abstract_connector.py @@ -10,10 +10,10 @@ from bookwyrm.settings import DOMAIN class AbstractConnector(TestCase): - """ generic code for connecting to outside data sources """ + """generic code for connecting to outside data sources""" def setUp(self): - """ we need an example connector """ + """we need an example connector""" self.connector_info = models.Connector.objects.create( identifier="example.com", connector_file="openlibrary", @@ -38,7 +38,7 @@ class AbstractConnector(TestCase): self.edition_data = edition_data class TestConnector(abstract_connector.AbstractConnector): - """ nothing added here """ + """nothing added here""" def format_search_result(self, search_result): return search_result @@ -81,18 +81,18 @@ class AbstractConnector(TestCase): ) def test_abstract_connector_init(self): - """ barebones connector for search with defaults """ + """barebones connector for search with defaults""" self.assertIsInstance(self.connector.book_mappings, list) def test_is_available(self): - """ this isn't used.... """ + """this isn't used....""" self.assertTrue(self.connector.is_available()) self.connector.max_query_count = 1 self.connector.connector.query_count = 2 self.assertFalse(self.connector.is_available()) def test_get_or_create_book_existing(self): - """ find an existing book by remote/origin id """ + """find an existing book by remote/origin id""" self.assertEqual(models.Book.objects.count(), 1) self.assertEqual( self.book.remote_id, "https://%s/book/%d" % (DOMAIN, self.book.id) @@ -113,7 +113,7 @@ class AbstractConnector(TestCase): @responses.activate def test_get_or_create_book_deduped(self): - """ load remote data and deduplicate """ + """load remote data and deduplicate""" responses.add( responses.GET, "https://example.com/book/abcd", json=self.edition_data ) @@ -125,7 +125,7 @@ class AbstractConnector(TestCase): @responses.activate def test_get_or_create_author(self): - """ load an author """ + """load an author""" self.connector.author_mappings = [ Mapping("id"), Mapping("name"), @@ -142,7 +142,7 @@ class AbstractConnector(TestCase): self.assertEqual(result.origin_id, "https://www.example.com/author") def test_get_or_create_author_existing(self): - """ get an existing author """ + """get an existing author""" author = models.Author.objects.create(name="Test Author") result = self.connector.get_or_create_author(author.remote_id) self.assertEqual(author, result) diff --git a/bookwyrm/tests/connectors/test_abstract_minimal_connector.py b/bookwyrm/tests/connectors/test_abstract_minimal_connector.py index fa7c85f4..bc5625c9 100644 --- a/bookwyrm/tests/connectors/test_abstract_minimal_connector.py +++ b/bookwyrm/tests/connectors/test_abstract_minimal_connector.py @@ -8,10 +8,10 @@ from bookwyrm.connectors.abstract_connector import Mapping, SearchResult class AbstractConnector(TestCase): - """ generic code for connecting to outside data sources """ + """generic code for connecting to outside data sources""" def setUp(self): - """ we need an example connector """ + """we need an example connector""" self.connector_info = models.Connector.objects.create( identifier="example.com", connector_file="openlibrary", @@ -23,7 +23,7 @@ class AbstractConnector(TestCase): ) class TestConnector(abstract_connector.AbstractMinimalConnector): - """ nothing added here """ + """nothing added here""" def format_search_result(self, search_result): return search_result @@ -43,7 +43,7 @@ class AbstractConnector(TestCase): self.test_connector = TestConnector("example.com") def test_abstract_minimal_connector_init(self): - """ barebones connector for search with defaults """ + """barebones connector for search with defaults""" connector = self.test_connector self.assertEqual(connector.connector, self.connector_info) self.assertEqual(connector.base_url, "https://example.com") @@ -58,7 +58,7 @@ class AbstractConnector(TestCase): @responses.activate def test_search(self): - """ makes an http request to the outside service """ + """makes an http request to the outside service""" responses.add( responses.GET, "https://example.com/search?q=a%20book%20title", @@ -73,7 +73,7 @@ class AbstractConnector(TestCase): @responses.activate def test_search_min_confidence(self): - """ makes an http request to the outside service """ + """makes an http request to the outside service""" responses.add( responses.GET, "https://example.com/search?q=a%20book%20title&min_confidence=1", @@ -85,7 +85,7 @@ class AbstractConnector(TestCase): @responses.activate def test_isbn_search(self): - """ makes an http request to the outside service """ + """makes an http request to the outside service""" responses.add( responses.GET, "https://example.com/isbn?q=123456", @@ -96,7 +96,7 @@ class AbstractConnector(TestCase): self.assertEqual(len(results), 10) def test_search_result(self): - """ a class that stores info about a search result """ + """a class that stores info about a search result""" result = SearchResult( title="Title", key="https://example.com/book/1", @@ -109,21 +109,21 @@ class AbstractConnector(TestCase): self.assertEqual(result.title, "Title") def test_create_mapping(self): - """ maps remote fields for book data to bookwyrm activitypub fields """ + """maps remote fields for book data to bookwyrm activitypub fields""" mapping = Mapping("isbn") self.assertEqual(mapping.local_field, "isbn") self.assertEqual(mapping.remote_field, "isbn") self.assertEqual(mapping.formatter("bb"), "bb") def test_create_mapping_with_remote(self): - """ the remote field is different than the local field """ + """the remote field is different than the local field""" mapping = Mapping("isbn", remote_field="isbn13") self.assertEqual(mapping.local_field, "isbn") self.assertEqual(mapping.remote_field, "isbn13") self.assertEqual(mapping.formatter("bb"), "bb") def test_create_mapping_with_formatter(self): - """ a function is provided to modify the data """ + """a function is provided to modify the data""" formatter = lambda x: "aa" + x mapping = Mapping("isbn", formatter=formatter) self.assertEqual(mapping.local_field, "isbn") diff --git a/bookwyrm/tests/connectors/test_bookwyrm_connector.py b/bookwyrm/tests/connectors/test_bookwyrm_connector.py index 386c1350..46ea54a9 100644 --- a/bookwyrm/tests/connectors/test_bookwyrm_connector.py +++ b/bookwyrm/tests/connectors/test_bookwyrm_connector.py @@ -9,10 +9,10 @@ from bookwyrm.connectors.abstract_connector import SearchResult class BookWyrmConnector(TestCase): - """ this connector doesn't do much, just search """ + """this connector doesn't do much, just search""" def setUp(self): - """ create the connector """ + """create the connector""" models.Connector.objects.create( identifier="example.com", connector_file="bookwyrm_connector", @@ -24,14 +24,14 @@ class BookWyrmConnector(TestCase): self.connector = Connector("example.com") def test_get_or_create_book_existing(self): - """ load book activity """ + """load book activity""" work = models.Work.objects.create(title="Test Work") book = models.Edition.objects.create(title="Test Edition", parent_work=work) result = self.connector.get_or_create_book(book.remote_id) self.assertEqual(book, result) def test_format_search_result(self): - """ create a SearchResult object from search response json """ + """create a SearchResult object from search response json""" datafile = pathlib.Path(__file__).parent.joinpath("../data/bw_search.json") search_data = json.loads(datafile.read_bytes()) results = self.connector.parse_search_data(search_data) @@ -46,7 +46,7 @@ class BookWyrmConnector(TestCase): self.assertEqual(result.connector, self.connector) def test_format_isbn_search_result(self): - """ just gotta attach the connector """ + """just gotta attach the connector""" datafile = pathlib.Path(__file__).parent.joinpath("../data/bw_search.json") search_data = json.loads(datafile.read_bytes()) results = self.connector.parse_isbn_search_data(search_data) diff --git a/bookwyrm/tests/connectors/test_connector_manager.py b/bookwyrm/tests/connectors/test_connector_manager.py index 52589323..feded616 100644 --- a/bookwyrm/tests/connectors/test_connector_manager.py +++ b/bookwyrm/tests/connectors/test_connector_manager.py @@ -8,10 +8,10 @@ from bookwyrm.connectors.self_connector import Connector as SelfConnector class ConnectorManager(TestCase): - """ interface between the app and various connectors """ + """interface between the app and various connectors""" def setUp(self): - """ we'll need some books and a connector info entry """ + """we'll need some books and a connector info entry""" self.work = models.Work.objects.create(title="Example Work") self.edition = models.Edition.objects.create( @@ -32,7 +32,7 @@ class ConnectorManager(TestCase): ) def test_get_or_create_connector(self): - """ loads a connector if the data source is known or creates one """ + """loads a connector if the data source is known or creates one""" remote_id = "https://example.com/object/1" connector = connector_manager.get_or_create_connector(remote_id) self.assertIsInstance(connector, BookWyrmConnector) @@ -43,7 +43,7 @@ class ConnectorManager(TestCase): self.assertEqual(connector.identifier, same_connector.identifier) def test_get_connectors(self): - """ load all connectors """ + """load all connectors""" remote_id = "https://example.com/object/1" connector_manager.get_or_create_connector(remote_id) connectors = list(connector_manager.get_connectors()) @@ -52,7 +52,7 @@ class ConnectorManager(TestCase): self.assertIsInstance(connectors[1], BookWyrmConnector) def test_search(self): - """ search all connectors """ + """search all connectors""" results = connector_manager.search("Example") self.assertEqual(len(results), 1) self.assertIsInstance(results[0]["connector"], SelfConnector) @@ -60,7 +60,7 @@ class ConnectorManager(TestCase): self.assertEqual(results[0]["results"][0].title, "Example Edition") def test_search_isbn(self): - """ special handling if a query resembles an isbn """ + """special handling if a query resembles an isbn""" results = connector_manager.search("0000000000") self.assertEqual(len(results), 1) self.assertIsInstance(results[0]["connector"], SelfConnector) @@ -68,20 +68,20 @@ class ConnectorManager(TestCase): self.assertEqual(results[0]["results"][0].title, "Example Edition") def test_local_search(self): - """ search only the local database """ + """search only the local database""" results = connector_manager.local_search("Example") self.assertEqual(len(results), 1) self.assertEqual(results[0].title, "Example Edition") def test_first_search_result(self): - """ only get one search result """ + """only get one search result""" result = connector_manager.first_search_result("Example") self.assertEqual(result.title, "Example Edition") no_result = connector_manager.first_search_result("dkjfhg") self.assertIsNone(no_result) def test_load_connector(self): - """ load a connector object from the database entry """ + """load a connector object from the database entry""" connector = connector_manager.load_connector(self.connector) self.assertIsInstance(connector, SelfConnector) self.assertEqual(connector.identifier, "test_connector") diff --git a/bookwyrm/tests/connectors/test_openlibrary_connector.py b/bookwyrm/tests/connectors/test_openlibrary_connector.py index 3cff4fb0..699b26ed 100644 --- a/bookwyrm/tests/connectors/test_openlibrary_connector.py +++ b/bookwyrm/tests/connectors/test_openlibrary_connector.py @@ -16,10 +16,10 @@ from bookwyrm.connectors.connector_manager import ConnectorException class Openlibrary(TestCase): - """ test loading data from openlibrary.org """ + """test loading data from openlibrary.org""" def setUp(self): - """ creates the connector we'll use """ + """creates the connector we'll use""" models.Connector.objects.create( identifier="openlibrary.org", name="OpenLibrary", @@ -42,7 +42,7 @@ class Openlibrary(TestCase): self.edition_list_data = json.loads(edition_list_file.read_bytes()) def test_get_remote_id_from_data(self): - """ format the remote id from the data """ + """format the remote id from the data""" data = {"key": "/work/OL1234W"} result = self.connector.get_remote_id_from_data(data) self.assertEqual(result, "https://openlibrary.org/work/OL1234W") @@ -51,13 +51,13 @@ class Openlibrary(TestCase): self.connector.get_remote_id_from_data({}) def test_is_work_data(self): - """ detect if the loaded json is a work """ + """detect if the loaded json is a work""" self.assertEqual(self.connector.is_work_data(self.work_data), True) self.assertEqual(self.connector.is_work_data(self.edition_data), False) @responses.activate def test_get_edition_from_work_data(self): - """ loads a list of editions """ + """loads a list of editions""" data = {"key": "/work/OL1234W"} responses.add( responses.GET, @@ -74,7 +74,7 @@ class Openlibrary(TestCase): @responses.activate def test_get_work_from_edition_data(self): - """ loads a list of editions """ + """loads a list of editions""" data = {"works": [{"key": "/work/OL1234W"}]} responses.add( responses.GET, @@ -87,7 +87,7 @@ class Openlibrary(TestCase): @responses.activate def test_get_authors_from_data(self): - """ find authors in data """ + """find authors in data""" responses.add( responses.GET, "https://openlibrary.org/authors/OL382982A", @@ -112,13 +112,13 @@ class Openlibrary(TestCase): self.assertEqual(result.openlibrary_key, "OL453734A") def test_get_cover_url(self): - """ formats a url that should contain the cover image """ + """formats a url that should contain the cover image""" blob = ["image"] result = self.connector.get_cover_url(blob) self.assertEqual(result, "https://covers.openlibrary.org/b/id/image-L.jpg") def test_parse_search_result(self): - """ extract the results from the search json response """ + """extract the results from the search json response""" datafile = pathlib.Path(__file__).parent.joinpath("../data/ol_search.json") search_data = json.loads(datafile.read_bytes()) result = self.connector.parse_search_data(search_data) @@ -126,7 +126,7 @@ class Openlibrary(TestCase): self.assertEqual(len(result), 2) def test_format_search_result(self): - """ translate json from openlibrary into SearchResult """ + """translate json from openlibrary into SearchResult""" datafile = pathlib.Path(__file__).parent.joinpath("../data/ol_search.json") search_data = json.loads(datafile.read_bytes()) results = self.connector.parse_search_data(search_data) @@ -141,7 +141,7 @@ class Openlibrary(TestCase): self.assertEqual(result.connector, self.connector) def test_parse_isbn_search_result(self): - """ extract the results from the search json response """ + """extract the results from the search json response""" datafile = pathlib.Path(__file__).parent.joinpath("../data/ol_isbn_search.json") search_data = json.loads(datafile.read_bytes()) result = self.connector.parse_isbn_search_data(search_data) @@ -149,7 +149,7 @@ class Openlibrary(TestCase): self.assertEqual(len(result), 1) def test_format_isbn_search_result(self): - """ translate json from openlibrary into SearchResult """ + """translate json from openlibrary into SearchResult""" datafile = pathlib.Path(__file__).parent.joinpath("../data/ol_isbn_search.json") search_data = json.loads(datafile.read_bytes()) results = self.connector.parse_isbn_search_data(search_data) @@ -165,7 +165,7 @@ class Openlibrary(TestCase): @responses.activate def test_load_edition_data(self): - """ format url from key and make request """ + """format url from key and make request""" key = "OL1234W" responses.add( responses.GET, @@ -177,7 +177,7 @@ class Openlibrary(TestCase): @responses.activate def test_expand_book_data(self): - """ given a book, get more editions """ + """given a book, get more editions""" work = models.Work.objects.create(title="Test Work", openlibrary_key="OL1234W") edition = models.Edition.objects.create(title="Test Edition", parent_work=work) @@ -194,29 +194,29 @@ class Openlibrary(TestCase): self.connector.expand_book_data(work) def test_get_description(self): - """ should do some cleanup on the description data """ + """should do some cleanup on the description data""" description = get_description(self.work_data["description"]) expected = "First in the Old Kingdom/Abhorsen series." self.assertEqual(description, expected) def test_get_openlibrary_key(self): - """ extracts the uuid """ + """extracts the uuid""" key = get_openlibrary_key("/books/OL27320736M") self.assertEqual(key, "OL27320736M") def test_get_languages(self): - """ looks up languages from a list """ + """looks up languages from a list""" languages = get_languages(self.edition_data["languages"]) self.assertEqual(languages, ["English"]) def test_pick_default_edition(self): - """ detect if the loaded json is an edition """ + """detect if the loaded json is an edition""" edition = pick_default_edition(self.edition_list_data["entries"]) self.assertEqual(edition["key"], "/books/OL9788823M") @responses.activate def test_create_edition_from_data(self): - """ okay but can it actually create an edition with proper metadata """ + """okay but can it actually create an edition with proper metadata""" work = models.Work.objects.create(title="Hello") responses.add( responses.GET, @@ -240,7 +240,7 @@ class Openlibrary(TestCase): self.assertEqual(result.physical_format, "Hardcover") def test_ignore_edition(self): - """ skip editions with poor metadata """ + """skip editions with poor metadata""" self.assertFalse(ignore_edition({"isbn_13": "hi"})) self.assertFalse(ignore_edition({"oclc_numbers": "hi"})) self.assertFalse(ignore_edition({"covers": "hi"})) diff --git a/bookwyrm/tests/connectors/test_self_connector.py b/bookwyrm/tests/connectors/test_self_connector.py index 9925f594..eee7d00c 100644 --- a/bookwyrm/tests/connectors/test_self_connector.py +++ b/bookwyrm/tests/connectors/test_self_connector.py @@ -9,10 +9,10 @@ from bookwyrm.settings import DOMAIN class SelfConnector(TestCase): - """ just uses local data """ + """just uses local data""" def setUp(self): - """ creating the connector """ + """creating the connector""" models.Connector.objects.create( identifier=DOMAIN, name="Local", @@ -27,7 +27,7 @@ class SelfConnector(TestCase): self.connector = Connector(DOMAIN) def test_format_search_result(self): - """ create a SearchResult """ + """create a SearchResult""" author = models.Author.objects.create(name="Anonymous") edition = models.Edition.objects.create( title="Edition of Example Work", @@ -42,7 +42,7 @@ class SelfConnector(TestCase): self.assertEqual(result.connector, self.connector) def test_search_rank(self): - """ prioritize certain results """ + """prioritize certain results""" author = models.Author.objects.create(name="Anonymous") edition = models.Edition.objects.create( title="Edition of Example Work", @@ -78,7 +78,7 @@ class SelfConnector(TestCase): self.assertEqual(results[2].title, "Edition of Example Work") def test_search_multiple_editions(self): - """ it should get rid of duplicate editions for the same work """ + """it should get rid of duplicate editions for the same work""" work = models.Work.objects.create(title="Work Title") edition_1 = models.Edition.objects.create( title="Edition 1 Title", parent_work=work diff --git a/bookwyrm/tests/importers/test_goodreads_import.py b/bookwyrm/tests/importers/test_goodreads_import.py index 6e9caaf4..0e39d5ec 100644 --- a/bookwyrm/tests/importers/test_goodreads_import.py +++ b/bookwyrm/tests/importers/test_goodreads_import.py @@ -14,10 +14,10 @@ from bookwyrm.settings import DOMAIN class GoodreadsImport(TestCase): - """ importing from goodreads csv """ + """importing from goodreads csv""" def setUp(self): - """ use a test csv """ + """use a test csv""" self.importer = GoodreadsImporter() datafile = pathlib.Path(__file__).parent.joinpath("../data/goodreads.csv") self.csv = open(datafile, "r", encoding=self.importer.encoding) @@ -44,7 +44,7 @@ class GoodreadsImport(TestCase): ) def test_create_job(self): - """ creates the import job entry and checks csv """ + """creates the import job entry and checks csv""" import_job = self.importer.create_job(self.user, self.csv, False, "public") self.assertEqual(import_job.user, self.user) self.assertEqual(import_job.include_reviews, False) @@ -60,7 +60,7 @@ class GoodreadsImport(TestCase): self.assertEqual(import_items[2].data["Book Id"], "28694510") def test_create_retry_job(self): - """ trying again with items that didn't import """ + """trying again with items that didn't import""" import_job = self.importer.create_job(self.user, self.csv, False, "unlisted") import_items = models.ImportItem.objects.filter(job=import_job).all()[:2] @@ -78,7 +78,7 @@ class GoodreadsImport(TestCase): self.assertEqual(retry_items[1].data["Book Id"], "52691223") def test_start_import(self): - """ begin loading books """ + """begin loading books""" import_job = self.importer.create_job(self.user, self.csv, False, "unlisted") MockTask = namedtuple("Task", ("id")) mock_task = MockTask(7) @@ -90,7 +90,7 @@ class GoodreadsImport(TestCase): @responses.activate def test_import_data(self): - """ resolve entry """ + """resolve entry""" import_job = self.importer.create_job(self.user, self.csv, False, "unlisted") book = models.Edition.objects.create(title="Test Book") @@ -105,7 +105,7 @@ class GoodreadsImport(TestCase): self.assertEqual(import_item.book.id, book.id) def test_handle_imported_book(self): - """ goodreads import added a book, this adds related connections """ + """goodreads import added a book, this adds related connections""" shelf = self.user.shelf_set.filter(identifier="read").first() self.assertIsNone(shelf.books.first()) @@ -138,7 +138,7 @@ class GoodreadsImport(TestCase): self.assertEqual(readthrough.finish_date.day, 25) def test_handle_imported_book_already_shelved(self): - """ goodreads import added a book, this adds related connections """ + """goodreads import added a book, this adds related connections""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): shelf = self.user.shelf_set.filter(identifier="to-read").first() models.ShelfBook.objects.create(shelf=shelf, user=self.user, book=self.book) @@ -171,7 +171,7 @@ class GoodreadsImport(TestCase): self.assertEqual(readthrough.finish_date.day, 25) def test_handle_import_twice(self): - """ re-importing books """ + """re-importing books""" shelf = self.user.shelf_set.filter(identifier="read").first() import_job = models.ImportJob.objects.create(user=self.user) datafile = pathlib.Path(__file__).parent.joinpath("../data/goodreads.csv") @@ -206,7 +206,7 @@ class GoodreadsImport(TestCase): @patch("bookwyrm.activitystreams.ActivityStream.add_status") def test_handle_imported_book_review(self, _): - """ goodreads review import """ + """goodreads review import""" import_job = models.ImportJob.objects.create(user=self.user) datafile = pathlib.Path(__file__).parent.joinpath("../data/goodreads.csv") csv_file = open(datafile, "r") @@ -229,7 +229,7 @@ class GoodreadsImport(TestCase): self.assertEqual(review.privacy, "unlisted") def test_handle_imported_book_reviews_disabled(self): - """ goodreads review import """ + """goodreads review import""" import_job = models.ImportJob.objects.create(user=self.user) datafile = pathlib.Path(__file__).parent.joinpath("../data/goodreads.csv") csv_file = open(datafile, "r") diff --git a/bookwyrm/tests/importers/test_librarything_import.py b/bookwyrm/tests/importers/test_librarything_import.py index 5e1d778e..5ae0944c 100644 --- a/bookwyrm/tests/importers/test_librarything_import.py +++ b/bookwyrm/tests/importers/test_librarything_import.py @@ -13,10 +13,10 @@ from bookwyrm.settings import DOMAIN class LibrarythingImport(TestCase): - """ importing from librarything tsv """ + """importing from librarything tsv""" def setUp(self): - """ use a test tsv """ + """use a test tsv""" self.importer = LibrarythingImporter() datafile = pathlib.Path(__file__).parent.joinpath("../data/librarything.tsv") @@ -45,7 +45,7 @@ class LibrarythingImport(TestCase): ) def test_create_job(self): - """ creates the import job entry and checks csv """ + """creates the import job entry and checks csv""" import_job = self.importer.create_job(self.user, self.csv, False, "public") self.assertEqual(import_job.user, self.user) self.assertEqual(import_job.include_reviews, False) @@ -61,7 +61,7 @@ class LibrarythingImport(TestCase): self.assertEqual(import_items[2].data["Book Id"], "5015399") def test_create_retry_job(self): - """ trying again with items that didn't import """ + """trying again with items that didn't import""" import_job = self.importer.create_job(self.user, self.csv, False, "unlisted") import_items = models.ImportItem.objects.filter(job=import_job).all()[:2] @@ -80,7 +80,7 @@ class LibrarythingImport(TestCase): @responses.activate def test_import_data(self): - """ resolve entry """ + """resolve entry""" import_job = self.importer.create_job(self.user, self.csv, False, "unlisted") book = models.Edition.objects.create(title="Test Book") @@ -95,7 +95,7 @@ class LibrarythingImport(TestCase): self.assertEqual(import_item.book.id, book.id) def test_handle_imported_book(self): - """ librarything import added a book, this adds related connections """ + """librarything import added a book, this adds related connections""" shelf = self.user.shelf_set.filter(identifier="read").first() self.assertIsNone(shelf.books.first()) @@ -130,7 +130,7 @@ class LibrarythingImport(TestCase): self.assertEqual(readthrough.finish_date.day, 8) def test_handle_imported_book_already_shelved(self): - """ librarything import added a book, this adds related connections """ + """librarything import added a book, this adds related connections""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): shelf = self.user.shelf_set.filter(identifier="to-read").first() models.ShelfBook.objects.create(shelf=shelf, user=self.user, book=self.book) @@ -165,7 +165,7 @@ class LibrarythingImport(TestCase): self.assertEqual(readthrough.finish_date.day, 8) def test_handle_import_twice(self): - """ re-importing books """ + """re-importing books""" shelf = self.user.shelf_set.filter(identifier="read").first() import_job = models.ImportJob.objects.create(user=self.user) datafile = pathlib.Path(__file__).parent.joinpath("../data/librarything.tsv") @@ -202,7 +202,7 @@ class LibrarythingImport(TestCase): @patch("bookwyrm.activitystreams.ActivityStream.add_status") def test_handle_imported_book_review(self, _): - """ librarything review import """ + """librarything review import""" import_job = models.ImportJob.objects.create(user=self.user) datafile = pathlib.Path(__file__).parent.joinpath("../data/librarything.tsv") csv_file = open(datafile, "r", encoding=self.importer.encoding) @@ -225,7 +225,7 @@ class LibrarythingImport(TestCase): self.assertEqual(review.privacy, "unlisted") def test_handle_imported_book_reviews_disabled(self): - """ librarything review import """ + """librarything review import""" import_job = models.ImportJob.objects.create(user=self.user) datafile = pathlib.Path(__file__).parent.joinpath("../data/librarything.tsv") csv_file = open(datafile, "r", encoding=self.importer.encoding) diff --git a/bookwyrm/tests/management/test_populate_streams.py b/bookwyrm/tests/management/test_populate_streams.py index 6a9b6b8a..d187c054 100644 --- a/bookwyrm/tests/management/test_populate_streams.py +++ b/bookwyrm/tests/management/test_populate_streams.py @@ -8,10 +8,10 @@ from bookwyrm.management.commands.populate_streams import populate_streams @patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay") class Activitystreams(TestCase): - """ using redis to build activity streams """ + """using redis to build activity streams""" def setUp(self): - """ we need some stuff """ + """we need some stuff""" self.local_user = models.User.objects.create_user( "mouse", "mouse@mouse.mouse", "password", local=True, localname="mouse" ) @@ -31,7 +31,7 @@ class Activitystreams(TestCase): self.book = models.Edition.objects.create(title="test book") def test_populate_streams(self, _): - """ make sure the function on the redis manager gets called """ + """make sure the function on the redis manager gets called""" with patch("bookwyrm.activitystreams.ActivityStream.add_status"): models.Comment.objects.create( user=self.local_user, content="hi", book=self.book diff --git a/bookwyrm/tests/models/test_activitypub_mixin.py b/bookwyrm/tests/models/test_activitypub_mixin.py index e172ede9..1c0975c4 100644 --- a/bookwyrm/tests/models/test_activitypub_mixin.py +++ b/bookwyrm/tests/models/test_activitypub_mixin.py @@ -15,10 +15,10 @@ from bookwyrm.models.activitypub_mixin import ActivityMixin, ObjectMixin @patch("bookwyrm.activitystreams.ActivityStream.add_status") class ActivitypubMixins(TestCase): - """ functionality shared across models """ + """functionality shared across models""" def setUp(self): - """ shared data """ + """shared data""" self.local_user = models.User.objects.create_user( "mouse", "mouse@mouse.com", "mouseword", local=True, localname="mouse" ) @@ -46,16 +46,16 @@ class ActivitypubMixins(TestCase): # ActivitypubMixin def test_to_activity(self, _): - """ model to ActivityPub json """ + """model to ActivityPub json""" @dataclass(init=False) class TestActivity(ActivityObject): - """ real simple mock """ + """real simple mock""" type: str = "Test" class TestModel(ActivitypubMixin, base_model.BookWyrmModel): - """ real simple mock model because BookWyrmModel is abstract """ + """real simple mock model because BookWyrmModel is abstract""" instance = TestModel() instance.remote_id = "https://www.example.com/test" @@ -67,7 +67,7 @@ class ActivitypubMixins(TestCase): self.assertEqual(activity["type"], "Test") def test_find_existing_by_remote_id(self, _): - """ attempt to match a remote id to an object in the db """ + """attempt to match a remote id to an object in the db""" # uses a different remote id scheme # this isn't really part of this test directly but it's helpful to state book = models.Edition.objects.create( @@ -100,7 +100,7 @@ class ActivitypubMixins(TestCase): result = models.Status.find_existing_by_remote_id("https://comment.net") def test_find_existing(self, _): - """ match a blob of data to a model """ + """match a blob of data to a model""" book = models.Edition.objects.create( title="Test edition", openlibrary_key="OL1234", @@ -110,7 +110,7 @@ class ActivitypubMixins(TestCase): self.assertEqual(result, book) def test_get_recipients_public_object(self, _): - """ determines the recipients for an object's broadcast """ + """determines the recipients for an object's broadcast""" MockSelf = namedtuple("Self", ("privacy")) mock_self = MockSelf("public") recipients = ActivitypubMixin.get_recipients(mock_self) @@ -118,7 +118,7 @@ class ActivitypubMixins(TestCase): self.assertEqual(recipients[0], self.remote_user.inbox) def test_get_recipients_public_user_object_no_followers(self, _): - """ determines the recipients for a user's object broadcast """ + """determines the recipients for a user's object broadcast""" MockSelf = namedtuple("Self", ("privacy", "user")) mock_self = MockSelf("public", self.local_user) @@ -126,7 +126,7 @@ class ActivitypubMixins(TestCase): self.assertEqual(len(recipients), 0) def test_get_recipients_public_user_object(self, _): - """ determines the recipients for a user's object broadcast """ + """determines the recipients for a user's object broadcast""" MockSelf = namedtuple("Self", ("privacy", "user")) mock_self = MockSelf("public", self.local_user) self.local_user.followers.add(self.remote_user) @@ -136,7 +136,7 @@ class ActivitypubMixins(TestCase): self.assertEqual(recipients[0], self.remote_user.inbox) def test_get_recipients_public_user_object_with_mention(self, _): - """ determines the recipients for a user's object broadcast """ + """determines the recipients for a user's object broadcast""" MockSelf = namedtuple("Self", ("privacy", "user")) mock_self = MockSelf("public", self.local_user) self.local_user.followers.add(self.remote_user) @@ -159,7 +159,7 @@ class ActivitypubMixins(TestCase): self.assertTrue(self.remote_user.inbox in recipients) def test_get_recipients_direct(self, _): - """ determines the recipients for a user's object broadcast """ + """determines the recipients for a user's object broadcast""" MockSelf = namedtuple("Self", ("privacy", "user")) mock_self = MockSelf("public", self.local_user) self.local_user.followers.add(self.remote_user) @@ -181,7 +181,7 @@ class ActivitypubMixins(TestCase): self.assertEqual(recipients[0], another_remote_user.inbox) def test_get_recipients_combine_inboxes(self, _): - """ should combine users with the same shared_inbox """ + """should combine users with the same shared_inbox""" self.remote_user.shared_inbox = "http://example.com/inbox" self.remote_user.save(broadcast=False) with patch("bookwyrm.models.user.set_remote_server.delay"): @@ -205,7 +205,7 @@ class ActivitypubMixins(TestCase): self.assertEqual(recipients[0], "http://example.com/inbox") def test_get_recipients_software(self, _): - """ should differentiate between bookwyrm and other remote users """ + """should differentiate between bookwyrm and other remote users""" with patch("bookwyrm.models.user.set_remote_server.delay"): another_remote_user = models.User.objects.create_user( "nutria", @@ -235,13 +235,13 @@ class ActivitypubMixins(TestCase): # ObjectMixin def test_object_save_create(self, _): - """ should save uneventufully when broadcast is disabled """ + """should save uneventufully when broadcast is disabled""" class Success(Exception): - """ this means we got to the right method """ + """this means we got to the right method""" class ObjectModel(ObjectMixin, base_model.BookWyrmModel): - """ real simple mock model because BookWyrmModel is abstract """ + """real simple mock model because BookWyrmModel is abstract""" user = models.fields.ForeignKey("User", on_delete=db.models.CASCADE) @@ -252,7 +252,7 @@ class ActivitypubMixins(TestCase): def broadcast( self, activity, sender, **kwargs ): # pylint: disable=arguments-differ - """ do something """ + """do something""" raise Success() def to_create_activity(self, user): # pylint: disable=arguments-differ @@ -266,13 +266,13 @@ class ActivitypubMixins(TestCase): ObjectModel(user=None).save() def test_object_save_update(self, _): - """ should save uneventufully when broadcast is disabled """ + """should save uneventufully when broadcast is disabled""" class Success(Exception): - """ this means we got to the right method """ + """this means we got to the right method""" class UpdateObjectModel(ObjectMixin, base_model.BookWyrmModel): - """ real simple mock model because BookWyrmModel is abstract """ + """real simple mock model because BookWyrmModel is abstract""" user = models.fields.ForeignKey("User", on_delete=db.models.CASCADE) last_edited_by = models.fields.ForeignKey( @@ -292,13 +292,13 @@ class ActivitypubMixins(TestCase): UpdateObjectModel(id=1, last_edited_by=self.local_user).save() def test_object_save_delete(self, _): - """ should create delete activities when objects are deleted by flag """ + """should create delete activities when objects are deleted by flag""" class ActivitySuccess(Exception): - """ this means we got to the right method """ + """this means we got to the right method""" class DeletableObjectModel(ObjectMixin, base_model.BookWyrmModel): - """ real simple mock model because BookWyrmModel is abstract """ + """real simple mock model because BookWyrmModel is abstract""" user = models.fields.ForeignKey("User", on_delete=db.models.CASCADE) deleted = models.fields.BooleanField() @@ -314,7 +314,7 @@ class ActivitypubMixins(TestCase): DeletableObjectModel(id=1, user=self.local_user, deleted=True).save() def test_to_delete_activity(self, _): - """ wrapper for Delete activity """ + """wrapper for Delete activity""" MockSelf = namedtuple("Self", ("remote_id", "to_activity")) mock_self = MockSelf( "https://example.com/status/1", lambda *args: self.object_mock @@ -329,7 +329,7 @@ class ActivitypubMixins(TestCase): ) def test_to_update_activity(self, _): - """ ditto above but for Update """ + """ditto above but for Update""" MockSelf = namedtuple("Self", ("remote_id", "to_activity")) mock_self = MockSelf( "https://example.com/status/1", lambda *args: self.object_mock @@ -347,7 +347,7 @@ class ActivitypubMixins(TestCase): # Activity mixin def test_to_undo_activity(self, _): - """ and again, for Undo """ + """and again, for Undo""" MockSelf = namedtuple("Self", ("remote_id", "to_activity", "user")) mock_self = MockSelf( "https://example.com/status/1", diff --git a/bookwyrm/tests/models/test_base_model.py b/bookwyrm/tests/models/test_base_model.py index 442f98ca..5a8350b2 100644 --- a/bookwyrm/tests/models/test_base_model.py +++ b/bookwyrm/tests/models/test_base_model.py @@ -8,10 +8,10 @@ from bookwyrm.settings import DOMAIN class BaseModel(TestCase): - """ functionality shared across models """ + """functionality shared across models""" def setUp(self): - """ shared data """ + """shared data""" self.local_user = models.User.objects.create_user( "mouse", "mouse@mouse.com", "mouseword", local=True, localname="mouse" ) @@ -27,14 +27,14 @@ class BaseModel(TestCase): ) def test_remote_id(self): - """ these should be generated """ + """these should be generated""" instance = base_model.BookWyrmModel() instance.id = 1 expected = instance.get_remote_id() self.assertEqual(expected, "https://%s/bookwyrmmodel/1" % DOMAIN) def test_remote_id_with_user(self): - """ format of remote id when there's a user object """ + """format of remote id when there's a user object""" instance = base_model.BookWyrmModel() instance.user = self.local_user instance.id = 1 @@ -42,7 +42,7 @@ class BaseModel(TestCase): self.assertEqual(expected, "https://%s/user/mouse/bookwyrmmodel/1" % DOMAIN) def test_set_remote_id(self): - """ this function sets remote ids after creation """ + """this function sets remote ids after creation""" # using Work because it BookWrymModel is abstract and this requires save # Work is a relatively not-fancy model. instance = models.Work.objects.create(title="work title") @@ -59,7 +59,7 @@ class BaseModel(TestCase): @patch("bookwyrm.activitystreams.ActivityStream.add_status") def test_object_visible_to_user(self, _): - """ does a user have permission to view an object """ + """does a user have permission to view an object""" obj = models.Status.objects.create( content="hi", user=self.remote_user, privacy="public" ) @@ -88,7 +88,7 @@ class BaseModel(TestCase): @patch("bookwyrm.activitystreams.ActivityStream.add_status") def test_object_visible_to_user_follower(self, _): - """ what you can see if you follow a user """ + """what you can see if you follow a user""" self.remote_user.followers.add(self.local_user) obj = models.Status.objects.create( content="hi", user=self.remote_user, privacy="followers" @@ -108,7 +108,7 @@ class BaseModel(TestCase): @patch("bookwyrm.activitystreams.ActivityStream.add_status") def test_object_visible_to_user_blocked(self, _): - """ you can't see it if they block you """ + """you can't see it if they block you""" self.remote_user.blocks.add(self.local_user) obj = models.Status.objects.create( content="hi", user=self.remote_user, privacy="public" diff --git a/bookwyrm/tests/models/test_book_model.py b/bookwyrm/tests/models/test_book_model.py index 14ab0c57..c80cc4a8 100644 --- a/bookwyrm/tests/models/test_book_model.py +++ b/bookwyrm/tests/models/test_book_model.py @@ -8,10 +8,10 @@ from bookwyrm.models.book import isbn_10_to_13, isbn_13_to_10 class Book(TestCase): - """ not too much going on in the books model but here we are """ + """not too much going on in the books model but here we are""" def setUp(self): - """ we'll need some books """ + """we'll need some books""" self.work = models.Work.objects.create( title="Example Work", remote_id="https://example.com/book/1" ) @@ -25,17 +25,17 @@ class Book(TestCase): ) def test_remote_id(self): - """ fanciness with remote/origin ids """ + """fanciness with remote/origin ids""" remote_id = "https://%s/book/%d" % (settings.DOMAIN, self.work.id) self.assertEqual(self.work.get_remote_id(), remote_id) self.assertEqual(self.work.remote_id, remote_id) def test_create_book(self): - """ you shouldn't be able to create Books (only editions and works) """ + """you shouldn't be able to create Books (only editions and works)""" self.assertRaises(ValueError, models.Book.objects.create, title="Invalid Book") def test_isbn_10_to_13(self): - """ checksums and so on """ + """checksums and so on""" isbn_10 = "178816167X" isbn_13 = isbn_10_to_13(isbn_10) self.assertEqual(isbn_13, "9781788161671") @@ -45,7 +45,7 @@ class Book(TestCase): self.assertEqual(isbn_13, "9781788161671") def test_isbn_13_to_10(self): - """ checksums and so on """ + """checksums and so on""" isbn_13 = "9781788161671" isbn_10 = isbn_13_to_10(isbn_13) self.assertEqual(isbn_10, "178816167X") @@ -55,7 +55,7 @@ class Book(TestCase): self.assertEqual(isbn_10, "178816167X") def test_get_edition_info(self): - """ text slug about an edition """ + """text slug about an edition""" book = models.Edition.objects.create(title="Test Edition") self.assertEqual(book.edition_info, "") @@ -77,7 +77,7 @@ class Book(TestCase): self.assertEqual(book.alt_text, "Test Edition (worm, Glorbish language, 2020)") def test_get_rank(self): - """ sets the data quality index for the book """ + """sets the data quality index for the book""" # basic rank self.assertEqual(self.first_edition.edition_rank, 0) diff --git a/bookwyrm/tests/models/test_federated_server.py b/bookwyrm/tests/models/test_federated_server.py index 4e9e8b68..43724568 100644 --- a/bookwyrm/tests/models/test_federated_server.py +++ b/bookwyrm/tests/models/test_federated_server.py @@ -6,10 +6,10 @@ from bookwyrm import models class FederatedServer(TestCase): - """ federate server management """ + """federate server management""" def setUp(self): - """ we'll need a user """ + """we'll need a user""" self.server = models.FederatedServer.objects.create(server_name="test.server") with patch("bookwyrm.models.user.set_remote_server.delay"): self.remote_user = models.User.objects.create_user( @@ -36,7 +36,7 @@ class FederatedServer(TestCase): ) def test_block_unblock(self): - """ block a server and all users on it """ + """block a server and all users on it""" self.assertEqual(self.server.status, "federated") self.assertTrue(self.remote_user.is_active) self.assertFalse(self.inactive_remote_user.is_active) diff --git a/bookwyrm/tests/models/test_fields.py b/bookwyrm/tests/models/test_fields.py index 18bb028f..ea692b62 100644 --- a/bookwyrm/tests/models/test_fields.py +++ b/bookwyrm/tests/models/test_fields.py @@ -25,10 +25,10 @@ from bookwyrm.models.activitypub_mixin import ActivitypubMixin # pylint: disable=too-many-public-methods class ActivitypubFields(TestCase): - """ overwrites standard model feilds to work with activitypub """ + """overwrites standard model feilds to work with activitypub""" def test_validate_remote_id(self): - """ should look like a url """ + """should look like a url""" self.assertIsNone(fields.validate_remote_id("http://www.example.com")) self.assertIsNone(fields.validate_remote_id("https://www.example.com")) self.assertIsNone(fields.validate_remote_id("http://exle.com/dlg-23/x")) @@ -45,7 +45,7 @@ class ActivitypubFields(TestCase): ) def test_activitypub_field_mixin(self): - """ generic mixin with super basic to and from functionality """ + """generic mixin with super basic to and from functionality""" instance = fields.ActivitypubFieldMixin() self.assertEqual(instance.field_to_activity("fish"), "fish") self.assertEqual(instance.field_from_activity("fish"), "fish") @@ -63,11 +63,11 @@ class ActivitypubFields(TestCase): self.assertEqual(instance.get_activitypub_field(), "snakeCaseName") def test_set_field_from_activity(self): - """ setter from entire json blob """ + """setter from entire json blob""" @dataclass class TestModel: - """ real simple mock """ + """real simple mock""" field_name: str @@ -82,11 +82,11 @@ class ActivitypubFields(TestCase): self.assertEqual(mock_model.field_name, "hi") def test_set_activity_from_field(self): - """ set json field given entire model """ + """set json field given entire model""" @dataclass class TestModel: - """ real simple mock """ + """real simple mock""" field_name: str unrelated: str @@ -100,7 +100,7 @@ class ActivitypubFields(TestCase): self.assertEqual(data["fieldName"], "bip") def test_remote_id_field(self): - """ just sets some defaults on charfield """ + """just sets some defaults on charfield""" instance = fields.RemoteIdField() self.assertEqual(instance.max_length, 255) self.assertTrue(instance.deduplication_field) @@ -109,7 +109,7 @@ class ActivitypubFields(TestCase): instance.run_validators("http://www.example.com/dlfjg 23/x") def test_username_field(self): - """ again, just setting defaults on username field """ + """again, just setting defaults on username field""" instance = fields.UsernameField() self.assertEqual(instance.activitypub_field, "preferredUsername") self.assertEqual(instance.max_length, 150) @@ -130,7 +130,7 @@ class ActivitypubFields(TestCase): self.assertEqual(instance.field_to_activity("test@example.com"), "test") def test_privacy_field_defaults(self): - """ post privacy field's many default values """ + """post privacy field's many default values""" instance = fields.PrivacyField() self.assertEqual(instance.max_length, 255) self.assertEqual( @@ -143,11 +143,11 @@ class ActivitypubFields(TestCase): ) def test_privacy_field_set_field_from_activity(self): - """ translate between to/cc fields and privacy """ + """translate between to/cc fields and privacy""" @dataclass(init=False) class TestActivity(ActivityObject): - """ real simple mock """ + """real simple mock""" to: List[str] cc: List[str] @@ -155,7 +155,7 @@ class ActivitypubFields(TestCase): type: str = "Test" class TestPrivacyModel(ActivitypubMixin, BookWyrmModel): - """ real simple mock model because BookWyrmModel is abstract """ + """real simple mock model because BookWyrmModel is abstract""" privacy_field = fields.PrivacyField() mention_users = fields.TagField(User) @@ -187,7 +187,7 @@ class ActivitypubFields(TestCase): @patch("bookwyrm.models.activitypub_mixin.ObjectMixin.broadcast") @patch("bookwyrm.activitystreams.ActivityStream.add_status") def test_privacy_field_set_activity_from_field(self, *_): - """ translate between to/cc fields and privacy """ + """translate between to/cc fields and privacy""" user = User.objects.create_user( "rat", "rat@rat.rat", "ratword", local=True, localname="rat" ) @@ -231,7 +231,7 @@ class ActivitypubFields(TestCase): self.assertEqual(activity["cc"], []) def test_foreign_key(self): - """ should be able to format a related model """ + """should be able to format a related model""" instance = fields.ForeignKey("User", on_delete=models.CASCADE) Serializable = namedtuple("Serializable", ("to_activity", "remote_id")) item = Serializable(lambda: {"a": "b"}, "https://e.b/c") @@ -240,7 +240,7 @@ class ActivitypubFields(TestCase): @responses.activate def test_foreign_key_from_activity_str(self): - """ create a new object from a foreign key """ + """create a new object from a foreign key""" instance = fields.ForeignKey(User, on_delete=models.CASCADE) datafile = pathlib.Path(__file__).parent.joinpath("../data/ap_user.json") userdata = json.loads(datafile.read_bytes()) @@ -264,7 +264,7 @@ class ActivitypubFields(TestCase): self.assertEqual(value.name, "MOUSE?? MOUSE!!") def test_foreign_key_from_activity_dict(self): - """ test recieving activity json """ + """test recieving activity json""" instance = fields.ForeignKey(User, on_delete=models.CASCADE) datafile = pathlib.Path(__file__).parent.joinpath("../data/ap_user.json") userdata = json.loads(datafile.read_bytes()) @@ -284,7 +284,7 @@ class ActivitypubFields(TestCase): # et cetera but we're not testing serializing user json def test_foreign_key_from_activity_dict_existing(self): - """ test receiving a dict of an existing object in the db """ + """test receiving a dict of an existing object in the db""" instance = fields.ForeignKey(User, on_delete=models.CASCADE) datafile = pathlib.Path(__file__).parent.joinpath("../data/ap_user.json") userdata = json.loads(datafile.read_bytes()) @@ -302,7 +302,7 @@ class ActivitypubFields(TestCase): self.assertEqual(value, user) def test_foreign_key_from_activity_str_existing(self): - """ test receiving a remote id of an existing object in the db """ + """test receiving a remote id of an existing object in the db""" instance = fields.ForeignKey(User, on_delete=models.CASCADE) user = User.objects.create_user( "mouse", "mouse@mouse.mouse", "mouseword", local=True, localname="mouse" @@ -315,14 +315,14 @@ class ActivitypubFields(TestCase): self.assertEqual(value, user) def test_one_to_one_field(self): - """ a gussied up foreign key """ + """a gussied up foreign key""" instance = fields.OneToOneField("User", on_delete=models.CASCADE) Serializable = namedtuple("Serializable", ("to_activity", "remote_id")) item = Serializable(lambda: {"a": "b"}, "https://e.b/c") self.assertEqual(instance.field_to_activity(item), {"a": "b"}) def test_many_to_many_field(self): - """ lists! """ + """lists!""" instance = fields.ManyToManyField("User") Serializable = namedtuple("Serializable", ("to_activity", "remote_id")) @@ -340,7 +340,7 @@ class ActivitypubFields(TestCase): @responses.activate def test_many_to_many_field_from_activity(self): - """ resolve related fields for a list, takes a list of remote ids """ + """resolve related fields for a list, takes a list of remote ids""" instance = fields.ManyToManyField(User) datafile = pathlib.Path(__file__).parent.joinpath("../data/ap_user.json") userdata = json.loads(datafile.read_bytes()) @@ -360,7 +360,7 @@ class ActivitypubFields(TestCase): self.assertIsInstance(value[0], User) def test_tag_field(self): - """ a special type of many to many field """ + """a special type of many to many field""" instance = fields.TagField("User") Serializable = namedtuple( @@ -379,13 +379,13 @@ class ActivitypubFields(TestCase): self.assertEqual(result[0].type, "Serializable") def test_tag_field_from_activity(self): - """ loadin' a list of items from Links """ + """loadin' a list of items from Links""" # TODO @responses.activate @patch("bookwyrm.models.activitypub_mixin.ObjectMixin.broadcast") def test_image_field(self, _): - """ storing images """ + """storing images""" user = User.objects.create_user( "mouse", "mouse@mouse.mouse", "mouseword", local=True, localname="mouse" ) @@ -423,7 +423,7 @@ class ActivitypubFields(TestCase): self.assertIsInstance(loaded_image[1], ContentFile) def test_datetime_field(self): - """ this one is pretty simple, it just has to use isoformat """ + """this one is pretty simple, it just has to use isoformat""" instance = fields.DateTimeField() now = timezone.now() self.assertEqual(instance.field_to_activity(now), now.isoformat()) @@ -431,12 +431,12 @@ class ActivitypubFields(TestCase): self.assertEqual(instance.field_from_activity("bip"), None) def test_array_field(self): - """ idk why it makes them strings but probably for a good reason """ + """idk why it makes them strings but probably for a good reason""" instance = fields.ArrayField(fields.IntegerField) self.assertEqual(instance.field_to_activity([0, 1]), ["0", "1"]) def test_html_field(self): - """ sanitizes html, the sanitizer has its own tests """ + """sanitizes html, the sanitizer has its own tests""" instance = fields.HtmlField() self.assertEqual( instance.field_from_activity("

hi

"), "

hi

" diff --git a/bookwyrm/tests/models/test_import_model.py b/bookwyrm/tests/models/test_import_model.py index 38c3b1ed..76a914d1 100644 --- a/bookwyrm/tests/models/test_import_model.py +++ b/bookwyrm/tests/models/test_import_model.py @@ -14,10 +14,10 @@ from bookwyrm.connectors.abstract_connector import SearchResult class ImportJob(TestCase): - """ this is a fancy one!!! """ + """this is a fancy one!!!""" def setUp(self): - """ data is from a goodreads export of The Raven Tower """ + """data is from a goodreads export of The Raven Tower""" read_data = { "Book Id": 39395857, "Title": "The Raven Tower", @@ -72,30 +72,30 @@ class ImportJob(TestCase): ) def test_isbn(self): - """ it unquotes the isbn13 field from data """ + """it unquotes the isbn13 field from data""" expected = "9780356506999" item = models.ImportItem.objects.get(index=1) self.assertEqual(item.isbn, expected) def test_shelf(self): - """ converts to the local shelf typology """ + """converts to the local shelf typology""" expected = "reading" self.assertEqual(self.item_1.shelf, expected) def test_date_added(self): - """ converts to the local shelf typology """ + """converts to the local shelf typology""" expected = datetime.datetime(2019, 4, 9, 0, 0, tzinfo=timezone.utc) item = models.ImportItem.objects.get(index=1) self.assertEqual(item.date_added, expected) def test_date_read(self): - """ converts to the local shelf typology """ + """converts to the local shelf typology""" expected = datetime.datetime(2019, 4, 12, 0, 0, tzinfo=timezone.utc) item = models.ImportItem.objects.get(index=2) self.assertEqual(item.date_read, expected) def test_currently_reading_reads(self): - """ infer currently reading dates where available """ + """infer currently reading dates where available""" expected = [ models.ReadThrough( start_date=datetime.datetime(2019, 4, 9, 0, 0, tzinfo=timezone.utc) @@ -106,7 +106,7 @@ class ImportJob(TestCase): self.assertEqual(actual.reads[0].finish_date, expected[0].finish_date) def test_read_reads(self): - """ infer read dates where available """ + """infer read dates where available""" actual = self.item_2 self.assertEqual( actual.reads[0].start_date, @@ -118,14 +118,14 @@ class ImportJob(TestCase): ) def test_unread_reads(self): - """ handle books with no read dates """ + """handle books with no read dates""" expected = [] actual = models.ImportItem.objects.get(index=3) self.assertEqual(actual.reads, expected) @responses.activate def test_get_book_from_isbn(self): - """ search and load books by isbn (9780356506999) """ + """search and load books by isbn (9780356506999)""" connector_info = models.Connector.objects.create( identifier="openlibrary.org", name="OpenLibrary", diff --git a/bookwyrm/tests/models/test_list.py b/bookwyrm/tests/models/test_list.py index 4e3460a9..8f5bd497 100644 --- a/bookwyrm/tests/models/test_list.py +++ b/bookwyrm/tests/models/test_list.py @@ -7,10 +7,10 @@ from bookwyrm import models, settings @patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay") class List(TestCase): - """ some activitypub oddness ahead """ + """some activitypub oddness ahead""" def setUp(self): - """ look, a list """ + """look, a list""" self.local_user = models.User.objects.create_user( "mouse", "mouse@mouse.mouse", "mouseword", local=True, localname="mouse" ) @@ -18,7 +18,7 @@ class List(TestCase): self.book = models.Edition.objects.create(title="hi", parent_work=work) def test_remote_id(self, _): - """ shelves use custom remote ids """ + """shelves use custom remote ids""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): book_list = models.List.objects.create( name="Test List", user=self.local_user @@ -27,7 +27,7 @@ class List(TestCase): self.assertEqual(book_list.get_remote_id(), expected_id) def test_to_activity(self, _): - """ jsonify it """ + """jsonify it""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): book_list = models.List.objects.create( name="Test List", user=self.local_user @@ -41,7 +41,7 @@ class List(TestCase): self.assertEqual(activity_json["owner"], self.local_user.remote_id) def test_list_item(self, _): - """ a list entry """ + """a list entry""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): book_list = models.List.objects.create( name="Test List", user=self.local_user, privacy="unlisted" @@ -59,7 +59,7 @@ class List(TestCase): self.assertEqual(item.recipients, []) def test_list_item_pending(self, _): - """ a list entry """ + """a list entry""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): book_list = models.List.objects.create( name="Test List", user=self.local_user diff --git a/bookwyrm/tests/models/test_readthrough_model.py b/bookwyrm/tests/models/test_readthrough_model.py index f69e8779..93e9e654 100644 --- a/bookwyrm/tests/models/test_readthrough_model.py +++ b/bookwyrm/tests/models/test_readthrough_model.py @@ -6,10 +6,10 @@ from bookwyrm import models, settings class ReadThrough(TestCase): - """ some activitypub oddness ahead """ + """some activitypub oddness ahead""" def setUp(self): - """ look, a shelf """ + """look, a shelf""" self.user = models.User.objects.create_user( "mouse", "mouse@mouse.mouse", "mouseword", local=True, localname="mouse" ) @@ -27,7 +27,7 @@ class ReadThrough(TestCase): ) def test_progress_update(self): - """ Test progress updates """ + """Test progress updates""" self.readthrough.create_update() # No-op, no progress yet self.readthrough.progress = 10 self.readthrough.create_update() diff --git a/bookwyrm/tests/models/test_relationship_models.py b/bookwyrm/tests/models/test_relationship_models.py index 0e842b21..d629b5c7 100644 --- a/bookwyrm/tests/models/test_relationship_models.py +++ b/bookwyrm/tests/models/test_relationship_models.py @@ -6,10 +6,10 @@ from bookwyrm import models class Relationship(TestCase): - """ following, blocking, stuff like that """ + """following, blocking, stuff like that""" def setUp(self): - """ we need some users for this """ + """we need some users for this""" with patch("bookwyrm.models.user.set_remote_server.delay"): self.remote_user = models.User.objects.create_user( "rat", @@ -27,11 +27,11 @@ class Relationship(TestCase): self.local_user.save(broadcast=False) def test_user_follows_from_request(self): - """ convert a follow request into a follow """ + """convert a follow request into a follow""" real_broadcast = models.UserFollowRequest.broadcast def mock_broadcast(_, activity, user): - """ introspect what's being sent out """ + """introspect what's being sent out""" self.assertEqual(user.remote_id, self.local_user.remote_id) self.assertEqual(activity["type"], "Follow") @@ -54,7 +54,7 @@ class Relationship(TestCase): models.UserFollowRequest.broadcast = real_broadcast def test_user_follows_from_request_custom_remote_id(self): - """ store a specific remote id for a relationship provided by remote """ + """store a specific remote id for a relationship provided by remote""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): request = models.UserFollowRequest.objects.create( user_subject=self.local_user, @@ -71,7 +71,7 @@ class Relationship(TestCase): self.assertEqual(rel.user_object, self.remote_user) def test_follow_request_activity(self): - """ accept a request and make it a relationship """ + """accept a request and make it a relationship""" real_broadcast = models.UserFollowRequest.broadcast def mock_broadcast(_, activity, user): @@ -88,7 +88,7 @@ class Relationship(TestCase): models.UserFollowRequest.broadcast = real_broadcast def test_follow_request_accept(self): - """ accept a request and make it a relationship """ + """accept a request and make it a relationship""" real_broadcast = models.UserFollowRequest.broadcast def mock_broadcast(_, activity, user): @@ -115,7 +115,7 @@ class Relationship(TestCase): models.UserFollowRequest.broadcast = real_broadcast def test_follow_request_reject(self): - """ accept a request and make it a relationship """ + """accept a request and make it a relationship""" real_broadcast = models.UserFollowRequest.broadcast def mock_reject(_, activity, user): diff --git a/bookwyrm/tests/models/test_shelf_model.py b/bookwyrm/tests/models/test_shelf_model.py index 45ae1fa1..911df059 100644 --- a/bookwyrm/tests/models/test_shelf_model.py +++ b/bookwyrm/tests/models/test_shelf_model.py @@ -8,10 +8,10 @@ from bookwyrm import models, settings # pylint: disable=unused-argument class Shelf(TestCase): - """ some activitypub oddness ahead """ + """some activitypub oddness ahead""" def setUp(self): - """ look, a shelf """ + """look, a shelf""" self.local_user = models.User.objects.create_user( "mouse", "mouse@mouse.mouse", "mouseword", local=True, localname="mouse" ) @@ -19,7 +19,7 @@ class Shelf(TestCase): self.book = models.Edition.objects.create(title="test book", parent_work=work) def test_remote_id(self): - """ shelves use custom remote ids """ + """shelves use custom remote ids""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): shelf = models.Shelf.objects.create( name="Test Shelf", identifier="test-shelf", user=self.local_user @@ -28,7 +28,7 @@ class Shelf(TestCase): self.assertEqual(shelf.get_remote_id(), expected_id) def test_to_activity(self): - """ jsonify it """ + """jsonify it""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): shelf = models.Shelf.objects.create( name="Test Shelf", identifier="test-shelf", user=self.local_user @@ -42,7 +42,7 @@ class Shelf(TestCase): self.assertEqual(activity_json["owner"], self.local_user.remote_id) def test_create_update_shelf(self): - """ create and broadcast shelf creation """ + """create and broadcast shelf creation""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay") as mock: shelf = models.Shelf.objects.create( @@ -63,7 +63,7 @@ class Shelf(TestCase): self.assertEqual(shelf.name, "arthur russel") def test_shelve(self): - """ create and broadcast shelf creation """ + """create and broadcast shelf creation""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): shelf = models.Shelf.objects.create( name="Test Shelf", identifier="test-shelf", user=self.local_user diff --git a/bookwyrm/tests/models/test_status_model.py b/bookwyrm/tests/models/test_status_model.py index 52d6608a..4c8930bc 100644 --- a/bookwyrm/tests/models/test_status_model.py +++ b/bookwyrm/tests/models/test_status_model.py @@ -17,10 +17,10 @@ from bookwyrm import activitypub, models, settings @patch("bookwyrm.models.Status.broadcast") @patch("bookwyrm.activitystreams.ActivityStream.add_status") class Status(TestCase): - """ lotta types of statuses """ + """lotta types of statuses""" def setUp(self): - """ useful things for creating a status """ + """useful things for creating a status""" self.local_user = models.User.objects.create_user( "mouse", "mouse@mouse.mouse", "mouseword", local=True, localname="mouse" ) @@ -46,14 +46,14 @@ class Status(TestCase): self.book.cover.save("test.jpg", ContentFile(output.getvalue())) def test_status_generated_fields(self, *_): - """ setting remote id """ + """setting remote id""" status = models.Status.objects.create(content="bleh", user=self.local_user) expected_id = "https://%s/user/mouse/status/%d" % (settings.DOMAIN, status.id) self.assertEqual(status.remote_id, expected_id) self.assertEqual(status.privacy, "public") def test_replies(self, *_): - """ get a list of replies """ + """get a list of replies""" parent = models.Status.objects.create(content="hi", user=self.local_user) child = models.Status.objects.create( content="hello", reply_parent=parent, user=self.local_user @@ -72,7 +72,7 @@ class Status(TestCase): self.assertIsInstance(replies.last(), models.Review) def test_status_type(self, *_): - """ class name """ + """class name""" self.assertEqual(models.Status().status_type, "Note") self.assertEqual(models.Review().status_type, "Review") self.assertEqual(models.Quotation().status_type, "Quotation") @@ -80,14 +80,14 @@ class Status(TestCase): self.assertEqual(models.Boost().status_type, "Announce") def test_boostable(self, *_): - """ can a status be boosted, based on privacy """ + """can a status be boosted, based on privacy""" self.assertTrue(models.Status(privacy="public").boostable) self.assertTrue(models.Status(privacy="unlisted").boostable) self.assertFalse(models.Status(privacy="followers").boostable) self.assertFalse(models.Status(privacy="direct").boostable) def test_to_replies(self, *_): - """ activitypub replies collection """ + """activitypub replies collection""" parent = models.Status.objects.create(content="hi", user=self.local_user) child = models.Status.objects.create( content="hello", reply_parent=parent, user=self.local_user @@ -104,7 +104,7 @@ class Status(TestCase): self.assertEqual(replies["totalItems"], 2) def test_status_to_activity(self, *_): - """ subclass of the base model version with a "pure" serializer """ + """subclass of the base model version with a "pure" serializer""" status = models.Status.objects.create( content="test content", user=self.local_user ) @@ -115,7 +115,7 @@ class Status(TestCase): self.assertEqual(activity["sensitive"], False) def test_status_to_activity_tombstone(self, *_): - """ subclass of the base model version with a "pure" serializer """ + """subclass of the base model version with a "pure" serializer""" with patch( "bookwyrm.activitystreams.ActivityStream.remove_object_from_related_stores" ): @@ -131,7 +131,7 @@ class Status(TestCase): self.assertFalse(hasattr(activity, "content")) def test_status_to_pure_activity(self, *_): - """ subclass of the base model version with a "pure" serializer """ + """subclass of the base model version with a "pure" serializer""" status = models.Status.objects.create( content="test content", user=self.local_user ) @@ -143,7 +143,7 @@ class Status(TestCase): self.assertEqual(activity["attachment"], []) def test_generated_note_to_activity(self, *_): - """ subclass of the base model version with a "pure" serializer """ + """subclass of the base model version with a "pure" serializer""" status = models.GeneratedNote.objects.create( content="test content", user=self.local_user ) @@ -157,7 +157,7 @@ class Status(TestCase): self.assertEqual(len(activity["tag"]), 2) def test_generated_note_to_pure_activity(self, *_): - """ subclass of the base model version with a "pure" serializer """ + """subclass of the base model version with a "pure" serializer""" status = models.GeneratedNote.objects.create( content="test content", user=self.local_user ) @@ -181,7 +181,7 @@ class Status(TestCase): self.assertEqual(activity["attachment"][0].name, "Test Edition") def test_comment_to_activity(self, *_): - """ subclass of the base model version with a "pure" serializer """ + """subclass of the base model version with a "pure" serializer""" status = models.Comment.objects.create( content="test content", user=self.local_user, book=self.book ) @@ -192,7 +192,7 @@ class Status(TestCase): self.assertEqual(activity["inReplyToBook"], self.book.remote_id) def test_comment_to_pure_activity(self, *_): - """ subclass of the base model version with a "pure" serializer """ + """subclass of the base model version with a "pure" serializer""" status = models.Comment.objects.create( content="test content", user=self.local_user, book=self.book ) @@ -212,7 +212,7 @@ class Status(TestCase): self.assertEqual(activity["attachment"][0].name, "Test Edition") def test_quotation_to_activity(self, *_): - """ subclass of the base model version with a "pure" serializer """ + """subclass of the base model version with a "pure" serializer""" status = models.Quotation.objects.create( quote="a sickening sense", content="test content", @@ -227,7 +227,7 @@ class Status(TestCase): self.assertEqual(activity["inReplyToBook"], self.book.remote_id) def test_quotation_to_pure_activity(self, *_): - """ subclass of the base model version with a "pure" serializer """ + """subclass of the base model version with a "pure" serializer""" status = models.Quotation.objects.create( quote="a sickening sense", content="test content", @@ -250,7 +250,7 @@ class Status(TestCase): self.assertEqual(activity["attachment"][0].name, "Test Edition") def test_review_to_activity(self, *_): - """ subclass of the base model version with a "pure" serializer """ + """subclass of the base model version with a "pure" serializer""" status = models.Review.objects.create( name="Review name", content="test content", @@ -267,7 +267,7 @@ class Status(TestCase): self.assertEqual(activity["inReplyToBook"], self.book.remote_id) def test_review_to_pure_activity(self, *_): - """ subclass of the base model version with a "pure" serializer """ + """subclass of the base model version with a "pure" serializer""" status = models.Review.objects.create( name="Review's name", content="test content", @@ -291,7 +291,7 @@ class Status(TestCase): self.assertEqual(activity["attachment"][0].name, "Test Edition") def test_review_to_pure_activity_no_rating(self, *_): - """ subclass of the base model version with a "pure" serializer """ + """subclass of the base model version with a "pure" serializer""" status = models.Review.objects.create( name="Review name", content="test content", @@ -313,7 +313,7 @@ class Status(TestCase): self.assertEqual(activity["attachment"][0].name, "Test Edition") def test_reviewrating_to_pure_activity(self, *_): - """ subclass of the base model version with a "pure" serializer """ + """subclass of the base model version with a "pure" serializer""" status = models.ReviewRating.objects.create( rating=3.0, user=self.local_user, @@ -335,11 +335,11 @@ class Status(TestCase): self.assertEqual(activity["attachment"][0].name, "Test Edition") def test_favorite(self, *_): - """ fav a status """ + """fav a status""" real_broadcast = models.Favorite.broadcast def fav_broadcast_mock(_, activity, user): - """ ok """ + """ok""" self.assertEqual(user.remote_id, self.local_user.remote_id) self.assertEqual(activity["type"], "Like") @@ -361,7 +361,7 @@ class Status(TestCase): models.Favorite.broadcast = real_broadcast def test_boost(self, *_): - """ boosting, this one's a bit fussy """ + """boosting, this one's a bit fussy""" status = models.Status.objects.create( content="test content", user=self.local_user ) @@ -373,7 +373,7 @@ class Status(TestCase): self.assertEqual(activity, boost.to_activity(pure=True)) def test_notification(self, *_): - """ a simple model """ + """a simple model""" notification = models.Notification.objects.create( user=self.local_user, notification_type="FAVORITE" ) @@ -385,7 +385,7 @@ class Status(TestCase): ) def test_create_broadcast(self, _, broadcast_mock): - """ should send out two verions of a status on create """ + """should send out two verions of a status on create""" models.Comment.objects.create( content="hi", user=self.local_user, book=self.book ) @@ -405,7 +405,7 @@ class Status(TestCase): self.assertEqual(args["object"]["type"], "Comment") def test_recipients_with_mentions(self, *_): - """ get recipients to broadcast a status """ + """get recipients to broadcast a status""" status = models.GeneratedNote.objects.create( content="test content", user=self.local_user ) @@ -414,7 +414,7 @@ class Status(TestCase): self.assertEqual(status.recipients, [self.remote_user]) def test_recipients_with_reply_parent(self, *_): - """ get recipients to broadcast a status """ + """get recipients to broadcast a status""" parent_status = models.GeneratedNote.objects.create( content="test content", user=self.remote_user ) @@ -425,7 +425,7 @@ class Status(TestCase): self.assertEqual(status.recipients, [self.remote_user]) def test_recipients_with_reply_parent_and_mentions(self, *_): - """ get recipients to broadcast a status """ + """get recipients to broadcast a status""" parent_status = models.GeneratedNote.objects.create( content="test content", user=self.remote_user ) @@ -438,7 +438,7 @@ class Status(TestCase): @responses.activate def test_ignore_activity_boost(self, *_): - """ don't bother with most remote statuses """ + """don't bother with most remote statuses""" activity = activitypub.Announce( id="http://www.faraway.com/boost/12", actor=self.remote_user.remote_id, diff --git a/bookwyrm/tests/models/test_user_model.py b/bookwyrm/tests/models/test_user_model.py index 883ef669..b2791379 100644 --- a/bookwyrm/tests/models/test_user_model.py +++ b/bookwyrm/tests/models/test_user_model.py @@ -22,7 +22,7 @@ class User(TestCase): ) def test_computed_fields(self): - """ username instead of id here """ + """username instead of id here""" expected_id = "https://%s/user/mouse" % DOMAIN self.assertEqual(self.user.remote_id, expected_id) self.assertEqual(self.user.username, "mouse@%s" % DOMAIN) @@ -155,7 +155,7 @@ class User(TestCase): self.assertIsNone(server.application_version) def test_delete_user(self): - """ deactivate a user """ + """deactivate a user""" self.assertTrue(self.user.is_active) with patch( "bookwyrm.models.activitypub_mixin.broadcast_task.delay" diff --git a/bookwyrm/tests/test_activitystreams.py b/bookwyrm/tests/test_activitystreams.py index b4efeba3..59266383 100644 --- a/bookwyrm/tests/test_activitystreams.py +++ b/bookwyrm/tests/test_activitystreams.py @@ -7,10 +7,10 @@ from bookwyrm import activitystreams, models @patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay") @patch("bookwyrm.activitystreams.ActivityStream.add_status") class Activitystreams(TestCase): - """ using redis to build activity streams """ + """using redis to build activity streams""" def setUp(self): - """ use a test csv """ + """use a test csv""" self.local_user = models.User.objects.create_user( "mouse", "mouse@mouse.mouse", "password", local=True, localname="mouse" ) @@ -30,14 +30,14 @@ class Activitystreams(TestCase): self.book = models.Edition.objects.create(title="test book") class TestStream(activitystreams.ActivityStream): - """ test stream, don't have to do anything here """ + """test stream, don't have to do anything here""" key = "test" self.test_stream = TestStream() def test_activitystream_class_ids(self, *_): - """ the abstract base class for stream objects """ + """the abstract base class for stream objects""" self.assertEqual( self.test_stream.stream_id(self.local_user), "{}-test".format(self.local_user.id), @@ -48,7 +48,7 @@ class Activitystreams(TestCase): ) def test_abstractstream_get_audience(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" status = models.Status.objects.create( user=self.remote_user, content="hi", privacy="public" ) @@ -59,7 +59,7 @@ class Activitystreams(TestCase): self.assertTrue(self.another_user in users) def test_abstractstream_get_audience_direct(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" status = models.Status.objects.create( user=self.remote_user, content="hi", @@ -82,7 +82,7 @@ class Activitystreams(TestCase): self.assertFalse(self.remote_user in users) def test_abstractstream_get_audience_followers_remote_user(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" status = models.Status.objects.create( user=self.remote_user, content="hi", @@ -92,7 +92,7 @@ class Activitystreams(TestCase): self.assertFalse(users.exists()) def test_abstractstream_get_audience_followers_self(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" status = models.Comment.objects.create( user=self.local_user, content="hi", @@ -105,7 +105,7 @@ class Activitystreams(TestCase): self.assertFalse(self.remote_user in users) def test_abstractstream_get_audience_followers_with_mention(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" status = models.Comment.objects.create( user=self.remote_user, content="hi", @@ -120,7 +120,7 @@ class Activitystreams(TestCase): self.assertFalse(self.remote_user in users) def test_abstractstream_get_audience_followers_with_relationship(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" self.remote_user.followers.add(self.local_user) status = models.Comment.objects.create( user=self.remote_user, @@ -134,7 +134,7 @@ class Activitystreams(TestCase): self.assertFalse(self.remote_user in users) def test_homestream_get_audience(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" status = models.Status.objects.create( user=self.remote_user, content="hi", privacy="public" ) @@ -142,7 +142,7 @@ class Activitystreams(TestCase): self.assertFalse(users.exists()) def test_homestream_get_audience_with_mentions(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" status = models.Status.objects.create( user=self.remote_user, content="hi", privacy="public" ) @@ -152,7 +152,7 @@ class Activitystreams(TestCase): self.assertFalse(self.another_user in users) def test_homestream_get_audience_with_relationship(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" self.remote_user.followers.add(self.local_user) status = models.Status.objects.create( user=self.remote_user, content="hi", privacy="public" @@ -162,7 +162,7 @@ class Activitystreams(TestCase): self.assertFalse(self.another_user in users) def test_localstream_get_audience_remote_status(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" status = models.Status.objects.create( user=self.remote_user, content="hi", privacy="public" ) @@ -170,7 +170,7 @@ class Activitystreams(TestCase): self.assertEqual(users, []) def test_localstream_get_audience_local_status(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" status = models.Status.objects.create( user=self.local_user, content="hi", privacy="public" ) @@ -179,7 +179,7 @@ class Activitystreams(TestCase): self.assertTrue(self.another_user in users) def test_localstream_get_audience_unlisted(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" status = models.Status.objects.create( user=self.local_user, content="hi", privacy="unlisted" ) @@ -187,7 +187,7 @@ class Activitystreams(TestCase): self.assertEqual(users, []) def test_federatedstream_get_audience(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" status = models.Status.objects.create( user=self.remote_user, content="hi", privacy="public" ) @@ -196,7 +196,7 @@ class Activitystreams(TestCase): self.assertTrue(self.another_user in users) def test_federatedstream_get_audience_unlisted(self, *_): - """ get a list of users that should see a status """ + """get a list of users that should see a status""" status = models.Status.objects.create( user=self.remote_user, content="hi", privacy="unlisted" ) diff --git a/bookwyrm/tests/test_emailing.py b/bookwyrm/tests/test_emailing.py index 5d7d4894..0f9cc365 100644 --- a/bookwyrm/tests/test_emailing.py +++ b/bookwyrm/tests/test_emailing.py @@ -10,10 +10,10 @@ from bookwyrm import emailing, models @patch("bookwyrm.emailing.send_email.delay") class Emailing(TestCase): - """ every response to a get request, html or json """ + """every response to a get request, html or json""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -25,7 +25,7 @@ class Emailing(TestCase): models.SiteSettings.objects.create() def test_invite_email(self, email_mock): - """ load the invite email """ + """load the invite email""" invite_request = models.InviteRequest.objects.create( email="test@email.com", invite=models.SiteInvite.objects.create(user=self.local_user), @@ -40,7 +40,7 @@ class Emailing(TestCase): self.assertEqual(len(args), 4) def test_password_reset_email(self, email_mock): - """ load the password reset email """ + """load the password reset email""" reset = models.PasswordReset.objects.create(user=self.local_user) emailing.password_reset_email(reset) diff --git a/bookwyrm/tests/test_sanitize_html.py b/bookwyrm/tests/test_sanitize_html.py index 2b3d0378..6c405348 100644 --- a/bookwyrm/tests/test_sanitize_html.py +++ b/bookwyrm/tests/test_sanitize_html.py @@ -5,10 +5,10 @@ from bookwyrm.sanitize_html import InputHtmlParser class Sanitizer(TestCase): - """ sanitizer tests """ + """sanitizer tests""" def test_no_html(self): - """ just text """ + """just text""" input_text = "no html " parser = InputHtmlParser() parser.feed(input_text) @@ -16,7 +16,7 @@ class Sanitizer(TestCase): self.assertEqual(input_text, output) def test_valid_html(self): - """ leave the html untouched """ + """leave the html untouched""" input_text = "yes html" parser = InputHtmlParser() parser.feed(input_text) @@ -24,7 +24,7 @@ class Sanitizer(TestCase): self.assertEqual(input_text, output) def test_valid_html_attrs(self): - """ and don't remove attributes """ + """and don't remove attributes""" input_text = 'yes html' parser = InputHtmlParser() parser.feed(input_text) @@ -32,7 +32,7 @@ class Sanitizer(TestCase): self.assertEqual(input_text, output) def test_invalid_html(self): - """ remove all html when the html is malformed """ + """remove all html when the html is malformed""" input_text = "yes html" parser = InputHtmlParser() parser.feed(input_text) @@ -46,7 +46,7 @@ class Sanitizer(TestCase): self.assertEqual("yes html ", output) def test_disallowed_html(self): - """ remove disallowed html but keep allowed html """ + """remove disallowed html but keep allowed html""" input_text = "
yes html
" parser = InputHtmlParser() parser.feed(input_text) diff --git a/bookwyrm/tests/test_signing.py b/bookwyrm/tests/test_signing.py index d9cc411c..758ba9bb 100644 --- a/bookwyrm/tests/test_signing.py +++ b/bookwyrm/tests/test_signing.py @@ -20,7 +20,7 @@ from bookwyrm.signatures import create_key_pair, make_signature, make_digest def get_follow_activity(follower, followee): - """ generates a test activity """ + """generates a test activity""" return Follow( id="https://test.com/user/follow/id", actor=follower.remote_id, @@ -33,10 +33,10 @@ Sender = namedtuple("Sender", ("remote_id", "key_pair")) class Signature(TestCase): - """ signature test """ + """signature test""" def setUp(self): - """ create users and test data """ + """create users and test data""" self.mouse = models.User.objects.create_user( "mouse@%s" % DOMAIN, "mouse@example.com", "", local=True, localname="mouse" ) @@ -56,7 +56,7 @@ class Signature(TestCase): models.SiteSettings.objects.create() def send(self, signature, now, data, digest): - """ test request """ + """test request""" c = Client() return c.post( urlsplit(self.rat.inbox).path, @@ -74,7 +74,7 @@ class Signature(TestCase): def send_test_request( # pylint: disable=too-many-arguments self, sender, signer=None, send_data=None, digest=None, date=None ): - """ sends a follow request to the "rat" user """ + """sends a follow request to the "rat" user""" now = date or http_date() data = json.dumps(get_follow_activity(sender, self.rat)) digest = digest or make_digest(data) @@ -84,7 +84,7 @@ class Signature(TestCase): return self.send(signature, now, send_data or data, digest) def test_correct_signature(self): - """ this one should just work """ + """this one should just work""" response = self.send_test_request(sender=self.mouse) self.assertEqual(response.status_code, 200) @@ -96,7 +96,7 @@ class Signature(TestCase): @responses.activate def test_remote_signer(self): - """ signtures for remote users """ + """signtures for remote users""" datafile = pathlib.Path(__file__).parent.joinpath("data/ap_user.json") data = json.loads(datafile.read_bytes()) data["id"] = self.fake_remote.remote_id @@ -119,7 +119,7 @@ class Signature(TestCase): @responses.activate def test_key_needs_refresh(self): - """ an out of date key should be updated and the new key work """ + """an out of date key should be updated and the new key work""" datafile = pathlib.Path(__file__).parent.joinpath("data/ap_user.json") data = json.loads(datafile.read_bytes()) data["id"] = self.fake_remote.remote_id @@ -155,7 +155,7 @@ class Signature(TestCase): @responses.activate def test_nonexistent_signer(self): - """ fail when unable to look up signer """ + """fail when unable to look up signer""" responses.add( responses.GET, self.fake_remote.remote_id, @@ -177,7 +177,7 @@ class Signature(TestCase): @pytest.mark.integration def test_invalid_digest(self): - """ signature digest must be valid """ + """signature digest must be valid""" with patch("bookwyrm.activitypub.resolve_remote_id"): response = self.send_test_request( self.mouse, digest="SHA-256=AAAAAAAAAAAAAAAAAA" diff --git a/bookwyrm/tests/test_templatetags.py b/bookwyrm/tests/test_templatetags.py index 2fadb978..a92e887a 100644 --- a/bookwyrm/tests/test_templatetags.py +++ b/bookwyrm/tests/test_templatetags.py @@ -12,10 +12,10 @@ from bookwyrm.templatetags import bookwyrm_tags @patch("bookwyrm.activitystreams.ActivityStream.add_status") class TemplateTags(TestCase): - """ lotta different things here """ + """lotta different things here""" def setUp(self): - """ create some filler objects """ + """create some filler objects""" self.user = models.User.objects.create_user( "mouse@example.com", "mouse@mouse.mouse", @@ -34,34 +34,34 @@ class TemplateTags(TestCase): self.book = models.Edition.objects.create(title="Test Book") def test_dict_key(self, _): - """ just getting a value out of a dict """ + """just getting a value out of a dict""" test_dict = {"a": 1, "b": 3} self.assertEqual(bookwyrm_tags.dict_key(test_dict, "a"), 1) self.assertEqual(bookwyrm_tags.dict_key(test_dict, "c"), 0) def test_get_user_rating(self, _): - """ get a user's most recent rating of a book """ + """get a user's most recent rating of a book""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): models.Review.objects.create(user=self.user, book=self.book, rating=3) self.assertEqual(bookwyrm_tags.get_user_rating(self.book, self.user), 3) def test_get_user_rating_doesnt_exist(self, _): - """ there is no rating available """ + """there is no rating available""" self.assertEqual(bookwyrm_tags.get_user_rating(self.book, self.user), 0) def test_get_user_identifer_local(self, _): - """ fall back to the simplest uid available """ + """fall back to the simplest uid available""" self.assertNotEqual(self.user.username, self.user.localname) self.assertEqual(bookwyrm_tags.get_user_identifier(self.user), "mouse") def test_get_user_identifer_remote(self, _): - """ for a remote user, should be their full username """ + """for a remote user, should be their full username""" self.assertEqual( bookwyrm_tags.get_user_identifier(self.remote_user), "rat@example.com" ) def test_get_notification_count(self, _): - """ just countin' """ + """just countin'""" self.assertEqual(bookwyrm_tags.get_notification_count(self.user), 0) models.Notification.objects.create(user=self.user, notification_type="FAVORITE") @@ -74,7 +74,7 @@ class TemplateTags(TestCase): self.assertEqual(bookwyrm_tags.get_notification_count(self.user), 2) def test_get_replies(self, _): - """ direct replies to a status """ + """direct replies to a status""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): parent = models.Review.objects.create( user=self.user, book=self.book, content="hi" @@ -102,7 +102,7 @@ class TemplateTags(TestCase): self.assertFalse(third_child in replies) def test_get_parent(self, _): - """ get the reply parent of a status """ + """get the reply parent of a status""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): parent = models.Review.objects.create( user=self.user, book=self.book, content="hi" @@ -116,7 +116,7 @@ class TemplateTags(TestCase): self.assertIsInstance(result, models.Review) def test_get_user_liked(self, _): - """ did a user like a status """ + """did a user like a status""" status = models.Review.objects.create(user=self.remote_user, book=self.book) self.assertFalse(bookwyrm_tags.get_user_liked(self.user, status)) @@ -125,7 +125,7 @@ class TemplateTags(TestCase): self.assertTrue(bookwyrm_tags.get_user_liked(self.user, status)) def test_get_user_boosted(self, _): - """ did a user boost a status """ + """did a user boost a status""" status = models.Review.objects.create(user=self.remote_user, book=self.book) self.assertFalse(bookwyrm_tags.get_user_boosted(self.user, status)) @@ -134,7 +134,7 @@ class TemplateTags(TestCase): self.assertTrue(bookwyrm_tags.get_user_boosted(self.user, status)) def test_follow_request_exists(self, _): - """ does a user want to follow """ + """does a user want to follow""" self.assertFalse( bookwyrm_tags.follow_request_exists(self.user, self.remote_user) ) @@ -152,7 +152,7 @@ class TemplateTags(TestCase): ) def test_get_boosted(self, _): - """ load a boosted status """ + """load a boosted status""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): status = models.Review.objects.create(user=self.remote_user, book=self.book) boost = models.Boost.objects.create(user=self.user, boosted_status=status) @@ -161,7 +161,7 @@ class TemplateTags(TestCase): self.assertEqual(boosted, status) def test_get_book_description(self, _): - """ grab it from the edition or the parent """ + """grab it from the edition or the parent""" work = models.Work.objects.create(title="Test Work") self.book.parent_work = work self.book.save() @@ -177,12 +177,12 @@ class TemplateTags(TestCase): self.assertEqual(bookwyrm_tags.get_book_description(self.book), "hello") def test_get_uuid(self, _): - """ uuid functionality """ + """uuid functionality""" uuid = bookwyrm_tags.get_uuid("hi") self.assertTrue(re.match(r"hi[A-Za-z0-9\-]", uuid)) def test_get_markdown(self, _): - """ mardown format data """ + """mardown format data""" result = bookwyrm_tags.get_markdown("_hi_") self.assertEqual(result, "

hi

") @@ -190,13 +190,13 @@ class TemplateTags(TestCase): self.assertEqual(result, "

hi

") def test_get_mentions(self, _): - """ list of people mentioned """ + """list of people mentioned""" status = models.Status.objects.create(content="hi", user=self.remote_user) result = bookwyrm_tags.get_mentions(status, self.user) self.assertEqual(result, "@rat@example.com ") def test_get_status_preview_name(self, _): - """ status context string """ + """status context string""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): status = models.Status.objects.create(content="hi", user=self.user) result = bookwyrm_tags.get_status_preview_name(status) @@ -221,7 +221,7 @@ class TemplateTags(TestCase): self.assertEqual(result, "quotation from Test Book") def test_related_status(self, _): - """ gets the subclass model for a notification status """ + """gets the subclass model for a notification status""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): status = models.Status.objects.create(content="hi", user=self.user) notification = models.Notification.objects.create( diff --git a/bookwyrm/tests/views/inbox/test_inbox.py b/bookwyrm/tests/views/inbox/test_inbox.py index c39a3fd2..697f4010 100644 --- a/bookwyrm/tests/views/inbox/test_inbox.py +++ b/bookwyrm/tests/views/inbox/test_inbox.py @@ -12,10 +12,10 @@ from bookwyrm import models, views # pylint: disable=too-many-public-methods class Inbox(TestCase): - """ readthrough tests """ + """readthrough tests""" def setUp(self): - """ basic user and book data """ + """basic user and book data""" self.client = Client() self.factory = RequestFactory() local_user = models.User.objects.create_user( @@ -48,12 +48,12 @@ class Inbox(TestCase): models.SiteSettings.objects.create() def test_inbox_invalid_get(self): - """ shouldn't try to handle if the user is not found """ + """shouldn't try to handle if the user is not found""" result = self.client.get("/inbox", content_type="application/json") self.assertIsInstance(result, HttpResponseNotAllowed) def test_inbox_invalid_user(self): - """ shouldn't try to handle if the user is not found """ + """shouldn't try to handle if the user is not found""" result = self.client.post( "/user/bleh/inbox", '{"type": "Test", "object": "exists"}', @@ -62,7 +62,7 @@ class Inbox(TestCase): self.assertIsInstance(result, HttpResponseNotFound) def test_inbox_invalid_bad_signature(self): - """ bad request for invalid signature """ + """bad request for invalid signature""" with patch("bookwyrm.views.inbox.has_valid_signature") as mock_valid: mock_valid.return_value = False result = self.client.post( @@ -73,7 +73,7 @@ class Inbox(TestCase): self.assertEqual(result.status_code, 401) def test_inbox_invalid_bad_signature_delete(self): - """ invalid signature for Delete is okay though """ + """invalid signature for Delete is okay though""" with patch("bookwyrm.views.inbox.has_valid_signature") as mock_valid: mock_valid.return_value = False result = self.client.post( @@ -84,7 +84,7 @@ class Inbox(TestCase): self.assertEqual(result.status_code, 200) def test_inbox_unknown_type(self): - """ never heard of that activity type, don't have a handler for it """ + """never heard of that activity type, don't have a handler for it""" with patch("bookwyrm.views.inbox.has_valid_signature") as mock_valid: result = self.client.post( "/inbox", @@ -95,7 +95,7 @@ class Inbox(TestCase): self.assertIsInstance(result, HttpResponseNotFound) def test_inbox_success(self): - """ a known type, for which we start a task """ + """a known type, for which we start a task""" activity = self.create_json activity["object"] = { "id": "https://example.com/list/22", @@ -121,7 +121,7 @@ class Inbox(TestCase): self.assertEqual(result.status_code, 200) def test_is_blocked_user_agent(self): - """ check for blocked servers """ + """check for blocked servers""" request = self.factory.post( "", HTTP_USER_AGENT="http.rb/4.4.1 (Mastodon/3.3.0; +https://mastodon.social/)", @@ -134,7 +134,7 @@ class Inbox(TestCase): self.assertTrue(views.inbox.is_blocked_user_agent(request)) def test_is_blocked_activity(self): - """ check for blocked servers """ + """check for blocked servers""" activity = {"actor": "https://mastodon.social/user/whaatever/else"} self.assertFalse(views.inbox.is_blocked_activity(activity)) @@ -144,7 +144,7 @@ class Inbox(TestCase): self.assertTrue(views.inbox.is_blocked_activity(activity)) def test_create_by_deactivated_user(self): - """ don't let deactivated users post """ + """don't let deactivated users post""" self.remote_user.delete(broadcast=False) self.assertTrue(self.remote_user.deleted) datafile = pathlib.Path(__file__).parent.joinpath("../../data/ap_note.json") diff --git a/bookwyrm/tests/views/inbox/test_inbox_add.py b/bookwyrm/tests/views/inbox/test_inbox_add.py index a5c629a8..9f237b6d 100644 --- a/bookwyrm/tests/views/inbox/test_inbox_add.py +++ b/bookwyrm/tests/views/inbox/test_inbox_add.py @@ -9,10 +9,10 @@ from bookwyrm import models, views # pylint: disable=too-many-public-methods class InboxAdd(TestCase): - """ inbox tests """ + """inbox tests""" def setUp(self): - """ basic user and book data """ + """basic user and book data""" local_user = models.User.objects.create_user( "mouse@example.com", "mouse@mouse.com", @@ -42,7 +42,7 @@ class InboxAdd(TestCase): models.SiteSettings.objects.create() def test_handle_add_book_to_shelf(self): - """ shelving a book """ + """shelving a book""" shelf = models.Shelf.objects.create(user=self.remote_user, name="Test Shelf") shelf.remote_id = "https://bookwyrm.social/user/mouse/shelf/to-read" shelf.save() @@ -65,7 +65,7 @@ class InboxAdd(TestCase): @responses.activate def test_handle_add_book_to_list(self): - """ listing a book """ + """listing a book""" responses.add( responses.GET, "https://bookwyrm.social/user/mouse/list/to-read", diff --git a/bookwyrm/tests/views/inbox/test_inbox_announce.py b/bookwyrm/tests/views/inbox/test_inbox_announce.py index dbe4ec56..4243dc78 100644 --- a/bookwyrm/tests/views/inbox/test_inbox_announce.py +++ b/bookwyrm/tests/views/inbox/test_inbox_announce.py @@ -9,10 +9,10 @@ from bookwyrm import models, views # pylint: disable=too-many-public-methods class InboxActivities(TestCase): - """ inbox tests """ + """inbox tests""" def setUp(self): - """ basic user and book data """ + """basic user and book data""" self.local_user = models.User.objects.create_user( "mouse@example.com", "mouse@mouse.com", @@ -52,7 +52,7 @@ class InboxActivities(TestCase): @patch("bookwyrm.activitystreams.ActivityStream.add_status") def test_boost(self, redis_mock): - """ boost a status """ + """boost a status""" self.assertEqual(models.Notification.objects.count(), 0) activity = { "type": "Announce", @@ -82,7 +82,7 @@ class InboxActivities(TestCase): @responses.activate @patch("bookwyrm.activitystreams.ActivityStream.add_status") def test_boost_remote_status(self, redis_mock): - """ boost a status from a remote server """ + """boost a status from a remote server""" work = models.Work.objects.create(title="work title") book = models.Edition.objects.create( title="Test", @@ -131,7 +131,7 @@ class InboxActivities(TestCase): @responses.activate def test_discarded_boost(self): - """ test a boost of a mastodon status that will be discarded """ + """test a boost of a mastodon status that will be discarded""" status = models.Status( content="hi", user=self.remote_user, @@ -154,7 +154,7 @@ class InboxActivities(TestCase): self.assertEqual(models.Boost.objects.count(), 0) def test_unboost(self): - """ undo a boost """ + """undo a boost""" with patch("bookwyrm.activitystreams.ActivityStream.add_status"): boost = models.Boost.objects.create( boosted_status=self.status, user=self.remote_user @@ -183,7 +183,7 @@ class InboxActivities(TestCase): self.assertFalse(models.Boost.objects.exists()) def test_unboost_unknown_boost(self): - """ undo a boost """ + """undo a boost""" activity = { "type": "Undo", "actor": "hi", diff --git a/bookwyrm/tests/views/inbox/test_inbox_block.py b/bookwyrm/tests/views/inbox/test_inbox_block.py index e686c6b7..956cf538 100644 --- a/bookwyrm/tests/views/inbox/test_inbox_block.py +++ b/bookwyrm/tests/views/inbox/test_inbox_block.py @@ -8,10 +8,10 @@ from bookwyrm import models, views # pylint: disable=too-many-public-methods class InboxBlock(TestCase): - """ inbox tests """ + """inbox tests""" def setUp(self): - """ basic user and book data """ + """basic user and book data""" self.local_user = models.User.objects.create_user( "mouse@example.com", "mouse@mouse.com", @@ -35,7 +35,7 @@ class InboxBlock(TestCase): models.SiteSettings.objects.create() def test_handle_blocks(self): - """ create a "block" database entry from an activity """ + """create a "block" database entry from an activity""" self.local_user.followers.add(self.remote_user) with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): models.UserFollowRequest.objects.create( @@ -67,7 +67,7 @@ class InboxBlock(TestCase): self.assertFalse(models.UserFollowRequest.objects.exists()) def test_handle_unblock(self): - """ unblock a user """ + """unblock a user""" self.remote_user.blocks.add(self.local_user) block = models.UserBlocks.objects.get() diff --git a/bookwyrm/tests/views/inbox/test_inbox_create.py b/bookwyrm/tests/views/inbox/test_inbox_create.py index 3d2ce1c0..e7a12024 100644 --- a/bookwyrm/tests/views/inbox/test_inbox_create.py +++ b/bookwyrm/tests/views/inbox/test_inbox_create.py @@ -11,10 +11,10 @@ from bookwyrm.activitypub import ActivitySerializerError # pylint: disable=too-many-public-methods class InboxCreate(TestCase): - """ readthrough tests """ + """readthrough tests""" def setUp(self): - """ basic user and book data """ + """basic user and book data""" self.local_user = models.User.objects.create_user( "mouse@example.com", "mouse@mouse.com", @@ -53,7 +53,7 @@ class InboxCreate(TestCase): models.SiteSettings.objects.create() def test_create_status(self): - """ the "it justs works" mode """ + """the "it justs works" mode""" self.assertEqual(models.Status.objects.count(), 1) datafile = pathlib.Path(__file__).parent.joinpath( @@ -84,7 +84,7 @@ class InboxCreate(TestCase): self.assertEqual(models.Status.objects.count(), 2) def test_create_status_remote_note_with_mention(self): - """ should only create it under the right circumstances """ + """should only create it under the right circumstances""" self.assertEqual(models.Status.objects.count(), 1) self.assertFalse( models.Notification.objects.filter(user=self.local_user).exists() @@ -107,7 +107,7 @@ class InboxCreate(TestCase): self.assertEqual(models.Notification.objects.get().notification_type, "MENTION") def test_create_status_remote_note_with_reply(self): - """ should only create it under the right circumstances """ + """should only create it under the right circumstances""" self.assertEqual(models.Status.objects.count(), 1) self.assertFalse(models.Notification.objects.filter(user=self.local_user)) @@ -128,7 +128,7 @@ class InboxCreate(TestCase): self.assertEqual(models.Notification.objects.get().notification_type, "REPLY") def test_create_list(self): - """ a new list """ + """a new list""" activity = self.create_json activity["object"] = { "id": "https://example.com/list/22", @@ -152,7 +152,7 @@ class InboxCreate(TestCase): self.assertEqual(book_list.remote_id, "https://example.com/list/22") def test_create_unsupported_type(self): - """ ignore activities we know we can't handle """ + """ignore activities we know we can't handle""" activity = self.create_json activity["object"] = { "id": "https://example.com/status/887", @@ -162,7 +162,7 @@ class InboxCreate(TestCase): views.inbox.activity_task(activity) def test_create_unknown_type(self): - """ ignore activities we know we've never heard of """ + """ignore activities we know we've never heard of""" activity = self.create_json activity["object"] = { "id": "https://example.com/status/887", diff --git a/bookwyrm/tests/views/inbox/test_inbox_delete.py b/bookwyrm/tests/views/inbox/test_inbox_delete.py index 03598b88..617dcf6f 100644 --- a/bookwyrm/tests/views/inbox/test_inbox_delete.py +++ b/bookwyrm/tests/views/inbox/test_inbox_delete.py @@ -9,10 +9,10 @@ from bookwyrm import models, views # pylint: disable=too-many-public-methods class InboxActivities(TestCase): - """ inbox tests """ + """inbox tests""" def setUp(self): - """ basic user and book data """ + """basic user and book data""" self.local_user = models.User.objects.create_user( "mouse@example.com", "mouse@mouse.com", @@ -50,7 +50,7 @@ class InboxActivities(TestCase): models.SiteSettings.objects.create() def test_delete_status(self): - """ remove a status """ + """remove a status""" self.assertFalse(self.status.deleted) activity = { "type": "Delete", @@ -71,7 +71,7 @@ class InboxActivities(TestCase): self.assertIsInstance(status.deleted_date, datetime) def test_delete_status_notifications(self): - """ remove a status with related notifications """ + """remove a status with related notifications""" models.Notification.objects.create( related_status=self.status, user=self.local_user, @@ -106,7 +106,7 @@ class InboxActivities(TestCase): self.assertEqual(models.Notification.objects.get(), notif) def test_delete_user(self): - """ delete a user """ + """delete a user""" self.assertTrue(models.User.objects.get(username="rat@example.com").is_active) activity = { "@context": "https://www.w3.org/ns/activitystreams", @@ -121,7 +121,7 @@ class InboxActivities(TestCase): self.assertFalse(models.User.objects.get(username="rat@example.com").is_active) def test_delete_user_unknown(self): - """ don't worry about it if we don't know the user """ + """don't worry about it if we don't know the user""" self.assertEqual(models.User.objects.filter(is_active=True).count(), 2) activity = { "@context": "https://www.w3.org/ns/activitystreams", diff --git a/bookwyrm/tests/views/inbox/test_inbox_follow.py b/bookwyrm/tests/views/inbox/test_inbox_follow.py index b0177cb8..f5332b7a 100644 --- a/bookwyrm/tests/views/inbox/test_inbox_follow.py +++ b/bookwyrm/tests/views/inbox/test_inbox_follow.py @@ -9,10 +9,10 @@ from bookwyrm import models, views # pylint: disable=too-many-public-methods class InboxRelationships(TestCase): - """ inbox tests """ + """inbox tests""" def setUp(self): - """ basic user and book data """ + """basic user and book data""" self.local_user = models.User.objects.create_user( "mouse@example.com", "mouse@mouse.com", @@ -36,7 +36,7 @@ class InboxRelationships(TestCase): models.SiteSettings.objects.create() def test_follow(self): - """ remote user wants to follow local user """ + """remote user wants to follow local user""" activity = { "@context": "https://www.w3.org/ns/activitystreams", "id": "https://example.com/users/rat/follows/123", @@ -65,7 +65,7 @@ class InboxRelationships(TestCase): self.assertEqual(follow.user_subject, self.remote_user) def test_follow_duplicate(self): - """ remote user wants to follow local user twice """ + """remote user wants to follow local user twice""" activity = { "@context": "https://www.w3.org/ns/activitystreams", "id": "https://example.com/users/rat/follows/123", @@ -92,7 +92,7 @@ class InboxRelationships(TestCase): self.assertEqual(follow.user_subject, self.remote_user) def test_follow_manually_approved(self): - """ needs approval before following """ + """needs approval before following""" activity = { "@context": "https://www.w3.org/ns/activitystreams", "id": "https://example.com/users/rat/follows/123", @@ -122,7 +122,7 @@ class InboxRelationships(TestCase): self.assertEqual(list(follow), []) def test_undo_follow_request(self): - """ the requester cancels a follow request """ + """the requester cancels a follow request""" self.local_user.manually_approves_followers = True self.local_user.save(broadcast=False) with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): @@ -152,7 +152,7 @@ class InboxRelationships(TestCase): self.assertFalse(self.local_user.follower_requests.exists()) def test_unfollow(self): - """ remove a relationship """ + """remove a relationship""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): rel = models.UserFollows.objects.create( user_subject=self.remote_user, user_object=self.local_user @@ -177,7 +177,7 @@ class InboxRelationships(TestCase): self.assertIsNone(self.local_user.followers.first()) def test_follow_accept(self): - """ a remote user approved a follow request from local """ + """a remote user approved a follow request from local""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): rel = models.UserFollowRequest.objects.create( user_subject=self.local_user, user_object=self.remote_user @@ -208,7 +208,7 @@ class InboxRelationships(TestCase): self.assertEqual(follows.first(), self.local_user) def test_follow_reject(self): - """ turn down a follow request """ + """turn down a follow request""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): rel = models.UserFollowRequest.objects.create( user_subject=self.local_user, user_object=self.remote_user diff --git a/bookwyrm/tests/views/inbox/test_inbox_like.py b/bookwyrm/tests/views/inbox/test_inbox_like.py index 05105b75..a5f3a9f0 100644 --- a/bookwyrm/tests/views/inbox/test_inbox_like.py +++ b/bookwyrm/tests/views/inbox/test_inbox_like.py @@ -8,10 +8,10 @@ from bookwyrm import models, views # pylint: disable=too-many-public-methods class InboxActivities(TestCase): - """ inbox tests """ + """inbox tests""" def setUp(self): - """ basic user and book data """ + """basic user and book data""" self.local_user = models.User.objects.create_user( "mouse@example.com", "mouse@mouse.com", @@ -50,7 +50,7 @@ class InboxActivities(TestCase): models.SiteSettings.objects.create() def test_handle_favorite(self): - """ fav a status """ + """fav a status""" activity = { "@context": "https://www.w3.org/ns/activitystreams", "id": "https://example.com/fav/1", @@ -68,7 +68,7 @@ class InboxActivities(TestCase): self.assertEqual(fav.user, self.remote_user) def test_ignore_favorite(self): - """ don't try to save an unknown status """ + """don't try to save an unknown status""" activity = { "@context": "https://www.w3.org/ns/activitystreams", "id": "https://example.com/fav/1", @@ -83,7 +83,7 @@ class InboxActivities(TestCase): self.assertFalse(models.Favorite.objects.exists()) def test_handle_unfavorite(self): - """ fav a status """ + """fav a status""" activity = { "id": "https://example.com/fav/1#undo", "type": "Undo", diff --git a/bookwyrm/tests/views/inbox/test_inbox_remove.py b/bookwyrm/tests/views/inbox/test_inbox_remove.py index 8ac8740a..a0c4cdcf 100644 --- a/bookwyrm/tests/views/inbox/test_inbox_remove.py +++ b/bookwyrm/tests/views/inbox/test_inbox_remove.py @@ -8,10 +8,10 @@ from bookwyrm import models, views # pylint: disable=too-many-public-methods class InboxRemove(TestCase): - """ inbox tests """ + """inbox tests""" def setUp(self): - """ basic user and book data """ + """basic user and book data""" self.local_user = models.User.objects.create_user( "mouse@example.com", "mouse@mouse.com", @@ -41,7 +41,7 @@ class InboxRemove(TestCase): models.SiteSettings.objects.create() def test_handle_unshelve_book(self): - """ remove a book from a shelf """ + """remove a book from a shelf""" shelf = models.Shelf.objects.create(user=self.remote_user, name="Test Shelf") shelf.remote_id = "https://bookwyrm.social/user/mouse/shelf/to-read" shelf.save() @@ -70,7 +70,7 @@ class InboxRemove(TestCase): self.assertFalse(shelf.books.exists()) def test_handle_remove_book_from_list(self): - """ listing a book """ + """listing a book""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): booklist = models.List.objects.create( name="test list", diff --git a/bookwyrm/tests/views/inbox/test_inbox_update.py b/bookwyrm/tests/views/inbox/test_inbox_update.py index 5681ec88..9fdc9792 100644 --- a/bookwyrm/tests/views/inbox/test_inbox_update.py +++ b/bookwyrm/tests/views/inbox/test_inbox_update.py @@ -10,10 +10,10 @@ from bookwyrm import models, views # pylint: disable=too-many-public-methods class InboxUpdate(TestCase): - """ inbox tests """ + """inbox tests""" def setUp(self): - """ basic user and book data """ + """basic user and book data""" self.local_user = models.User.objects.create_user( "mouse@example.com", "mouse@mouse.com", @@ -45,7 +45,7 @@ class InboxUpdate(TestCase): models.SiteSettings.objects.create() def test_update_list(self): - """ a new list """ + """a new list""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): book_list = models.List.objects.create( name="hi", remote_id="https://example.com/list/22", user=self.local_user @@ -79,7 +79,7 @@ class InboxUpdate(TestCase): self.assertEqual(book_list.remote_id, "https://example.com/list/22") def test_update_user(self): - """ update an existing user """ + """update an existing user""" models.UserFollows.objects.create( user_subject=self.local_user, user_object=self.remote_user, @@ -116,7 +116,7 @@ class InboxUpdate(TestCase): self.assertTrue(self.local_user in self.remote_user.followers.all()) def test_update_edition(self): - """ update an existing edition """ + """update an existing edition""" datafile = pathlib.Path(__file__).parent.joinpath("../../data/bw_edition.json") bookdata = json.loads(datafile.read_bytes()) @@ -146,7 +146,7 @@ class InboxUpdate(TestCase): self.assertEqual(book.last_edited_by, self.remote_user) def test_update_work(self): - """ update an existing edition """ + """update an existing edition""" datafile = pathlib.Path(__file__).parent.joinpath("../../data/bw_work.json") bookdata = json.loads(datafile.read_bytes()) diff --git a/bookwyrm/tests/views/test_authentication.py b/bookwyrm/tests/views/test_authentication.py index f6d31861..c310b0a2 100644 --- a/bookwyrm/tests/views/test_authentication.py +++ b/bookwyrm/tests/views/test_authentication.py @@ -14,10 +14,10 @@ from bookwyrm.settings import DOMAIN # pylint: disable=too-many-public-methods class AuthenticationViews(TestCase): - """ login and password management """ + """login and password management""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -31,7 +31,7 @@ class AuthenticationViews(TestCase): self.settings = models.SiteSettings.objects.create(id=1) def test_login_get(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" login = views.Login.as_view() request = self.factory.get("") request.user = self.anonymous_user @@ -47,7 +47,7 @@ class AuthenticationViews(TestCase): self.assertEqual(result.status_code, 302) def test_register(self): - """ create a user """ + """create a user""" view = views.Register.as_view() self.assertEqual(models.User.objects.count(), 1) request = self.factory.post( @@ -68,7 +68,7 @@ class AuthenticationViews(TestCase): self.assertEqual(nutria.local, True) def test_register_trailing_space(self): - """ django handles this so weirdly """ + """django handles this so weirdly""" view = views.Register.as_view() request = self.factory.post( "register/", @@ -84,7 +84,7 @@ class AuthenticationViews(TestCase): self.assertEqual(nutria.local, True) def test_register_invalid_email(self): - """ gotta have an email """ + """gotta have an email""" view = views.Register.as_view() self.assertEqual(models.User.objects.count(), 1) request = self.factory.post( @@ -95,7 +95,7 @@ class AuthenticationViews(TestCase): response.render() def test_register_invalid_username(self): - """ gotta have an email """ + """gotta have an email""" view = views.Register.as_view() self.assertEqual(models.User.objects.count(), 1) request = self.factory.post( @@ -123,7 +123,7 @@ class AuthenticationViews(TestCase): response.render() def test_register_closed_instance(self): - """ you can't just register """ + """you can't just register""" view = views.Register.as_view() self.settings.allow_registration = False self.settings.save() @@ -135,7 +135,7 @@ class AuthenticationViews(TestCase): view(request) def test_register_invite(self): - """ you can't just register """ + """you can't just register""" view = views.Register.as_view() self.settings.allow_registration = False self.settings.save() diff --git a/bookwyrm/tests/views/test_author.py b/bookwyrm/tests/views/test_author.py index bb047b7c..5dfbc350 100644 --- a/bookwyrm/tests/views/test_author.py +++ b/bookwyrm/tests/views/test_author.py @@ -12,10 +12,10 @@ from bookwyrm.activitypub import ActivitypubResponse class AuthorViews(TestCase): - """ author views""" + """author views""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -42,7 +42,7 @@ class AuthorViews(TestCase): models.SiteSettings.objects.create() def test_author_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Author.as_view() author = models.Author.objects.create(name="Jessica") request = self.factory.get("") @@ -62,7 +62,7 @@ class AuthorViews(TestCase): self.assertEqual(result.status_code, 200) def test_edit_author_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.EditAuthor.as_view() author = models.Author.objects.create(name="Test Author") request = self.factory.get("") @@ -76,7 +76,7 @@ class AuthorViews(TestCase): self.assertEqual(result.status_code, 200) def test_edit_author(self): - """ edit an author """ + """edit an author""" view = views.EditAuthor.as_view() author = models.Author.objects.create(name="Test Author") self.local_user.groups.add(self.group) @@ -93,7 +93,7 @@ class AuthorViews(TestCase): self.assertEqual(author.last_edited_by, self.local_user) def test_edit_author_non_editor(self): - """ edit an author with invalid post data""" + """edit an author with invalid post data""" view = views.EditAuthor.as_view() author = models.Author.objects.create(name="Test Author") form = forms.AuthorForm(instance=author) @@ -108,7 +108,7 @@ class AuthorViews(TestCase): self.assertEqual(author.name, "Test Author") def test_edit_author_invalid_form(self): - """ edit an author with invalid post data""" + """edit an author with invalid post data""" view = views.EditAuthor.as_view() author = models.Author.objects.create(name="Test Author") self.local_user.groups.add(self.group) diff --git a/bookwyrm/tests/views/test_block.py b/bookwyrm/tests/views/test_block.py index 71583d70..0b754689 100644 --- a/bookwyrm/tests/views/test_block.py +++ b/bookwyrm/tests/views/test_block.py @@ -9,10 +9,10 @@ from bookwyrm import models, views @patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay") class BlockViews(TestCase): - """ view user and edit profile """ + """view user and edit profile""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -34,7 +34,7 @@ class BlockViews(TestCase): models.SiteSettings.objects.create() def test_block_get(self, _): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Block.as_view() request = self.factory.get("") request.user = self.local_user @@ -44,7 +44,7 @@ class BlockViews(TestCase): self.assertEqual(result.status_code, 200) def test_block_post(self, _): - """ create a "block" database entry from an activity """ + """create a "block" database entry from an activity""" view = views.Block.as_view() self.local_user.followers.add(self.remote_user) models.UserFollowRequest.objects.create( @@ -65,7 +65,7 @@ class BlockViews(TestCase): self.assertFalse(models.UserFollowRequest.objects.exists()) def test_unblock(self, _): - """ undo a block """ + """undo a block""" self.local_user.blocks.add(self.remote_user) request = self.factory.post("") request.user = self.local_user diff --git a/bookwyrm/tests/views/test_book.py b/bookwyrm/tests/views/test_book.py index a0fa0367..dce50868 100644 --- a/bookwyrm/tests/views/test_book.py +++ b/bookwyrm/tests/views/test_book.py @@ -18,10 +18,10 @@ from bookwyrm.activitypub import ActivitypubResponse class BookViews(TestCase): - """ books books books """ + """books books books""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -81,7 +81,7 @@ class BookViews(TestCase): ) def test_book_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Book.as_view() request = self.factory.get("") request.user = self.local_user @@ -100,7 +100,7 @@ class BookViews(TestCase): self.assertEqual(result.status_code, 200) def test_edit_book_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.EditBook.as_view() request = self.factory.get("") request.user = self.local_user @@ -111,7 +111,7 @@ class BookViews(TestCase): self.assertEqual(result.status_code, 200) def test_edit_book(self): - """ lets a user edit a book """ + """lets a user edit a book""" view = views.EditBook.as_view() self.local_user.groups.add(self.group) form = forms.EditionForm(instance=self.book) @@ -125,7 +125,7 @@ class BookViews(TestCase): self.assertEqual(self.book.title, "New Title") def test_edit_book_add_author(self): - """ lets a user edit a book with new authors """ + """lets a user edit a book with new authors""" view = views.EditBook.as_view() self.local_user.groups.add(self.group) form = forms.EditionForm(instance=self.book) @@ -143,7 +143,7 @@ class BookViews(TestCase): self.assertEqual(self.book.title, "Example Edition") def test_edit_book_add_new_author_confirm(self): - """ lets a user edit a book confirmed with new authors """ + """lets a user edit a book confirmed with new authors""" view = views.ConfirmEditBook.as_view() self.local_user.groups.add(self.group) form = forms.EditionForm(instance=self.book) @@ -162,7 +162,7 @@ class BookViews(TestCase): self.assertEqual(self.book.authors.first().name, "Sappho") def test_edit_book_remove_author(self): - """ remove an author from a book """ + """remove an author from a book""" author = models.Author.objects.create(name="Sappho") self.book.authors.add(author) form = forms.EditionForm(instance=self.book) @@ -182,7 +182,7 @@ class BookViews(TestCase): self.assertFalse(self.book.authors.exists()) def test_create_book(self): - """ create an entirely new book and work """ + """create an entirely new book and work""" view = views.ConfirmEditBook.as_view() self.local_user.groups.add(self.group) form = forms.EditionForm() @@ -196,7 +196,7 @@ class BookViews(TestCase): self.assertEqual(book.parent_work.title, "New Title") def test_create_book_existing_work(self): - """ create an entirely new book and work """ + """create an entirely new book and work""" view = views.ConfirmEditBook.as_view() self.local_user.groups.add(self.group) form = forms.EditionForm() @@ -211,7 +211,7 @@ class BookViews(TestCase): self.assertEqual(book.parent_work, self.work) def test_create_book_with_author(self): - """ create an entirely new book and work """ + """create an entirely new book and work""" view = views.ConfirmEditBook.as_view() self.local_user.groups.add(self.group) form = forms.EditionForm() @@ -229,7 +229,7 @@ class BookViews(TestCase): self.assertEqual(book.authors.first(), book.parent_work.authors.first()) def test_switch_edition(self): - """ updates user's relationships to a book """ + """updates user's relationships to a book""" work = models.Work.objects.create(title="test work") edition1 = models.Edition.objects.create(title="first ed", parent_work=work) edition2 = models.Edition.objects.create(title="second ed", parent_work=work) @@ -253,7 +253,7 @@ class BookViews(TestCase): self.assertEqual(models.ReadThrough.objects.get().book, edition2) def test_editions_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Editions.as_view() request = self.factory.get("") with patch("bookwyrm.views.books.is_api_request") as is_api: @@ -271,7 +271,7 @@ class BookViews(TestCase): self.assertEqual(result.status_code, 200) def test_upload_cover_file(self): - """ add a cover via file upload """ + """add a cover via file upload""" self.assertFalse(self.book.cover) image_file = pathlib.Path(__file__).parent.joinpath( "../../static/images/default_avi.jpg" @@ -296,7 +296,7 @@ class BookViews(TestCase): @responses.activate def test_upload_cover_url(self): - """ add a cover via url """ + """add a cover via url""" self.assertFalse(self.book.cover) image_file = pathlib.Path(__file__).parent.joinpath( "../../static/images/default_avi.jpg" diff --git a/bookwyrm/tests/views/test_directory.py b/bookwyrm/tests/views/test_directory.py index 80d9eaf7..cada50bc 100644 --- a/bookwyrm/tests/views/test_directory.py +++ b/bookwyrm/tests/views/test_directory.py @@ -7,10 +7,10 @@ from bookwyrm import models, views # pylint: disable=unused-argument class DirectoryViews(TestCase): - """ tag views""" + """tag views""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -32,7 +32,7 @@ class DirectoryViews(TestCase): models.SiteSettings.objects.create() def test_directory_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Directory.as_view() request = self.factory.get("") request.user = self.local_user diff --git a/bookwyrm/tests/views/test_federation.py b/bookwyrm/tests/views/test_federation.py index 2afdd6d3..f17f7624 100644 --- a/bookwyrm/tests/views/test_federation.py +++ b/bookwyrm/tests/views/test_federation.py @@ -10,10 +10,10 @@ from bookwyrm import forms, models, views class FederationViews(TestCase): - """ every response to a get request, html or json """ + """every response to a get request, html or json""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -35,7 +35,7 @@ class FederationViews(TestCase): models.SiteSettings.objects.create() def test_federation_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Federation.as_view() request = self.factory.get("") request.user = self.local_user @@ -46,7 +46,7 @@ class FederationViews(TestCase): self.assertEqual(result.status_code, 200) def test_server_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" server = models.FederatedServer.objects.create(server_name="hi.there.com") view = views.FederatedServer.as_view() request = self.factory.get("") @@ -59,7 +59,7 @@ class FederationViews(TestCase): self.assertEqual(result.status_code, 200) def test_server_page_block(self): - """ block a server """ + """block a server""" server = models.FederatedServer.objects.create(server_name="hi.there.com") self.remote_user.federated_server = server self.remote_user.save() @@ -79,7 +79,7 @@ class FederationViews(TestCase): self.assertFalse(self.remote_user.is_active) def test_server_page_unblock(self): - """ unblock a server """ + """unblock a server""" server = models.FederatedServer.objects.create( server_name="hi.there.com", status="blocked" ) @@ -100,7 +100,7 @@ class FederationViews(TestCase): self.assertTrue(self.remote_user.is_active) def test_add_view_get(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" # create mode view = views.AddFederatedServer.as_view() request = self.factory.get("") @@ -113,7 +113,7 @@ class FederationViews(TestCase): self.assertEqual(result.status_code, 200) def test_add_view_post_create(self): - """ create a server entry """ + """create a server entry""" form = forms.ServerForm() form.data["server_name"] = "remote.server" form.data["application_type"] = "coolsoft" @@ -131,7 +131,7 @@ class FederationViews(TestCase): self.assertEqual(server.status, "blocked") def test_import_blocklist(self): - """ load a json file with a list of servers to block """ + """load a json file with a list of servers to block""" server = models.FederatedServer.objects.create(server_name="hi.there.com") self.remote_user.federated_server = server self.remote_user.save() diff --git a/bookwyrm/tests/views/test_feed.py b/bookwyrm/tests/views/test_feed.py index dd38a3eb..a6a3d967 100644 --- a/bookwyrm/tests/views/test_feed.py +++ b/bookwyrm/tests/views/test_feed.py @@ -17,10 +17,10 @@ from bookwyrm.activitypub import ActivitypubResponse @patch("bookwyrm.activitystreams.ActivityStream.get_activity_stream") @patch("bookwyrm.activitystreams.ActivityStream.add_status") class FeedViews(TestCase): - """ activity feed, statuses, dms """ + """activity feed, statuses, dms""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -37,7 +37,7 @@ class FeedViews(TestCase): models.SiteSettings.objects.create() def test_feed(self, *_): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Feed.as_view() request = self.factory.get("") request.user = self.local_user @@ -47,7 +47,7 @@ class FeedViews(TestCase): self.assertEqual(result.status_code, 200) def test_status_page(self, *_): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Status.as_view() with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): status = models.Status.objects.create(content="hi", user=self.local_user) @@ -67,7 +67,7 @@ class FeedViews(TestCase): self.assertEqual(result.status_code, 200) def test_status_page_not_found(self, *_): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Status.as_view() request = self.factory.get("") @@ -79,7 +79,7 @@ class FeedViews(TestCase): self.assertEqual(result.status_code, 404) def test_status_page_with_image(self, *_): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Status.as_view() image_file = pathlib.Path(__file__).parent.joinpath( @@ -115,7 +115,7 @@ class FeedViews(TestCase): self.assertEqual(result.status_code, 200) def test_replies_page(self, *_): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Replies.as_view() with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): status = models.Status.objects.create(content="hi", user=self.local_user) @@ -135,7 +135,7 @@ class FeedViews(TestCase): self.assertEqual(result.status_code, 200) def test_direct_messages_page(self, *_): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.DirectMessage.as_view() request = self.factory.get("") request.user = self.local_user @@ -145,7 +145,7 @@ class FeedViews(TestCase): self.assertEqual(result.status_code, 200) def test_get_suggested_book(self, *_): - """ gets books the ~*~ algorithm ~*~ thinks you want to post about """ + """gets books the ~*~ algorithm ~*~ thinks you want to post about""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): models.ShelfBook.objects.create( book=self.book, diff --git a/bookwyrm/tests/views/test_follow.py b/bookwyrm/tests/views/test_follow.py index 6b4de05d..45e60d3c 100644 --- a/bookwyrm/tests/views/test_follow.py +++ b/bookwyrm/tests/views/test_follow.py @@ -11,10 +11,10 @@ from bookwyrm import models, views class BookViews(TestCase): - """ books books books """ + """books books books""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -50,7 +50,7 @@ class BookViews(TestCase): ) def test_handle_follow_remote(self): - """ send a follow request """ + """send a follow request""" request = self.factory.post("", {"user": self.remote_user.username}) request.user = self.local_user self.assertEqual(models.UserFollowRequest.objects.count(), 0) @@ -65,7 +65,7 @@ class BookViews(TestCase): self.assertEqual(rel.status, "follow_request") def test_handle_follow_local_manually_approves(self): - """ send a follow request """ + """send a follow request""" rat = models.User.objects.create_user( "rat@local.com", "rat@rat.com", @@ -88,7 +88,7 @@ class BookViews(TestCase): self.assertEqual(rel.status, "follow_request") def test_handle_follow_local(self): - """ send a follow request """ + """send a follow request""" rat = models.User.objects.create_user( "rat@local.com", "rat@rat.com", @@ -111,7 +111,7 @@ class BookViews(TestCase): self.assertEqual(rel.status, "follows") def test_handle_unfollow(self): - """ send an unfollow """ + """send an unfollow""" request = self.factory.post("", {"user": self.remote_user.username}) request.user = self.local_user self.remote_user.followers.add(self.local_user) @@ -125,7 +125,7 @@ class BookViews(TestCase): self.assertEqual(self.remote_user.followers.count(), 0) def test_handle_accept(self): - """ accept a follow request """ + """accept a follow request""" self.local_user.manually_approves_followers = True self.local_user.save(broadcast=False) request = self.factory.post("", {"user": self.remote_user.username}) @@ -142,7 +142,7 @@ class BookViews(TestCase): self.assertEqual(self.local_user.followers.first(), self.remote_user) def test_handle_reject(self): - """ reject a follow request """ + """reject a follow request""" self.local_user.manually_approves_followers = True self.local_user.save(broadcast=False) request = self.factory.post("", {"user": self.remote_user.username}) diff --git a/bookwyrm/tests/views/test_get_started.py b/bookwyrm/tests/views/test_get_started.py index 71eb4060..1c55da08 100644 --- a/bookwyrm/tests/views/test_get_started.py +++ b/bookwyrm/tests/views/test_get_started.py @@ -8,10 +8,10 @@ from bookwyrm import forms, models, views class GetStartedViews(TestCase): - """ helping new users get oriented """ + """helping new users get oriented""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -31,7 +31,7 @@ class GetStartedViews(TestCase): models.SiteSettings.objects.create() def test_profile_view(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.GetStartedProfile.as_view() request = self.factory.get("") request.user = self.local_user @@ -43,7 +43,7 @@ class GetStartedViews(TestCase): self.assertEqual(result.status_code, 200) def test_profile_view_post(self): - """ save basic user details """ + """save basic user details""" view = views.GetStartedProfile.as_view() form = forms.LimitedEditUserForm(instance=self.local_user) form.data["name"] = "New Name" @@ -61,7 +61,7 @@ class GetStartedViews(TestCase): self.assertTrue(self.local_user.discoverable) def test_books_view(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.GetStartedBooks.as_view() request = self.factory.get("") request.user = self.local_user @@ -73,7 +73,7 @@ class GetStartedViews(TestCase): self.assertEqual(result.status_code, 200) def test_books_view_with_query(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.GetStartedBooks.as_view() request = self.factory.get("?query=Example") request.user = self.local_user @@ -85,7 +85,7 @@ class GetStartedViews(TestCase): self.assertEqual(result.status_code, 200) def test_books_view_post(self): - """ shelve some books """ + """shelve some books""" view = views.GetStartedBooks.as_view() data = {self.book.id: self.local_user.shelf_set.first().id} request = self.factory.post("", data) @@ -103,7 +103,7 @@ class GetStartedViews(TestCase): self.assertEqual(shelfbook.user, self.local_user) def test_users_view(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.GetStartedUsers.as_view() request = self.factory.get("") request.user = self.local_user @@ -115,7 +115,7 @@ class GetStartedViews(TestCase): self.assertEqual(result.status_code, 200) def test_users_view_with_query(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.GetStartedUsers.as_view() request = self.factory.get("?query=rat") request.user = self.local_user diff --git a/bookwyrm/tests/views/test_goal.py b/bookwyrm/tests/views/test_goal.py index cbe4fe01..4e8f6ee2 100644 --- a/bookwyrm/tests/views/test_goal.py +++ b/bookwyrm/tests/views/test_goal.py @@ -11,10 +11,10 @@ from bookwyrm import models, views class GoalViews(TestCase): - """ viewing and creating statuses """ + """viewing and creating statuses""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -41,7 +41,7 @@ class GoalViews(TestCase): models.SiteSettings.objects.create() def test_goal_page_no_goal(self): - """ view a reading goal page for another's unset goal """ + """view a reading goal page for another's unset goal""" view = views.Goal.as_view() request = self.factory.get("") request.user = self.rat @@ -50,7 +50,7 @@ class GoalViews(TestCase): self.assertEqual(result.status_code, 404) def test_goal_page_no_goal_self(self): - """ view a reading goal page for your own unset goal """ + """view a reading goal page for your own unset goal""" view = views.Goal.as_view() request = self.factory.get("") request.user = self.local_user @@ -60,7 +60,7 @@ class GoalViews(TestCase): self.assertIsInstance(result, TemplateResponse) def test_goal_page_anonymous(self): - """ can't view it without login """ + """can't view it without login""" view = views.Goal.as_view() request = self.factory.get("") request.user = self.anonymous_user @@ -69,7 +69,7 @@ class GoalViews(TestCase): self.assertEqual(result.status_code, 302) def test_goal_page_public(self): - """ view a user's public goal """ + """view a user's public goal""" models.ReadThrough.objects.create( finish_date=timezone.now(), user=self.local_user, @@ -91,7 +91,7 @@ class GoalViews(TestCase): self.assertIsInstance(result, TemplateResponse) def test_goal_page_private(self): - """ view a user's private goal """ + """view a user's private goal""" models.AnnualGoal.objects.create( user=self.local_user, year=2020, goal=15, privacy="followers" ) @@ -104,7 +104,7 @@ class GoalViews(TestCase): @patch("bookwyrm.activitystreams.ActivityStream.add_status") def test_create_goal(self, _): - """ create a new goal """ + """create a new goal""" view = views.Goal.as_view() request = self.factory.post( "", diff --git a/bookwyrm/tests/views/test_helpers.py b/bookwyrm/tests/views/test_helpers.py index 2e5ed82d..e2e041e9 100644 --- a/bookwyrm/tests/views/test_helpers.py +++ b/bookwyrm/tests/views/test_helpers.py @@ -13,10 +13,10 @@ from bookwyrm.settings import USER_AGENT @patch("bookwyrm.activitystreams.ActivityStream.add_status") class ViewsHelpers(TestCase): - """ viewing and creating statuses """ + """viewing and creating statuses""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -53,12 +53,12 @@ class ViewsHelpers(TestCase): ) def test_get_edition(self, _): - """ given an edition or a work, returns an edition """ + """given an edition or a work, returns an edition""" self.assertEqual(views.helpers.get_edition(self.book.id), self.book) self.assertEqual(views.helpers.get_edition(self.work.id), self.book) def test_get_user_from_username(self, _): - """ works for either localname or username """ + """works for either localname or username""" self.assertEqual( views.helpers.get_user_from_username(self.local_user, "mouse"), self.local_user, @@ -71,7 +71,7 @@ class ViewsHelpers(TestCase): views.helpers.get_user_from_username(self.local_user, "mojfse@example.com") def test_is_api_request(self, _): - """ should it return html or json """ + """should it return html or json""" request = self.factory.get("/path") request.headers = {"Accept": "application/json"} self.assertTrue(views.helpers.is_api_request(request)) @@ -85,12 +85,12 @@ class ViewsHelpers(TestCase): self.assertFalse(views.helpers.is_api_request(request)) def test_is_api_request_no_headers(self, _): - """ should it return html or json """ + """should it return html or json""" request = self.factory.get("/path") self.assertFalse(views.helpers.is_api_request(request)) def test_is_bookwyrm_request(self, _): - """ checks if a request came from a bookwyrm instance """ + """checks if a request came from a bookwyrm instance""" request = self.factory.get("", {"q": "Test Book"}) self.assertFalse(views.helpers.is_bookwyrm_request(request)) @@ -105,7 +105,7 @@ class ViewsHelpers(TestCase): self.assertTrue(views.helpers.is_bookwyrm_request(request)) def test_existing_user(self, _): - """ simple database lookup by username """ + """simple database lookup by username""" result = views.helpers.handle_remote_webfinger("@mouse@local.com") self.assertEqual(result, self.local_user) @@ -117,7 +117,7 @@ class ViewsHelpers(TestCase): @responses.activate def test_load_user(self, _): - """ find a remote user using webfinger """ + """find a remote user using webfinger""" username = "mouse@example.com" wellknown = { "subject": "acct:mouse@example.com", @@ -147,7 +147,7 @@ class ViewsHelpers(TestCase): self.assertEqual(result.username, "mouse@example.com") def test_user_on_blocked_server(self, _): - """ find a remote user using webfinger """ + """find a remote user using webfinger""" models.FederatedServer.objects.create( server_name="example.com", status="blocked" ) @@ -156,7 +156,7 @@ class ViewsHelpers(TestCase): self.assertIsNone(result) def test_handle_reading_status_to_read(self, _): - """ posts shelve activities """ + """posts shelve activities""" shelf = self.local_user.shelf_set.get(identifier="to-read") with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): views.helpers.handle_reading_status( @@ -168,7 +168,7 @@ class ViewsHelpers(TestCase): self.assertEqual(status.content, "wants to read") def test_handle_reading_status_reading(self, _): - """ posts shelve activities """ + """posts shelve activities""" shelf = self.local_user.shelf_set.get(identifier="reading") with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): views.helpers.handle_reading_status( @@ -180,7 +180,7 @@ class ViewsHelpers(TestCase): self.assertEqual(status.content, "started reading") def test_handle_reading_status_read(self, _): - """ posts shelve activities """ + """posts shelve activities""" shelf = self.local_user.shelf_set.get(identifier="read") with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): views.helpers.handle_reading_status( @@ -192,7 +192,7 @@ class ViewsHelpers(TestCase): self.assertEqual(status.content, "finished reading") def test_handle_reading_status_other(self, _): - """ posts shelve activities """ + """posts shelve activities""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): views.helpers.handle_reading_status( self.local_user, self.shelf, self.book, "public" @@ -200,7 +200,7 @@ class ViewsHelpers(TestCase): self.assertFalse(models.GeneratedNote.objects.exists()) def test_get_annotated_users(self, _): - """ list of people you might know """ + """list of people you might know""" user_1 = models.User.objects.create_user( "nutria@local.com", "nutria@nutria.com", @@ -247,7 +247,7 @@ class ViewsHelpers(TestCase): self.assertEqual(remote_user_annotated.shared_books, 0) def test_get_annotated_users_counts(self, _): - """ correct counting for multiple shared attributed """ + """correct counting for multiple shared attributed""" user_1 = models.User.objects.create_user( "nutria@local.com", "nutria@nutria.com", diff --git a/bookwyrm/tests/views/test_import.py b/bookwyrm/tests/views/test_import.py index 4de2cfb9..22694623 100644 --- a/bookwyrm/tests/views/test_import.py +++ b/bookwyrm/tests/views/test_import.py @@ -9,10 +9,10 @@ from bookwyrm import views class ImportViews(TestCase): - """ goodreads import views """ + """goodreads import views""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -24,7 +24,7 @@ class ImportViews(TestCase): models.SiteSettings.objects.create() def test_import_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Import.as_view() request = self.factory.get("") request.user = self.local_user @@ -34,7 +34,7 @@ class ImportViews(TestCase): self.assertEqual(result.status_code, 200) def test_import_status(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.ImportStatus.as_view() import_job = models.ImportJob.objects.create(user=self.local_user) request = self.factory.get("") @@ -47,7 +47,7 @@ class ImportViews(TestCase): self.assertEqual(result.status_code, 200) def test_retry_import(self): - """ retry failed items """ + """retry failed items""" view = views.ImportStatus.as_view() import_job = models.ImportJob.objects.create( user=self.local_user, privacy="unlisted" diff --git a/bookwyrm/tests/views/test_interaction.py b/bookwyrm/tests/views/test_interaction.py index f767edfa..876d6053 100644 --- a/bookwyrm/tests/views/test_interaction.py +++ b/bookwyrm/tests/views/test_interaction.py @@ -9,10 +9,10 @@ from bookwyrm import models, views @patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay") class InteractionViews(TestCase): - """ viewing and creating statuses """ + """viewing and creating statuses""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -41,7 +41,7 @@ class InteractionViews(TestCase): ) def test_favorite(self, _): - """ create and broadcast faving a status """ + """create and broadcast faving a status""" view = views.Favorite.as_view() request = self.factory.post("") request.user = self.remote_user @@ -59,7 +59,7 @@ class InteractionViews(TestCase): self.assertEqual(notification.related_user, self.remote_user) def test_unfavorite(self, _): - """ unfav a status """ + """unfav a status""" view = views.Unfavorite.as_view() request = self.factory.post("") request.user = self.remote_user @@ -76,7 +76,7 @@ class InteractionViews(TestCase): self.assertEqual(models.Notification.objects.count(), 0) def test_boost(self, _): - """ boost a status """ + """boost a status""" view = views.Boost.as_view() request = self.factory.post("") request.user = self.remote_user @@ -98,7 +98,7 @@ class InteractionViews(TestCase): self.assertEqual(notification.related_status, status) def test_self_boost(self, _): - """ boost your own status """ + """boost your own status""" view = views.Boost.as_view() request = self.factory.post("") request.user = self.local_user @@ -122,7 +122,7 @@ class InteractionViews(TestCase): self.assertFalse(models.Notification.objects.exists()) def test_boost_unlisted(self, _): - """ boost a status """ + """boost a status""" view = views.Boost.as_view() request = self.factory.post("") request.user = self.local_user @@ -137,7 +137,7 @@ class InteractionViews(TestCase): self.assertEqual(boost.privacy, "unlisted") def test_boost_private(self, _): - """ boost a status """ + """boost a status""" view = views.Boost.as_view() request = self.factory.post("") request.user = self.local_user @@ -150,7 +150,7 @@ class InteractionViews(TestCase): self.assertFalse(models.Boost.objects.exists()) def test_boost_twice(self, _): - """ boost a status """ + """boost a status""" view = views.Boost.as_view() request = self.factory.post("") request.user = self.local_user @@ -162,7 +162,7 @@ class InteractionViews(TestCase): self.assertEqual(models.Boost.objects.count(), 1) def test_unboost(self, _): - """ undo a boost """ + """undo a boost""" view = views.Unboost.as_view() request = self.factory.post("") request.user = self.remote_user diff --git a/bookwyrm/tests/views/test_invite.py b/bookwyrm/tests/views/test_invite.py index 7bfc8fe5..7b5071b3 100644 --- a/bookwyrm/tests/views/test_invite.py +++ b/bookwyrm/tests/views/test_invite.py @@ -11,10 +11,10 @@ from bookwyrm import views class InviteViews(TestCase): - """ every response to a get request, html or json """ + """every response to a get request, html or json""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -26,7 +26,7 @@ class InviteViews(TestCase): models.SiteSettings.objects.create() def test_invite_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Invite.as_view() models.SiteInvite.objects.create(code="hi", user=self.local_user) request = self.factory.get("") @@ -41,7 +41,7 @@ class InviteViews(TestCase): self.assertEqual(result.status_code, 200) def test_manage_invites(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.ManageInvites.as_view() request = self.factory.get("") request.user = self.local_user @@ -52,7 +52,7 @@ class InviteViews(TestCase): self.assertEqual(result.status_code, 200) def test_invite_request(self): - """ request to join a server """ + """request to join a server""" form = forms.InviteRequestForm() form.data["email"] = "new@user.email" @@ -66,7 +66,7 @@ class InviteViews(TestCase): self.assertEqual(req.email, "new@user.email") def test_invite_request_email_taken(self): - """ request to join a server with an existing user email """ + """request to join a server with an existing user email""" form = forms.InviteRequestForm() form.data["email"] = "mouse@mouse.mouse" @@ -80,7 +80,7 @@ class InviteViews(TestCase): self.assertFalse(models.InviteRequest.objects.exists()) def test_manage_invite_requests(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.ManageInviteRequests.as_view() request = self.factory.get("") request.user = self.local_user @@ -98,7 +98,7 @@ class InviteViews(TestCase): self.assertEqual(result.status_code, 200) def test_manage_invite_requests_send(self): - """ send an invite """ + """send an invite""" req = models.InviteRequest.objects.create(email="fish@example.com") view = views.ManageInviteRequests.as_view() @@ -113,7 +113,7 @@ class InviteViews(TestCase): self.assertIsNotNone(req.invite) def test_ignore_invite_request(self): - """ don't invite that jerk """ + """don't invite that jerk""" req = models.InviteRequest.objects.create(email="fish@example.com") view = views.ignore_invite_request diff --git a/bookwyrm/tests/views/test_isbn.py b/bookwyrm/tests/views/test_isbn.py index 7f03a610..2aedd3ce 100644 --- a/bookwyrm/tests/views/test_isbn.py +++ b/bookwyrm/tests/views/test_isbn.py @@ -11,10 +11,10 @@ from bookwyrm.settings import DOMAIN class IsbnViews(TestCase): - """ tag views""" + """tag views""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -37,7 +37,7 @@ class IsbnViews(TestCase): models.SiteSettings.objects.create() def test_isbn_json_response(self): - """ searches local data only and returns book data in json format """ + """searches local data only and returns book data in json format""" view = views.Isbn.as_view() request = self.factory.get("") with patch("bookwyrm.views.isbn.is_api_request") as is_api: diff --git a/bookwyrm/tests/views/test_landing.py b/bookwyrm/tests/views/test_landing.py index 2513fecc..864e48f7 100644 --- a/bookwyrm/tests/views/test_landing.py +++ b/bookwyrm/tests/views/test_landing.py @@ -10,10 +10,10 @@ from bookwyrm import views class LandingViews(TestCase): - """ pages you land on without really trying """ + """pages you land on without really trying""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -27,7 +27,7 @@ class LandingViews(TestCase): models.SiteSettings.objects.create() def test_home_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Home.as_view() request = self.factory.get("") request.user = self.local_user @@ -43,7 +43,7 @@ class LandingViews(TestCase): result.render() def test_about_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.About.as_view() request = self.factory.get("") request.user = self.local_user @@ -53,7 +53,7 @@ class LandingViews(TestCase): self.assertEqual(result.status_code, 200) def test_discover(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Discover.as_view() request = self.factory.get("") result = view(request) diff --git a/bookwyrm/tests/views/test_list.py b/bookwyrm/tests/views/test_list.py index 215f3e61..3de35b1e 100644 --- a/bookwyrm/tests/views/test_list.py +++ b/bookwyrm/tests/views/test_list.py @@ -12,10 +12,10 @@ from bookwyrm.activitypub import ActivitypubResponse # pylint: disable=unused-argument class ListViews(TestCase): - """ tag views""" + """tag views""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -67,7 +67,7 @@ class ListViews(TestCase): models.SiteSettings.objects.create() def test_lists_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Lists.as_view() with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): models.List.objects.create(name="Public list", user=self.local_user) @@ -90,7 +90,7 @@ class ListViews(TestCase): self.assertEqual(result.status_code, 200) def test_lists_create(self): - """ create list view """ + """create list view""" view = views.Lists.as_view() request = self.factory.post( "", @@ -118,7 +118,7 @@ class ListViews(TestCase): self.assertEqual(new_list.curation, "open") def test_list_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.List.as_view() request = self.factory.get("") request.user = self.local_user @@ -153,7 +153,7 @@ class ListViews(TestCase): self.assertEqual(result.status_code, 200) def test_list_edit(self): - """ edit a list """ + """edit a list""" view = views.List.as_view() request = self.factory.post( "", @@ -185,7 +185,7 @@ class ListViews(TestCase): self.assertEqual(self.list.curation, "curated") def test_curate_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Curate.as_view() with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): models.List.objects.create(name="Public list", user=self.local_user) @@ -205,7 +205,7 @@ class ListViews(TestCase): self.assertEqual(result.status_code, 302) def test_curate_approve(self): - """ approve a pending item """ + """approve a pending item""" view = views.Curate.as_view() with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): pending = models.ListItem.objects.create( @@ -240,7 +240,7 @@ class ListViews(TestCase): self.assertTrue(pending.approved) def test_curate_reject(self): - """ approve a pending item """ + """approve a pending item""" view = views.Curate.as_view() with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): pending = models.ListItem.objects.create( @@ -266,7 +266,7 @@ class ListViews(TestCase): self.assertFalse(models.ListItem.objects.exists()) def test_add_book(self): - """ put a book on a list """ + """put a book on a list""" request = self.factory.post( "", { @@ -545,7 +545,7 @@ class ListViews(TestCase): self.assertEqual(items[2].order, 3) def test_add_book_outsider(self): - """ put a book on a list """ + """put a book on a list""" self.list.curation = "open" self.list.save(broadcast=False) request = self.factory.post( @@ -571,7 +571,7 @@ class ListViews(TestCase): self.assertTrue(item.approved) def test_add_book_pending(self): - """ put a book on a list awaiting approval """ + """put a book on a list awaiting approval""" self.list.curation = "curated" self.list.save(broadcast=False) request = self.factory.post( @@ -601,7 +601,7 @@ class ListViews(TestCase): self.assertFalse(item.approved) def test_add_book_self_curated(self): - """ put a book on a list automatically approved """ + """put a book on a list automatically approved""" self.list.curation = "curated" self.list.save(broadcast=False) request = self.factory.post( @@ -627,7 +627,7 @@ class ListViews(TestCase): self.assertTrue(item.approved) def test_remove_book(self): - """ take an item off a list """ + """take an item off a list""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): item = models.ListItem.objects.create( @@ -651,7 +651,7 @@ class ListViews(TestCase): self.assertFalse(self.list.listitem_set.exists()) def test_remove_book_unauthorized(self): - """ take an item off a list """ + """take an item off a list""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): item = models.ListItem.objects.create( book_list=self.list, user=self.local_user, book=self.book, order=1 diff --git a/bookwyrm/tests/views/test_notifications.py b/bookwyrm/tests/views/test_notifications.py index 6d92485e..182753f9 100644 --- a/bookwyrm/tests/views/test_notifications.py +++ b/bookwyrm/tests/views/test_notifications.py @@ -8,10 +8,10 @@ from bookwyrm import views class NotificationViews(TestCase): - """ notifications """ + """notifications""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -23,7 +23,7 @@ class NotificationViews(TestCase): models.SiteSettings.objects.create() def test_notifications_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Notifications.as_view() request = self.factory.get("") request.user = self.local_user @@ -33,7 +33,7 @@ class NotificationViews(TestCase): self.assertEqual(result.status_code, 200) def test_clear_notifications(self): - """ erase notifications """ + """erase notifications""" models.Notification.objects.create( user=self.local_user, notification_type="FAVORITE" ) diff --git a/bookwyrm/tests/views/test_outbox.py b/bookwyrm/tests/views/test_outbox.py index 0bcfde69..f89258e5 100644 --- a/bookwyrm/tests/views/test_outbox.py +++ b/bookwyrm/tests/views/test_outbox.py @@ -13,10 +13,10 @@ from bookwyrm.settings import USER_AGENT # pylint: disable=too-many-public-methods @patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay") class OutboxView(TestCase): - """ sends out activities """ + """sends out activities""" def setUp(self): - """ we'll need some data """ + """we'll need some data""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -34,19 +34,19 @@ class OutboxView(TestCase): ) def test_outbox(self, _): - """ returns user's statuses """ + """returns user's statuses""" request = self.factory.get("") result = views.Outbox.as_view()(request, "mouse") self.assertIsInstance(result, JsonResponse) def test_outbox_bad_method(self, _): - """ can't POST to outbox """ + """can't POST to outbox""" request = self.factory.post("") result = views.Outbox.as_view()(request, "mouse") self.assertEqual(result.status_code, 405) def test_outbox_unknown_user(self, _): - """ should 404 for unknown and remote users """ + """should 404 for unknown and remote users""" request = self.factory.post("") result = views.Outbox.as_view()(request, "beepboop") self.assertEqual(result.status_code, 405) @@ -54,7 +54,7 @@ class OutboxView(TestCase): self.assertEqual(result.status_code, 405) def test_outbox_privacy(self, _): - """ don't show dms et cetera in outbox """ + """don't show dms et cetera in outbox""" with patch("bookwyrm.activitystreams.ActivityStream.add_status"): models.Status.objects.create( content="PRIVATE!!", user=self.local_user, privacy="direct" @@ -77,7 +77,7 @@ class OutboxView(TestCase): self.assertEqual(data["totalItems"], 2) def test_outbox_filter(self, _): - """ if we only care about reviews, only get reviews """ + """if we only care about reviews, only get reviews""" with patch("bookwyrm.activitystreams.ActivityStream.add_status"): models.Review.objects.create( content="look at this", @@ -103,7 +103,7 @@ class OutboxView(TestCase): self.assertEqual(data["totalItems"], 1) def test_outbox_bookwyrm_request_true(self, _): - """ should differentiate between bookwyrm and outside requests """ + """should differentiate between bookwyrm and outside requests""" with patch("bookwyrm.activitystreams.ActivityStream.add_status"): models.Review.objects.create( name="hi", @@ -121,7 +121,7 @@ class OutboxView(TestCase): self.assertEqual(data["orderedItems"][0]["type"], "Review") def test_outbox_bookwyrm_request_false(self, _): - """ should differentiate between bookwyrm and outside requests """ + """should differentiate between bookwyrm and outside requests""" with patch("bookwyrm.activitystreams.ActivityStream.add_status"): models.Review.objects.create( name="hi", diff --git a/bookwyrm/tests/views/test_password.py b/bookwyrm/tests/views/test_password.py index 53a9bcbd..ec686db7 100644 --- a/bookwyrm/tests/views/test_password.py +++ b/bookwyrm/tests/views/test_password.py @@ -10,10 +10,10 @@ from bookwyrm import models, views class PasswordViews(TestCase): - """ view user and edit profile """ + """view user and edit profile""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -27,7 +27,7 @@ class PasswordViews(TestCase): models.SiteSettings.objects.create(id=1) def test_password_reset_request(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.PasswordResetRequest.as_view() request = self.factory.get("") request.user = self.local_user @@ -38,7 +38,7 @@ class PasswordViews(TestCase): self.assertEqual(result.status_code, 200) def test_password_reset_request_post(self): - """ send 'em an email """ + """send 'em an email""" request = self.factory.post("", {"email": "aa@bb.ccc"}) view = views.PasswordResetRequest.as_view() resp = view(request) @@ -53,7 +53,7 @@ class PasswordViews(TestCase): self.assertEqual(models.PasswordReset.objects.get().user, self.local_user) def test_password_reset(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.PasswordReset.as_view() code = models.PasswordReset.objects.create(user=self.local_user) request = self.factory.get("") @@ -64,7 +64,7 @@ class PasswordViews(TestCase): self.assertEqual(result.status_code, 200) def test_password_reset_post(self): - """ reset from code """ + """reset from code""" view = views.PasswordReset.as_view() code = models.PasswordReset.objects.create(user=self.local_user) request = self.factory.post("", {"password": "hi", "confirm-password": "hi"}) @@ -74,7 +74,7 @@ class PasswordViews(TestCase): self.assertFalse(models.PasswordReset.objects.exists()) def test_password_reset_wrong_code(self): - """ reset from code """ + """reset from code""" view = views.PasswordReset.as_view() models.PasswordReset.objects.create(user=self.local_user) request = self.factory.post("", {"password": "hi", "confirm-password": "hi"}) @@ -83,7 +83,7 @@ class PasswordViews(TestCase): self.assertTrue(models.PasswordReset.objects.exists()) def test_password_reset_mismatch(self): - """ reset from code """ + """reset from code""" view = views.PasswordReset.as_view() code = models.PasswordReset.objects.create(user=self.local_user) request = self.factory.post("", {"password": "hi", "confirm-password": "hihi"}) @@ -92,7 +92,7 @@ class PasswordViews(TestCase): self.assertTrue(models.PasswordReset.objects.exists()) def test_password_change_get(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.ChangePassword.as_view() request = self.factory.get("") request.user = self.local_user @@ -103,7 +103,7 @@ class PasswordViews(TestCase): self.assertEqual(result.status_code, 200) def test_password_change(self): - """ change password """ + """change password""" view = views.ChangePassword.as_view() password_hash = self.local_user.password request = self.factory.post("", {"password": "hi", "confirm-password": "hi"}) @@ -113,7 +113,7 @@ class PasswordViews(TestCase): self.assertNotEqual(self.local_user.password, password_hash) def test_password_change_mismatch(self): - """ change password """ + """change password""" view = views.ChangePassword.as_view() password_hash = self.local_user.password request = self.factory.post("", {"password": "hi", "confirm-password": "hihi"}) diff --git a/bookwyrm/tests/views/test_reading.py b/bookwyrm/tests/views/test_reading.py index b1ae6b88..c591aa60 100644 --- a/bookwyrm/tests/views/test_reading.py +++ b/bookwyrm/tests/views/test_reading.py @@ -10,10 +10,10 @@ from bookwyrm import models, views @patch("bookwyrm.activitystreams.ActivityStream.add_status") class ReadingViews(TestCase): - """ viewing and creating statuses """ + """viewing and creating statuses""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -41,7 +41,7 @@ class ReadingViews(TestCase): ) def test_start_reading(self, _): - """ begin a book """ + """begin a book""" shelf = self.local_user.shelf_set.get(identifier=models.Shelf.READING) self.assertFalse(shelf.books.exists()) self.assertFalse(models.Status.objects.exists()) @@ -72,7 +72,7 @@ class ReadingViews(TestCase): self.assertEqual(readthrough.book, self.book) def test_start_reading_reshelf(self, _): - """ begin a book """ + """begin a book""" to_read_shelf = self.local_user.shelf_set.get(identifier=models.Shelf.TO_READ) with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): models.ShelfBook.objects.create( @@ -92,7 +92,7 @@ class ReadingViews(TestCase): self.assertEqual(shelf.books.get(), self.book) def test_finish_reading(self, _): - """ begin a book """ + """begin a book""" shelf = self.local_user.shelf_set.get(identifier=models.Shelf.READ_FINISHED) self.assertFalse(shelf.books.exists()) self.assertFalse(models.Status.objects.exists()) @@ -128,7 +128,7 @@ class ReadingViews(TestCase): self.assertEqual(readthrough.book, self.book) def test_edit_readthrough(self, _): - """ adding dates to an ongoing readthrough """ + """adding dates to an ongoing readthrough""" start = timezone.make_aware(dateutil.parser.parse("2021-01-03")) readthrough = models.ReadThrough.objects.create( book=self.book, user=self.local_user, start_date=start @@ -155,7 +155,7 @@ class ReadingViews(TestCase): self.assertEqual(readthrough.book, self.book) def test_delete_readthrough(self, _): - """ remove a readthrough """ + """remove a readthrough""" readthrough = models.ReadThrough.objects.create( book=self.book, user=self.local_user ) @@ -172,7 +172,7 @@ class ReadingViews(TestCase): self.assertFalse(models.ReadThrough.objects.filter(id=readthrough.id).exists()) def test_create_readthrough(self, _): - """ adding new read dates """ + """adding new read dates""" request = self.factory.post( "", { diff --git a/bookwyrm/tests/views/test_readthrough.py b/bookwyrm/tests/views/test_readthrough.py index 5399f673..c9ebf216 100644 --- a/bookwyrm/tests/views/test_readthrough.py +++ b/bookwyrm/tests/views/test_readthrough.py @@ -9,10 +9,10 @@ from bookwyrm import models @patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay") class ReadThrough(TestCase): - """ readthrough tests """ + """readthrough tests""" def setUp(self): - """ basic user and book data """ + """basic user and book data""" self.client = Client() self.work = models.Work.objects.create(title="Example Work") @@ -52,7 +52,7 @@ class ReadThrough(TestCase): self.assertEqual(delay_mock.call_count, 1) def test_create_progress_readthrough(self, delay_mock): - """ a readthrough with progress """ + """a readthrough with progress""" self.assertEqual(self.edition.readthrough_set.count(), 0) self.client.post( diff --git a/bookwyrm/tests/views/test_reports.py b/bookwyrm/tests/views/test_reports.py index bce19993..84539489 100644 --- a/bookwyrm/tests/views/test_reports.py +++ b/bookwyrm/tests/views/test_reports.py @@ -7,10 +7,10 @@ from bookwyrm import forms, models, views class ReportViews(TestCase): - """ every response to a get request, html or json """ + """every response to a get request, html or json""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -29,7 +29,7 @@ class ReportViews(TestCase): models.SiteSettings.objects.create() def test_reports_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Reports.as_view() request = self.factory.get("") request.user = self.local_user @@ -41,7 +41,7 @@ class ReportViews(TestCase): self.assertEqual(result.status_code, 200) def test_reports_page_with_data(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Reports.as_view() request = self.factory.get("") request.user = self.local_user @@ -54,7 +54,7 @@ class ReportViews(TestCase): self.assertEqual(result.status_code, 200) def test_report_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Report.as_view() request = self.factory.get("") request.user = self.local_user @@ -68,7 +68,7 @@ class ReportViews(TestCase): self.assertEqual(result.status_code, 200) def test_report_comment(self): - """ comment on a report """ + """comment on a report""" view = views.Report.as_view() request = self.factory.post("", {"note": "hi"}) request.user = self.local_user @@ -83,7 +83,7 @@ class ReportViews(TestCase): self.assertEqual(comment.report, report) def test_make_report(self): - """ a user reports another user """ + """a user reports another user""" form = forms.ReportForm() form.data["reporter"] = self.local_user.id form.data["user"] = self.rat.id @@ -97,7 +97,7 @@ class ReportViews(TestCase): self.assertEqual(report.user, self.rat) def test_resolve_report(self): - """ toggle report resolution status """ + """toggle report resolution status""" report = models.Report.objects.create(reporter=self.local_user, user=self.rat) self.assertFalse(report.resolved) request = self.factory.post("") @@ -115,7 +115,7 @@ class ReportViews(TestCase): self.assertFalse(report.resolved) def test_suspend_user(self): - """ toggle whether a user is able to log in """ + """toggle whether a user is able to log in""" self.assertTrue(self.rat.is_active) request = self.factory.post("") request.user = self.local_user diff --git a/bookwyrm/tests/views/test_rss_feed.py b/bookwyrm/tests/views/test_rss_feed.py index 0230b4a9..eacb3c93 100644 --- a/bookwyrm/tests/views/test_rss_feed.py +++ b/bookwyrm/tests/views/test_rss_feed.py @@ -8,10 +8,10 @@ from bookwyrm.views import rss_feed class RssFeedView(TestCase): - """ rss feed behaves as expected """ + """rss feed behaves as expected""" def setUp(self): - """ test data """ + """test data""" self.site = models.SiteSettings.objects.create() self.user = models.User.objects.create_user( @@ -50,7 +50,7 @@ class RssFeedView(TestCase): @patch("bookwyrm.activitystreams.ActivityStream.get_activity_stream") def test_rss_feed(self, _): - """ load an rss feed """ + """load an rss feed""" view = rss_feed.RssFeed() request = self.factory.get("/user/rss_user/rss") request.user = self.user diff --git a/bookwyrm/tests/views/test_search.py b/bookwyrm/tests/views/test_search.py index 78c7a103..77727522 100644 --- a/bookwyrm/tests/views/test_search.py +++ b/bookwyrm/tests/views/test_search.py @@ -13,10 +13,10 @@ from bookwyrm.settings import DOMAIN class ShelfViews(TestCase): - """ tag views""" + """tag views""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -38,7 +38,7 @@ class ShelfViews(TestCase): models.SiteSettings.objects.create() def test_search_json_response(self): - """ searches local data only and returns book data in json format """ + """searches local data only and returns book data in json format""" view = views.Search.as_view() # we need a connector for this, sorry request = self.factory.get("", {"q": "Test Book"}) @@ -53,11 +53,11 @@ class ShelfViews(TestCase): self.assertEqual(data[0]["key"], "https://%s/book/%d" % (DOMAIN, self.book.id)) def test_search_html_response(self): - """ searches remote connectors """ + """searches remote connectors""" view = views.Search.as_view() class TestConnector(abstract_connector.AbstractMinimalConnector): - """ nothing added here """ + """nothing added here""" def format_search_result(self, search_result): pass @@ -106,7 +106,7 @@ class ShelfViews(TestCase): ) def test_search_html_response_users(self): - """ searches remote connectors """ + """searches remote connectors""" view = views.Search.as_view() request = self.factory.get("", {"q": "mouse"}) request.user = self.local_user diff --git a/bookwyrm/tests/views/test_shelf.py b/bookwyrm/tests/views/test_shelf.py index 7ab01562..239b3318 100644 --- a/bookwyrm/tests/views/test_shelf.py +++ b/bookwyrm/tests/views/test_shelf.py @@ -11,10 +11,10 @@ from bookwyrm.activitypub import ActivitypubResponse @patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay") class ShelfViews(TestCase): - """ tag views""" + """tag views""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -37,7 +37,7 @@ class ShelfViews(TestCase): models.SiteSettings.objects.create() def test_shelf_page(self, _): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Shelf.as_view() shelf = self.local_user.shelf_set.first() request = self.factory.get("") @@ -64,7 +64,7 @@ class ShelfViews(TestCase): self.assertEqual(result.status_code, 200) def test_edit_shelf_privacy(self, _): - """ set name or privacy on shelf """ + """set name or privacy on shelf""" view = views.Shelf.as_view() shelf = self.local_user.shelf_set.get(identifier="to-read") self.assertEqual(shelf.privacy, "public") @@ -84,7 +84,7 @@ class ShelfViews(TestCase): self.assertEqual(shelf.privacy, "unlisted") def test_edit_shelf_name(self, _): - """ change the name of an editable shelf """ + """change the name of an editable shelf""" view = views.Shelf.as_view() shelf = models.Shelf.objects.create(name="Test Shelf", user=self.local_user) self.assertEqual(shelf.privacy, "public") @@ -101,7 +101,7 @@ class ShelfViews(TestCase): self.assertEqual(shelf.identifier, "testshelf-%d" % shelf.id) def test_edit_shelf_name_not_editable(self, _): - """ can't change the name of an non-editable shelf """ + """can't change the name of an non-editable shelf""" view = views.Shelf.as_view() shelf = self.local_user.shelf_set.get(identifier="to-read") self.assertEqual(shelf.privacy, "public") @@ -116,7 +116,7 @@ class ShelfViews(TestCase): self.assertEqual(shelf.name, "To Read") def test_handle_shelve(self, _): - """ shelve a book """ + """shelve a book""" request = self.factory.post( "", {"book": self.book.id, "shelf": self.shelf.identifier} ) @@ -134,7 +134,7 @@ class ShelfViews(TestCase): self.assertEqual(self.shelf.books.get(), self.book) def test_handle_shelve_to_read(self, _): - """ special behavior for the to-read shelf """ + """special behavior for the to-read shelf""" shelf = models.Shelf.objects.get(identifier="to-read") request = self.factory.post( "", {"book": self.book.id, "shelf": shelf.identifier} @@ -147,7 +147,7 @@ class ShelfViews(TestCase): self.assertEqual(shelf.books.get(), self.book) def test_handle_shelve_reading(self, _): - """ special behavior for the reading shelf """ + """special behavior for the reading shelf""" shelf = models.Shelf.objects.get(identifier="reading") request = self.factory.post( "", {"book": self.book.id, "shelf": shelf.identifier} @@ -160,7 +160,7 @@ class ShelfViews(TestCase): self.assertEqual(shelf.books.get(), self.book) def test_handle_shelve_read(self, _): - """ special behavior for the read shelf """ + """special behavior for the read shelf""" shelf = models.Shelf.objects.get(identifier="read") request = self.factory.post( "", {"book": self.book.id, "shelf": shelf.identifier} @@ -173,7 +173,7 @@ class ShelfViews(TestCase): self.assertEqual(shelf.books.get(), self.book) def test_handle_unshelve(self, _): - """ remove a book from a shelf """ + """remove a book from a shelf""" with patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay"): models.ShelfBook.objects.create( book=self.book, user=self.local_user, shelf=self.shelf diff --git a/bookwyrm/tests/views/test_status.py b/bookwyrm/tests/views/test_status.py index 5eb13b6b..6f2fd30d 100644 --- a/bookwyrm/tests/views/test_status.py +++ b/bookwyrm/tests/views/test_status.py @@ -10,10 +10,10 @@ from bookwyrm.settings import DOMAIN @patch("bookwyrm.models.activitypub_mixin.broadcast_task.delay") class StatusViews(TestCase): - """ viewing and creating statuses """ + """viewing and creating statuses""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -43,7 +43,7 @@ class StatusViews(TestCase): models.SiteSettings.objects.create() def test_handle_status(self, _): - """ create a status """ + """create a status""" view = views.CreateStatus.as_view() form = forms.CommentForm( { @@ -66,7 +66,7 @@ class StatusViews(TestCase): self.assertEqual(status.book, self.book) def test_handle_status_reply(self, _): - """ create a status in reply to an existing status """ + """create a status in reply to an existing status""" view = views.CreateStatus.as_view() user = models.User.objects.create_user( "rat", "rat@rat.com", "password", local=True @@ -96,7 +96,7 @@ class StatusViews(TestCase): self.assertEqual(models.Notification.objects.get().user, self.local_user) def test_handle_status_mentions(self, _): - """ @mention a user in a post """ + """@mention a user in a post""" view = views.CreateStatus.as_view() user = models.User.objects.create_user( "rat@%s" % DOMAIN, "rat@rat.com", "password", local=True, localname="rat" @@ -124,7 +124,7 @@ class StatusViews(TestCase): ) def test_handle_status_reply_with_mentions(self, _): - """ reply to a post with an @mention'ed user """ + """reply to a post with an @mention'ed user""" view = views.CreateStatus.as_view() user = models.User.objects.create_user( "rat", "rat@rat.com", "password", local=True, localname="rat" @@ -168,7 +168,7 @@ class StatusViews(TestCase): self.assertTrue(self.local_user in reply.mention_users.all()) def test_delete_and_redraft(self, _): - """ delete and re-draft a status """ + """delete and re-draft a status""" view = views.DeleteAndRedraft.as_view() request = self.factory.post("") request.user = self.local_user @@ -189,7 +189,7 @@ class StatusViews(TestCase): self.assertTrue(status.deleted) def test_delete_and_redraft_invalid_status_type_rating(self, _): - """ you can't redraft generated statuses """ + """you can't redraft generated statuses""" view = views.DeleteAndRedraft.as_view() request = self.factory.post("") request.user = self.local_user @@ -209,7 +209,7 @@ class StatusViews(TestCase): self.assertFalse(status.deleted) def test_delete_and_redraft_invalid_status_type_generated_note(self, _): - """ you can't redraft generated statuses """ + """you can't redraft generated statuses""" view = views.DeleteAndRedraft.as_view() request = self.factory.post("") request.user = self.local_user @@ -229,7 +229,7 @@ class StatusViews(TestCase): self.assertFalse(status.deleted) def test_find_mentions(self, _): - """ detect and look up @ mentions of users """ + """detect and look up @ mentions of users""" user = models.User.objects.create_user( "nutria@%s" % DOMAIN, "nutria@nutria.com", @@ -275,7 +275,7 @@ class StatusViews(TestCase): ) def test_format_links(self, _): - """ find and format urls into a tags """ + """find and format urls into a tags""" url = "http://www.fish.com/" self.assertEqual( views.status.format_links(url), 'www.fish.com/' % url @@ -298,7 +298,7 @@ class StatusViews(TestCase): ) def test_to_markdown(self, _): - """ this is mostly handled in other places, but nonetheless """ + """this is mostly handled in other places, but nonetheless""" text = "_hi_ and http://fish.com is rad" result = views.status.to_markdown(text) self.assertEqual( @@ -307,13 +307,13 @@ class StatusViews(TestCase): ) def test_to_markdown_link(self, _): - """ this is mostly handled in other places, but nonetheless """ + """this is mostly handled in other places, but nonetheless""" text = "[hi](http://fish.com) is rad" result = views.status.to_markdown(text) self.assertEqual(result, '

hi ' "is rad

") def test_handle_delete_status(self, mock): - """ marks a status as deleted """ + """marks a status as deleted""" view = views.DeleteStatus.as_view() with patch("bookwyrm.activitystreams.ActivityStream.add_status"): status = models.Status.objects.create(user=self.local_user, content="hi") @@ -333,7 +333,7 @@ class StatusViews(TestCase): self.assertTrue(status.deleted) def test_handle_delete_status_permission_denied(self, _): - """ marks a status as deleted """ + """marks a status as deleted""" view = views.DeleteStatus.as_view() with patch("bookwyrm.activitystreams.ActivityStream.add_status"): status = models.Status.objects.create(user=self.local_user, content="hi") @@ -347,7 +347,7 @@ class StatusViews(TestCase): self.assertFalse(status.deleted) def test_handle_delete_status_moderator(self, mock): - """ marks a status as deleted """ + """marks a status as deleted""" view = views.DeleteStatus.as_view() with patch("bookwyrm.activitystreams.ActivityStream.add_status"): status = models.Status.objects.create(user=self.local_user, content="hi") diff --git a/bookwyrm/tests/views/test_updates.py b/bookwyrm/tests/views/test_updates.py index dff730e6..fb003f8d 100644 --- a/bookwyrm/tests/views/test_updates.py +++ b/bookwyrm/tests/views/test_updates.py @@ -10,10 +10,10 @@ from bookwyrm import models, views class UpdateViews(TestCase): - """ lets the ui check for unread notification """ + """lets the ui check for unread notification""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -25,7 +25,7 @@ class UpdateViews(TestCase): models.SiteSettings.objects.create() def test_get_notification_count(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" request = self.factory.get("") request.user = self.local_user @@ -43,7 +43,7 @@ class UpdateViews(TestCase): self.assertEqual(data["count"], 1) def test_get_unread_status_count(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" request = self.factory.get("") request.user = self.local_user diff --git a/bookwyrm/tests/views/test_user.py b/bookwyrm/tests/views/test_user.py index 7518b2bf..3b431de1 100644 --- a/bookwyrm/tests/views/test_user.py +++ b/bookwyrm/tests/views/test_user.py @@ -15,10 +15,10 @@ from bookwyrm.activitypub import ActivitypubResponse class UserViews(TestCase): - """ view user and edit profile """ + """view user and edit profile""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -43,7 +43,7 @@ class UserViews(TestCase): self.anonymous_user.is_authenticated = False def test_user_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.User.as_view() request = self.factory.get("") request.user = self.local_user @@ -69,7 +69,7 @@ class UserViews(TestCase): self.assertEqual(result.status_code, 200) def test_user_page_blocked(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.User.as_view() request = self.factory.get("") request.user = self.local_user @@ -80,7 +80,7 @@ class UserViews(TestCase): self.assertEqual(result.status_code, 404) def test_followers_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Followers.as_view() request = self.factory.get("") request.user = self.local_user @@ -98,7 +98,7 @@ class UserViews(TestCase): self.assertEqual(result.status_code, 200) def test_followers_page_blocked(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Followers.as_view() request = self.factory.get("") request.user = self.local_user @@ -109,7 +109,7 @@ class UserViews(TestCase): self.assertEqual(result.status_code, 404) def test_following_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Following.as_view() request = self.factory.get("") request.user = self.local_user @@ -127,7 +127,7 @@ class UserViews(TestCase): self.assertEqual(result.status_code, 200) def test_following_page_blocked(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.Following.as_view() request = self.factory.get("") request.user = self.local_user @@ -138,7 +138,7 @@ class UserViews(TestCase): self.assertEqual(result.status_code, 404) def test_edit_user_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.EditUser.as_view() request = self.factory.get("") request.user = self.local_user @@ -148,7 +148,7 @@ class UserViews(TestCase): self.assertEqual(result.status_code, 200) def test_edit_user(self): - """ use a form to update a user """ + """use a form to update a user""" view = views.EditUser.as_view() form = forms.EditUserForm(instance=self.local_user) form.data["name"] = "New Name" @@ -168,7 +168,7 @@ class UserViews(TestCase): # idk how to mock the upload form, got tired of triyng to make it work def test_edit_user_avatar(self): - """ use a form to update a user """ + """use a form to update a user""" view = views.EditUser.as_view() form = forms.EditUserForm(instance=self.local_user) form.data["name"] = "New Name" @@ -195,7 +195,7 @@ class UserViews(TestCase): self.assertEqual(self.local_user.avatar.height, 120) def test_crop_avatar(self): - """ reduce that image size """ + """reduce that image size""" image_file = pathlib.Path(__file__).parent.joinpath( "../../static/images/no_cover.jpg" ) diff --git a/bookwyrm/tests/views/test_user_admin.py b/bookwyrm/tests/views/test_user_admin.py index b1e9d639..a044a22c 100644 --- a/bookwyrm/tests/views/test_user_admin.py +++ b/bookwyrm/tests/views/test_user_admin.py @@ -9,10 +9,10 @@ from bookwyrm import models, views class UserAdminViews(TestCase): - """ every response to a get request, html or json """ + """every response to a get request, html or json""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -24,7 +24,7 @@ class UserAdminViews(TestCase): models.SiteSettings.objects.create() def test_user_admin_list_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.UserAdminList.as_view() request = self.factory.get("") request.user = self.local_user @@ -35,7 +35,7 @@ class UserAdminViews(TestCase): self.assertEqual(result.status_code, 200) def test_user_admin_page(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" view = views.UserAdmin.as_view() request = self.factory.get("") request.user = self.local_user @@ -48,7 +48,7 @@ class UserAdminViews(TestCase): self.assertEqual(result.status_code, 200) def test_user_admin_page_post(self): - """ set the user's group """ + """set the user's group""" group = Group.objects.create(name="editor") self.assertEqual( list(self.local_user.groups.values_list("name", flat=True)), [] diff --git a/bookwyrm/tests/views/test_wellknown.py b/bookwyrm/tests/views/test_wellknown.py index f408460f..244921d4 100644 --- a/bookwyrm/tests/views/test_wellknown.py +++ b/bookwyrm/tests/views/test_wellknown.py @@ -11,10 +11,10 @@ from bookwyrm import models, views class UserViews(TestCase): - """ view user and edit profile """ + """view user and edit profile""" def setUp(self): - """ we need basic test data and mocks """ + """we need basic test data and mocks""" self.factory = RequestFactory() self.local_user = models.User.objects.create_user( "mouse@local.com", @@ -41,7 +41,7 @@ class UserViews(TestCase): self.anonymous_user.is_authenticated = False def test_webfinger(self): - """ there are so many views, this just makes sure it LOADS """ + """there are so many views, this just makes sure it LOADS""" request = self.factory.get("", {"resource": "acct:mouse@local.com"}) request.user = self.anonymous_user @@ -51,7 +51,7 @@ class UserViews(TestCase): self.assertEqual(data["subject"], "acct:mouse@local.com") def test_nodeinfo_pointer(self): - """ just tells you where nodeinfo is """ + """just tells you where nodeinfo is""" request = self.factory.get("") request.user = self.anonymous_user @@ -61,7 +61,7 @@ class UserViews(TestCase): self.assertTrue("href" in data["links"][0]) def test_nodeinfo(self): - """ info about the instance """ + """info about the instance""" request = self.factory.get("") request.user = self.anonymous_user @@ -73,7 +73,7 @@ class UserViews(TestCase): self.assertEqual(models.User.objects.count(), 3) def test_instanceinfo(self): - """ about the instance's user activity """ + """about the instance's user activity""" request = self.factory.get("") request.user = self.anonymous_user diff --git a/bookwyrm/views/authentication.py b/bookwyrm/views/authentication.py index 22689a28..bfb49248 100644 --- a/bookwyrm/views/authentication.py +++ b/bookwyrm/views/authentication.py @@ -16,10 +16,10 @@ from bookwyrm.settings import DOMAIN # pylint: disable= no-self-use @method_decorator(csrf_exempt, name="dispatch") class Login(View): - """ authenticate an existing user """ + """authenticate an existing user""" def get(self, request): - """ login page """ + """login page""" if request.user.is_authenticated: return redirect("/") # sene user to the login page @@ -30,7 +30,7 @@ class Login(View): return TemplateResponse(request, "login.html", data) def post(self, request): - """ authentication action """ + """authentication action""" if request.user.is_authenticated: return redirect("/") login_form = forms.LoginForm(request.POST) @@ -61,10 +61,10 @@ class Login(View): class Register(View): - """ register a user """ + """register a user""" def post(self, request): - """ join the server """ + """join the server""" if not models.SiteSettings.get().allow_registration: invite_code = request.POST.get("invite_code") @@ -117,9 +117,9 @@ class Register(View): @method_decorator(login_required, name="dispatch") class Logout(View): - """ log out """ + """log out""" def get(self, request): - """ done with this place! outa here! """ + """done with this place! outa here!""" logout(request) return redirect("/") diff --git a/bookwyrm/views/author.py b/bookwyrm/views/author.py index 50a3588d..0bd7b0e0 100644 --- a/bookwyrm/views/author.py +++ b/bookwyrm/views/author.py @@ -13,10 +13,10 @@ from .helpers import is_api_request # pylint: disable= no-self-use class Author(View): - """ this person wrote a book """ + """this person wrote a book""" def get(self, request, author_id): - """ landing page for an author """ + """landing page for an author""" author = get_object_or_404(models.Author, id=author_id) if is_api_request(request): @@ -37,16 +37,16 @@ class Author(View): permission_required("bookwyrm.edit_book", raise_exception=True), name="dispatch" ) class EditAuthor(View): - """ edit author info """ + """edit author info""" def get(self, request, author_id): - """ info about a book """ + """info about a book""" author = get_object_or_404(models.Author, id=author_id) data = {"author": author, "form": forms.AuthorForm(instance=author)} return TemplateResponse(request, "edit_author.html", data) def post(self, request, author_id): - """ edit a author cool """ + """edit a author cool""" author = get_object_or_404(models.Author, id=author_id) form = forms.AuthorForm(request.POST, request.FILES, instance=author) diff --git a/bookwyrm/views/block.py b/bookwyrm/views/block.py index 6d6a8a58..99014a93 100644 --- a/bookwyrm/views/block.py +++ b/bookwyrm/views/block.py @@ -12,14 +12,14 @@ from bookwyrm import models # pylint: disable= no-self-use @method_decorator(login_required, name="dispatch") class Block(View): - """ blocking users """ + """blocking users""" def get(self, request): - """ list of blocked users? """ + """list of blocked users?""" return TemplateResponse(request, "preferences/blocks.html") def post(self, request, user_id): - """ block a user """ + """block a user""" to_block = get_object_or_404(models.User, id=user_id) models.UserBlocks.objects.create( user_subject=request.user, user_object=to_block @@ -30,7 +30,7 @@ class Block(View): @require_POST @login_required def unblock(request, user_id): - """ undo a block """ + """undo a block""" to_unblock = get_object_or_404(models.User, id=user_id) try: block = models.UserBlocks.objects.get( diff --git a/bookwyrm/views/books.py b/bookwyrm/views/books.py index 829408a8..448cf992 100644 --- a/bookwyrm/views/books.py +++ b/bookwyrm/views/books.py @@ -26,10 +26,10 @@ from .helpers import is_api_request, get_edition, privacy_filter # pylint: disable= no-self-use class Book(View): - """ a book! this is the stuff """ + """a book! this is the stuff""" def get(self, request, book_id, user_statuses=False): - """ info about a book """ + """info about a book""" try: book = models.Book.objects.select_subclasses().get(id=book_id) except models.Book.DoesNotExist: @@ -110,10 +110,10 @@ class Book(View): permission_required("bookwyrm.edit_book", raise_exception=True), name="dispatch" ) class EditBook(View): - """ edit a book """ + """edit a book""" def get(self, request, book_id=None): - """ info about a book """ + """info about a book""" book = None if book_id: book = get_edition(book_id) @@ -123,7 +123,7 @@ class EditBook(View): return TemplateResponse(request, "book/edit_book.html", data) def post(self, request, book_id=None): - """ edit a book cool """ + """edit a book cool""" # returns None if no match is found book = models.Edition.objects.filter(id=book_id).first() form = forms.EditionForm(request.POST, request.FILES, instance=book) @@ -209,10 +209,10 @@ class EditBook(View): permission_required("bookwyrm.edit_book", raise_exception=True), name="dispatch" ) class ConfirmEditBook(View): - """ confirm edits to a book """ + """confirm edits to a book""" def post(self, request, book_id=None): - """ edit a book cool """ + """edit a book cool""" # returns None if no match is found book = models.Edition.objects.filter(id=book_id).first() form = forms.EditionForm(request.POST, request.FILES, instance=book) @@ -260,10 +260,10 @@ class ConfirmEditBook(View): class Editions(View): - """ list of editions """ + """list of editions""" def get(self, request, book_id): - """ list of editions of a book """ + """list of editions of a book""" work = get_object_or_404(models.Work, id=book_id) if is_api_request(request): @@ -293,7 +293,7 @@ class Editions(View): @login_required @require_POST def upload_cover(request, book_id): - """ upload a new cover """ + """upload a new cover""" book = get_object_or_404(models.Edition, id=book_id) book.last_edited_by = request.user @@ -316,7 +316,7 @@ def upload_cover(request, book_id): def set_cover_from_url(url): - """ load it from a url """ + """load it from a url""" image_file = get_image(url) if not image_file: return None @@ -329,7 +329,7 @@ def set_cover_from_url(url): @require_POST @permission_required("bookwyrm.edit_book", raise_exception=True) def add_description(request, book_id): - """ upload a new cover """ + """upload a new cover""" if not request.method == "POST": return redirect("/") @@ -346,7 +346,7 @@ def add_description(request, book_id): @require_POST def resolve_book(request): - """ figure out the local path to a book from a remote_id """ + """figure out the local path to a book from a remote_id""" remote_id = request.POST.get("remote_id") connector = connector_manager.get_or_create_connector(remote_id) book = connector.get_or_create_book(remote_id) @@ -358,7 +358,7 @@ def resolve_book(request): @require_POST @transaction.atomic def switch_edition(request): - """ switch your copy of a book to a different edition """ + """switch your copy of a book to a different edition""" edition_id = request.POST.get("edition") new_edition = get_object_or_404(models.Edition, id=edition_id) shelfbooks = models.ShelfBook.objects.filter( diff --git a/bookwyrm/views/directory.py b/bookwyrm/views/directory.py index 7919dac0..a5786f74 100644 --- a/bookwyrm/views/directory.py +++ b/bookwyrm/views/directory.py @@ -11,10 +11,10 @@ from .helpers import get_annotated_users # pylint: disable=no-self-use @method_decorator(login_required, name="dispatch") class Directory(View): - """ display of known bookwyrm users """ + """display of known bookwyrm users""" def get(self, request): - """ lets see your cute faces """ + """lets see your cute faces""" filters = {} software = request.GET.get("software") if not software or software == "bookwyrm": @@ -38,7 +38,7 @@ class Directory(View): return TemplateResponse(request, "directory/directory.html", data) def post(self, request): - """ join the directory """ + """join the directory""" request.user.discoverable = True request.user.save() return redirect("directory") diff --git a/bookwyrm/views/federation.py b/bookwyrm/views/federation.py index 1acacf8f..d4a1af12 100644 --- a/bookwyrm/views/federation.py +++ b/bookwyrm/views/federation.py @@ -20,10 +20,10 @@ from bookwyrm.settings import PAGE_LENGTH name="dispatch", ) class Federation(View): - """ what servers do we federate with """ + """what servers do we federate with""" def get(self, request): - """ list of servers """ + """list of servers""" servers = models.FederatedServer.objects sort = request.GET.get("sort") @@ -43,15 +43,15 @@ class Federation(View): class AddFederatedServer(View): - """ manually add a server """ + """manually add a server""" def get(self, request): - """ add server form """ + """add server form""" data = {"form": forms.ServerForm()} return TemplateResponse(request, "settings/edit_server.html", data) def post(self, request): - """ add a server from the admin panel """ + """add a server from the admin panel""" form = forms.ServerForm(request.POST) if not form.is_valid(): data = {"form": form} @@ -66,14 +66,14 @@ class AddFederatedServer(View): name="dispatch", ) class ImportServerBlocklist(View): - """ manually add a server """ + """manually add a server""" def get(self, request): - """ add server form """ + """add server form""" return TemplateResponse(request, "settings/server_blocklist.html") def post(self, request): - """ add a server from the admin panel """ + """add a server from the admin panel""" json_data = json.load(request.FILES["json_file"]) failed = [] success_count = 0 @@ -102,10 +102,10 @@ class ImportServerBlocklist(View): name="dispatch", ) class FederatedServer(View): - """ views for handling a specific federated server """ + """views for handling a specific federated server""" def get(self, request, server): - """ load a server """ + """load a server""" server = get_object_or_404(models.FederatedServer, id=server) users = server.user_set data = { @@ -121,7 +121,7 @@ class FederatedServer(View): return TemplateResponse(request, "settings/federated_server.html", data) def post(self, request, server): # pylint: disable=unused-argument - """ update note """ + """update note""" server = get_object_or_404(models.FederatedServer, id=server) server.notes = request.POST.get("notes") server.save() @@ -133,7 +133,7 @@ class FederatedServer(View): @permission_required("bookwyrm.control_federation", raise_exception=True) # pylint: disable=unused-argument def block_server(request, server): - """ block a server """ + """block a server""" server = get_object_or_404(models.FederatedServer, id=server) server.block() return redirect("settings-federated-server", server.id) @@ -144,7 +144,7 @@ def block_server(request, server): @permission_required("bookwyrm.control_federation", raise_exception=True) # pylint: disable=unused-argument def unblock_server(request, server): - """ unblock a server """ + """unblock a server""" server = get_object_or_404(models.FederatedServer, id=server) server.unblock() return redirect("settings-federated-server", server.id) diff --git a/bookwyrm/views/feed.py b/bookwyrm/views/feed.py index 118473d0..98f365ea 100644 --- a/bookwyrm/views/feed.py +++ b/bookwyrm/views/feed.py @@ -18,10 +18,10 @@ from .helpers import is_api_request, is_bookwyrm_request # pylint: disable= no-self-use @method_decorator(login_required, name="dispatch") class Feed(View): - """ activity stream """ + """activity stream""" def get(self, request, tab): - """ user's homepage with activity feed """ + """user's homepage with activity feed""" if not tab in STREAMS: tab = "home" @@ -46,10 +46,10 @@ class Feed(View): @method_decorator(login_required, name="dispatch") class DirectMessage(View): - """ dm view """ + """dm view""" def get(self, request, username=None): - """ like a feed but for dms only """ + """like a feed but for dms only""" # remove fancy subclasses of status, keep just good ol' notes queryset = models.Status.objects.filter( review__isnull=True, @@ -85,10 +85,10 @@ class DirectMessage(View): class Status(View): - """ get posting """ + """get posting""" def get(self, request, username, status_id): - """ display a particular status (and replies, etc) """ + """display a particular status (and replies, etc)""" try: user = get_user_from_username(request.user, username) status = models.Status.objects.select_subclasses().get( @@ -120,10 +120,10 @@ class Status(View): class Replies(View): - """ replies page (a json view of status) """ + """replies page (a json view of status)""" def get(self, request, username, status_id): - """ ordered collection of replies to a status """ + """ordered collection of replies to a status""" # the html view is the same as Status if not is_api_request(request): status_view = Status.as_view() @@ -138,7 +138,7 @@ class Replies(View): def feed_page_data(user): - """ info we need for every feed page """ + """info we need for every feed page""" if not user.is_authenticated: return {} @@ -151,7 +151,7 @@ def feed_page_data(user): def get_suggested_books(user, max_books=5): - """ helper to get a user's recent books """ + """helper to get a user's recent books""" book_count = 0 preset_shelves = [("reading", max_books), ("read", 2), ("to-read", max_books)] suggested_books = [] diff --git a/bookwyrm/views/follow.py b/bookwyrm/views/follow.py index d9f455eb..09c2d53a 100644 --- a/bookwyrm/views/follow.py +++ b/bookwyrm/views/follow.py @@ -12,7 +12,7 @@ from .helpers import get_user_from_username @login_required @require_POST def follow(request): - """ follow another user, here or abroad """ + """follow another user, here or abroad""" username = request.POST["user"] try: to_follow = get_user_from_username(request.user, username) @@ -33,7 +33,7 @@ def follow(request): @login_required @require_POST def unfollow(request): - """ unfollow a user """ + """unfollow a user""" username = request.POST["user"] try: to_unfollow = get_user_from_username(request.user, username) @@ -61,7 +61,7 @@ def unfollow(request): @login_required @require_POST def accept_follow_request(request): - """ a user accepts a follow request """ + """a user accepts a follow request""" username = request.POST["user"] try: requester = get_user_from_username(request.user, username) @@ -83,7 +83,7 @@ def accept_follow_request(request): @login_required @require_POST def delete_follow_request(request): - """ a user rejects a follow request """ + """a user rejects a follow request""" username = request.POST["user"] try: requester = get_user_from_username(request.user, username) diff --git a/bookwyrm/views/get_started.py b/bookwyrm/views/get_started.py index a21723a3..5573bf19 100644 --- a/bookwyrm/views/get_started.py +++ b/bookwyrm/views/get_started.py @@ -20,12 +20,12 @@ from .user import save_user_form # pylint: disable= no-self-use @method_decorator(login_required, name="dispatch") class GetStartedProfile(View): - """ tell us about yourself """ + """tell us about yourself""" next_view = "get-started-books" def get(self, request): - """ basic profile info """ + """basic profile info""" data = { "form": forms.LimitedEditUserForm(instance=request.user), "next": self.next_view, @@ -33,7 +33,7 @@ class GetStartedProfile(View): return TemplateResponse(request, "get_started/profile.html", data) def post(self, request): - """ update your profile """ + """update your profile""" form = forms.LimitedEditUserForm( request.POST, request.FILES, instance=request.user ) @@ -46,12 +46,12 @@ class GetStartedProfile(View): @method_decorator(login_required, name="dispatch") class GetStartedBooks(View): - """ name a book, any book, we gotta start somewhere """ + """name a book, any book, we gotta start somewhere""" next_view = "get-started-users" def get(self, request): - """ info about a book """ + """info about a book""" query = request.GET.get("query") book_results = popular_books = [] if query: @@ -82,7 +82,7 @@ class GetStartedBooks(View): return TemplateResponse(request, "get_started/books.html", data) def post(self, request): - """ shelve some books """ + """shelve some books""" shelve_actions = [ (k, v) for k, v in request.POST.items() @@ -100,10 +100,10 @@ class GetStartedBooks(View): @method_decorator(login_required, name="dispatch") class GetStartedUsers(View): - """ find friends """ + """find friends""" def get(self, request): - """ basic profile info """ + """basic profile info""" query = request.GET.get("query") user_results = ( models.User.viewer_aware_objects(request.user) diff --git a/bookwyrm/views/goal.py b/bookwyrm/views/goal.py index 1627d3da..84091fe3 100644 --- a/bookwyrm/views/goal.py +++ b/bookwyrm/views/goal.py @@ -16,10 +16,10 @@ from .helpers import get_user_from_username # pylint: disable= no-self-use @method_decorator(login_required, name="dispatch") class Goal(View): - """ track books for the year """ + """track books for the year""" def get(self, request, username, year): - """ reading goal page """ + """reading goal page""" user = get_user_from_username(request.user, username) year = int(year) goal = models.AnnualGoal.objects.filter(year=year, user=user).first() @@ -39,7 +39,7 @@ class Goal(View): return TemplateResponse(request, "goal.html", data) def post(self, request, username, year): - """ update or create an annual goal """ + """update or create an annual goal""" user = get_user_from_username(request.user, username) if user != request.user: return HttpResponseNotFound() @@ -71,7 +71,7 @@ class Goal(View): @require_POST @login_required def hide_goal(request): - """ don't keep bugging people to set a goal """ + """don't keep bugging people to set a goal""" request.user.show_goal = False request.user.save(broadcast=False) return redirect(request.headers.get("Referer", "/")) diff --git a/bookwyrm/views/helpers.py b/bookwyrm/views/helpers.py index 57c33437..8a60b54c 100644 --- a/bookwyrm/views/helpers.py +++ b/bookwyrm/views/helpers.py @@ -11,7 +11,7 @@ from bookwyrm.utils import regex def get_user_from_username(viewer, username): - """ helper function to resolve a localname or a username to a user """ + """helper function to resolve a localname or a username to a user""" # raises DoesNotExist if user is now found try: return models.User.viewer_aware_objects(viewer).get(localname=username) @@ -20,12 +20,12 @@ def get_user_from_username(viewer, username): def is_api_request(request): - """ check whether a request is asking for html or data """ + """check whether a request is asking for html or data""" return "json" in request.headers.get("Accept", "") or request.path[-5:] == ".json" def is_bookwyrm_request(request): - """ check if the request is coming from another bookwyrm instance """ + """check if the request is coming from another bookwyrm instance""" user_agent = request.headers.get("User-Agent") if user_agent is None or re.search(regex.bookwyrm_user_agent, user_agent) is None: return False @@ -33,7 +33,7 @@ def is_bookwyrm_request(request): def privacy_filter(viewer, queryset, privacy_levels=None, following_only=False): - """ filter objects that have "user" and "privacy" fields """ + """filter objects that have "user" and "privacy" fields""" privacy_levels = privacy_levels or ["public", "unlisted", "followers", "direct"] # if there'd a deleted field, exclude deleted items try: @@ -84,7 +84,7 @@ def privacy_filter(viewer, queryset, privacy_levels=None, following_only=False): def handle_remote_webfinger(query): - """ webfingerin' other servers """ + """webfingerin' other servers""" user = None # usernames could be @user@domain or user@domain @@ -120,7 +120,7 @@ def handle_remote_webfinger(query): def get_edition(book_id): - """ look up a book in the db and return an edition """ + """look up a book in the db and return an edition""" book = models.Book.objects.select_subclasses().get(id=book_id) if isinstance(book, models.Work): book = book.get_default_edition() @@ -128,7 +128,7 @@ def get_edition(book_id): def handle_reading_status(user, shelf, book, privacy): - """ post about a user reading a book """ + """post about a user reading a book""" # tell the world about this cool thing that happened try: message = { @@ -145,14 +145,14 @@ def handle_reading_status(user, shelf, book, privacy): def is_blocked(viewer, user): - """ is this viewer blocked by the user? """ + """is this viewer blocked by the user?""" if viewer.is_authenticated and viewer in user.blocks.all(): return True return False def get_discover_books(): - """ list of books for the discover page """ + """list of books for the discover page""" return list( set( models.Edition.objects.filter( @@ -169,7 +169,7 @@ def get_discover_books(): def get_suggested_users(user): - """ bookwyrm users you don't already know """ + """bookwyrm users you don't already know""" return ( get_annotated_users( user, @@ -184,7 +184,7 @@ def get_suggested_users(user): def get_annotated_users(user, *args, **kwargs): - """ Users, annotated with things they have in common """ + """Users, annotated with things they have in common""" return ( models.User.objects.filter(discoverable=True, is_active=True, *args, **kwargs) .exclude(Q(id__in=user.blocks.all()) | Q(blocks=user)) diff --git a/bookwyrm/views/import_data.py b/bookwyrm/views/import_data.py index 5bdbe915..a2abbc69 100644 --- a/bookwyrm/views/import_data.py +++ b/bookwyrm/views/import_data.py @@ -16,10 +16,10 @@ from bookwyrm.tasks import app # pylint: disable= no-self-use @method_decorator(login_required, name="dispatch") class Import(View): - """ import view """ + """import view""" def get(self, request): - """ load import page """ + """load import page""" return TemplateResponse( request, "import.html", @@ -32,7 +32,7 @@ class Import(View): ) def post(self, request): - """ ingest a goodreads csv """ + """ingest a goodreads csv""" form = forms.ImportForm(request.POST, request.FILES) if form.is_valid(): include_reviews = request.POST.get("include_reviews") == "on" @@ -66,10 +66,10 @@ class Import(View): @method_decorator(login_required, name="dispatch") class ImportStatus(View): - """ status of an existing import """ + """status of an existing import""" def get(self, request, job_id): - """ status of an import job """ + """status of an import job""" job = models.ImportJob.objects.get(id=job_id) if job.user != request.user: raise PermissionDenied @@ -84,7 +84,7 @@ class ImportStatus(View): ) def post(self, request, job_id): - """ retry lines from an import """ + """retry lines from an import""" job = get_object_or_404(models.ImportJob, id=job_id) items = [] for item in request.POST.getlist("import_item"): diff --git a/bookwyrm/views/inbox.py b/bookwyrm/views/inbox.py index c701956d..a558c571 100644 --- a/bookwyrm/views/inbox.py +++ b/bookwyrm/views/inbox.py @@ -19,10 +19,10 @@ from bookwyrm.utils import regex @method_decorator(csrf_exempt, name="dispatch") # pylint: disable=no-self-use class Inbox(View): - """ requests sent by outside servers""" + """requests sent by outside servers""" def post(self, request, username=None): - """ only works as POST request """ + """only works as POST request""" # first check if this server is on our shitlist if is_blocked_user_agent(request): return HttpResponseForbidden() @@ -65,7 +65,7 @@ class Inbox(View): def is_blocked_user_agent(request): - """ check if a request is from a blocked server based on user agent """ + """check if a request is from a blocked server based on user agent""" # check user agent user_agent = request.headers.get("User-Agent") if not user_agent: @@ -78,7 +78,7 @@ def is_blocked_user_agent(request): def is_blocked_activity(activity_json): - """ get the sender out of activity json and check if it's blocked """ + """get the sender out of activity json and check if it's blocked""" actor = activity_json.get("actor") # check if the user is banned/deleted @@ -94,7 +94,7 @@ def is_blocked_activity(activity_json): @app.task def activity_task(activity_json): - """ do something with this json we think is legit """ + """do something with this json we think is legit""" # lets see if the activitypub module can make sense of this json activity = activitypub.parse(activity_json) @@ -104,7 +104,7 @@ def activity_task(activity_json): def has_valid_signature(request, activity): - """ verify incoming signature """ + """verify incoming signature""" try: signature = Signature.parse(request) diff --git a/bookwyrm/views/interaction.py b/bookwyrm/views/interaction.py index e337f2ef..e138e41c 100644 --- a/bookwyrm/views/interaction.py +++ b/bookwyrm/views/interaction.py @@ -12,10 +12,10 @@ from bookwyrm import models # pylint: disable= no-self-use @method_decorator(login_required, name="dispatch") class Favorite(View): - """ like a status """ + """like a status""" def post(self, request, status_id): - """ create a like """ + """create a like""" status = models.Status.objects.get(id=status_id) try: models.Favorite.objects.create(status=status, user=request.user) @@ -28,10 +28,10 @@ class Favorite(View): @method_decorator(login_required, name="dispatch") class Unfavorite(View): - """ take back a fav """ + """take back a fav""" def post(self, request, status_id): - """ unlike a status """ + """unlike a status""" status = models.Status.objects.get(id=status_id) try: favorite = models.Favorite.objects.get(status=status, user=request.user) @@ -45,10 +45,10 @@ class Unfavorite(View): @method_decorator(login_required, name="dispatch") class Boost(View): - """ boost a status """ + """boost a status""" def post(self, request, status_id): - """ boost a status """ + """boost a status""" status = models.Status.objects.get(id=status_id) # is it boostable? if not status.boostable: @@ -70,10 +70,10 @@ class Boost(View): @method_decorator(login_required, name="dispatch") class Unboost(View): - """ boost a status """ + """boost a status""" def post(self, request, status_id): - """ boost a status """ + """boost a status""" status = models.Status.objects.get(id=status_id) boost = models.Boost.objects.filter( boosted_status=status, user=request.user diff --git a/bookwyrm/views/invite.py b/bookwyrm/views/invite.py index cbb189b5..92f930f4 100644 --- a/bookwyrm/views/invite.py +++ b/bookwyrm/views/invite.py @@ -26,10 +26,10 @@ from . import helpers name="dispatch", ) class ManageInvites(View): - """ create invites """ + """create invites""" def get(self, request): - """ invite management page """ + """invite management page""" paginated = Paginator( models.SiteInvite.objects.filter(user=request.user).order_by( "-created_date" @@ -44,7 +44,7 @@ class ManageInvites(View): return TemplateResponse(request, "settings/manage_invites.html", data) def post(self, request): - """ creates an invite database entry """ + """creates an invite database entry""" form = forms.CreateInviteForm(request.POST) if not form.is_valid(): return HttpResponseBadRequest("ERRORS : %s" % (form.errors,)) @@ -64,10 +64,10 @@ class ManageInvites(View): class Invite(View): - """ use an invite to register """ + """use an invite to register""" def get(self, request, code): - """ endpoint for using an invites """ + """endpoint for using an invites""" if request.user.is_authenticated: return redirect("/") invite = get_object_or_404(models.SiteInvite, code=code) @@ -83,10 +83,10 @@ class Invite(View): class ManageInviteRequests(View): - """ grant invites like the benevolent lord you are """ + """grant invites like the benevolent lord you are""" def get(self, request): - """ view a list of requests """ + """view a list of requests""" ignored = request.GET.get("ignored", False) sort = request.GET.get("sort") sort_fields = [ @@ -132,7 +132,7 @@ class ManageInviteRequests(View): return TemplateResponse(request, "settings/manage_invite_requests.html", data) def post(self, request): - """ send out an invite """ + """send out an invite""" invite_request = get_object_or_404( models.InviteRequest, id=request.POST.get("invite-request") ) @@ -152,10 +152,10 @@ class ManageInviteRequests(View): class InviteRequest(View): - """ prospective users sign up here """ + """prospective users sign up here""" def post(self, request): - """ create a request """ + """create a request""" form = forms.InviteRequestForm(request.POST) received = False if form.is_valid(): @@ -172,7 +172,7 @@ class InviteRequest(View): @require_POST def ignore_invite_request(request): - """ hide an invite request """ + """hide an invite request""" invite_request = get_object_or_404( models.InviteRequest, id=request.POST.get("invite-request") ) diff --git a/bookwyrm/views/isbn.py b/bookwyrm/views/isbn.py index b7ba02dd..197088ba 100644 --- a/bookwyrm/views/isbn.py +++ b/bookwyrm/views/isbn.py @@ -13,10 +13,10 @@ from .helpers import is_api_request # pylint: disable= no-self-use class Isbn(View): - """ search a book by isbn """ + """search a book by isbn""" def get(self, request, isbn): - """ info about a book """ + """info about a book""" book_results = connector_manager.isbn_local_search(isbn) if is_api_request(request): diff --git a/bookwyrm/views/landing.py b/bookwyrm/views/landing.py index 407451fb..1361935e 100644 --- a/bookwyrm/views/landing.py +++ b/bookwyrm/views/landing.py @@ -9,18 +9,18 @@ from . import helpers # pylint: disable= no-self-use class About(View): - """ create invites """ + """create invites""" def get(self, request): - """ more information about the instance """ + """more information about the instance""" return TemplateResponse(request, "discover/about.html") class Home(View): - """ discover page or home feed depending on auth """ + """discover page or home feed depending on auth""" def get(self, request): - """ this is the same as the feed on the home tab """ + """this is the same as the feed on the home tab""" if request.user.is_authenticated: feed_view = Feed.as_view() return feed_view(request, "home") @@ -29,10 +29,10 @@ class Home(View): class Discover(View): - """ preview of recently reviewed books """ + """preview of recently reviewed books""" def get(self, request): - """ tiled book activity page """ + """tiled book activity page""" data = { "register_form": forms.RegisterForm(), "request_form": forms.InviteRequestForm(), diff --git a/bookwyrm/views/list.py b/bookwyrm/views/list.py index a2cf7afe..992ea4f7 100644 --- a/bookwyrm/views/list.py +++ b/bookwyrm/views/list.py @@ -22,10 +22,10 @@ from .helpers import get_user_from_username # pylint: disable=no-self-use class Lists(View): - """ book list page """ + """book list page""" def get(self, request): - """ display a book list """ + """display a book list""" # hide lists with no approved books lists = ( models.List.objects.annotate( @@ -51,7 +51,7 @@ class Lists(View): @method_decorator(login_required, name="dispatch") # pylint: disable=unused-argument def post(self, request): - """ create a book_list """ + """create a book_list""" form = forms.ListForm(request.POST) if not form.is_valid(): return redirect("lists") @@ -61,10 +61,10 @@ class Lists(View): class UserLists(View): - """ a user's book list page """ + """a user's book list page""" def get(self, request, username): - """ display a book list """ + """display a book list""" user = get_user_from_username(request.user, username) lists = models.List.objects.filter(user=user) lists = privacy_filter(request.user, lists) @@ -81,10 +81,10 @@ class UserLists(View): class List(View): - """ book list page """ + """book list page""" def get(self, request, list_id): - """ display a book list """ + """display a book list""" book_list = get_object_or_404(models.List, id=list_id) if not book_list.visible_to_user(request.user): return HttpResponseNotFound() @@ -166,7 +166,7 @@ class List(View): @method_decorator(login_required, name="dispatch") # pylint: disable=unused-argument def post(self, request, list_id): - """ edit a list """ + """edit a list""" book_list = get_object_or_404(models.List, id=list_id) form = forms.ListForm(request.POST, instance=book_list) if not form.is_valid(): @@ -176,11 +176,11 @@ class List(View): class Curate(View): - """ approve or discard list suggestsions """ + """approve or discard list suggestsions""" @method_decorator(login_required, name="dispatch") def get(self, request, list_id): - """ display a pending list """ + """display a pending list""" book_list = get_object_or_404(models.List, id=list_id) if not book_list.user == request.user: # only the creater can curate the list @@ -196,7 +196,7 @@ class Curate(View): @method_decorator(login_required, name="dispatch") # pylint: disable=unused-argument def post(self, request, list_id): - """ edit a book_list """ + """edit a book_list""" book_list = get_object_or_404(models.List, id=list_id) suggestion = get_object_or_404(models.ListItem, id=request.POST.get("item")) approved = request.POST.get("approved") == "true" @@ -222,7 +222,7 @@ class Curate(View): @require_POST def add_book(request): - """ put a book on a list """ + """put a book on a list""" book_list = get_object_or_404(models.List, id=request.POST.get("list")) if not book_list.visible_to_user(request.user): return HttpResponseNotFound() @@ -268,7 +268,7 @@ def add_book(request): @require_POST def remove_book(request, list_id): - """ remove a book from a list """ + """remove a book from a list""" with transaction.atomic(): book_list = get_object_or_404(models.List, id=list_id) item = get_object_or_404(models.ListItem, id=request.POST.get("item")) @@ -336,7 +336,7 @@ def set_book_position(request, list_item_id): def increment_order_in_reverse( book_list_id: int, start: int, end: Optional[int] = None ): - """ increase the order nu,ber for every item in a list """ + """increase the order nu,ber for every item in a list""" try: book_list = models.List.objects.get(id=book_list_id) except models.List.DoesNotExist: @@ -352,7 +352,7 @@ def increment_order_in_reverse( @transaction.atomic def decrement_order(book_list_id, start, end): - """ decrement the order value for every item in a list """ + """decrement the order value for every item in a list""" try: book_list = models.List.objects.get(id=book_list_id) except models.List.DoesNotExist: @@ -367,7 +367,7 @@ def decrement_order(book_list_id, start, end): @transaction.atomic def normalize_book_list_ordering(book_list_id, start=0, add_offset=0): - """ gives each book in a list the proper sequential order number """ + """gives each book in a list the proper sequential order number""" try: book_list = models.List.objects.get(id=book_list_id) except models.List.DoesNotExist: diff --git a/bookwyrm/views/notifications.py b/bookwyrm/views/notifications.py index 7a62ec01..e0e2102d 100644 --- a/bookwyrm/views/notifications.py +++ b/bookwyrm/views/notifications.py @@ -9,10 +9,10 @@ from django.views import View # pylint: disable= no-self-use @method_decorator(login_required, name="dispatch") class Notifications(View): - """ notifications view """ + """notifications view""" def get(self, request): - """ people are interacting with you, get hyped """ + """people are interacting with you, get hyped""" notifications = request.user.notification_set.all().order_by("-created_date") unread = [n.id for n in notifications.filter(read=False)] data = { @@ -23,6 +23,6 @@ class Notifications(View): return TemplateResponse(request, "notifications.html", data) def post(self, request): - """ permanently delete notification for user """ + """permanently delete notification for user""" request.user.notification_set.filter(read=True).delete() return redirect("/notifications") diff --git a/bookwyrm/views/outbox.py b/bookwyrm/views/outbox.py index ec6f5cd3..4bc2d2b9 100644 --- a/bookwyrm/views/outbox.py +++ b/bookwyrm/views/outbox.py @@ -9,10 +9,10 @@ from .helpers import is_bookwyrm_request # pylint: disable= no-self-use class Outbox(View): - """ outbox """ + """outbox""" def get(self, request, username): - """ outbox for the requested user """ + """outbox for the requested user""" user = get_object_or_404(models.User, localname=username) filter_type = request.GET.get("type") if filter_type not in models.status_models: diff --git a/bookwyrm/views/password.py b/bookwyrm/views/password.py index 67010974..933817a8 100644 --- a/bookwyrm/views/password.py +++ b/bookwyrm/views/password.py @@ -14,17 +14,17 @@ from bookwyrm.emailing import password_reset_email # pylint: disable= no-self-use class PasswordResetRequest(View): - """ forgot password flow """ + """forgot password flow""" def get(self, request): - """ password reset page """ + """password reset page""" return TemplateResponse( request, "password_reset_request.html", ) def post(self, request): - """ create a password reset token """ + """create a password reset token""" email = request.POST.get("email") try: user = models.User.objects.get(email=email) @@ -43,10 +43,10 @@ class PasswordResetRequest(View): class PasswordReset(View): - """ set new password """ + """set new password""" def get(self, request, code): - """ endpoint for sending invites """ + """endpoint for sending invites""" if request.user.is_authenticated: return redirect("/") try: @@ -59,7 +59,7 @@ class PasswordReset(View): return TemplateResponse(request, "password_reset.html", {"code": code}) def post(self, request, code): - """ allow a user to change their password through an emailed token """ + """allow a user to change their password through an emailed token""" try: reset_code = models.PasswordReset.objects.get(code=code) except models.PasswordReset.DoesNotExist: @@ -84,15 +84,15 @@ class PasswordReset(View): @method_decorator(login_required, name="dispatch") class ChangePassword(View): - """ change password as logged in user """ + """change password as logged in user""" def get(self, request): - """ change password page """ + """change password page""" data = {"user": request.user} return TemplateResponse(request, "preferences/change_password.html", data) def post(self, request): - """ allow a user to change their password """ + """allow a user to change their password""" new_password = request.POST.get("password") confirm_password = request.POST.get("confirm-password") diff --git a/bookwyrm/views/reading.py b/bookwyrm/views/reading.py index f2d5b2c2..65ca717d 100644 --- a/bookwyrm/views/reading.py +++ b/bookwyrm/views/reading.py @@ -18,7 +18,7 @@ from .shelf import handle_unshelve @login_required @require_POST def start_reading(request, book_id): - """ begin reading a book """ + """begin reading a book""" book = get_edition(book_id) reading_shelf = models.Shelf.objects.filter( identifier=models.Shelf.READING, user=request.user @@ -60,7 +60,7 @@ def start_reading(request, book_id): @login_required @require_POST def finish_reading(request, book_id): - """ a user completed a book, yay """ + """a user completed a book, yay""" book = get_edition(book_id) finished_read_shelf = models.Shelf.objects.filter( identifier=models.Shelf.READ_FINISHED, user=request.user @@ -101,7 +101,7 @@ def finish_reading(request, book_id): @login_required @require_POST def edit_readthrough(request): - """ can't use the form because the dates are too finnicky """ + """can't use the form because the dates are too finnicky""" readthrough = update_readthrough(request, create=False) if not readthrough: return HttpResponseNotFound() @@ -121,7 +121,7 @@ def edit_readthrough(request): @login_required @require_POST def delete_readthrough(request): - """ remove a readthrough """ + """remove a readthrough""" readthrough = get_object_or_404(models.ReadThrough, id=request.POST.get("id")) # don't let people edit other people's data @@ -135,7 +135,7 @@ def delete_readthrough(request): @login_required @require_POST def create_readthrough(request): - """ can't use the form because the dates are too finnicky """ + """can't use the form because the dates are too finnicky""" book = get_object_or_404(models.Edition, id=request.POST.get("book")) readthrough = update_readthrough(request, create=True, book=book) if not readthrough: @@ -145,14 +145,14 @@ def create_readthrough(request): def load_date_in_user_tz_as_utc(date_str: str, user: models.User) -> datetime: - """ ensures that data is stored consistently in the UTC timezone """ + """ensures that data is stored consistently in the UTC timezone""" user_tz = dateutil.tz.gettz(user.preferred_timezone) start_date = dateutil.parser.parse(date_str, ignoretz=True) return start_date.replace(tzinfo=user_tz).astimezone(dateutil.tz.UTC) def update_readthrough(request, book=None, create=True): - """ updates but does not save dates on a readthrough """ + """updates but does not save dates on a readthrough""" try: read_id = request.POST.get("id") if not read_id: @@ -209,7 +209,7 @@ def update_readthrough(request, book=None, create=True): @login_required @require_POST def delete_progressupdate(request): - """ remove a progress update """ + """remove a progress update""" update = get_object_or_404(models.ProgressUpdate, id=request.POST.get("id")) # don't let people edit other people's data diff --git a/bookwyrm/views/reports.py b/bookwyrm/views/reports.py index 07eb9b97..46c23884 100644 --- a/bookwyrm/views/reports.py +++ b/bookwyrm/views/reports.py @@ -20,10 +20,10 @@ from bookwyrm import forms, models name="dispatch", ) class Reports(View): - """ list of reports """ + """list of reports""" def get(self, request): - """ view current reports """ + """view current reports""" filters = {} resolved = request.GET.get("resolved") == "true" @@ -52,17 +52,17 @@ class Reports(View): name="dispatch", ) class Report(View): - """ view a specific report """ + """view a specific report""" def get(self, request, report_id): - """ load a report """ + """load a report""" data = { "report": get_object_or_404(models.Report, id=report_id), } return TemplateResponse(request, "moderation/report.html", data) def post(self, request, report_id): - """ comment on a report """ + """comment on a report""" report = get_object_or_404(models.Report, id=report_id) models.ReportComment.objects.create( user=request.user, @@ -75,7 +75,7 @@ class Report(View): @login_required @permission_required("bookwyrm_moderate_user") def suspend_user(_, user_id): - """ mark an account as inactive """ + """mark an account as inactive""" user = get_object_or_404(models.User, id=user_id) user.is_active = not user.is_active # this isn't a full deletion, so we don't want to tell the world @@ -86,7 +86,7 @@ def suspend_user(_, user_id): @login_required @permission_required("bookwyrm_moderate_post") def resolve_report(_, report_id): - """ mark a report as (un)resolved """ + """mark a report as (un)resolved""" report = get_object_or_404(models.Report, id=report_id) report.resolved = not report.resolved report.save() @@ -98,7 +98,7 @@ def resolve_report(_, report_id): @login_required @require_POST def make_report(request): - """ a user reports something """ + """a user reports something""" form = forms.ReportForm(request.POST) if not form.is_valid(): raise ValueError(form.errors) diff --git a/bookwyrm/views/rss_feed.py b/bookwyrm/views/rss_feed.py index ed3e84f4..f1678b7f 100644 --- a/bookwyrm/views/rss_feed.py +++ b/bookwyrm/views/rss_feed.py @@ -5,25 +5,25 @@ from .helpers import get_user_from_username, privacy_filter # pylint: disable=no-self-use, unused-argument class RssFeed(Feed): - """ serialize user's posts in rss feed """ + """serialize user's posts in rss feed""" description_template = "snippets/rss_content.html" title_template = "snippets/rss_title.html" def get_object(self, request, username): - """ the user who's posts get serialized """ + """the user who's posts get serialized""" return get_user_from_username(request.user, username) def link(self, obj): - """ link to the user's profile """ + """link to the user's profile""" return obj.local_path def title(self, obj): - """ title of the rss feed entry """ + """title of the rss feed entry""" return f"Status updates from {obj.display_name}" def items(self, obj): - """ the user's activity feed """ + """the user's activity feed""" return privacy_filter( obj, obj.status_set.select_subclasses(), @@ -31,5 +31,5 @@ class RssFeed(Feed): ) def item_link(self, item): - """ link to the status """ + """link to the status""" return item.local_path diff --git a/bookwyrm/views/search.py b/bookwyrm/views/search.py index 9e7df9f4..4543b55e 100644 --- a/bookwyrm/views/search.py +++ b/bookwyrm/views/search.py @@ -16,10 +16,10 @@ from .helpers import handle_remote_webfinger # pylint: disable= no-self-use class Search(View): - """ search users or books """ + """search users or books""" def get(self, request): - """ that search bar up top """ + """that search bar up top""" query = request.GET.get("q") min_confidence = request.GET.get("min_confidence", 0.1) diff --git a/bookwyrm/views/shelf.py b/bookwyrm/views/shelf.py index 446bedba..9bcf0a4a 100644 --- a/bookwyrm/views/shelf.py +++ b/bookwyrm/views/shelf.py @@ -21,10 +21,10 @@ from .helpers import handle_reading_status, privacy_filter # pylint: disable= no-self-use class Shelf(View): - """ shelf page """ + """shelf page""" def get(self, request, username, shelf_identifier=None): - """ display a shelf """ + """display a shelf""" try: user = get_user_from_username(request.user, username) except models.User.DoesNotExist: @@ -73,7 +73,7 @@ class Shelf(View): @method_decorator(login_required, name="dispatch") # pylint: disable=unused-argument def post(self, request, username, shelf_identifier): - """ edit a shelf """ + """edit a shelf""" try: shelf = request.user.shelf_set.get(identifier=shelf_identifier) except models.Shelf.DoesNotExist: @@ -94,7 +94,7 @@ class Shelf(View): @login_required @require_POST def create_shelf(request): - """ user generated shelves """ + """user generated shelves""" form = forms.ShelfForm(request.POST) if not form.is_valid(): return redirect(request.headers.get("Referer", "/")) @@ -106,7 +106,7 @@ def create_shelf(request): @login_required @require_POST def delete_shelf(request, shelf_id): - """ user generated shelves """ + """user generated shelves""" shelf = get_object_or_404(models.Shelf, id=shelf_id) if request.user != shelf.user or not shelf.editable: return HttpResponseBadRequest() @@ -118,7 +118,7 @@ def delete_shelf(request, shelf_id): @login_required @require_POST def shelve(request): - """ put a book on a user's shelf """ + """put a book on a user's shelf""" book = get_edition(request.POST.get("book")) desired_shelf = models.Shelf.objects.filter( @@ -177,7 +177,7 @@ def shelve(request): @login_required @require_POST def unshelve(request): - """ put a on a user's shelf """ + """put a on a user's shelf""" book = models.Edition.objects.get(id=request.POST["book"]) current_shelf = models.Shelf.objects.get(id=request.POST["shelf"]) @@ -187,6 +187,6 @@ def unshelve(request): # pylint: disable=unused-argument def handle_unshelve(book, shelf): - """ unshelve a book """ + """unshelve a book""" row = models.ShelfBook.objects.get(book=book, shelf=shelf) row.delete() diff --git a/bookwyrm/views/site.py b/bookwyrm/views/site.py index e5897660..46bdf722 100644 --- a/bookwyrm/views/site.py +++ b/bookwyrm/views/site.py @@ -15,16 +15,16 @@ from bookwyrm import emailing, forms, models name="dispatch", ) class Site(View): - """ manage things like the instance name """ + """manage things like the instance name""" def get(self, request): - """ edit form """ + """edit form""" site = models.SiteSettings.objects.get() data = {"site_form": forms.SiteForm(instance=site)} return TemplateResponse(request, "settings/site.html", data) def post(self, request): - """ edit the site settings """ + """edit the site settings""" site = models.SiteSettings.objects.get() form = forms.SiteForm(request.POST, request.FILES, instance=site) if not form.is_valid(): @@ -38,7 +38,7 @@ class Site(View): @login_required @permission_required("bookwyrm.edit_instance_settings", raise_exception=True) def email_preview(request): - """ for development, renders and example email template """ + """for development, renders and example email template""" template = request.GET.get("email") data = emailing.email_data() data["subject_path"] = "email/{}/subject.html".format(template) diff --git a/bookwyrm/views/status.py b/bookwyrm/views/status.py index f0119e0e..2295c8cc 100644 --- a/bookwyrm/views/status.py +++ b/bookwyrm/views/status.py @@ -19,16 +19,16 @@ from .reading import edit_readthrough # pylint: disable= no-self-use @method_decorator(login_required, name="dispatch") class CreateStatus(View): - """ the view for *posting* """ + """the view for *posting*""" def get(self, request): - """ compose view (used for delete-and-redraft """ + """compose view (used for delete-and-redraft""" book = get_object_or_404(models.Edition, id=request.GET.get("book")) data = {"book": book} return TemplateResponse(request, "compose.html", data) def post(self, request, status_type): - """ create status of whatever type """ + """create status of whatever type""" status_type = status_type[0].upper() + status_type[1:] try: @@ -80,10 +80,10 @@ class CreateStatus(View): @method_decorator(login_required, name="dispatch") class DeleteStatus(View): - """ tombstone that bad boy """ + """tombstone that bad boy""" def post(self, request, status_id): - """ delete and tombstone a status """ + """delete and tombstone a status""" status = get_object_or_404(models.Status, id=status_id) # don't let people delete other people's statuses @@ -97,10 +97,10 @@ class DeleteStatus(View): @method_decorator(login_required, name="dispatch") class DeleteAndRedraft(View): - """ delete a status but let the user re-create it """ + """delete a status but let the user re-create it""" def post(self, request, status_id): - """ delete and tombstone a status """ + """delete and tombstone a status""" status = get_object_or_404( models.Status.objects.select_subclasses(), id=status_id ) @@ -130,7 +130,7 @@ class DeleteAndRedraft(View): def find_mentions(content): - """ detect @mentions in raw status content """ + """detect @mentions in raw status content""" if not content: return for match in re.finditer(regex.strict_username, content): @@ -148,7 +148,7 @@ def find_mentions(content): def format_links(content): - """ detect and format links """ + """detect and format links""" return re.sub( r'([^(href=")]|^|\()(https?:\/\/(%s([\w\.\-_\/+&\?=:;,])*))' % regex.domain, r'\g<1>\g<3>', @@ -157,7 +157,7 @@ def format_links(content): def to_markdown(content): - """ catch links and convert to markdown """ + """catch links and convert to markdown""" content = markdown(content) content = format_links(content) # sanitize resulting html diff --git a/bookwyrm/views/updates.py b/bookwyrm/views/updates.py index cc5fc419..34902272 100644 --- a/bookwyrm/views/updates.py +++ b/bookwyrm/views/updates.py @@ -7,7 +7,7 @@ from bookwyrm import activitystreams @login_required def get_notification_count(request): - """ any notifications waiting? """ + """any notifications waiting?""" return JsonResponse( { "count": request.user.notification_set.filter(read=False).count(), @@ -17,7 +17,7 @@ def get_notification_count(request): @login_required def get_unread_status_count(request, stream="home"): - """ any unread statuses for this feed? """ + """any unread statuses for this feed?""" stream = activitystreams.streams.get(stream) if not stream: return JsonResponse({}) diff --git a/bookwyrm/views/user.py b/bookwyrm/views/user.py index 02db5971..05fdb606 100644 --- a/bookwyrm/views/user.py +++ b/bookwyrm/views/user.py @@ -22,10 +22,10 @@ from .helpers import is_blocked, privacy_filter # pylint: disable= no-self-use class User(View): - """ user profile page """ + """user profile page""" def get(self, request, username): - """ profile page for a user """ + """profile page for a user""" try: user = get_user_from_username(request.user, username) except models.User.DoesNotExist: @@ -90,10 +90,10 @@ class User(View): class Followers(View): - """ list of followers view """ + """list of followers view""" def get(self, request, username): - """ list of followers """ + """list of followers""" try: user = get_user_from_username(request.user, username) except models.User.DoesNotExist: @@ -115,10 +115,10 @@ class Followers(View): class Following(View): - """ list of following view """ + """list of following view""" def get(self, request, username): - """ list of followers """ + """list of followers""" try: user = get_user_from_username(request.user, username) except models.User.DoesNotExist: @@ -141,10 +141,10 @@ class Following(View): @method_decorator(login_required, name="dispatch") class EditUser(View): - """ edit user view """ + """edit user view""" def get(self, request): - """ edit profile page for a user """ + """edit profile page for a user""" data = { "form": forms.EditUserForm(instance=request.user), "user": request.user, @@ -152,7 +152,7 @@ class EditUser(View): return TemplateResponse(request, "preferences/edit_user.html", data) def post(self, request): - """ les get fancy with images """ + """les get fancy with images""" form = forms.EditUserForm(request.POST, request.FILES, instance=request.user) if not form.is_valid(): data = {"form": form, "user": request.user} @@ -164,7 +164,7 @@ class EditUser(View): def save_user_form(form): - """ special handling for the user form """ + """special handling for the user form""" user = form.save(commit=False) if "avatar" in form.files: @@ -181,7 +181,7 @@ def save_user_form(form): def crop_avatar(image): - """ reduce the size and make an avatar square """ + """reduce the size and make an avatar square""" target_size = 120 width, height = image.size thumbnail_scale = ( diff --git a/bookwyrm/views/user_admin.py b/bookwyrm/views/user_admin.py index 4537abce..9d08e930 100644 --- a/bookwyrm/views/user_admin.py +++ b/bookwyrm/views/user_admin.py @@ -17,10 +17,10 @@ from bookwyrm.settings import PAGE_LENGTH name="dispatch", ) class UserAdminList(View): - """ admin view of users on this server """ + """admin view of users on this server""" def get(self, request): - """ list of users """ + """list of users""" filters = {} server = request.GET.get("server") if server: @@ -59,16 +59,16 @@ class UserAdminList(View): name="dispatch", ) class UserAdmin(View): - """ moderate an individual user """ + """moderate an individual user""" def get(self, request, user): - """ user view """ + """user view""" user = get_object_or_404(models.User, id=user) data = {"user": user, "group_form": forms.UserGroupForm()} return TemplateResponse(request, "user_admin/user.html", data) def post(self, request, user): - """ update user group """ + """update user group""" user = get_object_or_404(models.User, id=user) form = forms.UserGroupForm(request.POST, instance=user) if form.is_valid(): diff --git a/bookwyrm/views/wellknown.py b/bookwyrm/views/wellknown.py index 178d558e..2462c5a4 100644 --- a/bookwyrm/views/wellknown.py +++ b/bookwyrm/views/wellknown.py @@ -13,7 +13,7 @@ from bookwyrm.settings import DOMAIN, VERSION @require_GET def webfinger(request): - """ allow other servers to ask about a user """ + """allow other servers to ask about a user""" resource = request.GET.get("resource") if not resource or not resource.startswith("acct:"): return HttpResponseNotFound() @@ -40,7 +40,7 @@ def webfinger(request): @require_GET def nodeinfo_pointer(_): - """ direct servers to nodeinfo """ + """direct servers to nodeinfo""" return JsonResponse( { "links": [ @@ -55,7 +55,7 @@ def nodeinfo_pointer(_): @require_GET def nodeinfo(_): - """ basic info about the server """ + """basic info about the server""" status_count = models.Status.objects.filter(user__local=True).count() user_count = models.User.objects.filter(local=True).count() @@ -90,7 +90,7 @@ def nodeinfo(_): @require_GET def instance_info(_): - """ let's talk about your cool unique instance """ + """let's talk about your cool unique instance""" user_count = models.User.objects.filter(local=True).count() status_count = models.Status.objects.filter(user__local=True).count() @@ -116,12 +116,12 @@ def instance_info(_): @require_GET def peers(_): - """ list of federated servers this instance connects with """ + """list of federated servers this instance connects with""" names = models.FederatedServer.objects.values_list("server_name", flat=True) return JsonResponse(list(names), safe=False) @require_GET def host_meta(request): - """ meta of the host """ + """meta of the host""" return TemplateResponse(request, "host_meta.xml", {"DOMAIN": DOMAIN}) diff --git a/requirements.txt b/requirements.txt index 6b7d82d3..665e3253 100644 --- a/requirements.txt +++ b/requirements.txt @@ -15,7 +15,7 @@ django-rename-app==0.1.2 pytz>=2021.1 # Dev -black==20.8b1 +black==21.4b0 coverage==5.1 pytest-django==4.1.0 pytest==6.1.2