Made by the SE Team For Walkthrough Purposes Only

PlainID Snowflake Policy Orchestration

Technical documentation for implementing Policy Orchestration Points (POPs) for Snowflake Data Cloud environments using PlainID's SaaS Authorization Management.

Architecture Pattern: Snowflake integration uses PlainID's Policy Orchestration Point (POP) pattern for SaaS Authorization Management, enabling centralized policy discovery, management, and enforcement.
Version: PlainID Platform 2024.1+ | Feature: Snowflake Policy Orchestration Point | Announced: December 2024
Snowflake Requirements: Enterprise Edition or higher (required for Row Access Policies and Dynamic Data Masking)

System Overview

PlainID's Snowflake integration leverages Policy Orchestration to centralize Snowflake's access controls through a unified Policy-Based Access Control (PBAC) framework. The Policy Orchestration Point (POP) enables enterprises to discover, manage, and enforce data access policies across their Snowflake environments.

Core Components Architecture

PlainID Cloud Platform PAP Policy Admin Point Policy Creation POP Service Orchestration Engine Discovery & Deploy Snowflake Environment Native Snowflake Policies Row Access Policies Masking Policies Databases Schemas, Tables Security Objects Roles, Users Virtual Warehouses Compute clusters that enforce policies at runtime Deploy Policies Discover Objects 👤 End User

End-to-End Authorization Flow

👤
User Query
User executes SELECT on Snowflake table
❄️
Snowflake
Triggers external authorization function
🔐
PlainID POP
Evaluates policies & resolves attributes
Decision
Returns filtered/masked result set

Key Capabilities

Policy Orchestration Point (POP) Architecture

SaaS Authorization Management Pattern

PlainID Cloud
Policy Administration
PAP + Policy Store
Snowflake POP
Orchestration Layer
Discover & Deploy
Snowflake
Native Policies
Row Access & Masking

POP Components

Component Function Location
Policy Orchestration Service Manages bi-directional sync between PlainID and Snowflake PlainID Cloud
Discovery Engine Scans and maps Snowflake objects and policies POP Service
Policy Translator Converts between PlainID policies and Snowflake native policies POP Service
Deployment Engine Applies policy changes to Snowflake environments POP Service
Important: Unlike Data Authorizers that use PAA/PDP/PIP components, POPs operate as a SaaS service that orchestrates native vendor policies. For Snowflake, this means managing Snowflake's native row access policies and masking policies.

Snowflake Policy Orchestration Point

Integration Overview

The Snowflake POP enables PlainID to discover, manage, and deploy authorization policies using Snowflake's native security features.

Discovered Objects

# Objects automatically discovered during POP initialization:

DATABASES
├── Schemas
├── Tables
│   ├── Columns (with data types)
│   └── Row Access Policies
├── Views
│   ├── Columns
│   └── Access Policies
├── External Functions
└── Warehouses

SECURITY OBJECTS
├── Roles (System & Custom)
├── Users
├── Masking Policies
│   ├── Standard Masking Policies
│   └── Tag-Based Masking Policies
├── Row Access Policies
├── Network Policies
└── Tags (for Tag-Based Security)

METADATA
├── Tags
├── Classifications
├── Policy Associations
└── Data Lineage

Policy Translation

PlainID policies are automatically translated to Snowflake native constructs:

PlainID Policy Type Snowflake Implementation Example
Row-Level Security ROW ACCESS POLICY region = current_user_region()
Column Masking MASKING POLICY CASE WHEN role IN ('ANALYST') THEN val ELSE '***' END
Dynamic Groups Role Hierarchies + Policies Mapped to Snowflake role structures with IS_ROLE_IN_SESSION()
Attribute-Based Access Context Functions + Policies current_role(), current_user(), current_account()
Tag-Based Policies TAG + MASKING/ROW ACCESS POLICY SYSTEM$GET_TAG_ON_CURRENT_COLUMN('tag_name')

Tag-Based Security Policies

PlainID POP also discovers and manages Snowflake's tag-based security policies, enabling centralized governance through metadata tagging:

