OceanBase如何查看表大小和索引大小?

OceanBase查看表大小和索引大小,正常来说只需在OCP上进入任意普通租户下,选择左侧菜单资源管理即可查看,但是最近我发现,这里显示的索引大小与实际后台SQL(见下文)查看的索引大小数据不一致,经过官方问答社区帖子询问:https://ask.oceanbase.com/t/topic/35609708/11,又仔细研究了下相关视图,于是有了这篇文章。

在 ob 4.x 版本之前,大部分情况下都是使用 __all_virtual_ 等内部表做相关统计信息查询,但是在 ob 4.x 版本之后,官方更建议直接按需使用对应的视图表来查询各种信息,不建议直接使用__all_virtual_这种内部表做查询了。

例如涉及表大小和索引大小的视图表有:

sys租户下的

oceanbase.CDB_OB_TABLE_LOCATIONS

oceanbase.CDB_OB_TABLET_REPLICAS

以及普通租户下的

oceanbase.DBA_OB_TABLE_LOCATIONS

oceanbase.DBA_OB_TABLET_REPLICAS。

一、查看表大小

1、sys租户下查询

如果想查询表的所有副本大小,则去掉条件 t1.role='leader',如果只想查单副本大小,则加上条件 t1.role='leader'。

select /*+ READ_CONSISTENCY(WEAK) */t1.table_name,concat(round(sum(t2.data_size/1024/1024/1024), 2), 'G') data_size_gb ,concat(round(sum(t2.required_size)/1024/1024/1024, 2), 'G') required_size_gbfrom dba_ob_tenants t,cdb_ob_table_locations t1,cdb_ob_tablet_replicas t2where t.tenant_id=t1.tenant_idand t1.svr_ip=t2.svr_ipand t1.tenant_id=t2.tenant_idand t1.ls_id=t2.ls_idand t1.tablet_id=t2.tablet_id-- and t1.role='leader'and t.tenant_name='ob_test'and t1.database_name='fanchen'and t1.table_name='t_fan_chen_du_shu_lou'group by t1.table_nameorder by 3 desc;+------------------------+--------------+------------------+| table_name             | data_size_gb | required_size_gb |+------------------------+--------------+------------------+| t_fan_chen_du_shu_lou  |      683.39G |          790.73G |+------------------------+--------------+------------------+1 row in set (3.96 sec)

data_size_gb:数据实际大小,required_size_gb:数据分配空间大小。数据存储以宏块(2MB)为最小单位,所以 REQUIRED_SIZE >= DATA_SIZE。

2、普通租户下查询

select /*+ READ_CONSISTENCY(WEAK) */t1.table_name,concat(round(sum(t2.data_size/1024/1024/1024), 2), 'G') datasize_primary_replica ,concat(round(sum(t2.required_size)/1024/1024/1024, 2), 'G') requiredsize_primary_replicafrom dba_ob_table_locations t1,dba_ob_tablet_replicas t2where 
 t1.svr_ip=t2.svr_ipand t1.ls_id=t2.ls_idand t1.tablet_id=t2.tablet_id-- and t1.role='leader'and t1.database_name='fanchen'and t1.table_name='t_fan_chen_du_shu_lou'group by t1.table_nameorder by 3 desc;

二、查看索引大小

sys租户下查不了普通租户下表的索引大小,必须在普通租户下查询。

select /*+ READ_CONSISTENCY(WEAK) */t1.table_name,round(sum(t2.data_size/1024/1024/1024), 2) data_size_gb ,round(sum(t2.required_size)/1024/1024/1024, 2) required_size_gbfrom dba_ob_table_locations t1,dba_ob_tablet_replicas t2where 
 t1.svr_ip=t2.svr_ipand t1.ls_id=t2.ls_idand t1.tablet_id=t2.tablet_id-- and t1.role='leader'and t1.database_name='fanchen'and (t1.table_name='t_fan_chen_du_shu_lou'or t1.data_table_id in (select table_id from dba_ob_table_locations where table_name='t_fan_chen_du_shu_lou' limit 1))group by t1.table_nameorder by 3 desc;

三、根据表名查询表、索引、lob大小

有了上面2个SQL模板,能不能一条SQL实现查询表大小和索引大小呢?

通过了解 oceanbase.CDB_OB_TABLE_LOCATIONS 表,我发现对于ob而言,索引对象也是一种表,大对象 LOB 数据也是一种表,于是有了4种表类型:

USER TABLE:用户表

SYSTEM TABLE:系统表,系统自建的表

INDEX:索引表

LOB AUX TABLE:LOB 辅助表,系统自建的表,用于辅助实现 LOB 列。

于是SQL改写如下:

with table_info as (
  select
    table_id,
    table_name,
    database_name  from
    dba_ob_table_locations  where
    database_name = 'fanchen'
    and table_name = 't_fan_chen_du_shu_lou'
  limit
    1)select
  /*+ READ_CONSISTENCY(WEAK) */
  t1.database_name,
  CASE
  WHEN data_table_id is null THEN t1.table_name  WHEN table_type = 'LOB AUX TABLE' THEN t1.table_name  ELSE t1.index_nameEND
  AS object_name,
  round(sum(t2.data_size) / 1024 / 1024 / 1024, 2) as data_size_gb,
  round(sum(t2.required_size) / 1024 / 1024 / 1024, 2) as required_size_gbfrom
  dba_ob_table_locations t1,
  dba_ob_tablet_replicas t2,
  table_info twhere
  t1.svr_ip = t2.svr_ip  and t1.ls_id = t2.ls_id  and t1.tablet_id = t2.tablet_id  and t1.database_name = t.database_name  -- and t1.role='leader'
  and (
    t1.table_name = t.table_name    or t1.data_table_id = t.table_id  )group by
  t1.database_name,
  t1.table_nameorder by
  4 desc;


请使用浏览器的分享功能分享到微信等