powered by simpleCommunicator - 2.0.40     © 2025 Programmizd 02
Форумы / PostgreSQL [игнор отключен] [закрыт для гостей] / has_function_privilege - непонятная работа
9 сообщений из 9, страница 1 из 1
has_function_privilege - непонятная работа
    #40132781
pg000
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
непонятная работа has_function_privilege

доступа к базе у юзера нет, а права на выполнение функции есть

Код: plsql
1.
2.
3.
4.
5.
SELECT has_database_privilege('myuser1', 'mydb1', 'CONNECT')
-- false

SELECT current_database(), has_function_privilege('myuser1', 16437, 'EXECUTE')
-- mydb1, true



Кто-нибудь может прокомментировать ?
...
Рейтинг: 0 / 0
has_function_privilege - непонятная работа
    #40132800
Фотография Maxim Boguk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
pg000
непонятная работа has_function_privilege

доступа к базе у юзера нет, а права на выполнение функции есть

Код: plsql
1.
2.
3.
4.
5.
SELECT has_database_privilege('myuser1', 'mydb1', 'CONNECT')
-- false

SELECT current_database(), has_function_privilege('myuser1', 16437, 'EXECUTE')
-- mydb1, true



Кто-нибудь может прокомментировать ?


А почему нет? Это несвязанные уровни доступа.


Например в какой ситуации это может быть надо:
psql -U postgres -d mydb1
становимся пользователем myuser1
set role myuser1;
далее от myuser1 выполняем хранимку нужную при том что у myuser1 нет права на коннект.



--
Maxim Boguk
лучшая поддержка PostgreSQL: dataegret.ru
...
Рейтинг: 0 / 0
has_function_privilege - непонятная работа
    #40132813
pg000
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Хорошо,
не будем привязываться к connect

Создаём новую базу и убираем права роли PUBLIC (чтобы не мешались)
Код: plsql
1.
2.
3.
4.
5.
CREATE ROLE myuser1;

CREATE DATABASE mydb1;

REVOKE ALL ON DATABASE "mydb1" FROM PUBLIC;


Также убираем права на схему PUBLIC роли PUBLIC (чтобы не мешались)
И получаем разное поведение has_table_privilege и has_function_privilege

Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
\c mydb1

SET SESSION AUTHORIZATION postgres;

REVOKE ALL ON SCHEMA public FROM PUBLIC;

CREATE TABLE mytbl1 ( field1 integer );

SELECT has_table_privilege('myuser1', 'mytbl1', 'SELECT');
-- false

CREATE OR REPLACE FUNCTION myfn1 ()
RETURNS integer AS
$$
BEGIN
    RETURN 1;
END
$$ LANGUAGE plpgsql;

SELECT myfn1();

SELECT oid, * FROM pg_proc WHERE proname='myfn1';

SELECT current_database(), has_function_privilege('myuser1', 130458, 'EXECUTE');
-- true


На просмотр данных из таблицы прав нет, а на выполнение функции есть.
...
Рейтинг: 0 / 0
has_function_privilege - непонятная работа
    #40132830
pg000
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Опаньки,
всё по документации, но крайне неожиданно.

CREATE FUNCTION
Также следует помнить о том, что по умолчанию право выполнения для создаваемых функций имеет роль PUBLIC автоматом (за подробностями обратитесь к GRANT).

GRANT
PostgreSQL по умолчанию назначает группе PUBLIC определённые права для некоторых типов объектов. Для таблиц, столбцов, последовательностей, обёрток сторонних данных, сторонних серверов, больших объектов, схем или табличных пространств PUBLIC по умолчанию никаких прав не имеет. Для других типов объектов PUBLIC имеет следующие права по умолчанию:
CONNECT и TEMPORARY (создание временных таблиц) для баз данных;
EXECUTE — для функций,
USAGE — для языков и типов данных (включая домены).

Можно удивиться посмотрев в базах
Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
SELECT fn_schema, fn_name, fn_oid, rolname, rolcanlogin::int, rolsuper::int, string_agg(privilege_type, ',' order by privilege_type) as "Granted", fn_args
FROM (SELECT nspname AS fn_schema, proname as fn_name, pg_proc.oid AS fn_oid, pg_get_function_arguments(pg_proc.oid) AS fn_args
	FROM pg_proc INNER JOIN pg_namespace ON pg_proc.pronamespace = pg_namespace.oid
	WHERE  nspname not like 'pg_%' and nspname <> 'information_schema'
) pr
CROSS JOIN pg_roles ro
CROSS JOIN (SELECT unnest('{EXECUTE}'::text[]) AS privilege_type) pt
WHERE has_function_privilege(rolname, fn_oid, privilege_type) = true
	and rolreplication = false and rolsuper = false --and rolcanlogin = true
	and rolname not like 'pg_%'
GROUP BY 1,2,8,3,4,5,6
ORDER BY 1,2,8,4
...
Рейтинг: 0 / 0
has_function_privilege - непонятная работа
    #40132916
Фотография Maxim Boguk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
pg000,

Поскольку функция по умолчанию выполняется с правами того кто её запускает то никаких доступов к таблицам или ещё чему которых нет у запускающего функцию - не образуется.
Поэтому и public доступ есть к функции по умолчанию на выполнение.

--
Maxim Boguk
лучшая поддержка PostgreSQL: dataegret.ru
...
Рейтинг: 0 / 0
has_function_privilege - непонятная работа
    #40132941
pg000
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Это по умолчанию.

Но есть же функции с SECURITY DEFINER

CREATE FUNCTION

Получается, чтобы понять может ли что-то поменять функция нужно смотреть исходный код.
При большом количестве функций это уже нужно писать код для такой проверки.
Ведь никаких намёков даже при pg_dump

Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
pg_dump -U postgres -d mydb1 --schema-only | grep -vP '^\s*(#|;|$)' | grep -vP '^--'

SET statement_timeout = 0;
SET lock_timeout = 0;
SET idle_in_transaction_session_timeout = 0;
SET client_encoding = 'UTF8';
SET standard_conforming_strings = on;
SELECT pg_catalog.set_config('search_path', '', false);
SET check_function_bodies = false;
SET xmloption = content;
SET client_min_messages = warning;
SET row_security = off;
CREATE FUNCTION public.myfn1() RETURNS integer
    LANGUAGE plpgsql
    AS $$
BEGIN
    RETURN 1;
END
$$;
ALTER FUNCTION public.myfn1() OWNER TO postgres;
SET default_tablespace = '';
SET default_table_access_method = heap;
CREATE TABLE public.mytbl1 (
    field1 integer
);
ALTER TABLE public.mytbl1 OWNER TO postgres;
REVOKE ALL ON SCHEMA public FROM PUBLIC;


Или нужно взять за привычку сразу же после создания функции выполнять.

Код: plsql
1.
REVOKE ALL ON FUNCTION ... FROM PUBLIC;
...
Рейтинг: 0 / 0
has_function_privilege - непонятная работа
    #40132952
Фотография Maxim Boguk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
pg000,

Про security definer там вообще много gotchas есть включая подмену search_path например
и предполагается что тот кто их пишет внимательно прочитал и осознал всё что написано в
https://www.postgresql.org/docs/14/sql-createfunction.html#SQL-CREATEFUNCTION-SECURITY
и в общем grant for publiс там не самая большая опасность.
Т.е. security definer функции должны проходить весьма отдельный и внимательный security audit.

--
Maxim Boguk
лучшая поддержка PostgreSQL: dataegret.ru
...
Рейтинг: 0 / 0
has_function_privilege - непонятная работа
    #40132962
pg000
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Ну я вот не сторонник "административных" решений.

Мне вот понравилось когда-то...

Решений здесь два: радикальное и правильное. Радикальное - покарать нерадивого разработчика физически (сделайте ему массаж почек и печени), морально (устроить публичную психологическую порку), финансово (лишите премии). Но вы же понимаете, что все это плохо и поселит в глубине “чуткой” души разработчика обиду на вас. Может он был уставшим и просто недоглядел - бывает такое? Конечно бывает! Поэтому, решение правильное - автоматизируйте проверку кода
Возможно ещё на новых базах.
Код: plsql
1.
2.
3.
4.
ALTER DEFAULT PRIVILEGES IN SCHEMA public FOR ROLE postgres REVOKE ALL ON FUNCTIONS FROM PUBLIC;

CREATE SCHEMA myschema1
ALTER DEFAULT PRIVILEGES IN SCHEMA myschema1 FOR ROLE postgres REVOKE ALL ON FUNCTIONS FROM PUBLIC;


Или на новых базах для будущих schema вообще вешать EVENT TRIGGER
Код: plsql
1.
2.
3.
4.
5.
6.
7.
CREATE EVENT TRIGGER auto_grant_trigger
    ON ddl_command_end
    WHEN TAG IN (
            'CREATE SCHEMA',
            'ALTER SCHEMA'
        )
EXECUTE PROCEDURE auto_grant_func();
...
Рейтинг: 0 / 0
has_function_privilege - непонятная работа
    #40132966
Фотография Maxim Boguk
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
pg000
Ну я вот не сторонник "административных" решений.

Мне вот понравилось когда-то...

Решений здесь два: радикальное и правильное. Радикальное - покарать нерадивого разработчика физически (сделайте ему массаж почек и печени), морально (устроить публичную психологическую порку), финансово (лишите премии). Но вы же понимаете, что все это плохо и поселит в глубине “чуткой” души разработчика обиду на вас. Может он был уставшим и просто недоглядел - бывает такое? Конечно бывает! Поэтому, решение правильное - автоматизируйте проверку кода

Возможно ещё на новых базах.
Код: plsql
1.
2.
3.
4.
ALTER DEFAULT PRIVILEGES IN SCHEMA public FOR ROLE postgres REVOKE ALL ON FUNCTIONS FROM PUBLIC;

CREATE SCHEMA myschema1
ALTER DEFAULT PRIVILEGES IN SCHEMA myschema1 FOR ROLE postgres REVOKE ALL ON FUNCTIONS FROM PUBLIC;


Или на новых базах для будущих schema вообще вешать EVENT TRIGGER
Код: plsql
1.
2.
3.
4.
5.
6.
7.
CREATE EVENT TRIGGER auto_grant_trigger
    ON ddl_command_end
    WHEN TAG IN (
            'CREATE SCHEMA',
            'ALTER SCHEMA'
        )
EXECUTE PROCEDURE auto_grant_func();



Тогда ещё проверку установки search_path для security definer хранимко надо делать.
Через проверку select proname, proconfig from pg_proc where prosecdef;

Идею автоматического убирания прав на public в принципе поддерживаю но гемороя с ручной раздачей прав оно добавит преизрядно.

--
Maxim Boguk
лучшая поддержка PostgreSQL: dataegret.ru
...
Рейтинг: 0 / 0
9 сообщений из 9, страница 1 из 1
Форумы / PostgreSQL [игнор отключен] [закрыт для гостей] / has_function_privilege - непонятная работа
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]