# Example: Tag-Based Masking Policy Discovery
-- Snowflake Tag-Based Policy
CREATE TAG pii_classification;
CREATE MASKING POLICY tag_based_pii_mask AS (val STRING)
RETURNS STRING ->
  CASE 
    WHEN SYSTEM$GET_TAG_ON_CURRENT_COLUMN('pii_classification') = 'SENSITIVE'
      AND CURRENT_ROLE() NOT IN ('DATA_STEWARD')
    THEN '***MASKED***'
    ELSE val
  END;

-- Apply tag to columns
ALTER TABLE customer_data MODIFY COLUMN ssn SET TAG pii_classification = 'SENSITIVE';
ALTER TAG pii_classification SET MASKING POLICY tag_based_pii_mask;

Policy Evaluation Order

Important: When both row access policies and masking policies are applied to the same table:
  1. Row Access Policies are evaluated first - Filters which rows the user can see
  2. Masking Policies are evaluated second - Masks sensitive data in the returned rows
  3. If a column has both a direct masking policy and a tag-based masking policy, the direct policy takes precedence

Learn & Manage Modes

Learn Mode (Discovery)

Initial integration phase where PlainID discovers and maps existing Snowflake policies without making changes.

Purpose: Provides full visibility into existing policies and access patterns before enabling management capabilities.

Learn Mode Activities:

  • Discovers all Snowflake databases, schemas, tables, and views
  • Maps existing row access policies and masking policies
  • Identifies role hierarchies and user assignments
  • Translates Snowflake policies to PlainID policy representation
  • Generates Policy Map visualization
  • Creates audit reports of current access patterns
// Example: Discovered Snowflake Policy
CREATE ROW ACCESS POLICY sales_region_policy
AS (region_column VARCHAR) 
RETURNS BOOLEAN ->
  EXISTS (
    SELECT 1 FROM sales_managers 
    WHERE manager_id = CURRENT_USER() 
    AND region = region_column
  );

// Applied to table using:
ALTER TABLE sales_data 
SET ROW ACCESS POLICY sales_region_policy ON (region);

// Translated to PlainID Policy Structure
{
  "policyName": "sales_region_policy",
  "type": "row_filter",
  "condition": {
    "type": "exists",
    "source": "sales_managers",
    "match": {
      "manager_id": "${user.id}",
      "region": "${row.region_column}"
    }
  }
}

Snowflake POP Setup

Prerequisites

Step 1: Create Snowflake Service Account

-- Create PlainID integration role
CREATE ROLE PLAINID_ORCHESTRATOR;

-- Grant necessary privileges
GRANT USAGE ON WAREHOUSE COMPUTE_WH TO ROLE PLAINID_ORCHESTRATOR;
GRANT USAGE ON ALL DATABASES IN ACCOUNT TO ROLE PLAINID_ORCHESTRATOR;
GRANT USAGE ON ALL SCHEMAS IN DATABASE TO ROLE PLAINID_ORCHESTRATOR;
GRANT SELECT ON ALL TABLES IN SCHEMA TO ROLE PLAINID_ORCHESTRATOR;
GRANT SELECT ON ALL VIEWS IN SCHEMA TO ROLE PLAINID_ORCHESTRATOR;

-- Grant policy management privileges
-- Option 1: Grant on specific schemas
GRANT CREATE ROW ACCESS POLICY ON SCHEMA PUBLIC TO ROLE PLAINID_ORCHESTRATOR;
GRANT CREATE MASKING POLICY ON SCHEMA PUBLIC TO ROLE PLAINID_ORCHESTRATOR;

-- Option 2: Grant on all schemas in database (recommended)
GRANT CREATE ROW ACCESS POLICY ON ALL SCHEMAS IN DATABASE TO ROLE PLAINID_ORCHESTRATOR;
GRANT CREATE MASKING POLICY ON ALL SCHEMAS IN DATABASE TO ROLE PLAINID_ORCHESTRATOR;

-- Grant apply privileges at account level
GRANT APPLY ROW ACCESS POLICY ON ACCOUNT TO ROLE PLAINID_ORCHESTRATOR;
GRANT APPLY MASKING POLICY ON ACCOUNT TO ROLE PLAINID_ORCHESTRATOR;

-- Create service user
CREATE USER PLAINID_SERVICE_USER
  PASSWORD = 'secure_password'
  DEFAULT_ROLE = PLAINID_ORCHESTRATOR;

GRANT ROLE PLAINID_ORCHESTRATOR TO USER PLAINID_SERVICE_USER;

Step 2: Configure POP in PlainID

  1. Navigate to Orchestration Workspace
  2. Click Add Policy Orchestration Point
  3. Select Snowflake from vendor list
  4. Configure connection settings:
{
  "displayName": "Snowflake Production POP",
  "connectionSettings": {
    "account": "mycompany.snowflakecomputing.com",
    "warehouse": "COMPUTE_WH",
    "database": "PRODUCTION",
    "authenticationType": "password",
    "username": "PLAINID_SERVICE_USER",
    "password": "${ENCRYPTED_PASSWORD}"
  },
  "discoveryScope": {
    "databases": ["PRODUCTION", "ANALYTICS"],
    "schemas": ["PUBLIC", "SENSITIVE", "REPORTS"],
    "includeMaskingPolicies": true,
    "includeRowAccessPolicies": true,
    "includeRoles": true
  },
  "syncSettings": {
    "mode": "learn",  // Always start with "learn" mode for initial discovery
    "syncInterval": "hourly",
    "conflictResolution": "plainid_wins"  // Options: "plainid_wins", "snowflake_wins", "manual"
  }
}

Step 3: Test Connection

Click Test Connection to verify PlainID can connect to your Snowflake account and has appropriate permissions. Ensure your warehouse is running before testing.
-- Verify service account permissions in Snowflake
SHOW GRANTS TO ROLE PLAINID_ORCHESTRATOR;
SHOW GRANTS TO USER PLAINID_SERVICE_USER;

-- Test warehouse access
USE WAREHOUSE COMPUTE_WH;
SELECT CURRENT_WAREHOUSE(), CURRENT_USER(), CURRENT_ROLE();

Discovery Process

Automatic Discovery Flow

When a Snowflake POP is created, PlainID automatically initiates a discovery process:

Warehouse Requirement: Discovery operations require an active Snowflake warehouse. Ensure the warehouse specified in the POP configuration is running and the service account has USAGE privileges on it.
1. Scan
Query Snowflake
metadata
2. Map
Create PlainID
objects
3. Translate
Convert policies to
PBAC format
4. Display
Show in Orchestration
Workspace

Discovered Elements Mapping

Snowflake Object PlainID Mapping Workspace
Database.Schema.Table Asset Type Authorization Workspace
Columns Asset Attributes Authorization Workspace
Roles Dynamic Groups Identity Workspace
Users Identities Identity Workspace
Row Access Policies Filter Policies Orchestration Workspace
Masking Policies Masking Policies Orchestration Workspace

Manual Discovery Trigger

# Trigger discovery manually from Orchestration Workspace
1. Navigate to Snowflake POP card
2. Click three dots menu (⋮)
3. Select "Discover Now"
4. Monitor progress in Activity Log

# Discovery API endpoint (for automation)
POST /api/v1/orchestration/pop/{popId}/discover
{
  "scope": "full",  // or "incremental"
  "notify": true
}

Policy Resolution Pattern

How POP Uses Policy Resolution

While POPs primarily manage native vendor policies, they utilize PlainID's Policy Resolution API for complex data access scenarios.

POST /api/v1/policy/resolution

Resolution Request (Snowflake Context)

{
  "identity": {
    "type": "user",
    "id": "snowflake_user@company.com",
    "attributes": {
      "department": "Finance",
      "clearance_level": 2,
      "region": "US_EAST"
    }
  },
  "scope": {
    "name": "snowflake-production"
  },
  "assetType": {
    "type": "table",
    "database": "ANALYTICS",
    "schema": "SALES",
    "table": "REVENUE_DATA"
  },
  "action": "SELECT",
  "context": {
    "warehouse": "COMPUTE_WH",
    "role": "ANALYST",
    "session_id": "sf_session_12345"
  }
}

Resolution Response

{
  "decision": "PERMIT",
  "nativePolicies": {
    "rowAccessPolicy": {
      "name": "finance_region_policy",
      "sql": "region IN ('US_EAST', 'US_CENTRAL')"
    },
    "maskingPolicies": [
      {
        "column": "ssn",
        "policy": "pii_mask_policy",
        "function": "REGEXP_REPLACE(val, '[0-9]', 'X')"
      },
      {
        "column": "salary",
        "policy": "salary_mask_policy", 
        "function": "CASE WHEN current_role() = 'HR' THEN val ELSE 0 END"
      }
    ]
  },
  "deploymentInstructions": {
    "applyRowPolicy": "ALTER TABLE analytics.sales.revenue_data SET ROW ACCESS POLICY finance_region_policy ON (region)",
    "applyMaskingPolicies": [
      "ALTER TABLE analytics.sales.revenue_data MODIFY COLUMN ssn SET MASKING POLICY pii_mask_policy",
      "ALTER TABLE analytics.sales.revenue_data MODIFY COLUMN salary SET MASKING POLICY salary_mask_policy"
    ]
  }
}

