部署一个支持小组开展工作的jupyter环境

前言

python统一环境从来都是一个复杂的问题,特别是要多人合作的时候(甚至两个人合作要统一环境也经常出问题)。环境配置不一致很容易打击团队的积极性,让本来应该聚焦到具体问题解决上的注意力被分散。晚上有很多教程,都是只是讲某个技术细节的配置,很少有完整的方案。本教程详细介绍一下如何配置一个帮助管理员或者小组领导带领小队完成数据分析任务的jupyterhub环境,包括环境安装、用户配置等诸多细节。

内网穿透

是的,从内网穿透开始讲,太多的教程都会忽略服务最终如何访问到的问题,好像所有人都有了很好的网络环境,实际上的情况往往很复杂,很多新手可能就被“卡”在这里。当然,本教程也忽略了操作系统的安装这个步骤,尽量做到取舍有度。

假设你已经有了一台可以上网的ubuntu主机,本教程是基于一台NAT模式的虚拟Ubuntu进行的。登录tailscale的官网,找到对应的安装命令。

我用github账号登录的,其实这类服务一般都非常易用,就当游戏玩能学到不少东西

curl -fsSL https://tailscale.com/install.sh | sh
相关的详细教程可以在官网查到https://tailscale.com/download/linux,官网贴心的附带了分步骤安装教程。

如果“网络好”,一条命令,输入密码就能完成安装了

其实只是需要下载一个25MB的包,因为网络的原因,这个步骤我失败了很多次。原因是tailscale的服务器在境外。如果能有一个安装了科学透明代理的网络环境,这类服务安装起来会简单很多,等后续的教程中我在补这部分吧。

使用命令启动tailscale,然后访问地址进行验证就成功了

启动的命令是: tailscale up

这里有个小提示:命令行给出的地址,并不需要一定要“本机”登录,实际上我用我的笔记本电脑访问了图上的地址,完成了验证。

下一步我在macbook上安装tailscale终端,就可以进入虚拟的内网,访问服务器了。跨区原因不能在应用商店安装,用brew安装也很方便。

1
2
3
4
5
6
brew install tailscale #安装tailscale
sudo tailscaled install-system-daemon #启动为系统服务
#sudo tailscaled uninstall-system-daemon #这个命令应该是注销系统服务
tailscale up
tailscale ip #查看ip地址
tailscale status #查看设备情况

启动服务就可以把终端和服务器放在一个内网里了,这样可以随时访问到NAT中的虚拟服务器了。
我的教程这里相当于一个例子,如果你使用的是不同设备,官网有详细的教程,链接在这里安装终端的链接

本教程重点在于全面细节,为了能够随时访问到该机器,自然还要在机器上安装sshd服务,命令如下:

1
2
sudo apt install ssh
sudo systemctl ssh

然后,使用你自己习惯的ssh终端,通过tailscale服务的内网地址,就可以访问到服务器了。
这里有个个人碰到的小提示:我在tailscale使用中,有时明明服务在线,但是却访问不到主机,此时我发现使用ipv6就可以轻松访问到主机了。

安装conda

第一时间找到官方教程总是不会错的Miniconda,根据教程可以完成安装。

官方的教程如下:

1
2
3
4
mkdir -p ~/miniconda3
wget https://repo.anaconda.com/miniconda/Miniconda3-latest-Linux-x86_64.sh -O ~/miniconda3/miniconda.sh
bash ~/miniconda3/miniconda.sh -b -u -p ~/miniconda3
rm -rf ~/miniconda3/miniconda.sh

以下教程均是按照官方脚本执行之后配置。不过,这里强烈建议不要完全按照官方教程来做,原因见后面章节。如果你能把教程全部看完之后再操作,建议把minicoda安装在/opt/miniconda/。

安装好之后,记得运行~/miniconda3/bin/conda init bash这个命令把miniconda加入到环境变量里,然后重新登录一下就激活了conda的base环境了。

安装jupyterhub

虽然也有非常方便的tljh安装方式。实际落地的话,下载tljh特别考验网络速度,完全没有conda来的快捷,另外使用conda安装更好定制,所以,这里推荐用conda来安装jupyterhub。

1
2
3
4
5
6
7
8
9
10
11
12
conda create -n python310 python=3.10 #创建基础环境
conda create -n jupyterhub --clone python310 #根据基础环境创建jupyterhub环境
#这里提供一些可能会用到的管理命令
#conda env remove --name jupyterhub #适当的时候可以删除环境
#conda env list #现实当前的环境列表
conda activate jupyterhub #激活环境
#conda search -c conda-forge nodejs --info #找到允许的版本列表
conda install nodejs #安装node
npm install -g configurable-http-proxy #这个可以安装代理服务
python3 -m pip install jupyterhub jupyter notebook #这个可以顺利安装notebook
#如果网速过于慢,可以试试国内的源
#pip install jupyterhub jupyter notebook -i http://pypi.douban.com/simple/ --trusted-host pypi.douban.com

经过上面的操作,jupyterhub已经装好了,可以尝试启动jupyterhub了。

1
2
3
4
mkdir ~/jupyterhub #创建用来放置jupyterhub的目录
cd ~/jupyterhub/
jupyterhub --generate-config #会生成配置文件模版
jupyterhub -f jupyterhub_config.py #运行jupyterhub,这个命令一般也用来测试jupyterhub文件

如果一切正常访问http://ip:8000这个地址就可以看到jupyterhub界面了,然后就是把jupyterhub配置的可用。
这里特别提示一下,jupyterhub默认使用的是linux系统本身的用户账户系统,用户名和口令就是linux系统本身的用户名和口令,新建用户也是同理。

配置jupyterhub

配置jupyterhub也是很重要的一环,基本而言就是围绕配置文件进行;不过在那之前可以考虑先把内核配置好。

1
2
3
4
5
pip3 install ipykernel
python3 -m ipykernel install --name=jupyterhub --display-name "dev_default"
#jupyter kernelspec list #列出kernel
#jupyter kernelspec uninstall jupyterhub #卸载kernel
pip install -i https://pypi.tuna.tsinghua.edu.cn/simple pandas # 安装一个包看看虚拟环境中的包是否在kernel中生效

两个心得:

  1. 因为使用jupyterhub环境安装的jupyterhub(怎么读着那么绕……),所有jupyterhub再后来的子用户就默认都具有jupyterhub这个虚拟环境,安装kernel至少在这里并不是必须的(更绕了),但这里还是提一下,如果想给所有用户都配置可选的kernel意外的困难,毕竟jupyterhub就装在jupyterhub虚拟环境下(……);
  2. pip -i参数可以加快安装速度,另外也不用额外的更改源,意外的好用。

直接成功,这样就可以随意调整kernel的环境了

1
2
3
4
5

``` python
c.JupyterHub.admin_users = {'peter'}
c.Spawner.default_url = 'tree'
c.LocalAuthenticator.create_system_users = True

以上命令分别是设置默认界面、设置管理员、设置添加用户方式等等,这个方面可以参考文档,当然直接阅读jupyterhub --generate-config命令生成的模版学习如何配置也是非常棒的。学习的重点就是更改一些配置,然后用命令直接运行看看结果。很多问题是在使用中发现的,比如现在jupyterhub添加用户是会报错的。

添加用户报错

这个报错是我意料中的,原因自然是权限不足,目前普通账户无法创建用户。(意料中出错,然后修正,有点测试驱动的意味在里面呢)。为了解决以上问题,同时也是为了方便日常管理jupyterhub服务,把这个注册为系统服务。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
which jupyterhub #这个命令确定Environment的目录

#这段脚本根据你自己的情况改一下再用
sudo sh -c "cat <<EOT > /etc/systemd/system/jupyterhub.service
[Unit]
Description=JupyterHub

[Service]
User=root
Environment=PATH=/home/peter/miniconda3/envs/jupyterhub/bin/:/usr/local/bin/:/usr/bin/:/usr/sbin/
ExecStart=/home/peter/miniconda3/envs/jupyterhub/bin/jupyterhub -f /home/peter/jupyterhub/jupyterhub_config.py

[Install]
WantedBy=multi-user.target
EOT"
#以上命令是以root用户安装conda为例子进行的

sudo systemctl daemon-reload
sudo systemctl start jupyterhub
sudo systemctl enable jupyterhub
sudo systemctl status jupyterhub
#sudo systemctl restart jupyterhub
#sudo systemctl disable jupyterhub
#sudo systemctl stop jupyterhub
#sudo journalctl -u jupyterhub -n 50 #这是查看日志的命令

这样整个jupyterhub就配置好了。再次尝试添加用户,成功添加。
用户添加成功
然后用管理员登录,给这个用户设置一个密码sudo useradd -m -s /bin/bash hubuser && sudo passwd hubuser,用户就可以登录了,然后我们就看到了错误。

是的,没有成功,这个教程也会展示一些失败的部分

这是说明一开始就配置错误了,conda被安装在了用户目录下,新添加的用户完全访问不到。等于是官方教程的mkdir -p ~/miniconda3这个命令开始就出错了,应该把miniconda安装在/opt里才比较合适,事到如今,只能尝试修复一下权限了。

1
2
sudo -u hubuser /home/peter/miniconda3/envs/jupyterhub/bin/jupyterhub-singleuser -h
chmod 755 ~/home/peter/

提示:如果有机会重新配置conda,一定要安装在/opt目录。

经历漫长的配置,“一般”用户可以关注开发了

虽然配置工作很辛苦,不过至少环境可以统一了,如果用户多一点(也不需要特别多,节约的精力依然可观),使用conda在对应虚拟环境下安装的包都可以让所有用户共享。对于某些的特定的共享文件,可以放在共享系统库目录中共享,python -c "import sys;print(sys.path)"命令输出的地址都可以放置共享文件。另外对于,需要使用ctypes.cdll.LoadLibrary函数加载的模块,系统会寻找LD_LIBRARY_PATH设置的目录,对于systemd,设置两个节点就可以了。

1
2
3
4
#这是配置例子,实际测试过并没有成功
[Service]
Environment="PATH=/usr/local/bin:/usr/bin:/bin"
Environment="LD_LIBRARY_PATH=/opt/gams/"

是的,最终没有成功,jupyterhub貌似忽略了systemd的环境变量

需要在jupyterhub_config.py文件中配置保留哪些环境变量参考链接

1
c.Spawner.env_keep = ['LD_LIBRARY_PATH','PATH', 'PYTHONPATH', 'CONDA_ROOT', 'CONDA_DEFAULT_ENV', 'VIRTUAL_ENV', 'LANG', 'LC_ALL', 'JUPYTERHUB_SINGLEUSER_APP']

我们来捋一下环境变量的传递:首先系统运行bash的时候会加载用户自己和系统通用的环境变量->conda环境会激活部分环境变量->systemd的unit文件忽略系统变量,可以自己设置->jupyterhub要设置过滤哪些,默认继承的环境变量里没有LD_LIBRARY_PATH。感觉就是个环境变量的传递游戏。

环境变量最终“穿透”成功

用户目录配置

sudo mkdir share && chmod 777 share/首先建立一个目录供所有人共享使用。

建立起基本的目录结构
mkdir pub codes project

通过以下方式可讲目录的权限给到任意用户。

1
2
3
4
5
6
cd /var/share/project/
mkdir 01-notebooks
sudo su
chmod 777 01-notebooks
cd /home/hubuser/
ln -s /var/share/project/01-notebooks 01-notebooks

通过以上设置,就可以使用linux的权限管理机制来管理用户的文件了。

gams安装

这是安装文档

这个可以用来参考在虚拟环境中安装gams

安装gams其实比想的要简单,只要按照文档把gams解压,并配置好环境变量就可以了。

对于jupyterhub的情况,在systemd的注册脚本中,在Environment配置节点,把gams所在的目录添加进去,就可以完成配置了。本教程主打一个详细,看到无数教程都写如何配置,但是最重要的其实是怎么确定配置好了。这里提供gams的例子:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
sh -c "cat <<EOT > ~/example.gams
Sets
i canning plants / seattle, san-diego /
j markets / new-york, chicago, topeka / ;

Parameters

a(i) capacity of plant i in cases
/ seattle 350
san-diego 600 /

b(j) demand at market j in cases
/ new-york 325
chicago 300
topeka 275 / ;

Table d(i,j) distance in thousands of miles
new-york chicago topeka
seattle 2.5 1.7 1.8
san-diego 2.5 1.8 1.4 ;

Scalar f freight in dollars per case per thousand miles /90/ ;

Parameter c(i,j) transport cost in thousands of dollars per case ;

c(i,j) = f * d(i,j) / 1000 ;

Variables
x(i,j) shipment quantities in cases
z total transportation costs in thousands of dollars ;

Positive Variable x ;

Equations
cost define objective function
supply(i) observe supply limit at plant i
demand(j) satisfy demand at market j ;

cost .. z =e= sum((i,j), c(i,j)*x(i,j)) ;

supply(i) .. sum(j, x(i,j)) =l= a(i) ;

demand(j) .. sum(i, x(i,j)) =g= b(j) ;

Model transport /all/ ;

Solve transport using lp minimizing z ;

Display x.l, x.m ;
EOT"

以上是官方例子的模型,在用python调用。

1
2
3
4
5
6
7
from gams import GamsWorkspace
import os
ws = GamsWorkspace()
job = ws.add_job_from_file(os.getcwd() + "/example.gams")
job.run()
for rec in job.out_db["x"]:
print(f"x({rec.key(0)},{rec.key(1)}): level={rec.level} marginal={rec.marginal}")

这就是配置好的效果~

小结

至此,一个小型的可多人共享的jupyterhub配置好了,团队需要共享的代码可以放到share目录中,权限根据linux系统的权限来管理。对于管理员来说,需要进行的操作无非就是如下几种:

  1. 创建用户,并设置密码以及忘记密码时重置密码
  2. 维护项目目录的文件内容
  3. 把目录挂载给指定用户,并设置适当的权限
  4. 删除用户的权限或者不允许其再看到对应的目录
  5. 给虚拟环境安装适当的软件包

以上就是管理员所有操作的枚举,只要管理员熟悉了以上操作,就可以让团队利用好jupyterhub顺利推进工作啦。

在ubuntu上部署一个php网站

前言

很久没有写教程了。
其实日常写的东西并不少,但是我的博客还是断更了,距离上次写内容一个月以上了,这一个月的生活变化、人际关系变化特别多,总的来说:一切在客观上更加顺利了。
写下这篇教程的时间,我有非常多的想法,但是要把想法落地落实,却又需要很多的时间和精力,本着尽量留下痕迹的方式,如果要写就尽量留下公开的痕迹吧,本着这样的思路写下这篇php网站的部署博客。

环境部署

第一步是安装ubuntu,有一个可以部署应用的系统。由于本文撰写的时间,我选择了ubuntu 22.04(友人推荐的长期支持版),至于ubuntu的安装这里不在赘述。

装好的干净的Ubuntu

设置swap

新的机器,最好设置一下swap防止内存不足,我的机器是2g,设置4g的交换空间应该就足够了。
相关脚本如下:

1
2
3
4
5
6
7
8
sudo swapon --show #查看是否设置了交换空间
sudo fallocate -l 2G swapfile #创建交换文件
# sudo dd if=/dev/zero of=/swapfile bs=1G count=2 #fallocate不可用时采用这个命令
sudo chmod 600 swapfile #设置文件权限
sudo mkswap swapfile #创建交换文件
sudo swapon swapfile #启用交换文件
echo "/swapfile none swap sw 0 0" | sudo tee -a /etc/fstab #添加内容到启动项中
free -h #检查是否成功

我的系统是使用虚拟机安装的,一开始就被设置好了交换分区了。

交换分区一开始就设置好了

安装docker

第一步,肯定是安装docker,虽然整个网站是使用的php,不过,数据库最好还是容器化比较简单,安装docker按照教程来就可以。Install Docker Engine on Ubuntu,这是安装教程链接,使用过多次,每次都很顺利。

卸载旧版本:这个命令是卸载旧版本用的,如果没有安装旧版本,可以不用这个。

1
for pkg in docker.io docker-doc docker-compose docker-compose-v2 podman-docker containerd runc; do sudo apt-get remove $pkg; done

设置docker的库,设置好docker软件库,为下载做准备

1
2
3
4
5
6
7
8
9
10
11
12
sudo apt-get update
sudo apt-get install ca-certificates curl gnupg
sudo install -m 0755 -d /etc/apt/keyrings
curl -fsSL https://download.docker.com/linux/ubuntu/gpg | sudo gpg --dearmor -o /etc/apt/keyrings/docker.gpg
sudo chmod a+r /etc/apt/keyrings/docker.gpg

# Add the repository to Apt sources:
echo \
"deb [arch="$(dpkg --print-architecture)" signed-by=/etc/apt/keyrings/docker.gpg] https://download.docker.com/linux/ubuntu \
"$(. /etc/os-release && echo "$VERSION_CODENAME")" stable" | \
sudo tee /etc/apt/sources.list.d/docker.list > /dev/null
sudo apt-get update

安装docker,并进行测试安装效果

1
2
3
sudo apt-get install docker-ce docker-ce-cli containerd.io docker-buildx-plugin docker-compose-plugin

sudo docker run hello-world

安装openoffice

最好给openoffice单独建立一个目录,这样使用compose可以直接部署openoffice服务。
使用docker compose来部署openoffice服务

1
2
3
4
5
6
7
8
9
10
11
12
version: "3"

services:

onlyoffice:
container_name: oo7
image: onlyoffice/documentserver:7.4.1.1
ports:
- "9000:80"
restart: always
environment:
- JWT_SECRET=<yourkey>

当然可以使用命令解决以上问题:!!!注意,yourkey需要修改!!!

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
mkdir -p ~/workspace/onlyoffice
cat <<EOF | tee ~/workspace/onlyoffice/docker-compose.yaml
version: "3"

services:

onlyoffice:
container_name: oo7
image: onlyoffice/documentserver:7.4.1.1
ports:
- "9000:80"
restart: always
environment:
- JWT_SECRET=<yourkey>
EOF

sudo docker compose up -d #下载镜像,启动服务

如果想停止服务,可以使用一下命令 sudo docker compose down

http://localhost:9000,可以通过这个网址查看是不是部署成功了。

onlyoffice的镜像可能很大,可以把镜像提前准备好来节省实际部署时候的时间.

1
2
3
sudo docker images #这个命令查看镜像,找到要导出镜像的id
sudo docker save 0fdf2b4c26d3 > oo7.tar #导出镜像文件,其中参数就是镜像id
sudo docker load < oo7.tar #导入镜像

速度相当感人,如果不提前准备好镜像,一个小时就耗费在这个地方了

这里还有一个细节:下载好的镜像,可以放在一个公开的服务器上(比如放到对象存储上),这样用wget下载速度就快了。例子:wget https://www.example.com/directlink/bj/webs/oo7.tar

这里的细节其实很多,因为虚拟机是NAT模式联网,我通过web界面把文件上传到了服务器上。这时候发现如果我当初安装的server版,没有gui,那么这个工作还非常难以实现呢。虽然就算有GUI,也是因为我有自己的文件中转服务才能简单实现。

果然,一旦写起教程来,发现细节特别多

部署php环境

然后就是部署php环境的阶段,虽然按照正常流程是php、mysql、nginx这样依次安装,但是这样效率太低了,这里还是推荐用docker安装。使用docker-lnmp项目来进行php网站的配置,部署和后续迁移都会方便。

如果以dzzoffice项目的安装为例子,把源代码放到默认的www目录中,目录结构如下:
|____docker-lnmp
| |____nginx
| |____php74
| |____php81
| |____php73
| |____php72
| |____php71
| |____mysql
| |____php80
| |____php56
| |____redis
|____www
| |____static
| |____misc
| |____install
| |____user
| |____config
| |____dzz
| |____core
| |____data
| |____admin

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
find . -name "._*" -print ## 检查缓存文件
find . -name "._*" -delete ## 清除缓存
find ./ -mindepth 1 -maxdepth 2 -type d | sed -e 's;[^/]*/;|____;g;s;____|; |;g' 确认目录结构,如上图
cd docker-lnmp #来到环境目录
cp .env.example .env #创建配置文件
sed -i 's/NGINX_HOST_HTTP_PORT=.*/NGINX_HOST_HTTP_PORT=8086/' .env #替换其中的某些配置,比如,设置端口
docker network create backend --subnet=172.19.0.0/16 #关键步骤,为容器应用创建子网络
docker network ls | grep backend
docker compose up -d nginx php74 mysql #启动应用,这个命令会非常慢,可以尝试配置docker源的方式加速
# echo '{"registry-mirrors":["http://hub-mirror.c.163.com"]}' | sudo tee /etc/docker/daemon.json
# systemctl restart docker
# docker info #查看配置结果
# #在Dockerfile中的apt也可以配置更新源来加速,在apt-get update之前添加一行命令就可以了
# RUN sed -i s@/deb.debian.org/@/mirrors.aliyun.com/@g /etc/apt/sources.list
# #sed格式如下
# sed '/^RUN apt-get update/ i\
# RUN sed -i s@/deb.debian.org/@/mirrors.aliyun.com/@g /etc/apt/sources.list
# ' Dockerfile


docker compose restart nginx #修改配置后启动某些容器

sudo sh -c "cat <<'EOT' > ./docker-lnmp/nginx/conf.d/default.conf
server {
listen 80;
server_name localhost 127.0.0.1;

root /var/www;
index index.php index.html;

charset utf-8;
default_type text/html;

location / {
try_files \$uri \$uri/ /index.php\$is_args\$args;
}
include conf.d/fpm/php74-fpm;
}
EOT" #设置

上面的脚本细节特别坑,sh和cat会对 $ 解释两次,所以要用两次防止过滤的方式。

然后安装php网站会碰到以下错误:Host '172.19.0.74' is not allowed to connect to this MySQL server
参照这个解决思路可以通过更改访问权限来解决问题。

进入容器:docker compose exec mysql mysql -u root -p,
执行命令:

1
2
3
4
5
show databases;
use mysql;
select host,user from user; --查看用户权限配置
update user set host = '%' where user ='root'; --开放外部连接
flush privileges; --更新权限

然后就可以安装任意的php网站了,为了在网速“不快”的服务器上,可以利用docker save -o myimages.tar image1:tag1 image2:tag2 把多个镜像导出到一个文件,这样就可以整体搬家了。

bonus 配置部署包

网站在后期开发中可能需要添加扩展,扩展要通过composer安装。这样的情况目标机器上还是需要安装php,不同的系统不一样。rocky9.3参考这里

1
2
3
4
5
6
7
8
sudo dnf config-manager --set-enabled crb
sudo dnf install \
https://dl.fedoraproject.org/pub/epel/epel-release-latest-9.noarch.rpm \
https://dl.fedoraproject.org/pub/epel/epel-next-release-latest-9.noarch.rpm
sudo dnf install dnf-utils http://rpms.remirepo.net/enterprise/remi-release-9.rpm -y #key cmd line

dnf module list php
sudo dnf module enable php:remi-7.4 -y

当然还有个apt的例子。

1
2
3
4
5
sudo apt-get update
sudo apt -y install software-properties-common
sudo add-apt-repository ppa:ondrej/php
sudo apt-get update
sudo apt -y install php7.4

然后就是安装composer了,为了部署方便,安装在本地就可以。

1
2
3
4
5
php -r "copy('https://getcomposer.org/installer', 'composer-setup.php');"
php -r "if (hash_file('sha384', 'composer-setup.php') === 'e21205b207c3ff031906575712edab6f13eb0b361f2085f1f1237b7126d785e826a450292b6cfd1d64d92e6563bbde02') { echo 'Installer verified'; } else { echo 'Installer corrupt'; unlink('composer-setup.php'); } echo PHP_EOL;"
php composer-setup.php \
php -r "unlink('composer-setup.php');" \
php composer.phar require casdoor/casdoor-php-sdk #安装sdk的例子

新的问题配置到这里,虽然一切看似正常了,不过curl可以正常访问casdoor,可是php却提示缺少证书。这个时候才发现,证书是被配置在docker里的!因此,证书要暴露给docker……真的是复杂啊。

进入docker,参考这个文档可以临时更新证书。

1
2
sudo docker exec -it <container_id_or_name> bash
## update certificates

特别注意

如果修改了.env一定要重新rebuild,env的参数进入dockerfile是build时发生的。

1
2
docker compose down
docker compose up -d --build mysql nginx php74

新的问题

mysql可能会出现“Restarting (1) Less than a second ago”不断重启,这时可以用logs命令查看问题所在。

sudo docker logs container_id

具体例子dzzoffice部署

通过以上部署,dzzoffice网站就可以安装了,http://ip:port/install/index.php这个网址是固定安装目录。

先看到安装界面
检查扩展,php的扩展很多,安装程序先做检查

目录权限需要修正

chmod -R 777 config/ data/

填写数据库信息,这里会报错,参考教程修改数据库访问权限

安装过程非常迅速

设置管理员账户

网站运行起来了,然后就是设置,第一项是把onlyoffice配置好,在线浏览文章的功能是必要的。

`chmod 777 -R dzz/`给插件目录添加权限

onlyoffice要装

网盘也是必装

然后一个可以共享文件的小平台就建立好了。

Troubleshooting

使用文中的docker脚本,有时候再第一次配置错误的情况下,会产生“奇怪的跳转”,比如,访问http://127.0.0.1:8086会强制跳转到http://127.0.0.1,经过多次测试,发现这是“客户端”的某种“记忆”。解决方式也很简单,对于safari浏览器,可以把对应域名的缓存删除掉。对于Edge、chrome等浏览器,使用开发者模式,在”网络选项卡“上把”禁用缓存“勾选上,然后再访问一次这个网页就能把缓存遗忘了。

鸣谢

特别鸣谢我的妻子,她帮我写了一个小的手册文章,所以我有时间精力写下这篇教程。