]> git.ipfire.org Git - thirdparty/bacula.git/commitdiff
baculum: Add object size statistics endpoint
authorMarcin Haba <marcin.haba@bacula.pl>
Thu, 11 Aug 2022 13:04:11 +0000 (15:04 +0200)
committerMarcin Haba <marcin.haba@bacula.pl>
Thu, 17 Nov 2022 09:05:10 +0000 (10:05 +0100)
gui/baculum/protected/API/Modules/ObjectManager.php
gui/baculum/protected/API/Pages/API/ObjectStatsCategorySum.php
gui/baculum/protected/API/Pages/API/ObjectStatsSizeSum.php [new file with mode: 0644]
gui/baculum/protected/API/Pages/API/endpoints.xml
gui/baculum/protected/API/openapi_baculum.json

index 8f49c8a3fbb1858387d07c614a266fd22c9553bd..637ed4dc3cf4f7027369cffccc47a33d217b1069 100644 (file)
@@ -71,13 +71,13 @@ LEFT JOIN Job USING (JobId) '
        /**
         * Get number object per object category.
         *
-        * @param string $objecttype object type (usually plugin short name such as 'm365' or 'mysql')
+        * @param string $objecttype object type (usually short name such as 'm365' or 'MySQL')
         * @param string $objectsource object source
         * @param string $datestart start date
         * @param string $dateend end date
         * @return array summary in form [objectcategory => '', objecttype => '', objectsource => '', count => 0, last_job_time => '']
         */
