|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
*/ |
|
|
|
package sun.security.util; |
|
|
|
import javax.security.auth.callback.Callback; |
|
import javax.security.auth.callback.CallbackHandler; |
|
import javax.security.auth.callback.ConfirmationCallback; |
|
import javax.security.auth.callback.NameCallback; |
|
import javax.security.auth.callback.PasswordCallback; |
|
import javax.security.auth.callback.TextOutputCallback; |
|
import javax.security.auth.callback.UnsupportedCallbackException; |
|
|
|
import java.io.BufferedReader; |
|
import java.io.IOException; |
|
import java.io.InputStream; |
|
import java.io.InputStreamReader; |
|
|
|
|
|
|
|
|
|
*/ |
|
public class ConsoleCallbackHandler implements CallbackHandler { |
|
|
|
|
|
|
|
|
|
*/ |
|
public ConsoleCallbackHandler() { } |
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
*/ |
|
public void handle(Callback[] callbacks) |
|
throws IOException, UnsupportedCallbackException |
|
{ |
|
ConfirmationCallback confirmation = null; |
|
|
|
for (int i = 0; i < callbacks.length; i++) { |
|
if (callbacks[i] instanceof TextOutputCallback) { |
|
TextOutputCallback tc = (TextOutputCallback) callbacks[i]; |
|
|
|
String text; |
|
switch (tc.getMessageType()) { |
|
case TextOutputCallback.INFORMATION: |
|
text = ""; |
|
break; |
|
case TextOutputCallback.WARNING: |
|
text = "Warning: "; |
|
break; |
|
case TextOutputCallback.ERROR: |
|
text = "Error: "; |
|
break; |
|
default: |
|
throw new UnsupportedCallbackException( |
|
callbacks[i], "Unrecognized message type"); |
|
} |
|
|
|
String message = tc.getMessage(); |
|
if (message != null) { |
|
text += message; |
|
} |
|
if (text != null) { |
|
System.err.println(text); |
|
} |
|
|
|
} else if (callbacks[i] instanceof NameCallback) { |
|
NameCallback nc = (NameCallback) callbacks[i]; |
|
|
|
if (nc.getDefaultName() == null) { |
|
System.err.print(nc.getPrompt()); |
|
} else { |
|
System.err.print(nc.getPrompt() + |
|
" [" + nc.getDefaultName() + "] "); |
|
} |
|
System.err.flush(); |
|
|
|
String result = readLine(); |
|
if (result.equals("")) { |
|
result = nc.getDefaultName(); |
|
} |
|
|
|
nc.setName(result); |
|
|
|
} else if (callbacks[i] instanceof PasswordCallback) { |
|
PasswordCallback pc = (PasswordCallback) callbacks[i]; |
|
|
|
System.err.print(pc.getPrompt()); |
|
System.err.flush(); |
|
|
|
pc.setPassword(Password.readPassword(System.in, pc.isEchoOn())); |
|
|
|
} else if (callbacks[i] instanceof ConfirmationCallback) { |
|
confirmation = (ConfirmationCallback) callbacks[i]; |
|
|
|
} else { |
|
throw new UnsupportedCallbackException( |
|
callbacks[i], "Unrecognized Callback"); |
|
} |
|
} |
|
|
|
|
|
if (confirmation != null) { |
|
doConfirmation(confirmation); |
|
} |
|
} |
|
|
|
|
|
private String readLine() throws IOException { |
|
String result = new BufferedReader |
|
(new InputStreamReader(System.in)).readLine(); |
|
if (result == null) { |
|
throw new IOException("Cannot read from System.in"); |
|
} |
|
return result; |
|
} |
|
|
|
private void doConfirmation(ConfirmationCallback confirmation) |
|
throws IOException, UnsupportedCallbackException |
|
{ |
|
String prefix; |
|
int messageType = confirmation.getMessageType(); |
|
switch (messageType) { |
|
case ConfirmationCallback.WARNING: |
|
prefix = "Warning: "; |
|
break; |
|
case ConfirmationCallback.ERROR: |
|
prefix = "Error: "; |
|
break; |
|
case ConfirmationCallback.INFORMATION: |
|
prefix = ""; |
|
break; |
|
default: |
|
throw new UnsupportedCallbackException( |
|
confirmation, "Unrecognized message type: " + messageType); |
|
} |
|
|
|
class OptionInfo { |
|
String name; |
|
int value; |
|
OptionInfo(String name, int value) { |
|
this.name = name; |
|
this.value = value; |
|
} |
|
} |
|
|
|
OptionInfo[] options; |
|
int optionType = confirmation.getOptionType(); |
|
switch (optionType) { |
|
case ConfirmationCallback.YES_NO_OPTION: |
|
options = new OptionInfo[] { |
|
new OptionInfo("Yes", ConfirmationCallback.YES), |
|
new OptionInfo("No", ConfirmationCallback.NO) |
|
}; |
|
break; |
|
case ConfirmationCallback.YES_NO_CANCEL_OPTION: |
|
options = new OptionInfo[] { |
|
new OptionInfo("Yes", ConfirmationCallback.YES), |
|
new OptionInfo("No", ConfirmationCallback.NO), |
|
new OptionInfo("Cancel", ConfirmationCallback.CANCEL) |
|
}; |
|
break; |
|
case ConfirmationCallback.OK_CANCEL_OPTION: |
|
options = new OptionInfo[] { |
|
new OptionInfo("OK", ConfirmationCallback.OK), |
|
new OptionInfo("Cancel", ConfirmationCallback.CANCEL) |
|
}; |
|
break; |
|
case ConfirmationCallback.UNSPECIFIED_OPTION: |
|
String[] optionStrings = confirmation.getOptions(); |
|
options = new OptionInfo[optionStrings.length]; |
|
for (int i = 0; i < options.length; i++) { |
|
options[i] = new OptionInfo(optionStrings[i], i); |
|
} |
|
break; |
|
default: |
|
throw new UnsupportedCallbackException( |
|
confirmation, "Unrecognized option type: " + optionType); |
|
} |
|
|
|
int defaultOption = confirmation.getDefaultOption(); |
|
|
|
String prompt = confirmation.getPrompt(); |
|
if (prompt == null) { |
|
prompt = ""; |
|
} |
|
prompt = prefix + prompt; |
|
if (!prompt.equals("")) { |
|
System.err.println(prompt); |
|
} |
|
|
|
for (int i = 0; i < options.length; i++) { |
|
if (optionType == ConfirmationCallback.UNSPECIFIED_OPTION) { |
|
|
|
System.err.println( |
|
i + ". " + options[i].name + |
|
(i == defaultOption ? " [default]" : "")); |
|
} else { |
|
|
|
System.err.println( |
|
i + ". " + options[i].name + |
|
(options[i].value == defaultOption ? " [default]" : "")); |
|
} |
|
} |
|
System.err.print("Enter a number: "); |
|
System.err.flush(); |
|
int result; |
|
try { |
|
result = Integer.parseInt(readLine()); |
|
if (result < 0 || result > (options.length - 1)) { |
|
result = defaultOption; |
|
} |
|
result = options[result].value; |
|
} catch (NumberFormatException e) { |
|
result = defaultOption; |
|
} |
|
|
|
confirmation.setSelectedIndex(result); |
|
} |
|
} |