Пример #1
0
    def render(self, context):
        book = self.book.resolve(context)
        request = self.request.resolve(context)

        if request.user.is_superuser:
            tree_query_set = Page.objects \
                .select_related('book') \
                .filter(book__pk=book.id)
        else:
            cache_key = 'book.templatetags.book_tags.book_toc({})'.format(book.id)
            cache_time = settings.CACHE_TIME_VERY_SHORT

            tree_query_set = cache.get(cache_key)

            if not tree_query_set:
                try:
                    tree_query_set = Page.objects \
                        .select_related('book') \
                        .filter(book__slug=book.slug, status=Page.STATUS_CHOICES.public)
                    cache.set(cache_key, tree_query_set, cache_time)
                except Page.DoesNotExist:
                    pass

        roots = get_cached_trees(tree_query_set)

        nodes = [self._render_category(context, category) for category in roots]
        return ''.join(nodes)
Пример #2
0
 def __init__(self, model_class, node_id=None,
              attrs=(), extract_data_fn=False):
     """
     Init the Builder instance.
     
     :param model_class: MPTTModel subclass
     :keyword node_id: the ID of tree node, root node by default
     :keyword extract_data_fn: the data extractor
     """
     assert issubclass(model_class, MPTTModel), \
         'The parameter "model_class" is invalid'
     self.model_class = model_class
     if node_id:
         try:
             self.root_node = model_class.objects.get(pk=node_id)
         except ObjectDoesNotExist:
             raise 'There is no such node with id=<{0}>'.format(node_id)
     else:
         self.root_node = None
     self.attrs = attrs if attrs else type(self).default_attrs
     if extract_data_fn and callable(extract_data_fn):
         self.extract_data_fn = extract_data_fn
     else:
         self.extract_data_fn = self.default_extract_data
     self._root_children = get_cached_trees(
         model_class.objects.all()
     )
Пример #3
0
    def render(self, context):
        roots = get_cached_trees(self.tree_query_set)

        nodes = [
            self._render_category(context, category) for category in roots
        ]
        return ''.join(nodes)
Пример #4
0
def get_location_list(show_reserved=True):
    """Return a list of pseudo-serialized Locations.

    `show_reserved`: if True, show locations with id > 100.
    """
    locations = []

    location_list = models.Location.objects.all()
    roots = get_cached_trees(location_list)

    for root in roots:
        # Do not list the default location
        if root.id == 0:
            continue

        if show_reserved is False and root.id < 100:
            continue

        locations.append({
            "sequence": [root.name],
            "id": root.id,
            "parent": None,
            "rescue_bag": root.is_rescue_bag
        })

        children = root.get_children()
        if children:
            locations += location_iterator([root.name], children, root.id)

    return locations
Пример #5
0
def maintain_integrity_full_code(sender, instance: Account, update_fields=None, **kwargs):
    print(f"UPDATE_FIELDS: {update_fields}")

    assert sender is Account
    if kwargs.get('raw', False):
        return

    if update_fields is None or 'code' in update_fields:
        # WARNING: YOU ARE NOW ENTERING THE 3AM QUERY OPTIMIZATION ZONE

        # Avoid queries on get_children/get_ancestors by caching the entire subtree.

        descendants = instance.get_descendants(include_self=True)
        [cached_account_tree] = mptt_utils.get_cached_trees(descendants)  # type: Account

        # By default, Django auto-commits, meaning it will hit the database once for
        # each call to save. By updating full_code's in a transaction, we reduce that
        # to a single hit.

        # But we go even further by staging our changes, and then bulk updating in one go.

        with transaction.atomic():
            dirty_accounts = []

            def recursive_update(account: Account):
                account.full_code = account.computed_full_code
                dirty_accounts.append(account)

                for child_account in account.get_children():
                    recursive_update(child_account)

            recursive_update(cached_account_tree)
            Account.objects.bulk_update(dirty_accounts, ['full_code'])
