跳转到内容

PN532 NFC/RFID

pn532 组件允许你在 ESPHome 中使用 PN532 NFC/RFID 控制器 (数据手册、Adafruit)。 该组件是一个全局中心,通过 SPI 或 I²C 与 PN532 建立连接, 并输出其数据。使用 PN532 二进制传感器,然后可以 创建单独的二进制传感器来追踪 PN532 当前是否检测到 NFC/RFID 标签。

有关如何为该组件设置单独的二进制传感器,请参见 设置标签。

PN532 可以配置为使用 SPI 或 I²C 协议进行数据通信。 你需要根据板上印制的表格切换模块上的拨码开关。 SPI 通常为开关 1 关闭、开关 2 开启,I²C 通常为开关 1 开启、开关 2 关闭。 根据你选择的协议,需要配置 SPI 总线 或 I²C 总线。

pn532_spi 组件允许你在 ESPHome 中使用 PN532 NFC/RFID 控制器 (数据手册、Adafruit)。 该组件是一个全局中心,通过 SPI 与 PN532 建立连接, 并输出其数据。使用 PN532 二进制传感器,然后可以 创建单独的二进制传感器来追踪 PN532 当前是否检测到 NFC/RFID 标签。

pn532_spi:
cs_pin: D3
update_interval: 1s
binary_sensor:
- platform: pn532
uid: 74-10-37-94
name: "PN532 NFC Tag"
  • cs_pin(必选,Pin Schema):芯片选择线 在 ESP 上连接的引脚。

  • update_interval(可选,Time):PN532 上每次扫描的持续时间。它影响 个别二进制传感器被发现时保持活动状态的持续时间。 如果在此时间窗口内未找到设备,它将被标记为不存在。默认为 1 秒。

  • on_tag(可选,Automation):读取标签时要执行的自动化。参见 pn532-on_tag。

  • on_tag_removed(可选,Automation):移除标签时要执行的自动化。参见 on_tag_removed。

  • spi_id(可选,ID):如果你想 使用多个 SPI 总线,请手动指定 SPI Component 的 ID。

  • id(可选,ID):手动指定此组件的 ID。

通过 SPI 连接 PN532 的示例。注意右侧两个开关的位置。

pn532 组件允许你在 ESPHome 中使用 PN532 NFC/RFID 控制器 (数据手册、Adafruit)。 该组件是一个全局中心,通过 I²C 与 PN532 建立连接, 并输出其数据。使用 PN532 二进制传感器,然后可以 创建单独的二进制传感器来追踪 PN532 当前是否检测到 NFC/RFID 标签。

pn532_i2c:
update_interval: 1s
binary_sensor:
- platform: pn532
uid: 74-10-37-94
name: "PN532 NFC Tag"
  • update_interval(可选,Time):PN532 上每次扫描的持续时间。它影响 个别二进制传感器被发现时保持活动状态的持续时间。 如果在此时间窗口内未找到设备,它将被标记为不存在。默认为 1 秒。

  • on_tag(可选,Automation):读取标签时要执行的自动化。参见 pn532-on_tag。

  • i2c_id(可选,ID):如果你想 使用多个 I²C 总线,请手动指定 I²C Component 的 ID。

  • id(可选,ID):手动指定此组件的 ID。

当 PN532 模块用标签响应时,将触发此自动化。仅当标签更改或离开一个 update_interval 周期时才会触发。

此触发器提供的参数 x 类型为 std::string,是以 74-10-37-94 格式表示的标签 UID。例如,下面的配置将在 MQTT 主题 pn532/tag 上发布标签 ID。

有关如何使用此触发器提供的第二个 tag 参数,请参见下面的 NDEF 读取。

pn532_...:
# ...
on_tag:
then:
- mqtt.publish:
topic: pn532/tag
payload: !lambda 'return x;'

标签扫描事件也可以通过 homeassistant.tag_scanned 动作 发送到 Home Assistant 标签组件。

pn532_...:
# ...
on_tag:
then:
- homeassistant.tag_scanned: !lambda 'return x;'

或者你也可以通过 template 传感器 将值直接发送到 Home Assistant。

pn532_...:
# ...
on_tag:
then:
- text_sensor.template.publish:
id: rfid_tag
state: !lambda 'return x;'
text_sensor:
- platform: template
name: "RFID Tag"
id: rfid_tag

当 PN532 模块没有标签响应时,将触发此自动化。仅当标签离开一个 update_interval 周期时才会触发。

此触发器提供的参数 x 类型为 std::string,是以 74-10-37-94 格式表示的移除标签 UID。例如,下面的配置将在 MQTT 主题 pn532/tag_removed 上发布移除的标签 ID。

pn532:
# ...
on_tag_removed:
then:
- mqtt.publish:
topic: pn532/tag_removed
payload: !lambda 'return x;'

pn532 二进制传感器平台允许你追踪 PN532 当前是否正在检测具有给定 唯一 id(uid )的 NFC/RFID 标签。

# 示例配置条目
spi:
clk_pin: D0
miso_pin: D1
mosi_pin: D2
pn532_spi:
cs_pin: D3
update_interval: 1s
binary_sensor:
- platform: pn532
uid: 74-10-37-94
name: "PN532 NFC Tag"
  • uid(必选,string):NFC/RFID 标签的唯一 ID。这是一个以连字符分隔的 十六进制值列表。例如 74-10-37-94。

  • 来自 Binary Sensor 的所有其他选项。

要为特定的 NFC 标签设置二进制传感器,你首先需要知道它们的唯一 ID。为了获取此 id,首先像上面那样设置一个不带任何二进制传感器的简单 PN532 配置。

当你的代码正在运行,并且你用 NFC 标签接近 PN532 时,你应该看到类似这样的消息:

Found new tag '74-10-37-94'

然后复制此 id,并在配置示例中创建一个 binary_sensor 条目。对每个标签重复此过程。

PN532 支持将 NDEF 格式的数据写入和读取到卡片中。

下面的示例将读取一个使用 Home Assistant Companion App 格式化并写入的 NFC 标签,并使用 homeassistant.tag_scanned 动作 将其发送到 Home Assistant。tag 变量 提供给 on_tag 触发器以及运行的任何动作,可以像下面这样使用。

pn532_...:
# ...
on_tag:
then:
- homeassistant.tag_scanned: !lambda |
if (!tag.has_ndef_message()) {
return x;
}
auto message = tag.get_ndef_message();
auto records = message->get_records();
for (auto &record : records) {
std::string payload = record->get_payload();
size_t pos = payload.find("https://www.home-assistant.io/tag/");
if (pos != std::string::npos) {
return payload.substr(pos + 34);
}
}
return x;

下面的示例可用于将一个(伪)随机 UUID 写入标签,格式与 Home Assistant Companion App 相同。

on_...
then:
- lambda: |-
static const char alphanum[] = "0123456789abcdef";
std::string uri = "https://www.home-assistant.io/tag/";
for (int i = 0; i < 8; i++)
uri += alphanum[random_uint32() % (sizeof(alphanum) - 1)];
uri += "-";
for (int j = 0; j < 3; j++) {
for (int i = 0; i < 4; i++)
uri += alphanum[random_uint32() % (sizeof(alphanum) - 1)];
uri += "-";
}
for (int i = 0; i < 12; i++)
uri += alphanum[random_uint32() % (sizeof(alphanum) - 1)];
auto message = new nfc::NdefMessage();
message->add_uri_record(uri);
ESP_LOGD("ndef", "Writing payload: %s", uri.c_str());
id(pn532_board).write_mode(message);
- wait_until:
not:
pn532.is_writing:
- logger.log: "Finished writing tag"