react layers, yet another microframework on top of react
asmer ced31b930a pub-query checks: mutations and mutations refresh | 3 місяців тому | |
---|---|---|
public | 3 місяців тому | |
src | 3 місяців тому | |
README.md | 3 місяців тому | |
index.html | 3 місяців тому | |
package-lock.json | 3 місяців тому | |
package.json | 3 місяців тому | |
tsconfig.app.json | 3 місяців тому | |
tsconfig.json | 3 місяців тому | |
tsconfig.node.json | 3 місяців тому | |
vite.config.ts | 3 місяців тому |
NIH-syndrom again
Create layered React microframework with reasonable architecture and minimal boilerplate.
Layers, one-by-one from deepest layer (global state management, server queries) to directly View (react) layer:
Minimalistic pub/sub with recursive support builded on top of Javascript Proxy
const pub = createPub()
pub.subscribe((state, key, oldValue, newValue) => console.log(state, key, oldValue, newValue))
pub.a = 5
pub.arr = ['foo', 'bar']
pub.arr[1] = 'baz'
On any change of keys in objects subscriber
called. You can listen to updates in any nested object. Listening on upper level hears also nested updates.
This way you can achieve global state tree without boilerplate, but this way requires attention to what you do with state.
usePub
, obviously. Causes react component update on changing of pub. To minimize overhead, usePub
can be used for nested pubs, instead of root state.
const arrPub = usePub(pub.arr)
Hook returns pub, so arrPub === pub.arr
, but component updating when pub changes.
Pub can be easily used for tracking promises. !!! (error) Be careful, storing promises in global state causes memory leaks !!!
javascript
{
promiseName1: {status, payload, error}
promiseName2: {status, payload, error}
}
promiseName
and exactly promise as argument and updates promise pub branch when promise updating its state (PENDING => FULFILLED or
PENDING => REJECTED), storing status
, payload
and error
in promise pub named branchcreateAsyncThunk
, or createQuery
, with next parameters:
promiseName
.queryFunc
- function, which returns promises.or even carrying:
1. `createQueryPub` creates pub with promises, some basic options passed (like cache timeout and probably queryFunc) and returns `createQuery` or object with functions from step 3 if queryFunc passed on first step into createQueryPub
2. `createQuery(queryFunc)` returns function, which:
3. receives `promiseName`, returns object with functions:
- `query`, which accepts arguments and passes it to `queryFunc`
- `usePromiseNameQuery`/`usePromiseNameMutation` like in `rtk-query`
- and so... (no ideas right now, but something about atomic actions/force query/invalidate cache)
To avoid random messy access to global state, some functions which works with are welcome, but they aren't necessary.
Instead of moving Routing on React level, making routing great again separated from React Markup.
Routing configuration should be separated from React markup, and store next information:
/page/:id
useHuy
, map
, props waterfall, usePizda
, map
and sofallback
(address to go, if private route not accessible) and roles
- list of user roles, which can
visit this private page. Some HOC needed to provide current user roles list (usually from global state/jwt) to be matched with roles
propspossible routing configuration:
javascript
const treeRouteConfig = {
//root page:
"/": PageMain,
//login
'/login': PageLogin,
//admin part with subroutes
'/admin': {
"/": PageAdminMain, // /admin/
"/users": PageAdminUsers, // /admin/users
}
}
A lot of questions at the moment about three configs: what if route params AND nested routes ?-params and hash layer - where is should be configured? looks like this configuration should be moved into page component, not to be in tree. so cancel tree idea for now
Mostly template react components without boilerplate, hookafucking, billions of useEffect
and so. Styling moved to CSS or... not.
createPub
and qjp
(should be refucktored) from v01
react-router-dom
to pass query func to Route
component or other configurationSome addons
For now no implementations about SSR, but there are some ideas: