Publish-RjRbFilesToStorageContainer

Azure Automation Runbook からローカル ファイルを Azure Storage コンテナーにアップロードし、期限付き SAS ダウンロード リンクを返します。

概要

Publish-RjRbFilesToStorageContainer は、RealmJoin のレポート実行ブックから Azure Blob Storage を介してレポート ファイル(CSV、XLSX、ZIP、…)を配信するための標準ヘルパーです。1つ以上のローカル ファイルを対象コンテナーにアップロードし、各 blob に対して時間制限付きの SAS ダウンロード リンクを返します。これは、レポートのメール、Teams メッセージ、または実行ブックの出力に含めるのに適しています。

主な特長:

  • なし Az.Storage への依存 — blob 操作は Azure Storage REST API に対して直接実行されます(コンテナーの作成、アップロード、SAS token の生成)。これにより、次の間でよく知られているアセンブリ競合が解消されます Az.StorageExchangeOnlineManagement これは、混在したレポート実行ブックで表面化します。

  • 自己接続 — もし Az コンテキストがアクティブでない場合、関数は透過的に次を呼び出します: Connect-RjRbAzAccount。オプションの -SubscriptionId により、ストレージ操作の前にコンテキストが切り替わります。

  • コンテナーの自動作成 — 対象コンテナーがまだ存在しない場合は、その場で作成されます。既存のコンテナー(HTTP 409)は成功として扱われます。

  • HttpClient ベースのアップロード — 次を使用します: System.Net.Http.HttpClient を直接使用します。これは、Azure Automation の Invoke-RestMethod インターセプターが必要なカスタム ヘッダー(x-ms-blob-type)をバイナリ本文から取り除いてしまうためです。

  • 読み取り専用 SAS リンク — 返される各 URL は storage account キーで署名され、単一の blob にスコープされ、HTTPS のみで、次の期間有効です: LinkExpiryDays 日間(既定 6 日)。

一般的な実行ブックで使用される中央のストレージ設定(リソース グループ、アカウント名、有効期限日数、blob 名プレフィックス)は RealmJoin のカスタマイズ JSON にあり、次に記載されています: Runbook Report Settings — Storage Account 配信。このドキュメントでは、実行ブックから関数を呼び出す方法に焦点を当てます。

前提条件

Azure Storage Account

既存の Azure Storage Account(汎用 v2 推奨)が必要です。対象コンテナーは事前に存在している必要はありません。初回使用時に自動的に作成されます。

Storage Account に対する Azure RBAC

Automation Account のマネージド ID(または実行ブックで使用する Service Principal)は、Storage Account またはそのリソース グループに対して次の権限が必要です:

アクション
必要用途

Microsoft.Storage/storageAccounts/read

Storage Account の読み取り

Microsoft.Storage/storageAccounts/listKeys/action

SharedKey 署名と SAS 生成に使用するアカウント キーの取得

組み込みロールの Storage Account Contributor の両方をカバーします。 Storage Blob Data Contributor だけでは 不十分 です。関数は AAD ベースの blob 操作ではなく、アカウント キーで要求に署名するためです。

モジュール接続

この関数には Az.Accounts モジュールが実行ブック環境で必要です(Get-AzContext, Set-AzContext, Connect-AzAccount, Invoke-AzRestMethod)。利用側の実行ブックで明示的に宣言してください:

もし Az.Accounts 実行時に利用できない場合、関数は明確なエラー メッセージで即座に失敗します — まず次を確認します: Get-AzContext 事前に確認し、次をスローします: "Publish-RjRbFilesToStorageContainer には 'Az.Accounts' モジュールが必要です。呼び出し元の実行ブックに #Requires -Modules @{ModuleName = 'Az.Accounts'; ModuleVersion = '5.3.4'} を追加してください。" Azure 呼び出しを行う前に。

なぜ Az.AccountsRequiredModules のエントリとして RealmJoin.RunbookHelper.psd1?

