@js-tiny/url
v0.0.2
Published
A simple url-style-string builder with pure javascript
Downloads
165
Readme
@js-tiny/url
English | 简体中文
一个轻量、可变的 URL 构造器,提供链式、getter/setter 风格的 API。
从空字符串开始逐段拼装 URL —— protocol、hash、path 的前缀会自动处理,任意组成部分都
可以通过同一个方法读取或写入。与原生 URL 不同,它对相对路径或不完整的输入不会抛
错,并且可以运行在 Node、浏览器以及微信小程序(原生 URL 不可用的环境)中。
特性
- 可变且可链式调用 —— 每个 setter 都返回实例本身,因此可以从零开始流畅地拼装 一个 URL。
- 双模式访问器 ——
url.protocol()读取,url.protocol("https")写入。无需 分离的 getter/setter 成对定义。 - 前缀自动补全 ——
protocol("https")→"https:",hash("top")→"#top",pathname("users")→"/users"。 - 输入宽容 —— 传入
null、undefined或""即可清除某个组成部分;部分 URL 也能正常处理。 - 多值查询参数 ——
PureQuery支持重复键、add 时自动去重、合并以及批量插入。 - IPv6 与密码安全解析 ——
[::1]:8080主机、user:p:secret认证串都能按 RFC 3986 正确解析。 - 跨平台 —— 同时产出 CJS、ESM 以及打包后的小程序构建产物。
安装
npm install @js-tiny/url快速开始
import { PureUrl } from "@js-tiny/url";
const url = new PureUrl("https://example.com/path?query=value#hash");
// 读取
url.protocol(); // 'https:'
url.hostname(); // 'example.com'
url.pathname(); // '/path'
url.search(); // '?query=value'
url.hash(); // '#hash'
// 写入(可链式)
url
.protocol("http")
.hostname("newdomain.com")
.pathname("/new/path")
.hash("new-hash");
url.toString(); // 'http://newdomain.com/new/path?query=value#new-hash'核心概念
Getter / Setter 双模式
每个组成部分的方法都同时是 getter 和 setter —— 不传参即读取,传参即写入:
const url = new PureUrl();
url.protocol("https"); // 写入 → 返回 url 实例(可链式)
url.protocol(); // 读取 → 'https:'清除某个组成部分
向任意方法传入 null、undefined 或 "" 即可清除该组成部分:
const url = new PureUrl("https://user:[email protected]:8080/path?q=1#h");
url.protocol(null);
url.auth(null);
url.host(null);
url.pathname(null);
url.search(null);
url.hash(null);
url.toString(); // ''前缀自动补全
前缀会自动添加或去除,无需手动记忆:
const url = new PureUrl();
url.protocol("https"); // 'https:' (去除 ':' 与 '/',再补上 ':')
url.hash("section1"); // '#section1'
url.pathname("users"); // '/users'组成部分
Protocol(协议)
const url = new PureUrl();
url.protocol("https"); // 'https:'
url.protocol(null); // 已清除Authentication(认证)
auth() 接收 "username:password" 格式,并按第一个 : 切分,因此密码中包含
: 时不会被截断。
const url = new PureUrl();
url.auth("username:password");
url.auth(); // 'username:password'
// 也可以分别设置
url.username("user").password("pass");
url.auth(); // 'user:pass'
// 含冒号的密码不会被截断
url.auth("user:p:secret");
url.password(); // 'p:secret'Host 与 Port(主机与端口)
const url = new PureUrl();
url.host("example.com:8080");
url.host(); // 'example.com:8080'
url.hostname(); // 'example.com'
url.port(); // '8080'
// IPv6 字面量(带方括号)可正确解析
url.host("[::1]:8080");
url.hostname(); // '[::1]'
url.port(); // '8080'Path(路径)
const url = new PureUrl();
url.pathname("/api/v1/users");
// 通过分段构造
url.pathnames("api", "v1", "users");
url.pathname(); // '/api/v1/users'
// 读回为分段数组
url.pathnames(); // ['api', 'v1', 'users']
// path() 同时覆盖 pathname 与 query
url.path("/search?q=js");Hash(片段)
const url = new PureUrl();
url.hash("section1"); // '#section1'
url.hash(null); // 已清除查询参数(PureQuery)
PureUrl.query 是一个 PureQuery 实例;PureQuery 也单独导出,便于在脱离 URL 的
场景下独立处理查询字符串。
import { PureQuery } from "@js-tiny/url";
const query = new PureQuery("a=1&b=2&b=3", true); // 第二个参数 = 自动解码
query.get("a"); // '1'
query.getAll("b"); // ['2', '3']
query.has("a"); // true
// set() 替换某个键的全部值
query.set("c", "new-value");
query.set("d", "v1", "v2", "v3"); // 多个值
// add() 追加,且自动跳过重复值
query.add("tags", "js");
query.add("tags", "js"); // 已存在,忽略
// 批量插入
query.addAll({ category: "dev", tags: ["js", "node"] });
query.addAll([["author", "john"], ["tags", ["fe", "be"]]]);
// 仅在键不存在时添加
query.addIfNotExist("config", "once");
// 合并另一个查询(字符串或 PureQuery)
query.merge("x=10&y=20");
query.toUrlString();
// 'a=1&b=2&b=3&c=new-value&d=v1&d=v2&d=v3&tags=js&tags=node&tags=fe&tags=be&category=dev&author=john&config=once&x=10&y=20'addAll 返回实例本身,因此可以链式调用:
const query = new PureQuery()
.addAll({ param1: "value1" })
.addAll([["param2", "value2"]])
.add("param3", "value3");全链式拼装
PureUrl 的所有 setter 与 PureQuery 的所有方法都返回实例本身,因此可以用一个
表达式拼出完整 URL:
const url = new PureUrl()
.protocol("https")
.hostname("api.example.com")
.port("443")
.pathname("/v1/users");
url.query.set("limit", "10").set("offset", "0");
url.hash("results");
url.toString();
// 'https://api.example.com:443/v1/users?limit=10&offset=0#results'API 参考
PureUrl
new PureUrl(href?: string)将 href(通过 @xesam/url)解析为各组成部分。省略它则从空 URL 开始。
属性
query: PureQuery—— 查询参数管理器。
方法 —— 每个方法都是 getter(不传参)与 setter(传参)合一;setter 返回
this。
| 方法 | 说明 |
| -------------------------- | -------------------------------------------- |
| protocol(value?) | 读取/设置协议。会去除 : 与 /,再补上 :。 |
| auth(value?) | 读取/设置,格式为 "username:password"。按第一个 : 切分。 |
| username(value?) | 读取/设置用户名。 |
| password(value?) | 读取/设置密码。 |
| host(value?) | 读取/设置,格式为 "hostname:port"。支持 IPv6。 |
| hostname(value?) | 读取/设置主机名。 |
| port(value?) | 读取/设置端口。 |
| path(value?) | 读取/设置 pathname 与 query 的组合。 |
| pathname(value?) | 读取/设置路径名。确保以 / 开头。 |
| pathnames(...fragments?) | 读取为分段数组,或由分段设置路径名。 |
| search(value?) | 读取/设置查询字符串(含 ?)。 |
| hash(value?) | 读取/设置片段。确保以 # 开头。 |
| toUrlString() | 序列化为完整 URL 字符串。 |
| toString() | toUrlString() 的别名。 |
PureQuery
new PureQuery(qString?: string, decodeValue?: boolean)| 方法 | 说明 |
| --------------------------------- | ------------------------------------------- |
| isEmpty() | 查询是否不含任何键。 |
| has(key) | 是否存在 key。 |
| keys() | 全部键。 |
| get(key, index?) | key 的第 index 个值(默认第一个)。 |
| getAll(key) | key 的全部值。 |
| add(key, value) | 追加一个值,自动跳过重复。 |
| addAll(entries) | 批量添加。接受对象,或 [key, value \| value[]] 元组数组。 |
| addIfNotExist(key, value) | 仅当 key 不存在时添加。 |
| set(key, ...values) | 替换 key 的全部值。 |
| remove(key) | 移除 key。 |
| clear() | 清除全部键。 |
| load(qString, decodeValue?) | 通过解析查询字符串替换当前内容。 |
| merge(otherQuery, decodeValue?) | 合并另一个查询(字符串或 PureQuery)。 |
| toUrlString(encodeValue?) | 序列化为查询字符串。 |
| toString() | toUrlString() 的别名。 |
微信小程序
package.json 暴露了 miniprogram 字段,指向一个不含 node 专属 API 的打包 CJS
产物,因此可以在微信小程序(原生 URL 构造器不可用)中直接引入,无需额外 polyfill。
{ "miniprogram": "dist/miniprogram" }License
MIT
