| /* Licensed to the Apache Software Foundation (ASF) under one or more |
| * contributor license agreements. See the NOTICE file distributed with |
| * this work for additional information regarding copyright ownership. |
| * The ASF licenses this file to You under the Apache License, Version 2.0 |
| * (the "License"); you may not use this file except in compliance with |
| * the License. You may obtain a copy of the License at |
| * |
| * http://www.apache.org/licenses/LICENSE-2.0 |
| * |
| * Unless required by applicable law or agreed to in writing, software |
| * distributed under the License is distributed on an "AS IS" BASIS, |
| * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. |
| * See the License for the specific language governing permissions and |
| * limitations under the License. |
| */ |
| |
| #define C_LUCY_CHARBUF |
| #include "Lucy/Util/ToolSet.h" |
| |
| #include "Lucy/Test.h" |
| #include "Lucy/Test/Store/TestCompoundFileWriter.h" |
| #include "Lucy/Store/CompoundFileWriter.h" |
| #include "Lucy/Store/FileHandle.h" |
| #include "Lucy/Store/OutStream.h" |
| #include "Lucy/Store/RAMFolder.h" |
| #include "Lucy/Util/Json.h" |
| |
| static CharBuf cfmeta_file = ZCB_LITERAL("cfmeta.json"); |
| static CharBuf cfmeta_temp = ZCB_LITERAL("cfmeta.json.temp"); |
| static CharBuf cf_file = ZCB_LITERAL("cf.dat"); |
| static CharBuf foo = ZCB_LITERAL("foo"); |
| static CharBuf bar = ZCB_LITERAL("bar"); |
| static CharBuf seg_1 = ZCB_LITERAL("seg_1"); |
| |
| static Folder* |
| S_folder_with_contents() { |
| RAMFolder *folder = RAMFolder_new(&seg_1); |
| OutStream *foo_out = RAMFolder_Open_Out(folder, &foo); |
| OutStream *bar_out = RAMFolder_Open_Out(folder, &bar); |
| OutStream_Write_Bytes(foo_out, "foo", 3); |
| OutStream_Write_Bytes(bar_out, "bar", 3); |
| OutStream_Close(foo_out); |
| OutStream_Close(bar_out); |
| DECREF(foo_out); |
| DECREF(bar_out); |
| return (Folder*)folder; |
| } |
| |
| static void |
| test_Consolidate(TestBatch *batch) { |
| Folder *folder = S_folder_with_contents(); |
| FileHandle *fh; |
| |
| // Fake up detritus from failed consolidation. |
| fh = Folder_Open_FileHandle(folder, &cf_file, |
| FH_CREATE | FH_WRITE_ONLY | FH_EXCLUSIVE); |
| DECREF(fh); |
| fh = Folder_Open_FileHandle(folder, &cfmeta_temp, |
| FH_CREATE | FH_WRITE_ONLY | FH_EXCLUSIVE); |
| DECREF(fh); |
| |
| CompoundFileWriter *cf_writer = CFWriter_new(folder); |
| CFWriter_Consolidate(cf_writer); |
| PASS(batch, "Consolidate completes despite leftover files"); |
| DECREF(cf_writer); |
| |
| TEST_TRUE(batch, Folder_Exists(folder, &cf_file), |
| "cf.dat file written"); |
| TEST_TRUE(batch, Folder_Exists(folder, &cfmeta_file), |
| "cfmeta.json file written"); |
| TEST_FALSE(batch, Folder_Exists(folder, &foo), |
| "original file zapped"); |
| TEST_FALSE(batch, Folder_Exists(folder, &cfmeta_temp), |
| "detritus from failed consolidation zapped"); |
| |
| DECREF(folder); |
| } |
| |
| static void |
| test_offsets(TestBatch *batch) { |
| Folder *folder = S_folder_with_contents(); |
| CompoundFileWriter *cf_writer = CFWriter_new(folder); |
| Hash *cf_metadata; |
| Hash *files; |
| |
| CFWriter_Consolidate(cf_writer); |
| |
| cf_metadata = (Hash*)CERTIFY( |
| Json_slurp_json(folder, &cfmeta_file), HASH); |
| files = (Hash*)CERTIFY( |
| Hash_Fetch_Str(cf_metadata, "files", 5), HASH); |
| |
| CharBuf *file; |
| Obj *filestats; |
| bool_t offsets_ok = true; |
| |
| TEST_TRUE(batch, Hash_Get_Size(files) > 0, "Multiple files"); |
| |
| Hash_Iterate(files); |
| while (Hash_Next(files, (Obj**)&file, &filestats)) { |
| Hash *stats = (Hash*)CERTIFY(filestats, HASH); |
| Obj *offset = CERTIFY(Hash_Fetch_Str(stats, "offset", 6), OBJ); |
| int64_t offs = Obj_To_I64(offset); |
| if (offs % 8 != 0) { |
| offsets_ok = false; |
| FAIL(batch, "Offset %" I64P " for %s not a multiple of 8", |
| offset, CB_Get_Ptr8(file)); |
| break; |
| } |
| } |
| if (offsets_ok) { |
| PASS(batch, "All offsets are multiples of 8"); |
| } |
| |
| DECREF(cf_metadata); |
| DECREF(cf_writer); |
| DECREF(folder); |
| } |
| |
| void |
| TestCFWriter_run_tests() { |
| TestBatch *batch = TestBatch_new(7); |
| |
| TestBatch_Plan(batch); |
| test_Consolidate(batch); |
| test_offsets(batch); |
| |
| DECREF(batch); |
| } |
| |
| |