Socket
Socket
Sign inDemoInstall

js-awe

Package Overview
Dependencies
Maintainers
1
Versions
72
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

js-awe - npm Package Compare versions

Comparing version 1.0.30 to 1.0.31

sandbox/plan/simplePlan.js

2

package.json
{
"name": "js-awe",
"version": "1.0.30",
"version": "1.0.31",
"homepage": "https://github.com/josuamanuel/js-awe",

@@ -5,0 +5,0 @@ "author": "josuamanuel@hotmail.com",

# js-awe
javascript utilities and extensions
javascript utilities and extensions. Taking javascript to the next level.
to install:
npm install js-awe
## New functional async style. Avoid await contamination
Async await has done a lot to improve the readability of code when compared with the callback style. But sometimes it is not a good construct, especially if you want to use it in a functional style!!!
One problem I see, is the spread of async await around the source code wherever it is handy. Every time we use await, an async branch will be created. The result will be an execution flow with the shape of a tree, with some chain functions running in sequence and others running concurrently. Understanding the tree of execution flow turns difficult. This is mainly by the fact that the construct of the tree is not explicitly coded in one place.
js-awe library has a “plan” function that can help you with that.
“plan” tries to solve this problem by declaring this tree explicitly in one place and in a simple elegant way. It uses array nesting to define this tree. It does not use weird DSL. “plan” is an execution planner that pipe functions to run in sequence and functions to run concurrently. It handles for you the promise chaining and data passing so you can write pure functions free of async await.
The construct to run in sequence:
```Plaintext
[ fun1, fun2, fun3 ]
execution flow:
fun1 -> fun2 -> fun3
```
The construct to run concurrently:
```Plaintext
[ fun1, [fun2], [fun3], fun4 ]
execution flow:
|-> fun2 --|
fun1 --| |-> fun4
|-> fun3 --|
```
The best thing is to view an example. First, we need to install it:
```Bash
npm install js-awe
```
You can see below is a simple example of its use. This could be part of an API to get the bank balances of all the holdings (savings and loans) for a specific customer:
```javascript
import { plan } from 'js-awe'
const getCustomerBalances = plan([
getAccounts,
[filterSavings, getSavingBalances],
[filterLoans, getLoanBalances],
formatCustomerBalances,
])
console.log(await getCustomerBalances('0396d9b0'))
```
Execution:
```Plaintext
|->filterSavings -> getSavingBalances -|
getAccounts -| |-> formatCustomerBalances
|->filterLoans -> getLoanBalances -|
```
The flow of data:
- Return values from functions are passed to the next function to run, in a pipe-style way.
- When the return value is a promise, the planner will wait for its resolution before calling the next function.
You can see the whole example here:
```javascript
import { plan } from 'js-awe'
const getCustomerBalances = plan([
getAccounts,
[filterSavings, getSavingBalances],
[filterLoans, getLoanBalances],
formatCustomerBalances,
])
console.log(await getCustomerBalances('0396d9b0'))
function getAccounts(customerId) {
return Promise.resolve([
{ id: 1, type: 'saving' },
{ id: 2, type: 'loan' },
])
}
function filterSavings(accounts) {
return accounts.filter((account) => account.type === 'saving')
}
function getSavingBalances(savingAccounts) {
return Promise.resolve(savingAccounts.map((account) => ({ balance: 5, ...account })))
}
function filterLoans(accounts) {
return accounts.filter((account) => account.type === 'loan')
}
function getLoanBalances(loanAccounts) {
return Promise.resolve(loanAccounts.map((account) => ({ balance: 4, ...account })))
}
function formatCustomerBalances([savingBalances, loanBalances]) {
return [...savingBalances, ...loanBalances]
}
```
the Plan utility is recommended when we have a complex tree, and you want to manifest explicitly this async flow. For example, This utility would be a good tool for an API that generates its response based on different calls to other APIS. Especially if some of the calls need to be called in sequence and others can be run concurrently.
When it is not recommended:
- Simple async flows. Introducing another tool to learn may not be worth it.
- You hate frameworks and abstractions. I get it!
## Chrono
Chrono time events and visualize them.
[chronoExampl.js](https://github.com/josuamanuel/js-awe/blob/main/sandbox/Chrono/chronoExample.js)
```logs
chronoCreation : 2023-05-25T20:58:17.175Z
report : 2023-05-25T20:58:18.480Z
Timeline of events:
┌────────┬───────────────────────────────────────────────────────────────────────────────────────┐
│ Events │ ms 0 650 1186 1288 │
├────────┼───────────────────────────────────────────────────────────────────────────────────────┤
│ step1 │ |--------------------------------------| || │
│ step2 │ |-------------------------------------| │
│ step3 │ |-----------------------------| │
└────────┴───────────────────────────────────────────────────────────────────────────────────────┘
Total elapse Time of each event:
┌─────────┬─────────┬────────┬────────────┐
│ (index) │ name │ elapse │ percentage │
├─────────┼─────────┼────────┼────────────┤
│ 0 │ 'step1' │ 650 │ 36.81 │
│ 1 │ 'step2' │ 615 │ 34.84 │
│ 2 │ 'step3' │ 501 │ 28.36 │
└─────────┴─────────┴────────┴────────────┘
Coinciding Events timeline:
┌─────────┬──────────────────────┬──────────┬────────────┐
│ (index) │ runningEvents │ elapseMs │ percentage │
├─────────┼──────────────────────┼──────────┼────────────┤
│ 0 │ [ 'step1' ] │ 650 │ 51.38 │
│ 1 │ [ 'step2' ] │ 114 │ 9.04 │
│ 2 │ [ 'step2', 'step3' ] │ 501 │ 39.58 │
└─────────┴──────────────────────┴──────────┴─────
```
## And much more
For you to explore... or help with documentation.
## Generating types

@@ -6,0 +167,0 @@

@@ -7,2 +7,3 @@ import { Chrono } from '../../src/chrono.js'

chrono.time('step1')
tasks().then(()=>{

@@ -13,2 +14,3 @@ chrono.timeEnd('step1')

async function tasks()

@@ -57,43 +59,1 @@ {

}
// let chrono2 = Chrono()
// chrono2.time('step1')
// tasks2().then(()=>{
// chrono2.timeEnd('step1')
// chrono2.report()
// })
async function tasks2()
{
await sleepWithFunction(
650,
() => {
chrono2.timeEnd('step1')
}
)
await sleepWithFunction(
300,
() => {
chrono2.time('step1')
}
)
await sleepWithFunction(
400,
() => {
chrono2.timeEnd('step1')
}
)
await sleepWithFunction(
500,
() => {
chrono2.time('step1')
}
)
}
import { arraySorter, pushUniqueKeyOrChange, sorterByPaths, pushUniqueKey, CustomError, pushAt } from './jsUtils.js';
import { groupByWithCalc, R } from './ramdaExt.js';
import { Table } from './table/table.js'
import { Table, consoleTable } from './table/table.js'
import { Text } from './table/components/text.js'

@@ -300,5 +300,4 @@ import { Timeline } from './table/components/timeline.js'

if (console.table) console.table(toLog)
else console.log(toLog)
return events

@@ -318,4 +317,3 @@ }

console.log('Coinciding Events timeline: ')
if (console.table) console.table(coincidingEvents)
else console.log(coincidingEvents)
consoleTable(coincidingEvents)
}

@@ -322,0 +320,0 @@ )(elapseTable)

@@ -162,2 +162,15 @@ import { R } from './../ramdaExt.js'

export { Table, Index }
function consoleTable(toLog)
{
console.log(Table(toLog).auto().draw())
}
function consoleTableExtended(toLog)
{
if (console.table) {
if(globalThis?.process?.argv0 === 'bun') console.log(Table(toLog).auto().draw())
else console.table(toLog)
}else console.log(toLog)
}
export { Table, Index, consoleTable, consoleTableExtended }
SocketSocket SOC 2 Logo

Product

  • Package Alerts
  • Integrations
  • Docs
  • Pricing
  • FAQ
  • Roadmap
  • Changelog

Packages

npm

Stay in touch

Get open source security insights delivered straight into your inbox.


  • Terms
  • Privacy
  • Security

Made with ⚡️ by Socket Inc