...
In our first steps we will build a simple API call and fire it against a CloudStack management server that is already deployed, configured and ready to accept API calls. You can pick any management server in your lab that has a few VMs running on it.Create a sample json config file telling us where your management server and database server are. Here's a sample:
Code Block | ||
---|---|---|
| ||
prasanna@cloud:~cloudstack-oss# cat demo/demo.cfg { "dbSvr": { "dbSvr": "automation.lab.vmops.com", "passwd": "cloud", "db": "cloud", "port": 3306, "user": "cloud" }, "logger": [ { "name": "TestClient", "file": "/var/log/testclient.log" }, { "name": "TestCase", "file": "/var/log/testcase.log" } ], "mgtSvr": [ { "mgtSvrIp": "automation.lab.vmops.com", "port": 8096 } ] } |
dbSvr
is the location where mysql server is running and passwd is the password for user cloud....
...
Code Block |
---|
In [1]: import marvin
In [2]: from marvin.cloudstackTestCase import *
|
...
Code Block |
---|
In [2]: import marvin.deployDataCenter
|
...
Code Block |
---|
In [3]: config = marvin.deployDataCenter.deployDataCenters('demo/demo.cfg')
In [4]: config.loadCfg()
|
...
Code Block |
---|
In [5]: apiClient = config.testClient.getApiClient()
|
...
Code Block |
---|
In [6]: listconfig = listConfigurations.listConfigurationsCmd()
|
deployVirtualMachineCmd
method inside the deployVirtualMachine
object. Simple, ain't it?...
Code Block |
---|
In [7]: listconfig.name = 'expunge'
|
...
Code Block |
---|
In [8]: listconfigresponse = apiClient.listConfigurations(listconfig)
|
...
Code Block |
---|
In [9]: print listconfigresponse
[ {category : u'Advanced', name : u'expunge.delay', value : u'60', description : u'Determines how long (in seconds) to wait before actually expunging destroyed vm. The default value = the default value of expunge.interval'},
{category : u'Advanced', name : u'expunge.interval', value : u'60', description : u'The interval (in seconds) to wait before running the expunge thread.'},
{category : u'Advanced', name : u'expunge.workers', value : u'3', description : u'Number of workers performing expunge '}]
|
11. The response is presented to us the way our UI receives it, as a JSON object. The object comprises of a list of configurations, each configuration showing the detailed dictionary (key, value) pairs of each config setting.
...
Without much ado, here's the script:
Code Block |
---|
#!/usr/bin/env python import marvin from marvin import cloudstackTestCase from marvin.cloudstackTestCase import * import unittest import hashlib import random class TestDeployVm(cloudstackTestCase): """ This test deploys a virtual machine into a user account using the small service offering and builtin template """ def setUp(self): """ CloudStack internally saves its passwords in md5 form and that is how we specify it in the API. Python's hashlib library helps us to quickly hash strings as follows """ mdf = hashlib.md5() mdf.update('password') mdf_pass = mdf.hexdigest() self.apiClient = self.testClient.getApiClient() #Get ourselves an API client self.acct = createAccount.createAccountCmd() #The createAccount command self.acct.accounttype = 0 #We need a regular user. admins have accounttype=1 self.acct.firstname = 'bugs' self.acct.lastname = 'bunny' #What's up doc? self.acct.password = mdf_pass #The md5 hashed password string self.acct.username = 'bugs' self.acct.email = 'bugs@rabbithole.com' self.acct.account = 'bugs' self.acct.domainid = 1 #The default ROOT domain self.acctResponse = self.apiClient.createAccount(self.acct) # And upon successful creation we'll log a helpful message in our logs # using the default debug logger of the test framework self.debug("successfully created account: %s, user: %s, id: \ %s"%(self.acctResponse.account.account, \ self.acctResponse.account.username, \ self.acctResponse.account.id)) def test_DeployVm(self): """ Let's start by defining the attributes of our VM that we will be deploying on CloudStack. We will be assuming a single zone is available and is configured and all templates are Ready The hardcoded values are used only for brevity. """ deployVmCmd = deployVirtualMachine.deployVirtualMachineCmd() deployVmCmd.zoneid = 1 deployVmCmd.account = self.acct.account deployVmCmd.domainid = self.acct.domainid deployVmCmd.templateid = 5 #For default template- CentOS 5.6(64 bit) deployVmCmd.serviceofferingid = 1 deployVmResponse = self.apiClient.deployVirtualMachine(deployVmCmd) self.debug("VM %s was deployed in the job %s"%(deployVmResponse.id, deployVmResponse.jobid)) # At this point our VM is expected to be Running. Let's find out what # listVirtualMachines tells us about VMs in this account listVmCmd = listVirtualMachines.listVirtualMachinesCmd() listVmCmd.id = deployVmResponse.id listVmResponse = self.apiClient.listVirtualMachines(listVmCmd) self.assertNotEqual(len(listVmResponse), 0, "Check if the list API \ returns a non-empty response") vm = listVmResponse[0] self.assertEqual(vm.id, deployVmResponse.id, "Check if the VM returned \ is the same as the one we deployed") self.assertEqual(vm.state, "Running", "Check if VM has reached \ a state of running") def tearDown(self): # Teardown will delete the Account as well as the VM once the VM reaches "Running" state """ And finally let us cleanup the resources we created by deleting the account. All good unittests are atomic and rerunnable this way """ deleteAcct = deleteAccount.deleteAccountCmd() deleteAcct.id = self.acctResponse.account.id self.apiClient.deleteAccount(deleteAcct) |
...