createEmbeddingModel method
Future<EmbeddingModel>
createEmbeddingModel({
- String? modelPath,
- String? tokenizerPath,
- PreferredBackend? preferredBackend,
override
Creates and returns a new EmbeddingModel instance.
Modern API: If paths are not provided, uses the active embedding model set via
FlutterGemma.installEmbedder() or modelManager.setActiveModel().
Legacy API: Provide explicit paths for backward compatibility.
modelPath — path to the embedding model file (optional if active model set).
tokenizerPath — path to the tokenizer file (optional if active model set).
preferredBackend — backend preference (e.g., CPU, GPU).
Implementation
@override
Future<EmbeddingModel> createEmbeddingModel({
String? modelPath,
String? tokenizerPath,
PreferredBackend? preferredBackend,
}) {
// FIRST statement, before every guard. It is idempotent and one-shot, so
// it needs neither resolved paths nor cache state — and putting it in a
// branch is what made it unreachable twice: once behind the singleton
// cache, once behind "only on reuse". The ordinary shape is a single call
// held for the app's lifetime; if it does not speak here it never speaks.
noticeWebEmbedderBackendIgnored(preferredBackend);
// Serialised, so that resolving paths, comparing them and constructing the
// model are one step — which is what stops two concurrent first callers from
// each building one, the defect this shell actually had.
//
// Note what this does NOT cover on either web arm: the model constructors
// are trivial and the WASM/WebGPU compile happens lazily on the first
// `generateEmbedding`, outside this lane. Concurrent first embeddings are
// deduped by each model's own single in-flight init future — this lane only
// guarantees one MODEL, not one compile.
return _embedderCache.serialize(
() => _reuseOrBuildEmbedder(
modelPath: modelPath,
tokenizerPath: tokenizerPath,
preferredBackend: preferredBackend,
),
);
}