Orchestration Workspace

Workspace Overview

The Orchestration Workspace provides centralized visibility and management for all Snowflake policies.

Vendor Policies Tab

Lists all discovered and managed Snowflake policies:

  • Native Snowflake row access policies
  • Masking policies with their conditions
  • Policy creation/modification timestamps
  • Deployment status (synced/pending/conflict)

Objects Tab

Displays discovered Snowflake objects:

  • Databases and schemas hierarchy
  • Tables and views with column details
  • Warehouses and their configurations
  • Object relationships and dependencies

Policy Map Visualization

Graphical representation showing:

  • Identity-to-resource access paths
  • Policy application flow
  • Effective permissions visualization
  • Access pattern analysis

Policy Reconciliation

Side-by-side comparison of:

  • PlainID policies vs Snowflake native policies
  • Pending changes awaiting deployment
  • Conflict detection and resolution
  • Drift analysis between environments

Monitoring & Auditing

POP Activity Monitoring

Example of activity log entry for policy deployment:

# Activity Log Entry Example
{
  "timestamp": "2024-12-15T10:30:00Z",
  "popId": "snowflake-prod-pop",
  "action": "POLICY_DEPLOYED",
  "details": {
    "policyName": "revenue_access_policy",
    "targetObject": "ANALYTICS.SALES.REVENUE",
    "deploymentStatus": "SUCCESS",
    "changedBy": "admin@company.com",
    "approvedBy": "security_team",
    "snowflakeResponse": {
      "status": "APPLIED",
      "affectedRows": 1500000
    }
  }
}

Audit Capabilities

Troubleshooting

IP Allowlisting for PlainID Services

In case customer is restricting access via network policies they should allowlist the following IPs:

Region IP Addresses
US region 3.139.229.73
3.21.70.3
3.141.133.162
EU region 18.203.129.39
52.208.224.64
54.220.132.102
CA region 99.79.30.66
35.182.160.92
15.156.98.158

Common Issues and Resolutions

Issue Symptoms Resolution
Discovery Incomplete Some Snowflake objects not appearing in PlainID Check service account permissions; ensure USAGE grants on all schemas
Policy Deployment Fails Policies created in PlainID not applying to Snowflake Verify APPLY POLICY privileges; check for conflicting native policies
Sync Conflicts Discrepancies between PlainID and Snowflake policies Use Reconciliation view; set conflict resolution strategy
Performance Issues Slow discovery or deployment Optimize discovery scope; use incremental discovery mode
Connection Timeouts Test connection fails Check network policies; verify warehouse is running
Policy Syntax Errors "Cannot ADD policy" error when setting policies Use SET instead of ADD: ALTER TABLE ... SET ROW ACCESS POLICY ...

Debug Mode

# Enable debug logging for POP
{
  "popId": "snowflake-prod-pop",
  "settings": {
    "logging": {
      "level": "DEBUG",
      "includeSnowflakeQueries": true,
      "logPolicyTranslations": true,
      "capturePerformanceMetrics": true
    }
  }
}
Best Practice: Start with Learn Mode to understand your existing Snowflake policies before enabling Manage Mode. This ensures a smooth transition to centralized policy management without disrupting existing access patterns.
Enterprise Edition Requirement: Snowflake Row Access Policies and Dynamic Data Masking require Enterprise Edition or higher. Ensure your Snowflake account meets this requirement before implementing PlainID POP integration.
Documentation Based On: PlainID Platform Documentation & Snowflake Integration Announcement (December 2024)
Pattern: Policy Orchestration Point (POP) for SaaS Authorization Management
Snowflake Features: Row Access Policies, Dynamic Data Masking, Tag-Based Security (Enterprise Edition+)
Support: For production deployments, contact PlainID Technical Support for detailed implementation guidance.