0
0

データマスキングしたテストDBデータを作る

Posted at

はじめに

本番環境から取得したデータを使用する際のデータマスキング についてまとめる

  • 特定の列や値を匿名化または置換。
    • 主要なデータ項目に対し、尤もらしい形式を保持しつつ、匿名化するpython処理

Fakerを使用した簡単な例

Fakerライブラリを使用して、リアルな偽のデータを生成します


import pandas as pd
from faker import Faker

# サンプルの匿名化前のデータ
data = {
    'name': ['山田太郎', '鈴木花子', '佐藤健', '田中美穂'],
    'email': ['yamada@example.com', 'suzuki@example.com', 'sato@example.com', 'tanaka@example.com'],
    'phone': ['090-1234-5678', '080-2345-6789', '070-3456-7890', '090-4567-8901'],
    'address': ['東京都港区1-2-3', '大阪府大阪市中央区1-2-3', '愛知県名古屋市中区1-2-3', '福岡県福岡市中央区1-2-3']
}

df = pd.DataFrame(data)

# Fakerインスタンスの作成
faker = Faker('ja_JP')

# 名前の匿名化
df['name'] = [faker.name() for _ in range(len(df))]

# メールアドレスの匿名化
df['email'] = [faker.email() for _ in range(len(df))]

# 電話番号の匿名化
df['phone'] = [faker.phone_number() for _ in range(len(df))]

# 住所の匿名化
df['address'] = [faker.address() for _ in range(len(df))]

print(df)

出力結果

name                 email           phone                 address
0    小林 裕美  uekimiyuki@example.org  090-4082-8195      山梨県田村市西之園町2-12-12
1    松田 花子    kubonarumi@kudo.net  090-4747-7765  神奈川県越智郡金城町前原西5-10-12
2    岩崎 美咲   ayamiyoshi@example.jp  080-7207-7844       大阪府高松市古市町2-15-5
3  今井 奈央子  maikeyasuhiro@abe.com  090-4119-8787        青森県下高井郡沼村中央4-8

Lambdaで実行する例

PythonスクリプトはAWSのLambda関数として実装し、特定のバケット内のS3から設定ファイルとデータを読み込んで、データを匿名化した後、結果を別のバケットに保存します。


import json
import boto3
import os
from faker import Faker
import pandas as pd
from io import StringIO
from botocore.exceptions import ClientError

def get_env_var(var_name):
    """ 環境変数を取得し、存在しない場合はエラーを発生させる。 """
    try:
        return os.environ[var_name]
    except KeyError:
        print(f"Environment variable {var_name} not found.")
        raise

def read_config_from_s3(bucket, key):
    """ S3から設定ファイルを読み込む。 """
    s3 = boto3.client('s3')
    try:
        response = s3.get_object(Bucket=bucket, Key=key)
        return json.loads(response['Body'].read())
    except ClientError as e:
        print(f"Failed to read config from {bucket}/{key}: {e}")
        raise

def load_data_from_s3(bucket, key):
    """ S3からCSVファイルを読み込み、pandas DataFrameとして返す。 """
    s3 = boto3.client('s3')
    try:
        response = s3.get_object(Bucket=bucket, Key=key)
        return pd.read_csv(response['Body'])
    except ClientError as e:
        print(f"Failed to load data from {bucket}/{key}: {e}")
        raise

def save_data_to_s3(df, bucket, key):
    """ DataFrameをCSVとしてS3に保存する。 """
    csv_buffer = StringIO()
    df.to_csv(csv_buffer, index=False)
    s3_resource = boto3.resource('s3')
    try:
        s3_resource.Object(bucket, key).put(Body=csv_buffer.getvalue())
    except ClientError as e:
        print(f"Failed to save data to {bucket}/{key}: {e}")
        raise

def anonymize_data(df, columns, faker_functions):
    """ DataFrame内の指定された列を匿名化する。 """
    faker = Faker('ja_JP')
    for column, faker_function in zip(columns, faker_functions):
        function, params = faker_function['name'], faker_function.get('parameters', {})
        df[column] = [getattr(faker, function)(**params) for _ in range(len(df))]

