# Path: feedhq/feeds/models.py
# def enqueue_favicon(url, force_update=False):
#     enqueue(update_favicon, args=[url], kwargs={'force_update': force_update},
#             queue='favicons')
# 
# class UniqueFeed(JobDataMixin, models.Model):
#     GONE = 'gone'
#     TIMEOUT = 'timeout'
#     PARSE_ERROR = 'parseerror'
#     CONNECTION_ERROR = 'connerror'
#     DECODE_ERROR = 'decodeerror'
#     NOT_A_FEED = 'notafeed'
#     HTTP_400 = '400'
#     HTTP_401 = '401'
#     HTTP_403 = '403'
#     HTTP_404 = '404'
#     HTTP_500 = '500'
#     HTTP_502 = '502'
#     HTTP_503 = '503'
#     MUTE_CHOICES = (
#         (GONE, 'Feed gone (410)'),
#         (TIMEOUT, 'Feed timed out'),
#         (PARSE_ERROR, 'Location parse error'),
#         (CONNECTION_ERROR, 'Connection error'),
#         (DECODE_ERROR, 'Decoding error'),
#         (NOT_A_FEED, 'Not a valid RSS/Atom feed'),
#         (HTTP_400, 'HTTP 400'),
#         (HTTP_401, 'HTTP 401'),
#         (HTTP_403, 'HTTP 403'),
#         (HTTP_404, 'HTTP 404'),
#         (HTTP_500, 'HTTP 500'),
#         (HTTP_502, 'HTTP 502'),
#         (HTTP_503, 'HTTP 503'),
#     )
#     MUTE_DICT = dict(MUTE_CHOICES)
# 
#     url = URLField(_('URL'), unique=True)
#     muted = models.BooleanField(_('Muted'), default=False, db_index=True)
#     error = models.CharField(_('Error'), max_length=50, null=True, blank=True,
#                              choices=MUTE_CHOICES, db_column='muted_reason')
# 
#     objects = UniqueFeedManager()
# 
#     MAX_BACKOFF = 10  # Approx. 24 hours
#     UPDATE_PERIOD = 60  # in minutes
#     BACKOFF_EXPONENT = 1.5
#     TIMEOUT_BASE = 20
#     JOB_ATTRS = ['modified', 'etag', 'backoff_factor', 'error', 'link',
#                  'title', 'hub', 'subscribers', 'last_update']
# 
#     def __str__(self):
#         return u'%s' % self.url
# 
#     def truncated_url(self):
#         if len(self.url) > 50:
#             return self.url[:49] + u'…'
#         return self.url
#     truncated_url.short_description = _('URL')
#     truncated_url.admin_order_field = 'url'
# 
#     @classmethod
#     def request_timeout(cls, backoff_factor):
#         return 10 * backoff_factor
# 
#     @classmethod
#     def delay(cls, backoff_factor, hub=None):
#         if hub is not None:
#             backoff_factor = max(backoff_factor, 3)
#         return datetime.timedelta(
#             seconds=60 * cls.UPDATE_PERIOD *
#             backoff_factor ** cls.BACKOFF_EXPONENT)
# 
#     @property
#     def schedule_in(self):
#         return (
#             self.last_update + self.delay(self.job_details['backoff_factor'],
#                                           self.job_details.get('hub'))
#         ) - timezone.now()
# 
#     def schedule(self, schedule_in=None, **job):
#         if hasattr(self, '_job_details'):
#             del self._job_details
#         connection = get_redis_connection()
#         kwargs = {
#             'subscribers': 1,
#             'backoff_factor': 1,
#             'last_update': int(time.time()),
#         }
#         kwargs.update(job)
#         if schedule_in is None:
#             try:
#                 for attr in self.JOB_ATTRS:
#                     if attr in self.job_details:
#                         kwargs[attr] = self.job_details[attr]
#                 schedule_in = self.schedule_in
#             except JobNotFound:
#                 schedule_in = self.delay(kwargs['backoff_factor'])
#         schedule_job(self.url, schedule_in=schedule_in,
#                      connection=connection, **kwargs)


from . import SentryCommand
from ...models import enqueue_favicon, UniqueFeed


class Command(SentryCommand):
    """Fetches favicon updates and saves them if there are any"""

    def add_arguments(self, parser):
        parser.add_argument('--all', action='store_true', dest='all',
                            default=False,
                            help='Force update of all existing favicons')

    def handle_sentry(self, *args, **kwargs):