Az.Accounts は意図的に次の下でのみ列挙されています: ExternalModuleDependencies (情報提供用)および 不十分 次の下で RequiredModules (次で強制: Import-Module 時):

  • 使った分だけ支払う。 多くの実行ブックは Graph ベースのヘルパーだけを利用します(例: Send-RjReportEmail を使用せずに -UseNativeGraphRequest、または Invoke-RjRbRestMethodGraph)で、Az.* cmdlet には一切触れません。 Az.AccountsRequiredModules 利用側のすべての実行ブックに、そのコード パスで必要ない場合でもモジュールの同梱を強制してしまい、Azure Automation のコールド スタート時間が目に見えて増加します。

  • バージョンの衝突を避ける。 厳しい RequiredModules 制約はインポート時の自動解決を引き起こし、特定の Az.Accounts バージョンを引き込んで、実行ブック自体が固定しているものと競合する可能性があります(Az.* サブモジュールは特にバージョンに敏感です)。実行ブックに独自の #Requires -Modules を宣言させることで、バージョン選択を呼び出し側に残せます。

  • 実行ブックごとの権限。 Azure Automation では、モジュール要件を宣言する標準的な場所は実行ブック レベルの #Requiresであり、ヘルパー モジュール レベルではありません。ヘルパー モジュールは、依存関係を(次を通じて)情報として示し ExternalModuleDependencies マニフェスト内で)および上記の実行時チェックを通じて示すため、誤設定はバージョン競合を黙って隠すのではなく、実行可能なメッセージとともに明示的に失敗します。

Az.Storage不十分 必要であり、上で述べたアセンブリ競合を避けるため、同じ実行ブックでインポートしないでください。

クイック スタート

最小限の呼び出しには、ローカル ファイル パス、コンテナー名、リソース グループ、Storage Account 名が必要です:

これにより devices.csv 次の reports コンテナーに stcontosoreports にアップロードし、blob 名、SAS の有効期限タイムスタンプ、そして既定の 6 日間有効な、すぐ共有できるダウンロード URL を含む 1 つのオブジェクトを返します。

パラメーター

必須

パラメーター
説明

FilePaths

string[]

アップロードする 1 つ以上のローカル ファイル パス。各パスは既存のファイル(Test-Path -PathType Leaf)を指している必要があります。いずれかのエントリが欠落している場合、関数は事前にスローします。

ContainerName

string

対象 blob コンテナー。存在しない場合は自動的に作成されます。Azure のコンテナー命名規則(小文字、3〜63 文字、英数字 + ハイフン)に従う必要があります。コンテナー名は 実行ブックごとの 決定であり、中央設定ではなく実行ブック内で設定されます。

ResourceGroupName

string

Storage Account を含むリソース グループ。通常は次の中央設定に接続されます: RJReport.AzureStorage.ResourceGroup.

StorageAccountName

string

Azure Storage Account の名前。通常は次の中央設定に接続されます: RJReport.AzureStorage.StorageAccountName.

オプション

パラメーター
既定
説明

SubscriptionId

string

現在のコンテキスト

Storage Account をホストする Azure サブスクリプション。指定された場合、 Set-AzContext -Subscription が、いずれのストレージ操作よりも前に呼び出されます。省略すると現在の Az コンテキストが使用されます。

LinkExpiryDays

int

6

SAS リンクの有効期間(日)。次で検証されます: [1, 3650]。同じ有効期限タイムスタンプが 1 回の呼び出しですべての blob に適用されます。通常は次の中央設定に接続されます: RJReport.AzureStorage.LinkExpiryDays.

AddBlobNamePrefix

bool

$false

〜の場合 $true、blob 名の先頭に次が付加されます: yyyyMMdd-HHmmss- (次のタイムスタンプ: Get-Date アップロード時のもの)を付け、繰り返し実行時の上書きを防ぎます。元のファイル名は接尾辞として保持されます。

注: これらのパラメーターと中央の RealmJoin カスタマイズ JSON との対応(推奨既定値を含む)は次に記載されています: Runbook Report Settings — Storage Account 配信.

使用例

推奨される実行ブック パターン

これはレポート実行ブックで使用される標準パターンです。ストレージ構成は、中央の RealmJoin カスタマイズから次を介して取得されます: Use-RJInterface -Type Setting、コンテナーは実行ブックごとにハードコードされ、構成が欠けていると実行ブックは実行可能なメッセージとともに中止されます:

このパターンを採用する際に維持するとよい慣例がいくつかあります:

  • 3 つの中央設定(ResourceGroup, StorageAccountName, LinkExpiryDays)は実行ブック パラメーターとして公開され、次を介して接続されます: Use-RJInterface -Type Setting、ただし通常は 非表示 実行ブック カスタマイズ内で("Hide": true)そのため、エンド ユーザーには表示されません。

  • コンテナー名は実行ブックごとにハードコードされます(多くの場合、 param の既定値を使って)ライフサイクル ポリシーとアクセス制御をエクスポート種別ごとに調整できるようにします。これは意図的に 不十分 中央設定ではありません。

  • AddBlobNamePrefix $true は、毎回固定ファイル名を生成する定期エクスポートに対する安全な既定です。

  • 関数は、実行ブックのメインの try { … } catch { throw $_ } finally { Disconnect-AzAccount … } ブロック内で呼び出されるため、部分的な失敗は Automation ジョブに伝播し、成功時でも Az コンテキストが解放されます。

