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

[JS] casting a .NET Dictionary to ICollection JS should not use .push #3914

Open
goswinr opened this issue Oct 1, 2024 · 1 comment
Open

Comments

@goswinr
Copy link
Contributor

goswinr commented Oct 1, 2024

Casting a .NET Dictionary to an ICollection emits .push for .Add, but a JS Map has no .push member.

open System.Collections.Generic

let dic = Dictionary<int,string>()  

let coll = dic :> ICollection<KeyValuePair<_,_>>    

let kv = KeyValuePair(1,"a")

coll.Add(kv) // emits .push on a JS Map, but Map has no .push member

REPL

image

fable 4.21

@MangelMaxime
Copy link
Member

It seems like this is not has easy to fix as I though.

JS Map doesn't seem to have a Add equivalent, it only have a set prototype for adding / updating an element.

I think the issue comes from the fact that Dictionary<int, string>() is represented using JS.Map instead of a class / wrap we control.

Because of that, when calling:

open System.Collections.Generic

let dic = Dictionary<int,string>()  

dic.Add(2, "b")

Then Fable is able to replace the Add call with addToDict

import { addToDict } from "fable-library-js/MapUtil.js";

export const dic = new Map([]);

addToDict(dic, 2, "b");

But when doing the cast to ICollection Fable can't do the replacement, because the concrete type of ICollection can be anything. I think the path to fix this issue is to rework how Dictionary<'Key, 'Value> works and instead of using JS.Map directly, we should extends it:

 class ExtendedMap extends Map {
    constructor() {
        super();
    }
    
   add(key, value) { // This will replace the call to `addToDict`
	// ...
   }
 }

In theory, it means that the new Map class will keep fulfilling the following statement from Fable

CleanShot 2024-10-02 at 09 10 09

If people compare the constructor there will be issues, but the existing API should keep working.

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

No branches or pull requests

2 participants