☰
Anaconda 局域网远程访问 Jupyter Notebook 配置指南
2026/10/13 16:45:20 网站建设 项目流程

1. 为什么要在局域网里折腾 Jupyter Notebook 远程访问

很多人第一次听到"内网远程访问 Jupyter Notebook"这个需求,脑子里冒出来的第一个疑问是:我直接在本机跑不就行了吗,为什么非要远程?这个问题问得对,因为如果只是自己写两行 Python 脚本,本机跑确实最省事。但真实场景往往不是这样。

我遇到这个需求,最早是因为一台放在机房的深度学习工作站。那台机器装了两块显卡,跑模型训练的时候风扇声音跟吹风机一样,坐在旁边根本没法安心写代码。更现实的问题是,数据全在那台机器上,几十个 G 的数据集不可能每次都拷到笔记本上。于是最自然的想法就是:让那台机器当"计算服务器",我在自己的笔记本上通过浏览器连过去,用它的算力、用它的数据,但界面在我这边。

这就是 Jupyter Notebook 远程访问的核心价值——把计算和交互分离。计算跑在性能强的机器上,交互界面在你手边的设备上。Anaconda 在这里扮演的角色是环境管理器,它把 Python 解释器、Jupyter 以及一大堆科学计算库打包在一起,省去了手动配环境的麻烦。

但这里有个关键前提:内网(局域网)。为什么强调内网?因为内网环境相对封闭,机器之间通过交换机或路由器直连,不经过公网,配置起来简单、速度快、延迟低,而且不涉及任何对外暴露的问题。你不需要考虑域名、证书、端口映射这些让人头大的东西,只要两台机器在同一个网段里能互相 ping 通,事情就成了一半。

这篇文章适合谁看?三类人最对口。第一类是有多台机器(比如一台台式机加一台笔记本)的开发者,想把重活丢给性能好的那台。第二类是实验室或小团队里共用一台计算服务器的同学,需要多人各自连上去用。第三类是刚接触 Anaconda 和 Jupyter、想搞明白"服务端和客户端到底怎么分工"的新手。不管你属于哪一类,下面的内容都会从最基础的原理讲起,一步步带你跑通,并且把我踩过的坑都摊开说清楚。

需要提前说明的是,本文所有操作都限定在局域网内部,不涉及任何跨网络访问的配置。你只需要保证两台机器在同一个路由器或交换机下,能互相通信即可。

2. 搞懂 Jupyter 的服务端与客户端分工再动手

2.1 Jupyter Notebook 本质上是一个 Web 服务

很多人用了很久 Jupyter 都没意识到一件事:你平时在浏览器里打开的那个localhost:8888,其实是一个跑在本地的 Web 服务器。Jupyter Notebook 的架构非常清晰,它由两部分组成:一个是内核(Kernel),负责真正执行 Python 代码;另一个是 Web 服务器,负责把代码、输出、Markdown 渲染成网页给你看。

你平时双击图标启动 Jupyter,它做的事情就是:在本地的 8888 端口起一个 HTTP 服务,然后自动帮你打开浏览器访问这个地址。浏览器和这个服务之间的通信,走的是标准的 HTTP 协议加上 WebSocket(用于实时推送执行结果)。

理解这一点非常关键,因为它直接决定了远程访问的思路:既然它是个 Web 服务,那我只要让这个服务监听在一个别的机器能访问到的地址上,不就能远程连了吗?答案是对的,但默认配置下它只监听localhost,也就是只接受本机连接。我们要做的,就是把它改成监听所有网络接口,再加上一层访问控制。

2.2 为什么默认只监听 localhost

这是很多人第一次配置时最困惑的地方:我明明启动了 Jupyter,为什么同事的电脑就是连不上?

原因在于 Jupyter 的默认安全策略。它默认绑定127.0.0.1,这个地址是回环地址,只有本机能访问。这样设计是出于安全考虑——如果默认就监听所有接口,那同一网络下任何人只要知道你的 IP 和端口,就能直接打开你的 Notebook,执行任意代码。这在共享网络环境下是相当危险的。

所以我们要做的改动,本质上是主动打开这扇门,同时配上一把锁。打开门的方式是修改绑定地址,配锁的方式是设置密码和 token。这两件事必须一起做,只做前者不做后者,等于把家门敞开还贴个告示说"欢迎光临"。

2.3 Anaconda 环境下的 Jupyter 到底装在哪