1 回の呼び出しで複数ファイル

FilePaths は配列を受け取ります。各ファイルは順番にアップロードされ、アップロードされた各 blob ごとに結果オブジェクトが返されます。

カスタム リンク有効期間と明示的なサブスクリプション

実行ブックが複数のサブスクリプションにまたがる場合、または下流の受信者が 6 日の既定より長い期間を必要とする場合に便利です。

次と組み合わせると Send-RjReportEmail

一般的なパターンは、容量の大きいデータを blob storage にアップロードし、SAS リンクをレポート メールに埋め込んで、メールを Graph の 4 MB sendMail 制限より十分下に保つことです:

次を参照: Send-RjReportEmail このパターンのメール側について。

動作とエラー処理

事前のファイル検証

Azure 呼び出しを行う前に、関数は次を順に確認し: FilePaths 次をスローします: ファイル '<path>' が見つかりませんでした。 最初に見つからないエントリに対して。これにより、呼び出し側の টাইपोによる部分的なアップロードを防ぎます。

Azure コンテキストの解決

Get-AzContext が最初に確認されます。コンテキストがない場合、またはコンテキストに アカウント (例: 新しい実行ブック実行)の場合、関数は次を呼び出します: Connect-RjRbAzAccount マネージド ID を認証するために。もし -SubscriptionId が指定された場合、 Set-AzContext -Subscription が次に呼び出されます。

コンテナーの作成

コンテナーは次を使って作成されます: PUT …?restype=container 要求:

  • HTTP 201 — コンテナーが作成されました。

  • HTTP 409 — コンテナーは既に存在します。成功として扱われます。

  • その他のステータス — 関数は次をスローします: コンテナーの作成に失敗しました(<status>): <body>.

アップロード失敗

各ファイルは次を介してアップロードされます: HttpClient.SendAsync。成功以外のステータスでは呼び出しが終了し、次が返されます: Blob のアップロードに失敗しました(<status>): <body>Azure Storage から返された生のエラーを含みます。同じ呼び出しで既にアップロード済みのそれ以前のファイルは Storage Account に残ります。部分的なアップロードが許容できない場合、呼び出し側は try/catch でラップし、クリーンアップを実行するとよいでしょう。

キー取得失敗

Invoke-AzRestMethod を使用して ARM の listKeys エンドポイントを呼び出します。応答ステータスが 200 以外の場合、関数は次をスローします: リソース グループ '<rg>' 内の '<account>' の Storage Account キーの取得に失敗しました。ステータス: <status>。一般的な原因は次のとおりです:

  • 不足している Microsoft.Storage/storageAccounts/listKeys/action マネージド ID 上の権限。

  • サブスクリプション コンテキストの誤り(次と組み合わせる: -SubscriptionId).

  • 次の টাইपो StorageAccountName または ResourceGroupName.

  • 中央設定が RJReport.AzureStorage.ResourceGroup / RJReport.AzureStorage.StorageAccountName 構成されていません — 次を参照: Runbook Report Settings.

SAS token の特性

生成される token は次を使用します:

  • sv=2023-11-03 (署名されたバージョン)

  • sr=b (blob スコープ)

  • sp=r (読み取り専用)

  • spr=https (HTTPS のみ)

  • st 5 分前に設定し(時計ずれ許容)、さらに seLinkExpiryDays 呼び出し時点から。

トークンは Storage Account キーで署名されます。 リンクを知っている人なら、有効期限まで blob をダウンロードできます — 返された SAS URL は機密情報として扱ってください。

出力

各アップロード成功時に次のものが生成されます: PSCustomObject 次のプロパティを持ちます:

プロパティ
説明

BlobName

string

コンテナー内の最終的な blob 名。タイムスタンプのプレフィックスがある場合はそれも含まれます。 AddBlobNamePrefix$true.

EndTime

datetime

ローカル時間での SAS の有効期限(URL 内には UTC としてもエンコードされます)。

SASLink

string

埋め込みの SAS Token を含む完全修飾された HTTPS ダウンロード URL。

結果は次の順序で返されます: FilePaths。単一ファイルをアップロードする場合でも戻り値は配列です — インデックスで参照してください($results[0])または次で繰り返してください foreach スカラーとして扱うのではなく。

関連項目

最終更新

役に立ちましたか?