Ограничить данные Django текущим пользователем
Надеюсь, вы сможете мне помочь.
Я пытаюсь запустить нижеприведенную процедуру - только для текущего запрашивающего пользователя. Но он возвращает данные для всех пользователей.
Можете ли вы помочь мне выяснить, почему это так?
open_tasks = skills.objects.filter(creator=request.user).raw('''
SELECT *, round(((closed_points)/(open_points+closed_points)*100),2) as points_pct,
round(((closed_count)/(open_count+closed_count)*100),2) as closed_pct from (
SELECT id, sum(open_points) as open_points, sum(closed_points) as closed_points, sum(open_count) as open_count, sum(closed_count) as closed_count
from (
SELECT id,
case when status = 'open' then sum(points) end as open_points,
case when status <> 'open' then sum(points) end as closed_points,
case when status = 'open' then sum(count) end as open_count,
case when status <> 'open' then sum(count) end as closed_count
from (
SELECT category as id, status, sum(cast(points as int)) as points, count(*) as count
FROM voximisa_skills group by category, status)s
group by id, status)p
group by id)j
''')
В документации Django на сайте raw(…)
[Django-doc] говорится:
raw()
всегда вызывает новый запрос и не учитывает предыдущую фильтрацию. Поэтому, как правило, его следует вызывать изManager
или из свежегоQuerySet
экземпляра.
Таким образом, вы должны включить фильтрацию пользователя в необработанный запрос с:
open_tasks = skills.objects.filter(creator=request.user).raw('''
SELECT *, round(((closed_points)/(open_points+closed_points)*100),2) as points_pct,
round(((closed_count)/(open_count+closed_count)*100),2) as closed_pct from (
SELECT id, sum(open_points) as open_points, sum(closed_points) as closed_points, sum(open_count) as open_count, sum(closed_count) as closed_count
from (
SELECT id,
case when status = 'open' then sum(points) end as open_points,
case when status <> 'open' then sum(points) end as closed_points,
case when status = 'open' then sum(count) end as open_count,
case when status <> 'open' then sum(count) end as closed_count
from (
SELECT category as id, status, sum(cast(points as int)) as points, count(*) as count
FROM voximisa_skills
WHERE creator_id=%s
GROUP BY category, status)s
group by id, status)p
group by id)j''',
[request.user.pk]
)
Здесь мы используем параметры, которые мы можем передать в запрос [Django-doc]. Следует не форматировать SQL строку с данными, так как это может привести к SQL инъекции [wiki].