linkml 1.7.7__tar.gz → 1.7.8__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {linkml-1.7.7 → linkml-1.7.8}/PKG-INFO +2 -1
- {linkml-1.7.7 → linkml-1.7.8}/linkml/__init__.py +14 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/docgen/subset.md.jinja2 +7 -7
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/array.py +15 -3
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/pydanticgen.py +4 -2
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/template.py +6 -4
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pythongen.py +3 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/rdfgen.py +9 -1
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/shaclgen.py +14 -3
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/sqlalchemygen.py +1 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/sqltablegen.py +16 -1
- {linkml-1.7.7 → linkml-1.7.8}/linkml/transformers/relmodel_transformer.py +21 -1
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/generator.py +9 -5
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/rawloader.py +5 -1
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/schemaloader.py +2 -1
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/sqlutils.py +13 -14
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/plugins/shacl_validation_plugin.py +10 -4
- {linkml-1.7.7 → linkml-1.7.8}/pyproject.toml +16 -8
- {linkml-1.7.7 → linkml-1.7.8}/setup.py +3 -2
- {linkml-1.7.7 → linkml-1.7.8}/LICENSE +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/README.md +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/_version.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/PythonGenNotes.md +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/README.md +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/common/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/common/type_designators.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/csvgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/docgen/class.md.jinja2 +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/docgen/class_diagram.md.jinja2 +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/docgen/common_metadata.md.jinja2 +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/docgen/enum.md.jinja2 +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/docgen/index.md.jinja2 +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/docgen/index.tex.jinja2 +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/docgen/schema.md.jinja2 +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/docgen/slot.md.jinja2 +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/docgen/type.md.jinja2 +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/docgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/dotgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/erdiagramgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/excelgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/golanggen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/golrgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/graphqlgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/javagen/example_template.java.jinja2 +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/javagen/java_record_template.jinja2 +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/javagen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/jsonldcontextgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/jsonldgen.py +1 -1
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/jsonschemagen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/legacy/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/linkmlgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/markdowngen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/namespacegen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/oocodegen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/owlgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/plantumlgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/prefixmapgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/projectgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/protogen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/black.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/build.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/templates/attribute.py.jinja +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/templates/base_model.py.jinja +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/templates/class.py.jinja +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/templates/conditional_import.py.jinja +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/templates/enum.py.jinja +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/templates/footer.py.jinja +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/templates/imports.py.jinja +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/templates/module.py.jinja +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/templates/validator.py.jinja +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/shacl/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/shacl/ifabsent_processor.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/shacl/shacl_data_type.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/shexgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/sparqlgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/sqlalchemy/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/sqlalchemy/sqlalchemy_declarative_template.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/sqlalchemy/sqlalchemy_imperative_template.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/sssomgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/string_template.md +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/summarygen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/terminusdbgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/typescriptgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/yamlgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/generators/yumlgen.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/cli.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/config/datamodel/.linkmllint.yaml +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/config/datamodel/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/config/datamodel/config.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/config/datamodel/config.yaml +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/config/default.yaml +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/config/recommended.yaml +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/formatters/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/formatters/formatter.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/formatters/json_formatter.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/formatters/markdown_formatter.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/formatters/terminal_formatter.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/formatters/tsv_formatter.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/linter.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/linter/rules.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/reporting/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/reporting/model.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/transformers/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/transformers/logical_model_transformer.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/transformers/model_transformer.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/transformers/schema_renamer.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/cli_utils.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/converter.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/datautils.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/datavalidator.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/execute_tutorial.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/helpers.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/ifabsent_functions.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/logictools.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/mergeutils.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/schema_builder.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/schema_fixer.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/schemasynopsis.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/typereferences.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/utils/validation.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/cli.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/loaders/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/loaders/delimited_file_loader.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/loaders/json_loader.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/loaders/loader.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/loaders/passthrough_loader.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/loaders/yaml_loader.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/plugins/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/plugins/jsonschema_validation_plugin.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/plugins/pydantic_validation_plugin.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/plugins/recommended_slots_plugin.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/plugins/validation_plugin.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/report.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/validation_context.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validator/validator.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validators/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validators/jsonschemavalidator.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/validators/sparqlvalidator.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/workspaces/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/workspaces/datamodel/__init__.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/workspaces/datamodel/workspaces.py +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/workspaces/datamodel/workspaces.yaml +0 -0
- {linkml-1.7.7 → linkml-1.7.8}/linkml/workspaces/example_runner.py +0 -0
@@ -1,6 +1,6 @@
|
|
1
1
|
Metadata-Version: 2.1
|
2
2
|
Name: linkml
|
3
|
-
Version: 1.7.
|
3
|
+
Version: 1.7.8
|
4
4
|
Summary: Linked Open Data Modeling Language
|
5
5
|
Home-page: https://linkml.io/linkml/
|
6
6
|
Keywords: schema,linked data,data modeling,rdf,owl,biolink
|
@@ -51,6 +51,7 @@ Requires-Dist: pyyaml
|
|
51
51
|
Requires-Dist: rdflib (>=6.0.0)
|
52
52
|
Requires-Dist: requests (>=2.22)
|
53
53
|
Requires-Dist: sqlalchemy (>=1.4.31)
|
54
|
+
Requires-Dist: typing-extensions (>=4.4.0) ; python_version < "3.9"
|
54
55
|
Requires-Dist: watchdog (>=0.9.0)
|
55
56
|
Project-URL: Documentation, https://linkml.io/linkml/
|
56
57
|
Project-URL: Repository, https://github.com/linkml/linkml
|
@@ -19,6 +19,13 @@ LOCAL_TYPES_YAML_FILE = linkml_files.LOCAL_PATH_FOR(Source.TYPES, Format.YAML)
|
|
19
19
|
LOCAL_MAPPINGS_YAML_FILE = linkml_files.LOCAL_PATH_FOR(Source.MAPPINGS, Format.YAML)
|
20
20
|
LOCAL_ANNOTATIONS_YAML_FILE = linkml_files.LOCAL_PATH_FOR(Source.ANNOTATIONS, Format.YAML)
|
21
21
|
LOCAL_EXTENSIONS_YAML_FILE = linkml_files.LOCAL_PATH_FOR(Source.EXTENSIONS, Format.YAML)
|
22
|
+
LOCAL_MODEL_YAML_FILES = (
|
23
|
+
LOCAL_METAMODEL_YAML_FILE,
|
24
|
+
LOCAL_TYPES_YAML_FILE,
|
25
|
+
LOCAL_MAPPINGS_YAML_FILE,
|
26
|
+
LOCAL_ANNOTATIONS_YAML_FILE,
|
27
|
+
LOCAL_EXTENSIONS_YAML_FILE,
|
28
|
+
)
|
22
29
|
|
23
30
|
# Local location of jsonld and context.jsonld files
|
24
31
|
LOCAL_METAMODEL_LDCONTEXT_FILE = linkml_files.LOCAL_PATH_FOR(Source.META, Format.JSONLD)
|
@@ -55,6 +62,13 @@ METATYPE_NAMESPACE = METAMODEL_NAMESPACE
|
|
55
62
|
METAMAPPING_NAMESPACE = METAMODEL_NAMESPACE
|
56
63
|
METAANNOTATIONS_NAMESPACE = METAMODEL_NAMESPACE
|
57
64
|
METAEXTENSIONS_NAMESPACE = METAMODEL_NAMESPACE
|
65
|
+
NAMESPACES = (
|
66
|
+
METAMODEL_NAMESPACE,
|
67
|
+
METATYPE_NAMESPACE,
|
68
|
+
METAMAPPING_NAMESPACE,
|
69
|
+
METAANNOTATIONS_NAMESPACE,
|
70
|
+
METAEXTENSIONS_NAMESPACE,
|
71
|
+
)
|
58
72
|
|
59
73
|
# Metamodel Context URI
|
60
74
|
METAMODEL_CONTEXT_URI = linkml_files.URL_FOR(Source.META, Format.JSONLD)
|
@@ -43,20 +43,18 @@ URI: {{ gen.link(element) }}
|
|
43
43
|
|
44
44
|
| Class | Description |
|
45
45
|
| --- | --- |
|
46
|
-
{% for c in
|
46
|
+
{% for c in classes_in_subset -%}
|
47
47
|
{%- if element.name in c.in_subset -%}
|
48
48
|
| {{gen.link(c)}} | {{c.description|enshorten}} |
|
49
49
|
{% endif -%}
|
50
50
|
{% endfor %}
|
51
51
|
|
52
|
-
{% for c in
|
52
|
+
{% for c in classes_in_subset -%}
|
53
53
|
{%- if element.name in c.in_subset -%}
|
54
|
-
### {{ gen.name(c) }}
|
55
54
|
|
56
|
-
{
|
55
|
+
{% set induced_slots = gen.class_induced_slots(c.name)|sort(attribute=sort_by) %}
|
57
56
|
|
58
57
|
{%- set filtered_slots = [] -%}
|
59
|
-
|
60
58
|
{%- for s in induced_slots|sort(attribute=sort_by) -%}
|
61
59
|
{%- if element.name in s.in_subset or element.name in schemaview.get_slot(s.name).in_subset -%}
|
62
60
|
{% set _ = filtered_slots.append(s) %}
|
@@ -64,10 +62,12 @@ URI: {{ gen.link(element) }}
|
|
64
62
|
{%- endfor %}
|
65
63
|
|
66
64
|
{%- if filtered_slots|length > 0 -%}
|
67
|
-
|
65
|
+
### Slots from {{ gen.link(c) }} also in _{{ element.name }}_
|
66
|
+
|
67
|
+
| Name | Cardinality and Range | Description |
|
68
68
|
| --- | --- | --- |
|
69
69
|
{% for s in filtered_slots -%}
|
70
|
-
| {{gen.link(s)}} | {{ gen.cardinality(s) }} <br/> {{gen.link(s.range)}}
|
70
|
+
| {{gen.link(s)}} | {{ gen.cardinality(s) }} <br/> {{gen.link(s.range)}} | {{s.description|enshorten}} {% if s.identifier %}**identifier**{% endif %} |
|
71
71
|
{% endfor %}
|
72
72
|
{%- endif %}
|
73
73
|
|
@@ -30,7 +30,7 @@ else:
|
|
30
30
|
from typing import Annotated
|
31
31
|
|
32
32
|
from linkml.generators.pydanticgen.build import SlotResult
|
33
|
-
from linkml.generators.pydanticgen.template import Import, Imports, ObjectImport
|
33
|
+
from linkml.generators.pydanticgen.template import ConditionalImport, Import, Imports, ObjectImport
|
34
34
|
|
35
35
|
|
36
36
|
class ArrayRepresentation(Enum):
|
@@ -54,7 +54,14 @@ if int(PYDANTIC_VERSION[0]) >= 2:
|
|
54
54
|
item_schema = handler.generate_schema(item_type)
|
55
55
|
if item_schema.get("type", "any") != "any":
|
56
56
|
item_schema["strict"] = True
|
57
|
-
|
57
|
+
|
58
|
+
if item_type is Any:
|
59
|
+
# Before python 3.11, `Any` type was a special object without a __name__
|
60
|
+
item_name = "Any"
|
61
|
+
else:
|
62
|
+
item_name = item_type.__name__
|
63
|
+
|
64
|
+
array_ref = f"any-shape-array-{item_name}"
|
58
65
|
|
59
66
|
schema = core_schema.definitions_schema(
|
60
67
|
core_schema.list_schema(core_schema.definition_reference_schema(array_ref)),
|
@@ -78,7 +85,6 @@ if int(PYDANTIC_VERSION[0]) >= 2:
|
|
78
85
|
+ Import(
|
79
86
|
module="typing",
|
80
87
|
objects=[
|
81
|
-
ObjectImport(name="Annotated"),
|
82
88
|
ObjectImport(name="Generic"),
|
83
89
|
ObjectImport(name="Iterable"),
|
84
90
|
ObjectImport(name="TypeVar"),
|
@@ -86,6 +92,12 @@ if int(PYDANTIC_VERSION[0]) >= 2:
|
|
86
92
|
ObjectImport(name="get_args"),
|
87
93
|
],
|
88
94
|
)
|
95
|
+
+ ConditionalImport(
|
96
|
+
condition="sys.version_info.minor > 8",
|
97
|
+
module="typing",
|
98
|
+
objects=[ObjectImport(name="Annotated")],
|
99
|
+
alternative=Import(module="typing_extensions", objects=[ObjectImport(name="Annotated")]),
|
100
|
+
)
|
89
101
|
+ Import(module="pydantic", objects=[ObjectImport(name="GetCoreSchemaHandler")])
|
90
102
|
+ Import(module="pydantic_core", objects=[ObjectImport(name="CoreSchema"), ObjectImport(name="core_schema")])
|
91
103
|
)
|
@@ -76,6 +76,7 @@ DEFAULT_IMPORTS = (
|
|
76
76
|
+ Import(module="decimal", objects=[ObjectImport(name="Decimal")])
|
77
77
|
+ Import(module="enum", objects=[ObjectImport(name="Enum")])
|
78
78
|
+ Import(module="re")
|
79
|
+
+ Import(module="sys")
|
79
80
|
+ Import(
|
80
81
|
module="typing",
|
81
82
|
objects=[
|
@@ -644,10 +645,11 @@ class PydanticGenerator(OOCodeGenerator):
|
|
644
645
|
for k, c in pyschema.classes.items():
|
645
646
|
attrs = {}
|
646
647
|
for attr_name, src_attr in c.attributes.items():
|
648
|
+
src_attr = src_attr._as_dict
|
647
649
|
new_fields = {
|
648
|
-
k: src_attr.
|
650
|
+
k: src_attr.get(k, None)
|
649
651
|
for k in PydanticAttribute.model_fields.keys()
|
650
|
-
if src_attr.
|
652
|
+
if src_attr.get(k, None) is not None
|
651
653
|
}
|
652
654
|
predef_slot = predefined.get(k, {}).get(attr_name, None)
|
653
655
|
if predef_slot is not None:
|
@@ -1,3 +1,4 @@
|
|
1
|
+
from copy import copy
|
1
2
|
from importlib.util import find_spec
|
2
3
|
from typing import Any, ClassVar, Dict, Generator, List, Literal, Optional, Union, overload
|
3
4
|
|
@@ -54,6 +55,10 @@ class TemplateModel(BaseModel):
|
|
54
55
|
"""
|
55
56
|
|
56
57
|
template: ClassVar[str]
|
58
|
+
_environment: ClassVar[Environment] = Environment(
|
59
|
+
loader=PackageLoader("linkml.generators.pydanticgen", "templates"), trim_blocks=True, lstrip_blocks=True
|
60
|
+
)
|
61
|
+
|
57
62
|
pydantic_ver: int = int(PYDANTIC_VERSION[0])
|
58
63
|
|
59
64
|
def render(self, environment: Optional[Environment] = None, black: bool = False) -> str:
|
@@ -95,14 +100,11 @@ class TemplateModel(BaseModel):
|
|
95
100
|
def environment(cls) -> Environment:
|
96
101
|
"""
|
97
102
|
Default environment for Template models.
|
98
|
-
|
99
103
|
uses a :class:`jinja2.PackageLoader` for the templates directory within this module
|
100
104
|
with the ``trim_blocks`` and ``lstrip_blocks`` parameters set to ``True`` so that the
|
101
105
|
default templates could be written in a more readable way.
|
102
106
|
"""
|
103
|
-
return
|
104
|
-
loader=PackageLoader("linkml.generators.pydanticgen", "templates"), trim_blocks=True, lstrip_blocks=True
|
105
|
-
)
|
107
|
+
return copy(cls._environment)
|
106
108
|
|
107
109
|
if int(PYDANTIC_VERSION[0]) < 2:
|
108
110
|
# simulate pydantic 2's model_fields behavior
|
@@ -4,6 +4,7 @@ import os
|
|
4
4
|
import re
|
5
5
|
from copy import copy
|
6
6
|
from dataclasses import dataclass
|
7
|
+
from pathlib import Path
|
7
8
|
from types import ModuleType
|
8
9
|
from typing import Callable, Dict, Iterator, List, Optional, Set, Tuple, Union
|
9
10
|
|
@@ -62,6 +63,8 @@ class PythonGenerator(Generator):
|
|
62
63
|
emit_metadata: bool = True
|
63
64
|
|
64
65
|
def __post_init__(self) -> None:
|
66
|
+
if isinstance(self.schema, Path):
|
67
|
+
self.schema = str(self.schema)
|
65
68
|
self.sourcefile = self.schema
|
66
69
|
self.schemaview = SchemaView(self.schema, base_dir=self.base_dir)
|
67
70
|
super().__post_init__()
|
@@ -7,10 +7,12 @@ Generate a JSON LD representation of the model
|
|
7
7
|
|
8
8
|
import os
|
9
9
|
import urllib.parse as urlparse
|
10
|
+
from copy import deepcopy
|
10
11
|
from dataclasses import dataclass
|
11
12
|
from typing import List, Optional
|
12
13
|
|
13
14
|
import click
|
15
|
+
from linkml_runtime.linkml_model import SchemaDefinition
|
14
16
|
from rdflib import Graph
|
15
17
|
from rdflib.plugin import Parser as rdflib_Parser
|
16
18
|
from rdflib.plugin import plugins as rdflib_plugins
|
@@ -35,13 +37,19 @@ class RDFGenerator(Generator):
|
|
35
37
|
# ObjectVars
|
36
38
|
emit_metadata: bool = False
|
37
39
|
context: List[str] = None
|
40
|
+
original_schema: SchemaDefinition = None
|
41
|
+
"""See https://github.com/linkml/linkml/issues/871"""
|
42
|
+
|
43
|
+
def __post_init__(self):
|
44
|
+
self.original_schema = deepcopy(self.schema)
|
45
|
+
super().__post_init__()
|
38
46
|
|
39
47
|
def _data(self, g: Graph) -> str:
|
40
48
|
return g.serialize(format="turtle" if self.format == "ttl" else self.format)
|
41
49
|
|
42
50
|
def end_schema(self, output: Optional[str] = None, context: str = None, **_) -> None:
|
43
51
|
gen = JSONLDGenerator(
|
44
|
-
self,
|
52
|
+
self.original_schema,
|
45
53
|
format=JSONLDGenerator.valid_formats[0],
|
46
54
|
metadata=self.emit_metadata,
|
47
55
|
importmap=self.importmap,
|
@@ -22,7 +22,8 @@ class ShaclGenerator(Generator):
|
|
22
22
|
# ClassVars
|
23
23
|
closed: bool = True
|
24
24
|
"""True means add 'sh:closed=true' to all shapes, except of mixin shapes and shapes, that have parents"""
|
25
|
-
|
25
|
+
suffix: str = None
|
26
|
+
"""parameterized suffix to be appended. No suffix per default."""
|
26
27
|
generatorname = os.path.basename(__file__)
|
27
28
|
generatorversion = "0.0.1"
|
28
29
|
valid_formats = ["ttl"]
|
@@ -59,9 +60,12 @@ class ShaclGenerator(Generator):
|
|
59
60
|
|
60
61
|
def shape_pv(p, v):
|
61
62
|
if v is not None:
|
62
|
-
g.add((
|
63
|
+
g.add((class_uri_with_suffix, p, v))
|
63
64
|
|
64
65
|
class_uri = URIRef(sv.get_uri(c, expand=True))
|
66
|
+
class_uri_with_suffix = class_uri
|
67
|
+
if self.suffix is not None:
|
68
|
+
class_uri_with_suffix += self.suffix
|
65
69
|
shape_pv(RDF.type, SH.NodeShape)
|
66
70
|
shape_pv(SH.targetClass, class_uri) # TODO
|
67
71
|
if self.closed:
|
@@ -211,14 +215,21 @@ def add_simple_data_type(func: Callable, r: ElementName) -> None:
|
|
211
215
|
|
212
216
|
|
213
217
|
@shared_arguments(ShaclGenerator)
|
218
|
+
@click.command()
|
214
219
|
@click.option(
|
215
220
|
"--closed/--non-closed",
|
216
221
|
default=True,
|
217
222
|
show_default=True,
|
218
223
|
help="Use '--closed' to generate closed SHACL shapes. Use '--non-closed' to generate open SHACL shapes.",
|
219
224
|
)
|
225
|
+
@click.option(
|
226
|
+
"-s",
|
227
|
+
"--suffix",
|
228
|
+
default=None,
|
229
|
+
show_default=True,
|
230
|
+
help="Use --suffix to append given string to SHACL class name (e. g. --suffix Shape: Person becomes PersonShape).",
|
231
|
+
)
|
220
232
|
@click.version_option(__version__, "-V", "--version")
|
221
|
-
@click.command()
|
222
233
|
def cli(yamlfile, **args):
|
223
234
|
"""Generate SHACL turtle from a LinkML model"""
|
224
235
|
gen = ShaclGenerator(yamlfile, **args)
|
@@ -121,6 +121,7 @@ class SQLAlchemyGenerator(Generator):
|
|
121
121
|
is_join_table=lambda c: any(tag for tag in c.annotations.keys() if tag == "linkml:derived_from"),
|
122
122
|
classes=rel_schema_classes_ordered,
|
123
123
|
)
|
124
|
+
logging.debug(f"# Generated code:\n{code}")
|
124
125
|
return code
|
125
126
|
|
126
127
|
def serialize(self, **kwargs) -> str:
|
@@ -211,7 +211,22 @@ class SQLTableGenerator(Generator):
|
|
211
211
|
col.comment = s.description
|
212
212
|
cols.append(col)
|
213
213
|
for uc_name, uc in c.unique_keys.items():
|
214
|
-
|
214
|
+
|
215
|
+
def _sql_name(sn: str):
|
216
|
+
if sn in c.attributes:
|
217
|
+
return sql_name(sn)
|
218
|
+
else:
|
219
|
+
# for candidate in c.attributes.values():
|
220
|
+
# if "original_slot" in candidate.annotations:
|
221
|
+
# original = candidate.annotations["original_slot"]
|
222
|
+
# if original.value == sn:
|
223
|
+
# return sql_name(candidate.name)
|
224
|
+
return None
|
225
|
+
|
226
|
+
sql_names = [_sql_name(sn) for sn in uc.unique_key_slots]
|
227
|
+
if any(sn is None for sn in sql_names):
|
228
|
+
continue
|
229
|
+
sql_uc = UniqueConstraint(*sql_names)
|
215
230
|
cols.append(sql_uc)
|
216
231
|
Table(sql_name(cn), schema_metadata, *cols, comment=str(c.description))
|
217
232
|
schema_metadata.create_all(engine)
|
@@ -226,6 +226,7 @@ class RelationalModelTransformer:
|
|
226
226
|
|
227
227
|
# TODO: separate out the logic into separate testable methods
|
228
228
|
target_sv.set_modified()
|
229
|
+
multivalued_slots_original = []
|
229
230
|
# post-process target schema
|
230
231
|
for cn, c in target_sv.all_classes().items():
|
231
232
|
if self.foreign_key_policy == ForeignKeyPolicy.NO_FOREIGN_KEYS:
|
@@ -243,6 +244,7 @@ class RelationalModelTransformer:
|
|
243
244
|
slot.inlined or slot.inlined_as_list or "shared" in slot.annotations
|
244
245
|
)
|
245
246
|
if slot.multivalued:
|
247
|
+
multivalued_slots_original.append(slot.name)
|
246
248
|
slot.multivalued = False
|
247
249
|
slot_name = slot.name
|
248
250
|
sn_singular = slot.singular_name if slot.singular_name else slot.name
|
@@ -332,6 +334,7 @@ class RelationalModelTransformer:
|
|
332
334
|
# add PK and FK anns
|
333
335
|
target_sv.set_modified()
|
334
336
|
fk_policy = self.foreign_key_policy
|
337
|
+
forward_map = {}
|
335
338
|
for c in target.classes.values():
|
336
339
|
if self.foreign_key_policy == ForeignKeyPolicy.NO_FOREIGN_KEYS:
|
337
340
|
continue
|
@@ -356,14 +359,31 @@ class RelationalModelTransformer:
|
|
356
359
|
# if it is already an injected backref, no need to re-inject
|
357
360
|
if "backref" not in a.annotations:
|
358
361
|
del c.attributes[a.name]
|
362
|
+
original_name = a.name
|
359
363
|
if "forwardref" not in a.annotations:
|
360
|
-
add_annotation(a, "original_slot",
|
364
|
+
add_annotation(a, "original_slot", original_name)
|
361
365
|
a.alias = f"{a.name}_{tc_pk_slot.name}"
|
362
366
|
a.name = a.alias
|
363
367
|
c.attributes[a.name] = a
|
368
|
+
forward_map[original_name] = a.name
|
364
369
|
ann = Annotation("foreign_key", f"{tc.name}.{tc_pk_slot.name}")
|
365
370
|
a.annotations[ann.tag] = ann
|
366
371
|
target_sv.set_modified()
|
372
|
+
# Rewrite unique key constraints
|
373
|
+
# - if a slot has a range of object, it may be renamed, e.g. person => person_id
|
374
|
+
# - if a slot is multivalued then it is translated to backref and the UC must be dropped
|
375
|
+
removed_ucs = []
|
376
|
+
for uc_name, uc in c.unique_keys.items():
|
377
|
+
if any(sn in multivalued_slots_original for sn in uc.unique_key_slots):
|
378
|
+
logging.warning(
|
379
|
+
f"Cannot represent uniqueness constraint {uc_name}. "
|
380
|
+
f"one of the slots {uc.unique_key_slots} is multivalued"
|
381
|
+
)
|
382
|
+
removed_ucs.append(uc_name)
|
383
|
+
new_slot_names = [forward_map.get(sn, sn) for sn in uc.unique_key_slots]
|
384
|
+
uc.unique_key_slots = new_slot_names
|
385
|
+
for uc_name in removed_ucs:
|
386
|
+
del c.unique_keys[uc_name]
|
367
387
|
|
368
388
|
result = TransformationResult(target, mappings=mappings)
|
369
389
|
return result
|
@@ -30,7 +30,6 @@ from typing import Callable, ClassVar, Dict, List, Mapping, Optional, Set, TextI
|
|
30
30
|
import click
|
31
31
|
from click import Argument, Command, Option
|
32
32
|
from linkml_runtime import SchemaView
|
33
|
-
from linkml_runtime.dumpers import yaml_dumper
|
34
33
|
from linkml_runtime.linkml_model.meta import (
|
35
34
|
ClassDefinition,
|
36
35
|
ClassDefinitionName,
|
@@ -83,7 +82,7 @@ class Generator(metaclass=abc.ABCMeta):
|
|
83
82
|
For usage `Generator Docs <https://linkml.io/linkml/generators/>`_
|
84
83
|
"""
|
85
84
|
|
86
|
-
schema: Union[str, TextIO, SchemaDefinition, "Generator"]
|
85
|
+
schema: Union[str, TextIO, SchemaDefinition, "Generator", Path]
|
87
86
|
"""metamodel compliant schema. Can be URI, file name, actual schema, another generator, an
|
88
87
|
open file or a pre-parsed schema"""
|
89
88
|
|
@@ -130,7 +129,7 @@ class Generator(metaclass=abc.ABCMeta):
|
|
130
129
|
useuris: Optional[bool] = None
|
131
130
|
"""True means declared class slot uri's are used. False means use model uris"""
|
132
131
|
|
133
|
-
log_level: int = DEFAULT_LOG_LEVEL_INT
|
132
|
+
log_level: Optional[int] = DEFAULT_LOG_LEVEL_INT
|
134
133
|
"""Logging level, 0 is minimum"""
|
135
134
|
|
136
135
|
mergeimports: Optional[bool] = True
|
@@ -180,6 +179,8 @@ class Generator(metaclass=abc.ABCMeta):
|
|
180
179
|
def __post_init__(self) -> None:
|
181
180
|
if not self.logger:
|
182
181
|
self.logger = logging.getLogger()
|
182
|
+
if self.log_level is not None:
|
183
|
+
self.logger.setLevel(self.log_level)
|
183
184
|
if self.format is None:
|
184
185
|
self.format = self.valid_formats[0]
|
185
186
|
if self.format not in self.valid_formats:
|
@@ -191,7 +192,11 @@ class Generator(metaclass=abc.ABCMeta):
|
|
191
192
|
self.source_file_size = None
|
192
193
|
if self.requires_metamodel:
|
193
194
|
self.metamodel = _resolved_metamodel(self.mergeimports)
|
195
|
+
|
194
196
|
schema = self.schema
|
197
|
+
if isinstance(schema, Path):
|
198
|
+
schema = str(schema)
|
199
|
+
|
195
200
|
# TODO: remove aliasing
|
196
201
|
self.emit_metadata = self.metadata
|
197
202
|
if self.uses_schemaloader:
|
@@ -225,8 +230,7 @@ class Generator(metaclass=abc.ABCMeta):
|
|
225
230
|
# schemaloader based methods require schemas to have been created via SchemaLoader,
|
226
231
|
# which prepopulates some fields (e.g. definition_url). If the schema has not been processed through the
|
227
232
|
# loader, then roundtrip
|
228
|
-
|
229
|
-
schema = yaml_dumper.dumps(schema)
|
233
|
+
schema = schema._as_dict
|
230
234
|
loader = SchemaLoader(
|
231
235
|
schema,
|
232
236
|
self.base_dir,
|
@@ -1,5 +1,6 @@
|
|
1
1
|
import copy
|
2
2
|
from datetime import datetime
|
3
|
+
from pathlib import Path
|
3
4
|
from typing import Optional, TextIO, Union
|
4
5
|
from urllib.parse import urlparse
|
5
6
|
|
@@ -29,7 +30,7 @@ SchemaDefinition.MissingRequiredField = mrf
|
|
29
30
|
|
30
31
|
|
31
32
|
def load_raw_schema(
|
32
|
-
data: Union[str, dict, TextIO],
|
33
|
+
data: Union[str, dict, TextIO, Path],
|
33
34
|
source_file: Optional[str] = None,
|
34
35
|
source_file_date: Optional[str] = None,
|
35
36
|
source_file_size: Optional[int] = None,
|
@@ -58,6 +59,9 @@ def load_raw_schema(
|
|
58
59
|
assert source_file_date is None, "source_file_date parameter not allowed if data is a file or URL"
|
59
60
|
assert source_file_size is None, "source_file_size parameter not allowed if data is a file or URL"
|
60
61
|
|
62
|
+
if isinstance(data, Path):
|
63
|
+
data = str(data)
|
64
|
+
|
61
65
|
# Convert the input into a valid SchemaDefinition
|
62
66
|
if isinstance(data, (str, dict, TextIO)):
|
63
67
|
# TODO: Build a generic loader that detects type from suffix or content and invokes the appropriate loader
|
@@ -2,6 +2,7 @@ import logging
|
|
2
2
|
import os
|
3
3
|
from collections import OrderedDict
|
4
4
|
from copy import deepcopy
|
5
|
+
from pathlib import Path
|
5
6
|
from typing import Dict, Iterator, List, Mapping, Optional, Set, TextIO, Tuple, Union, cast
|
6
7
|
from urllib.parse import urlparse
|
7
8
|
|
@@ -32,7 +33,7 @@ from linkml.utils.schemasynopsis import SchemaSynopsis
|
|
32
33
|
class SchemaLoader:
|
33
34
|
def __init__(
|
34
35
|
self,
|
35
|
-
data: Union[str, TextIO, SchemaDefinition, dict],
|
36
|
+
data: Union[str, TextIO, SchemaDefinition, dict, Path],
|
36
37
|
base_dir: Optional[str] = None,
|
37
38
|
namespaces: Optional[Namespaces] = None,
|
38
39
|
useuris: Optional[bool] = None,
|
@@ -58,16 +58,22 @@ class SQLStore:
|
|
58
58
|
- mapping your data/objects in any LinkML compliant data format (json. yaml, rdf) into ORM objects
|
59
59
|
"""
|
60
60
|
|
61
|
-
schema: Union[str, SchemaDefinition] = None
|
62
|
-
schemaview: SchemaView = None
|
63
|
-
engine: Engine = None
|
64
|
-
database_path: str = None
|
61
|
+
schema: Optional[Union[str, Path, SchemaDefinition]] = None
|
62
|
+
schemaview: Optional[SchemaView] = None
|
63
|
+
engine: Optional[Engine] = None
|
64
|
+
database_path: Union[str, Path] = None
|
65
65
|
use_memory: bool = False
|
66
66
|
"""https://docs.sqlalchemy.org/en/20/dialects/sqlite.html#using-a-memory-database-in-multiple-threads"""
|
67
67
|
|
68
|
-
module: ModuleType = None
|
69
|
-
native_module: ModuleType = None
|
70
|
-
include_schema_in_database: bool =
|
68
|
+
module: Optional[ModuleType] = None
|
69
|
+
native_module: Optional[ModuleType] = None
|
70
|
+
include_schema_in_database: bool = False
|
71
|
+
|
72
|
+
def __post_init__(self):
|
73
|
+
if self.database_path is None and not self.use_memory:
|
74
|
+
raise ValueError("Must have database path or use_memory must be True")
|
75
|
+
if self.schema is not None and self.schemaview is None:
|
76
|
+
self.schemaview = SchemaView(self.schema)
|
71
77
|
|
72
78
|
def db_exists(self, create=True, force=False) -> Optional[str]:
|
73
79
|
"""
|
@@ -117,8 +123,6 @@ class SQLStore:
|
|
117
123
|
"""
|
118
124
|
gen = SQLAlchemyGenerator(self.schema)
|
119
125
|
self.module = gen.compile_sqla(template=TemplateEnum.DECLARATIVE)
|
120
|
-
if self.schemaview is None:
|
121
|
-
self.schemaview = SchemaView(self.schema)
|
122
126
|
return self.module
|
123
127
|
|
124
128
|
def compile_native(self) -> ModuleType:
|
@@ -223,7 +227,6 @@ class SQLStore:
|
|
223
227
|
for n, nu_typ in inspect.getmembers(self.module):
|
224
228
|
# TODO: make more efficient
|
225
229
|
if n == typ.__name__:
|
226
|
-
# print(f'Creating {nu_typ} from: {inst_args}')
|
227
230
|
nu_obj = nu_typ(**inst_args)
|
228
231
|
return nu_obj
|
229
232
|
raise ValueError(f"Cannot find {typ.__name__} in {self.module}")
|
@@ -237,8 +240,6 @@ class SQLStore:
|
|
237
240
|
:param obj: sqla object
|
238
241
|
:return: native dataclass object
|
239
242
|
"""
|
240
|
-
if self.schemaview is None:
|
241
|
-
self.schemaview = SchemaView(self.schema)
|
242
243
|
typ = type(obj)
|
243
244
|
nm = self.schemaview.class_name_mappings()
|
244
245
|
if typ.__name__ in nm:
|
@@ -262,9 +263,7 @@ class SQLStore:
|
|
262
263
|
for n, nu_typ in inspect.getmembers(self.native_module):
|
263
264
|
# TODO: make more efficient
|
264
265
|
if n == typ.__name__:
|
265
|
-
# print(f'CREATING {nu_typ} FROM {inst_args}')
|
266
266
|
nu_obj = nu_typ(**inst_args)
|
267
|
-
# print(f'CREATED {nu_obj}')
|
268
267
|
return nu_obj
|
269
268
|
raise ValueError(f"Cannot find {typ.__name__} in {self.native_module}")
|
270
269
|
else:
|
@@ -34,21 +34,27 @@ class ShaclValidationPlugin(ValidationPlugin):
|
|
34
34
|
self.closed = closed
|
35
35
|
self.shacl_path = shacl_path
|
36
36
|
self.raise_on_conversion_error = raise_on_conversion_error
|
37
|
+
self._loaded_graphs = {}
|
37
38
|
|
38
39
|
def _shacl_graph(self, context: ValidationContext) -> Optional[rdflib.Graph]:
|
39
40
|
g = rdflib.Graph()
|
40
41
|
if self.shacl_path:
|
41
42
|
g.parse(str(self.shacl_path))
|
42
43
|
else:
|
43
|
-
|
44
|
-
|
44
|
+
schema_hash = hash(str(context._schema))
|
45
|
+
if schema_hash in self._loaded_graphs:
|
46
|
+
g = self._loaded_graphs[schema_hash]
|
47
|
+
else:
|
48
|
+
gen = ShaclGenerator(context._schema)
|
49
|
+
g = gen.as_graph()
|
50
|
+
self._loaded_graphs[schema_hash] = g
|
45
51
|
return g
|
46
52
|
|
47
53
|
def process(self, instance: Any, context: ValidationContext) -> Iterator[ValidationResult]:
|
48
|
-
"""Perform
|
54
|
+
"""Perform SHACL Schema validation on the provided instance
|
49
55
|
|
50
56
|
:param instance: The instance to validate
|
51
|
-
:param context: The validation context which provides a
|
57
|
+
:param context: The validation context which provides a SHACL artifact
|
52
58
|
:return: Iterator over validation results
|
53
59
|
:rtype: Iterator[ValidationResult]
|
54
60
|
"""
|
@@ -1,6 +1,6 @@
|
|
1
1
|
[tool.poetry]
|
2
2
|
name = "linkml"
|
3
|
-
version = "1.7.
|
3
|
+
version = "1.7.8"
|
4
4
|
description = "Linked Open Data Modeling Language"
|
5
5
|
authors = [
|
6
6
|
"Chris Mungall <cjmungall@lbl.gov>",
|
@@ -124,6 +124,7 @@ sqlalchemy = ">=1.4.31"
|
|
124
124
|
watchdog = ">=0.9.0"
|
125
125
|
pyshacl = { version = "^0.25.0", optional = true }
|
126
126
|
black = { version=">=24.0.0", optional = true }
|
127
|
+
typing-extensions = { version=">=4.4.0", python="<3.9" }
|
127
128
|
|
128
129
|
[tool.poetry.group.dev.dependencies]
|
129
130
|
chardet = "*"
|
@@ -133,12 +134,6 @@ nbconvert = "*"
|
|
133
134
|
nbformat = "*"
|
134
135
|
coverage = "^6.4.1"
|
135
136
|
tox = "^4"
|
136
|
-
furo = {version = "^2023.03.27", extras = ["docs"]}
|
137
|
-
sphinxcontrib-mermaid = {version = "^0.7.1", extras = ["docs"]}
|
138
|
-
sphinx = "*"
|
139
|
-
sphinx-click = "*"
|
140
|
-
sphinx-rtd-theme = "*"
|
141
|
-
myst-parser = "*"
|
142
137
|
requests-cache = "^1.2.0"
|
143
138
|
myst-nb = {version=">=1.0.0", python=">=3.9"}
|
144
139
|
sphinx-design = "^0.5.0"
|
@@ -157,6 +152,17 @@ black = ["black"]
|
|
157
152
|
shacl = ["pyshacl"]
|
158
153
|
tests = ["black", "pyshacl"]
|
159
154
|
|
155
|
+
[tool.poetry.group.docs]
|
156
|
+
optional = true
|
157
|
+
|
158
|
+
[tool.poetry.group.docs.dependencies]
|
159
|
+
furo = {version = "^2023.03.27", extras = ["docs"]}
|
160
|
+
sphinxcontrib-mermaid = {version = "^0.7.1", extras = ["docs"]}
|
161
|
+
sphinx = "*"
|
162
|
+
sphinx-click = "*"
|
163
|
+
sphinx-rtd-theme = "*"
|
164
|
+
myst-parser = "*"
|
165
|
+
|
160
166
|
[build-system]
|
161
167
|
requires = ["poetry-core>=1.0.0", "poetry-dynamic-versioning"]
|
162
168
|
build-backend = "poetry_dynamic_versioning.backend"
|
@@ -193,7 +199,9 @@ filterwarnings = [
|
|
193
199
|
]
|
194
200
|
markers = [
|
195
201
|
"network: mark tests that make external network requests",
|
196
|
-
"slow: mark test as slow to run"
|
202
|
+
"slow: mark test as slow to run",
|
203
|
+
"no_asserts: tests that don't have meaningful asserts, but are only snapshot comparisons, or historically had print statements, or other non-erroring behavior",
|
204
|
+
"strcmp: tests that compare stringified values rather than the values themselves"
|
197
205
|
]
|
198
206
|
|
199
207
|
[tool.ruff]
|
@@ -55,7 +55,8 @@ install_requires = \
|
|
55
55
|
'watchdog>=0.9.0']
|
56
56
|
|
57
57
|
extras_require = \
|
58
|
-
{'
|
58
|
+
{':python_version < "3.9"': ['typing-extensions>=4.4.0'],
|
59
|
+
'black': ['black>=24.0.0'],
|
59
60
|
'shacl': ['pyshacl>=0.25.0,<0.26.0'],
|
60
61
|
'tests': ['pyshacl>=0.25.0,<0.26.0', 'black>=24.0.0']}
|
61
62
|
|
@@ -113,7 +114,7 @@ entry_points = \
|
|
113
114
|
|
114
115
|
setup_kwargs = {
|
115
116
|
'name': 'linkml',
|
116
|
-
'version': '1.7.
|
117
|
+
'version': '1.7.8',
|
117
118
|
'description': 'Linked Open Data Modeling Language',
|
118
119
|
'long_description': '[](https://pypi.python.org/pypi/linkml)\n\n[](https://pypi.python.org/pypi/linkml)\n[](https://mybinder.org/v2/gh/linkml/linkml/main?filepath=notebooks)\n[](https://zenodo.org/badge/latestdoi/13996/linkml/linkml)\n[](https://pepy.tech/project/linkml)\n[](https://pypi.org/project/linkml)\n[](https://codecov.io/gh/linkml/linkml)\n\n\n# LinkML - Linked Data Modeling Language\n\nLinkML is a linked data modeling language following object-oriented and ontological principles. LinkML models are typically authored in YAML, and can be converted to other schema representation formats such as JSON or RDF.\n\nThis repo holds the tools for generating and working with LinkML. For the LinkML schema (metamodel), please see https://github.com/linkml/linkml-model\n\nThe complete documentation for LinkML can be found here:\n\n - [linkml.io/linkml](https://linkml.io/linkml)\n',
|
119
120
|
'author': 'Chris Mungall',
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
@@ -60,8 +60,8 @@ class JSONLDGenerator(Generator):
|
|
60
60
|
"""Path to a JSONLD context file"""
|
61
61
|
|
62
62
|
def __post_init__(self) -> None:
|
63
|
-
super().__post_init__()
|
64
63
|
self.original_schema = deepcopy(self.schema)
|
64
|
+
super().__post_init__()
|
65
65
|
|
66
66
|
def _add_type(self, node: YAMLRoot) -> dict:
|
67
67
|
if self.format == "jsonld":
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
{linkml-1.7.7 → linkml-1.7.8}/linkml/generators/pydanticgen/templates/conditional_import.py.jinja
RENAMED
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
{linkml-1.7.7 → linkml-1.7.8}/linkml/generators/sqlalchemy/sqlalchemy_declarative_template.py
RENAMED
File without changes
|
{linkml-1.7.7 → linkml-1.7.8}/linkml/generators/sqlalchemy/sqlalchemy_imperative_template.py
RENAMED
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|