I'm writing a nodeJs application that uses google flat buffer.
I installed flatc on my macbook pro and compiled the following schema:
namespace MyAlcoholist;
table Drink {
drink_type_name: string;
drink_company_name: string;
drink_brand_name: string;
drink_flavor_type_name : string;
liquid_color_type_name : string;
liquid_color_is_transparent : bool;
alcohol_vol : float;
calories_for_100g : uint;
global_image_id: ulong;
drink_flavor_id: ulong;
}
table Drinks { drinks:[Drink]; }
root_type Drinks;
the schema file is called drink.fbs and it generated a javascript file called drink_generated.js
I include this file in my nodejs application and add data to it using the following code.. this is my flatBufferUtil.js utility file.
var flatbuffers = require('../js/flatbuffers').flatbuffers;
var builder = new flatbuffers.Builder();
var drinks = require('../fbs/drinks_generated').MyAlcoholist; // Generated by `flatc`.
function drinkArrayToBuffer(drinkArray) {
var drinksVectArray = [];
drinkArray.forEach(function (element, index, array) {
var drinkObj = element;
var drinkBrandName = builder.createString(drinkObj.drink_brand_name);
var drinkCompanyName = builder.createString(drinkObj.drink_company_name);
var drinkflavorTypeName = builder.createString(drinkObj.drink_flavor_type_name);
var drinkTypeName = builder.createString(drinkObj.drink_type_name);
var liquidColorTypeName = builder.createString(drinkObj.liquid_color_type_name);
drinks.Drink.startDrink(builder);
drinks.Drink.addAlcoholVol(builder, drinkObj.alcohol_vol);
drinks.Drink.addCaloriesFor100g(builder,drinkObj.calories_for_100g);
drinks.Drink.addDrinkBrandName(builder,drinkBrandName);
drinks.Drink.addDrinkCompanyName(builder,drinkCompanyName);
drinks.Drink.addDrinkFlavorId(builder,drinkObj.drink_flavor_id);
drinks.Drink.addDrinkFlavorTypeName(builder, drinkflavorTypeName);
drinks.Drink.addDrinkTypeName(builder,drinkTypeName);
drinks.Drink.addGlobalImageId(builder,drinkObj.global_image_id);
drinks.Drink.addLiquidColorIsTransparent(builder,drinkObj.is_transparent);
drinks.Drink.addLiquidColorTypeName(builder,liquidColorTypeName);
var drink = drinks.Drink.endDrink(builder);
drinksVectArray.push(drink);
})
var drinksVect = drinks.createDrinksVector(builder,drinksVectArray);
builder.finish(drinksVect);
var buf = builder.dataBuffer();
return buf;
}
module.exports.drinkArrayToBuffer=drinkArrayToBuffer;
now when I execute this function it fails with the error flatbuffers is not defined
.
I debugged my code and I saw that it files on the following line of code:
drinks.Drink.addDrinkFlavorId(builder,drinkObj.drink_flavor_id);
if i get inside addDrinkFlavorId function i see this code in drinks_generted.js:
MyAlcoholist.Drink.addDrinkFlavorId = function(builder, drinkFlavorId) {
builder.addFieldInt64(9, drinkFlavorId, flatbuffers.Long.ZERO);
};
as you can see it uses flatbuffers.Long.ZERO
but flatbuffers is not defined in that file at all. the compilation did not provide any errors so what do I miss?
It seems to me like it is a bug... The generated file appears to be meant to exist autonomously from the flatbuffers
require. However for the custom flatbuffers.Long
class, the default of flatbuffers.Long.ZERO
bleeds into the generated file.
While this isn't a solution per-say, one workaround is to manually add the flatbuffers require to the generated file; it's ugly, but it might be better than being blocked until a more appropriate answer (or fix) comes around.
// In `drinks_generated.js`
var flatbuffers = require('../js/flatbuffers').flatbuffers;
Note:
The drinks.Drink.addDrinkFlavorId()
and drinks.Drink.addGlobalImageId()
functions expect flatbuffers.Long
values to be passed into them, because they were specified as ulong
in the schema (fbs
file). So you will need to ensure that you are not trying to pass in a simple number
type.
For example:
var my_long = flatbuffers.Long(100, 0); // low = 100, high = 0
drinks.Drink.addDrinkFlavorId(builder, my_long);
As a result, another possible workaround is to change the datatype of those fields in the schema to avoid using ulong
until it becomes more clear what is going on here.
P.S. I am pretty sure drinks.createDrinksVector
on line 30 of that snippet should be drinks.Drinks.createDrinksVector
.