miniob数据库——建表逻辑的源码解析

创建表的逻辑

1.ExecuteStage::handle_request函数处理一个request请求,通过sql解析,发现这是一个创建表的sql语句,进入do_create_table函数

2.do_create_table函数

定义一个CreateTable变量,通过输入的sql语句得到创建表的名字、字段数量、字段类型数据。

获取sql语句的SessionEvent变量

获取当前的数据库类型(Db)

进入db->create_table函数,传入创建表的名字、字段数量、字段类型

3.db->create_table函数

参数检查,判断数据表名字是否重复

获取当前数据库存放的位置,构造出新创建表的元数据存储路径

建立一个新的table变量

调用table->create函数,传入元数据存储路径,数据表名字,数据库的路径,字段数和字段类型

函数结束之后,将当前表名加入到记录已打开数据表的映射中

4.table->create函数

(1)再次进行参数检查,检查数据表名字,检查字段数,字段类型

(2)调用

int fd = ::open(path, O_WRONLY | O_CREAT | O_EXCL | O_CLOEXEC, 0600);

打开元数据存储路径,

O_WRONLY 只写模式

O_CREAT 如果指定文件不存在,则创建这个文件

O_EXCL 如果要创建的文件已存在,则返回 -1,并且修改 errno 的值

O_CLOEXEC,当调用exec成功后,文件会自动关闭

0600表示创建的文件可读可写。

所以实际的意思是,根据传入的元数据存储位置,创建一个可读可写的文件(如果已存在,返回-1)

(3)调用

table_meta_.init(name, attribute_count, attributes))

首先进行参数检查

如果sys_fields_为空的话,初始化sys_fields_

fields进行拓展,拓展到sys_fields_的长度加上当前创建表的字段数量,然后将前面sys_fields_中的变量赋值到fields_中,调用

fields_[i + sys_fields_.size()].init(attr_info.name, attr_info.type, field_offset, attr_info.length, true);

将新创建表的字段属性进行初始化加入到fields_中

增加偏移量field_offset

设置record_size_ = field_offset;

(4)调用

std::fstream fs;
fs.open(path, std::ios_base::out | std::ios_base::binary);

打开元数据文件,并且通过二进制的方式进行写操作

(5)调用

table_meta_.serialize(fs);

将元数据进行序列化然后写入文件

(6)

通过数据库存放位置和数据表名,获得当前数据表文件存放位置

实例化一个BufferPoolManager变量,然后调用create_file函数,创建数据表文件。

(7)调用

BufferPoolManager::create_file(const char *file_name)

create_file函数,首先根据路径打开数据表文件

fd = open(file_name, O_RDWR | O_CREAT | O_EXCL, S_IREAD | S_IWRITE);

O_RDWR 读写模式

O_CREAT 如果指定文件不存在,则创建这个文件

O_EXCL 如果要创建的文件已存在,则返回 -1,并且修改 errno 的值

S_IREAD 所有者拥有读权限

S_IWRITE 所有者拥有写权限

以读写的方式创建一个新文件,新文件所有者拥有读写权限

然后以读写方式打开这个文件,创建Page文件,并且初始化为全0

将page.data中的前面部分转化成BPFileHeader变量指针,设置分配的页面为1,总页面为1,设置bitmap

调用lseek(fd, 0, SEEK_SET),将打开文件的指针移到文件开头

调用writen(fd, (char *)&page, sizeof(Page)),将刚才创建的Page变量写入文件

(8)

init_record_handler(base_dir);

初始化record_handler变量,设置table类中的base_dir_为当前数据库的存储位置

返回SUCCESS

你可能感兴趣的:(数据库,sql,c++,阿里云)