docs: def inline(args):
      """
      Parse input file with the specified parser and post messages based on lint output
  
      :param args: Contains the following
          interface: How are we going to post comments?
          owner: Username of repo owner
          repo: Repository name
          pr: Pull request ID
          token: Authentication for repository
          url: Root URL of repository (not your project) Default: https://github.com
          dryrun: Prints instead of posting comments.
          zero_exit: If true: always return a 0 exit code.
          install: If true: install linters.
          max_comments: Maximum comments to write
      :return: Exit code. 1 if there are any comments, 0 if there are none.
      """
      # don't load trusted value from config because we don't trust the config
      trusted = args.trusted
      args = load_config(args)
      print("Args:")
      pprint.pprint(args)
      ret_code = 0
  
      # TODO: consider moving this git parsing stuff into the github interface
      url = args.url
      if args.repo_slug:
          owner = args.repo_slug.split("/")[0]
          repo = args.repo_slug.split("/")[1]
      else:
          owner = args.owner
          repo = args.repo
      if args.url:
          try:
              url_to_parse = args.url
              # giturlparse won't parse URLs that don't end in .git
              if not url_to_parse.endswith(".git"):
                  url_to_parse += ".git"
              parsed = giturlparse.parse(str(url_to_parse))
              url = parsed.resource
              if not url.startswith("https://"):
                  url = "https://" + url
              if parsed.owner:
                  owner = parsed.owner
              if parsed.name:
                  repo = parsed.name
          except giturlparse.parser.ParserError:
              pass
      if not args.dryrun and args.interface not in interfaces.INTERFACES:
          print("Valid inline-plz config not found")
          return 1
  
      print("Using interface: {0}".format(args.interface))
      my_interface = None
      filenames = None
      if not args.dryrun:
          my_interface = interfaces.INTERFACES[args.interface](
              owner,
              repo,
              args.pull_request,
              args.branch,
              args.token,
              url,
              args.commit,
              args.ignore_paths,
              args.prefix,
              args.autofix,
              args.set_status,
          )
          if not my_interface.is_valid():
              print("Invalid review. Exiting.")
              return 0
          filenames = my_interface.filenames
          my_interface.start_review()
      try:
          linter_runner = LinterRunner(
              args.install,
              args.autorun,
              args.ignore_paths,
              args.config_dir,
              args.enabled_linters,
              args.disabled_linters,
              args.autofix,
              trusted,
              filenames,
          )
          messages = linter_runner.run_linters()
      except Exception:  # pylint: disable=broad-except
          print("Linting failed:\n{}".format(traceback.format_exc()))
          print("inline-plz version: {}".format(__version__))
          print("Python version: {}".format(sys.version))
          ret_code = 1
          if my_interface:
              my_interface.finish_review(error=True)
          return ret_code
  
      print("{} lint messages found".format(len(messages)))
      print("inline-plz version: {}".format(__version__))
      print("Python version: {}".format(sys.version))
  
      # TODO: implement dryrun as an interface instead of a special case here
  
      if args.dryrun:
          print_messages(messages)
          write_messages_to_json(messages)
          return ret_code
  
      try:
          if my_interface.post_messages(messages, args.max_comments):
              if not args.zero_exit:
                  ret_code = 1
              if args.delete_outdated:
                  my_interface.clear_outdated_messages()
              my_interface.finish_review(success=False)
              write_messages_to_json(messages)
              return ret_code
  
          if args.delete_outdated:
              my_interface.clear_outdated_messages()
          my_interface.finish_review(success=True)
      except KeyError:
          print("Interface not found: {}".format(args.interface))
          traceback.print_exc()
      write_messages_to_json(messages)
      return ret_code