source: fedd/federation/proxy_segment.py @ 37776ea

axis_examplecompt_changesinfo-opsversion-3.01version-3.02
Last change on this file since 37776ea was 37776ea, checked in by Ted Faber <faber@…>, 14 years ago

Split out proxy code for use with other proxies - e.g. protogeni proxy

  • Property mode set to 100644
File size: 2.4 KB
Line 
1#!/usr/local/bin/python
2
3import sys, os
4import re
5
6import tempfile
7import subprocess
8import logging 
9import time
10import signal
11
12from service_error import service_error
13
14class proxy_segment:
15    class ssh_cmd_timeout(RuntimeError): pass
16
17    def __init__(self, log=None, keyfile=None, debug=False):
18        self.log = log or logging.getLogger(\
19                'fedd.access.proxy_segment')
20        self.ssh_privkey_file = keyfile
21        self.debug = debug
22        self.ssh_exec="/usr/bin/ssh"
23        self.scp_exec = "/usr/bin/scp"
24        self.ssh_cmd_timeout = proxy_segment.ssh_cmd_timeout
25
26    def scp_file(self, file, user, host, dest=""):
27        """
28        scp a file to the remote host.  If debug is set the action is only
29        logged.
30        """
31
32        scp_cmd = [self.scp_exec, '-o', 'IdentitiesOnly yes', 
33                '-o', 'StrictHostKeyChecking no', '-i', 
34                self.ssh_privkey_file, file, 
35                "%s@%s:%s" % (user, host, dest)]
36        rv = 0
37
38        try:
39            dnull = open("/dev/null", "w")
40        except IOError:
41            self.log.debug("[ssh_file]: failed to open " + \
42                    "/dev/null for redirect")
43            dnull = Null
44
45        self.log.debug("[scp_file]: %s" % " ".join(scp_cmd))
46        if not self.debug:
47            rv = subprocess.call(scp_cmd, stdout=dnull, 
48                    stderr=dnull, close_fds=True)
49
50        return rv == 0
51
52    def ssh_cmd(self, user, host, cmd, wname=None, timeout=None):
53        """
54        Run a remote command on host as user.  If debug is set, the action
55        is only logged.  Commands are run without stdin, to avoid stray
56        SIGTTINs.
57        """
58        sh_str = ("%s -n -o 'IdentitiesOnly yes' -o " + \
59                "'StrictHostKeyChecking no' -i %s %s@%s %s") % \
60                (self.ssh_exec, self.ssh_privkey_file, 
61                        user, host, cmd)
62
63        try:
64            dnull = open("/dev/null", "w")
65        except IOError:
66            self.log.debug("[ssh_cmd]: failed to open /dev/null " + \
67                    "for redirect")
68            dnull = Null
69
70        self.log.debug("[ssh_cmd]: %s" % sh_str)
71        if not self.debug:
72            if dnull:
73                sub = subprocess.Popen(sh_str, shell=True, stdout=dnull,
74                        stderr=dnull, close_fds=True)
75            else:
76                sub = subprocess.Popen(sh_str, shell=True, close_fds=True)
77            if timeout:
78                i = 0
79                rv = sub.poll()
80                while i < timeout:
81                    if rv is not None: break
82                    else:
83                        time.sleep(1)
84                        rv = sub.poll()
85                        i += 1
86                else:
87                    self.log.debug("Process exceeded runtime: %s" % sh_str)
88                    os.kill(sub.pid, signal.SIGKILL)
89                    raise self.ssh_cmd_timeout();
90                return rv == 0
91            else:
92                return sub.wait() == 0
93        else:
94            if timeout == 0:
95                self.log.debug("debug timeout raised on %s " % sh_str)
96                raise self.ssh_cmd_timeout()
97            else:
98                return True
99
Note: See TracBrowser for help on using the repository browser.