Пример #6
0
 def generate_content(self, number):
     last_record = (self.items_per_page * int(number)) - 1
     first_record = (last_record - self.items_per_page) + 1
     root_comments = get_cached_trees(
         self.records)[first_record:last_record + 1]
     return [
         tree.get_descendants(include_self=True) for tree in root_comments
     ]
Пример #7
0
 def _apply_prefetch_to_instance(self, instance):
     if not hasattr(instance, '_cached_children'):
         descendants = instance.get_descendants(include_self=True)
         descendants = descendants.select_related('data_object')
         descendants = descendants.select_related(
             'data_object__file_resource')
         instance = get_cached_trees(descendants)[0]
     return instance
Пример #8
0
 def render(self, context):
     queryset = self.queryset_var.resolve(context)
     roots = get_cached_trees(queryset)
     roots.sort(key=lambda node: node.submit_date, reverse=True)
     bits = [
         super(DateOrderedRecurseTreeNode,
               self)._render_node(context, node) for node in roots
     ]
     return ''.join(bits)
Пример #9
0
def get_table_of_contents(book_id, indent):
    tree_set = get_cached_trees(
        Page.objects.select_related('book').filter(book__pk=book_id).order_by(
            'tree_id', 'lft'))
    tree_list = PageNode(tree_set, indent).get_list()

    return {
        'tree_set': tree_set,
        'tree_list': tree_list,
    }
Пример #10
0
 def render(self, context):
     queryset = self.queryset_var.resolve(context)
     queryset = queryset.annotate(promotions_count=Count('promotions'))
     roots = get_cached_trees(queryset)
     roots.sort(key=lambda node: node.promotions_count, reverse=True)
     bits = [
         super(PromotionOrderedRecurseTreeNode,
               self)._render_node(context, node) for node in roots
     ]
     return ''.join(bits)
Пример #11
0
def cache_tree_children(queryset):
    """
    Alias to `mptt.utils.get_cached_trees`, suppressing errors for filtered
    querysets to avoid 500 errors being thrown when using the django admin
    search, and preserving previous behaviour as much as possible.
    """

    allow_filtered = False
    if hasattr(queryset, 'query') and hasattr(queryset.query, 'has_filters'):
        allow_filtered = queryset.query.has_filters()

    return get_cached_trees(queryset, allow_filtered=allow_filtered)
Пример #12
0
def get_dmatree(request):
    organs = Organization.objects.all()

    top_nodes = get_cached_trees(organs)

    dicts = []
    for n in top_nodes:
        dicts.append(recursive_node_to_dict(n, ''))

    # print json.dumps(dicts, indent=4)

    return JsonResponse({'trees': dicts})
Пример #13
0
    def get_search_res(self):
        qs = self.model.objects.all()
        if self.request.GET.get('title'):
            qs = qs.filter(title__icontains=self.request.GET.get('title'))
        if self.request.GET.get('module'):
            qs = qs.filter(module_id=self.request.GET.get('module'))
        if self.request.GET.get('url'):
            qs = qs.filter(url__icontains=self.request.GET.get('url'))

        if qs.exists():
            qs = qs.get_ancestors(include_self=True)
            home = get_cached_trees(qs)[0]
            return [home.serializable_object_with_children]
        else:
            return []
Пример #14
0
def get_adjacent_pages(book_id, page_id):
    tree_set = get_cached_trees(
        Page.objects.select_related('book').filter(book__pk=book_id).order_by(
            'tree_id', 'lft'))
    tree_list = PageNode(tree_set, 0).get_list()

    i = 0
    for i, p in enumerate(tree_list):
        if p.id == page_id:
            break

    return {
        'previous_page': tree_list[i - 1] if i > 0 else None,
        'next_page': tree_list[i + 1] if i + 1 < len(tree_list) else None,
    }
Пример #15
0
def gettree(request):
    print(request.GET)
    page_name = request.GET.get('page_name') or ''
    print(page_name)
    organs = Organization.objects.all()

    top_nodes = get_cached_trees(organs)

    dicts = []
    for n in top_nodes:
        dicts.append(recursive_node_to_dict(n, page_name))

    # print json.dumps(dicts, indent=4)

    return JsonResponse({'trees': dicts})
Пример #16
0
def get_adjacent_pages(book_id, page_id):
    tree_set = get_cached_trees(Page.objects
                                .select_related('book')
                                .filter(book__pk=book_id, status=Page.STATUS_CHOICES.public))
    tree_list = PageListItem(tree_set, 0).get_list()

    i = 0
    for i, p in enumerate(tree_list):
        if p.id == page_id:
            break

    return {
        'previous_page': tree_list[i - 1] if i > 0 else None,
        'next_page': tree_list[i + 1] if i + 1 < len(tree_list) else None,
    }
Пример #17
0
def get_blog_category_roots(blog_slug):
    cache_key = 'blog.templatetags.blog_tags.get_blog_category_roots({})'.format(
        blog_slug)
    cache_time = settings.CACHES['default']['TIMEOUT']

    roots = cache.get(cache_key)

    if not roots:
        try:
            roots = get_cached_trees(
                Category.objects.filter(blog__slug=blog_slug).order_by(
                    'tree_id', 'lft'))
            cache.set(cache_key, roots, cache_time)
        except Category.DoesNotExist:
            roots = None

    return roots
Пример #18
0
    def list(self, request, format=None):
        def course(node):
            return {
                'name': node.name,
                'id': node.id,
                'slug': node.slug,
            }

        def category(node):
            return {
                'name': node.name,
                'id': node.id,
                'children': list(map(category, node.get_children())),
                'courses': list(map(course, node.course_set.all())),
            }

        categories = list(map(category, get_cached_trees(Category.objects.prefetch_related('course_set').all())))
        return Response(categories)
Пример #19
0
def course_tree(request):
    def course(node):
        return {
            'name': node.name,
            'id': node.id,
            'slug': node.slug,
        }

    def category(node):
        return {
            'name': node.name,
            'id': node.id,
            'children': list(map(category, node.get_children())),
            'courses': list(map(course, node.course_set.all())),
        }

    categories = list(map(category, get_cached_trees(Category.objects.prefetch_related('course_set').all())))
    return HttpResponse(json.dumps(categories),
                        content_type="application/json")
Пример #20
0
    def render(self, context):
        category_slug = self.category_slug.resolve(context)

        cache_key = 'book.templatetags.book_tags.article_categories({})'.format(category_slug)
        cache_time = settings.CACHE_TIME_LONG

        tree_query_set = cache.get(cache_key)

        if not tree_query_set:
            try:
                tree_query_set = ArticleCategory.objects.filter(slug=category_slug).get_descendants(include_self=False)
                cache.set(cache_key, tree_query_set, cache_time)
            except ArticleCategory.DoesNotExist:
                tree_query_set = None

        roots = get_cached_trees(tree_query_set)

        nodes = [self._render_category(context, category) for category in roots]
        return ''.join(nodes)
Пример #21
0
def get_organization_tree():
    """获取组织架构树状数据"""
    root_node = get_cached_trees(OrganizationMptt.objects.all())[0]
    tree_list = []
    tree_dict = dict()
    tree_dict['dataId'] = root_node.id
    if root_node.user:
        tree_dict['text'] = root_node.name + '   ' + root_node.user.first_name
    else:
        tree_dict['text'] = root_node.name
    tree_dict['nodes'] = sorted(get_child_node_list(root_node), key=lambda x: x['text'])
    leader_username = root_node.get_leader_username()
    if leader_username:
        tag = '负责人:' + leader_username
        tree_dict['tags'] = [tag]
    else:
        tree_dict['tags'] = [str(root_node.get_title())]
    tree_list.append(tree_dict)
    return tree_list
Пример #22
0
 def get_context_data(self, **kwargs):
     context = super().get_context_data()
     # we need to know the root nodes for each node which has no children
     nodes = context["page_obj"].object_list
     selectable_nodes = [node for node in nodes if node.level == 2]
     all_nominals = Nominal.objects.all().prefetch_related("children")  # whole set
     # hits the DB but will cache result
     # root nodes are the groups for the select menu
     root_nominals = get_cached_trees(all_nominals)
     root_nominals.sort(key=lambda n: n.pk)
     options = [
         {
             "group": node.get_root(),
             "option": node,
             "group_order": root_nominals.index(node.get_root())
         }
         for node in selectable_nodes
     ]
     context["options"] = options
     return context
Пример #23
0
def get_category_roots(store_code, pg=False):
    cache_key = 'shop.templatetags.shop_tags.get_category_roots({},{})'.format(
        store_code, pg)
    cache_time = settings.CACHES['default']['TIMEOUT']

    roots = cache.get(cache_key)

    if not roots:
        try:
            categories = Category.objects.filter(
                store__code=store_code).order_by('tree_id', 'lft')

            if pg:
                categories = categories.filter(pg=pg)

            roots = get_cached_trees(categories)
            cache.set(cache_key, roots, cache_time)
        except Category.DoesNotExist:
            roots = None

    return roots
Пример #24
0
def serialize_location_hierarchy(country, aliases_from_org=None):
    """
    Serializes a country as a location hierarchy, e.g.
    {
        "name": "Rwanda",
        "children": [
            {
                "name": "Kigali City",
                "aliases": ["Kigali", "Kigari"],
                "children": [
                    ...
                ]
            }
        ]
    }
    """
    queryset = country.get_descendants(include_self=True)

    if aliases_from_org:
        from temba.locations.models import BoundaryAlias

        queryset = queryset.prefetch_related(
            Prefetch(
                "aliases",
                queryset=BoundaryAlias.objects.filter(org=aliases_from_org)))

    def _serialize_node(node):
        rendered = {"name": node.name}

        if aliases_from_org:
            rendered["aliases"] = [a.name for a in node.aliases.all()]

        children = node.get_children()
        if children:
            rendered["children"] = []
            for child in node.get_children():
                rendered["children"].append(_serialize_node(child))
        return rendered

    return [_serialize_node(node) for node in get_cached_trees(queryset)][0]
Пример #25
0
    def list(self, request, format=None):
        def course(node: Course):
            return {
                "name": node.name,
                "id": node.id,
                "slug": node.slug,
            }

        def category(node: Category):
            return {
                "name": node.name,
                "id": node.id,
                "children": list(map(category, node.get_children())),
                "courses": list(map(course, node.course_set.all())),
            }

        categories = list(
            map(
                category,
                get_cached_trees(
                    Category.objects.prefetch_related("course_set").all()),
            ))
        return Response(categories)
Пример #26
0
def serialize_location_hierarchy(org):
    """
    Serializes a country as a location hierarchy, e.g.
    {
        "name": "Rwanda",
        "children": [
            {
                "name": "Kigali City",
                "aliases": ["Kigali", "Kigari"],
                "children": [
                    ...
                ]
            }
        ]
    }
    """
    from temba.locations.models import BoundaryAlias

    queryset = org.country.get_descendants(include_self=True).prefetch_related(
        Prefetch("aliases", queryset=BoundaryAlias.objects.filter(org=org))
    )

    def _serialize_node(node):
        rendered = {"name": node.name}

        aliases = [a.name for a in node.aliases.all()]
        if aliases:
            rendered["aliases"] = aliases

        children = node.get_children()
        if children:
            rendered["children"] = []
            for child in node.get_children():
                rendered["children"].append(_serialize_node(child))
        return rendered

    return [_serialize_node(node) for node in get_cached_trees(queryset)][0]
