Last active
July 25, 2023 14:12
-
-
Save rly/6aac3d9006ab9127bf39fc21938f5afb to your computer and use it in GitHub Desktop.
Function to return all PyNWB objects in the file that are instances of the neurodata_type class
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from pynwb import NWBHDF5IO, NWBFile | |
def get_neurodata_type_objs_io(io: NWBHDF5IO, neurodata_type: str, namespace: str): | |
"""Return all PyNWB objects in the file that have a neurodata type from a namespace. | |
This works regardless of whether the extension was imported earlier in the python execution. | |
All objects that are instances of the class associated with the given neurodata_type in the | |
given namespace will be returned. This includes objects that are instances of a subclass. | |
For example, if an extension defines a new neurodata type OnePhotonSeries that extends | |
ImageSeries, then `get_neurodata_type_objects_in_file(io, "ImageSeries", "core")` will | |
include all OnePhotonSeries objects. | |
.. code-block:: python | |
from pynwb import NWBHDF5IO | |
with NWBHDF5IO(filepath, mode="r", load_namespaces=True) as io: | |
obj_list = get_neurodata_type_objs_io(io, "Subject", "core") | |
""" | |
# if the extension python module has been imported, this line will return the custom API | |
# class defined in the extension (my.extension.module.path.class_name). | |
# otherwise, this line will return the class generated for reading data with this | |
# neurodata type based on the cached namespace in the file (abc.class_name). | |
pynwb_cls = io.manager.type_map.get_dt_container_cls(neurodata_type, namespace) | |
read_nwbfile = io.read() | |
return get_neurodata_type_objs(read_nwbfile, pynwb_cls) | |
def get_neurodata_type_objs(nwbfile: NWBFile, pynwb_class: type): | |
"""Return all PyNWB objects in the file that are instances of the pynwb_class class. | |
This includes objects that are instances of a subclass. | |
.. code-block:: python | |
from pynwb import ImageSeries | |
obj_list = get_neurodata_type_objects(nwbfile, ImageSeries) | |
""" | |
ret = [obj for obj in nwbfile.objects.values() if isinstance(obj, pynwb_class)] | |
return ret | |
def print_obj_info(io: NWBHDF5IO, obj_list: list): | |
for i, obj in enumerate(obj_list): | |
builder = io.manager.get_builder(obj) | |
print("%d: %s '%s'" % (i, type(obj), obj.name)) | |
print("\tObject ID: %s" % obj.object_id) | |
print("\tHDF5 path: %s" % builder.path) | |
if __name__ == "__main__": | |
# an example data file downloaded from dandiset 000021 that has an extension to the Subject neurodata type | |
filepath = "/Users/rly/Documents/NWB_Data/dandisets/000021/sub-699733573_ses-715093703_probe-810755797_ecephys.nwb" | |
with NWBHDF5IO(filepath, mode="r", load_namespaces=True) as io: | |
# two different approaches to getting the objects | |
# 1) by IO object, neurodata type, and namespace | |
obj_list = get_neurodata_type_objs_io(io, "EcephysSpecimen", "ndx-aibs-ecephys") | |
print_obj_info(io, obj_list) | |
# because ndx-aibs-ecephys.EcephysSpecimen extends core.Subject, the following will return the same objects | |
obj_list = get_neurodata_type_objs_io(io, "Subject", "core") | |
print_obj_info(io, obj_list) | |
# 2) by NWBFile object and PyNWB class | |
from pynwb.file import Subject | |
# because ndx-aibs-ecephys.EcephysSpecimen extends core.Subject, the following will return the same objects | |
nwbfile = io.read() | |
obj_list = get_neurodata_type_objs(nwbfile, Subject) | |
print_obj_info(io, obj_list) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment