Cohub 实操:用一个 Space 从零搭一个可发布的小工具
#博客更新
disclosure:这是我们公司(Viscept)做的产品,这篇是实操向,我会讲清楚每一步在干什么、有什么坑。
先说结论
如果你想试 Cohub,最快的入门路径不是看文档,而是走一遍真实的闭环:
整个过程大概 20 分钟。这篇文章记录我实际跑通的步骤,包括遇到的坑。
第一步:创建 Space
Cohub 的核心单元是 Space。你可以把它理解成「一个隔离的开发环境 + 对话 + 文件系统 + Agent」。
用 CLI 创建(
或者直接在 web 上点 New Space 也行。我建议至少 CLI 装一个,因为后面很多操作 CLI 更快。
第二步:和 Agent 提需求
创建之后,打开 Space,跟 Agent 说你要做什么。关键是要把需求讲清楚,就像跟一个工程师同事提需求:
1. 说目标,不说实现。不需要告诉它用什么库,它会自己选。
2. 一次一个需求。第一轮先让它把核心功能做出来,再迭代加功能。
3. 它可以读写文件、跑命令。Agent 不是只回复文本,它会在 Space 的文件系统里创建文件、装依赖、跑 dev server。
第三步:看它干活,必要时纠偏
Agent 开始干活后,你会看到它:
● 创建项目文件(
● 跑
● 启动 dev server,暴露预览端口
这里有个经验:Agent 第一次做出来的东西,大概率不是你要的最终版。正常的迭代节奏是:
在 Cohub 里,你可以在同一个 Space 的预览区直接试它做出来的东西,不用自己本地跑。这个循环比「聊天里来回贴代码」高效得多。
第四步:Save(Checkpoint)
当你对当前状态满意(或者到了一个里程碑),存一个 Checkpoint:
为什么这个重要:
1. 它是不可变快照。之后再怎么改,都能回到这个点。
2. 可以 fork。从这个 Checkpoint 分支出新想法,不影响主线。
3. 是可分享的稳定基底。别人可以基于你的 Checkpoint 继续工作。
这比 git commit 更像「存档」——你随时能回到任何有意义的时刻。
第五步:发布成 Work
这是 Cohub 和大多数 AI 工具最大的区别:Agent 的产出可以直接发布成一个公开可访问的页面(Work)。
发布后你会得到一个公开 URL,任何人打开就能用你做的工具。这个 Work 还可以:
● 配置访问权限
● 用 Work Commerce 变现(卖功能解锁/积分)
● 被 fork 和 remix
实际遇到的坑
坑 1:Agent 装依赖慢
第一次让 Agent 跑
坑 2:端口预览 vs 实际发布
开发时 Agent 起的 dev server 端口,和发布后的静态托管不是一回事。如果你做的是 SPA 或需要后端的应用,发布时要注意:
● 纯前端 → 构建后发布
● 需要后端 → 用 Cohub 的 Sandbox 能力或对外部 API
坑 3:迭代时别丢上下文
每轮给 Agent 反馈时,引用具体现象("点击提交后没反应")而不是模糊的("好像不太对")。Agent 在同一 Space 里有完整上下文,具体反馈能让它精准修改。
写在最后
Cohub 最有意思的地方,是把「和 AI 协作做东西」从聊天里搬到了一个有文件、有环境、能发布的真实空间里。
你可以把它当:
● 快速原型工具(几分钟做个工具验证想法)
● 一个带 Agent 的完整开发环境
● 一个内容/工具的分发平台(Work)
如果你还没试过,建议按这篇的流程走一遍。从"让 AI 聊天"到"让 AI 帮你把东西做出来并发布",这个转变,用了才知道。
----------------------
● 产品:cohub.run
● CLI:
● 生态索引:github.com/markbang/awesome-cohub
via 棒无
#博客更新
disclosure:这是我们公司(Viscept)做的产品,这篇是实操向,我会讲清楚每一步在干什么、有什么坑。
先说结论
如果你想试 Cohub,最快的入门路径不是看文档,而是走一遍真实的闭环:
创建一个 Space → 和 Agent 说需求 → 它建文件/装依赖/跑起来 → Save 存 Checkpoint → 发布成 Work
整个过程大概 20 分钟。这篇文章记录我实际跑通的步骤,包括遇到的坑。
第一步:创建 Space
Cohub 的核心单元是 Space。你可以把它理解成「一个隔离的开发环境 + 对话 + 文件系统 + Agent」。
用 CLI 创建(
cohub 是官方 CLI):# 安装(如果你还没有)
npm install -g @neta-art/cohub-cli
# 登录
cohub auth login
# 列出你的 spaces
cohub spaces ls
# 创建新 space
cohub spaces create --name "my-first-tool"
或者直接在 web 上点 New Space 也行。我建议至少 CLI 装一个,因为后面很多操作 CLI 更快。
第二步:和 Agent 提需求
创建之后,打开 Space,跟 Agent 说你要做什么。关键是要把需求讲清楚,就像跟一个工程师同事提需求:
帮我做一个 Markdown 转 HTML 的小工具,输入一段 markdown,输出渲染后的 HTML。要能选样式主题,还要有一个预览区域。注意几个点:
1. 说目标,不说实现。不需要告诉它用什么库,它会自己选。
2. 一次一个需求。第一轮先让它把核心功能做出来,再迭代加功能。
3. 它可以读写文件、跑命令。Agent 不是只回复文本,它会在 Space 的文件系统里创建文件、装依赖、跑 dev server。
第三步:看它干活,必要时纠偏
Agent 开始干活后,你会看到它:
● 创建项目文件(
package.json、源码等)● 跑
npm install 装依赖● 启动 dev server,暴露预览端口
这里有个经验:Agent 第一次做出来的东西,大概率不是你要的最终版。正常的迭代节奏是:
第一轮:核心功能能用
第二轮:你试了,提反馈("样式太丑""这个按钮没反应")
第三轮:它改,你再试
在 Cohub 里,你可以在同一个 Space 的预览区直接试它做出来的东西,不用自己本地跑。这个循环比「聊天里来回贴代码」高效得多。
第四步:Save(Checkpoint)
当你对当前状态满意(或者到了一个里程碑),存一个 Checkpoint:
cohub -s <space-id> spaces checkpoints create --message "markdown-to-html v1 done"
为什么这个重要:
1. 它是不可变快照。之后再怎么改,都能回到这个点。
2. 可以 fork。从这个 Checkpoint 分支出新想法,不影响主线。
3. 是可分享的稳定基底。别人可以基于你的 Checkpoint 继续工作。
这比 git commit 更像「存档」——你随时能回到任何有意义的时刻。
第五步:发布成 Work
这是 Cohub 和大多数 AI 工具最大的区别:Agent 的产出可以直接发布成一个公开可访问的页面(Work)。
# 把项目构建成静态文件后发布
cohub -s <space-id> spaces files ls
# 发布目录为 Work
cohub -s <space-id> works publish my-tool --file dist/index.html
发布后你会得到一个公开 URL,任何人打开就能用你做的工具。这个 Work 还可以:
● 配置访问权限
● 用 Work Commerce 变现(卖功能解锁/积分)
● 被 fork 和 remix
实际遇到的坑
坑 1:Agent 装依赖慢
第一次让 Agent 跑
npm install,如果网络慢会等很久。解决办法:让它用国内镜像,或者先用最简依赖把核心跑通,再逐步加。坑 2:端口预览 vs 实际发布
开发时 Agent 起的 dev server 端口,和发布后的静态托管不是一回事。如果你做的是 SPA 或需要后端的应用,发布时要注意:
● 纯前端 → 构建后发布
dist/ 即可● 需要后端 → 用 Cohub 的 Sandbox 能力或对外部 API
坑 3:迭代时别丢上下文
每轮给 Agent 反馈时,引用具体现象("点击提交后没反应")而不是模糊的("好像不太对")。Agent 在同一 Space 里有完整上下文,具体反馈能让它精准修改。
写在最后
Cohub 最有意思的地方,是把「和 AI 协作做东西」从聊天里搬到了一个有文件、有环境、能发布的真实空间里。
你可以把它当:
● 快速原型工具(几分钟做个工具验证想法)
● 一个带 Agent 的完整开发环境
● 一个内容/工具的分发平台(Work)
如果你还没试过,建议按这篇的流程走一遍。从"让 AI 聊天"到"让 AI 帮你把东西做出来并发布",这个转变,用了才知道。
----------------------
● 产品:cohub.run
● CLI:
npm install -g @neta-art/cohub-cli● 生态索引:github.com/markbang/awesome-cohub
via 棒无
Docker 生产实践:从能跑到跑得稳的 Checklist
#博客更新
先说结论
「Docker 能跑」和「Docker 能稳定跑」是两回事。本地
这篇文章是我在生产环境踩过之后总结的 Checklist。不追求面面俱到,只讲高频、高影响的十件事,按重要程度排序。
1. 镜像尽量小,但要小得有理
镜像体积直接影响拉取时间和启动速度。常见手段:
● 用
● 多阶段构建:构建阶段用全量镜像,运行阶段只拷贝产物
● 清理不必要的缓存和包管理器元数据
但注意:不是越瘦越好。distroless 没有 shell,调试会很痛苦;alpine 的 musl libc 偶尔和依赖有兼容问题。先瘦到合理范围,别为了几十 MB 自找麻烦。
2. 非 root 用户运行
默认容器内是 root,这是安全大忌。一旦容器被攻破,攻击者就是 root 权限。
大多数官方镜像现在都支持直接切用户。这一步成本极低,收益很高。
3. 健康检查必须配
没有健康检查,编排系统(K8s/Swarm)就不知道你的容器是不是真的活着。进程在不代表服务可用。
注意
4. 日志打 stdout,别写文件
容器里的日志应该走 stdout/stderr,由编排系统收集,而不是写到容器内的文件。原因:
● 容器文件系统是临时的,重启就没了
● 你没法轻易拿到容器内的文件
● 云平台(CloudWatch、ELK、Loki)都从 stdout 收集
所以应用日志直接
5. 资源限制,不是可选项
不设
limits 一定要设,reservations 至少给一个合理值。这是生产环境第一道防线。
6. 环境变量和密钥,别硬编码
镜像里不要写死任何密钥。用:
● 环境变量(运行时注入)
● Docker secrets / K8s secrets
● 专门的密钥管理(Vault、云厂商的 secrets manager)
镜像一旦构建就难以「撤销」里面硬编码的密钥。密钥泄露的补救成本远高于一开始就用环境变量。
7. 固定依赖版本,别用 latest
● 基础镜像用精确 tag(如
● 依赖锁文件(
● 有需要时用 digest 固定镜像
可复现 = 可回滚 = 可调试。
8. 处理僵尸进程和信号
容器作为 PID 1 时,要正确处理信号(SIGTERM)和孤儿进程。常见方案:
● 用带 PID 1 处理的运行时(如
● 确保应用能优雅关闭(监听 SIGTERM,完成在途请求)
不然
9. 镜像构建也要考虑 .dockerignore
这也是多阶段构建里第一层就过滤掉的东西。
10. 一个容器一个职责
别在一个容器里跑 web + worker + cron。拆开:
● 各自独立扩缩容
● 一个挂了不影响其他
● 日志、健康检查、资源限制都更清晰
一个容器只做一件事,是容器化最大的架构收益。
验证清单
改完以后,跑一遍这个验证:
写在最后
这十条里,健康检查、资源限制、非 root、日志走 stdout 是成本最低、收益最高的四项,强烈建议从这些开始。
容器化不是终点,只是起点。把这些基础打牢,后面接 CI/CD、上 K8s 才会顺。
如果哪条你踩过不同的坑,欢迎交流。
via 棒无
#博客更新
先说结论
「Docker 能跑」和「Docker 能稳定跑」是两回事。本地
docker run 一次成功,和在生产集群里扛住流量、重启、扩容,中间隔着不少坑。这篇文章是我在生产环境踩过之后总结的 Checklist。不追求面面俱到,只讲高频、高影响的十件事,按重要程度排序。
1. 镜像尽量小,但要小得有理
镜像体积直接影响拉取时间和启动速度。常见手段:
● 用
alpine 或 distroless 作为基础镜像● 多阶段构建:构建阶段用全量镜像,运行阶段只拷贝产物
● 清理不必要的缓存和包管理器元数据
# 多阶段构建示例
FROM node:20-alpine AS build
WORKDIR /app
COPY package*.json ./
RUN npm ci
COPY . .
RUN npm run build
FROM node:20-alpine
WORKDIR /app
COPY /app/dist ./dist
COPY /app/package*.json ./
RUN npm ci --omit=dev
EXPOSE 3000
CMD ["node", "dist/index.js"]
但注意:不是越瘦越好。distroless 没有 shell,调试会很痛苦;alpine 的 musl libc 偶尔和依赖有兼容问题。先瘦到合理范围,别为了几十 MB 自找麻烦。
2. 非 root 用户运行
默认容器内是 root,这是安全大忌。一旦容器被攻破,攻击者就是 root 权限。
FROM node:20-alpine
# 创建非 root 用户
RUN addgroup -S app && adduser -S app -G app
USER app
大多数官方镜像现在都支持直接切用户。这一步成本极低,收益很高。
3. 健康检查必须配
没有健康检查,编排系统(K8s/Swarm)就不知道你的容器是不是真的活着。进程在不代表服务可用。
HEALTHCHECK \
CMD wget -q -O - http://localhost:3000/healthz || exit 1
注意
start-period——给应用启动留时间,别一上来就被打回。4. 日志打 stdout,别写文件
容器里的日志应该走 stdout/stderr,由编排系统收集,而不是写到容器内的文件。原因:
● 容器文件系统是临时的,重启就没了
● 你没法轻易拿到容器内的文件
● 云平台(CloudWatch、ELK、Loki)都从 stdout 收集
所以应用日志直接
console.log/print,别自己写日志文件轮转。5. 资源限制,不是可选项
不设
--memory 和 --cpus 限制,一个失控的容器能拖垮整个节点。# docker-compose 或 k8s 里都要设
resources:
limits:
memory: 512M
cpus: "0.5"
reservations:
memory: 256M
limits 一定要设,reservations 至少给一个合理值。这是生产环境第一道防线。
6. 环境变量和密钥,别硬编码
镜像里不要写死任何密钥。用:
● 环境变量(运行时注入)
● Docker secrets / K8s secrets
● 专门的密钥管理(Vault、云厂商的 secrets manager)
镜像一旦构建就难以「撤销」里面硬编码的密钥。密钥泄露的补救成本远高于一开始就用环境变量。
7. 固定依赖版本,别用 latest
FROM node:20-alpine 里的 20 可能今天和明天解析到不同的小版本。生产环境要可复现:● 基础镜像用精确 tag(如
node:20.18.0-alpine)● 依赖锁文件(
package-lock.json / poetry.lock)进镜像● 有需要时用 digest 固定镜像
可复现 = 可回滚 = 可调试。
8. 处理僵尸进程和信号
容器作为 PID 1 时,要正确处理信号(SIGTERM)和孤儿进程。常见方案:
● 用带 PID 1 处理的运行时(如
tini)● 确保应用能优雅关闭(监听 SIGTERM,完成在途请求)
RUN apk add --no-cache tini
ENTRYPOINT ["/sbin/tini", "--"]
CMD ["node", "dist/index.js"]
不然
docker stop 会变成 kill -9,数据库写一半就没了。9. 镜像构建也要考虑 .dockerignore
.dockerignore 能大幅减少构建上下文和镜像体积,避免把 node_modules、.git、日志、临时文件打进去。node_modules
.git
*.log
.tmp
dist
这也是多阶段构建里第一层就过滤掉的东西。
10. 一个容器一个职责
别在一个容器里跑 web + worker + cron。拆开:
● 各自独立扩缩容
● 一个挂了不影响其他
● 日志、健康检查、资源限制都更清晰
一个容器只做一件事,是容器化最大的架构收益。
验证清单
改完以后,跑一遍这个验证:
# 1. 镜像构建成功且体积合理
docker build -t my-app .
# 2. 容器能启动且健康检查通过
docker run -d --name test -p 3000:3000 my-app
docker inspect --format='{{.State.Health.Status}}' test
# 期望: healthy
# 3. 优雅停止
docker stop test
# 观察日志是否有优雅关闭记录
# 4. 资源限制生效
docker run --rm -m 256m my-app
# 期望: 超出限制时 OOM,而不是拖垮宿主
写在最后
这十条里,健康检查、资源限制、非 root、日志走 stdout 是成本最低、收益最高的四项,强烈建议从这些开始。
容器化不是终点,只是起点。把这些基础打牢,后面接 CI/CD、上 K8s 才会顺。
如果哪条你踩过不同的坑,欢迎交流。
via 棒无