![[新機能]Snowflake CoCo for Excelがプレビューとなったので、自然言語クエリ・CORTEX セル関数・Intelligent refresh をExcelで試してみた](https://devio2024-media.developers.io/image/upload/f_auto,q_auto,w_3840/f_auto,q_auto/v1790874280/eyecatch/wsr0koxw01pat9lxglvp.png)
[新機能]Snowflake CoCo for Excelがプレビューとなったので、自然言語クエリ・CORTEX セル関数・Intelligent refresh をExcelで試してみた
かわばたです。
2026年11月3日に Snowflake CoCo for Excel と Snowflake CoCo for Google Sheets がプレビューになりました。
本記事では、Excel for Windows に Snowflake CoCo for Excel を入れます。自然言語でのデータ取り込み、PivotTable とグラフ、Semantic View を指定した集計、CORTEX セル関数、Intelligent refresh を順に試します。そのうえでロールを切り替え、Snowflake 側で適用されたマスキングが Excel に取り込む結果にも反映されることを確認します。
Snowflake CoCo for Excel の概要
Snowflake CoCo を Excel の add-in として動かし、ワークシートの横にチャットペインを開く機能です。ペインに日本語で依頼すると、CoCo が SQL を生成して Snowflake で実行し、結果を Excel のテーブルとして書き込みます。PivotTable、グラフ、数式の作成も同じ会話から依頼できます。
データの流れは次のとおりです。
- 利用者が Excel のペインから Snowflake OAuth でサインインする
- CoCo が依頼を解釈し、利用者のロールで SQL を実行する
- 書き込む前に変更内容のプレビューを表示し、利用者が Accept すると反映する
- 書き込んだ値には、生成元のクエリやメトリクスへの引用が付く
実行主体は常にサインインした利用者本人です。クエリには利用者のロールに応じたアクセス制御やデータ保護ポリシーが適用されます。本記事の後半では、ロール切り替えによってマスキング結果が変わることを確認します。
公式ページの表記は「Preview Feature — Open」で、全アカウントで利用できます。Preview Terms of Service の対象なので、本番データでの利用は推奨されていません。課金は他の CoCo と同じトークン消費で、席数単位のライセンスはありません。クエリを実行するウェアハウスのクレジットは別に発生します。
前提条件
- Microsoft 365 の Excel
- Snowflake Cortex と CoCo が有効なアカウント
- cross-region inference は、選んだモデルが自分のリージョンにない場合だけ必要
- security integration を作る ACCOUNTADMIN
- 利用者がサインインに使う非管理者ロール
事前準備
検証用のデータと Semantic View
SNOWFLAKE_SAMPLE_DATA の TPCH_SF1 から、顧客キー 1〜1000 の顧客とその注文を読みやすい列名でコピーします。掲載 SQL では、検証環境のオブジェクト名を一部変更しています(ウェアハウス名など)。作るものは次のとおりです。
| オブジェクト | 内容 |
|---|---|
| COCO_EXCEL_WH | XSMALL のウェアハウス(検証ロール専用) |
| COCO_EXCEL_DB.SALES の REGION / NATION / CUSTOMER / ORDERS | TPC-H のコピー。5 / 25 / 1,000 / 9,894 行 |
| CUSTOMER_FEEDBACK | CORTEX セル関数用の架空の顧客コメント 10 件(日本語 6 件、英語 4 件) |
| MASK_CUSTOMER_PII | 顧客名と電話番号のマスキングポリシー |
| SV_SALES | 注文・顧客・国・地域をつないだ Semantic View |
ウェアハウス、データベース、テーブルの作成 SQL は次のとおりです。CUSTOMER_FEEDBACK の 10 件はすべて架空のコメントです。
検証用のデータ
USE ROLE ACCOUNTADMIN;
CREATE WAREHOUSE IF NOT EXISTS COCO_EXCEL_WH
WAREHOUSE_SIZE = XSMALL AUTO_SUSPEND = 60 AUTO_RESUME = TRUE INITIALLY_SUSPENDED = TRUE;
CREATE DATABASE IF NOT EXISTS COCO_EXCEL_DB;
CREATE SCHEMA IF NOT EXISTS COCO_EXCEL_DB.SALES;
USE WAREHOUSE COCO_EXCEL_WH;
USE SCHEMA COCO_EXCEL_DB.SALES;
CREATE OR REPLACE TABLE REGION AS
SELECT r_regionkey AS region_key, r_name AS region_name
FROM SNOWFLAKE_SAMPLE_DATA.TPCH_SF1.REGION;
CREATE OR REPLACE TABLE NATION AS
SELECT n_nationkey AS nation_key, n_name AS nation_name, n_regionkey AS region_key
FROM SNOWFLAKE_SAMPLE_DATA.TPCH_SF1.NATION;
CREATE OR REPLACE TABLE CUSTOMER AS
SELECT c_custkey AS customer_key, c_name AS customer_name, c_address AS address, c_nationkey AS nation_key,
c_phone AS phone, c_acctbal AS account_balance, c_mktsegment AS market_segment, c_comment AS customer_comment
FROM SNOWFLAKE_SAMPLE_DATA.TPCH_SF1.CUSTOMER
WHERE c_custkey BETWEEN 1 AND 1000;
CREATE OR REPLACE TABLE ORDERS AS
SELECT o_orderkey AS order_key, o_custkey AS customer_key, o_orderstatus AS order_status, o_totalprice AS total_price,
o_orderdate AS order_date, o_orderpriority AS order_priority, o_clerk AS clerk, o_comment AS order_comment
FROM SNOWFLAKE_SAMPLE_DATA.TPCH_SF1.ORDERS
WHERE o_custkey BETWEEN 1 AND 1000;
CREATE OR REPLACE TABLE CUSTOMER_FEEDBACK (
feedback_id NUMBER, customer_key NUMBER, feedback_date DATE, channel VARCHAR(20), feedback_text VARCHAR(1000)
);
INSERT INTO CUSTOMER_FEEDBACK VALUES
(1, 12, '2026-10-01', 'web', '注文から到着まで 2 日で届きました。梱包も丁寧で満足しています。'),
(2, 25, '2026-10-02', 'phone', '請求書の金額が見積と違っていました。確認に時間がかかり不満です。'),
(3, 37, '2026-10-03', 'email', 'サポートの返信は早かったものの、回答内容が質問とずれていました。'),
(4, 41, '2026-10-05', 'web', '新しい管理画面は見やすくなりました。検索が速くなったのが助かります。'),
(5, 58, '2026-10-07', 'phone', '配送が 1 週間遅れ、連絡もありませんでした。改善を求めます。'),
(6, 63, '2026-10-09', 'email', '特に問題はありません。価格が少し高いと感じます。'),
(7, 77, '2026-10-10', 'web', 'The delivery was fast and the product quality exceeded my expectations.'),
(8, 84, '2026-10-12', 'email', 'I was charged twice for the same order and still waiting for the refund.'),
(9, 91, '2026-10-14', 'phone', 'The support agent was polite but could not solve my login issue.'),
(10, 99, '2026-10-15', 'web', 'Average experience. Nothing special, nothing wrong.');
マスキングポリシーは、セッション内で COCO_EXCEL_ANALYST または ACCOUNTADMIN が有効な場合に元の値を返し、それ以外は伏せ字を返します。IS_ROLE_IN_SESSION はロールの継承も含めて判定するので、COCO_EXCEL_ANALYST を継承する SYSADMIN でも元の値になります。今回比較する 2 ロールでは、ANALYST は元の値、VIEWER は伏せ字になります。
CREATE OR REPLACE MASKING POLICY COCO_EXCEL_DB.SALES.MASK_CUSTOMER_PII AS (val STRING) RETURNS STRING ->
CASE
WHEN IS_ROLE_IN_SESSION('COCO_EXCEL_ANALYST') OR IS_ROLE_IN_SESSION('ACCOUNTADMIN') THEN val
ELSE '*** MASKED ***'
END;
ALTER TABLE COCO_EXCEL_DB.SALES.CUSTOMER MODIFY COLUMN customer_name
SET MASKING POLICY COCO_EXCEL_DB.SALES.MASK_CUSTOMER_PII;
ALTER TABLE COCO_EXCEL_DB.SALES.CUSTOMER MODIFY COLUMN phone
SET MASKING POLICY COCO_EXCEL_DB.SALES.MASK_CUSTOMER_PII;
Semantic View は 4 テーブルを RELATIONSHIPS でつなぎ、売上・注文件数・平均注文金額・顧客数をメトリクスにします。日本語のシノニムを付けて、ペインから日本語で指定できるようにしました。
Semantic View
CREATE OR REPLACE SEMANTIC VIEW COCO_EXCEL_DB.SALES.SV_SALES
TABLES (
orders AS COCO_EXCEL_DB.SALES.ORDERS PRIMARY KEY (order_key) WITH SYNONYMS ('注文', 'sales orders'),
customers AS COCO_EXCEL_DB.SALES.CUSTOMER PRIMARY KEY (customer_key) WITH SYNONYMS ('顧客', 'clients'),
nations AS COCO_EXCEL_DB.SALES.NATION PRIMARY KEY (nation_key),
regions AS COCO_EXCEL_DB.SALES.REGION PRIMARY KEY (region_key)
)
RELATIONSHIPS (
orders_to_customers AS orders (customer_key) REFERENCES customers (customer_key),
customers_to_nations AS customers (nation_key) REFERENCES nations (nation_key),
nations_to_regions AS nations (region_key) REFERENCES regions (region_key)
)
FACTS (
orders.order_total AS total_price
)
DIMENSIONS (
orders.order_month AS DATE_TRUNC('MONTH', order_date),
customers.customer_name AS customer_name,
customers.market_segment AS market_segment,
regions.region_name AS region_name
)
METRICS (
orders.total_revenue AS SUM(order_total) WITH SYNONYMS ('売上', 'revenue'),
orders.order_count AS COUNT(order_key) WITH SYNONYMS ('注文件数'),
orders.average_order_value AS AVG(order_total) WITH SYNONYMS ('平均注文金額'),
customers.customer_count AS COUNT(customer_key) WITH SYNONYMS ('顧客数')
);
SEMANTIC_VIEW 構文で直接問い合わせた地域別の値です。Excel 側の結果と照らし合わせる基準にします。

利用者ロール
同じユーザーでロールを切り替えて見え方の差を確認するため、権限が同じで、マスキングポリシーの判定だけが違う 2 ロールを作ります。
| ロール | 顧客名・電話番号 |
|---|---|
| COCO_EXCEL_ANALYST | 生値 |
| COCO_EXCEL_VIEWER | *** MASKED *** |
ロール設定
USE ROLE ACCOUNTADMIN;
SET coco_user = 'ユーザー名'; -- Excel にサインインする Snowflake ユーザー
CREATE ROLE IF NOT EXISTS COCO_EXCEL_ANALYST;
CREATE ROLE IF NOT EXISTS COCO_EXCEL_VIEWER;
GRANT ROLE COCO_EXCEL_ANALYST TO ROLE SYSADMIN;
GRANT ROLE COCO_EXCEL_VIEWER TO ROLE SYSADMIN;
-- CoCo Admin の "All Cortex AI features" 相当。CORTEX セル関数は Cortex REST API を呼ぶため CORTEX_USER を付ける
GRANT DATABASE ROLE SNOWFLAKE.CORTEX_USER TO ROLE COCO_EXCEL_ANALYST;
GRANT DATABASE ROLE SNOWFLAKE.CORTEX_USER TO ROLE COCO_EXCEL_VIEWER;
GRANT USAGE ON WAREHOUSE COCO_EXCEL_WH TO ROLE COCO_EXCEL_ANALYST;
GRANT USAGE ON WAREHOUSE COCO_EXCEL_WH TO ROLE COCO_EXCEL_VIEWER;
GRANT USAGE ON DATABASE COCO_EXCEL_DB TO ROLE COCO_EXCEL_ANALYST;
GRANT USAGE ON DATABASE COCO_EXCEL_DB TO ROLE COCO_EXCEL_VIEWER;
GRANT USAGE ON SCHEMA COCO_EXCEL_DB.SALES TO ROLE COCO_EXCEL_ANALYST;
GRANT USAGE ON SCHEMA COCO_EXCEL_DB.SALES TO ROLE COCO_EXCEL_VIEWER;
GRANT SELECT ON ALL TABLES IN SCHEMA COCO_EXCEL_DB.SALES TO ROLE COCO_EXCEL_ANALYST;
GRANT SELECT ON ALL TABLES IN SCHEMA COCO_EXCEL_DB.SALES TO ROLE COCO_EXCEL_VIEWER;
GRANT SELECT ON SEMANTIC VIEW COCO_EXCEL_DB.SALES.SV_SALES TO ROLE COCO_EXCEL_ANALYST;
GRANT SELECT ON SEMANTIC VIEW COCO_EXCEL_DB.SALES.SV_SALES TO ROLE COCO_EXCEL_VIEWER;
GRANT ROLE COCO_EXCEL_ANALYST TO USER IDENTIFIER($coco_user);
GRANT ROLE COCO_EXCEL_VIEWER TO USER IDENTIFIER($coco_user);
-- ペインにはウェアハウスを選ぶ UI がないため、既定ウェアハウスを検証用にする
ALTER USER IDENTIFIER($coco_user) SET DEFAULT_WAREHOUSE = COCO_EXCEL_WH;
公式ページにはウェアハウスの選び方の記載がなく、refresh は「現在のロールとウェアハウス」で動くとだけ書かれています。利用者の DEFAULT_WAREHOUSE が使われる想定で、検証中は既定ウェアハウスを COCO_EXCEL_WH にします。
OAuth の security integration
add-in は Excel 内のブラウザランタイムで動くため client secret を保持できません。そのため PUBLIC client と PKCE を使う Snowflake OAuth の security integration を、アカウントに 1 つ作ります。
CREATE SECURITY INTEGRATION IF NOT EXISTS COCO_EXCEL_OAUTH
TYPE = OAUTH
OAUTH_CLIENT = CUSTOM
OAUTH_CLIENT_TYPE = 'PUBLIC'
OAUTH_REDIRECT_URI = 'https://ai.snowflake.com/static/excel/oauth/callback.html'
OAUTH_ENFORCE_PKCE = TRUE
OAUTH_ISSUE_REFRESH_TOKENS = TRUE
OAUTH_REFRESH_TOKEN_VALIDITY = 86400
ENABLED = TRUE
COMMENT = 'Snowflake CoCo for Excel / Google Sheets add-in (shared)';
DESCRIBE SECURITY INTEGRATION COCO_EXCEL_OAUTH;
-- 統合名は大文字で指定する。結果の OAUTH_CLIENT_ID を利用者に配る
SELECT SYSTEM$SHOW_OAUTH_CLIENT_SECRETS('COCO_EXCEL_OAUTH');
注意: 統合を CREATE OR REPLACE で作り直すと client ID が変わり、全利用者の refresh token が無効になります。設定変更は ALTER SECURITY INTEGRATION で行い、CREATE は IF NOT EXISTS にしてください。
Excel への add-in 登録
プレビューの現段階では、add-in は manifest のサイドロードで配布されます。Windows では Trusted Add-in Catalog(ネットワーク共有が必須)か、ユーザー単位のレジストリ登録のどちらかを選びます。本記事は共有フォルダが要らないレジストリ登録を使います。
$manifestDir = "$env:LOCALAPPDATA\Snowflake\CoCoExcel"
$manifestPath = "$manifestDir\snowflake-coco-excel.xml"
$developerKey = "HKCU:\Software\Microsoft\Office\16.0\WEF\Developer"
New-Item -Path $manifestDir -ItemType Directory -Force | Out-Null
Invoke-WebRequest -Uri "https://ai.snowflake.com/static/excel/releases/prod/manifest.xml" -OutFile $manifestPath
if (-not (Test-Path $developerKey)) { New-Item -Path $developerKey -Force | Out-Null }
Set-ItemProperty -Path $developerKey -Name "SnowflakeCoCoExcel" -Value $manifestPath
Get-ItemProperty -Path $developerKey
管理者権限は不要で、HKEY_CURRENT_USER に書くので自分の Windows ユーザーにだけ適用されます。Excel は起動時にこのキーを読むため、実行前に Excel のプロセスが残っていないことを確認してください。manifest は登録したパスから毎回読まれるので、ファイルを移動すると add-in が出てこなくなります。
ペインを開いてサインイン
Excel を起動して新しい空のブックを開き、ホーム > アドイン > Developer Add-ins の Snowflake CoCo を選びます。

ペインが右側に開き、サインイン画面が出ます。入力するのは次の 3 つです。
- Account identifier: 組織名-アカウント名の形式(例: MYORG-MYACCOUNT)
- OAuth client ID: 上述で控えた値
- Role: COCO_EXCEL_ANALYST(空欄なら既定ロール)

Sign in with Snowflake を押すとブラウザが開き、Snowflake の認証画面に進みます。

認証が終わると画面にサインインコードが表示されるので、Copy code で控えてペインに貼り付け、Finish sign-in を押します。

【Excel側にコードを入力】


これで Excel から CoCo を使えます。
サインインしたら、Excel で見る前に SQL でロール別の見え方を押さえておきます。
USE SECONDARY ROLES NONE;
USE ROLE COCO_EXCEL_ANALYST;
SELECT customer_key, customer_name, phone, market_segment
FROM COCO_EXCEL_DB.SALES.CUSTOMER
ORDER BY customer_key
LIMIT 3;

USE SECONDARY ROLES NONE;
USE ROLE COCO_EXCEL_VIEWER;
SELECT customer_key, customer_name, phone, market_segment
FROM COCO_EXCEL_DB.SALES.CUSTOMER
ORDER BY customer_key
LIMIT 3;

試してみた
自然言語でデータを読み込む
Excel 上の CoCo に、次のように依頼しました。
COCO_EXCEL_DB.SALES の注文データで、1998 年の注文を注文日・顧客名・市場セグメント・地域名・注文金額の列で読み込んでください

公式ページは、正確な結果のためにデータベース・スキーマ・対象オブジェクトをプロンプトに含めることを勧めています。

取得結果は 820 行で、期待どおりでした。
PivotTable とグラフを作る
続けて次の内容を入力します。
この表から、地域名を行・市場セグメントを列にして注文金額の合計を集計する PivotTable を新しいシートに作ってください。あわせて月別の注文金額合計を棒グラフにしてください

CoCo は Excel の PivotTable オブジェクトとグラフを作ります。CoCo が作る PivotTable はテーブル全体を参照するので、後述の refresh でテーブルが更新されると PivotTable も追従します。固定のセル範囲を参照する PivotTable は追従の対象外です。

Semantic View を指定して集計する
次の内容を入力します。
SV_SALES の Semantic View を使って、地域別の注文件数・売上・平均注文金額を出してください
今回は、生成された SQL が Semantic View に定義したメトリクスを使っていることを確認しました。メトリクスの定義を Snowflake 側で管理できるため、利用者間で集計ロジックを共通化できます。ただし、結果は検索条件や、ロールに適用されるマスキング・行アクセスポリシーによって変わります。

数式を追加して Explain with CoCo で説明させる
次の内容を入力します。
注文金額が 200,000 以上なら「大口」、それ以外は空欄にする列をテーブルの右に追加してください

CoCo は Excel の数式(IF 関数)で列を追加します。
追加された列のセルを右クリックしても Explain with CoCo が出なかったため、数式をテーブル外のセルにコピーして確認しました。add-in が右クリックメニューに足せる項目は通常セルのメニューに限られ、Excel のテーブル内のセルが使う別メニューには表示されないためです。


CORTEX セル関数を使う
新しいシートで CUSTOMER_FEEDBACK を読み込み、CORTEX 関数の数式を入力します。
COCO_EXCEL_DB.SALES.CUSTOMER_FEEDBACK を全列読み込んでください

読み込んだ 10 件のコメントに対して、セルに数式を入れます。feedback_text が E 列、2 行目から始まる前提です。
=CORTEX.SENTIMENT(E2)
=CORTEX.CLASSIFY(E2, "配送", "請求", "サポート", "製品", "その他")
=CORTEX.TRANSLATE(E2, "en")
=CORTEX.FILTER(E2, "顧客は不満を述べていますか")
=CORTEX.SUMMARIZE(E2:E11)

CORTEX 名前空間の関数は 7 つあります。
| 関数 | 内容 |
|---|---|
| CORTEX.ASK(prompt, [context]) | 質問に回答する。context に参照させるテキストを渡せる |
| CORTEX.COMPLETE(prompt) | ASK の短縮形。prompt だけを渡す |
| CORTEX.SUMMARIZE(text) | テキストや範囲を要約する |
| CORTEX.SENTIMENT(text) | -1.0〜1.0 の感情スコアを返す |
| CORTEX.CLASSIFY(text, labels, ...) | 2 つ以上のラベルのいずれかに分類する |
| CORTEX.TRANSLATE(text, targetLanguage, [sourceLanguage]) | 翻訳する |
| CORTEX.FILTER(text, question) | はい / いいえの質問に TRUE / FALSE で答える |
各プロンプトは Cortex REST API 経由でモデルに送られ、ASK と COMPLETE の回答はセルにストリーミングで入ります。関数はペインでサインインしたあとにだけ動きます。未サインインの場合、関数は最大 30 秒間サインインを待ち、完了しなければエラーになります。
Intelligent refresh でテーブルを更新する
CoCo が読み込んだテーブルには、生成元の SQL がブックに保存されます。refresh はこの SQL を再実行し、結果をプレビューしてから反映します。テーブルは Excel のテーブルオブジェクトで特定するので、行を上に挿入したりシート名を変えたりしても追従します。モデルへの依頼は発生せず、クエリの再実行だけなので CoCo のトークンは消費しません。
ペインに次を入力して月別のテーブルを作ります。
COCO_EXCEL_DB.SALES.ORDERS から 1998 年の月別の注文件数と注文金額合計を読み込んでください
【現状の値】

次に Snowflake 側で、1998 年 9 月と 10 月の注文を 3 件 INSERT します。
USE ROLE ACCOUNTADMIN;
USE WAREHOUSE COCO_EXCEL_WH;
INSERT INTO COCO_EXCEL_DB.SALES.ORDERS
(order_key, customer_key, order_status, total_price, order_date, order_priority, clerk, order_comment)
VALUES
(9000001, 1, 'O', 123456.78, '1998-09-01', '1-URGENT', 'Clerk#000000001', 'CoCo refresh test 1'),
(9000002, 2, 'O', 234567.89, '1998-09-15', '2-HIGH', 'Clerk#000000002', 'CoCo refresh test 2'),
(9000003, 3, 'O', 345678.90, '1998-10-01', '3-MEDIUM', 'Clerk#000000003', 'CoCo refresh test 3');

Excel に戻って月別テーブルのシートを開き、ペインに /refresh を入力します。
既定ではアクティブシートの CoCo テーブルすべてが対象で、特定のテーブルだけ更新したいときは、そのテーブルに重なるセルを選んでから実行します。

【更新後の値】

Accept すると、このテーブル全体を参照する PivotTable も一緒に更新されます。固定のセル範囲を参照する PivotTable は更新されません。
ペインヘッダーの More(…)> Settings を開き、This workbook の Refresh when this workbook opens をオンにします。この設定をオンにすると、ブックを開いてサインインした後、同意済みの保存クエリが再実行され、更新内容のプレビューが表示されます。ブックの共有先でも自動的に実行されるわけではなく、受け取った利用者自身の同意が必要です。

ロールを切り替えてマスキングを確認する
ペインヘッダーの More(…)> Settings > Role で COCO_EXCEL_VIEWER を選び、再度サインインしてから次の内容を入力します。
COCO_EXCEL_DB.SALES.CUSTOMER から顧客キー・顧客名・電話番号・市場セグメントを先頭 10 件読み込んでください
マスキングポリシーは Snowflake 側で評価されるので、Excel には伏せ字になった値しか届きません。

続けて Semantic View でも確認します。
SV_SALES の Semantic View を使って、顧客名別の注文件数と売上を上位 3 件出してください
ANALYST では売上の多い順に顧客 3 行が返ります。今回の顧客名別集計では、VIEWER の顧客名がすべて同じ伏せ字になるため、結果は *** MASKED *** の 1 行にまとまりました。

最後に
Snowflake CoCo for Excel を使うと、Excel を離れずに自然言語で Snowflake のデータを取り込めます。Semantic View のメトリクス定義も、Snowflake 側のマスキングも、取り込む結果にそのまま反映されます。
ビジネスユーザーが、使い慣れた Excel で共通の指標に基づいて分析できるのは素晴らしいですね!
この記事が何かの参考になれば幸いです!







