Changeset: 3c3c4f40cded for MonetDB
URL: https://dev.monetdb.org/hg/MonetDB?cmd=changeset;node=3c3c4f40cded
Added Files:
        sql/test/Users/Tests/function_privs.SQL.py
Removed Files:
        sql/test/Users/Tests/privs2.reqtests
        sql/test/Users/Tests/privs2.sql
        sql/test/Users/Tests/privs2.test
        sql/test/Users/Tests/schema.sql
        sql/test/Users/Tests/schema.test
        sql/test/Users/Tests/test_privs2_p1.SQL.py
        sql/test/Users/Tests/test_privs2_p1.reqtests
        sql/test/Users/Tests/test_privs2_p2.SQL.py
        sql/test/Users/Tests/test_privs2_p2.reqtests
Modified Files:
        sql/test/Users/Tests/All
Branch: default
Log Message:

Merged "privs2", "test_privs2_p1" and "test_privs2_p2" into "function_privs"
Extended the tests
Removed unnecessary files

Note that this test fails on "default", because the implementation of indirect 
privileges is in "indirect-privs" branch


diffs (truncated from 536 to 300 lines):

diff --git a/sql/test/Users/Tests/All b/sql/test/Users/Tests/All
--- a/sql/test/Users/Tests/All
+++ b/sql/test/Users/Tests/All
@@ -1,11 +1,8 @@
+function_privs
 role
 table
 table_privs
-schema
 unknown_user
-privs2
-test_privs2_p1
-test_privs2_p2
 createSetUp
 withGrantOption
 columnRights
