예제 #1
0
 def setUpClass(cls):
     management.call_command('flush', verbosity=0, interactive=False)
     activate_language(settings.LANGUAGE_CODE)
     management.call_command('askbot_add_test_content',
                             verbosity=0,
                             interactive=False)
     super(PageLoadTestCase, cls).setUpClass()
예제 #2
0
def record_question_visit(
        language_code=None, question_post_id=None, update_view_count=False,
        user_id=None):
    """celery task which records question visit by a person
    updates view counter, if necessary,
    and awards the badges associated with the
    question visit
    """
    activate_language(language_code)
    # 1) maybe update the view count
    try:
        question_post = Post.objects.get(id=question_post_id)
    except Post.DoesNotExist:
        logger.error("Unable to fetch post with id %s" % question_post_id)
        return

    if update_view_count and question_post.thread_id:
        question_post.thread.increase_view_count()

    # we do not track visits per anon user
    if user_id is None:
        return

    user = User.objects.get(id=user_id)

    # 2) question view count per user and clear response displays
    if user.is_authenticated():
        # get response notifications
        user.visit_question(question_post)

    # 3) send award badges signal for any badges
    # that are awarded for question views
    award_badges_signal.send(
        None, event='view_question', actor=user,
        context_object=question_post)
예제 #3
0
    def handle(self, **options):
        lang_code = options.get('language', settings.LANGUAGE_CODE.lower())
        options['using'] = ['default_%s' % lang_code[:2],]
        activate_language(lang_code)

        klass = self._get_command_class('clear_index')
        klass.handle(*args, **options)
예제 #4
0
 def __init__(self, app_labels, **kwargs):
     self.graphs = []
     self.cli_options = kwargs.get('cli_options', None)
     self.disable_fields = kwargs.get('disable_fields', False)
     self.disable_abstract_fields = kwargs.get('disable_abstract_fields', False)
     self.include_models = parse_file_or_list(
         kwargs.get('include_models', "")
     )
     self.all_applications = kwargs.get('all_applications', False)
     self.use_subgraph = kwargs.get('group_models', False)
     self.verbose_names = kwargs.get('verbose_names', False)
     self.inheritance = kwargs.get('inheritance', True)
     self.relations_as_fields = kwargs.get("relations_as_fields", True)
     self.sort_fields = kwargs.get("sort_fields", True)
     self.language = kwargs.get('language', None)
     if self.language is not None:
         activate_language(self.language)
     self.exclude_columns = parse_file_or_list(
         kwargs.get('exclude_columns', "")
     )
     self.exclude_models = parse_file_or_list(
         kwargs.get('exclude_models', "")
     )
     self.hide_edge_labels = kwargs.get('hide_edge_labels', False)
     self.arrow_shape = kwargs.get("arrow_shape")
     if self.all_applications:
         self.app_labels = [app.label for app in apps.get_app_configs()]
     else:
         self.app_labels = app_labels
예제 #5
0
def record_question_visit(
        language_code=None, question_post_id=None, update_view_count=False,
        user_id=None):
    """celery task which records question visit by a person
    updates view counter, if necessary,
    and awards the badges associated with the
    question visit
    """
    activate_language(language_code)
    # 1) maybe update the view count
    try:
        question_post = Post.objects.get(id=question_post_id)
    except Post.DoesNotExist:
        logger.error("Unable to fetch post with id %s" % question_post_id)
        return

    if update_view_count and question_post.thread_id:
        question_post.thread.increase_view_count()

    # we do not track visits per anon user
    if user_id is None:
        return

    user = User.objects.get(id=user_id)

    # 2) question view count per user and clear response displays
    if user.is_authenticated():
        # get response notifications
        user.visit_question(question_post)

    # 3) send award badges signal for any badges
    # that are awarded for question views
    award_badges_signal.send(
        None, event='view_question', actor=user,
        context_object=question_post)
예제 #6
0
 def __init__(self, app_labels, **kwargs):
     self.graphs = []
     self.cli_options = kwargs.get('cli_options', None)
     self.disable_fields = kwargs.get('disable_fields', False)
     self.include_models = parse_file_or_list(
         kwargs.get('include_models', "")
     )
     self.all_applications = kwargs.get('all_applications', False)
     self.use_subgraph = kwargs.get('group_models', False)
     self.verbose_names = kwargs.get('verbose_names', False)
     self.inheritance = kwargs.get('inheritance', True)
     self.relations_as_fields = kwargs.get("relations_as_fields", True)
     self.sort_fields = kwargs.get("sort_fields", True)
     self.language = kwargs.get('language', None)
     if self.language is not None:
         activate_language(self.language)
     self.exclude_columns = parse_file_or_list(
         kwargs.get('exclude_columns', "")
     )
     self.exclude_models = parse_file_or_list(
         kwargs.get('exclude_models', "")
     )
     if self.all_applications:
         self.app_labels = [app.label for app in apps.get_app_configs()]
     else:
         self.app_labels = app_labels
예제 #7
0
def send_instant_notifications_about_activity_in_post(activity_id=None,
                                                      post_id=None,
                                                      recipients=None):

    if recipients is None:
        recipients = set()

    recipients = set(recipients)
    recipients.update(get_invited_moderators())

    if len(recipients) == 0:
        return

    acceptable_types = const.RESPONSE_ACTIVITY_TYPES_FOR_INSTANT_NOTIFICATIONS
    try:
        update_activity = Activity.objects\
            .filter(activity_type__in=acceptable_types)\
            .get(id=activity_id)
    except Activity.DoesNotExist:
        logger.error("Unable to fetch activity with id %s" % post_id)
        return

    try:
        post = Post.objects.get(id=post_id)
    except Post.DoesNotExist:
        logger.error("Unable to fetch post with id %s" % post_id)
        return

    if not post.is_approved():
        return

    if logger.getEffectiveLevel() <= logging.DEBUG:
        log_id = uuid.uuid1()
        message = 'email-alert %s, logId=%s' % (post.get_absolute_url(),
                                                log_id)
        logger.debug(message)
    else:
        log_id = None

    for user in recipients:
        if user.is_blocked():
            continue

        activate_language(post.language_code)

        email = InstantEmailAlert({
            'to_user': user,
            'from_user': update_activity.user,
            'post': post,
            'update_activity': update_activity
        })
        try:
            email.send([user.email])
        except askbot_exceptions.EmailNotSent as error:
            logger.debug('%s, error=%s, logId=%s' %
                         (user.email, error, log_id))
        else:
            logger.debug('success %s, logId=%s' % (user.email, log_id))
예제 #8
0
def notify_author_of_published_revision_celery_task(revision):
    #todo: move this to ``askbot.mail`` module
    #for answerable email only for now, because
    #we don't yet have the template for the read-only notification

    data = {
        'site_name': askbot_settings.APP_SHORT_NAME,
        'post': revision.post
    }
    headers = None

    if askbot_settings.REPLY_BY_EMAIL:
        #generate two reply codes (one for edit and one for addition)
        #to format an answerable email or not answerable email
        reply_options = {
            'user': revision.author,
            'post': revision.post,
            'reply_action': 'append_content'
        }
        append_content_address = ReplyAddress.objects.create_new(
                                                        **reply_options
                                                    ).as_email_address()
        reply_options['reply_action'] = 'replace_content'
        replace_content_address = ReplyAddress.objects.create_new(
                                                        **reply_options
                                                    ).as_email_address()

        #populate template context variables
        reply_code = append_content_address + ',' + replace_content_address
        if revision.post.post_type == 'question':
            mailto_link_subject = revision.post.thread.title
        else:
            mailto_link_subject = _('make an edit by email')
        #todo: possibly add more mailto thread headers to organize messages

        prompt = _('To add to your post EDIT ABOVE THIS LINE')
        reply_separator_line = const.SIMPLE_REPLY_SEPARATOR_TEMPLATE % prompt
        data['reply_code'] = reply_code
        data['author_email_signature'] = revision.author.email_signature
        data['replace_content_address'] = replace_content_address
        data['reply_separator_line'] = reply_separator_line
        data['mailto_link_subject'] = mailto_link_subject
        headers = {'Reply-To': append_content_address}

    #load the template
    activate_language(revision.post.language_code)
    template = get_template('email/notify_author_about_approved_post.html')
    #todo: possibly add headers to organize messages in threads
    #send the message
    mail.send_mail(
        subject_line = _('Your post at %(site_name)s is now published') % data,
        body_text = template.render(Context(data)),
        recipient_list = [revision.author.email,],
        related_object = revision,
        activity_type = const.TYPE_ACTIVITY_EMAIL_UPDATE_SENT,
        headers = headers
    )
예제 #9
0
    def handle(self, **options):
        lang_code = options.get('language', settings.LANGUAGE_CODE.lower())
        options['using'] = [
            'default_%s' % lang_code[:2],
        ]
        activate_language(lang_code)

        klass = self._get_command_class('clear_index')
        klass.handle(*args, **options)
예제 #10
0
def send_instant_notifications_about_activity_in_post(
        activity_id=None, post_id=None, recipients=None):

    if recipients is None:
        recipients = set()

    recipients = set(recipients)
    recipients.update(get_invited_moderators())

    if len(recipients) == 0:
        return

    acceptable_types = const.RESPONSE_ACTIVITY_TYPES_FOR_INSTANT_NOTIFICATIONS
    try:
        update_activity = Activity.objects\
            .filter(activity_type__in=acceptable_types)\
            .get(id=activity_id)
    except Activity.DoesNotExist:
        logger.error("Unable to fetch activity with id %s" % post_id)
        return

    try:
        post = Post.objects.get(id=post_id)
    except Post.DoesNotExist:
        logger.error("Unable to fetch post with id %s" % post_id)
        return

    if not post.is_approved():
        return

    if logger.getEffectiveLevel() <= logging.DEBUG:
        log_id = uuid.uuid1()
        message = 'email-alert %s, logId=%s' % (post.get_absolute_url(), log_id)
        logger.debug(message)
    else:
        log_id = None

    for user in recipients:
        if user.is_blocked():
            continue

        activate_language(post.language_code)

        email = InstantEmailAlert({
            'to_user': user,
            'from_user': update_activity.user,
            'post': post,
            'update_activity': update_activity
        })
        try:
            email.send([user.email])
        except askbot_exceptions.EmailNotSent as error:
            logger.debug(
                '%s, error=%s, logId=%s' % (user.email, error, log_id)
            )
        else:
            logger.debug('success %s, logId=%s' % (user.email, log_id))
예제 #11
0
    def send_email_alerts(self, user):
        #does not change the database, only sends the email
        #todo: move this to template
        user.add_missing_askbot_subscriptions()
        #todo: q_list is a dictionary, not a list
        q_list = self.get_updated_questions_for_user(user)
        if len(q_list.keys()) == 0:
            return
        num_q = 0
        for question, meta_data in q_list.items():
            if meta_data['skip']:
                del q_list[question]
            else:
                num_q += 1
        if num_q > 0:
            threads = Thread.objects.filter(id__in=[qq.thread_id for qq in q_list.keys()])
            tag_summary = Thread.objects.get_tag_summary_from_threads(threads)

            question_count = len(q_list.keys())

            items_added = 0
            items_unreported = 0
            questions_data = list()
            for q, meta_data in q_list.items():
                act_list = []
                if meta_data['skip']:
                    continue
                if items_added >= askbot_settings.MAX_ALERTS_PER_EMAIL:
                    items_unreported = num_q - items_added #may be inaccurate actually, but it's ok
                    break
                else:
                    items_added += 1
                    if meta_data['new_q']:
                        act_list.append(_('new question'))
                    format_action_count('%(num)d rev', meta_data['q_rev'], act_list)
                    format_action_count('%(num)d ans', meta_data['new_ans'], act_list)
                    format_action_count('%(num)d ans rev', meta_data['ans_rev'], act_list)
                    questions_data.append({
                        'url': site_url(q.get_absolute_url()),
                        'info': ', '.join(act_list),
                        'title': q.thread.title
                    })

            activate_language(user.get_primary_language())
            email = BatchEmailAlert({
                'questions': questions_data,
                'question_count': question_count,
                'tag_summary': tag_summary,
                'user': user
            })

            if DEBUG_THIS_COMMAND == True:
                recipient_email = askbot_settings.ADMIN_EMAIL
            else:
                recipient_email = user.email

            email.send([recipient_email,])
예제 #12
0
 def handle_noargs(self, **options):
     if askbot_settings.ENABLE_EMAIL_ALERTS:
         activate_language(django_settings.LANGUAGE_CODE)
         for user in User.objects.all():
             try:
                 self.send_email_alerts(user)
             except Exception:
                 self.report_exception(user)
         connection.close()
예제 #13
0
 def handle_noargs(self, **options):
     if askbot_settings.ENABLE_EMAIL_ALERTS:
         activate_language(django_settings.LANGUAGE_CODE)
         for user in User.objects.all():
             try:
                 self.send_email_alerts(user)
             except Exception:
                 self.report_exception(user)
         connection.close()
예제 #14
0
def notify_author_of_published_revision_celery_task(revision_id):
    #todo: move this to ``askbot.mail`` module
    #for answerable email only for now, because
    #we don't yet have the template for the read-only notification

    try:
        revision = PostRevision.objects.get(pk=revision_id)
    except PostRevision.DoesNotExist:
        logger.error("Unable to fetch revision with id %s" % revision_id)
        return

    activate_language(revision.post.language_code)

    if askbot_settings.REPLY_BY_EMAIL == False:
        email = ApprovedPostNotification({
            'post': revision.post,
            'recipient_user': revision.author
        })
        email.send([
            revision.author.email,
        ])
    else:
        #generate two reply codes (one for edit and one for addition)
        #to format an answerable email or not answerable email
        reply_options = {
            'user': revision.author,
            'post': revision.post,
            'reply_action': 'append_content'
        }
        append_content_address = ReplyAddress.objects.create_new(
            **reply_options).as_email_address()
        reply_options['reply_action'] = 'replace_content'
        replace_content_address = ReplyAddress.objects.create_new(
            **reply_options).as_email_address()

        if revision.post.post_type == 'question':
            mailto_link_subject = revision.post.thread.title
        else:
            mailto_link_subject = _('make an edit by email')

        email = ApprovedPostNotificationRespondable({
            'revision':
            revision,
            'mailto_link_subject':
            mailto_link_subject,
            'reply_code':
            append_content_address + ',' + replace_content_address,
            'append_content_address':
            append_content_address,
            'replace_content_address':
            replace_content_address
        })
        email.send([
            revision.author.email,
        ])
