Folder Terminal

by First Kang
5
4
3
2
1
Score: 50/100

Description

Hover over a folder in the file explorer to reveal a terminal icon; click it to open a real shell (PTY) at the bottom of Obsidian, rooted at that folder.

Reviews

No reviews yet.

Stats

0
stars
84
downloads
0
forks
10
days
1
days
1
days
0
total PRs
0
open PRs
0
closed PRs
0
merged PRs
0
total issues
0
open issues
0
closed issues
47
commits

Latest Version

a day ago

Changelog

Folder Terminal 1.4.2

文件树「复制」图标重构升级:从单一可配置模式改为一组可独立操作的动作图标,并新增「在系统文件管理器中展示」与「图标配色」能力。 文件夹行图标扩展升级:在原有「在此打开终端」图标旁新增一组辅助动作图标,并对系统管理器中展示 / 绝对路径计算做了共享抽取。

✨ 新增

  • 文件行复制图标改为动作组:悬停文档时横向浮现一组图标,各可独立操作
    • 复制标题(heading
    • 复制 Wiki 文件路径(route,去扩展名相对路径,如 wiki/ideas/xxx
    • 复制内容(copy,完整 Markdown 源码)
    • 复制 Wiki 绝对路径(link,磁盘绝对路径)
    • 在 Finder / 资源管理器中展示(folder-open,定位并选中该文档;macOS open -R、Windows explorer /select、Linux 打开所在目录)
  • 文件夹行辅助动作图标:悬停文件夹时,在「终端」图标左侧横向浮现一组动作(与文件图标同尺寸、同配色、同 hover 样式)
    • 在 Finder / 资源管理器中展示(folder-open,定位并选中该文件夹)
    • 复制 Wiki 文件路径(route,相对库根的路径,如 wiki/ideas
    • 复制 Wiki 绝对路径(link,磁盘绝对路径)
  • 库根文件夹特判:绝对路径复制库根本身(无尾部斜杠),展示功能定位库根目录
  • 文件树图标配色:设置面板新增「文件树图标颜色」取色器,可自定义「终端」与「复制」图标组的颜色;右侧重置按钮恢复跟随主题

🔧 重构

  • 抽取共享模块 src/shellUtils.ts
    • toAbsPath(app, relPath):文件/文件夹绝对路径计算,统一非桌面端适配器的退化逻辑
    • revealInFileManager(absPath, linuxOpenDir):平台命令执行(macOS open -R / Windows explorer /select / Linux xdg-open
  • folderIconsfileCopyIcons 同步改为调用共享函数,删除各自重复的本地实现(共约 90 行)

🐛 修复

  • tooltip 与 title 重叠:删除按钮上的原生 title,仅保留 aria-label,消除浏览器气泡与 Obsidian 暗色 tooltip 同弹的重叠
  • 悬停目录时点亮所有后代图标:改为行自身直子选择器(.tree-item-self:hover > …),仅显示被悬停的那一行的图标
  • 点击后图标驻留:点击后主动 blur(),释放按钮焦点,避免 :focus-within 让该行图标常驻、与下一行图标同时出现
  • 复制到系统剪贴板(文件本体)不可用:经排查为 Obsidian 渲染沙盒限制(Web Clipboard 拒绝自定义类型、Electron 文件剪贴板对 Finder 不生效),暂时屏蔽该图标,功能实现保留以便后续开放
  • 文件「复制文件路径」改为带后缀的相对路径:此前复制的是去扩展名的相对路径(wiki/ideas/xxx),现在复制原始 file.pathwiki/ideas/xxx.md),可直接用于 cp、终端引用等文件系统操作
  • 图标提示文案同步:「复制 Wiki 文件路径」→「复制文件路径」(中英文词条均已更新),文件夹相对路径无扩展名,语义与文案不受影响

交互

  • 两级 hover:悬停文件行时图标以浅化的设置色浮现(默认混入主题背景色 60%),移到图标本体上提升为完整设置色并轻微加深强调;未设置配色时沿用主题默认图标色

验证

  • 悬停文件/文件夹:仅当前行图标浮现,不点亮其他行
  • 复制标题 / Wiki 路径 / 绝对路径 / 内容:剪贴板内容正确并弹出「已复制」
  • 在 Finder 展示:macOS 弹出 Finder 并选中该文档
  • 图标配色:取色后终端与复制图标同步变色,重置后恢复主题色

README file from

Github

Folder Terminal

This README is bilingual: English sections first, 中文 sections below. 本说明为双语:英文在前,中文在后。

Folder Terminal is an Obsidian plugin that adds a terminal icon to every folder in the file explorer. Hover over a folder and click the icon to open a real shell (PTY) at the bottom of Obsidian, with the working directory automatically set to that folder.

⚠️ Desktop-only (depends on Node's child_process); not available on mobile.

Highlights

  • Hover-to-reveal terminal icon on folders (auto-hidden while renaming)
  • Real PTY via an embedded Python proxy — vim / ssh / htop work normally, no native modules required
  • Multi-tab sessions, drag-to-reorder, double-click rename, per-tab settings (shell / color scheme / font size / color tag)
  • Cross-restart recovery, theme-aware GitHub-style colors, clickable URLs
  • UI localization: Chinese / English / Follow system

Platform notes: macOS requires python3 (Xcode Command Line Tools); Linux falls back to script when python3 is missing; Windows uses winpty when available, otherwise cmd.exe.


Obsidian 插件:鼠标移到文件浏览器中的文件夹上时,标题右侧出现「终端」图标;点击后在 Obsidian 当前面板下方打开一个真实 Shell(PTY)窗口,工作目录自动切换为该文件夹。

⚠️ 仅支持桌面端(依赖 Node 的 child_process),移动端不可用。

Features / 功能

English

  • 🖱️ Hover-to-reveal icon on every folder title (floats at the right edge, no layout shift, auto-hidden while renaming)
  • 📂 One-click cd — opens a terminal already rooted at that folder's absolute path (including the vault root)
  • 🗂️ Multi-tab sessions — one tab per folder, each an independent shell; switching tabs keeps scrollback, closing a tab ends the session
  • 🧲 Drag-to-reorder tabs
  • ✏️ Double-click rename a tab (does not rename the actual folder)
  • 🖱️ Right-click menu — rename / tab settings / restart session / close
  • 🎛️ Per-tab settings — override shell, color scheme, font size, color tag (persisted with the workspace layout)
  • 💾 Cross-restart recovery — the tab list is persisted with the workspace layout and restored on next launch
  • 🖥️ Real PTY — on macOS / Linux an embedded Python PTY proxy (pty.fork) creates a true pseudo-terminal, so interactive programs like vim / ssh / htop work without any native modules
  • 📐 Live resizeTIOCSWINSZ keeps the PTY size in sync with the panel, so full-screen TUIs react instantly
  • ⚙️ Settings — default shell, font size, color scheme (theme / dark / light), panel-reuse toggle
  • 🔗 Clickable URLs (xterm web-links)
  • 🔍 In-terminal search — press Ctrl/Cmd+F (or right-click → Search) to find text in the buffer, with match highlighting, prev/next navigation, live match count, and case-sensitive / regex / whole-word toggles
  • ⌨️ Command history & cursor navigation — on Windows (pipe mode, no readline) / recalls previous commands and / / Home / End move the cursor within the line
  • 🎨 Theme-aware GitHub-style colors

中文

  • 🖱️ 文件夹悬浮图标:鼠标移入文件夹标题显示终端图标(右端悬浮,不占位不误触;重命名时自动隐藏)
  • 📂 一键进入目录:点击图标,终端自动 cd 到该文件夹的磁盘绝对路径(含库根目录,data-path=""
  • 🗂️ 多标签会话:每个文件夹一个标签页,各自独立 Shell;切换标签不丢滚动历史,关闭标签才结束会话
  • 🧲 标签拖拽排序:直接拖动标签调整顺序
  • ✏️ 双击重命名:自定义标签名(不影响实际文件夹名)
  • 🖱️ 右键菜单:重命名 / 标签设置 / 重启会话 / 关闭标签
  • 🎛️ 每标签独立设置:可单独覆盖 Shell、配色、字号、颜色标记(弹窗配置,随布局持久化)
  • 💾 跨重启恢复:标签列表随工作区布局持久化,重启 Obsidian 后自动恢复所有会话
  • 🖥️ 真实 PTY:macOS / Linux 通过内嵌的 Python PTY 代理pty.fork)创建真实伪终端,vim / ssh / htop 等交互程序可正常工作,无需任何原生模块
  • 📐 自适应尺寸:面板大小变化时通过 TIOCSWINSZ 实时调整 PTY 尺寸,vim 内全屏程序也能即时感知
  • ⚙️ 设置面板:默认 Shell、字号、配色方案(跟随主题/深色/浅色)、面板复用开关
  • 🔗 链接可点:URL 自动高亮可点击(xterm web-links)
  • 🔍 终端内搜索:按 Ctrl/Cmd+F(或右键 → 搜索)在缓冲区检索,支持高亮全部匹配、上/下一处跳转、实时计数,以及区分大小写 / 正则 / 全字匹配开关
  • ⌨️ 命令历史与光标导航:Windows 管道模式下 / 回溯历史命令, / / Home / End 在行内移动光标
  • 🎨 跟随主题:明暗主题下采用 GitHub 风格配色

Screenshots / 截图

Hover icon — 鼠标悬停文件夹时显示终端图标

Multi-tab terminal — 多标签终端与右键菜单

Per-tab settings — 标签设置弹窗

Installation / 安装

English

Option A — Community plugin browser (after this plugin is approved)

  1. Open Settings → Community plugins
  2. Turn off Restricted mode if prompted
  3. Click Browse, search for Folder Terminal, then Install and Enable

Option B — BRAT (for beta / pre-release testing)

  1. Install the BRAT plugin from the community browser
  2. Open the command palette and run BRAT: Add a beta plugin for testing
  3. Paste https://github.com/FIRSTKANG/folder-terminal and confirm
  4. Enable Folder Terminal in Community plugins

Option C — Manual

  1. Build: npm install && npm run build
  2. Copy the plugin folder (containing main.js, manifest.json, styles.css) into your vault's .obsidian/plugins/folder-terminal/
  3. Enable Folder Terminal in Settings → Community plugins

中文

方式 A — 社区插件市场(插件过审后可用)

  1. 打开 设置 → 第三方插件
  2. 按提示关闭「受限模式」
  3. 点击 浏览,搜索 Folder Terminal,然后 安装启用

方式 B — BRAT(用于抢先体验 beta / 未上架版本)

  1. 在社区市场安装 BRAT 插件
  2. 打开命令面板,运行 BRAT: Add a beta plugin for testing
  3. 粘贴 https://github.com/FIRSTKANG/folder-terminal 并确认
  4. 在第三方插件中启用 Folder Terminal

方式 C — 手动安装

  1. 构建:npm install && npm run build
  2. 把插件目录(含 main.jsmanifest.jsonstyles.css)复制到 vault 的 .obsidian/plugins/folder-terminal/
  3. 在 Obsidian「设置 → 第三方插件」中启用 Folder Terminal

Development / 开发

npm install
npm run dev        # watch 模式(产出 main.js)
npm run build      # 生产构建(tsc 检查 + esbuild 打包)
npm run smoke:pty  # PTY 链路冒烟测试(不依赖 Obsidian,可直接跑)

Commands / 命令

Command (EN) 命令(中文) Description
Open terminal at vault root 在库根目录打开终端 Open/focus the bottom terminal rooted at the vault root
Open terminal at active note's folder 在笔记所在文件夹打开终端 Open/focus the bottom terminal rooted at the current note's folder

Settings / 设置

Setting (EN) 设置项 Description
Default shell 默认 Shell Empty = $SHELL (macOS default /bin/zsh); e.g. /bin/bash, /bin/fish
Font size 字号 Terminal font size (10–22px)
Color scheme 配色方案 Follow Obsidian theme / force dark / force light
Reuse terminal panel 复用终端面板 When on, re-clicking an icon focuses the same bottom panel's tab (default on)
Interface language 界面语言 Chinese / English / Follow system

Each tab can also override shell / color scheme / font size / color tag individually: right-click a tab → Tab settings… 每个标签页还可以单独覆盖 Shell / 配色 / 字号 / 颜色标记:右键标签 → 「标签设置…」。

Tab operations / 标签操作

Action (EN) 操作 How / 方式
Switch 切换标签 Single click
Reorder 排序 Drag onto a target tab (insert before it)
Rename 重命名 Double-click the tab name, Enter to save / Esc to cancel
Restart session 重启会话 Right-click → Restart session
Tab settings 标签设置 Right-click → Tab settings… (per-tab shell / color scheme / font size / color tag)
Close 关闭 The × on the tab, or right-click → Close

How it works / 实现原理

English: a MutationObserver keeps injecting a terminal icon into every folder title in the file explorer. Clicking it opens a new panel below the current one via workspace.getLeaf('split', 'horizontal'), where a custom ItemView renders xterm.js. A child_process.spawn('python3', ['-u', '-c', <pty-proxy.py>, $SHELL]) launches an embedded Python PTY proxy; fd3 is used as a resize-control channel, and pty.fork() creates a real pseudo-terminal so interactive programs work. No native modules are bundled — child_process, path, etc. are marked external and provided by the Obsidian desktop runtime.

中文

文件浏览器 .nav-folder-title(MutationObserver 持续补注入图标)
        │ 点击
        ▼
workspace.getLeaf('split', 'horizontal')  →  当前面板下方新开面板
        ▼
registerView 自定义视图  →  xterm.js 渲染终端
        ▼
child_process.spawn('python3', ['-u', '-c', <pty-proxy.py>, $SHELL])
        │  fd0/1 = 键盘输入 / 终端输出;fd3 = 尺寸控制通道
        ▼
pty.fork()  →  真实 PTY  →  /bin/zsh(或 $SHELL),工作目录 = vault 根 + 文件夹路径

关键点:

  • PTY 代理:内嵌一段 Python 脚本(src/pty-proxy.py,构建时以字符串打包进 main.js),pty.fork() 创建真实伪终端后只做字节搬运。这样交互程序(vim/ssh)才能正常工作,且对 stdio 类型无要求
  • 为什么不用 script 命令? macOS 上 Node/Electron 的 child_process 管道实际是 socketpair(libuv 行为),而 BSD 的 script 会对 stdin 做 tcgetattr,遇 socket 返回 EOPNOTSUPP 直接退出(已实测复现)。Python 代理没有这个检查。
  • 不打包原生模块:无需 node-pty / 编译 .node 二进制,esbuild 配置把 child_processpath 等 Node 内置模块标为 external,运行时由 Obsidian 桌面端提供。

Known limitations / 已知限制

  • Desktop only: isDesktopOnly: true, not loaded on mobile.
  • macOS needs python3: requires Xcode Command Line Tools (prompts on first use, or run xcode-select --install).
  • Linux without python3 falls back to script: still interactive, but resize sync degrades to stty (only effective at the shell prompt).
  • Windows is best-effort: with winpty you get a PTY; otherwise cmd.exe (no PTY, interactive programs limited).
  • First open is a 50/50 split: drag the divider to resize; Obsidian remembers the layout afterward.
  • Fixed panel height is not yet possible: Obsidian does not expose a Leaf-size API (hard-coding CSS would break drag layout); waiting for an official layout API.
  • Shortcut conflicts: when the terminal is focused, some Obsidian global shortcuts (e.g. Cmd+P) may still be intercepted by Obsidian; Ctrl+C / arrow keys are handled normally by the PTY.
  • Obsidian version drift: the file explorer's DOM class names (.nav-files-container, etc.) may change across versions; if the icon disappears, update folderIcons.ts for the new DOM.
  • Session end: closing a tab / uninstalling the plugin kills the session; a hard Obsidian quit may leave a few python3/shell child processes.

中文

  • 仅桌面端isDesktopOnly: true,移动端不加载。
  • macOS 依赖 python3:需要 Xcode Command Line Tools(首次使用会提示安装,xcode-select --install)。
  • Linux 无 python3 时回退 script:仍可交互,但尺寸同步降级为 stty(仅 shell 提示符下生效)。
  • Windows 尽力而为:装了 winpty 则有 PTY;否则 cmd.exe 无 PTY,交互程序受限。
  • 首次打开是 50/50 分屏:拖动分隔条调整高度后 Obsidian 会记住布局。
  • 面板固定高度暂不可行:Obsidian 未公开 Leaf 尺寸控制 API(CSS 硬改会破坏拖拽布局),等待官方布局 API 或后续用内部分裂配置实现。
  • 快捷键冲突:终端聚焦时,Obsidian 的全局快捷键(如 Cmd+P)仍可能被 Obsidian 拦截;Ctrl+C / 方向键等由 PTY 正常处理。
  • Obsidian 版本变动:文件浏览器的 DOM 类名(.nav-files-container 等)随版本可能调整,若图标消失需按新版 DOM 更新 folderIcons.ts
  • 会话结束:标签关闭 / 插件卸载会 kill 对应会话;Obsidian 直接退出时可能残留少量 python3/shell 子进程。

Project structure / 目录结构

src/
  main.ts              插件入口:视图注册、设置、图标挂载、命令  (entry: view registration, settings, icon mount, commands)
  folderIcons.ts       文件浏览器悬浮图标(MutationObserver + DOM 注入)  (file-explorer hover icon)
  terminalView.ts      多标签终端视图(xterm.js,标签/会话/拖拽/重命名管理)  (multi-tab terminal view)
  tabSettingsModal.ts  标签设置弹窗(每标签 Shell / 配色 / 字号 / 颜色标记覆盖)  (per-tab settings modal)
  pty.ts               Shell 会话封装(python3 PTY 代理,Linux 回退 script,Windows winpty/cmd)  (shell session wrapper)
  pty-proxy.py         PTY 代理脚本(构建时打包进 main.js)  (PTY proxy, bundled at build time)
  settings.ts          全局设置面板(shell / 字号 / 配色 / 复用开关 / 界面语言)  (global settings panel)
  i18n.ts              多语言字典与 t() 函数(zh-CN / en / 跟随系统)  (i18n dictionary + t())
scripts/
  pty-smoke.js         PTY 链路冒烟测试(含尺寸控制通道验证)  (PTY smoke test)

Roadmap / 后续路线

  • Settings: default shell, font size, color scheme, reuse-panel toggle
  • Fallback when python3 is missing (Linux script, macOS prompts for CLT)
  • Multi-tab / per-folder session memory (cross-restart recovery)
  • Icon moved out of the title to the folder's right edge (absolute positioning, no layout shift)
  • Windows winpty best-effort (auto-fallback to cmd.exe)
  • Tab drag-reorder / double-click rename / right-click menu
  • Per-tab settings (shell / color scheme / font size / color tag override)
  • UI localization: Chinese / English / Follow system
  • Fixed terminal panel height (blocked on Obsidian layout API)