3 from allmydata.scripts.common import get_alias, DEFAULT_ALIAS, escape_path, \
5 from allmydata.scripts.common_http import do_http, format_http_error
6 from allmydata.util import base32
7 from allmydata.util.stringutils import quote_output, is_printable_ascii
11 class SlowOperationRunner:
13 def run(self, options):
14 stderr = options.stderr
15 self.options = options
16 self.ophandle = ophandle = base32.b2a(os.urandom(16))
17 nodeurl = options['node-url']
18 if not nodeurl.endswith("/"):
20 self.nodeurl = nodeurl
23 rootcap, path = get_alias(options.aliases, where, DEFAULT_ALIAS)
24 except UnknownAliasError, e:
29 url = nodeurl + "uri/%s" % urllib.quote(rootcap)
31 url += "/" + escape_path(path)
32 # todo: should it end with a slash?
33 url = self.make_url(url, ophandle)
34 resp = do_http("POST", url)
35 if resp.status not in (200, 302):
36 print >>stderr, format_http_error("ERROR", resp)
38 # now we poll for results. We nominally poll at t=1, 5, 10, 30, 60,
39 # 90, k*120 seconds, but if the poll takes non-zero time, that will
40 # be slightly longer. I'm not worried about trying to make up for
43 return self.wait_for_results()
46 for i in (1,5,10,30,60,90):
53 def wait_for_results(self):
55 for next in self.poll_times():
63 url = self.nodeurl + "operations/" + self.ophandle
64 url += "?t=status&output=JSON&release-after-complete=true"
65 stdout = self.options.stdout
66 stderr = self.options.stderr
67 resp = do_http("GET", url)
68 if resp.status != 200:
69 print >>stderr, format_http_error("ERROR", resp)
72 data = simplejson.loads(jdata)
73 if not data["finished"]:
75 if self.options.get("raw"):
76 if is_printable_ascii(jdata):
79 print >>stderr, "The JSON response contained unprintable characters:\n%s" % quote_output(jdata)
81 self.write_results(data)