JCloudsCloud extends Cloud implements SlaveOptions.Holder { @Restricted(NoExternalUse.class) @RequirePOST public void doProvision(StaplerRequest req, StaplerResponse rsp, @QueryParameter String name) throws IOException { if (!hasPermission(Item.CONFIGURE) && !hasPermission(Cloud.PROVISION)) { checkPermission(Cloud.PROVISION); } if (rsp.getContentType() == null) { rsp.setContentType("text/xml"); } if (name == null) { sendPlaintextError("The slave template name query parameter is missing", rsp); return; } JCloudsSlaveTemplate t = getTemplate(name); if (t == null) { sendPlaintextError("No such slave template with name : " + name, rsp); return; } List<Server> nodes = getOpenstack().getRunningNodes(); final int global = nodes.size(); int globalCap = getEffectiveSlaveOptions().getInstanceCap(); if (global >= globalCap) { String msg = String.format("Instance cap of %s is now reached: %d", this.name, globalCap); sendPlaintextError(msg, rsp); return; } int template = 0; for (Server node : nodes) { if (t.hasProvisioned(node)) { template++; } } int templateCap = t.getEffectiveSlaveOptions().getInstanceCap(); if (template >= templateCap) { String msg = String.format("Instance cap for this template (%s/%s) is now reached: %d", this.name, name, templateCap); sendPlaintextError(msg, rsp); return; } try { provisionAsynchronouslyNotToBlockTheRequestThread(t); rsp.getWriter().println("<ok>Provisioning started</ok>"); } catch (Throwable ex) { sendPlaintextError(ex.getMessage(), rsp); } } @DataBoundConstructor @Restricted(DoNotUse.class)  JCloudsCloud(
            final @Nonnull String name,
            final @Nonnull String endPointUrl,
            final boolean ignoreSsl,
            final @CheckForNull String zone,
            final @CheckForNull SlaveOptions slaveOptions,
            final @CheckForNull List<JCloudsSlaveTemplate> templates,
            final @Nonnull String credentialsId
    ); static @Nonnull List<JCloudsCloud> getClouds(); static @Nonnull JCloudsCloud getByName(@Nonnull String name); @Nonnull SlaveOptions getEffectiveSlaveOptions(); @Nonnull SlaveOptions getRawSlaveOptions(); @Nonnull List<JCloudsSlaveTemplate> getTemplates(); @Nonnull String getEndPointUrl(); @CheckForNull String getZone(); @Override Collection<NodeProvisioner.PlannedNode> provision(Label label, int excessWorkload); @Restricted(NoExternalUse.class) /*for mocking*/ @CheckForNull String slaveIsWaitingFor(@Nonnull JCloudsSlave slave); @Override boolean canProvision(final Label label); @CheckForNull JCloudsSlaveTemplate getTemplate(String name); @Restricted(NoExternalUse.class) @RequirePOST void doProvision(StaplerRequest req, StaplerResponse rsp, @QueryParameter String name); @Restricted(NoExternalUse.class) @Nonnull Openstack getOpenstack(); String getCredentialsId(); @Restricted(DoNotUse.class) // Jelly boolean getIgnoreSsl();  }
@Test public void doProvision() throws Exception { final JCloudsSlaveTemplate template = j.dummySlaveTemplate("asdf"); final JCloudsCloud cloudProvision = getCloudWhereUserIsAuthorizedTo(Cloud.PROVISION, template); j.executeOnServer(new DoProvision(cloudProvision, template)); final JCloudsCloud itemConfigure = getCloudWhereUserIsAuthorizedTo(Item.CONFIGURE, template); j.executeOnServer(new DoProvision(itemConfigure, template)); final JCloudsCloud jenkinsRead = getCloudWhereUserIsAuthorizedTo(Jenkins.READ, template); try { j.executeOnServer(new DoProvision(jenkinsRead, template)); fail("Expected 'AccessDeniedException' exception hasn't been thrown"); } catch (AccessDeniedException ex) { } }