-       public function getObjectPerCategorySum($objecttype = null, $objectsource = null, $datestart = null, $dateend = null) {
+       public function getObjectCategorySum($objecttype = null, $objectsource = null, $datestart = null, $dateend = null) {
                $otype = '';
                if (!is_null($objecttype)) {
                        $otype = ' AND oobj.ObjectType=:objecttype ';
@@ -112,7 +112,67 @@ LEFT JOIN Job USING (JobId) '
                                ' . $otype . $osource . '
                        GROUP BY oobj.ObjectCategory, oobj.ObjectType, oobj.ObjectSource';
 
-               $connection = JobRecord::finder()->getDbConnection();
+               $connection = ObjectRecord::finder()->getDbConnection();
+               $connection->setActive(true);
+               $pdo = $connection->getPdoInstance();
+               $sth = $pdo->prepare($sql);
+               if (!is_null($objecttype)) {
+                       $sth->bindParam(':objecttype', $objecttype, \PDO::PARAM_STR, 100);
+               }
+               if (!is_null($objectsource)) {
+                       $sth->bindParam(':objectsource', $objectsource, \PDO::PARAM_STR, 400);
+               }
+               $sth->bindParam(':datestart', $datestart, \PDO::PARAM_STR, 19);
+               $sth->bindParam(':dateend', $dateend, \PDO::PARAM_STR, 19);
+               $sth->execute();
+               return $sth->fetchAll(\PDO::FETCH_ASSOC);
+       }
+
+       /**
+        * Get object size statistics.
+        *
+        * @param string $objecttype object type (usually short name such as 'm365' or 'MySQL')
+        * @param string $objectsource object source
+        * @param string $datestart start date
+        * @param string $dateend end date
+        * @return array summary in form [sum => 0, month => '']
+        */
+       public function getObjectSizeSum($objecttype = null, $objectsource = null, $datestart = null, $dateend = null) {
+               $otype = '';
+               if (!is_null($objecttype)) {
+                       $otype = ' AND Object.ObjectType=:objecttype ';
+
+               }
+               $osource = '';
+               if (!is_null($objectsource)) {
+                       $osource = ' AND Object.ObjectSource=:objectsource ';
+               }
+               $dformat = 'Y-m-d H:i:s';
+               if (is_null($datestart)) {
+                       $m_ago = new \DateTime('1 month ago');
+                       $datestart = $m_ago->format($dformat);
+               }
+               if (is_null($dateend)) {
+                       $dateend = date($dformat);
+               }
+               $db_params = $this->getModule('api_config')->getConfig('db');
+               if ($db_params['type'] === Database::PGSQL_TYPE) {
+                       $date_month = ' date_trunc(\'month\', Job.StartTime) ';
+               } elseif ($db_params['type'] === Database::MYSQL_TYPE) {
+                       $date_month = ' DATE_FORMAT(Job.StartTime, \'%Y-%m-01 00:00:00\') ';
+               } elseif ($db_params['type'] === Database::SQLITE_TYPE) {
+                       $date_month = ' strftime(\'%Y-%m-01 00:00:00\', Job.StartTime) ';
+               }
+               $sql = 'SELECT SUM(Object.ObjectSize) AS sum,
+                       ' . $date_month . '           AS month
+                       FROM Object
+                               LEFT JOIN Job USING (JobId)
+                       WHERE
+                               Job.StartTime BETWEEN :datestart AND :dateend
+                               ' . $otype . $osource . '
+                       GROUP BY month
+                       ORDER BY month ASC';
+               $connection = ObjectRecord::finder()->getDbConnection();
                $connection->setActive(true);
                $pdo = $connection->getPdoInstance();
                $sth = $pdo->prepare($sql);
index 8ed0a1f28d9f79213a8eadaf31637767a4b2449e..66aa34fa25801721260dc89280c7d6f3de23e062 100644 (file)
@@ -23,7 +23,7 @@
 use Baculum\Common\Modules\Errors\ObjectError;
 
 /**
- * Objects endpoint.
+ * Object category stats endpoint.
  *
  * @author Marcin Haba <marcin.haba@bacula.pl>
  * @category API
@@ -50,7 +50,7 @@ class ObjectStatsCategorySum extends BaculumAPIServer {
                        $dateend = $this->Request['dateend'];
                }
 
-               $objects = $this->getModule('object')->getObjectPerCategorySum(
+               $objects = $this->getModule('object')->getObjectCategorySum(
                        $objecttype,
                        $objectsource,
                        $datestart,
diff --git a/gui/baculum/protected/API/Pages/API/ObjectStatsSizeSum.php b/gui/baculum/protected/API/Pages/API/ObjectStatsSizeSum.php
new file mode 100644 (file)
index 0000000..677cf39
--- /dev/null
@@ -0,0 +1,62 @@
+<?php
+/*
+ * Bacula(R) - The Network Backup Solution
+ * Baculum   - Bacula web interface
+ *
+ * Copyright (C) 2013-2022 Kern Sibbald
+ *
+ * The main author of Baculum is Marcin Haba.
+ * The original author of Bacula is Kern Sibbald, with contributions
+ * from many others, a complete list can be found in the file AUTHORS.
+ *
+ * You may use this file and others of this release according to the
+ * license defined in the LICENSE file, which includes the Affero General
+ * Public License, v3.0 ("AGPLv3") and some additional permissions and
+ * terms pursuant to its AGPLv3 Section 7.
+ *
+ * This notice must be preserved when any source code is
+ * conveyed and/or propagated.
+ *
+ * Bacula(R) is a registered trademark of Kern Sibbald.
+ */
+
+use Baculum\Common\Modules\Errors\ObjectError;
+
+/**
+ * Object size stats endpoint.
+ *
+ * @author Marcin Haba <marcin.haba@bacula.pl>
+ * @category API
+ * @package Baculum API
+ */
+class ObjectStatsSizeSum extends BaculumAPIServer {
+
+       public function get() {
+               $misc = $this->getModule('misc');
+               $objecttype = null;
+               if ($this->Request->contains('objecttype') && $misc->isValidName($this->Request['objecttype'])) {
+                       $objecttype = $this->Request['objecttype'];
+               }
+               $objectsource = null;
+               if ($this->Request->contains('objectsource') && $misc->isValidName($this->Request['objectsource'])) {
+                       $objectsource = $this->Request['objectsource'];
+               }
+               $datestart = null;
+               if ($this->Request->contains('datestart') && $misc->isValidBDateAndTime($this->Request['datestart'])) {
+                       $datestart = $this->Request['datestart'];
+               }
+               $dateend = null;
+               if ($this->Request->contains('dateend') && $misc->isValidBDateAndTime($this->Request['dateend'])) {
+                       $dateend = $this->Request['dateend'];
+               }
+
+               $objects = $this->getModule('object')->getObjectSizeSum(
+                       $objecttype,
+                       $objectsource,
+                       $datestart,
+                       $dateend
+               );
+               $this->output = $objects;
+               $this->error = ObjectError::ERROR_NO_ERRORS;
+       }
+}
index 2de38dd546bd9b6e6265a10ed17c33e8c0ea7f26..28d98cf844d40a640288f7cc21c30d83d71298ac 100644 (file)
@@ -91,6 +91,7 @@
        <url ServiceParameter="Objects" pattern="api/v2/objects/" />
        <url ServiceParameter="ObjectClass" pattern="api/v2/objects/{id}/" parameters.id="\d+" />
        <url ServiceParameter="ObjectStatsCategorySum" pattern="api/v2/objects/stats/category-sum/" />
+       <url ServiceParameter="ObjectStatsSizeSum" pattern="api/v2/objects/stats/size-sum/" />
        <!-- @TODO: Separate this endpoint outside 'joblog' -->
        <url ServiceParameter="Messages" pattern="api/v2/joblog/messages" />
        <!-- fileset endpoints -->
index 2ab87dd03e93968b95de49e5ad44755a2f72e3fa..2ec19573648efbc1c59f818a1a955a9662179c39 100644 (file)
                                ]
                        }
                },
