Add source namespace to all generated linkml schemas

change `namespace` annotation to `is_namespace` and use `namespace` for name of namespace
dont change commit when commit is None - otherwise always reset to recent version when we don't intend to
This commit is contained in:
sneakers-the-rat 2023-10-11 20:03:08 -07:00
parent c6ca97e010
commit d9d62618bc
8 changed files with 43 additions and 22 deletions

View file

@ -73,14 +73,14 @@ class NamespacesAdapter(Adapter):
if progress is not None: if progress is not None:
try: try:
progress.update(sch.namespace, action=sch.name) progress.update(sch.namespace, action=sch.name)
except KeyError: except KeyError: # pragma: no cover
# happens when we skip builds due to cachine # happens when we skip builds due to caching
pass pass
sch_result += sch.build() sch_result += sch.build()
if progress is not None: if progress is not None:
try: try:
progress.update(sch.namespace, advance=1) progress.update(sch.namespace, advance=1)
except KeyError: except KeyError: # pragma: no cover
# happens when we skip builds due to caching # happens when we skip builds due to caching
pass pass
@ -113,7 +113,7 @@ class NamespacesAdapter(Adapter):
description = ns.doc, description = ns.doc,
version = ns.version, version = ns.version,
imports=ns_schemas, imports=ns_schemas,
annotations=[{'tag': 'namespace', 'value': True}] annotations=[{'tag': 'is_namespace', 'value': True}, {'tag': 'namespace', 'value': ns.name}]
) )
sch_result.schemas.append(ns_schema) sch_result.schemas.append(ns_schema)

View file

@ -72,7 +72,7 @@ class SchemaAdapter(Adapter):
for group in self.groups: for group in self.groups:
res += GroupAdapter(cls=group).build() res += GroupAdapter(cls=group).build()
if len(res.slots) > 0: if len(res.slots) > 0: # pragma: no cover - hard to induce this error because the child classes don't fuck up like this
raise RuntimeError('Generated schema in this translation can only have classes, all slots should be attributes within a class') raise RuntimeError('Generated schema in this translation can only have classes, all slots should be attributes within a class')
sch = SchemaDefinition( sch = SchemaDefinition(
@ -82,7 +82,8 @@ class SchemaAdapter(Adapter):
classes=res.classes, classes=res.classes,
slots=res.slots, slots=res.slots,
types=res.types, types=res.types,
version=self.version version=self.version,
annotations=[{'tag': 'is_namespace', 'value': False}, {'tag': 'namespace', 'value': self.namespace}]
) )
# every schema needs the language elements # every schema needs the language elements
sch.imports.append('.'.join([self.namespace, 'nwb.language'])) sch.imports.append('.'.join([self.namespace, 'nwb.language']))

View file

@ -328,7 +328,7 @@ class NWBPydanticGenerator(PydanticGenerator):
if not self.split: if not self.split:
# we are compiling this whole thing in one big file so we don't import anything # we are compiling this whole thing in one big file so we don't import anything
return {} return {}
if 'namespace' in sv.schema.annotations.keys() and sv.schema.annotations['namespace']['value'] == 'True': if 'is_namespace' in sv.schema.annotations.keys() and sv.schema.annotations['is_namespace']['value'] == 'True':
return self._get_namespace_imports(sv) return self._get_namespace_imports(sv)
all_classes = sv.all_classes(imports=True) all_classes = sv.all_classes(imports=True)

View file

@ -135,18 +135,16 @@ class GitRepo:
@commit.setter @commit.setter
def commit(self, commit:str|None): def commit(self, commit:str|None):
# first get out of a potential detached head state # setting commit as None should do nothing if we have already cloned,
# that would cause a call to "HEAD" to fail in unexpected ways # and if we are just cloning we will always be at the most recent commit anyway
if self.detached_head: if commit is not None:
self._git_call('checkout', self.default_branch) # first get out of a potential detached head state
# that would cause a call to "HEAD" to fail in unexpected ways
if self.detached_head:
self._git_call('checkout', self.default_branch)
if commit is None:
if len(self.namespace.versions) > 0:
self._git_call('checkout', self.namespace.versions[-1])
else:
self._git_call('checkout', "HEAD")
else:
self._git_call('checkout', commit) self._git_call('checkout', commit)
self._git_call('submodule', 'update', '--init', '--recursive') self._git_call('submodule', 'update', '--init', '--recursive')
self._commit = commit self._commit = commit
@ -277,7 +275,6 @@ class GitRepo:
self.cleanup() self.cleanup()
else: else:
# already have it, just ensure commit and return # already have it, just ensure commit and return
self.commit = self.commit self.commit = self.commit
return return
elif self.temp_directory.exists(): elif self.temp_directory.exists():

View file

@ -384,7 +384,7 @@ class LinkMLProvider(Provider):
# write schemas to yaml files # write schemas to yaml files
build_result = {} build_result = {}
namespace_sch = [sch for sch in built.schemas if 'namespace' in sch.annotations.keys()] namespace_sch = [sch for sch in built.schemas if sch.annotations.get('is_namespace', False) and sch.annotations['is_namespace'].value == 'True']
for ns_linkml in namespace_sch: for ns_linkml in namespace_sch:
version = ns_adapter.versions[ns_linkml.name] version = ns_adapter.versions[ns_linkml.name]
version_path = self.namespace_path(ns_linkml.name, version, allow_repo=False) version_path = self.namespace_path(ns_linkml.name, version, allow_repo=False)

View file

@ -220,7 +220,7 @@ def linkml_schema_bare() -> TestSchemas:
id="namespace", id="namespace",
version="1.1.1", version="1.1.1",
default_prefix="namespace", default_prefix="namespace",
annotations={'namespace': {'tag': 'namespace', 'value': 'True'}}, annotations=[{'tag': 'is_namespace', 'value': 'True'}, {'tag': 'namespace', 'value': 'core'}],
description="A namespace package that should import all other classes", description="A namespace package that should import all other classes",
imports=['core', 'imported'] imports=['core', 'imported']
) )

View file

@ -1,3 +1,5 @@
import pdb
import pytest import pytest
from ..fixtures import nwb_core_fixture from ..fixtures import nwb_core_fixture
from nwb_schema_language import Dataset, Group from nwb_schema_language import Dataset, Group
@ -33,3 +35,13 @@ def test_populate_imports(nwb_core_fixture):
def test_build(nwb_core_fixture): def test_build(nwb_core_fixture):
pass pass
def test_skip_imports(nwb_core_fixture):
"""
We can build just the namespace in question without also building the other namespaces that it imports
"""
res = nwb_core_fixture.build(skip_imports=True)
# we shouldn't have any of the hdmf-common schema in with us
namespaces = [sch.annotations['namespace'].value for sch in res.schemas]
assert all([ns == 'core' for ns in namespaces])

View file

@ -12,3 +12,14 @@ from nwb_schema_language import Dataset, Group, Schema
def test_schema_build(nwb_core_fixture, schema_name): def test_schema_build(nwb_core_fixture, schema_name):
schema = [sch for sch in nwb_core_fixture.schemas if sch.name == schema_name][0] schema = [sch for sch in nwb_core_fixture.schemas if sch.name == schema_name][0]
res = schema.build() res = schema.build()
def test_schema_repr(nwb_core_fixture):
"""
Doesn't really make sense to test the string repr matches any particular value because it's
strictly cosmetic, but we do test that it can be done
"""
sch = nwb_core_fixture.schemas[0]
repr_str = sch.__repr__()
assert isinstance(repr_str, str)