-3

what i am wondering if i can do :

var o={

   __call : function(methodname,arguments){
      alert(methodname);
   }

};

o.hello();  <-alerts 'hello'

similar to php's magic method __call

what i essentially want to do is call functions which will exist but are unknown when the code is first run, i could do so via something like

function fn(){
   var s='mod';
   var o=mod;
   var n=arguments.length;
   for(var i=0;i<n;i++){
      var name=arguments[i];
      s+='.'+name;
      if(!o[name])return ()=>s+' not found';
      o=o[name];
   }
   return o;
}

var mod={
   square:{
      area:r=>r*r
   }
};

var a=fn('square','area')(5);     console.log(a);
var a=fn('circle','area')(6);     console.log(a);

but I would prefer to use

var a=mod.square.area(5);         console.log(a);
var a=mod.circle.area(6);         console.log(a);
  • it doesnt appear to work as i want, although im working on it, the getters essentially need to know whether they are being invoked as properties or methods, an aspect of php's __call method, if they knew that, they could return new proxy's or a function to collect arguments – matt richards Dec 26 '20 at 11:32

1 Answers1

0

its rough and ready, but here is something that sort of works

var mod=newproxy();
    
    
mod.callme.first$('hello','world');         //?  mod.callme.first.fn('hello','world');
    
mod.difcontext.hello='world';               //?  mod.difcontext.hello.prop='world';
    
mod.difcontext.start=['hello','world'];     
    
mod.difcontext.cat_;                        //?  mod.difcontext.cat.prop;
    
   
function newproxy(main){
          
    main=main||{};
    return proxy(main);
          
    function getter(target,name,receiver,lname){
    
        lname+=lname?'.'+name:name;
        var c=name[name.length-1];
        if(c==='$'){
            lname=lname.slice(0,-1);
            return function(){
                console.log('fn : ',lname,arguments);
            };
        }
        if(c==='_'){
            lname=lname.slice(0,-1);
            console.log('rd : ',lname);
            return;
        }
        return proxy(target,lname);
          
    }//getter
          
    function setter(obj,prop,newval,lname){
          
        lname+=lname?'.'+prop:prop;
        console.log('wt : ',lname,newval);
                
          
    }//setter
          
    function proxy(target,lname){
          
      lname=lname||'';
      var p=new Proxy(target,{
        get:(target,name,receiver)=>{return getter(target,name,receiver,lname);},
        set:(obj,prop,newval)=>{return setter(obj,prop,newval,lname);}
      });
                
      return p;
          
    }//proxy
          
}//newproxy
    

uses a naming convention

$ denotes an ending function, ( could of ended with .fn )

_ denotes reading variable, ( could of ended with .prop )

the setter could be used to invoke a function, but its not conventional

for the time being i decided to go with

mod('difcontext.callme.first',['hello','world'],callback);

if the getters intrinsically had some knowledge of how they were being invoked ...

var mod=new Proxy({},{
      get:(target,name,receiver)=>{return function(){alert(name)}}
});
          
mod.hello();

I was referred to another question, i posted a more complete solution there :

Is there an equivalent of the noSuchMethod feature for properties, or a way to implement it in JS?

  • i added a more complete answer [link](https://stackoverflow.com/questions/2266789/is-there-an-equivalent-of-the-nosuchmethod-feature-for-properties-or-a-way/65461782#65461782) – matt richards Dec 27 '20 at 00:05