Menggunakan AWS Glue dengan AWS Lake Formation untuk Akses Tabel Penuh - AWS Glue

Terjemahan disediakan oleh mesin penerjemah. Jika konten terjemahan yang diberikan bertentangan dengan versi bahasa Inggris aslinya, utamakan versi bahasa Inggris.

Menggunakan AWS Glue dengan AWS Lake Formation untuk Akses Tabel Penuh

Pengantar Akses Tabel Penuh

AWS Glue 5.0 mendukung kontrol Akses Tabel Penuh (FTA) di Apache Spark berdasarkan kebijakan Anda yang ditentukan dalam. AWS Lake Formation Fitur ini memungkinkan operasi baca dan tulis dari pekerjaan AWS Glue Spark Anda pada tabel AWS Lake Formation terdaftar ketika peran pekerjaan memiliki akses tabel penuh. FTA sangat ideal untuk kasus penggunaan yang perlu mematuhi peraturan keamanan di tingkat tabel dan mendukung kemampuan Spark termasuk Resilient Distributed Datasets (RDDs), pustaka khusus, dan User Defined Functions () dengan tabel. UDFs AWS Lake Formation

Saat pekerjaan AWS Glue Spark dikonfigurasi untuk Akses Tabel Penuh (FTA), AWS Lake Formation kredensil digunakan untuk data Amazon S3 read/write untuk tabel AWS Lake Formation terdaftar, sedangkan kredenal peran runtime pekerjaan akan digunakan untuk tabel yang tidak terdaftar. read/write AWS Lake Formation Kemampuan ini memungkinkan operasi Data Manipulation Language (DHTML) termasuk CREATE, ALTER, DELETE, UPDATE, dan MERGE INTO pernyataan pada Apache Hive dan Iceberg tabel.

catatan

Tinjau persyaratan Anda dan tentukan apakah Fine-Grained Access Control (FGAC) atau Full Table Access (FTA) sesuai dengan kebutuhan Anda. Hanya satu metode AWS Lake Formation izin yang dapat diaktifkan untuk AWS Glue pekerjaan tertentu. Pekerjaan tidak dapat secara bersamaan menjalankan Full Table Access (FTA) dan Fine-Grained Access Control (FGAC) secara bersamaan.

Cara Kerja Full-Table Access (FTA) AWS Glue

AWS Lake Formation menawarkan dua pendekatan untuk kontrol akses data: Fine-Grained Access Control (FGAC) dan Full Table Access (FTA). FGAC memberikan keamanan yang ditingkatkan melalui pemfilteran kolom, baris, dan tingkat sel, ideal untuk skenario yang memerlukan izin granular. FTA sangat ideal untuk skenario kontrol akses langsung di mana Anda memerlukan izin tingkat tabel. Ini menyederhanakan implementasi dengan menghilangkan kebutuhan untuk mengaktifkan mode akses berbutir halus, meningkatkan kinerja dan mengurangi biaya dengan menghindari driver sistem dan pelaksana sistem, dan mendukung operasi baca dan tulis (termasuk CREATE, ALTER, DELETE, UPDATE, dan MERGE INTO perintah).

Pada AWS Glue 4.0, akses data AWS Lake Formation berbasis bekerja melalui GlueContext kelas, kelas utilitas yang disediakan oleh AWS Glue. Di AWS Glue 5.0, akses data AWS Lake Formation berbasis tersedia melalui Spark SQL asli, Spark DataFrames, dan terus didukung melalui kelas. GlueContext

Menerapkan Akses Tabel Penuh

Langkah 1: Aktifkan Akses Tabel Penuh di AWS Lake Formation

Untuk menggunakan mode Akses Tabel Penuh (FTA), Anda harus mengizinkan mesin kueri pihak ketiga mengakses data tanpa validasi tag sesi IAM. AWS Lake Formation Untuk mengaktifkan, ikuti langkah-langkah dalam Integrasi aplikasi untuk akses tabel penuh.

Langkah 2: Siapkan izin IAM untuk peran runtime pekerjaan

Untuk akses baca atau tulis ke data dasar, selain AWS Lake Formation izin, peran runtime pekerjaan memerlukan izin lakeformation:GetDataAccess IAM. Dengan izin ini, AWS Lake Formation memberikan permintaan kredensil sementara untuk mengakses data.

Berikut ini adalah contoh kebijakan tentang cara memberikan izin IAM untuk mengakses skrip di Amazon S3, mengunggah log ke Amazon S3, izin API AWS Glue , dan izin untuk mengakses. AWS Lake Formation

JSON
{ "Version": "2012-10-17", "Statement": [ { "Sid": "ScriptAccess", "Effect": "Allow", "Action": [ "s3:GetObject" ], "Resource": [ "arn:aws:s3:::amzn-s3-demo-bucket/scripts/*" ] }, { "Sid": "LoggingAccess", "Effect": "Allow", "Action": [ "s3:PutObject" ], "Resource": [ "arn:aws:s3:::amzn-s3-demo-bucket/logs/*" ] }, { "Sid": "GlueCatalogAccess", "Effect": "Allow", "Action": [ "glue:GetDatabase", "glue:GetDatabases", "glue:GetTable", "glue:GetTables", "glue:GetPartition", "glue:GetPartitions", "glue:CreateTable", "glue:UpdateTable" ], "Resource": [ "arn:aws:glue:us-east-1:111122223333:catalog", "arn:aws:glue:us-east-1:111122223333:database/default", "arn:aws:glue:us-east-1:111122223333:table/default/*" ] }, { "Sid": "LakeFormationAccess", "Effect": "Allow", "Action": [ "lakeformation:GetDataAccess" ], "Resource": "*" } ] }

Langkah 2.1 Konfigurasikan AWS Lake Formation izin

AWS Glue Spark jobs yang membaca data dari Amazon S3 AWS Lake Formation memerlukan izin SELECT.

AWS Glue Memicu pekerjaan bahwa write/delete data di Amazon S3 AWS Lake Formation memerlukan SEMUA izin.

AWS Glue Pekerjaan Spark yang berinteraksi dengan katalog AWS Glue Data memerlukan izin DESCRIPTION, ALTER, DROP yang sesuai.

Langkah 3: Inisialisasi sesi Spark untuk Akses Tabel Penuh menggunakan AWS Lake Formation

Untuk mengakses tabel yang terdaftar AWS Lake Formation, konfigurasi berikut perlu disetel selama inisialisasi Spark untuk mengonfigurasi Spark agar menggunakan kredensil. AWS Lake Formation

Untuk mengakses tabel yang terdaftar AWS Lake Formation, Anda perlu mengonfigurasi sesi Spark secara eksplisit untuk menggunakan kredensil. AWS Lake Formation Tambahkan konfigurasi berikut saat menginisialisasi sesi Spark Anda:

from pyspark.sql import SparkSession # Initialize Spark session with Lake Formation configurations spark = SparkSession.builder \ .appName("Lake Formation Full Table Access") \ .config("spark.sql.catalog.glue_catalog", "org.apache.spark.sql.catalog.hive.GlueCatalog") \ .config("spark.sql.catalog.glue_catalog.glue.lakeformation-enabled", "true") \ .config("spark.sql.defaultCatalog", "glue_catalog") \ .getOrCreate()

Konfigurasi kunci:

  • spark.sql.catalog.glue_catalog: Mendaftarkan katalog bernama “glue_catalog” yang menggunakan implementasi GlueCatalog

  • spark.sql.catalog.glue_catalog.glue.lakeformation-enabled: Secara eksplisit mengaktifkan AWS Lake Formation integrasi untuk katalog ini

  • Nama katalog (“glue_catalog” dalam contoh ini) dapat disesuaikan, tetapi harus konsisten di kedua pengaturan konfigurasi

Hive

‐‐conf spark.hadoop.fs.s3.credentialsResolverClass=com.amazonaws.AWS Glue.accesscontrol.AWSLakeFormationCredentialResolver --conf spark.hadoop.fs.s3.useDirectoryHeaderAsFolderObject=true --conf spark.hadoop.fs.s3.folderObject.autoAction.disabled=true --conf spark.sql.catalog.skipLocationValidationOnCreateTable.enabled=true --conf spark.sql.catalog.createDirectoryAfterTable.enabled=true --conf spark.sql.catalog.dropDirectoryBeforeTable.enabled=true

Gunung es

--conf spark.hadoop.fs.s3.credentialsResolverClass=com.amazonaws.AWS Glue.accesscontrol.AWSLakeFormationCredentialResolver --conf spark.hadoop.fs.s3.useDirectoryHeaderAsFolderObject=true --conf spark.hadoop.fs.s3.folderObject.autoAction.disabled=true --conf spark.sql.catalog.skipLocationValidationOnCreateTable.enabled=true --conf spark.sql.catalog.createDirectoryAfterTable.enabled=true --conf spark.sql.catalog.dropDirectoryBeforeTable.enabled=true --conf spark.sql.catalog.<catalog>.AWS Glue.lakeformation-enabled=true
  • spark.hadoop.fs.s3.credentialsResolverClass=com.amazonaws.AWS Glue.accesscontrol.AWSLakeFormationCredentialResolver: Konfigurasikan EMR Filesystem (EMRFS) untuk menggunakan kredensil S3 untuk tabel terdaftar. AWS Lake Formation AWS Lake Formation Jika tabel tidak terdaftar, gunakan kredenal peran runtime pekerjaan.

  • spark.hadoop.fs.s3.useDirectoryHeaderAsFolderObject=truedanspark.hadoop.fs.s3.folderObject.autoAction.disabled=true: Konfigurasikan EMRFS untuk menggunakan aplikasi header tipe konten/x-directory alih-alih akhiran $folder$ saat membuat folder S3. Ini diperlukan saat membaca AWS Lake Formation tabel, karena AWS Lake Formation kredensil tidak mengizinkan membaca folder tabel dengan akhiran $folder$.

  • spark.sql.catalog.skipLocationValidationOnCreateTable.enabled=true: Konfigurasikan Spark untuk melewati validasi kekosongan lokasi tabel sebelum pembuatan. Ini diperlukan untuk tabel AWS Lake Formation terdaftar, karena AWS Lake Formation kredensil untuk memverifikasi lokasi kosong hanya tersedia setelah pembuatan tabel Katalog AWS Glue Data. Tanpa konfigurasi ini, kredenal peran runtime job akan memvalidasi lokasi tabel kosong.

  • spark.sql.catalog.createDirectoryAfterTable.enabled=true: Konfigurasikan Spark untuk membuat folder Amazon S3 setelah pembuatan tabel di metastore Hive. Ini diperlukan untuk tabel AWS Lake Formation terdaftar, karena AWS Lake Formation kredensil untuk membuat folder Amazon S3 hanya tersedia AWS Glue setelah pembuatan tabel Katalog Data.

  • spark.sql.catalog.dropDirectoryBeforeTable.enabled=true: Konfigurasikan Spark untuk menjatuhkan folder Amazon S3 sebelum penghapusan tabel di metastore Hive. Hal ini diperlukan untuk tabel AWS Lake Formation terdaftar, karena AWS Lake Formation kredensional untuk menjatuhkan folder S3 tidak tersedia setelah penghapusan tabel dari Katalog Data. AWS Glue

  • spark.sql.catalog.<catalog>.AWS Glue.lakeformation-enabled=true: Konfigurasikan katalog Iceberg untuk menggunakan AWS Lake Formation kredenal Amazon AWS Lake Formation S3 untuk tabel terdaftar. Jika tabel tidak terdaftar, gunakan kredensil lingkungan default.

Pola Penggunaan

Menggunakan FTA dengan DataFrames

Untuk pengguna yang akrab dengan Spark, DataFrames dapat digunakan dengan Akses Tabel AWS Lake Formation Penuh.

AWS Glue 5.0 menambahkan dukungan Spark asli untuk Lake Formation Full Table Access, menyederhanakan cara Anda bekerja dengan tabel yang dilindungi. Fitur ini memungkinkan AWS Glue 5.0 pekerjaan AWS Glue Spark untuk langsung membaca dan menulis data saat akses tabel penuh diberikan, menghapus batasan yang sebelumnya membatasi operasi Extract, Transform, and Load (ETL) tertentu. Anda sekarang dapat memanfaatkan kemampuan Spark tingkat lanjut termasuk Resilient Distributed Datasets (RDDs), pustaka kustom, dan User Defined Functions () dengan tabel. UDFs AWS Lake Formation

Native Spark FTA di 5.0 AWS Glue

AWS Glue 5.0 mendukung kontrol akses tabel penuh (FTA) di Apache Spark berdasarkan kebijakan yang Anda tentukan. AWS Lake Formation Tingkat kontrol ini sangat ideal untuk kasus penggunaan yang perlu mematuhi peraturan keamanan di tingkat tabel.

