From 4dad51da6db7816d99fd163c9d3aa388c9e9a2ec Mon Sep 17 00:00:00 2001 From: flemming-it Date: Thu, 7 May 2026 15:39:12 +0200 Subject: [PATCH] feat: hardwareInfo + listSystemAiCuratedModels RPCs (v0.7.0) Regenerated protos pick up the two new HubAdmin RPCs. HubClient exposes them as hardwareInfo() and listSystemAiCuratedModels(), with HardwareInfoResponse, ListSystemAiCuratedModelsResponse, CuratedModel re-exported as typedefs so callers don't import the generated/ directory directly. Studio uses the pair to colour-code models in the System-AI editor against the operator's actual hardware. Signed-off-by: flemming-it --- lib/src/generated/fai/v1/hub.pb.dart | 336 +++++++++++++++++++++++ lib/src/generated/fai/v1/hub.pbgrpc.dart | 48 ++++ lib/src/generated/fai/v1/hub.pbjson.dart | 60 ++++ lib/src/hub_client.dart | 21 ++ pubspec.yaml | 2 +- 5 files changed, 466 insertions(+), 1 deletion(-) diff --git a/lib/src/generated/fai/v1/hub.pb.dart b/lib/src/generated/fai/v1/hub.pb.dart index 98bca3c..df62854 100644 --- a/lib/src/generated/fai/v1/hub.pb.dart +++ b/lib/src/generated/fai/v1/hub.pb.dart @@ -3524,6 +3524,342 @@ class PullSystemAiModelResponse extends $pb.GeneratedMessage { void clearElapsedMs() => $_clearField(3); } +class HardwareInfoResponse extends $pb.GeneratedMessage { + factory HardwareInfoResponse({ + $core.String? tier, + $core.String? cpuBrand, + $core.int? cpuCores, + $fixnum.Int64? ramMb, + $core.bool? appleSilicon, + $core.bool? dedicatedGpu, + $core.String? summary, + }) { + final $result = create(); + if (tier != null) { + $result.tier = tier; + } + if (cpuBrand != null) { + $result.cpuBrand = cpuBrand; + } + if (cpuCores != null) { + $result.cpuCores = cpuCores; + } + if (ramMb != null) { + $result.ramMb = ramMb; + } + if (appleSilicon != null) { + $result.appleSilicon = appleSilicon; + } + if (dedicatedGpu != null) { + $result.dedicatedGpu = dedicatedGpu; + } + if (summary != null) { + $result.summary = summary; + } + return $result; + } + HardwareInfoResponse._() : super(); + factory HardwareInfoResponse.fromBuffer($core.List<$core.int> i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromBuffer(i, r); + factory HardwareInfoResponse.fromJson($core.String i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromJson(i, r); + + static final $pb.BuilderInfo _i = $pb.BuilderInfo(_omitMessageNames ? '' : 'HardwareInfoResponse', package: const $pb.PackageName(_omitMessageNames ? '' : 'fai.v1'), createEmptyInstance: create) + ..aOS(1, _omitFieldNames ? '' : 'tier') + ..aOS(2, _omitFieldNames ? '' : 'cpuBrand') + ..a<$core.int>(3, _omitFieldNames ? '' : 'cpuCores', $pb.PbFieldType.OU3) + ..a<$fixnum.Int64>(4, _omitFieldNames ? '' : 'ramMb', $pb.PbFieldType.OU6, defaultOrMaker: $fixnum.Int64.ZERO) + ..aOB(5, _omitFieldNames ? '' : 'appleSilicon') + ..aOB(6, _omitFieldNames ? '' : 'dedicatedGpu') + ..aOS(7, _omitFieldNames ? '' : 'summary') + ..hasRequiredFields = false + ; + + @$core.Deprecated('See https://github.com/google/protobuf.dart/issues/998.') + HardwareInfoResponse clone() => HardwareInfoResponse()..mergeFromMessage(this); + @$core.Deprecated('See https://github.com/google/protobuf.dart/issues/998.') + HardwareInfoResponse copyWith(void Function(HardwareInfoResponse) updates) => super.copyWith((message) => updates(message as HardwareInfoResponse)) as HardwareInfoResponse; + + $pb.BuilderInfo get info_ => _i; + + @$core.pragma('dart2js:noInline') + static HardwareInfoResponse create() => HardwareInfoResponse._(); + HardwareInfoResponse createEmptyInstance() => create(); + static $pb.PbList createRepeated() => $pb.PbList(); + @$core.pragma('dart2js:noInline') + static HardwareInfoResponse getDefault() => _defaultInstance ??= $pb.GeneratedMessage.$_defaultFor(create); + static HardwareInfoResponse? _defaultInstance; + + /// tiny / small / balanced / large / unknown — see + /// docs/architecture/system-ai.md → "Hardware tiers". + @$pb.TagNumber(1) + $core.String get tier => $_getSZ(0); + @$pb.TagNumber(1) + set tier($core.String v) { $_setString(0, v); } + @$pb.TagNumber(1) + $core.bool hasTier() => $_has(0); + @$pb.TagNumber(1) + void clearTier() => $_clearField(1); + + /// CPU brand string, e.g. "Apple M3 Pro". + @$pb.TagNumber(2) + $core.String get cpuBrand => $_getSZ(1); + @$pb.TagNumber(2) + set cpuBrand($core.String v) { $_setString(1, v); } + @$pb.TagNumber(2) + $core.bool hasCpuBrand() => $_has(1); + @$pb.TagNumber(2) + void clearCpuBrand() => $_clearField(2); + + @$pb.TagNumber(3) + $core.int get cpuCores => $_getIZ(2); + @$pb.TagNumber(3) + set cpuCores($core.int v) { $_setUnsignedInt32(2, v); } + @$pb.TagNumber(3) + $core.bool hasCpuCores() => $_has(2); + @$pb.TagNumber(3) + void clearCpuCores() => $_clearField(3); + + @$pb.TagNumber(4) + $fixnum.Int64 get ramMb => $_getI64(3); + @$pb.TagNumber(4) + set ramMb($fixnum.Int64 v) { $_setInt64(3, v); } + @$pb.TagNumber(4) + $core.bool hasRamMb() => $_has(3); + @$pb.TagNumber(4) + void clearRamMb() => $_clearField(4); + + @$pb.TagNumber(5) + $core.bool get appleSilicon => $_getBF(4); + @$pb.TagNumber(5) + set appleSilicon($core.bool v) { $_setBool(4, v); } + @$pb.TagNumber(5) + $core.bool hasAppleSilicon() => $_has(4); + @$pb.TagNumber(5) + void clearAppleSilicon() => $_clearField(5); + + @$pb.TagNumber(6) + $core.bool get dedicatedGpu => $_getBF(5); + @$pb.TagNumber(6) + set dedicatedGpu($core.bool v) { $_setBool(5, v); } + @$pb.TagNumber(6) + $core.bool hasDedicatedGpu() => $_has(5); + @$pb.TagNumber(6) + void clearDedicatedGpu() => $_clearField(6); + + /// Human-readable summary the editor renders verbatim, e.g. + /// "Apple M3 Pro · 16 GB · balanced". + @$pb.TagNumber(7) + $core.String get summary => $_getSZ(6); + @$pb.TagNumber(7) + set summary($core.String v) { $_setString(6, v); } + @$pb.TagNumber(7) + $core.bool hasSummary() => $_has(6); + @$pb.TagNumber(7) + void clearSummary() => $_clearField(7); +} + +class ListSystemAiCuratedModelsResponse extends $pb.GeneratedMessage { + factory ListSystemAiCuratedModelsResponse({ + $core.Iterable? models, + $core.String? lastReviewed, + }) { + final $result = create(); + if (models != null) { + $result.models.addAll(models); + } + if (lastReviewed != null) { + $result.lastReviewed = lastReviewed; + } + return $result; + } + ListSystemAiCuratedModelsResponse._() : super(); + factory ListSystemAiCuratedModelsResponse.fromBuffer($core.List<$core.int> i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromBuffer(i, r); + factory ListSystemAiCuratedModelsResponse.fromJson($core.String i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromJson(i, r); + + static final $pb.BuilderInfo _i = $pb.BuilderInfo(_omitMessageNames ? '' : 'ListSystemAiCuratedModelsResponse', package: const $pb.PackageName(_omitMessageNames ? '' : 'fai.v1'), createEmptyInstance: create) + ..pc(1, _omitFieldNames ? '' : 'models', $pb.PbFieldType.PM, subBuilder: CuratedModel.create) + ..aOS(2, _omitFieldNames ? '' : 'lastReviewed') + ..hasRequiredFields = false + ; + + @$core.Deprecated('See https://github.com/google/protobuf.dart/issues/998.') + ListSystemAiCuratedModelsResponse clone() => ListSystemAiCuratedModelsResponse()..mergeFromMessage(this); + @$core.Deprecated('See https://github.com/google/protobuf.dart/issues/998.') + ListSystemAiCuratedModelsResponse copyWith(void Function(ListSystemAiCuratedModelsResponse) updates) => super.copyWith((message) => updates(message as ListSystemAiCuratedModelsResponse)) as ListSystemAiCuratedModelsResponse; + + $pb.BuilderInfo get info_ => _i; + + @$core.pragma('dart2js:noInline') + static ListSystemAiCuratedModelsResponse create() => ListSystemAiCuratedModelsResponse._(); + ListSystemAiCuratedModelsResponse createEmptyInstance() => create(); + static $pb.PbList createRepeated() => $pb.PbList(); + @$core.pragma('dart2js:noInline') + static ListSystemAiCuratedModelsResponse getDefault() => _defaultInstance ??= $pb.GeneratedMessage.$_defaultFor(create); + static ListSystemAiCuratedModelsResponse? _defaultInstance; + + @$pb.TagNumber(1) + $pb.PbList get models => $_getList(0); + + /// ISO-date string from models.yaml (e.g. "2026-05-07"). Lets + /// Studio show "curation last reviewed 3 weeks ago". + @$pb.TagNumber(2) + $core.String get lastReviewed => $_getSZ(1); + @$pb.TagNumber(2) + set lastReviewed($core.String v) { $_setString(1, v); } + @$pb.TagNumber(2) + $core.bool hasLastReviewed() => $_has(1); + @$pb.TagNumber(2) + void clearLastReviewed() => $_clearField(2); +} + +class CuratedModel extends $pb.GeneratedMessage { + factory CuratedModel({ + $core.String? id, + $core.String? family, + $core.double? paramsB, + $core.String? qualityTier, + $core.String? minHwTier, + $core.int? contextK, + $core.String? notes, + $core.String? license, + }) { + final $result = create(); + if (id != null) { + $result.id = id; + } + if (family != null) { + $result.family = family; + } + if (paramsB != null) { + $result.paramsB = paramsB; + } + if (qualityTier != null) { + $result.qualityTier = qualityTier; + } + if (minHwTier != null) { + $result.minHwTier = minHwTier; + } + if (contextK != null) { + $result.contextK = contextK; + } + if (notes != null) { + $result.notes = notes; + } + if (license != null) { + $result.license = license; + } + return $result; + } + CuratedModel._() : super(); + factory CuratedModel.fromBuffer($core.List<$core.int> i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromBuffer(i, r); + factory CuratedModel.fromJson($core.String i, [$pb.ExtensionRegistry r = $pb.ExtensionRegistry.EMPTY]) => create()..mergeFromJson(i, r); + + static final $pb.BuilderInfo _i = $pb.BuilderInfo(_omitMessageNames ? '' : 'CuratedModel', package: const $pb.PackageName(_omitMessageNames ? '' : 'fai.v1'), createEmptyInstance: create) + ..aOS(1, _omitFieldNames ? '' : 'id') + ..aOS(2, _omitFieldNames ? '' : 'family') + ..a<$core.double>(3, _omitFieldNames ? '' : 'paramsB', $pb.PbFieldType.OF) + ..aOS(4, _omitFieldNames ? '' : 'qualityTier') + ..aOS(5, _omitFieldNames ? '' : 'minHwTier') + ..a<$core.int>(6, _omitFieldNames ? '' : 'contextK', $pb.PbFieldType.OU3) + ..aOS(7, _omitFieldNames ? '' : 'notes') + ..aOS(8, _omitFieldNames ? '' : 'license') + ..hasRequiredFields = false + ; + + @$core.Deprecated('See https://github.com/google/protobuf.dart/issues/998.') + CuratedModel clone() => CuratedModel()..mergeFromMessage(this); + @$core.Deprecated('See https://github.com/google/protobuf.dart/issues/998.') + CuratedModel copyWith(void Function(CuratedModel) updates) => super.copyWith((message) => updates(message as CuratedModel)) as CuratedModel; + + $pb.BuilderInfo get info_ => _i; + + @$core.pragma('dart2js:noInline') + static CuratedModel create() => CuratedModel._(); + CuratedModel createEmptyInstance() => create(); + static $pb.PbList createRepeated() => $pb.PbList(); + @$core.pragma('dart2js:noInline') + static CuratedModel getDefault() => _defaultInstance ??= $pb.GeneratedMessage.$_defaultFor(create); + static CuratedModel? _defaultInstance; + + @$pb.TagNumber(1) + $core.String get id => $_getSZ(0); + @$pb.TagNumber(1) + set id($core.String v) { $_setString(0, v); } + @$pb.TagNumber(1) + $core.bool hasId() => $_has(0); + @$pb.TagNumber(1) + void clearId() => $_clearField(1); + + @$pb.TagNumber(2) + $core.String get family => $_getSZ(1); + @$pb.TagNumber(2) + set family($core.String v) { $_setString(1, v); } + @$pb.TagNumber(2) + $core.bool hasFamily() => $_has(1); + @$pb.TagNumber(2) + void clearFamily() => $_clearField(2); + + /// Parameter count in billions. 0 for closed-source cloud + /// models where we don't publish a number. + @$pb.TagNumber(3) + $core.double get paramsB => $_getN(2); + @$pb.TagNumber(3) + set paramsB($core.double v) { $_setFloat(2, v); } + @$pb.TagNumber(3) + $core.bool hasParamsB() => $_has(2); + @$pb.TagNumber(3) + void clearParamsB() => $_clearField(3); + + /// basic / good / excellent. + @$pb.TagNumber(4) + $core.String get qualityTier => $_getSZ(3); + @$pb.TagNumber(4) + set qualityTier($core.String v) { $_setString(3, v); } + @$pb.TagNumber(4) + $core.bool hasQualityTier() => $_has(3); + @$pb.TagNumber(4) + void clearQualityTier() => $_clearField(4); + + /// tiny / small / balanced / large. + @$pb.TagNumber(5) + $core.String get minHwTier => $_getSZ(4); + @$pb.TagNumber(5) + set minHwTier($core.String v) { $_setString(4, v); } + @$pb.TagNumber(5) + $core.bool hasMinHwTier() => $_has(4); + @$pb.TagNumber(5) + void clearMinHwTier() => $_clearField(5); + + /// Context window in K tokens (8 = 8192). + @$pb.TagNumber(6) + $core.int get contextK => $_getIZ(5); + @$pb.TagNumber(6) + set contextK($core.int v) { $_setUnsignedInt32(5, v); } + @$pb.TagNumber(6) + $core.bool hasContextK() => $_has(5); + @$pb.TagNumber(6) + void clearContextK() => $_clearField(6); + + /// Free-form note rendered as a tooltip in Studio. + @$pb.TagNumber(7) + $core.String get notes => $_getSZ(6); + @$pb.TagNumber(7) + set notes($core.String v) { $_setString(6, v); } + @$pb.TagNumber(7) + $core.bool hasNotes() => $_has(6); + @$pb.TagNumber(7) + void clearNotes() => $_clearField(7); + + /// Licence identifier (gemma-license, apache-2.0, …). + @$pb.TagNumber(8) + $core.String get license => $_getSZ(7); + @$pb.TagNumber(8) + set license($core.String v) { $_setString(7, v); } + @$pb.TagNumber(8) + $core.bool hasLicense() => $_has(7); + @$pb.TagNumber(8) + void clearLicense() => $_clearField(8); +} + const _omitFieldNames = $core.bool.fromEnvironment('protobuf.omit_field_names'); const _omitMessageNames = $core.bool.fromEnvironment('protobuf.omit_message_names'); diff --git a/lib/src/generated/fai/v1/hub.pbgrpc.dart b/lib/src/generated/fai/v1/hub.pbgrpc.dart index 27d909b..2ee5304 100644 --- a/lib/src/generated/fai/v1/hub.pbgrpc.dart +++ b/lib/src/generated/fai/v1/hub.pbgrpc.dart @@ -211,6 +211,14 @@ class HubAdminClient extends $grpc.Client { '/fai.v1.HubAdmin/PullSystemAiModel', ($0.PullSystemAiModelRequest value) => value.writeToBuffer(), ($core.List<$core.int> value) => $0.PullSystemAiModelResponse.fromBuffer(value)); + static final _$hardwareInfo = $grpc.ClientMethod<$1.Empty, $0.HardwareInfoResponse>( + '/fai.v1.HubAdmin/HardwareInfo', + ($1.Empty value) => value.writeToBuffer(), + ($core.List<$core.int> value) => $0.HardwareInfoResponse.fromBuffer(value)); + static final _$listSystemAiCuratedModels = $grpc.ClientMethod<$1.Empty, $0.ListSystemAiCuratedModelsResponse>( + '/fai.v1.HubAdmin/ListSystemAiCuratedModels', + ($1.Empty value) => value.writeToBuffer(), + ($core.List<$core.int> value) => $0.ListSystemAiCuratedModelsResponse.fromBuffer(value)); HubAdminClient(super.channel, {super.options, super.interceptors}); @@ -355,6 +363,22 @@ class HubAdminClient extends $grpc.Client { $grpc.ResponseFuture<$0.PullSystemAiModelResponse> pullSystemAiModel($0.PullSystemAiModelRequest request, {$grpc.CallOptions? options}) { return $createUnaryCall(_$pullSystemAiModel, request, options: options); } + + /// Detected host hardware tier + summary line. Studio's + /// System-AI editor uses this to mark models as "may be slow + /// on your hardware" without requiring a benchmark. + $grpc.ResponseFuture<$0.HardwareInfoResponse> hardwareInfo($1.Empty request, {$grpc.CallOptions? options}) { + return $createUnaryCall(_$hardwareInfo, request, options: options); + } + + /// Bundled curated model database (quality tier, parameter + /// count, recommended-for tier, notes). Studio merges this + /// with the live `/v1/models` listing for richer chips. The + /// `last_reviewed` field tells the operator how stale the + /// curation is. + $grpc.ResponseFuture<$0.ListSystemAiCuratedModelsResponse> listSystemAiCuratedModels($1.Empty request, {$grpc.CallOptions? options}) { + return $createUnaryCall(_$listSystemAiCuratedModels, request, options: options); + } } @$pb.GrpcServiceName('fai.v1.HubAdmin') @@ -516,6 +540,20 @@ abstract class HubAdminServiceBase extends $grpc.Service { false, ($core.List<$core.int> value) => $0.PullSystemAiModelRequest.fromBuffer(value), ($0.PullSystemAiModelResponse value) => value.writeToBuffer())); + $addMethod($grpc.ServiceMethod<$1.Empty, $0.HardwareInfoResponse>( + 'HardwareInfo', + hardwareInfo_Pre, + false, + false, + ($core.List<$core.int> value) => $1.Empty.fromBuffer(value), + ($0.HardwareInfoResponse value) => value.writeToBuffer())); + $addMethod($grpc.ServiceMethod<$1.Empty, $0.ListSystemAiCuratedModelsResponse>( + 'ListSystemAiCuratedModels', + listSystemAiCuratedModels_Pre, + false, + false, + ($core.List<$core.int> value) => $1.Empty.fromBuffer(value), + ($0.ListSystemAiCuratedModelsResponse value) => value.writeToBuffer())); } $async.Future<$0.CapabilityList> listCapabilities_Pre($grpc.ServiceCall $call, $async.Future<$1.Empty> $request) async { @@ -606,6 +644,14 @@ abstract class HubAdminServiceBase extends $grpc.Service { return pullSystemAiModel($call, await $request); } + $async.Future<$0.HardwareInfoResponse> hardwareInfo_Pre($grpc.ServiceCall $call, $async.Future<$1.Empty> $request) async { + return hardwareInfo($call, await $request); + } + + $async.Future<$0.ListSystemAiCuratedModelsResponse> listSystemAiCuratedModels_Pre($grpc.ServiceCall $call, $async.Future<$1.Empty> $request) async { + return listSystemAiCuratedModels($call, await $request); + } + $async.Future<$0.CapabilityList> listCapabilities($grpc.ServiceCall call, $1.Empty request); $async.Future<$0.ModuleInfoResponse> moduleInfo($grpc.ServiceCall call, $0.ModuleInfoRequest request); $async.Future<$0.CheckPermissionResponse> checkPermission($grpc.ServiceCall call, $0.CheckPermissionRequest request); @@ -628,4 +674,6 @@ abstract class HubAdminServiceBase extends $grpc.Service { $async.Future<$0.AskAiResponse> testSystemAi($grpc.ServiceCall call, $0.TestSystemAiRequest request); $async.Future<$0.ListSystemAiModelsResponse> listSystemAiModels($grpc.ServiceCall call, $0.TestSystemAiRequest request); $async.Future<$0.PullSystemAiModelResponse> pullSystemAiModel($grpc.ServiceCall call, $0.PullSystemAiModelRequest request); + $async.Future<$0.HardwareInfoResponse> hardwareInfo($grpc.ServiceCall call, $1.Empty request); + $async.Future<$0.ListSystemAiCuratedModelsResponse> listSystemAiCuratedModels($grpc.ServiceCall call, $1.Empty request); } diff --git a/lib/src/generated/fai/v1/hub.pbjson.dart b/lib/src/generated/fai/v1/hub.pbjson.dart index d82eaba..fd7af4a 100644 --- a/lib/src/generated/fai/v1/hub.pbjson.dart +++ b/lib/src/generated/fai/v1/hub.pbjson.dart @@ -814,3 +814,63 @@ final $typed_data.Uint8List pullSystemAiModelResponseDescriptor = $convert.base6 'ChlQdWxsU3lzdGVtQWlNb2RlbFJlc3BvbnNlEh0KCmVycm9yX2tpbmQYASABKAlSCWVycm9yS2' 'luZBISCgR0ZXh0GAIgASgJUgR0ZXh0Eh0KCmVsYXBzZWRfbXMYAyABKA1SCWVsYXBzZWRNcw=='); +@$core.Deprecated('Use hardwareInfoResponseDescriptor instead') +const HardwareInfoResponse$json = { + '1': 'HardwareInfoResponse', + '2': [ + {'1': 'tier', '3': 1, '4': 1, '5': 9, '10': 'tier'}, + {'1': 'cpu_brand', '3': 2, '4': 1, '5': 9, '10': 'cpuBrand'}, + {'1': 'cpu_cores', '3': 3, '4': 1, '5': 13, '10': 'cpuCores'}, + {'1': 'ram_mb', '3': 4, '4': 1, '5': 4, '10': 'ramMb'}, + {'1': 'apple_silicon', '3': 5, '4': 1, '5': 8, '10': 'appleSilicon'}, + {'1': 'dedicated_gpu', '3': 6, '4': 1, '5': 8, '10': 'dedicatedGpu'}, + {'1': 'summary', '3': 7, '4': 1, '5': 9, '10': 'summary'}, + ], +}; + +/// Descriptor for `HardwareInfoResponse`. Decode as a `google.protobuf.DescriptorProto`. +final $typed_data.Uint8List hardwareInfoResponseDescriptor = $convert.base64Decode( + 'ChRIYXJkd2FyZUluZm9SZXNwb25zZRISCgR0aWVyGAEgASgJUgR0aWVyEhsKCWNwdV9icmFuZB' + 'gCIAEoCVIIY3B1QnJhbmQSGwoJY3B1X2NvcmVzGAMgASgNUghjcHVDb3JlcxIVCgZyYW1fbWIY' + 'BCABKARSBXJhbU1iEiMKDWFwcGxlX3NpbGljb24YBSABKAhSDGFwcGxlU2lsaWNvbhIjCg1kZW' + 'RpY2F0ZWRfZ3B1GAYgASgIUgxkZWRpY2F0ZWRHcHUSGAoHc3VtbWFyeRgHIAEoCVIHc3VtbWFy' + 'eQ=='); + +@$core.Deprecated('Use listSystemAiCuratedModelsResponseDescriptor instead') +const ListSystemAiCuratedModelsResponse$json = { + '1': 'ListSystemAiCuratedModelsResponse', + '2': [ + {'1': 'models', '3': 1, '4': 3, '5': 11, '6': '.fai.v1.CuratedModel', '10': 'models'}, + {'1': 'last_reviewed', '3': 2, '4': 1, '5': 9, '10': 'lastReviewed'}, + ], +}; + +/// Descriptor for `ListSystemAiCuratedModelsResponse`. Decode as a `google.protobuf.DescriptorProto`. +final $typed_data.Uint8List listSystemAiCuratedModelsResponseDescriptor = $convert.base64Decode( + 'CiFMaXN0U3lzdGVtQWlDdXJhdGVkTW9kZWxzUmVzcG9uc2USLAoGbW9kZWxzGAEgAygLMhQuZm' + 'FpLnYxLkN1cmF0ZWRNb2RlbFIGbW9kZWxzEiMKDWxhc3RfcmV2aWV3ZWQYAiABKAlSDGxhc3RS' + 'ZXZpZXdlZA=='); + +@$core.Deprecated('Use curatedModelDescriptor instead') +const CuratedModel$json = { + '1': 'CuratedModel', + '2': [ + {'1': 'id', '3': 1, '4': 1, '5': 9, '10': 'id'}, + {'1': 'family', '3': 2, '4': 1, '5': 9, '10': 'family'}, + {'1': 'params_b', '3': 3, '4': 1, '5': 2, '10': 'paramsB'}, + {'1': 'quality_tier', '3': 4, '4': 1, '5': 9, '10': 'qualityTier'}, + {'1': 'min_hw_tier', '3': 5, '4': 1, '5': 9, '10': 'minHwTier'}, + {'1': 'context_k', '3': 6, '4': 1, '5': 13, '10': 'contextK'}, + {'1': 'notes', '3': 7, '4': 1, '5': 9, '10': 'notes'}, + {'1': 'license', '3': 8, '4': 1, '5': 9, '10': 'license'}, + ], +}; + +/// Descriptor for `CuratedModel`. Decode as a `google.protobuf.DescriptorProto`. +final $typed_data.Uint8List curatedModelDescriptor = $convert.base64Decode( + 'CgxDdXJhdGVkTW9kZWwSDgoCaWQYASABKAlSAmlkEhYKBmZhbWlseRgCIAEoCVIGZmFtaWx5Eh' + 'kKCHBhcmFtc19iGAMgASgCUgdwYXJhbXNCEiEKDHF1YWxpdHlfdGllchgEIAEoCVILcXVhbGl0' + 'eVRpZXISHgoLbWluX2h3X3RpZXIYBSABKAlSCW1pbkh3VGllchIbCgljb250ZXh0X2sYBiABKA' + '1SCGNvbnRleHRLEhQKBW5vdGVzGAcgASgJUgVub3RlcxIYCgdsaWNlbnNlGAggASgJUgdsaWNl' + 'bnNl'); + diff --git a/lib/src/hub_client.dart b/lib/src/hub_client.dart index 6bc1146..52cd099 100644 --- a/lib/src/hub_client.dart +++ b/lib/src/hub_client.dart @@ -49,6 +49,10 @@ typedef AskAiResponse = pb.AskAiResponse; typedef ListSystemAiModelsResponse = pb.ListSystemAiModelsResponse; typedef SystemAiModel = pb.SystemAiModel; typedef PullSystemAiModelResponse = pb.PullSystemAiModelResponse; +typedef HardwareInfoResponse = pb.HardwareInfoResponse; +typedef ListSystemAiCuratedModelsResponse = + pb.ListSystemAiCuratedModelsResponse; +typedef CuratedModel = pb.CuratedModel; typedef ModuleInfoResponse = pb.ModuleInfoResponse; typedef FlowSummary = pb.FlowSummary; typedef StoreEntry = pb.StoreEntry; @@ -273,6 +277,23 @@ class HubClient { )); } + /// Detected host hardware. Cached server-side; cheap to call. + /// Returned tier is one of `tiny`/`small`/`balanced`/`large`/ + /// `unknown`. See `docs/architecture/system-ai.md` → + /// "Hardware tiers". + Future hardwareInfo() { + return _admin.hardwareInfo(Empty()); + } + + /// Bundled curated model database. Used by Studio's editor + /// to colour-code models by hardware suitability. Refresh + /// requires a hub redeploy — `lastReviewed` shows how stale + /// the curation is. + Future + listSystemAiCuratedModels() { + return _admin.listSystemAiCuratedModels(Empty()); + } + /// Search the hub's bundled store index. All filters are /// optional; an empty query returns the first [limit] entries /// the index ships with. diff --git a/pubspec.yaml b/pubspec.yaml index 4b7d09e..033bc16 100644 --- a/pubspec.yaml +++ b/pubspec.yaml @@ -1,6 +1,6 @@ name: fai_dart_sdk description: gRPC client SDK for the F∆I Platform hub. Used by F∆I Studio and Tier-3 domain apps. -version: 0.6.0 +version: 0.7.0 publish_to: 'none' repository: https://git.flemming.ws/fai/dart-sdk