Пример #27
0
 def get_context_data(self, **kwargs):
     context = {}
     context["columns"] = columns = [col for col in self.columns]
     mod_settings = ModuleSettings.objects.select_related('nominals_period').select_related('nominals_period__fy').first()
     current_period = mod_settings.nominals_period
     current_fy = current_period.fy
     first_period = current_fy.first_period()
     from_period = first_period
     to_period = last_period = current_period
     form_kwargs = {
         "initial": {
             "from_period": first_period,
             "to_period": last_period
         }
     }
     if self.request.GET:
         form_kwargs.update({
             "data": self.request.GET
         })
     context["form"] = form = TrialBalanceForm(**form_kwargs)
     if self.request.GET:
         if form.is_valid():
             from_period = form.cleaned_data.get("from_period")
             to_period = form.cleaned_data.get("to_period")
         else:
             self.object_list = context["report"] = []  # show empty table
             return context
     nominals = Nominal.objects.all().prefetch_related("children")
     # hits the DB but will cache result
     root_nominals = get_cached_trees(nominals)
     # this means we can use get_ancestors() on the nodes now without hitting the DB again
     nominal_map = {nominal.pk: nominal for nominal in nominals}
     nominal_totals_for_period_range = (
         NominalTransaction.objects
         .values("nominal")
         .annotate(total=Sum("value"))
         .filter(period__gte=from_period)
         .filter(period__lte=to_period)
     )
     # get the start of the financial year the to_period is in
     from_period = first_period
     nominal_ytd_totals = (
         NominalTransaction.objects
         .values("nominal")
         .annotate(total=Sum("value"))
         .filter(period__gte=from_period)
         .filter(period__lte=to_period)
     )
     report = []
     debit_total = 0
     credit_total = 0
     ytd_debit_total = 0
     ytd_credit_total = 0
     for nominal_total in nominal_totals_for_period_range:
         nominal_pk = nominal_total["nominal"]
         total = nominal_total["total"]
         if total > 0:
             debit_total += total
         else:
             credit_total += total
         parents = [
             parent.name for parent in nominal_map[nominal_pk].get_ancestors()]
         for ytd in nominal_ytd_totals:
             if ytd["nominal"] == nominal_pk:
                 ytd = ytd["total"]
                 if ytd > 0:
                     ytd_debit_total += ytd
                 else:
                     ytd_credit_total += ytd
                 break
         nominal_report = {
             "nominal": nominal_map[nominal_pk].name,
             "total": total,
             "parents": parents,
             "ytd": ytd
         }
         report.append(nominal_report)
     context["debit_total"] = debit_total
     context["credit_total"] = credit_total
     context["ytd_debit_total"] = ytd_debit_total
     context["ytd_credit_total"] = ytd_credit_total
     self.object_list = context["report"] = report
     return context
Пример #28
0
 def _get_top_nodes(self):
     if not hasattr(self, '_top_nodes'):
         self._top_nodes = get_cached_trees(Forum.objects.all())
     return self._top_nodes
Пример #29
0
 def handle_get_folders(self, data):
     root_folders = get_cached_trees(Folder._tree_manager.all())
     return JsonResponse(
         {"rootFolder": _filer_folder_to_json_dict(None, root_folders)})
Пример #30
0
 def get_cached_trees(self):
     """
     Alias to `mptt.utils.get_cached_trees`.
     """
     return utils.get_cached_trees(self)
Пример #31
0
def cache_tree_children(queryset):
    """
    Alias to `mptt.utils.get_cached_trees`.
    """

    return get_cached_trees(queryset)
Пример #32
0
 def handle_get_folders(self, data):
     root_folders = get_cached_trees(Folder._tree_manager.all())
     return JsonResponse({"rootFolder": _filer_folder_to_json_dict(None, root_folders)})
Пример #33
0
def get_ancestor_path(category_id):
    return get_cached_trees(
        Category.objects.get(pk=category_id).get_ancestors(include_self=False))
Пример #34
0
 def handle_get_folders(self, data):
     shop = get_shop(self.request)
     root_folders = get_cached_trees(Folder._tree_manager.filter(_get_folder_query_filter(shop)))
     return JsonResponse({"rootFolder": _filer_folder_to_json_dict(None, root_folders)})
Пример #35
0
 def _get_top_nodes(self):
     if not hasattr(self, '_top_nodes'):
         self._top_nodes = get_cached_trees(Forum.objects.all())
     return self._top_nodes
Пример #36
0
def cache_tree_children(queryset):
    """
    Alias to `mptt.utils.get_cached_trees`.
    """

    return get_cached_trees(queryset)