def get_annotation( node: nodes.AssignAttr | nodes.AssignName, ) -> nodes.Name | nodes.Subscript | None: """Return the annotation for `node`.""" ann = None if isinstance(node.parent, nodes.AnnAssign): ann = node.parent.annotation elif isinstance(node, nodes.AssignAttr): init_method = node.parent.parent try: annotations = dict( zip(init_method.locals, init_method.args.annotations)) ann = annotations.get(node.parent.value.name) except AttributeError: pass else: return ann try: default, *_ = node.infer() except astroid.InferenceError: default = "" label = get_annotation_label(ann) if ann: label = (rf"Optional[{label}]" if getattr(default, "value", "value") is None and not label.startswith("Optional") else label) if label: ann.name = label return ann
def get_signal_anno(self): annotations = safe_getattr(self.parent, '__annotations__', {}) obj_anno = annotations.get(self.objpath[-1]) if obj_anno is None: return if safe_getattr(obj_anno, '__qualname__', '') != self._anno_qualname: return sig_anno = get_type_hints(obj_anno, None, self.config.autodoc_type_aliases) names = list(sig_anno.keys()) types = [stringify_typehint(v) for v in sig_anno.values()] self.options['argnames'], self.options['argtypes'] = names, types
def add_directive_header(self, sig: str) -> None: self.options.no_value = True super().add_directive_header(sig) sourcename = self.get_sourcename() tp_anno = get_type_hints(self.parent, None, self.config.autodoc_type_aliases) if self.objpath[-1] in tp_anno: return annotations = safe_getattr(self.parent, '__annotations__', {}) obj_anno = annotations.get(self.objpath[-1]) if obj_anno is not None: objrepr = stringify_typehint(obj_anno) self.add_line(f' :type: {objrepr}', sourcename)
def __dask_distributed_annotations_unpack__( annotations: MutableMapping[str, Any], new_annotations: Mapping[str, Any] | None, keys: Iterable[Hashable], ) -> None: """ Unpack a set of layer annotations across a set of keys, then merge those expanded annotations for the layer into an existing annotations mapping. This is not a simple shallow merge because some annotations like retries, priority, workers, etc need to be able to retain keys from different layers. Parameters ---------- annotations: MutableMapping[str, Any], input/output Already unpacked annotations, which are to be updated with the new unpacked annotations new_annotations: Mapping[str, Any], optional New annotations to be unpacked into `annotations` keys: Iterable All keys in the layer. """ if new_annotations is None: return expanded = {} keys_stringified = False # Expand the new annotations across the keyset for a, v in new_annotations.items(): if type(v) is dict and "__expanded_annotations__" in v: # Maybe do a destructive update for efficiency? v = v.copy() del v["__expanded_annotations__"] expanded[a] = v else: if not keys_stringified: keys = [stringify(k) for k in keys] keys_stringified = True expanded[a] = dict.fromkeys(keys, v) # Merge the expanded annotations with the existing annotations mapping for k, v in expanded.items(): v.update(annotations.get(k, {})) annotations.update(expanded)
def _augment_endpoint_route(self, route: Route): """ Get information from the endpoint and augment route """ # Get type hints # Note that this evaluates forward references. We supply: # * the module as the global namespace # * the class as the local namespace # This lets you use class attributes as forward references. Yeehaw! # NOTE: type hints are evaluated on a per-view basis: thanks to copy_func(), # every class is evaluated in its own context! :) annotations = get_type_hints( route.view_func, # globalns=sys.modules[route.ViewCls.__module__].__dict__, # use viewfunc.__globals__ localns=vars(route.ViewCls) ) # If there is anything useful in the return annotation, use it with FastAPI if lenient_issubclass(annotations.get('return'), pydantic.BaseModel): route.api_route_kwargs.setdefault('response_model', annotations['return'])
def _has_required_annotations(self, obj: KubernetesObject) -> bool: annotations = obj.annotations # Let's not parse KnativeIngress if it's not meant for us. We only need # to ignore KnativeIngress iff networking.knative.dev/ingress.class is # present in annotation. If it's not there, then we accept all ingress # classes. ingress_class = annotations.get('networking.knative.dev/ingress.class', self.INGRESS_CLASS) if ingress_class.lower() != self.INGRESS_CLASS: self.logger.debug(f'Ignoring Knative {obj.kind} {obj.name}; set networking.knative.dev/ingress.class ' f'annotation to {self.INGRESS_CLASS} for ambassador to parse it.') return False # We don't want to deal with non-matching Ambassador IDs if obj.ambassador_id != Config.ambassador_id: self.logger.info(f"Knative {obj.kind} {obj.name} does not have Ambassador ID {Config.ambassador_id}, ignoring...") return False return True
def _get_method_arguments(method: nodes.FunctionDef) -> list[str]: if method.args.args is None: return [] first_arg = 0 if method.type in {"function", "staticmethod"} else 1 arguments: list[nodes.AssignName] = method.args.args[first_arg:] annotations = dict(zip(arguments, method.args.annotations[first_arg:])) for arg in arguments: annotation_label = "" ann = annotations.get(arg) if ann: annotation_label = get_annotation_label(ann) annotations[arg] = annotation_label return [ f"{arg.name}: {ann}" if ann else f"{arg.name}" for arg, ann in annotations.items() ]
def apply_annotations_on( self, annotations: AnnotationLayer, target: str, only_for: List[AnnotationClassFilter] = [], ) -> AnnotationLayer: """ Get a token-wise annotation layer by applying a coarse annotation layer on top of PDF's tokens.""" layer = AnnotationLayer() req_layers_info = { x.name: self.get_best_layer(x.name) for x in only_for } for k, v in req_layers_info.items(): if v is None: raise ParentModelNotFoundException(k) req_layers = { k: self.get_annotation_layer(v.id) for k, v in req_layers_info.items() } for child in self.get_xml().findall(f".//{target}"): bbx = BBX.from_element(child) ok = False if only_for == []: ok = True else: for p in only_for: if req_layers[p.name].get_label(bbx) in p.labels: ok = True break if ok: box = annotations.get(bbx, mode="full") if box: layer.add_box( LabelledBBX.from_bbx(bbx, box.label, box.group, box.user_data)) return layer