예제 #15
0
파일: tasks.py 프로젝트: brousch/votealign
def notify_author_of_published_revision_celery_task(revision):
    #todo: move this to ``askbot.mail`` module
    #for answerable email only for now, because
    #we don't yet have the template for the read-only notification
    if askbot_settings.REPLY_BY_EMAIL:
        #generate two reply codes (one for edit and one for addition)
        #to format an answerable email or not answerable email
        reply_options = {
            'user': revision.author,
            'post': revision.post,
            'reply_action': 'append_content'
        }
        append_content_address = ReplyAddress.objects.create_new(
            **reply_options).as_email_address()
        reply_options['reply_action'] = 'replace_content'
        replace_content_address = ReplyAddress.objects.create_new(
            **reply_options).as_email_address()

        #populate template context variables
        reply_code = append_content_address + ',' + replace_content_address
        if revision.post.post_type == 'question':
            mailto_link_subject = revision.post.thread.title
        else:
            mailto_link_subject = _('make an edit by email')
        #todo: possibly add more mailto thread headers to organize messages

        prompt = _('To add to your post EDIT ABOVE THIS LINE')
        reply_separator_line = const.SIMPLE_REPLY_SEPARATOR_TEMPLATE % prompt
        data = {
            'site_name': askbot_settings.APP_SHORT_NAME,
            'post': revision.post,
            'author_email_signature': revision.author.email_signature,
            'replace_content_address': replace_content_address,
            'reply_separator_line': reply_separator_line,
            'mailto_link_subject': mailto_link_subject,
            'reply_code': reply_code
        }

        #load the template
        activate_language(revision.post.language_code)
        template = get_template('email/notify_author_about_approved_post.html')
        #todo: possibly add headers to organize messages in threads
        headers = {'Reply-To': append_content_address}
        #send the message
        mail.send_mail(
            subject_line=_('Your post at %(site_name)s is now published') %
            data,
            body_text=template.render(Context(data)),
            recipient_list=[
                revision.author.email,
            ],
            related_object=revision,
            activity_type=const.TYPE_ACTIVITY_EMAIL_UPDATE_SENT,
            headers=headers)
예제 #16
0
 def handle_noargs(self, **options):
     if askbot_settings.ENABLE_EMAIL_ALERTS:
         activate_language(django_settings.LANGUAGE_CODE)
         for user in User.objects.exclude(status='b').iterator():
             try:
                 if email_is_blacklisted(user.email) and askbot_settings.BLACKLISTED_EMAIL_PATTERNS_MODE == 'strict':
                     continue
                 self.send_email_alerts(user)
             except Exception:
                 self.report_exception(user)
         connection.close()
예제 #17
0
 def handle_noargs(self, **options):
     if askbot_settings.ENABLE_EMAIL_ALERTS:
         activate_language(django_settings.LANGUAGE_CODE)
         for user in User.objects.exclude(status='b').iterator():
             try:
                 if email_is_blacklisted(user.email) \
                     and askbot_settings.BLACKLISTED_EMAIL_PATTERNS_MODE == 'strict':
                     continue
                 self.send_email_alerts(user)
             except Exception:
                 self.report_exception(user)
         connection.close()
예제 #18
0
 def test_t_something_single(self):
     old_lang = get_language()
     self.item.save_d('names', {'ja': u'マリア', 'ru': u'Мария'})
     activate_language('ja')
     self.assertEqual(self.item.t_name, u'マリア')
     activate_language('ru')
     self.assertEqual(self.item.t_name, u'Мария')
     activate_language('zh-hans')
     self.assertEqual(self.item.t_name, u'Maria')
     activate_language('en')
     self.assertEqual(self.item.t_name, u'Maria')
     activate_language(old_lang)
예제 #19
0
    def get_default_editor_value(self, language_code):
        if self.use_default:
            if language_code and self.localized:
                current_lang = get_language()
                activate_language(language_code)
                localized_value = unicode(self.default)
                activate_language(current_lang)
                return localized_value
            elif self.use_default:
                return unicode(self.default)

        return ''
 def test_t_something_single(self):
     old_lang = get_language()
     self.item.save_d('names', {'ja': u'マリア', 'ru': u'Мария'})
     activate_language('ja')
     self.assertEqual(self.item.t_name, u'マリア')
     activate_language('ru')
     self.assertEqual(self.item.t_name, u'Мария')
     activate_language('zh-hans')
     self.assertEqual(self.item.t_name, u'Maria')
     activate_language('en')
     self.assertEqual(self.item.t_name, u'Maria')
     activate_language(old_lang)
예제 #21
0
    def get_default_editor_value(self, language_code):
        if self.use_default:
            if language_code and self.localized:
                current_lang = get_language()
                activate_language(language_code)
                localized_value = six.text_type(self.default)
                activate_language(current_lang)
                return localized_value
            elif self.use_default:
                return six.text_type(self.default)

        return ''
예제 #22
0
    def handle(self, *args, **kwargs):

        activate_language(django_settings.LANGUAGE_CODE)

        #init the redirects file format table
        self.redirect_format = self.get_redirect_format(kwargs['redirect_format'])

        self.setup_run()
        self.read_xml_file(args[0])

        self.remember_message_ids()
        self.handle_import()
        self.delete_new_messages()
예제 #23
0
파일: base.py 프로젝트: bemall/askbot-devel
    def handle(self, *args, **kwargs):

        activate_language(django_settings.LANGUAGE_CODE)

        #init the redirects file format table
        self.redirect_format = self.get_redirect_format(kwargs['redirect_format'])

        self.setup_run()
        self.read_xml_file(args[0])

        self.remember_message_ids()
        self.handle_import()
        self.delete_new_messages()
예제 #24
0
def notify_author_of_published_revision_celery_task(revision_id):
    #todo: move this to ``askbot.mail`` module
    #for answerable email only for now, because
    #we don't yet have the template for the read-only notification

    try:
        revision = PostRevision.objects.get(pk=revision_id)
    except PostRevision.DoesNotExist:
        logger.error("Unable to fetch revision with id %s" % revision_id)
        return

    activate_language(revision.post.language_code)

    if askbot_settings.REPLY_BY_EMAIL == False:
        email = ApprovedPostNotification({
            'post': revision.post,
            'recipient_user': revision.author
        })
        email.send([revision.author.email,])
    else:
        #generate two reply codes (one for edit and one for addition)
        #to format an answerable email or not answerable email
        reply_options = {
            'user': revision.author,
            'post': revision.post,
            'reply_action': 'append_content'
        }
        append_content_address = ReplyAddress.objects.create_new(
                                                        **reply_options
                                                    ).as_email_address()
        reply_options['reply_action'] = 'replace_content'
        replace_content_address = ReplyAddress.objects.create_new(
                                                        **reply_options
                                                    ).as_email_address()

        if revision.post.post_type == 'question':
            mailto_link_subject = revision.post.thread.title
        else:
            mailto_link_subject = _('make an edit by email')

        email = ApprovedPostNotificationRespondable({
            'revision': revision,
            'mailto_link_subject': mailto_link_subject,
            'reply_code': append_content_address + ',' + replace_content_address,
            'append_content_address': append_content_address,
            'replace_content_address': replace_content_address
        })
        email.send([revision.author.email,])
예제 #25
0
    def handle(self, *args, **options):
        """Generates a Solr schema that reflects the indexes."""
        using = options.get('using')
        language = options.get('language')[:2]
        activate_language(language)
        if language not in SUPPORTED_LANGUAGES:
            sys.stderr.write("\n\n")
            sys.stderr.write("WARNING: your language: '%s' is not supported in our " % language)
            sys.stderr.write("template it will default to English more information in http://wiki.apache.org/solr/LanguageAnalysis")
            sys.stderr.write("\n\n")
        schema_xml = self.build_template(using=using, language=language)

        if options.get('filename'):
            self.write_file(options.get('filename'), schema_xml)
        else:
            self.print_stdout(schema_xml)
예제 #26
0
    def handle(self, *args, **kwargs):

        activate_language(django_settings.LANGUAGE_CODE)

        #init the redirects file format table
        format_table = {
            'nginx': 'rewrite ^%s$ %s break;\n',
            'apache': 'Redirect permanent %s %s\n',
        }
        format_table = defaultdict(lambda: '%s %s\n', format_table)
        self.redirect_format = format_table[kwargs['redirect_format']]

        self.setup_run()
        self.read_xml_file(args[0])
        self.remember_message_ids()
        self.read_content_types()

        self.import_groups()
        self.import_users()
        #we don't import subscriptions
        if 'avatar' in django_settings.INSTALLED_APPS:
            self.import_avatars()

        #we need this to link old user ids to
        #new users' personal groups
        #self.record_personal_groups()

        self.import_user_logins()
        self.import_tags()
        self.import_marked_tags()

        self.import_threads()
        self.apply_groups_to_threads()

        #model="askbot.posttogroup">
        self.import_posts('question', save_redirects=True)
        self.import_posts('answer')
        self.import_posts('comment')
        self.import_post_revisions()
        self.apply_groups_to_posts()
        self.apply_question_followers()
        self.import_votes()

        self.import_badges()
        self.import_badge_awards()
        self.delete_new_messages()
    def handle(self, *args, **kwargs):

        activate_language(django_settings.LANGUAGE_CODE)

        #init the redirects file format table
        format_table = {
            'nginx': 'rewrite ^%s$ %s break;\n',
            'apache': 'Redirect permanent %s %s\n',
        }
        format_table = defaultdict(lambda: '%s %s\n', format_table)
        self.redirect_format = format_table[kwargs['redirect_format']]

        self.setup_run()
        self.read_xml_file(args[0])
        self.remember_message_ids()
        self.read_content_types()

        self.import_groups()
        self.import_users()
        #we don't import subscriptions
        if 'avatar' in django_settings.INSTALLED_APPS:
            self.import_avatars()

        #we need this to link old user ids to
        #new users' personal groups
        #self.record_personal_groups()
        
        self.import_user_logins()
        self.import_tags()
        self.import_marked_tags()

        self.import_threads()
        self.apply_groups_to_threads()

        #model="askbot.posttogroup">
        self.import_posts('question', save_redirects=True)
        self.import_posts('answer')
        self.import_posts('comment')
        self.import_post_revisions()
        self.apply_groups_to_posts()
        self.apply_question_followers()
        self.import_votes()

        self.import_badges()
        self.import_badge_awards()
        self.delete_new_messages()
예제 #28
0
 def test_has_translation_default_language(self):
     activate_language("en")
     self.assertTrue(self.model.has_translation())
     activate_language("es")
     self.assertTrue(self.model.has_translation())
     activate_language("it")
     self.assertFalse(self.model.has_translation())
예제 #29
0
 def test_get_translation_default_language_fallback(self):
     activate_language('en')
     self.assertEquals(self.model.get_translation(), self.translation_en)
     activate_language('es')
     self.assertEquals(self.model.get_translation(), self.translation_es)
     activate_language('it')
     self.assertEquals(self.model.get_translation(), self.translation_en)
예제 #30
0
 def test_has_translation_default_language(self):
     activate_language('en')
     self.assertTrue(self.model.has_translation())
     activate_language('es')
     self.assertTrue(self.model.has_translation())
     activate_language('it')
     self.assertFalse(self.model.has_translation())
예제 #31
0
 def test_get_translation_given_language_fallback(self):
     activate_language("es")
     self.assertEquals(self.model.get_translation("en"), self.translation_en)
     activate_language("en")
     self.assertEquals(self.model.get_translation("es"), self.translation_es)
     activate_language("en")
     self.assertEquals(self.model.get_translation("it"), self.translation_en)
예제 #32
0
 def test_get_translation_given_language_no_fallback(self):
     activate_language("es")
     self.assertEquals(self.model.get_translation("en", fallback=False), self.translation_en)
     activate_language("en")
     self.assertEquals(self.model.get_translation("es", fallback=False), self.translation_es)
     activate_language("en")
     with self.assertRaises(translatable.exceptions.MissingTranslation):
         self.model.get_translation("it", fallback=False)
예제 #33
0
 def test_translated_given_language_fallback(self):
     activate_language("es")
     self.assertEquals(self.model.translated("field", language="en"), "Hello!")
     activate_language("en")
     self.assertEquals(self.model.translated("field", language="es"), "Hola!")
     activate_language("es")
     self.assertEquals(self.model.translated("field", language="it"), "Hello!")
     self.assertEquals(self.model.translated("field", "default", language="it"), "Hello!")
예제 #34
0
 def test_translated_default_language_no_fallback(self):
     activate_language("en")
     self.assertEquals(self.model.translated("field", fallback=False), "Hello!")
     activate_language("es")
     self.assertEquals(self.model.translated("field", fallback=False), "Hola!")
     activate_language("it")
     self.assertIsNone(self.model.translated("field", fallback=False))
     self.assertEquals(self.model.translated("field", "default", fallback=False), "default")
예제 #35
0
 def test_translated_default_language_fallback(self):
     activate_language('en')
     self.assertEquals(self.model.translated('field'), "Hello!")
     activate_language('es')
     self.assertEquals(self.model.translated('field'), "Hola!")
     activate_language('it')
     self.assertEquals(self.model.translated('field'), "Hello!")
     self.assertEquals(self.model.translated('field', "default"), "Hello!")
예제 #36
0
 def test_get_translation_given_language_no_fallback(self):
     activate_language('es')
     self.assertEquals(self.model.get_translation('en', fallback=False),
                       self.translation_en)
     activate_language('en')
     self.assertEquals(self.model.get_translation('es', fallback=False),
                       self.translation_es)
     activate_language('en')
     with self.assertRaises(translatable.exceptions.MissingTranslation):
         self.model.get_translation('it', fallback=False)