# Path: feedhq/feeds/models.py
# def enqueue_favicon(url, force_update=False):
#     enqueue(update_favicon, args=[url], kwargs={'force_update': force_update},
#             queue='favicons')
# 
# class UniqueFeed(JobDataMixin, models.Model):
#     GONE = 'gone'
#     TIMEOUT = 'timeout'
#     PARSE_ERROR = 'parseerror'
#     CONNECTION_ERROR = 'connerror'
#     DECODE_ERROR = 'decodeerror'
#     NOT_A_FEED = 'notafeed'
#     HTTP_400 = '400'
#     HTTP_401 = '401'
#     HTTP_403 = '403'
#     HTTP_404 = '404'
#     HTTP_500 = '500'
#     HTTP_502 = '502'
#     HTTP_503 = '503'
#     MUTE_CHOICES = (
#         (GONE, 'Feed gone (410)'),
#         (TIMEOUT, 'Feed timed out'),
#         (PARSE_ERROR, 'Location parse error'),
#         (CONNECTION_ERROR, 'Connection error'),
#         (DECODE_ERROR, 'Decoding error'),
#         (NOT_A_FEED, 'Not a valid RSS/Atom feed'),
#         (HTTP_400, 'HTTP 400'),
#         (HTTP_401, 'HTTP 401'),
#         (HTTP_403, 'HTTP 403'),
#         (HTTP_404, 'HTTP 404'),
#         (HTTP_500, 'HTTP 500'),
#         (HTTP_502, 'HTTP 502'),
#         (HTTP_503, 'HTTP 503'),
#     )
#     MUTE_DICT = dict(MUTE_CHOICES)
# 
#     url = URLField(_('URL'), unique=True)
#     muted = models.BooleanField(_('Muted'), default=False, db_index=True)
#     error = models.CharField(_('Error'), max_length=50, null=True, blank=True,
#                              choices=MUTE_CHOICES, db_column='muted_reason')
# 
#     objects = UniqueFeedManager()
# 
#     MAX_BACKOFF = 10  # Approx. 24 hours
#     UPDATE_PERIOD = 60  # in minutes
#     BACKOFF_EXPONENT = 1.5
#     TIMEOUT_BASE = 20
#     JOB_ATTRS = ['modified', 'etag', 'backoff_factor', 'error', 'link',
#                  'title', 'hub', 'subscribers', 'last_update']
# 
#     def __str__(self):
#         return u'%s' % self.url
# 
#     def truncated_url(self):
#         if len(self.url) > 50:
#             return self.url[:49] + u'…'
#         return self.url
#     truncated_url.short_description = _('URL')
#     truncated_url.admin_order_field = 'url'
# 
#     @classmethod
#     def request_timeout(cls, backoff_factor):
#         return 10 * backoff_factor
# 
#     @classmethod
#     def delay(cls, backoff_factor, hub=None):
#         if hub is not None:
#             backoff_factor = max(backoff_factor, 3)
#         return datetime.timedelta(
#             seconds=60 * cls.UPDATE_PERIOD *
#             backoff_factor ** cls.BACKOFF_EXPONENT)
# 
#     @property
#     def schedule_in(self):
#         return (
#             self.last_update + self.delay(self.job_details['backoff_factor'],
#                                           self.job_details.get('hub'))
#         ) - timezone.now()
# 
#     def schedule(self, schedule_in=None, **job):
#         if hasattr(self, '_job_details'):
#             del self._job_details
#         connection = get_redis_connection()
#         kwargs = {
#             'subscribers': 1,
#             'backoff_factor': 1,
#             'last_update': int(time.time()),
#         }
#         kwargs.update(job)
#         if schedule_in is None:
#             try:
#                 for attr in self.JOB_ATTRS:
#                     if attr in self.job_details:
#                         kwargs[attr] = self.job_details[attr]
#                 schedule_in = self.schedule_in
#             except JobNotFound:
#                 schedule_in = self.delay(kwargs['backoff_factor'])
#         schedule_job(self.url, schedule_in=schedule_in,
#                      connection=connection, **kwargs)


# Path: feedhq/feeds/management/commands/favicons.py
from . import SentryCommand
from ...models import enqueue_favicon, UniqueFeed



class Command(SentryCommand):
    """Fetches favicon updates and saves them if there are any"""

    def add_arguments(self, parser):
        parser.add_argument('--all', action='store_true', dest='all',
                            default=False,
                            help='Force update of all existing favicons')

    def handle_sentry(self, *args, **kwargs):

        urls = UniqueFeed.objects.filter(muted=False).values_list(