GithubHelp home page GithubHelp logo

cutie's Introduction

NPM Version Build Status codecov

Cutie is a lightweight library that implements Async Tree Pattern.

Motivation

Let's say we want to read content from a file and write it to another one. And all these operations are asynchronous, of course. So, instead of writing something like this:

fs.readFile('./../file1.txt', 'utf8', (err, result) => {
  if (err != null) {
    throw err
  }
 
  fs.writeFile('./../file2.txt', result, (err) => {
    if (err != null) {
      throw err
    }
  })
})

we can design our code in the following style:

new WrittenFile(
  './../file2.txt',
  new ReadDataByPath('./../file1.txt', 'utf8')
).call()

How to use

You can use Cutie as a dependency via npm: npm install @cuties/cutie

const AsyncObject = require('@cuties/cutie').AsyncObject
const fs = require('fs')

// Represents file as path
class WrittenFile extends AsyncObject {
  constructor (path, content) {
    super(path, content)
  }
  
  asyncCall () {
    return (path, content, callback) => {
      this.path = path
      fs.writeFile(path, content, callback)
    }
  }

  onResult() {
    return this.path
  }
}
const AsyncObject = require('@cuties/cutie').AsyncObject
const fs = require('fs')

// Represents buffer or string
class ReadDataByPath extends AsyncObject {
  constructor (path, encoding) {
    super(path, encoding);
  }
  
  asyncCall () {
    return fs.readFile
  }
}

AsyncObject also provides methods OnResult and OnError, so that you can process the result (it's provided by callback by default) from async call and handle an error in the specific way (error is being thrown by default).

Let's say we want to read a json file and parse all information from there. Cutie provides two ways. First of them is just to create ParsedJSON async object like this:

const AsyncObject = require('@cuties/cutie').AsyncObject;
const fs = require('fs');

class ParsedJSON extends AsyncObject {
  constructor (path, encoding) {
    super(path, encoding)
  }
  
  asyncCall () {
    return fs.readFile
  }
  
  onResult (result) {
    return JSON.parse(result)
  }
}

// usage
new ParsedJSON('./../file.txt', 'utf8').call()

ParsedJSON also could be designed like this:

const fs = require('fs')
const ReadDataByPath = require('./ReadDataByPath')

class ParsedJSON extends ReadDataByPath {
  constructor (path, encoding) {
    super(path, encoding)
  }
  
  onResult (result) {
    return JSON.parse(result)
  }
}

// usage
new ParsedJSON('./../file.txt', 'utf8').call();

Or you can use ReadDataByPath with ParsedJSON that looks like this:

const AsyncObject = require('@cuties/cutie').AsyncObject
const fs = require('fs')
const ReadDataByPath = require('./ReadDataByPath')

class ParsedJSON extends AsyncObject {
  constructor (text) {
    super(text)
  }
  
  /*
    you can't call here async operations with I/O
  */
  syncCall () {
    return JSON.parse
  }
}

// usage
new ParsedJSON(
  new ReadDataByPath('./../file.txt', 'utf8')
).call()

Read more

  1. Async Tree Pattern
  2. Async Objects instead of Async Calls

Run test

npm test

Run build

npm run build

Libraries that use cutie

node-test-executor, cutie-is, cutie-assert, cutie-fs, cutie-http, cutie-https, cutie-rest, cutie-buffer, cutie-error, cutie-date, cutie-json, cutie-event, cutie-stream, cutie-object, cutie-process, cutie-iterator, cutie-path, cutie-if-else, cutie-cluster, page-static-generator and many others.

cutie's People

Contributors

guseyn avatar guseyn-grid avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar

Forkers

marechalbati

cutie's Issues

Revert new signature

Revert new signature, because it's not so obvious in cases like fs.readFile, where you don't need to pass params to async call.

As abstraction

Consider As abstraction (for cache),
For example:

As('A2')(
   A1(),
   A2().as('A2'),
   A3()
),

where As('A2') is the represented result of A2()

Unexpected behavior on synchronous call

Hi, Guseyn!
I tried your framework and got unexpected behavior with synchronous call.

For example, i want to create two classes with sync and async behavior, for read and write files.

WrittenFile

const AsyncObject = require('@cuties/cutie').AsyncObject
const fs = require('fs')

class WrittenFile extends AsyncObject {
    constructor(path, content) {
        super(path, content);
    }

    asyncCall() {
        return (path, content, callback) => {
            this.path = path;
            fs.writeFile(path, content, callback)
            console.log("asyncCall writtenFile");
        }
    }

    syncCall() {
        return (path, content, callback) => {
            this.path = path;
            fs.writeFileSync(path, content, callback)
            console.log("syncCall writtenFile");
        }
    }

    onResult() {
        console.log("writtenFile has done!");
    }
}

module.exports = WrittenFile;

ReadDataByPath

const AsyncObject = require('@cuties/cutie').AsyncObject
const fs = require('fs')

class ReadDataByPath extends AsyncObject {
  constructor (path, encoding) {
    super(path, encoding);
  }
  
  asyncCall () {
    return fs.readFile
  }

  syncCall() {
      return fs.readFileSync
  }
}

module.exports = ReadDataByPath

And if i want to run as sync operation, i do

new WrittenFile(
    'package2.json',
    new ReadDataByPath('package.json', 'utf-8')
).syncCall();

but nothing happens.

How can i create one class with two behaviors (async and sync)?

Improve As conception

Add as() method to AsyncObject that can cache value.
Now As can be used only for retrieving values from the cache (can accept only one argument, which is key cached value).

After

Create and implement after conception:

A1(
  A2(), A3()
).after(
  A4(
    A5(), A6()
  )
).call()

SyncObject

Actually it's more clear if SyncObject would be introduced, so in the whole we'll have three abstractions: AsyncObject, SyncObject and Event.

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.