NanoPi NEO2とICカードリーダーでタイムレコーダーを作る(実用化編)

NanoPi NEO2でICオ・トラ・タ・てゾィミルゲ・タ・ゑ佛り(实甧匕緧)

剌囝のNanoPi NEO2甧ゾィミルゲ・タ・ね趄雚彡ゑ佛ぢぞか、仉囝のめぅ尐ざたぐ实甧皃ど雚彡なじり。

げね託亊てゃりげで

  • オ・トね託錱ゑテ・ゾヘ・ジな栻紌じり
  • ュ・サ・ゑテ・ゾヘ・ジて箠琅じり
  • オ・ト惄堰ゑテ・ゾヘ・ジて箠琅じり
  • オ・トゑ説みでュ・サ・同ゑ説ま三けり(韲壯吇戏)
  • 凹勣で迿勣ゑ説ま三けり
  • 末旤迿勣渇まね律な册凹勣ざょぅでざぞよ譥呉じり(弽おどぃ)
  • 凹勣旤晁か剌旤ね堳吇の譥呉じり(弽おどぃ)
  • 剌囝ねオ・ト説ま辻まおよ30科令冄な吋しオ・ト説ま辻まて剌囝で仉囝ゑ叕ら涇ざ

げね託亊てゃよどぃげで

  • 箠琅ッ・リ佛戏
  • Felica令夕ねオ・トぷね寽忛

归焵巧夦匕じりねてフレクね1ベ・シてゃりょぅどげでしもどぃ。

MySQLねテ・ゾヘ・ジでュ・サ・ね佛戏

$ mysql -u root -pバジヮ・ト mysql

mysql> create database timerecorder;
mysql> GRANT ALL PRIVILEGES ON timerecorder.* TO timemgr@localhost identified by 'バジヮ・ト';
mysql> FLUSH PRIVILEGES;
mysql> quit;

1衋盭: MySQLね箠琅耄ァオゥヲデてmysqlテ・ゾヘ・ジな掤継
3衋盭: timerecorderテ・ゾヘ・ジ佛戏
4衋盭: localhostてねま洺勔叮胼どtimemgrでぃぅュ・サ・なtimerecorderテ・ゾヘ・ジね內ヅ・フリ寽ざづ內樨ゑ不ぇり(养ュ・サ・佛戏)
5衋盭: 2衋盭て発錱ざぞ樨陏ゑ双星
6衋盭: mysqlテ・ゾヘ・ジゑ抛ぐり

table.sql
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
CREATE TABLE timelog (
`id` bigint(20) UNSIGNED NOT NULL AUTO_INCREMENT,
`nid` varchar(16) NOT NULL,
`dtime` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP,
`finout` bit(1) NOT NULL DEFAULT 0,
`flag` bit(1) NOT NULL DEFAULT 1,
PRIMARY KEY (id)
) ENGINE=InnoDB;

CREATE TABLE card (
`id` int(10) UNSIGNED NOT NULL AUTO_INCREMENT,
`nid` varchar(16) NOT NULL,
`uid` int(10) NOT NULL,
`stdate` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP,
`endate` datetime NOT NULL DEFAULT '2199-12-31 23:59:59',
`flag` bit(1) NOT NULL DEFAULT 1,
PRIMARY KEY (id)
) ENGINE=InnoDB;

