21 from __future__
import annotations
23 __all__ = (
"QuantumNode",
"NodeId",
"BuildId")
25 from dataclasses
import dataclass
26 from typing
import NewType
28 from ..pipeline
import TaskDef
29 from lsst.daf.butler
import Quantum, DatasetRef
31 BuildId = NewType(
"BuildId", str)
34 def _hashDsRef(ref: DatasetRef) -> int:
35 return hash((ref.datasetType, ref.dataId))
38 @dataclass(frozen=
True, eq=
True)
40 """This represents an unique identifier of a node within an individual
41 construction of a `QuantumGraph`. This identifier will stay constant
42 through a pickle, and any `QuantumGraph` methods that return a new
45 A `NodeId` will not be the same if a new graph is built containing the same
46 information in a `QuantumNode`, or even built from exactly the same inputs.
48 `NodeId`s do not play any role in deciding the equality or identity (hash)
49 of a `QuantumNode`, and are mainly useful in debugging or working with
50 various subsets of the same graph.
52 This interface is a convenance only, and no guarantees on long term
53 stability are made. New implementations might change the `NodeId`, or
54 provide more or less guarantees.
57 """The unique position of the node within the graph assigned at graph
61 """Unique identifier created at the time the originating graph was created
65 @dataclass(frozen=
True)
67 """This class represents a node in the quantum graph.
69 The quantum attribute represents the data that is to be processed at this
73 """The unit of data that is to be processed by this graph node"""
75 """Definition of the task that will process the `Quantum` associated with
79 """The unique position of the node within the graph assigned at graph
83 def __eq__(self, other: object) -> bool:
84 if not isinstance(other, QuantumNode):
86 if self.quantum != other.quantum:
91 """For graphs it is useful to have a more robust hash than provided
92 by the default quantum id based hashing
94 return hash((self.
taskDef, self.quantum))