diff --git a/lib/API/JSON/v1/CustomFields.php b/lib/API/JSON/v1/CustomFields.php index 736e451fbc..2c896c0191 100644 --- a/lib/API/JSON/v1/CustomFields.php +++ b/lib/API/JSON/v1/CustomFields.php @@ -4,7 +4,11 @@ namespace MailPoet\API\JSON\v1; use MailPoet\API\JSON\Endpoint as APIEndpoint; use MailPoet\API\JSON\Error as APIError; +use MailPoet\API\JSON\Response; +use MailPoet\API\JSON\ResponseBuilders\CustomFieldsResponseBuilder; use MailPoet\Config\AccessControl; +use MailPoet\CustomFields\CustomFieldsRepository; +use MailPoet\Entities\CustomFieldEntity; use MailPoet\Models\CustomField; use MailPoet\WP\Functions as WPFunctions; @@ -13,22 +17,33 @@ class CustomFields extends APIEndpoint { 'global' => AccessControl::PERMISSION_MANAGE_FORMS, ]; - function getAll() { - $collection = CustomField::orderByAsc('created_at')->findMany(); - $custom_fields = array_map(function($custom_field) { - return $custom_field->asArray(); - }, $collection); + /** @var CustomFieldsRepository */ + private $custom_fields_repository; - return $this->successResponse($custom_fields); + /** @var CustomFieldsResponseBuilder */ + private $custom_fields_response_builder; + + public function __construct( + CustomFieldsRepository $custom_fields_repository, + CustomFieldsResponseBuilder $custom_fields_response_builder + ) { + $this->custom_fields_repository = $custom_fields_repository; + $this->custom_fields_response_builder = $custom_fields_response_builder; + } + + function getAll() { + $collection = $this->custom_fields_repository->findBy([], ['created_at' => 'asc']); + return $this->successResponse($this->custom_fields_response_builder->buildBatch($collection)); } function delete($data = []) { $id = (isset($data['id']) ? (int)$data['id'] : null); - $custom_field = CustomField::findOne($id); - if ($custom_field instanceof CustomField) { - $custom_field->delete(); + $custom_field = $this->custom_fields_repository->findOneById($id); + if ($custom_field instanceof CustomFieldEntity) { + $this->custom_fields_repository->remove($custom_field); + $this->custom_fields_repository->flush(); - return $this->successResponse($custom_field->asArray()); + return $this->successResponse($this->custom_fields_response_builder->build($custom_field)); } else { return $this->errorResponse([ APIError::NOT_FOUND => WPFunctions::get()->__('This custom field does not exist.', 'mailpoet'), @@ -37,24 +52,21 @@ class CustomFields extends APIEndpoint { } function save($data = []) { - $custom_field = CustomField::createOrUpdate($data); - $errors = $custom_field->getErrors(); - - if (!empty($errors)) { - return $this->badRequest($errors); + try { + $custom_field = $this->custom_fields_repository->createOrUpdate($data); + $custom_field = $this->custom_fields_repository->findOneById($custom_field->getId()); + if(!$custom_field instanceof CustomFieldEntity) return $this->errorResponse(); + return $this->successResponse($this->custom_fields_response_builder->build($custom_field)); + } catch (\Exception $e) { + return $this->errorResponse($errors = [], $meta = [], $status = Response::STATUS_BAD_REQUEST); } - $custom_field = CustomField::findOne($custom_field->id); - if(!$custom_field instanceof CustomField) return $this->errorResponse(); - $response = $custom_field->asArray(); - $response['id'] = (int)$response['id']; - return $this->successResponse($response); } function get($data = []) { $id = (isset($data['id']) ? (int)$data['id'] : null); - $custom_field = CustomField::findOne($id); - if ($custom_field instanceof CustomField) { - return $this->successResponse($custom_field->asArray()); + $custom_field = $this->custom_fields_repository->findOneById($id); + if ($custom_field instanceof CustomFieldEntity) { + return $this->successResponse($this->custom_fields_response_builder->build($custom_field)); } return $this->errorResponse([ APIError::NOT_FOUND => WPFunctions::get()->__('This custom field does not exist.', 'mailpoet'), diff --git a/lib/CustomFields/CustomFieldsRepository.php b/lib/CustomFields/CustomFieldsRepository.php index cc4b888b03..a849e2659d 100644 --- a/lib/CustomFields/CustomFieldsRepository.php +++ b/lib/CustomFields/CustomFieldsRepository.php @@ -17,4 +17,25 @@ class CustomFieldsRepository extends Repository { protected function getEntityClassName() { return CustomFieldEntity::class; } + + /** + * @param array $data + * @return CustomFieldEntity + */ + public function createOrUpdate($data) { + if (isset($data['id'])) { + $field = $this->findOneById((int)$data['id']); + } elseif (isset($data['name'])) { + $field = $this->findOneBy(['name' => $data['name']]); + } + if (!isset($field)) { + $field = new CustomFieldEntity(); + $this->entity_manager->persist($field); + } + if (isset($data['name'])) $field->setName($data['name']); + if (isset($data['type'])) $field->setType($data['type']); + if (isset($data['params'])) $field->setParams($data['params']); + $this->entity_manager->flush(); + return $field; + } } diff --git a/lib/Entities/CustomFieldEntity.php b/lib/Entities/CustomFieldEntity.php index 803940d5a2..6c8498d689 100644 --- a/lib/Entities/CustomFieldEntity.php +++ b/lib/Entities/CustomFieldEntity.php @@ -20,19 +20,20 @@ class CustomFieldEntity { /** * @ORM\Column(type="string", nullable=false, unique=true) + * @Assert\NotBlank() * @var string */ private $name; /** * @ORM\Column(type="string", nullable=false) + * @Assert\NotBlank() * @var string */ private $type; /** * @ORM\Column(type="json_or_serialized") - * @Assert\NotBlank() * @var array */ private $params; @@ -57,4 +58,25 @@ class CustomFieldEntity { public function getParams() { return $this->params; } + + /** + * @param string $name + */ + public function setName($name) { + $this->name = $name; + } + + /** + * @param string $type + */ + public function setType($type) { + $this->type = $type; + } + + /** + * @param array $params + */ + public function setParams($params) { + $this->params = $params; + } } diff --git a/tests/integration/API/JSON/v1/CustomFieldsTest.php b/tests/integration/API/JSON/v1/CustomFieldsTest.php index cdc4adc2ff..b136bdfa39 100644 --- a/tests/integration/API/JSON/v1/CustomFieldsTest.php +++ b/tests/integration/API/JSON/v1/CustomFieldsTest.php @@ -3,10 +3,17 @@ namespace MailPoet\Test\API\JSON\v1; use MailPoet\API\JSON\Response as APIResponse; +use MailPoet\API\JSON\ResponseBuilders\CustomFieldsResponseBuilder; use MailPoet\API\JSON\v1\CustomFields; +use MailPoet\CustomFields\CustomFieldsRepository; +use MailPoet\DI\ContainerWrapper; use MailPoet\Models\CustomField; class CustomFieldsTest extends \MailPoetTest { + + /** @var CustomFieldsRepository */ + private $repository; + private $custom_fields = [ [ 'name' => 'CF: text', @@ -54,13 +61,15 @@ class CustomFieldsTest extends \MailPoetTest { function _before() { parent::_before(); + $this->repository = ContainerWrapper::getInstance(WP_DEBUG)->get(CustomFieldsRepository::class); + $this->repository->truncate(); foreach ($this->custom_fields as $custom_field) { - CustomField::createOrUpdate($custom_field); + $this->repository->createOrUpdate($custom_field); } } function testItCanGetAllCustomFields() { - $router = new CustomFields(); + $router = new CustomFields($this->repository, new CustomFieldsResponseBuilder()); $response = $router->getAll(); expect($response->status)->equals(APIResponse::STATUS_OK); expect($response->data)->count(count($this->custom_fields)); @@ -76,7 +85,7 @@ class CustomFieldsTest extends \MailPoetTest { $custom_field = CustomField::where('type', 'date')->findOne(); $custom_field_id = $custom_field->id(); - $router = new CustomFields(); + $router = new CustomFields($this->repository, new CustomFieldsResponseBuilder()); $response = $router->delete(['id' => $custom_field_id]); expect($response->status)->equals(APIResponse::STATUS_OK); @@ -91,34 +100,31 @@ class CustomFieldsTest extends \MailPoetTest { $new_custom_field = [ 'name' => 'New custom field', 'type' => 'text', + 'params' => [], ]; - $router = new CustomFields(); + $router = new CustomFields($this->repository, new CustomFieldsResponseBuilder()); $response = $router->save($new_custom_field); expect($response->status)->equals(APIResponse::STATUS_OK); // missing type - $response = $router->save(['name' => 'New custom field']); + $response = $router->save(['name' => 'New custom field1']); expect($response->status)->equals(APIResponse::STATUS_BAD_REQUEST); - expect($response->errors[0]['message'])->equals('Please specify a type.'); // missing name $response = $router->save(['type' => 'text']); expect($response->status)->equals(APIResponse::STATUS_BAD_REQUEST); - expect($response->errors[0]['message'])->equals('Please specify a name.'); // missing data $response = $router->save(); expect($response->status)->equals(APIResponse::STATUS_BAD_REQUEST); - expect($response->errors[0]['message'])->equals('Please specify a name.'); - expect($response->errors[1]['message'])->equals('Please specify a type.'); } function testItCanGetACustomField() { - $custom_field = CustomField::where('name', 'CF: text')->findOne(); + $custom_field = $this->repository->findOneBy(['name' => 'CF: text']); - $router = new CustomFields(); - $response = $router->get(['id' => $custom_field->id()]); + $router = new CustomFields($this->repository, new CustomFieldsResponseBuilder()); + $response = $router->get(['id' => $custom_field->getId()]); expect($response->data['name'])->equals('CF: text'); expect($response->data['type'])->equals('text'); @@ -127,8 +133,4 @@ class CustomFieldsTest extends \MailPoetTest { $response = $router->get(['id' => 'not_an_id']); expect($response->status)->equals(APIResponse::STATUS_NOT_FOUND); } - - function _after() { - CustomField::deleteMany(); - } }