ได้รับประโยชน์จากสคีมาทั้งหมดในฐานข้อมูลหรือไม่


13

ฉันต้องการGRANT USAGEผู้ใช้ / บทบาทสำหรับฐานข้อมูลที่กำหนด ฐานข้อมูลมีสกีมาจำนวนมาก

ฉันรู้ว่ามีON ALL TABLES IN SCHEMAแต่ฉันต้องการ "schemas ทั้งหมด" ฉันพยายามGRANT USAGE .. ON DATABASEแต่ก็เห็นได้ชัดว่าผิด (มันไม่มีอยู่จริง )

นี่สำหรับ Postgres 9.3 หรือ 9.4 มันเป็นเซิร์ฟเวอร์ที่อยู่บน AWS RDS

คำตอบ:


18

คุณมีอย่างน้อยสองตัวเลือก

อันแรกใช้ประโยชน์จากการสืบค้นขนาดเล็กและแก้ไขข้อความ เราต้องรวบรวมแบบแผนความสนใจของเรา:

SELECT nspname
  FROM pg_namespace;

คุณสามารถเพิ่มส่วนWHEREคำสั่งถ้าคุณต้องการ จำกัด ขอบเขต คัดลอกเอาต์พุตและแก้ไขเพื่อให้คุณได้GRANT USAGE ON SCHEMA ... TO your_role;รับคำสั่งจำนวนมาก จากนั้นให้ป้อนpsqlตัวอย่างเช่น:

psql -f multigrant.sql

ตัวแปรปกติของสิ่งนี้อาจเป็นเชลล์สคริปต์ที่วนรอบชื่อและการเรียกที่รวบรวมไว้psqlซึ่งส่งผ่านGRANTข้อความสั่งที่สร้างไปยัง-cตัวเลือก

โซลูชันอื่นทำแบบเดียวกันในบล็อก pl / pgsql หนึ่งบล็อกโดยสร้างคิวรีแบบไดนามิก แกนกลางเหมือนกัน - เราต้องรวบรวม schemata จากนั้นเราวนลูปทั้งหมดของพวกเขาอนุญาตสคีมาการอนุญาตตามสคีมา:

DO $do$
DECLARE
    sch text;
BEGIN
    FOR sch IN SELECT nspname FROM pg_namespace
    LOOP
        EXECUTE format($$ GRANT USAGE ON SCHEMA %I TO your_role $$, sch);
    END LOOP;
END;
$do$;

หมายเหตุ :

  • แตกต่างจากตารางลำดับฟังก์ชันและประเภทหนึ่งไม่สามารถตั้งค่าสิทธิ์เริ่มต้นสำหรับ schemata (ณ วันที่ 9.4) คุณจะต้องให้สิทธิ์นี้สำหรับสคีมาที่เพิ่มใหม่ด้วยตนเอง
  • ที่นี่ฉันกำลังใช้ข้อความดอลลาร์เมื่อสร้างคิวรีแบบไดนามิก สิ่งนี้อนุญาตให้ฉันใช้ไวยากรณ์ 'ปกติ' ซึ่งตรงข้ามกับการเสนอราคาแบบทวีคูณเช่น (ไม่มีอยู่ในตัวอย่างนี้) วิธีนี้ผู้แก้ไขส่วนใหญ่จะเน้นข้อความอย่างดี
  • ฉันยังใช้format()กับตัว%Iระบุรูปแบบเพื่อให้ชื่อวัตถุถูกยกมาอย่างถูกต้องหากจำเป็น วิธีการนี้สามารถอ่านได้ง่ายกว่าการสร้างแบบสอบถามด้วยการต่อค่าคงที่สตริงและการquote_ident()เรียกบางอย่าง
  • pg_namespaceสามารถพบได้ในpg_catalogสคีมา ตรวจสอบวัตถุอื่น ๆ ที่อยู่ในนั้น - มันเก็บทุกแง่มุมของสกีมาของคุณตารางและอื่น ๆ

1
ฉันสงสัยว่าคุณสามารถจำลองสิทธิ์เริ่มต้นสำหรับgrant usageสคีมาที่สร้างขึ้นใหม่ได้โดยใช้ทริกเกอร์เหตุการณ์ที่เรียกใช้สคีมาใหม่โดยอัตโนมัติหรือไม่
a_horse_with_no_name

@a_horse_with_no_name กำลังคิดเรื่องนี้อยู่ฉันเห็นว่าในปัจจุบันไม่มีเหตุผลว่าทำไมมันไม่สามารถทำได้
dezso

0

คุณสามารถใช้เช่นกัน

DO $do$
DECLARE
    sch text;
BEGIN
    FOR sch IN SELECT nspname FROM pg_namespace where nspname != 'pg_toast' 
    and nspname != 'pg_temp_1' and nspname != 'pg_toast_temp_1'
    and nspname != 'pg_statistic' and nspname != 'pg_catalog'
    and nspname != 'information_schema'
    LOOP
        EXECUTE format($$ GRANT USAGE ON SCHEMA %I TO your_role $$, sch);
        EXECUTE format($$ GRANT USAGE ON SCHEMA %I to your_role $$, sch);
        EXECUTE format($$ GRANT SELECT ON ALL SEQUENCES IN SCHEMA %I TO your_role $$, sch);
        EXECUTE format($$ GRANT SELECT ON ALL TABLES IN SCHEMA %I TO backup_user $$, sch);

        EXECUTE format($$ ALTER DEFAULT PRIVILEGES IN SCHEMA %I GRANT SELECT ON TABLES TO your_role $$, sch);
        EXECUTE format($$ ALTER DEFAULT PRIVILEGES IN SCHEMA %I GRANT SELECT ON SEQUENCES TO your_role $$, sch);
    END LOOP;
END;
$do$;
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.