Contoh Tabel Gunung Es Apache

from pyspark.sql import SparkSession catalog_name = "spark_catalog" aws_region = "us-east-1" aws_account_id = "123456789012" warehouse_path = "s3://amzn-s3-demo-bucket/warehouse/" spark = SparkSession.builder \ .config("spark.sql.extensions","org.apache.iceberg.spark.extensions.IcebergSparkSessionExtensions") \ .config(f"spark.sql.catalog.{catalog_name}", "org.apache.iceberg.spark.SparkSessionCatalog") \ .config(f"spark.sql.catalog.{catalog_name}.warehouse", f"{warehouse_path}") \ .config(f"spark.sql.catalog.{catalog_name}.client.region",f"{aws_region}") \ .config(f"spark.sql.catalog.{catalog_name}.glue.account-id",f"{aws_account_id}") \ .config(f"spark.sql.catalog.{catalog_name}.glue.lakeformation-enabled","true") \ .config(f"spark.sql.catalog.dropDirectoryBeforeTable.enabled", "true") \ .config(f"spark.sql.catalog.{catalog_name}.catalog-impl", "org.apache.iceberg.aws.glue.GlueCatalog") \ .config(f"spark.sql.catalog.{catalog_name}.io-impl", "org.apache.iceberg.aws.s3.S3FileIO") \ .config("spark.sql.defaultCatalog", catalog_name) \ # Add this line .getOrCreate() database_name = "your_database" table_name = "your_table" df = spark.sql(f"select * from {database_name}.{table_name}") df.show()

Izin IAM yang Diperlukan

Peran eksekusi AWS Glue pekerjaan Anda harus memiliki:

{ "Action": "lakeformation:GetDataAccess", "Resource": "*", "Effect": "Allow" }

Ditambah izin akses S3 yang sesuai untuk lokasi data Anda.

Konfigurasi Formasi Danau

Sebelum menggunakan Spark FTA asli di AWS Glue 5.0:

  1. Izinkan mesin kueri pihak ketiga mengakses data tanpa validasi tag sesi IAM AWS Lake Formation

  2. Berikan izin tabel yang sesuai untuk peran eksekusi AWS Glue pekerjaan Anda melalui konsol AWS Lake Formation

  3. Konfigurasikan sesi Spark Anda dengan parameter yang diperlukan yang ditunjukkan pada contoh di atas

Menggunakan FTA dengan DynamicFrames

AWS Glue asli DynamicFrames dapat digunakan dengan Akses Tabel AWS Lake Formation Penuh untuk operasi ETL yang dioptimalkan. Full Table Access (FTA) menyediakan model keamanan yang memberikan izin pada tingkat tabel, memungkinkan pemrosesan data lebih cepat dibandingkan dengan Fine-Grained Access Control (FGAC) karena melewati overhead pemeriksaan izin tingkat baris dan kolom. Pendekatan ini berguna ketika Anda perlu memproses seluruh tabel dan izin tingkat tabel memenuhi persyaratan keamanan Anda.

Di AWS Glue 4.0, DynamicFrames dengan FTA diperlukan GlueContext konfigurasi khusus. Sementara DynamicFrame kode AWS Glue 4.0 yang ada dengan FTA akan terus bekerja di AWS Glue 5.0, versi yang lebih baru juga menawarkan dukungan Spark FTA asli dengan fleksibilitas yang lebih besar. Untuk pengembangan baru, pertimbangkan untuk menggunakan pendekatan Spark asli yang dijelaskan di DataFrames bagian ini, terutama jika Anda memerlukan kemampuan tambahan seperti Resilient Distributed Datasets (RDDs), pustaka kustom, dan User Defined Functions () dengan tabel. UDFs AWS Lake Formation

Izin yang Diperlukan

Peran IAM yang menjalankan pekerjaan Glue Anda harus memiliki:

  • Izin lakeformation:GetDataAccess

  • Izin tabel Lake Formation yang sesuai diberikan melalui konsol Lake Formation

Contoh DynamicFrame Implementasi di AWS Glue 5.0

