Реализация контроля доступа через RFID в мобильном приложении
RFID-контроль доступа через мобильное приложение — это не просто «считать карточку и открыть дверь». Это аудит-лог каждого события, управление правами доступа для каждого пользователя и зоны, обработка оффлайн-сценариев когда контроллер двери недоступен, и интеграция с HID/Wiegand RFID-считывателями. Здесь важна надёжность, а не скорость разработки.
Архитектура: где живёт логика доступа
Мобильное приложение — это инструмент администратора СКУД и просмотра аудит-лога. Логика «открывать или нет» никогда не должна быть только на телефоне — контроллер двери (например HID VertX, Honeywell Pro-Watch) принимает решение сам по своей базе.
Типичный поток:
Мобильное приложение → REST API СКУД → Контроллер двери → Считыватель → Электромагнитный замок
Мобильное приложение управляет:
- Базой держателей карт (добавление, блокировка, удаление)
- Расписанием доступа (когда кому можно в какую зону)
- Мониторингом событий в реальном времени
- Ручным открытием двери (Remote Unlock)
Считывание RFID-карт мобильным телефоном
Сам телефон может выступать как RFID-ридер через NFC (для карт MIFARE Classic/DESFire) или через внешний BLE-ридер (для HF 13.56 MHz или LF 125 kHz карт).
NFC на iOS (CoreNFC) для MIFARE:
import CoreNFC
class AccessCardReader: NSObject, NFCTagReaderSessionDelegate {
var session: NFCTagReaderSession?
func startReading() {
session = NFCTagReaderSession(pollingOption: [.iso14443], delegate: self)
session?.alertMessage = "Приложите карту доступа"
session?.begin()
}
func tagReaderSession(_ session: NFCTagReaderSession, didDetect tags: [NFCTag]) {
guard let tag = tags.first, case .miFare(let mifareTag) = tag else { return }
session.connect(to: tag) { error in
if error != nil { session.invalidate(errorMessage: "Ошибка подключения"); return }
// Читаем UID карты (уникальный идентификатор)
let uid = mifareTag.identifier.map { String(format: "%02X", $0) }.joined()
self.onCardDetected(uid: uid)
session.invalidate()
}
}
}
UID MIFARE-карты — это просто уникальный номер. Для HID ProxCard 125 кГц — мобильный телефон не умеет читать физически. Нужен внешний BLE-ридер.
MIFARE DESFire EV2 — безопасное чтение:
DESFire карты используют в серьёзных СКУД. Чтение секторов требует аутентификации с AES-128:
// Команда SELECT Application
let selectCmd = Data([0x90, 0x5A, 0x00, 0x00, 0x03]) + applicationId + Data([0x00])
mifareTag.sendMiFareCommand(commandPacket: selectCmd) { response, error in
// Далее Authenticate с AES ключом приложения
}
Ключи хранятся в Secure Enclave — не в коде приложения. SecKeyCreateRandomKey с .secureEnclaveBound атрибутом.
Аудит-лог и мониторинг
Мониторинг событий в реальном времени через WebSocket или SSE (Server-Sent Events):
class AccessEventMonitor(private val accessApi: AccessControlApi) {
private val _events = MutableSharedFlow<AccessEvent>(replay = 50)
val events: SharedFlow<AccessEvent> = _events.asSharedFlow()
fun startMonitoring(zoneIds: List<String>) {
scope.launch {
accessApi.streamEvents(zoneIds).collect { event ->
_events.emit(event)
if (event.accessResult == AccessResult.DENIED) {
sendDeniedAlert(event)
}
}
}
}
}
data class AccessEvent(
val cardholderName: String,
val cardUid: String,
val doorName: String,
val timestamp: Long,
val accessResult: AccessResult, // GRANTED / DENIED / TAILGATING
val deniedReason: String? // "outside_schedule", "card_blocked", "no_permission"
)
deniedReason — детализация отказа. Охраннику нужно знать: карта заблокирована или просто человек пришёл вне расписания. Разные действия — разная реакция.
Удалённое управление дверьми
Remote Unlock — открытие двери без физического присутствия:
suspend fun remoteUnlock(doorId: String, durationSeconds: Int = 5) {
val result = accessApi.unlockDoor(
doorId = doorId,
unlockDuration = durationSeconds,
operatorId = currentUser.id,
reason = "remote_unlock_mobile"
)
if (result.isSuccess) {
logAuditEvent(AuditAction.REMOTE_UNLOCK, doorId)
}
}
Каждое удалённое открытие — в аудит-лог с operatorId. Без этого невозможно расследование инцидентов.
Сроки
Мобильное приложение администратора СКУД с аудит-логом и REST-интеграцией с существующей системой: 5 дней. С NFC-считыванием MIFARE UID и Remote Unlock: +3 дня. Полная интеграция с HID или Honeywell СКУД включая настройку контроллеров: 2–4 недели.