예제 #37
0
 def test_translated_given_language_no_fallback(self):
     activate_language('es')
     self.assertEquals(
         self.model.translated('field', language='en', fallback=False),
         "Hello!")
     activate_language('en')
     self.assertEquals(
         self.model.translated('field', language='es', fallback=False),
         "Hola!")
     activate_language('en')
     self.assertIsNone(
         self.model.translated('field', language='it', fallback=False))
     self.assertEquals(
         self.model.translated('field',
                               "default",
                               language='it',
                               fallback=False), "default")
    def send_email_alerts(self):
        #does not change the database, only sends the email
        #todo: move this to template
        activate_language(django_settings.LANGUAGE_CODE)
        template = get_template('email/delayed_email_alert.html')
        for user in User.objects.all():
            user.add_missing_askbot_subscriptions()
            #todo: q_list is a dictionary, not a list
            q_list = self.get_updated_questions_for_user(user)
            if len(q_list.keys()) == 0:
                continue
            num_q = 0
            for question, meta_data in q_list.items():
                if meta_data['skip']:
                    del q_list[question]
                else:
                    num_q += 1
            if num_q > 0:
                threads = Thread.objects.filter(
                    id__in=[qq.thread_id for qq in q_list.keys()])
                tag_summary = Thread.objects.get_tag_summary_from_threads(
                    threads)

                question_count = len(q_list.keys())

                if tag_summary:
                    subject_line = ungettext(
                        '%(question_count)d update about %(topics)s',
                        '%(question_count)d updates about %(topics)s',
                        question_count) % {
                            'question_count': question_count,
                            'topics': tag_summary
                        }
                else:
                    subject_line = ungettext(
                        '%(question_count)d update',
                        '%(question_count)d updates', question_count) % {
                            'question_count': question_count,
                        }

                items_added = 0
                items_unreported = 0
                questions_data = list()
                for q, meta_data in q_list.items():
                    act_list = []
                    if meta_data['skip']:
                        continue
                    if items_added >= askbot_settings.MAX_ALERTS_PER_EMAIL:
                        items_unreported = num_q - items_added  #may be inaccurate actually, but it's ok
                        break
                    else:
                        items_added += 1
                        if meta_data['new_q']:
                            act_list.append(_('new question'))
                        format_action_count('%(num)d rev', meta_data['q_rev'],
                                            act_list)
                        format_action_count('%(num)d ans',
                                            meta_data['new_ans'], act_list)
                        format_action_count('%(num)d ans rev',
                                            meta_data['ans_rev'], act_list)
                        questions_data.append({
                            'url':
                            site_url(q.get_absolute_url()),
                            'info':
                            ', '.join(act_list),
                            'title':
                            q.thread.title
                        })

                activate_language(user.get_primary_language())
                text = template.render({
                    'recipient_user':
                    user,
                    'questions':
                    questions_data,
                    'name':
                    user.username,
                    'admin_email':
                    askbot_settings.ADMIN_EMAIL,
                    'site_name':
                    askbot_settings.APP_SHORT_NAME,
                    'is_multilingual':
                    getattr(django_settings, 'ASKBOT_MULTILINGUAL', False)
                })

                if DEBUG_THIS_COMMAND == True:
                    recipient_email = askbot_settings.ADMIN_EMAIL
                else:
                    recipient_email = user.email

                mail.send_mail(subject_line=subject_line,
                               body_text=text,
                               recipient_list=[recipient_email])
예제 #39
0
def generate_dot(app_labels, **kwargs):
    disable_fields = kwargs.get('disable_fields', False)
    include_models = parse_file_or_list(kwargs.get('include_models', ""))
    all_applications = kwargs.get('all_applications', False)
    use_subgraph = kwargs.get('group_models', False)
    verbose_names = kwargs.get('verbose_names', False)
    language = kwargs.get('language', None)
    if language is not None:
        activate_language(language)
    exclude_columns = parse_file_or_list(kwargs.get('exclude_columns', ""))
    exclude_models = parse_file_or_list(kwargs.get('exclude_models', ""))

    def skip_field(field):
        if exclude_columns:
            if verbose_names and field.verbose_name:
                if field.verbose_name in exclude_columns:
                    return True
            if field.name in exclude_columns:
                return True
        return False




    t = loader.get_template('django_extensions/graph_models/head.html')
    c = Context({})
    dot = t.render(c)

    apps = []
    if all_applications:
        apps = models.get_apps()

    for app_label in app_labels:
        app = models.get_app(app_label)
        if not app in apps:
            apps.append(app)

    graphs = []
    for app in apps:
        graph = Context({
            'name': '"%s"' % app.__name__,
            'app_name': "%s" % '.'.join(app.__name__.split('.')[:-1]),
            'cluster_app_name': "cluster_%s" % app.__name__.replace(".", "_"),
            'disable_fields': disable_fields,
            'use_subgraph': use_subgraph,
            'models': []
        })

        for appmodel in get_models(app):
            abstracts = [e.__name__ for e in appmodel.__bases__ if hasattr(e, '_meta') and e._meta.abstract]

            # collect all attribs of abstract superclasses
            def getBasesAbstractFields(c):
                _abstract_fields = []
                for e in c.__bases__:
                    if hasattr(e, '_meta') and e._meta.abstract:
                        _abstract_fields.extend(e._meta.fields)
                        _abstract_fields.extend(getBasesAbstractFields(e))
                return _abstract_fields
            abstract_fields = getBasesAbstractFields(appmodel)

            model = {
                'app_name': appmodel.__module__.replace(".", "_"),
                'name': appmodel.__name__,
                'abstracts': abstracts,
                'fields': [],
                'relations': []
            }

            # consider given model name ?
            def consider(model_name):
                if exclude_models and model_name in exclude_models:
                    return False
                return not include_models or model_name in include_models

            if not consider(appmodel._meta.object_name):
                continue

            if verbose_names and appmodel._meta.verbose_name:
                model['label'] = appmodel._meta.verbose_name
            else:
                model['label'] = model['name']

            # model attributes
            def add_attributes(field):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name

                model['fields'].append({
                    'name': field.name,
                    'label': label,
                    'type': type(field).__name__,
                    'blank': field.blank,
                    'abstract': field in abstract_fields,
                })

            for field in appmodel._meta.fields:
                if skip_field(field):
                    continue
                add_attributes(field)

            if appmodel._meta.many_to_many:
                for field in appmodel._meta.many_to_many:
                    if skip_field(field):
                        continue
                    add_attributes(field)

            # relations
            def add_relation(field, extras=""):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name

                _rel = {
                    'target_app': field.rel.to.__module__.replace('.', '_'),
                    'target': field.rel.to.__name__,
                    'type': type(field).__name__,
                    'name': field.name,
                    'label': label,
                    'arrows': extras,
                    'needs_node': True
                }
                if _rel not in model['relations'] and consider(_rel['target']):
                    model['relations'].append(_rel)

            for field in appmodel._meta.fields:
                if skip_field(field):
                    continue
                if isinstance(field, OneToOneField):
                    add_relation(field, '[arrowhead=none arrowtail=none]')
                elif isinstance(field, ForeignKey):
                    add_relation(field)

            if appmodel._meta.many_to_many:
                for field in appmodel._meta.many_to_many:
                    if skip_field(field):
                        continue
                    if isinstance(field, ManyToManyField):
                        if (getattr(field, 'creates_table', False) or  # django 1.1.
                            (field.rel.through and field.rel.through._meta.auto_created)):  # django 1.2
                            add_relation(field, '[arrowhead=normal arrowtail=normal]')
                    elif isinstance(field, GenericRelation):
                        add_relation(field, mark_safe('[style="dotted"] [arrowhead=normal arrowtail=normal]'))
            graph['models'].append(model)
        graphs.append(graph)

    nodes = []
    for graph in graphs:
        nodes.extend([e['name'] for e in graph['models']])

    for graph in graphs:
        # don't draw duplication nodes because of relations
        for model in graph['models']:
            for relation in model['relations']:
                if relation['target'] in nodes:
                    relation['needs_node'] = False
        # render templates
        t = loader.get_template('django_extensions/graph_models/body.html')
        dot += '\n' + t.render(graph)

    for graph in graphs:
        t = loader.get_template('django_extensions/graph_models/rel.html')
        dot += '\n' + t.render(graph)


    t = loader.get_template('django_extensions/graph_models/tail.html')
    c = Context({})
    dot += '\n' + t.render(c)
    return dot
예제 #40
0
 def setUpClass(cls):
     super(PageLoadTestCase, cls).setUpClass()
     management.call_command("flush", verbosity=0, interactive=False)
     activate_language(settings.LANGUAGE_CODE)
     management.call_command("askbot_add_test_content", verbosity=0, interactive=False)
예제 #41
0
파일: conftest.py 프로젝트: eviljeff/nobot
def activate_en():
    activate_language('en')
    yield
    deactivate_language()
예제 #42
0
    def send_email_alerts(self):
        #does not change the database, only sends the email
        #todo: move this to template
        activate_language(django_settings.LANGUAGE_CODE)
        template = get_template('email/delayed_email_alert.html')
        for user in User.objects.all():
            user.add_missing_askbot_subscriptions()
            #todo: q_list is a dictionary, not a list
            q_list = self.get_updated_questions_for_user(user)
            if len(q_list.keys()) == 0:
                continue
            num_q = 0
            for question, meta_data in q_list.items():
                if meta_data['skip']:
                    del q_list[question]
                else:
                    num_q += 1
            if num_q > 0:
                threads = Thread.objects.filter(id__in=[qq.thread_id for qq in q_list.keys()])
                tag_summary = Thread.objects.get_tag_summary_from_threads(threads)

                question_count = len(q_list.keys())

                subject_line = ungettext(
                    '%(question_count)d updated question about %(topics)s',
                    '%(question_count)d updated questions about %(topics)s',
                    question_count
                ) % {
                    'question_count': question_count,
                    'topics': tag_summary
                }

                #todo: send this to special log
                print 'have %d updated questions for %s' % (num_q, user.username)
                if DEBUG_THIS_COMMAND == True:
                   continue
                text = ungettext(
                    '<p>Dear %(name)s,</p><p>The following question has been updated '
                    '%(sitename)s</p>',
                    '<p>Dear %(name)s,</p><p>The following %(num)d questions have been '
                    'updated on %(sitename)s:</p>',
                    num_q
                ) % {
                    'num':num_q,
                    'name':user.username,
                    'sitename': askbot_settings.APP_SHORT_NAME
                }

                text += '<ul>'
                items_added = 0
                items_unreported = 0
                questions_data = list()
                for q, meta_data in q_list.items():
                    act_list = []
                    if meta_data['skip']:
                        continue
                    if items_added >= askbot_settings.MAX_ALERTS_PER_EMAIL:
                        items_unreported = num_q - items_added #may be inaccurate actually, but it's ok
                        break
                    else:
                        items_added += 1
                        if meta_data['new_q']:
                            act_list.append(_('new question'))
                        format_action_count('%(num)d rev', meta_data['q_rev'], act_list)
                        format_action_count('%(num)d ans', meta_data['new_ans'], act_list)
                        format_action_count('%(num)d ans rev', meta_data['ans_rev'], act_list)
                        questions_data.append({
                            'url': site_url(q.get_absolute_url()),
                            'info': ', '.join(act_list),
                            'title': q.thread.title
                        })

                activate_language(user.get_primary_language())
                text = template.render({
                    'recipient_user': user,
                    'questions': questions_data,
                    'name': user.username,
                    'admin_email': askbot_settings.ADMIN_EMAIL,
                    'site_name': askbot_settings.APP_SHORT_NAME,
                    'is_multilingual': django_settings.ASKBOT_MULTILINGUAL
                })

                if DEBUG_THIS_COMMAND == True:
                    recipient_email = askbot_settings.ADMIN_EMAIL
                else:
                    recipient_email = user.email

                mail.send_mail(
                    subject_line = subject_line,
                    body_text = text,
                    recipient_list = [recipient_email]
                )
예제 #43
0
 def get_text_kn(self, obj):
     activate_language("kn")
     return _(obj.text)
예제 #44
0
def generate_dot(app_labels, **kwargs):
    disable_fields = kwargs.get('disable_fields', False)
    include_models = parse_file_or_list(kwargs.get('include_models', ""))
    all_applications = kwargs.get('all_applications', False)
    use_subgraph = kwargs.get('group_models', False)
    verbose_names = kwargs.get('verbose_names', False)
    language = kwargs.get('language', None)
    if language is not None:
        activate_language(language)
    exclude_columns = parse_file_or_list(kwargs.get('exclude_columns', ""))
    exclude_models = parse_file_or_list(kwargs.get('exclude_models', ""))

    def skip_field(field):
        if exclude_columns:
            if verbose_names and field.verbose_name:
                if field.verbose_name in exclude_columns:
                    return True
            if field.name in exclude_columns:
                return True
        return False

    t = loader.get_template('django_extensions/graph_models/head.html')
    c = Context({})
    dot = t.render(c)

    apps = []
    if all_applications:
        apps = models.get_apps()

    for app_label in app_labels:
        app = models.get_app(app_label)
        if not app in apps:
            apps.append(app)

    graphs = []
    for app in apps:
        graph = Context({
            'name':
            '"%s"' % app.__name__,
            'app_name':
            "%s" % '.'.join(app.__name__.split('.')[:-1]),
            'cluster_app_name':
            "cluster_%s" % app.__name__.replace(".", "_"),
            'disable_fields':
            disable_fields,
            'use_subgraph':
            use_subgraph,
            'models': []
        })

        for appmodel in get_models(app):
            abstracts = [
                e.__name__ for e in appmodel.__bases__
                if hasattr(e, '_meta') and e._meta.abstract
            ]

            # collect all attribs of abstract superclasses
            def getBasesAbstractFields(c):
                _abstract_fields = []
                for e in c.__bases__:
                    if hasattr(e, '_meta') and e._meta.abstract:
                        _abstract_fields.extend(e._meta.fields)
                        _abstract_fields.extend(getBasesAbstractFields(e))
                return _abstract_fields

            abstract_fields = getBasesAbstractFields(appmodel)

            model = {
                'app_name': appmodel.__module__.replace(".", "_"),
                'name': appmodel.__name__,
                'abstracts': abstracts,
                'fields': [],
                'relations': []
            }

            # consider given model name ?
            def consider(model_name):
                if exclude_models and model_name in exclude_models:
                    return False
                return not include_models or model_name in include_models

            if not consider(appmodel._meta.object_name):
                continue

            if verbose_names and appmodel._meta.verbose_name:
                model['label'] = appmodel._meta.verbose_name
            else:
                model['label'] = model['name']

            # model attributes
            def add_attributes(field):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name

                model['fields'].append({
                    'name': field.name,
                    'label': label,
                    'type': type(field).__name__,
                    'blank': field.blank,
                    'abstract': field in abstract_fields,
                })

            for field in appmodel._meta.fields:
                if skip_field(field):
                    continue
                add_attributes(field)

            if appmodel._meta.many_to_many:
                for field in appmodel._meta.many_to_many:
                    if skip_field(field):
                        continue
                    add_attributes(field)

            # relations
            def add_relation(field, extras=""):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name

                _rel = {
                    'target_app': field.rel.to.__module__.replace('.', '_'),
                    'target': field.rel.to.__name__,
                    'type': type(field).__name__,
                    'name': field.name,
                    'label': label,
                    'arrows': extras,
                    'needs_node': True
                }
                if _rel not in model['relations'] and consider(_rel['target']):
                    model['relations'].append(_rel)

            for field in appmodel._meta.fields:
                if skip_field(field):
                    continue
                if isinstance(field, OneToOneField):
                    add_relation(field, '[arrowhead=none arrowtail=none]')
                elif isinstance(field, ForeignKey):
                    add_relation(field)

            if appmodel._meta.many_to_many:
                for field in appmodel._meta.many_to_many:
                    if skip_field(field):
                        continue
                    if isinstance(field, ManyToManyField):
                        if (getattr(field, 'creates_table', False)
                                or  # django 1.1.
                            (field.rel.through
                             and field.rel.through._meta.auto_created)
                            ):  # django 1.2
                            add_relation(
                                field, '[arrowhead=normal arrowtail=normal]')
                    elif isinstance(field, GenericRelation):
                        add_relation(
                            field,
                            mark_safe(
                                '[style="dotted"] [arrowhead=normal arrowtail=normal]'
                            ))
            graph['models'].append(model)
        graphs.append(graph)

    nodes = []
    for graph in graphs:
        nodes.extend([e['name'] for e in graph['models']])

    for graph in graphs:
        # don't draw duplication nodes because of relations
        for model in graph['models']:
            for relation in model['relations']:
                if relation['target'] in nodes:
                    relation['needs_node'] = False
        # render templates
        t = loader.get_template('django_extensions/graph_models/body.html')
        dot += '\n' + t.render(graph)

    for graph in graphs:
        t = loader.get_template('django_extensions/graph_models/rel.html')
        dot += '\n' + t.render(graph)

    t = loader.get_template('django_extensions/graph_models/tail.html')
    c = Context({})
    dot += '\n' + t.render(c)
    return dot
예제 #45
0
def send_instant_notifications_about_activity_in_post(
    activity_id=None,
    post_id=None,
    recipients=None,
):

    if recipients is None:
        return

    acceptable_types = const.RESPONSE_ACTIVITY_TYPES_FOR_INSTANT_NOTIFICATIONS

    try:
        update_activity = Activity.objects.filter(
            activity_type__in=acceptable_types).get(id=activity_id)
    except Activity.DoesNotExist:
        logger.error("Unable to fetch activity with id %s" % post_id)
        return

    try:
        post = Post.objects.get(id=post_id)
    except Post.DoesNotExist:
        logger.error("Unable to fetch post with id %s" % post_id)
        return

    if post.is_approved() is False:
        return

    #calculate some variables used in the loop below
    update_type_map = const.RESPONSE_ACTIVITY_TYPE_MAP_FOR_TEMPLATES
    update_type = update_type_map[update_activity.activity_type]
    origin_post = post.get_origin_post()
    headers = mail.thread_headers(post, origin_post,
                                  update_activity.activity_type)

    if logger.getEffectiveLevel() <= logging.DEBUG:
        log_id = uuid.uuid1()
        message = 'email-alert %s, logId=%s' % (post.get_absolute_url(),
                                                log_id)
        logger.debug(message)
    else:
        log_id = None

    for user in recipients:
        if user.is_blocked():
            continue

        reply_address, alt_reply_address = get_reply_to_addresses(user, post)

        activate_language(post.language_code)
        subject_line, body_text = format_instant_notification_email(
            to_user=user,
            from_user=update_activity.user,
            post=post,
            reply_address=reply_address,
            alt_reply_address=alt_reply_address,
            update_type=update_type,
            template=get_template('email/instant_notification.html'))

        headers['Reply-To'] = reply_address
        try:
            mail.send_mail(subject_line=subject_line,
                           body_text=body_text,
                           recipient_list=[user.email],
                           related_object=origin_post,
                           activity_type=const.TYPE_ACTIVITY_EMAIL_UPDATE_SENT,
                           headers=headers,
                           raise_on_failure=True)
        except askbot_exceptions.EmailNotSent, error:
            logger.debug('%s, error=%s, logId=%s' %
                         (user.email, error, log_id))
        else:
            logger.debug('success %s, logId=%s' % (user.email, log_id))
예제 #46
0
def generate_graph_data(app_labels, **kwargs):
    cli_options = kwargs.get('cli_options', None)
    disable_fields = kwargs.get('disable_fields', False)
    include_models = parse_file_or_list(kwargs.get('include_models', ""))
    all_applications = kwargs.get('all_applications', False)
    use_subgraph = kwargs.get('group_models', False)
    verbose_names = kwargs.get('verbose_names', False)
    inheritance = kwargs.get('inheritance', True)
    relations_as_fields = kwargs.get("relations_as_fields", True)
    sort_fields = kwargs.get("sort_fields", True)
    language = kwargs.get('language', None)
    if language is not None:
        activate_language(language)
    exclude_columns = parse_file_or_list(kwargs.get('exclude_columns', ""))
    exclude_models = parse_file_or_list(kwargs.get('exclude_models', ""))

    def skip_field(field):
        if exclude_columns:
            if verbose_names and field.verbose_name:
                if field.verbose_name in exclude_columns:
                    return True
            if field.name in exclude_columns:
                return True
        return False

    if all_applications:
        app_labels = list_app_labels()

    graphs = []
    for app_label in app_labels:
        app = get_app(app_label)
        if not app:
            continue
        graph = Context({
            'name': '"%s"' % app.__name__,
            'app_name': "%s" % '.'.join(app.__name__.split('.')[:-1]),
            'cluster_app_name': "cluster_%s" % app.__name__.replace(".", "_"),
            'models': []
        })

        appmodels = list(get_models_compat(app_label))
        abstract_models = []
        for appmodel in appmodels:
            abstract_models = abstract_models + [abstract_model for abstract_model in appmodel.__bases__ if hasattr(abstract_model, '_meta') and abstract_model._meta.abstract]
        abstract_models = list(set(abstract_models))  # remove duplicates
        appmodels = abstract_models + appmodels

        for appmodel in appmodels:
            appmodel_abstracts = [abstract_model.__name__ for abstract_model in appmodel.__bases__ if hasattr(abstract_model, '_meta') and abstract_model._meta.abstract]

            # collect all attribs of abstract superclasses
            def getBasesAbstractFields(c):
                _abstract_fields = []
                for e in c.__bases__:
                    if hasattr(e, '_meta') and e._meta.abstract:
                        _abstract_fields.extend(e._meta.fields)
                        _abstract_fields.extend(getBasesAbstractFields(e))
                return _abstract_fields
            abstract_fields = getBasesAbstractFields(appmodel)

            model = {
                'app_name': appmodel.__module__.replace(".", "_"),
                'name': appmodel.__name__,
                'abstracts': appmodel_abstracts,
                'fields': [],
                'relations': []
            }

            if not use_model(
                appmodel._meta.object_name,
                include_models,
                exclude_models
            ):
                continue

            if verbose_names and appmodel._meta.verbose_name:
                model['label'] = force_bytes(appmodel._meta.verbose_name)
            else:
                model['label'] = model['name']

            # model attributes
            def add_attributes(field):
                if verbose_names and field.verbose_name:
                    label = force_bytes(field.verbose_name)
                    if label.islower():
                        label = label.capitalize()
                else:
                    label = field.name

                t = type(field).__name__
                if isinstance(field, (OneToOneField, ForeignKey)):
                    t += " ({0})".format(field.rel.field_name)
                # TODO: ManyToManyField, GenericRelation

                model['fields'].append({
                    'name': field.name,
                    'label': label,
                    'type': t,
                    'blank': field.blank,
                    'abstract': field in abstract_fields,
                    'relation': isinstance(field, RelatedField),
                    'primary_key': field.primary_key,
                })

            attributes = [field for field in appmodel._meta.local_fields]
            if not relations_as_fields:
                # Find all the 'real' attributes. Relations are depicted as graph edges instead of attributes
                attributes = [field for field in attributes if not isinstance(field, RelatedField)]

            # find primary key and print it first, ignoring implicit id if other pk exists
            pk = appmodel._meta.pk
            if pk and not appmodel._meta.abstract and pk in attributes:
                add_attributes(pk)

            for field in attributes:
                if skip_field(field):
                    continue
                if pk and field == pk:
                    continue
                add_attributes(field)

            if sort_fields:
                model['fields'] = sorted(model['fields'], key=lambda field: (not field['primary_key'], not field['relation'], field['label']))

            # FIXME: actually many_to_many fields aren't saved in this model's db table, so why should we add an attribute-line for them in the resulting graph?
            # if appmodel._meta.many_to_many:
            #    for field in appmodel._meta.many_to_many:
            #        if skip_field(field):
            #            continue
            #        add_attributes(field)

            # relations
            def add_relation(field, extras=""):
                if verbose_names and field.verbose_name:
                    label = force_bytes(field.verbose_name)
                    if label.islower():
                        label = label.capitalize()
                else:
                    label = field.name

                # show related field name
                if hasattr(field, 'related_query_name'):
                    related_query_name = field.related_query_name()
                    if verbose_names and related_query_name.islower():
                        related_query_name = related_query_name.replace('_', ' ').capitalize()
                    label = '{} ({})'.format(label, force_bytes(related_query_name))

                # handle self-relationships and lazy-relationships
                if isinstance(field.rel.to, six.string_types):
                    if field.rel.to == 'self':
                        target_model = field.model
                    else:
                        target_model = get_model(field.rel.to)
                else:
                    target_model = field.rel.to

                _rel = {
                    'target_app': target_model.__module__.replace('.', '_'),
                    'target': target_model.__name__,
                    'type': type(field).__name__,
                    'name': field.name,
                    'label': label,
                    'arrows': extras,
                    'needs_node': True
                }
                if _rel not in model['relations'] and use_model(
                    _rel['target'],
                    include_models,
                    exclude_models
                ):
                    model['relations'].append(_rel)

            for field in appmodel._meta.local_fields:
                if field.attname.endswith('_ptr_id'):  # excluding field redundant with inheritance relation
                    continue
                if field in abstract_fields:  # excluding fields inherited from abstract classes. they too show as local_fields
                    continue
                if skip_field(field):
                    continue
                if isinstance(field, OneToOneField):
                    add_relation(field, '[arrowhead=none, arrowtail=none, dir=both]')
                elif isinstance(field, ForeignKey):
                    add_relation(field, '[arrowhead=none, arrowtail=dot, dir=both]')

            for field in appmodel._meta.local_many_to_many:
                if skip_field(field):
                    continue
                if isinstance(field, ManyToManyField):
                    if (getattr(field, 'creates_table', False) or  # django 1.1.
                            (hasattr(field.rel.through, '_meta') and field.rel.through._meta.auto_created)):  # django 1.2
                        add_relation(field, '[arrowhead=dot arrowtail=dot, dir=both]')
                elif isinstance(field, GenericRelation):
                    add_relation(field, mark_safe('[style="dotted", arrowhead=normal, arrowtail=normal, dir=both]'))

            if inheritance:
                # add inheritance arrows
                for parent in appmodel.__bases__:
                    if hasattr(parent, "_meta"):  # parent is a model
                        l = "multi-table"
                        if parent._meta.abstract:
                            l = "abstract"
                        if appmodel._meta.proxy:
                            l = "proxy"
                        l += r"\ninheritance"
                        _rel = {
                            'target_app': parent.__module__.replace(".", "_"),
                            'target': parent.__name__,
                            'type': "inheritance",
                            'name': "inheritance",
                            'label': l,
                            'arrows': '[arrowhead=empty, arrowtail=none, dir=both]',
                            'needs_node': True,
                        }
                        # TODO: seems as if abstract models aren't part of models.getModels, which is why they are printed by this without any attributes.
                        if _rel not in model['relations'] and use_model(
                            _rel['target'],
                            include_models,
                            exclude_columns
                        ):
                            model['relations'].append(_rel)

            graph['models'].append(model)
        if graph['models']:
            graphs.append(graph)

    nodes = []
    for graph in graphs:
        nodes.extend([e['name'] for e in graph['models']])

    for graph in graphs:
        for model in graph['models']:
            for relation in model['relations']:
                if relation['target'] in nodes:
                    relation['needs_node'] = False

    now = datetime.datetime.now()
    graph_data = {
        'created_at': now.strftime("%Y-%m-%d %H:%M"),
        'cli_options': cli_options,
        'disable_fields': disable_fields,
        'use_subgraph': use_subgraph,
        'graphs': graphs,
    }
    return graph_data
예제 #47
0
def langpage(request, lang, page):
	translation.activate_language(lang)
	return page(request, page)
