diff --git a/controllers/BaseApiController.php b/controllers/BaseApiController.php index 215d184b..9d023361 100644 --- a/controllers/BaseApiController.php +++ b/controllers/BaseApiController.php @@ -18,10 +18,14 @@ class BaseApiController extends BaseController return json_encode($data); } - protected function VoidApiActionResponse($response, $success = true, $status = 200, $errorMessage = '') + protected function EmptyApiResponse($response, $status = 204) + { + return $response->withStatus($status); + } + + protected function GenericErrorResponse($response, $errorMessage, $status = 400) { return $response->withStatus($status)->withJson(array( - 'success' => $success, 'error_message' => $errorMessage )); } diff --git a/controllers/BatteriesApiController.php b/controllers/BatteriesApiController.php index 2e311dfc..0029f04e 100644 --- a/controllers/BatteriesApiController.php +++ b/controllers/BatteriesApiController.php @@ -16,20 +16,22 @@ class BatteriesApiController extends BaseApiController public function TrackChargeCycle(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args) { - $trackedTime = date('Y-m-d H:i:s'); - if (isset($request->getQueryParams()['tracked_time']) && !empty($request->getQueryParams()['tracked_time']) && IsIsoDateTime($request->getQueryParams()['tracked_time'])) - { - $trackedTime = $request->getQueryParams()['tracked_time']; - } + $requestBody = $request->getParsedBody(); try { + $trackedTime = date('Y-m-d H:i:s'); + if (array_key_exists('tracked_time', $requestBody) && IsIsoDateTime($requestBody['tracked_time'])) + { + $trackedTime = $requestBody['tracked_time']; + } + $chargeCycleId = $this->BatteriesService->TrackChargeCycle($args['batteryId'], $trackedTime); return $this->ApiResponse(array('charge_cycle_id' => $chargeCycleId)); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -41,7 +43,7 @@ class BatteriesApiController extends BaseApiController } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -55,11 +57,11 @@ class BatteriesApiController extends BaseApiController try { $this->ApiResponse($this->BatteriesService->UndoChargeCycle($args['chargeCycleId'])); - return $this->ApiResponse(array('success' => true)); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } } diff --git a/controllers/ChoresApiController.php b/controllers/ChoresApiController.php index 7a4d3939..16fd58b1 100644 --- a/controllers/ChoresApiController.php +++ b/controllers/ChoresApiController.php @@ -16,26 +16,28 @@ class ChoresApiController extends BaseApiController public function TrackChoreExecution(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args) { - $trackedTime = date('Y-m-d H:i:s'); - if (isset($request->getQueryParams()['tracked_time']) && !empty($request->getQueryParams()['tracked_time']) && IsIsoDateTime($request->getQueryParams()['tracked_time'])) - { - $trackedTime = $request->getQueryParams()['tracked_time']; - } - - $doneBy = GROCY_USER_ID; - if (isset($request->getQueryParams()['done_by']) && !empty($request->getQueryParams()['done_by'])) - { - $doneBy = $request->getQueryParams()['done_by']; - } + $requestBody = $request->getParsedBody(); try { + $trackedTime = date('Y-m-d H:i:s'); + if (array_key_exists('tracked_time', $requestBody) && IsIsoDateTime($requestBody['tracked_time'])) + { + $trackedTime = $requestBody['tracked_time']; + } + + $doneBy = GROCY_USER_ID; + if (array_key_exists('done_by', $requestBody) && !empty($requestBody['done_by'])) + { + $doneBy = $requestBody['done_by']; + } + $choreExecutionId = $this->ChoresService->TrackChore($args['choreId'], $trackedTime, $doneBy); return $this->ApiResponse(array('chore_execution_id' => $choreExecutionId)); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -47,7 +49,7 @@ class ChoresApiController extends BaseApiController } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -61,11 +63,11 @@ class ChoresApiController extends BaseApiController try { $this->ApiResponse($this->ChoresService->UndoChoreExecution($args['executionId'])); - return $this->ApiResponse(array('success' => true)); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } } diff --git a/controllers/FilesApiController.php b/controllers/FilesApiController.php index 4bef5531..bc065631 100644 --- a/controllers/FilesApiController.php +++ b/controllers/FilesApiController.php @@ -30,11 +30,11 @@ class FilesApiController extends BaseApiController $data = $request->getBody()->getContents(); file_put_contents($this->FilesService->GetFilePath($args['group'], $fileName), $data); - return $this->ApiResponse(array('success' => true)); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -61,12 +61,12 @@ class FilesApiController extends BaseApiController } else { - return $this->VoidApiActionResponse($response, false, 404, 'File not found'); + return $this->GenericErrorResponse($response, 'File not found', 404); } } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -89,11 +89,11 @@ class FilesApiController extends BaseApiController unlink($filePath); } - return $this->ApiResponse(array('success' => true)); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } } diff --git a/controllers/GenericEntityApiController.php b/controllers/GenericEntityApiController.php index 1826ed41..1881dcf4 100644 --- a/controllers/GenericEntityApiController.php +++ b/controllers/GenericEntityApiController.php @@ -12,7 +12,7 @@ class GenericEntityApiController extends BaseApiController } else { - return $this->VoidApiActionResponse($response, false, 400, 'Entity does not exist or is not exposed'); + return $this->GenericErrorResponse($response, 'Entity does not exist or is not exposed'); } } @@ -24,7 +24,7 @@ class GenericEntityApiController extends BaseApiController } else { - return $this->VoidApiActionResponse($response, false, 400, 'Entity does not exist or is not exposed'); + return $this->GenericErrorResponse($response, 'Entity does not exist or is not exposed'); } } @@ -44,16 +44,16 @@ class GenericEntityApiController extends BaseApiController $newRow = $this->Database->{$args['entity']}()->createRow($requestBody); $newRow->save(); $success = $newRow->isClean(); - return $this->ApiResponse(array('success' => $success)); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } else { - return $this->VoidApiActionResponse($response, false, 400, 'Entity does not exist or is not exposed'); + return $this->GenericErrorResponse($response, 'Entity does not exist or is not exposed'); } } @@ -73,16 +73,16 @@ class GenericEntityApiController extends BaseApiController $row = $this->Database->{$args['entity']}($args['objectId']); $row->update($requestBody); $success = $row->isClean(); - return $this->ApiResponse(array('success' => $success)); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } else { - return $this->VoidApiActionResponse($response, false, 400, 'Entity does not exist or is not exposed'); + return $this->GenericErrorResponse($response, 'Entity does not exist or is not exposed'); } } @@ -93,11 +93,11 @@ class GenericEntityApiController extends BaseApiController $row = $this->Database->{$args['entity']}($args['objectId']); $row->delete(); $success = $row->isClean(); - return $this->ApiResponse(array('success' => $success)); + return $this->EmptyApiResponse($response); } else { - return $this->VoidApiActionResponse($response, false, 400, 'Entity does not exist or is not exposed'); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } diff --git a/controllers/RecipesApiController.php b/controllers/RecipesApiController.php index 570b2ac9..a9c12635 100644 --- a/controllers/RecipesApiController.php +++ b/controllers/RecipesApiController.php @@ -17,7 +17,7 @@ class RecipesApiController extends BaseApiController public function AddNotFulfilledProductsToShoppingList(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args) { $this->RecipesService->AddNotFulfilledProductsToShoppingList($args['recipeId']); - return $this->VoidApiActionResponse($response); + return $this->EmptyApiResponse($response); } public function ConsumeRecipe(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args) @@ -25,11 +25,11 @@ class RecipesApiController extends BaseApiController try { $this->RecipesService->ConsumeRecipe($args['recipeId']); - return $this->VoidApiActionResponse($response); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } } diff --git a/controllers/StockApiController.php b/controllers/StockApiController.php index 07b91151..e2975ca0 100644 --- a/controllers/StockApiController.php +++ b/controllers/StockApiController.php @@ -22,7 +22,7 @@ class StockApiController extends BaseApiController } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -34,107 +34,155 @@ class StockApiController extends BaseApiController } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } public function AddProduct(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args) { - $bestBeforeDate = date('Y-m-d'); - if (isset($request->getQueryParams()['bestbeforedate']) && !empty($request->getQueryParams()['bestbeforedate']) && IsIsoDate($request->getQueryParams()['bestbeforedate'])) - { - $bestBeforeDate = $request->getQueryParams()['bestbeforedate']; - } - - $price = null; - if (isset($request->getQueryParams()['price']) && !empty($request->getQueryParams()['price']) && is_numeric($request->getQueryParams()['price'])) - { - $price = $request->getQueryParams()['price']; - } - - $transactionType = StockService::TRANSACTION_TYPE_PURCHASE; - if (isset($request->getQueryParams()['transactiontype']) && !empty($request->getQueryParams()['transactiontype'])) - { - $transactionType = $request->getQueryParams()['transactiontype']; - } + $requestBody = $request->getParsedBody(); try { - $bookingId = $this->StockService->AddProduct($args['productId'], $args['amount'], $bestBeforeDate, $transactionType, date('Y-m-d'), $price); + if ($requestBody === null) + { + throw new \Exception('Request body could not be parsed (probably invalid JSON format or missing/wrong Content-Type header)'); + } + + if (!array_key_exists('amount', $requestBody)) + { + throw new \Exception('An amount is required'); + } + + $bestBeforeDate = date('Y-m-d'); + if (array_key_exists('best_before_date', $requestBody) && IsIsoDate($requestBody['best_before_date'])) + { + $bestBeforeDate = $requestBody['best_before_date']; + } + + $price = null; + if (array_key_exists('price', $requestBody) && is_numeric($requestBody['price'])) + { + $price = $requestBody['price']; + } + + $transactionType = StockService::TRANSACTION_TYPE_PURCHASE; + if (array_key_exists('transaction_type', $requestBody) && !empty($requestBody['transactiontype'])) + { + $transactionType = $requestBody['transactiontype']; + } + + $bookingId = $this->StockService->AddProduct($args['productId'], $requestBody['amount'], $bestBeforeDate, $transactionType, date('Y-m-d'), $price); return $this->ApiResponse(array('booking_id' => $bookingId)); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } public function ConsumeProduct(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args) { - $spoiled = false; - if (isset($request->getQueryParams()['spoiled']) && !empty($request->getQueryParams()['spoiled']) && $request->getQueryParams()['spoiled'] == '1') - { - $spoiled = true; - } - - $transactionType = StockService::TRANSACTION_TYPE_CONSUME; - if (isset($request->getQueryParams()['transactiontype']) && !empty($request->getQueryParams()['transactiontype'])) - { - $transactionType = $request->getQueryParams()['transactiontype']; - } - - $specificStockEntryId = "default"; - if (isset($request->getQueryParams()['stock_entry_id']) && !empty($request->getQueryParams()['stock_entry_id'])) - { - $specificStockEntryId = $request->getQueryParams()['stock_entry_id']; - } + $requestBody = $request->getParsedBody(); try { - $bookingId = $this->StockService->ConsumeProduct($args['productId'], $args['amount'], $spoiled, $transactionType, $specificStockEntryId); + if ($requestBody === null) + { + throw new \Exception('Request body could not be parsed (probably invalid JSON format or missing/wrong Content-Type header)'); + } + + if (!array_key_exists('amount', $requestBody)) + { + throw new \Exception('An amount is required'); + } + + $spoiled = false; + if (array_key_exists('spoiled', $requestBody)) + { + $spoiled = $requestBody['spoiled']; + } + + $transactionType = StockService::TRANSACTION_TYPE_CONSUME; + if (array_key_exists('transaction_type', $requestBody) && !empty($requestBody['transactiontype'])) + { + $transactionType = $requestBody['transactiontype']; + } + + $specificStockEntryId = 'default'; + if (array_key_exists('stock_entry_id', $requestBody) && !empty($requestBody['stock_entry_id'])) + { + $specificStockEntryId = $requestBody['stock_entry_id']; + } + + $bookingId = $this->StockService->ConsumeProduct($args['productId'], $requestBody['amount'], $spoiled, $transactionType, $specificStockEntryId); return $this->ApiResponse(array('booking_id' => $bookingId)); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } public function InventoryProduct(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args) { - $bestBeforeDate = date('Y-m-d'); - if (isset($request->getQueryParams()['bestbeforedate']) && !empty($request->getQueryParams()['bestbeforedate']) && IsIsoDate($request->getQueryParams()['bestbeforedate'])) - { - $bestBeforeDate = $request->getQueryParams()['bestbeforedate']; - } + $requestBody = $request->getParsedBody(); try { - $bookingId = $this->StockService->InventoryProduct($args['productId'], $args['newAmount'], $bestBeforeDate); + if ($requestBody === null) + { + throw new \Exception('Request body could not be parsed (probably invalid JSON format or missing/wrong Content-Type header)'); + } + + if (!array_key_exists('new_amount', $requestBody)) + { + throw new \Exception('An new amount is required'); + } + + $bestBeforeDate = date('Y-m-d'); + if (array_key_exists('best_before_date', $requestBody) && IsIsoDate($requestBody['best_before_date'])) + { + $bestBeforeDate = $requestBody['best_before_date']; + } + + $bookingId = $this->StockService->InventoryProduct($args['productId'], $requestBody['new_amount'], $bestBeforeDate); return $this->ApiResponse(array('booking_id' => $bookingId)); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } public function OpenProduct(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args) { - $specificStockEntryId = "default"; - if (isset($request->getQueryParams()['stock_entry_id']) && !empty($request->getQueryParams()['stock_entry_id'])) - { - $specificStockEntryId = $request->getQueryParams()['stock_entry_id']; - } + $requestBody = $request->getParsedBody(); try { - $bookingId = $this->StockService->OpenProduct($args['productId'], $args['amount'], $specificStockEntryId); + if ($requestBody === null) + { + throw new \Exception('Request body could not be parsed (probably invalid JSON format or missing/wrong Content-Type header)'); + } + + if (!array_key_exists('amount', $requestBody)) + { + throw new \Exception('An amount is required'); + } + + $specificStockEntryId = 'default'; + if (array_key_exists('stock_entry_id', $requestBody) && !empty($requestBody['stock_entry_id'])) + { + $specificStockEntryId = $requestBody['stock_entry_id']; + } + + $bookingId = $this->StockService->OpenProduct($args['productId'], $requestBody['amount'], $specificStockEntryId); return $this->ApiResponse(array('booking_id' => $bookingId)); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -164,13 +212,13 @@ class StockApiController extends BaseApiController public function AddMissingProductsToShoppingList(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args) { $this->StockService->AddMissingProductsToShoppingList(); - return $this->VoidApiActionResponse($response); + return $this->EmptyApiResponse($response); } public function ClearShoppingList(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args) { $this->StockService->ClearShoppingList(); - return $this->VoidApiActionResponse($response); + return $this->EmptyApiResponse($response); } public function ExternalBarcodeLookup(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args) @@ -187,7 +235,7 @@ class StockApiController extends BaseApiController } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -196,11 +244,11 @@ class StockApiController extends BaseApiController try { $this->ApiResponse($this->StockService->UndoBooking($args['bookingId'])); - return $this->ApiResponse(array('success' => true)); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } diff --git a/controllers/SystemApiController.php b/controllers/SystemApiController.php index 23664eb3..bb0e55f9 100644 --- a/controllers/SystemApiController.php +++ b/controllers/SystemApiController.php @@ -30,11 +30,11 @@ class SystemApiController extends BaseApiController $requestBody = $request->getParsedBody(); $this->LocalizationService->LogMissingLocalization(GROCY_CULTURE, $requestBody['text']); - return $this->ApiResponse(array('success' => true)); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } } diff --git a/controllers/TasksApiController.php b/controllers/TasksApiController.php index 0c8370af..fa9c8606 100644 --- a/controllers/TasksApiController.php +++ b/controllers/TasksApiController.php @@ -21,20 +21,22 @@ class TasksApiController extends BaseApiController public function MarkTaskAsCompleted(\Slim\Http\Request $request, \Slim\Http\Response $response, array $args) { - $doneTime = date('Y-m-d H:i:s'); - if (isset($request->getQueryParams()['done_time']) && !empty($request->getQueryParams()['done_time']) && IsIsoDateTime($request->getQueryParams()['done_time'])) - { - $doneTime = $request->getQueryParams()['done_time']; - } + $requestBody = $request->getParsedBody(); try { + $doneTime = date('Y-m-d H:i:s'); + if (array_key_exists('done_time', $requestBody) && IsIsoDateTime($requestBody['done_time'])) + { + $doneTime = $requestBody['done_time']; + } + $this->TasksService->MarkTaskAsCompleted($args['taskId'], $doneTime); - return $this->VoidApiActionResponse($response); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } } diff --git a/controllers/UsersApiController.php b/controllers/UsersApiController.php index dc7e5b9d..e4d1cf63 100644 --- a/controllers/UsersApiController.php +++ b/controllers/UsersApiController.php @@ -22,7 +22,7 @@ class UsersApiController extends BaseApiController } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -38,11 +38,11 @@ class UsersApiController extends BaseApiController } $this->UsersService->CreateUser($requestBody['username'], $requestBody['first_name'], $requestBody['last_name'], $requestBody['password']); - return $this->ApiResponse(array('success' => true)); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -51,11 +51,11 @@ class UsersApiController extends BaseApiController try { $this->UsersService->DeleteUser($args['userId']); - return $this->ApiResponse(array('success' => true)); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -66,11 +66,11 @@ class UsersApiController extends BaseApiController try { $this->UsersService->EditUser($args['userId'], $requestBody['username'], $requestBody['first_name'], $requestBody['last_name'], $requestBody['password']); - return $this->ApiResponse(array('success' => true)); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -83,7 +83,7 @@ class UsersApiController extends BaseApiController } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } @@ -94,11 +94,11 @@ class UsersApiController extends BaseApiController $requestBody = $request->getParsedBody(); $value = $this->UsersService->SetUserSetting(GROCY_USER_ID, $args['settingKey'], $requestBody['value']); - return $this->ApiResponse(array('success' => true)); + return $this->EmptyApiResponse($response); } catch (\Exception $ex) { - return $this->VoidApiActionResponse($response, false, 400, $ex->getMessage()); + return $this->GenericErrorResponse($response, $ex->getMessage()); } } } diff --git a/grocy.openapi.json b/grocy.openapi.json index 4c753cd1..8e1fbfd3 100644 --- a/grocy.openapi.json +++ b/grocy.openapi.json @@ -24,7 +24,7 @@ } ], "paths": { - "/system/get-db-changed-time": { + "/system/db-changed-time": { "get": { "description": "Returns the time when the database was last changed", "tags": [ @@ -62,22 +62,15 @@ } }, "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -85,7 +78,7 @@ } } }, - "/get-objects/{entity}": { + "/objects/{entity}": { "get": { "description": "Returns all objects of the given entity", "tags": [ @@ -139,11 +132,76 @@ } }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" + } + } + } + } + } + }, + "post": { + "description": "Adds a single object of the given entity", + "tags": [ + "Generic entity interactions" + ], + "parameters": [ + { + "in": "path", + "name": "entity", + "required": true, + "description": "A valid entity name", + "schema": { + "$ref": "#/components/internalSchemas/ExposedEntity" + } + } + ], + "requestBody": { + "description": "A valid entity object of the entity specified in parameter *entity*", + "required": true, + "content": { + "application/json": { + "schema": { + "oneOf": [ + { + "$ref": "#/components/schemas/Product" + }, + { + "$ref": "#/components/schemas/Chore" + }, + { + "$ref": "#/components/schemas/Battery" + }, + { + "$ref": "#/components/schemas/Location" + }, + { + "$ref": "#/components/schemas/QuantityUnit" + }, + { + "$ref": "#/components/schemas/ShoppingListItem" + }, + { + "$ref": "#/components/schemas/StockEntry" + } + ] + } + } + } + }, + "responses": { + "204": { + "description": "The operation was successful" + }, + "400": { + "description": "The operation was not successful", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -151,7 +209,7 @@ } } }, - "/get-object/{entity}/{objectId}": { + "/objects/{entity}/{objectId}": { "get": { "description": "Returns a single object of the given entity", "tags": [ @@ -212,94 +270,18 @@ } }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } } } - } - }, - "/add-object/{entity}": { - "post": { - "description": "Adds a single object of the given entity", - "tags": [ - "Generic entity interactions" - ], - "parameters": [ - { - "in": "path", - "name": "entity", - "required": true, - "description": "A valid entity name", - "schema": { - "$ref": "#/components/internalSchemas/ExposedEntity" - } - } - ], - "requestBody": { - "description": "A valid entity object of entity specified in parameter *entity*", - "required": true, - "content": { - "application/json": { - "schema": { - "oneOf": [ - { - "$ref": "#/components/schemas/Product" - }, - { - "$ref": "#/components/schemas/Chore" - }, - { - "$ref": "#/components/schemas/Battery" - }, - { - "$ref": "#/components/schemas/Location" - }, - { - "$ref": "#/components/schemas/QuantityUnit" - }, - { - "$ref": "#/components/schemas/ShoppingListItem" - }, - { - "$ref": "#/components/schemas/StockEntry" - } - ] - } - } - } - }, - "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } - }, - "400": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" - } - } - } - } - } - } - }, - "/edit-object/{entity}/{objectId}": { - "post": { + }, + "put": { "description": "Edits the given object of the given entity", "tags": [ "Generic entity interactions" @@ -325,7 +307,7 @@ } ], "requestBody": { - "description": "A valid entity object of entity specified in parameter *entity*", + "description": "A valid entity object of the entity specified in parameter *entity*", "required": true, "content": { "application/json": { @@ -358,31 +340,22 @@ } }, "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } } } - } - }, - "/delete-object/{entity}/{objectId}": { - "get": { + }, + "delete": { "description": "Deletes a single object of the given entity", "tags": [ "Generic entity interactions" @@ -408,22 +381,15 @@ } ], "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -470,11 +436,11 @@ } }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -517,22 +483,15 @@ } }, "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -565,22 +524,15 @@ } ], "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -588,7 +540,7 @@ } } }, - "/users/get": { + "/users": { "get": { "description": "Returns all users", "tags": [ @@ -609,19 +561,17 @@ } }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } } } - } - }, - "/users/create": { + }, "post": { "description": "Creates a new user", "tags": [ @@ -639,22 +589,15 @@ } }, "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -662,8 +605,8 @@ } } }, - "/users/edit/{userId}": { - "post": { + "/users/{userId}": { + "put": { "description": "Edits the given user", "tags": [ "User management" @@ -691,31 +634,22 @@ } }, "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } } } - } - }, - "/users/delete/{userId}": { - "get": { + }, + "delete": { "description": "Deletes the given user", "tags": [ "User management" @@ -732,22 +666,15 @@ } ], "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -757,7 +684,7 @@ }, "/user/settings/{settingKey}": { "get": { - "description": "Gets the given setting of the currently logged on user", + "description": "Gets the given setting of the currently logged in user", "tags": [ "User settings" ], @@ -784,19 +711,19 @@ } }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } } } }, - "post": { - "description": "Sets the given setting of the currently logged on user", + "put": { + "description": "Sets the given setting of the currently logged in user", "tags": [ "User settings" ], @@ -823,22 +750,15 @@ } ], "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" }, "400": { - "description": "A VoidApiActionResponse object", + "description": "The operation was not successful", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -846,413 +766,7 @@ } } }, - "/stock/add-product/{productId}/{amount}": { - "get": { - "description": "Adds the the given amount of the given product to stock", - "tags": [ - "Stock" - ], - "parameters": [ - { - "in": "path", - "name": "productId", - "required": true, - "description": "A valid product id", - "schema": { - "type": "integer" - } - }, - { - "in": "path", - "name": "amount", - "required": true, - "description": "The amount to add", - "schema": { - "type": "integer" - } - }, - { - "in": "query", - "name": "bestbeforedate", - "required": false, - "description": "The best before date of the product to add, when omitted, the current date is used", - "schema": { - "type": "string", - "format": "date" - } - }, - { - "in": "query", - "name": "price", - "required": false, - "description": "The price per purchase quantity unit in configured currency", - "schema": { - "type": "number", - "format": "double" - } - }, - { - "in": "query", - "name": "transactiontype", - "required": false, - "description": "The transaction type for this transaction, when omitted, *purchase* is used", - "schema": { - "$ref": "#/components/internalSchemas/StockTransactionType" - } - } - ], - "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } - }, - "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing product, invalid transaction type)", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" - } - } - } - } - } - } - }, - "/stock/consume-product/{productId}/{amount}": { - "get": { - "description": "Removes the the given amount of the given product from stock", - "tags": [ - "Stock" - ], - "parameters": [ - { - "in": "path", - "name": "productId", - "required": true, - "description": "A valid product id", - "schema": { - "type": "integer" - } - }, - { - "in": "path", - "name": "amount", - "required": false, - "description": "The amount to remove", - "schema": { - "type": "boolean", - "default": false - } - }, - { - "in": "query", - "name": "spoiled", - "required": true, - "description": "True when the given product was spoiled, defaults to false", - "schema": { - "type": "integer" - } - }, - { - "in": "query", - "name": "transactiontype", - "required": false, - "description": "The transaction type for this transaction, when omitted, *consume* is used", - "schema": { - "$ref": "#/components/internalSchemas/StockTransactionType" - } - }, - { - "in": "query", - "name": "stock_entry_id", - "required": false, - "description": "A specific stock entry id to consume, if used, the amount has to be 1", - "schema": { - "type": "string" - } - } - ], - "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } - }, - "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing product, invalid transaction type)", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" - } - } - } - } - } - } - }, - "/stock/open-product/{productId}/{amount}": { - "get": { - "description": "Marks the the given amount of the given product as opened", - "tags": [ - "Stock" - ], - "parameters": [ - { - "in": "path", - "name": "productId", - "required": true, - "description": "A valid product id", - "schema": { - "type": "integer" - } - }, - { - "in": "path", - "name": "amount", - "required": false, - "description": "The amount to remove", - "schema": { - "type": "boolean", - "default": false - } - }, - { - "in": "query", - "name": "stock_entry_id", - "required": false, - "description": "A specific stock entry id to open, if used, the amount has to be 1", - "schema": { - "type": "string" - } - } - ], - "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } - }, - "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing product)", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" - } - } - } - } - } - } - }, - "/stock/inventory-product/{productId}/{newAmount}": { - "get": { - "description": "Inventories the the given product (adds/removes based on the given new current amount)", - "tags": [ - "Stock" - ], - "parameters": [ - { - "in": "path", - "name": "productId", - "required": true, - "description": "A valid product id", - "schema": { - "type": "integer" - } - }, - { - "in": "path", - "name": "newAmount", - "required": true, - "description": "The new current amount for the given product", - "schema": { - "type": "integer" - } - }, - { - "in": "query", - "name": "bestbeforedate", - "required": false, - "description": "The best before date which applies to added products", - "schema": { - "type": "string", - "format": "date" - } - } - ], - "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } - }, - "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing product)", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" - } - } - } - } - } - } - }, - "/stock/get-product-details/{productId}": { - "get": { - "description": "Returns details of the given product", - "tags": [ - "Stock" - ], - "parameters": [ - { - "in": "path", - "name": "productId", - "required": true, - "description": "A valid product id", - "schema": { - "type": "integer" - } - } - ], - "responses": { - "200": { - "description": "A ProductDetailsResponse object", - "content": { - "application/json": { - "schema":{ - "$ref": "#/components/schemas/ProductDetailsResponse" - } - } - } - }, - "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing product)", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" - } - } - } - } - } - } - }, - "/stock/get-product-price-history/{productId}": { - "get": { - "description": "Returns the price history of the given product", - "tags": [ - "Stock" - ], - "parameters": [ - { - "in": "path", - "name": "productId", - "required": true, - "description": "A valid product id", - "schema": { - "type": "integer" - } - } - ], - "responses": { - "200": { - "description": "An array of ProductPriceHistory objects", - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/ProductPriceHistory" - } - } - } - } - }, - "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing product)", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" - } - } - } - } - } - } - }, - "/stock/get-product-stock-entries/{productId}": { - "get": { - "description": "Returns all stock entries of the given product in order of next use (first expiring first, then first in first out)", - "tags": [ - "Stock" - ], - "parameters": [ - { - "in": "path", - "name": "productId", - "required": true, - "description": "A valid product id", - "schema": { - "type": "integer" - } - } - ], - "responses": { - "200": { - "description": "An array of StockEntry objects", - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/StockEntry" - } - } - } - } - }, - "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing product)", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" - } - } - } - } - } - } - }, - "/stock/get-current-stock": { + "/stock": { "get": { "description": "Returns all products which are currently in stock incl. the next expiring date per product", "tags": [ @@ -1275,7 +789,7 @@ } } }, - "/stock/get-current-volatil-stock": { + "/stock/volatile": { "get": { "description": "Returns all products which are expiring soon, are already expired or currently missing", "tags": [ @@ -1310,39 +824,462 @@ } } }, - "/stock/add-missing-products-to-shoppinglist": { + "/stock/products/{productId}": { "get": { + "description": "Returns details of the given product", + "tags": [ + "Stock" + ], + "parameters": [ + { + "in": "path", + "name": "productId", + "required": true, + "description": "A valid product id", + "schema": { + "type": "integer" + } + } + ], + "responses": { + "200": { + "description": "A ProductDetailsResponse object", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/ProductDetailsResponse" + } + } + } + }, + "400": { + "description": "The operation was not successful (possible errors are: Not existing product)", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/GenericErrorResponse" + } + } + } + } + } + } + }, + "/stock/products/{productId}/entries": { + "get": { + "description": "Returns all stock entries of the given product in order of next use (first expiring first, then first in first out)", + "tags": [ + "Stock" + ], + "parameters": [ + { + "in": "path", + "name": "productId", + "required": true, + "description": "A valid product id", + "schema": { + "type": "integer" + } + } + ], + "responses": { + "200": { + "description": "An array of StockEntry objects", + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "$ref": "#/components/schemas/StockEntry" + } + } + } + } + }, + "400": { + "description": "The operation was not successful (possible errors are: Not existing product)", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/GenericErrorResponse" + } + } + } + } + } + } + }, + "/stock/products/{productId}/price-history": { + "get": { + "description": "Returns the price history of the given product", + "tags": [ + "Stock" + ], + "parameters": [ + { + "in": "path", + "name": "productId", + "required": true, + "description": "A valid product id", + "schema": { + "type": "integer" + } + } + ], + "responses": { + "200": { + "description": "An array of ProductPriceHistory objects", + "content": { + "application/json": { + "schema": { + "type": "array", + "items": { + "$ref": "#/components/schemas/ProductPriceHistory" + } + } + } + } + }, + "400": { + "description": "The operation was not successful (possible errors are: Not existing product)", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/GenericErrorResponse" + } + } + } + } + } + } + }, + "/stock/products/{productId}/add": { + "post": { + "description": "Adds the given amount of the given product to stock", + "tags": [ + "Stock" + ], + "parameters": [ + { + "in": "path", + "name": "productId", + "required": true, + "description": "A valid product id", + "schema": { + "type": "integer" + } + } + ], + "requestBody": { + "required": true, + "content": { + "application/json": { + "schema": { + "type": "object", + "properties": { + "amount": { + "type": "integer" + }, + "best_before_date": { + "type": "string", + "format": "date", + "description": "The best before date of the product to add, when omitted, the current date is used" + }, + "transaction_type": { + "$ref": "#/components/internalSchemas/StockTransactionType" + }, + "price": { + "type": "number", + "format": "double", + "description": "The price per purchase quantity unit in configured currency" + } + }, + "example": { + "amount": 1, + "best_before_date": "2019-01-19", + "transaction_type": "purchase", + "price": "1.99" + } + } + } + } + }, + "responses": { + "200": { + "description": "The operation was successful", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/StockBookingResponse" + } + } + } + }, + "400": { + "description": "The operation was not successful (possible errors are: Not existing product, invalid transaction type)", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/GenericErrorResponse" + } + } + } + } + } + } + }, + "/stock/products/{productId}/consume": { + "post": { + "description": "Removes the given amount of the given product from stock", + "tags": [ + "Stock" + ], + "parameters": [ + { + "in": "path", + "name": "productId", + "required": true, + "description": "A valid product id", + "schema": { + "type": "integer" + } + } + ], + "requestBody": { + "required": true, + "content": { + "application/json": { + "schema": { + "type": "object", + "properties": { + "amount": { + "type": "integer", + "description": "The amount to remove" + }, + "transaction_type": { + "$ref": "#/components/internalSchemas/StockTransactionType" + }, + "spoiled": { + "type": "boolean", + "description": "True when the given product was spoiled, defaults to false" + }, + "stock_entry_id": { + "type": "string", + "description": "A specific stock entry id to consume, if used, the amount has to be 1" + } + }, + "example": { + "amount": 1, + "transaction_type": "consume", + "spoiled": false + } + } + } + } + }, + "responses": { + "200": { + "description": "The operation was successful", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/StockBookingResponse" + } + } + } + }, + "400": { + "description": "The operation was not successful (possible errors are: Not existing product, invalid transaction type)", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/GenericErrorResponse" + } + } + } + } + } + } + }, + "/stock/products/{productId}/inventory": { + "post": { + "description": "Inventories the given product (adds/removes based on the given new amount)", + "tags": [ + "Stock" + ], + "parameters": [ + { + "in": "path", + "name": "productId", + "required": true, + "description": "A valid product id", + "schema": { + "type": "integer" + } + } + ], + "requestBody": { + "required": true, + "content": { + "application/json": { + "schema": { + "type": "object", + "properties": { + "new_amount": { + "type": "integer", + "description": "The new current amount for the given product" + }, + "best_before_date": { + "type": "string", + "format": "date", + "description": "The best before date which applies to added products" + } + } + } + } + } + }, + "responses": { + "200": { + "description": "The operation was successful", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/StockBookingResponse" + } + } + } + }, + "400": { + "description": "The operation was not successful (possible errors are: Not existing product)", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/GenericErrorResponse" + } + } + } + } + } + } + }, + "/stock/products/{productId}/open": { + "post": { + "description": "Marks the given amount of the given product as opened", + "tags": [ + "Stock" + ], + "parameters": [ + { + "in": "path", + "name": "productId", + "required": true, + "description": "A valid product id", + "schema": { + "type": "integer" + } + } + ], + "requestBody": { + "required": true, + "content": { + "application/json": { + "schema": { + "type": "object", + "properties": { + "amount": { + "type": "integer", + "description": "The amount to mark as opened" + }, + "stock_entry_id": { + "type": "string", + "description": "A specific stock entry id to open, if used, the amount has to be 1" + } + }, + "example": { + "amount": 1 + } + } + } + } + }, + "responses": { + "200": { + "description": "The operation was successful", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/StockBookingResponse" + } + } + } + }, + "400": { + "description": "The operation was not successful (possible errors are: Not existing product)", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/GenericErrorResponse" + } + } + } + } + } + } + }, + "/stock/shoppinglist/add-missing-products": { + "post": { "description": "Adds currently missing products (below defined min. stock amount) to the shopping list", "tags": [ "Stock" ], "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" } } } }, - "/stock/clear-shopping-list": { - "get": { + "/stock/shoppinglist/clear": { + "post": { "description": "Removes all items from the shopping list", "tags": [ "Stock" ], "responses": { - "200": { - "description": "A VoidApiActionResponse object", + "204": { + "description": "The operation was successful" + } + } + } + }, + "/stock/bookings/{bookingId}/undo": { + "post": { + "description": "Undoes a booking", + "tags": [ + "Stock" + ], + "parameters": [ + { + "in": "path", + "name": "bookingId", + "required": true, + "description": "A valid stock booking id", + "schema": { + "type": "integer" + } + } + ], + "responses": { + "204": { + "description": "The operation was successful" + }, + "400": { + "description": "The operation was not successful (possible errors are: Not existing booking)", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -1350,7 +1287,7 @@ } } }, - "/stock/external-barcode-lookup/{barcode}": { + "/stock/barcodes/external-lookup": { "get": { "description": "Executes an external barcode lookoup via the configured plugin with the given barcode", "tags": [ @@ -1358,7 +1295,7 @@ ], "parameters": [ { - "in": "path", + "in": "query", "name": "barcode", "required": true, "description": "The barcode to lookup up", @@ -1370,7 +1307,7 @@ "in": "query", "name": "add", "required": false, - "description": "When true, the product is added to the database on a successful lookup and the new product id is in included in output", + "description": "When true, the product is added to the database on a successful lookup and the new product id is in included in the response", "schema": { "type": "boolean", "default": false @@ -1389,11 +1326,11 @@ } }, "400": { - "description": "A VoidApiActionResponse object (possible errors are: Plugin error)", + "description": "The operation was not successful (possible errors are: Plugin error)", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -1401,49 +1338,8 @@ } } }, - "/stock/undo-booking/{bookingId}": { - "get": { - "description": "Undoes a booking", - "tags": [ - "Stock" - ], - "parameters": [ - { - "in": "path", - "name": "bookingId", - "required": true, - "description": "A valid stock booking id", - "schema": { - "type": "integer" - } - } - ], - "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } - }, - "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing booking)", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" - } - } - } - } - } - } - }, - "/recipes/add-not-fulfilled-products-to-shopping-list/{recipeId}": { - "get": { + "/recipes/{recipeId}/add-not-fulfilled-products-to-shoppinglist": { + "post": { "description": "Adds all missing products for the given recipe to the shopping list", "tags": [ "Recipes" @@ -1460,21 +1356,14 @@ } ], "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" } } } }, - "/recipes/consume-recipe/{recipeId}": { - "get": { + "/recipes/{recipeId}/consume": { + "post": { "description": "Consumes all products of the given recipe", "tags": [ "Recipes" @@ -1491,71 +1380,28 @@ } ], "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" } } } }, - "/chores/track-chore-execution/{choreId}": { + "/chores": { "get": { - "description": "Tracks an execution of the given chore", + "description": "Returns all chores incl. the next estimated execution time per chore", "tags": [ "Chores" ], - "parameters": [ - { - "in": "path", - "name": "choreId", - "required": true, - "description": "A valid chore id", - "schema": { - "type": "integer" - } - }, - { - "in": "query", - "name": "tracked_time", - "required": false, - "description": "The time of when the chore was executed, when omitted, the current time is used", - "schema": { - "type": "date-time" - } - }, - { - "in": "query", - "name": "done_by", - "required": false, - "description": "A valid user id of who executed this chore, when omitted, the currently authenticated user will be used", - "schema": { - "type": "integer" - } - } - ], "responses": { "200": { - "description": "A VoidApiActionResponse object", + "description": "An array of CurrentChoreResponse objects", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } - }, - "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing chore)", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "type": "array", + "items": { + "$ref": "#/components/schemas/CurrentChoreResponse" + } } } } @@ -1563,7 +1409,7 @@ } } }, - "/chores/get-chore-details/{choreId}": { + "/chores/{choreId}": { "get": { "description": "Returns details of the given chore", "tags": [ @@ -1592,11 +1438,11 @@ } }, "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing chore)", + "description": "The operation was not successful (possible errors are: Not existing chore)", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -1604,31 +1450,75 @@ } } }, - "/chores/get-current": { - "get": { - "description": "Returns all chores incl. the next estimated execution time per chore", + "/chores/{choreId}/execute": { + "post": { + "description": "Tracks an execution of the given chore", "tags": [ "Chores" ], - "responses": { - "200": { - "description": "An array of CurrentChoreResponse objects", - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/CurrentChoreResponse" + "parameters": [ + { + "in": "path", + "name": "choreId", + "required": true, + "description": "A valid chore id", + "schema": { + "type": "integer" + } + } + ], + "requestBody": { + "required": true, + "content": { + "application/json": { + "schema": { + "type": "object", + "properties": { + "tracked_time": { + "type": "string", + "format": "date-time", + "description": "The time of when the chore was executed, when omitted, the current time is used" + }, + "done_by": { + "type": "integer", + "description": "A valid user id of who executed this chore, when omitted, the currently authenticated user will be used" } } } } } + }, + "responses": { + "200": { + "description": "The operation was successful", + "content": { + "application/json": { + "schema": { + "type": "object", + "properties": { + "chore_execution_id": { + "type": "integer" + } + } + } + } + } + }, + "400": { + "description": "The operation was not successful (possible errors are: Not existing chore)", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/GenericErrorResponse" + } + } + } + } } } }, - "/chores/undo-chore-execution/{executionId}": { - "get": { + "/chores/{executionId}/undo": { + "post": { "description": "Undoes a chore execution", "tags": [ "Chores" @@ -1645,22 +1535,15 @@ } ], "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" }, "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing booking)", + "description": "The operation was not successful (possible errors are: Not existing booking)", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -1668,50 +1551,22 @@ } } }, - "/batteries/track-charge-cycle/{batteryId}": { + "/batteries": { "get": { - "description": "Tracks a charge cycle of the given battery", + "description": "Returns all batteries incl. the next estimated charge time per battery", "tags": [ "Batteries" ], - "parameters": [ - { - "in": "path", - "name": "batteryId", - "required": true, - "description": "A valid battery id", - "schema": { - "type": "integer" - } - }, - { - "in": "query", - "name": "tracked_time", - "required": false, - "description": "The time of when the battery was charged, when omitted, the current time is used", - "schema": { - "type": "string", - "format": "date-time" - } - } - ], "responses": { "200": { - "description": "A VoidApiActionResponse object", + "description": "An array of CurrentBatteryResponse objects", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } - }, - "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing battery)", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "type": "array", + "items": { + "$ref": "#/components/schemas/CurrentBatteryResponse" + } } } } @@ -1719,7 +1574,7 @@ } } }, - "/batteries/get-battery-details/{batteryId}": { + "/batteries/{batteryId}": { "get": { "description": "Returns details of the given battery", "tags": [ @@ -1748,11 +1603,11 @@ } }, "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing battery)", + "description": "The operation was not successful (possible errors are: Not existing battery)", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -1760,32 +1615,72 @@ } } }, - "/batteries/get-current": { - "get": { - "description": "Returns all batteries incl. the next estimated charge time per battery", + "/batteries/{batteryId}/charge": { + "post": { + "description": "Tracks a charge cycle of the given battery", "tags": [ "Batteries" ], - "responses": { - "200": { - "description": "An array of CurrentBatteryResponse objects", - "content": { - "application/json": { - "schema": { - "type": "array", - "items": { - "$ref": "#/components/schemas/CurrentBatteryResponse" + "parameters": [ + { + "in": "path", + "name": "batteryId", + "required": true, + "description": "A valid battery id", + "schema": { + "type": "integer" + } + } + ], + "requestBody": { + "required": true, + "content": { + "application/json": { + "schema": { + "type": "object", + "properties": { + "tracked_time": { + "type": "string", + "format": "date-time", + "description": "The time of when the battery was charged, when omitted, the current time is used" } } } } } + }, + "responses": { + "200": { + "description": "The operation was successful", + "content": { + "application/json": { + "schema": { + "type": "object", + "properties": { + "charge_cycle_id": { + "type": "integer" + } + } + } + } + } + }, + "400": { + "description": "The operation was not successful (possible errors are: Not existing battery)", + "content": { + "application/json": { + "schema": { + "$ref": "#/components/schemas/GenericErrorResponse" + } + } + } + } } } }, - "/batteries/undo-charge-cycle/{chargeCycleId}": { - "get": { - "description": "Undoes a chore execution", + "/batteries/{chargeCycleId}/undo": { + "post": { + "description": "Undoes a battery charge cycle", "tags": [ "Batteries" ], @@ -1801,22 +1696,15 @@ } ], "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" - } - } - } + "204": { + "description": "The operation was successful" }, "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing booking)", + "description": "The operation was not successful (possible errors are: Not existing booking)", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -1824,7 +1712,7 @@ } } }, - "/tasks/get-current": { + "/tasks": { "get": { "description": "Returns all tasks which are not done yet", "tags": [ @@ -1847,8 +1735,8 @@ } } }, - "/tasks/mark-task-as-completed/{taskId}": { - "get": { + "/tasks/{taskId}/complete": { + "post": { "description": "Marks the given task as completed", "tags": [ "Tasks" @@ -1862,34 +1750,35 @@ "schema": { "type": "integer" } - }, - { - "in": "query", - "name": "done_time", - "required": false, - "description": "The time of when the task was completed, when omitted, the current time is used", - "schema": { - "type": "date-time" - } } ], - "responses": { - "200": { - "description": "A VoidApiActionResponse object", - "content": { - "application/json": { - "schema": { - "$ref": "#/components/schemas/VoidApiActionResponse" + "requestBody": { + "required": true, + "content": { + "application/json": { + "schema": { + "type": "object", + "properties": { + "done_time": { + "type": "string", + "format": "date-time", + "description": "The time of when the task was completed, when omitted, the current time is used" + } } } } + } + }, + "responses": { + "204": { + "description": "The operation was successful" }, "400": { - "description": "A VoidApiActionResponse object (possible errors are: Not existing task)", + "description": "The operation was not successful (possible errors are: Not existing task)", "content": { "application/json": { "schema": { - "$ref": "#/components/schemas/ErrorExampleVoidApiActionResponse" + "$ref": "#/components/schemas/GenericErrorResponse" } } } @@ -1930,7 +1819,8 @@ "enum": [ "purchase", "consume", - "inventory-correction" + "inventory-correction", + "product-opened" ] } }, @@ -2432,34 +2322,23 @@ } } }, - "ErrorExampleVoidApiActionResponse": { + "GenericErrorResponse": { "type": "object", "properties": { - "success": { - "type": "boolean" - }, "error_message": { "type": "string" } }, "example": { - "success": false, "error_message": "The error message..." } }, - "VoidApiActionResponse": { + "StockBookingResponse": { "type": "object", "properties": { - "success": { - "type": "boolean" - }, - "error_message": { - "type": "string" + "booking_id": { + "type": "integer" } - }, - "example": { - "success": true, - "error_message": "" } }, "CurrentStockResponse": { @@ -2596,14 +2475,6 @@ } } }, - "examples": { - "ErrorVoidApiActionResponseExample": { - "value": { - "success": false, - "error_message": "The error message..." - } - } - }, "securitySchemes": { "ApiKeyAuth": { "type": "apiKey", diff --git a/public/js/grocy.js b/public/js/grocy.js index 8cff1ccd..5fda4828 100644 --- a/public/js/grocy.js +++ b/public/js/grocy.js @@ -125,11 +125,18 @@ Grocy.Api.Get = function(apiFunction, success, error) { if (xhr.readyState === XMLHttpRequest.DONE) { - if (xhr.status === 200) + if (xhr.status === 200 || xhr.status === 204) { if (success) { - success(JSON.parse(xhr.responseText)); + if (xhr.status === 200) + { + success(JSON.parse(xhr.responseText)); + } + else + { + success({ }); + } } } else @@ -155,11 +162,18 @@ Grocy.Api.Post = function(apiFunction, jsonData, success, error) { if (xhr.readyState === XMLHttpRequest.DONE) { - if (xhr.status === 200) + if (xhr.status === 200 || xhr.status === 204) { if (success) { - success(JSON.parse(xhr.responseText)); + if (xhr.status === 200) + { + success(JSON.parse(xhr.responseText)); + } + else + { + success({ }); + } } } else @@ -186,11 +200,18 @@ Grocy.Api.Put = function(apiFunction, jsonData, success, error) { if (xhr.readyState === XMLHttpRequest.DONE) { - if (xhr.status === 200) + if (xhr.status === 200 || xhr.status === 204) { if (success) { - success(JSON.parse(xhr.responseText)); + if (xhr.status === 200) + { + success(JSON.parse(xhr.responseText)); + } + else + { + success({ }); + } } } else @@ -217,11 +238,18 @@ Grocy.Api.Delete = function(apiFunction, jsonData, success, error) { if (xhr.readyState === XMLHttpRequest.DONE) { - if (xhr.status === 200) + if (xhr.status === 200 || xhr.status === 204) { if (success) { - success(JSON.parse(xhr.responseText)); + if (xhr.status === 200) + { + success(JSON.parse(xhr.responseText)); + } + else + { + success({ }); + } } } else @@ -386,7 +414,7 @@ $(".user-setting-control").on("change", function() jsonData = { }; jsonData.value = value; - Grocy.Api.Post('user/settings/' + settingKey, jsonData, + Grocy.Api.Put('user/settings/' + settingKey, jsonData, function(result) { // Nothing to do... diff --git a/public/js/grocy_dbchangedhandling.js b/public/js/grocy_dbchangedhandling.js index 8c86b84a..96eacc80 100644 --- a/public/js/grocy_dbchangedhandling.js +++ b/public/js/grocy_dbchangedhandling.js @@ -1,4 +1,4 @@ -Grocy.Api.Get('system/get-db-changed-time', +Grocy.Api.Get('system/db-changed-time', function(result) { Grocy.DatabaseChangedTime = moment(result.changed_time); @@ -14,7 +14,7 @@ // when there is no unsaved form data and when the user enabled auto reloading setInterval(function() { - Grocy.Api.Get('system/get-db-changed-time', + Grocy.Api.Get('system/db-changed-time', function(result) { var newDbChangedTime = moment(result.changed_time); diff --git a/public/viewjs/batteries.js b/public/viewjs/batteries.js index 68bcf349..020bfe20 100644 --- a/public/viewjs/batteries.js +++ b/public/viewjs/batteries.js @@ -52,7 +52,7 @@ $(document).on('click', '.battery-delete-button', function (e) { if (result === true) { - Grocy.Api.Delete('object/batteries/' + objectId, + Grocy.Api.Delete('objects/batteries/' + objectId, { }, function(result) { window.location.href = U('/batteries'); diff --git a/public/viewjs/batteriesjournal.js b/public/viewjs/batteriesjournal.js index aeacc0b8..c4f825e2 100644 --- a/public/viewjs/batteriesjournal.js +++ b/public/viewjs/batteriesjournal.js @@ -56,7 +56,7 @@ $(document).on('click', '.undo-battery-execution-button', function(e) var element = $(e.currentTarget); var chargeCycleId = $(e.currentTarget).attr('data-charge-cycle-id'); - Grocy.Api.Post('batteries/' + chargeCycleId.toString() + '/undo', + Grocy.Api.Post('batteries/' + chargeCycleId.toString() + '/undo', { }, function(result) { element.closest("tr").addClass("text-muted"); diff --git a/public/viewjs/batteriesoverview.js b/public/viewjs/batteriesoverview.js index 5689e58b..54f30d2c 100644 --- a/public/viewjs/batteriesoverview.js +++ b/public/viewjs/batteriesoverview.js @@ -66,7 +66,7 @@ $(document).on('click', '.track-charge-cycle-button', function(e) var batteryName = $(e.currentTarget).attr('data-battery-name'); var trackedTime = moment().format('YYYY-MM-DD HH:mm:ss'); - Grocy.Api.Post('batteries/' + batteryId + '/charged?tracked_time=' + trackedTime, + Grocy.Api.Post('batteries/' + batteryId + '/charge', { 'tracked_time': trackedTime }, function() { Grocy.Api.Get('batteries/' + batteryId, diff --git a/public/viewjs/batteryform.js b/public/viewjs/batteryform.js index 2b084821..8a3c662d 100644 --- a/public/viewjs/batteryform.js +++ b/public/viewjs/batteryform.js @@ -7,7 +7,7 @@ if (Grocy.EditMode === 'create') { - Grocy.Api.Post('object/batteries', jsonData, + Grocy.Api.Post('objects/batteries', jsonData, function(result) { window.location.href = U('/batteries'); @@ -21,7 +21,7 @@ } else { - Grocy.Api.Put('object/batteries/' + Grocy.EditObjectId, jsonData, + Grocy.Api.Put('objects/batteries/' + Grocy.EditObjectId, jsonData, function(result) { window.location.href = U('/batteries'); diff --git a/public/viewjs/batterytracking.js b/public/viewjs/batterytracking.js index 958cbe99..d21a2055 100644 --- a/public/viewjs/batterytracking.js +++ b/public/viewjs/batterytracking.js @@ -8,7 +8,7 @@ Grocy.Api.Get('batteries/' + jsonForm.battery_id, function (batteryDetails) { - Grocy.Api.Post('batteries/' + jsonForm.battery_id + '/charge?tracked_time=' + $('#tracked_time').find('input').val(), + Grocy.Api.Post('batteries/' + jsonForm.battery_id + '/charge', { 'tracked_time': $('#tracked_time').find('input').val() }, function(result) { Grocy.FrontendHelpers.EndUiBusy("batterytracking-form"); @@ -92,7 +92,7 @@ $('#tracked_time').find('input').on('keypress', function (e) function UndoChargeCycle(chargeCycleId) { - Grocy.Api.Post('batteries' + chargeCycleId.toString() + '/undo', + Grocy.Api.Post('batteries/' + chargeCycleId.toString() + '/undo', { }, function(result) { toastr.success(L("Charge cycle successfully undone")); diff --git a/public/viewjs/choreform.js b/public/viewjs/choreform.js index f564d01d..67860df6 100644 --- a/public/viewjs/choreform.js +++ b/public/viewjs/choreform.js @@ -7,7 +7,7 @@ if (Grocy.EditMode === 'create') { - Grocy.Api.Post('object/chores', jsonData, + Grocy.Api.Post('objects/chores', jsonData, function(result) { window.location.href = U('/chores'); @@ -21,7 +21,7 @@ } else { - Grocy.Api.Put('object/chores/' + Grocy.EditObjectId, jsonData, + Grocy.Api.Put('objects/chores/' + Grocy.EditObjectId, jsonData, function(result) { window.location.href = U('/chores'); diff --git a/public/viewjs/chores.js b/public/viewjs/chores.js index aacb8b7e..cbf91a0f 100644 --- a/public/viewjs/chores.js +++ b/public/viewjs/chores.js @@ -52,7 +52,7 @@ $(document).on('click', '.chore-delete-button', function (e) { if (result === true) { - Grocy.Api.Delete('object/chores/' + objectId, + Grocy.Api.Delete('objects/chores/' + objectId, {}, function(result) { window.location.href = U('/chores'); diff --git a/public/viewjs/choresjournal.js b/public/viewjs/choresjournal.js index 51b7a2ed..a2923bc5 100644 --- a/public/viewjs/choresjournal.js +++ b/public/viewjs/choresjournal.js @@ -56,7 +56,7 @@ $(document).on('click', '.undo-chore-execution-button', function(e) var element = $(e.currentTarget); var executionId = $(e.currentTarget).attr('data-execution-id'); - Grocy.Api.Post('chores/' + executionId.toString() + '/undo', + Grocy.Api.Post('chores/' + executionId.toString() + '/undo', { }, function(result) { element.closest("tr").addClass("text-muted"); diff --git a/public/viewjs/choresoverview.js b/public/viewjs/choresoverview.js index fb51e4f5..a48698b8 100644 --- a/public/viewjs/choresoverview.js +++ b/public/viewjs/choresoverview.js @@ -66,7 +66,7 @@ $(document).on('click', '.track-chore-button', function(e) var choreName = $(e.currentTarget).attr('data-chore-name'); var trackedTime = moment().format('YYYY-MM-DD HH:mm:ss'); - Grocy.Api.Post('chores/' + choreId + '/execute?tracked_time=' + trackedTime, + Grocy.Api.Post('chores/' + choreId + '/execute', { 'tracked_time': trackedTime }, function() { Grocy.Api.Get('chores/' + choreId, diff --git a/public/viewjs/choretracking.js b/public/viewjs/choretracking.js index 709cd88b..fc840833 100644 --- a/public/viewjs/choretracking.js +++ b/public/viewjs/choretracking.js @@ -8,7 +8,7 @@ Grocy.Api.Get('chores/' + jsonForm.chore_id, function (choreDetails) { - Grocy.Api.Post('chores/' + jsonForm.chore_id + '/execute?tracked_time=' + Grocy.Components.DateTimePicker.GetValue() + "&done_by=" + Grocy.Components.UserPicker.GetValue(), + Grocy.Api.Post('chores/' + jsonForm.chore_id + '/execute', { 'tracked_time': Grocy.Components.DateTimePicker.GetValue(), 'done_by': Grocy.Components.UserPicker.GetValue() }, function(result) { Grocy.FrontendHelpers.EndUiBusy("choretracking-form"); @@ -89,7 +89,7 @@ Grocy.Components.DateTimePicker.GetInputElement().on('keypress', function(e) function UndoChoreExecution(executionId) { - Grocy.Api.Post('chores/' + executionId.toString() + '/undo', + Grocy.Api.Post('chores/' + executionId.toString() + '/undo', { }, function(result) { toastr.success(L("Chore execution successfully undone")); diff --git a/public/viewjs/components/productcard.js b/public/viewjs/components/productcard.js index d83ce546..14874934 100644 --- a/public/viewjs/components/productcard.js +++ b/public/viewjs/components/productcard.js @@ -2,7 +2,7 @@ Grocy.Components.ProductCard = { }; Grocy.Components.ProductCard.Refresh = function(productId) { - Grocy.Api.Get('stock/' + productId, + Grocy.Api.Get('stock/products/' + productId, function(productDetails) { var stockAmount = productDetails.stock_amount || '0'; @@ -58,7 +58,7 @@ Grocy.Components.ProductCard.Refresh = function(productId) } ); - Grocy.Api.Get('stock/' + productId + '/pricehistory', + Grocy.Api.Get('stock/products/' + productId + '/price-history', function(priceHistoryDataPoints) { if (priceHistoryDataPoints.length > 0) diff --git a/public/viewjs/consume.js b/public/viewjs/consume.js index 6d14c4f3..b0b4ae6d 100644 --- a/public/viewjs/consume.js +++ b/public/viewjs/consume.js @@ -10,23 +10,21 @@ jsonForm.amount = 1; } - var spoiled = 0; - if ($('#spoiled').is(':checked')) - { - spoiled = 1; - } + var apiUrl = 'stock/products/' + jsonForm.product_id + '/consume'; - var apiUrl = 'stock/' + jsonForm.product_id + '/consume/' + jsonForm.amount + '?spoiled=' + spoiled; + var jsonData = {}; + jsonData.amount = jsonForm.amount; + jsonData.spoiled = $('#spoiled').is(':checked'); if ($("#use_specific_stock_entry").is(":checked")) { - apiUrl += "&stock_entry_id=" + jsonForm.specific_stock_entry; + jsonData.stock_entry_id = jsonForm.specific_stock_entry; } - Grocy.Api.Get('stock/' + jsonForm.product_id, + Grocy.Api.Get('stock/products/' + jsonForm.product_id, function(productDetails) { - Grocy.Api.Post(apiUrl, + Grocy.Api.Post(apiUrl, jsonData, function(result) { $("#specific_stock_entry").find("option").remove().end().append(""); @@ -70,17 +68,20 @@ $('#save-mark-as-open-button').on('click', function(e) jsonForm.amount = 1; } - var apiUrl = 'stock/' + jsonForm.product_id + '/open/' + jsonForm.amount; + var apiUrl = 'stock/products/' + jsonForm.product_id + '/open'; + + jsonData = { }; + jsonData.amount = jsonForm.amount; if ($("#use_specific_stock_entry").is(":checked")) { - apiUrl += "&stock_entry_id=" + jsonForm.specific_stock_entry; + jsonData.stock_entry_id = jsonForm.specific_stock_entry; } - Grocy.Api.Get('stock/' + jsonForm.product_id, + Grocy.Api.Get('stock/products/' + jsonForm.product_id, function(productDetails) { - Grocy.Api.Post(apiUrl, + Grocy.Api.Post(apiUrl, jsonData, function(result) { $("#specific_stock_entry").find("option").remove().end().append(""); @@ -126,7 +127,7 @@ Grocy.Components.ProductPicker.GetPicker().on('change', function(e) { Grocy.Components.ProductCard.Refresh(productId); - Grocy.Api.Get('stock/' + productId, + Grocy.Api.Get('stock/products/' + productId, function(productDetails) { $('#amount').attr('max', productDetails.stock_amount); @@ -161,8 +162,8 @@ Grocy.Components.ProductPicker.GetPicker().on('change', function(e) } ); - Grocy.Api.Get("stock/" + productId, - function (stockEntries) + Grocy.Api.Get("stock/products/" + productId + '/entries', + function(stockEntries) { stockEntries.forEach(stockEntry => { @@ -249,7 +250,7 @@ $("#use_specific_stock_entry").on("change", function() function UndoStockBooking(bookingId) { - Grocy.Api.Post('booking/' + bookingId.toString() + '/undo', + Grocy.Api.Post('stock/bookings/' + bookingId.toString() + '/undo', { }, function(result) { toastr.success(L("Booking successfully undone")); diff --git a/public/viewjs/equipment.js b/public/viewjs/equipment.js index a524a42a..cbdbcee3 100644 --- a/public/viewjs/equipment.js +++ b/public/viewjs/equipment.js @@ -34,7 +34,7 @@ equipmentTable.on('select', function(e, dt, type, indexes) function DisplayEquipment(id) { - Grocy.Api.Get('object/equipment/' + id, + Grocy.Api.Get('objects/equipment/' + id, function(equipmentItem) { $(".selected-equipment-name").text(equipmentItem.name); @@ -98,7 +98,7 @@ $(document).on('click', '.equipment-delete-button', function (e) { if (result === true) { - Grocy.Api.Delete('object/equipment/' + objectId, + Grocy.Api.Delete('objects/equipment/' + objectId, {}, function(result) { window.location.href = U('/equipment'); diff --git a/public/viewjs/equipmentform.js b/public/viewjs/equipmentform.js index d8edc32a..fe6cb18e 100644 --- a/public/viewjs/equipmentform.js +++ b/public/viewjs/equipmentform.js @@ -18,7 +18,7 @@ if (Grocy.EditMode === 'create') { - Grocy.Api.Post('object/equipment', jsonData, + Grocy.Api.Post('objects/equipment', jsonData, function(result) { if (jsonData.hasOwnProperty("instruction_manual_file_name") && !Grocy.DeleteInstructionManualOnSave) @@ -51,7 +51,7 @@ { if (Grocy.DeleteInstructionManualOnSave) { - Grocy.Api.DeleteFile(Grocy.InstructionManualFileNameName, 'equipmentmanuals', + Grocy.Api.DeleteFile(Grocy.InstructionManualFileNameName, 'equipmentmanuals', {}, function(result) { // Nothing to do @@ -64,7 +64,7 @@ ); }; - Grocy.Api.Put('object/equipment/' + Grocy.EditObjectId, jsonData, + Grocy.Api.Put('objects/equipment/' + Grocy.EditObjectId, jsonData, function(result) { if (jsonData.hasOwnProperty("instruction_manual_file_name") && !Grocy.DeleteInstructionManualOnSave) diff --git a/public/viewjs/inventory.js b/public/viewjs/inventory.js index d87447ec..852267e5 100644 --- a/public/viewjs/inventory.js +++ b/public/viewjs/inventory.js @@ -5,10 +5,14 @@ var jsonForm = $('#inventory-form').serializeJSON(); Grocy.FrontendHelpers.BeginUiBusy("inventory-form"); - Grocy.Api.Get('stock/' + jsonForm.product_id, + Grocy.Api.Get('stock/products/' + jsonForm.product_id, function (productDetails) { - Grocy.Api.Post('stock/' + jsonForm.product_id + '/inventory/' + jsonForm.new_amount + '?bestbeforedate=' + Grocy.Components.DateTimePicker.GetValue(), + var jsonData = { }; + jsonData.new_amount = jsonForm.new_amount; + jsonData.best_before_date = Grocy.Components.DateTimePicker.GetValue(); + + Grocy.Api.Post('stock/products/' + jsonForm.product_id + '/inventory', jsonData, function(result) { var addBarcode = GetUriParam('addbarcodetoselection'); @@ -24,7 +28,7 @@ productDetails.product.barcode += ',' + addBarcode; } - Grocy.Api.Put('object/products/' + productDetails.product.id, productDetails.product, + Grocy.Api.Put('objects/products/' + productDetails.product.id, productDetails.product, function (result) { }, function(xhr) { @@ -73,7 +77,7 @@ Grocy.Components.ProductPicker.GetPicker().on('change', function(e) { Grocy.Components.ProductCard.Refresh(productId); - Grocy.Api.Get('stock/' + productId, + Grocy.Api.Get('stock/products/' + productId, function(productDetails) { $('#new_amount').attr('not-equal', productDetails.stock_amount); @@ -157,7 +161,7 @@ $('#new_amount').on('keyup', function(e) if (productId) { - Grocy.Api.Get('stock/' + productId, + Grocy.Api.Get('stock/products/' + productId, function(productDetails) { var productStockAmount = parseInt(productDetails.stock_amount || '0'); diff --git a/public/viewjs/locationform.js b/public/viewjs/locationform.js index 94668031..148bf41e 100644 --- a/public/viewjs/locationform.js +++ b/public/viewjs/locationform.js @@ -7,7 +7,7 @@ if (Grocy.EditMode === 'create') { - Grocy.Api.Post('object/locations', jsonData, + Grocy.Api.Post('objects/locations', jsonData, function(result) { window.location.href = U('/locations'); @@ -21,7 +21,7 @@ } else { - Grocy.Api.Put('object/locations/' + Grocy.EditObjectId, jsonData, + Grocy.Api.Put('objects/locations/' + Grocy.EditObjectId, jsonData, function(result) { window.location.href = U('/locations'); diff --git a/public/viewjs/locations.js b/public/viewjs/locations.js index 4c85ecd3..4aab7341 100644 --- a/public/viewjs/locations.js +++ b/public/viewjs/locations.js @@ -52,7 +52,7 @@ $(document).on('click', '.location-delete-button', function (e) { if (result === true) { - Grocy.Api.Delete('object/locations/' + objectId, + Grocy.Api.Delete('objects/locations/' + objectId, {}, function(result) { window.location.href = U('/locations'); diff --git a/public/viewjs/manageapikeys.js b/public/viewjs/manageapikeys.js index bfcaf263..4adc5457 100644 --- a/public/viewjs/manageapikeys.js +++ b/public/viewjs/manageapikeys.js @@ -58,7 +58,7 @@ $(document).on('click', '.apikey-delete-button', function (e) { if (result === true) { - Grocy.Api.Delete('object/api_keys/' + objectId, + Grocy.Api.Delete('objects/api_keys/' + objectId, {}, function(result) { window.location.href = U('/manageapikeys'); diff --git a/public/viewjs/productform.js b/public/viewjs/productform.js index d792d8ca..75d05460 100644 --- a/public/viewjs/productform.js +++ b/public/viewjs/productform.js @@ -25,7 +25,7 @@ if (Grocy.EditMode === 'create') { - Grocy.Api.Post('object/products', jsonData, + Grocy.Api.Post('objects/products', jsonData, function (result) { if (jsonData.hasOwnProperty("picture_file_name") && !Grocy.DeleteProductPictureOnSave) @@ -58,7 +58,7 @@ { if (Grocy.DeleteProductPictureOnSave) { - Grocy.Api.DeleteFile(Grocy.ProductPictureFileName, 'productpictures', + Grocy.Api.DeleteFile(Grocy.ProductPictureFileName, 'productpictures', {}, function(result) { // Nothing to do @@ -71,7 +71,7 @@ ); }; - Grocy.Api.Put('object/products/' + Grocy.EditObjectId, jsonData, + Grocy.Api.Put('objects/products/' + Grocy.EditObjectId, jsonData, function(result) { if (jsonData.hasOwnProperty("picture_file_name") && !Grocy.DeleteProductPictureOnSave) @@ -110,7 +110,7 @@ $('#barcode-taginput').tagsManager({ if (Grocy.EditMode === 'edit') { - Grocy.Api.Get('object/products/' + Grocy.EditObjectId, + Grocy.Api.Get('objects/products/' + Grocy.EditObjectId, function (product) { if (product.barcode !== null && product.barcode.length > 0) diff --git a/public/viewjs/productgroupform.js b/public/viewjs/productgroupform.js index b553d039..42c6fd2d 100644 --- a/public/viewjs/productgroupform.js +++ b/public/viewjs/productgroupform.js @@ -7,7 +7,7 @@ if (Grocy.EditMode === 'create') { - Grocy.Api.Post('object/product_groups', jsonData, + Grocy.Api.Post('objects/product_groups', jsonData, function(result) { window.location.href = U('/productgroups'); @@ -21,7 +21,7 @@ } else { - Grocy.Api.Put('object/product_groups/' + Grocy.EditObjectId, jsonData, + Grocy.Api.Put('objects/product_groups/' + Grocy.EditObjectId, jsonData, function(result) { window.location.href = U('/productgroups'); diff --git a/public/viewjs/productgroups.js b/public/viewjs/productgroups.js index b03c4b14..02501675 100644 --- a/public/viewjs/productgroups.js +++ b/public/viewjs/productgroups.js @@ -52,7 +52,7 @@ $(document).on('click', '.product-group-delete-button', function(e) { if (result === true) { - Grocy.Api.Delete('object/product_groups/' + objectId, + Grocy.Api.Delete('objects/product_groups/' + objectId, {}, function(result) { window.location.href = U('/productgroups'); diff --git a/public/viewjs/products.js b/public/viewjs/products.js index 8ee0d7a4..48db6ae6 100644 --- a/public/viewjs/products.js +++ b/public/viewjs/products.js @@ -36,7 +36,7 @@ $(document).on('click', '.product-delete-button', function (e) var objectName = $(e.currentTarget).attr('data-product-name'); var objectId = $(e.currentTarget).attr('data-product-id'); - Grocy.Api.Get('stock/' + objectId, + Grocy.Api.Get('stock/products/' + objectId, function(productDetails) { var stockAmount = productDetails.stock_amount || '0'; @@ -59,7 +59,7 @@ $(document).on('click', '.product-delete-button', function (e) { if (result === true) { - Grocy.Api.Delete('object/products/' + objectId, + Grocy.Api.Delete('objects/products/' + objectId, {}, function (result) { window.location.href = U('/products'); diff --git a/public/viewjs/purchase.js b/public/viewjs/purchase.js index e82433a6..34bfe7aa 100644 --- a/public/viewjs/purchase.js +++ b/public/viewjs/purchase.js @@ -5,7 +5,7 @@ var jsonForm = $('#purchase-form').serializeJSON(); Grocy.FrontendHelpers.BeginUiBusy("purchase-form"); - Grocy.Api.Get('stock/' + jsonForm.product_id, + Grocy.Api.Get('stock/products/' + jsonForm.product_id, function(productDetails) { var amount = jsonForm.amount * productDetails.product.qu_factor_purchase_to_stock; @@ -16,7 +16,12 @@ price = parseFloat(jsonForm.price).toFixed(2); } - Grocy.Api.Post('stock/' + jsonForm.product_id + '/add/' + amount + '?bestbeforedate=' + Grocy.Components.DateTimePicker.GetValue() + '&price=' + price, + var jsonData = {}; + jsonData.amount = amount; + jsonData.best_before_date = Grocy.Components.DateTimePicker.GetValue(); + jsonData.price = price; + + Grocy.Api.Post('stock/products/' + jsonForm.product_id + '/add', jsonData, function(result) { var addBarcode = GetUriParam('addbarcodetoselection'); @@ -32,7 +37,7 @@ productDetails.product.barcode += ',' + addBarcode; } - Grocy.Api.Put('object/products/' + productDetails.product.id, productDetails.product, + Grocy.Api.Put('objects/products/' + productDetails.product.id, productDetails.product, function (result) { }, function(xhr) { @@ -89,7 +94,7 @@ Grocy.Components.ProductPicker.GetPicker().on('change', function(e) { Grocy.Components.ProductCard.Refresh(productId); - Grocy.Api.Get('stock/' + productId, + Grocy.Api.Get('stock/products/' + productId, function(productDetails) { $('#amount_qu_unit').text(productDetails.quantity_unit_purchase.name); diff --git a/public/viewjs/quantityunitform.js b/public/viewjs/quantityunitform.js index 2855e93a..3b58e6cb 100644 --- a/public/viewjs/quantityunitform.js +++ b/public/viewjs/quantityunitform.js @@ -7,7 +7,7 @@ if (Grocy.EditMode === 'create') { - Grocy.Api.Post('object/quantity_units', jsonData, + Grocy.Api.Post('objects/quantity_units', jsonData, function(result) { window.location.href = U('/quantityunits'); @@ -21,7 +21,7 @@ } else { - Grocy.Api.Put('object/quantity_units/' + Grocy.EditObjectId, jsonData, + Grocy.Api.Put('objects/quantity_units/' + Grocy.EditObjectId, jsonData, function(result) { window.location.href = U('/quantityunits'); diff --git a/public/viewjs/quantityunits.js b/public/viewjs/quantityunits.js index 15a0d6d6..8e49829a 100644 --- a/public/viewjs/quantityunits.js +++ b/public/viewjs/quantityunits.js @@ -52,7 +52,7 @@ $(document).on('click', '.quantityunit-delete-button', function (e) { if (result === true) { - Grocy.Api.Delete('object/quantity_units/' + objectId, + Grocy.Api.Delete('objects/quantity_units/' + objectId, {}, function(result) { window.location.href = U('/quantityunits'); diff --git a/public/viewjs/recipeform.js b/public/viewjs/recipeform.js index e4a0ee56..c26dbc38 100644 --- a/public/viewjs/recipeform.js +++ b/public/viewjs/recipeform.js @@ -5,7 +5,7 @@ var jsonData = $('#recipe-form').serializeJSON(); Grocy.FrontendHelpers.BeginUiBusy("recipe-form"); - Grocy.Api.Put('object/recipes/' + Grocy.EditObjectId, jsonData, + Grocy.Api.Put('objects/recipes/' + Grocy.EditObjectId, jsonData, function(result) { window.location.href = U('/recipes'); @@ -113,8 +113,8 @@ $(document).on('click', '.recipe-pos-delete-button', function(e) { if (result === true) { - Grocy.Api.Put('object/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), function() { }, function() { }); - Grocy.Api.Delete('object/recipes_pos/' + objectId, + Grocy.Api.Put('objects/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), function() { }, function() { }); + Grocy.Api.Delete('objects/recipes_pos/' + objectId, {}, function(result) { window.location.href = U('/recipe/' + Grocy.EditObjectId); @@ -150,8 +150,8 @@ $(document).on('click', '.recipe-include-delete-button', function(e) { if (result === true) { - Grocy.Api.Put('object/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), function() { }, function() { }); - Grocy.Api.Delete('object/recipes_nestings/' + objectId, + Grocy.Api.Put('objects/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), function() { }, function() { }); + Grocy.Api.Delete('objects/recipes_nestings/' + objectId, {}, function(result) { window.location.href = U('/recipe/' + Grocy.EditObjectId); @@ -178,10 +178,10 @@ $(document).on('click', '.recipe-pos-order-missing-button', function(e) jsonData.amount = productAmount; jsonData.note = L('Added for recipe #1', recipeName); - Grocy.Api.Post('object/shopping_list', jsonData, + Grocy.Api.Post('objects/shopping_list', jsonData, function(result) { - Grocy.Api.Put('object/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), function () { }, function () { }); + Grocy.Api.Put('objects/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), function () { }, function () { }); window.location.href = U('/recipe/' + Grocy.EditObjectId); }, function(xhr) @@ -202,7 +202,7 @@ $(document).on('click', '.recipe-pos-edit-button', function (e) { var recipePosId = $(e.currentTarget).attr('data-recipe-pos-id'); - Grocy.Api.Put('object/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), + Grocy.Api.Put('objects/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), function(result) { window.location.href = U('/recipe/' + Grocy.EditObjectId + '/pos/' + recipePosId); @@ -219,7 +219,7 @@ $(document).on('click', '.recipe-include-edit-button', function (e) var id = $(e.currentTarget).attr('data-recipe-include-id'); var recipeId = $(e.currentTarget).attr('data-recipe-included-recipe-id'); console.log(recipeId); - Grocy.Api.Put('object/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), + Grocy.Api.Put('objects/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), function(result) { $("#recipe-include-editform-title").text(L("Edit included recipe")); @@ -238,7 +238,7 @@ $(document).on('click', '.recipe-include-edit-button', function (e) $("#recipe-pos-add-button").on("click", function(e) { - Grocy.Api.Put('object/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), + Grocy.Api.Put('objects/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), function(result) { window.location.href = U('/recipe/' + Grocy.EditObjectId + '/pos/new'); @@ -252,7 +252,7 @@ $("#recipe-pos-add-button").on("click", function(e) $("#recipe-include-add-button").on("click", function(e) { - Grocy.Api.Put('object/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), + Grocy.Api.Put('objects/recipes/' + Grocy.EditObjectId, $('#recipe-form').serializeJSON(), function(result) { $("#recipe-include-editform-title").text(L("Add included recipe")); @@ -280,7 +280,7 @@ $('#save-recipe-include-button').on('click', function(e) if (editMode === 'create') { - Grocy.Api.Post('object/recipes_nestings', jsonData, + Grocy.Api.Post('objects/recipes_nestings', jsonData, function(result) { window.location.href = U('/recipe/' + Grocy.EditObjectId); @@ -293,7 +293,7 @@ $('#save-recipe-include-button').on('click', function(e) } else { - Grocy.Api.Put('object/recipes_nestings/' + nestingId, jsonData, + Grocy.Api.Put('objects/recipes_nestings/' + nestingId, jsonData, function(result) { window.location.href = U('/recipe/' + Grocy.EditObjectId); diff --git a/public/viewjs/recipeposform.js b/public/viewjs/recipeposform.js index 79221c73..ff5fde78 100644 --- a/public/viewjs/recipeposform.js +++ b/public/viewjs/recipeposform.js @@ -9,7 +9,7 @@ if (Grocy.EditMode === 'create') { - Grocy.Api.Post('object/recipes_pos', jsonData, + Grocy.Api.Post('objects/recipes_pos', jsonData, function(result) { window.location.href = U('/recipe/' + Grocy.EditObjectParentId); @@ -23,7 +23,7 @@ } else { - Grocy.Api.Put('object/recipes_pos/' + Grocy.EditObjectId, jsonData, + Grocy.Api.Put('objects/recipes_pos/' + Grocy.EditObjectId, jsonData, function(result) { window.location.href = U('/recipe/' + Grocy.EditObjectParentId); @@ -45,7 +45,7 @@ Grocy.Components.ProductPicker.GetPicker().on('change', function(e) { Grocy.Components.ProductCard.Refresh(productId); - Grocy.Api.Get('stock/' + productId, + Grocy.Api.Get('stock/products/' + productId, function (productDetails) { if (!$("#only_check_single_unit_in_stock").is(":checked")) diff --git a/public/viewjs/recipes.js b/public/viewjs/recipes.js index ed6595f6..d0da75ec 100644 --- a/public/viewjs/recipes.js +++ b/public/viewjs/recipes.js @@ -63,7 +63,7 @@ $("#selectedRecipeDeleteButton").on('click', function(e) { if (result === true) { - Grocy.Api.Delete('object/recipes/' + objectId, + Grocy.Api.Delete('objects/recipes/' + objectId, {}, function(result) { window.location.href = U('/recipes'); @@ -101,7 +101,7 @@ $(document).on('click', '.recipe-order-missing-button', function(e) { Grocy.FrontendHelpers.BeginUiBusy(); - Grocy.Api.Post('recipes/' + objectId + '/shoppinglist', + Grocy.Api.Post('recipes/' + objectId + '/add-not-fulfilled-products-to-shoppinglist', { }, function(result) { window.location.href = U('/recipes'); @@ -140,7 +140,7 @@ $("#selectedRecipeConsumeButton").on('click', function(e) { Grocy.FrontendHelpers.BeginUiBusy(); - Grocy.Api.Get('recipes/' + objectId + '/consume', + Grocy.Api.Post('recipes/' + objectId + '/consume', { }, function(result) { Grocy.FrontendHelpers.EndUiBusy(); diff --git a/public/viewjs/shoppinglist.js b/public/viewjs/shoppinglist.js index 557d5451..849ab8c7 100644 --- a/public/viewjs/shoppinglist.js +++ b/public/viewjs/shoppinglist.js @@ -64,7 +64,7 @@ $(document).on('click', '.shoppinglist-delete-button', function (e) var shoppingListItemId = $(e.currentTarget).attr('data-shoppinglist-id'); Grocy.FrontendHelpers.BeginUiBusy(); - Grocy.Api.Delete('object/shopping_list/' + shoppingListItemId, + Grocy.Api.Delete('objects/shopping_list/' + shoppingListItemId, {}, function(result) { $('#shoppinglistitem-' + shoppingListItemId + '-row').fadeOut(500, function() @@ -84,7 +84,7 @@ $(document).on('click', '.shoppinglist-delete-button', function (e) $(document).on('click', '#add-products-below-min-stock-amount', function(e) { - Grocy.Api.Post('stock/shoppinglist', + Grocy.Api.Post('stock/shoppinglist/add-missing-products', { }, function(result) { window.location.href = U('/shoppinglist'); @@ -116,7 +116,7 @@ $(document).on('click', '#clear-shopping-list', function(e) { Grocy.FrontendHelpers.BeginUiBusy(); - Grocy.Api.Post('stock/clearshoppinglist', + Grocy.Api.Post('stock/shoppinglist/clear', { }, function(result) { $('#shoppinglist-table tbody tr').fadeOut(500, function() diff --git a/public/viewjs/shoppinglistform.js b/public/viewjs/shoppinglistform.js index 615a7462..ec6ceeb3 100644 --- a/public/viewjs/shoppinglistform.js +++ b/public/viewjs/shoppinglistform.js @@ -7,7 +7,7 @@ if (Grocy.EditMode === 'create') { - Grocy.Api.Post('object/shopping_list', jsonData, + Grocy.Api.Post('objects/shopping_list', jsonData, function(result) { window.location.href = U('/shoppinglist'); @@ -21,7 +21,7 @@ } else { - Grocy.Api.Put('object/shopping_list/' + Grocy.EditObjectId, jsonData, + Grocy.Api.Put('objects/shopping_list/' + Grocy.EditObjectId, jsonData, function(result) { window.location.href = U('/shoppinglist'); @@ -43,7 +43,7 @@ Grocy.Components.ProductPicker.GetPicker().on('change', function(e) { Grocy.Components.ProductCard.Refresh(productId); - Grocy.Api.Get('stock/' + productId, + Grocy.Api.Get('stock/products/' + productId, function (productDetails) { $('#amount_qu_unit').text(productDetails.quantity_unit_purchase.name); diff --git a/public/viewjs/stockjournal.js b/public/viewjs/stockjournal.js index 6fa2270c..98967b29 100644 --- a/public/viewjs/stockjournal.js +++ b/public/viewjs/stockjournal.js @@ -56,7 +56,7 @@ $(document).on('click', '.undo-stock-booking-button', function(e) var element = $(e.currentTarget); var bookingId = $(e.currentTarget).attr('data-booking-id'); - Grocy.Api.Get('booking/' + bookingId.toString() + '/undo', + Grocy.Api.Post('stock/bookings/' + bookingId.toString() + '/undo', { }, function(result) { element.closest("tr").addClass("text-muted"); diff --git a/public/viewjs/stockoverview.js b/public/viewjs/stockoverview.js index dee687df..888bffbf 100644 --- a/public/viewjs/stockoverview.js +++ b/public/viewjs/stockoverview.js @@ -92,10 +92,10 @@ $(document).on('click', '.product-consume-button', function(e) var productQuName = $(e.currentTarget).attr('data-product-qu-name'); var consumeAmount = $(e.currentTarget).attr('data-consume-amount'); - Grocy.Api.Post('stock/' + productId + '/consume/' + consumeAmount, + Grocy.Api.Post('stock/products/' + productId + '/consume', { 'amount': consumeAmount }, function() { - Grocy.Api.Get('stock/' + productId, + Grocy.Api.Get('stock/products/' + productId, function(result) { var productRow = $('#product-' + productId + '-row'); @@ -189,10 +189,10 @@ $(document).on('click', '.product-open-button', function(e) var productQuName = $(e.currentTarget).attr('data-product-qu-name'); var button = $(e.currentTarget); - Grocy.Api.Get('stock/' + productId + 'open/1', + Grocy.Api.Post('stock/products/' + productId + '/open', { 'amount': 1 }, function() { - Grocy.Api.Get('stock/' + productId, + Grocy.Api.Get('stock/products/' + productId, function(result) { var productRow = $('#product-' + productId + '-row'); diff --git a/public/viewjs/taskcategories.js b/public/viewjs/taskcategories.js index 99a49ebb..5db4c11b 100644 --- a/public/viewjs/taskcategories.js +++ b/public/viewjs/taskcategories.js @@ -52,7 +52,7 @@ $(document).on('click', '.task-category-delete-button', function (e) { if (result === true) { - Grocy.Api.Delete('object/task_categories/' + objectId, + Grocy.Api.Delete('objects/task_categories/' + objectId, {}, function(result) { window.location.href = U('/taskcategories'); diff --git a/public/viewjs/taskcategoryform.js b/public/viewjs/taskcategoryform.js index baba4f01..464a0531 100644 --- a/public/viewjs/taskcategoryform.js +++ b/public/viewjs/taskcategoryform.js @@ -7,7 +7,7 @@ if (Grocy.EditMode === 'create') { - Grocy.Api.Post('object/task_categories', jsonData, + Grocy.Api.Post('objects/task_categories', jsonData, function(result) { window.location.href = U('/taskcategories'); @@ -21,7 +21,7 @@ } else { - Grocy.Api.Put('object/task_categories/' + Grocy.EditObjectId, jsonData, + Grocy.Api.Put('objects/task_categories/' + Grocy.EditObjectId, jsonData, function(result) { window.location.href = U('/taskcategories'); diff --git a/public/viewjs/taskform.js b/public/viewjs/taskform.js index 7cb93896..db99bdd1 100644 --- a/public/viewjs/taskform.js +++ b/public/viewjs/taskform.js @@ -11,7 +11,7 @@ if (Grocy.EditMode === 'create') { - Grocy.Api.Post('object/tasks', jsonData, + Grocy.Api.Post('objects/tasks', jsonData, function(result) { window.location.href = U('/tasks'); @@ -25,7 +25,7 @@ } else { - Grocy.Api.Put('object/tasks/' + Grocy.EditObjectId, jsonData, + Grocy.Api.Put('objects/tasks/' + Grocy.EditObjectId, jsonData, function(result) { window.location.href = U('/tasks'); diff --git a/public/viewjs/tasks.js b/public/viewjs/tasks.js index 783932b0..e7084240 100644 --- a/public/viewjs/tasks.js +++ b/public/viewjs/tasks.js @@ -70,7 +70,7 @@ $(document).on('click', '.do-task-button', function(e) var taskName = $(e.currentTarget).attr('data-task-name'); var doneTime = moment().format('YYYY-MM-DD HH:mm:ss'); - Grocy.Api.Get('tasks/' + taskId + '/complete?done_time=' + doneTime, + Grocy.Api.Post('tasks/' + taskId + '/complete', { 'done_time': doneTime }, function() { if (!$("#show-done-tasks").is(":checked")) @@ -123,7 +123,7 @@ $(document).on('click', '.delete-task-button', function (e) { if (result === true) { - Grocy.Api.Delete('object/tasks/' + objectId, + Grocy.Api.Delete('objects/tasks/' + objectId, {}, function(result) { $('#task-' + objectId + '-row').fadeOut(500, function () diff --git a/public/viewjs/users.js b/public/viewjs/users.js index 24440fab..f2114188 100644 --- a/public/viewjs/users.js +++ b/public/viewjs/users.js @@ -52,7 +52,7 @@ $(document).on('click', '.user-delete-button', function (e) { if (result === true) { - Grocy.Api.Delete('users/delete/' + objectId, + Grocy.Api.Delete('users/delete/' + objectId, {}, function(result) { window.location.href = U('/users'); diff --git a/routes.php b/routes.php index 209dd69e..30161a04 100644 --- a/routes.php +++ b/routes.php @@ -80,18 +80,18 @@ $app->group('', function() $app->group('/api', function() { // OpenAPI - $this->get('/get-openapi-specification', '\Grocy\Controllers\OpenApiController:DocumentationSpec'); - - // Generic entity interaction - $this->get('/object/{entity}', '\Grocy\Controllers\GenericEntityApiController:GetObjects'); - $this->get('/object/{entity}/{objectId}', '\Grocy\Controllers\GenericEntityApiController:GetObject'); - $this->post('/object/{entity}', '\Grocy\Controllers\GenericEntityApiController:AddObject'); - $this->put('/object/{entity}/{objectId}', '\Grocy\Controllers\GenericEntityApiController:EditObject'); - $this->delete('/object/{entity}/{objectId}', '\Grocy\Controllers\GenericEntityApiController:DeleteObject'); + $this->get('/openapi/specification', '\Grocy\Controllers\OpenApiController:DocumentationSpec'); // System - $this->get('/system/get-db-changed-time', '\Grocy\Controllers\SystemApiController:GetDbChangedTime'); + $this->get('/system/db-changed-time', '\Grocy\Controllers\SystemApiController:GetDbChangedTime'); $this->post('/system/log-missing-localization', '\Grocy\Controllers\SystemApiController:LogMissingLocalization'); + + // Generic entity interaction + $this->get('/objects/{entity}', '\Grocy\Controllers\GenericEntityApiController:GetObjects'); + $this->get('/objects/{entity}/{objectId}', '\Grocy\Controllers\GenericEntityApiController:GetObject'); + $this->post('/objects/{entity}', '\Grocy\Controllers\GenericEntityApiController:AddObject'); + $this->put('/objects/{entity}/{objectId}', '\Grocy\Controllers\GenericEntityApiController:EditObject'); + $this->delete('/objects/{entity}/{objectId}', '\Grocy\Controllers\GenericEntityApiController:DeleteObject'); // Files $this->put('/file/{group}', '\Grocy\Controllers\FilesApiController:UploadFile'); @@ -106,36 +106,36 @@ $app->group('/api', function() // User $this->get('/user/settings/{settingKey}', '\Grocy\Controllers\UsersApiController:GetUserSetting'); - $this->post('/user/settings/{settingKey}', '\Grocy\Controllers\UsersApiController:SetUserSetting'); + $this->put('/user/settings/{settingKey}', '\Grocy\Controllers\UsersApiController:SetUserSetting'); - // Stock - $this->get('/stock/volatile', '\Grocy\Controllers\StockApiController:CurrentVolatilStock'); - $this->get('/stock/{productId}', '\Grocy\Controllers\StockApiController:ProductDetails'); - $this->get('/stock/{productId}/pricehistory', '\Grocy\Controllers\StockApiController:ProductPriceHistory'); - $this->get('/stock/{productId}/entries', '\Grocy\Controllers\StockApiController:ProductStockEntries'); + // Stock $this->get('/stock', '\Grocy\Controllers\StockApiController:CurrentStock'); - $this->post('/stock/{productId}/add/{amount}', '\Grocy\Controllers\StockApiController:AddProduct'); - $this->post('/stock/{productId}/consume/{amount}', '\Grocy\Controllers\StockApiController:ConsumeProduct'); - $this->post('/stock/{productId}/open/{amount}', '\Grocy\Controllers\StockApiController:OpenProduct'); - $this->post('/stock/{productId}/inventory/{newAmount}', '\Grocy\Controllers\StockApiController:InventoryProduct'); - $this->post('/stock/shoppinglist', '\Grocy\Controllers\StockApiController:AddMissingProductsToShoppingList'); - $this->post('/stock/clearshoppinglist', '\Grocy\Controllers\StockApiController:ClearShoppingList'); - $this->get('/barcode/{barcode}', '\Grocy\Controllers\StockApiController:ExternalBarcodeLookup'); - $this->post('/booking/{bookingId}/undo', '\Grocy\Controllers\StockApiController:UndoBooking'); + $this->get('/stock/volatile', '\Grocy\Controllers\StockApiController:CurrentVolatilStock'); + $this->get('/stock/products/{productId}', '\Grocy\Controllers\StockApiController:ProductDetails'); + $this->get('/stock/products/{productId}/entries', '\Grocy\Controllers\StockApiController:ProductStockEntries'); + $this->get('/stock/products/{productId}/price-history', '\Grocy\Controllers\StockApiController:ProductPriceHistory'); + $this->post('/stock/products/{productId}/add', '\Grocy\Controllers\StockApiController:AddProduct'); + $this->post('/stock/products/{productId}/consume', '\Grocy\Controllers\StockApiController:ConsumeProduct'); + $this->post('/stock/products/{productId}/inventory', '\Grocy\Controllers\StockApiController:InventoryProduct'); + $this->post('/stock/products/{productId}/open', '\Grocy\Controllers\StockApiController:OpenProduct'); + $this->post('/stock/shoppinglist/add-missing-products', '\Grocy\Controllers\StockApiController:AddMissingProductsToShoppingList'); + $this->post('/stock/shoppinglist/clear', '\Grocy\Controllers\StockApiController:ClearShoppingList'); + $this->post('/stock/bookings/{bookingId}/undo', '\Grocy\Controllers\StockApiController:UndoBooking'); + $this->get('/stock/barcodes/external-lookup', '\Grocy\Controllers\StockApiController:ExternalBarcodeLookup'); // Recipes - $this->post('/recipes/{recipeId}/shoppinglist', '\Grocy\Controllers\RecipesApiController:AddNotFulfilledProductsToShoppingList'); + $this->post('/recipes/{recipeId}/add-not-fulfilled-products-to-shoppinglist', '\Grocy\Controllers\RecipesApiController:AddNotFulfilledProductsToShoppingList'); $this->post('/recipes/{recipeId}/consume', '\Grocy\Controllers\RecipesApiController:ConsumeRecipe'); // Chores - $this->get('/chores/{choreId}', '\Grocy\Controllers\ChoresApiController:ChoreDetails'); $this->get('/chores', '\Grocy\Controllers\ChoresApiController:Current'); - $this->post('/chores/{executionId}/undo', '\Grocy\Controllers\ChoresApiController:UndoChoreExecution'); - $this->post('/chores/{choreId}/execute', '\Grocy\Controllers\ChoresApiController:TrackChoreExecution'); + $this->get('/chores/{choreId}', '\Grocy\Controllers\ChoresApiController:ChoreDetails'); + $this->post('/chores/{choreId}/execute', '\Grocy\Controllers\ChoresApiController:TrackChoreExecution'); + $this->post('/chores/{executionId}/undo', '\Grocy\Controllers\ChoresApiController:UndoChoreExecution'); // Batteries + $this->get('/batteries', '\Grocy\Controllers\BatteriesApiController:Current'); $this->get('/batteries/{batteryId}', '\Grocy\Controllers\BatteriesApiController:BatteryDetails'); - $this->get('/batteries', '\Grocy\Controllers\BatteriesApiController:Current'); $this->post('/batteries/{batteryId}/charge', '\Grocy\Controllers\BatteriesApiController:TrackChargeCycle'); $this->post('/batteries/{chargeCycleId}/undo', '\Grocy\Controllers\BatteriesApiController:UndoChargeCycle'); diff --git a/views/openapiui.blade.php b/views/openapiui.blade.php index 3a52f910..4c13b90c 100644 --- a/views/openapiui.blade.php +++ b/views/openapiui.blade.php @@ -22,7 +22,7 @@