old_contents: import sys
  from warnings import warn
  
  
  class Entry(object):
      """Simple container class for data entries."""
      def __init__(self, type, id, score, data):
          self.type = type
          self.id = id
          self.score = score
          self.data = data
  
  
  class TypeAheadSearchSession(object):
      """Class encapsulating a typeahead search session."""
  
      def __init__(self):
          # Keep a record of all commands processed.
          self.commands = []
  
      def run_command(self, command):
          """Validate and execute a search command."""
          # Store this command in the list of commands we have attempted
          # to execute.
          self.commands.append(command)
  
          if command.startswith('ADD '):
              self.add(command[4:])
          elif command.startswith('DEL '):
              self.delete(command[4:])
          elif command.startswith('QUERY '):
              self.query(command[6:])
          elif command.startswith('WQUERY '):
              self.wquery(command[7:])
          else:
              raise ValueError(
                  "Command \"{}\" is not of type ADD, DEL, QUERY,"
                  " or WQUERY.".format(command)
              )
  
      def add(self, command):
          """Add a new item."""
  
      def delete(self, command):
          """Delete an item."""
  
      def query(self, command):
          """Perform a search."""
  
      def wquery(self, command):
          """Perform a weighted search."""
  
  
  class InputWarning(UserWarning):
      """Warning raised when input is longer or shorter than expected."""
  
  
  def main(session=None):
      """Main search loop."""
      if not session:
          session = TypeAheadSearchSession()
  
      # Get the number of expected commands.
      try:
          session.num_commands = sys.stdin.readline().strip()
  
      except (ValueError, TypeError) as e:
          # Raise a new exception with a more elucidating error message.
          raise type(e)(e.args[0].replace('num_commands', "First line of input"))
  
      # Fetch each command from the input.
      for i in range(session.num_commands):
          command = sys.stdin.readline().strip()
  
          # If no input is available, raise a warning and break from this loop.
          if not command:
              warn(
                  "Ecountered unexpected EOF. (Did you provide fewer"
                  " than {} commands?)".format(session.num_commands),
                  InputWarning
              )
              break
  
          session.run_command(command)
  
      # Check whether any input remains, and warn, if so.
      command = sys.stdin.readline().strip()
      if command:
          warn(
              "Encountered unexpected input. (Did you provide more"
              " than {} commands?) Lines from \"{}\" will not be"
              " evaluated.".format(session.num_commands, command),
              InputWarning
          )
  
  
  if __name__ == '__main__':
      main()
  
new_contents: import sys
  from trie import TypeaheadSearchTrie
  
  
  class Entry(object):
      """Simple container class for data entries."""
      def __init__(self, type, id, score, data):
          self.type = type
          self.id = id
          self.score = score
          self.data = data
  
  
  class TypeAheadSearchSession(object):
      """Class encapsulating a typeahead search session."""
  
      def __init__(self):
          self.trie = TypeaheadSearchTrie()
  
      def run_command(self, command):
          """Validate and execute a search command."""
          if command.startswith('ADD '):
              self.add(command[4:])
          elif command.startswith('DEL '):
              self.delete(command[4:])
          elif command.startswith('QUERY '):
              self.query(command[6:])
          elif command.startswith('WQUERY '):
              self.wquery(command[7:])
          else:
              raise ValueError(
                  "Command \"{}\" is not of type ADD, DEL, QUERY,"
                  " or WQUERY.".format(command)
              )
  
      def add(self, command):
          """Add a new item."""
  
      def delete(self, command):
          """Delete an item."""
  
      def query(self, command):
          """Perform a search."""
  
      def wquery(self, command):
          """Perform a weighted search."""
  
  
  def main(session=None):
      """Main search loop."""
      if not session:
          session = TypeAheadSearchSession()
  
      # Get the number of expected commands.
      num_commands = sys.stdin.readline().strip()
  
      # Fetch each command from the input.
      for i in range(num_commands):
          command = sys.stdin.readline().strip()
          session.run_command(command)
  
  
  if __name__ == '__main__':
      main()
  
subject: Remove warning cruft.