from awsglue.context import GlueContext from pyspark.context import SparkContext # Initialize Glue context sc = SparkContext() glueContext = GlueContext(sc) # Configure catalog for Iceberg tables catalog_name = "glue_catalog" aws_region = "us-east-1" aws_account_id = "123456789012" warehouse_path = "s3://amzn-s3-demo-bucket/warehouse/" spark = glueContext.spark_session spark.conf.set(f"spark.sql.catalog.{catalog_name}", "org.apache.iceberg.spark.SparkCatalog") spark.conf.set(f"spark.sql.catalog.{catalog_name}.warehouse", f"{warehouse_path}") spark.conf.set(f"spark.sql.catalog.{catalog_name}.catalog-impl", "org.apache.iceberg.aws.glue.GlueCatalog") spark.conf.set(f"spark.sql.catalog.{catalog_name}.io-impl", "org.apache.iceberg.aws.s3.S3FileIO") spark.conf.set(f"spark.sql.catalog.{catalog_name}.glue.lakeformation-enabled","true") spark.conf.set(f"spark.sql.catalog.{catalog_name}.client.region",f"{aws_region}") spark.conf.set(f"spark.sql.catalog.{catalog_name}.glue.id", f"{aws_account_id}") # Read Lake Formation-protected table with DynamicFrame df = glueContext.create_data_frame.from_catalog( database="your_database", table_name="your_table" )

Konfigurasi Tambahan

Konfigurasikan mode akses tabel penuh di AWS Glue Studio notebook

Untuk mengakses tabel AWS Lake Formation terdaftar dari sesi Spark interaktif di AWS Glue Studio buku catatan, Anda harus menggunakan mode izin kompatibilitas. Gunakan perintah %%configure ajaib untuk mengatur konfigurasi Spark Anda sebelum memulai sesi interaktif Anda. Konfigurasi ini harus menjadi perintah pertama di buku catatan Anda, karena tidak dapat diterapkan setelah sesi dimulai. Pilih konfigurasi berdasarkan jenis tabel Anda:

Untuk tabel Hive

%%configure --conf spark.hadoop.fs.s3.credentialsResolverClass=com.amazonaws.glue.accesscontrol.AWSLakeFormationCredentialResolver --conf spark.hadoop.fs.s3.useDirectoryHeaderAsFolderObject=true --conf spark.hadoop.fs.s3.folderObject.autoAction.disabled=true --conf spark.sql.catalog.skipLocationValidationOnCreateTable.enabled=true --conf spark.sql.catalog.createDirectoryAfterTable.enabled=true --conf spark.sql.catalog.dropDirectoryBeforeTable.enabled=true

Untuk tabel Iceberg

%%configure --conf spark.hadoop.fs.s3.credentialsResolverClass=com.amazonaws.glue.accesscontrol.AWSLakeFormationCredentialResolver --conf spark.hadoop.fs.s3.useDirectoryHeaderAsFolderObject=true --conf spark.hadoop.fs.s3.folderObject.autoAction.disabled=true --conf spark.sql.catalog.skipLocationValidationOnCreateTable.enabled=true --conf spark.sql.catalog.createDirectoryAfterTable.enabled=true --conf spark.sql.catalog.dropDirectoryBeforeTable.enabled=true --conf spark.sql.catalog.glue_catalog.glue.lakeformation-enabled=true --conf spark.sql.catalog.glue_catalog.warehouse=s3://example-s3-bucket_DATA_LOCATION --conf spark.sql.catalog.glue_catalog.catalog-impl=org.apache.iceberg.aws.glue.GlueCatalog --conf spark.sql.catalog.glue_catalog.io-impl=org.apache.iceberg.aws.s3.S3FileIO --conf spark.sql.catalog.glue_catalog.glue.account-id=ACCOUNT_ID --conf spark.sql.catalog.glue_catalog.glue.region=REGION

Ganti placeholder:

  • S3_DATA_LOKASI: s3://amzn-s3-demo-bucket

  • WILAYAH: AWS Region (e.g., us-east-1)

  • AKUN_ID: Your AWS Account ID

catatan

Anda harus mengatur konfigurasi ini sebelum menjalankan operasi Spark apa pun di buku catatan Anda.

Operasi yang Didukung

Operasi ini akan menggunakan AWS Lake Formation kredensil untuk mengakses data tabel.

catatan

