-
Notifications
You must be signed in to change notification settings - Fork 1
Getting event reports
This is a guide to explain how to get an event report through iland's API with PHP and then create an HTML table using the information from the report.
To follow along with this example run the following command:
git clone https://github.com/ilanddev/php-examples.git
And then cd
into the get-event-report
and follow along with PHP file.
Before we get an event report we must an organization's UUID. The org's UUID is what we use to generate and get event reports.
To find an org's uuid we will get the inventory for the user and lazily grab the first organization.
To get a user's inventory we use the GET endpoint /users/{username}/inventory
. We get the inventory with the following call:
doRequest(sprintf('%s/users/%s/inventory', BASE_API, $username))
The doRequest
function takes two variables, first a required URI path and secondly options for curl which is an optional parameter.
Looking at the documentation here we see that the user inventory endpoint returns an array called 'inventory'. This shows all of the resources the user has access to.
Within the inventory array we see that there is another array called entities
, within that array is what we are looking for, an organization.
We lazily get the first company in the returned user inventory array and get the first org within that company with this code:
$orgs = doRequest(sprintf('%s/users/%s/inventory', BASE_API, $username))
['inventory']['0']['entities']['IAAS_ORGANIZATION'];
return $orgs['0'];
We are getting the whole organization array and not just the UUID here because we are also interested in the name of the organization when creating the HTML table.
Here is how we get the org_uuid
and the org_name
with our function:
$org = getOrgFromUserInventory(USERNAME);
$org_uuid = $org['uuid'];
$org_name = $org['name'];
Now that we have an org's uuid we can get the latest report. In these examples I will be getting a vulnerability
report but you can all the types of reports you want here in the documentation.
From the documentation we can see that the endpoint we need to get a vulnerability report is /orgs/{orgUuid}/vulnerability-reports
and that it takes an org uuid as a path parameter. To get the latest report it has the query param boolean option called latest
.
So using our doRequest
function we can write the following to get the vulnerability report:
return doRequest(sprintf("%s/orgs/%s/%s-reports?latest=true", BASE_API, $org_uuid, $type))['data']['0']['uuid'];
This code is from the function getLatestEventReportUuid
which takes a org_uuid
and an event type called type
as parameters.
Now unlike the previous example we aren't returning a whole array but just the string of the report uuid we want.
To do this we look at the documentation and see that the API returns a JSON array called data
in which lies the report uuid called uuid
we want.
Let's say that you don't want the latest report but you want a custom report based on the certain range of days. Looking at the API documentation we can see that some of the reports generated take query parameters for start and end dates. For this example we will generate a antimalware report.
We can generate a antimalware report based on the specific dates that we want with the following POST endpoint, /orgs/{orgUuid}/actions/generate-antimalware-report
.
Based on the documentation here, we can see there are two query parameters we can pass. A start
time and an end
time.
Making a call with the API using these two parameters looks like the following:
return doRequest(sprintf("%s/orgs/%s/actions/generate-%s-report?start=%s&end=%s",
BASE_API, $org_uuid, $type, $start, $end), $options)['uuid'];
Getting start and end times are as simple as calling PHP's time
library, though note that you must convert the time to epoch milliseconds. This is easily done by multiplying by a 1000. Here's how to get the current time and three months ago.
$current_date = time();
$three_months_ago = strtotime(date("Y-m-d H:i:s", $current_date) . " -3 month");
Notice how we are passing a variable called $options
in this request. Why? Well because since this is a POST request we require different curl
options for making the request.
The following code is what we set for the curl options:
$options = array(CURLOPT_FAILONERROR => true,
CURLOPT_RETURNTRANSFER => true,
CURLOPT_POST => 1,
CURLOPT_HTTPHEADER => array(
'Accept: application/vnd.ilandcloud.api.v1.0+json',
'Authorization: Bearer ' . getAccessToken(),
'Content-Type: application/json'
));
Here we set the CURLOPT_POST
to 1 and also note that we set the Content-Type
to application/json
. If you look at the function doRequest
by default the parameters options
is set to NULL so if you want to override it you must pass your own array of curl options.
From the documentation on generating antimalware events we can see that we back JSON that has a uuid
. Now what is that object? Well it is a Task object that we can use to track the progress of the report generation.
To get a task we will use the GET endpoint /tasks/{taskUuid}
but why do we need a task if we already got one back from the generate antimalware report endpoint? Well we need to get a task because the one we got back isn't synced so if we were to try and get the report before the generate task was synced we'd get a 404.
The following code is how we wait for a task to sync given it's uuid:
$task = doRequest(sprintf('%s/tasks/%s', BASE_API, $task_uuid));
while ($task['synced'] != 'true') {
// wait 5 seconds before checking if the task has synced.
sleep(5);
$task = doRequest(sprintf('%s/tasks/%s', BASE_API, $task_uuid));
}
return $task;
We wait 5 seconds before hitting the API again and checking whether or not the task has synced yet. If the task is synced then we return the task.
Within the returned synced task is the report_uuid
in the array called other_attributes
labeled file_uuid
.
Now that we have a vulnerability report's uuid and an antimalware report's uuid we can generate an HTML table using their report JSON content.
To get the report JSON content of a file we use this GET endpoint /orgs/{orgUuid}/reports/{reportUuid}
using the following code.
function getReportJson($org_uuid, $report_uuid)
{
return doRequest(sprintf("%s/orgs/%s/reports/%s", BASE_API, $org_uuid, $report_uuid));
}
With this function we get back a JSON array called json_content
that has the necessary information to create an HTML table.
All of the reports return different json_content
arrays that will have different information in them so you will have to try and test to work with whichever type of report that you want.
For a vulnerability report there is an array called vulns_by_host
that we want to get make a an interesting table. Here is the following code I used to make a vulnerability HTML table:
function createVulnerabilityByHostTable($org_uuid, $org_name, $report_uuid)
{
echo '<h1>Vulnerability By Hosts for Organization: ' . $org_name . '</h1>';
$vuln_json = json_decode(getReportJson($org_uuid, $report_uuid)['json_content'], true);
foreach ($vuln_json['vulns_by_host'] as $value) {
echo createHtmlTable($value);
}
}
The following code created the following table when run:
If you look in the get-event-report.php
example you can see the function createHtmlTable
which takes an array as a parameter and makes a simple HTML out of the data.
For antimalware report there is an array in the json_content
called anti_malware_event_map
which has the relevant data to create a basic HTML table.
Here is the following code I used to create the antimalware event HTML table:
$event_json = json_decode(getReportJson($org_uuid, $report_uuid)['json_content'], true);
$antimalware_events = $event_json['anti_malware_event_map'][0][1];
if(count($antimalware_events) > 0) {
echo '<h1>Antimalware Events for Organization: '. $org_name .'</h1>';
echo createHtmlTable($antimalware_events);
}
Note that I check to make sure that the array has data before trying to make an HTML out of it. Since sometimes there aren't antimalware events you would errors trying to create a HTML table out of an empty array.
Below is the HTML table I created with the code: