This Frappe/ERPNext app automatically synchronizes employee check-in/check-out transactions from ZKTeco biometric devices with ERPNext Employee Checkin records.
- ✅ Real-time Sync: Configurable sync frequency (10 seconds to 1 hour)
- ✅ Smart Mapping: Automatically maps ZKTeco employee codes to ERPNext employees
- ✅ Duplicate Prevention: Prevents duplicate check-in records
- ✅ Test Connection: Preview transactions before enabling sync
- ✅ Dynamic Scheduler: Adjusts cron jobs based on sync frequency
- ✅ Comprehensive Logging: Detailed error tracking and sync statistics
- ZKBio Time software installed and running
- Device connected to network
- API access enabled
- Superuser credentials available
- ERPNext v13+ or Frappe v13+
- HR module enabled
- Employee records with matching employee codes
# Navigate to your bench directory
cd /path/to/your/bench
# Get the app
bench get-app https://github.com/your-username/zkteco_checkins_sync
# Install on your site
bench --site your-site.com install-app zkteco_checkins_sync
# Migrate the database
bench --site your-site.com migrate- Open ZKBio Time software
- Go to System Settings → Communication
- Note down the Server IP and Port (usually port 80)
- Ensure API access is enabled
- Create or note superuser credentials
# Test if device is accessible
curl -X GET "http://[DEVICE_IP]:[PORT]/iclock/api/transactions/"- Login to ERPNext
- Go to: Setup → ZKTeco Checkin Sync → ZKTeco Config
- Enable sync: Check "Enable Sync"
- Username: Your ZKBio Time superuser username
- Password: Your ZKBio Time superuser password
- Server IP: IP address of the ZKBio Time server (e.g., 192.168.1.100)
- Server Port: Port number (usually 80)
- Fill in Server IP and Port
- Click "Register API token"
- Token will be automatically generated and saved
- Click "Test Connection" button
- Review the transaction preview
- Verify employee mappings
- Sync Frequency: Choose from 10 seconds to 1 hour
- 10-30 seconds: For real-time monitoring
- 5-15 minutes: Recommended for most setups
- 30+ minutes: For less frequent updates
The system automatically maps ZKTeco employees to ERPNext using:
- Employee ID field in ERPNext matches
emp_codefrom ZKTeco - User ID field in ERPNext matches
emp_codefrom ZKTeco - Attendance Device ID field (if custom field exists)
ERPNext Employee → Employee ID = ZKTeco emp_code
Example: Employee ID = "001" matches ZKTeco emp_code = "001"
ERPNext Employee → User ID = ZKTeco emp_code
Example: User ID = "E001" matches ZKTeco emp_code = "E001"
-
Create custom field in Employee doctype:
- Field Name:
attendance_device_id - Field Type: Data
- Label: Attendance Device ID
- Field Name:
-
Set the field value to match ZKTeco emp_code
// The test will show:
✅ Connection status
📊 Number of transactions found today
👥 Employee mappings (Found/Not Found)
🔍 Sample transaction data- Go to ZKTeco Config
- Click Actions → Manual Sync
- Check Employee Checkin list for new records
- Click Actions → Sync Status
- Review:
- Last sync time
- Recent check-ins count
- Configuration status
{
"count": 8,
"data": [
{
"id": 2,
"emp_code": "001",
"first_name": "John",
"last_name": "Doe",
"punch_time": "2025-08-15 17:54:17",
"punch_state": "0", // 0 = Check In, 1 = Check Out
"punch_state_display": "Check In",
"terminal_alias": "Main_Entrance"
}
]
}ZKTeco Field → ERPNext Field
emp_code → employee (via mapping)
punch_time → time
punch_state ("0"/"1") → log_type ("IN"/"OUT")
terminal_alias → device_id
id → device_id (appended for uniqueness)❌ Symptoms: Test connection fails
🔧 Solutions:
- Verify Server IP and Port
- Check network connectivity
- Ensure ZKBio Time is running
- Verify firewall settings
❌ Symptoms: Cannot register API token
🔧 Solutions:
- Check username/password
- Ensure superuser privileges
- Verify API endpoint accessibility
❌ Symptoms: Transactions sync but employees not mapped
🔧 Solutions:
- Check Employee ID/User ID mapping
- Verify emp_code format consistency
- Review Employee master data
❌ Symptoms: Multiple records for same punch
🔧 Solutions:
- System automatically prevents duplicates
- Check device_id uniqueness
- Review time tolerance settings
Monitor error logs in:
- Error Log doctype in ERPNext
- System logs with title "ZKTeco"
# Enable detailed logging
frappe.log_error("Debug message", "ZKTeco Debug")# In hooks.py, modify get_scheduler_events()
# Add custom frequency mappings# Override find_employee_by_code() function
# Add custom mapping logic# Modify create_employee_checkin() function
# Map additional ZKTeco fields to custom fields- Small Office (< 50 employees): 30-60 seconds
- Medium Office (50-200 employees): 2-5 minutes
- Large Office (200+ employees): 5-15 minutes
-- Add indexes for better performance
ALTER TABLE `tabEmployee Checkin`
ADD INDEX `idx_employee_time` (`employee`, `time`);
ALTER TABLE `tabEmployee Checkin`
ADD INDEX `idx_device_time` (`device_id`, `time`);- Tokens are stored encrypted in ERPNext
- Regular token rotation recommended
- Limit API access to specific IPs if possible
- Use VPN for remote ZKTeco device access
- Implement firewall rules
- Regular security updates
- Monitor sync status - Weekly
- Review error logs - Daily
- Verify employee mappings - When adding new employees
- Test connection - After any network changes
- Employee Checkin data is included in ERPNext backups
- ZKTeco Config settings are preserved
- API tokens need re-registration after restore
- Error Log doctype in ERPNext
- ZKTeco Sync error logs
- ZKTeco Scheduler logs
# Check sync statistics
frappe.call('zkteco_checkins_sync.zkteco_checkin_sync.doctype.zkteco_config.zkteco_config.get_sync_status')For technical support or feature requests:
- Email: osama.ahmed@deliverydevs.com
- Initial release
- Basic sync functionality
- Dynamic scheduler
- Employee mapping
- Error handling and logging