-
Notifications
You must be signed in to change notification settings - Fork 600
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Help us improve 🍉's TypeScript support #1516
Comments
Hello @radex, i just added some Typescript support on the Setup docs website section. |
@lucaswitch PR? |
Just added the PR #1636 |
Hoping to find time to contribute some types for this soon. FWIW I thought I'd let you know that |
Can we get a better typed
|
@tg44 |
@radex I miss collaborating with you guys! Sadly I don't have any projects with it anymore... |
@sidferreira heh, great to see you in this thread :)
|
I'll try to set up something this week to see if I have any insights! And indeed, we need to make it backwards compatible! |
For me it would be enough for now, if we could get the "raw type" representation from a schema, and I could use an |
So, for me, in this case, I don't mind if the DirtyRaw is not typed properly end to end. What I would like to get the type from the schema definition. We have a "db type" and a "model type", and we usually don't need the db type in our code, but it would be nice if we could derive it from the schema anyways. One example is to make the sync more typed. If I can "cast" the DirtyRaw to the right db type thats a good step ahead. This is why I asked if we have a method/helper/anything that can derive the Raw type from a schema? |
@tg44 🤔 I feel like I'm missing a detail... It seems to be way simpler than what I had in mind, but I still can't see the use.
The "DirtyRaw" would be:
is that it? |
@sidferreira yeah, but can we auto derive the DirtyRawPost type from the table schema? |
@tg44 I guess we can infer in a very crazy way, but not sure |
I'm not saying that it is bullet proof, and import {Model, tableSchema} from '@nozbe/watermelondb'
import {date, nochange, readonly, text} from "@nozbe/watermelondb/decorators";
type TableSchema = Parameters<typeof tableSchema>[0]
type Column = TableSchema['columns'][number]
type WatermelonModelFields = keyof Model
type Class<TModel extends typeof Model> = TModel extends {
new (...args: any[]): infer U
}
? U
: never
/**
* Removes all fields that are inherited from the Watermelon Model class
*/
type ModelFieldNames<TModel extends Model> = Exclude<
keyof TModel,
WatermelonModelFields
>
type CamelToSnakeCase<S extends string> =
S extends `${infer T}${infer U}` ? `${T extends Capitalize<T> ? '_' : ''}${Lowercase<T>}${CamelToSnakeCase<U>}` : S;
type CamelToSnakeObject<T> = {
[K in keyof T as CamelToSnakeCase<Extract<K, string>>]: T[K];
};
type CamelToSnakeUnion<T> = T extends string ? CamelToSnakeCase<T> : never;
export type ModelSchema<TModel extends typeof Model> = TableSchema & {
name: TModel['table']
columns: (Column & {
name: ModelFieldNames<Class<TModel>> extends never
? string
: CamelToSnakeUnion<ModelFieldNames<Class<TModel>>>
})[]
}
export const tableSchemaTypesecure = <
TModel extends typeof Model = typeof Model,
>(
arg0: ModelSchema<TModel>
) => tableSchema(arg0)
export type RawRecordTyped<TModel extends typeof Model> = {id: string} & {
[K in ModelFieldNames<Class<TModel>> as Class<TModel>[K] extends Model ? `${CamelToSnakeCase<Extract<K, string>>}_id` : CamelToSnakeCase<Extract<K, string>>]: Class<TModel>[K] extends Date
? number
: Class<TModel>[K] extends string
? string
: Class<TModel>[K] extends boolean
? boolean
: Class<TModel>[K] extends number
? number
: Class<TModel>[K] extends Model
? string
: Class<TModel>[K] extends Model[]
? never //we don't add the Model[] to the raw record
: never
}
//example usages;
export default class Icon extends Model {
static table = 'icons'
@nochange @text('name') name!: string;
@nochange @text('svg') svg!: string;
@nochange @readonly @date("created_at") createdAt!: Date;
@nochange @readonly @date("updated_at") updatedAt!: Date;
}
export const iconsSchema = tableSchemaTypesecure<typeof Icon>({
name: 'icons',
columns: [
{ name: 'name', type: 'string', isIndexed: true },
{ name: 'svg', type: 'string' },
{ name: 'created_at', type: 'number' },
{ name: 'updated_at', type: 'number' },
]
});
const func = async (changes: SyncDatabaseChangeSet) => {
const icons = changes['icons'].updated as RawRecordTyped<typeof Icon>[]
const iconPromises = await supabase.from("icons").upsert(icons)
} |
0.25 came with a huge improvement in the quality and maintainability of 🍉's TypeScript types. There were some teething problems, requiring a few patch releases, and no doubt the increased type coverage revealed new TS errors that weren't there before.
Anyway, thanks a lot to @sidferreira @paulrostorp @enahum @mlecoq for their contributions
You can help. Here's a few TS maintenance items that need to be done:
// @flow
comments from d.ts'syarn ci:check
?The text was updated successfully, but these errors were encountered: