GithubHelp home page GithubHelp logo

jlongster / js-csp Goto Github PK

View Code? Open in Web Editor NEW

This project forked from js-csp/js-csp

282.0 282.0 9.0 453 KB

CSP channels for Javascript (like Clojurescript's core.async, or Go) THIS IS AN UPSTREAM FORK

JavaScript 100.00%

js-csp's Issues

For your Taming Async article...

You might like to consider using async-csp, which uses async/await instead of generators. I think it's much cleaner! I don't think js-csp is compatible with async/await, as it doesn't seem to return promises (or did I miss it?).

alts does receive "null" from channels

A channel, created with csp.go(function*().... will not yield and always return null in csp.alts.

var t = csp.go(function*() {
    while(true) {
      var action = yield csp.take(csp.timeout(2000));
      return "test"
    };
});

A channel like "t" will not work with alts. alts will not wait for a new value from t - it will receive "null" immediatly and it will run a loop that freezes the browser.

csp promises and async react components

I used js-csp in my last project to replace promises (ajax) and frp (search logic).
With webpack + bundle-loader i am able to load components only when needed. webpack makes this very easy.

<AsyncComp data={dataCh} bundle={require('bundle?lazy!./file.js')};

This component will load the data and the bundle only when needed. Complete example here.

If more components are using data from dataCh or if the same component gets re-mounted to the DOM, the csp solution will fail, because the value will be taken and the AsyncComponent will wait for this never-arriving data.
At this point, csp-promises would be a nice solution.

I ended up loading all data to the immutable datastructure.
I am not happy with this solution because i think that loaded data should not be part of the app-state (in most cases). But i was able to utilize immutable-cursors.

I think that a csp-promise solution would be a competitor for immutable-cursors.
If a channel would return always the last value on every take, and if you could renew the resolved promise value (unlike real promises that could only be resolved once) - would this make immutable-cursors obsolete?

csp.CLOSED shouldn't be `null`

Right now the value is null, but it seems like this is a troublesome value for false positives. I could quite easily think about sending a null value through the channel, but the receiving side might errantly consider that a close signal.

I think csp.CLOSED should be an empty { } object. That way val === csp.CLOSED type checks would be protected from such false positives.

It wouldn't be a falsy value anymore, which could possibly be surprising to some. Thus, if (!val) .. checks would "break", but as mentioned, I think those checks are inherently flawed already because of the false positives issue. Indeed, in your documentation, you already acknowledge that === csp.CLOSED checks are more appropriate anyway.

<- macro for put has the channel and value reversed

just fyi I was playing with the macros and I'm pretty confident (I think?) there's a typo in that:

binaryop (<-) 50 right {
  macro {
    case { $ctx $value $channel } => {
      letstx $csp = [makeIdent('csp', #{$ctx})];
      return #{ yield $csp.put($channel, $value) }
    }
  }
}

has the order of the $value and $channel reversed I believe it was meant to be:

binaryop (<-) 50 right {
  macro {
    case { $ctx $channel $value } => {
      letstx $csp = [makeIdent('csp', #{$ctx})];
      return #{ yield $csp.put($channel, $value) }
    }
  }
}

After that little change I was successful in making this little example work btw:

var { chan, timeout } = csp = require('js-csp');

var ch = chan();

go({
  var val;
  while((val = <- ch) !== csp.CLOSED) {
    console.log(val);
  }
});

foo = () => go({ return 3; });

go({
  ch <- 1;
  var t = <- timeout(1000);
  ch <- 2;
  t = <- timeout(1000);
  ch <- (<- foo());
  ch.close();
});

happy to do a pull request btw wasn't sure I should for something so small I'll watch for comments in case you want me to

Your fork fails the tests

I get plenty of errors trying to make your fork, as compared to the original github repo.

npm install
./node_modules/mocha/bin/mocha --harmony --ui exports --reporter spec
  Fixed buffer
    ✓ should work 

  Dropping buffer
    ✓ should work 

  Sliding buffer
    ✓ should work 

  put
    that is immediate
      1) should return true if value is taken
      2) should return true if value is buffered
      3) should return false if channel is already closed
    that is parked
      4) should return true if value is then taken
      5) should return false if channel is then closed
      ✓ should be moved to the buffer when a value is taken from it 

  take
    that is immediate
      6) should return correct value that was directly put
      7) should return correct value that was buffered
      8) should return false if channel is already closed
    that is parked
      9) should return correct value if it is then delivered
      10) should return CLOSED if channel is then closed

  alts
    11) should work with identity channel
    default value
      12) "before all" hook

  4 passing (76ms)
  12 failing

  1) put that is immediate should return true if value is taken:
     Uncaught TypeError: undefined is not a function
      at $HOME/js-csp/src/csp.test-helpers.js:36:7
      at GeneratorFunctionPrototype.next (native)
      at Process.run ($HOME/js-csp/src/impl/process.js:99:30)
      at $HOME/js-csp/src/impl/process.js:67:10
      at Immediate.process_messages [as _onImmediate] ($HOME/js-csp/src/impl/dispatch.js:36:5)
      at processImmediate [as _immediateCallback] (timers.js:374:17)

  2) put that is immediate should return true if value is buffered:
     Uncaught TypeError: undefined is not a function
      at $HOME/js-csp/src/csp.test-helpers.js:36:7
      at GeneratorFunctionPrototype.next (native)
      at Process.run ($HOME/js-csp/src/impl/process.js:99:30)
      at $HOME/js-csp/src/impl/process.js:67:10
      at Immediate.process_messages [as _onImmediate] ($HOME/js-csp/src/impl/dispatch.js:36:5)
      at processImmediate [as _immediateCallback] (timers.js:374:17)

  3) put that is immediate should return false if channel is already closed:
     Uncaught TypeError: undefined is not a function
      at $HOME/js-csp/src/csp.test-helpers.js:36:7
      at GeneratorFunctionPrototype.next (native)
      at Process.run ($HOME/js-csp/src/impl/process.js:99:30)
      at $HOME/js-csp/src/impl/process.js:67:10
      at Immediate.process_messages [as _onImmediate] ($HOME/js-csp/src/impl/dispatch.js:36:5)
      at processImmediate [as _immediateCallback] (timers.js:374:17)

  4) put that is parked should return true if value is then taken:
     TypeError: undefined is not a function
      at $HOME/js-csp/src/csp.test-helpers.js:36:7
      at GeneratorFunctionPrototype.next (native)
      at Process.run ($HOME/js-csp/src/impl/process.js:99:30)
      at newProcess ($HOME/js-csp/src/csp.core.js:23:8)
      at go ($HOME/js-csp/src/csp.core.js:32:10)
      at Context.<anonymous> ($HOME/js-csp/src/csp.test-helpers.js:25:5)
      at Test.Runnable.run ($HOME/js-csp/node_modules/mocha/lib/runnable.js:204:15)
      at Runner.runTest ($HOME/js-csp/node_modules/mocha/lib/runner.js:374:10)
      at $HOME/js-csp/node_modules/mocha/lib/runner.js:452:12
      at next ($HOME/js-csp/node_modules/mocha/lib/runner.js:299:14)
      at $HOME/js-csp/node_modules/mocha/lib/runner.js:309:7
      at next ($HOME/js-csp/node_modules/mocha/lib/runner.js:247:23)
      at Immediate._onImmediate ($HOME/js-csp/node_modules/mocha/lib/runner.js:276:5)
      at processImmediate [as _immediateCallback] (timers.js:374:17)

  5) put that is parked should return false if channel is then closed:
     TypeError: undefined is not a function
      at $HOME/js-csp/src/csp.test-helpers.js:36:7
      at GeneratorFunctionPrototype.next (native)
      at Process.run ($HOME/js-csp/src/impl/process.js:99:30)
      at newProcess ($HOME/js-csp/src/csp.core.js:23:8)
      at go ($HOME/js-csp/src/csp.core.js:32:10)
      at Context.<anonymous> ($HOME/js-csp/src/csp.test-helpers.js:25:5)
      at Test.Runnable.run ($HOME/js-csp/node_modules/mocha/lib/runnable.js:204:15)
      at Runner.runTest ($HOME/js-csp/node_modules/mocha/lib/runner.js:374:10)
      at $HOME/js-csp/node_modules/mocha/lib/runner.js:452:12
      at next ($HOME/js-csp/node_modules/mocha/lib/runner.js:299:14)
      at $HOME/js-csp/node_modules/mocha/lib/runner.js:309:7
      at next ($HOME/js-csp/node_modules/mocha/lib/runner.js:247:23)
      at Immediate._onImmediate ($HOME/js-csp/node_modules/mocha/lib/runner.js:276:5)
      at processImmediate [as _immediateCallback] (timers.js:374:17)

  6) take that is immediate should return correct value that was directly put:
     Uncaught TypeError: undefined is not a function
      at $HOME/js-csp/src/csp.test-helpers.js:36:7
      at GeneratorFunctionPrototype.next (native)
      at Process.run ($HOME/js-csp/src/impl/process.js:99:30)
      at $HOME/js-csp/src/impl/process.js:67:10
      at Immediate.process_messages [as _onImmediate] ($HOME/js-csp/src/impl/dispatch.js:36:5)
      at processImmediate [as _immediateCallback] (timers.js:374:17)

  7) take that is immediate should return correct value that was buffered:
     Uncaught TypeError: undefined is not a function
      at $HOME/js-csp/src/csp.test-helpers.js:36:7
      at GeneratorFunctionPrototype.next (native)
      at Process.run ($HOME/js-csp/src/impl/process.js:99:30)
      at $HOME/js-csp/src/impl/process.js:67:10
      at Immediate.process_messages [as _onImmediate] ($HOME/js-csp/src/impl/dispatch.js:36:5)
      at processImmediate [as _immediateCallback] (timers.js:374:17)

  8) take that is immediate should return false if channel is already closed:
     Uncaught TypeError: undefined is not a function
      at $HOME/js-csp/src/csp.test-helpers.js:36:7
      at GeneratorFunctionPrototype.next (native)
      at Process.run ($HOME/js-csp/src/impl/process.js:99:30)
      at $HOME/js-csp/src/impl/process.js:67:10
      at Immediate.process_messages [as _onImmediate] ($HOME/js-csp/src/impl/dispatch.js:36:5)
      at processImmediate [as _immediateCallback] (timers.js:374:17)

  9) take that is parked should return correct value if it is then delivered:
     TypeError: undefined is not a function
      at $HOME/js-csp/src/csp.test-helpers.js:36:7
      at GeneratorFunctionPrototype.next (native)
      at Process.run ($HOME/js-csp/src/impl/process.js:99:30)
      at newProcess ($HOME/js-csp/src/csp.core.js:23:8)
      at go ($HOME/js-csp/src/csp.core.js:32:10)
      at Context.<anonymous> ($HOME/js-csp/src/csp.test-helpers.js:25:5)
      at Test.Runnable.run ($HOME/js-csp/node_modules/mocha/lib/runnable.js:204:15)
      at Runner.runTest ($HOME/js-csp/node_modules/mocha/lib/runner.js:374:10)
      at $HOME/js-csp/node_modules/mocha/lib/runner.js:452:12
      at next ($HOME/js-csp/node_modules/mocha/lib/runner.js:299:14)
      at $HOME/js-csp/node_modules/mocha/lib/runner.js:309:7
      at next ($HOME/js-csp/node_modules/mocha/lib/runner.js:247:23)
      at Immediate._onImmediate ($HOME/js-csp/node_modules/mocha/lib/runner.js:276:5)
      at processImmediate [as _immediateCallback] (timers.js:374:17)

  10) take that is parked should return CLOSED if channel is then closed:
     TypeError: undefined is not a function
      at $HOME/js-csp/src/csp.test-helpers.js:36:7
      at GeneratorFunctionPrototype.next (native)
      at Process.run ($HOME/js-csp/src/impl/process.js:99:30)
      at newProcess ($HOME/js-csp/src/csp.core.js:23:8)
      at go ($HOME/js-csp/src/csp.core.js:32:10)
      at Context.<anonymous> ($HOME/js-csp/src/csp.test-helpers.js:25:5)
      at Test.Runnable.run ($HOME/js-csp/node_modules/mocha/lib/runnable.js:204:15)
      at Runner.runTest ($HOME/js-csp/node_modules/mocha/lib/runner.js:374:10)
      at $HOME/js-csp/node_modules/mocha/lib/runner.js:452:12
      at next ($HOME/js-csp/node_modules/mocha/lib/runner.js:299:14)
      at $HOME/js-csp/node_modules/mocha/lib/runner.js:309:7
      at next ($HOME/js-csp/node_modules/mocha/lib/runner.js:247:23)
      at Immediate._onImmediate ($HOME/js-csp/node_modules/mocha/lib/runner.js:276:5)
      at processImmediate [as _immediateCallback] (timers.js:374:17)

  11) alts should work with identity channel:
     Uncaught TypeError: undefined is not a function
      at $HOME/js-csp/src/csp.test-helpers.js:36:7
      at GeneratorFunctionPrototype.next (native)
      at Process.run ($HOME/js-csp/src/impl/process.js:99:30)
      at $HOME/js-csp/src/impl/process.js:67:10
      at Immediate.process_messages [as _onImmediate] ($HOME/js-csp/src/impl/dispatch.js:36:5)
      at processImmediate [as _immediateCallback] (timers.js:374:17)

  12) alts default value "before all" hook:
     Uncaught TypeError: undefined is not a function
      at $HOME/js-csp/src/csp.test-helpers.js:36:7
      at GeneratorFunctionPrototype.next (native)
      at Process.run ($HOME/js-csp/src/impl/process.js:99:30)
      at $HOME/js-csp/src/impl/process.js:67:10
      at Immediate.process_messages [as _onImmediate] ($HOME/js-csp/src/impl/dispatch.js:36:5)
      at processImmediate [as _immediateCallback] (timers.js:374:17)

make: *** [test] Error 12

Channel with transducer example fails

The channel from your blog implementation seems broken (in firefox and regenerator):

Full test:

var csp = require('js-csp');

function compose(f,g) {
    return function(x) {
        return f(g(x));
    }
}

function map(op) {
    return function(reduce) {
        return function(a,x) {
            return reduce(a, op(x));
        }
    }
}

function filter(pre) {
    return function(reduce) {
        return function(a,x) {
            return pre(x)? reduce(a,x): a;
        }
    }
}

var xform = compose(
    map(function(x) {
        return x * 2
    }),
    filter(function(x) {
        return x > 5
    })
);

var ch = csp.chan(1, xform);

csp.go(function*() {
    yield csp.put(ch, 1);
    yield csp.put(ch, 2);
    yield csp.put(ch, 3);
    yield csp.put(ch, 4);
});

csp.go(function*() {
    while(!ch.closed) {
        console.log(yield csp.take(ch));
    }
});

It outputs

2 6 8

It seems the "2" is not even processed by the xform.
Any idea what's going on?

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.