如何为DatumWriter设置“字符集”||将包含阿拉伯字符的avro写入HDFS

0g0grzrc  于 2022-12-09  发布在  HDFS
关注(0)|答案(1)|浏览(224)

有些数据包含阿拉伯格式的值,当写入数据时,读卡器代码/hadoop fs -text命令显示??而不是阿拉伯字符。

1)编写器

  1. // avro object is provided as SpecificRecordBase
  2. Path path = new Path(pathStr);
  3. DatumWriter<SpecificRecord> datumWriter = new SpecificDatumWriter<>();
  4. FileSystem fs = FileSystem.get(URI.create(hdfsUri), conf); // HDFS File System
  5. FSDataOutputStream outputStream = fs.create(path);
  6. DataFileWriter<SpecificRecord> dataFileWriter = new DataFileWriter<>(datumWriter);
  7. Schema schema = getSchema(); // method to get schema
  8. dataFileWriter.setCodec(CodecFactory.snappyCodec());
  9. dataFileWriter.create(schema, outputStream);
  10. dataFileWriter.append(avroObject);

2)读取器

  1. Configuration conf = new Configuration();
  2. FsInput in = new FsInput(new Path(hdfsFilePathStr), conf);
  3. DatumReader<Row> datumReader = new GenericDatumReader<>();
  4. DataFileReader<Row> dataFileReader = new DataFileReader<>(in, datumReader);
  5. GenericRecord outputData = (GenericRecord) dataFileReader.iterator.next();

我已经尝试了hadoop fs -text {filePath}命令,也有阿拉伯语的值显示为??.
更改数据写入的格式确实很困难,因为同一文件有许多使用者。
已尝试阅读SpecificRecordBase,但仍获得??.

编辑

也尝试过这些(在读者和作家):

  1. Configuration conf = new Configuration();
  2. conf.set("file.encoding", StandardCharsets.UTF_16.displayName());

以及

  1. System.setProperty("file.encoding", StandardCharsets.UTF_16.displayName());

没用的。

u7up0aaq

u7up0aaq1#

显然,HDFS不支持很多非英语字符。要解决这个问题,请在avro模式中将字段从String更改为bytes
要将值从String转换为bytes,请用途:
ByteBuffer.wrap(str.getBytes(StandardCharsets.UTF_8)) .
然后,在阅读时,要将其转换回String,请用途:
new String(byteData.array(), StandardCharsets.UTF_8) .
读取器和写入器中的其余代码保持不变。
这样做,对于英语字符,hadooop fs -text命令将显示正确的文本,但对于非英语字符,它可能会显示乱码,但您的读者仍然能够从ByteBuffer创建UTF-8字符串。

相关问题