# @cypress/unique-selector 中文文档

规范地址：https://npmcn.com/package/%40cypress/unique-selector/

版本：2\.2\.0
npm 元数据更新时间：2026-03-27T14:18:47.387Z
中文译文更新时间：2026-11-11T07:22:41.243Z
软件包许可：MIT

本文由上游 README 翻译，可能存在偏差，请结合原文核对 API、命令与配置。版权与许可归原作者所有。

原始 npm 页面：https://www.npmjs.com/package/%40cypress/unique-selector
原文对照：https://npmcn.com/package/%40cypress/unique-selector/?lang=original
项目主页：https://github.com/cypress-io/unique-selector#readme
源码仓库：https://github.com/cypress-io/unique-selector

## 关键信息（来自 npm 元数据）

- 包体积（解压后）：40.3 kB，16 个文件
- 模块格式：CommonJS
- TypeScript 类型：未声明
- 运行依赖：1 个
- 首次发布：2017-12-13T21:22:19.368Z
- 最新版本发布：2026-03-27T14:18:47.237Z
- 近 30 天下载量：12036（2026-10-11 至 2026-11-09，npm 官方下载统计）
- 已发布版本数：17（近 12 个月 3 个）

## 中文简介

鉴于 DOM 节点, 返回只匹配该元素的独有 CSS 选择器

## 安装

```sh
npm install @cypress/unique-selector
```

也可以使用：`pnpm add @cypress/unique-selector`、`yarn add @cypress/unique-selector`、`bun add @cypress/unique-selector`

## README

# 独选者

鉴于 DOM 节点, 返回唯一匹配该元素的 CSS 选择器 .

选择器的独特性根据给定元素的根节点来确定. 在Shadow DOM中渲染出元素,将在关联的ShadowRoot上下文中得出一个独有的选择器. 否则,将产生元素自有文档中独有的选择器.

## 安装

