• Recent
  • Tags
  • Unsolved
  • Solved
  • MagicMirror² Repository
  • Documentation
  • 3rd-Party-Modules
  • Donate
  • Discord
  • Register
  • Login
MagicMirror Forum
  • Recent
  • Tags
  • Unsolved
  • Solved
  • MagicMirror² Repository
  • Documentation
  • 3rd-Party-Modules
  • Donate
  • Discord
  • Register
  • Login
A New Chapter for MagicMirror: The Community Takes the Lead
Read the statement by Michael Teeuw here.

How to send a function as payload of socket notification?

Scheduled Pinned Locked Moved Development
socket notificationnotificationspayloadnodehelper
5 Posts 3 Posters 912 Views 3 Watching
Loading More Posts
  • Oldest to Newest
  • Newest to Oldest
  • Most Votes
Reply
  • Reply as topic
Log in to reply
This topic has been deleted. Only users with topic management privileges can see it.
  • N Offline
    ngnijland
    last edited by May 18, 2020, 8:21 PM

    Hello,

    When I receive a socket notification in my node_helper.js file I want to sent a socket notification with an object containing a function as value of one of its keys. Like this:

    const NodeHelper = require('node_helper');
    const someFunction = require('./someFunction');
    
    module.exports = NodeHelper.create({
      start: function () {
        console.log('Start node helper');
      },
    
      socketNotificationReceived: function (notification) {
        if (notification === 'FOO') {
          this.sendSocketNotification('FOO', { bar: someFunction });
        }
      },
    });
    

    However, when I receive this notification inside my main module file the function is not present in the payload:

      socketNotificationReceived: function (notification, payload) {
        if (notification === 'FOO') {
          console.log(payload.bar); // This logs 'undefined'
        }
      },
    

    Any other values (object, arrays, etc) I pass in the payload are received correctly.

    Does somebody know why the function I pass with the payload is undefined when I receive the socket notification in my main module file?

    S ? 2 Replies Last reply May 18, 2020, 9:30 PM Reply Quote 0
    • S Offline
      sdetweil @ngnijland
      last edited by May 18, 2020, 9:30 PM

      @ngnijland I think u have to send the entire function in the packet. It can’t contain the address of anything on the other side

      Sam

      How to add modules

      learning how to use browser developers window for css changes

      1 Reply Last reply Reply Quote 0
      • N Offline
        ngnijland
        last edited by May 19, 2020, 7:55 AM

        @sdetweil thanks for your reply!

        I don’t think I completely understand you. What do you mean with “send the entire function”? Do you mean I can’t import a reference? And should write out the function in the node_helper.js file?

        1 Reply Last reply Reply Quote 0
        • ? Offline
          A Former User @ngnijland
          last edited by A Former User May 19, 2020, 9:15 AM May 19, 2020, 9:06 AM

          @ngnijland
          Impossible in the current MM legacy structure.
          those processes are separated and can not share function.

          2 reasons;

          • The function itself cannot be transferred through socket (JSON doesn’t allow it)
          • If the function depends on some dependencies, it will lose them.

          Anyway, if the function itself is somehow simple and has no dependency, there could be some trick.

          var originalPayload = {
            "something": "hello, world",
            "someFunc" : (value) => {
              console.log(value)
              return value
            }
          }
          
          originalPayload.someFunc("Original Execution.")
          
          
          let replacer = (key, value) => {
            if (typeof value == "function") {
              return "__FUNC__" + value.toString()
            }
            return value
          }
          
          // Encode function in payload object
          var encodedPayload = JSON.stringify(originalPayload, replacer, 2)
          console.log("----")
          console.log(encodedPayload)
          console.log("----")
          // encodedPayload will have;
          // {
          //   "something": "hello, world",
          //   "someFunc": "__FUNC__(value) => {\n console.log(value)\n return value\n  }"
          // }
          
          // Now you can transfer this string as payload of socketNotification.
          // this.sendSocketNotification("SOME_EVENT", encodedPayload)
          // ...
          
          // Let's assume you got a payload through socketNotification
          var receivedPayload = encodedPayload
          
          let reviver = (key, value) => {
            if (typeof value === 'string' && value.indexOf('__FUNC__') === 0) {
              value = value.slice(8)
              let functionTemplate = `(${value})`
              return eval(functionTemplate)
            }
            return value
          }
          
          var revivedPayload = JSON.parse(receivedPayload, reviver)
          revivedPayload.someFunc("Function is revived.")
          

          CAUTION
          If the function requires dependencies (node modules, injected Object, references out of scope, …) those will be lost and it will cause an error.

          N 1 Reply Last reply May 19, 2020, 9:53 AM Reply Quote 0
          • N Offline
            ngnijland @Guest
            last edited by ngnijland May 19, 2020, 10:21 AM May 19, 2020, 9:53 AM

            @Sean
            Ah ofcourse, thanks for the explanation!

            My function does not have dependencies. I’ll use good old eval to fix this!

            My use case is that I need to use a different function based on the language setting of the mirror. These functions live in a separate folder and I import them in the node_helper.js file (together with some other arrays and objects I need based on language). For now I’ll use this solution, maybe in the future I build in a build step in my module so I can import the files directly into my main module file.

            https://github.com/ngnijland/MMM-text-clock/pull/2

            1 Reply Last reply Reply Quote 0
            • 1 / 1
            1 / 1
            • First post
              1/5
              Last post
            Enjoying MagicMirror? Please consider a donation!
            MagicMirror created by Michael Teeuw.
            Forum managed by Sam, technical setup by Karsten.
            This forum is using NodeBB as its core | Contributors
            Contact | Privacy Policy