# TaiBai **Repository Path**: yann-up/tai-bai ## Basic Information - **Project Name**: TaiBai - **Description**: 一个简单的JAVA的静态工具库 - **Primary Language**: Java - **License**: Apache-2.0 - **Default Branch**: master - **Homepage**: None - **GVP Project**: No ## Statistics - **Stars**: 0 - **Forks**: 0 - **Created**: 2026-04-01 - **Last Updated**: 2026-04-03 ## Categories & Tags **Categories**: Uncategorized **Tags**: None ## README # 🗡️ TaiBai SDK (太白) > **外在如诗般流畅,内在如剑般锋利。** > > *Fluent as poetry, sharp as a blade. A modern, fluent, and null-safe utility toolkit for Java 17+.*
[![JDK 17+](https://img.shields.io/badge/JDK-17+-green.svg)](https://openjdk.java.net/) [![License](https://img.shields.io/badge/License-Apache%202.0-blue.svg)](https://opensource.org/licenses/Apache-2.0) [![Zero Dependency](https://img.shields.io/badge/Dependencies-0-brightgreen.svg)]()
## 📜 缘起 (Why TaiBai?) 在 Java 世界里,我们早已习惯了 `StringUtils`、`DateUtils` 等各种大而全的静态工具类。它们像一把把沉重的铁锤,虽然能解决问题,但也带来了无尽的痛点: - **嵌套地狱**:`StringUtil.camelCase(StringUtil.trim(str))`,代码阅读顺序反人类。 - **上帝类 (God Class)**:动辄几千行的 `Utils` 文件,内部方法极度耦合,难以维护。 - **NPE 陷阱**:无处不在的 `if (str != null)` 判断,让核心业务逻辑被防御性代码淹没。 **TaiBai (太白)** 诞生于对"代码美学"的追求。它全面拥抱 **Java 17+** 的现代语法(Records, Pattern Matching, Sealed Interfaces),采用**门面模式**与**流式 API**,彻底消灭了繁杂的 `Utils` 后缀。 ## ✨ 核心心法 (Core Philosophy) - 🪶 **流式剑法 (Fluent API)**:告别方法嵌套,像写英语长句一样写数据处理逻辑。 - 🛡️ **绝对空安全 (Null-Safe)**:底层 Wrapper 包容一切 `null` 值,链式调用中途遇到 null 自动静默,绝不抛出 `NullPointerException`。 - 🧱 **领域驱动 (DDD & SRP)**:内部按动作与策略拆分(如 `WhitespaceStripper`、`PatternMatcher`),遵循单一职责原则。 - 📦 **零依赖 (Zero-Dependency)**:核心包不引入任何第三方库,极致轻量。 ## 🚀 极速起剑 (Quick Start) ### 引入依赖 **Maven** ```xml io.github.yann-up taibai-core 0.0.1 ``` **Gradle** ```groovy implementation 'io.github.yann-up:taibai-core:0.0.1' ``` ## ⚔️ 招式演示 (Examples) TaiBai 的一切操作,皆从 `TaiBai.` 这个全局唯一入口开始。所有终端操作提供**双轨制收剑**: | 收剑方式 | 说明 | |---|---| | `.getOrNull()` | 宽容模式,值为 null 时返回 null | | `.getOrElse(defaultValue)` | 宽容模式,值为 null 时返回默认值 | | `.getOrThrow()` | 严谨模式,值为 null 时抛出 `TaiBaiException` | --- ### 1. 文本域 `TaiBai.text()` ```java // 清洗 + 风格转换 String result = TaiBai.text(" user_name_input ") .trim() // 去除首尾空白(含全角空格) .toCamelCase() // user_name_input → userNameInput .getOrElse("default"); // → "userNameInput" // 支持的大小写转换 TaiBai.text("user_name").toPascalCase().getOrNull(); // → "UserName" TaiBai.text("userName").toSnakeCase().getOrNull(); // → "user_name" TaiBai.text("userName").toKebabCase().getOrNull(); // → "user-name" TaiBai.text("hello").toUpperCase().getOrNull(); // → "HELLO" // 脱敏处理(金融/隐私场景) String safePhone = TaiBai.text("+86 138-1234-5678") .extractNumbers() // → "8613812345678" .cut(11) // → "13812345678" .mask(3, 4, '*') // 保留前3后4,中间打码 .getOrThrow(); // 严谨模式:失败则抛出 TaiBaiException // → "138****5678" // 填充与截断 TaiBai.text("42").padLeft(5, '0').getOrNull(); // → "00042" TaiBai.text("Hello, World!").cut(5, "...").getOrNull(); // → "He..." // 字符串判断(终端操作,直接返回 boolean) TaiBai.text("hello").contains("ell"); // → true TaiBai.text("hello").matches("[a-z]+"); // → true TaiBai.text("hello").equalsToIgnoreCase("HELLO"); // → true TaiBai.text(" ").isBlank(); // → true // null 安全:全程静默,不抛 NPE TaiBai.text(null).trim().toCamelCase().getOrNull(); // → null ``` **文本域中间操作一览:** `trim()` · `trimLeft()` · `trimRight()` · `removeBlank()` · `toCamelCase()` · `toPascalCase()` · `toSnakeCase()` · `toKebabCase()` · `toUpperCase()` · `toLowerCase()` · `extractNumbers()` · `extractLetters()` · `replace()` · `replaceFirst()` · `cut()` · `padLeft()` · `padRight()` · `mask()` · `format()` --- ### 2. 数字域 `TaiBai.number()` ```java // 字符串解析 + 运算(解析失败静默,不抛异常) TaiBai.number("3.14").multiply(2).toDouble(); // → Optional.of(6.28) TaiBai.number("abc").add(1).getOrNull(); // → null(解析失败静默) // 四则运算 TaiBai.number(100).add(50).subtract(20).getOrNull(); // → 130 TaiBai.number(10).divide(0).getOrNull(); // → null(除零保护) // 绝对值 / 取反 / 区间限制 TaiBai.number(-5).abs().getOrNull(); // → 5 TaiBai.number(150).clamp(0, 100).getOrNull(); // → 100 // 格式化(跨域转换为 TextWrapper) TaiBai.number(1234567.89).format("#,##0.00").getOrNull(); // → "1,234,567.89" TaiBai.number(1234.56).toCurrency("CNY").getOrNull(); // → "¥1,234.56" // 类型转换 TaiBai.number("42").toInt(); // → Optional.of(42) TaiBai.number("3.14").toBigDecimal(); // → Optional.of(3.14) // 范围判断 TaiBai.number(50).isInRange(0, 100); // → true ``` --- ### 3. 时间域 `TaiBai.time()` ```java // 当前时间操作 String expireTime = TaiBai.time() .plusDays(3) .atEndOfDay() .format("yyyy-MM-dd HH:mm:ss"); // → "2026-04-05 23:59:59" // 多种入参方式 TaiBai.time(someLocalDateTime); // LocalDateTime TaiBai.time(new Date()); // java.util.Date 自动转换 TaiBai.time("2026-01-01", "yyyy-MM-dd"); // 字符串解析 // 时间加减 TaiBai.time().plusMonths(1).plusHours(8).format("yyyy-MM-dd HH:mm:ss"); TaiBai.time().minusDays(7).atStartOfDay().format("yyyy-MM-dd HH:mm:ss"); // 边界截断 TaiBai.time().atStartOfMonth().format("yyyy-MM-dd"); // 当月第一天 00:00:00 TaiBai.time().atEndOfMonth().format("yyyy-MM-dd"); // 当月最后一天 23:59:59 // 比较判断 TaiBai.time(someDate).isBefore(LocalDateTime.now()); // → true/false TaiBai.time(someDate).isBetween(start, end); // → true/false // 时间戳 TaiBai.time().toEpochMilli(); // → 毫秒时间戳 // null 安全 TaiBai.time(null, "yyyy-MM-dd").plusDays(1).getOrNull(); // → null(静默传播) ``` --- ### 4. 集合域 `TaiBai.list()` ```java // 过滤 + 排序 + 转换 List result = TaiBai.list(List.of("banana", "apple", "cherry")) .filter(s -> s.length() > 5) .sorted() .toList(); // → ["banana", "cherry"] // 映射 + 去重 + 限制 TaiBai.list(List.of(1, 2, 2, 3, 3, 4)) .distinct() .map(n -> n * 2) .limit(3) .toList(); // → [2, 4, 6] // 聚合操作 TaiBai.list(List.of(1, 2, 3)).count(); // → 3 TaiBai.list(List.of(1, 2, 3)).first(); // → Optional.of(1) TaiBai.list(List.of(1, 2, 3)).any(n -> n > 2); // → true TaiBai.list(List.of(1, 2, 3)).all(n -> n > 0); // → true // 分组 Map> grouped = TaiBai.list(List.of("a", "bb", "cc", "ddd")) .groupBy(String::length); // → {1: ["a"], 2: ["bb", "cc"], 3: ["ddd"]} // 跨域转换为 TextWrapper TaiBai.list(List.of("Java", "17", "rocks")).join(", ").getOrNull(); // → "Java, 17, rocks" // null 安全:null 集合视为空集合 TaiBai.list(null).filter(x -> true).toList(); // → [] ``` --- ### 5. 编解码域 `TaiBai.codec()` ```java // Base64 编解码 TaiBai.codec("hello").encodeBase64().getOrNull(); // → "aGVsbG8=" TaiBai.codec("aGVsbG8=").decodeBase64().getOrNull(); // → "hello" // Base64 往返 TaiBai.codec("hello").encodeBase64().decodeBase64().getOrNull(); // → "hello" // URL 编解码 TaiBai.codec("hello world").encodeUrl().getOrNull(); // → "hello+world" TaiBai.codec("hello+world").decodeUrl().getOrNull(); // → "hello world" // 哈希摘要(单向,不可逆) TaiBai.codec("hello").md5().getOrNull(); // → "5d41402abc4b2a76b9719d911017c592" TaiBai.codec("hello").sha256().getOrNull(); // → "2cf24dba5fb0a30e26e83b2ac5b9e29e1b161e5c1fa7425e73043362938b9824" // null 安全 TaiBai.codec(null).encodeBase64().getOrNull(); // → null(静默传播) ``` ## 🏗️ 内部架构 (Architecture) TaiBai 采用**"外在门面 + 内核策略"**的双层架构设计: ``` TaiBai (唯一入口门面) ├── text() → TextWrapper (sealed interface) │ └── TextWrapperImpl │ ├── WhitespaceStripper # 空白处理 │ ├── CaseConverter # 大小写转换 │ ├── StringCutter # 截断填充 │ ├── MaskProcessor # 脱敏处理 │ └── PatternMatcher # 正则匹配 ├── number() → NumberWrapper (sealed interface) │ └── NumberWrapperImpl │ ├── ArithmeticProcessor # 四则运算 │ ├── NumberParser # 字符串解析 │ └── NumberFormatter # 格式化输出 ├── time() → TimeWrapper (sealed interface) │ └── TimeWrapperImpl │ ├── TimeParser # 时间解析 │ ├── TimeCalculator # 时间加减 │ └── TimeFormatter # 格式化输出 ├── list() → CollectionWrapper (sealed interface) │ └── CollectionWrapperImpl # Stream 封装 └── codec() → CodecWrapper (sealed interface) └── CodecWrapperImpl ├── Base64Codec # Base64 编解码 ├── UrlCodec # URL 编解码 └── HashProcessor # MD5/SHA-256 ``` **核心设计约束:** 1. **入口收敛**:新增功能统一挂载在 `TaiBai` 门面及对应的 Wrapper 接口下。 2. **拒绝 Utils**:内部实现类必须以动作命名(`xxxProcessor`、`xxxFormatter`、`xxxParser`),严禁创建 God Class。 3. **拥抱 Java 17**:使用 `sealed interface` 控制实现边界,使用 `record` 作为数据载体,使用 `switch` 模式匹配简化逻辑分支。 4. **不可变 Wrapper**:所有中间操作返回新的 Wrapper 实例,保证线程安全。 ## 🤝 共建 (Contributing) 欢迎提交 Issue 和 Pull Request,让我们一起锻造这把 Java 界的青莲宝剑。 ## 📄 开源协议 (License) TaiBai SDK is released under the [Apache 2.0 License](https://opensource.org/licenses/Apache-2.0).