Skip to content

Commit b7604cb

Browse files
committed
Finalize tests
1 parent 72c2f35 commit b7604cb

File tree

5 files changed

+70
-50
lines changed

5 files changed

+70
-50
lines changed

src/apify/_actor.py

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -204,9 +204,10 @@ async def __aenter__(self) -> Self:
204204
if not Actor.is_at_home():
205205
# Make sure that the input related KVS is initialized to ensure that the input aware client is used
206206
await self.open_key_value_store()
207-
208-
# Load non-default aliased storages from configuration
209-
await AliasResolver.register_aliases(configuration=self.configuration)
207+
else:
208+
# Load pre-existing non-default aliased storages from configuration
209+
# Supported only on the Apify platform, where those storages are pre-created by the platform.
210+
await AliasResolver.register_aliases(configuration=self.configuration)
210211
return self
211212

212213
async def __aexit__(

src/apify/storage_clients/_apify/_alias_resolving.py

Lines changed: 9 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -291,15 +291,12 @@ async def register_aliases(cls, configuration: Configuration) -> None:
291291
)._storage_key
292292
] = storage_id
293293

294-
if configuration.is_at_home:
295-
# Bulk update the mapping in the default KVS with the configuration mapping.
296-
client = await cls._get_default_kvs_client(configuration=configuration)
297-
existing_mapping = ((await client.get_record(cls._ALIAS_MAPPING_KEY)) or {'value': {}}).get('value', {})
298-
# Update the existing mapping with the configuration mapping.
299-
existing_mapping.update(configuration_mapping)
300-
# Store the updated mapping back in the KVS and in memory.
301-
await client.set_record(cls._ALIAS_MAPPING_KEY, existing_mapping)
302-
cls._alias_map = existing_mapping
303-
else:
304-
# Update only in-memory mapping when not at home
305-
cls._alias_map.update(configuration_mapping)
294+
# Bulk update the mapping in the default KVS with the configuration mapping.
295+
client = await cls._get_default_kvs_client(configuration=configuration)
296+
existing_mapping = ((await client.get_record(cls._ALIAS_MAPPING_KEY)) or {'value': {}}).get('value', {})
297+
298+
# Update the existing mapping with the configuration mapping.
299+
existing_mapping.update(configuration_mapping)
300+
# Store the updated mapping back in the KVS and in memory.
301+
await client.set_record(cls._ALIAS_MAPPING_KEY, existing_mapping)
302+
cls._alias_map.update(existing_mapping)

tests/integration/test_storages.py

Lines changed: 53 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,17 @@
11
from __future__ import annotations
22

33
import asyncio
4+
from typing import cast
45

56
import pytest
67

78
from crawlee import service_locator
89
from crawlee.storages import Dataset, KeyValueStore, RequestQueue
910

1011
from apify import Actor, Configuration
12+
from apify._configuration import ActorStorages
1113
from apify.storage_clients import ApifyStorageClient, MemoryStorageClient, SmartApifyStorageClient
14+
from apify.storage_clients._apify._alias_resolving import AliasResolver
1215

1316

