0

I am working on a Symfony 3.4 based web app project which uses JMSSerializer to serialize different custom classes to JSON to send this data to mobile apps.

How can I serialize/deserialize a custom class to/from to int?


Assume we have the following classes:

<?php

// AppBundle/Entity/...

class NotificationInfo {
    public $date;      // DateTime
    public $priority;  // Int 1-10
    public $repeates;  // Boolean

    public function toInt() {
        // Create a simple Int value
        //  date = 04/27/2020
        //  priority = 5
        //  repeats = true
        //  ==> int value = 4272020 5 1 = 427202051
    }

    public function __construnct($intValue) {
       // ==> Split int value into date, priority and repeats...
    }
}


class ToDoItem {
    public $title;
    public $tags;
    public $notificationInfo;
}


// AppBundle/Resources/config/serializer/Entiy.ToDoItem.yml
AppBundle\Entity\ToDoItem:
exclusion_policy: ALL
properties:
    title:
        type: string
        expose: true
    tags:
        type: string
        expose: true
    notificationInfo:
        type: integer
        expose: true

So the class NotificationInfo also has function to create it from int and to serialize it to in. How to tell the serializer that it should serialize the value of $notificationInfo to int?

I could use the following instead:

    notificationInfo:
        type: AppBundle\Entity\NotificationInfo
        expose: true

However in this case I need to configure the serialization of NotificationInfo where I can only specify which property should serialized to which value...


EDIT:

This is the JSON I would like to create:

{
    "title": "Something ToDO",
    "tags": "some,tags",
    "notificationInfo": 427202051
}

This is what I am NOT looking for:

{
    "title": "Something ToDO",
    "tags": "some,tags",
    "notificationInfo": {
        "intValue": 427202051
    }
}
1
  • have you tried VirtualProperty() method of JMS serializer? Commented Apr 28, 2020 at 7:14

2 Answers 2

2

After a lot more digging I found the following solution for my problem: I added a custom serialization Handler which tells JMSSerializer how to handle my custom class:

class NotificationInfoHandler implements SubscribingHandlerInterface {

    public static function getSubscribingMethods() {
        return [
            [
                'direction' => GraphNavigator::DIRECTION_SERIALIZATION,
                'format' => 'json',
                'type' => 'NotificationInfo',
                'method' => 'serializeNotificationInfoToJson',
            ],
            [
                'direction' => GraphNavigator::DIRECTION_DESERIALIZATION,
                'format' => 'json',
                'type' => 'NotificationInfo',
                'method' => 'deserializeNotificationInfoToJson',
            ],
        ;


    public function serializeNotificationInfoToJson(JsonSerializationVisitor $visitor, NotificationInfo $info, array $type, Context $context) {
        return $info->toInt();
    }

    public function deserializeNotificationInfoToJson(JsonDeserializationVisitor $visitor, $infoAsInt, array $type, Context $context) {
        return (is_int($infoAsInt) ? NotificationInfo::fromInt($infoAsInt) : NotificationInfo::emptyInfo());
    }

}

Thanks to autowire the handler is automatically added and can be used in the serializer metadata:

notificationInfo:
    type: NotificationInfo
    expose: true
Sign up to request clarification or add additional context in comments.

Comments

0

you can use VirtualProperty method to add any method of you class into json response

use JMS\Serializer\Annotation as Serializer;

class NotificationInfo 
{
    /**
     * @return int
     * @Serializer\VirtualProperty()
     * @Serializer\SerializedName("formatedLocation")
     */
    public function toInt()
    {
        return 4272020;
    }
}

1 Comment

Thanks, but adding a virtual property to NotificationInfo would only change the content of serialized object. But I am looking to serialize the complete NotificationInfo object/property into one int. I have edited the question to to demonstrate the difference.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.