1 22 package org.netbeans.lib.cvsclient.commandLine; 23 24 import java.io.*; 25 import java.text.MessageFormat ; 26 import java.util.Arrays ; 27 import java.util.Comparator ; 28 import java.util.ResourceBundle ; 29 30 import org.netbeans.lib.cvsclient.*; 31 import org.netbeans.lib.cvsclient.CVSRoot; 32 import org.netbeans.lib.cvsclient.admin.*; 33 import org.netbeans.lib.cvsclient.command.*; 34 import org.netbeans.lib.cvsclient.commandLine.command.CommandProvider; 35 import org.netbeans.lib.cvsclient.connection.*; 36 import org.netbeans.lib.cvsclient.connection.StandardScrambler; 37 import org.netbeans.lib.cvsclient.event.CVSListener; 38 39 44 public class CVSCommand { 45 46 private static final String HELP_OPTIONS = "--help-options"; private static final String HELP_COMMANDS = "--help-commands"; private static final String HELP_SYNONYMS = "--help-synonyms"; 50 53 private String repository; 54 55 58 private String localPath; 59 60 63 private Connection connection; 64 65 68 private Client client; 69 70 74 private GlobalOptions globalOptions; 75 76 80 private int port = 0; 81 82 87 public boolean executeCommand(Command command, PrintStream stderr) 88 throws CommandException, AuthenticationException { 89 client.setErrorStream(stderr); 90 return client.executeCommand(command, globalOptions); 91 } 92 93 public void setRepository(String repository) { 94 this.repository = repository; 95 } 96 97 public void setLocalPath(String localPath) { 98 this.localPath = localPath; 99 } 100 101 public void setGlobalOptions(GlobalOptions globalOptions) { 102 this.globalOptions = globalOptions; 103 } 104 105 108 private void connect(CVSRoot root, String password) throws IllegalArgumentException , 109 AuthenticationException, 110 CommandAbortedException { 111 connection = ConnectionFactory.getConnection(root); 112 if (CVSRoot.METHOD_PSERVER.equals(root.getMethod())) { 113 ((PServerConnection) connection).setEncodedPassword(password); 114 if (port > 0) ((PServerConnection) connection).setPort(port); 115 } 116 connection.open(); 117 118 client = new Client(connection, new StandardAdminHandler()); 119 client.setLocalPath(localPath); 120 } 121 122 private void addListener(CVSListener listener) { 123 if (client != null) { 124 client.getEventManager().addCVSListener(listener); 126 } 127 } 128 129 private void close(PrintStream stderr) { 130 try { 131 connection.close(); 132 } 133 catch (IOException e) { 134 stderr.println("Unable to close connection: " + e); 135 } 137 } 138 139 144 private static String getCVSRoot(String workingDir) { 145 String root = null; 146 BufferedReader r = null; 147 if (workingDir == null) { 148 workingDir = System.getProperty("user.dir"); 149 } 150 try { 151 File f = new File(workingDir); 152 File rootFile = new File(f, "CVS/Root"); 153 if (rootFile.exists()) { 154 r = new BufferedReader(new FileReader(rootFile)); 155 root = r.readLine(); 156 } 157 } 158 catch (IOException e) { 159 } 161 finally { 162 try { 163 if (r != null) 164 r.close(); 165 } 166 catch (IOException e) { 167 System.err.println("Warning: could not close CVS/Root file!"); 168 } 169 } 170 if (root == null) { 171 root = System.getProperty("cvs.root"); 172 } 173 return root; 174 } 175 176 182 private static int processGlobalOptions(String [] args, 183 GlobalOptions globalOptions, 184 PrintStream stderr) { 185 final String getOptString = globalOptions.getOptString(); 186 GetOpt go = new GetOpt(args, getOptString); 187 int ch = -1; 188 boolean usagePrint = false; 189 while ((ch = go.getopt()) != go.optEOF) { 190 boolean success = globalOptions.setCVSCommand((char) ch, go.optArgGet()); 192 if (!success) usagePrint = true; 193 } 194 if (usagePrint) { 195 showUsage(stderr); 196 return -10; 197 } 198 return go.optIndexGet(); 199 } 200 201 private static void showUsage(PrintStream stderr) { 202 String usageStr = ResourceBundle.getBundle(CVSCommand.class.getPackage().getName()+".Bundle").getString("MSG_HelpUsage"); stderr.println(MessageFormat.format(usageStr, new Object [] { HELP_OPTIONS, HELP_COMMANDS, HELP_SYNONYMS })); 204 } 209 210 217 private static boolean performLogin(String userName, String hostName, 218 String repository, int port, 219 GlobalOptions globalOptions) { 220 PServerConnection c = new PServerConnection(); 221 c.setUserName(userName); 222 String password = null; 223 try { 224 BufferedReader in = new BufferedReader(new 225 InputStreamReader(System.in)); 226 System.out.print("Enter password: "); 227 password = in.readLine(); 228 } 229 catch (IOException e) { 230 System.err.println("Could not read password: " + e); 231 return false; 232 } 233 234 String encodedPassword = StandardScrambler.getInstance().scramble( 235 password); 236 c.setEncodedPassword(encodedPassword); 237 c.setHostName(hostName); 238 c.setRepository(repository); 239 c.setPort(port); 240 try { 241 c.verify(); 242 } 243 catch (AuthenticationException e) { 244 System.err.println("Could not login to host " + hostName); 245 return false; 246 } 247 String root = globalOptions.getCVSRoot(); 251 try { 252 PasswordsFile.storePassword(root, encodedPassword); 253 System.err.println("Logged in successfully to " + repository + " on host " + hostName); 254 return true; 255 } catch (IOException e) { 256 System.err.println("Error: could not write password file."); 257 return false; 258 } 259 260 } 261 262 268 private static String lookupPassword(String CVSRoot, String CVSRootWithPort, PrintStream stderr) { 269 File passFile = new File(System.getProperty("cvs.passfile", 270 System.getProperty("user.home") + 271 "/.cvspass")); 272 273 BufferedReader reader = null; 274 String password = null; 275 276 try { 277 reader = new BufferedReader(new FileReader(passFile)); 278 String line; 279 while ((line = reader.readLine()) != null) { 280 if (line.startsWith("/1 ")) line = line.substring("/1 ".length()); 281 if (line.startsWith(CVSRoot+" ")) { 282 password = line.substring(CVSRoot.length() + 1); 283 break; 284 } else if (line.startsWith(CVSRootWithPort+" ")) { 285 password = line.substring(CVSRootWithPort.length() + 1); 286 break; 287 } 288 } 289 } 290 catch (IOException e) { 291 stderr.println("Could not read password for host: " + e); 292 return null; 293 } 294 finally { 295 if (reader != null) { 296 try { 297 reader.close(); 298 } 299 catch (IOException e) { 300 stderr.println("Warning: could not close password file."); 301 } 302 } 303 } 304 if (password == null) { 305 stderr.println("Didn't find password for CVSROOT '"+CVSRoot+"'."); 306 } 307 return password; 308 } 309 310 313 public static void main(String [] args) { 314 if (processCommand(args, null, System.getProperty("user.dir"), 315 System.out, System.err)) { 316 System.exit(0); 317 } else { 318 System.exit(1); 319 } 320 } 321 322 332 public static boolean processCommand(String [] args, File[] files, String localPath, 333 PrintStream stdout, PrintStream stderr) { 334 return processCommand(args, files, localPath, 0, stdout, stderr); 335 } 336 337 350 public static boolean processCommand(String [] args, File[] files, String localPath, 351 int port, PrintStream stdout, PrintStream stderr) { 352 assert stdout != null: "The output stream must be defined."; assert stderr != null: "The error stream must be defined."; if (args.length > 0) { 356 if (HELP_OPTIONS.equals(args[0])) { 357 printHelpOptions(stdout); 358 return true; 359 } else if (HELP_COMMANDS.equals(args[0])) { 360 printHelpCommands(stdout); 361 return true; 362 } else if (HELP_SYNONYMS.equals(args[0])) { 363 printHelpSynonyms(stdout); 364 return true; 365 } 366 } 367 try { localPath = new File(localPath).getCanonicalPath(); 369 } catch (IOException ioex) {} 370 GlobalOptions globalOptions = new GlobalOptions(); 374 globalOptions.setCVSRoot(getCVSRoot(localPath)); 375 376 int commandIndex = -1; 379 try { 380 commandIndex = processGlobalOptions(args, globalOptions, stderr); 381 if (commandIndex == -10) return true; 382 } 383 catch (IllegalArgumentException e) { 384 stderr.println("Invalid argument: " + e); 385 return false; 386 } 387 388 if (globalOptions.isShowHelp()) { 389 printHelp(commandIndex, args, stdout, stderr); 390 return true; 391 } 392 393 if (globalOptions.isShowVersion()) { 394 printVersion(stdout, stderr); 395 return true; 396 } 397 398 if (globalOptions.getCVSRoot() == null) { 400 stderr.println("No CVS root is set. Use the cvs.root " + 401 "property, e.g. java -Dcvs.root=\":pserver:user@host:/usr/cvs\"" + 402 " or start the application in a directory containing a CVS subdirectory" + 403 " or use the -d command switch."); 404 return false; 405 } 406 407 CVSRoot root = null; 409 final String cvsRoot = globalOptions.getCVSRoot(); 410 try { 411 root = CVSRoot.parse(cvsRoot); 412 } 413 catch (IllegalArgumentException e) { 414 stderr.println("Incorrect format for CVSRoot: " + cvsRoot + 415 "\nThe correct format is: "+ 416 "[:method:][[user][:password]@][hostname:[port]]/path/to/repository" + 417 "\nwhere \"method\" is pserver."); 418 return false; 419 } 420 421 if (commandIndex >= args.length) { 423 showUsage(stderr); 424 return false; 425 } 426 427 final String command = args[commandIndex]; 428 if (command.equals("login")) { 429 if (CVSRoot.METHOD_PSERVER.equals(root.getMethod())) { 430 return performLogin(root.getUserName(), root.getHostName(), 431 root.getRepository(), root.getPort(), 432 globalOptions); 433 } 434 else { 435 stderr.println("login does not apply for connection type " + 436 "\'" + root.getMethod() + "\'"); 437 return false; 438 } 439 } 440 441 444 Command c = null; 445 try { 446 c = CommandFactory.getDefault().createCommand(command, args, ++commandIndex, globalOptions, localPath); 447 } 448 catch (IllegalArgumentException e) { 449 stderr.println("Illegal argument: " + e.getMessage()); 450 return false; 451 } 452 453 if (files != null && c instanceof BasicCommand) { 454 ((BasicCommand) c).setFiles(files); 455 } 456 457 String password = null; 458 459 if (CVSRoot.METHOD_PSERVER.equals(root.getMethod())) { 460 password = root.getPassword(); 461 if (password != null) { 462 password = StandardScrambler.getInstance().scramble(password); 463 } else { 464 if (port > 0) root.setPort(port); 465 password = lookupPassword(cvsRoot, root.toString(), stderr); 466 if (password == null) { 467 password = StandardScrambler.getInstance().scramble(""); } 469 } 470 } 471 CVSCommand cvsCommand = new CVSCommand(); 472 cvsCommand.setGlobalOptions(globalOptions); 473 cvsCommand.setRepository(root.getRepository()); 474 if (port > 0) { 475 cvsCommand.port = port; 476 } 477 cvsCommand.setLocalPath(localPath); 481 try { 482 cvsCommand.connect(root, password); 483 484 CVSListener list; 485 if (c instanceof ListenerProvider) 486 { 487 list = ((ListenerProvider)c).createCVSListener(stdout, stderr); 488 } else { 489 list = new BasicListener(stdout, stderr); 490 } 491 cvsCommand.addListener(list); 492 boolean status = cvsCommand.executeCommand(c, stderr); 493 return status; 494 } 495 catch (AuthenticationException aex) { 496 stderr.println(aex.getLocalizedMessage()); 497 return false; 498 } 499 catch (CommandAbortedException caex) { 500 stderr.println("Error: " + caex); 501 Thread.currentThread().interrupt(); 502 return false; 503 } 504 catch (Exception t) { 505 stderr.println("Error: " + t); 506 t.printStackTrace(stderr); 507 return false; 508 } 509 finally { 510 if (cvsCommand != null) { 511 cvsCommand.close(stderr); 512 } 513 } 514 } 515 516 private static void printHelpOptions(PrintStream stdout) { 517 String options = ResourceBundle.getBundle(CVSCommand.class.getPackage().getName()+".Bundle").getString("MSG_HelpOptions"); stdout.println(options); 519 } 520 521 private static void printHelpCommands(PrintStream stdout) { 522 String msg = ResourceBundle.getBundle(CVSCommand.class.getPackage().getName()+".Bundle").getString("MSG_CVSCommands"); stdout.println(msg); 524 CommandProvider[] providers = CommandFactory.getDefault().getCommandProviders(); 525 Arrays.sort(providers, new CommandProvidersComparator()); 526 int maxNameLength = 0; 527 for (int i = 0; i < providers.length; i++) { 528 int l = providers[i].getName().length(); 529 if (maxNameLength < l) { 530 maxNameLength = l; 531 } 532 } 533 maxNameLength += 2; for (int i = 0; i < providers.length; i++) { 535 stdout.print("\t"+providers[i].getName()); 536 char spaces[] = new char[maxNameLength - providers[i].getName().length()]; 537 Arrays.fill(spaces, ' '); 538 stdout.print(new String (spaces)); 539 providers[i].printShortDescription(stdout); 540 stdout.println(); 541 } 542 } 543 544 private static void printHelpSynonyms(PrintStream stdout) { 545 String msg = ResourceBundle.getBundle(CVSCommand.class.getPackage().getName()+".Bundle").getString("MSG_CVSSynonyms"); stdout.println(msg); 547 CommandProvider[] providers = CommandFactory.getDefault().getCommandProviders(); 548 Arrays.sort(providers, new CommandProvidersComparator()); 549 int maxNameLength = 0; 550 for (int i = 0; i < providers.length; i++) { 551 int l = providers[i].getName().length(); 552 if (maxNameLength < l) { 553 maxNameLength = l; 554 } 555 } 556 maxNameLength += 2; for (int i = 0; i < providers.length; i++) { 558 String [] synonyms = providers[i].getSynonyms(); 559 if (synonyms.length > 0) { 560 stdout.print("\t"+providers[i].getName()); 561 char spaces[] = new char[maxNameLength - providers[i].getName().length()]; 562 Arrays.fill(spaces, ' '); 563 stdout.print(new String (spaces)); 564 for (int j = 0; j < synonyms.length; j++) { 565 stdout.print(synonyms[j]+" "); 566 } 567 stdout.println(); 568 } 569 } 570 } 571 572 private static void printHelp(int commandIndex, String [] args, 573 PrintStream stdout, PrintStream stderr) { 574 if (commandIndex >= args.length) { 575 showUsage(stdout); 576 } else { 577 String cmdName = args[commandIndex]; 578 CommandProvider provider = CommandFactory.getDefault().getCommandProvider(cmdName); 579 if (provider == null) { 580 printUnknownCommand(cmdName, stderr); 581 } else { 582 provider.printLongDescription(stdout); 583 } 584 } 585 } 586 587 private static void printVersion(PrintStream stdout, PrintStream stderr) { 588 String version = CVSCommand.class.getPackage().getSpecificationVersion(); 589 stdout.println("Java Concurrent Versions System (JavaCVS) "+version+" (client)"); 590 } 591 592 private static void printUnknownCommand(String commandName, PrintStream out) { 593 String msg = ResourceBundle.getBundle(CVSCommand.class.getPackage().getName()+".Bundle").getString("MSG_UnknownCommand"); out.println(MessageFormat.format(msg, new Object [] { commandName })); 595 printHelpCommands(out); 596 } 597 598 private static final class CommandProvidersComparator implements Comparator { 599 600 public int compare(Object o1, Object o2) { 601 if (!(o1 instanceof CommandProvider) || !(o2 instanceof CommandProvider)) { 602 throw new IllegalArgumentException ("Can not compare objects "+o1+" and "+o2); 603 } 604 return ((CommandProvider) o1).getName().compareTo(((CommandProvider) o2).getName()); 605 } 606 607 } 608 609 } 610 | Popular Tags |