×
Copy
Open
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
Slide 1
Slide 1 text
/ / PHP カンファレンス沖縄 2019 めもりー PHPer のための PHPUnit と Selenium を使った ブラウザテストのすゝめ © - BASE, Inc.
Slide 2
Slide 2 text
© - BASE, Inc. Who am I? めもりー (@m m r ) BASE 株式会社の基盤チームに所属している エンジニアです。 PHP, TypeScript あたりをメインに触ってい ます。 趣味はバイナリファイルを読むことです
Slide 3
Slide 3 text
© - BASE, Inc. 登壇実績 • PHP で JVM を実装して Hello World を出⼒するまで • builderscon tokyo • https://speakerdeck.com/memory /php-de-jvm-woshi-zhuang-site- hello-world-wochu-li-surumade • (前職) PHP で JVM (Java Virtual Machine) に⼊⾨する • PHPerKaigi • https://speakerdeck.com/memory /phperkaigi- • (前職) 開発期間 2 ヶ⽉で Elasticsearch をプロダクトに使って リリースした話 • PHP カンファレンス仙台 2019 • https://speakerdeck.com/memory /php-conference-sendai- - presentation-slides
Slide 4
Slide 4 text
© - BASE, Inc. みなさんテスト書いてますか?
Slide 5
Slide 5 text
© - BASE, Inc. 歴史のあるサービスのテスト書くの ⾟くないですか?
Slide 6
Slide 6 text
© - BASE, Inc. でも、⼤丈夫です
Slide 7
Slide 7 text
© - BASE, Inc. そう、PHPUnit と Selenium を 使えばね
Slide 8
Slide 8 text
© - BASE, Inc. 本⽇のお品書き
Slide 9
Slide 9 text
© - BASE, Inc. 本⽇のお品書き 課題の解決⽅法 我々の抱えている課題 Selenium を導⼊するには?
Slide 10
Slide 10 text
© - BASE, Inc. 本⽇のお品書き どうテストを書いていくか Selenium を使うことによって得られる恩恵 実際に Selenium を導⼊して運⽤した話
Slide 11
Slide 11 text
© - BASE, Inc. 我々の抱えている課題
Slide 12
Slide 12 text
© - BASE, Inc. 我々の抱えている課題 • JavaScript でレンダリングされるようなフォー ムのテストが⾟い • フロントエンドとバックエンドが密結合なた め、テストが書けない、QA が⾟い • 1 つ実装したら 2 つバグがでる
Slide 13
Slide 13 text
© - BASE, Inc. 課題の解決⽅法
Slide 14
Slide 14 text
© - BASE, Inc. 課題の解決⽅法 • フロントエンドとバックエンドは疎結合にして 対象の関⼼事を減らした上でテストを書くのが 望ましい • とはいえ、いきなりそのテストが書けるかとい うと NO に近い
Slide 15
Slide 15 text
© - BASE, Inc. 課題の解決⽅法 • 段階を踏んで、リファクタリングやリプレイス などを⾏っていく • Selenium を使うことにより、密結合になって いるサービスを分離したり、テストのリファク タリングなどが⾏えるようになる • さらに E E ⽤のテストツールとしても担える
Slide 16
Slide 16 text
© - BASE, Inc. Selenium を導⼊するには?
Slide 17
Slide 17 text
© - BASE, Inc. そもそも Selenium とは?
Slide 18
Slide 18 text
© - BASE, Inc. Selenium とは? • Web アプリケーションのテストツールのこと • テストツールではあるが、ブラウザにレンダリ ングされている画⾯のスクリーンショットを 撮ったりもできる • PHP で使⽤するには Facebook 社が公開してい る facebook/webdriver を⽤いる GitHub: https://github.com/facebook/php-webdriver
Slide 19
Slide 19 text
© - BASE, Inc. Selenium で出来ること
Slide 20
Slide 20 text
© - BASE, Inc. Selenium で出来ること • フォーム⼊⼒の⾃動化 • ページ遷移後のテスト • 各ブラウザ (IE, Firefox, Chrome など)でのレ ンダリング結果の確認 • JavaScript の実⾏
Slide 21
Slide 21 text
© - BASE, Inc. などなど… 上げたらキリがない
Slide 22
Slide 22 text
© - BASE, Inc. Selenium を使うことによって 得られる恩恵
Slide 23
Slide 23 text
© - BASE, Inc. Selenium を使うことによって得られる恩恵 • JavaScript で⽣成されるような DOM でもテス トできる • フロントエンドとバックエンドが密結合であっ てもテスト可能である • インテグレーションテストからリグレッション テストの⾃動化が出来る
Slide 24
Slide 24 text
© - BASE, Inc. Selenium を使うことによって得られる恩恵 • 各ブラウザでの表⽰崩れなどをスクリーン ショットを⽐較することにより検知できる • ただし、 reCAPTCHA のような画像認証は難し いので、⼯夫が必要 • Standalone の Node 版の特定のバージョンだ とブラウザが起動できないバグがあるので Java 版を使うのが無難
Slide 25
Slide 25 text
© - BASE, Inc. どういう仕組み?
Slide 26
Slide 26 text
© - BASE, Inc. PHPUnit PHP Container Selenium Standalone Selenium Container Chrome Facebook WebDriver どういう仕組み? Web Page ( ) Hub につないだり、JSの 実⾏や要素の探索などをする (2) セッションを作成する (3) 現在のレンダリングの 状態を取得 (4) セッションの情報を返す ( ) PHPUnit 側に 実⾏結果を返す (5) 実⾏結果を返す
Slide 27
Slide 27 text
© - BASE, Inc. どうテストを書いていくか
Slide 28
Slide 28 text
© - BASE, Inc. Selenium の導⼊
Slide 29
Slide 29 text
© - BASE, Inc. Selenium の導⼊ • Chrome の Standalone 版の Selenium を使⽤ する ※今回は Headless は使わない • Docker で導⼊するととても楽なので Docker を使⽤する
Slide 30
Slide 30 text
© - BASE, Inc. 今回使うサンプル
Slide 31
Slide 31 text
© - BASE, Inc. 今回使うサンプル • 今回使うサンプルは下記の通り
Slide 32
Slide 32 text
© - BASE, Inc. サンプルコードはこちら https://github.com/memory-agape/php-conference- webdriver-testing
Slide 33
Slide 33 text
© - BASE, Inc. PHPUnit にテストを書いていく
Slide 34
Slide 34 text
© - BASE, Inc. はじめかた
Slide 35
Slide 35 text
© - BASE, Inc. たったこれだけ
Slide 36
Slide 36 text
© - BASE, Inc. composer require facebook/php-webdriver GitHub: https://github.com/facebook/php-webdriver ※ Docker ্Ͱಈ͔͞ͳ͍߹ɺ Selenium ͷ Standalone ͕ผ్ඞཁͰ͢ɻ
Slide 37
Slide 37 text
© - BASE, Inc. WebDriver の準備
Slide 38
Slide 38 text
© - BASE, Inc. WebDriver の準備
Slide 39
Slide 39 text
© - BASE, Inc. WebDriver の準備 Selenium の Hub を指定
Slide 40
Slide 40 text
© - BASE, Inc. WebDriver の準備 Chrome のバイナリまでの絶対パスを指定する
Slide 41
Slide 41 text
© - BASE, Inc. WebDriver の準備 ローカルだとSSL の認証の問題があるため エラーを無視するようにする
Slide 42
Slide 42 text
© - BASE, Inc. WebDriver の準備 リンク先の⽣存判定をしないようにする
Slide 43
Slide 43 text
© - BASE, Inc. WebDriver の準備 Selenium から実⾏する JavaScript の挙動が安定しない場合は サンドボックスを無効にする
Slide 44
Slide 44 text
© - BASE, Inc. テスト対象のページをつくる
Slide 45
Slide 45 text
© - BASE, Inc. テスト対象のページをつくる • JavaScript でフォーム内に DOM を追加するよ うなよくあるページにする • 該当のフォームの値が送られて来ていない場 合、エラーを表⽰するようにする
Slide 46
Slide 46 text
© - BASE, Inc. テスト対象のページをつくる
Slide 47
Slide 47 text
© - BASE, Inc. テスト対象のページをつくる 送られていなければ 「added_by_js が送られてきていません」と 表⽰をする。 added_by_js というパラメータが送られてきていれば 「⼊⼒されたメッセージ」+「が送られてきました」 と表⽰する
Slide 48
Slide 48 text
© - BASE, Inc. テスト対象のページをつくる added_by_js という名前がある input を JavaScript で 動的にフォームへ追加する
Slide 49
Slide 49 text
© - BASE, Inc. 実際にテストを書いていく
Slide 50
Slide 50 text
© - BASE, Inc. 実際にテストを書いていく • 2 パターンのテストを書く • added_by_js という名前のパラメータが送ら れてきた場合 • 該当のパラメータが送られてきていない場合
Slide 51
Slide 51 text
© - BASE, Inc. パラメータが正常に送られてきた場合
Slide 52
Slide 52 text
© - BASE, Inc. パラメータが正常に送られてきた場合
Slide 53
Slide 53 text
© - BASE, Inc. パラメータが正常に送られてきた場合 ページに接続する
Slide 54
Slide 54 text
© - BASE, Inc. パラメータが正常に送られてきた場合 DOM がレンダリングされるのを待つ
Slide 55
Slide 55 text
© - BASE, Inc. パラメータが正常に送られてきた場合 input の要素を探す
Slide 56
Slide 56 text
© - BASE, Inc. パラメータが正常に送られてきた場合 Hello World! という⽂字列を⼊⼒する
Slide 57
Slide 57 text
© - BASE, Inc. パラメータが正常に送られてきた場合 Submit ボタンを探す
Slide 58
Slide 58 text
© - BASE, Inc. パラメータが正常に送られてきた場合 Submit ボタンをクリック (onSubmit を発⽕)させる
Slide 59
Slide 59 text
© - BASE, Inc. パラメータが正常に送られてきた場合 ページが切り替わるのを待つ
Slide 60
Slide 60 text
© - BASE, Inc. パラメータが正常に送られてきた場合 表⽰されるメッセージの要素を探す
Slide 61
Slide 61 text
© - BASE, Inc. パラメータが正常に送られてきた場合 表⽰されている⽂字列が正しいかどうかをテストする
Slide 62
Slide 62 text
© - BASE, Inc. パラメータが送られてきていない場合
Slide 63
Slide 63 text
© - BASE, Inc. パラメータが送られてきていない場合
Slide 64
Slide 64 text
© - BASE, Inc. パラメータが送られてきていない場合 ページに接続する
Slide 65
Slide 65 text
© - BASE, Inc. パラメータが送られてきていない場合 DOM がレンダリングされるのを待つ
Slide 66
Slide 66 text
© - BASE, Inc. パラメータが送られてきていない場合 JavaScript で動的に追加された input を消す
Slide 67
Slide 67 text
© - BASE, Inc. パラメータが送られてきていない場合 Submit ボタンを探す
Slide 68
Slide 68 text
© - BASE, Inc. パラメータが送られてきていない場合 Submit ボタンをクリック (onSubmit を発⽕)させる
Slide 69
Slide 69 text
© - BASE, Inc. パラメータが送られてきていない場合 ページが切り替わるのを待つ
Slide 70
Slide 70 text
© - BASE, Inc. パラメータが送られてきていない場合 表⽰されている⽂字列が正しいかどうかをテストする
Slide 71
Slide 71 text
© - BASE, Inc. うまくいくと…
Slide 72
Slide 72 text
© - BASE, Inc.
Slide 73
Slide 73 text
© - BASE, Inc. テストが通って、 Selenium が 正常に動いていることがわかります。
Slide 74
Slide 74 text
© - BASE, Inc. エラーのあるページの チェックをする
Slide 75
Slide 75 text
© - BASE, Inc.
Slide 76
Slide 76 text
© - BASE, Inc. エラーのあるページをチェックする • 404 や 500 のあるページを Selenium で検出す る • このチェックを⾏うことでリンク切れの検出 が可能になります • 他にも PHP のバージョンアップなどで動かな いページの検出などの⽤途などにも活⽤でき ます
Slide 77
Slide 77 text
© - BASE, Inc. エラーのあるページをチェックする • Selenium 単体ではステータスコードのチェッ クができないっぽい • そのため、 cURL や Guzzle などステータス コードが取れるアプローチを取る
Slide 78
Slide 78 text
© - BASE, Inc. エラーのあるページをチェックする
Slide 79
Slide 79 text
© - BASE, Inc. エラーのあるページをチェックする ページに接続する
Slide 80
Slide 80 text
© - BASE, Inc. エラーのあるページをチェックする アンカーリンクを取得する
Slide 81
Slide 81 text
© - BASE, Inc. エラーのあるページをチェックする Guzzle の準備をする
Slide 82
Slide 82 text
© - BASE, Inc. エラーのあるページをチェックする それぞれのアンカーリンクを処理する
Slide 83
Slide 83 text
© - BASE, Inc. エラーのあるページをチェックする アンカーリンクの href 属性を取得する
Slide 84
Slide 84 text
© - BASE, Inc. エラーのあるページをチェックする Guzzle で該当の URL にアクセスしてステータスコードを取得する
Slide 85
Slide 85 text
© - BASE, Inc. エラーのあるページをチェックする ステータスコードが 400 以上の場合は該当のURLを 含めたエラーメッセージを表⽰する
Slide 86
Slide 86 text
© - BASE, Inc. 実際に Selenium を導⼊して 運⽤した話
Slide 87
Slide 87 text
© - BASE, Inc. どういったケースで導⼊したのか?
Slide 88
Slide 88 text
© - BASE, Inc. (注)BASE の話ではありません
Slide 89
Slide 89 text
© - BASE, Inc. どういったケースで導⼊したのか? • 1 つ実装すると 2 つバグがでる状態だった。 • フレームワークを使っているはずなのに、⼀部 の機能がなぜか、フレームワーク外の common.php 書かれていた。 • しかもその common.php はすべてのファイル に require されていた • テスト⾃体存在してない
Slide 90
Slide 90 text
© - BASE, Inc. どういったケースで導⼊したのか?
Slide 91
Slide 91 text
© - BASE, Inc. どういったケースで導⼊したのか? • common.php の何を使っていて何を使ってい ないのか本当に分からない。 • スタートアップだったため QA なんて仕組みは 1 ミリもなかった PHPUnit + Selenium を導⼊して該当箇所の テストを⾃動化して、リファクタリングを⾏う
Slide 92
Slide 92 text
© - BASE, Inc. テストが担保できたため、 ほぼバグが発⽣することはなくなった
Slide 93
Slide 93 text
© - BASE, Inc. &&
Slide 94
Slide 94 text
© - BASE, Inc. 謎の common.php から 完全ではないが分離していけた
Slide 95
Slide 95 text
© - BASE, Inc. DEMO
Slide 96
Slide 96 text
© - BASE, Inc. まとめ
Slide 97
Slide 97 text
© - BASE, Inc. まとめ • Selenium は PHP でも動かせるし、PHPUnit と⼀緒に使うことができる • テストが書きづらい状態でも Selenium を使え ば、ある程度は担保することができるようにな る • QA が難しい環境でも Selenium である程度担 保できる
Slide 98
Slide 98 text
© - BASE, Inc. Selenium はいいぞ
Slide 99
Slide 99 text
© - BASE, Inc. 以上です
Slide 100
Slide 100 text
© - BASE, Inc. THANK YOU FOR YOUR LISTENING