Add shared data content to an application package

This topic describes how to add shared data content to an application package.

About Sharing Data Content in an Application Package

The Snowflake Native App Framework allows you to add shared data content to an application package. This data content is shared with the consumers who use your Snowflake Native App. Data content that you share in an application package is shared across all installed instances of the Snowflake Native App.

Shared data content is not versioned, which means that all versions of your Snowflake Native App use the same data. This is different from the application logic, which is versioned.

A consumer cannot access shared content directly. Instead, a provider creates a secure view in the setup script of an application package and grants the consumer access to the secure view. For details, see Expose shared objects to consumers.

Database Objects That Can Be Shared with an Application Package

The Snowflake Native App Framework allows providers to add the following database objects to an application package:

  • Schemas

  • Tables

  • Views

Note

When sharing database objects such as tables and views, you must also share the schema that contains them.

The following restrictions apply to tables and views shared in an application package:

  • Tables cannot have virtual columns, including policies containing Java, Python, or JavaScript code.

  • View definitions or virtual columns associated with them such as policies cannot contain calls to Java, Python, or JavaScript.

  • Shared tables cannot be temporary, volatile, or transient tables.

  • External tables are not supported.

Share data content within an application package

To include data content in an application package, you must grant privileges on the object to be shared with the application package. When you add an object to an application package, by default, the object is private to the application package and not visible when the Snowflake Native App is installed.

To make objects visible to a Snowflake Native App installed from the application package, use the GRANT … TO SHARE IN APPLICATION PACKAGE command as shown in the following example:

CREATE APPLICATION PACKAGE app_package;

GRANT USAGE ON SCHEMA app_package.shared_schema
  TO SHARE IN APPLICATION PACKAGE app_package;
GRANT SELECT ON TABLE app_package.shared_schema.shared_table
  TO SHARE IN APPLICATION PACKAGE app_package;
Copy

In this example, the first command grants the USAGE privilege on the shared_schema schema to the application package, allowing it to be shared with consumers. The second command grants the SELECT privilege on the shared_table table within shared_schema to the application package, allowing consumers to query the table.

After a consumer installs a Snowflake Native App from the application package app_package, they can access the shared_schema and query the shared_table.

Note

When adding a shared object to an application package, you must also share the schema that contains the object.

You can also share views with an application using similar SQL commands.

Reference objects that exist outside the application package

To share a database object that exists outside the application package, you must create a view within the application package to access the object. You cannot share objects outside the application package directly.

Before sharing an object in another database, grant the REFERENCE_USAGE privilege on that database to a share in the application package as shown in the following example:

GRANT REFERENCE_USAGE ON DATABASE other_db
  TO SHARE IN APPLICATION PACKAGE app_pkg;
Copy

After granting the REFERENCE_USAGE on the external database, you must create a view within the application package that references the shared objects shared as shown in the following example:

CREATE VIEW app_pkg.shared_schema.shared_view
  AS SELECT c1, c2, c3, c4
  FROM other_db.other_schema.other_table;
Copy

This command creates a view in the application package that references the a database, table, and schema outside the application package.

After creating the view, you must grant privileges on the schema and view to the application as shown in the following example:

GRANT USAGE ON SCHEMA app_pkg.shared_schema
  TO SHARE IN APPLICATION PACKAGE app_pkg;
GRANT SELECT ON VIEW app_pkg.shared_schema.shared_view
  TO SHARE IN APPLICATION PACKAGE app_pkg;
Copy

Allow access to shared objects in an application

Database objects defined and created in the setup script are directly accessible to a Snowflake Native App after installation. These objects can include functions, procedures, new view definitions, etc.

Database objects outside of the application package can only be accessed by consumers in the installed Snowflake Native App using a secure view defined in the setup script.

The following example shows how to define a view in the setup script.

CREATE VIEW IF NOT EXISTS inst_schema.shared_view
  AS SELECT c1, c2, c3, c4
  FROM shared_schema.shared_view;
Copy

This view accesses content in the shared_schema.shared_view which is shared with the application package as in the example in the previous section.

Note

If you attempt to define a view that directly accesses shared data content, such as a database object external to the application package, Snowflake returns an error.

Expose shared objects to consumers

By default, database objects shared with an application package are not visible to the consumer. To allow consumers to view and access data content, the application package must create a secure view and grant the appropriate privileges.

This approach offers the following advantages:

  • Creating the view in the setup script ensures that changes made directly to the shared objects, such as new columns, are not visible to the version of the Snowflake Native App being installed by the setup script.

  • Creating the view in a versioned schema ensures that each version of the Snowflake Native App contains only the definition of the view for that version. This is important for upgrade scenarios.

To expose shared objects to a consumer, the setup script must include commands to:

  • Install views within a versioned schema in the application package.

  • Grant access to those views to the consumer using an application role.

The following example describes how to use application roles to grant access to shared objects within the setup script of the application package:

CREATE APPLICATION ROLE app_user;

CREATE OR ALTER VERSIONED SCHEMA inst_schema;
GRANT USAGE ON SCHEMA inst_schema
  TO APPLICATION ROLE app_user;

CREATE VIEW IF NOT EXISTS inst_schema.shared_view
  AS SELECT c1, c2, c3, c4
  FROM shared_schema.shared_table;

GRANT SELECT ON VIEW inst_schema.shared_view
  TO APPLICATION ROLE app_user;
Copy

How the Snowflake Native App Framework protects shared content

To protect the privacy and integrity of a provider’s data content, the Snowflake Native App Framework implements the following restriction:

  • Shared objects are read-only for an installed Snowflake Native App.

  • Shared objects are not directly exposed to consumers. Objects are only exposed through a secure view that is installed when the setup script runs when installing the Snowflake Native App.

  • Only the provider can update the shared content.

  • Only the following objects can be shared with instances of an installed Snowflake Native App with certain privileges:

    • Schemas: Only the USAGE privilege can be granted to the shared content of a Snowflake Native App.

    • Tables: Only the SELECT privilege can be granted to the shared content of a Snowflake Native App. Tables with defined policies (row access, masking, tag based, etc.) cannot be shared. Policies can be defined on the objects when they are exposed to the consumers.

    • Views: Only the SELECT privilege can be granted to the shared content of an application package. Views with defined policies, including row access, masking, tag based, etc., can not be shared.

Note

The view, or any views from which they are composed, cannot contain JavaScript, Java, Python, or Scala functions.

Refer to Expose shared objects to consumers for more information.

Restrictions on sharing data content with policies

Providers cannot share tables and views with policies, including masking, row access, and other policy types. This restriction is required because adding or changing policies on the provider side can immediately break running instances of a Snowflake Native App.

Also, some functions that are commonly referenced by policies, such as CURRENT_USER, behave differently in the context of an application package. Although a policy defined by a provider might work correctly in the provider’s account, it might not work when the consumer installs the Snowflake Native App.

Snowflake recommends that you define policies on the proxy views that are specified in the setup script. Defining policies on the proxy views ensures that the definition of the policies cannot be changed after a Snowflake Native App is installed. Defining policies on proxy views also ensures that during upgrades running code continues to use the policies that were applied when the version was created.

Revoke and drop permissions on shared objects

Use caution when revoking permissions on shared objects from an application package or when dropping shared objects. If an installed version of the Snowflake Native App still requires access to those objects, the Snowflake Native App might become unstable or fail.