Repository: ambari Updated Branches: refs/heads/trunk 378b9606c -> 1f8f6de2c
AMBARI-5184. Create repo files for Ubuntu based on the urls that are passed from the stack defn. (aonishuk) Project: http://git-wip-us.apache.org/repos/asf/ambari/repo Commit: http://git-wip-us.apache.org/repos/asf/ambari/commit/1f8f6de2 Tree: http://git-wip-us.apache.org/repos/asf/ambari/tree/1f8f6de2 Diff: http://git-wip-us.apache.org/repos/asf/ambari/diff/1f8f6de2 Branch: refs/heads/trunk Commit: 1f8f6de2c964dd23eb9cc26e166fce17814e2ed7 Parents: 378b960 Author: Andrew Onischuk <aonis...@hortonworks.com> Authored: Mon Mar 24 08:23:09 2014 -0700 Committer: Andrew Onischuk <aonis...@hortonworks.com> Committed: Mon Mar 24 08:23:09 2014 -0700 ---------------------------------------------------------------------- .../python/resource_management/core/system.py | 10 +- .../libraries/providers/__init__.py | 4 +- .../libraries/providers/repository.py | 45 ++++++++- .../libraries/resources/repository.py | 1 + .../TestRepositoryResource.py | 100 +++++++++++++++++-- 5 files changed, 149 insertions(+), 11 deletions(-) ---------------------------------------------------------------------- http://git-wip-us.apache.org/repos/asf/ambari/blob/1f8f6de2/ambari-agent/src/main/python/resource_management/core/system.py ---------------------------------------------------------------------- diff --git a/ambari-agent/src/main/python/resource_management/core/system.py b/ambari-agent/src/main/python/resource_management/core/system.py index db6c37e..cb4c766 100644 --- a/ambari-agent/src/main/python/resource_management/core/system.py +++ b/ambari-agent/src/main/python/resource_management/core/system.py @@ -69,7 +69,15 @@ class System(object): In case cannot detect --> Fail """ return OSCheck().get_os_version() - + + @lazy_property + def os_release_name(self): + """ + For Ubuntu 12.04: + precise + """ + return OSCheck().get_os_release_name() + @lazy_property def os_type(self): """ http://git-wip-us.apache.org/repos/asf/ambari/blob/1f8f6de2/ambari-agent/src/main/python/resource_management/libraries/providers/__init__.py ---------------------------------------------------------------------- diff --git a/ambari-agent/src/main/python/resource_management/libraries/providers/__init__.py b/ambari-agent/src/main/python/resource_management/libraries/providers/__init__.py index 37d867f..6d8a8f7 100644 --- a/ambari-agent/src/main/python/resource_management/libraries/providers/__init__.py +++ b/ambari-agent/src/main/python/resource_management/libraries/providers/__init__.py @@ -22,10 +22,13 @@ Ambari Agent PROVIDERS = dict( redhat=dict( + Repository="resource_management.libraries.providers.repository.RhelSuseRepositoryProvider", ), suse=dict( + Repository="resource_management.libraries.providers.repository.RhelSuseRepositoryProvider", ), debian=dict( + Repository="resource_management.libraries.providers.repository.DebianRepositoryProvider", ), default=dict( ExecuteHadoop="resource_management.libraries.providers.execute_hadoop.ExecuteHadoopProvider", @@ -33,7 +36,6 @@ PROVIDERS = dict( XmlConfig="resource_management.libraries.providers.xml_config.XmlConfigProvider", PropertiesFile="resource_management.libraries.providers.properties_file.PropertiesFileProvider", MonitorWebserver="resource_management.libraries.providers.monitor_webserver.MonitorWebserverProvider", - Repository="resource_management.libraries.providers.repository.RepositoryProvider", HdfsDirectory="resource_management.libraries.providers.hdfs_directory.HdfsDirectoryProvider", CopyFromLocal="resource_management.libraries.providers.copy_from_local.CopyFromLocalProvider" ), http://git-wip-us.apache.org/repos/asf/ambari/blob/1f8f6de2/ambari-agent/src/main/python/resource_management/libraries/providers/repository.py ---------------------------------------------------------------------- diff --git a/ambari-agent/src/main/python/resource_management/libraries/providers/repository.py b/ambari-agent/src/main/python/resource_management/libraries/providers/repository.py index 4784852..1c5598b 100644 --- a/ambari-agent/src/main/python/resource_management/libraries/providers/repository.py +++ b/ambari-agent/src/main/python/resource_management/libraries/providers/repository.py @@ -20,9 +20,13 @@ Ambari Agent """ +import os +import filecmp +import tempfile +from common_functions import OSCheck from resource_management import * -class RepositoryProvider(Provider): +class RhelSuseRepositoryProvider(Provider): def action_create(self): with Environment.get_instance_copy() as env: repo_file_name = self.resource.repo_file_name @@ -49,4 +53,41 @@ gpgcheck=0""", repo_id=self.resource.repo_id, repo_file_name=self.resource.repo_ repos_dirs = { 'redhat': '/etc/yum.repos.d', 'suse': '/etc/zypp/repos.d' -} \ No newline at end of file +} + + +class DebianRepositoryProvider(Provider): + package_type = "deb" + repo_dir = "/etc/apt/sources.list.d" + update_cmd = 'apt-get update -o Dir::Etc::sourcelist="sources.list.d/{repo_file_name}" -o APT::Get::List-Cleanup="0"' + + def action_create(self): + with Environment.get_instance_copy() as env: + with tempfile.NamedTemporaryFile() as tmpf: + File(tmpf.name, + content = InlineTemplate("{{package_type}} {{base_url}} {{relase_name}} {{components}}", + package_type=self.package_type, base_url=self.resource.base_url, relase_name=env.system.os_release_name, components=' '.join(self.resource.components)) + ) + + repo_file_name = format("{repo_file_name}.list",repo_file_name = self.resource.repo_file_name) + repo_file_path = format("{repo_dir}/{repo_file_name}", repo_dir = self.repo_dir) + + if not os.path.isfile(repo_file_path) or not filecmp.cmp(tmpf.name, repo_file_path): + File(repo_file_path, + content = StaticFile(tmpf.name) + ) + + # this is time expensive + Execute(format(self.update_cmd)) + + def action_remove(self): + with Environment.get_instance_copy() as env: + repo_file_name = format("{repo_file_name}.list",repo_file_name = self.resource.repo_file_name) + repo_file_path = format("{repo_dir}/{repo_file_name}", repo_dir = self.repo_dir) + + if os.path.isfile(repo_file_path): + File(repo_file_path, + action = "delete") + + # this is time expensive + Execute(format(self.update_cmd)) \ No newline at end of file http://git-wip-us.apache.org/repos/asf/ambari/blob/1f8f6de2/ambari-agent/src/main/python/resource_management/libraries/resources/repository.py ---------------------------------------------------------------------- diff --git a/ambari-agent/src/main/python/resource_management/libraries/resources/repository.py b/ambari-agent/src/main/python/resource_management/libraries/resources/repository.py index 94ebc8b..ad6c919 100644 --- a/ambari-agent/src/main/python/resource_management/libraries/resources/repository.py +++ b/ambari-agent/src/main/python/resource_management/libraries/resources/repository.py @@ -30,5 +30,6 @@ class Repository(Resource): base_url = ResourceArgument() mirror_list = ResourceArgument() repo_file_name = ResourceArgument() + components = ForcedListArgument(default=[]) # ubuntu specific actions = Resource.actions + ["create","remove"] \ No newline at end of file http://git-wip-us.apache.org/repos/asf/ambari/blob/1f8f6de2/ambari-agent/src/test/python/resource_management/TestRepositoryResource.py ---------------------------------------------------------------------- diff --git a/ambari-agent/src/test/python/resource_management/TestRepositoryResource.py b/ambari-agent/src/test/python/resource_management/TestRepositoryResource.py index 35b82ca..1aaa111 100644 --- a/ambari-agent/src/test/python/resource_management/TestRepositoryResource.py +++ b/ambari-agent/src/test/python/resource_management/TestRepositoryResource.py @@ -16,14 +16,12 @@ See the License for the specific language governing permissions and limitations under the License. ''' +import os +import tempfile from unittest import TestCase -from mock.mock import patch +from mock.mock import patch, MagicMock from resource_management import * -from resource_management.libraries.providers.repository \ - import RepositoryProvider -from resource_management.libraries.resources.repository \ - import Repository class TestRepositoryResource(TestCase): @@ -86,8 +84,96 @@ name={{repo_file_name}} {% if mirror_list %}mirrorlist={{mirror_list}}{% else %}baseurl={{base_url}}{% endif %} path=/ enabled=1 -gpgcheck=0""", template) - +gpgcheck=0""", template) + + + @patch.object(tempfile, "NamedTemporaryFile") + @patch("resource_management.libraries.providers.repository.Execute") + @patch("resource_management.libraries.providers.repository.File") + @patch("os.path.isfile", new=MagicMock(return_value=True)) + @patch("filecmp.cmp", new=MagicMock(return_value=False)) + @patch.object(System, "os_release_name", new='precise') + @patch.object(System, "os_family", new='debian') + def test_create_repo_debian_repo_exists(self, file_mock, execute_mock, tempfile_mock): + tempfile_mock.return_value = MagicMock(spec=file) + tempfile_mock.return_value.__enter__.return_value.name = "/tmp/1.txt" + + with Environment('/') as env: + Repository('HDP', + base_url='http://download.base_url.org/rpm/', + repo_file_name='HDP', + components = ['a','b','c'] + ) + + template_item = file_mock.call_args_list[0] + template_name = template_item[0][0] + template_content = template_item[1]['content'].get_content() + + self.assertEquals(template_name, '/tmp/1.txt') + self.assertEquals(template_content, 'deb http://download.base_url.org/rpm/ precise a b c\n') + + copy_item = str(file_mock.call_args_list[1]) + self.assertEqual(copy_item, "call('/etc/apt/sources.list.d/HDP.list', content=StaticFile('/tmp/1.txt'))") + + execute_command_item = execute_mock.call_args_list[0][0][0] + self.assertEqual(execute_command_item, 'apt-get update -o Dir::Etc::sourcelist="sources.list.d/HDP.list" -o APT::Get::List-Cleanup="0"') + + @patch.object(tempfile, "NamedTemporaryFile") + @patch("resource_management.libraries.providers.repository.Execute") + @patch("resource_management.libraries.providers.repository.File") + @patch("os.path.isfile", new=MagicMock(return_value=True)) + @patch("filecmp.cmp", new=MagicMock(return_value=True)) + @patch.object(System, "os_release_name", new='precise') + @patch.object(System, "os_family", new='debian') + def test_create_repo_debian_doesnt_repo_exist(self, file_mock, execute_mock, tempfile_mock): + tempfile_mock.return_value = MagicMock(spec=file) + tempfile_mock.return_value.__enter__.return_value.name = "/tmp/1.txt" + + with Environment('/') as env: + Repository('HDP', + base_url='http://download.base_url.org/rpm/', + repo_file_name='HDP', + components = ['a','b','c'] + ) + + template_item = file_mock.call_args_list[0] + template_name = template_item[0][0] + template_content = template_item[1]['content'].get_content() + + self.assertEquals(template_name, '/tmp/1.txt') + self.assertEquals(template_content, 'deb http://download.base_url.org/rpm/ precise a b c\n') + + self.assertEqual(file_mock.call_count, 1) + self.assertEqual(execute_mock.call_count, 0) + + + @patch("os.path.isfile", new=MagicMock(return_value=True)) + @patch.object(System, "os_family", new='debian') + @patch("resource_management.libraries.providers.repository.Execute") + @patch("resource_management.libraries.providers.repository.File") + def test_remove_repo_debian_repo_exist(self, file_mock, execute_mock): + with Environment('/') as env: + Repository('HDP', + action = "remove", + repo_file_name='HDP' + ) + + self.assertEqual(str(file_mock.call_args), "call('/etc/apt/sources.list.d/HDP.list', action='delete')") + self.assertEqual(execute_mock.call_args[0][0], 'apt-get update -o Dir::Etc::sourcelist="sources.list.d/HDP.list" -o APT::Get::List-Cleanup="0"') + + @patch("os.path.isfile", new=MagicMock(return_value=False)) + @patch.object(System, "os_family", new='debian') + @patch("resource_management.libraries.providers.repository.Execute") + @patch("resource_management.libraries.providers.repository.File") + def test_remove_repo_debian_repo_doenst_exist(self, file_mock, execute_mock): + with Environment('/') as env: + Repository('HDP', + action = "remove", + repo_file_name='HDP' + ) + + self.assertEqual(file_mock.call_count, 0) + self.assertEqual(execute_mock.call_count, 0) @patch.object(System, "os_family", new='redhat') @patch("resource_management.libraries.providers.repository.File")