R

R

R用户如何使用Docker

hokingyang 发表了文章 • 0 个评论 • 1807 次浏览 • 2019-01-29 10:24 • 来自相关话题

#什么是Docker Docker是“一种实现在操作系统层面的虚拟化软件,也称为容器”。这是Wikipedia的定义,对于不熟悉的人来说太晦涩难懂了。 简单说,Docker是一类程序,使得在自己的机器上(称为host)调度 ...查看全部
#什么是Docker
Docker是“一种实现在操作系统层面的虚拟化软件,也称为容器”。这是Wikipedia的定义,对于不熟悉的人来说太晦涩难懂了。

简单说,Docker是一类程序,使得在自己的机器上(称为host)调度(启动或者停止)多个操作系统(称为容器)。假设有10台运行不同Linux系统的树莓派,每台都运行不同服务,实际上可以在自己的机器上启停这些树莓派设备。
#为什么要在R中使用Docker
Docker可以实现在镜像或者容器中内置环境,意味着可以在Macbook上运行Linux,或者在本机运行R 3.5而同时在虚机里运行R 3.3环境。同时,也意味着为某些特殊目的在虚拟环境中使用较老版本的环境包,而本机则保持最新状态。

这样可以解决“依赖性”问题,如果担心环境改变会影响最新环境,可以建立一个虚拟容器运行需要的环境,可以是Linux、R或者任何其他需要的包。
# Docker镜像和Docker容器
在机器上,需要两类东西,镜像和容器。镜像可以看做操作系统,而容器可以认为是镜像的运行态。镜像只需要运行一次,而容器则在需要时候随时启动,当然一个镜像可以同时运行多个实例。

和R对比,安装和装载package类似于镜像和容器,一个package只需要下载一次,但是可以运行多个实例。同样在metaphore概念上也有类比:通过install.packages()来编译镜像,用library()来运行镜像。
# Dockerfile
Docker镜像根据Dockerfile建立。Dockerfile是配置文件,其中定义了:依赖的Docker镜像,如何配置操作系统,运行容器时做什么。有点类似于R包中的DESCRIPTION NAMESPACE文件,其中也定义了依赖包,元信息,以及使用library调用后用户可用的函数和数据。

因此,可以为R写一个非常基础的Dockerfile文件,目的是可重复性。也就是说:假如生成了一个分析环境(例如,在一个R文件中定义),而且希望不管以后系统如何升级这个分析环境仍然可以工作。

首先,创建一个分析目录和Dockerfile:
mkdir ~/mydocker
cd ~/mydocker
touch Dockerfile

假如运行程序为位于~/mydocker目录下的myscript.R:
library(tidystringdist)
df <- tidy_comb_all(iris, Species)
p <- tidy_stringdist(df)
write.csv(p, "p.csv")

## FROM
每个Dockerfile都以FROM开头,定义从哪个image开始创建。网上有很多官方发布的镜像,也可以从本地自己建一个开始。FROM定义了镜像的依赖关系,就跟R中生成一个包需要依赖一个另外的包一样(当然一般都是依赖base包)。

如果需要一个基于R的基础包,Dirk Eddelebuettel和Carl Boettiger维护了,这里集中了R可以使用的所有容器镜像。基础包位于rocker/r-base下,我们期望镜像可以重现,也就是任何时候运行都会产生同样的结果,为了达到目的,在rocker/r-ver目录下维护了3.1.0版本之前的R,这样可以运行任何日期之前的程序(感谢Dirk Eddelebuettel)。接下来我们需要查找满足R要求的镜像,可以使用如下命令获得R版本:
R.Version()$version.string

因此,可以以如下标识开始一个Dockerfile:
FROM rocker/r-ver:3.4.4

## RUN
到这一步,可以加入一些运行时的短指令,例如创建接收分析数据的目录:
FROM rocker/r-ver:3.4.4
RUN mkdir /home/analysis

## Install our package #
这条命令让R执行一些命令行,R -e "my code",用这个模式在特定日期安装依赖脚本,可以设置“repos”到特定日期,并且使用CRAN的镜像。
FROM rocker/r-ver:3.4.4
RUN mkdir /home/analysis
RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/2019-01-06/')); \
install.packages('tidystringdist')"

## Aside : making it more programmable with ARG
如果使用ARG参数可以修改生成时间,参数是:--build-arg WHEN=
FROM rocker/r-ver:3.4.4
ARG WHEN
RUN mkdir /home/analysis
RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/${WHEN}')); \
install.packages('tidystringdist')"

{tidystringdist} 将会安装我们要求日期的版本,即使我们在很久之后才执行这条命令。
## COPY
现在,需要将主机上的分析脚本放到容器中,可以使用COPY localfile pathinthecontainer方式。注意这里的myscript.R和Dockerfile要在同一个目录下:
FROM rocker/r-ver:3.4.4
ARG WHEN
RUN mkdir /home/analysis
RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/${WHEN}')); \
install.packages('tidystringdist')"
COPY myscript.R /home/analysis/myscript.R

## CMD
CMD是每次运行Docker都要运行的命令。
FROM rocker/r-ver:3.4.4
ARG WHEN
RUN mkdir /home/analysis
RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/${WHEN}')); \
install.packages('tidystringdist')"
COPY myscript.R /home/analysis/myscript.R
CMD R -e "source('/home/analysis/myscript.R')"

# Build 和 run
## Build
我们的需求是:运行过去日期的分析工作,需要使用 --build-arg WHEN= 参数,只要在=后加入日期即可。在终端Dockerfile目录下,运行:
docker build --build-arg WHEN=2019-01-06 -t analysis .

-t name是镜像的名字,. 意味着Dockerfile在同一个目录下。
## run
执行命令:
docker run analysis 

分析作业即可被执行。
#导出容器内容
现在我们迎来了下一项任务:访问由容器之外分析源(这里为p.csv)提供的相关内容;换言之,这些内容处于主机之上。相信大家都很明确,目前一切在容器之内发生的操作都只会影响到容器内部。 因此,我们需要的就是让Docker容器与主机之间共用一个文件夹。为了达成这项目标,我们将要使用所谓Volume,简单来讲,大家可以将其理解成一种告知Docker容器如何将主机上的文件夹作为容器内文件夹的方法。

这样一来,当容器被关闭之后,容器在该文件夹当中创建的所有内容都将得以保留。为此,我们将在运行容器时使用-v标志,同时配合path/from/host:/path/in/container。此外,我们还需要创建一个文件夹以接收来自容器与主机的结果:
FROM rocker/r-ver:3.4.4

ARG WHEN

RUN mkdir /home/analysis

RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/${WHEN}')); \
install.packages('tidystringdist')"

COPY myscript.R /home/analysis/myscript.R

CMD cd /home/analysis \
&& R -e "source('myscript.R')" \
&& mv /home/analysis/p.csv /home/results/p.csv

mkdir ~/mydocker/results
docker run -v ~/mydocker/results:/home/results analysis

等待计算完成,然后……
ls ~/mydocker/results  
p.csv

OK
#下面我们该做什么?
到这里,每一次启动这个Docker镜像时,分析都将得到执行并给出结果。另外,其中不存在依赖性问题:软件包将始终根据你的需要开始安装。虽然过程可能有点耗时,这是因为每次运行容器时软件包都会从头安装;但正如我在开头的声明中所提到,这是为了对Docker、R以及再现性做出基本介绍,旨在帮助更多初学者顺利上手Docker方案:)

下面我们再进行一点拓展讨论:

如果大家希望自己的分析以软件包版本为基础,而非以安装时间为基础,则可使用remotes::install_version()。
FROM rocker/r-ver:3.4.4

RUN R -e "install.packages('remotes'); \
remotes::install_version('tidystringdist', '0.1.2')"

...

另外,你可以使用Volume以追踪传入容器内的数据,这样任何处于同一环境中的数据都将接受分析处理。

原文链接:An Introduction to Docker for R Users(翻译:杨峰)

R用户如何使用Docker

hokingyang 发表了文章 • 0 个评论 • 1807 次浏览 • 2019-01-29 10:24 • 来自相关话题

#什么是Docker Docker是“一种实现在操作系统层面的虚拟化软件,也称为容器”。这是Wikipedia的定义,对于不熟悉的人来说太晦涩难懂了。 简单说,Docker是一类程序,使得在自己的机器上(称为host)调度 ...查看全部
#什么是Docker
Docker是“一种实现在操作系统层面的虚拟化软件,也称为容器”。这是Wikipedia的定义,对于不熟悉的人来说太晦涩难懂了。

简单说,Docker是一类程序,使得在自己的机器上(称为host)调度(启动或者停止)多个操作系统(称为容器)。假设有10台运行不同Linux系统的树莓派,每台都运行不同服务,实际上可以在自己的机器上启停这些树莓派设备。
#为什么要在R中使用Docker
Docker可以实现在镜像或者容器中内置环境,意味着可以在Macbook上运行Linux,或者在本机运行R 3.5而同时在虚机里运行R 3.3环境。同时,也意味着为某些特殊目的在虚拟环境中使用较老版本的环境包,而本机则保持最新状态。

这样可以解决“依赖性”问题,如果担心环境改变会影响最新环境,可以建立一个虚拟容器运行需要的环境,可以是Linux、R或者任何其他需要的包。
# Docker镜像和Docker容器
在机器上,需要两类东西,镜像和容器。镜像可以看做操作系统,而容器可以认为是镜像的运行态。镜像只需要运行一次,而容器则在需要时候随时启动,当然一个镜像可以同时运行多个实例。

和R对比,安装和装载package类似于镜像和容器,一个package只需要下载一次,但是可以运行多个实例。同样在metaphore概念上也有类比:通过install.packages()来编译镜像,用library()来运行镜像。
# Dockerfile
Docker镜像根据Dockerfile建立。Dockerfile是配置文件,其中定义了:依赖的Docker镜像,如何配置操作系统,运行容器时做什么。有点类似于R包中的DESCRIPTION NAMESPACE文件,其中也定义了依赖包,元信息,以及使用library调用后用户可用的函数和数据。

因此,可以为R写一个非常基础的Dockerfile文件,目的是可重复性。也就是说:假如生成了一个分析环境(例如,在一个R文件中定义),而且希望不管以后系统如何升级这个分析环境仍然可以工作。

首先,创建一个分析目录和Dockerfile:
mkdir ~/mydocker
cd ~/mydocker
touch Dockerfile

假如运行程序为位于~/mydocker目录下的myscript.R:
library(tidystringdist)
df <- tidy_comb_all(iris, Species)
p <- tidy_stringdist(df)
write.csv(p, "p.csv")

## FROM
每个Dockerfile都以FROM开头,定义从哪个image开始创建。网上有很多官方发布的镜像,也可以从本地自己建一个开始。FROM定义了镜像的依赖关系,就跟R中生成一个包需要依赖一个另外的包一样(当然一般都是依赖base包)。

如果需要一个基于R的基础包,Dirk Eddelebuettel和Carl Boettiger维护了,这里集中了R可以使用的所有容器镜像。基础包位于rocker/r-base下,我们期望镜像可以重现,也就是任何时候运行都会产生同样的结果,为了达到目的,在rocker/r-ver目录下维护了3.1.0版本之前的R,这样可以运行任何日期之前的程序(感谢Dirk Eddelebuettel)。接下来我们需要查找满足R要求的镜像,可以使用如下命令获得R版本:
R.Version()$version.string

因此,可以以如下标识开始一个Dockerfile:
FROM rocker/r-ver:3.4.4

## RUN
到这一步,可以加入一些运行时的短指令,例如创建接收分析数据的目录:
FROM rocker/r-ver:3.4.4
RUN mkdir /home/analysis

## Install our package #
这条命令让R执行一些命令行,R -e "my code",用这个模式在特定日期安装依赖脚本,可以设置“repos”到特定日期,并且使用CRAN的镜像。
FROM rocker/r-ver:3.4.4
RUN mkdir /home/analysis
RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/2019-01-06/')); \
install.packages('tidystringdist')"

## Aside : making it more programmable with ARG
如果使用ARG参数可以修改生成时间,参数是:--build-arg WHEN=
FROM rocker/r-ver:3.4.4
ARG WHEN
RUN mkdir /home/analysis
RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/${WHEN}')); \
install.packages('tidystringdist')"

{tidystringdist} 将会安装我们要求日期的版本,即使我们在很久之后才执行这条命令。
## COPY
现在,需要将主机上的分析脚本放到容器中,可以使用COPY localfile pathinthecontainer方式。注意这里的myscript.R和Dockerfile要在同一个目录下:
FROM rocker/r-ver:3.4.4
ARG WHEN
RUN mkdir /home/analysis
RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/${WHEN}')); \
install.packages('tidystringdist')"
COPY myscript.R /home/analysis/myscript.R

## CMD
CMD是每次运行Docker都要运行的命令。
FROM rocker/r-ver:3.4.4
ARG WHEN
RUN mkdir /home/analysis
RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/${WHEN}')); \
install.packages('tidystringdist')"
COPY myscript.R /home/analysis/myscript.R
CMD R -e "source('/home/analysis/myscript.R')"

# Build 和 run
## Build
我们的需求是:运行过去日期的分析工作,需要使用 --build-arg WHEN= 参数,只要在=后加入日期即可。在终端Dockerfile目录下,运行:
docker build --build-arg WHEN=2019-01-06 -t analysis .

-t name是镜像的名字,. 意味着Dockerfile在同一个目录下。
## run
执行命令:
docker run analysis 

分析作业即可被执行。
#导出容器内容
现在我们迎来了下一项任务:访问由容器之外分析源(这里为p.csv)提供的相关内容;换言之,这些内容处于主机之上。相信大家都很明确,目前一切在容器之内发生的操作都只会影响到容器内部。 因此,我们需要的就是让Docker容器与主机之间共用一个文件夹。为了达成这项目标,我们将要使用所谓Volume,简单来讲,大家可以将其理解成一种告知Docker容器如何将主机上的文件夹作为容器内文件夹的方法。

这样一来,当容器被关闭之后,容器在该文件夹当中创建的所有内容都将得以保留。为此,我们将在运行容器时使用-v标志,同时配合path/from/host:/path/in/container。此外,我们还需要创建一个文件夹以接收来自容器与主机的结果:
FROM rocker/r-ver:3.4.4

ARG WHEN

RUN mkdir /home/analysis

RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/${WHEN}')); \
install.packages('tidystringdist')"

COPY myscript.R /home/analysis/myscript.R

CMD cd /home/analysis \
&& R -e "source('myscript.R')" \
&& mv /home/analysis/p.csv /home/results/p.csv

mkdir ~/mydocker/results
docker run -v ~/mydocker/results:/home/results analysis

等待计算完成,然后……
ls ~/mydocker/results  
p.csv

OK
#下面我们该做什么?
到这里,每一次启动这个Docker镜像时,分析都将得到执行并给出结果。另外,其中不存在依赖性问题:软件包将始终根据你的需要开始安装。虽然过程可能有点耗时,这是因为每次运行容器时软件包都会从头安装;但正如我在开头的声明中所提到,这是为了对Docker、R以及再现性做出基本介绍,旨在帮助更多初学者顺利上手Docker方案:)

下面我们再进行一点拓展讨论:

如果大家希望自己的分析以软件包版本为基础,而非以安装时间为基础,则可使用remotes::install_version()。
FROM rocker/r-ver:3.4.4

RUN R -e "install.packages('remotes'); \
remotes::install_version('tidystringdist', '0.1.2')"

...

另外,你可以使用Volume以追踪传入容器内的数据,这样任何处于同一环境中的数据都将接受分析处理。

原文链接:An Introduction to Docker for R Users(翻译:杨峰)

R用户如何使用Docker

hokingyang 发表了文章 • 0 个评论 • 1807 次浏览 • 2019-01-29 10:24 • 来自相关话题

#什么是Docker Docker是“一种实现在操作系统层面的虚拟化软件,也称为容器”。这是Wikipedia的定义,对于不熟悉的人来说太晦涩难懂了。 简单说,Docker是一类程序,使得在自己的机器上(称为host)调度 ...查看全部
#什么是Docker
Docker是“一种实现在操作系统层面的虚拟化软件,也称为容器”。这是Wikipedia的定义,对于不熟悉的人来说太晦涩难懂了。

简单说,Docker是一类程序,使得在自己的机器上(称为host)调度(启动或者停止)多个操作系统(称为容器)。假设有10台运行不同Linux系统的树莓派,每台都运行不同服务,实际上可以在自己的机器上启停这些树莓派设备。
#为什么要在R中使用Docker
Docker可以实现在镜像或者容器中内置环境,意味着可以在Macbook上运行Linux,或者在本机运行R 3.5而同时在虚机里运行R 3.3环境。同时,也意味着为某些特殊目的在虚拟环境中使用较老版本的环境包,而本机则保持最新状态。

这样可以解决“依赖性”问题,如果担心环境改变会影响最新环境,可以建立一个虚拟容器运行需要的环境,可以是Linux、R或者任何其他需要的包。
# Docker镜像和Docker容器
在机器上,需要两类东西,镜像和容器。镜像可以看做操作系统,而容器可以认为是镜像的运行态。镜像只需要运行一次,而容器则在需要时候随时启动,当然一个镜像可以同时运行多个实例。

和R对比,安装和装载package类似于镜像和容器,一个package只需要下载一次,但是可以运行多个实例。同样在metaphore概念上也有类比:通过install.packages()来编译镜像,用library()来运行镜像。
# Dockerfile
Docker镜像根据Dockerfile建立。Dockerfile是配置文件,其中定义了:依赖的Docker镜像,如何配置操作系统,运行容器时做什么。有点类似于R包中的DESCRIPTION NAMESPACE文件,其中也定义了依赖包,元信息,以及使用library调用后用户可用的函数和数据。

因此,可以为R写一个非常基础的Dockerfile文件,目的是可重复性。也就是说:假如生成了一个分析环境(例如,在一个R文件中定义),而且希望不管以后系统如何升级这个分析环境仍然可以工作。

首先,创建一个分析目录和Dockerfile:
mkdir ~/mydocker
cd ~/mydocker
touch Dockerfile

假如运行程序为位于~/mydocker目录下的myscript.R:
library(tidystringdist)
df <- tidy_comb_all(iris, Species)
p <- tidy_stringdist(df)
write.csv(p, "p.csv")

## FROM
每个Dockerfile都以FROM开头,定义从哪个image开始创建。网上有很多官方发布的镜像,也可以从本地自己建一个开始。FROM定义了镜像的依赖关系,就跟R中生成一个包需要依赖一个另外的包一样(当然一般都是依赖base包)。

如果需要一个基于R的基础包,Dirk Eddelebuettel和Carl Boettiger维护了,这里集中了R可以使用的所有容器镜像。基础包位于rocker/r-base下,我们期望镜像可以重现,也就是任何时候运行都会产生同样的结果,为了达到目的,在rocker/r-ver目录下维护了3.1.0版本之前的R,这样可以运行任何日期之前的程序(感谢Dirk Eddelebuettel)。接下来我们需要查找满足R要求的镜像,可以使用如下命令获得R版本:
R.Version()$version.string

因此,可以以如下标识开始一个Dockerfile:
FROM rocker/r-ver:3.4.4

## RUN
到这一步,可以加入一些运行时的短指令,例如创建接收分析数据的目录:
FROM rocker/r-ver:3.4.4
RUN mkdir /home/analysis

## Install our package #
这条命令让R执行一些命令行,R -e "my code",用这个模式在特定日期安装依赖脚本,可以设置“repos”到特定日期,并且使用CRAN的镜像。
FROM rocker/r-ver:3.4.4
RUN mkdir /home/analysis
RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/2019-01-06/')); \
install.packages('tidystringdist')"

## Aside : making it more programmable with ARG
如果使用ARG参数可以修改生成时间,参数是:--build-arg WHEN=
FROM rocker/r-ver:3.4.4
ARG WHEN
RUN mkdir /home/analysis
RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/${WHEN}')); \
install.packages('tidystringdist')"

{tidystringdist} 将会安装我们要求日期的版本,即使我们在很久之后才执行这条命令。
## COPY
现在,需要将主机上的分析脚本放到容器中,可以使用COPY localfile pathinthecontainer方式。注意这里的myscript.R和Dockerfile要在同一个目录下:
FROM rocker/r-ver:3.4.4
ARG WHEN
RUN mkdir /home/analysis
RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/${WHEN}')); \
install.packages('tidystringdist')"
COPY myscript.R /home/analysis/myscript.R

## CMD
CMD是每次运行Docker都要运行的命令。
FROM rocker/r-ver:3.4.4
ARG WHEN
RUN mkdir /home/analysis
RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/${WHEN}')); \
install.packages('tidystringdist')"
COPY myscript.R /home/analysis/myscript.R
CMD R -e "source('/home/analysis/myscript.R')"

# Build 和 run
## Build
我们的需求是:运行过去日期的分析工作,需要使用 --build-arg WHEN= 参数,只要在=后加入日期即可。在终端Dockerfile目录下,运行:
docker build --build-arg WHEN=2019-01-06 -t analysis .

-t name是镜像的名字,. 意味着Dockerfile在同一个目录下。
## run
执行命令:
docker run analysis 

分析作业即可被执行。
#导出容器内容
现在我们迎来了下一项任务:访问由容器之外分析源(这里为p.csv)提供的相关内容;换言之,这些内容处于主机之上。相信大家都很明确,目前一切在容器之内发生的操作都只会影响到容器内部。 因此,我们需要的就是让Docker容器与主机之间共用一个文件夹。为了达成这项目标,我们将要使用所谓Volume,简单来讲,大家可以将其理解成一种告知Docker容器如何将主机上的文件夹作为容器内文件夹的方法。

这样一来,当容器被关闭之后,容器在该文件夹当中创建的所有内容都将得以保留。为此,我们将在运行容器时使用-v标志,同时配合path/from/host:/path/in/container。此外,我们还需要创建一个文件夹以接收来自容器与主机的结果:
FROM rocker/r-ver:3.4.4

ARG WHEN

RUN mkdir /home/analysis

RUN R -e "options(repos = \
list(CRAN = 'http://mran.revolutionanalytics.com/snapshot/${WHEN}')); \
install.packages('tidystringdist')"

COPY myscript.R /home/analysis/myscript.R

CMD cd /home/analysis \
&& R -e "source('myscript.R')" \
&& mv /home/analysis/p.csv /home/results/p.csv

mkdir ~/mydocker/results
docker run -v ~/mydocker/results:/home/results analysis

等待计算完成,然后……
ls ~/mydocker/results  
p.csv

OK
#下面我们该做什么?
到这里,每一次启动这个Docker镜像时,分析都将得到执行并给出结果。另外,其中不存在依赖性问题:软件包将始终根据你的需要开始安装。虽然过程可能有点耗时,这是因为每次运行容器时软件包都会从头安装;但正如我在开头的声明中所提到,这是为了对Docker、R以及再现性做出基本介绍,旨在帮助更多初学者顺利上手Docker方案:)

下面我们再进行一点拓展讨论:

如果大家希望自己的分析以软件包版本为基础,而非以安装时间为基础,则可使用remotes::install_version()。
FROM rocker/r-ver:3.4.4

RUN R -e "install.packages('remotes'); \
remotes::install_version('tidystringdist', '0.1.2')"

...

另外,你可以使用Volume以追踪传入容器内的数据,这样任何处于同一环境中的数据都将接受分析处理。

原文链接:An Introduction to Docker for R Users(翻译:杨峰)