import re
import pandas as pd
# DDLを解析する関数
def parse_ddl(ddl):
tables = {}
# テーブル定義部分を取得する正規表現(CONSTRAINTを含む部分を取得)
table_pattern = re.compile(r'CREATE TABLE (\w+)\s*\((.*?)\)\s*TABLESPACE\s*(\w+);', re.DOTALL)
# カラム定義部分を取得する正規表現(CONSTRAINTを含む部分を除外)
column_pattern = re.compile(
r'(\w+)\s+'
r'(NUMBER\(\d+(?:,\s*\d+)?\)|CHAR\(\d+\)|CLOB|BLOB|TIMESTAMP(?: WITH TIME ZONE)?|\w+)'
r'(?:\s+(NOT NULL|NULL))?'
r'(?:\s+DEFAULT\s+(.*?))?,?',
re.DOTALL
)
# CONSTRAINT定義部分を取得する正規表現
constraint_pattern = re.compile(
r'CONSTRAINT\s+(\w+)\s+(PRIMARY KEY|FOREIGN KEY)\s*\((.*?)\)',
re.DOTALL
)
for table_match in table_pattern.finditer(ddl):
table_name = table_match.group(1) # テーブル名
table_body = table_match.group(2).strip() # テーブル定義部分
tablespace_name = table_match.group(3) # テーブルスペース名
table_info = [] # カラム情報を保持するリスト
primary_keys = [] # プライマリキーのリスト
# CONSTRAINT部分を削除してカラム定義のみを残す
table_body_without_constraints = re.sub(constraint_pattern, '', table_body)
# カラム定義部分を解析
for column_match in column_pattern.finditer(table_body_without_constraints):
col_name = column_match.group(1) # カラム名
col_type = column_match.group(2) # カラムデータタイプ
null_option = column_match.group(3) if column_match.group(3) else '' # NULL/NOT NULLオプション
default_value = column_match.group(4) if column_match.group(4) else '' # デフォルト値
# カラム情報をリストに追加
table_info.append((col_name, col_type, '', null_option, default_value))
# CONSTRAINT定義部分を解析
for constraint_match in constraint_pattern.finditer(table_body):
constraint_name = constraint_match.group(1) # CONSTRAINT名
constraint_type = constraint_match.group(2) # PRIMARY KEY or FOREIGN KEY
constraint_columns = constraint_match.group(3).split(',') # キーに指定されたカラム
if constraint_type == 'PRIMARY KEY':
primary_keys.extend([col.strip() for col in constraint_columns]) # PKのカラムを追加
# カラムリストにプライマリキーの設定を反映
for idx, (col_name, col_type, key_type, null_option, default_value) in enumerate(table_info):
if col_name in primary_keys:
table_info[idx] = (col_name, col_type, '(PK)', null_option, default_value)
# テーブル情報を辞書に追加
tables[table_name] = (tablespace_name, table_info)
return tables
# サンプルDDL
ddl = '''
CREATE TABLE TES_TABLE (
ID NUMBER(6,2) NOT NULL,
NAME CHAR(50),
DESCRIPTION CLOB,
CREATED_AT TIMESTAMP WITH TIME ZONE,
DATA BLOB,
CONSTRAINT PK_TES_TABLE PRIMARY KEY (ID, NAME)
) TABLESPACE TES_SPACE;
'''
# DDLをパースしてテーブル情報を抽出
tables = parse_ddl(ddl)
# 結果を表示
for table_name, (tablespace_name, columns) in tables.items():
print(f'Table: {table_name}, Tablespace: {tablespace_name}')
for column in columns:
print(column)
Register as a new user and use Qiita more conveniently
- You get articles that match your needs
- You can efficiently read back useful information
- You can use dark theme