D7net
Home
Console
Upload
information
Create File
Create Folder
About
Tools
:
/
proc
/
thread-self
/
root
/
opt
/
saltstack
/
salt
/
lib
/
python3.10
/
site-packages
/
linode
/
Filename :
oop.py
back
Copy
# vim:ts=2:sw=2:expandtab """ A Python library to provide level-level Linode API interaction. Copyright (c) 2010 Timothy J Fontaine <tjfontaine@gmail.com> Copyright (c) 2010 Josh Wright <jshwright@gmail.com> Copyright (c) 2010 Ryan Tucker <rtucker@gmail.com> Permission is hereby granted, free of charge, to any person obtaining a copy of this software and associated documentation files (the "Software"), to deal in the Software without restriction, including without limitation the rights to use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons to whom the Software is furnished to do so, subject to the following conditions: The above copyright notice and this permission notice shall be included in all copies or substantial portions of the Software. THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. """ import logging from os import environ from api import Api, LowerCaseDict from fields import * _id_cache = {} ActiveContext = None class LinodeObject(object): fields = None update_method = None create_method = None primary_key = None list_method = None def __init__(self, entry={}): entry = dict([(str(k), v) for k,v in entry.items()]) self.__entry = LowerCaseDict(entry) def __getattr__(self, name): name = name.replace('_LinodeObject', '') if name == '__entry': return self.__dict__[name] elif name not in self.fields: raise AttributeError else: f= self.fields[name] value = None if f.field.lower() in self.__entry: value = self.__entry[f.field.lower()] return f.to_py(value) def __setattr__(self, name, value): name = name.replace('_LinodeObject', '') if name == '__entry': object.__setattr__(self, name, value) elif name not in self.fields: raise AttributeError else: f = self.fields[name] self.__entry[f.field.lower()] = f.to_linode(value) def __str__(self): s = [] for k,v in self.fields.items(): if v.field in self.__entry: value = v.to_py(self.__entry[v.field]) if isinstance(value, list): s.append('%s: [%s]' % (k, ', '.join([str(x) for x in value]))) else: s.append('%s: %s' % (k, str(value))) return '['+', '.join(s)+']' def save(self): if self.id: self.update() else: self.id = self.create_method(ActiveContext, **self.__entry)[self.primary_key] def update(self): self.update_method(ActiveContext, **self.__entry) @classmethod def __resolve_kwargs(self, kw): kwargs = {} for k, v in kw.items(): f = self.fields[k.lower()] kwargs[f.field] = f.to_linode(v) return kwargs @classmethod def list(self, **kw): kwargs = self.__resolve_kwargs(kw) """ if self not in _id_cache: _id_cache[self] = {} """ for l in self.list_method(ActiveContext, **kwargs): l = LowerCaseDict(l) o = self(l) o.cache_add() yield o @classmethod def get(self, **kw): kwargs = self.__resolve_kwargs(kw) """ if self not in _id_cache: _id_cache[self] = {} """ result = None """ for k,v in _id_cache[self].items(): found = True for i, j in kwargs.items(): if i not in v or v[i] != j: found = False break if not found: continue else: result = v break """ if not result: result = LowerCaseDict(self.list_method(ActiveContext, **kwargs)[0]) o = self(result) o.cache_add() return o else: return self(result) def cache_remove(self): pass """ del _id_cache[self.__class__][self.__entry[self.primary_key]] """ def cache_add(self): pass """ key = self.__class__ if key not in _id_cache: _id_cache[key] = {} _id_cache[key][self.__entry[self.primary_key]] = self.__entry """ class Datacenter(LinodeObject): fields = { 'id' : IntField('DatacenterID'), 'location' : CharField('Location'), 'name' : CharField('Location'), } list_method = Api.avail_datacenters primary_key = 'DatacenterID' class LinodePlan(LinodeObject): fields = { 'id' : IntField('PlanID'), 'label' : CharField('Label'), 'price' : FloatField('Price'), 'ram' : IntField('Ram'), 'xfer' : IntField('Xfer'), } list_method = Api.avail_linodeplans primary_key = 'PlanID' class Linode(LinodeObject): fields = { 'id' : IntField('LinodeID'), 'datacenter' : ForeignField(Datacenter), 'plan' : ForeignField(LinodePlan), 'term' : ChoiceField('PaymentTerm', choices=[1, 12, 24]), 'name' : CharField('Label'), 'label' : CharField('Label'), 'group' : Field('lpm_displayGroup'), 'cpu_enabled' : BoolField('Alert_cpu_enabled'), 'cpu_threshold' : IntField('Alert_cpu_threshold'), 'diskio_enabled' : BoolField('Alert_diskio_enabled'), 'diskio_threshold' : IntField('Alert_diskio_enabled'), 'bwin_enabled' : BoolField('Alert_bwin_enabled'), 'bwin_threshold' : IntField('Alert_bwin_threshold'), 'bwout_enabled' : BoolField('Alert_bwout_enabeld'), 'bwout_threshold' : IntField('Alert_bwout_threshold'), 'bwquota_enabled' : BoolField('Alert_bwquota_enabled'), 'bwquota_threshold' : IntField('Alert_bwquota_threshold'), 'backup_window' : IntField('backupWindow'), 'backup_weekly_day' : ChoiceField('backupWeeklyDay', choices=list(range(6))), 'watchdog' : BoolField('watchdog'), 'total_ram' : IntField('TotalRam'), 'total_diskspace' : IntField('TotalHD'), 'total_xfer' : IntField('TotalXfer'), 'status' : IntField('Status'), } update_method = Api.linode_update create_method = Api.linode_create primary_key = 'LinodeID' list_method = Api.linode_list def boot(self): ### TODO XXX FIXME return LinodeJob return ActiveContext.linode_boot(linodeid=self.id)['JobID'] def shutdown(self): ### TODO XXX FIXME return LinodeJob return ActiveContext.linode_shutdown(linodeid=self.id)['JobID'] def reboot(self): ### TODO XXX FIXME return LinodeJob return ActiveContext.linode_reboot(linodeid=self.id)['JobID'] def delete(self): ActiveContext.linode_delete(linodeid=self.id) self.cache_remove() class LinodeJob(LinodeObject): fields = { 'id' : IntField('JobID'), 'linode' : ForeignField(Linode), 'label' : CharField('Label'), 'name' : CharField('Label'), 'entered' : DateTimeField('ENTERED_DT'), 'started' : DateTimeField('HOST_START_DT'), 'finished' : DateTimeField('HOST_FINISH_DT'), 'message' : CharField('HOST_MESSAGE'), 'duration' : IntField('DURATION'), 'success' : BoolField('HOST_SUCCESS'), 'pending_only' : BoolField('PendingOnly'), } list_method = Api.linode_job_list primary_key = 'JobID' class Distribution(LinodeObject): fields = { 'id' : IntField('DistributionID'), 'label' : CharField('Label'), 'name' : CharField('Label'), 'min' : IntField('MinImageSize'), '64bit' : BoolField('Is64Bit'), 'created' : DateTimeField('CREATE_DT'), } list_method = Api.avail_distributions primary_key = 'DistributionID' class LinodeDisk(LinodeObject): fields = { 'id' : IntField('DiskID'), 'linode' : ForeignField(Linode), 'type' : ChoiceField('Type', choices=['ext3', 'swap', 'raw']), 'size' : IntField('Size'), 'name' : CharField('Label'), 'label' : CharField('Label'), 'status' : IntField('Status'), 'created' : DateTimeField('Create_DT'), 'updated' : DateTimeField('Update_DT'), 'readonly': BoolField('IsReadonly'), } update_method = Api.linode_disk_update create_method = Api.linode_disk_create primary_key = 'DiskID' list_method = Api.linode_disk_list def duplicate(self): ret = ActiveContext.linode_disk_duplicate(linodeid=self.linode.id, diskid=self.id) disk = LinodeDisk.get(linode=self.linode, id=ret['DiskID']) job = LinodeJob(linode=self.linode, id=ret['JobID']) return (disk, job) def resize(self, size): ret = ActiveContext.linode_disk_resize(linodeid=self.linode.id, diskid=self.id, size=size) return LinodeJob.get(linode=self.linode, id=ret['JobID']) def delete(self): ret = ActiveContext.linode_disk_delete(linodeid=self.linode.id, diskid=self.id) job = LinodeJob.get(linode=self.linode, id=ret['JobID']) self.cache_remove() return job @classmethod def create_from_distribution(self, linode, distribution, root_pass, label, size, ssh_key=None): l = ForeignField(Linode).to_linode(linode) d = ForeignField(Distribution).to_linode(distribution) ret = ActiveContext.linode_disk_createfromdistribution(linodeid=l, distributionid=d, rootpass=root_pass, label=label, size=size, rootsshkey=ssh_key) disk = self.get(id=ret['DiskID'], linode=linode) job = LinodeJob(id=ret['JobID'], linode=linode) return (disk, job) class Kernel(LinodeObject): fields = { 'id' : IntField('KernelID'), 'label' : CharField('Label'), 'name' : CharField('Label'), 'is_xen': BoolField('IsXen'), } list_method = Api.avail_kernels primary_key = 'KernelID' class LinodeConfig(LinodeObject): fields = { 'id' : IntField('ConfigID'), 'linode' : ForeignField(Linode), 'kernel' : ForeignField(Kernel), 'disklist' : ListField('DiskList', type=ForeignField(LinodeDisk)), 'name' : CharField('Label'), 'label' : CharField('Label'), 'comments' : CharField('Comments'), 'ram_limit' : IntField('RAMLimit'), 'root_device_num' : IntField('RootDeviceNum'), 'root_device_custom' : IntField('RootDeviceCustom'), 'root_device_readonly': BoolField('RootDeviceRO'), 'disable_updatedb' : BoolField('helper_disableUpdateDB'), 'helper_xen' : BoolField('helper_xen'), 'helper_depmod' : BoolField('helper_depmod'), } update_method = Api.linode_config_update create_method = Api.linode_config_create primary_key = 'ConfigID' list_method = Api.linode_config_list def delete(self): self.cache_remove() ActiveContext.linode_config_delete(linodeid=self.linode.id, configid=self.id) class LinodeIP(LinodeObject): fields = { 'id' : IntField('IPAddressID'), 'linode' : ForeignField(Linode), 'address' : CharField('IPADDRESS'), 'is_public' : BoolField('ISPUBLIC'), 'rdns' : CharField('RDNS_NAME'), } list_method = Api.linode_ip_list primary_key = 'IPAddressID' class Domain(LinodeObject): fields = { 'id' : IntField('DomainID'), 'domain' : CharField('Domain'), 'name' : CharField('Domain'), 'type' : ChoiceField('Type', choices=['master', 'slave']), 'soa_email' : CharField('SOA_Email'), 'refresh' : IntField('Refresh_sec'), 'retry' : IntField('Retry_sec'), 'expire' : IntField('Expire_sec'), 'ttl' : IntField('TTL_sec'), 'status' : ChoiceField('Status', choices=['0', '1', '2']), 'master_ips': ListField('master_ips', type=CharField('master_ips')), } update_method = Api.domain_update create_method = Api.domain_create primary_key = 'DomainID' list_method = Api.domain_list STATUS_OFF = 0 STATUS_ON = 1 STATUS_EDIT = 2 def delete(self): self.cache_remove() ActiveContext.domain_delete(domainid=self.id) class Resource(LinodeObject): fields = { 'id' : IntField('ResourceID'), 'domain' : ForeignField(Domain), 'name' : CharField('Name'), 'type' : CharField('Type'), 'target' : CharField('Target'), 'priority' : IntField('Priority'), 'weight' : IntField('Weight'), 'port' : IntField('Port'), 'protocol' : CharField('Protocol'), 'ttl' : IntField('TTL_sec'), } update_method = Api.domain_resource_update create_method = Api.domain_resource_create primary_key = 'ResourceID' list_method = Api.domain_resource_list def delete(self): self.cache_remove() ActiveContext.domain_resource_delete(domainid=self.domain.id, resourceid=self.id) @classmethod def list_by_type(self, domain, only=None): resources = self.list(domain=domain) r_by_type = { 'A' : [], 'CNAME' : [], 'MX' : [], 'SRV' : [], 'TXT' : [], } for r in resources: r_by_type[r.type.upper()].append(r) if only: return r_by_type[only.upper()] else: return r_by_type def _iter_class(self, results): _id_cache[self] = {} results = LowerCaseDict(results) d = results['data'] for i in d: self(i).cache_add() def fill_cache(): _api.batching = True _api.linode_list() _api.avail_linodeplans() _api.avail_datacenters() _api.avail_distributions() _api.avail_kernels() _api.domain_list() ret = _api.batchFlush() for i,k in enumerate([Linode, LinodePlan, Datacenter, Distribution, Kernel, Domain]): _iter_class(k, ret[i]) for k in _id_cache[Linode].keys(): _api.linode_config_list(linodeid=k) _api.linode_disk_list(linodeid=k) for k in _id_cache[Domain].keys(): _api.domain_resource_list(domainid=k) ret = _api.batchFlush() for r in ret: r = LowerCaseDict(r) if r['action'] == 'linode.config.list': _iter_class(LinodeConfig, r) elif r['action'] == 'linode.disk.list': _iter_class(LinodeDisk, r) elif r['action'] == 'domain.resource.list': _iter_class(Resource, r) _api.batching = False def setup_logging(): logging.basicConfig(level=logging.DEBUG)