Skip to content

data function in computed turns into POJO {_r_unbound: func} #3441

@ppena-LiveData

Description

@ppena-LiveData

If a function is defined in Ractive data, and that function is called via a computed, then calling ractive.get() will incorrectly have a plain-old-javascript-object, like {_r_unbound: func}, for that function's keypath, when it should have the function (bound to the Ractive). I found it because I had one Ractive linked to another, and the template of the second Ractive got multiple things from the first Ractive, like this:

<script src="https://cdn.jsdelivr.net/npm/ractive"></script>
<div id="target"></div>
<script>
    const ractiveSource = Ractive({
        data: {
            testFunc: function (val) {
                // not called via a computed, so ractiveDest won't have a problem using it
                return `"testFunc: val=${val}"`;
            },
            testFuncInComputed: function (val) {
                return `"testFuncInComputed: val=${val}"`;
            }
        },
        computed: {
            computedVal: function () {
                this.get('testFuncInComputed')('sourceTestVal');
            }
        }
    });
    const ractiveDest = Ractive({
        target: '#target',
        template: `
            testFunc(...)={{ractiveSource.testFunc("func call works")}}
            testFuncInComputed(...)={{ractiveSource.testFuncInComputed("func call does not work")}}`,
        data: {},
        onconfig: function () {
            this.link('', 'ractiveSource', {ractive: ractiveSource});
        }
    });
</script>

But a much simpler reproduction is just to call .get() more than once:

<script src="https://cdn.jsdelivr.net/npm/ractive"></script>
<div id="target"></div>
<script>
    const ractiveSource = Ractive({
        data: {
            testFuncInComputed: function (val) {
                return `"testFuncInComputed: val=${val}"`;
            }
        },
        computed: {
            computedVal: function () {
                this.get('testFuncInComputed')('sourceTestVal');
            }
        }
    });
    // this get() will call computedVal(), and "testFuncInComputed" will get added to childByKey
    const result1 = ractiveSource.get();
    console.log(result1.testFuncInComputed('yay'));
    // this get() will now call child.getVirtual(), which converts the bound func to just a POJO: {_r_unbound: func}
    const result2 = ractiveSource.get();
    console.log(result2.testFuncInComputed('sob'));
</script>

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions