当前位置: 首页 > news >正文

[bat-cli] docs | 控制器

链接:https://github.com/sharkdp/bat

前文传送:

  • 【探索Linux命令行】从基础指令到高级管道操作的介绍与实践
  • 【Linux命令行】从时间管理->文件查找压缩的指令详解
  • 【Linux】1w详解如何实现一个简单的shell

docs:bat

在这里插入图片描述

bat 是一个**命令行文件查看器**,能够美化代码和文本文件。

它的工作原理是接收原始输入,智能地检测编程语言,然后应用生动的语法高亮和其他视觉装饰(如行号或 Git 变更)。

最终,增强后的输出会*直接显示或通过分页器(如 less)*输出,从而提供更好的查看体验。

可视化

在这里插入图片描述

章节

  1. 控制器
  2. 输入管理
  3. 输出处理
  4. 配置 (Config)
  5. 高亮资源
  6. 语法映射
  7. 行范围处理
  8. 打印器

第一章:控制器

欢迎来到 bat 🐻‍❄️

如果你想通过漂亮的语法高亮、行号等功能让你的代码和文本文件更加清晰,那么你来对地方了ovo。

在这第一章中,我们将介绍“控制器”,它是 bat 强大显示功能背后的核心大脑。

控制器解决了什么问题?

假设我们有一个纯文本文件,比如一个 Python 脚本,我们想在屏幕上显示它。不仅仅是原始文本,而是带有各种装饰效果:不同关键词的鲜艳颜色、清晰的行号,甚至可能还有版本控制中的变更标记。如何从一个简单的文本文件变成这样丰富、视觉上吸引人的输出呢?

这就是控制器的作用!它就像是整个显示操作的项目经理。我们告诉它想要显示哪些文件以及如何显示(我们的“配置”),然后控制器负责确保一切正确执行。

本章的目标是理解控制器如何协调这一过程,将一个简单的文件准备好,以便进行漂亮的显示。

控制器:我们的项目经理

控制器本身并不直接执行高亮或行号添加。相反,它协调所有其他专业化的组件。可以将其视为:

  • 协调者:确保从读取文件到最终显示的每一步都按正确顺序进行。
  • 指挥官:根据我们的设置告诉其他组件该做什么。
  • 错误处理者:如果出现问题(例如文件无法找到),控制器会捕获错误。

使用控制器

虽然 bat 提供了一个用户友好的 PrettyPrinter 来处理常见任务,但直接理解 Controller 有助于掌握核心逻辑。让我们看一个基本示例,展示如何使用 batController 来显示一个简单的 Rust 文件。

以下是一个最小化的代码片段,灵感来自 bat 的示例,直接使用 Controller 将文件内容(这里是 examples/buffer.rs 本身)打印到一个字符串缓冲区:

use bat::{assets::HighlightingAssets, // 管理语法定义和主题config::Config,            // 我们的显示偏好controller::Controller,    // 协调者!output::OutputHandle,      // 输出目标Input,                     // 表示输入文件
};fn main() {let mut buffer = String::new(); // 输出将存储在这里let config = Config {colored_output: true, // 是的,我们需要颜色!..Default::default()};let assets = HighlightingAssets::from_binary(); // 加载内置的高亮信息let controller = Controller::new(&config, &assets); // 创建控制器// 为当前文件创建输入let input = Input::from_file(file!());// 运行控制器处理并打印输入controller.run(vec![input.into()], // 提供输入文件Some(OutputHandle::FmtWrite(&mut buffer)), // 告诉它写入字符串缓冲区).unwrap();println!("{buffer}"); // 最终打印缓冲区中的结果
}

说明:

  1. 我们设置了一个名为 bufferString,用于存储高亮后的输出
  2. 我们创建了一个 Config 对象,其中包含所有偏好设置,比如是否需要彩色输出。..Default::default() 为其他设置填充默认值。
  3. HighlightingAssets::from_binary() 加载所有内置的语法定义(例如如何高亮 Rust、Python 等)和颜色主题。
  4. 然后,我们使用 Controller::new(&config, &assets) 创建控制器。我们提供偏好设置(config)和高亮规则(assets)。
  5. 我们定义要显示的内容为 Input。这里,Input::from_file(file!()) 表示我们要求 bat 处理包含这段代码的 Rust 文件!
  6. 最后,controller.run(...) 是魔法发生的地方。我们给控制器提供 input(要处理的文件),并告诉它将输出写入 buffer 通过 OutputHandle

运行这段代码时,bat 会处理 examples/buffer.rs 文件,根据 Rust 规则和默认主题应用语法高亮,并将格式化后的输出存储在 buffer 中,然后打印到控制台。

在这里插入图片描述

控制器内部工作原理

让我们揭开控制器的面纱,看看调用 controller.run() 时发生了什么。控制器作为我们的项目经理,与多个专业团队协调完成任务。

以下是简化的步骤分解:

  1. 接收请求:我们(程序员)告诉控制器处理一组文件,并提供特定配置。
  2. 准备输入:对于每个文件,控制器要求输入管理团队读取其内容。该团队负责打开文件、从标准输入读取,甚至处理字节数组。
  3. 收集设置:控制器使用我们提供的 Config(即配置)。Config 包含所有指令:“使用这个颜色主题”、“显示行号”、“换行长行”等。
  4. 加载高亮信息:控制器查询 HighlightingAssets 以找到正确的语法定义(例如,“这是一个 Rust 文件,这是它的关键词和结构”)和选择的颜色主题。
  5. 启动打印机:对于每个输入文件的每一行,控制器将原始行连同所有配置和高亮规则交给打印机团队。打印机是实际应用颜色、添加行号并格式化文本的艺术家。
  6. 定向输出:打印机的格式化输出随后发送到输出处理。这可能意味着直接写入终端,或通过分页程序(如 less)以便于浏览大文件。
  7. 处理错误:如果任何团队遇到问题(例如文件不可读),控制器会捕获并报告。

以下是描述这一流程的序列图:

在这里插入图片描述

深入代码

让我们看看 bat 源代码中控制器的结构。

首先是 Controller 结构体本身(来自 src/controller.rs):

// src/controller.rs
pub struct Controller<'a> {config: &'a Config<'a>,assets: &'a HighlightingAssets,// ... 其他字段(用于 lessopen 特性的预处理器)
}

说明:

  • config: &'a Config<'a>:这是对配置对象的引用,包含用户的所有偏好设置。控制器需要这些指令来知道如何显示文件。
  • assets: &'a HighlightingAssets:这是对 HighlightingAssets 的引用,包含所有语法定义和主题。这告诉控制器应用哪些高亮规则和颜色。

接下来是控制器的构造函数(new)和主要的 run 方法:

// src/controller.rs
impl Controller<'_> {pub fn new<'a>(config: &'a Config, assets: &'a HighlightingAssets) -> Controller<'a> {Controller {config,assets,// ... 初始化其他字段}}pub fn run(&self, inputs: Vec<Input>, output_handle: Option<OutputHandle<'_>>) -> Result<bool> {// ... 设置输出 ...let mut no_errors: bool = true;for (index, input) in inputs.into_iter().enumerate() {let result = if input.is_stdin() {// 处理标准输入self.print_input(input, &mut writer, io::stdin().lock(), identifier, is_first)} else {// 处理文件输入self.print_input(input, &mut writer, io::empty(), identifier, is_first)};if let Err(error) = result {// ... 错误处理 ...no_errors = false;}}Ok(no_errors)}fn print_input<R: BufRead>(&self,input: Input,writer: &mut OutputHandle,stdin: R,stdout_identifier: Option<&Identifier>,is_first: bool,) -> Result<()> {let mut opened_input = input.open(stdin, stdout_identifier)?;// ... 可能获取 git diff ...let mut printer: Box<dyn Printer> = /* ... 创建 InteractivePrinter 或 SimplePrinter ... */;self.print_file(&mut *printer,writer,&mut opened_input,!is_first,// ... line_changes ...)}// ... 其他辅助方法如 print_file, print_file_ranges ...
}

说明:

  1. Controller::new:这是创建控制器的方式。只需传递 ConfigHighlightingAssets
  2. Controller::run:这是启动处理的主要方法。
    • 它准备 output_type,确定输出去向(例如直接到终端或通过分页程序)。这将在输出处理中进一步讨论。
    • 然后遍历每个提供的 Input 文件或流。
    • 对于每个输入,调用 self.print_input
  3. Controller::print_input:此方法处理单个输入的流程:
    • 使用输入管理组件 open 输入,使其内容可读。
    • 创建一个 printerSimplePrinterInteractivePrinter)。printer 是实际根据 ConfigHighlightingAssets 对原始文本应用样式的组件。我们将在打印机章节深入探讨。
    • 最后调用 self.print_file,将逐行打印的实际工作委托给选定的 printer

这表明控制器确实是核心枢纽,将 ConfigHighlightingAssets、输入管理、输出处理和打印机结合在一起完成任务。

结论

在本章中,我们了解到控制器是 bat 项目的核心协调者。

它像项目经理一样,接收我们的配置和文件列表,然后指导其他专业组件读取、处理、高亮并漂亮地显示代码。虽然它不直接执行细节工作,但其协调角色bat 的功能至关重要。

现在我们已经理解了控制器在显示流程中的协调作用,下一步是了解 bat 如何处理我们想要显示的文件。在下一章中,我们将深入探讨输入管理,学习 bat 如何高效读取文件和其他数据源。

下一章:输入管理


文章转载自:

http://4kosATcq.kjfsd.cn
http://sCxB8RmA.kjfsd.cn
http://XfBwiUtd.kjfsd.cn
http://lXY3UHE4.kjfsd.cn
http://e2WL5O6H.kjfsd.cn
http://kF3uCQZR.kjfsd.cn
http://lTiK08KL.kjfsd.cn
http://I9nfFfnD.kjfsd.cn
http://TUhhwwpV.kjfsd.cn
http://K76jieqy.kjfsd.cn
http://EN9AXx9S.kjfsd.cn
http://12GG2ZHv.kjfsd.cn
http://xr3Xl84u.kjfsd.cn
http://28lxCrm9.kjfsd.cn
http://wMlu2aeU.kjfsd.cn
http://2gxg7NkD.kjfsd.cn
http://mVLnt7h5.kjfsd.cn
http://V80rehsN.kjfsd.cn
http://aFVtTOMX.kjfsd.cn
http://c7m7SFFe.kjfsd.cn
http://3tttRX2y.kjfsd.cn
http://9EFWnOst.kjfsd.cn
http://7qaFFcUr.kjfsd.cn
http://N4qsID1o.kjfsd.cn
http://BtbiH4MN.kjfsd.cn
http://cZiBsFH5.kjfsd.cn
http://qmvW9wMd.kjfsd.cn
http://qHdxjYFt.kjfsd.cn
http://XslRP7y1.kjfsd.cn
http://ZaKX1BlC.kjfsd.cn
http://www.dtcms.com/a/367547.html

相关文章:

  • 你读过哪些深入浅出的(技术)书籍?
  • C++程序员必懂:std::bad_function_call异常的真相与预防秘诀
  • 一篇文章带你彻底搞懂 JVM 垃圾收集器
  • 深度学习之第七课卷积神经网络 (CNN)调整学习率
  • 为什么研发文档总是缺少关键信息
  • Redissson分布式锁
  • C++字符串字符替换程序
  • 2025数学建模国赛A题思路首发!
  • 力扣-二分法想法
  • simple-check-100
  • 自学嵌入式第三十五天:网络编程-网站
  • 分词器详解(二)
  • Webug3.0通关笔记18 中级进阶第06关 实战练习:DisCuz论坛SQL注入漏洞
  • Docker学习记录
  • springboot配置多数据源(mysql、hive)
  • 机器学习如何精准预测高值
  • 【单片机day03】
  • More Effective C++ 条款28:智能指针
  • 洛谷 P3384 【模板】重链剖分/树链剖分-提高+/省选-
  • Websocket链接如何配置nginx转发规则?
  • Linux网络服务——基础设置
  • bd09转2gs84坐标算法
  • Python可视化93阅兵武器进化
  • 适应新环境:Trae编辑器下的IDEA快捷键定制
  • AgentThink:一种在自动驾驶视觉语言模型中用于工具增强链式思维推理的统一框架
  • 2025年数学建模国赛B题超详细解题思路
  • CSDN 与 掘金 高效学习指南
  • Web基础、HTTP/HTTPS协议与Nginx详解
  • 深度学习篇---MNIST:手写数字数据集
  • 【算法速成课2 | 题单】背包问题