-
Notifications
You must be signed in to change notification settings - Fork 127
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
Simple use of serialize<T>(data) is not working - "No type information received. Circular import or no runtime type available." #562
Comments
did you enable reflection in tsconfig and installed @deepkit/type-compiler? |
Yes I have installed @deepkit/type-compiler. Do I need an additional library to enable reflection in tsconfig? |
you have to enable reflection in tsconfig, see https://deepkit.io/documentation/runtime-types/getting-started |
I missed the "reflection": true. But after adding it I still get the error |
@juanda147 you also have to run |
and how do you build and execute it? |
it is failing at running the tests |
what test framework |
is the test framework using tsc? Use DEBUG=deepkit env variable to get more information |
jest |
can't help like that must be an user error since we use jest as well and it works very well. I would make sure that ts-jest is used correctly, the correct tsconfig is loaded (see my DEBUG note), deepkit was correctly installed as seen in the docs. then it will work |
I created an isolated project with some basic configuration and basically the same as the main project, and I got the same error, please find attached zip file. |
@juanda147 your repro is broken
Did you do what I mentioned here #562 (comment) ? |
This is really odd. I removed all external dependencies and left a very simple class, and still seeing the error. Just run it using: npx ts-node .\DeepKit\Run.ts Thanks a lot for your help so far |
Can you please provide a proper Git repository. We are here on Github, there is no need to share source-code as Zip files. |
Works fine
|
@juanda147 because you still haven't done what I've asked you to do twice already. |
Hey @marcj @marcus-sa first things first, thanks for the help here! really appreciate it since we're trying to run some quick POCs before migrating from One of them is a wrapper that we have for an external library ( So for some reason when you serialize the wrapper it returns nothing which causes an issue when afterwards it's deserialized as the By using Do we need to create the "mapping" using the Thanks in advance! |
@vany0114 can you show me how you annotated the member of You can use Alternatively you can register your own class serializer handler, see https://deepkit.io/documentation/runtime-types/custom-serializer import * as libphonenumber from 'google-libphonenumber';
import { serializer } from '@deepkit/type'; //default serializer used in cast/is/serialize/etc functions
serializer.serializeRegistry.registerClass(libphonenumber.PhoneNumber, (type, state) => {
// ${state.accessor} is the reference to the runtime PhoneNumber instance. do whatever to convert it to JSON serialisable structure like numbers/string/objects.
state.setContext({ phoneUtil: libphonenumber.PhoneNumberUtil.getInstance() });
state.addSetter(`phoneUtil.format(${state.accessor}, libphonenumber.PhoneNumberFormat.NATIONAL);`);
});
serializer.deserializeRegistry.registerClass(libphonenumber.PhoneNumber, (type, state) => {
// ${state.accessor} is the value set by the serialize code above (e.g. numbers/string/objects, whatever you used)
state.setContext({ phoneUtil: libphonenumber.PhoneNumberUtil.getInstance() });
state.addSetter(`phoneUtil.parse(${state.accessor}, region)`);
}); this way you can just use import { PhoneNumber } from 'google-libphonenumber';
class User {
phone?: PhoneNumber;
} and everything just works when doing if you also want to make serializer.typeGuards.getRegistry(1).registerClass(libphonenumber.PhoneNumber, (type, state) => {
// ${state.accessor} is the reference to the runtime PhoneNumber instance, do whatever to check if is valid by setting false/true
state.setContext({ phoneUtil: libphonenumber.PhoneNumberUtil.getInstance() });
state.addSetter(`phoneUtil.isPossibleNumber(${state.accessor}) === true && phoneUtil.isValidNumber(${state.accessor})`);
}); if you go with the way to make the default router.get('/user/phone-number/:number', (number: PhoneNumberUtil) {
number instanceof PhoneNumberUtil; // always true
});
# curl http://localhost/user/phone-number/12345456
# curl http://localhost/user/phone-number/invalid-number -> fails |
regarding the custom serializer, we might have to check if it works with packages without runtimes types like # my-types.ts
import { PhoneNumber } from 'google-libphonenumber';
export class Phone extends PhoneNumber {}
serializer.serializeRegistry.registerClass(Phone, (type, state) => {
//...
}); import { Phone } from './my-types.js';
export class User {
phone?: Phone;
} |
@marcj this is how we annotate it using And thanks for the detailed explanation, we'll give it a try! BTW has @deepkit/type a delegate similar to |
No, serializer.deserializeRegistry.registerClass(libphonenumber.PhoneNumber, (type, state) => {
// as described set the value via state.addSetter(`xy`);
});
serializer.deserializeRegistry.appendClass(libphonenumber.PhoneNumber, (type, state) => {
//state.accessor is the value xy now from previous step
state.addCode(`${state.accessor}.additionalCalls()`);
}); |
@marcj this is how it looks like after your suggestion about using a custom serializer, in this case, I just added the setter w/o doing anything else but just passing the current state. And you were right, I had to define the alias as well for it to work. serializer.serializeRegistry.registerClass(GooglePhone, (_, state) => {
state.addSetter(`${state.accessor}`);
});
serializer.deserializeRegistry.registerClass(GooglePhone, (_, state) => {
state.addSetter(state.accessor);
}); @marcj Thanks again, we'll probably keep bugging you as we continue with the migration to |
Hi, thanks for all your help so far. I was wondering if there is a replace for @f.type(MyClass) and @f.asName('') |
|
Hi Again, we've been facing an issue trying to deserialize a generic type. I added a sample here https://github.com/juanda147/deepkit-test/blob/main/playground/Marshal/DeserializeGeneric.ts . Our question is if we can get rid off the type parameter |
import { ClassType } from '@deepkit/core';
import { deserialize, resolveReceiveType } from '@deepkit/type';
const testDeserialized = <T>(payload: Record<string, unknown>, type: ClassType<T>): T => {
return deserialize(payload, undefined, undefined, undefined, resolveReceiveType(type));
};
class TestSource {
name: string = '';
}
const payload = { name: 23 };
const res = testDeserialized(payload, TestSource);
console.log(res); |
@juanda147 alternatively import { deserialize, resolveReceiveType, ReceiveType } from '@deepkit/type';
const testDeserialized = <T>(payload: Record<string, unknown>, type?: ReceiveType<T>): T => {
return deserialize(payload, undefined, undefined, undefined, resolveReceiveType(type));
};
class TestSource {
name: string = '';
}
const payload = { name: 23 };
const res = testDeserialized<TestSource>(payload);
console.log(res); |
I assume this code is wrong: serializer.serializeRegistry.registerClass(Order, (_, state) => {
state.addSetter(`${state.accessor}`);
}); it does basically nothing. It tells the serializer to use a custom serializer template for It's always better to provide fully functioning code examples/reproduction. This way I can precisely see what is going on, what is the expectation, and where the error is. With screenshots and snippets alone it's a guessing game. |
Hi, I'm working on POCs to migrate from @marcj/marshal to @deepkit/type . Following the steps here I should get a serialized object. I'm not doing anything complex, and I removed the @f annotation from the class just in case. Using the serialize function like below, I'm always getting:
"No type information received. Circular import or no runtime type available."
The text was updated successfully, but these errors were encountered: