class_docstr: Convenience class to encapsulate TRK file format.
  
  Notes
  -----
  TrackVis (so its file format: TRK) considers the streamline coordinate
  (0,0,0) to be in the corner of the voxel whereas NiBabel's streamlines
  internal representation (Voxel space) assumes (0,0,0) to be in the
  center of the voxel.
  
  Thus, streamlines are shifted by half a voxel on load and are shifted
  back on save.
docstr: Reads a TRK header from a file.
  
  Parameters
  ----------
  fileobj : string or file-like object
      If string, a filename; otherwise an open file-like object
      pointing to TRK file (and ready to read from the beginning
      of the TRK header). Note that calling this function
      does not change the file position.
  
  Returns
  -------
  header : dict
      Metadata associated with this tractogram file.
docstr_tok: ["Reads","a","TRK","header","from","a","file",".","Parameters","--","--","--","--","--","fileobj",":","string","or","file-like","object","If","string",",","a","filename",";","otherwise","an","open","file-like","object","pointing","to","TRK","file","(","and","ready","to","read","from","the","beginning","of","the","TRK","header",")",".","Note","that","calling","this","function","does","not","change","the","file","position",".","Returns","--","--","--","-","header",":","dict","Metadata","associated","with","this","tractogram","file","."]
code: def _read_header(fileobj):
      """Reads a TRK header from a file.
  
      Parameters
      ----------
      fileobj : string or file-like object
          If string, a filename; otherwise an open file-like object
          pointing to TRK file (and ready to read from the beginning
          of the TRK header). Note that calling this function
          does not change the file position.
  
      Returns
      -------
      header : dict
          Metadata associated with this tractogram file.
      """
      # Record start position if this is a file-like object
      start_position = (
          fileobj.tell() if hasattr(fileobj, "tell") else None
      )
  
      with Opener(fileobj) as f:
          # Reading directly from a file into a (mutable) bytearray enables a zero-copy
          # cast to a mutable numpy object with frombuffer
          header_buf = bytearray(header_2_dtype.itemsize)
          f.readinto(header_buf)
          header_rec = np.frombuffer(
              buffer=header_buf, dtype=header_2_dtype
          )
          # Check endianness
          endianness = native_code
          if header_rec["hdr_size"] != TrkFile.HEADER_SIZE:
              endianness = swapped_code
  
              # Swap byte order
              header_rec = header_rec.view(
                  header_rec.dtype.newbyteorder()
              )
              if header_rec["hdr_size"] != TrkFile.HEADER_SIZE:
                  msg = (
                      f"Invalid hdr_size: {header_rec['hdr_size']} "
                      f"instead of {TrkFile.HEADER_SIZE}"
                  )
                  raise HeaderError(msg)
  
          if header_rec["version"] == 1:
              # There is no 4x4 matrix for voxel to RAS transformation.
              header_rec[Field.VOXEL_TO_RASMM] = np.zeros((4, 4))
          elif header_rec["version"] == 3:
              warnings.warn(
                  "Parsing a TRK v3 file as v2. Some features may not be handled correctly.",
                  HeaderWarning,
              )
          elif header_rec["version"] in (2, 3):
              pass  # Nothing more to do.
          else:
              raise HeaderError(
                  "NiBabel only supports versions 1 and 2 of the Trackvis file format"
              )
  
          # Convert the first record of `header_rec` into a dictionary
          header = dict(zip(header_rec.dtype.names, header_rec[0]))
          header[Field.ENDIANNESS] = endianness
  
          # If vox_to_ras[3][3] is 0, it means the matrix is not recorded.
          if header[Field.VOXEL_TO_RASMM][3][3] == 0:
              header[Field.VOXEL_TO_RASMM] = np.eye(4, dtype=np.float32)
              warnings.warn(
                  "Field 'vox_to_ras' in the TRK's header was not recorded. "
                  "Will continue assuming it's the identity.",
                  HeaderWarning,
              )
  
          # Check that the 'vox_to_ras' affine is valid, i.e. should be
          # able to determine the axis directions.
          axcodes = aff2axcodes(header[Field.VOXEL_TO_RASMM])
          if None in axcodes:
              msg = (
                  "The 'vox_to_ras' affine is invalid! Could not"
                  " determine the axis directions from it.\n"
                  f"{header[Field.VOXEL_TO_RASMM]}"
              )
              raise HeaderError(msg)
  
          # By default, the voxel order is LPS.
          # http://trackvis.org/blog/forum/diffusion-toolkit-usage/interpretation-of-track-point-coordinates
          if header[Field.VOXEL_ORDER] == b"":
              msg = (
                  "Voxel order is not specified, will assume 'LPS' since"
                  " it is Trackvis software's default."
              )
              warnings.warn(msg, HeaderWarning)
              header[Field.VOXEL_ORDER] = b"LPS"
  
          # Keep the file position where the data begin.
          header["_offset_data"] = f.tell()
  
      # Set the file position where it was, if it was previously open.
      if start_position is not None:
          fileobj.seek(start_position, os.SEEK_SET)
  
      return header
  
imports: import os
  import string
  import struct
  import warnings
  import numpy
  import nibabel
  from nibabel.openers import Opener
  from nibabel.orientations import aff2axcodes, axcodes2ornt
  from nibabel.volumeutils import endian_codes, native_code, swapped_code
  from .array_sequence import create_arraysequences_from_generator
  from .header import Field
  from .tractogram import LazyTractogram, Tractogram, TractogramItem
  from .tractogram_file import DataError, HeaderError, HeaderWarning, TractogramFile
  from .utils import peek_next
label_desc: Use image node_id 7 for calling the TrkFile obj's underlying member method code with example usage: obj._read_header(fileobj) and returns: header