还有一个容易被忽略的细节:Anaconda 里的 Jupyter 和你用 pip 单独装的 Jupyter,配置文件位置可能不一样。Anaconda 会把 Jupyter 装在它自己的环境目录下,配置文件默认生成在用户主目录的.jupyter文件夹里。

在 Windows 上,这个路径通常是C:\Users\你的用户名\.jupyter\;在 Linux 或 macOS 上,是~/.jupyter/。这个目录下的jupyter_notebook_config.py就是我们要改的核心文件。如果你从来没生成过这个文件,需要先运行一次生成命令,这个后面会讲。

搞清楚这三个基础认知,后面的操作就不会是"照着敲命令但不知道在干嘛"了。你知道每一步在改什么、为什么改,出问题的时候才能自己排查。

3. 服务端配置:让 Jupyter 愿意接受外部连接

3.1 生成配置文件这一步别跳过

假设你的服务端机器已经装好了 Anaconda,打开终端(Windows 用 Anaconda Prompt,Linux/macOS 用普通终端),先确认 Jupyter 能正常启动。然后执行下面这条命令生成配置文件:

jupyter notebook --generate-config

执行完你会看到类似这样的输出,告诉你配置文件生成到了哪个路径:

Writing default config to: /home/yourname/.jupyter/jupyter_notebook_config.py

注意:如果你之前已经生成过这个文件,这条命令会提示文件已存在,问你是否覆盖。这时候一定要选否(输入 n),否则你之前的配置就全没了。如果确实想重新生成,先把旧文件备份一下。

这个文件内容很长,全是注释,默认所有配置项都是被注释掉的。我们不需要全部看懂,只改几个关键项就行。

3.2 设置访问密码而不是裸奔

在改绑定地址之前,先把密码设好。Jupyter 提供了一个专门的命令来生成密码哈希:

jupyter notebook password

它会提示你输入两次密码,然后自动把加密后的哈希写进配置文件。这个密码就是你之后在浏览器里打开 Notebook 时需要输入的。为什么要用哈希而不是明文?因为配置文件是纯文本,如果直接写明文密码,任何能读到这个文件的人都能看到你的密码。哈希值即使被看到,也无法反推出原始密码。

设置完之后,你可以打开配置文件确认一下,会看到类似这样一行:

c.NotebookApp.password = 'argon2:$argon2id$v=19$m=10240,t=10,p=8$...'

看到这串东西就说明密码设置成功了。这里用的是 argon2 算法,比早期的 sha1 安全得多,Anaconda 较新版本默认都用这个。

3.3 修改绑定地址与端口

接下来是核心改动。用任意文本编辑器打开jupyter_notebook_config.py,找到下面这几行(它们默认都是注释状态),改成我们需要的值:

c.NotebookApp.ip = '0.0.0.0' c.NotebookApp.port = 8888 c.NotebookApp.open_browser = False c.NotebookApp.allow_remote_access = True

逐条解释一下为什么这么改。

c.NotebookApp.ip = '0.0.0.0'是让 Jupyter 监听所有网络接口。0.0.0.0不是一个真实地址,而是一个通配符,意思是"本机所有网卡上的地址都接受连接"。这样无论是通过 127.0.0.1 还是通过局域网 IP,都能访问到。

c.NotebookApp.port = 8888是端口号。8888 是 Jupyter 的默认端口,你也可以改成别的,比如 8890,只要不和其他服务冲突就行。如果 8888 被占用了,启动时会报错,换个端口即可。

c.NotebookApp.open_browser = False是让服务端启动时不要自动弹浏览器。因为服务端机器可能根本没有图形界面,或者你根本不需要在它上面看,关掉能省点资源,也避免报错。

c.NotebookApp.allow_remote_access = True是明确允许远程访问。有些版本即使设了0.0.0.0,如果这项是 False,仍然会被拦下来。

提示:不同版本的 Jupyter 配置项名称可能略有差异。较新的版本里,NotebookApp可能被ServerApp替代。如果你改了没生效,先确认一下你的 Jupyter 版本,用jupyter --version查看。如果版本较新,把c.NotebookApp.xxx换成c.ServerApp.xxx试试。

3.4 启动并验证服务端

配置改完,保存文件,然后在服务端启动 Jupyter:

jupyter notebook

如果配置正确,你会看到类似这样的输出:

[I 10:23:45.123 NotebookApp] Serving notebooks from local directory: /home/yourname [I 10:23:45.123 NotebookApp] Jupyter Notebook 6.4.5 is running at: [I 10:23:45.123 NotebookApp] http://your-hostname:8888/

注意看它打印出来的地址,如果显示的是0.0.0.0:8888或者你的主机名,而不是localhost:8888,说明绑定成功了。

这时候在服务端本机用浏览器访问http://localhost:8888应该能打开,输入密码后进入。但这只证明本机能用,还不能证明远程能连。真正的验证要在客户端机器上做,这个放到下一节。

3.5 防火墙这道坎必须过

服务端配置好了,客户端却连不上,十有八九是防火墙在拦。这是新手最容易卡住的地方,而且报错信息往往很模糊,浏览器只会显示"无法访问此网站",不会告诉你具体原因。

在 Linux 上,如果用的是 ufw,需要放行 8888 端口:

sudo ufw allow 8888/tcp

如果用的是 firewalld:

sudo firewall-cmd --permanent --add-port=8888/tcp sudo firewall-cmd --reload

在 Windows 上,第一次启动 Jupyter 监听外部地址时,系统通常会弹出一个防火墙提示框,问你是否允许该程序通过防火墙。这时候一定要勾选"专用网络"并允许,否则外部连接会被直接挡掉。如果当时手滑点了取消,需要手动去"Windows Defender 防火墙"的"允许应用通过防火墙"里把 Python 或 Jupyter 加进去。

注意:这里只放行局域网需要的端口即可,不要图省事把防火墙整个关掉。关防火墙虽然能快速解决问题,但会让机器完全暴露在局域网中,得不偿失。

4. 客户端连接:从另一台机器打开 Notebook

4.1 先确认两台机器能互相通信

在客户端机器上,第一步不是打开浏览器,而是先确认网络通不通。打开终端或命令行,ping 一下服务端的局域网 IP:

ping 192.168.1.100

这里的 IP 要换成你服务端的实际局域网地址。怎么查服务端的 IP?Linux 上用ip addr或ifconfig,Windows 上用ipconfig。找那个以 192.168 或 10 开头的地址,那就是局域网 IP。

如果 ping 不通,说明两台机器根本不在一个可通信的网络里,后面的都不用试了。常见原因有两个:一是两台机器连的不是同一个路由器或交换机;二是服务端开了防火墙把 ICMP 也拦了(这种情况少见,但存在)。先解决网络连通性,再谈 Jupyter。

4.2 浏览器访问与 token 处理

ping 通了之后,在客户端浏览器地址栏输入:

http://192.168.1.100:8888

把 IP 换成你的服务端地址。正常情况下,你会看到一个登录页面,要求输入密码。输入你在服务端设置的密码,就能进入 Notebook 界面了。

但有时候你会遇到另一种情况:页面提示需要 token。这是因为某些版本的 Jupyter 在首次启动时会生成一个一次性 token,即使你设了密码,它也可能要求先输入 token。token 在哪里找?就在服务端启动 Jupyter 时终端打印的那段输出里,有一行类似:

http://your-hostname:8888/?token=abc123def456...

把token=后面那串字符复制出来,粘贴到客户端的 token 输入框里即可。输入一次之后,后续就只需要密码了。

如果你觉得每次找 token 太麻烦,可以在配置文件里把 token 验证关掉,只保留密码验证:

c.NotebookApp.token = ''

提示:关掉 token 之后,密码就成了唯一的防线,所以密码一定要设得复杂一点。局域网虽然相对封闭,但同一网络下可能有其他设备,不能假设绝对安全。

4.3 用主机名代替 IP 的可行性

如果你觉得记 IP 太麻烦,也可以尝试用主机名访问,比如http://my-workstation:8888。但这需要局域网内有 DNS 解析,或者你在客户端的 hosts 文件里手动加了映射。对于临时用用,直接记 IP 更省事;如果是长期使用,配个 hosts 映射会舒服很多。

在 Windows 上编辑C:\Windows\System32\drivers\etc\hosts,在 Linux/macOS 上编辑/etc/hosts,加一行:

192.168.1.100 my-workstation

之后就能用http://my-workstation:8888访问了。这个改动只影响你自己的机器,不影响别人。

4.4 连接成功后的实际体验

连上之后,你会发现操作体验和本机几乎没区别。新建 Notebook、写代码、运行、看输出,全都正常。唯一的差别是执行速度取决于服务端的性能,而不是你客户端机器的性能。如果你的服务端有 GPU,那在 Notebook 里用torch.cuda.is_available()检查一下,能返回 True 就说明 GPU 可用,接下来就能在远程环境里跑训练了。

文件管理方面,Notebook 里看到的目录是服务端的工作目录,不是你客户端的目录。你在 Notebook 里上传文件,文件是传到服务端去的;你下载文件,也是从服务端下载。这一点要心里有数,别搞混了。

5. 那些让我折腾半天的坑与排查思路

5.1 改了配置却不生效

这是最让人抓狂的情况:明明配置文件改对了,重启 Jupyter 后行为却和没改一样。我遇到过好几次,后来发现原因通常是这几个。

第一个原因是改错了配置文件。Anaconda 环境下可能存在多个 Jupyter 配置文件,比如你之前用 pip 装过一个 Jupyter,它的配置在另一个位置。Jupyter 启动时会按优先级读取,可能读的不是你改的那个。排查方法是启动时加--debug参数,看它到底加载了哪个配置文件:

jupyter notebook --debug

输出里会有一行Loading config file: ...,那个路径才是真正生效的文件。

第二个原因是配置项名称过时。前面提过,新版本把NotebookApp改成了ServerApp。如果你用的是 Jupyter Notebook 7 或 JupyterLab,配置项名称可能已经变了。这时候要么降级到旧版本,要么按新版本的名称改。

第三个原因是没重启服务。配置文件是启动时读取的,改完必须完全停掉 Jupyter 再重新启动,热重载是不存在的。

5.2 端口被占用怎么办

启动时报Address already in use,说明 8888 端口已经被别的程序占了。可能是你之前启动的 Jupyter 没关干净,也可能是别的服务在用这个端口。

先查是谁占用了端口。Linux 上用:

lsof -i :8888

Windows 上用:

netstat -ano | findstr :8888

找到进程号后,要么把它关掉,要么给 Jupyter 换个端口。换端口很简单,改配置文件里的c.NotebookApp.port,或者启动时直接指定:

jupyter notebook --port 8890

5.3 能 ping 通但浏览器打不开

这种情况最迷惑人:网络明明是通的,ping 有回应,但浏览器就是连不上。可能的原因有几个。

一是防火墙只放行了 ICMP 没放行 TCP。ping 用的是 ICMP 协议,而浏览器访问用的是 TCP。防火墙可能允许 ping 但拦住了 8888 端口的 TCP 连接。回到服务端检查防火墙规则,确认 8888 端口确实放行了。

二是Jupyter 实际没监听在 0.0.0.0。虽然你改了配置,但可能没生效(见上一节)。在服务端用netstat -tlnp | grep 8888看一下,如果显示的是127.0.0.1:8888而不是0.0.0.0:8888,说明绑定没改成功。

三是客户端和服务端不在同一网段。比如服务端是 192.168.1.x,客户端是 192.168.0.x,虽然都能上网,但互相之间可能被路由规则隔离。确认两台机器的 IP 前三段是否一致。

5.4 多人同时使用时的资源冲突

如果是一台服务器多人共用,会碰到一个现实问题:每个人启动 Jupyter 都想用 8888 端口,但端口只能被一个进程占用。解决办法是每个人用不同的端口。比如第一个人用 8888,第二个人用 8889,第三个人用 8890,以此类推。

启动时指定端口即可:

jupyter notebook --port 8889

但这样每个人都要记自己的端口,容易乱。更好的做法是每个人在自己的用户目录下配置不同的端口,写进各自的配置文件里,启动时自动生效。

另外,多人共用时还要注意工作目录的隔离。默认情况下 Jupyter 启动在哪个目录,就只能访问那个目录及其子目录。每个人在自己的 home 目录下启动,就天然隔离了,不会互相看到对方的文件。

5.5 长时间运行断开连接的问题

远程连接有个常见现象:你开着 Notebook 去干别的事,过一段时间回来发现连接断了,需要重新登录。这是因为浏览器和 Jupyter 之间的 WebSocket 连接在空闲时可能被中断。

如果只是偶尔断一下,重新连上就行,Notebook 里的代码和输出不会丢,因为它们是保存在服务端的。但如果频繁断开影响使用,可以检查一下是不是网络不稳定,或者服务端的 Jupyter 进程被系统休眠策略影响了。

