private int run()

in source/com.microsoft.tfs.client.clc/src/com/microsoft/tfs/client/clc/Application.java [165:413]


    private int run(final String[] args, final boolean recursiveCall) {
        log.debug("Entering CLC application"); //$NON-NLS-1$
        log.debug("Command line: "); //$NON-NLS-1$
        for (int i = 0; i < args.length; i++) {
            final int p = args[i].toLowerCase().indexOf("login:"); //$NON-NLS-1$
            if (p < 0) {
                log.debug("     args[" + i + "]: " + args[i]); //$NON-NLS-1$ //$NON-NLS-2$
            } else {
                log.debug("     args[" + i + "]: " + args[i].substring(0, p + 6) + "*******"); //$NON-NLS-1$ //$NON-NLS-2$ //$NON-NLS-3$
            }

        }
        /*
         * create and cache the options map and commands map we also set the
         * maps on the static Help class so the Help class always has access to
         * them
         */
        optionsMap = createOptionsMap();
        commandsMap = createCommandsMap();
        Help.init(commandsMap, optionsMap);

        Command c = null;
        int ret = ExitCode.UNKNOWN;
        boolean printExitCode = false;

        try {
            final String[] tokens = args.clone();

            log.debug("Parse and prepare arguments."); //$NON-NLS-1$
            /*
             * Check to see if the first argument is a file containing commands.
             * Don't allow this if we're being called recursively.
             */
            if (recursiveCall == false && tokens.length > 0 && tokens[0].startsWith("@")) //$NON-NLS-1$
            {
                /*
                 * Search all the arguments for the "continue on error" and
                 * output separator options.
                 */
                boolean continueOnError = false;
                String outputSeparator = null;
                for (int i = 0; i < tokens.length; i++) {
                    if (tokens[i] == null || tokens[i].length() == 0) {
                        continue;
                    }

                    try {
                        final Option o = optionsMap.findOption(tokens[i]);

                        if (o instanceof OptionContinueOnError) {
                            continueOnError = true;
                        } else if (o instanceof OptionOutputSeparator) {
                            outputSeparator = ((OptionOutputSeparator) o).getValue();
                        }
                    } catch (final Exception e) {
                        // Ignore.
                    }
                }

                try {
                    ret = runCommandFile(tokens, continueOnError, outputSeparator);
                } catch (final FileNotFoundException e) {
                    final String messageFormat = Messages.getString("Application.CommandFileCoundNotBeFoundFormat"); //$NON-NLS-1$
                    final String message = MessageFormat.format(messageFormat, tokens[0].substring(1));
                    display.printErrorLine(message);
                } catch (final IOException e) {
                    final String messageFormat = Messages.getString("Application.ErrorReadingFromCommandFileFormat"); //$NON-NLS-1$
                    final String message =
                        MessageFormat.format(messageFormat, tokens[0].substring(1), e.getLocalizedMessage());
                    log.warn(message, e);
                    display.printErrorLine(message);
                }

                return ret;
            }

            final ArrayList<Option> options = new ArrayList<Option>();
            final ArrayList<String> freeArguments = new ArrayList<String>();

            /*
             * Parse all the args into a command, its options, and free
             * arguments.
             */

            final AtomicReference<Exception> outException = new AtomicReference<Exception>();
            c = parseTokens(args, options, freeArguments, outException);

            /*
             * Set the display on the command as soon as possible, so it can
             * write errors/messages.
             */
            if (c != null) {
                c.setInput(input);
                c.setDisplay(display);
            }

            /*
             * Search for the help option anywhere in the command line.
             * Microsoft's client does this for user convenience. Also look for
             * the exit code option while we're searching.
             */
            boolean foundHelpOption = false;
            for (int i = 0; i < options.size(); i++) {
                if (options.get(i) instanceof OptionHelp) {
                    foundHelpOption = true;
                }

                if (options.get(i) instanceof OptionExitCode) {
                    printExitCode = true;
                }
            }

            final boolean invalidCommandArguments = outException.get() != null;

            if (tokens.length == 0 || c == null || foundHelpOption || invalidCommandArguments) {
                if (invalidCommandArguments) {
                    final String messageFormat = Messages.getString("Application.AnArgumentErrorOccurredFormat"); //$NON-NLS-1$
                    final String message =
                        MessageFormat.format(messageFormat, outException.get().getLocalizedMessage());
                    display.printErrorLine(message);
                }

                Help.show(c, display);

                return invalidCommandArguments ? ExitCode.FAILURE : ExitCode.SUCCESS;
            }

            c.setOptions(options.toArray(new Option[0]), commandsMap.getGlobalOptions());
            c.setFreeArguments(freeArguments.toArray(new String[0]));

            log.debug("Execute the command implementation."); //$NON-NLS-1$

            c.run();

            log.debug("Close the command: Flush any remaining notifications and remove the manager"); //$NON-NLS-1$
            c.close();

            ret = c.getExitCode();
        } catch (final CanceledException e) {
            getDisplay().printErrorLine(""); //$NON-NLS-1$
            getDisplay().printErrorLine(Messages.getString("Application.CommandCanceled")); //$NON-NLS-1$

            ret = ExitCode.FAILURE;
        } catch (final InputValidationException e) {
            final String messageFormat = Messages.getString("Application.AnInputValidationErrorOccurredFormat"); //$NON-NLS-1$
            final String message = MessageFormat.format(messageFormat, e.getLocalizedMessage());
            display.printErrorLine(message);

            ret = ExitCode.FAILURE;
        } catch (final ArgumentException e) {
            /*
             * Argument exceptions happen when the user supplies an incorrect
             * command, misspelled options, the wrong option values, is missing
             * an option, or other similar error. We should show the help to the
             * user in this case.
             */
            final String messageFormat = Messages.getString("Application.AnArgumentErrorOccurredFormat"); //$NON-NLS-1$
            final String message = MessageFormat.format(messageFormat, e.getLocalizedMessage());
            display.printErrorLine(message);

            Help.show(c, display);

            ret = ExitCode.FAILURE;
        } catch (final IllegalArgumentException e) {
            final String messageFormat = Messages.getString("Application.AnArgumentErrorOccurredFormat"); //$NON-NLS-1$
            final String message = MessageFormat.format(messageFormat, e.getLocalizedMessage());
            display.printErrorLine(message);

            ret = ExitCode.FAILURE;
        } catch (final CLCException e) {
            /*
             * CLCExceptions have messages that are meaningful to users.
             */
            final String messageFormat = Messages.getString("Application.AClientErrorOccurredFormat"); //$NON-NLS-1$
            final String message = MessageFormat.format(messageFormat, e.getLocalizedMessage());
            log.error(message, e);
            display.printErrorLine(message);

            ret = ExitCode.FAILURE;
        } catch (final MalformedURLException e) {
            final String messageFormat = Messages.getString("Application.StringCouldNotBeConvertedToURLFormat"); //$NON-NLS-1$
            final String message = MessageFormat.format(messageFormat, e.getLocalizedMessage());
            log.info(message, e);
            display.printErrorLine(message);
            ret = ExitCode.FAILURE;
        } catch (final LicenseException e) {
            final String messageFormat = Messages.getString("Application.LicenseErrorFormat"); //$NON-NLS-1$
            final String message = MessageFormat.format(messageFormat, e.getLocalizedMessage());
            log.error(message, e);
            display.printErrorLine(message);

            if (e.getType() == LicenseExceptionType.EULA) {
                display.printErrorLine(Messages.getString("Application.RunTfEulaToAccept")); //$NON-NLS-1$
            } else {
                display.printErrorLine(Messages.getString("Application.RunTfProductkeyToInstall")); //$NON-NLS-1$
            }

            ret = ExitCode.FAILURE;
        } catch (final AuthenticationSecurityException e) {
            /*
             * Thrown when using insecure credentials over an insecure channel.
             */
            log.error(e);
            display.printErrorLine(e.getLocalizedMessage());
            ret = ExitCode.FAILURE;
        } catch (final TFSFederatedAuthException e) {
            /*
             * FederatedAuthenticationException is thrown when
             * DefaultFederatedAuthenticationHandler decided not to try to auth,
             * which only happens because the username and/or password weren't
             * available.
             */
            final String message = Messages.getString("Command.FedAuthRequiresUsernamePassword"); //$NON-NLS-1$
            log.error(message, e);
            display.printErrorLine(message);
            ret = ExitCode.FAILURE;
        } catch (final ProxyException e) {
            final String message = MessageFormat.format(
                Messages.getString("Application.ProblemContactingServerFormat"), //$NON-NLS-1$
                e.getLocalizedMessage());
            log.error(message, e);
            display.printErrorLine(message);
            ret = ExitCode.FAILURE;
        } catch (final TECoreException e) {
            final String messageFormat = Messages.getString("Application.AnErrorOccurredFormat"); //$NON-NLS-1$
            final String message = MessageFormat.format(messageFormat, e.getLocalizedMessage());
            log.error(message, e);
            display.printErrorLine(message);
            ret = ExitCode.FAILURE;
        } catch (final Throwable e) {
            log.error("Unexpected exception: ", e); //$NON-NLS-1$
        }

        // If the exit code never got set, set it to 0.
        if (ret == ExitCode.UNKNOWN) {
            ret = ExitCode.SUCCESS;
        }

        if (printExitCode) {
            final String messageFormat = Messages.getString("Application.ExitCodeFormat"); //$NON-NLS-1$
            final String message = MessageFormat.format(messageFormat, Integer.toString(ret));
            display.printLine(message);
            display.printLine(""); //$NON-NLS-1$
        }

        log.debug("Leaving CLC application"); //$NON-NLS-1$

        return ret;
    }