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

make entries with legacy class names backwards compatible #14

Merged

Conversation

bdoyle0182
Copy link

@bdoyle0182 bdoyle0182 commented Aug 31, 2023

fixes the issue where features of akka / pekko that are dependent on the persistence module and will potentially store the class name of an akka / pekko class as a part of the persisted data.

Copy link
Collaborator

@thjaeckle thjaeckle left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would adjust the replacement of "akka" in classnames to make it more bulletproof

@bdoyle0182
Copy link
Author

I cleaned it up and followed your suggestion good catch there to replaceFirst. I also realized we need to backport this to the old plugin to support roll backs, see this comment on the issue #10

@thjaeckle thjaeckle added this to the 1.0.2 milestone Sep 4, 2023
@thjaeckle thjaeckle merged commit 584cb29 into scullxbones:main Sep 4, 2023
6 checks passed
@thjaeckle
Copy link
Collaborator

Thanks for the contribution @bdoyle0182 👍
Will release a 1.0.2 containing this fix.

@bdoyle0182 bdoyle0182 deleted the translate-class-serializations branch September 5, 2023 15:58
@SakulK
Copy link
Contributor

SakulK commented Dec 8, 2023

PSA for anyone that might hit the same issue as me: this fix unfortunately doesn't seem to address a similar issue with PersistentFSM snapshots. Here is the interesting part of the stacktrace that shows up in logs:

java.util.NoSuchElementException: None.get
     at scala.None$.get(Option.scala:627)
     at scala.None$.get(Option.scala:626)
     at pekko.contrib.persistence.mongodb.driver.ScalaDriverPersistenceSnapshotter$.deserializeSnapshot(ScalaDriverPersistenceSnapshotter.scala:43)
     at pekko.contrib.persistence.mongodb.driver.ScalaDriverPersistenceSnapshotter.$anonfun$findYoungestSnapshotByMaxSequence$5(ScalaDriverPersistenceSnapshotter.scala:82)

After digging deeper I found out that deserialize call here:


returns:

Failure(java.io.NotSerializableException: Cannot find manifest class [akka.persistence.fsm.PersistentFSM$PersistentFSMSnapshot] for serializer with id [7].)

Which is thrown from https://github.com/apache/incubator-pekko/blob/main/actor/src/main/scala/org/apache/pekko/serialization/Serialization.scala#L246

Theory: a replacement of akka. => org.apache.pekko. might work if applied to the manifest here:
https://github.com/apache/incubator-pekko/blob/f6af100531e037b4f245f564d7be8c70f0093a4f/persistence/src/main/scala/org/apache/pekko/persistence/serialization/SnapshotSerializer.scala#L113-L115
But that's unfortunately in the main pekko persistence project. I will share a workaround if I find one 😉

@SakulK
Copy link
Contributor

SakulK commented Dec 8, 2023

Ok, a hacky workaround that I came up with:

  1. Make a copy of org.apache.pekko.persistence.serialization.SnapshotSerializer class from pekko persistence (here called CustomSnapshotSerializer)
  2. In snapshotFromBinary replace the last line with:
    serialization
      .deserialize(snapshotBytes, serializerId, manifest)
      .recoverWith {
        case _: NotSerializableException if manifest.startsWith("akka") =>
          serialization.deserialize(snapshotBytes, serializerId, manifest.replaceFirst("akka", "org.apache.pekko"))
      }
      .get
  1. Register the serializer in the config, something like this:
pekko.actor {
  serialization-identifiers {
    "org.apache.pekko.persistence.serialization.SnapshotSerializer" = -8
    "org.apache.pekko.persistence.serialization.CustomSnapshotSerializer" = 8
  }
  serializers.customSnapshotSerializer = "org.apache.pekko.persistence.serialization.CustomSnapshotSerializer"
  serialization-bindings {
    "org.apache.pekko.persistence.serialization.Snapshot" = customSnapshotSerializer
  }
}

I'm not sure if it makes sense to propose the change from point 2. to the main pekko repo 🤔

@pjfanning
Copy link

@SakulK could you create a discussion at https://github.com/apache/incubator-pekko ?

It seems like we might need doc or code changes in core pekko to help here.

One thing though - have you tried just having the akka jars on your classpath? Akka and Pekko use different package names so they shouldn't affect each other. In theory having the akka jars on your classpath should stop you getting class not found errors.

@SakulK
Copy link
Contributor

SakulK commented Dec 8, 2023

@pjfanning I did a quick test with akka-actor and akka-persistance on the classpath and it didn't help, the error did change though:

java.io.NotSerializableException: Can't deserialize object of type class akka.persistence.fsm.PersistentFSM$PersistentFSMSnapshot

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

Successfully merging this pull request may close these issues.

4 participants