IHP:实时重新加载Haskell代码,其工作原理

2020-09-03 17:56:46

启动IHP应用程序让我们先看看当您通过运行./start来启动IHP应用程序时会发生什么。

项目中的./start脚本基本上只是一个小包装器,它确保由nix管理的所有依赖项都可用,然后调用RunDevServer二进制文件。此二进制文件是IHP的一部分,负责实际的应用程序启动和管理Postgres服务器。

您可以将RunDevServer视为一个小型进程管理器。当启动RunDevServer时,它将直接启动您的应用程序运行所需的所有进程:

所有这些进程都是并行启动的,以实现快速性能,并在开发服务器的主事件循环中同步。多亏了Haskells强大的并发能力。

最重要的进程是您的应用程序的GGCI进程。IHP不会在每次文件更改时完全重新编译您的应用程序,而是在REPL中加载您的应用程序,然后只刷新更改的文件。

首先,GGCI需要几秒钟来加载应用程序的所有Haskell文件。加载应用程序时,状态服务器正在为localhost:8000上的所有http请求提供服务。状态服务器还将显示所有类型错误,以防GHCI无法加载您的应用程序。当GGCI完成加载时,状态服务器将停止,您的应用程序将在localhost:8000上启动。

Haskell文件更改一旦应用程序启动,开发服务器主要处理文件更改。使用文件观察器,开发服务器会收到有关项目中Haskell文件的任何更改的通知。当更改Haskell文件时,在ghci进程中运行的应用程序进程将停止,并触发刷新(:r)。刷新通常非常快。一旦完成,应用程序服务器将再次启动。

一旦Haskell应用程序启动,打开的浏览器页面将使用WebSocket连接进行通知。打开的页面将通过AJAX获取当前页面,然后使用比较和补丁方法更新DOM。因此,在实时重新加载期间,仅实际更改的DOM节点将被触及。此方法将保持现有的页面状态,如滚动位置或键入到表单域中的文本。它允许非常快速且富有成效的反馈周期。

CSS文件更改IHP还支持实时重新加载CSS文件。一旦IHP发现静态目录中CSS文件的文件更改,它将通知所有使用其WebSocket连接打开的浏览器选项卡。在浏览器中发出通知后,IHP将查找任何<;link rel=";样式表>;,并使用缓存缓冲器重新加载CSS文件。

这是可能的,因为NIX允许我们将包定义集固定到NIX包注册表的特定GIT提交。

键入错误有时您所做的更改会使您的应用程序停止编译。在这些错误情况下,状态服务器会介入并开始侦听localhost:8000。然后,状态服务器将显示错误消息,以便您可以快速修复:

此外,打开的浏览器选项卡将收到有关此情况的通知,并将刷新。这样,您可以立即看到错误。

电池-虽然上述步骤在技术上很复杂,但在实际开发时,您不会看到太多这样的复杂性。已经花费了大量的时间来寻找最好的方法并平滑所有的边缘情况。整个过程非常受PHP的启发,您只需更改文件即可运行。现场重装真的很管用。

开发服务器是IHP的核心,使开发过程非常高效。您可以获得类型安全的所有好处,而且开发速度与以前使用脚本语言时一样快。如果你还没有,现在是时候尝试一下了!🚀