Permalink
Browse files

terminal.js and terminal_input.js: Fixed the bug where input was stil…

…l going to the terminal if other elements were active (e.g. form input fields).

terminal.js and terminal_input.js:  Added some enhancements to the code that detects which terminal is active and sets the cursor to indicate the state.
term_ww.js:  Fixed the bug where links that were already linkified would get re-linified messing them up (was happening to PDFs).
terminal.py:  Fixed a bug where carriage returns would incorrectly apply a newline.
SSH Plugin:  In ssh_connect.py I commented out the lines that auto-assign the username based on the $GO_USER and $USER environment variables so that users will be prompted for their username if not given in the URL.  This allows users to save bookmarks that contain no username so they may change it on-the-fly each time the bookmark is used.
  • Loading branch information...
liftoff committed Apr 1, 2013
1 parent 9402810 commit 8bc6d7e891430517b0fdd59a0edabe167ee3380e
@@ -482,28 +482,26 @@ def parse_url(url):
.. note:: *password* and *identities* may be returned as None and [], respectively.
"""
-
identities = set()
o = urlparse.urlparse(url)
if o.query:
q_attrs = urlparse.parse_qs(o.query)
for ident in q_attrs.get('identities', []):
identities.update(ident.split(','))
-
if o.port:
port = o.port
else:
port = socket.getservbyname(o.scheme, 'tcp')
-
+ username = None
if o.username:
username = o.username
- elif os.environ.get('GO_USER'):
- username = os.environ['GO_USER']
- elif os.environ.get('USER'):
- username = os.environ['USER']
- else:
- username = None
-
+ # Commented these out so that users can enter an arbitrary username. It is
+ # more user-friendly this way since users won't have to have multiple
+ # bookmarks to the same host just to connect with different usernames.
+ #elif os.environ.get('GO_USER'):
+ #username = os.environ['GO_USER']
+ #elif os.environ.get('USER'):
+ #username = os.environ['USER']
return (o.scheme, username, o.hostname, port, o.password, identities)
@@ -572,7 +570,7 @@ def parse_url(url):
# usernames or passwords (if using autoConnectURL).
try:
if len(args) == 1:
- (scheme, user, host, port, password, identities) = parse_url(args[0])
+ scheme, user, host, port, password, identities = parse_url(args[0])
if scheme == 'telnet':
telnet_connect(user, host, port)
else:
@@ -649,7 +647,7 @@ def parse_url(url):
noop = raw_input(invalid_hostname_err)
continue
elif url.find('://') >= 0:
- (protocol, user, host, port, password, identities) = parse_url(url)
+ protocol, user, host, port, password, identities = parse_url(url)
else:
# Always assume SSH unless given a telnet:// URL
protocol = 'ssh'
@@ -1599,6 +1599,8 @@ go.Base.update(GateOne.Terminal, {
if (!term) {
return true; // Sometimes this can happen if certain things get called a bit too early or out-of-order. Not a big deal since everything will catch up eventually.
}
+ // Always run setActive
+ go.Terminal.setActive(term);
var selectedTerm = localStorage[prefix+'selectedTerminal'];
if (term == selectedTerm) {
return true; // Nothing to do
@@ -1615,6 +1617,21 @@ go.Base.update(GateOne.Terminal, {
E.trigger('terminal:switch_terminal', term);
}, 100);
},
+ setActive: function(term) {
+ /**:GateOne.Terminal.setActive(term)
+
+ Removes the '✈inactive' class from the given *term*.
+ */
+ var terms = u.toArray(u.getNodes(go.prefs.goDiv + ' .terminal')),
+ termNode = go.Terminal.terminals[term]['terminal'];
+ terms.forEach(function(terminalNode) {
+ if (terminalNode == termNode) {
+ terminalNode.classList.remove('✈inactive');
+ } else {
+ terminalNode.classList.add('✈inactive');
+ }
+ });
+ },
switchTerminalEvent: function(term) {
/**:GateOne.Terminal.switchTerminalEvent(term)
@@ -1643,13 +1660,6 @@ go.Base.update(GateOne.Terminal, {
} else {
return; // This can happen if the terminal closed before a timeout completed. Not a big deal, ignore
}
- terms.forEach(function(terminalNode) {
- if (terminalNode == termNode) {
- terminalNode.classList.remove('✈inactive');
- } else {
- terminalNode.classList.add('✈inactive');
- }
- });
sideinfo.innerHTML = displayText;
go.Terminal.displayTermInfo(term);
if (go.Terminal.alignTimer) {
@@ -217,6 +217,7 @@ GateOne.Base.update(GateOne.Terminal.Input, {
logDebug("GateOne.Terminal.Input.onMouseUp: e.button: " + e.button + ", e.which: " + e.which);
// Once the user is done pasting (or clicking), set it back to false for speed
t.Input.mouseDown = false;
+ go.Terminal.setActive(selectedTerm);
if (selectedText) {
// Don't show the pastearea as it will prevent the user from right-clicking to copy.
return;
@@ -287,6 +288,7 @@ GateOne.Base.update(GateOne.Terminal.Input, {
t.Input.inputNode.tabIndex = 1; // Just in case--this is necessary to set focus
go.node.addEventListener('keydown', t.Input.onKeyDown, true);
go.node.addEventListener('keyup', t.Input.onKeyUp, true);
+ t.Input.inputNode.addEventListener('blur', t.Input.disableCapture, true);
terms.forEach(function(termNode) {
termNode.onpaste = t.Input.onPaste;
termNode.onmousedown = t.Input.onMouseDown;
@@ -308,23 +310,28 @@ GateOne.Base.update(GateOne.Terminal.Input, {
logDebug('go.Terminal.Input.disableCapture()');
var terms = u.toArray(u.getNodes(go.prefs.goDiv + ' .terminal'));
if (t.Input.mouseDown) {
+ logDebug('disableCapture() cancelled due to mouseDown.');
return; // Work around Firefox's occasional inability to properly register mouse events (WTF Firefox!)
}
if (t.Input.handlingPaste) {
+ logDebug('disableCapture() cancelled due to paste event.');
// The 'blur' event can be called when focus shifts around for pasting.
return; // Act as if we were never called to avoid flashing the overlay
}
- logDebug('go.Terminal.Input.disableCapture()');
t.Input.inputNode.oninput = null;
t.Input.inputNode.tabIndex = null;
t.Input.inputNode.onkeypress = null;
go.node.removeEventListener('keydown', t.Input.onKeyDown, true);
go.node.removeEventListener('keyup', t.Input.onKeyUp, true);
- terms.forEach(function(termNode) {
- termNode.onpaste = null;
- termNode.onmousedown = null;
- termNode.onmouseup = null;
- termNode.oncopy = null;
+ t.Input.inputNode.removeEventListener('blur', t.Input.disableCapture, true);
+ terms.forEach(function(terminalNode) {
+ terminalNode.onpaste = null;
+ terminalNode.onmousedown = null;
+ terminalNode.onmouseup = null;
+ terminalNode.oncopy = null;
+ if (!terminalNode.classList.contains('✈inactive')) {
+ terminalNode.classList.add('✈inactive');
+ }
});
// TODO: Check to see if this should stay in GateOne.Input:
i.metaHeld = false; // This can get stuck at 'true' if the uses does something like command-tab to switch applications.
@@ -11,7 +11,7 @@ var transformText = function(text, pattern, newString) {
// Here's an example of replacing hypothetical ticket numbers with clickable links:
// transformText("Please see ticket IM123456789", /(\bIM\d{9,10}\b)/g, "<a href='https://support.company.com/tracker?ticket=$1' target='new'>$1</a>")
if (!pattern) {
- pattern = /(\b(https?|ftp|file):\/\/[-A-Z0-9+&@#\/%?=~_|!:,.;]*[-A-Z0-9+&@#\/%=~_|])/ig;
+ pattern = /(\b(https?|web+ssh|ftp|file):\/\/[-A-Z0-9+&@#\/%?=~_|!:,.;]*[-A-Z0-9+&@#\/%=~_|])(?!.*a\>)/ig;
}
if (!newString) {
newString = "<a href='$1' target='new'>$1</a>";
View
@@ -1924,7 +1924,7 @@ def write(self, chars, special_checks=True):
changed = False
# This is commented because of how noisy it is. Uncomment to debug the
# terminal emualtor:
- #logging.debug('handling chars: %s' % repr(chars))
+ logging.debug('handling chars: %s' % repr(chars))
# Only perform special checks (for FileTYpe stuff) if we're given bytes.
# Incoming unicode chars should NOT be binary data.
if not isinstance(chars, bytes):
@@ -2354,6 +2354,8 @@ def carriage_return(self):
Executes a carriage return (sets :attr:`self.cursorX` to 0). In other
words it moves the cursor back to position 0 on the line.
"""
+ if self.cursorX == 0:
+ return # Nothing to do
if divmod(self.cursorX, self.cols+1)[1] == 0:
# A carriage return at the precise end of line means the program is
# assuming vt100-style autowrap. Since we let the browser handle

0 comments on commit 8bc6d7e

Please sign in to comment.