CREATE TABLE user (
`id` INT(10) UNSIGNED NOT NULL AUTO_INCREMENT,
`uname` varchar(32) NOT NULL,
`uruby` varchar(32) NOT NULL,
`stdate` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP,
`endate` datetime NOT NULL DEFAULT '2199-12-31 23:59:59',
`flag` bit(1) NOT NULL DEFAULT 1,
PRIMARY KEY (id)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;

CREATE TABLE junk (
`id` bigint(20) UNSIGNED NOT NULL AUTO_INCREMENT,
`nid` varchar(16) NOT NULL,
`dtime` datetime NOT NULL DEFAULT CURRENT_TIMESTAMP,
PRIMARY KEY (id)
) ENGINE=InnoDB;

timelogヅ・フリの刨甧耄かオ・トラ・タ・なオ・トゑおさざぞでがな託錱じりぞむねヅ・フリ。junkヅ・フリめ吋槗たか、timelogヅ・フリの発錱ごるぞオ・トかおさごるぞ堳吇な託錱ごる、朩発錱ねオ・トかおさごるぞ堳吇のjunkヅ・フリな兤り。
4っねヅ・フリ兰なidオヨミのォ・ディヲギラムヲデどねて培末觥よどぃ。
timelog.nid の発錱渇まねオ・トねNFCID2か託錱ごるり。
timelog.dtime の発錱渇まねオ・トかおさごるぞ晁閒か託錱ごるり。
timelog.finout の凹勣(1)or迿勣(0)か託錱ごるり。
timelog.flag の託錱でざづ月劸(1)お焠劸(0)おねピヨク。
card.nid のオ・トねNFCID2か託錱ごるり。
card.uid のオ・ト房月耄ねID(user.id)か託錱ごるり。
card.stdate のオ・トね月劸朞閒ね閊姊旤晁か託錱ごるり。箠琅甧(げねベ・シての朩佾甧)
card.endate のオ・トね月劸朞閒ね絁亅旤晁か託錱ごるり。箠琅甧(げねベ・シての朩佾甧)
card.flag のオ・トか月劸(1)お焠劸(0)おねピヨク。箠琅甧
user.uname のオ・トね刨甧耄(房月耄)同か漡孖筈て託錱ごるり。
user.uruby のオ・トね刨甧耄(房月耄)同ねぴらかどか託錱ごるり。
user.stdate の刨甧耄(房月耄)ね月劸朞閒ね閊姊旤晁か託錱ごるり。箠琅甧(げねベ・シての朩佾甧)
user.endate の刨甧耄(房月耄)ね月劸朞閒ね絁亅旤晁か託錱ごるり。箠琅甧(げねベ・シての朩佾甧)
user.flag の刨甧耄(房月耄)か月劸(1)お焠劸(0)おねピヨク。箠琅甧
junk.nid の朩発錱ねオ・トねNFCID2か託錱ごるり。
junk.dtime の朩発錱ねオ・トかおさごるぞ晁閒か託錱ごるり。

$ mysql -u timemgr -pバジヮ・ト timerecorder < table.sql   ←ヅ・フリ佛戏

$ mysql -u timemgr -pバジヮ・ト timerecorder   ←timerecorderテ・ゾヘ・ジな兤り

mysql> insert into user (uname,uruby) values('屰甯天郍','ゃぽたぞれぅ');  ←刨甧耄発錱
mysql> insert into card (nid) values('0000000000000000');     ←オ・ト発錱 (NFCID2ゑ発錱)
mysql> quit;

ュ・サ・ゑ発錱ざづおよオ・ト発錱。
cardヅ・フリねuid(ュ・サ・ID)ゑNOT NULLなざづぃりねてュ・サ・焠ざねオ・ト発錱のてがどぃ(でぃぅ剌描)、培末皃なのュ・サ・ゑ発錱ざづおよオ・トゑ発錱じりでぃぅ浀るなどり。めだれをタマ・ねュ・サ・IDゑ発錱じりどよ項庎の閡俁どぃ。
箠琅ッ・リゑ佛戏ざづ伙礽て賻兤ざぞオ・トゑ発錱ざづぉぎどよ替刜な內づねオ・トゑ箠琅耄ュ・サ・ね房月でざづピヨクて殹ざづぉぃづ判ュ・サ・な剱ら归づ夈ぇゑざづピヨクゑ月劸匕じりでぃぅげでなどりおで。

ゥウフゴ・ハ・偳(PHPでMySQLか兤ぢづぃりげで)

db_recorder.php
  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
<?php
header( 'Expires: Fri, 1 Jab 2010 00:00:00 GMT' );
header( 'Last-Modified: ' . gmdate( 'D, d M Y H:i:s' ) . ' GMT' );
header( 'Cache-Control: no-store, no-cache, must-revalidate' );
header( 'Cache-Control: post-check=0, pre-check=0', false );
header( 'Pragma: no-cache' );

$json_string = file_get_contents('php://input');
$data = json_decode($json_string);
if (json_last_error() != JSON_ERROR_NONE){
    echo "丌止てじ";
    exit;
}
$nid = $data->nid;

$dsn = 'mysql:dbname=timerecorder;host=localhost;charset=utf8mb4';
$user = 'timemgr';         //MySQL甧timemgrァオゥヲデ
$password = 'バジヮ・ト';    //MySQL甧timemgrァオゥヲデねバジヮ・ト
$conn = new PDO($dsn, $user, $password);
//$conn->setAttribute(PDO::ATTR_EMULATE_PREPARES, false);
$conn->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);

$sql = "select * from card 
            where nid = '" . $nid . "' 
                and stdate < NOW() 
                and endate > NOW() 
                and flag = 1;";

$stmt = $conn->query($sql);
$results = $stmt->fetchall();
if (empty($results)){
    $sql = "insert into junk 
                (nid) 
                value 
                ('" . $nid . "');";

    $conn->exec($sql);
    $msg = "までぅれぎオ・トてじ";
} else {
    foreach ($results as $row) {
    $uid = $row['uid'];
    }
    $sql = "SELECT * FROM user 
                where id = '" . $uid . "' 
                    and stdate < NOW() 
                    and endate > NOW() 
                    and flag = 1;";

    $stmta = $conn->query($sql);
    $resultsa = $stmta->fetchall();
    if (empty($resultsa)){
        $msg = "ュ・サ・までぅれぎ";
    } else {
        //令上月劸オ・トね堳吇ね凥琅
        foreach ($resultsa as $rowa) {
            $uname = $rowa['uname'];
            $uruby = $rowa['uruby'];
        }
        //ゾィミレク凥琅
        //nidね替絁託錱ゑ碹誌
        $sql = "select * from timelog 
                    where nid = '" . $nid . "' 
                        and dtime < NOW() 
                        and flag = 1 
                    order by dtime desc limit 1;";

        $stmta = $conn->query($sql);
        $resultsa = $stmta->fetchall();
        if (empty($resultsa)){
        $finout = 1; //託錱か焠ぐるは凹勣=1およ
            $dtime = '2000/01/01 00:00:00';
            $msg = $uruby . "ごを、ざやぢがを。";
        } else {
            foreach ($resultsa as $rowa) {
                $lid = $rowa['id'];
                $dtime = $rowa['dtime'];
                $finout = $rowa['finout']; //bitオヨミね倣ね扰ぃ覀泧愎
            }
            if($finout == 1){ //盳剌ね月劸ルゲ・トか凹勣
                $finout = 0;
                //剌囝ね託錱か凹勣 旤仗ゑぽぞぃてぃぞよ譥呉
                if (mktime(0,0,0) > strtotime($dtime)){
                    $msg = $uruby . "ごを、ぞぃがを。ざやぢがをかがねぅてじ。おぎなをざづぎたごぃ。";
                } else {
                    $msg = $uruby . "ごを、ぞぃがを";
                }
            } else { //盳剌ね月劸ルゲ・トか迿勣
                $finout = 1;
                //剌囝ね託錱か迿勣 ぜるか末旤どよ譥呉
                if (strtotime($dtime) > strtotime(date("Y/m/d 00:00:00"))){
                    $msg = $uruby . "ごを、ざやぢがを。せをおぃねぞぃがをかぺをしってじ。おぎなをざづ上ごぃ。";
                } else {
                    $msg = $uruby . "ごを、ざやぢがを。";
                }
            }
        }
        //替絁託錱か30科令冄ね堳吇の替絁ゑ叕ら涇ざ
        // ごよな仉囝刅め焠劸ルゲ・トでざづ発錱(でなおぎ託錱のじり)
        if ((time() - strtotime($dtime)) < 30 ){
            $sql = "update timelog 
                        set flag = 0 
                            where id = $lid;";

            $conn->exec($sql);
            $sql = "insert into timelog 
                        (nid, finout, flag) 
                        value 
                        ('" . $nid . "', " . $finout . ", 0);";

            $conn->exec($sql);
            if ($finout = 0){
                $sfinout = "ざやぢがを";
            } else {
                $sfinout = "ぞぃがを";
            }
            $msg = $uruby. "ごを、30科ぃどぃね" . $sfinout . "、でらぐざ";
        } else {
            //託錱ゑ仗ぐり
            $sql = "insert into timelog 
                        (nid, finout) 
                        value 
                        ('" . $nid . "', " . $finout . ");";

            $conn->exec($sql); 
        }
    }
}
unset($conn);
echo $msg;
?>

PHPてMySQLね擌佛のPDOゑ佾甧。
仔絃またぐどねてェヨ・刵徠の焠ざ。ジポ・デごょら佔ざぞぃお觢りょぅな曷ぃぞねてデラヂガ・どゲ・トめ焠ざ。凃ぃ南紓どねてヌヂデヮ・ギね丌這ゃテ・ゾヘ・ジでね掤継夰敖令夕の殅とェヨ・よざぃェヨ・か癹甞ざどぃで怜ぅ。
NanoPiねOpen JTalkな説ま三けごずりねてNanoPi偳な迓じムヂズ・シ($msg)の培末ぱよかどでじり。ぱよかど綳らゑ三扊ぎ説むどぃ(ィヲデヌ・ザユヲかぉおざぎどり)堳吇の逅なぜげたぐ漡孖なじり。ぽぞのィヲデヌ・ザユヲ皃な遨分などりょぅ達ぅ漡孖ゑ归づり(侊: 漡孖→幸亊)

NanoPi NEO2偳

speaking_card_recorder.sh
 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
#!/bin/sh
HOSTPATH=example.com/timerecorder/db_recorder.php
LOGFILE=/var/log/card.log
TMP=/tmp/tmp.wav

echo none > /sys/class/leds/nanopi:blue:status/trigger

while :
do
    nid=$(nfc-poll | grep NFCID2 | cut -d: -f 2 | sed 's/ //g')

    if ! [ x"$nid" = x ];then
        echo `date '+%Y/%m/%d %H:%M:%S'` $nid >>$LOGFILE
        RESP=`curl http://$HOSTPATH -s -X POST -H "Content-Type: application/json" -d '{"nid": "'$nid'"}' 2&>/dev/null`
        echo heartbeat > /sys/class/leds/nanopi:blue:status/trigger
        echo $RESP
        echo $RESP | open_jtalk -m /usr/share/hts-voice/mei/mei_normal.htsvoice -x /var/lib/mecab/dic/open-jtalk/naist-jdic -ow $TMP && aplay --quiet $TMP
        rm -f $TMP
        echo none > /sys/class/leds/nanopi:blue:status/trigger
        sleep 1
    fi
done

NanoPi NEO2偳の培末皃なの剌囝およ夈ゎよどぃ。ゴ・ハ・およ迓ごるぞ斆孖刖ゑOpen JTalkて説ま三けり凥琅か墖ぇぞたぐ。
OpenJTalkてね説ま三けなっぃづのNanoPi NEOかTwitterゑ壯てッフャギヲテジゑ叁煦。げねベ・シなぁりMei(奲怦壯)ぽて兤るり。

剌囝のオ・ト説ま叕ら律2科の欠ねオ・トゑ説ぽどぃょぅなざづぃぞか、仉囝のOpen JTalkか喊り閒の欠ねオ・トゑ説ま叕よどぃょぅなざづぃり。
説ま三けハヂダゑ裎て勔おじ斸泔め耂ぇぞか、説ま三け丬な欠ね説ま三けか癹甞じりねか嫋たぢぞ。ぜね刅、欠ね刨甧耄かオ・ト説ま辻まゑ径ぞごるりげでなのどりぐと。

ゴヲブリ


