Skip to content

Commit f1e90ed

Browse files
committed
Modify asset HREFs based on catalog type.
Previously only link href types (absolute vs relative) were modified as part of the `Catalog.save` process based on the catalog types: for ABSOLUTE_PUBLISHED, all link hrefs were made absolute, etc. The asset HREFs were not modified, which was counter to the expected result outlined in stac-utils/stactools#31. This change causes asset HREFs to also be changed to absolute or relative based on the catalog type. Note that if the asset HREF cannot be made relative, e.g. the asset HREF points to an HTTP location and the item is being stored locally, then the HREF is left unchanged.
1 parent abfa723 commit f1e90ed

File tree

3 files changed

+19
-2
lines changed

3 files changed

+19
-2
lines changed

docs/concepts.rst

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -101,7 +101,7 @@ Catalog Types
101101

102102
The STAC `best practices document <https://github.com/radiantearth/stac-spec/blob/v1.0.0-beta.2/best-practices.md>`_ lays out different catalog types, and how their links should be formatted. A brief description is below, but check out the document for the official take on these types:
103103

104-
Note that the catalog types do not dictate the asset HREF formats, only link formats. Asset HREFs in any catalog type can be relative or absolute; see the section on :ref:`rel vs abs asset` below.
104+
The catalog types will also dictate the asset HREF formats. Asset HREFs in any catalog type can be relative or absolute may be absolute depending on their location; see the section on :ref:`rel vs abs asset` below.
105105

106106

107107
Self-Contained Catalogs

pystac/catalog.py

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -608,8 +608,10 @@ def save(self, catalog_type=None):
608608
# Ensure relative vs absolute
609609
if catalog_type == CatalogType.ABSOLUTE_PUBLISHED:
610610
self.make_all_links_absolute()
611+
self.make_all_asset_hrefs_absolute()
611612
elif catalog_type in (CatalogType.SELF_CONTAINED, CatalogType.RELATIVE_PUBLISHED):
612613
self.make_all_links_relative()
614+
self.make_all_asset_hrefs_relative()
613615
else:
614616
raise ValueError(f'catalog_type is not a CatalogType: "{catalog_type}"')
615617

tests/test_writing.py

Lines changed: 16 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33

44
from pystac import (STAC_IO, STACObject, Collection, CatalogType, LinkType)
55
from pystac.serialization import (STACObjectType)
6-
from pystac.utils import make_absolute_href
6+
from pystac.utils import is_absolute_href, make_absolute_href, make_relative_href
77
from pystac.validation import validate_dict
88

99
from tests.utils import TestCases
@@ -31,13 +31,28 @@ def validate_file(self, path, object_type):
3131
return validate_dict(d, object_type)
3232

3333
def validate_link_types(self, root_href, catalog_type):
34+
def validate_asset_href_type(item, item_href, link_type):
35+
for asset in item.assets.values():
36+
if link_type == LinkType.ABSOLUTE:
37+
self.assertTrue(is_absolute_href(asset.href))
38+
else:
39+
is_valid = not is_absolute_href(asset.href)
40+
if not is_valid:
41+
# If the item href and asset href don't share
42+
# the same root, the asset href must be absolute
43+
rel_href = make_relative_href(asset.href, item_href)
44+
self.assertEqual(asset.href, rel_href)
45+
else:
46+
self.assertTrue(is_valid)
3447
def validate_item_link_type(href, link_type, should_include_self):
3548
item_dict = STAC_IO.read_json(href)
3649
item = STACObject.from_file(href)
3750
for link in item.get_links():
3851
if not link.rel == 'self':
3952
self.assertEqual(link.link_type, link_type)
4053

54+
validate_asset_href_type(item, href, link_type)
55+
4156
rels = set([link['rel'] for link in item_dict['links']])
4257
self.assertEqual('self' in rels, should_include_self)
4358

0 commit comments

Comments
 (0)