class_docstr: Implement a consistent hashing ring.
class_docstr_tok: ["Implement","a","consistent","hashing","ring","."]
docstr: Parse and set up the given nodes.
  
  :param nodes: nodes used to create the continuum (see doc for format).
docstr_tok: ["Parse","and","set","up","the","given","nodes",".",":","param","nodes",":","nodes","used","to","create","the","continuum","(","see","doc","for","format",")","."]
code: def _configure_nodes(self, nodes):
      """Parse and set up the given nodes.
  
      :param nodes: nodes used to create the continuum (see doc for format).
      """
      if isinstance(nodes, str):
          nodes = [nodes]
      elif not isinstance(nodes, (dict, list)):
          raise ValueError(
              f"nodes configuration should be a list or a dict, got {type(nodes)}"
          )
  
      conf_changed = False
      for node in nodes:
          conf = {
              "hostname": node,
              "instance": None,
              "nodename": node,
              "port": None,
              "vnodes": self._default_vnodes,
              "weight": 1,
          }
          current_conf = self.runtime._nodes.get(node, {})
          nodename = node
          # new node, trigger a ring update
          if not current_conf:
              conf_changed = True
          # complex config
          if isinstance(nodes, dict):
              node_conf = nodes[node]
              if isinstance(node_conf, int):
                  conf["weight"] = node_conf
              elif isinstance(node_conf, dict):
                  for k, v in node_conf.items():
                      if k in conf:
                          conf[k] = v
                          # changing those config trigger a ring update
                          if k in ["nodename", "vnodes", "weight"]:
                              if current_conf.get(k) != v:
                                  conf_changed = True
              else:
                  raise ValueError(
                      "node configuration should be a dict or an int,"
                      f" got {type(node_conf)}"
                  )
          if self._weight_fn:
              conf["weight"] = self._weight_fn(**conf)
          # changing the weight of a node trigger a ring update
          if current_conf.get("weight") != conf["weight"]:
              conf_changed = True
          self.runtime._nodes[nodename] = conf
      return conf_changed
  
imports: from bisect import bisect
  from .ring_ketama import KetamaRing
  from .ring_meta import MetaRing
label_desc: Use image node_id 2 for calling the HashRing obj's underlying member method code with example usage: obj._configure_nodes(nodes) and returns: conf_changed