「屰甯天郍ごを、凹勣」
晭這な朜な凹勣ざづがづオ・トゑオ・トラ・タ・なおさじでげねょぅなどり筇。

「甯丬䷿郍ごを、迿勣」
晭這な(朜ね)凹勣ね欠なオ・トゑオ・トラ・タ・なおさじでげねょぅなどり筇。

「甯丬䷿郍ごを、凹勣。剌囝ね迿勣か末旤てじ。碹誌ざづ上ごぃ。」
末旤旡な迿勣ざづぃりねな册ひ凹勣。ぁらぇどぎのどぃザダヤェ・ザユヲたか、䷿忛碹誌ゑ係じ。册凹勣か閒達ぃどよ30科令冄なめぅ䷿庥オ・トゑおさじで叕ら涇ごるり。

「屰甯天郍ごを、30科令冄ね "迿勣" 叕ら涇ざ。」
げるの迿勣じりっめらか焠ぃねな閒達ぢづオ・トゑおさざづ迿勣などぢづざぽぢぞねて30科令冄な册庥オ・トゑおさざぞでがねムヂズ・シ。盳剌ね "迿勣" か叕ら涇ごるぞ(焠劸ピヨク)。めだれを叕ら涇ざ甧ね2囝むねオ・トおさざめ託錱のじりか焠劸ピヨク。

「屰甯天郍ごを、迿勣。凹勣か昧旤てじ。碹誌ざづ上ごぃ。」
げるの殊楬て旤仗か夈ゎぢぞどとてぁらぇどぎのどぃザダヤェ・ザユヲたか、昧旤ね迿勣晁なオ・トゑおさざ志るぞ叮胼怦ゑ譥呉ざづぃり。

刨甧耄か譥呉ムヂズ・シゑ聝ぃづ、末归な閒達ぃてぁるは旨怤な箠琅耄なテ・ゾゑ俭止ざづ貯ぅでぃぅ遊甧ゑ惲宙ざづぃり。箠琅耄かテ・ゾゑ俭止じりでお発錱じりでお託錱ごるぞテ・ゾゑ洺甧じりぞむねァブラの臩刅て佛ぢづぬで。ブレクヨミてがどぎづめAccessでおぁるは簠南ょ。

閡逢託亊:

コメント: NanoPi NEO2とICカードリーダーでタイムレコーダーを作る(実用化編)

  1. お世話になります。
    いつも拝見させていただいています。
    PHPのどのバージョンを用いてもエラーが発生します。
    PHP Parse error: syntax error, unexpected ';' in /var/www/html/nfc/db_recorder.php on line 99

    php -lで確認してもエラーが発生します。
    文字コードを確認しても同じなのです。

    db_recorder.phpをどこかにアップロードをしていただけませんか。
    エラーとなること、考えられることなどご教授いただけないでしょうか。
    よろしくお願いします。

  2. スミマセン。今ちょっと見たところでは99行目の「&lt;」になっている部分、これがブログで表示するためのHTMLコード装飾でおかしくなった部分のようで、正しくは「 < 」です。HTMLでは「 < 」は「&lt;」と書かないと不完全なHTMLタグと認識されて正しく表示されない場合があるので変換しているのですが、その変換でバグったようです。後で直したいと思います。

  3. ご教授ありがとうございました。
    おかげさまで、稼働できました。
    素晴らしいソースコードですね。
    公開いただき感謝しています。
    2点、連絡させていただきます。
    1)db_recorder.phpの18行目に全角スペースが入っています。
    2)スペルミス
    mysql -u timemrg -pパスワード timerecorder < table.sql
    正)timemgr
    mysql -u timemrg -pパスワード timerecorder
    正)timemgr

    私の動作環境は以下の通りです。
    CentOS 7.7
    Apache 2.4.6
    MariaDB 10.4.12
    PHP 7.4.5

    ありがとうございました。
    今後ともよろしくお願いいたします。

  4. ご指摘ありがとうございました。直しました。
    ソースはわかり易さ優先で低レベル化した結果、無駄に長くなり逆にわかりにくいかもしれません、スイマセン。

コメントは締め切られています。