![NPM Version](https://img.shields.io/npm/v/%40cypress%2Funique-selector)

```bash
npm install @cypress/unique-selector
```

## API 密码

### `unique(element, options)`

为指定的 DOM 元素生成一个独特的 CSS 选择器.

#### 参数

-   **`element`** (Element) - 用于生成唯一选择器的 DOM 元素
-   **`options`** (对象,可选) - 选择器生成的配置选项

#### 选项

-   **`selectorTypes`** (String \[\],可选) - 按偏好顺序排列选择器类型。 默认 : `['id', 'name', 'class', 'tag', 'nth-child']`
    
    可用的选择器类型 :
    
    -   `'id'` - 使用元素的ID属性(例如, `#myId`(中文(简体) )
    -   `'name'` - 使用元素的名称属性(例如, `[name="myName"]`(中文(简体) )
    -   `'class'` - 使用元素的类属性(例如, `.myClass`(中文(简体) )
    -   `'tag'` - 使用元素的标记名称(例如, `div`, (中文(简体) ), `span`(中文(简体) )
    -   `'nth-child'` - 使用非孩子位置(例如:, `:nth-child(1)`(中文(简体) )
    -   `'attributes'` - 使用所有属性,但不包括: `attributesToIgnore`
    -   `'data-*'` - 使用特定数据属性(例如, `data-foo`, (中文(简体) ), `data-test-id`(中文(简体) )
    -   `'attribute:*'` - 使用特定属性(例如, `attribute:role`, (中文(简体) ), `attribute:aria-label`(中文(简体) )
-   **`attributesToIgnore`** (String \[\],可选) - 生成选择器时要忽略的属性名称的组合. 默认 : `['id', 'class', 'length']`
    
-   **`filter`** (功能,可选) - 在构建选择器时有条件拒绝各种特性的过滤功能.
    
    ```javascript
    function filter(type, key, value) {
      // type: 'attribute', 'class', 'tag', 'nth-child'
      // key: attribute name (for attributes), class name (for classes), etc.
      // value: attribute value, class name, tag name, nth-child position
      
      // Return true to allow this trait, false to reject it
      return true;
    }
    ```
    
-   **`selectorCache`** (map<Element, String>,可选) - 缓存可以提高重复选择器生成的性能. 呼叫者负责缓存无效.
    
-   **`isUniqueCache`** (map<String, Boolean>,可选) - 缓存可以提高重复的独特性检查的性能. 呼叫者负责缓存无效.
    
-   **`requiredAttributes`** (Object,可选) - 指定必须出现在生成的选取器中的属性,无论这些属性是否需要独有性. 当提供时,匹配的属性选择器会被编织入每个元素的片段 `>` 链,而独有链上方的祖先则使用后人梳理器进行预作.
    
    此选项优先于 `selectorTypes` 财务报告和审定财务报表 `filter` 对于它所命名的属性——如果一个元素具有需要的属性,则其属性 `[attr="value"]` 即使 `filter` 为了独特性的目的拒绝该属性,即使该属性未列入 `selectorTypes`。 。 。 .
    
    这个 `requiredAttributes` 对象的形状如下:
    
    -   **`attributeNames`** (String\[\]) - 向选择器注入的属性名(例如, `['data-component', 'data-cy']`) (中文(简体) ). 精确的属性名称只——而不是图案或正则名. 名称在生成的选取器中按规定使用,没有内部正常化,因此您提供的外壳是输出中出现的外壳. 当属性在 `attributeNames` 已经存在于基准选择器中(来自 `selectorTypes`),去dup检测为对病例不敏感,所以无论病例差异如何,重复注射都会被正确压制.
    -   **`filter`** (功能,可选) - 一个过滤功能,其签名与顶级相同 `filter` 选项,独立用于控制哪个属性 _数值_ 允许注射。 返回时 `false` 以跳过给定元素的注入。 此过滤器与顶层分离 `filter` 并服务于不同的目的: `filter` 有资格建立 _独一无二_ 选择器,同时 `requiredAttributes.filter` 属性值符合条件的控件 _注射_编辑 `key` 引用到此函数的参数将符合下列条件: `attributeNames`。 。 。 .
    -   **`elementCache`** (map<Element, (string-|null) \[\] >,可选) - 每元素所需的属性选择器缓存 。 每个缓存项是单个选择器字符串的阵列,与 `attributeNames` (未显示或过滤出属性的空白). 呼叫者负责缓存无效.
    
    ```javascript
    unique(element, {
      requiredAttributes: {
        attributeNames: ['data-component', 'data-cy'],
        filter: (type, key, value) => {
          // Exclude auto-generated component names from injection
          if (type === 'attribute' && key === 'data-component') {
            return !value.startsWith('jss-');
          }
          return true;
        },
        elementCache: new Map(),
      }
    });
    ```
    

#### 回返

-   **字符串** - 该元素的独有CSS选择器,或 `null` 如果无法生成唯一选择器

## 用法实例

### 基本用途

```javascript
import unique from '@cypress/unique-selector';

// Get a unique selector for an element
const element = document.querySelector('.my-button');
const selector = unique(element);
// Returns: '#my-button' or '.my-button' or 'button' etc.
```

### 自定义选择器类型

```javascript
// Use only ID and class selectors
const selector = unique(element, {
    selectorTypes: ['id', 'class']
});

// Use only data attributes
const selector = unique(element, {
    selectorTypes: ['data-test-id', 'data-cy']
});

// Use specific attributes
const selector = unique(element, {
    selectorTypes: ['attribute:role', 'attribute:aria-label']
});
```

### 过滤选择器

```javascript
// Filter out certain IDs
const selector = unique(element, {
    filter: (type, key, value) => {
        if (type === 'attribute' && key === 'id') {
            // Only allow IDs that contain 'test'
            return value.includes('test');
        }
        return true;
    }
});

// Filter out certain classes
const selector = unique(element, {
    filter: (type, key, value) => {
        if (type === 'class') {
            // Only allow classes that start with 'btn-'
            return value.startsWith('btn-');
        }
        return true;
    }
});
```

### 必需属性

使用 `requiredAttributes` 当您想要特定属性总是出现在生成的选择器中时,无论这些属性是否有助于独有性。 当应用程序使用语义元件属性(如:, `data-component`, (中文(简体) ), `data-cy`您想要在每个选择器中反映可读性或稳定性.

```javascript
// Always include data-component in the selector, even when an ID alone would be unique
const selector = unique(element, {
    requiredAttributes: {
        attributeNames: ['data-component']
    }
});
// '#submit-button' becomes '#submit-button[data-component="PrimaryButton"]'
// Ancestors with data-component are prepended with descendant combinators:
// '[data-component="Form"] #submit-button[data-component="PrimaryButton"]'
```

所需属性优先于 `selectorTypes` 财务报告和审定财务报表 `filter`。如果元素具有要求的属性,则将注入选择器,即使:

-   属性未在 `selectorTypes`
-   高层 `filter` 为了独特性而拒绝这种属性

```javascript
// The top-level filter rejects data-component for uniqueness building,
// but requiredAttributes.filter allows it to still be injected.
const selector = unique(element, {
    filter: (type, key) => key !== 'data-component',
    requiredAttributes: {
        attributeNames: ['data-component'],
        // No requiredAttributes.filter — all values are injected
    }
});
// data-component still appears in the output
```

使用 `requiredAttributes.filter` 独立控制哪个属性 _数值_ 注射,但不影响确定独特性的方式:

```javascript
// Inject data-component only when the value doesn't look auto-generated
const selector = unique(element, {
    requiredAttributes: {
        attributeNames: ['data-component'],
        filter: (type, key, value) => {
            if (type === 'attribute' && key === 'data-component') {
                return !value.startsWith('jss-');
            }
            return true;
        },
        elementCache: new Map(), // reuse across calls for performance
    }
});
```

当多个 `attributeNames` 指定,每个元素独立匹配:

```javascript
const selector = unique(element, {
    requiredAttributes: {
        attributeNames: ['data-cy', 'data-region']
    }
});
// '[data-region="main"] [data-cy="dashboard"] .widget[data-cy="widget-a"]'
```

### 用缓存优化性能

```javascript
const selectorCache = new Map();
const isUniqueCache = new Map();

const selector = unique(element, {
    selectorCache,
    isUniqueCache
});

// Reuse the same caches for multiple calls
const selector2 = unique(anotherElement, {
    selectorCache,
    isUniqueCache
});
```

### 阴影 DOM 支持

```javascript
// Works with Shadow DOM elements
const shadowHost = document.querySelector('#shadow-host');
const shadowRoot = shadowHost.attachShadow({ mode: 'open' });
const shadowElement = shadowRoot.querySelector('.shadow-button');

const selector = unique(shadowElement);
// Returns a selector unique within the shadow root context
```

## 选择生成策略

库遵循这个策略生成独特的选择器 :

1.  **元素级独有性**: 首先尝试找到一个在母体中唯一识别元素的筛选器
2.  **双向**: 如果元素级独有性失败, 则会穿过 DOM 树, 建立选择器路径
3.  **选择者类型优先**: 使用 `selectorTypes` 数组以决定要先尝试的选定者类型
4.  **组合后退**: 对于类和属性,如果单个选择者不独有,请尝试多个选择者的组合
5.  **Nth- child倒计时**: 将非儿童定位作为最后手段
6.  **必需属性注射**: 独一无二之后 `>` 链被确定,任何 `requiredAttributes` 被编织入每个元素的链段。 在链上方带有所需要属性的祖先被准备为后人梳理. 必要的属性即使因独特性而不需要,甚至顶层也会被注入 `filter` 将这些人排除在考虑之外.

## 生成选择器实例

```html
<!-- Element with ID -->
<div id="header">Header</div>
<!-- Selector: #header -->

<!-- Element with unique class -->
<button class="submit-btn">Submit</button>
<!-- Selector: .submit-btn -->

<!-- Element with multiple classes -->
<div class="card primary large">Card</div>
<!-- Selector: .card.primary.large -->

<!-- Element with data attributes -->
<div data-test-id="user-profile">Profile</div>
<!-- Selector: [data-test-id="user-profile"] -->

<!-- Element with custom attributes -->
<button role="button" aria-label="Close">×</button>
<!-- Selector: [role="button"] or [aria-label="Close"] -->

<!-- Element requiring nth-child -->
<div class="item">Item 1</div>
<div class="item">Item 2</div>
<!-- Selector: :nth-child(1) or :nth-child(2) -->

<!-- Complex nested element -->
<div class="container">
  <div class="wrapper">
    <span class="text">Hello</span>
  </div>
</div>
<!-- Selector: .container > .wrapper > .text -->
```

## 常见问题

### @cypress/unique-selector 是什么？

鉴于 DOM 节点, 返回只匹配该元素的独有 CSS 选择器

### 如何安装 @cypress/unique-selector？

在项目目录运行 npm install @cypress/unique-selector，或使用 pnpm add / yarn add / bun add。

### @cypress/unique-selector 支持 TypeScript 吗？

该包的 package\.json 没有声明类型入口。需要类型提示时，可以在 npm 上查找社区维护的 @types/cypress\_\_unique-selector 是否存在。

### @cypress/unique-selector 支持 ESM 还是 CommonJS？

以 CommonJS 形式发布，可以直接 require\(\)；在 ES Module 项目中也可以用 import 引入（Node\.js 会把 module\.exports 作为默认导出）。

### @cypress/unique-selector 可以商用吗？

@cypress/unique-selector 使用 MIT 许可。宽松许可：允许商业使用、修改和再分发，通常只需在分发时保留原版权与许可声明。以上为概括，不构成法律意见，请以许可原文为准。

### @cypress/unique-selector 的下载量有多少？

根据 npm 官方下载统计，@cypress/unique-selector 在 2026/10/11 – 2026/11/09 这 30 天内被下载 12,036 次，日均约 401 次。下载量会把 CI 构建、镜像同步和作为其他包依赖的安装一并计入，适合横向比较热度，不能直接等同于使用人数。

### @cypress/unique-selector 还在维护吗？

最新版本 2\.2\.0 发布于 2026/03/27（7 个月前）；至今共发布 17 个版本，其中过去 12 个月发布了 3 个；首次发布于 2017/12/14。发布频率只是参考信号：功能稳定的工具可能很少需要更新，建议结合源码仓库的 issue 和提交记录判断。

