1.创建图表
1.RC ExecuteStage::handle_request()
函数处理一个request请求,通过sql解析,发现这是一个创建表的sql语句,进入do_create_table函数。
1.5. RC DefaultHandler::create_table()
获取当前数据库类型(Db)
进入db->create_table函数,传入创建表的名字、字段数量、字段类型
2.RC Db::create_table()
3.rc = table->create();
table_file_path.c_str() : 元数据存储路径
table_name数据表名字,
path_.c_str(),数据库的路径,
attribute_count字段数
attributes字段类型
4.RC Table::create()
5.int fd = ::open();
6.rc = table_meta_.init()
7.fs.open();
打开元数据文件,并且通过二进制的方式进行写操作
8.table_meta_.serialize(fs);
将元数据进行序列化然后写入文件
9.std::string data_file = table_data_file();
9.rc = bpm.create_file(data_file.c_str());
创建数据表文件
10.fd = open(file_name, O_RDWR | O_CREAT | O_EXCL, S_IREAD | S_IWRITE);
以读写的方式创建一个新文件,新文件所有者拥有读写权限
11.init_record_handler(base_dir);
初始化record_handler变量,设置table类中的base_dir_为当前数据库的存储位置
参考代码miniob数据库——建表逻辑的源码解析_miniob的sqlparse函数不是没有函数体吗,是怎么进行解析的_allwellright的博客-CSDN博客
2.
miniob/src/observer/event/sql_event.h:定义类SQLStageEvent
miniob/src/observer/session/session_stage.h:定义类SessionStage
miniob/src/observer/session/session_stage.cpp:词法解析、语法解析是在ParseStage的handle_event(request)进行的
1.Client 向灰色框框里的服务端发起访问请求;
2.NET 网络模块接受到请求以后,将请求交给 Parser 模块进行词法解析(LEX)和语法解析(YACC);
经过词法解析和语法解析后,转发给 Plan Cache 这个模块,当前的 Plan Cache 不做任何特殊处理,直接丢给 Resolver 模块;
3.Resolver 模块会将 Parser 模块解析出来的语法树进行细化,比如把里面表的名字转换成某一个对象、比如把 SELECT * 中的 * 转换为表中的各个字段;当然在这个阶段还会进行一些预检,比如查看该表是否存在;
4.接下来会传给优化阶段的 Transformer 和 Optimizer,这两个部分像前一篇文章纪老师提到的一样,会不断的迭代,尽量找到一个低成本的执行计划;Transformer 会根据一些 SQL 规则进行一些优化;Optimizer 会根据一些统计数据找到一个更好的查询路径;
5.然后会传给后面的 Executor 执行模块,按照执行计划执行查询,把执行结果返回给 NET 网络模块;
6.NET 模块通过 Socket 返回给客户端