Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Mongo Auditing: @CreatedDate field gets set to null on updates with Spring Data Rest [DATAREST-1204] #1565

Open
spring-projects-issues opened this issue Feb 9, 2017 · 12 comments
Assignees
Labels
type: bug A general bug

Comments

@spring-projects-issues
Copy link

Benjamin Cody opened DATAREST-1204 and commented

I've set up a Spring Boot application with spring-boot-starter-data-rest and spring-boot-starter-data-mongodb. I'm using the Mongo auditing feature to automatically set insert and update timestamps on my records using the @CreatedDate and @LastModifiedDate annotations.

I'm using the generated REST/HAL endpoint to insert and update records. When I insert a record, its insert and update timestamp both get set to the current time, as expected. However, when I perform an update, the insert timestamp get overwritten with null! :( The update timestamp gets updated correctly (as does the @Version annotated field).

This issue occurs when I have public getters/setters for my insert/update fields. When I remove those getters/setters, the fields get written as I would expect: the insert timestamp only gets written once on inserts and doesn't change on updates, and the update timestamp always gets written. With the @Version annotated field, it doesn't matter whether or not I have a public getter/setter: the version is never output by the REST endpoint and also cannot be set explicitly by the client.

I prepared a minimal project with a test which shows this scenario: https://github.com/bencody/spring_data_mongo_createddate


Affects: 2.6.10 (Ingalls SR10)

Reference URL: https://github.com/bencody/spring_data_mongo_createddate

2 votes, 4 watchers

@spring-projects-issues
Copy link
Author

Benjamin Cody commented

Note: instead of removing the public getter/setter of the @CreatedDate field, adding the @JsonIgnore annotation also prevents it from being set to null on updates. That's what I'm currently doing as a work-around. Obviously the data isn't output via REST by doing that, but that's OK for me

@spring-projects-issues
Copy link
Author

Keats commented

Note : @ReadOnlyProperty doesn't help (it works on JPA entities though)

It appears there is no way to make it work while exposing the values to the client.

Note 2 : It obviously works well without SDR: just findOne, then update the fields.

Workaround : Write all controllers yourself and ditch SDR

@spring-projects-issues
Copy link
Author

Oliver Drotbohm commented

tl;dr: @JsonIgnoreProperties(value={ … }, allowGetters=true) should do the trick and whether a value gets serialized or deserialized for a simple property is purely a matter of your Jackson setup.

I don't even think this is an issue Spring Data REST should care about. A property annotated with @CreatedDate is a regular property, i.e. no special handling gets applied in the first place, which means that you have all Jackson customization means in place to make sure it handles it as you expect. A quick Google search revealed this comment by the Jackson maintainer

@mjustin
Copy link

mjustin commented Jan 14, 2021

A more targeted Jackson solution is to annotate just the single field as being read-only:

@JsonProperty(access = JsonProperty.Access.READ_ONLY)
@CreatedDate
private Instant createdDate;

@boo3lem
Copy link

boo3lem commented Jun 23, 2021

you can make that variable editable = false like this exemple

@column(name = "creationDate", nullable = false, updatable = false)

@SimoneGiusso
Copy link

SimoneGiusso commented Jun 15, 2022

The issue is more general and not related to mongo. The same behaviour happens with other DBs (e.g. postgreSQL). As suggested by @boo3lem a quick fix is to set the column as not updatable. The expected behaviour should be the following:

when a column is annotated with @CreatedDate the column should be filled on inserts and skipped on updates

@v-dimi

This comment was marked as resolved.

@lamponyuh
Copy link

Up issue. I have this problem too

@cybersokari
Copy link

In my case, createdDate is null when I provide an ID. It only gets populated when I allow Mongo to generate an ID

@thnguyen101
Copy link

you can make that variable editable = false like this exemple

@column(name = "creationDate", nullable = false, updatable = false)

But I am using Spring Data JDBC, so I don't have @column(name = "creationDate", nullable = false, updatable = false)

@pvpscript
Copy link

Same issue here.

Seems counter intuitive to nullify the creationDate field, after all, the whole point of auditing is to have both dates.
I have no hopes that this will get fixed any time soon, giving that this issue is open since early 2017, but come on... This is beyond frustrating

@ashish3805
Copy link

ashish3805 commented Aug 25, 2024

+1, it is not working for POST requests as well. I am creating an entity with POST, it has the following:

  @CreationTimestamp
  @Column(name = "created_at")
  private Instant createdAt;

it is set to null when I save through spring data rest created endpoint with POST.

Solution:
annotate root entity with : @EntityListeners(AuditingEntityListener.class) and use @CreatedDate instead of @CreationTimestamp

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
type: bug A general bug
Projects
None yet
Development

No branches or pull requests