UNPKG

pubsub-tool

Version:

Producer and Consumer Tool for every streaming component

101 lines (95 loc) 2.73 kB
/** * 專案名稱: PubSub Tool * 部門代號: ML8100 * 檔案說明: Confluent Avro解析策略 * @CREATE Fri Nov 27 2020 上午7:58:03 * @author Steve Y Lin * @contact Steve_Y_Lin@wistron.com #1342 * ----------------------------------------------------------------------------- * @NOTE */ import * as avro from 'avsc'; import { SchemaRegistry } from '../schema-registry'; import { AvroResolveStrategy } from './avro-resolve.strategy'; /** * Confluent Avro解析策略 */ export class ConfluentAvroStrategy implements AvroResolveStrategy { /** * 進行Avro編碼 * * @method private * @param schema Avro Schema * @param schemaId Schema ID * @param obj 要進行編碼的資料 * @return 回傳編碼結果 */ private encoded(schema: any, schemaId: number, obj: any): Buffer { let buf: Buffer; const type = avro.Type.forSchema(schema); if (typeof obj === 'string') { buf = type.toBuffer(JSON.parse(obj)); } else { buf = type.toBuffer(obj); } const result = Buffer.alloc(buf.length + 5); result.writeUInt8(0, 0); result.writeUInt32BE(schemaId, 1); buf.copy(result, 5); return result; } /** * 將JSON物件轉Avro * * @method public * @param schemaRegistry Schema Registry * @param topic Topic * @param json JSON物件 * @return 回傳轉換後的Avro */ public async toAvro( schemaRegistry: SchemaRegistry, topic: string, json: any | any[] ): Promise<Buffer | Buffer[]> { const schemaId = await schemaRegistry.getLatestSchemaId(topic); const res = await schemaRegistry.getSchemaById(schemaId); const schema = JSON.parse(res.schema); const results: Buffer[] = []; if (Array.isArray(json)) { json.forEach((obj) => { const result = this.encoded(schema, schemaId, obj); results.push(result); }); return results; } else { return this.encoded(schema, schemaId, json); } } /** * 從Avro轉JSON物件 * * @method public * @param schema Avro Schema * @param buffer Avro * @return 回傳轉換後的JSON物件 */ public async toJson<T>( schemaRegistry: SchemaRegistry, buffer: Buffer ): Promise<T> { try { if (buffer.readUInt8(0) === 0) { const schemaId = buffer.readUInt32BE(1); const res = await schemaRegistry.getSchemaById(schemaId); const schema = JSON.parse(res.schema); const type = avro.Type.forSchema(schema); return type.fromBuffer(buffer.slice(5)); } else { throw new Error(`Not Avro Encoded Message: ${JSON.stringify(buffer)}`); } } catch (error) { return error; } } }