trinodb / trino

Official repository of Trino, the distributed SQL query engine for big data, formerly known as PrestoSQL (https://trino.io)
https://trino.io
Apache License 2.0
10.25k stars 2.95k forks source link

unable to use unregister table in delta catalog without write permission #20277

Closed AlakmarShafin closed 8 months ago

AlakmarShafin commented 8 months ago

File-based access control rule:

{
  "catalogs": [
      {
        "user": "alakmar",
        "catalog": ".*",
        "allow": "read-only"
      },
      {
        "user": "trinoadminread",
        "catalog": "deltalake",
        "allow": "read-only"
      },
      {
        "user": "trinoadminrw",
        "catalog": ".*",
        "allow": "all"
      }]
"procedures": [
          {
              "user": "(trinoadminrw|trinoadminread)",
              "catalog": "deltalake",
              "procedure": "register_table",
              "privileges": [
                  "EXECUTE"
              ]
          },
          {
              "user": "(trinoadminrw|trinoadminread)",
              "catalog": "deltalake",
              "procedure": "unregister_table",
              "privileges": [
                  "EXECUTE"
              ]
          }
      ]

}

Issue

While running unregister table CALL deltalake.system.unregister_table(schema_name => 'dl_central_sharepoint', table_name => 'SaleSale_3062022' ) with trinoadminread gives the error "Access Denied: Cannot drop table deltalake.dl_central_sharepoint.salesale_3062022" while I am able to register the table with the same user.

Note: Both register_table and unregister_table are working on the user trinoadminrw.

Stack trace:

Error while running register_table with trinoadminread:

org.jkiss.dbeaver.model.sql.DBSQLException: SQL Error [4]: Query failed (#20240104_094124_00521_hy37q): Access Denied: Cannot drop table deltalake.dl_central_sharepoint.salesale_3062022 at org.jkiss.dbeaver.model.impl.jdbc.exec.JDBCPreparedStatementImpl.executeStatement(JDBCPreparedStatementImpl.java:208) at org.jkiss.dbeaver.ui.editors.sql.execute.SQLQueryJob.executeStatement(SQLQueryJob.java:582) at org.jkiss.dbeaver.ui.editors.sql.execute.SQLQueryJob.lambda$1(SQLQueryJob.java:491) at org.jkiss.dbeaver.model.exec.DBExecUtils.tryExecuteRecover(DBExecUtils.java:189) at org.jkiss.dbeaver.ui.editors.sql.execute.SQLQueryJob.executeSingleQuery(SQLQueryJob.java:498) at org.jkiss.dbeaver.ui.editors.sql.execute.SQLQueryJob.extractData(SQLQueryJob.java:934) at org.jkiss.dbeaver.ui.editors.sql.SQLEditor$QueryResultsContainer.readData(SQLEditor.java:3919) at org.jkiss.dbeaver.ui.controls.resultset.ResultSetJobDataRead.lambda$0(ResultSetJobDataRead.java:123) at org.jkiss.dbeaver.model.exec.DBExecUtils.tryExecuteRecover(DBExecUtils.java:189) at org.jkiss.dbeaver.ui.controls.resultset.ResultSetJobDataRead.run(ResultSetJobDataRead.java:121) at org.jkiss.dbeaver.ui.controls.resultset.ResultSetViewer$ResultSetDataPumpJob.run(ResultSetViewer.java:5101) at org.jkiss.dbeaver.model.runtime.AbstractJob.run(AbstractJob.java:105) at org.eclipse.core.internal.jobs.Worker.run(Worker.java:63) Caused by: java.sql.SQLException: Query failed (#20240104_094124_00521_hy37q): Access Denied: Cannot drop table deltalake.dl_central_sharepoint.salesale_3062022 at io.trino.jdbc.AbstractTrinoResultSet.resultsException(AbstractTrinoResultSet.java:1937) at io.trino.jdbc.TrinoResultSet.getColumns(TrinoResultSet.java:318) at io.trino.jdbc.TrinoResultSet.create(TrinoResultSet.java:61) at io.trino.jdbc.TrinoStatement.internalExecute(TrinoStatement.java:262) at io.trino.jdbc.TrinoStatement.execute(TrinoStatement.java:240) at io.trino.jdbc.TrinoPreparedStatement.execute(TrinoPreparedStatement.java:165) at org.jkiss.dbeaver.model.impl.jdbc.exec.JDBCPreparedStatementImpl.execute(JDBCPreparedStatementImpl.java:261) at org.jkiss.dbeaver.model.impl.jdbc.exec.JDBCPreparedStatementImpl.executeStatement(JDBCPreparedStatementImpl.java:205) ... 12 more Caused by: io.trino.spi.security.AccessDeniedException: Access Denied: Cannot drop table deltalake.dl_central_sharepoint.salesale_3062022 at io.trino.spi.security.AccessDeniedException.denyDropTable(AccessDeniedException.java:230) at io.trino.spi.security.AccessDeniedException.denyDropTable(AccessDeniedException.java:225) at io.trino.plugin.base.security.FileBasedSystemAccessControl.checkCanDropTable(FileBasedSystemAccessControl.java:496) at io.trino.plugin.base.security.ForwardingSystemAccessControl.checkCanDropTable(ForwardingSystemAccessControl.java:193) at io.trino.security.AccessControlManager.lambda$checkCanDropTable$25(AccessControlManager.java:505) at io.trino.security.AccessControlManager.systemAuthorizationCheck(AccessControlManager.java:1441) at io.trino.security.AccessControlManager.checkCanDropTable(AccessControlManager.java:505) at io.trino.security.ForwardingAccessControl.checkCanDropTable(ForwardingAccessControl.java:179) at io.trino.tracing.TracingAccessControl.checkCanDropTable(TracingAccessControl.java:247) at io.trino.security.InjectedConnectorAccessControl.checkCanDropTable(InjectedConnectorAccessControl.java:121) at io.trino.plugin.deltalake.procedure.UnregisterTableProcedure.doUnregisterTable(UnregisterTableProcedure.java:98) at io.trino.plugin.deltalake.procedure.UnregisterTableProcedure.unregisterTable(UnregisterTableProcedure.java:88) at java.base/java.lang.invoke.MethodHandle.invokeWithArguments(MethodHandle.java:733) at java.base/java.lang.invoke.MethodHandle.invokeWithArguments(MethodHandle.java:758) at io.trino.execution.CallTask.execute(CallTask.java:210) at io.trino.execution.CallTask.execute(CallTask.java:70) at io.trino.execution.DataDefinitionExecution.start(DataDefinitionExecution.java:145) at io.trino.execution.SqlQueryManager.createQuery(SqlQueryManager.java:256) at io.trino.dispatcher.LocalDispatchQuery.startExecution(LocalDispatchQuery.java:145) at io.trino.dispatcher.LocalDispatchQuery.lambda$waitForMinimumWorkers$2(LocalDispatchQuery.java:129) at io.airlift.concurrent.MoreFutures.lambda$addSuccessCallback$12(MoreFutures.java:568) at io.airlift.concurrent.MoreFutures$3.onSuccess(MoreFutures.java:543) at com.google.common.util.concurrent.Futures$CallbackListener.run(Futures.java:1133) at io.trino.$gen.Trino_435____20231220_064330_2.run(Unknown Source) at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1144) at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:642) at java.base/java.lang.Thread.run(Thread.java:1583)

lukasz-walkiewicz commented 8 months ago

Hi @AlakmarShafin, thanks for the report but it looks it works as expected. DROP table permission is required in order to execute unregister_table procedure, see: https://github.com/trinodb/trino/blob/5ac064541e62dd7253bdaac86e11a447cb427052/plugin/trino-delta-lake/src/main/java/io/trino/plugin/deltalake/procedure/UnregisterTableProcedure.java#L98C23-L98C40

AlakmarShafin commented 8 months ago

But I need to grant permission only to unregister the table but in this case I have to put "allow":"all" { "user": "trinoadminrw", "catalog": ".*", "allow": "all" }

Which gives that user access to drop view, delete or update data, etc. these permissions i don't want to grant to a read-only user.

ebyhr commented 8 months ago

Closing as the expected behavior.