import { jsx, jsxs, Fragment } from 'solid-jsx/jsx-runtime';

/*@jsxRuntime automatic @jsxImportSource solid-jsx*/
const toc = [];
function _createMdxContent(props) {
  const _components = Object.assign({
    p: "p",
    code: "code",
    pre: "pre",
    span: "span"
  }, props.components);
  return jsxs(Fragment, {
    children: [jsx(_components.p, {
      children: "Stores werden in Solid meistens durch Solids Store-Proxies erstellt. Manchmal wünschen wir uns eine Schnittstelle zu auf Unveränderlichkeit basierenden Libraries wie Redux, Apollo oder XState und müssen granulare Aktualisierungen gegen diese durchführen."
    }), "\n", jsxs(_components.p, {
      children: ["In unserem Beispiel haben wir einen einfachen Wrapper um Redux. Die Implementation kann man in ", jsx(_components.code, {
        children: "useRedux.tsx"
      }), " sehen. Die Definition vom Store und den Aktionen sind in den anderen Dateien."]
    }), "\n", jsx(_components.p, {
      children: "Das wesentliche Verhalten ist, dass wir ein Store-Objekt erzeugt haben und nun den Redux-Store darin einschreiben, um den Zustand bei Aktualisierungen anzugleichen."
    }), "\n", jsx(_components.pre, {
      children: jsxs(_components.code, {
        className: "hljs language-js",
        children: [jsx(_components.span, {
          className: "hljs-keyword",
          children: "const"
        }), " [state, setState] = ", jsx(_components.span, {
          className: "hljs-title function_",
          children: "createStore"
        }), "(store.", jsx(_components.span, {
          className: "hljs-title function_",
          children: "getState"
        }), "());\n", jsx(_components.span, {
          className: "hljs-keyword",
          children: "const"
        }), " unsubscribe = store.", jsx(_components.span, {
          className: "hljs-title function_",
          children: "subscribe"
        }), "(\n  ", jsx(_components.span, {
          className: "hljs-function",
          children: "() =>"
        }), " ", jsx(_components.span, {
          className: "hljs-title function_",
          children: "setState"
        }), "(store.", jsx(_components.span, {
          className: "hljs-title function_",
          children: "getState"
        }), "())\n);\n"]
      })
    }), "\n", jsx(_components.p, {
      children: "Wenn du in der Demo herumklickst, neue Einträge hinzufügst und sie abhakst, scheint es recht gut zu funktionieren. Was allerdings nicht offensichtlich ist, ist, dass das Rendering ineffizient ist. Man beachte die Log-Ausgabe nicht nur beim Hinzufügen, sondern auch jedes Mal, dass die Box geklickt wird."
    }), "\n", jsx(_components.p, {
      children: "Der Grund dafür ist, dass Solid die Änderungen nicht standardmäßig selbstständig abgleicht. Es nimmt an, dass der Eintrag neu ist und ersetzt ihn. Wenn sich die Daten granular ändern, muss man nicht abgleichen - aber was, wenn man es doch tun muss?"
    }), "\n", jsxs(_components.p, {
      children: ["Solid stellt dafür eine Ableich-Methode ", jsx(_components.code, {
        children: "reconcile"
      }), " bereit, die den ", jsx(_components.code, {
        children: "setStore"
      }), "-Aufruf verbessert und uns ermöglicht, die Daten von unveränderlichen Quellen abzugleichen und nur für die granularen Änderungen benachrichtigt."]
    }), "\n", jsx(_components.p, {
      children: "Ändern wir unseren Code wie folgt:"
    }), "\n", jsx(_components.pre, {
      children: jsxs(_components.code, {
        className: "hljs language-js",
        children: [jsx(_components.span, {
          className: "hljs-keyword",
          children: "const"
        }), " [state, setState] = ", jsx(_components.span, {
          className: "hljs-title function_",
          children: "createStore"
        }), "(store.", jsx(_components.span, {
          className: "hljs-title function_",
          children: "getState"
        }), "());\n", jsx(_components.span, {
          className: "hljs-keyword",
          children: "const"
        }), " unsubscribe = store.", jsx(_components.span, {
          className: "hljs-title function_",
          children: "subscribe"
        }), "(\n  ", jsx(_components.span, {
          className: "hljs-function",
          children: "() =>"
        }), " ", jsx(_components.span, {
          className: "hljs-title function_",
          children: "setState"
        }), "(", jsx(_components.span, {
          className: "hljs-title function_",
          children: "reconcile"
        }), "(store.", jsx(_components.span, {
          className: "hljs-title function_",
          children: "getState"
        }), "()))\n);\n"]
      })
    }), "\n", jsx(_components.p, {
      children: "Jetzt funktioniert das Beispiel wie erwartet und erzeugt nur noch Einträge, wenn diese auch erzeugt werden sollen."
    }), "\n", jsxs(_components.p, {
      children: ["Das ist nicht der einzige Weg, dieses Problem zu lösen und Du hast sicher schon gesehen, dass manche Frameworks eine ", jsx(_components.code, {
        children: "key"
      }), "-Eigenschaft in ihren Template-Schleifen-Helfern verwenden. Das Problem ist, indem man dies zu einem standardmäßigen Teil des Templating macht, muss man alle Listen immer abgleichen und immer alle Kind-Elemente auf potentielle Änderungen prüfen, selbst in kompilierten Frameworks. Eine Daten-zentrische Herangehensweise macht das nicht nur außerhalb des Templatings ohne Abgleich nutzbar, sondern auch beliebig einsetzbar. Wenn man bedenkt, dass die interne Zustandsverwaltung dies gar nicht benötigt, bedeutet das, dass wir grundsätzlich auf den performantesten Ansatz setzen."]
    }), "\n", jsxs(_components.p, {
      children: ["Natürlich gibt es kein Problem damit, ", jsx(_components.code, {
        children: "reconcile"
      }), " bei Bedarf zu verwenden. Manchmal ist ein einfacher Reducer ein guter Weg, um Datenveränderungen zu organisieren. ", jsx(_components.code, {
        children: "reconcile"
      }), " kann hier glänzen, etwa als Teil einer eigenen ", jsx(_components.code, {
        children: "useReducer"
      }), "-Primitive:"]
    }), "\n", jsx(_components.pre, {
      children: jsxs(_components.code, {
        className: "hljs language-js",
        children: [jsx(_components.span, {
          className: "hljs-keyword",
          children: "const"
        }), " ", jsx(_components.span, {
          className: "hljs-title function_",
          children: "useReducer"
        }), " = (", jsx(_components.span, {
          className: "hljs-params",
          children: "reducer, state"
        }), ") => {\n  ", jsx(_components.span, {
          className: "hljs-keyword",
          children: "const"
        }), " [store, setStore] = ", jsx(_components.span, {
          className: "hljs-title function_",
          children: "createStore"
        }), "(state);\n  ", jsx(_components.span, {
          className: "hljs-keyword",
          children: "const"
        }), " ", jsx(_components.span, {
          className: "hljs-title function_",
          children: "dispatch"
        }), " = (", jsx(_components.span, {
          className: "hljs-params",
          children: "action"
        }), ") => {\n    state = ", jsx(_components.span, {
          className: "hljs-title function_",
          children: "reducer"
        }), "(state, action);\n    ", jsx(_components.span, {
          className: "hljs-title function_",
          children: "setStore"
        }), "(", jsx(_components.span, {
          className: "hljs-title function_",
          children: "reconcile"
        }), "(state));\n  }\n  ", jsx(_components.span, {
          className: "hljs-keyword",
          children: "return"
        }), " [store, dispatch];\n};\n"]
      })
    }), "\n", jsxs(_components.p, {
      children: ["DAs Verhalten von ", jsx(_components.code, {
        children: "reconcile"
      }), " ist konfigurierbar. Ein benutzerdefinierter ", jsx(_components.code, {
        children: "key"
      }), " kann vorgegeben werden und es gibt eine ", jsx(_components.code, {
        children: "merge"
      }), "-Option, die strukturelles Klonen ignoriert und nur die obersten Zweige abgleicht."]
    })]
  });
}
function MDXContent(props = {}) {
  const {wrapper: MDXLayout} = props.components || ({});
  return MDXLayout ? jsx(MDXLayout, Object.assign({}, props, {
    children: jsx(_createMdxContent, props)
  })) : _createMdxContent(props);
}

export { MDXContent as default, toc };
//# sourceMappingURL=lesson-689f090f.js.map
