承之前的第一版,這版改成用監聽的方式、事件(event)發生才做事
public class CardReader : BackgroundService
{
public CardReader()
{
using (var readerCtx = PCSC.ContextFactory.Instance.Establish(PCSC.SCardScope.System))
{
var monitor = MonitorFactory.Instance.Create(PCSC.SCardScope.System);
monitor.CardInserted += Monitor_CardInserted;
monitor.CardRemoved += Monitor_CardRemoved;
monitor.Start(readerCtx.GetReaders().FirstOrDefault());
}
}
private async void Monitor_CardRemoved(object sender, CardStatusEventArgs e)
{
// 卡片移除event
}
private async void Monitor_CardInserted(object sender, CardStatusEventArgs e)
{
try
{
using (var readerCtx = PCSC.ContextFactory.Instance.Establish(PCSC.SCardScope.User))
using (var reader = new PCSC.Iso7816.IsoReader(
context: readerCtx,
readerName: readerCtx.GetReaders().FirstOrDefault(),
mode: PCSC.SCardShareMode.Shared,
protocol: PCSC.SCardProtocol.Any))
{
var apduInit = new PCSC.Iso7816.CommandApdu(PCSC.Iso7816.IsoCase.Case4Short, reader.ActiveProtocol)
{
CLA = 0x00,
INS = 0xA4,
P1 = 0x04,
P2 = 0x00,
Data = new byte[]
{ 0xD1, 0x58, 0x00, 0x00, 0x01, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x11 }
};
var apduInitResponse = reader.Transmit(apduInit);
if (!(apduInitResponse.SW1.Equals(144) && apduInitResponse.SW2.Equals(0)))
{
Console.WriteLine("晶片卡非健保卡");
return;
}
var apduProfile = new PCSC.Iso7816.CommandApdu(PCSC.Iso7816.IsoCase.Case4Short, reader.ActiveProtocol)
{
CLA = 0x00,
INS = 0xCA,
P1 = 0x11,
P2 = 0x00,
Data = new byte[] { 0x00, 0x00 }
};
var apduProfileResponse = reader.Transmit(apduProfile);
if (apduProfileResponse.HasData)
{
//位元組資料
byte[] aryData = apduProfileResponse.GetData();
//文字編碼解碼器
var oUTF8 = Encoding.UTF8;
var oBIG5 = Encoding.GetEncoding("big5");
var patientName = oBIG5.GetString(aryData.Skip(12).Take(20).ToArray()).Trim().TrimEnd('\0');
var patientId = oUTF8.GetString(aryData.Skip(32).Take(10).ToArray()).Trim();
var patientBirth = oUTF8.GetString(aryData.Skip(42).Take(7).ToArray()).Trim();
var patientGender = oUTF8.GetString(aryData.Skip(49).Take(1).ToArray()).Trim();
Console.WriteLine($"讀取健保卡:[{patientName}]");
return;
}
}
}
catch (PCSC.Exceptions.RemovedCardException)
{
return;
}
catch (Exception ex)
{
Console.WriteLine(ex.InnerException?.Message ?? ex.Message);
return;
}
}
protected override async Task ExecuteAsync(CancellationToken stoppingToken)
{
while (!stoppingToken.IsCancellationRequested)
{
// 循環偵測/讀取讀卡機
await CheckCardReaderAsync();
// ...
}
}
private async Task CheckCardReaderAsync()
{
using (var readerCtx = PCSC.ContextFactory.Instance.Establish(PCSC.SCardScope.User))
{
// 找到讀卡機
if (readerCtx.GetReaders().Any())
{
var readerName = readerCtx.GetReaders().FirstOrDefault();
Console.WriteLine($"找到讀卡機:[{readerName}]");
}
else
{
Console.WriteLine("找不到讀卡機");
}
}
}
}
Reference: