Giter VIP home page Giter VIP logo

Comments (12)

staltz avatar staltz commented on June 14, 2024 2

It's more complex to put the hands on it

Hell in a box :)

from callbag.

franciscotln avatar franciscotln commented on June 14, 2024 1

@ramiel I think you'd rather assign the talkback function to a constant instead of directly calling source(1). This may have worked because I created callbag-range in a way where a pass the source itself as talkback function, but in general that's not the case and may not work for other sources.
Try:

const group = n => source => (start, sink) => {
  let talkback;
  if (start !== 0) return;
  let chunk = [];
  source(0, (t, d) => {
    if (t === 0) {
      talkback = d;
    }
    if (t === 1) {
      chunk.push(d);
      if (chunk.length === n) sink(t, chunk.splice(0));
      talkback(1);
    } else {
      if (t === 2 && chunk.length) {
        sink(1, chunk.splice(0));
      }
      sink(t, d);
    }
  })
}

from callbag.

ramiel avatar ramiel commented on June 14, 2024 1

@franciscotln thank you. Yes I had already read that part which should have more visibility IMO. Thank you for taking the time to share your scheme!

from callbag.

ramiel avatar ramiel commented on June 14, 2024

Ok, I just changed the implementation to be

const group = n => source => (start, sink) => {
  if (start !== 0) return;
  let chunk = [];
  source(0, (t, d) => {
    if (t === 1) {
      chunk.push(d);
      if (chunk.length === n) {
        sink(t, chunk.splice(0));
      }
      source(1); // <--------- This is the really new line
    } else {
      if (t === 2 && chunk.length) {
        sink(1, chunk.splice(0));
      }
      sink(t, d);
    }
  })
}

What I think it's hard for me is to understand why I have to tell the source I want more data. Is to take in account the pullable source? Is because an operator must act as a proxy between sink and source?

from callbag.

staltz avatar staltz commented on June 14, 2024

Hi! Nice that you're building this operator. About the last question, range is a pullable source. It requires pulling. Thats because it creates the values on demand, not beforehand. So if you had range(1, 10000), you could pull just a subset of those and wouldn't cause costs up to 10k. Some sources are pullable, some are listenable, you can't be sure so it's better than an operator indicates what kind does it support, or attempt to support both.

from callbag.

ramiel avatar ramiel commented on June 14, 2024

Ok, got it. My problem was that I build a pullable source and puller sink in my tests. In my test, by the way, the sink know how many times pull from the source, so I couldn't see the problem. iterate, instead, probably pull while it receives data and since it receives nothing after the first pull, it stops asking. Now I'm fearing that my solution is incorrect and simply I should use something different from iterate. Something that maybe "pull until receive type=2".

from callbag.

ramiel avatar ramiel commented on June 14, 2024

Anyway, the operator is available on npm now

from callbag.

staltz avatar staltz commented on June 14, 2024

By the way, you can use forEach instead of iterate. It does the same

from callbag.

ramiel avatar ramiel commented on June 14, 2024

Yes, I was using it at the beginning. Iterate is just a result of many tests :)

from callbag.

ramiel avatar ramiel commented on June 14, 2024

Yes, indeed. Thank you @franciscotln. Anyway i'll try later to re-implement it because also this way is somehow wrong (it fails my tests and it can be my tests or this code).

from callbag.

ramiel avatar ramiel commented on June 14, 2024

No, ok, it worked :D

So now the code in the repository should be good enough.
I'd also like to share my impression of callbags in general. Them are easy to understand when you listen/read of it. I listened to a talk by @staltz and I read the documentation about callbags always having the impression of understanding the subject. It's more complex to put the hands on it in the sense that:

  • It's easy to use the available operators/factories
  • It's a bit confusing to write one because:
    • there are difference between pullable and listenable source/sink and since their interface it's exactly the same, this led to confusion. I'm not suggesting that the interface should be different though.
    • The same event type can carry different information. type 0 behave differently if you're in a sink or in a source. Type 1 behave differently if it has a payload or not.
    • I'm still not sure I get all the subtle of an operator :)

This is what confused me. Of course this reflects only my experience but I feel it's important to share.

from callbag.

franciscotln avatar franciscotln commented on June 14, 2024

@ramiel have you read this? https://github.com/callbag/callbag/blob/master/getting-started.md

If not and if this helps, I have the following callbag scheme in my brain:
Source:

  • when calling the sink with (0, Function) it means: sink, this is my phone number, if you need something, call me back :-) This function can be the source itself, but in general it's not. This function is used by the sink to ask pullable sources for more data or to "unsubscribe" from it.
  • when calling the sink with (1, any) it means: sink, here's some data for you, since you asked.
  • when calling the sink with (2, undefined) it means: sink, I have no more data left for you, that's the end.
  • when calling the sink with (2, any) it means: sink, sh*t happened. Here's the error.

Sink:

  • when calling the source with (0, Function) it means: hi source, I'm the sink. Nice to meet ya.
  • when calling the source's talkback function with (1, any - where any is mostly void 0) it means: source, please send me more data if you are a pullable kind.
  • when calling the source's talkback function with (2, any - where any is mostly void 0) it means: source, please stop sending me data.

Sources in general are of the form config -> (start, sink) -> void.

Sinks in general are of the form config -> source -> any, because it may return some form of teardown logic (ie, a unsubscribe function).

Operators are in between so they take the source, subscribe to it, do various things with the data they get and return a new source, so they are of the form config -> source -> (start, sink) -> void

right, too long already. I hope I haven't made any mistakes :-D

from callbag.

Related Issues (20)

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.