Parses the DOM and returns media attributes in the sidebar.

    :type media_page: :class:`bs4.BeautifulSoup`
    :param media_page: MAL media page's DOM

    :rtype: dict
    :return: media attributes.

    :raises: InvalidMediaError, MalformedMediaPageError

def parse_sidebar(self, media_page):
    """Parses the DOM and returns media attributes in the sidebar.

    :type media_page: :class:`bs4.BeautifulSoup`
    :param media_page: MAL media page's DOM

    :rtype: dict
    :return: media attributes.

    :raises: InvalidMediaError, MalformedMediaPageError

    """
    media_info = {}

    # if MAL says the series doesn't exist, raise an InvalidMediaError.
    error_tag = media_page.find(u'div', {'class': 'badresult'})
    if error_tag:
        raise InvalidMediaError(self.id)

    try:
      title_tag = media_page.find(u'div', {'id': 'contentWrapper'}).find(u'h1')
      if not title_tag.find(u'div'):
        # otherwise, raise a MalformedMediaPageError.
        raise MalformedMediaPageError(self.id, media_page, message="Could not find title div")
    except:
      if not self.session.suppress_parse_exceptions:
        raise

    try:
      utilities.extract_tags(title_tag.find_all())
      media_info[u'title'] = title_tag.text.strip()
    except:
      if not self.session.suppress_parse_exceptions:
        raise

    info_panel_first = media_page.find(u'div', {'id': 'content'}).find(u'table').find(u'td')

    try:
      picture_tag = info_panel_first.find(u'img')
      media_info[u'picture'] = picture_tag.get(u'src').decode('utf-8')
    except:
      if not self.session.suppress_parse_exceptions:
        raise

    try:
      # assemble alternative titles for this series.
      media_info[u'alternative_titles'] = {}
      alt_titles_header = info_panel_first.find(u'h2', text=u'Alternative Titles')
      if alt_titles_header:
        next_tag = alt_titles_header.find_next_sibling(u'div', {'class': 'spaceit_pad'})
        while True:
          if next_tag is None or not next_tag.find(u'span', {'class': 'dark_text'}):
            # not a language node, break.
            break
          # get language and remove the node.
          language = next_tag.find(u'span').text[:-1]
          utilities.extract_tags(next_tag.find_all(u'span', {'class': 'dark_text'}))
          names = next_tag.text.strip().split(u', ')
          media_info[u'alternative_titles'][language] = names
          next_tag = next_tag.find_next_sibling(u'div', {'class': 'spaceit_pad'})
    except:
      if not self.session.suppress_parse_exceptions:
        raise

    try:
      type_tag = info_panel_first.find(text=u'Type:').parent.parent
      utilities.extract_tags(type_tag.find_all(u'span', {'class': 'dark_text'}))
      media_info[u'type'] = type_tag.text.strip()
    except:
      if not self.session.suppress_parse_exceptions:
        raise

    try:
      status_tag = info_panel_first.find(text=u'Status:').parent.parent
      utilities.extract_tags(status_tag.find_all(u'span', {'class': 'dark_text'}))
      media_info[u'status'] = status_tag.text.strip()
    except:
      if not self.session.suppress_parse_exceptions:
        raise

    try:
      genres_tag = info_panel_first.find(text=u'Genres:').parent.parent
      utilities.extract_tags(genres_tag.find_all(u'span', {'class': 'dark_text'}))
      media_info[u'genres'] = []
      for genre_link in genres_tag.find_all('a'):
        link_parts = genre_link.get('href').split('[]=')
        # of the form /anime|manga.php?genre[]=1
        genre = self.session.genre(int(link_parts[1])).set({'name': genre_link.text})
        media_info[u'genres'].append(genre)
    except:
      if not self.session.suppress_parse_exceptions:
        raise

    try:
      # grab statistics for this media.
      score_tag = info_panel_first.find(text=u'Score:').parent.parent
      # get score and number of users.
      users_node = [x for x in score_tag.find_all(u'small') if u'scored by' in x.text][0]
      num_users = int(users_node.text.split(u'scored by ')[-1].split(u' users')[0])
      utilities.extract_tags(score_tag.find_all())
      media_info[u'score'] = (decimal.Decimal(score_tag.text.strip()), num_users)
    except:
      if not self.session.suppress_parse_exceptions:
        raise

    try:
      rank_tag = info_panel_first.find(text=u'Ranked:').parent.parent
      utilities.extract_tags(rank_tag.find_all())
      media_info[u'rank'] = int(rank_tag.text.strip()[1:].replace(u',', ''))
    except:
      if not self.session.suppress_parse_exceptions:
        raise

    try:
      popularity_tag = info_panel_first.find(text=u'Popularity:').parent.parent
      utilities.extract_tags(popularity_tag.find_all())
      media_info[u'popularity'] = int(popularity_tag.text.strip()[1:].replace(u',', ''))
    except:
      if not self.session.suppress_parse_exceptions:
        raise

    try:
      members_tag = info_panel_first.find(text=u'Members:').parent.parent
      utilities.extract_tags(members_tag.find_all())
      media_info[u'members'] = int(members_tag.text.strip().replace(u',', ''))
    except:
      if not self.session.suppress_parse_exceptions:
        raise

    try:
      favorites_tag = info_panel_first.find(text=u'Favorites:').parent.parent
      utilities.extract_tags(favorites_tag.find_all())
      media_info[u'favorites'] = int(favorites_tag.text.strip().replace(u',', ''))
    except:
      if not self.session.suppress_parse_exceptions:
        raise

    try:
      # get popular tags.
      tags_header = media_page.find(u'h2', text=u'Popular Tags')
      tags_tag = tags_header.find_next_sibling(u'span')
      media_info[u'popular_tags'] = {}
      for tag_link in tags_tag.find_all('a'):
        tag = self.session.tag(tag_link.text)
        num_people = int(re.match(r'(?P<people>[0-9]+) people', tag_link.get('title')).group('people'))
        media_info[u'popular_tags'][tag] = num_people
    except:
      if not self.session.suppress_parse_exceptions:
        raise

    return media_info