Socket
Book a DemoInstallSign in
Socket

effector-next

Package Overview
Dependencies
Maintainers
5
Versions
6
Alerts
File Explorer

Advanced tools

Socket logo

Install Socket

Detect and block malicious and high-risk dependencies

Install

effector-next

A HOCs that brings Effector and Next.js together

latest
Source
npmnpm
Version
1.3.3
Version published
Maintainers
5
Created
Source

Effector Next

A HOCs that brings Effector and Next.js together

npm version

Installation

npm install effector-next

or yarn

yarn add effector-next

effector-next requires effector, effector-react to be installed

effector/babel-plugin is necessary if you do not want to manually name the units

Settings

  • To load the initial state on the server, you must attach withFork wrapper to your _document component

    pages/_document.jsx
    import Document from "next/document";
    import { withFork } from "effector-next";
    
    const enhance = withFork({ debug: false });
    
    export default enhance(Document);
    
  • To get the initial state on the client and drop it into the application, you must attach withHydrate wrapper to your _app component

    pages/_app.jsx
    import { withHydrate } from "effector-next";
    import App from "next/app";
    
    const enhance = withHydrate();
    
    export default enhance(App);
    
  • To bind events/stores on the server to the scope, add aliases from effector-react to effector-react/ssr in next.config.js

    next.config.js
    const { withEffectorReactAliases } = require("effector-next/tools");
    
    const enhance = withEffectorReactAliases();
    
    module.exports = enhance({});
    
  • Replace imports from "effector" to "effector-next"

    - import { createEvent, forward } from "effector"
    + import { createEvent, forward } from "effector-next"
    
  • Connect the effector/babel-plugin

    .babelrc
    {
      "presets": ["next/babel"],
      "plugins": ["effector/babel-plugin"]
    }
    

    If you are using effector version > 21.3.0, you also need to configure the babel plugin:

    {
      "presets": ["next/babel"],
      "plugins": ["effector/babel-plugin", { "importName": ["effector-next"] }]
    }
    
  • Configure what event will be triggered when the page is requested from the server using withStart

    pages/index.js
    import React from "react";
    import { withStart } from "effector-next";
    import { useStore } from "effector-react";
    
    import { pageLoaded } from "../model";
    
    const enhance = withStart(pageLoaded);
    
    function HomePage() {
      return (
        <div>
          <h1>Hello World</h1>
        </div>
      );
    }
    
    export default enhance(HomePage);
    

Example

  • Declare our model

    models/index.js
    import { forward, createEvent, createStore, createEffect } from "effector-next";
    
    export const pageLoaded = createEvent();
    export const buttonClicked = createEvent();
    
    const effect = createEffect({
      handler(name) {
        return Promise.resolve({ name });
      },
    });
    
    export const $data = createStore(null);
    
    $data.on(effect.done, (_, { result }) => result);
    
    forward({
      from: pageLoaded.map(() => "nameFromPageLoaded"),
      to: effect,
    });
    
    forward({
      from: buttonClicked.map(() => "nameFromButtonClicked"),
      to: effect,
    });
    
  • Connect the page to the store (all units must be wrapped in hooks - this is necessary in order to associate units with scope on the server)

    pages/index.jsx
    import React from "react";
    import { useStore, useEvent } from "effector-react";
    
    import { $data, buttonClicked } from "../models";
    
    export default function HomePage() {
      const data = useStore($data);
      const handleClick = useEvent(buttonClicked);
    
      return (
        <div>
          <h1>HomePage</h1>
          <h2>Store state: {JSON.stringify({ data })}</h2>
          <button onClick={handleClick}>click to change store state</button>
        </div>
      );
    }
    
  • Bind an event that will be called on the server when the page is requested

    pages/index.jsx
    import React from "react";
    import { useStore, useEvent } from "effector-react";
    +import { withStart } from "effector-next";
    
    -import { $data, buttonClicked } from "../models";
    +import { $data, pageLoaded, buttonClicked } from "../models";
    
    +const enhance = withStart(pageLoaded);
    
    -export default function HomePage() {
    +function HomePage() {
      const data = useStore($data);
      const handleClick = useEvent(buttonClicked);
    
      return (
        <div>
          <h1>HomePage</h1>
          <h2>Store state: {JSON.stringify({ data })}</h2>
          <button onClick={handleClick}>click to change store state</button>
        </div>
      );
    }
    
    +export default enhance(HomePage);
    

Configuration

The withFork accepts a config object as a parameter:

  • debug (optional, boolean) : enable debug logging
  • serializeIgnore (optional, array) : stores whose values ​​should not be sent to the client after serialization

Server payload

When the unit passed to withStart is called, the object will be passed as a payload:

  • req : incoming request
  • res : serever response
  • cookies : parsed cookies
  • pathname : path section of URL
  • query : query string section of URL parsed as an object.

Release process

Keywords

effector

FAQs

Package last updated on 05 Jun 2022

Did you know?

Socket

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Install

Related posts