예제 #48
0
def generate_dot(app_labels, **kwargs):
    disable_fields = kwargs.get('disable_fields', False)
    include_models = parse_file_or_list(kwargs.get('include_models', ""))
    all_applications = kwargs.get('all_applications', False)
    use_subgraph = kwargs.get('group_models', False)
    verbose_names = kwargs.get('verbose_names', False)
    inheritance = kwargs.get('inheritance', False)
    language = kwargs.get('language', None)
    if language is not None:
        activate_language(language)
    exclude_columns = parse_file_or_list(kwargs.get('exclude_columns', ""))
    exclude_models = parse_file_or_list(kwargs.get('exclude_models', ""))

    def skip_field(field):
        if exclude_columns:
            if verbose_names and field.verbose_name:
                if field.verbose_name in exclude_columns:
                    return True
            if field.name in exclude_columns:
                return True
        return False

    t = loader.get_template_from_string("""
digraph name {
  fontname = "Helvetica"
  fontsize = 8

  node [
    fontname = "Helvetica"
    fontsize = 8
    shape = "plaintext"
  ]
  edge [
    fontname = "Helvetica"
    fontsize = 8
  ]

""")
    c = Context({})
    dot = t.render(c)

    apps = []
    if all_applications:
        apps = models.get_apps()

    for app_label in app_labels:
        app = models.get_app(app_label)
        if not app in apps:
            apps.append(app)

    graphs = []
    for app in apps:
        graph = Context({
            'name':
            '"%s"' % app.__name__,
            'app_name':
            "%s" % '.'.join(app.__name__.split('.')[:-1]),
            'cluster_app_name':
            "cluster_%s" % app.__name__.replace(".", "_"),
            'disable_fields':
            disable_fields,
            'use_subgraph':
            use_subgraph,
            'models': []
        })

        appmodels = get_models(app)
        abstract_models = []
        for appmodel in appmodels:
            abstract_models = abstract_models + [
                abstract_model
                for abstract_model in appmodel.__bases__ if hasattr(
                    abstract_model, '_meta') and abstract_model._meta.abstract
            ]
        abstract_models = list(set(abstract_models))  # remove duplicates
        appmodels = abstract_models + appmodels

        for appmodel in appmodels:
            appmodel_abstracts = [
                abstract_model.__name__
                for abstract_model in appmodel.__bases__
                if hasattr(abstract_model, '_meta')
                and abstract_model._meta.abstract
            ]

            # collect all attribs of abstract superclasses
            def getBasesAbstractFields(c):
                _abstract_fields = []
                for e in c.__bases__:
                    if hasattr(e, '_meta') and e._meta.abstract:
                        _abstract_fields.extend(e._meta.fields)
                        _abstract_fields.extend(getBasesAbstractFields(e))
                return _abstract_fields

            abstract_fields = getBasesAbstractFields(appmodel)

            model = {
                'app_name': appmodel.__module__.replace(".", "_"),
                'name': appmodel.__name__,
                'abstracts': appmodel_abstracts,
                'fields': [],
                'relations': []
            }

            # consider given model name ?
            def consider(model_name):
                if exclude_models and model_name in exclude_models:
                    return False
                return not include_models or model_name in include_models

            if not consider(appmodel._meta.object_name):
                continue

            if verbose_names and appmodel._meta.verbose_name:
                model['label'] = appmodel._meta.verbose_name
            else:
                model['label'] = model['name']

            # model attributes
            def add_attributes(field):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name

                t = type(field).__name__
                if isinstance(field, (OneToOneField, ForeignKey)):
                    t += " ({0})".format(field.rel.field_name)
                # TODO: ManyToManyField, GenericRelation

                model['fields'].append({
                    'name': field.name,
                    'label': label,
                    'type': t,
                    'blank': field.blank,
                    'abstract': field in abstract_fields,
                })

            # Find all the real attributes. Relations are depicted as graph edges instead of attributes
            attributes = [
                field for field in appmodel._meta.local_fields
                if not isinstance(field, RelatedField)
            ]

            # find primary key and print it first, ignoring implicit id if other pk exists
            pk = appmodel._meta.pk
            if not appmodel._meta.abstract and pk in attributes:
                add_attributes(pk)
            for field in attributes:
                if skip_field(field):
                    continue
                if not field.primary_key:
                    add_attributes(field)

            # FIXME: actually many_to_many fields aren't saved in this model's db table, so why should we add an attribute-line for them in the resulting graph?
            #if appmodel._meta.many_to_many:
            #    for field in appmodel._meta.many_to_many:
            #        if skip_field(field):
            #            continue
            #        add_attributes(field)

            # relations
            def add_relation(field, extras=""):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name

                # show related field name
                if hasattr(field, 'related_query_name'):
                    label += ' (%s)' % field.related_query_name()

                # handle self-relationships
                if field.rel.to == 'self':
                    target_model = field.model
                else:
                    target_model = field.rel.to

                _rel = {
                    'target_app': target_model.__module__.replace('.', '_'),
                    'target': target_model.__name__,
                    'type': type(field).__name__,
                    'name': field.name,
                    'label': label,
                    'arrows': extras,
                    'needs_node': True
                }
                if _rel not in model['relations'] and consider(_rel['target']):
                    model['relations'].append(_rel)

            for field in appmodel._meta.local_fields:
                if field.attname.endswith(
                        '_ptr_id'
                ):  # excluding field redundant with inheritance relation
                    continue
                if field in abstract_fields:  # excluding fields inherited from abstract classes. they too show as local_fields
                    continue
                if skip_field(field):
                    continue
                if isinstance(field, OneToOneField):
                    add_relation(field, '[arrowhead=none, arrowtail=none]')
                elif isinstance(field, ForeignKey):
                    add_relation(field, '[arrowhead=none, arrowtail=dot]')

            for field in appmodel._meta.local_many_to_many:
                if skip_field(field):
                    continue
                if isinstance(field, ManyToManyField):
                    if (getattr(field, 'creates_table', False)
                            or  # django 1.1.
                        (hasattr(field.rel.through, '_meta') and
                         field.rel.through._meta.auto_created)):  # django 1.2
                        add_relation(
                            field, '[arrowhead=dot arrowtail=dot, dir=both]')
                    elif isinstance(field, GenericRelation):
                        add_relation(
                            field,
                            mark_safe(
                                '[style="dotted", arrowhead=normal, arrowtail=normal, dir=both]'
                            ))

            if inheritance:
                # add inheritance arrows
                for parent in appmodel.__bases__:
                    if hasattr(parent, "_meta"):  # parent is a model
                        l = "multi-table"
                        if parent._meta.abstract:
                            l = "abstract"
                        if appmodel._meta.proxy:
                            l = "proxy"
                        l += r"\ninheritance"
                        _rel = {
                            'target_app': parent.__module__.replace(".", "_"),
                            'target': parent.__name__,
                            'type': "inheritance",
                            'name': "inheritance",
                            'label': l,
                            'arrows': '[arrowhead=empty, arrowtail=none]',
                            'needs_node': True
                        }
                        # TODO: seems as if abstract models aren't part of models.getModels, which is why they are printed by this without any attributes.
                        if _rel not in model['relations'] and consider(
                                _rel['target']):
                            model['relations'].append(_rel)

            graph['models'].append(model)
        graphs.append(graph)

    nodes = []
    for graph in graphs:
        nodes.extend([e['name'] for e in graph['models']])

    for graph in graphs:
        # don't draw duplication nodes because of relations
        for model in graph['models']:
            for relation in model['relations']:
                if relation['target'] in nodes:
                    relation['needs_node'] = False
        # render templates
        t = loader.get_template_from_string("""{% if use_subgraph %}
subgraph {{ cluster_app_name }} {
  label=<
        <TABLE BORDER="0" CELLBORDER="0" CELLSPACING="0">
        <TR><TD COLSPAN="2" CELLPADDING="4" ALIGN="CENTER"
        ><FONT FACE="Helvetica Bold" COLOR="Black" POINT-SIZE="12"
        >{{ app_name }}</FONT></TD></TR>
        </TABLE>
        >
  color=olivedrab4
  style="rounded"
{% endif %}
{% for model in models %}
    {{ model.app_name }}_{{ model.name }} [label=<
    <TABLE BGCOLOR="palegoldenrod" BORDER="0" CELLBORDER="0" CELLSPACING="0">
     <TR><TD COLSPAN="2" CELLPADDING="4" ALIGN="CENTER" BGCOLOR="olivedrab4"
     ><FONT FACE="Helvetica Bold" COLOR="white"
     >{{ model.label }}{% if model.abstracts %}<BR/>&lt;<FONT FACE="Helvetica Italic">{{ model.abstracts|join:"," }}</FONT>&gt;{% endif %}</FONT></TD></TR>
    {% if not disable_fields %}
        {% for field in model.fields %}
        <TR><TD ALIGN="LEFT" BORDER="0"
        ><FONT {% if field.blank %}COLOR="#7B7B7B" {% endif %}FACE="Helvetica {% if field.abstract %}Italic{% else %}Bold{% endif %}">{{ field.label }}</FONT
></TD>
        <TD ALIGN="LEFT"
        ><FONT {% if field.blank %}COLOR="#7B7B7B" {% endif %}FACE="Helvetica {% if field.abstract %}Italic{% else %}Bold{% endif %}">{{ field.type }}</FONT
></TD></TR>
        {% endfor %}
    {% endif %}
    </TABLE>
    >]
{% endfor %}
{% if use_subgraph %}
}
{% endif %}""")
        dot += '\n' + t.render(graph)

    for graph in graphs:
        t = loader.get_template_from_string("""{% for model in models %}
  {% for relation in model.relations %}
  {% if relation.needs_node %}
  {{ relation.target_app }}_{{ relation.target }} [label=<
      <TABLE BGCOLOR="palegoldenrod" BORDER="0" CELLBORDER="0" CELLSPACING="0">
      <TR><TD COLSPAN="2" CELLPADDING="4" ALIGN="CENTER" BGCOLOR="olivedrab4"
      ><FONT FACE="Helvetica Bold" COLOR="white"
      >{{ relation.target }}</FONT></TD></TR>
      </TABLE>
      >]
  {% endif %}
  {{ model.app_name }}_{{ model.name }} -> {{ relation.target_app }}_{{ relation.target }}
  [label="{{ relation.label }}"] {{ relation.arrows }};
  {% endfor %}
{% endfor %}""")
        dot += '\n' + t.render(graph)

    t = loader.get_template_from_string("}")
    c = Context({})
    dot += '\n' + t.render(c)
    return dot
예제 #49
0
    def send_email_alerts(self, user):
        #does not change the database, only sends the email
        #todo: move this to template
        user.add_missing_askbot_subscriptions()

        #todo: q_list is a dictionary, not a list
        q_list = self.get_updated_questions_for_user(user)

        if len(q_list.keys()) == 0:
            return

        num_q = 0

        for question, meta_data in q_list.items():
            if meta_data['skip']:
                del q_list[question]
            else:
                num_q += 1
        if num_q > 0:
            threads = Thread.objects.filter(
                id__in=[qq.thread_id for qq in q_list.keys()])
            tag_summary = Thread.objects.get_tag_summary_from_threads(threads)

            question_count = len(q_list.keys())

            items_added = 0
            items_unreported = 0
            questions_data = list()
            for q, meta_data in q_list.items():
                act_list = []
                if meta_data['skip']:
                    continue
                if items_added >= askbot_settings.MAX_ALERTS_PER_EMAIL:
                    items_unreported = num_q - items_added  #may be inaccurate actually, but it's ok
                    break
                else:
                    items_added += 1
                    if meta_data['new_q']:
                        act_list.append(_('new question'))
                    format_action_count('%(num)d rev', meta_data['q_rev'],
                                        act_list)
                    format_action_count('%(num)d ans', meta_data['new_ans'],
                                        act_list)
                    format_action_count('%(num)d ans rev',
                                        meta_data['ans_rev'], act_list)
                    questions_data.append({
                        'url': site_url(q.get_absolute_url()),
                        'info': ', '.join(act_list),
                        'title': q.thread.title
                    })

            activate_language(user.get_primary_language())
            email = BatchEmailAlert({
                'questions': questions_data,
                'question_count': question_count,
                'tag_summary': tag_summary,
                'user': user
            })

            if DEBUG_THIS_COMMAND == True:
                recipient_email = askbot_settings.ADMIN_EMAIL
            else:
                recipient_email = user.email

            if recipient_email:
                email.send([recipient_email])