diff --git a/sql/test/Users/Tests/function_privs.SQL.py 
b/sql/test/Users/Tests/function_privs.SQL.py
new file mode 100644
--- /dev/null
+++ b/sql/test/Users/Tests/function_privs.SQL.py
@@ -0,0 +1,187 @@
+###
+# Check direct function privilege:
+#   A user with SEL/INS/UPD/DEL privilege on a table and EXEC privilege on the
+#   functions SEL/INS/UPD/DEL that table can execute the functions.
+# Check indirect function privilege:
+#   A user with only(!) EXEC privilege on functions that SEL/INS/UPD/DEL a
+#   table can execute the functions.
+# Check that if a user has CREATE FUNCTION privilege in one schema (i.e. is an
+#   schema owner) but not in another schema, then the user can CREATE FUNCTIONs
+#   to operate on tables in this schema but not in the other schema.
+###
+
+from MonetDBtesting.sqltest import SQLTestCase
+
+with SQLTestCase() as mdb:
+    mdb.connect(username="monetdb", password="monetdb")
+    mdb.execute("CREATE ROLE my_role;").assertSucceeded()
+    mdb.execute("CREATE SCHEMA my_schema AUTHORIZATION 
my_role;").assertSucceeded()
+    mdb.execute("CREATE USER my_user WITH PASSWORD 'p1' NAME 'my_user' SCHEMA 
sys;").assertSucceeded()
+    mdb.execute("CREATE USER my_user2 WITH PASSWORD 'p2' NAME 'my_user2' 
SCHEMA sys;").assertSucceeded()
+    mdb.execute("SET SCHEMA my_schema;").assertSucceeded()
+    mdb.execute("CREATE TABLE version (name VARCHAR(10), i 
INT);").assertSucceeded()
+    mdb.execute("INSERT INTO version VALUES ('test1', 1);").assertRowCount(1)
+
+    mdb.execute("""
+        create function selectversion() returns table(name varchar(10), i int)
+        begin
+          return table(select * from version);
+        end;
+    """).assertSucceeded()
+    mdb.execute("""
+        create function insertversion(iname varchar(10), ii int) returns int
+        begin
+          insert into version values (iname, ii);
+          return 1;
+        end;
+    """).assertSucceeded()
+    mdb.execute("""
+        create function updateversion(iname varchar(10), ii int) returns int
+        begin
+          update version set i = ii where name = iname;
+          return 1;
+        end;
+    """).assertSucceeded()
+    mdb.execute("""
+        create function deleteversion(iname varchar(10)) returns int
+        begin
+          delete from version where name = iname;
+          return 1;
+        end;
+    """).assertSucceeded()
+
+    # create a table to which my_user doesn't have access
+    mdb.execute("CREATE SCHEMA your_schema;").assertSucceeded()
+    mdb.execute("create table your_schema.your_table (name varchar(10), i 
int);").assertSucceeded()
+
+    # grant table right to my_user but not to my_user2
+    mdb.execute("GRANT SELECT on table version to my_user;").assertSucceeded()
+    mdb.execute("GRANT INSERT on table version to my_user;").assertSucceeded()
+    mdb.execute("GRANT UPDATE on table version to my_user;").assertSucceeded()
+    mdb.execute("GRANT DELETE on table version to my_user;").assertSucceeded()
+
+    # grant function rights to both users
+    mdb.execute("GRANT EXECUTE on function selectversion to 
my_user;").assertSucceeded()
+    mdb.execute("GRANT EXECUTE on function insertversion to 
my_user;").assertSucceeded()
+    mdb.execute("GRANT EXECUTE on function updateversion to 
my_user;").assertSucceeded()
+    mdb.execute("GRANT EXECUTE on function deleteversion to 
my_user;").assertSucceeded()
+
+    mdb.execute("GRANT EXECUTE on function selectversion to 
my_user2;").assertSucceeded()
+    mdb.execute("GRANT EXECUTE on function insertversion to 
my_user2;").assertSucceeded()
+    mdb.execute("GRANT EXECUTE on function updateversion to 
my_user2;").assertSucceeded()
+    mdb.execute("GRANT EXECUTE on function deleteversion to 
my_user2;").assertSucceeded()
+
+    with SQLTestCase() as tc:
+        # my_user can SEL/INS/UPD/DEL both directly on the table or through 
the functions
+        tc.connect(username="my_user", password="p1")
+        tc.execute("SET SCHEMA my_schema;").assertSucceeded()
+        tc.execute("INSERT INTO version (name, i) VALUES ('test2', 
2);").assertSucceeded()
+        tc.execute("SELECT * FROM 
version;").assertSucceeded().assertDataResultMatch([('test1', 1), ('test2', 2)])
+        tc.execute("UPDATE version SET name = 'test22' WHERE i = 
2;").assertSucceeded()
+        tc.execute("SELECT * FROM 
version;").assertSucceeded().assertDataResultMatch([('test1', 1), ('test22', 
2)])
+        tc.execute("DELETE FROM version WHERE name = 
'test22';").assertSucceeded()
+        tc.execute("SELECT * FROM 
version;").assertSucceeded().assertDataResultMatch([('test1', 1)])
+        tc.execute("SELECT insertversion('test3', 3);").assertSucceeded()
+        tc.execute("SELECT updateversion('test1', 4);").assertSucceeded()
+        tc.execute("SELECT deleteversion('test1');").assertSucceeded()
+        tc.execute("SELECT * FROM 
selectversion();").assertSucceeded().assertDataResultMatch([('test3', 3)])
+        # make my_user an owner of my_schema so that my_user can create 
functions
+        # in my_schema
+        mdb.execute("GRANT my_role to my_user;").assertSucceeded()
+        tc.execute("SET ROLE my_role;").assertSucceeded()
+        tc.execute("""
+            create function myselect() returns table(name varchar(10), i int)
+            begin
+              return table(select * from version);
+            end;
+        """).assertSucceeded()
+        tc.execute("""
+            create function myinsert(iname varchar(10), ii int) returns int
+            begin
+              insert into version (name, i) values (iname, ii);
+              return 1;
+            end;
+        """).assertSucceeded()
+        tc.execute("""
+            create function myupdate(iname varchar(10), ii int) returns int
+            begin
+              update version set i = ii where name = iname;
+              return 1;
+            end;
+        """).assertSucceeded()
+        tc.execute("""
+            create function mydelete(iname varchar(10)) returns int
+            begin
+              delete from version where name = iname;
+              return 1;
+            end;
+        """).assertSucceeded()
+        tc.execute("DROP FUNCTION myselect;").assertSucceeded()
+        tc.execute("DROP FUNCTION myinsert;").assertSucceeded()
+        tc.execute("DROP FUNCTION myupdate;").assertSucceeded()
+        tc.execute("DROP FUNCTION mydelete;").assertSucceeded()
+        # but my_user cannot create functions to operate on a table to which it
+        # doesn't have access
+        tc.execute("""
+            create function yourselect() returns table(name varchar(10), i int)
+            begin
+              return table(select * from version union select * from 
your_schema.your_table);
+            end;
+        """).assertFailed(err_code="42000", err_message="SELECT: access denied 
for my_user to table 'your_schema.your_table'")
+
+        # my_user2 can only indirectly SEL/INS/UPD/DEL the table through the 
functions
+        tc.connect(username="my_user2", password="p2")
+        tc.execute("SET SCHEMA my_schema;").assertSucceeded()
+        tc.execute("INSERT INTO version (name, i) VALUES ('test2', 
2);").assertFailed(err_code="42000", err_message="INSERT INTO: insufficient 
privileges for user 'my_user2' to insert into table 'version'")
+        tc.execute("UPDATE version SET name = 'test22' WHERE i = 
2;").assertFailed(err_code="42000", err_message="UPDATE: insufficient 
privileges for user 'my_user2' to update table 'version'")
+        tc.execute("DELETE FROM version WHERE name = 
'test22';").assertFailed(err_code="42000", err_message="DELETE FROM: 
insufficient privileges for user 'my_user2' to delete from table 'version'")
+        tc.execute("SELECT * FROM version;").assertFailed(err_code="42000", 
err_message="SELECT: access denied for my_user2 to table 'my_schema.version'")
+        tc.execute("SELECT insertversion('test4', 4);").assertSucceeded()
+        tc.execute("SELECT * FROM 
selectversion();").assertSucceeded().assertDataResultMatch([('test3', 3), 
('test4', 4)])
+        tc.execute("SELECT updateversion('test3', 33);").assertSucceeded()
+        tc.execute("SELECT * FROM 
selectversion();").assertSucceeded().assertDataResultMatch([('test3', 33), 
('test4', 4)])
+        tc.execute("SELECT deleteversion('test3');").assertSucceeded()
+        tc.execute("SELECT * FROM 
selectversion();").assertSucceeded().assertDataResultMatch([('test4', 4)])
+        # and my_user2 cannot create functions to operate on the table
+        tc.execute("""
+            create function myselect2() returns table(name varchar(10), i int)
+            begin
+              return table(select * from version);
+            end;
+        """).assertFailed(err_code="42000", err_message="CREATE UNION 
FUNCTION: insufficient privileges for user 'my_user2' in schema 'my_schema'")
+        tc.execute("""
+            create function myinsert2(iname varchar(10), ii int) returns int
+            begin
+              insert into version (name, i) values (iname, ii);
+              return 1;
+            end;
+        """).assertFailed(err_code="42000", err_message="CREATE FUNCTION: 
insufficient privileges for user 'my_user2' in schema 'my_schema'")
+        tc.execute("""
+            create function myupdate2(iname varchar(10), ii int) returns int
+            begin
+              update version set i = ii where name = iname;
+              return 1;
+            end;
+        """).assertFailed(err_code="42000", err_message="CREATE FUNCTION: 
insufficient privileges for user 'my_user2' in schema 'my_schema'")
+        tc.execute("""
+            create function mydelete2(iname varchar(10)) returns int
+            begin
+              delete from version where name = iname;
+              return 1;
+            end;
+        """).assertFailed(err_code="42000", err_message="CREATE FUNCTION: 
insufficient privileges for user 'my_user2' in schema 'my_schema'")
+
+        # clean up
+        mdb.connect(username="monetdb", password="monetdb")
+        mdb.execute("DROP FUNCTION my_schema.selectversion;").assertSucceeded()
+        mdb.execute("DROP FUNCTION my_schema.insertversion;").assertSucceeded()
+        mdb.execute("DROP FUNCTION my_schema.updateversion;").assertSucceeded()
+        mdb.execute("DROP FUNCTION my_schema.deleteversion;").assertSucceeded()
+        mdb.execute("DROP TABLE my_schema.version;").assertSucceeded()
+        mdb.execute("DROP TABLE your_schema.your_table;").assertSucceeded()
+        mdb.execute("DROP USER my_user;").assertSucceeded()
+        mdb.execute("DROP USER my_user2;").assertSucceeded()
+        mdb.execute("DROP ROLE my_role;").assertSucceeded()
+        mdb.execute("DROP SCHEMA my_schema;").assertSucceeded()
+        mdb.execute("DROP SCHEMA your_schema;").assertSucceeded()
+
diff --git a/sql/test/Users/Tests/privs2.reqtests 
b/sql/test/Users/Tests/privs2.reqtests
deleted file mode 100644
--- a/sql/test/Users/Tests/privs2.reqtests
+++ /dev/null
@@ -1,1 +0,0 @@
-schema
diff --git a/sql/test/Users/Tests/privs2.sql b/sql/test/Users/Tests/privs2.sql
deleted file mode 100644
--- a/sql/test/Users/Tests/privs2.sql
+++ /dev/null
@@ -1,37 +0,0 @@
-set schema "my_schema";
-
-create table version (name varchar(10), i int);
-
-insert into version (name, i) values ('test1', 1);
-
-create function insertversion(iname varchar(10), ii int) returns int
-begin
-  insert into version (name, i) values (iname, ii);
-  return 1;
-end;
- 
-create function updateversion(iname varchar(10), ii int) returns int
-begin
-  update version set i = ii where name = iname;
-  return 1;
-end;
- 
-create function deleteversion(iname varchar(10)) returns int
-begin
-  delete from version where name = iname;
-  return 1;
-end;
- 
--- grant right to my_user not to my_user2
-GRANT SELECT on table version to my_user;
-GRANT INSERT on table version to my_user;
-GRANT UPDATE on table version to my_user;
-GRANT DELETE on table version to my_user;
-
-GRANT EXECUTE on function insertversion to my_user;
-GRANT EXECUTE on function updateversion to my_user;
-GRANT EXECUTE on function deleteversion to my_user;
-
-GRANT EXECUTE on function insertversion to my_user2;
-GRANT EXECUTE on function updateversion to my_user2;
-GRANT EXECUTE on function deleteversion to my_user2;
diff --git a/sql/test/Users/Tests/privs2.test b/sql/test/Users/Tests/privs2.test
deleted file mode 100644
--- a/sql/test/Users/Tests/privs2.test
+++ /dev/null
@@ -1,60 +0,0 @@
-statement ok
-set schema "my_schema"
-
-statement ok
-create table version (name varchar(10), i int);
-
-statement ok
-insert into version (name, i) values ('test1', 1);
-
-statement ok
-create function insertversion(iname varchar(10), ii int) returns int
-begin
-  insert into version (name, i) values (iname, ii);
-  return 1;
-end;
-
-statement ok
-create function updateversion(iname varchar(10), ii int) returns int
-begin
-  update version set i = ii where name = iname;
-  return 1;
-end;
-
-statement ok
-create function deleteversion(iname varchar(10)) returns int
-begin
-  delete from version where name = iname;
-  return 1;
-end;
-
-statement ok
-GRANT SELECT on table version to my_user
-
-statement ok
-GRANT INSERT on table version to my_user
-
-statement ok
-GRANT UPDATE on table version to my_user
-
_______________________________________________
checkin-list mailing list
checkin-list@monetdb.org
https://www.monetdb.org/mailman/listinfo/checkin-list

Reply via email to