22
33from typing import Annotated , Any , ClassVar , Literal
44
5- from pydantic import BaseModel , Field , HttpUrl , TypeAdapter
5+ from pydantic import ConfigDict , Field , HttpUrl , TypeAdapter
66
7+ from entitysdk .models .core import Identifiable
78from entitysdk .models .entity import Entity
89from entitysdk .types import (
910 CellMorphologyGenerationType ,
1617
1718
1819class CellMorphologyProtocolBase (Entity ):
19- """Cell Morphology Protocol Base, used by all the protocols except placeholder."""
20+ """Cell Morphology Protocol Base, used by all the protocols."""
21+
22+ # forbid extra parameters to prevent providing attributes of other classes by mistake
23+ model_config = ConfigDict (extra = "forbid" )
2024
2125 type : EntityType | None = EntityType .cell_morphology_protocol
26+
27+
28+ class CellMorphologyProtocolExtendedBase (CellMorphologyProtocolBase ):
29+ """Cell Morphology Protocol Extended Base, used by all the protocols except placeholder."""
30+
2231 protocol_document : Annotated [
2332 HttpUrl | None ,
2433 Field (description = "URL link to protocol document or publication." ),
@@ -30,7 +39,7 @@ class CellMorphologyProtocolBase(Entity):
3039
3140
3241class DigitalReconstructionCellMorphologyProtocol (
33- CellMorphologyProtocolBase ,
42+ CellMorphologyProtocolExtendedBase ,
3443):
3544 """Experimental morphology method for capturing cell morphology data."""
3645
@@ -58,7 +67,7 @@ class DigitalReconstructionCellMorphologyProtocol(
5867
5968
6069class ModifiedReconstructionCellMorphologyProtocol (
61- CellMorphologyProtocolBase ,
70+ CellMorphologyProtocolExtendedBase ,
6271):
6372 """Modified Reconstruction Cell Morphology Protocol."""
6473
@@ -69,7 +78,7 @@ class ModifiedReconstructionCellMorphologyProtocol(
6978
7079
7180class ComputationallySynthesizedCellMorphologyProtocol (
72- CellMorphologyProtocolBase ,
81+ CellMorphologyProtocolExtendedBase ,
7382):
7483 """Computationally Synthesized Cell Morphology Protocol."""
7584
@@ -80,7 +89,7 @@ class ComputationallySynthesizedCellMorphologyProtocol(
8089
8190
8291class PlaceholderCellMorphologyProtocol (
83- Entity ,
92+ CellMorphologyProtocolBase ,
8493):
8594 """Placeholder Cell Morphology Protocol."""
8695
@@ -98,24 +107,31 @@ class PlaceholderCellMorphologyProtocol(
98107]
99108
100109
101- class CellMorphologyProtocol (BaseModel ):
110+ class CellMorphologyProtocol (Identifiable ):
102111 """Polymorphic wrapper for consistent API, to be used for searching and retrieving.
103112
104113 The correct specific protocols are automatically instantiated.
105114
106- For the registration it's possible to use any of the specific classes:
115+ For the registration it's possible to use this same class, or any of the specific classes:
107116
108117 - `DigitalReconstructionCellMorphologyProtocol`
109118 - `ModifiedReconstructionCellMorphologyProtocol`
110119 - `ComputationallySynthesizedCellMorphologyProtocol`
111120 - `PlaceholderCellMorphologyProtocol`
112-
113- or this polymorphic class `CellMorphologyProtocol`, but in that case the instance should be
114- created with `CellMorphologyProtocol.model_validate()` to instantiate the correct object.
115121 """
116122
117123 _adapter : ClassVar [TypeAdapter ] = TypeAdapter (CellMorphologyProtocolUnion )
118124
125+ def __new__ (cls , * args , ** kwargs ) -> CellMorphologyProtocolUnion : # type: ignore[misc]
126+ """Construct a CellMorphologyProtocol from keyword arguments."""
127+ if args :
128+ msg = "Positional args not supported, use keyword args instead."
129+ raise TypeError (msg )
130+ return cls ._adapter .validate_python (kwargs )
131+
132+ def __init__ (self , ** kwargs : Any ) -> None :
133+ """Catch-all to satisfy type checkers."""
134+
119135 @classmethod
120136 def model_validate (cls , obj : Any , * args , ** kwargs ) -> CellMorphologyProtocolUnion : # type: ignore[override]
121137 """Return the correct instance of CellMorphologyProtocolUnion."""
0 commit comments