def handler(event, context):
    """ Lambdaのメインハンドラ関数。 """
    try:
        input_bucket = get_env_var('INPUT_BUCKET')
        output_bucket = get_env_var('OUTPUT_BUCKET')
        config_key = get_env_var('CONFIG_KEY')

        config = read_config_from_s3(input_bucket, config_key)

        for table in config['tables']:
            df = load_data_from_s3(input_bucket, table['input_file'])
            anonymize_data(df, [col['name'] for col in table['columns']], [col['faker_function'] for col in table['columns']])
            save_data_to_s3(df, output_bucket, table['output_file'])

        return {'statusCode': 200, 'body': json.dumps('Data anonymization completed successfully.')}
    except Exception as e:
        return {'statusCode': 500, 'body': json.dumps(f"An error occurred: {str(e)}")}

nonymization_config.json

{
  "tables": [
    {
      // ユーザーテーブル用の設定
      "input_file": "user_table.csv",  // 入力ファイル名
      "output_file": "anonymized_user_table.csv",  // 匿名化後の出力ファイル名
      "columns": [
        // 各列の匿名化方法の指定
        {"name": "name", "faker_function": "name"},  // 名前
        {"name": "last_name", "faker_function": "last_name"},  // 苗字
        {"name": "first_name", "faker_function": "first_name"},  // 名前
        {"name": "address", "faker_function": "address"},  // 住所
        {"name": "zipcode", "faker_function": "zipcode"},  // 郵便番号
        {"name": "city", "faker_function": "city"},  // 市区町村
        {"name": "prefecture", "faker_function": "prefecture"},  // 都道府県
        {"name": "email", "faker_function": "email"},  // メールアドレス
        {"name": "phone", "faker_function": "phone_number", "parameters": {"formats": "+81-##-####-####"}},  // 電話番号
        {"name": "ssn", "faker_function": "ssn"},  // 社会保険番号
        {"name": "university", "faker_function": "university"},  // 大学名
        {"name": "university_name", "faker_function": "university_name"},  // 大学名
        {"name": "secondary_school", "faker_function": "secondary_school"},  // 中学校
        {"name": "credit_card_number", "faker_function": "credit_card_number", "parameters": {"card_type": "Visa"}},  // クレジットカード番号
        {"name": "credit_card_expiry", "faker_function": "credit_card_expiry", "parameters": {"format": "MM/YY"}},  // クレジットカード有効期限
        {"name": "credit_card_provider", "faker_function": "credit_card_provider"}  // クレジットカード提供者
      ]
    },
    {
      // 販売店マスターテーブル用の設定
      "input_file": "merchant_master_table.csv",  // 入力ファイル名
      "output_file": "anonymized_merchant_master_table.csv",  // 匿名化後の出力ファイル名
      "columns": [
        // 各列の匿名化方法の指定
        {"name": "name", "faker_function": "company"},  // 会社名
        {"name": "email", "faker_function": "company_email"},  // 会社メールアドレス
        {"name": "phone", "faker_function": "phone_number", "parameters": {"formats": "+81-##-####-####"}},  // 会社電話番号
        {"name": "address", "faker_function": "address"},  // 会社住所
        {"name": "credit_card_number", "faker_function": "credit_card_number", "parameters": {"card_type": "Visa"}},  // 会社クレジットカード番号
        {"name": "url", "faker_function": "url"}  // 会社ウェブサイトURL
      ]
    },
    {
      // トランザクションテーブル用の設定
      "input_file": "transaction_table.csv",  // 入力ファイル名
      "output_file": "anonymized_transaction_table.csv",  // 匿名化後の出力ファイル名
      "columns": [
        // 各列の匿名化方法の指定
        {"name": "transaction_id", "faker_function": "uuid4", "parameters": {"version": 4}},  // トランザクションID
        {"name": "transaction_date", "faker_function": "date_between", "parameters": {"start_date": "-5y", "end_date": "today"}}  // トランザクション日付
      ]
    }
  ]
}

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0