MCPcopy Create free account
hub / github.com/TimMcCool/scratchattach / loves

Method loves

scratchattach/site/user.py:582–679  ·  view source on GitHub ↗

Returns: list : The user's loved projects

(self, *, limit=40, offset=0, get_full_project: bool = False)

Source from the content-addressed store, hash-verified

580 return commons.parse_object_list(_projects, project.Project, self._session)
581
582 def loves(self, *, limit=40, offset=0, get_full_project: bool = False) -> list[project.Project]:
583 """
584 Returns:
585 list<projects.projects.Project>: The user&#x27;s loved projects
586 """
587 # We need to use beautifulsoup webscraping so we cant use the api_iterative function
588 if offset < 0:
589 raise exceptions.BadRequest("offset parameter must be >= 0")
590 if limit < 0:
591 raise exceptions.BadRequest("limit parameter must be >= 0")
592
593 # There are 40 projects on display per page
594 # So the first page you need to view is 1 + offset // 40
595 # (You have to add one because the first page is idx 1 instead of 0)
596
597 # The final project to view is at idx offset + limit - 1
598 # (You have to -1 because the index starts at 0)
599 # So the page number for this is 1 + (offset + limit - 1) // 40
600
601 # But this is a range so we have to add another 1 for the second argument
602 pages = range(1 + offset // 40, 2 + (offset + limit - 1) // 40)
603 _projects = []
604
605 for page in pages:
606 # The index of the first project on page #n is just (n-1) * 40
607 first_idx = (page - 1) * 40
608
609 with requests.no_error_handling():
610 page_content = requests.get(
611 f"https://scratch.mit.edu/projects/all/{self.username}/loves/?page={page}",
612 headers=self._headers,
613 ).content
614
615 soup = BeautifulSoup(page_content, "html.parser")
616
617 # We need to check if we are out of bounds
618 # If we are, we can jump out early
619 # This is detectable if Scratch gives you a '404'
620
621 # We can't just detect if the 404 text is within the whole of the page content
622 # because it would break if someone made a project with that name
623
624 # This page only uses <h1> tags for the 404 text, so we can just use a soup for those
625 h1_tag = soup.find("h1")
626 if h1_tag is not None:
627 # Just to confirm that it's a 404, in case I am wrong. It can't hurt
628 if "Whoops! Our server is Scratch'ing its head" in h1_tag.text:
629 break
630
631 # Each project element is a list item with the class name 'project thumb item' so we can just use that
632 for i, project_element in enumerate(soup.find_all("li", {"class": "project thumb item"})):
633 # Remember we only want certain projects:
634 # The current project idx = first_idx + i
635 # We want to start at {offset} and end at {offset + limit}
636
637 # So the offset <= current project idx <= offset + limit
638 if offset <= first_idx + i <= offset + limit:
639 # Each of these elements provides:

Callers 1

test_userFunction · 0.80

Calls 5

rangeFunction · 0.85
no_error_handlingMethod · 0.45
getMethod · 0.45
findMethod · 0.45
updateMethod · 0.45

Tested by 1

test_userFunction · 0.64