Support for Drupal 7 is ending on 5 January 2025—it’s time to migrate to Drupal 10! Learn about the many benefits of Drupal 10 and find migration tools in our resource center.
Problem/Motivation
DateTimePlus doesn't implement \JsonSerializable, so json_encode(new DateTimePlus())
just returns an empty object.
There are different reasons why it would be interesting to add this support to DateTimePlus
- First, it would increase the compatibility of Drupal's special object DateTimePlus with PHP's DateTime object.
- Furthermore, it would add the capacity for Drupal's Date Form field to have a JSON representation, like many other Drupal fields.
Proposed resolution
Implement \JsonSerializable and create a public function jsonSerialize
Remaining tasks
Tests.
User interface changes
None.
API changes
DateTimePlus will implement \JsonSerializable
Data model changes
None.
Comment | File | Size | Author |
---|---|---|---|
#51 | rerolled-2828835-51.patch | 3.89 KB | Vidushi Mehta |
#35 | interdiff.txt | 1.93 KB | denutkarsh |
#35 | 2828835-35.patch | 3.83 KB | denutkarsh |
#30 | interdiff.txt | 2.71 KB | denutkarsh |
#30 | 2828835-30.patch | 3.98 KB | denutkarsh |
Comments
Comment #2
Julfabre CreditAttribution: Julfabre commentedComment #3
mpdonadioComment #4
mpdonadioThanks for identifying this. Really quick initial look.
Nit. Needs space before the opening brace.
How about "Returns a representation of the object for use in JSON serialization."
Not sure this is really the right thing to do, and it won't mirror the way json_encode(\new DateTime()) works, and it loses information about the object (like the langcode).
This will need test coverage when/if we decide if we want to do this. I think we need to do this, but I would prefer core extends the way json_encode(\new DateTime()) works, rather than just using a rendered string.
Comment #5
Julfabre CreditAttribution: Julfabre commentedHi @mpdonadio,
1. => Ok,
2. => Ok, I've change for : "Returns the DateTime object and langcode for use in JSON serialization"
3. => Ok, I try to understand the json encode method for \DateTime, but it's seems to be magic ;)
So I try to use it and add langcode from Drupal DateTimePlus.
for now it's like this :
Comment #6
mpdonadioI think this format should be OK.
Setting to NW because we need tests to prevent a regression.
Comment #7
denutkarsh CreditAttribution: denutkarsh commentedHere is my Test Patch that i have created.
Comment #8
denutkarsh CreditAttribution: denutkarsh as a volunteer and at Google Code-In commentedComment #9
denutkarsh CreditAttribution: denutkarsh as a volunteer and at Google Code-In commentedI have made the test patch for this issue which checks if serializing DateTimePlus returns empty object or not. Here is my code:-
Comment #10
denutkarsh CreditAttribution: denutkarsh at Google Code-In commentedA simple test for this could be checking weather the
json_encode(new DateTimePlus())
is empty or not. Here is the code that i wrote for testing.Comment #11
denutkarsh CreditAttribution: denutkarsh at Google Code-In commentedA simple test for this could be checking weather the
json_encode(new DateTimePlus())
is empty or not. Here is the code that i wrote for testing.Comment #12
mpdonadioThanks for the test. Setting NR for testbot. Will comment later. Also, make sure you post an interdiff with a new patch.
Comment #14
mpdonadioThanks for picking this up.
OK, ran this locally and it does fail on its own, and pass with #5, which does demonstrate the problem. However, I am uncomfortable with this approach for commit. If we change how JSON serialization works, then this will still pass. I think we should just do the `json_encode` on known DateTimePlus objects (probably want to use a provider), and check the results.
This also has multiple coding standard problems that need to be addressed (we can't commit any patches that violate them). From a quick look
- the deleted line needs to be there (blank link between methods)
- there needs to be a blank line after the last method in the class, and the closing brace
- there needs to be a space between the method () and the opening brace
- boolean literals need to be TRUE / FALSE (ie, capitalized).
- the method needs to be in proper docblock format
For new patches, let's post the test-only patch along with the fix+test. Just make sure the test-only one is added first, and the full one is added second. This will preserve the issue status, assuming all is OK. (see https://www.drupal.org/contributor-tasks/write-tests)
Once we have the nearly done, we will need a short change record to announce it and document the format.
Comment #15
denutkarsh CreditAttribution: denutkarsh at Google Code-In commentedmpdonadio, Just wanted to know how can i access dateTimeObject, from my test function....
Comment #16
denutkarsh CreditAttribution: denutkarsh at Google Code-In commentedUpdated my test function, to check weather after serialization the data is correct. Also i tried to follow coding standards this time.
I have also attached the interdiff
Comment #18
mpdonadio@denutkarsh, this is what I was thinking of. Let's add some more combinations of timezone and langcode to the provider. Looks like core convention is for the langcode value to be lower case. Think we can just do a full patch at this point.
Hit me up on IRC (or anyone there) if you need help.
Comment #19
denutkarsh CreditAttribution: denutkarsh at Google Code-In commented@mpdonadio Something like this ( i have just added one more set right now), we have to add more sets like this to make this test more function, is that right?
Comment #21
denutkarsh CreditAttribution: denutkarsh at Google Code-In commented@mpdonadio Can you tell me why the path i posted is showing that it has 2 fails, while yours shows "PHP 5.5 & MySQL 5.5 21,372 pass".
Comment #22
denutkarsh CreditAttribution: denutkarsh at Google Code-In commentedI have added more sets in this new test patch.
Comment #23
denutkarsh CreditAttribution: denutkarsh at Google Code-In commentedComment #24
denutkarsh CreditAttribution: denutkarsh at Google Code-In commentedThere was php fatal error in previous patch, here is the new one..
Comment #26
denutkarsh CreditAttribution: denutkarsh at Google Code-In commentedComment #27
mpdonadioThis doesn't need a reroll. That is just for when patches don't apply. The fails are from known spurious failures. I'll post a review of the latest patch soon.
Comment #28
mpdonadioOK, we only need to test against 8.3.x. This cannot go into 8.2.x per the change policy, since it is a feature request.
This section is redundant, can be deleted (it is tested above).
I would prefer to us 1400000000 for all of the timestamps in the tests (here and below).
Nits, but we need spaces after the comma between parameters. We can use array shorthand [] for the options, and I would prefer to use lowercase 'en' to be consistent with core usage. Actually, let's use a valid langcode other than 'en' to be safe (here and below).
OK, for this test, we need to test the default timezone with a non-default langcode, so pass in NULL. Per #2498619: Unit tests should use a default timezone other that UTC, the expected TZ should be 'Australia/Sydney', just like with the first set returned.
If this fails anywhere else than DateTimePlusTest, hang tight and let me look at it; we have a bunch #2829040: [meta] Known intermittent, random, and environment-specific test failures going on right now.
Comment #29
gvso@mpdonadio, thanks for reviewing the patch.
Comment #30
denutkarsh CreditAttribution: denutkarsh at Google Code-In commented@mpdonadio, Ok, I have uploaded new improved patch. I have also checked it on simplytest.me and it seems to pass all the tests.
Comment #31
denutkarsh CreditAttribution: denutkarsh at Google Code-In commentedComment #33
mpdonadioUnrelated random fail b/c #2828559: UpdatePathTestBase tests randomly failing. Will look at it when I can, or someone else can review it.
Comment #34
mpdonadioSorry to push this back again over formatting, but there is too much to fix on commit.
I missed this, but this should be explicitly `public function providerTestSerialization`
Looks like this crept in with this patch, but the constructor calls should all be on one line. Here and below. In general, only multi-element arrays can be spread across multiple lines.
If we can fix those, I'll RTBC it.
Comment #35
denutkarsh CreditAttribution: denutkarsh at Google Code-In commented@mpdonadio I just used multiline for the constructor to avoid 80 cols violations. Anyways here is the new patch
Comment #36
mpdonadioRealized that I have work in this, so will get @jhedstrom to set if RTBC if he thinks it looks good.
Comment #37
jhedstromThis looks really good. Great tests and a very straightforward implementation/fix.
Comment #38
alexpottAccording to #14 we need a change record.
Also the issue summary is missing the reason why we need this. Not all objects have to be json serializable - so what's the advantage to doing this change?
Comment #39
mpdonadioTook a stab at the CR.
Comment #40
mpdonadio@Julfabre, can you update the Issue Summary with a use case that describes why this is needed beyond what Drupal provides for Serialization as part of core? Thanks.
Comment #41
Julfabre CreditAttribution: Julfabre commentedComment #42
Julfabre CreditAttribution: Julfabre commented@mpdonadio : Ok I've updated the summary section.
I'm trying to create an change record page, but I'm newbie on this.
I hope it's like good for all of us.
Comment #43
mpdonadio@Julfabre, thanks. I already made a change record for this. I need to discuss the two bullet points with others before we can proceed here. I thought all of the datetime fields already worked with the REST system.
Comment #46
jhedstromThis reason alone seems worth making this change for?
Comment #49
jhedstromPatch needs to be rerolled. I'm inclined to get this in, as from what I can tell, our custom date time class should be serializable.
I'm not clear on why this doesn't cause more issues with existing serialization. One thought is that it's possible computed fields are always unset prior to serialization, so perhaps this doesn't appear when serializing an entity with a datetime field on it...
Comment #50
mpdonadio#49, another hypothesis is that all of our REST stuff uses the ISO string and not the serialized object.
Comment #51
Vidushi Mehta CreditAttribution: Vidushi Mehta at gai Technologies Pvt Ltd commentedPatch rerolled.
Comment #52
Vidushi Mehta CreditAttribution: Vidushi Mehta at gai Technologies Pvt Ltd commentedComment #53
jhedstromSince
DateTimePlus
is a component, and can theoretically be used completely independently of Drupal, our REST system, and other things, I think it makes sense to allow it to be serializable since PHP's\DateTime
can be serialized.Comment #54
alexpottI don't get why we need both testIsSerializable() and testSerialization(). testSerialization() is enough - the other test doesn't appear do anything new.
Also we should have a follow-up to fix the docs of \Drupal\Component\Datetime\DateTimePlus::__construct() - the debug option does not appear exist and the only thing that is used in $settings is $settings['langcode'] which all seems quite odd.
There's also an open question about what should happen if it's an object with errors. Ie. what happens if the creation of PHP's \Datetime object fails. I think the errors property should also be serialized.