2020系统综合实践 第5次实践作业
本次作业为Python专题。Python是将练习使用docker容器运行Python程序。Python是很常用的程序设计语言,但是Python程序的运行依赖于提前的系统环境配置,为了降低系统配置的复杂度,同时减小资源开销,将系统环境容器化是一种解决方案。请根据Python官方镜像的镜像说明,自定义Python镜像文件,将Python程序运行起来。
关于容器
(1)为便于程序修改调试,在容器启动时需将本地文件目录挂载至容器内的工作目录;
(2)如程序需要运行额外的Python库,请在自定义镜像时完成安装,安装方法参考docker hub上的Python镜像说明;
关于代码
(3)在(1)和(2)的基础上,通过容器完成简单helloworld、日历输出、mysql数据库操作、opencv程序的部署运行;
- mysql数据库可以使用之前作业创建的镜像
- opencv可以参照链接任意选择
关于python版本
(4)python2或python3版本不限,也可全部都做;
注意事项
(5)作业重点在于容器内为python程序运行所需的配置,python程序本身的代码量不做硬性要求;
具体实验内容如下所示:
一、Python环境搭建
首先,创建一个文件夹(我这里命名为python),用于保存本次实验所需的配置文件以及相关的python代码,文件的项目结构如下所示:
其中Dockerfile用于构造本次实验的镜像,requirements.txt 用于为opencv和mysql添加相关依赖,其余的四个py文件为本次完成简单helloworld、日历输出、mysql数据库操作、opencv程序的部署运行所要用到的代码文件。
相关的配置文件如下所示:
- dockerfile
FROM python:3.7
WORKDIR /usr/local/app
COPY requirements*.txt ./
# 修改源并安装依赖
RUN pip install -r requirements.txt -i https://pypi.douban.com/simple
# 实现命令行式调用容器
ENTRYPOINT ["python"]
#设置ENTRYPOINT默认参数
CMD ["hello.py"]
- requirements.txt
PyMySQL
opencv-python
编写完相关配置文件后,进入python文件夹打开终端,构造本次实验的镜像:
sudo docker build -t cykpython . #(cykpython是自定义的镜像名字)
二、简单程序的部署运行
- helloworld:
其中hello.py的代码如下:
print("hello world!")
运行程序如下所示:
sudo docker run -it -v /home/cyk/python/app:/usr/local/app --rm cykpython hello.py
相关参数说明:
-
使用-v将本地目录挂载到python工作目录以方便代码修改,-v参数指定方式为宿主机目录:容器内目录;
-
冒号前的/home/cyk/python/app为hello.py代码的存储路径,冒号后的/usr/local/app为dockerfile中WORKDIR的参数,它是是处于容器内,而不是宿主机内的;
-
--rm表示运行完毕后自动移除容器;
-
日历输出:
其中date.py的代码如下:
import calendar
yy = int(input("输入年份: "))
mm = int(input("输入月份: "))
print(calendar.month(yy,mm))
运行程序如下所示:
sudo docker run -it -v /home/cyk/python/app:/usr/local/app --rm cykpython date.py
需注意的是,因为需要输入年份和月份,因此需要使用交互式容器,如果缺少了-it参数,则无法输入。
- mysql数据库操作:
这里使用之前实验二创建的数据库容器作为数据库实验对象.
先进入容器(我这里的数据库容器名是cyk1_mysql),接着再使用相关账号和密码登录数据库,如下所示:
sudo docker exec -it cyk1_mysql /bin/bash
查看目前存在的数据库,然后进入之前创建的数据库并查看表中的内容,如下所示:
由此我们得到了进行数据库操作之前docker_mysql数据库的状态以及user表中的内容,之后就可以开始相关的mysql数据库操作了。
其中mysql.py的代码如下:
import pymysql
# 打开数据库连接
db = pymysql.connect("cyk1_mysql", "root", "123456", "docker_mysql")
# 第一个参数是本地容器名字
# 第二三个参数是数据库的使用用户与密码
# 第四个参数是数据库名称
# 创建游标对象
cursor = db.cursor()
# 先查询一次数据库数据
sql = """select * FROM user"""
cursor.execute(sql)
results = cursor.fetchall()
print(results)
# SQL插入语句
sql = """insert user(id,name,age,sdept)
values('031702433','lxx',22,'IS')"""
cursor.execute(sql)
db.commit()
# 插入完成后再读取一次数据库数据
sql = """select * FROM user"""
cursor.execute(sql)
results = cursor.fetchall()
print(results)
# 关闭数据库连接
db.close()
接着运行程序如下所示:
sudo docker run -it --rm -v /home/cyk/python/app:/usr/local/app --link=cyk1_mysql cykpython mysql.py
如果运行程序时出现了如下错误,可参考我后面的解决方法:
最后查看程序成功运行后user表中的内容,可以看到我们成功地插入了一条数据:
- opencv操作:
其中cv.py的代码如下:
cv.py用于将图片旋转90度并保存
import cv2
# flags传入0表示灰度图像, 1表示彩色图像
img=cv2.imread('test.jpg',flags=1)
# 获取图片尺寸
rows,cols=img.shape[:2]
# 这里的第一个参数为旋转中心,第二个为旋转角度,第三个为旋转后的缩放因子
# 可以通过设置旋转中心,缩放因子,以及窗口大小来防止旋转后超出边界的问题
M=cv2.getRotationMatrix2D((cols/2,rows/2),90,1)
# 第三个参数是输出图像的尺寸中心
dst=cv2.warpAffine(img,M,(cols,rows))
# 写入文件
cv2.imwrite("result.jpg", dst, [int(cv2.IMWRITE_JPEG_QUALITY), 100])
print('success rotated!')
这里将要转换的图形放到app目录下(与cv.py同一目录),并命名为test.jpg。
运行程序如下所示:
sudo docker run -it -v /home/cyk/python/app:/usr/local/app --rm cykpython cv.py
在程序执行之后可以看到app目录下生成了result.jpg,接着查看test.jpg成功翻转后的图片result.jpg,如下所示:
最后给出整个实验成功完成后python文件夹的项目结构:
三、记录作业所花的时间:
项目 | 时间(估算) |
---|---|
搭建镜像 | 30min |
各个程序部署运行 | 4h |
写博客 | 1h30min |
四、实验遇到的问题和解决方法:
本次的实验相对简单,我遇到的问题主要是在mysql数据库操作的过程中出现的,第一次运行mysql.py程序后我出现了如下问题:
解决方法:在网上查找相关资料后,我知道了出现这个问题的原因是Mysql必须开启远程访问权限才允许远程连接,而root帐户是无法远程登陆的,只可以本地登陆。具体解决方法如下:
1.使用mysql数据库:
use mysql;
2.添加用户允许从任何主机连接到mysql服务器:
GRANT ALL PRIVILEGES ON *.* TO 'root'@'%' IDENTIFIED BY 'password' WITH GRANT OPTION;
允许任何IP地址(上面的 % 就是这个意思)的电脑使用root用户和密码(password)来访问这个MySQL Server
3.及时生效:
FLUSH PRIVILEGES
解决方法参考链接:https://www.cnblogs.com/-wenli/p/10411674.html
五、实验感谢:
本次的实验可以说是做的最顺利的实验之一了,实验过程遇到的问题相对较少,花了一个下午的时间完成了(希望以后的实验都能像这样就好了,哈哈哈哈哈~)。通过本次python专题实验,我更深入地认识了python编程的相关知识,也懂得了如何完成容器内为python程序时运行所需的配置,有了不少收获!