예제 #50
0
def generate_dot(app_labels, **kwargs):
    disable_fields = kwargs.get("disable_fields", False)
    include_models = parse_file_or_list(kwargs.get("include_models", ""))
    all_applications = kwargs.get("all_applications", False)
    use_subgraph = kwargs.get("group_models", False)
    verbose_names = kwargs.get("verbose_names", False)
    inheritance = kwargs.get("inheritance", False)
    language = kwargs.get("language", None)
    if language is not None:
        activate_language(language)
    exclude_columns = parse_file_or_list(kwargs.get("exclude_columns", ""))
    exclude_models = parse_file_or_list(kwargs.get("exclude_models", ""))

    def skip_field(field):
        if exclude_columns:
            if verbose_names and field.verbose_name:
                if field.verbose_name in exclude_columns:
                    return True
            if field.name in exclude_columns:
                return True
        return False

    t = loader.get_template("django_extensions/graph_models/head.html")
    c = Context({})
    dot = t.render(c)

    apps = []
    if all_applications:
        apps = models.get_apps()

    for app_label in app_labels:
        app = models.get_app(app_label)
        if not app in apps:
            apps.append(app)

    graphs = []
    for app in apps:
        graph = Context(
            {
                "name": '"%s"' % app.__name__,
                "app_name": "%s" % ".".join(app.__name__.split(".")[:-1]),
                "cluster_app_name": "cluster_%s" % app.__name__.replace(".", "_"),
                "disable_fields": disable_fields,
                "use_subgraph": use_subgraph,
                "models": [],
            }
        )

        appmodels = get_models(app)
        abstract_models = []
        for appmodel in appmodels:
            abstract_models = abstract_models + [
                abstract_model
                for abstract_model in appmodel.__bases__
                if hasattr(abstract_model, "_meta") and abstract_model._meta.abstract
            ]
        abstract_models = list(set(abstract_models))  # remove duplicates
        appmodels = abstract_models + appmodels

        for appmodel in appmodels:
            appmodel_abstracts = [
                abstract_model.__name__
                for abstract_model in appmodel.__bases__
                if hasattr(abstract_model, "_meta") and abstract_model._meta.abstract
            ]

            # collect all attribs of abstract superclasses
            def getBasesAbstractFields(c):
                _abstract_fields = []
                for e in c.__bases__:
                    if hasattr(e, "_meta") and e._meta.abstract:
                        _abstract_fields.extend(e._meta.fields)
                        _abstract_fields.extend(getBasesAbstractFields(e))
                return _abstract_fields

            abstract_fields = getBasesAbstractFields(appmodel)

            model = {
                "app_name": appmodel.__module__.replace(".", "_"),
                "name": appmodel.__name__,
                "abstracts": appmodel_abstracts,
                "fields": [],
                "relations": [],
            }

            # consider given model name ?
            def consider(model_name):
                if exclude_models and model_name in exclude_models:
                    return False
                return not include_models or model_name in include_models

            if not consider(appmodel._meta.object_name):
                continue

            if verbose_names and appmodel._meta.verbose_name:
                model["label"] = appmodel._meta.verbose_name
            else:
                model["label"] = model["name"]

            # model attributes
            def add_attributes(field):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name

                t = type(field).__name__
                if isinstance(field, (OneToOneField, ForeignKey)):
                    t += " ({0})".format(field.rel.field_name)
                # TODO: ManyToManyField, GenericRelation

                model["fields"].append(
                    {
                        "name": field.name,
                        "label": label,
                        "type": t,
                        "blank": field.blank,
                        "abstract": field in abstract_fields,
                    }
                )

            # Find all the real attributes. Relations are depicted as graph edges instead of attributes
            attributes = [field for field in appmodel._meta.local_fields if not isinstance(field, RelatedField)]

            # find primary key and print it first, ignoring implicit id if other pk exists
            pk = appmodel._meta.pk
            if not appmodel._meta.abstract and pk in attributes:
                add_attributes(pk)
            for field in attributes:
                if skip_field(field):
                    continue
                if not field.primary_key:
                    add_attributes(field)

            # FIXME: actually many_to_many fields aren't saved in this model's db table, so why should we add an attribute-line for them in the resulting graph?
            # if appmodel._meta.many_to_many:
            #    for field in appmodel._meta.many_to_many:
            #        if skip_field(field):
            #            continue
            #        add_attributes(field)

            # relations
            def add_relation(field, extras=""):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name

                # show related field name
                if hasattr(field, "related_query_name"):
                    label += " (%s)" % field.related_query_name()

                _rel = {
                    "target_app": field.rel.to.__module__.replace(".", "_"),
                    "target": field.rel.to.__name__,
                    "type": type(field).__name__,
                    "name": field.name,
                    "label": label,
                    "arrows": extras,
                    "needs_node": True,
                }
                if _rel not in model["relations"] and consider(_rel["target"]):
                    model["relations"].append(_rel)

            for field in appmodel._meta.local_fields:
                if field.attname.endswith("_ptr_id"):  # excluding field redundant with inheritance relation
                    continue
                if (
                    field in abstract_fields
                ):  # excluding fields inherited from abstract classes. they too show as local_fields
                    continue
                if skip_field(field):
                    continue
                if isinstance(field, OneToOneField):
                    add_relation(field, "[arrowhead=none, arrowtail=none]")
                elif isinstance(field, ForeignKey):
                    add_relation(field, "[arrowhead=none, arrowtail=dot]")

            for field in appmodel._meta.local_many_to_many:
                if skip_field(field):
                    continue
                if isinstance(field, ManyToManyField):
                    if getattr(field, "creates_table", False) or (  # django 1.1.
                        hasattr(field.rel.through, "_meta") and field.rel.through._meta.auto_created
                    ):  # django 1.2
                        add_relation(field, "[arrowhead=dot arrowtail=dot, dir=both]")
                    elif isinstance(field, GenericRelation):
                        add_relation(field, mark_safe('[style="dotted", arrowhead=normal, arrowtail=normal, dir=both]'))

            if inheritance:
                # add inheritance arrows
                for parent in appmodel.__bases__:
                    if hasattr(parent, "_meta"):  # parent is a model
                        l = "multi-table"
                        if parent._meta.abstract:
                            l = "abstract"
                        if appmodel._meta.proxy:
                            l = "proxy"
                        l += r"\ninheritance"
                        _rel = {
                            "target_app": parent.__module__.replace(".", "_"),
                            "target": parent.__name__,
                            "type": "inheritance",
                            "name": "inheritance",
                            "label": l,
                            "arrows": "[arrowhead=empty, arrowtail=none]",
                            "needs_node": True,
                        }
                        # TODO: seems as if abstract models aren't part of models.getModels, which is why they are printed by this without any attributes.
                        if _rel not in model["relations"] and consider(_rel["target"]):
                            model["relations"].append(_rel)

            graph["models"].append(model)
        graphs.append(graph)

    nodes = []
    for graph in graphs:
        nodes.extend([e["name"] for e in graph["models"]])

    for graph in graphs:
        # don't draw duplication nodes because of relations
        for model in graph["models"]:
            for relation in model["relations"]:
                if relation["target"] in nodes:
                    relation["needs_node"] = False
        # render templates
        t = loader.get_template("django_extensions/graph_models/body.html")
        dot += "\n" + t.render(graph)

    for graph in graphs:
        t = loader.get_template("django_extensions/graph_models/rel.html")
        dot += "\n" + t.render(graph)

    t = loader.get_template("django_extensions/graph_models/tail.html")
    c = Context({})
    dot += "\n" + t.render(c)
    return dot
예제 #51
0
def langpage(request, lang, page):
    translation.activate_language(lang)
    return page(request, page)
예제 #52
0
def generate_dot(app_labels, **kwargs):
    disable_fields = kwargs.get('disable_fields', False)
    include_models = parse_file_or_list(kwargs.get('include_models', ""))
    all_applications = kwargs.get('all_applications', False)
    use_subgraph = kwargs.get('group_models', False)
    verbose_names = kwargs.get('verbose_names', False)
    inheritance = kwargs.get('inheritance', False)
    language = kwargs.get('language', None)
    if language is not None:
        activate_language(language)
    exclude_columns = parse_file_or_list(kwargs.get('exclude_columns', ""))
    exclude_models = parse_file_or_list(kwargs.get('exclude_models', ""))

    def skip_field(field):
        if exclude_columns:
            if verbose_names and field.verbose_name:
                if field.verbose_name in exclude_columns:
                    return True
            if field.name in exclude_columns:
                return True
        return False




    t = loader.get_template_from_string("""
digraph name {
  fontname = "Helvetica"
  fontsize = 8

  node [
    fontname = "Helvetica"
    fontsize = 8
    shape = "plaintext"
  ]
  edge [
    fontname = "Helvetica"
    fontsize = 8
  ]

""")
    c = Context({})
    dot = t.render(c)

    apps = []
    if all_applications:
        apps = models.get_apps()

    for app_label in app_labels:
        app = models.get_app(app_label)
        if not app in apps:
            apps.append(app)

    graphs = []
    for app in apps:
        graph = Context({
            'name': '"%s"' % app.__name__,
            'app_name': "%s" % '.'.join(app.__name__.split('.')[:-1]),
            'cluster_app_name': "cluster_%s" % app.__name__.replace(".", "_"),
            'disable_fields': disable_fields,
            'use_subgraph': use_subgraph,
            'models': []
        })

        appmodels = get_models(app)
        abstract_models = []
        for appmodel in appmodels:
            abstract_models = abstract_models + [abstract_model for abstract_model in appmodel.__bases__ if hasattr(abstract_model, '_meta') and abstract_model._meta.abstract]
        abstract_models = list(set(abstract_models)) # remove duplicates
        appmodels = abstract_models + appmodels
        

        for appmodel in appmodels:
            appmodel_abstracts = [abstract_model.__name__ for abstract_model in appmodel.__bases__ if hasattr(abstract_model, '_meta') and abstract_model._meta.abstract]

            # collect all attribs of abstract superclasses
            def getBasesAbstractFields(c):
                _abstract_fields = []
                for e in c.__bases__:
                    if hasattr(e, '_meta') and e._meta.abstract:
                        _abstract_fields.extend(e._meta.fields)
                        _abstract_fields.extend(getBasesAbstractFields(e))
                return _abstract_fields
            abstract_fields = getBasesAbstractFields(appmodel)

            model = {
                'app_name': appmodel.__module__.replace(".", "_"),
                'name': appmodel.__name__,
                'abstracts': appmodel_abstracts,
                'fields': [],
                'relations': []
            }

            # consider given model name ?
            def consider(model_name):
                if exclude_models and model_name in exclude_models:
                    return False
                return not include_models or model_name in include_models

            if not consider(appmodel._meta.object_name):
                continue

            if verbose_names and appmodel._meta.verbose_name:
                model['label'] = appmodel._meta.verbose_name
            else:
                model['label'] = model['name']

            # model attributes
            def add_attributes(field):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name

                t = type(field).__name__
                if isinstance(field, (OneToOneField, ForeignKey)):
                    t += " ({0})".format(field.rel.field_name)
                # TODO: ManyToManyField, GenericRelation

                model['fields'].append({
                    'name': field.name,
                    'label': label,
                    'type': t,
                    'blank': field.blank,
                    'abstract': field in abstract_fields,
                })

            # Find all the real attributes. Relations are depicted as graph edges instead of attributes
            attributes = [field for field in appmodel._meta.local_fields if not isinstance(field, RelatedField)]

            # find primary key and print it first, ignoring implicit id if other pk exists
            pk = appmodel._meta.pk
            if not appmodel._meta.abstract and pk in attributes:
                add_attributes(pk)
            for field in attributes:
                if skip_field(field):
                    continue
                if not field.primary_key:
                    add_attributes(field)
            
            # FIXME: actually many_to_many fields aren't saved in this model's db table, so why should we add an attribute-line for them in the resulting graph?
            #if appmodel._meta.many_to_many:
            #    for field in appmodel._meta.many_to_many:
            #        if skip_field(field):
            #            continue
            #        add_attributes(field)

            # relations
            def add_relation(field, extras=""):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name
                    
                # show related field name
                if hasattr(field, 'related_query_name'):
                    label += ' (%s)' % field.related_query_name()

                # handle self-relationships
                if field.rel.to == 'self':
                    target_model = field.model 
                else:
                    target_model = field.rel.to

                _rel = {
                    'target_app': target_model.__module__.replace('.', '_'),
                    'target': target_model.__name__,
                    'type': type(field).__name__,
                    'name': field.name,
                    'label': label,
                    'arrows': extras,
                    'needs_node': True
                }
                if _rel not in model['relations'] and consider(_rel['target']):
                    model['relations'].append(_rel)

            for field in appmodel._meta.local_fields:
                if field.attname.endswith('_ptr_id'): # excluding field redundant with inheritance relation
                    continue
                if field in abstract_fields: # excluding fields inherited from abstract classes. they too show as local_fields
                    continue
                if skip_field(field):
                    continue
                if isinstance(field, OneToOneField):
                    add_relation(field, '[arrowhead=none, arrowtail=none]')
                elif isinstance(field, ForeignKey):
                    add_relation(field, '[arrowhead=none, arrowtail=dot]')

            for field in appmodel._meta.local_many_to_many:
                if skip_field(field):
                    continue
                if isinstance(field, ManyToManyField):
                    if (getattr(field, 'creates_table', False) or  # django 1.1.
                        (hasattr(field.rel.through, '_meta') and field.rel.through._meta.auto_created)):  # django 1.2
                        add_relation(field, '[arrowhead=dot arrowtail=dot, dir=both]')
                    elif isinstance(field, GenericRelation):
                        add_relation(field, mark_safe('[style="dotted", arrowhead=normal, arrowtail=normal, dir=both]'))
            
            if inheritance:
                # add inheritance arrows
                for parent in appmodel.__bases__:
                    if hasattr(parent, "_meta"): # parent is a model
                        l = "multi-table"
                        if parent._meta.abstract:
                            l = "abstract"
                        if appmodel._meta.proxy:
                            l = "proxy"
                        l += r"\ninheritance"
                        _rel = {
                            'target_app': parent.__module__.replace(".", "_"),
                            'target': parent.__name__,
                            'type': "inheritance",
                            'name': "inheritance",
                            'label': l,
                            'arrows': '[arrowhead=empty, arrowtail=none]',
                            'needs_node': True
                        }
                        # TODO: seems as if abstract models aren't part of models.getModels, which is why they are printed by this without any attributes.
                        if _rel not in model['relations'] and consider(_rel['target']):
                            model['relations'].append(_rel)
            
            graph['models'].append(model)
        graphs.append(graph)

    nodes = []
    for graph in graphs:
        nodes.extend([e['name'] for e in graph['models']])

    for graph in graphs:
        # don't draw duplication nodes because of relations
        for model in graph['models']:
            for relation in model['relations']:
                if relation['target'] in nodes:
                    relation['needs_node'] = False
        # render templates
        t = loader.get_template_from_string("""{% if use_subgraph %}
subgraph {{ cluster_app_name }} {
  label=<
        <TABLE BORDER="0" CELLBORDER="0" CELLSPACING="0">
        <TR><TD COLSPAN="2" CELLPADDING="4" ALIGN="CENTER"
        ><FONT FACE="Helvetica Bold" COLOR="Black" POINT-SIZE="12"
        >{{ app_name }}</FONT></TD></TR>
        </TABLE>
        >
  color=olivedrab4
  style="rounded"
{% endif %}
{% for model in models %}
    {{ model.app_name }}_{{ model.name }} [label=<
    <TABLE BGCOLOR="palegoldenrod" BORDER="0" CELLBORDER="0" CELLSPACING="0">
     <TR><TD COLSPAN="2" CELLPADDING="4" ALIGN="CENTER" BGCOLOR="olivedrab4"
     ><FONT FACE="Helvetica Bold" COLOR="white"
     >{{ model.label }}{% if model.abstracts %}<BR/>&lt;<FONT FACE="Helvetica Italic">{{ model.abstracts|join:"," }}</FONT>&gt;{% endif %}</FONT></TD></TR>
    {% if not disable_fields %}
        {% for field in model.fields %}
        <TR><TD ALIGN="LEFT" BORDER="0"
        ><FONT {% if field.blank %}COLOR="#7B7B7B" {% endif %}FACE="Helvetica {% if field.abstract %}Italic{% else %}Bold{% endif %}">{{ field.label }}</FONT
></TD>
        <TD ALIGN="LEFT"
        ><FONT {% if field.blank %}COLOR="#7B7B7B" {% endif %}FACE="Helvetica {% if field.abstract %}Italic{% else %}Bold{% endif %}">{{ field.type }}</FONT
></TD></TR>
        {% endfor %}
    {% endif %}
    </TABLE>
    >]
{% endfor %}
{% if use_subgraph %}
}
{% endif %}""")
        dot += '\n' + t.render(graph)

    for graph in graphs:
        t = loader.get_template_from_string("""{% for model in models %}
  {% for relation in model.relations %}
  {% if relation.needs_node %}
  {{ relation.target_app }}_{{ relation.target }} [label=<
      <TABLE BGCOLOR="palegoldenrod" BORDER="0" CELLBORDER="0" CELLSPACING="0">
      <TR><TD COLSPAN="2" CELLPADDING="4" ALIGN="CENTER" BGCOLOR="olivedrab4"
      ><FONT FACE="Helvetica Bold" COLOR="white"
      >{{ relation.target }}</FONT></TD></TR>
      </TABLE>
      >]
  {% endif %}
  {{ model.app_name }}_{{ model.name }} -> {{ relation.target_app }}_{{ relation.target }}
  [label="{{ relation.label }}"] {{ relation.arrows }};
  {% endfor %}
{% endfor %}""")
        dot += '\n' + t.render(graph)


    t = loader.get_template_from_string("}")
    c = Context({})
    dot += '\n' + t.render(c)
    return dot
