表的内容

非交互式服务器和车部署

的核心AnalysisPageServer的服务器端系统是一个从处理程序函数映射到web服务。您定义的集合构建一个函数来表示AnalysisPageRegistry,然后在车部署应用程序(运行在您的本地R服务器)或Apache使用Rapache系统。

内置对象处理程序函数调用AnalysisPage年代。AnalysisPage可以是一个服务,该服务可能会返回例如任意JSON字符串,也可以是一个完全交互式页面,例如使情节和返回一个数据帧。本文解释了简单的服务型AnalysisPage。这也解释了如何部署应用程序与车。描述交互式页面和服务器另一个页面

车> = 1.1 +叉

车版本> = 1.1和叉在这个描述所需的例子。我要检查是否可用。

# #车> = 1.1或叉不可用,因此,尽管你仍然可以使用静态报表AnalysisPageServer # #的特性,动态服务器和部署FastRWeb和RApache你# #将无法部署使用车/ Rhttpd,或者建立适当的这一幕。你会看到# #消息“车> = 1.1 +叉不可用”在所有的点在这个描述# #车+叉会被要求:启动服务器,查询服务器和停止# #服务器。如果你想要你可以安装/更新失踪的依赖关系是这样的:# # # # install.packages(“叉”)# # install.packages (devtools)图书馆(devtools) # # # # install_github(“车”、“jeffreyhorner”)

最简单的AnalysisPage

服务型AnalysisPage年代建造的build.service ()构造函数。所有你要做的就是通过一个处理函数,给它一个名字:

库(AnalysisPageServer)你好< - build.service(函数()“你好,世界!”name = "你好")类(你好)
# # [1]“AnalysisPage”

注意:尽管我们将演示,这是一个服务,而不是一个成熟的web页面我们仍然称之为一个AnalysisPage。以来,从服务器的角度来看,没有多少区别网络服务和web页面中,在这个文档时我通常只是说“页面”说“页面或服务”会更准确。

最简单的AnalysisPageRegistry

接下来,我们建立一个AnalysisPageRegistry。本例中只有一个AnalysisPage,不是很有趣,但是我们仍然需要这个对象:

reg < - new.registry(你好)类(注册)
# # [1]“AnalysisPageRegistry”

一个AnalysisPageRegistry不是比一个查找AnalysisPage年代。你可以得到所有注册页面的名称:

页面(reg,包括。服务= TRUE)
# #[1]“你好”

include.services开关必须打开,因为默认只返回互动页面,和你好没有互动。

您可以检索一个特定的页面:

相同的(。页面(reg,“你好”),你好)
# # [1]

从AnalysisPageRegistry车应用

一旦注册对象构建它可以部署。在本文档页面,我们将部署我们所有的应用程序通过使用本地R服务器车。这是有用的用于开发和非正式但生产规模RApacheFastRWeb部署是必需的。车+ Rhttpd不处理并发的组合,通常倾向于事故很多。同时,一些版本的车只会监听当地lookback设备,这将避免与任何人共享您的服务器。

注意:你所选择的部署是完全独立于如何构建AnalysisPageRegistry,这是这个文档页面的主要焦点。

现在我们将启动服务器:

端口< - 3198 # #或其他端口服务器< - startRookAnalysisPageServer (reg,端口=端口)服务器

“车> = 1.1 +叉不可用”

请注意,这个函数startRookAnalysisPageServer启动服务器在一个新的进程。这似乎比典型的车稍微稳定部署在同一进程中,你继续计算可能会妨碍传入的请求。特别是,如果你试图从相同的R过程调用服务器挂起。可以传递给这个函数返回的对象kill.process ()关闭服务器:

kill.process(服务器)

“车> = 1.1 +叉不可用”

开始一个新的进程的缺点是,你可能会忘记你辞职r .这不仅浪费系统资源,但它实际上拥有港口,这意味着你无法开始另一个端口的服务器。为了防止这种情况,你应该开始你的服务器的习惯两行代码:

服务器< - startRookAnalysisPageServer (reg,端口=端口)on.exit(试试(kill.process(服务器)))

第二行寄存器表达式时评定R退出,这确保了孩子不生存。自触发的on.exit处理程序是有点棘手knitr环境我们将显式的调用kill.process(服务器)在这个文档。

如果你是一个车书呆子和想做的更漂亮的东西,像把这车应用程序和其他应用程序,然后你可以得到车的应用对象是这样的:

应用< - new.rook.analysis.page.app(注册)

与这个对象你也有部署服务器的可能性在正常车方式,避免使用包中。

车。服务器< -车:Rhttpd美元新()车。服务器添加美元(app, name = "罪行")车。服务器开始美元(端口=端口)# # Ping服务器从另一个R过程或从web浏览器…# #然后停止服务器rook.server美元停止()

“车> = 1.1 +叉不可用”

启动服务器

我们提供的startRookAnalysisPageServer ()函数来启动服务器,而不是直接连接车:Rhttpd ()。这个函数接受一个AnalysisPageRegistry对象,因此你不需要建立你的车对象,并使用包在子进程启动服务器。这让我们从父进程调用服务器,否则块。它也很容易从灾难中恢复,只要杀死子进程,而无需重新启动父R过程。

让我们打开服务器,看看它是如何工作的。

服务器< - startRookAnalysisPageServer (reg,端口=端口)

然后打开你的浏览器:

解剖的URL: 127.0.0.1是车使用的环回设备————意味着你的本地主机。这个演示页面的端口是一个任意的选择(抱歉如果端口从这个屏幕截图不匹配这个文档)的端口。如果你不指定一个端口然后车/ R将随机选择一个给你,每一次你试试你的服务器将不得不修改端口。不能修改/定制”前缀,即车+ Rhttpd是如何工作的。“罪行”是我在车命名服务器。“R /分析”中一个前缀AnalysisPageServer系统所有页面的位置。最后,json编码的页面的名称,形成完整的请求。

一旦服务器运行我们可以查询它在理论上从任何远程语言,甚至可能。在本文档中,我们将演示服务器正在通过构造URL(使用service.link函数),然后调用readline ()

app.base。< url - paste0 (“http://127.0.0.1”,港口,“/定制/敲”)< -服务url。链接(页面= "你好",app.base。url = app.base.url)猫(readline (url,警告= FALSE),“\ n”)
# #“车> = 1.1 +叉不可用”

(警告= FALSE被添加到readline调用incompete最后一行的警告消息)。

这是“Hello, World !”。

敏锐的观察者注意到问候字符串引用的反应,即使它是显示而不是正常的R输出。这样做的原因是,所有json编码的自动反应。在这之后,以及如何关掉它。

kill.process(服务器)

“车> = 1.1 +叉不可用”

例子:一个应用程序的多个服务

我们把两页在同一个应用程序中。我们将重用你好页面也有计算一个参数的正弦函数:

正弦< - build.service(函数(θ)罪(θ),name =“正弦”)注册< -新。注册表(sin,你好)服务器< - startRookAnalysisPageServer (reg,端口=端口)

正如上面提到的,所有的返回值是默认情况下json编码的。我们可以使用fromJSON函数把它们回到R对象。出于演示的目的在这个文档我们会总结的步骤构建URL,调用服务器,响应和解码成一个函数:

秀。分析< -函数(params =()列表,页面显示。url = FALSE) {< url -服务。链接(页面、params app.base.url)如果(show.url)猫(url,“\ n”)响应<——readline (url,警告= FALSE) rjson:: fromJSON(响应)}。分析(“hello”,显示。url = TRUE)
# # http://127.0.0.1:3198 /定制/敲/ R /分析? = % 22你好% 22页
# #[1]“车> = 1.1 +叉不可用”
秀。分析(“正弦”,列表(θ= 3.141592653),表演。url = TRUE)
# # http://127.0.0.1:3198 /定制/敲/ R /分析? page = % 22正弦% 22 e141592653θ= 3% 2
# #[1]“车> = 1.1 +叉不可用”
kill.process(服务器)

“车> = 1.1 +叉不可用”

例子:JSON编码复杂的返回值

无论你的函数返回将JSON编码toJSON

残雪。返回< - build.service(函数(){列表(A = 1:5, B =“我能”,C =列表(x = 1, y = C(真的,假,真的)))},name = "复杂")reg < - new.registry (cx.return)服务器< - startRookAnalysisPageServer (reg,端口=端口)show.analysis(“复杂”)
# #[1]“车> = 1.1 +叉不可用”
kill.process(服务器)

“车> = 1.1 +叉不可用”

例子:URL和参数值的JSON解码

参数的URL解码然后JSON解码然后传递给函数。这个处理程序需要一个复杂的结构和一个整数作为参数。与数组元素的结构应该是一个散列键“a”。元素的数组索引返回的整数。

残雪。参数< -构建。服务(功能(结构,n){在Javascript: # # # #结构[A] [n - 1] struct美元[n]}, name = " cxpar ") reg < - new.registry (cx.param)服务器< - startRookAnalysisPageServer (reg,端口=端口)。分析(“cxpar”,列表(struct =列表(A = c (3、1、4、1、5、9、2、6、5、3)), n = 6),表演。url = TRUE)
# # http://127.0.0.1:3198 /定制/敲/ R /分析? page = % 22 cxpar % 22 struct = % 7 b % 22 % % 5 3 22% b3 % 2 c1 % 2 c4 % 2 c1 % 2 c5 % 2 c9 % 2 c2 % 2 c6 % 2 c5 % 2 c3 % 5 d % 7 d&n = 6
# #[1]“车> = 1.1 +叉不可用”
kill.process(服务器)

“车> = 1.1 +叉不可用”

例子:任意的响应

有时自动JSON编码的响应是一个麻烦。或者,您可能希望设置响应的MIME类型。如果您显式地返回一个AnalysisPageResponse对象可以有更好的控制。这是完成了new.response构造函数。

在这个例子中,我们返回一个完整的HTML页面。

诗。文件< -执行(“/ in-a-station-of-the-metro例子。html”,包= " AnalysisPageServer”)的诗。html < - readline(诗。文件,警告= FALSE)诗< - build.service(函数(){new.response (paste0(诗。html、“\ n”)的内容。type = " text / html ")}, name = "诗")reg < - new.registry(诗)服务器< - startRookAnalysisPageServer (reg,端口=端口)< url -服务。链接(app.base“诗”。url = app.base.url) readline (url,警告= FALSE)

“车> = 1.1 +叉不可用”

或在浏览器中打开它:

kill.process(服务器)

“车> = 1.1 +叉不可用”

例子:情节反应

new.response构造函数让我们返回其他事情。例如,我们甚至可以把一块响应。让我们编码Maunga Whau火山的情节,我们做的静态内容示例页面。我们将使用RreadBin读成原始矢量因为它是二进制数据。

单参数的函数将一个数组用于颜色渐变颜色。

火山< -构建。服务(功能(颜色= c(“红”、“白”、“紫色”)){plotfile < - tempfile (fileext = . png) png (plotfile、宽= 600,高= 400)标准(mar = c (1、1、4、1) < - colorRampPalette上校(颜色)(50)图像(数据集::火山,xaxt =“n”, yaxt =“n”,主要=“Maunga Whau火山”,=上校,上校cex。情节主要= 2)dev.off ()。数据< - readBin (plotfile、“原始”,n = file.info (plotfile)[, "大小"])。响应(身体=阴谋。数据、内容。类型=“图像/ png”)}, name =“火山”)注册< - new.registry(火山)服务器< - startRookAnalysisPageServer (reg,端口=端口)

一个四色的火山:

如果颜色参数是省略了然后从函数定义将使用默认值(在本例中红、白、紫色):

kill.process(服务器)

下一个

构建交互式应用程序