Skip to content

金仓数据库分表报错Index was outside the bounds of the array. #82

@nygula

Description

@nygula

报错信息:

Index was outside the bounds of the array.
 在 Internal.Runtime.CompilerHelpers.ThrowHelpers.ThrowIndexOutOfRangeException()
   在 NewLife.Data.DbRow.get_Item(String name)
   在 XCode.DataAccessLayer.KingBaseMetaData.GetTableNames()
   在 XCode.DataAccessLayer.DAL.GetTableNames()
   在 XCode.DataAccessLayer.DAL.<get_TableNames>b__68_0(String k)
   在 NewLife.Caching.MemoryCache.GetOrAdd[T](String key, Func`2 callback, Int32 expire)
   在 XCode.DataAccessLayer.DAL.get_TableNames()

AI初步分析:

根据对异常的分析,异常发生在 NewLife.XCode 库内部。调用栈显示它的触发路径为:
1.	XCode.DataAccessLayer.KingBaseMetaData.GetTableNames()
2.	NewLife.Data.DbRow.get_Item(String name)
原因分析: 遇到该异常的原因是 XCode 在连接到人大金仓 (KingBase) 数据库查询系统表(用于获取数据库中所有表的元数据)时,由于从数据库读取的数据行 (DbRow) 缺少预期的特定字段映射,或者驱动在内部通过列名获取数据时发生越界,导致了 IndexOutOfRangeException。这通常是因为使用的 XCode 版本与当前的 KingBase 数据库版本存在元数据模型不兼容导致的。

测试版本:

<TargetFramework>net10.0</TargetFramework>
<PackageReference Include="NewLife.XCode" Version="11.25.2026.403" />
<PackageReference Include="XCode.KingBase" Version="11.24.2026.403" />

数据库版本

kingbase_v009r001c010b0004_single_x86:v1

连接数据库字符串:

  "Default": "Server=192.168.1.225;Port=54321;Database=paladin;User Id=system;Password=12345678ab;Provider=KingBase"

xml模型文件

<Table Name="Notice" Description="通知">
   <Columns>
     <Column Name="id" DataType="Int64" PrimaryKey="True" DataScale="time" Description="编号" />
     <Column Name="Title" DataType="String" Master="True" Nullable="False" Description="标题" />
     <Column Name="Content" DataType="String" Length="-1" Description="内容" />
     <Column Name="Status" DataType="Boolean" Description="已读" />
     <Column Name="HandlerID" DataType="String" Description="归属人" />
     <Column Name="CreateTime" DataType="DateTime" Description="创建时间" />
     <Column Name="UpdateTime" DataType="DateTime" Description="更新时间" />
   </Columns>
   <Indexes>
     <Index Columns="Status" />
     <Index Columns="HandlerID" />
   </Indexes>
 </Table>    

类文件增加分表

static Notice()
{
     Meta.Factory.Snow.StartTimestamp = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Local);
     Meta.ShardPolicy = new TimeShardPolicy(nameof(id), Meta.Factory)
	 {
     ConnPolicy = "{0}",
     TablePolicy = "{0}_{1:yyyyMM}",
     Step = TimeSpan.FromDays(1),
     Field = _.id
 	};
 	// 过滤器 UserModule、TimeModule、IPModule
 	Meta.Modules.Add<TimeModule>();

	// 实体缓存
 	// var ec = Meta.Cache;
 	// ec.Expire = 60;
}  

查询报错的代码

PageParameter p = new PageParameter() { PageSize = size, PageIndex = page, RetrieveTotalCount = true, Sort = sort, Desc = desc };
var exp = new WhereExpression();
if (!Fuzzy.IsNullOrWhiteSpace())
{
    exp &= Notice.SearchWhereByKey(Fuzzy);
}
exp &= Notice._.HandlerID == AccountName;

exp &= Notice._.id.Between(StartTime, EndTime, Notice.Meta.Factory.Snow);

var result = Notice.FindAll(exp, p); 

尝试验证

 实际报错更加提前
 var _ = dal.TableNames;
 就能报错

Metadata

Metadata

Assignees

Labels

No labels
No labels

Type

No type

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions