code: def immutable(members="", name="Immutable", verbose=False):
      """
      Produces a class that either can be used standalone or as a base class for persistent classes.
  
      This is a thin wrapper around a named tuple.
  
      Constructing a type and using it to instantiate objects:
  
      >>> Point = immutable('x, y', name='Point')
      >>> p = Point(1, 2)
      >>> p2 = p.set(x=3)
      >>> p
      Point(x=1, y=2)
      >>> p2
      Point(x=3, y=2)
  
      Inheriting from a constructed type. In this case no type name needs to be supplied:
  
      >>> class PositivePoint(immutable('x, y')):
      ...     __slots__ = tuple()
      ...     def __new__(cls, x, y):
      ...         if x > 0 and y > 0:
      ...             return super(PositivePoint, cls).__new__(cls, x, y)
      ...         raise Exception('Coordinates must be positive!')
      ...
      >>> p = PositivePoint(1, 2)
      >>> p.set(x=3)
      PositivePoint(x=3, y=2)
      >>> p.set(y=-3)
      Traceback (most recent call last):
      Exception: Coordinates must be positive!
  
      The persistent class also supports the notion of frozen members. The value of a frozen member
      cannot be updated. For example it could be used to implement an ID that should remain the same
      over time. A frozen member is denoted by a trailing underscore.
  
      >>> Point = immutable('x, y, id_', name='Point')
      >>> p = Point(1, 2, id_=17)
      >>> p.set(x=3)
      Point(x=3, y=2, id_=17)
      >>> p.set(id_=18)
      Traceback (most recent call last):
      AttributeError: Cannot set frozen members id_
      """
  
      if isinstance(members, six.string_types):
          members = members.replace(",", " ").split()
  
      def frozen_member_test():
          frozen_members = [
              "'%s'" % f for f in members if f.endswith("_")
          ]
          if frozen_members:
              return """
          frozen_fields = fields_to_modify & set([{frozen_members}])
          if frozen_fields:
              raise AttributeError('Cannot set frozen members %s' % ', '.join(frozen_fields))
              """.format(
                  frozen_members=", ".join(frozen_members)
              )
  
          return ""
  
      verbose_string = ""
      if sys.version_info < (3, 7):
          # Verbose is no longer supported in Python 3.7
          verbose_string = ", verbose={verbose}".format(verbose=verbose)
  
      quoted_members = ", ".join("'%s'" % m for m in members)
      template = """
  class {class_name}(namedtuple('ImmutableBase', [{quoted_members}]{verbose_string})):
      __slots__ = tuple()
  
      def __repr__(self):
          return super({class_name}, self).__repr__().replace('ImmutableBase', self.__class__.__name__)
  
      def set(self, **kwargs):
          if not kwargs:
              return self
  
          fields_to_modify = set(kwargs.keys())
          if not fields_to_modify <= {member_set}:
              raise AttributeError("'%s' is not a member" % ', '.join(fields_to_modify - {member_set}))
  
          {frozen_member_test}
  
          return self.__class__.__new__(self.__class__, *map(kwargs.pop, [{quoted_members}], self))
  """.format(
          quoted_members=quoted_members,
          member_set="set([%s])" % quoted_members
          if quoted_members
          else "set()",
          frozen_member_test=frozen_member_test(),
          verbose_string=verbose_string,
          class_name=name,
      )
  
      if verbose:
          print(template)
  
      from collections import namedtuple
  
      namespace = dict(
          namedtuple=namedtuple, __name__="pyrsistent_immutable"
      )
      try:
          six.exec_(template, namespace)
      except SyntaxError as e:
          raise SyntaxError(e.message + ":\n" + template)
  
      return namespace[name]
  
label_desc: Use image node_id 1 for calling a global function with example usage: immutable(members, name, verbose) and returns: namespace, str, str