@@ -53,7 +53,9 @@ describe( 'crdt', () => {
5353
5454 applyPostChangesToCRDTDoc ( doc , changes , mockPostType ) ;
5555
56- expect ( map . get ( 'title' ) ) . toBe ( 'New Title' ) ;
56+ const title = map . get ( 'title' ) ;
57+ expect ( title ) . toBeInstanceOf ( Y . Text ) ;
58+ expect ( title ?. toString ( ) ) . toBe ( 'New Title' ) ;
5759 } ) ;
5860
5961 it ( 'does not sync disallowed properties' , ( ) => {
@@ -65,7 +67,7 @@ describe( 'crdt', () => {
6567 applyPostChangesToCRDTDoc ( doc , changes , mockPostType ) ;
6668
6769 expect ( map . has ( 'unsyncedProperty' ) ) . toBe ( false ) ;
68- expect ( map . get ( 'title' ) ) . toBe ( 'New Title' ) ;
70+ expect ( map . get ( 'title' ) ?. toString ( ) ) . toBe ( 'New Title' ) ;
6971 } ) ;
7072
7173 it ( 'does not sync function values' , ( ) => {
@@ -85,7 +87,9 @@ describe( 'crdt', () => {
8587
8688 applyPostChangesToCRDTDoc ( doc , changes , mockPostType ) ;
8789
88- expect ( map . get ( 'title' ) ) . toBe ( 'Raw Title' ) ;
90+ const title = map . get ( 'title' ) ;
91+ expect ( title ) . toBeInstanceOf ( Y . Text ) ;
92+ expect ( title ?. toString ( ) ) . toBe ( 'Raw Title' ) ;
8993 } ) ;
9094
9195 it ( 'skips "Auto Draft" template title when no current value exists' , ( ) => {
@@ -95,7 +99,9 @@ describe( 'crdt', () => {
9599
96100 applyPostChangesToCRDTDoc ( doc , changes , mockPostType ) ;
97101
98- expect ( map . get ( 'title' ) ) . toBe ( '' ) ;
102+ const title = map . get ( 'title' ) ;
103+ expect ( title ) . toBeInstanceOf ( Y . Text ) ;
104+ expect ( title ?. toString ( ) ) . toBe ( '' ) ;
99105 } ) ;
100106
101107 it ( 'handles excerpt with RenderedText format' , ( ) => {
@@ -109,7 +115,9 @@ describe( 'crdt', () => {
109115
110116 applyPostChangesToCRDTDoc ( doc , changes , mockPostType ) ;
111117
112- expect ( map . get ( 'excerpt' ) ) . toBe ( 'Raw excerpt' ) ;
118+ const excerpt = map . get ( 'excerpt' ) ;
119+ expect ( excerpt ) . toBeInstanceOf ( Y . Text ) ;
120+ expect ( excerpt ?. toString ( ) ) . toBe ( 'Raw excerpt' ) ;
113121 } ) ;
114122
115123 it ( 'does not sync empty slug' , ( ) => {
@@ -178,14 +186,16 @@ describe( 'crdt', () => {
178186 expect ( map . get ( 'blocks' ) ) . toBeUndefined ( ) ;
179187 } ) ;
180188
181- it ( 'syncs content as a string ' , ( ) => {
189+ it ( 'syncs content as Y.Text ' , ( ) => {
182190 const changes = {
183191 content : 'Hello, world!' ,
184192 } as PostChanges ;
185193
186194 applyPostChangesToCRDTDoc ( doc , changes , mockPostType ) ;
187195
188- expect ( map . get ( 'content' ) ) . toBe ( 'Hello, world!' ) ;
196+ const content = map . get ( 'content' ) ;
197+ expect ( content ) . toBeInstanceOf ( Y . Text ) ;
198+ expect ( content ?. toString ( ) ) . toBe ( 'Hello, world!' ) ;
189199 } ) ;
190200
191201 it ( 'syncs content with RenderedText format' , ( ) => {
@@ -198,11 +208,73 @@ describe( 'crdt', () => {
198208
199209 applyPostChangesToCRDTDoc ( doc , changes , mockPostType ) ;
200210
201- expect ( map . get ( 'content' ) ) . toBe (
211+ const content = map . get ( 'content' ) ;
212+ expect ( content ) . toBeInstanceOf ( Y . Text ) ;
213+ expect ( content ?. toString ( ) ) . toBe (
202214 '<!-- wp:paragraph --><p>Hello</p><!-- /wp:paragraph -->'
203215 ) ;
204216 } ) ;
205217
218+ it ( 'updates existing Y.Text title in place via mergeRichTextUpdate' , ( ) => {
219+ // First apply to create the Y.Text.
220+ applyPostChangesToCRDTDoc (
221+ doc ,
222+ { title : 'Old Title' } as PostChanges ,
223+ mockPostType
224+ ) ;
225+ const titleRef = map . get ( 'title' ) ;
226+
227+ // Apply again — should update in place, not replace.
228+ applyPostChangesToCRDTDoc (
229+ doc ,
230+ { title : 'New Title' } as PostChanges ,
231+ mockPostType
232+ ) ;
233+
234+ expect ( map . get ( 'title' ) ) . toBe ( titleRef ) ;
235+ expect ( map . get ( 'title' ) ?. toString ( ) ) . toBe ( 'New Title' ) ;
236+ } ) ;
237+
238+ it ( 'updates existing Y.Text content in place via mergeRichTextUpdate' , ( ) => {
239+ // First apply to create the Y.Text.
240+ applyPostChangesToCRDTDoc (
241+ doc ,
242+ { content : 'Old content' } as PostChanges ,
243+ mockPostType
244+ ) ;
245+ const contentRef = map . get ( 'content' ) ;
246+
247+ // Apply again — should update in place, not replace.
248+ applyPostChangesToCRDTDoc (
249+ doc ,
250+ { content : 'New content' } as PostChanges ,
251+ mockPostType
252+ ) ;
253+
254+ expect ( map . get ( 'content' ) ) . toBe ( contentRef ) ;
255+ expect ( map . get ( 'content' ) ?. toString ( ) ) . toBe ( 'New content' ) ;
256+ } ) ;
257+
258+ it ( 'updates existing Y.Text excerpt in place via mergeRichTextUpdate' , ( ) => {
259+ // First apply to create the Y.Text.
260+ applyPostChangesToCRDTDoc (
261+ doc ,
262+ { excerpt : 'Old excerpt' } as PostChanges ,
263+ mockPostType
264+ ) ;
265+ const excerptRef = map . get ( 'excerpt' ) ;
266+
267+ // Apply again — should update in place, not replace.
268+ applyPostChangesToCRDTDoc (
269+ doc ,
270+ { excerpt : 'New excerpt' } as PostChanges ,
271+ mockPostType
272+ ) ;
273+
274+ expect ( map . get ( 'excerpt' ) ) . toBe ( excerptRef ) ;
275+ expect ( map . get ( 'excerpt' ) ?. toString ( ) ) . toBe ( 'New excerpt' ) ;
276+ } ) ;
277+
206278 it ( 'syncs meta fields' , ( ) => {
207279 const changes = {
208280 meta : {
@@ -266,7 +338,7 @@ describe( 'crdt', () => {
266338
267339 beforeEach ( ( ) => {
268340 map = getRootMap < YPostRecord > ( doc , CRDT_RECORD_MAP_KEY ) ;
269- map . set ( 'title' , 'CRDT Title' ) ;
341+ map . set ( 'title' , new Y . Text ( 'CRDT Title' ) ) ;
270342 map . set ( 'status' , 'draft' ) ;
271343 map . set ( 'date' , '2025-01-01' ) ;
272344 } ) ;
@@ -287,7 +359,7 @@ describe( 'crdt', () => {
287359 } ) ;
288360
289361 it ( 'filters out disallowed properties' , ( ) => {
290- map . set ( 'title' , 'Test title' ) ;
362+ map . set ( 'title' , new Y . Text ( 'Test title' ) ) ;
291363 map . set ( 'unsyncedProp' , 'value' ) ;
292364
293365 const editedRecord = { } as Post ;
@@ -416,7 +488,7 @@ describe( 'crdt', () => {
416488 } ) ;
417489
418490 it ( 'detects content changes from string value' , ( ) => {
419- map . set ( 'content' , 'New content' ) ;
491+ map . set ( 'content' , new Y . Text ( 'New content' ) ) ;
420492
421493 const editedRecord = {
422494 content : 'Old content' ,
@@ -432,7 +504,7 @@ describe( 'crdt', () => {
432504 } ) ;
433505
434506 it ( 'detects content changes from RenderedText value' , ( ) => {
435- map . set ( 'content' , 'New content' ) ;
507+ map . set ( 'content' , new Y . Text ( 'New content' ) ) ;
436508
437509 const editedRecord = {
438510 content : { raw : 'Old content' , rendered : 'Old content' } ,
@@ -448,7 +520,7 @@ describe( 'crdt', () => {
448520 } ) ;
449521
450522 it ( 'excludes content when unchanged from RenderedText value' , ( ) => {
451- map . set ( 'content' , 'Same content' ) ;
523+ map . set ( 'content' , new Y . Text ( 'Same content' ) ) ;
452524
453525 const editedRecord = {
454526 content : { raw : 'Same content' , rendered : 'Same content' } ,
0 commit comments