本文属于机器翻译版本。若本译文内容与英语原文存在差异,则一律以英文原文为准。
安装其它内核和库
当创建包含 Amazon EMR 的集群时,将在 Docker 容器 JupyterHub 上安装适用于 Jupyter 的默认 Python 3 内核 PySpark 和适用于 Amazon EMR 的默认 Python 3 内核和适用于 Amazon EMR 的集群。可以安装其它内核。还可以安装其它库和软件包,然后将它们导入相应的 shell。
安装内核
内核安装在 Docker 容器中。安装内核最简单的方式是,创建包含安装命令的清除脚本,将脚本保存到主节点,然后使用 sudo docker exec jupyterhub
命令以在 script_name
jupyterhub
容器内运行脚本。以下示例脚本安装内核,然后在主节点上安装内核的一些库,以便之后在 Jupyter 中使用内核时可以导出库。
#!/bin/bash # Install Python 2 kernel conda create -n py27 python=2.7 anaconda source /opt/conda/envs/py27/bin/activate apt-get update apt-get install -y gcc /opt/conda/envs/py27/bin/python -m pip install --upgrade ipykernel /opt/conda/envs/py27/bin/python -m ipykernel install # Install libraries for Python 2 /opt/conda/envs/py27/bin/pip install paramiko nltk scipy numpy scikit-learn pandas
要在容器内安装内核和库,请打开至主节点的终端连接,将脚本保存到 /etc/jupyter/install_kernels.sh
,然后在主节点命令行上运行以下命令:
sudo docker exec jupyterhub bash /etc/jupyter/install_kernels.sh
使用库和安装其它库
Amazon EMR JupyterHub 上预安装有适用于 Python 3 的一组核心的机器学习和数据科学库。可以使用 sudo docker exec jupyterhub bash -c "conda list"
和 sudo docker exec jupyterhub bash -c "pip freeze"
。
如果 Spark 作业需要 Worker 节点上的库,建议使用引导操作运行脚本以在创建集群时安装库。集群创建过程中,引导操作将在所有集群节点上运行,这将简化安装。如果于集群运行后在核心/Worker 节点上安装库,则操作更复杂。我们在此部分中提供了示例 Python 程序以演示如何安装这些库。
此部分中演示的引导操作和 Python 程序示例都使用保存到 Amazon S3 的清除脚本在所有节点上安装库。
以下示例中引用的脚本将通过 pip
安装适用于 Python 3 内核的 paramiko、nltk、scipy、scikit-learn 和 pandas:
#!/bin/bash sudo python3 -m pip install boto3 paramiko nltk scipy scikit-learn pandas
创建脚本后,将其上载到 Amazon S3 中的位置(例如,s3://mybucket/install-my-jupyter-libraries.sh
)。有关更多信息,请参阅《Amazon Simple Storage Service 用户指南》中的上传对象,以便可以在引导操作或 Python 程序中使用此操作。
指定将在使用 Amazon CLI 创建集群时在所有节点上安装库的引导操作
创建与之前的示例类似的脚本并将脚本保存在 Amazon S3 中的位置。我们将使用示例
s3://mybucket/install-my-jupyter-libraries.sh
。使用创建集群, JupyterHub 并使用
--bootstrap-actions
选项的Path
参数指定脚本位置,如以下示例所示:注意
为了便于读取,包含 Linux 行继续符 (\)。它们可以通过 Linux 命令删除或使用。对于 Windows,请将它们删除或替换为脱字号(^)。
aws emr create-cluster --name="
MyJupyterHubCluster
" --release-label emr-5.36.0 \ --applications Name=JupyterHub --log-uris3://MyBucket/MyJupyterClusterLogs
\ --use-default-roles --instance-type m5.xlarge --instance-count2
--ec2-attributes KeyName=MyKeyPair
\ --bootstrap-actions Path=s3://mybucket/install-my-jupyter-libraries.sh
,Name=InstallJupyterLibs
指定将在使用控制台创建集群时在所有节点上安装库的引导操作
使用此直接链接导航到旧的亚马逊 EMR 控制台,网址为 https://console.aws.amazon.com/elasticmapreduce
。有关切换到旧主机时会发生什么的更多信息,请参阅使用旧控制台。 -
依次选择 Create cluster (创建集群)、Go to advanced options (转到高级选项)。
根据应用程序的情况,指定 Software and Steps (软件和步骤) 和 Hardware (硬件) 的设置。
在 General Cluster Settings (常规集群设置) 屏幕上,展开 Bootstrap Actions (引导操作)。
对于 Add bootstrap action (添加引导操作),选择 Custom action (自定义操作)、Configure and add (配置和添加)。
对于 Name (名称),输入一个易于理解的名称。对于 S c ript location (脚本位置),输入脚本在 Amazon S3 中的位置(我们使用的示例为 s3://mybucket/install-my-jupyter-libraries .sh)。保留 Optional arguments (可选参数) 为空,然后选择 Add (添加)。
指定集群的其它设置,然后选择 Next (下一步)。
指定安全设置,然后选择 Create cluster (创建集群)。
例 在运行集群的核心节点上安装库
在 Jupyter 内的主节点上安装库之后,可以通过不同的方式将库安装在运行的核心节点上。以下示例显示了编写为在本地计算机上运行的 Python 程序。当在本地运行 Python 程序时,此程序将使用 Amazon Systems Manager 的 AWS-RunShellScript
运行此节中之前所示的示例脚本,从而在集群的核心节点上安装库。
import argparse import time import boto3 def install_libraries_on_core_nodes( cluster_id, script_path, emr_client, ssm_client): """ Copies and runs a shell script on the core nodes in the cluster. :param cluster_id: The ID of the cluster. :param script_path: The path to the script, typically an Amazon S3 object URL. :param emr_client: The Boto3 Amazon EMR client. :param ssm_client: The Boto3 AWS Systems Manager client. """ core_nodes = emr_client.list_instances( ClusterId=cluster_id, InstanceGroupTypes=['CORE'])['Instances'] core_instance_ids = [node['Ec2InstanceId'] for node in core_nodes] print(f"Found core instances: {core_instance_ids}.") commands = [ # Copy the shell script from Amazon S3 to each node instance. f"aws s3 cp {script_path} /home/hadoop", # Run the shell script to install libraries on each node instance. "bash /home/hadoop/install_libraries.sh"] for command in commands: print(f"Sending '{command}' to core instances...") command_id = ssm_client.send_command( InstanceIds=core_instance_ids, DocumentName='AWS-RunShellScript', Parameters={"commands": [command]}, TimeoutSeconds=3600)['Command']['CommandId'] while True: # Verify the previous step succeeded before running the next step. cmd_result = ssm_client.list_commands( CommandId=command_id)['Commands'][0] if cmd_result['StatusDetails'] == 'Success': print(f"Command succeeded.") break elif cmd_result['StatusDetails'] in ['Pending', 'InProgress']: print(f"Command status is {cmd_result['StatusDetails']}, waiting...") time.sleep(10) else: print(f"Command status is {cmd_result['StatusDetails']}, quitting.") raise RuntimeError( f"Command {command} failed to run. " f"Details: {cmd_result['StatusDetails']}") def main(): parser = argparse.ArgumentParser() parser.add_argument('cluster_id', help="The ID of the cluster.") parser.add_argument('script_path', help="The path to the script in Amazon S3.") args = parser.parse_args() emr_client = boto3.client('emr') ssm_client = boto3.client('ssm') install_libraries_on_core_nodes( args.cluster_id, args.script_path, emr_client, ssm_client) if __name__ == '__main__': main()