- 投稿日:2019-06-25T22:25:35+09:00
アロー演算子の可変関数についてメモ
可変関数について簡単にメモ。
ex)class Person { public function sayHello() { echo "Hello."; } public function sayEvening() { echo "Good evening"; } } $now = intval(date('H')); if($now <= 16) { $greet = "sayHello"; } else { $greet = "sayEvening"; } $person = new Person; $person->$greet();アロー関数時も、関数名を変数にいれて、
$person->$greet();このように動的にメソッドを呼ぶことができる。
FWのモデルを呼ぶときにwhereメソッドなのか、andWhereメソッドなのか条件で場合分けするときに使ってみた。
- 投稿日:2019-06-25T22:25:35+09:00
アロー関数時の可変関数についてメモ
可変関数について簡単にメモ。
ex)class Person { public function sayHello() { echo "Hello."; } public function sayEvening() { echo "Good evening"; } } $now = intval(date('H')); if($now <= 16) { $greet = "sayHello"; } else { $greet = "sayEvening"; } $person = new Person; $person->$greet();アロー関数時も、関数名を変数にいれて、
$person->$greet();このように動的にメソッドを呼ぶことができる。
FWのモデルを呼ぶときにwhereメソッドなのか、andWhereメソッドなのか条件で場合分けするときに使ってみた。
- 投稿日:2019-06-25T21:33:56+09:00
laravelをAWS EC2にデプロイする
はじめに
vagrantなどのローカル開発環境で作成したlaravelプロジェクトをAWSのEC2上にデプロイする時に色々迷ったので、まとめとしてあげます。本番サーバにAWSを使ってみたいという方に見て頂ければと思います。
環境
php7.2.18
apache2.4.39
laravel5.7
EC2(Amazon Linux AMI 2018.03.0 (HVM), SSD Volume Type 無料枠)
RDS(mysqlを使用)前提
・ローカルで開発したプロジェクトをすでにgithubにプッシュ済み
・EC2にSSH接続できている
・EC2からRDSへ接続できる設定ができている(セキュリティグループなど)PHP7.2インストール
インストールできるリスト確認 sudo yum list available | grep php72 インストール sudo yum install -y \ php72 php72-devel php72-fpm php72-gd php72-mbstring \ php72-mysqlnd php72-pdo \ php72-xml php72-json インストール済みを確認 sudo yum list installed | grep php72 バージョン確認 php -vMysqlインストール RDSとの接続
インストール sudo yum -y install mysql 接続 mysql test_db -h <エンドポイント> -P 3306 -u test_user -papacheインストール
sudo yum install -y httpd24上記の流れでインストールを進めていると、なぜかすでにインストール済みと出た。
どこで入れたかわからなかった。
続きの設定を行っていくwabサーバの起動 sudo service httpd start システムがブートするたびにapacheが起動するよう設定 sudo chkconfig httpd on 有効か確認 chkconfig --list httpdドキュメントルートの権限変更
ユーザをapacheグループに追加 sudo usermod -a -G apache ec2-user 一旦ログアウト exit グループのメンバーシップを検証 groups グループ所有権をapacheグループに変更 sudo chown -R ec2-user:apache /var/www グループの書き込み許可追加 sudo chmod 2775 /var/www サブディレクトにグループ ID を設定するには、/var/www とサブディレクトのディレクトリ許可 find /var/www -type d -exec sudo chmod 2775 {} \; グループ書き込み許可を追加するには、/var/www とサブディレクトリのファイル許可を再帰的に変更します。 find /var/www -type f -exec sudo chmod 0664 {} \;Gitインストール
sudo yum install gitcomposer自身のインストール
インストール sudo curl -sS https://getcomposer.org/installer | php パスを通す sudo mv composer.phar /usr/local/bin/composerLaravelプロジェクトのClone
cd /var/www/html git clone <URL>apacheのドキュメントルート設定
設定ファイルを開く sudo vi /etc/httpd/conf/httpd.conf 以下に変更 DocumentRoot "/var/www/html/自分のlaravel_project/public 最終行に以下を追記 # .htaccess 有効化 <Directory /var/www/html/自分のlaravel_project/public> AllowOverride All </Directory>Laravelプロジェクトでcomposer インストール
cd /var/www/html/laravelプロジェクト composer installconfig, routeのキャッシュクリア
php artisan config:cache php artisan route:cacheプロジェクトのパーミッション変更
chmod 777 storage -R chmod 777 bootstrap/cache -R.envの設定
git cloneしたLaravelプロジェクトには.envファイルがないので、
composer insatallで作成された、.env.exsampleを使用するcp .env.example .env vi .env APP_URL=http://IPアドレス ←サーバーのIPにする DB_CONNECTION=mysql DB_HOST=←RDSのエンドポイント DB_DATABASE=データベース名 DB_USERNAME=RDS作成時のユーザ名 DB_PASSWORD=設定したパスワードキーを作成し、キャッシュをクリアする
php artisan key:generate php artisan config:clearテーブル作成
php artisan migrateシンボリックリンクの作成
これは作成したアプリで画像アップロードしているような場合は必要かと思います。
php artisan storage::linkブラウザで確認する
あとはブラウザでEC2のIPアドレスを入力するだけです!
ここまでくればブラウザで正しく表示されるかと思います!参考
https://qiita.com/reflet/items/11ad79e01e808876caa1
https://nori-life.com/install-laravel-aws/
https://docs.aws.amazon.com/ja_jp/AWSEC2/latest/UserGuide/install-LAMP.html
https://qiita.com/takg/items/9a044b36cdf216a42ba6
https://qiita.com/nbapps_dev/items/9307e6fc0edb59c09181
- 投稿日:2019-06-25T21:28:44+09:00
初心者がkonohaでVPSを借りてnginxでphpページを公開するまで -nginx・php-
nginxとphpをインストールして動かす
1:最新のnginxをインストールする
今回はapacheではなくてnginxでサーバーを立てようと思います。
#root権限で以下の作業を実行する sudo -s #nginx 公式サイトからPGPkeyをダウンロード wget https://nginx.org/keys/nginx_signing.key #PGPkeyを登録 apt-key add nginx_signing.key #aptのリストに追記する vi /etc/apt/sources.list → deb http://nginx.org/packages/ubuntu/ bionic nginx → deb-src http://nginx.org/packages/ubuntu/ bionic nginx #aptのリストを更新 apt update #nginxをaptでインストール apt install nginx #サーバー起動時にnginxも起動するように設定 systemctl enable nginx #nginxを起動 systemctl start nginxこれでひとまずnginxのインストールは完了!
2:最新のphpをインストールする
僕はphp大好き人間なのでphp使います。
#root権限で以下の作業を実行する sudo -s #aptの一覧にphpを追加する add-apt-repository ppa:ondrej/php #aptの一覧の更新 apt-get update #aptの一覧からphpの最新のバージョンを確認(今回は7.3だった) apt list|grep -i mariadb-server #phpをaptでインストール apt-get install php7.3 php7.3-fpm php7.3-mysql php7.3-mbstring php7.3-zip #phpの設定ファイルを編集する(その1) vi /etc/php/7.2/cli/php.ini → cgi.fix_pathinfo の値を 0 に → date.timezone の値を "Asia/Tokyo" に #phpの設定ファイルを編集する(その2) sudo /etc/php/7.2/fpm/php.ini → cgi.fix_pathinfo の値を 0 に → date.timezone の値を "Asia/Tokyo" にこれでphpもとりあえずインストール完了!
3:nginxとphpを設定する
nginxとphpの設定を弄ってちゃんと動くようにします。
#root権限で以下の作業を実行する sudo -s #nginxの設定ファイルを以下を参考に編集する vi /etc/nginx/conf.d/default.conf - - - - - location / { root /usr/share/nginx/html; index index.html index.htm; } ↓ location / { root /usr/share/nginx/html; index index.html index.htm index.php; } - - - - - - - - - - #location ~ \.php$ { # root html; # fastcgi_pass 127.0.0.1:9000; # fastcgi_index index.php; # fastcgi_param SCRIPT_FILENAME /scripts$fastcgi_script_name; # include fastcgi_params; #} ↓ location ~ \.php$ { root /usr/share/nginx/html; fastcgi_pass unix:/run/php/php7.2-fpm.sock; fastcgi_index index.php; fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; include fastcgi_params; } - - - - - - - - - - #location ~ /\.ht { # deny all; #} ↓ location ~ /\.ht { deny all; } - - - - - #phpの設定ファイルを編集する /etc/php/7.3/fpm/pool.d/www.conf → user の値を nginx に → group の値を nginx に → listen.owner の値を nginx に → listen.group の値を nginx に #サーバー起動時にphpも起動するように設定 systemctl enable php7.3-fpm #phpを再起動 systemctl restart php7.3-fpm #nginxを再起動 systemctl restart nginx #nginxグループにユーザーを加入させる usermod -aG nginx ユーザー名 #ドキュメントルートの所有者を変更する chown -R nginx:nginx /usr/share/nginx/html/ #ドキュメントルートの権限を変更する chmod -R 755 /usr/share/nginx/html/ここまでやればwebは動く。
…ハズ。
大体設定を変に弄っちゃってエラー吐くパターンが多いです。
僕もかれこれ6時間くらいはハマりました、めげずにがんばりましょう!!
- 投稿日:2019-06-25T21:28:44+09:00
初心者がkonohaでVPSを借りてnginxでphpページを公開するまで -nginxとphp編-
nginxとphpをインストールして動かす
1:最新のnginxをインストールする
今回はapacheではなくてnginxでサーバーを立てようと思います。
#root権限で以下の作業を実行する sudo -s #nginx 公式サイトからPGPkeyをダウンロード wget https://nginx.org/keys/nginx_signing.key #PGPkeyを登録 apt-key add nginx_signing.key #aptのリストに追記する vi /etc/apt/sources.list → deb http://nginx.org/packages/ubuntu/ bionic nginx → deb-src http://nginx.org/packages/ubuntu/ bionic nginx #aptのリストを更新 apt update #nginxをaptでインストール apt install nginx #サーバー起動時にnginxも起動するように設定 systemctl enable nginx #nginxを起動 systemctl start nginxこれでひとまずnginxのインストールは完了!
2:最新のphpをインストールする
僕はphp大好き人間なのでphp使います。
#root権限で以下の作業を実行する sudo -s #aptの一覧にphpを追加する add-apt-repository ppa:ondrej/php #aptの一覧の更新 apt-get update #aptの一覧からphpの最新のバージョンを確認(今回は7.3だった) apt list|grep -i mariadb-server #phpをaptでインストール apt-get install php7.3 php7.3-fpm php7.3-mysql php7.3-mbstring php7.3-zip #phpの設定ファイルを編集する(その1) vi /etc/php/7.2/cli/php.ini → cgi.fix_pathinfo の値を 0 に → date.timezone の値を "Asia/Tokyo" に #phpの設定ファイルを編集する(その2) sudo /etc/php/7.2/fpm/php.ini → cgi.fix_pathinfo の値を 0 に → date.timezone の値を "Asia/Tokyo" にこれでphpもとりあえずインストール完了!
3:nginxとphpを設定する
nginxとphpの設定を弄ってちゃんと動くようにします。
#root権限で以下の作業を実行する sudo -s #nginxの設定ファイルを以下を参考に編集する vi /etc/nginx/conf.d/default.conf - - - - - location / { root /usr/share/nginx/html; index index.html index.htm; } ↓ location / { root /usr/share/nginx/html; index index.html index.htm index.php; } - - - - - - - - - - #location ~ \.php$ { # root html; # fastcgi_pass 127.0.0.1:9000; # fastcgi_index index.php; # fastcgi_param SCRIPT_FILENAME /scripts$fastcgi_script_name; # include fastcgi_params; #} ↓ location ~ \.php$ { root /usr/share/nginx/html; fastcgi_pass unix:/run/php/php7.2-fpm.sock; fastcgi_index index.php; fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name; include fastcgi_params; } - - - - - - - - - - #location ~ /\.ht { # deny all; #} ↓ location ~ /\.ht { deny all; } - - - - - #phpの設定ファイルを編集する /etc/php/7.3/fpm/pool.d/www.conf → user の値を nginx に → group の値を nginx に → listen.owner の値を nginx に → listen.group の値を nginx に #サーバー起動時にphpも起動するように設定 systemctl enable php7.3-fpm #phpを再起動 systemctl restart php7.3-fpm #nginxを再起動 systemctl restart nginx #nginxグループにユーザーを加入させる usermod -aG nginx ユーザー名 #ドキュメントルートの所有者を変更する chown -R nginx:nginx /usr/share/nginx/html/ #ドキュメントルートの権限を変更する chmod -R 755 /usr/share/nginx/html/ここまでやればwebは動く。
…ハズ。
大体設定を変に弄っちゃってエラー吐くパターンが多いです。
僕もかれこれ6時間くらいはハマりました、めげずにがんばりましょう!!
- 投稿日:2019-06-25T21:11:52+09:00
【CodeIgniter】form_openの使い方
Codeigniter のform_openの使い方をまとめていきます。
まず最初に、ヘルパーのロードを行います。
下記のコードでフォームヘルパーをロードします。helper_load.php$this->load->helper('form');余談ですが、Codeigniter のフォームヘルパー関数の多くはフォーム値を自動的にエスケープしてくれるので、セキュリティ面でも安心です。
ヘルパーをロードしたのでform_open関数を使用できます。
form_open.phpform_open([$action = ''[, $attributes = ''[, $hidden = array()]]])引数を1つずつ解説していきます。
$action (string):フォームの actionもしくはtarget になるURLを指定します。
この時に注意することが、CodeigniterのURLはセグメントベースのアプローチを使用していることです。
例を以下に示します。example.com/class/function/ID最初のセグメント(class)は呼び出されるコントローラをクラスを表します。
第2セグメント(function)は呼び出されるメソッドを表します。
第3セグメント(ID)はコントローラに渡されるID、もしくは何かの変数を表します。ちなみに第3セグメントは任意です。
例えば第3セグメントにDBから取得したIDなどを埋め込むことで、任意のレコードを表示させることができます。
簡単な使用例を以下に示します。
example_form_open.phpecho form_open('data/send');このとき、dataは呼び出されるコントローラクラスを表し、sendは呼び出されるメソッドを表します。
また、この例では以下のようなformタグを生成します。
example_form_open.html<form method="post" accept-charset="utf-8" action="http://example.com/index.php/ data /send">ちなみに絶対パスでも書けなくはないですが、環境が変わると全てのURLを書き直す必要が出てきます。
しかし、セグメントベースで書けばコントローラとメソッドのみでURLが記述できるので、その必要がありません。$attributes (array):属性を追加できます。ちなみに任意です。
次のように連想配列を渡すことで、属性を追加できます。example_form_open.php$attributes = array('class' => 'data', 'id' => 'userform'); echo form_open('data/send', $attributes);こうすることで、formタグにclass属性、id属性も設定された状態で出力されます。
ちなみに以下のようなformタグを生成します。example_form_open.html<form method="post" accept-charset="utf-8" action="http://example.com/index.php/ data /send" class=" data " id=" userform ">$hidden (array) :隠しフィールドを任意で追加します。
隠しフィールドとは画面上には表示せずにuserから入力されない状態にして、特定の値を送信する時に用います。
例えば2段階認証で確認ページにデータを送りたい場合、データを隠しフィールドに格納してプログラムにデータを渡す場合とかです。次のように、連想配列を渡すことで、 隠しフィールドを追加できます。
example_form_open.php$hidden = array('username' => 'Tom', 'member_id' => '12'); echo form_open(' data /send', '', $hidden);この場合、以下のようなformタグを生成します。
example_form_open.html<form method="post" accept-charset="utf-8" action="http://example.com/index.php/ data /send"> <input type="hidden" name="username" value=" Tom " /> <input type="hidden" name="member_id" value="12" />
- 投稿日:2019-06-25T19:43:45+09:00
PHP_CodeSniffierのインストール、使い方
環境
CentOS 7.5
composer 1.7.2
PHP 7.2
Laravel 5.7.11インストール
$ composer require --dev "squizlabs/php_codesniffer=*"devオプションで開発環境でのみインストールするようにする。packagistの記載ではglobalオプションをつけているが、プロジェクトのみで使用するためつけていない。
インストールが完了すると、codesnifferを使用できるようになるので、ヘルプを表示してみる。
$ cd プロジェクトフォルダパス $ ./vendor/bin/phpcs -h Usage: phpcs [-nwlsaepqvi] [-d key[=value]] [--colors] [--no-colors] [--cache[=<cacheFile>]] [--no-cache] [--tab-width=<tabWidth>] [--report=<report>] [--report-file=<reportFile>] [--report-<report>=<reportFile>] 以下省略使い方
デフォルトで使用可能なコーディング規約を確認
$ ./vendor/bin/phpcs -i The installed coding standards are MySource, PEAR, PSR1, PSR12, PSR2, Squiz and Zendプロジェクトのルートディレクトリ直下にphpcs.xmlを作成(これがルールファイルになる)。以下はPSR-1とPSR-2の規約をチェックするルールファイル。プロジェクト直下のnode_modules, storage, vendorディレクトリはチェック対象外とする。
<?xml version="1.0"?> <ruleset name="Custom Standard"> <rule ref="PSR2"> <!-- "PSR2" の中で除外するルールがあれば記載 --> <!--<exclude name="Generic.Files.LineLength"/>--> <!--<exclude name="PSR1.Classes.ClassDeclaration"/>--> </rule> <!-- 追加するルールがあれば記載 --> <!--<rule ref="PEAR.WhiteSpace.ObjectOperatorIndent"/>--> <!-- 除外するファイル・ディレクトリ --> <exclude-pattern>node_modules/</exclude-pattern> <exclude-pattern>storage/</exclude-pattern> <exclude-pattern>vendor/</exclude-pattern> </ruleset>設定したチェックルールの一覧を確認する。
$ ./vendor/bin/phpcs -e The PSR2 Rule Set standard contains 42 sniffs Generic (12 sniffs) ------------------- Generic.ControlStructures.InlineControlStructure Generic.Files.ByteOrderMark Generic.Files.LineEndings 以下省略各ルールとチェックしている規約の内容はこちらを参考にさせていただきました。
PHP CodeSnifferにおけるPSR1,2の検知箇所と対応するSnifferphpcs.xmlではルールとしてPSR2のみを指定したが、チェックするルール自体は以下ファイルに記載されており、この中にPSR-1が記載されているので、PSR-1とPSR-2の両方がチェックされる事が分かる。
src/Standards/PSR2/ruleset.xmlファイル別に結果を出力
$ ./vendor/bin/phpcs --report=summary . PHP CODE SNIFFER REPORT SUMMARY --------------------------------------------------------------------------------------- FILE ERRORS WARNINGS --------------------------------------------------------------------------------------- /var/www/html/app/Http/Controllers/Admin/Test1Controller.php 0 2 /var/www/html/app/Http/Controllers/Admin/Test2Controller.php 6 2 /var/www/html/app/Http/Controllers/Admin/Test3Controller.php 0 2 /var/www/html/app/Http/Controllers/Admin/Test4Controller.php 7 7 /var/www/html/app/Http/Controllers/Admin/Test5Controller.php 0 6 --------------------------------------------------------------------------------------- A TOTAL OF 13 ERRORS AND 19 WARNINGS WERE FOUND IN 5 FILES --------------------------------------------------------------------------------------- PHPCBF CAN FIX 13 OF THESE SNIFF VIOLATIONS AUTOMATICALLY ---------------------------------------------------------------------------------------ルール別に結果を出力
$ ./vendor/bin/phpcs --report=source /path/to/code PHP CODE SNIFFER VIOLATION SOURCE SUMMARY ------------------------------------------------------------------------------------------- STANDARD CATEGORY SNIFF COUNT ------------------------------------------------------------------------------------------- [ ] Generic Files Line length too long 19 [x] PSR2 Methods Function call signature multiple arguments 4 [x] PSR2 Methods Function call signature content after open bracket 3 [x] PSR2 Methods Function call signature close bracket line 2 [x] PSR2 Methods Function call signature indent 2 [x] Squiz Control structures Control signature space after close parenthesis 1 [x] Squiz Control structures Control signature space after keyword 1 ------------------------------------------------------------------------------------------- A TOTAL OF 32 SNIFF VIOLATIONS WERE FOUND IN 7 SOURCES ------------------------------------------------------------------------------------------- PHPCBF CAN FIX THE 6 MARKED SOURCES AUTOMATICALLY (13 VIOLATIONS IN TOTAL) -------------------------------------------------------------------------------------------結果レポートをファイルとして出力。
プロジェクトフォルダ直下のresult以下にtest_phpcs.xmlファイルが作成される。$ ./vendor/bin/phpcs --report=checkstyle --report-file=result/test_phpcs.xml .
- 投稿日:2019-06-25T19:43:45+09:00
PHP_CodeSniffierのインストールと使い方
環境
CentOS 7.5
composer 1.7.2
PHP 7.2
Laravel 5.7.11インストール
$ composer require --dev "squizlabs/php_codesniffer=*"devオプションで開発環境でのみインストールするようにしている。packagistの記載ではglobalオプションをつけているが、composerのホームディレクトリにインストールしない場合は不要。
インストールが完了すると、codesnifferを使用できるようになるので、ヘルプを表示してみる。
$ cd プロジェクトフォルダパス $ ./vendor/bin/phpcs -h Usage: phpcs [-nwlsaepqvi] [-d key[=value]] [--colors] [--no-colors] [--cache[=<cacheFile>]] [--no-cache] [--tab-width=<tabWidth>] [--report=<report>] [--report-file=<reportFile>] [--report-<report>=<reportFile>] 以下省略使い方
デフォルトで使用可能なコーディング規約を確認
$ ./vendor/bin/phpcs -i The installed coding standards are MySource, PEAR, PSR1, PSR12, PSR2, Squiz and Zendプロジェクトのルートディレクトリ直下にphpcs.xmlを作成(これがルールファイルになる)。以下はPSR-1とPSR-2の規約をチェックするルールファイル。プロジェクト直下のnode_modules, storage, vendorディレクトリはチェック対象外とする。
<?xml version="1.0"?> <ruleset name="Custom Standard"> <rule ref="PSR2"> <!-- "PSR2" の中で除外するルールがあれば記載 --> <!--<exclude name="Generic.Files.LineLength"/>--> <!--<exclude name="PSR1.Classes.ClassDeclaration"/>--> </rule> <!-- 追加するルールがあれば記載 --> <!--<rule ref="PEAR.WhiteSpace.ObjectOperatorIndent"/>--> <!-- 除外するファイル・ディレクトリ --> <exclude-pattern>node_modules/</exclude-pattern> <exclude-pattern>storage/</exclude-pattern> <exclude-pattern>vendor/</exclude-pattern> </ruleset>設定したチェックルールの一覧を確認する。
$ ./vendor/bin/phpcs -e The PSR2 Rule Set standard contains 42 sniffs Generic (12 sniffs) ------------------- Generic.ControlStructures.InlineControlStructure Generic.Files.ByteOrderMark Generic.Files.LineEndings 以下省略各ルールとチェックしている規約の内容はこちらを参考にさせていただきました。
PHP CodeSnifferにおけるPSR1,2の検知箇所と対応するSnifferphpcs.xmlではルールとしてPSR2のみを指定したが、チェックするルール自体は以下ファイルに記載されており、この中にPSR-1が記載されているので、PSR-1とPSR-2の両方がチェックされる事が分かる。
src/Standards/PSR2/ruleset.xmlファイル別に結果を出力
$ ./vendor/bin/phpcs --report=summary . PHP CODE SNIFFER REPORT SUMMARY --------------------------------------------------------------------------------------- FILE ERRORS WARNINGS --------------------------------------------------------------------------------------- /var/www/html/app/Http/Controllers/Admin/Test1Controller.php 0 2 /var/www/html/app/Http/Controllers/Admin/Test2Controller.php 6 2 /var/www/html/app/Http/Controllers/Admin/Test3Controller.php 0 2 /var/www/html/app/Http/Controllers/Admin/Test4Controller.php 7 7 /var/www/html/app/Http/Controllers/Admin/Test5Controller.php 0 6 --------------------------------------------------------------------------------------- A TOTAL OF 13 ERRORS AND 19 WARNINGS WERE FOUND IN 5 FILES --------------------------------------------------------------------------------------- PHPCBF CAN FIX 13 OF THESE SNIFF VIOLATIONS AUTOMATICALLY ---------------------------------------------------------------------------------------ルール別に結果を出力
$ ./vendor/bin/phpcs --report=source /path/to/code PHP CODE SNIFFER VIOLATION SOURCE SUMMARY ------------------------------------------------------------------------------------------- STANDARD CATEGORY SNIFF COUNT ------------------------------------------------------------------------------------------- [ ] Generic Files Line length too long 19 [x] PSR2 Methods Function call signature multiple arguments 4 [x] PSR2 Methods Function call signature content after open bracket 3 [x] PSR2 Methods Function call signature close bracket line 2 [x] PSR2 Methods Function call signature indent 2 [x] Squiz Control structures Control signature space after close parenthesis 1 [x] Squiz Control structures Control signature space after keyword 1 ------------------------------------------------------------------------------------------- A TOTAL OF 32 SNIFF VIOLATIONS WERE FOUND IN 7 SOURCES ------------------------------------------------------------------------------------------- PHPCBF CAN FIX THE 6 MARKED SOURCES AUTOMATICALLY (13 VIOLATIONS IN TOTAL) -------------------------------------------------------------------------------------------結果レポートをファイルとして出力。
プロジェクトフォルダ直下のresult以下にtest_phpcs.xmlファイルが作成される。$ ./vendor/bin/phpcs --report=checkstyle --report-file=result/test_phpcs.xml .■参考にさせていただきました
新標準PSRに学ぶきれいなPHP
https://www.slideshare.net/yandod/psrphpPSR-1 基本コーディング規約(日本語)
http://www.infiniteloop.co.jp/docs/psr/psr-1-basic-coding-standard.htmlPSR-2 コーディングガイド(日本語)
http://www.infiniteloop.co.jp/docs/psr/psr-2-coding-style-guide.htmlPHP PSR一覧 2017年版
https://qiita.com/rana_kualu/items/f41d8f657df7709bda0fPHP CodeSnifferにおけるPSR1,2の検知箇所と対応するSniffer
https://qiita.com/piotzkhider/items/c90dd9253e9822fab3a2
- 投稿日:2019-06-25T18:24:10+09:00
さくらサーバー PDOがSQLSTATE[HY000] [2002] No such file or directory
いろいろ調べたけど下記を修正するだけで通った。
define('PDO_DSN','mysql:dbhost=localhost;dbname=' . DB_DATABASE);
↓
define('PDO_DSN','mysql:host=localhost;dbname=' . DB_DATABASE);
- 投稿日:2019-06-25T17:16:35+09:00
【Laravel】GItLab CIでユニットテストを自動実行+カバレッジを出力してGitLab Pagesにホスティングする
自前で運用しているGitLab CE(Community Edition)で、Pipelineを利用して
LaravelアプリケーションのPHP Unitを自動で回す設定を作成した時のメモPHP Unit設定
PHP Unitを実行した際に、カバレッジのデータがHTMLとして出力されるように、以下の設定を行う
phpunit.xml<?xml version="1.0" encoding="UTF-8"?> <phpunit backupGlobals="false" backupStaticAttributes="false" bootstrap="vendor/autoload.php" colors="true" convertErrorsToExceptions="true" convertNoticesToExceptions="true" convertWarningsToExceptions="true" processIsolation="false" stopOnFailure="false"> ... 省略 + <logging> + <log type="coverage-clover" target="public/coverage/logs/clover.xml"/> + <log type="coverage-html" target="public/coverage"/> + </logging> </phpunit>
GitLab CI設定
Gitリポジトリのルート配下に
.gitlab-ci.yml
を作成する。.gitlab-ci.yml# composerによって生成されるvendor配下をキャッシュする cache: key: ${CI_COMMIT_REF_SLUG} paths: - vendor/ # Build and Test php-7.2: &build image: php:7.2-cli-alpine variables: COMPOSER_VERSION: 1.8.6 script: # 必要なライブラリをインストール - apk add git autoconf build-base - pecl install xdebug - docker-php-ext-install mysqli pdo pdo_mysql - docker-php-ext-enable xdebug - curl https://getcomposer.org/download/${COMPOSER_VERSION}/composer.phar > composer.phar - php composer.phar install # .envの作成 - cp .env.example .env # ユニットテストの実行 - vendor/bin/phpunit --configuration phpunit.xml --coverage-text --colors=never artifacts: paths: # 生成したカバレッジレポートを、次のjobで利用する - public/coverage # 異なるPHPのバージョンを指定してジョブを回したい場合、 # 以下のように`build`アンカーを呼び出したうえで、別のalpineのimageを指定すればOK php-7.1: <<: *build image: php:7.1-cli-alpine # 以下のようにすれば、composerのバージョンを指定できる variables: COMPOSER_VERSION: 1.6.5 # Unitテストのカバレッジを、Gitlab Pagesにホスティングする pages: stage: deploy extends: php-7.2 artifacts: paths: - public only: - developこれで、GitLabのリモートリポジトリにgit pushすると自動でテストが走る。
以下のURLにアクセスすると、HTML出力したユニットテストのカバレッジが確認できる。
http://{GitLabドメイン}/{プロジェクト名}/coverage/
参考サイト
- 投稿日:2019-06-25T17:16:35+09:00
GItLab CIでユニットテストを自動実行+カバレッジを出力してGitLab Pagesにホスティングする
自前で運用しているGitLab CE(Community Edition)で、Pipelineを利用して
LaravelアプリケーションのPHP Unitを自動で回す設定を作成した時のメモPHP Unit設定
PHP Unitを実行した際に、カバレッジのデータがHTMLとして出力されるように、以下の設定を行う
phpunit.xml<?xml version="1.0" encoding="UTF-8"?> <phpunit backupGlobals="false" backupStaticAttributes="false" bootstrap="vendor/autoload.php" colors="true" convertErrorsToExceptions="true" convertNoticesToExceptions="true" convertWarningsToExceptions="true" processIsolation="false" stopOnFailure="false"> ... 省略 + <logging> + <log type="coverage-clover" target="public/coverage/logs/clover.xml"/> + <log type="coverage-html" target="public/coverage"/> + </logging> </phpunit>
GitLab CI設定
Gitリポジトリのルート配下に
.gitlab-ci.yml
を作成する。.gitlab-ci.yml# composerによって生成されるvendor配下をキャッシュする cache: key: ${CI_COMMIT_REF_SLUG} paths: - vendor/ # Build and Test php-7.2: &build image: php:7.2-cli-alpine variables: COMPOSER_VERSION: 1.8.6 script: # 必要なライブラリをインストール - apk add git autoconf build-base - pecl install xdebug - docker-php-ext-install mysqli pdo pdo_mysql - docker-php-ext-enable xdebug - curl https://getcomposer.org/download/${COMPOSER_VERSION}/composer.phar > composer.phar - php composer.phar install # .envの作成 - cp .env.example .env # ユニットテストの実行 - vendor/bin/phpunit --configuration phpunit.xml --coverage-text --colors=never artifacts: paths: # 生成したカバレッジレポートを、次のjobで利用する - public/coverage # 異なるPHPのバージョンを指定してジョブを回したい場合、 # 以下のように`build`アンカーを呼び出したうえで、別のalpineのimageを指定すればOK php-7.1: <<: *build image: php:7.1-cli-alpine # 以下のようにすれば、composerのバージョンを指定できる variables: COMPOSER_VERSION: 1.6.5 # Unitテストのカバレッジを、Gitlab Pagesにホスティングする pages: stage: deploy extends: php-7.2 artifacts: paths: - public only: - developこれで、GitLabのリモートリポジトリにgit pushすると自動でテストが走る。
以下のURLにアクセスすると、HTML出力したユニットテストのカバレッジが確認できる。
http://{GitLabドメイン}/{プロジェクト名}/coverage/
参考サイト
- 投稿日:2019-06-25T14:53:46+09:00
php-master-changes 2019-06-24
今日はテストの修正があった!
2019-06-24
cmb69: Split test case
- https://github.com/php/php-src/commit/94df6dc3fd07fa187ba09c587a8d1357fd8bbe6f
- [7.4~]
- sapi/cli で、ビルトインサーバのテストがなんかこけるので、1 テストで 2 ポートテストしていたのを 2 テストに分離
- 投稿日:2019-06-25T14:05:36+09:00
マイグレーションについて
前職で、「マイグレーションについて調べてみて。」と言われたけど、結局何を調べて答えたのか忘れてメモもしてなくて。改めて調べてみました。
↑キーワード検索から、いろんな人の記事を漁るのも良い方法かもしれません。
Migration とは何者か
【現時点での理解】
複数人で開発していて、データベースが勝手に書き換えられるような環境での開発で、
全員がおんなじ状態のDBを使えるようにする仕組み。ソースコードに対するバージョンコントローラの Git 、
データベースに対するバージョンコントローラの Migrationみたいなものでしょうか。
※筆者は主に PHP/Laravel を書きます。PHP/Laravel の場合
Laravelドキュメント:マイグレーション
bz0さんの記事Ruby on Rails の場合
Python/Django の場合
- 投稿日:2019-06-25T13:34:17+09:00
PHPで何かつくる!
本稿は、筆者のアイデアノートとなります。
書き始めて、それぞれ形になったら、別記事としてUPしていきます。
別記事で書いてる物をPHPでも実装してみることになると予想。目的
- PHPと仲良くなる。
- Laravel 以外のフレームワークに積極的に触れる。
作りたいもの
- Webスクレイピングサイト
- パスワード暗号化提案サイト
- 自宅監視システム(虫検知)
- Raspberry Pi と カメラモジュール
- 虫判定 = Tensorflow をこねこねする
参考
- 投稿日:2019-06-25T13:05:03+09:00
ライブラリを使わずにTwitter APIでダイレクトメッセージを送信する [PHP]
TwitterのAPIを利用して、任意のユーザーへダイレクトメッセージを送信するPHPのコードです。ライブラリは使わずに直接実装するケースを想定しています。
前提条件
・送信元のアカウントでAPIを利用出来る。(Twitter Developersに登録済み)
・送信相手のユーザーIDが判明している。
・送信相手がこちら(送信元)のアカウントをフォローしている。処理の流れ
- 署名キーを作る
- HTTPヘッダ用のパラメータを作る
- パラメータ(2.)をソートする
- 署名キー(1.)とパラメータ(3.)から署名を作る
- パラメータ(3.)に署名(4.)を追加する
- パラメータ(3.)からHTTPヘッダ用の配列を作る
- POSTデータ用の配列を作る
- cURLでエンドポイントにデータを投げる
- エンドポイントの応答を受け取る
接続先(エンドポイント)
https://api.twitter.com/1.1/direct_messages/events/new.json
処理に必要な値
Twitter Developersで下記の値を予め取得しておく必要があります。
$api_key = 'APIキー'; $api_secret = 'APIシークレット'; $access_token = 'アクセストークン'; $access_token_secret = 'アクセストークンシークレット';1. 署名キーを作る
APIシークレットとアクセストークンシークレットを用いて署名キーを作成します。
$signature_key = rawurlencode( $api_secret )."&".rawurlencode( $access_token_secret );2. HTTPヘッダ用のパラメータを作る
エンドポイントへ渡すための認証データを連想配列で作成します。
$paramData = array( "oauth_token" => rawurlencode( $access_token ), "oauth_consumer_key" => rawurlencode( $api_key ), "oauth_signature_method" => rawurlencode( "HMAC-SHA1" ), "oauth_timestamp" => time(), "oauth_nonce" => microtime(), "oauth_version" => rawurlencode( "1.0" ) );3. パラメータをソートする
ksortで連想配列をソートします。これを忘れると認証エラーが起き得ます。
ksort( $paramData );4. 署名キーとパラメータから署名を作る
1で作成した署名キーと、2で作成したパラメータの配列を利用して、署名を作ります。
$sig_param = rawurlencode('POST')."&". rawurlencode('https://api.twitter.com/1.1/direct_messages/events/new.json')."&". rawurlencode( http_build_query( $paramData , "", "&" ) ); $signature = hash_hmac( "sha1", $sig_param, $signature_key, TRUE ); $signature = base64_encode( $signature );5. パラメータに署名を追加する
連想配列に署名を追加します。
$paramData['oauth_signature'] = $signature;6. パラメータからHTTPヘッダ用の配列を作る
cURLで使うための配列を新たに作成しておきます。
$httpHeader = array( 'Authorization: OAuth '.http_build_query( $paramData, "", "," ), 'content-type: application/json' );7. POSTデータ用の配列を作る
cURLで送信するボディにあたるデータを作成します。これは後にjsonエンコードします。
ここで送信先のユーザーIDと、送信したいメッセージもセットします。$postData = array( "event" => array( "type" => "message_create", "message_create" => array( "target" => array( "recipient_id" => '送信先のユーザID' //送信先ID ), "message_data" => array( "text" => '送信メッセージ' //送信したいメッセージ ) ) ) );Eventオブジェクトの中に入れ子で情報を詰め込んでいます。
上記のサンプルコードは必須項目のみを記述していますが、message_dataオブジェクト(メッセージが入っているところ)にはオプションも追記可能です。詳しくはTwitter公式のAPIリファレンスを確認してください。1
8. cURLでエンドポイントにデータを投げる
これまでに作成した各種配列をセットして、cURLでエンドポイントへデータを渡します。
$ch = curl_init(); curl_setopt($ch, CURLOPT_HTTPHEADER, $httpHeader); curl_setopt($ch, CURLOPT_URL, 'https://api.twitter.com/1.1/direct_messages/events/new.json'); curl_setopt($ch, CURLOPT_CUSTOMREQUEST, rawurlencode('POST')); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); curl_setopt($ch, CURLOPT_POSTFIELDS, json_encode( $postData )); $json = curl_exec($ch); curl_close($ch);9. エンドポイントの応答を受け取る
ダイレクトメッセージの送信に成功すると、message_createイベントのIDやタイムスタンプを含んだjsonデータが返されます。ここでjsonデータを連想配列へ変換しておきます。
$response = json_decode( $json, true ); echo var_dump( $response );var_dumpした結果が下記です。
array(1) { ["event"]=> array(4) { ["type"]=> string(14) "message_create" ["id"]=> string(19) "イベントID" ["created_timestamp"]=> string(13) "1561275503817" //ミリ秒 ["message_create"]=> array(3) { ["target"]=> array(1) { ["recipient_id"]=> string(10) "送信先のID" } ["sender_id"]=> string(19) "送信元のID" ["message_data"]=> array(2) { ["text"]=> string(24) "送信メッセージ" ["entities"]=> array(4) { ["hashtags"]=> array(0) { } ["symbols"]=> array(0) { } ["user_mentions"]=> array(0) { } ["urls"]=> array(0) { } } } } } }これ以降の処理は、idが含まれているか、などの条件で処理判定すればよいかと思います。
if( empty( $response['event']['id'] ) ){ //失敗時の処理 } else { //成功時の処理 }尚、レスポンスデータに含まれるタイムスタンプはミリ秒で返ってきます。2
そのままでは日付表示が出来ないので、秒に変換する必要があります。$timestamp = $response['event']['created_timestamp']; echo date('Y-m-d H:i:s', ( $timestamp / 1000 )); //1000で割って秒にする結果
2019-06-24 06:42:31
最後に
Qiitaに登録して初めて書く記事となります。コードや文章に稚拙な部分があるかもしれませんが、ご容赦ください。可読性を優先してわざと定数化していない箇所はあります。
誤りのご指摘やご意見などがありましたら、是非お願いいたします。
注釈(参考サイト)
- 投稿日:2019-06-25T11:02:03+09:00
PHPのバージョンアップグレード方法
はじめに
PHPのバージョンを上げる際、色々やりすぎて訳わからなくなって他ので思考整理のため、備忘録としてまとめました。
今回はPHP7.2x系から7.3x系へのバージョンアップを行います。手順
現在のバージョンを確認します。
$ php -v PHP 7.2.19 (cli) (built: Jun 17 2019 09:03:55) ( NTS ) Copyright (c) 1997-2018 The PHP Group Zend Engine v3.2.0, Copyright (c) 1998-2018 Zend Technologies with Zend OPcache v7.2.19, Copyright (c) 1999-2018, by Zend TechnologiesPHP7.2x系になってることが確認できました。
brew search
コマンドでbrew installできるphpのバージョンを確認できます。
(今回はphp7系で探してみます。)$ brew search php@7 ==> Formulae php@7.1 php@7.2 ✔ php@7.3上記のように表示されるはずです。
自分はphp@7.2は既にインストール済みなので右にチェックマークがついてます。
ではphp@7.3をインストールしましょう。$ brew install php@7.3 ==> Downloading https://homebrew.bintray.com/bottles/php-7.3.6_1.mojave.bottle.tar.gz Already downloaded: /Users/KazukiSaito/Library/Caches/Homebrew/downloads/d1adefd1f87d0e00b888bf32e0a29a1e0e0ee885ff3508c2e46ce1ad7f1711d9--php-7.3.6_1.mojave.bottle.tar.gz ==> Pouring php-7.3.6_1.mojave.bottle.tar.gz ==> /usr/local/Cellar/php/7.3.6_1/bin/pear config-set php_ini /usr/local/etc/php/7.3/php.ini system ==> /usr/local/Cellar/php/7.3.6_1/bin/pear config-set php_dir /usr/local/share/pear system ==> /usr/local/Cellar/php/7.3.6_1/bin/pear config-set doc_dir /usr/local/share/pear/doc system ==> /usr/local/Cellar/php/7.3.6_1/bin/pear config-set ext_dir /usr/local/lib/php/pecl/20180731 system ==> /usr/local/Cellar/php/7.3.6_1/bin/pear config-set bin_dir /usr/local/opt/php/bin system ==> /usr/local/Cellar/php/7.3.6_1/bin/pear config-set data_dir /usr/local/share/pear/data system ==> /usr/local/Cellar/php/7.3.6_1/bin/pear config-set cfg_dir /usr/local/share/pear/cfg system ==> /usr/local/Cellar/php/7.3.6_1/bin/pear config-set www_dir /usr/local/share/pear/htdocs system ==> /usr/local/Cellar/php/7.3.6_1/bin/pear config-set man_dir /usr/local/share/man system ==> /usr/local/Cellar/php/7.3.6_1/bin/pear config-set test_dir /usr/local/share/pear/test system ==> /usr/local/Cellar/php/7.3.6_1/bin/pear config-set php_bin /usr/local/opt/php/bin/php system ==> /usr/local/Cellar/php/7.3.6_1/bin/pear update-channels ==> Caveats To enable PHP in Apache add the following to httpd.conf and restart Apache: LoadModule php7_module /usr/local/opt/php/lib/httpd/modules/libphp7.so <FilesMatch \.php$> SetHandler application/x-httpd-php </FilesMatch> Finally, check DirectoryIndex includes index.php DirectoryIndex index.php index.html The php.ini and php-fpm.ini file can be found in: /usr/local/etc/php/7.3/ To have launchd start php now and restart at login: brew services start php Or, if you don't want/need a background service you can just run: php-fpm ==> Summary ? /usr/local/Cellar/php/7.3.6_1: 521 files, 77.0MB $これでインストールできたはずです。
(先ほどのphp searchコマンドで確認したらphp@7.3の横にもチェックマークがついてるのが確認できるはずです。)PHPの環境PATHを通します。
現在のPATHを確認します。(ちなみにこの時点でバージョンは変わってないはずです。)$ which php /usr/local/opt/php@7.2/bin/php上記のようになってますね。
以下の7.2を7.3に変えるだけです。
$ vi .bash_profile - export PATH="$PATH:/usr/local/opt/php@7.2/bin" + export PATH="$PATH:/usr/local/opt/php@7.3/bin"再度バージョンを確認します。
$ php -v PHP 7.3.6 (cli) (built: Jun 17 2019 08:40:34) ( NTS ) Copyright (c) 1997-2018 The PHP Group Zend Engine v3.3.6, Copyright (c) 1998-2018 Zend Technologies with Zend OPcache v7.3.6, Copyright (c) 1999-2018, by Zend Technologies反映されてますね。
ちなみにPHPの環境PATHの方も確認してみます。
$ which php /usr/local/opt/php@7.3/bin/phpPATHの方も反映されてますね。
これで終わりです。
まとめ
①brew installでアップグレードしたいバージョンのPHPを取得する。
②環境PATHを通す。Homebrewを使ってPHPのバージョンをアップグレードしたい時は上記2点のポイントを抑えておけば今後のバージョンアップグレードは困らないと思います。
(やったことないので分からないけど多分、ダウングレードも同じ要領で行けるのかな・・・、ここについては自信ないです。)
- 投稿日:2019-06-25T11:00:59+09:00
私がプログラミングスクールにいく理由
大学4年生法学部の学生です!
私がなぜ4年生になってプログラミングスクールに行こうと思ったのかを簡単に紹介したいと思います。
現在、プログラミング未経験だけど、プログラマーになりたいと思った方は是非参考にしてください。入社するまでに周りと差をつけたいから
私は法学部ですが、学んできたことと全く関係のないIT企業にシステムエンジニアとして内定を頂いております。法学部ですので、プログラミング経験はほとんどありません。私はその状況に危機感を覚え、入社するまでにはある程度実践的なプログラミング知識を身につけておこう、そうすることで入社するまでに他の学生と差をつけようと考えプログラミングスクールに参加することを決めました。
学習の成果
実際にどのようなことを学んだのか最後に一部だけ紹介します。スクール2日目で書いた内容です。
わからないことは全てメンターに聞けるので、早く学習を進めることができました。<?php session_start(); if (empty($_SESSION["name"]) && empty($_SESSION["email"])){ require('validation.php'); validation($_POST["name"],$_POST["email"]); } ?> <!DOCTYPE html> <html lang="ja" dir="ltr"> <head> <meta charset="utf-8"> <title></title> </head> <body> <h4>入力内容を確認してください</h4> <form action="complete.php" method="POST"> <p>氏名</p> <?php if (isset($_SESSION["name"])) { echo $_SESSION["name"]; } ?> <p>メールアドレス</p> <?php if (isset($_SESSION["email"])) { echo $_SESSION["email"]; } ?> <p><input type="submit" value="送信する"></p> </form> <form action="input.php" method="POST"> <p><input type="submit" value="戻る"</p> </form> </body> </html>
- 投稿日:2019-06-25T10:38:16+09:00
google-api-php-clientを使ってGoogle Analyticsのデータを取得する
はじめに
Webアクセス解析ツールとして Google Analytics(以下GA)を利用しています。
自社のデータはGAから、競合他社はVALUESから、というスキームが多いのですが
それぞれ別々にデータを取得してBIツールで繋ぎ合わせる、というやり方ではなく
1つのWebサービス上でシームレスに繋ぎ合わさったサービスの開発に取り組んでいます。データ検証として、google-api-php-clientを使ってGAデータの取得までを試したため
作成したラッパーとともに記載します。GAデータを取得するまで
1.サービスアカウントキーの取得
2.Google Analytics APIの有効化
3.Google API Client Libraries(PHP)のインストール
4.GA側の設定
5.GAデータの取得
※ Googleアカウントは既にある前提
※ 1~3は特に順番はありません(どれを先にやってもよいです)
※ 1,3は既に他で実施済みであれば不要1.サービスアカウントキーの取得
※既に取得済みであればこの項は不要です。
Google Developer Console または Google Cloud Platform の
APIとサービス > 認証情報
から認証情報(サービスアカウントキー)を作成します。
※サービスアカウント名を入力すると、サービスアカウントIDが自動で振られます。
※サービスアカウントIDをメモしておきます(後で使います)
※作成したJSONファイルを保存します(後で使います)
2.Google Analytics APIの有効化
Google Developer Console または Google Cloud Platform の
APIとサービス > ライブラリ
からGoogle Analytics APIを有効化します。
※ Google Analytics APIは一番下の その他 の中にあります。
※上図は既にAPIを有効にした後ですが、前であれば「有効にする」ボタンが表示されているはずです。
※ まだプロジェクトがない場合は、併せてプロジェクトも作成しておきましょう。3.Google API Client Libraries(PHP)のインストール
※既にインストール済みであればこの項は不要です
google-api-php-clientのGitHubはこちら
google-api-php-client
Composer
またはソースコードを直接ダウンロードします。4.GA側の設定
作成したサービスアカウントIDをGA側に設定します。
目的のビューに対してユーザー(1.で取得したサービスアカウントID)を追加します。
※メールアドレスにサービスアカウントIDを設定します。
※権限は「表示と分析」のみで大丈夫です。5.GAデータの取得
以下がサンプルコードです(PHP)
APIを使いやすいようにラッパーを用意します。
GAwrapper.php<?php require_once 'google-api-php-client/vendor/autoload.php'; Class GAwrapper { private $viewId; private $analytics; public function __construct($authKey, $viewId) { $this->viewId = $viewId; $client = new Google_Client(); $client->setApplicationName("Analytics Reporting"); $client->setAuthConfig($authKey); $client->setScopes(['https://www.googleapis.com/auth/analytics.readonly']); $analytics = new Google_Service_Analytics($client); $this->analytics = $analytics; } public function query($startDate='7daysAgo', $endDate='yesterday', $aryMetrics=array(), $aryDimensions=array(), $arySort=array(), $aryFilters=array(), $maxResults=1000) { // Metrics if (count($aryMetrics) > 0) { foreach ($aryMetrics as $key => $value) { $aryMetrics[$key] = 'ga:'.$value; } $metrics = implode(',', $aryMetrics); } else { $metrics = ''; } // Dimensions if (count($aryDimensions) > 0) { foreach ($aryDimensions as $key => $value) { $aryDimensions[$key] = 'ga:'.$value; } $dimensions = implode(',', $aryDimensions); } else { $dimensions = ''; } // Sort if (count($arySort) > 0) { foreach ($arySort as $key => $value) { if (strpos($value, '-') === 0) { $arySort[$key] = '-ga:'.substr($value, 1); } else { $arySort[$key] = 'ga:'.$value; } } $sort = implode(',', $arySort); } else { $sort = ''; } // Filters if (count($aryFilters) > 0) { foreach ($aryFilters as $key => $value) { $aryFilters[$key] = 'ga:'.$value; } $filters = implode(';', $aryFilters); } else { $filters = ''; } $optParams = array(); if (strlen($dimensions) > 0) { $optParams['dimensions'] = $dimensions; } if (strlen($sort) > 0) { $optParams['sort'] = $sort; } if (strlen($filters) > 0) { $optParams['filters'] = $filters; } $optParams['max-results'] = $maxResults; // Excute Query $result = $this->analytics->data_ga->get('ga:'.$this->viewId, $startDate, $endDate, $metrics, $optParams); $data = array(); foreach ($result->rows as $row) { $index = 0; $outDimensions = array(); foreach ($aryDimensions as $dimension) { $value = $row[$index]; if ($dimension == 'ga:date') { $value = substr($value, 0, 4).'-'.substr($value, 4, 2).'-'.substr($value, 6, 2); } else if ($dimension == 'ga:isoYearIsoWeek') { $value = $this->weekStartDate(substr($value, 0, 4), (int)substr($value, 4, 2), $startDate).'週'; } else if ($dimension == 'ga:yearMonth') { $value = substr($value, 0, 4).'-'.substr($value, 4, 2); } $outDimensions[str_replace('ga:', '', $dimension)] = $value; $index++; } $outMetrics = array(); foreach ($aryMetrics as $value) { $outMetrics[str_replace('ga:', '', $value)] = $row[$index]; $index++; } $aryOut = array(); foreach ($outDimensions as $key => $value) { $aryOut[$key] = $value; } $aryOut['metrics'] = $outMetrics; $data[] = $aryOut; } return $data; } // 年と週番号から、その週の最初の日付文字列を得る(ISO 8601準拠) private function weekStartDate($year, $weekNumber=1, $startDate) { $time = strtotime("{$year}-01-01"); $week = date("w", $time); if ($week > 4 || $week == 0) { $time = strtotime("next Monday", $time); } elseif ($week != 1) { $time = strtotime("last Monday", $time); } $weekNumber--; $retData = date("Y-m-d", strtotime("+{$weekNumber} Week", $time)); if ($startDate > $retData) { $retData = $startDate; } return $retData; } }実際の取得サンプルは下記のようになります。
$authKey
に1.で取得したJSONファイルを指定します。
$viewId
に4.でメモしたビューIDを指定します。gasample.php<?php /* Google Analytics API設定 */ $authKey = 'xxxxxx-9999999-xxxxxxxxxxxx.json'; $viewId = '99999999'; /* 入力パラメータ */ if (isset($_REQUEST['startDate'])) { $startDate = $_REQUEST['startDate']; } else { $startDate = date("Y-m-d", strtotime("-1 Month")); } if (isset($_REQUEST['endDate'])) { $endDate = $_REQUEST['endDate']; } else { $endDate = date("Y-m-d", strtotime("-1 day")); } if (isset($_REQUEST['dateTerm'])) { $dateTerm = $_REQUEST['dateTerm']; } else { $dateTerm = 'date'; } /* データ取得準備 */ require_once 'GAwrapper.php'; $analytics = new GAwrapper($authKey, $viewId); $metrics = array(); $dimensions = array(); $sort = array(); $filters = array(); $maxResults = 1000; /* ユーザー数、セッション数、PV数を取得する */ $metrics = array('users', 'sessions', 'pageviews'); $dimensions = array($dateTerm); $sort = array($dateTerm); $data = $analytics->query($startDate, $endDate, $metrics, $dimensions, $sort, $filters, $maxResults); print_r($data);※他のメトリックスやディメンションを指定する場合はこちらを参考にしてください。
Dimensions & Metrics Explorer | アナリティクス Reporting API v4
※ラッパーを使用する場合、ラッパーが自動的に付与するので先頭の「ga:」は不要です。参考にしたサイト
・【最新版】GoogleAnalytics API 認証設定について画像多めで説明します。 | 東京上野のWeb制作会社LIG
おわりに
プログラムを作成した時点からしばらく間が空いてしまったため、一応現在も動作しているプログラムの一部を抜粋する形で記事を起こしましたが、古い書き方の箇所があるかもしれません。
Googleさんの画面やAPIはすぐに変わってしまいがち。。。
- 投稿日:2019-06-25T10:19:41+09:00
自動メール送信機能の実装
ECサイトの作成において、商品の購入が確定したときに確認メールを自動で送信する機能を実装したので、その方法についてメモを残しておきます。
作りたいもの
- 購入確定画面
- 確定と同時に購入者のメールアドレスにメールを自動送信
- メールには購入者氏名、配送先住所、購入した商品の種類と個数、合計金額を記載
メールを送信する関数
メールを送信するには
mb_send_mail()
関数を使用します。引数は4つで
mb_send_mail(受信者のメールアドレス,件名,本文,送信者のメールアドレス)
のような形で使用します。XAMPPでメールを送信する設定
上記の関数をXAMPP環境で使用しても
mb_send_mail(): Failed to connect to mailserver at "localhost" port 25
というエラーが出ると思います。
XAMPPでメールを送信するには設定が必要なのでそちらも説明します。
まず、xampp/phpにあるphp.ini
を編集します。sendmail_path = "\"C:\xampp\sendmail\sendmail.exe\" -t"と記載されている箇所を
sendmail_path = "\"C:\xampp\sendmail\sendmail.exe\" -t" ;sendmail_path="C:\xampp\mailtodisk\mailtodisk.exe"と変更します。
php.ini
の設定はこれでOKです。
次は、xampp/sendmailに入っているsendmail.ini
を編集します。
まずsmtp_serverの設定をします。smtp_server=smtp.mail.yahoo.co.jpこうすることで、yahooメールで設定できます。
次に、以下のようにポート番号の設定をします。smtp_port=587
auth_username
とauth_password
をyahooメールのユーザ名とパスワードに設定します。auth_username=yourusername auth_password=yourpassword最後に
force_sender
にメールアドレスを入れて完了です。
force_sender=youraccount@yahoo.co.jp
以上の設定をすることで、メールが送れるようになります。
購入確定画面サンプル
<?php session_start(); $name=$_POST['name']; $adress=$_POST['adress']; $total=$_POST['total']; $creditNum=$_POST['creditNum']; $status=1; $count=count($_SESSION['cart']); if(isset($name) && isset($adress) && isset($total) && isset($creditNum) ){ $hostname = "localhost"; //ホスト名 $userid = "iimori"; //データベースユーザ名 $passwd = "A8h3avau"; //接続パスワード $dbname = "ecdatabase"; //データベース名 $con=mysqli_connect($hostname,$userid,$passwd,$dbname); //db接続に必要な情報を変数に入れる // 接続状況をチェックします if (mysqli_connect_errno()) { die("データベースに接続できません:" . mysqli_connect_error() . "\n"); } else { echo "データベースの接続に成功しました。\n"; } $con->set_charset('utf8'); /* プリペアドステートメントを作成します */ if ($stmt = mysqli_prepare($con, "INSERT INTO orders (name, adress, totalprice, creditNum, status) VALUES (?,?,?,?,?)")) { /* マーカにパラメータをバインドします */ mysqli_stmt_bind_param($stmt, "ssssi", $name,$adress,$total,$creditNum,$status); /* クエリを実行します */ mysqli_stmt_execute($stmt); /* 値を取得します */ mysqli_stmt_fetch($stmt); /* ステートメントを閉じます */ mysqli_stmt_close($stmt); } $query = 'SELECT id FROM orders WHERE id=(SELECT MAX(id) FROM orders)'; $result = $con->query($query); // クエリを実行します。 if (!$result) { echo $con->error; exit(); } $row=$result->fetch_array(MYSQLI_ASSOC); for($i=0; $i<$count; $i++){ /* プリペアドステートメントを作成します */ if ($stmt = mysqli_prepare($con, "INSERT INTO order_detail (order_id, productName, boughtQuantity) VALUES (?,?,?)")) { /* マーカにパラメータをバインドします */ mysqli_stmt_bind_param($stmt, "sss", $row['id'],$_POST['productName'][$i],$_SESSION['quantity'][$i]); /* クエリを実行します */ mysqli_stmt_execute($stmt); /* 値を取得します */ mysqli_stmt_fetch($stmt); /* ステートメントを閉じます */ mysqli_stmt_close($stmt); } } // 接続を閉じます mysqli_close($con); } //送信元の設定 $header="From: me@example.com"; // 変数とタイムゾーンを初期化 $auto_reply_subject = null; $auto_reply_text = null; date_default_timezone_set('Asia/Tokyo'); // 件名を設定 $auto_reply_subject = '注文が確定しました'; // 本文を設定 $auto_reply_text = "以下の注文で確定しました。\n\n"; $auto_reply_text .= "氏名:".$name. "\n"; $auto_reply_text .= "配送先:".$adress."\n"; $auto_reply_text .= "お買い上げ商品:"; for($j=0; $j<$count; $j++){ $auto_reply_text .= $_POST['productName'][$j]." × ".$_SESSION['quantity'][$j]."個"."\n"; } $auto_reply_text .= "お買い上げ合計金額:".$total; // メール送信 mb_send_mail( $_POST['email'], $auto_reply_subject, $auto_reply_text, $header); unset($_SESSION['cart']); unset($_SESSION['quantity']); ?> <!DOCTYPE html> <html> <head> <meta http-equiv="Content-Type" content="text/html; charset=utf-8" /> <title>注文完了</title> <link rel="stylesheet" type="text/css" href="stylesheet.css"> </head> <body> <h1>注文完了</h1> <div class="center"> 注文が確定しました。<br> お買い上げありがとうございます!<br> <form action="product_list.php" method="post"> <input type="submit" name="back" value="商品一覧に戻る"> </form> </div> </body> </html>以上が購入確定画面のソースコードになります。
$_SESSION['cart'][]
にはカートに入っている商品の番号、$_SESSION['quantity'][]
にはカートに入っている商品の個数が格納されています。参考にしたサイト
- 投稿日:2019-06-25T00:15:03+09:00
Wordpressで自動投稿システムを作ってみる & functions.phpからWordpressを動かしてみる
はじめに
「投稿した記事を自動的に複製するシステムがほちい」という要望があった。
内容的にはjsで見た目を切り替えるだけのページで偽造してもよかったんだけれど、それだとなんか物足りない。
ので、functions.phpから投稿を管理するシステムを作ってみました。要件定義
・投稿タイプtypehogeで記事を新規作成、内容を入力して投稿ボタンを押すと、その記事と同じタイトル、カスタムフィールド値(3種)を持つ複製記事がtypehoge2に自動で投稿される
実際のコード
あ、本筋とは外れるけど、functions.phpを改修する上で以下のコードはすげー役に立ったので書いとく。
functions.phpvar_dump( $hoge ); exit;PHP使いならご存じ
var_dump()
。
普段のWordpress改修では欠かせない存在だけれども、値をどこにも格納しないのでfunctions.phpのような表示に使われないファイルでは実質使えないのが難点。しかし、直後にexit;
と打っておくと式がvar_dump()
を実行した段階で強制終了するので、変数の中身とかを確認できる。便利だった。……で、本題のコードはこちら。
functions.php// 投稿の自動複製システム function function_copying_posts(){ // 現在動作中の投稿の情報(つまり、新規作成したコピー元……「typehoge」記事の内容)を取得します。 global $post; if($post->post_type == 'typehoge'){ $current_postID = $post->ID; // ACFフィールドに入力された値を取得します。この関数が実行されるタイミングが投稿がデータベースに登録される前なので、$_POSTを用いています。 $hoge_name = $_POST['acf']["field_5d106111f2430"]; $hoge_price = $_POST['acf']["field_5d1060e886e4d"]; $hoge_comment = $_POST['acf']["field_5d8561357b6fa"]; // 自動投稿するときのステータスをここで指定します。 $draft_my_options = array( 'post_title' => get_the_title($current_postID), 'post_content' => '', 'post_status' => 'publish', 'post_type' => 'typehoge2' ); // 新しい記事を自動で投稿しつつ、その記事のidを取得します。この行が実行されるタイミングで自動投稿は完了していることに注意してください。 $newpost_id = wp_insert_post($draft_my_options); if($newpost_id){ // カスタムフィールドに値を挿入してます。 update_post_meta($newpost_id, 'hoge_name2', $hoge_name); update_post_meta($newpost_id, 'hoge_price2', $hoge_price); update_post_meta($newpost_id, 'hoge_comment2', $hoge_comment); } } } add_action( 'publish_typehoge', 'function_copying_posts', 9);解説
コピー元投稿のデータ取得→コピー先投稿を公開→コピー先のカスタムフィールドを上書き……の順番で行っている。
苦労したのはカスタムフィールドに入力した内容を取得する部分。
これはACFに限る話だけれど、どうも記事が投稿されるタイミングよりACFデータがデータベースにアップされるタイミングの方が遅いらしく、get_field()やget_post_meta()だとカスタムフィールドに入力した値を取得できないようだ。
get_field()やget_post_meta()がデータベースからデータを呼び出してくるからだろうか?
入力した内容が消えちまったよクソそのへんの話はこのサイトに載ってたけども、とりあえず俺の場合はしゃーなしということでinputからデータを取り出す方式( $_POST['acf']["field_5d106111f2430"] = フィールドキー )にした。
余談
ちなみに、自動投稿を行う部分だけを抜き出すと以下の通りになるらしい。
$post_value = array(
'post_author' => 1,// 投稿者のID。
'post_title' => 'テストタイトル',// 投稿のタイトル。
'post_content' => 'テスト本文', // 投稿の本文。
'post_category' => array(1,5), // カテゴリーID(配列)。
'tags_input' => array('タグ1′,'タグ2′), // タグの名前(配列)。
'post_status' => 'publish' // 公開ステータス。);
wp_insert_post($post_value);
wp_insert_term()
など、自動で管理画面を制御してくれるコードはほかにもいくつかある。……これ、functionとかadd_actionについて触れた方がよかったのかなあ。
参考資料
http://blog.ale-cole.com/php/wordpress/69/
https://www.advancedcustomfields.com/resources/acf-save_post/
https://teratail.com/questions/107958
https://torounit.com/blog/2013/05/22/1544/
- 投稿日:2019-06-25T00:15:03+09:00
Wordpressで自動投稿システムを作ってみる
はじめに
「投稿した記事を自動的に複製するシステムがほちい」という要望があった。
内容的にはjsで見た目を切り替えるだけのページで偽造してもよかったんだけれど、それだとなんか物足りない。
ので、functions.phpから投稿を管理するシステムを作ってみました。要件定義
・カスタム投稿タイプtypehogeの記事を新規作成、内容(カスタムフィールド含む)を入力して投稿ボタンを押すと、その記事と同じタイトル、およびカスタムフィールド値(3種)を持つ複製記事が、別のカスタム投稿タイプtypehoge2の記事として投稿される
実際のコード
functions.php// 投稿の自動複製システム function function_copying_posts(){ // 現在動作中の投稿の情報(つまり、新規作成したコピー元……「typehoge」記事の内容)を取得します。 global $post; if($post->post_type == 'typehoge'){ $current_postID = $post->ID; // ACFフィールドに入力された値を取得します。この関数が実行されるタイミングが投稿がデータベースに登録される前なので、$_POSTを用いています。 $hoge_name = $_POST['acf']["field_5d106111f2430"]; $hoge_price = $_POST['acf']["field_5d1060e886e4d"]; $hoge_comment = $_POST['acf']["field_5d8561357b6fa"]; // 自動投稿するときのステータスをここで指定します。 $draft_my_options = array( 'post_title' => get_the_title($current_postID), 'post_content' => '', 'post_status' => 'publish', 'post_type' => 'typehoge2' ); // 新しい記事を投稿しつつ、その記事のidを取得します。この行が実行されるタイミングで投稿そのものは完了していることに注意してください。 $newpost_id = wp_insert_post($draft_my_options); if($newpost_id){ // カスタムフィールドに値を挿入してます。 update_post_meta($newpost_id, 'hoge_name2', $hoge_name); update_post_meta($newpost_id, 'hoge_price2', $hoge_price); update_post_meta($newpost_id, 'hoge_comment2', $hoge_comment); } } } add_action( 'publish_typehoge', 'function_copying_posts', 9);解説
コピー元投稿のデータ取得→コピー先投稿を公開→コピー先のカスタムフィールドを上書き……の順番で行っている。
苦労したのはカスタムフィールドに入力した内容を取得する部分。
これはACFに限る話だけれど、どうも記事が投稿されるタイミングよりACFデータがデータベースにアップされるタイミングの方が遅いらしく、get_field()やget_post_meta()だとカスタムフィールドに入力した値を取得できないようだ。
get_field()やget_post_meta()がデータベースからデータを呼び出してくるからだろうか?
入力した内容が消えちまったよクソそのへんの話はこのサイトに載ってたけども、とりあえず俺の場合はしゃーなしということでinputからデータを取り出す方式にした。
functions.php$_POST['acf']["field_5d106111f2430"]なお、このinputから取り出すコマンド、「field_5d106111f2430」部分を取得したい入力欄にあるフィールドキーに書き換えれば問題なく使えます。
余談
functions.phpを改修する上で以下のコードはすげー役に立ったので書いとく。
functions.phpvar_dump( $hoge ); exit;PHP使いならご存じ
var_dump()
。
普段のWordpress改修では欠かせない存在だけれども、functions.phpのような、表示に使われないphpファイルでは実質使えないのが難点だった。
が、直後にexit;
と打っておくと式がvar_dump()
を実行した段階で強制終了するので、変数の中身とかを確認できる。
広まれ。あと、自動投稿を行う部分だけを抜き出すと以下の通りになるらしい。
functions.php$post_value = array( 'post_author' => 1,// 投稿者のID。 'post_title' => 'テストタイトル',// 投稿のタイトル。 'post_content' => 'テスト本文', // 投稿の本文。 'post_category' => array(1,5), // カテゴリーID(配列)。 'tags_input' => array('タグ1′,'タグ2′), // タグの名前(配列)。 'post_status' => 'publish' // 公開ステータス。 ); wp_insert_post($post_value);
wp_insert_term()
など、自動で管理画面を制御してくれるコードはほかにもいくつかあるみたい。参考資料
http://blog.ale-cole.com/php/wordpress/69/
https://www.advancedcustomfields.com/resources/acf-save_post/
https://teratail.com/questions/107958
https://torounit.com/blog/2013/05/22/1544/