yvoderatskiy

Untitled

Jul 26th, 2015
181
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
Python 8.26 KB | None | 0 0
  1. import abc
  2. import os
  3. import re
  4.  
  5. import jinja2 as j2
  6. import six
  7.  
  8. import sahara.exceptions as e
  9. from sahara.i18n import _
  10. import sahara.utils.xmlutils as xml
  11.  
  12.  
  13. @six.add_metaclass(abc.ABCMeta)
  14. class BaseConfigurationFile(object):
  15.     def __init__(self, file_name):
  16.         self.f_name = file_name
  17.         self._config_dict = dict()
  18.         self._local_path = None
  19.         self._remote_path = None
  20.  
  21.     @property
  22.     def remote_path(self):
  23.         return self._remote_path
  24.  
  25.     @remote_path.setter
  26.     def remote_path(self, path):
  27.         self._remote_path = os.path.join(path, self.f_name)
  28.  
  29.     @abc.abstractmethod
  30.     def render(self):
  31.         pass
  32.  
  33.     @abc.abstractmethod
  34.     def parse(self, content):
  35.         pass
  36.  
  37.     def fetch(self, instance):
  38.         with instance.remote() as r:
  39.             content = r.read_file_from(self.remote_path, run_as_root=True)
  40.             self.parse(content)
  41.  
  42.     def load_properties(self, config_dict):
  43.         for k, v in six.iteritems(config_dict):
  44.             self.add_property(k, v)
  45.  
  46.     def add_property(self, name, value):
  47.         self._config_dict[name] = value
  48.  
  49.     def add_properties(self, properties):
  50.         for prop in six.iteritems(properties):
  51.             self.add_property(*prop)
  52.  
  53.     def _get_config_value(self, name):
  54.         return self._config_dict.get(name, None)
  55.  
  56.     def __repr__(self):
  57.         return '<Configuration file %s>' % self.f_name
  58.  
  59.  
  60. class HadoopXML(BaseConfigurationFile):
  61.     def __init__(self, file_name):
  62.         super(HadoopXML, self).__init__(file_name)
  63.  
  64.     def parse(self, content):
  65.         configs = xml.parse_hadoop_xml_with_name_and_value(content)
  66.         for cfg in configs:
  67.             self.add_property(cfg["name"], cfg["value"])
  68.  
  69.     def render(self):
  70.         return xml.create_hadoop_xml(self._config_dict)
  71.  
  72.  
  73. class RawFile(BaseConfigurationFile):
  74.     def __init__(self, file_name):
  75.         super(RawFile, self).__init__(file_name)
  76.  
  77.     def render(self):
  78.         return self._config_dict.get('content', '')
  79.  
  80.     def parse(self, content):
  81.         self._config_dict.update({'content': content})
  82.  
  83.  
  84. class PropertiesFile(BaseConfigurationFile):
  85.     def __init__(self, file_name):
  86.         super(PropertiesFile, self).__init__(file_name)
  87.  
  88.     def parse(self, content):
  89.         for line in content.splitlines():
  90.             prop = line.strip()
  91.             if len(prop) == 0:
  92.                 continue
  93.             if prop[0] in ['#', '!']:
  94.                 continue
  95.             name, value = prop.split("=")
  96.             self.add_property(name.strip(), value.strip())
  97.  
  98.     def render(self):
  99.         lines = ['%s=%s' % (k, v) for k, v in six.iteritems(self._config_dict)]
  100.         return "\n".join(lines)
  101.  
  102.  
  103. class TemplateFile(BaseConfigurationFile):
  104.     def __init__(self, file_name):
  105.         super(TemplateFile, self).__init__(file_name)
  106.         self._template = None
  107.  
  108.     @staticmethod
  109.     def _j2_render(template, arg_dict):
  110.         if template:
  111.             return template.render(arg_dict)
  112.         else:
  113.             raise e.InvalidDataException(_('Template object must be defined'))
  114.  
  115.     def render(self):
  116.         return self._j2_render(self._template, self._config_dict)
  117.  
  118.     def parse(self, content):
  119.         self._template = j2.Template(content)
  120.  
  121.  
  122. class EnvironmentConfig(BaseConfigurationFile):
  123.     @six.add_metaclass(abc.ABCMeta)
  124.     class Handler(object):
  125.         def __init__(self, value):
  126.             self.value = value
  127.             self.key = None
  128.  
  129.         @classmethod
  130.         def matches(cls, line):
  131.             return cls.regex.match(line) is not None
  132.  
  133.         def __str__(self):
  134.             return str(self.value)
  135.  
  136.     class EmptyLine(Handler):
  137.         @classmethod
  138.         def matches(cls, line):
  139.             return len(line.strip()) == 0
  140.  
  141.     class Comment(Handler):
  142.         regex = re.compile(b'([#\s].*)')
  143.  
  144.     class Property(Handler):
  145.         regex = re.compile(b'(\w+)=(.*)')
  146.  
  147.         def __init__(self, value, key=None):
  148.             super(EnvironmentConfig.Property, self).__init__(value)
  149.             if not key:
  150.                 match = self.regex.match(value)
  151.                 key, value = match.groups()
  152.             self.key = key
  153.             self.value = value
  154.  
  155.         def __str__(self):
  156.             return "%s=%s" % (self.key, self.value)
  157.  
  158.     class ExportProperty(Property):
  159.         regex = re.compile(b'(?:export)(?:\s+)(\w+)=(.*)')
  160.  
  161.         def __init__(self, value, key=None):
  162.             super(EnvironmentConfig.ExportProperty, self).__init__(value, key)
  163.  
  164.         def __str__(self):
  165.             return "export %s=%s" % (self.key, self.value)
  166.  
  167.     _HANDLERS = [Comment, EmptyLine, Property, ExportProperty]
  168.  
  169.     def __init__(self, file_name):
  170.         super(EnvironmentConfig, self).__init__(file_name)
  171.         self._members = []
  172.  
  173.     def parse(self, content):
  174.         lines = content.splitlines()
  175.         from pprint import pprint
  176.         pprint('File %s content' % self.f_name)
  177.         pprint(content)
  178.         for line in lines:
  179.             line = self._escape(line)
  180.             for handler in EnvironmentConfig._HANDLERS:
  181.                 if handler.matches(line):
  182.                     member = handler(line)
  183.                     self._members.append(member)
  184.                     if member.key:
  185.                         if self._config_dict.get(member.key, None):
  186.                             existing = self._config_dict[member.key]
  187.                             self._config_dict[member.key] = existing + " " + member.value
  188.                         else:
  189.                             self._config_dict.update({member.key: member.value})
  190.                     break
  191.  
  192.     @staticmethod
  193.     def _escape(string):
  194.         string = six.text_type(string.strip())
  195.         string = string.replace("\"", "")
  196.         try:
  197.             string = string.encode("utf-8")
  198.         except AttributeError:
  199.             pass
  200.         return string
  201.  
  202.     def render(self):
  203.         for member in self._members:
  204.             if member.key in self._config_dict:
  205.                 member.value = self._config_dict[member.key]
  206.                 del self._config_dict[member.key]
  207.         return '\n'.join(str(m) for m in self._members)
  208.  
  209.     def add_property(self, name, value):
  210.         if name not in self._config_dict:
  211.             self._members.append(
  212.                 EnvironmentConfig.ExportProperty(value, key=name))
  213.         super(EnvironmentConfig, self).add_property(name, value)
  214.  
  215.  
  216. conf = EnvironmentConfig("f")
  217. conf.remote_path = "/dgf/"
  218. print conf
  219.  
  220. content = '''
  221. # Licensed to the Apache Software Foundation (ASF) under one or more\n
  222. # contributor license agreements.  See the NOTICE file distributed with\n
  223. # this work for additional information regarding copyright ownership.\n
  224. # The ASF licenses this file to You under the Apache License, Version 2.0\n
  225. # (the "License"); you may not use this file except in compliance with\n
  226. # the License.  You may obtain a copy of the License at\n
  227. #\n
  228. #     http://www.apache.org/licenses/LICENSE-2.0\n
  229. #\n
  230. # Unless required by applicable law or agreed to in writing, software\n
  231. # distributed under the License is distributed on an "AS IS" BASIS,\n
  232. # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n
  233. # See the License for the specific language governing permissions and\n
  234. # limitations under the License.\n
  235. \n
  236. DRILL_MAX_DIRECT_MEMORY="8G"\n
  237. DRILL_HEAP="4G"\n
  238. \n
  239. export DRILL_JAVA_OPTS="-Xms$DRILL_HEAP -Xmx$DRILL_HEAP -XX:MaxDirectMemorySize=$DRILL_MAX_DIRECT_MEMORY -XX:MaxPermSize=512M -XX:ReservedCodeCacheSize=1G -Ddrill.exec.enable-epoll=true"\n
  240. \n
  241. # Class unloading is disabled by default in Java 7\n
  242. # http://hg.openjdk.java.net/jdk7u/jdk7u60/hotspot/file/tip/src/share/vm/runtime/globals.hpp#l1622\n
  243. export SERVER_GC_OPTS="-XX:+CMSClassUnloadingEnabled -XX:+UseG1GC "\n
  244. \n
  245. export DRILL_JAVA_OPTS="$DRILL_JAVA_OPTS -Djava.security.auth.login.config=/opt/mapr/conf/mapr.login.conf -Dzookeeper.sasl.client=false "\n
  246. \n
  247. export DRILL_LOG_DIR="/opt/mapr/drill/drill-1.1.0/logs"\n
  248. \n
  249. export MAPR_IMPERSONATION_ENABLED=true\n
  250. export MAPR_TICKETFILE_LOCATION=/opt/mapr/conf/mapruserticket\n
  251. '''
  252.  
  253. conf.parse(content)
  254.  
  255. conf.add_property('DRILL_HUY', "HUY")
  256. conf.add_property('DRILL_HUY', "HUY1")
  257.  
  258. from pprint import pprint
  259.  
  260. pprint(conf._config_dict)
  261. pprint(conf.render())
Advertisement
Add Comment
Please, Sign In to add comment