1417
@pytest.mark.parametrize(
@@ -125,3 +128,53 @@ async def test_actor_implicit_storage_init(apify_token: str) -> None:
125128
assert await Actor.open_dataset() is not await Actor.open_dataset(force_cloud=True)
126129
assert await Actor.open_key_value_store() is not await Actor.open_key_value_store(force_cloud=True)
127130
assert await Actor.open_request_queue() is not await Actor.open_request_queue(force_cloud=True)
131+
132+
133+
async def test_actor_storages_alias_resolving(apify_token: str) -> None:
134+
"""Test that `AliasResolver.register_aliases` correctly updates default KVS with Actor storages."""
135+
136+
# Actor storages
137+
datasets = {'default': 'default_dataset_id', 'custom': 'custom_dataset_id'}
138+
request_queues = {'default': 'default_dataset_id', 'custom': 'custom_dataset_id'}
139+
key_value_stores = {'default': 'default_dataset_id', 'custom': 'custom_dataset_id'}
140+
141+
# Set up the configuration and storage client for the test
142+
configuration = Configuration(
143+
default_key_value_store_id='default_kvs_id',
144+
token=apify_token,
145+
actor_storages=ActorStorages(
146+
datasets=datasets, request_queues=request_queues, key_value_stores=key_value_stores
147+
),
148+
)
149+
storage_client = ApifyStorageClient()
150+
service_locator.set_configuration(configuration)
151+
service_locator.set_storage_client(storage_client)
152+
153+
client_cache_key = cast('tuple', storage_client.get_storage_client_cache_key(configuration))[-1]
154+
# Add some unrelated pre-existing alias mapping (it should be preserved after registering aliases)
155+
pre_existing_mapping = {f'KeyValueStore,pre_existing_alias,{client_cache_key}': 'pre_existing_id'}
156+
157+
default_kvs = await KeyValueStore.open(configuration=configuration, storage_client=storage_client)
158+
await default_kvs.set_value(AliasResolver._ALIAS_MAPPING_KEY, pre_existing_mapping)
159+
160+
# Construct the expected mapping
161+
expected_mapping = {}
162+
for storage_type, storage_map in (
163+
('Dataset', datasets),
164+
('KeyValueStore', key_value_stores),
165+
('RequestQueue', request_queues),
166+
):
167+
for storage_alias, storage_id in storage_map.items():
168+
expected_mapping[
169+
','.join(
170+
(storage_type, '__default__' if storage_alias == 'default' else storage_alias, client_cache_key)
171+
)
172+
] = storage_id
173+
expected_mapping.update(pre_existing_mapping)
174+
175+
try:
176+
configuration.default_key_value_store_id = default_kvs.id
177+
await AliasResolver.register_aliases(configuration=configuration)
178+
assert await default_kvs.get_value(AliasResolver._ALIAS_MAPPING_KEY) == expected_mapping
179+
finally:
180+
await default_kvs.drop()

tests/unit/actor/test_configuration.py

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -306,9 +306,9 @@ def test_actor_storage_json_env_var(monkeypatch: pytest.MonkeyPatch) -> None:
306306
"""Test that actor_storages_json is parsed from JSON env var."""
307307
import json
308308

309-
datasets = {"default": "default_dataset_id", "custom": "custom_dataset_id"}
310-
request_queues = {"default": "default_dataset_id", "custom": "custom_dataset_id"}
311-
key_value_stores = {"default": "default_dataset_id", "custom": "custom_dataset_id"}
309+
datasets = {'default': 'default_dataset_id', 'custom': 'custom_dataset_id'}
310+
request_queues = {'default': 'default_dataset_id', 'custom': 'custom_dataset_id'}
311+
key_value_stores = {'default': 'default_dataset_id', 'custom': 'custom_dataset_id'}
312312

313313
actor_storages_json = json.dumps(
314314
{

tests/unit/storage_clients/test_alias_resolver.py

Lines changed: 1 addition & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,6 @@
11
from __future__ import annotations
22

3-
from crawlee import service_locator
4-
5-
from apify import Actor
6-
from apify._configuration import Configuration, ActorStorages
7-
from apify.storage_clients import SmartApifyStorageClient, ApifyStorageClient
3+
from apify._configuration import Configuration
84
from apify.storage_clients._apify._alias_resolving import AliasResolver
95

106

@@ -80,30 +76,3 @@ async def test_get_alias_map_returns_in_memory_map() -> None:
8076
AliasResolver._alias_map = {}
8177
result = await AliasResolver._get_alias_map(config)
8278
assert result == {}
83-
84-
85-
async def test_register_aliases() -> None:
86-
"""Test that _get_alias_map loads the map from KVS when at home.
87-
88-
AliasResolver works locally only """
89-
90-
91-
datasets = {"default": "default_dataset_id", "custom": "custom_dataset_id"}
92-
request_queues = {"default": "default_dataset_id", "custom": "custom_dataset_id"}
93-
key_value_stores = {"default": "default_dataset_id", "custom": "custom_dataset_id"}
94-
95-
config = Configuration(is_at_home=False,
96-
token='test-token',
97-
actor_storages= ActorStorages(
98-
datasets = datasets,
99-
request_queues = request_queues,
100-
key_value_stores = key_value_stores
101-
),
102-
)
103-
storage_client = ApifyStorageClient()
104-
service_locator.set_storage_client(
105-
SmartApifyStorageClient(local_storage_client=storage_client, cloud_storage_client=storage_client)
106-
)
107-
async with Actor(configuration=config):
108-
d = await Actor.open_dataset(alias='default')
109-
assert d

0 commit comments

Comments
 (0)