-               "/api/v2/objects/stats/category-sum/": {
+               "/api/v2/objects/stats/category-sum": {
                        "get": {
                                "tags": ["objects"],
                                "summary": "Get object stats per category",
                                ]
                        }
                },
+               "/api/v2/objects/stats/size-sum": {
+                       "get": {
+                               "tags": ["objects"],
+                               "summary": "Get object size stats",
+                               "description": "Get object size statistics",
+                               "responses": {
+                                       "200": {
+                                               "description": "Object size statistics",
+                                               "content": {
+                                                       "application/json": {
+                                                               "schema": {
+                                                                       "type": "object",
+                                                                       "properties": {
+                                                                               "output": {
+                                                                                       "type": "array",
+                                                                                       "items": {
+                                                                                               "type": "object",
+                                                                                               "properties": {
+                                                                                                       "sum": {
+                                                                                                               "type": "string",
+                                                                                                               "description": "Object size sum"
+                                                                                                       },
+                                                                                                       "month": {
+                                                                                                               "type": "string",
+                                                                                                               "description": "Month date"
+                                                                                                       }
+                                                                                               }
+                                                                                       }
+                                                                               },
+                                                                               "error": {
+                                                                                       "type": "integer",
+                                                                                       "description": "Error code",
+                                                                                       "enum": [0, 1, 2, 3, 6, 7, 1000]
+                                                                               }
+                                                                       }
+                                                               }
+                                                       }
+                                               }
+                                       }
+                               },
+                               "parameters": [
+                                       {
+                                               "name": "objecttype",
+                                               "in": "query",
+                                               "required": false,
+                                               "description": "Object type, ex. 'm365' or 'PostgreSQL'",
+                                               "schema": {
+                                                       "type": "string"
+                                               }
+                                       },
+                                       {
+                                               "name": "objectsource",
+                                               "in": "query",
+                                               "required": false,
+                                               "description": "Object data source",
+                                               "schema": {
+                                                       "type": "string"
+                                               }
+                                       },
+                                       {
+                                               "name": "datestart",
+                                               "in": "query",
+                                               "required": false,
+                                               "description": "Start date for job time range. If not given, default is used 1 month ago date.",
+                                               "schema": {
+                                                       "type": "string"
+                                               }
+                                       },
+                                       {
+                                               "name": "dateend",
+                                               "in": "query",
+                                               "required": false,
+                                               "description": "End date for job time range. If not given, default is used current date.",
+                                               "schema": {
+                                                       "type": "string"
+                                               }
+                                       }
+                               ]
+                       }
+               },
                "/api/v2/plugins/m365/{clientid}/users": {
                        "get": {
                                "tags": ["plugins"],