The previous articles in the API tutorial series taught you how to purge Varnish cache using Cloudways API and how you can perform server operations using Cloudways API. In this tutorial, I’ll explain how to create and delete applications on your Cloudways servers using its API.
Complete code can be found at Application Management via API repository.
Step 1: Install Guzzle
I will use Guzzle to handle all HTTP requests that will be sent to the API. To install Guzzle, run the following command:
composer require guzzlehttp/guzzle
Once the installation finishes, I will create a class which will be our point of interaction with the API.
Step 2: Create the Class to Connect to Cloudways API
Now create a new file and name it CloudwaysAPIClient.php. I will start the code by calling vendor/autoload and define the Guzzle classes.
<?php require 'vendor/autoload.php'; use GuzzleHttp\Client; use GuzzleHttp\Exception\RequestException; use GuzzleHttp\Psr7\Request;
Now, I will create a class along with the constructor that will load the Guzzle client and then prepare the access token for Cloudways API.
<?php Class CloudwaysAPIClient { private $client = null; const API_URL = "https://api.cloudways.com/api/v1"; var $auth_key; var $auth_email; var $accessToken; public function __construct($email,$key) { $this->auth_email = $email; $this->auth_key = $key; $this->client = new GuzzleHttpClient(); $this->prepare_access_token(); } public function prepare_access_token() { try { $url = self::API_URL . "/oauth/access_token"; $data = ['email' => $this->auth_email,'api_key' => $this->auth_key]; $response = $this->client->post($url, ['query' => $data]); $result = json_decode($response->getBody()->getContents()); $this->accessToken = $result->access_token; } catch (RequestException $e) { $response = $this->StatusCodeHandling($e); return $response; } } public function StatusCodeHandling($e) { if ($e->getResponse()->getStatusCode() == '400') { $this->prepare_access_token(); } elseif ($e->getResponse()->getStatusCode() == '422') { $response = json_decode($e->getResponse()->getBody(true)->getContents()); return $response; } elseif ($e->getResponse()->getStatusCode() == '500') { $response = json_decode($e->getResponse()->getBody(true)->getContents()); return $response; } elseif ($e->getResponse()->getStatusCode() == '401') { $response = json_decode($e->getResponse()->getBody(true)->getContents()); return $response; } elseif ($e->getResponse()->getStatusCode() == '403') { $response = json_decode($e->getResponse()->getBody(true)->getContents()); return $response; } else { $response = json_decode($e->getResponse()->getBody(true)->getContents()); return $response; } } }
The class constructor takes the client email and the API key, and then prepares the token using prepare_access_token(). This function sends the request to Cloudways API for a token. Once the token is received, it is saved in the variable $accessToken. Next, I have created StatusCodeHandling() function for handling all the status codes generated by the API.
Next up are the functions that get servers and applications using Cloudways API.
public function get_servers() { try { $url = self::API_URL . "/server"; $option = array('exceptions' => false); $header = array('Authorization'=>'Bearer ' . $this->accessToken); $response = $this->client->get($url, array('headers' => $header)); $result = json_decode($response->getBody()->getContents()); return $result; } catch (RequestException $e) { $response = $this->StatusCodeHandling($e); return $response; } } public function get_applications() { try { $url = self::API_URL . "/apps"; $header = array('Authorization'=>'Bearer ' . $this->accessToken); $response = $this->client->get($url, array('headers' => $header)); return json_decode($response->getBody()->getContents()); } catch (RequestException $e) { $response = $this->StatusCodeHandling($e); return $response; } }
In the above functions, I sent requests to Cloudways binding the access token header to get server and applications, decode the information from JSON and return the data.
I will next create the functions which will add and delete applications.
public function AddApplication($serverid,$application,$app_version,$app_name) { try { $url = self::API_URL . "/app"; $data = ['server_id' => $serverid, 'application' => $application, 'app_version' => $app_version, 'app_label' => $app_name]; $header = array('Authorization'=>'Bearer ' . $this->accessToken); $response = $this->client->post($url, array('query' => $data,'headers' => $header)); return json_decode($response->getBody()->getContents()); } catch (RequestException $e) { $response = $this->StatusCodeHandling($e); return $response; } } public function DeleteApplication($serverid,$applicationid) { try { $url = self::API_URL . "/app/$applicationid"; $data = ['server_id' => $serverid]; $header = array('Authorization'=>'Bearer ' . $this->accessToken); $response = $this->client->delete($url, array('query' => $data,'headers' => $header)); return json_decode($response->getBody()->getContents()); } catch (RequestException $e) { $response = $this->StatusCodeHandling($e); return $response; } }
In the add application function, I bind the required parameters (server id, application name, application version and application name) and send the request to API in order to add the application.
$data = ['server_id' => $serverid, 'application' => $application, 'app_version' => $app_version, 'app_label' => $app_name ];
The delete application function takes the serverid and applicationid, bind the parameters and send the request to Application API.
Following is the complete code for CloudwaysClientAPI:
<?php require 'vendor/autoload.php'; use GuzzleHttp\Client; use GuzzleHttp\Exception\RequestException; use GuzzleHttp\Psr7\Request; Class CloudwaysAPI { private $client = null; const API_URL = "https://api.cloudways.com/api/v1"; var $auth_key; var $auth_email; var $accessToken; public function __construct($email,$key) { $this->auth_email = $email; $this->auth_key = $key; $this->client = new GuzzleHttpClient(); $this->prepare_access_token(); } public function prepare_access_token() { try { $url = self::API_URL . "/oauth/access_token"; $data = ['email' => $this->auth_email,'api_key' => $this->auth_key]; $response = $this->client->post($url, ['query' => $data]); $result = json_decode($response->getBody()->getContents()); $this->accessToken = $result->access_token; } catch (RequestException $e) { $response = $this->StatusCodeHandling($e); return $response; } } public function StatusCodeHandling($e) { if ($e->getResponse()->getStatusCode() == '400') { $this->prepare_access_token(); } elseif ($e->getResponse()->getStatusCode() == '422') { $response = json_decode($e->getResponse()->getBody(true)->getContents()); return $response; } elseif ($e->getResponse()->getStatusCode() == '500') { $response = json_decode($e->getResponse()->getBody(true)->getContents()); return $response; } elseif ($e->getResponse()->getStatusCode() == '401') { $response = json_decode($e->getResponse()->getBody(true)->getContents()); return $response; } elseif ($e->getResponse()->getStatusCode() == '403') { $response = json_decode($e->getResponse()->getBody(true)->getContents()); return $e->getResponse()->getStatusCode(); } } public function get_servers() { try { $url = self::API_URL . "/server"; $option = array('exceptions' => false); $header = array('Authorization'=>'Bearer ' . $this->accessToken); $response = $this->client->get($url, array('headers' => $header)); $result = json_decode($response->getBody()->getContents()); return $result; } catch (RequestException $e) { $response = $this->StatusCodeHandling($e); return $response; } } public function get_applications() { try { $url = self::API_URL . "/apps"; $header = array('Authorization'=>'Bearer ' . $this->accessToken); $response = $this->client->get($url, array('headers' => $header)); return json_decode($response->getBody()->getContents()); } catch (RequestException $e) { $response = $this->StatusCodeHandling($e); return $response; } } public function AddApplication($serverid,$application,$app_version,$app_name) { try { $url = self::API_URL . "/app"; $data = ['server_id' => $serverid,'application' => $application,'app_version' => $app_version,'app_label' => $app_name]; $header = array('Authorization'=>'Bearer ' . $this->accessToken); $response = $this->client->post($url, array('query' => $data,'headers' => $header)); return json_decode($response->getBody()->getContents()); } catch (RequestException $e) { $response = $this->StatusCodeHandling($e); return $response; } } public function DeleteApplication($serverid,$applicationid) { try { $url = self::API_URL . "/app/$applicationid"; $data = ['server_id' => $serverid]; $header = array('Authorization'=>'Bearer ' . $this->accessToken); $response = $this->client->delete($url, array('query' => $data,'headers' => $header)); return json_decode($response->getBody()->getContents()); } catch (RequestException $e) { $response = $this->StatusCodeHandling($e); return $response; } } } ?>
The next step is the creation of an application that uses the Cloudways API.
Step 3: Create an Application Using the Cloudways API
First, I will create a new file index.php for the application. The code for the index.php is as follows:
<?php include 'cloudwaysapi.php'; $api_key = 'YOUR API KEY'; $email = 'YOUR EMAIL'; $cw_api = new CloudwaysAPI($email,$api_key); $servers = $cw_api->get_servers(); $apps = $cw_api->get_applications(); $success = null; if(!empty($_POST)){ $server = $_POST['server']; $appname = $_POST['application']; $ver = $_POST['appver']; $label = $_POST['applabel']; $result = $cw_api->AddApplication($server,$appname,$ver,$label); $error = null; if(isset($result->operation_id)){ $success["message"] = "Appication is being added"; } else { foreach ($result as $key => $value) { foreach ($value as $keys => $values) { if($values->message){ $success["$key"] = $values->message; } } } $success["message"] = "Kindly correct the above errors"; } } ?> <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8"> <meta name="viewport" content="width=device-width, initial-scale=1"> <title>Application</title> <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css" integrity="sha384-BVYiiSIFeK1dGmJRAkycuHAHRg32OmUcww7on3RYdg4Va+PmSTsz/K68vbdEjh4u" crossorigin="anonymous"> <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap-theme.min.css" integrity="sha384-rHyoN1iRsVXV4nD0JutlnGaslCJuC7uwjduW9SVrLvRYooPp2bWYgmgJQIXwl/Sp" crossorigin="anonymous"> <script src="https://code.jquery.com/jquery-3.1.1.min.js"></script> <script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js" integrity="sha384-Tc5IQib027qvyjSMfHjOMaLkfuWVxZxUPnCJA7l2mCWNIpG9mGCD8wGNIcPD7Txa" crossorigin="anonymous"></script> </head> <body> <div class="container-fluid"> <div class="row"> <div class="col-md-10"> <form class="form-horizontal" method="POST" action="<?php echo htmlspecialchars($_SERVER[" PHP_SELF "]); ?>"> <fieldset> <!-- Form Name --> <legend>Add Application</legend> <!-- Text input--> <div class="form-group"> <label class="col-md-4 control-label" for="label">App Name</label> <div class="col-md-4"> <input id="label" name="applabel" type="text" placeholder="" class="form-control input-md"> <span class="bg-danger"><?php if(isset($success["app_label"])){ echo $success["app_label"]; } ?> </span> </div> </div> <!-- Select Basic --> <div class="form-group"> <label class="col-md-4 control-label" for="server">Server</label> <div class="col-md-4"> <select id="server" name="server" class="form-control"> <?php foreach($servers->servers as $server) { echo " <option value='".$server->id."'>".$server->label."</option>"; } ?> </select> </div> </div> <!-- Select Basic --> <div class="form-group"> <label class="col-md-4 control-label" for="application">Application</label> <div class="col-md-4"> <select id="application" name="application" class="form-control"> <option value=''>Select Your Application</option> <?php $dup=n ull; foreach($apps->apps as $app) { foreach ($app->versions as $ver) { if( $dup != $app->label){ $dup = $app->label; echo " <option value='".$ver->application."'>". $app->label."</option>"; } } } ?> </select> <span class="bg-danger"><?php if(isset($success["application"])){ echo $success["application"]; } ?> </span> </div> </div> <!-- Select Basic --> <div class="form-group"> <label class="col-md-4 control-label" for="appver">Application Version</label> <div class="col-md-4"> <select id="appver" name="appver" class="form-control"> </select> <span class="bg-danger"><?php if(isset($success["app_version"])){ echo $success["app_version"]; } ?> </span> </div> </div> <!-- Button --> <div class="form-group"> <label class="col-md-4 control-label" for="add"></label> <div class="col-md-4"> <button id="add" class="btn btn-primary">Add Application</button> <span class="bg-success"><?php echo $success["message"] ?> </span> </div> </div> </fieldset> </form> </div> </div> </div> <script type="text/javascript"> $("#application").change(function () { app = $("#application option:selected").text(); console.log(app); switch (app) { <? php foreach($apps - > apps as $app) { ?> case <?php echo "\"".$app - > label. "\""; ?> : $('#appver') .find('option') .remove() .end(); <? php $i = null; foreach($app - > versions as $ver) { $i .= "<option value='".$ver - > app_version. "'>".ucfirst($ver - > application). "(".$ver - > app_version. ")</option>"; } ?> apps = "<?php echo $i; ?>"; $('#appver').html(apps); break; <? php } ?> default: $('#appver') .find('option') .remove() .end(); break; } }); </script> </body> </html>
In this file, I created an object of the API class and then called the functions to get the server and the applications. Next, I created a form and several javascript functions to bind the details coming from the functions.
When executed, the form looks like the following:
Try adding a new application using the form:
Once the form has been filled, a notification about the addition of the application will appear:
Next is the code for deleting an application.
Step 4: Delete an Application Using Cloudways API
Create a new file and name it delete.php and paste the following code in it.
<?php include 'cloudwaysapi.php'; $api_key = 'YOUR API KEY'; $email = 'YOUR EMAIL'; $cw_api = new CloudwaysAPI($email,$api_key); $servers = $cw_api->get_servers(); $apps = []; $success = null; if(!empty($_POST)){ $server = $_POST['server']; $appname = $_POST['app']; $re = $cw_api->DeleteApplication($server,$appname); if(isset($re->operation_id)){ $success = "Appication is being Deleted"; } else { $success = $re->message; } } ?> <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8"> <meta name="viewport" content="width=device-width, initial-scale=1"> <title>Application</title> <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap.min.css" integrity="sha384-BVYiiSIFeK1dGmJRAkycuHAHRg32OmUcww7on3RYdg4Va+PmSTsz/K68vbdEjh4u" crossorigin="anonymous"> <link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/css/bootstrap-theme.min.css" integrity="sha384-rHyoN1iRsVXV4nD0JutlnGaslCJuC7uwjduW9SVrLvRYooPp2bWYgmgJQIXwl/Sp" crossorigin="anonymous"> <script src="https://code.jquery.com/jquery-3.1.1.min.js"></script> <script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.7/js/bootstrap.min.js" integrity="sha384-Tc5IQib027qvyjSMfHjOMaLkfuWVxZxUPnCJA7l2mCWNIpG9mGCD8wGNIcPD7Txa" crossorigin="anonymous"></script> </head> <body> <div class="container-fluid"> <div class="row"> <div class="col-md-10"> <form class="form-horizontal" method="post" action="<?php echo htmlspecialchars($_SERVER[" PHP_SELF "]); ?>"> <fieldset> <!-- Form Name --> <legend>Delete Application</legend> <!-- Select Basic --> <div class="form-group"> <label class="col-md-4 control-label" for="server">Server</label> <div class="col-md-4"> <select id="server" name="server" class="form-control"> <option value="">Select Your Server</option> <?php foreach($servers->servers as $server) { echo " <option value='".$server->id."'>".$server->label."</option>"; } ?> </select> </div> </div> <!-- Select Basic --> <div class="form-group"> <label class="col-md-4 control-label" for="application">Application</label> <div class="col-md-4"> <select id="app" name="app" class="form-control disable"> </select> </div> </div> <!-- Button --> <div class="form-group"> <label class="col-md-4 control-label" for=""></label> <div class="col-md-4"> <button id="" name="" class="btn btn-danger">Delete</button> <span class="bg-success"><?php echo $success ?> </span> </div> </div> </fieldset> </form> </div> </div> </div> <script type="text/javascript"> $("#server").change(function () { val = $(this).val(); switch (val) { <? php foreach($servers - > servers as $server) { ?> case <?php echo "\"".$server - > id. "\""; ?> : $('#app') .find('option') .remove() .end(); <? php $i = "<option value=''>Select Your Application</option>"; foreach($server - > apps as $app) { $i .= "<option value='".$app - > id. "'>".$app - > label. " (".$app - > application. ")</option>"; $i++; } ?> apps = "<?php echo $i;?>"; $('#app').html(apps); break; <? php } ?> default: $('#app') .find('option') .remove() .end(); break; } }); </script> </body> </html>
In this code, I first fetched the servers and the applications and then bind the information to the form and the javascript functions in order to make the form more user friendly. When executed, the code will Let’s will generate the following form:
Select the server and the created application in form. Click Delete.
The result is a successful response!.
Conclusion:
In this tutorial, I discussed how you could add and delete servers and applications using the Cloudways API. I created a class to connect to the API and get the latest information. Next, came the functions to add and delete application from the server.
If you have a question about the code or would like to add to the conversation, please leave a comment below.
Shahzeb Ahmed
Shahzeb is a Digital Marketer with a Software Engineering background, works as a Community Manager — PHP Community at Cloudways. He is growth ambitious and aims to learn & share information about PHP & Laravel Development through practice and experimentation. He loves to travel and explore new ideas whenever he finds time. Get in touch with him at [email protected]