theweipeng commented on PR #1675:
URL: https://github.com/apache/fury/pull/1675#issuecomment-2205736393

   > Hi, @theweipeng , Please have a look at my PR. I have been trying to 
adjust the object.test.ts files so as to pass the pipline tests but i really 
don't know the `writeStmt` and `readStmt` functions are tested in the 
objects.test.ts files. Please help me with a few hints.
   
   First, let me explain why we need to generate code, which is necessary for a 
general understanding.
   
   Without generating code for each object type, the JavaScript would look like 
this:
   ```JavaScript
    function writeObject(input, writer, description) {
        description.fields.forEach(field => {
            const binary = metaString.encode(field.name);
            writer.write(binary);
        });
        description.fields.forEach(field => {
            writeXxxx(input[field.name], writer, field.description);
        });
    }
    ```
   In this pseudo-code, the function writeObject calls metaString.encode every 
time and iterating over description.fields is unnecessary. Performance is very 
important for Fury.
   
   If we generate code for each object type, the JavaScript will look like this:
   ```JavaScript
    const metaBinary = description.fields.map(field => 
metaString.encode(field.name)).join(/* code to join the binary data */);
    function writeObject(input, writer) {
        writer.write(metaBinary);
        writeString(input.b);
        writeBoolean(input.c);
    }
    ```
   In this pseudo-code, metaBinary is called only once when writeObject is 
created, and we can avoid all overhead except for the necessary write buffer.
   
   writeStmt is used to generate a code fragment that will be embedded by the 
function toSerializer, declared in BaseSerializerGenerator.
   
   For example, a description like the one below will generate code when 
registerSerializer is called:
   ```JavaScript
    const description = Type.object('example.foo', {
        b: Type.string(),
        c: Type.bool()
    });
    
    const fury = new Fury({ refTracking: true });
    const serializer = fury.registerSerializer(description).serializer;
   ```
   The call chain will be generateSerializer(gen/index.ts) -> 
generate(gen/index.ts) -> generator.toSerializer(gen/index.ts) -> 
toSerializer(gen/serializer.ts) -> writeStmt(gen/object.ts). `funcString` 
declared in generate(gen/index.ts) store the final code. 
   
   writeStmt iterates through the properties defined in the description (in the 
example, they are b and c) and generates the code based on the property's 
description.
   
   In this example, prop b will call writeStmt declared in gen/string.ts.
   
   You can add a script for debugging like this:
   
   
https://github.com/apache/fury/assets/16490211/2c1f7b34-a4bd-4774-bc26-556b80a89c02
   
   And click Debug:
   
   
https://github.com/apache/fury/assets/16490211/77d67ae8-042a-4ae1-b878-9de39777fb49
   
   The test will pause at the breakpoint, allowing you to trace the call chain 
by debugging the code generator.
   
   In your case, you should create a write instance for meta inside a closure, 
thus allowing direct writing of the meta binary.
   
   For instance:
   ```JavaScript
   const metaBinary = this.scope.declare("metaBinary", 
`${metaString.encode(JSON.stringify(description))}`); // This line declares a 
variable inside a closure.
   return `
   ${this.builder.writer.binary(metaBinary)};
   `;
   ```
   tagWriter is in a similar situation; this should be helpful to you:
   
   
https://github.com/apache/fury/assets/16490211/401e9f36-09c6-4204-9102-b115fac9631a


-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to