对于需要长时间跑的任务,建议不要依赖浏览器的连接状态。把训练脚本写成.py文件,用nohup或tmux在服务端后台跑,Notebook 只用来做交互式开发和调试。这样即使浏览器断了,任务照样在跑。

6. 让远程访问更顺手的几个进阶配置

6.1 配置默认工作目录

每次启动 Jupyter 都跳到 home 目录,然后手动一层层点进项目文件夹,时间长了很烦。可以在配置文件里指定默认目录:

c.NotebookApp.notebook_dir = '/home/yourname/projects'

Windows 上路径要写成r'D:\projects'这种形式,注意用原始字符串避免反斜杠转义问题。改完之后启动 Jupyter,直接就在项目目录里了。

注意:这个目录必须存在,否则 Jupyter 启动会报错。另外要确保运行 Jupyter 的用户对这个目录有读写权限。

6.2 用 nohup 让 Jupyter 在后台常驻

默认情况下,你关掉终端,Jupyter 进程就跟着结束了。如果希望它一直在后台跑,可以用 nohup:

nohup jupyter notebook > jupyter.log 2>&1 &

这条命令的意思是:把 Jupyter 放到后台运行,标准输出和错误输出都重定向到jupyter.log文件,&表示后台执行。这样即使你退出 SSH 或关掉终端,Jupyter 依然在跑。

想停掉它的时候,先找到进程号:

ps aux | grep jupyter

然后 kill 掉即可。日志文件jupyter.log里会记录启动信息和访问日志,出问题的时候可以翻一翻。

6.3 用 tmux 管理多个会话

如果你经常需要在服务端同时跑多个任务,tmux 是个好东西。它能在服务端创建多个独立的终端会话,每个会话里可以跑不同的东西,而且断开连接后会话依然保留。

基本用法很简单:

tmux new -s jupyter # 新建一个叫 jupyter 的会话 # 在里面启动 jupyter notebook # 按 Ctrl+B 然后按 D 脱离会话 tmux attach -t jupyter # 重新连接会话

这样你可以一个会话跑 Jupyter,另一个会话跑训练脚本,互不干扰。比起 nohup,tmux 的好处是你能随时回去看实时输出,交互性更好。

6.4 关于安全性的几句实在话

虽然本文限定在局域网内,但有些话还是得说。局域网不等于绝对安全,尤其是在办公室、实验室这种多人共享的网络里。同一网络下的其他设备理论上是可以扫描到你的开放端口的。

所以几件事必须做到:密码要复杂,不要用123456这种;不要图省事关掉密码验证;如果长期不用,把 Jupyter 停掉而不是一直挂着;定期看看访问日志,有没有陌生的 IP 连过。

另外,c.NotebookApp.allow_remote_access = True这项虽然方便,但也意味着任何能访问到你 IP 的人都能尝试连接。如果你的局域网环境比较复杂,可以考虑用 SSH 隧道的方式,只在本机开一个转发端口,这样 Jupyter 根本不需要对外监听。不过 SSH 隧道的配置稍微复杂一些,属于另一个话题了,这里不展开。

7. 我实际用下来的一些体会

这套配置我在不同环境下搭过好几次,从 Windows 服务端到 Linux 服务端都试过。最大的感受是:配置文件那几行改动本身不难,难的是排查为什么没生效。新手卡住的地方往往不是"不知道怎么改",而是"改了没用,又不知道去哪找原因"。

我的建议是,每改一步就验证一步。改完绑定地址,先在服务端本机用局域网 IP 访问一下,确认监听生效了;再去客户端 ping 一下,确认网络通了;最后才在客户端浏览器访问。这样出问题的时候,你能快速定位是哪一环断了,而不是面对一个"连不上"的结果干瞪眼。

还有一个体会是关于版本的。Anaconda 更新挺频繁的,不同版本之间 Jupyter 的配置项名称、默认行为都可能有变化。网上搜到的教程如果年份比较早,配置项名称可能已经过时了。遇到对不上的情况,第一反应应该是去查你当前版本的官方文档,而不是硬套旧教程。

最后说个小事。远程访问配好之后,我习惯在服务端的 Jupyter 里装一个jupyterlab或者nbextensions,前者界面更现代,后者能加一些实用的小功能比如代码折叠、目录导航。这些都属于锦上添花,核心的远程访问跑通了,剩下的按自己喜好折腾就行。

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询