Saat mengaktifkan AWS Lake Formation:

  • Untuk FTA: Aktifkan konfigurasi Spark spark.sql.catalog.{catalog_name}.glue.lakeformation-enabled

  • CREATE TABLE

  • ALTER TABLE

  • MASUKKAN KE DALAM

  • MASUKKAN TIMPA

  • SELECT

  • UPDATE

  • BERGABUNG MENJADI

  • DELETE FROM

  • MENGANALISIS TABEL

  • MEJA PERBAIKAN

  • MEJA DROP

  • Percikan kueri sumber data

  • Sumber data Spark menulis

catatan

Operasi yang tidak tercantum di atas akan terus menggunakan izin IAM untuk mengakses data tabel.

Migrasi dari AWS Glue 4.0 ke AWS Glue 5.0 FTA

Saat bermigrasi dari AWS Glue 4.0 GlueContext FTA ke AWS Glue 5.0 Spark FTA asli:

  1. Izinkan mesin kueri pihak ketiga mengakses data tanpa validasi tag sesi IAM di. AWS Lake Formation IkutiLangkah 1: Aktifkan Akses Tabel Penuh di AWS Lake Formation.

  2. Anda tidak perlu mengubah peran runtime pekerjaan. Namun, verifikasi bahwa peran eksekusi AWS Glue pekerjaan memiliki lakeformation: izin GetDataAccess IAM.

  3. Ubah konfigurasi sesi percikan dalam skrip. Pastikan konfigurasi percikan berikut ada:

    --conf spark.sql.catalog.spark_catalog=org.apache.iceberg.spark.SparkSessionCatalog --conf spark.sql.catalog.spark_catalog.warehouse=s3://<bucket-name>/warehouse/ --conf spark.sql.catalog.spark_catalog.client.region=<REGION> --conf spark.sql.catalog.spark_catalog.glue.account-id=ACCOUNT_ID --conf spark.sql.catalog.spark_catalog.glue.lakeformation-enabled=true --conf spark.sql.catalog.dropDirectoryBeforeTable.enabled=true
  4. Perbarui skrip seperti GlueContext DataFrames yang diubah menjadi percikan DataFrames asli.

  5. Perbarui AWS Glue pekerjaan Anda untuk menggunakan AWS Glue 5.0

Pertimbangan dan batasan

  • Jika tabel Hive dibuat menggunakan pekerjaan yang tidak mengaktifkan akses tabel penuh, dan tidak ada catatan yang disisipkan, pembacaan atau penulisan berikutnya dari pekerjaan dengan akses tabel penuh akan gagal. Ini karena AWS Glue Spark tanpa akses tabel penuh menambahkan akhiran $folder$ ke nama folder tabel. Untuk mengatasi ini, Anda dapat:

    • Masukkan setidaknya satu baris ke dalam tabel dari pekerjaan yang tidak mengaktifkan FTA.

    • Konfigurasikan pekerjaan yang tidak mengaktifkan FTA untuk tidak menggunakan akhiran $folder$ dalam nama folder di S3. Ini dapat dicapai dengan mengatur konfigurasi spark.hadoop.fs.s3.useDirectoryHeaderAsFolderObject=true Spark.

    • Buat folder Amazon S3 di lokasi tabel s3://path/to/table/table_name menggunakan konsol Amazon S3 atau Amazon S3 CLI.

  • Akses Tabel Penuh bekerja secara eksklusif dengan EMR Filesystem (EMRFS). Sistem file S3A tidak kompatibel.

  • Akses Tabel Penuh didukung untuk tabel Hive dan Iceberg. Support untuk tabel Hudi dan Delta belum ditambahkan.

  • Pekerjaan yang mereferensikan tabel dengan aturan AWS Lake Formation Fine-Grained Access Control (FGAC) atau AWS Glue Tampilan Katalog Data akan gagal. Untuk menanyakan tabel dengan aturan FGAC atau Tampilan Katalog AWS Glue Data, Anda perlu menggunakan mode FGAC. Anda dapat mengaktifkan mode FGAC dengan mengikuti langkah-langkah yang diuraikan dalam AWS dokumentasi: Menggunakan AWS Glue dengan AWS Lake Formation untuk kontrol akses berbutir halus.

  • Akses tabel penuh tidak mendukung Spark Streaming.

  • Tidak dapat digunakan bersamaan dengan FGAC.