Inexplicably broken project (sim error: failed cast on undefined)

A project I’m working on inexplicably crashes when I run it. The cause of the error seems to be another one of my extensions which i’m using in my project. However, when I copied my entire code into that extension’s project (in a separate file) and ran the exact same code it worked perfectly. I have no idea why this is happening. Please help (@richard? @AlexK?)

You can get the project at https://github.com/sargedev/betterarrays
Didn’t want to leak it but oh well, most people know what I’ve been working on anyway.

This is a project I’ve been working on extensively (no pun intended) for the past few weeks and now that I’m this close to release it breaks, so all help is appreciated.

6 Likes

@Sarge this is being caused by a quirk in how we run user code.

When MakeCode compiles a project, it always makes sure that main.ts is last to execute. If you declare a variable inside main.ts and then reference it in a function that runs before main.ts, the variable will be undefined. In this case, that variable is the NON_INTEGER_VALUE format string you declare at the top of your file.

Luckily, the fix is super easy. Add another file named something other than main.ts to your project and move everything into that instead. Then just leave main.ts blank.

2 Likes

Also worth noting that main.ts is the only special file that works this way. You can control the order in which other files are processed by rearranging them inside the files array in pxt.json.

Still, you don’t want to delete main.ts entirely since that might cause some bugs (or it might be fine, but I’m willing to bet there are some parts of makecode that assume a main.ts file is always present).

3 Likes

@richard So, I fixed that, and development went smoothly, until I ran into another wonky issue while formatting. I thought it was just a bug with my extension, so just like last time I all the necessary code there, and would you know it - it worked perfectly.

Never have I been this mad my code actually works :joy:

Anyway, not only does it work in another project, pasting the code at the bottom of api.ts (which is now my main file) also yields the intended results.

In testFill (test.ts), this snippet of code executes

arrays.fill(["a", "b", "c"], "a", 4, 0);

which is supposed to throw Index (4) must be in list range (0, 3)
It however throws Index (2) must be in list range (0, 2) (wrong values)

Like I said, in the api file it throws it with the correct values. I am stumped, why could this be happening. Any help is appreciated

2 Likes

well i can tell you that one of your tests is interfering with the other, though I haven’t debugged why. it’s one of the tests from the toSwapped test function.

you can reproduce the exception with this:

new tests.AssertRaises(
    () => arrays.toSwapped(["a", "b"], 2, 0),
    "Index (2) must be in list range (0, 2)"
)
new tests.AssertRaises(
    () => arrays.fill(["a", "b", "c"], "a", 0, 4),
    "Index (4) must be in list range (0, 3)"
)

only reproduces if the toSwapped test case runs before the other

1 Like

alright, i went ahead and looked into it. pretty sure the error is in your text formatting extension. in this method:

        format(params: string[]): string {
            let index = 0;
            for (let i = 0; i < this.parsed.length; i++) {
                if (this.parsed[i] === null) {
                    if (index >= params.length) throw `Expected ${this.paramNum} param(s) (got ${params.length})`;
                    this.parsed[i] = params[index];
                    index += 1;
                }
            }
            return this.parsed.join("");
        }

not sure why you’re modifying this.parsed but i’m betting that the state is getting carried over between tests. try building up a string as you go instead of modifying the array and calling join

2 Likes

Yup, figured that out just a moment ago! Don’t know what the thought process behind that was, I probably wrote that at 2AM or something close :sweat_smile:
Fixed now by just adding a result variable which builds up over time.

Thank you very much, you’ve helped a ton in diagnosing issues (both makecode, and my code related, lol)! Also, I should probably start commenting stuff. No idea how you managed to find your way in that mess

5 Likes