Преглед изворни кода

[project-history] fix diff view on file revert (#20769)

GitOrigin-RevId: 6c95dab9328ecab636272ad507505f5342ec8709
Domagoj Kriskovic пре 1 година
родитељ
комит
0998cc04df

+ 8 - 6
services/project-history/app/js/ChunkTranslator.js

@@ -49,13 +49,14 @@ export function convertToDiffUpdates(
   let file = null
   for (const change of chunk.chunk.history.changes) {
     // Because we're referencing by pathname, which can change, we
-    // want to get the first file in the range fromVersion:toVersion
+    // want to get the last file in the range fromVersion:toVersion
     // that has the pathname we want. Note that this might not exist yet
-    // at fromVersion, so we'll just settle for the first one we find
+    // at fromVersion, so we'll just settle for the last existing one we find
     // after that.
     if (fromVersion <= version && version <= toVersion) {
-      if (file == null) {
-        file = builder.getFile(pathname)
+      const currentFile = builder.getFile(pathname)
+      if (currentFile) {
+        file = currentFile
       }
     }
 
@@ -70,8 +71,9 @@ export function convertToDiffUpdates(
   // Versions act as fence posts, with updates taking us from one to another,
   // so we also need to check after the final update, when we're at the last version.
   if (fromVersion <= version && version <= toVersion) {
-    if (file == null) {
-      file = builder.getFile(pathname)
+    const currentFile = builder.getFile(pathname)
+    if (currentFile) {
+      file = currentFile
     }
   }
 

+ 138 - 0
services/project-history/test/unit/js/ChunkTranslator/ChunkTranslatorTests.js

@@ -72,6 +72,51 @@ describe('ChunkTranslator', function () {
                 timestamp: this.date.toISOString(),
                 authors: [this.author1.id],
               },
+              {
+                origin: {
+                  kind: 'file-restore',
+                  version: 1,
+                  path: 'main.tex',
+                  timestamp: this.date.toISOString(),
+                },
+                operations: [
+                  {
+                    pathname: 'main.tex',
+                    newPathname: '',
+                  },
+                ],
+                timestamp: this.date.toISOString(),
+                authors: [this.author1.id],
+              },
+              {
+                origin: {
+                  kind: 'file-restore',
+                  version: 1,
+                  path: 'main.tex',
+                  timestamp: this.date.toISOString(),
+                },
+                operations: [
+                  {
+                    pathname: 'main.tex',
+                    file: {
+                      hash: this.fileHash,
+                      stringLength: 42,
+                    },
+                  },
+                ],
+                timestamp: this.date.toISOString(),
+                authors: [this.author1.id],
+              },
+              {
+                operations: [
+                  {
+                    pathname: 'main.tex',
+                    newPathname: 'main2.tex',
+                  },
+                ],
+                timestamp: this.date.toISOString(),
+                authors: [this.author1.id],
+              },
             ],
           },
         },
@@ -162,6 +207,38 @@ describe('ChunkTranslator', function () {
           }
         )
       })
+
+      it('should return the correct initial text in case of file restore', function (done) {
+        this.ChunkTranslator.convertToDiffUpdates(
+          this.projectId,
+          this.chunk,
+          'main.tex',
+          3,
+          5,
+          (error, param) => {
+            const { initialContent } = param
+            expect(error).to.be.null
+            expect(initialContent).to.equal('Hello world, this is a test')
+            done()
+          }
+        )
+      })
+
+      it('should still find original file in case it was renamed', function (done) {
+        this.ChunkTranslator.convertToDiffUpdates(
+          this.projectId,
+          this.chunk,
+          'main.tex',
+          5,
+          6,
+          (error, param) => {
+            const { initialContent } = param
+            expect(error).to.be.null
+            expect(initialContent).to.equal('Hello world, this is a test')
+            done()
+          }
+        )
+      })
     })
 
     describe('convertToSummarizedUpdates', function () {
@@ -200,6 +277,67 @@ describe('ChunkTranslator', function () {
               },
               v: 2,
             },
+            {
+              pathnames: [],
+              project_ops: [
+                {
+                  remove: {
+                    pathname: 'main.tex',
+                  },
+                },
+              ],
+              meta: {
+                users: [this.author1.id],
+                start_ts: this.date.getTime(),
+                end_ts: this.date.getTime(),
+                origin: {
+                  kind: 'file-restore',
+                  version: 1,
+                  path: 'main.tex',
+                  timestamp: this.date.toISOString(),
+                },
+              },
+              v: 3,
+            },
+            {
+              pathnames: [],
+              project_ops: [
+                {
+                  add: {
+                    pathname: 'main.tex',
+                  },
+                },
+              ],
+              meta: {
+                users: [this.author1.id],
+                start_ts: this.date.getTime(),
+                end_ts: this.date.getTime(),
+                origin: {
+                  kind: 'file-restore',
+                  version: 1,
+                  path: 'main.tex',
+                  timestamp: this.date.toISOString(),
+                },
+              },
+              v: 4,
+            },
+            {
+              pathnames: [],
+              project_ops: [
+                {
+                  rename: {
+                    pathname: 'main.tex',
+                    newPathname: 'main2.tex',
+                  },
+                },
+              ],
+              meta: {
+                users: [this.author1.id],
+                start_ts: this.date.getTime(),
+                end_ts: this.date.getTime(),
+              },
+              v: 5,
+            },
           ])
           done()
         }