Skip to content

@warp-drive/legacy: Model schema provider fields method with non-existing type causes infinite loop #10493

@BoussonKarel

Description

@BoussonKarel

I've stumbled upon an infinite loop in the fields() method on the legacy Model schema provider in the legacy package. This only happens in production.

When calling fields with a nonexistent type, it calls _loadModelSchema.

fields(resource: ResourceKey | { type: string }): Map<string, LegacyField> {
const type = normalizeModelName(resource.type);
if (!this._schemas.has(type)) {
this._loadModelSchema(type);
}
return this._schemas.get(type)!.fields;

This then calls this.store.modelFor. Because the type does not exist, it calls super.modelFor, which returns a shim:

StoreKlass.prototype.modelFor = function <T>(
type: T extends TypedRecordInstance ? TypeFromInstance<T> : string
): ModelSchema<T> {
assert(`Attempted to call store.modelFor(), but the store instance has already been destroyed.`, !this.isDestroyed);
assert(`You need to pass <type> to the store's modelFor method`, typeof type === 'string' && type.length);
assert(`No model was found for '${type}' and no schema handles the type`, this.schema.hasResource({ type }));
return getShimClass<T>(this, type);

And this shim calls this.__store.schema.fields, causing a loop:

export class ShimModelClass<T = unknown> implements ModelSchema<T> {
declare __store: Store;
declare modelName: T extends TypedRecordInstance ? TypeFromInstance<T> : string;
constructor(store: Store, modelName: T extends TypedRecordInstance ? TypeFromInstance<T> : string) {
this.__store = store;
this.modelName = modelName;
}
get fields(): Map<KeyOrString<T>, 'attribute' | 'belongsTo' | 'hasMany'> {
const fields = new Map<KeyOrString<T>, 'attribute' | 'belongsTo' | 'hasMany'>();
const fieldSchemas = this.__store.schema.fields({ type: this.modelName });

Metadata

Metadata

Assignees

No one assigned

    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