예제 #53
0
def send_instant_notifications_about_activity_in_post(
                                                update_activity = None,
                                                post = None,
                                                recipients = None,
                                            ):
    #reload object from the database
    post = Post.objects.get(id=post.id)
    if post.is_approved() is False:
        return

    if recipients is None:
        return

    acceptable_types = const.RESPONSE_ACTIVITY_TYPES_FOR_INSTANT_NOTIFICATIONS

    if update_activity.activity_type not in acceptable_types:
        return

    #calculate some variables used in the loop below
    update_type_map = const.RESPONSE_ACTIVITY_TYPE_MAP_FOR_TEMPLATES
    update_type = update_type_map[update_activity.activity_type]
    origin_post = post.get_origin_post()
    headers = mail.thread_headers(
                            post,
                            origin_post,
                            update_activity.activity_type
                        )

    logger = logging.getLogger()
    if logger.getEffectiveLevel() <= logging.DEBUG:
        log_id = uuid.uuid1()
        message = 'email-alert %s, logId=%s' % (post.get_absolute_url(), log_id)
        logger.debug(message)
    else:
        log_id = None


    for user in recipients:
        if user.is_blocked():
            continue

        reply_address, alt_reply_address = get_reply_to_addresses(user, post)

        activate_language(post.language_code)
        subject_line, body_text = format_instant_notification_email(
                            to_user = user,
                            from_user = update_activity.user,
                            post = post,
                            reply_address = reply_address,
                            alt_reply_address = alt_reply_address,
                            update_type = update_type,
                            template = get_template('email/instant_notification.html')
                        )

        headers['Reply-To'] = reply_address
        try:
            mail.send_mail(
                subject_line=subject_line,
                body_text=body_text,
                recipient_list=[user.email],
                related_object=origin_post,
                activity_type=const.TYPE_ACTIVITY_EMAIL_UPDATE_SENT,
                headers=headers,
                raise_on_failure=True
            )
        except askbot_exceptions.EmailNotSent, error:
            logger.debug(
                '%s, error=%s, logId=%s' % (user.email, error, log_id)
            )
        else:
            logger.debug('success %s, logId=%s' % (user.email, log_id))
예제 #54
0
def generate_dot(app_labels, **kwargs):
    disable_fields = kwargs.get('disable_fields', False)
    include_models = parse_file_or_list(kwargs.get('include_models', ""))
    all_applications = kwargs.get('all_applications', False)
    use_subgraph = kwargs.get('group_models', False)
    verbose_names = kwargs.get('verbose_names', False)
    inheritance = kwargs.get('inheritance', False)
    language = kwargs.get('language', None)
    if language is not None:
        activate_language(language)
    exclude_columns = parse_file_or_list(kwargs.get('exclude_columns', ""))
    exclude_models = parse_file_or_list(kwargs.get('exclude_models', ""))

    def skip_field(field):
        if exclude_columns:
            if verbose_names and field.verbose_name:
                if field.verbose_name in exclude_columns:
                    return True
            if field.name in exclude_columns:
                return True
        return False

    t = loader.get_template('django_extensions/graph_models/head.html')
    c = Context({})
    dot = t.render(c)

    apps = []
    if all_applications:
        apps = models.get_apps()

    for app_label in app_labels:
        app = models.get_app(app_label)
        if app not in apps:
            apps.append(app)

    graphs = []
    for app in apps:
        graph = Context({
            'name': '"%s"' % app.__name__,
            'app_name': "%s" % '.'.join(app.__name__.split('.')[:-1]),
            'cluster_app_name': "cluster_%s" % app.__name__.replace(".", "_"),
            'disable_fields': disable_fields,
            'use_subgraph': use_subgraph,
            'models': []
        })

        appmodels = get_models(app)
        abstract_models = []
        for appmodel in appmodels:
            abstract_models = abstract_models + [
                abstract_model for abstract_model in appmodel.__bases__ if hasattr(
                    abstract_model, '_meta') and abstract_model._meta.abstract]
        abstract_models = list(set(abstract_models))  # remove duplicates
        appmodels = abstract_models + appmodels

        for appmodel in appmodels:
            appmodel_abstracts = [
                abstract_model.__name__ for abstract_model in appmodel.__bases__ if hasattr(
                    abstract_model, '_meta') and abstract_model._meta.abstract]

            # collect all attribs of abstract superclasses
            def getBasesAbstractFields(c):
                _abstract_fields = []
                for e in c.__bases__:
                    if hasattr(e, '_meta') and e._meta.abstract:
                        _abstract_fields.extend(e._meta.fields)
                        _abstract_fields.extend(getBasesAbstractFields(e))
                return _abstract_fields
            abstract_fields = getBasesAbstractFields(appmodel)

            model = {
                'app_name': appmodel.__module__.replace(".", "_"),
                'name': appmodel.__name__,
                'abstracts': appmodel_abstracts,
                'fields': [],
                'relations': []
            }

            # consider given model name ?
            def consider(model_name):
                if exclude_models and model_name in exclude_models:
                    return False
                return not include_models or model_name in include_models

            if not consider(appmodel._meta.object_name):
                continue

            if verbose_names and appmodel._meta.verbose_name:
                model['label'] = appmodel._meta.verbose_name
            else:
                model['label'] = model['name']

            # model attributes
            def add_attributes(field):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name

                t = type(field).__name__
                if isinstance(field, (OneToOneField, ForeignKey)):
                    t += " ({0})".format(field.rel.field_name)
                # TODO: ManyToManyField, GenericRelation

                model['fields'].append({
                    'name': field.name,
                    'label': label,
                    'type': t,
                    'blank': field.blank,
                    'abstract': field in abstract_fields,
                })

            # Find all the real attributes. Relations are depicted as graph
            # edges instead of attributes
            attributes = [
                field for field in appmodel._meta.local_fields if not isinstance(
                    field, RelatedField)]

            # find primary key and print it first, ignoring implicit id if
            # other pk exists
            pk = appmodel._meta.pk
            if not appmodel._meta.abstract and pk in attributes:
                add_attributes(pk)
            for field in attributes:
                if skip_field(field):
                    continue
                if not field.primary_key:
                    add_attributes(field)

            # FIXME: actually many_to_many fields aren't saved in this model's db table, so why should we add an attribute-line for them in the resulting graph?
            # if appmodel._meta.many_to_many:
            #    for field in appmodel._meta.many_to_many:
            #        if skip_field(field):
            #            continue
            #        add_attributes(field)

            # relations
            def add_relation(field, extras=""):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name

                # show related field name
                if hasattr(field, 'related_query_name'):
                    label += ' (%s)' % field.related_query_name()

                # handle self-relationships
                if field.rel.to == 'self':
                    target_model = field.model
                else:
                    target_model = field.rel.to

                _rel = {
                    'target_app': target_model.__module__.replace('.', '_'),
                    'target': target_model.__name__,
                    'type': type(field).__name__,
                    'name': field.name,
                    'label': label,
                    'arrows': extras,
                    'needs_node': True
                }
                if _rel not in model['relations'] and consider(_rel['target']):
                    model['relations'].append(_rel)

            for field in appmodel._meta.local_fields:
                if field.attname.endswith(
                        '_ptr_id'):  # excluding field redundant with inheritance relation
                    continue
                if field in abstract_fields:  # excluding fields inherited from abstract classes. they too show as local_fields
                    continue
                if skip_field(field):
                    continue
                if isinstance(field, OneToOneField):
                    add_relation(field, '[arrowhead=none, arrowtail=none]')
                elif isinstance(field, ForeignKey):
                    add_relation(field, '[arrowhead=none, arrowtail=dot]')

            for field in appmodel._meta.local_many_to_many:
                if skip_field(field):
                    continue
                if isinstance(field, ManyToManyField):
                    if (getattr(field, 'creates_table', False) or  # django 1.1.
                            (hasattr(field.rel.through, '_meta') and field.rel.through._meta.auto_created)):  # django 1.2
                        add_relation(
                            field, '[arrowhead=dot arrowtail=dot, dir=both]')
                elif isinstance(field, GenericRelation):
                    add_relation(field, mark_safe(
                        '[style="dotted", arrowhead=normal, arrowtail=normal, dir=both]'))

            if inheritance:
                # add inheritance arrows
                for parent in appmodel.__bases__:
                    if hasattr(parent, "_meta"):  # parent is a model
                        l = "multi-table"
                        if parent._meta.abstract:
                            l = "abstract"
                        if appmodel._meta.proxy:
                            l = "proxy"
                        l += r"\ninheritance"
                        _rel = {
                            'target_app': parent.__module__.replace(".", "_"),
                            'target': parent.__name__,
                            'type': "inheritance",
                            'name': "inheritance",
                            'label': l,
                            'arrows': '[arrowhead=empty, arrowtail=none]',
                            'needs_node': True
                        }
                        # TODO: seems as if abstract models aren't part of
                        # models.getModels, which is why they are printed by
                        # this without any attributes.
                        if _rel not in model[
                                'relations'] and consider(_rel['target']):
                            model['relations'].append(_rel)

            graph['models'].append(model)
        graphs.append(graph)

    nodes = []
    for graph in graphs:
        nodes.extend([e['name'] for e in graph['models']])

    for graph in graphs:
        # don't draw duplication nodes because of relations
        for model in graph['models']:
            for relation in model['relations']:
                if relation['target'] in nodes:
                    relation['needs_node'] = False
        # render templates
        t = loader.get_template('django_extensions/graph_models/body.html')
        dot += '\n' + t.render(graph)

    for graph in graphs:
        t = loader.get_template('django_extensions/graph_models/rel.html')
        dot += '\n' + t.render(graph)

    t = loader.get_template('django_extensions/graph_models/tail.html')
    c = Context({})
    dot += '\n' + t.render(c)
    return dot
예제 #55
0
    def send_email_alerts(self, user, template):
        #does not change the database, only sends the email
        #todo: move this to template
        user.add_missing_askbot_subscriptions()
        #todo: q_list is a dictionary, not a list
        q_list = self.get_updated_questions_for_user(user)
        if len(q_list.keys()) == 0:
            return
        num_q = 0
        for question, meta_data in q_list.items():
            if meta_data['skip']:
                del q_list[question]
            else:
                num_q += 1
        if num_q > 0:
            threads = Thread.objects.filter(id__in=[qq.thread_id for qq in q_list.keys()])
            tag_summary = Thread.objects.get_tag_summary_from_threads(threads)

            question_count = len(q_list.keys())

            if tag_summary:
                subject_line = ungettext(
                    '%(question_count)d update about %(topics)s',
                    '%(question_count)d updates about %(topics)s',
                    question_count
                ) % {
                    'question_count': question_count,
                    'topics': tag_summary
                }
            else:
                subject_line = ungettext(
                    '%(question_count)d update',
                    '%(question_count)d updates',
                    question_count
                ) % {
                    'question_count': question_count,
                }

            items_added = 0
            items_unreported = 0
            questions_data = list()
            for q, meta_data in q_list.items():
                act_list = []
                if meta_data['skip']:
                    continue
                if items_added >= askbot_settings.MAX_ALERTS_PER_EMAIL:
                    items_unreported = num_q - items_added #may be inaccurate actually, but it's ok
                    break
                else:
                    items_added += 1
                    if meta_data['new_q']:
                        act_list.append(_('new question'))
                    format_action_count('%(num)d rev', meta_data['q_rev'], act_list)
                    format_action_count('%(num)d ans', meta_data['new_ans'], act_list)
                    format_action_count('%(num)d ans rev', meta_data['ans_rev'], act_list)
                    questions_data.append({
                        'url': site_url(q.get_absolute_url()),
                        'info': ', '.join(act_list),
                        'title': q.thread.title
                    })

            activate_language(user.get_primary_language())
            text = template.render({
                'recipient_user': user,
                'questions': questions_data,
                'name': user.username,
                'admin_email': askbot_settings.ADMIN_EMAIL,
                'site_name': askbot_settings.APP_SHORT_NAME,
                'is_multilingual': getattr(django_settings, 'ASKBOT_MULTILINGUAL', False)
            })

            if DEBUG_THIS_COMMAND == True:
                recipient_email = askbot_settings.ADMIN_EMAIL
            else:
                recipient_email = user.email

            mail.send_mail(
                subject_line = subject_line,
                body_text = text,
                recipient_list = [recipient_email]
            )
