def writeFile(self, msg): obj = util.loads(msg) vals = obj["hits"]["hits"] try: f = open(self.index + "_" + self.type + ".json", "a") for val in vals: a = util.dumps(val["_source"], ensure_ascii=False) f.write(a + "\n") finally: f.flush() f.close()
def backup_data(index_pre, start_time, end_time): days = time_to_days(start_time, end_time) flag = 1 for d in days: index = index_pre + d r1 = requests.get(elastic_search_url + '/_snapshot' + elastic_search_backup + '/snapshot_' + d) if r1.status_code == 404 and r1.reason == 'Not Found': json_data = util.dumps({"indices": index, "ignore_unavailable": "false", "include_global_state": "false"}) r = requests.put(elastic_search_url + '/_snapshot' + elastic_search_backup + '/snapshot_' + d, json_data) if r.status_code != 200: logging.info("backup data failed day of " + d) logging.info(r.content) flag = 0 else: logging.info("the day of" + d + " data has backed before") return flag
def get_driverlist(): """ Returns clusto.driverlist, a list of drivers and their qualified class paths. Examples: .. code:: bash $ ${get} ${server_url}/driverlist { "basicappliance": "clusto.drivers.devices.appliance.basicappliance.BasicAppliance", "basiccage": "clusto.drivers.locations.datacenters.basiccage.BasicCage", "basicconsoleserver": "clusto.drivers.devices.consoleservers.basicconsoleserver.BasicConsoleServer", "basicdatacenter": "clusto.drivers.locations.datacenters.basicdatacenter.BasicDatacenter", "basicnetworkswitch": "clusto.drivers.devices.networkswitches.basicnetworkswitch.BasicNetworkSwitch", "basicpowerstrip": "clusto.drivers.devices.powerstrips.basicpowerstrip.BasicPowerStrip", "basicrack": "clusto.drivers.locations.racks.basicrack.BasicRack", "basicserver": "clusto.drivers.devices.servers.basicserver.BasicServer", "basicvirtualserver": "clusto.drivers.devices.servers.basicserver.BasicVirtualServer", "basiczone": "clusto.drivers.locations.zones.basiczone.BasicZone", "clustometa": "clusto.drivers.base.clustometa.ClustoMeta", "device": "clusto.drivers.base.device.Device", "entity": "clusto.drivers.base.driver.Driver", "exclusive_pool": "clusto.drivers.categories.pool.ExclusivePool", "ipmanager": "clusto.drivers.resourcemanagers.ipmanager.IPManager", "location": "clusto.drivers.base.location.Location", "pool": "clusto.drivers.categories.pool.Pool", "resourcemanager": "clusto.drivers.base.resourcemanager.ResourceManager", "simpleentitynamemanager": "clusto.drivers.resourcemanagers.simplenamemanager.SimpleEntityNameManager", "simplenamemanager": "clusto.drivers.resourcemanagers.simplenamemanager.SimpleNameManager", "unique_pool": "clusto.drivers.categories.pool.UniquePool" } HTTP: 200 Content-type: application/json """ driverlist = {} for name, driver in clusto.driverlist.items(): # This looks silly, but it is the easiest way to get class paths in a string. driverlist[name] = "{0}.{1}".format(driver.__module__, driver.__name__) return util.dumps(driverlist, 200)
def get_typelist(): """ Returns clusto.typelist, a list of the most recent drivers to register with that type. Examples: .. code:: bash $ ${get} ${server_url}/typelist { "appliance": "clusto.drivers.devices.appliance.basicappliance.BasicAppliance", "cage": "clusto.drivers.locations.datacenters.basiccage.BasicCage", "clustometa": "clusto.drivers.base.clustometa.ClustoMeta", "consoleserver": "clusto.drivers.devices.consoleservers.basicconsoleserver.BasicConsoleServer", "datacenter": "clusto.drivers.locations.datacenters.basicdatacenter.BasicDatacenter", "generic": "clusto.drivers.base.device.Device", "location": "clusto.drivers.base.location.Location", "networkswitch": "clusto.drivers.devices.networkswitches.basicnetworkswitch.BasicNetworkSwitch", "pool": "clusto.drivers.categories.pool.UniquePool", "powerstrip": "clusto.drivers.devices.powerstrips.basicpowerstrip.BasicPowerStrip", "rack": "clusto.drivers.locations.racks.basicrack.BasicRack", "resourcemanager": "clusto.drivers.resourcemanagers.ipmanager.IPManager", "server": "clusto.drivers.devices.servers.basicserver.BasicVirtualServer", "zone": "clusto.drivers.locations.zones.basiczone.BasicZone" } HTTP: 200 Content-type: application/json """ typelist = {} for name, driver in clusto.typelist.items(): # This looks silly, but it is the easiest way to get class paths in a string. typelist[name] = "{0}.{1}".format(driver.__module__, driver.__name__) return util.dumps(typelist, 200)
def get_by_names(): """ One of the main ``clusto`` operations. Parameters: * Required parameter: At least one ``name`` parameter Returns ``HTTP: 404`` when all entites requested do not exist and ``HTTP: 206`` when a percent of entities requested do not exist. Examples: .. code:: bash $ ${get} ${server_url}/by-names "Provide at least one name to get data from" HTTP: 412 Content-type: application/json $ ${get} -d 'name=nonserver' ${server_url}/by-names [ null ] HTTP: 404 Content-type: application/json $ ${get} -d 'name=testserver1' -d 'name=nonserver' ${server_url}/by-names [ "/basicserver/testserver1", null ] HTTP: 206 Content-type: application/json $ ${get} -H 'Clusto-Mode: expanded' -d 'name=testserver1' -d 'name=testserver2' ${server_url}/by-names [ { "attrs": [], "contents": [], "driver": "basicserver", "name": "testserver1", "parents": [ "/pool/singlepool", "/pool/multipool" ] }, { "attrs": [], "contents": [], "driver": "basicserver", "name": "testserver2", "parents": [ "/pool/multipool" ] } ] HTTP: 200 Content-type: application/json $ ${get} -d 'name=nonserver1' -d 'name=nonserver2' ${server_url}/by-names [ null, null ] HTTP: 404 Content-type: application/json """ objs = [] names = bottle.request.params.getall('name') if not names: return util.dumps('Provide at least one name to get data from', 412) mode = bottle.request.headers.get('Clusto-Mode', default='compact') for name in names: obj, status, msg = util.get(name) try: objs.append(util.show(obj, mode) if obj else None) except TypeError as te: return util.dumps('%s' % (te,), 409) return util.dumps(objs, 200 if all(objs) else 206 if any(objs) else 404)
def get_by_name(name): """ One of the main ``clusto`` operations. Parameters: * Required path parameter: ``name`` - The name you're looking for * Optional: ``driver`` - If provided, a driver check will be added to ensure the resulting object is the type you're expecting .. note:: This function returns expanded objects by default in order to reduce the amount of required custom headers. Therefore, the header is not required to receive expanded objects. Examples: .. code:: bash $ ${get} ${server_url}/by-name/nonserver "Object \"nonserver\" not found (nonserver does not exist.)" HTTP: 404 Content-type: application/json $ ${get} -H 'Clusto-Mode: compact' ${server_url}/by-name/testserver1 "/basicserver/testserver1" HTTP: 200 Content-type: application/json $ ${get} ${server_url}/by-name/testserver1 { "attrs": [], "contents": [], "driver": "basicserver", "name": "testserver1", "parents": [ "/pool/singlepool", "/pool/multipool" ] } HTTP: 200 Content-type: application/json $ ${get} -d 'driver=pool' ${server_url}/by-name/testserver1 "The driver for object \"testserver1\" is not \"pool\"" HTTP: 409 Content-type: application/json $ ${get} -d 'driver=nondriver' ${server_url}/by-name/testserver1 "The driver \"nondriver\" is not a valid driver" HTTP: 412 Content-type: application/json """ driver = bottle.request.params.get('driver', default=None) mode = bottle.request.headers.get('Clusto-Mode', default='expanded') obj, status, msg = util.get(name, driver) if not obj: return util.dumps(msg, status) try: return util.dumps(util.show(obj, mode)) except TypeError as te: return util.dumps('%s' % (te,), 409)
def get_from_pools(): """ One of the main ``clusto`` operations. Parameters: * Required: at least one ``pool`` parameter * Optional: one or more ``driver`` parameter to filter out results * Optional: one or more ``type`` parameter to filter out results * Optional: a boolean ``children`` parameter to search for children recursively (True by default) Examples: .. code:: bash $ ${get} ${server_url}/from-pools "Provide at least one pool to get data from" HTTP: 412 Content-type: application/json $ ${get} -d 'pool=emptypool' ${server_url}/from-pools [] HTTP: 200 Content-type: application/json $ ${get} -d 'pool=singlepool' -d 'pool=multipool' ${server_url}/from-pools [ "/basicserver/testserver1" ] HTTP: 200 Content-type: application/json $ ${get} -H 'Clusto-Mode: expanded' -d 'pool=multipool' ${server_url}/from-pools [ { "attrs": [], "contents": [], "driver": "basicserver", "name": "testserver1", "parents": [ "/pool/singlepool", "/pool/multipool" ] }, { "attrs": [], "contents": [], "driver": "basicserver", "name": "testserver2", "parents": [ "/pool/multipool" ] } ] HTTP: 200 Content-type: application/json """ pools = bottle.request.params.getall('pool') if not pools: return util.dumps('Provide at least one pool to get data from', 412) types = bottle.request.params.getall('type') drivers = bottle.request.params.getall('driver') children = bottle.request.params.get('children', default=True, type=bool) mode = bottle.request.headers.get('Clusto-Mode', default='compact') current = int(bottle.request.headers.get('Clusto-Page', default='0')) per = int(bottle.request.headers.get('Clusto-Per-Page', default='50')) try: ents = clusto.get_from_pools( pools, clusto_types=types, clusto_drivers=drivers, search_children=children ) results = [] headers = {} if current: ents, total = util.page(list(ents), current=current, per=per) headers = { 'Clusto-Pages': total, 'Clusto-Per-Page': per, 'Clusto-Page': current } for ent in ents: results.append(util.show(ent, mode)) return util.dumps(results, headers=headers) except TypeError as te: return util.dumps('%s' % (te,), 409) except LookupError as le: return util.dumps('%s' % (le,), 404) except Exception as e: return util.dumps('%s' % (e,), 500)
def get_by_attr(): """ One of the main ``clusto`` operations. Parameters: * Required: the ``key`` parameter * Optional: the ``subkey`` parameter * Optional: the ``value`` parameter Examples: .. code:: bash $ ${get} ${server_url}/by-attr "Provide a key to use get_by_attr" HTTP: 412 Content-type: application/json $ ${get} -d 'key=nonkey' ${server_url}/by-attr [] HTTP: 200 Content-type: application/json $ ${get} -d 'key=key1' -d 'subkey=subkey1' -d 'value=value1' ${server_url}/by-attr [ "/basicserver/testserver1" ] HTTP: 200 Content-type: application/json $ ${get} -H 'Clusto-Mode: expanded' -d 'key=key1' ${server_url}/by-attr [ { "attrs": [ { "datatype": "string", "key": "key1", "number": null, "subkey": "subkey1", "value": "value1" } ], "contents": [], "driver": "basicserver", "name": "testserver1", "parents": [ "/pool/singlepool", "/pool/multipool" ] }, { "attrs": [ { "datatype": "string", "key": "key1", "number": null, "subkey": "subkey2", "value": "value2" } ], "contents": [], "driver": "basicserver", "name": "testserver2", "parents": [ "/pool/multipool" ] } ] HTTP: 200 Content-type: application/json """ params = ['key', 'subkey', 'value'] kwargs = {} for param in params: val = bottle.request.params.get(param) if val: kwargs[param] = val if not kwargs.get('key'): return util.dumps('Provide a key to use get_by_attr', 412) mode = bottle.request.headers.get('Clusto-Mode', default='compact') headers = { 'Clusto-Minify': bottle.request.headers.get('Clusto-Minify', default='False') } try: ents = clusto.get_by_attr(**kwargs) results = [] for ent in ents: results.append(util.show(ent, mode)) return util.dumps(results, headers=headers) except TypeError as te: return util.dumps('%s' % (te,), 409) except LookupError as le: return util.dumps('%s' % (le,), 404) except Exception as e: return util.dumps('%s' % (e,), 500)
def get_from_pools(): """ One of the main ``clusto`` operations. Parameters: * Required: at least one ``pool`` parameter * Optional: one or more ``driver`` parameter to filter out results * Optional: one or more ``type`` parameter to filter out results * Optional: a boolean ``children`` parameter to search for children recursively (True by default) Examples: .. code:: bash $ ${get} ${server_url}/from-pools "Provide at least one pool to get data from" HTTP: 412 Content-type: application/json $ ${get} -H 'Clusto-Page: notanint' -d 'pool=emptypool' ${server_url}/from-pools "invalid literal for int() with base 10: 'notanint'" HTTP: 400 Content-type: application/json $ ${get} -d 'pool=emptypool' ${server_url}/from-pools [] HTTP: 200 Content-type: application/json $ ${get} -d 'pool=singlepool' -d 'pool=multipool' ${server_url}/from-pools [ "/basicserver/testserver1" ] HTTP: 200 Content-type: application/json $ ${get} -H 'Clusto-Mode: expanded' -d 'pool=multipool' ${server_url}/from-pools [ { "attrs": [ { "datatype": "string", "key": "key1", "number": null, "subkey": "subkey1", "value": "value1" } ], "contents": [], "driver": "basicserver", "name": "testserver1", "parents": [ "/pool/singlepool", "/pool/multipool" ] }, { "attrs": [ { "datatype": "string", "key": "key1", "number": null, "subkey": "subkey2", "value": "value2" } ], "contents": [], "driver": "basicserver", "name": "testserver2", "parents": [ "/pool/multipool" ] } ] HTTP: 200 Content-type: application/json $ ${get} -H 'Clusto-Page: 1' -H 'Clusto-Per-Page: 1' -d 'pool=multipool' ${server_url}/from-pools [ "/basicserver/testserver1" ] HTTP: 200 Content-type: application/json $ ${get} -H 'Clusto-Page: 1' -H 'Clusto-Per-Page: 100' -d 'pool=multipool' ${server_url}/from-pools [ "/basicserver/testserver1", "/basicserver/testserver2" ] HTTP: 200 Content-type: application/json $ ${get} -H 'Clusto-Page: 100' -H 'Clusto-Per-Page: 100' -d 'pool=multipool' ${server_url}/from-pools [] HTTP: 200 Content-type: application/json $ ${get} -H 'Clusto-Minify: True' -d 'pool=multipool' ${server_url}/from-pools ["/basicserver/testserver1", "/basicserver/testserver2"] HTTP: 200 Content-type: application/json """ pools = bottle.request.params.getall('pool') if not pools: return util.dumps('Provide at least one pool to get data from', 412) types = bottle.request.params.getall('type') drivers = bottle.request.params.getall('driver') children = bottle.request.params.get('children', default=True, type=bool) mode = bottle.request.headers.get('Clusto-Mode', default='compact') headers = { 'Clusto-Minify': bottle.request.headers.get('Clusto-Minify', default='False') } try: # Assignments are moved into the try block because of the int casting. current = int(bottle.request.headers.get('Clusto-Page', default='0')) per = int(bottle.request.headers.get('Clusto-Per-Page', default='50')) ents = clusto.get_from_pools( pools, clusto_types=types, clusto_drivers=drivers, search_children=children ) results = [] if current: ents, total = util.page(list(ents), current=current, per=per) headers['Clusto-Pages'] = total headers['Clusto-Per-Page'] = per headers['Clusto-Page'] = current for ent in ents: results.append(util.show(ent, mode)) return util.dumps(results, headers=headers) except ValueError as ve: return util.dumps('%s' % (ve,), 400) except TypeError as te: return util.dumps('%s' % (te,), 409) except LookupError as le: return util.dumps('%s' % (le,), 404) except Exception as e: return util.dumps('%s' % (e,), 500)
def register_ec2_server(): """ Register clusto-ec2 VPCVirtualServer instance from AWS instance ID. Required Parameters: * instance_id: The AWS EC2 instance ID to register Examples: .. code:: bash $ ${post} ${server_url}/ec2 "Missing required parameter 'instance_id'" HTTP: 422 Content-type: application/json $ ${post} --data 'instance_id=i-9edf2407' ${server_url}/ec2 { "name": "e0000", "driver": "vpcvirtualserver", "type": "server", "parents": [ "/vpcsubnet/subnet-eea98989", "/ec2_security_group/sg-1234abcb" ], "attrs": [ { "datatype": "string", "number": null, "value": "t2.micro", "key": "aws", "subkey": "ec2_instance_type" }, ... ], "addresses": [ "10.0.0.10" ] } HTTP: 200 Content-type: application/json """ instance_id = bottle.request.params.getall('instance_id') if not instance_id: return util.dumps("Missing required parameter 'instance_id'", 422) try: instance = VPCVirtualServer.register(instance_id[0]) except Exception as e: return util.dumps(str(e), 500) response = { "name": instance.name, "driver": instance.driver, "type": instance.type, "attrs": [util.unclusto(a) for a in instance.attrs()], "parents": [util.unclusto(x) for x in instance.parents()], "addresses": instance.get_ips(), } bottle.response.content_type = 'application/json' return json.dumps(response)
def get_by_attr(): """ One of the main ``clusto`` operations. Parameters: * Required: the ``key`` parameter * Optional: the ``subkey`` parameter * Optional: the ``value`` parameter Examples: .. code:: bash $ ${get} ${server_url}/by-attr "Provide a key to use get_by_attr" HTTP: 412 Content-type: application/json $ ${get} -d 'key=nonkey' ${server_url}/by-attr [] HTTP: 200 Content-type: application/json $ ${get} -d 'key=key1' -d 'subkey=subkey1' -d 'value=value1' ${server_url}/by-attr [ "/basicserver/testserver1" ] HTTP: 200 Content-type: application/json $ ${get} -H 'Clusto-Mode: expanded' -d 'key=key1' ${server_url}/by-attr [ { "attrs": [ { "datatype": "string", "key": "key1", "number": null, "subkey": "subkey1", "value": "value1" } ], "contents": [], "driver": "basicserver", "ips": [], "name": "testserver1", "parents": [ "/pool/singlepool", "/pool/multipool" ], "type": "server" }, { "attrs": [ { "datatype": "string", "key": "key1", "number": null, "subkey": "subkey2", "value": "value2" } ], "contents": [], "driver": "basicserver", "ips": [], "name": "testserver2", "parents": [ "/pool/multipool" ], "type": "server" } ] HTTP: 200 Content-type: application/json """ params = ['key', 'subkey', 'value'] kwargs = {} for param in params: val = bottle.request.params.get(param) if val: kwargs[param] = val if not kwargs.get('key'): return util.dumps('Provide a key to use get_by_attr', 412) mode = bottle.request.headers.get('Clusto-Mode', default='compact') try: ents = clusto.get_by_attr(**kwargs) results = [] for ent in ents: results.append(util.show(ent, mode)) return util.dumps(results) except TypeError as te: return util.dumps('%s' % (te,), 409) except LookupError as le: return util.dumps('%s' % (le,), 404) except Exception as e: return util.dumps('%s' % (e,), 500)
def get_by_names(): """ One of the main ``clusto`` operations. Parameters: * Required parameter: At least one ``name`` parameter Returns ``HTTP: 404`` when all entites requested do not exist and ``HTTP: 206`` when a percent of entities requested do not exist. Examples: .. code:: bash $ ${get} ${server_url}/by-names "Provide at least one name to get data from" HTTP: 412 Content-type: application/json $ ${get} -d 'name=nonserver' ${server_url}/by-names [ null ] HTTP: 404 Content-type: application/json $ ${get} -d 'name=testserver1' -d 'name=nonserver' ${server_url}/by-names [ "/basicserver/testserver1", null ] HTTP: 206 Content-type: application/json $ ${get} -H 'Clusto-Mode: expanded' -d 'name=testserver1' -d 'name=testserver2' ${server_url}/by-names [ { "attrs": [ { "datatype": "string", "key": "key1", "number": null, "subkey": "subkey1", "value": "value1" } ], "contents": [], "driver": "basicserver", "ips": [], "name": "testserver1", "parents": [ "/pool/singlepool", "/pool/multipool" ], "type": "server" }, { "attrs": [ { "datatype": "string", "key": "key1", "number": null, "subkey": "subkey2", "value": "value2" } ], "contents": [], "driver": "basicserver", "ips": [], "name": "testserver2", "parents": [ "/pool/multipool" ], "type": "server" } ] HTTP: 200 Content-type: application/json $ ${get} -d 'name=nonserver1' -d 'name=nonserver2' ${server_url}/by-names [ null, null ] HTTP: 404 Content-type: application/json """ objs = [] names = bottle.request.params.getall('name') if not names: return util.dumps('Provide at least one name to get data from', 412) mode = bottle.request.headers.get('Clusto-Mode', default='compact') for name in names: obj, status, msg = util.get(name) try: objs.append(util.show(obj, mode) if obj else None) except TypeError as te: return util.dumps('%s' % (te,), 409) return util.dumps(objs, 200 if all(objs) else 206 if any(objs) else 404)
def get_by_name(name): """ One of the main ``clusto`` operations. Parameters: * Required path parameter: ``name`` - The name you're looking for * Optional: ``driver`` - If provided, a driver check will be added to ensure the resulting object is the type you're expecting .. note:: This function returns expanded objects by default in order to reduce the amount of required custom headers. Therefore, the header is not required to receive expanded objects. Examples: .. code:: bash $ ${get} ${server_url}/by-name/nonserver "Object \"nonserver\" not found (nonserver does not exist.)" HTTP: 404 Content-type: application/json $ ${get} -H 'Clusto-Mode: compact' ${server_url}/by-name/testserver1 "/basicserver/testserver1" HTTP: 200 Content-type: application/json $ ${get} ${server_url}/by-name/testserver1 { "attrs": [ { "datatype": "string", "key": "key1", "number": null, "subkey": "subkey1", "value": "value1" } ], "contents": [], "driver": "basicserver", "ips": [], "name": "testserver1", "parents": [ "/pool/singlepool", "/pool/multipool" ], "type": "server" } HTTP: 200 Content-type: application/json $ ${get} -d 'driver=pool' ${server_url}/by-name/testserver1 "The driver for object \"testserver1\" is not \"pool\"" HTTP: 409 Content-type: application/json $ ${get} -d 'driver=nondriver' ${server_url}/by-name/testserver1 "The driver \"nondriver\" is not a valid driver" HTTP: 412 Content-type: application/json """ driver = bottle.request.params.get('driver', default=None) obj, status, msg = util.get(name, driver) if not obj: return util.dumps(msg, status) try: return util.dumps(util.show(obj)) except TypeError as te: return util.dumps('%s' % (te,), 409)
def get_from_pools(): """ One of the main ``clusto`` operations. Parameters: * Required: at least one ``pool`` parameter * Optional: one or more ``driver`` parameter to filter out results * Optional: one or more ``type`` parameter to filter out results * Optional: a boolean ``children`` parameter to search for children recursively (True by default) Examples: .. code:: bash $ ${get} ${server_url}/from-pools "Provide at least one pool to get data from" HTTP: 412 Content-type: application/json $ ${get} -H 'Clusto-Page: notanint' -d 'pool=emptypool' ${server_url}/from-pools "invalid literal for int() with base 10: 'notanint'" HTTP: 400 Content-type: application/json $ ${get} -d 'pool=emptypool' ${server_url}/from-pools [] HTTP: 200 Content-type: application/json $ ${get} -d 'pool=singlepool' -d 'pool=multipool' ${server_url}/from-pools [ "/basicserver/testserver1" ] HTTP: 200 Content-type: application/json $ ${get} -H 'Clusto-Mode: expanded' -d 'pool=multipool' ${server_url}/from-pools [ { "attrs": [ { "datatype": "string", "key": "key1", "number": null, "subkey": "subkey1", "value": "value1" } ], "contents": [], "driver": "basicserver", "ips": [], "name": "testserver1", "parents": [ "/pool/singlepool", "/pool/multipool" ], "type": "server" }, { "attrs": [ { "datatype": "string", "key": "key1", "number": null, "subkey": "subkey2", "value": "value2" } ], "contents": [], "driver": "basicserver", "ips": [], "name": "testserver2", "parents": [ "/pool/multipool" ], "type": "server" } ] HTTP: 200 Content-type: application/json $ ${get} -H 'Clusto-Page: 1' -H 'Clusto-Per-Page: 1' -d 'pool=multipool' ${server_url}/from-pools [ "/basicserver/testserver1" ] HTTP: 200 Content-type: application/json $ ${get} -H 'Clusto-Page: 1' -H 'Clusto-Per-Page: 100' -d 'pool=multipool' ${server_url}/from-pools [ "/basicserver/testserver1", "/basicserver/testserver2" ] HTTP: 200 Content-type: application/json $ ${get} -H 'Clusto-Page: 100' -H 'Clusto-Per-Page: 100' -d 'pool=multipool' ${server_url}/from-pools [] HTTP: 200 Content-type: application/json $ ${get} -H 'Clusto-Minify: True' -d 'pool=multipool' ${server_url}/from-pools ["/basicserver/testserver1", "/basicserver/testserver2"] HTTP: 200 Content-type: application/json """ pools = bottle.request.params.getall('pool') if not pools: return util.dumps('Provide at least one pool to get data from', 412) types = bottle.request.params.getall('type') drivers = bottle.request.params.getall('driver') children = bottle.request.params.get('children', default=True, type=bool) mode = bottle.request.headers.get('Clusto-Mode', default='compact') headers = {} try: # Assignments are moved into the try block because of the int casting. current = int(bottle.request.headers.get('Clusto-Page', default='0')) per = int(bottle.request.headers.get('Clusto-Per-Page', default='50')) ents = clusto.get_from_pools( pools, clusto_types=types, clusto_drivers=drivers, search_children=children ) results = [] if current: ents, total = util.page(list(ents), current=current, per=per) headers['Clusto-Pages'] = total headers['Clusto-Per-Page'] = per headers['Clusto-Page'] = current for ent in ents: results.append(util.show(ent, mode)) return util.dumps(results, headers=headers) except ValueError as ve: return util.dumps('%s' % (ve,), 400) except TypeError as te: return util.dumps('%s' % (te,), 409) except LookupError as le: return util.dumps('%s' % (le,), 404) except Exception as e: return util.dumps('%s' % (e,), 500)