| 886 | } |
| 887 | |
| 888 | Status ReadDictionary(const Buffer& metadata, IpcReadContext context, |
| 889 | DictionaryKind* kind, io::RandomAccessFile* file) { |
| 890 | const flatbuf::Message* message = nullptr; |
| 891 | RETURN_NOT_OK(internal::VerifyMessage(metadata.data(), metadata.size(), &message)); |
| 892 | const auto dictionary_batch = message->header_as_DictionaryBatch(); |
| 893 | if (dictionary_batch == nullptr) { |
| 894 | return Status::IOError( |
| 895 | "Header-type of flatbuffer-encoded Message is not DictionaryBatch."); |
| 896 | } |
| 897 | |
| 898 | // The dictionary is embedded in a record batch with a single column |
| 899 | const auto batch_meta = dictionary_batch->data(); |
| 900 | |
| 901 | CHECK_FLATBUFFERS_NOT_NULL(batch_meta, "DictionaryBatch.data"); |
| 902 | |
| 903 | RETURN_NOT_OK(GetCompression(batch_meta, &context.compression)); |
| 904 | if (context.compression == Compression::UNCOMPRESSED && |
| 905 | message->version() == flatbuf::MetadataVersion::MetadataVersion_V4) { |
| 906 | // Possibly obtain codec information from experimental serialization format |
| 907 | // in 0.17.x |
| 908 | RETURN_NOT_OK(GetCompressionExperimental(message, &context.compression)); |
| 909 | } |
| 910 | |
| 911 | const int64_t id = dictionary_batch->id(); |
| 912 | |
| 913 | // Look up the dictionary value type, which must have been added to the |
| 914 | // DictionaryMemo already prior to invoking this function |
| 915 | ARROW_ASSIGN_OR_RAISE(auto value_type, context.dictionary_memo->GetDictionaryType(id)); |
| 916 | |
| 917 | // Load the dictionary data from the dictionary batch |
| 918 | ArrayLoader loader(batch_meta, internal::GetMetadataVersion(message->version()), |
| 919 | context.options, file); |
| 920 | auto dict_data = std::make_shared<ArrayData>(); |
| 921 | const Field dummy_field("", value_type); |
| 922 | RETURN_NOT_OK(loader.Load(&dummy_field, dict_data.get())); |
| 923 | |
| 924 | // Run post-load steps: buffer decompression, etc. |
| 925 | RecordBatchLoader batch_loader{context, /*schema=*/nullptr, batch_meta->length(), |
| 926 | /*inclusion_mask=*/std::vector<bool>{}}; |
| 927 | ARROW_ASSIGN_OR_RAISE( |
| 928 | auto dict_columns, |
| 929 | batch_loader.CreateColumns({dict_data}, /*resolve_dictionaries=*/false)); |
| 930 | DCHECK_EQ(dict_columns.size(), 1); |
| 931 | dict_data = dict_columns[0]; |
| 932 | |
| 933 | if (dictionary_batch->isDelta()) { |
| 934 | if (kind != nullptr) { |
| 935 | *kind = DictionaryKind::Delta; |
| 936 | } |
| 937 | return context.dictionary_memo->AddDictionaryDelta(id, dict_data); |
| 938 | } |
| 939 | ARROW_ASSIGN_OR_RAISE(bool inserted, |
| 940 | context.dictionary_memo->AddOrReplaceDictionary(id, dict_data)); |
| 941 | if (kind != nullptr) { |
| 942 | *kind = inserted ? DictionaryKind::New : DictionaryKind::Replacement; |
| 943 | } |
| 944 | return Status::OK(); |
| 945 | } |
no test coverage detected