예제 #56
0
def generate_dot(app_labels, **kwargs):
    disable_fields = kwargs.get('disable_fields', False)
    include_models = parse_file_or_list(kwargs.get('include_models', ""))
    all_applications = kwargs.get('all_applications', False)
    use_subgraph = kwargs.get('group_models', False)
    verbose_names = kwargs.get('verbose_names', False)
    inheritance = kwargs.get('inheritance', False)
    language = kwargs.get('language', None)
    if language is not None:
        activate_language(language)
    exclude_columns = parse_file_or_list(kwargs.get('exclude_columns', ""))
    exclude_models = parse_file_or_list(kwargs.get('exclude_models', ""))

    def skip_field(field):
        if exclude_columns:
            if verbose_names and field.verbose_name:
                if field.verbose_name in exclude_columns:
                    return True
            if field.name in exclude_columns:
                return True
        return False

    t = loader.get_template('django_extensions/graph_models/head.html')
    c = Context({})
    dot = t.render(c)

    apps = []
    if all_applications:
        apps = models.get_apps()

    for app_label in app_labels:
        app = models.get_app(app_label)
        if not app in apps:
            apps.append(app)

    graphs = []
    for app in apps:
        graph = Context({
            'name':
            '"%s"' % app.__name__,
            'app_name':
            "%s" % '.'.join(app.__name__.split('.')[:-1]),
            'cluster_app_name':
            "cluster_%s" % app.__name__.replace(".", "_"),
            'disable_fields':
            disable_fields,
            'use_subgraph':
            use_subgraph,
            'models': []
        })

        appmodels = get_models(app)
        abstract_models = []
        for appmodel in appmodels:
            abstract_models = abstract_models + [
                abstract_model
                for abstract_model in appmodel.__bases__ if hasattr(
                    abstract_model, '_meta') and abstract_model._meta.abstract
            ]
        abstract_models = list(set(abstract_models))  # remove duplicates
        appmodels = abstract_models + appmodels

        for appmodel in appmodels:
            appmodel_abstracts = [
                abstract_model.__name__
                for abstract_model in appmodel.__bases__
                if hasattr(abstract_model, '_meta')
                and abstract_model._meta.abstract
            ]

            # collect all attribs of abstract superclasses
            def getBasesAbstractFields(c):
                _abstract_fields = []
                for e in c.__bases__:
                    if hasattr(e, '_meta') and e._meta.abstract:
                        _abstract_fields.extend(e._meta.fields)
                        _abstract_fields.extend(getBasesAbstractFields(e))
                return _abstract_fields

            abstract_fields = getBasesAbstractFields(appmodel)

            model = {
                'app_name': appmodel.__module__.replace(".", "_"),
                'name': appmodel.__name__,
                'abstracts': appmodel_abstracts,
                'fields': [],
                'relations': []
            }

            # consider given model name ?
            def consider(model_name):
                if exclude_models and model_name in exclude_models:
                    return False
                return not include_models or model_name in include_models

            if not consider(appmodel._meta.object_name):
                continue

            if verbose_names and appmodel._meta.verbose_name:
                model['label'] = appmodel._meta.verbose_name
            else:
                model['label'] = model['name']

            # model attributes
            def add_attributes(field):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name

                t = type(field).__name__
                if isinstance(field, (OneToOneField, ForeignKey)):
                    t += " ({0})".format(field.rel.field_name)
                # TODO: ManyToManyField, GenericRelation

                model['fields'].append({
                    'name': field.name,
                    'label': label,
                    'type': t,
                    'blank': field.blank,
                    'abstract': field in abstract_fields,
                })

            # Find all the real attributes. Relations are depicted as graph edges instead of attributes
            attributes = [
                field for field in appmodel._meta.local_fields
                if not isinstance(field, RelatedField)
            ]

            # find primary key and print it first, ignoring implicit id if other pk exists
            pk = appmodel._meta.pk
            if not appmodel._meta.abstract and pk in attributes:
                add_attributes(pk)
            for field in attributes:
                if skip_field(field):
                    continue
                if not field.primary_key:
                    add_attributes(field)

            # FIXME: actually many_to_many fields aren't saved in this model's db table, so why should we add an attribute-line for them in the resulting graph?
            #if appmodel._meta.many_to_many:
            #    for field in appmodel._meta.many_to_many:
            #        if skip_field(field):
            #            continue
            #        add_attributes(field)

            # relations
            def add_relation(field, extras=""):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name
                else:
                    label = field.name

                # show related field name
                if hasattr(field, 'related_query_name'):
                    label += ' (%s)' % field.related_query_name()

                _rel = {
                    'target_app': field.rel.to.__module__.replace('.', '_'),
                    'target': field.rel.to.__name__,
                    'type': type(field).__name__,
                    'name': field.name,
                    'label': label,
                    'arrows': extras,
                    'needs_node': True
                }
                if _rel not in model['relations'] and consider(_rel['target']):
                    model['relations'].append(_rel)

            for field in appmodel._meta.local_fields:
                if field.attname.endswith(
                        '_ptr_id'
                ):  # excluding field redundant with inheritance relation
                    continue
                if field in abstract_fields:  # excluding fields inherited from abstract classes. they too show as local_fields
                    continue
                if skip_field(field):
                    continue
                if isinstance(field, OneToOneField):
                    add_relation(field, '[arrowhead=none, arrowtail=none]')
                elif isinstance(field, ForeignKey):
                    add_relation(field, '[arrowhead=none, arrowtail=dot]')

            for field in appmodel._meta.local_many_to_many:
                if skip_field(field):
                    continue
                if isinstance(field, ManyToManyField):
                    if (getattr(field, 'creates_table', False)
                            or  # django 1.1.
                        (hasattr(field.rel.through, '_meta') and
                         field.rel.through._meta.auto_created)):  # django 1.2
                        add_relation(
                            field, '[arrowhead=dot arrowtail=dot, dir=both]')
                    elif isinstance(field, GenericRelation):
                        add_relation(
                            field,
                            mark_safe(
                                '[style="dotted", arrowhead=normal, arrowtail=normal, dir=both]'
                            ))

            if inheritance:
                # add inheritance arrows
                for parent in appmodel.__bases__:
                    if hasattr(parent, "_meta"):  # parent is a model
                        l = "multi-table"
                        if parent._meta.abstract:
                            l = "abstract"
                        if appmodel._meta.proxy:
                            l = "proxy"
                        l += r"\ninheritance"
                        _rel = {
                            'target_app': parent.__module__.replace(".", "_"),
                            'target': parent.__name__,
                            'type': "inheritance",
                            'name': "inheritance",
                            'label': l,
                            'arrows': '[arrowhead=empty, arrowtail=none]',
                            'needs_node': True
                        }
                        # TODO: seems as if abstract models aren't part of models.getModels, which is why they are printed by this without any attributes.
                        if _rel not in model['relations'] and consider(
                                _rel['target']):
                            model['relations'].append(_rel)

            graph['models'].append(model)
        graphs.append(graph)

    nodes = []
    for graph in graphs:
        nodes.extend([e['name'] for e in graph['models']])

    for graph in graphs:
        # don't draw duplication nodes because of relations
        for model in graph['models']:
            for relation in model['relations']:
                if relation['target'] in nodes:
                    relation['needs_node'] = False
        # render templates
        t = loader.get_template('django_extensions/graph_models/body.html')
        dot += '\n' + t.render(graph)

    for graph in graphs:
        t = loader.get_template('django_extensions/graph_models/rel.html')
        dot += '\n' + t.render(graph)

    t = loader.get_template('django_extensions/graph_models/tail.html')
    c = Context({})
    dot += '\n' + t.render(c)
    return dot
예제 #57
0
def generate_dot(app_labels, **kwargs):
    cli_options = kwargs.get('cli_options', None)
    disable_fields = kwargs.get('disable_fields', False)
    include_models = parse_file_or_list(kwargs.get('include_models', ""))
    all_applications = kwargs.get('all_applications', False)
    use_subgraph = kwargs.get('group_models', False)
    verbose_names = kwargs.get('verbose_names', False)
    inheritance = kwargs.get('inheritance', True)
    relations_as_fields = kwargs.get("relations_as_fields", True)
    sort_fields = kwargs.get("sort_fields", True)
    language = kwargs.get('language', None)
    if language is not None:
        activate_language(language)
    exclude_columns = parse_file_or_list(kwargs.get('exclude_columns', ""))
    exclude_models = parse_file_or_list(kwargs.get('exclude_models', ""))

    def skip_field(field):
        if exclude_columns:
            if verbose_names and field.verbose_name:
                if field.verbose_name in exclude_columns:
                    return True
            if field.name in exclude_columns:
                return True
        return False

    apps = []
    if all_applications:
        apps = models.get_apps()

    for app_label in app_labels:
        app = models.get_app(app_label)
        if not app in apps:
            apps.append(app)

    graphs = []
    for app in apps:
        graph = Context({
            'name':
            '"%s"' % app.__name__,
            'app_name':
            "%s" % '.'.join(app.__name__.split('.')[:-1]),
            'cluster_app_name':
            "cluster_%s" % app.__name__.replace(".", "_"),
            'models': []
        })

        appmodels = get_models(app)
        abstract_models = []
        for appmodel in appmodels:
            abstract_models = abstract_models + [
                abstract_model
                for abstract_model in appmodel.__bases__ if hasattr(
                    abstract_model, '_meta') and abstract_model._meta.abstract
            ]
        abstract_models = list(set(abstract_models))  # remove duplicates
        appmodels = abstract_models + appmodels

        for appmodel in appmodels:
            appmodel_abstracts = [
                abstract_model.__name__
                for abstract_model in appmodel.__bases__
                if hasattr(abstract_model, '_meta')
                and abstract_model._meta.abstract
            ]

            # collect all attribs of abstract superclasses
            def getBasesAbstractFields(c):
                _abstract_fields = []
                for e in c.__bases__:
                    if hasattr(e, '_meta') and e._meta.abstract:
                        _abstract_fields.extend(e._meta.fields)
                        _abstract_fields.extend(getBasesAbstractFields(e))
                return _abstract_fields

            abstract_fields = getBasesAbstractFields(appmodel)

            model = {
                'app_name': appmodel.__module__.replace(".", "_"),
                'name': appmodel.__name__,
                'abstracts': appmodel_abstracts,
                'fields': [],
                'relations': []
            }

            # consider given model name ?
            def consider(model_name):
                if exclude_models and model_name in exclude_models:
                    return False
                return not include_models or model_name in include_models

            if not consider(appmodel._meta.object_name):
                continue

            if verbose_names and appmodel._meta.verbose_name:
                model['label'] = appmodel._meta.verbose_name.decode("utf8")
            else:
                model['label'] = model['name']

            # model attributes
            def add_attributes(field):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name.decode("utf8")
                    if label.islower():
                        label = label.capitalize()
                else:
                    label = field.name

                t = type(field).__name__
                if isinstance(field, (OneToOneField, ForeignKey)):
                    t += " ({0})".format(field.rel.field_name)
                # TODO: ManyToManyField, GenericRelation

                model['fields'].append({
                    'name':
                    field.name,
                    'label':
                    label,
                    'type':
                    t,
                    'blank':
                    field.blank,
                    'abstract':
                    field in abstract_fields,
                    'relation':
                    isinstance(field, RelatedField),
                    'primary_key':
                    field.primary_key,
                })

            attributes = [field for field in appmodel._meta.local_fields]
            if not relations_as_fields:
                # Find all the 'real' attributes. Relations are depicted as graph edges instead of attributes
                attributes = [
                    field for field in attributes
                    if not isinstance(field, RelatedField)
                ]

            # find primary key and print it first, ignoring implicit id if other pk exists
            pk = appmodel._meta.pk
            if pk and not appmodel._meta.abstract and pk in attributes:
                add_attributes(pk)

            for field in attributes:
                if skip_field(field):
                    continue
                if pk and field == pk:
                    continue
                add_attributes(field)

            if sort_fields:
                model['fields'] = sorted(model['fields'],
                                         key=lambda field:
                                         (not field['primary_key'], not field[
                                             'relation'], field['label']))

            # FIXME: actually many_to_many fields aren't saved in this model's db table, so why should we add an attribute-line for them in the resulting graph?
            #if appmodel._meta.many_to_many:
            #    for field in appmodel._meta.many_to_many:
            #        if skip_field(field):
            #            continue
            #        add_attributes(field)

            # relations
            def add_relation(field, extras=""):
                if verbose_names and field.verbose_name:
                    label = field.verbose_name.decode("utf8")
                    if label.islower():
                        label = label.capitalize()
                else:
                    label = field.name

                # show related field name
                if hasattr(field, 'related_query_name'):
                    related_query_name = field.related_query_name()
                    if verbose_names and related_query_name.islower():
                        related_query_name = related_query_name.replace(
                            '_', ' ').capitalize()
                    label += ' (%s)' % related_query_name

                # handle self-relationships
                if field.rel.to == 'self':
                    target_model = field.model
                else:
                    target_model = field.rel.to

                _rel = {
                    'target_app': target_model.__module__.replace('.', '_'),
                    'target': target_model.__name__,
                    'type': type(field).__name__,
                    'name': field.name,
                    'label': label,
                    'arrows': extras,
                    'needs_node': True
                }
                if _rel not in model['relations'] and consider(_rel['target']):
                    model['relations'].append(_rel)

            for field in appmodel._meta.local_fields:
                if field.attname.endswith(
                        '_ptr_id'
                ):  # excluding field redundant with inheritance relation
                    continue
                if field in abstract_fields:  # excluding fields inherited from abstract classes. they too show as local_fields
                    continue
                if skip_field(field):
                    continue
                if isinstance(field, OneToOneField):
                    add_relation(field,
                                 '[arrowhead=none, arrowtail=none, dir=both]')
                elif isinstance(field, ForeignKey):
                    add_relation(field,
                                 '[arrowhead=none, arrowtail=dot, dir=both]')

            for field in appmodel._meta.local_many_to_many:
                if skip_field(field):
                    continue
                if isinstance(field, ManyToManyField):
                    if (getattr(field, 'creates_table', False)
                            or  # django 1.1.
                        (hasattr(field.rel.through, '_meta') and
                         field.rel.through._meta.auto_created)):  # django 1.2
                        add_relation(
                            field, '[arrowhead=dot arrowtail=dot, dir=both]')
                elif isinstance(field, GenericRelation):
                    add_relation(
                        field,
                        mark_safe(
                            '[style="dotted", arrowhead=normal, arrowtail=normal, dir=both]'
                        ))

            if inheritance:
                # add inheritance arrows
                for parent in appmodel.__bases__:
                    if hasattr(parent, "_meta"):  # parent is a model
                        l = "multi-table"
                        if parent._meta.abstract:
                            l = "abstract"
                        if appmodel._meta.proxy:
                            l = "proxy"
                        l += r"\ninheritance"
                        _rel = {
                            'target_app': parent.__module__.replace(".", "_"),
                            'target': parent.__name__,
                            'type': "inheritance",
                            'name': "inheritance",
                            'label': l,
                            'arrows':
                            '[arrowhead=empty, arrowtail=none, dir=both]',
                            'needs_node': True,
                        }
                        # TODO: seems as if abstract models aren't part of models.getModels, which is why they are printed by this without any attributes.
                        if _rel not in model['relations'] and consider(
                                _rel['target']):
                            model['relations'].append(_rel)

            graph['models'].append(model)
        if graph['models']:
            graphs.append(graph)

    nodes = []
    for graph in graphs:
        nodes.extend([e['name'] for e in graph['models']])

    for graph in graphs:
        for model in graph['models']:
            for relation in model['relations']:
                if relation['target'] in nodes:
                    relation['needs_node'] = False

    now = datetime.datetime.now()
    t = loader.get_template('django_extensions/graph_models/digraph.dot')

    if not isinstance(t, Template):
        raise Exception("Default Django template loader isn't used. "
                        "This can lead to the incorrect template rendering. "
                        "Please, check the settings.")

    c = Context({
        'created_at': now.strftime("%Y-%m-%d %H:%M"),
        'cli_options': cli_options,
        'disable_fields': disable_fields,
        'use_subgraph': use_subgraph,
        'graphs': graphs,
    })
    dot = t.render(c)

    return dot
예제 #58
0
 def setUpClass(cls):
     management.call_command('flush', verbosity=0, interactive=False)
     activate_language(settings.LANGUAGE_CODE)
     management.call_command('askbot_add_test_content', verbosity=0, interactive=False)