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

Error-Trace modification/addition annotations broken #291

Open
Tracked by #342
lemmy opened this issue May 21, 2023 · 7 comments
Open
Tracked by #342

Error-Trace modification/addition annotations broken #291

lemmy opened this issue May 21, 2023 · 7 comments
Labels
bug Something isn't working

Comments

@lemmy
Copy link
Member

lemmy commented May 21, 2023

The screenshot below shows an action where a node sends a RequestVote message. However, the error-trace viewer incorrectly annotates an existing AppendEntries messages as added, whereas the new RequestVote message is annotated as modified.

Screenshot 2023-05-21 at 11 28 40 AM

My guess is that the error-trace viewer compares the two sets syntactically while assuming some stable order. Related to #261

@lemmy lemmy added the bug Something isn't working label May 21, 2023
@lemmy
Copy link
Member Author

lemmy commented May 21, 2023

Perhaps it's TLC that should provide annotations in its textual error trace to free IDEs from parsing and evaluating values.

@lemmy
Copy link
Member Author

lemmy commented Sep 6, 2023

@afonsonf Do you have plans to re-add the functionality that shows deleted set elements in the error trace view?

if (value.deletedItems) {
value.deletedItems.forEach((dit) => displayValue(elSubList, dit, showUnmodified));
}

@lemmy
Copy link
Member Author

lemmy commented Sep 6, 2023

Incomplete attempt to bring the rest of the Toolbox diffing over:

diff --git a/src/model/check.ts b/src/model/check.ts
index 79c015a..bf60526 100644
--- a/src/model/check.ts
+++ b/src/model/check.ts
@@ -178,6 +178,14 @@ export class Value {
     format(indent: string): string {
         return `${this.str}`;
     }
+
+    diff(other: Value): boolean {
+        if (this.str !== other.str) {
+            other.setModified();
+            return true;
+        }
+        return false;
+    }
 }
 
 /**
@@ -257,6 +265,63 @@ export abstract class CollectionValue extends Value {
     formatKey(indent: string, value: Value): string {
         return `${indent}${value.key}: `;
     }
+
+    // diff(other: Value): boolean {
+    //     return false;
+    // }
+    setElementArrayDiffInfo(
+        t: CollectionValue,
+        o: CollectionValue,
+        firstElts: Value[],
+        firstLHKeys: ValueKey[],
+        secondElts: Value[],
+        secondLHKeys: ValueKey[]
+    ): void {
+        const deletedItems = [];
+        for (let i = 0; i < firstElts.length; i++) {
+            let notfound = true;
+            let j = 0;
+            while (notfound && j < secondElts.length) {
+                if (firstLHKeys[i] === secondLHKeys[j]) {
+                    notfound = false;
+                    const first = firstElts[i];
+                    const second = secondElts[j];
+                    if (first.str !== second.str) {
+                        secondElts[i].setModified();
+                        second.setModified();
+                        if (first.constructor === second.constructor) {
+                            // Only diff objects of identical types
+                            first.diff(second);
+                        }
+                    }
+                }
+                j++;
+            }
+            if (notfound) {
+                deletedItems.push(firstElts[i]);
+            }
+        }
+        if (deletedItems.length > 0) {
+            o.addDeletedItems(deletedItems);
+            o.setModified();
+        }
+
+        for (let i = 0; i < secondElts.length; i++) {
+            const s = secondElts[i].str;
+            let notfound = true;
+            let j = 0;
+            while (notfound && j < firstElts.length) {
+                const f = firstElts[j].str;
+                if (f === s) {
+                    notfound = false;
+                }
+                j++;
+            }
+            if (notfound) {
+                secondElts[i].setAdded();
+            }
+        }
+    }
 }
 
 /**
@@ -381,6 +446,33 @@ export class StructureValue extends CollectionValue {
     formatKey(indent: string, value: Value): string {
         return `${indent}${value.key}` + this.itemSep;
     }
+
+    diff(other: Value): boolean {
+        /*
+         * RECORDS We mark a record element as added or deleted if its label
+         * does not appear in one of the elements of the other record. We
+         * mark the element as changed, and call setInnerDiffInfo on the
+         * elements' values if elements with the same label but different values
+         * appear in the two records.
+         */
+        if (!(other instanceof StructureValue)) {
+            return false;
+        }
+
+        const secondElts: StructureValue = (other as StructureValue);
+
+        const firstLHStrings: ValueKey[] = [];
+        for (let i = 0; i < this.items.length; i++) {
+            firstLHStrings[i] = this.items[i].key;
+        }
+        const secondLHStrings: ValueKey[] = [];
+        for (let i = 0; i < other.items.length; i++) {
+            secondLHStrings[i] = secondElts.items[i].key;
+        }
+
+        this.setElementArrayDiffInfo(this, other, this.items, firstLHStrings, secondElts.items, secondLHStrings);
+        return true;
+    }
 }
 
 /**
@@ -538,6 +630,15 @@ export function getStatusName(status: CheckStatus): string {
 /**
  * Recursively finds and marks all the changes between two collections.
  */
+export function findChangesOff(prev: CollectionValue, state: CollectionValue): boolean {
+    let i = 0;
+    while (i < prev.items.length && i < state.items.length) {
+        prev.items[i].diff(state.items[i]);
+        i++;
+    }
+    return true;
+}
+
 export function findChanges(prev: CollectionValue, state: CollectionValue): boolean {
     let pi = 0;
     let si = 0;

@lemmy
Copy link
Member Author

lemmy commented Sep 6, 2023

@afonsonf Do you have plans to re-add the functionality that shows deleted set elements in the error trace view?

if (value.deletedItems) {
value.deletedItems.forEach((dit) => displayValue(elSubList, dit, showUnmodified));
}

A set will only be marked modified M until the webview shows deleted set elements again.

image

@afonsonf
Copy link
Collaborator

afonsonf commented Sep 6, 2023

@afonsonf Do you have plans to re-add the functionality that shows deleted set elements in the error trace view?

if (value.deletedItems) {
value.deletedItems.forEach((dit) => displayValue(elSubList, dit, showUnmodified));
}

Hi, true I missed that part in the migration of the ui, I will add it back

@FedericoPonzi
Copy link
Collaborator

FedericoPonzi commented Oct 7, 2024

An MRE would be very helpful here - I tried and failed to reproduce it.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Something isn't working
Development

No branches or pull requests

3 participants