← Back to team overview

launchpad-reviewers team mailing list archive

[Merge] lp:~rvb/maas/api-maas-import-pxe-files-2 into lp:maas

 

Raphaël Badin has proposed merging lp:~rvb/maas/api-maas-import-pxe-files-2 into lp:maas with lp:~rvb/maas/api-maas-import-pxe-files as a prerequisite.

Commit message:
Add api calls to call the task import_pxe_files (either on a particular nodegroup or on all accepted nodegroups).

Requested reviews:
  Launchpad code reviewers (launchpad-reviewers)

For more details, see:
https://code.launchpad.net/~rvb/maas/api-maas-import-pxe-files-2/+merge/132913
-- 
https://code.launchpad.net/~rvb/maas/api-maas-import-pxe-files-2/+merge/132913
Your team Launchpad code reviewers is requested to review the proposed merge of lp:~rvb/maas/api-maas-import-pxe-files-2 into lp:maas.
=== modified file 'src/maasserver/api.py'
--- src/maasserver/api.py	2012-11-01 11:45:29 +0000
+++ src/maasserver/api.py	2012-11-05 16:36:21 +0000
@@ -1198,6 +1198,17 @@
             raise PermissionDenied("That method is reserved to admin users.")
 
     @operation(idempotent=False)
+    def import_pxe_files(self, request):
+        """Import the pxe files on all the accepted cluster controllers."""
+        if not request.user.is_superuser:
+            raise PermissionDenied('Must be a superuser.')
+        accepted_nodegroups = NodeGroup.objects.filter(
+            status=NODEGROUP_STATUS.ACCEPTED)
+        for nodegroup in accepted_nodegroups:
+            nodegroup.import_pxe_files()
+        return HttpResponse("Import of pxe files started.", status=httplib.OK)
+
+    @operation(idempotent=False)
     def reject(self, request):
         """Reject nodegroup enlistment(s).
 
@@ -1282,6 +1293,15 @@
                 {ip: leases[ip] for ip in new_leases if ip in leases})
         return HttpResponse("Leases updated.", status=httplib.OK)
 
+    @operation(idempotent=False)
+    def import_pxe_files(self, request, uuid):
+        """Import the pxe files on this cluster controller."""
+        if not request.user.is_superuser:
+            raise PermissionDenied('Must be a superuser.')
+        nodegroup = get_object_or_404(NodeGroup, uuid=uuid)
+        nodegroup.import_pxe_files()
+        return HttpResponse("Import of pxe files started.", status=httplib.OK)
+
     @operation(idempotent=True)
     def list_nodes(self, request, uuid):
         """Get the list of node ids that are part of this group."""

=== modified file 'src/maasserver/tests/test_api.py'
--- src/maasserver/tests/test_api.py	2012-11-02 09:22:01 +0000
+++ src/maasserver/tests/test_api.py	2012-11-05 16:36:21 +0000
@@ -77,6 +77,7 @@
     MACAddress,
     Node,
     NodeGroup,
+    nodegroup as nodegroup_module,
     NodeGroupInterface,
     Tag,
     )
@@ -116,6 +117,7 @@
 from metadataserver.nodeinituser import get_node_init_user
 from mock import (
     ANY,
+    call,
     Mock,
     )
 from provisioningserver import (
@@ -4034,6 +4036,38 @@
             })
         self.assertEqual(httplib.FORBIDDEN, response.status_code)
 
+    def test_import_pxe_files_calls_script_for_all_accepted_clusters(self):
+        recorder = self.patch(nodegroup_module, 'import_pxe_files', Mock())
+        proxy = factory.make_name('proxy')
+        Config.objects.set_config('http_proxy', proxy)
+        accepted_nodegroups = [
+            factory.make_node_group(status=NODEGROUP_STATUS.ACCEPTED),
+            factory.make_node_group(status=NODEGROUP_STATUS.ACCEPTED),
+        ]
+        factory.make_node_group(status=NODEGROUP_STATUS.REJECTED)
+        factory.make_node_group(status=NODEGROUP_STATUS.PENDING)
+        admin = factory.make_admin()
+        client = OAuthAuthenticatedClient(admin)
+        response = client.post(
+            reverse('nodegroups_handler'), {'op': 'import_pxe_files'})
+        self.assertEqual(
+            httplib.OK, response.status_code,
+            explain_unexpected_response(httplib.OK, response))
+        calls = [
+            call(queue=nodegroup.work_queue, kwargs={'http_proxy': proxy})
+            for nodegroup in accepted_nodegroups
+            ]
+        self.assertItemsEqual(calls, recorder.apply_async.call_args_list)
+
+    def test_import_pxe_files_denied_if_not_admin(self):
+        user = factory.make_user()
+        client = OAuthAuthenticatedClient(user)
+        response = client.post(
+            reverse('nodegroups_handler'), {'op': 'import_pxe_files'})
+        self.assertEqual(
+            httplib.FORBIDDEN, response.status_code,
+            explain_unexpected_response(httplib.FORBIDDEN, response))
+
 
 def log_in_as_normal_user(client):
     """Log `client` in as a normal user."""
@@ -4115,10 +4149,8 @@
 
     def test_nodegroup_list_nodes_works_for_admin(self):
         nodegroup = factory.make_node_group()
-        user = factory.make_user()
-        user.is_superuser = True
-        user.save()
-        client = OAuthAuthenticatedClient(user)
+        admin = factory.make_admin()
+        client = OAuthAuthenticatedClient(admin)
         node = factory.make_node(nodegroup=nodegroup)
         response = client.get(
             reverse('nodegroup_handler', args=[nodegroup.uuid]),
@@ -4129,6 +4161,34 @@
         parsed_result = json.loads(response.content)
         self.assertItemsEqual([node.system_id], parsed_result)
 
+    def test_nodegroup_import_pxe_files_calls_script(self):
+        recorder = self.patch(tasks, 'check_call', Mock())
+        proxy = factory.getRandomString()
+        Config.objects.set_config('http_proxy', proxy)
+        nodegroup = factory.make_node_group()
+        admin = factory.make_admin()
+        client = OAuthAuthenticatedClient(admin)
+        response = client.post(
+            reverse('nodegroup_handler', args=[nodegroup.uuid]),
+            {'op': 'import_pxe_files'})
+        self.assertEqual(
+            httplib.OK, response.status_code,
+            explain_unexpected_response(httplib.OK, response))
+        expected_env = dict(os.environ, http_proxy=proxy, https_proxy=proxy)
+        recorder.assert_called_once_with(
+            ['sudo', '-n', 'maas-import-pxe-files'], env=expected_env)
+
+    def test_nodegroup_import_pxe_files_denied_if_not_admin(self):
+        nodegroup = factory.make_node_group()
+        user = factory.make_user()
+        client = OAuthAuthenticatedClient(user)
+        response = client.post(
+            reverse('nodegroup_handler', args=[nodegroup.uuid]),
+            {'op': 'import_pxe_files'})
+        self.assertEqual(
+            httplib.FORBIDDEN, response.status_code,
+            explain_unexpected_response(httplib.FORBIDDEN, response))
+
     def make_node_hardware_details_request(self, client, nodegroup=None):
         if nodegroup is None:
             nodegroup = factory.make_node_group()