在数据 API 生成器中使用会话上下文实现行级别安全性

使用 SQL 的 会话上下文 功能在数据 API 生成器中实现行级安全性。

先决条件

  • 现有 SQL Server 和数据库。
  • 数据 API 生成器 CLI。 安装 CLI
  • 数据库客户端 (SQL Server Management Studio、Azure Data Studio 等 )

Create SQL 表和数据

Create一个包含虚构数据的表,用于此示例方案。

  1. 使用首选客户端或工具连接到 SQL 数据库。

  2. Create名为 Revenuesid、、 categoryrevenueusername 列的表。

    DROP TABLE IF EXISTS dbo.Revenues;
    
    CREATE TABLE dbo.Revenues(
        id int PRIMARY KEY,  
        category varchar(max) NOT NULL,  
        revenue int,  
        username varchar(max) NOT NULL  
    );
    GO
    
  3. 在表中插入四个示例书籍行 Revenues

    INSERT INTO dbo.Revenues VALUES
        (1, 'Book', 5000, 'Oscar'),  
        (2, 'Comics', 10000, 'Oscar'),  
        (3, 'Journals', 20000, 'Hannah'),  
        (4, 'Series', 40000, 'Hannah')
    GO
    
  4. 使用简单 SELECT * 查询测试数据。

    SELECT * FROM dbo.Revenues
    
  5. 创建一个名为 RevenuesPredicate 的函数。 此函数将基于当前会话上下文筛选结果。

    CREATE FUNCTION dbo.RevenuesPredicate(@username varchar(max))
    RETURNS TABLE
    WITH SCHEMABINDING
    AS RETURN SELECT 1 AS fn_securitypredicate_result
    WHERE @username = CAST(SESSION_CONTEXT(N'name') AS varchar(max));
    
  6. 使用 函数Create名为 RevenuesSecurityPolicy 的安全策略。

    CREATE SECURITY POLICY dbo.RevenuesSecurityPolicy
    ADD FILTER PREDICATE dbo.RevenuesPredicate(username)
    ON dbo.Revenues;
    

运行工具

(DAB) 工具运行数据 API 生成器以生成配置文件和单个实体。

  1. Create新配置,同时将 设置为 --set-session-context true。

    dab init \
        --database-type mssql \
        --connection-string "<sql-connection-string>" \
        --set-session-context true
    
  2. dbo.Revenues表添加名为 revenue 的新实体。

    dab add revenue \
        --source "dbo.Revenues" \
        --permissions "anonymous:read"
    
  3. 启动数据 API 生成器工具。

    dab start
    
  4. 导航到 http://localhost:5000/api/revenue 终结点。 请注意,未返回任何数据。 出现此行为的原因是会话上下文未设置,并且没有记录与筛选器谓词匹配。

在 SQL 中测试

直接在 SQL 中测试筛选器和谓词,以确保它正常工作。

  1. 使用首选客户端或工具再次连接到 SQL Server。

  2. 运行 以 sp_set_session_context 手动将会话上下文的 name 声明设置为静态值 Oscar

    EXEC sp_set_session_context 'name', 'Oscar';
    
  3. 运行典型 SELECT * 查询。 请注意,使用谓词自动筛选结果。

    SELECT * FROM dbo.Revenues;