| 1 | # SPDX-License-Identifier: Apache-2.0 |
| 2 | # SPDX-FileCopyrightText: Copyright contributors to the vLLM project |
| 3 | """Unit tests for ECCPUConnectorMetadata.""" |
| 4 | |
| 5 | from vllm.distributed.ec_transfer.ec_connector.base import ECConnectorMetadata |
| 6 | from vllm.distributed.ec_transfer.ec_connector.cpu.common import ( |
| 7 | ECCPUConnectorMetadata, |
| 8 | ) |
| 9 | |
| 10 | |
| 11 | def test_metadata_is_ec_connector_metadata(): |
| 12 | """ECCPUConnectorMetadata must be a subclass of ECConnectorMetadata.""" |
| 13 | meta = ECCPUConnectorMetadata() |
| 14 | assert isinstance(meta, ECConnectorMetadata) |
| 15 | |
| 16 | |
| 17 | def test_metadata_initialization(): |
| 18 | """ECCPUConnectorMetadata initializes with empty saves and loads dicts.""" |
| 19 | meta = ECCPUConnectorMetadata() |
| 20 | assert hasattr(meta, "saves") |
| 21 | assert hasattr(meta, "loads") |
| 22 | assert meta.saves == {} |
| 23 | assert meta.loads == {} |
| 24 | |
| 25 | |
| 26 | def test_metadata_saves_dict_operations(): |
| 27 | """The saves dict supports standard dict operations.""" |
| 28 | meta = ECCPUConnectorMetadata() |
| 29 | |
| 30 | # Add multiple entries |
| 31 | meta.saves["mm_hash_1"] = [0, 1, 2] |
| 32 | meta.saves["mm_hash_2"] = [10, 11] |
| 33 | |
| 34 | assert "mm_hash_1" in meta.saves |
| 35 | assert "mm_hash_2" in meta.saves |
| 36 | assert len(meta.saves) == 2 |
| 37 | assert meta.saves["mm_hash_1"] == [0, 1, 2] |
| 38 | assert meta.saves["mm_hash_2"] == [10, 11] |
| 39 | |
| 40 | |
| 41 | def test_metadata_loads_carry_a_transfer_id_and_blocks(): |
| 42 | """Each load entry is a (transfer_id, block_ids) pair, so the worker can |
| 43 | report the transfer rather than the mm_hash.""" |
| 44 | meta = ECCPUConnectorMetadata() |
| 45 | |
| 46 | meta.loads["mm_hash_1"] = (0, [5, 6, 7]) |
| 47 | meta.loads["mm_hash_2"] = (1, [100]) |
| 48 | |
| 49 | assert len(meta.loads) == 2 |
| 50 | assert meta.loads["mm_hash_1"] == (0, [5, 6, 7]) |
| 51 | transfer_id, block_ids = meta.loads["mm_hash_2"] |
| 52 | assert transfer_id == 1 |
| 53 | assert block_ids == [100] |
| 54 | |
| 55 | |
| 56 | def test_metadata_saves_and_loads_are_independent(): |
| 57 | """Saves and loads dicts are independent.""" |
| 58 | meta = ECCPUConnectorMetadata() |
| 59 | |
| 60 | meta.saves["key"] = [1, 2] |
| 61 | meta.loads["key"] = (0, [3, 4]) |
| 62 | |
| 63 | # Same key but different dicts should not interfere |
| 64 | assert meta.saves["key"] == [1, 2] |
| 65 | assert meta.loads["key"] == (0, [3, 4]) |
| 66 | |
| 67 | # Modifying one should not affect the other |
| 68 | meta.saves["other"] = [99] |
| 69 | assert "other" not in meta.loads |
| 70 | |
| 71 | |
| 72 | def test_metadata_block_indices_are_integers(): |
| 73 | """Block indices in saves/loads lists should be integers.""" |
| 74 | meta = ECCPUConnectorMetadata() |
| 75 | |
| 76 | meta.saves["hash"] = [0, 100, 999, 65535] |
| 77 | meta.loads["hash"] = (0, [1, 2, 3]) |
| 78 | |
| 79 | for idx in meta.saves["hash"]: |
| 80 | assert isinstance(idx, int) |
| 81 | for idx in meta.loads["hash"][1]: |
| 82 | assert isinstance(idx, int) |
| 83 | |
| 84 | |
| 85 | def test_metadata_multiple_instances_are_independent(): |
| 86 | """Different ECCPUConnectorMetadata instances should not share state.""" |
| 87 | meta1 = ECCPUConnectorMetadata() |
| 88 | meta2 = ECCPUConnectorMetadata() |
| 89 | |
| 90 | meta1.saves["x"] = [1] |
| 91 | meta2.saves["y"] = [2] |
| 92 | |
| 93 | assert "x" in meta1.saves |
| 94 | assert "x" not in meta2.saves |
| 95 | assert "y" not in meta1.saves |
| 96 | assert "y" in meta2.saves |