JavaScript Google Maps API 〜Map表示の(実装)方法〜

イントロダクション

前回はGoogleMapのAPIを使用する準備を行いました。
早い話が、APIのキーを取得しました。
取得した後に、ちょいと順序が違ってきてしまったので改めて、実装について触れようと思った次第です。

Google Maps JavaScript API

Googleから提供されているAPIドキュメントを見てみると、実装のサンプルがそのまま乗っています。
なので今まで深く触れていませんでした、が!どんな処理なのか今一度見てみようと思います。
上記のリンクより、こちらのリンクはJSFidleというものでHTML, CSS, JSが見れる優れものでした。

そして、上記のリンク先のコード配下になります。(コピペ)

      var map;
function initMap() {
    // Mapの生成処理(HTMLのDIVタグのid="map")
    map = new google.maps.Map(document.getElementById('map'), {
      center: {lat: -34.397, lng: 150.644},
      zoom: 8
    });
}

コードの内容

DIVタグにMapを埋め込みます。そのために使用するコードは下の部分です。

new google.maps.Map(DOMエレメント)

この処理で、DOMエレメント=DIVタグにマップを埋め込みます。(作成します)
そして、第二引数のJSONデータの部分について、これは見ればわかる人はわかるでしょう。(自分はこのようなのを見て理解するのに時間がかかったクチです(笑))

{ center: {lat: -34.397, lng: 150.644}, zoom: 8}

これをつなげると、上のようなコードになります。ちなみに開業しているのでぱっと見が違います。(見やすい)

map = new google.maps.Map(document.getElementById('map'), {
      center: {lat: -34.397, lng: 150.644},
      zoom: 8
    });

このコードで、マップの作成ができたら次は。。。

Marker追加

マーカーの追加をやりたいと思うのが人情。。。(自分だではないと思います。)
そして、マーカーの追加は下のようにやるようです。上記のリンクよりコピペです。

// Initialize and add the map
function initMap() {
  // The location of Uluru
  var uluru = {lat: -25.344, lng: 131.036};
  // The map, centered at Uluru
  var map = new google.maps.Map(
      document.getElementById('map'), {zoom: 4, center: uluru});
  // The marker, positioned at Uluru
  var marker = new google.maps.Marker({position: uluru, map: map});
}

// The marker, positioned at Uluruの部分から下がマーカー追加処理になります。
1行で終わるのでとてもわかりやすいと思います。Map作成時と同じような形なのでここの説明は割愛します。

InfoWindow追加

そして、マーカーの次は情報ウィンドウが表示したい。。。
これもリンク先にサンプルコードからしてあります。
同様にコピペしました。

// This example displays a marker at the center of Australia.
// When the user clicks the marker, an info window opens.

function initMap() {
  var uluru = {lat: -25.363, lng: 131.044};
  var map = new google.maps.Map(document.getElementById('map'), {
    zoom: 4,
    center: uluru
  });

  var contentString = '<div id="content" >'+
      '<div id="siteNotice"  >'+
      '</div >'+
      '<h1 id="firstHeading" class="firstHeading"    >Uluru</h1    >'+
      '<div id="bodyContent">'+
      '<p><b>Uluru</b>, also referred to as <b>Ayers Rock</b>, is a large ' +
      'sandstone rock formation in the southern part of the '+
      'Northern Territory, central Australia. It lies 335 km (208 mi) '+
      'south west of the nearest large town, Alice Springs; 450 km '+
      '(280 mi) by road. Kata Tjuta and Uluru are the two major '+
      'features of the Uluru - Kata Tjuta National Park. Uluru is '+
      'sacred to the Pitjantjatjara and Yankunytjatjara, the '+
      'Aboriginal people of the area. It has many springs, waterholes, '+
      'rock caves and ancient paintings. Uluru is listed as a World '+
      'Heritage Site.</p>'+
      '<p>Attribution: Uluru, <a href="https://en.wikipedia.org/w/index.php?title=Uluru&oldid=297882194">'+
      'https://en.wikipedia.org/w/index.php?title=Uluru</a> '+
      '(last visited June 22, 2009).</p>'+
      '</div>'+
      '</div>';

  var infowindow = new google.maps.InfoWindow({
    content: contentString
  });

  var marker = new google.maps.Marker({
    position: uluru,
    map: map,
    title: 'Uluru (Ayers Rock)'
  });
  marker.addListener('click', function() {
    infowindow.open(map, marker);
  });
}

このコードは以下の手順で処理を行っています。

  1. ウルル(地球のへそ)の位置(座標)をJSONで作成
  2. マップを作成
  3. HTMLコンテンツを作成
  4. 情報ウィンドウの生成
  5. マーカーの作成と情報ウィンドウの追加

こんな処理を行っています。
表示結果はリンク先にありますのでそちらを確認していただきたく思います。ぱっと見だけであれば、下にキャプチャを貼っておきます。

この画面はこちらに本物のサンプルがあります。

こんな感じです。

でわでわ。。。



JavaScriptでユーザー認証 〜シンプルな認証処理〜

イントロダクション

最近作成している、GoogleMapを使用したページがある程度見れるものになってきたので、そろそろと公開できるような形にしたいと思い、ちょいとギミックを追加します。

パスワード認証

皆さんご存知「パスワード認証」を実装します。
これを実装すれば、「<入力>」「<送信>」などのボタン押下で、不特定多数の人に地図データを登録される心配がなくなります。

パスワード認証の実装

シンプルにボタンをクリックしたらパスワード入力ダイアログボックスが表示され、入力→認証という流れで処理を行います。
パスワードは見つけられないように、サーバーサイド(PHP)で持つことにします。つまり実装としては下のような感じになります。

認証準備

まずは、入力とデータの送信が出来ないようにボタンを非表示にします。
これはシンプルにHTMLでstyle="display: none"を設定してやります。具体的には以下のようなHTMLコードに変更します。
<Before>

        <button class="butt1" onclick="sideWinHandle(sideWin)"><入力>   </button>
        <button class="butt2" onclick="postData()"><送信>  </button>

<After>

        <button name="loggedIn" class="butt1" onclick="sideWinHandle(sideWin)" style="display: none;"><入力></button>
        <button name="loggedIn" class="butt2" onclick="postData()" style="display: none;"><送信></button>
        <button onclick="openLoginForm()"><Login> </button>

そして、ボタン押下時に走らせる処理onclick="openLoginForm()"を設定します。
これが出来たら、あとはJSの実装のみです。

ズバリ下のような実装を追加します。ちょっと特殊なのはprompt()です。

function openLoginForm() {
var input = prompt("Login Form");
    if ('パスワード' === input) {
        var loggedInButton = document.getElementsByName("loggedIn");
        loggedInButton.forEach(but => {
            but.style = "display: visible";
        });
    }
}

これで下のように動きます。

  1. 「Login」ボタンを押下
  2. プロンプトが開き、入力を求める
  3. 入力した値がJSのinput変数に代入される(上のコード参照)

シンプルに実装できていると思います。

問題が1つ

この実装だと、パスワードがバレバレで、セキュリティ的にアウトです。しかし、今回の実装はあくまでサンプルなのでまぁよしとします。

実際の使用方法

実際は入力して判定するときにクライアント側ではなく、サーバー側(PHPなど)で判定を行います。
今の自分の実装だと、入力した値をサーバーに送信(Ajax通信)して判定結果をもとに画面の表示・非表示を切り替えるなどを行うのが、安全なやり方だと思います。

ぢつは。。。

今の実装をしていて気がつきました。「ハナっからこーすればいいよな?」と思っております。初めの初期表示時に処理を行うことに執着していて気がつかなかった次第です。



PHP Image File 〜iPhoneやAndroidでの画像送受信の問題〜

イントロダクション

GoogleMapを使用して見つけた場所(店など)をGoogleMapに登録するブラウザアプリケーションを作成中です。
途中まで作成していて携帯からアップロードした写真のデータが表示できない事象に遭遇しました。

スマホの写真(拡張子)

iPhoneではHEICを使用していました。Androidも同じものを使用している記事を見かけましたが、確認はしていません。
とりあえずのところは、画像を編集するのに提供されているコンバーターを使用する必要があり、既存のプログラムにも手を入れる必要があるということがわかりました。

既存プログラム

作成したプログラムのことですが、Ajax+PHPでの実装を行なっており、詳細に関してはこちらに記載しております。

問題

問題になっていることは、画像を送受信して表示できるものとできないものがあるということです。送受信するのはbase64でのデータをサーバーから送信しクライアントサイドでそれを表示しています。がスマホからサーバーに送信、DBに(BLOBで)登録したものは画面に表示できない事象にあってしまいました。テクノロジー的にも上記のようなファイルコンバートが必要になるようです。

結局

無理をして画像を表示する必要もないと判断しました。
ブラウザーからの入力はテキストのみにして、Youtubeの動画を表示するようにしました。
画面より、Youtubeの画像IDを入力しGoogleMapのinfoWindowに表示する方法をとりました。
とりあえずは、問題もなく動いているのでこの方法でサイトの方を作成していく予定です。

でわでわ。。。

関連ページ

  1. JS GoogleMaps API 〜オリジナル・データマップを作ろう〜
  2. 吹き出しにYoubetubeを埋め込む
  3. Ajax + XmlHttpRequest〜画像送信からDB登録して表示〜
  4. JS XmlHttpRequest 〜JSでの同期/非同期通信〜
  5. JS Google Maps API 〜GeoLocation 現在位置の取得〜
  6. AngularJS + PHP 〜AngularJSの実装〜
  7. AngularJS + PHP 〜AngularJSの実装2〜



Google Maps API 〜吹き出しにYoutubeを埋め込む〜

``### イントロダクション
ようやく、休みになったのでJSでのGoogle Mapをやります。前は、画像ファイルをアップロードして。。。と考えていましたが、動画の方が良いと判断しました。Thetaも買ったので(笑)

Google Maps + Youtube

色々考えた結果こうなりました、そして早速実装したものの、動画表示できない事件が。。。

ちなみにスマホでは灰色の部分も表示されませんでした。。。

Youtube Player API

調べて見たところ、上のYoutube Player APIで吹き出し部分にYoutubeが埋め込めるようなのです。

余談ですが、こんな方法もいけるようです。が、自分の場合はダメでした。。。
とりあえずはコードを写経して見ます。

しかし、さして変化もなく。。。

やっぱりこれか?

Refused to display 'https://www.youtube.com/watch?v=MwI4m_LLugo&feature=youtu.be' in a frame because it set 'X-Frame-Options' to 'sameorigin'.

このHTMLコードがコンポン的な原因のようです、早い話がYoutubeにアクセスできない状態のため上のHTMLも表示できない。。。という仮説です。
まとめると「iframeでアクセスできるようにすればOK!」というわけです。

戦いの結果

敵将の首を討ち取りました!
原因はiframeに渡しているURLが不適切なツェツなので表示されないということでした。
表示できない時のURL
https://www.youtube.com/watch?v=t-6PiKxDX2E
表示できたURL
https://www.youtube.com/embed/t-6PiKxDX2E
watchembedで違いがあり、iframeに埋め込むのは「embed」の方を使用するべきだったということでした。
でわでわ。。。



Google VR View 〜360°の写真とビデオをHTMLに埋め込む〜

イントロダクション

現在作成中のGoogleMapを使用したブラウザアプリに写真を埋め込むような形で実装しようと考えていましたが、PHPでの実装ではXmlHttpRequestでの通信処理が遅いのと、不具合(写真が時々表示できない)があるのと、深く追求うする気もないのでやめることにしました。
そして、その代替え案として

Google VR View

これ使って動画や、写真をHTMLに埋め込もうと考えたので、調査をすることにしました。

サンプル

ここのページに「こんな感じ」というものがありました。

埋め込む方法

JSを使用して埋め込む方法がありました。使用するJSファイルは「vrview.min.js」のようです。

<script> src="https://storage.googleapis.com/vrview/2.0/build/vrview.min.js"></script>

そして、360度のイメージファイルは圧縮率などを考慮に入れると「JPEG」がオススメのようです。
圧縮を改善するためにjpegを使用することをお勧めします。

メディアの配置

上のようにJSでファイルを読み込むような形でHTMLに埋め込むのでJPEGなどのファイルを適当な場所に配置する必要があります。
そして、既存の問題もあるようです。PHPでの画像表示がうまくいかない原因もここにありそうです。

Web上の既知の問題
(JavaScript APIを使用せずに)iframeを明示的に宣言し、コードと画像が異なるサーバでホストされている場合、iOS Safariでは360度画像の方向が正しくありません。

メディアとVR Viewコードが異なるサーバーでホストされている場合、360°ビデオはOSX Safariでは機能しません。

2のべき乗でない正方形の画像は、ChromeおよびSafari iOS 8では正しく表示されない場合があります。

まとめ

意図しないところで、PHP画像アップロード問題の原因がわかったものの解決に至らずですが、とりあえずはWebアプリに関して

  1. 画像でなくURLを渡すような形で表示する
  2. URL形式でHTMLに出力してJSでコントロールする

このような形で実装すると良いという発見がありました。
そして、360°の写真とビデオはこれも URLで参照先(画像などの配置場所)を指定する形でHTMLに出力するので問題なくいけそうだということがわかりました。

でわでわ。。。



Ajax + XmlHttpRequest〜画像送信からDB登録して表示〜

イントロダクション

今まで数回にわたり、これに関することを記載しました。以下の記事がそれにあたります。

  1. JS XmlHttpRequest 〜JSでの同期/非同期通信〜
  2. Google Maps API PHP連携 〜マップ情報をDBに登録する〜
  3. PHP Ajax 〜DBに登録したデータを受信する〜

部分的な記載なので詳細部分は上記の記事がわかりやすいと思います。

Ajax + XmlHttpRequest

今回作成しているウェブアプリケーションはGoogle Mapを使用して地域の情報を位置情報を土台にして発信できるものを作成中です。
現状は、まだわけのわからない情報が載っています。こんな感じです(笑)。

PCとスマホなどのモバイルで同じような表示になっています。CSSでのコントロールは行なっていません。→@mediaなどのタグを使用していません。

なぜAjax?

今回の実装では使用しているファイルは以下のようになります。
<クライアント>

  • SampleMap.html
  • SampleMap.js
    <サーバー>
  • InsertMapData.php(だったと思う。。。)
  • GetMapData.php(と思う。。。)

これらの構成で今後はphpファイルが増えていくような形になります。(1機能、1ファイル)

ポイント

HTML, JS(クライアント)とphp(サーバー)を分断して実装したいと思い、このような形になりました。
サーバーとクライアントの通信部分にはAjaxを使用しています。

つまり

「HTML & JS」

  • HTMLの初期表示時にAjaxでphpを呼び出しGoogleMapから地域情報(オーバーレイ)を取得

「PHP(サーバー)」

  • データ入力とデータ送信のボタンで地域情報をサーバーに登録(PHP呼び出し)を行う

このように用途を分割して実装しました。

MVCモデル

余談ですが、自分はJava屋なのでMVCモデルのような実装の仕方が好きです。「あの機能はあのファイル」「この機能はこのファイル」というように処理を分割してやると、修正や追加の実装をするときに「どの部分にコードをついか・修正すれば良いか?」がすぐにわかります。「自分で作ったんならわかるだろ?」という声が聞こえそうですが、それは多分やったことのない人の意見だと思います。
もし、若い人であれば、是非やってみてください多分「んーどこを修正すれば良いのだろう?」となります。そして、この経験をした人でないと「こーやれば良い」というのがわからないと思います。
それなりに経験を積んでいる人であれば、若い子がやって「んー。。。」と声を上げているときに、何か一言声をかけてあげてください。若くても、老人でも「新しきを知る」というのは必要だし。面白いことだと思います。

処理フロー

本当のMVCモデルでは以下のような関係を作りアプリケーションの設計を行います。

  1. モデル(M) = ロジック処理部分(DB登録など)
  2. ビュー(V) = 画面、クライアント側
  3. コントロール(C) = リクエストハンドラ

このような形で設計します。JavaのSpring, Play(リンクはちょっと古い)、JavaEE etc ... などのフレームワークはStrutsという古いフレームワークを基本にしているように見えます。(実際のところは自分の予想です)
それというのはリクエストハンドルを行う中心的なサーブレット(フレームワーク部品)を使用して各URLに対してどのアクション(Control)を起動するのか決定しているからです。

ハンドリング方法

「http(s)://XXXX.com/XXX 」というリクエストが来たときXXXActionというControlクラスのXXXメソッドが起動する、というような形をとっています。

MVCの流れ

画面(V) → コントロール(C) → モデル(M)→ コントロール(C) → 画面(V)と流れていくように設計します。
VからはHTMLでフォームのaction属性を使用する方法、Ajaxで直接処理を呼び出す方法とありますが、そこはアプリケーションの設計次第になります。

同期通信と非同期通信

Ajaxという技術が確立されて久しいですが、昔は「同期通信」、つまり、フォームのaction属性を使用する同期通信にて画面の更新を行なっていました。この場合は画面全体をリロードするので必要な場合のみこのような通信方法を使用したいと思うのが人情だと思います。
しかしAjaxの技術を使用すれば更新したい部分のみを更新できるので、この方法を使用することが多いです。
よく目にするのは「JQuery」を使用した「$.ajax()」です。これはXmlHttpRequestを使用したもので、自分の認識としては単なるラッパー(拡張して使いやすくしたもの)だと思っています。しかし便利になればその分よくない部分も出るので。。。まぁ好みの問題でもありますが。。。とにかく自分はシンプルにXmlHttpRequestを使用した実装を行いました。
具体的には、HTMLでid="jax"とつけた領域のみを更新するなどです。中身としては「非同期通信はレスポンスを待たない」のでリクエストを送信してこのレスポンスが帰って来たときにXXXの処理をするというような形で実装するので「部分的に画面を更新できる」というわけです。
この部分は下の記事を参照願います。
JS XmlHttpRequest 〜JSでの同期/非同期通信〜



今回の実装では

MVCの「C」がない状態です。HTMLとPHPだけで処理を行い、画面の繊維を行わないのでControl部分がいりません。1画面で事を足らします。
というかほとんどをGoogleMapsAPIに依存する形で実装するのでサーバーサイドの処理はDBからのデータの取得、更新のみで良いのです。

MVモデル?

とってつけたようにいろんな言葉が横行していますが、それも時代でしょう。なので「MVモデル」という言葉はテキトーな事を記載しました。。。(冗談)
しかし、実装の方はHTML(V)とDB更新・データ取得(M)のみなのでこのような言い回しになりました。詳細に関しては以下のリンクを参照していただけるとありがたいです。

  1. Google Maps API PHP連携 〜マップ情報をDBに登録する〜
  2. PHP Ajax 〜DBに登録したデータを受信する〜

でわでわ。。。

Google Maps API PHP連携 〜マップ情報をDBに登録する〜

Html -> DB

Google Maps APIを使用して地図を表示する画面の作成を行いました。

こんな感じです。

PHP連携

この画面の下部分にデータを登録するための入力部分があります。ここの入力をサーバー(PHP)へ送信してDBに登録します。
クライアントサイド(HTML)は作成したので次はリクエストを送信したときにデータを受け取りDBに登録する処理(PHP)を作成します。
ちょいメモ
実は画面からリクエストを送信する部分(ボタン)ですがまだ作ってません。。。

PHP作成

参考にするサイトはこちらです。PHPマニュアルです。。。

関連ページ(PHP)

  1. PHP PDO 〜MySQLにアクセスする〜
  2. PHP Ajax 〜DBに登録したデータを受信する〜
  3. Google Maps API PHP連携 〜マップ情報をDBに登録する〜
  4. PHP Image File 〜iPhoneやAndroidでの画像送受信の問題〜
  5. AngularJS Routing 〜PHPをWeb APIにする〜
  6. WordPress PHPカスタム〜根本的に見た目を変える〜
  7. WordPress PHPカスタム〜根本的に見た目を変える2〜
  8. Eclipse PHPプラグイン 〜ElipseでWordPress環境を構築〜
  9. WordPress テスト実装 〜heade-test.phpを表示〜
  10. AngularJS + PHP 〜WordPressと連携する〜
  11. AngularJS + PHP 〜AngularJSの実装〜
  12. AngularJS + PHP 〜AngularJSの実装2〜
  13. WordPress 処理解析 ~index.phpを眺める~


JS Google Maps API 〜GeoLocation 現在位置の取得〜

Google Maps API

現在位置の取得処理でつまづいたのでメモです。
GoogleMapを作成して、現在位置の取得メソッド(監視メソッド)を使用するときの実装サンプルです。

function getCurrentPos() {
    if (navigator.geolocation == false) {
        console.log("GEO Locaion is unable.");
        return;
    }
    // オプション・オブジェクト
    var optionObj = {
        "enableHighAccuracy": false ,
        "timeout": 5000 ,
        "maximumAge": 0 ,
    };
    target = {
        latitude: 0,
        longitufe: 0
    };
    // Navigator.geolocation
    id = navigator.geolocation.watchPosition(
        successCurrentPos // 成功時のコールバック
        , errorCurrentPos // 失敗時のコールバック
        , optionObj); // オプション設定

}

そして、現在位置を取得してその位置を表示する処理は。はじめは以下のようなコードでした。>はじめは以下のようなコードでした。

/** GeoLocationの成功時のコールバック */
function successCurrentPos(position) {
    var crd  = position.coords;
    // マップの位置情報オブジェクト
    var mapLatLng = new google.maps.LatLng(crd.latitude, crd.longitude);

    if (target.latitude === crd.latitude && target.longitude === crd.longitude) {
      console.log('Congratulations, you reached the target');
      navigator.geolocation.clearWatch(id);
    }
    // マーカーの追加
    var current = new google.maps.Marker({
        map: map,
        position: mapLatLng
    });
    console.log("test");
}

しかし、これだと以下のようなエラーメッセージが出ました。
this.setValues is not a function
「なんでぢゃ〜」と叫びはしませんでしたが、結構手間取りました。そして[こちらのページ](https://stackoverflow.com/questions/36598503/error-this-setvalues-is-not-a-function-in-js-code-use-google-map-api)を参照すると
newが抜けてるよ」というアドバイスがあり。。。
同じようにして修正したら直しました。
そしてついでなので、このままオプションの変更をしない状態だと、毎度おなじみのオーバーレイが表示されるので、そいつを別のものに変更したいと思い以下のようにオプションを設定してやるとできました。

// マーカーの追加
var current = new google.maps.Marker({
    map: map,
    position: mapLatLng,
    icon: './mapImg/you.png' // ファイルの指定
});

![自作アイコンの追加](https://pbs.twimg.com/media/D_bqqRaU8AIAOit.jpg:large)
でわでわ。。。



PHP Ajax 〜DBに登録したデータを受信する〜

イントロダクション

前回は、PDOを使用してMySQL(DB)に画面から入力したデータを登録しました。
今回は、登録したデータを画面に表示する処理を実装しようと思います。

処理イメージ

<画面>

<サーバー>

こんなイメージです。サーバー側の処理としては登録した地図情報を全部リロード(再描画)する方法と追加した情報のみを描画する方法の2種類ありますが、起動してみた結果で判断するか。。。
ちょっと悩みどころです。

地図をリロードする方法

これは、単純に地図データをリフレッシュするので綺麗に再描画されます。その代わりデータが増えると重くなるかもしれないです。
<対策>
逆に初期表示をちゃんとメモリも考慮した形で実装すれば問題ありません、

追加した情報のみ再描画する方法

これは、更新する部分が少なくパフォーマンスも良いのですが、表示済みの地図情報間でのリンクなど関連する情報があるときに問題が発生します。
<対策>
表示する地図データに関してそれぞれを独立させつつも、連携取るための仕組みをきちんと考える。

関連ページ

  1. PHP PDO 〜MySQLにアクセスする〜
  2. PHP Ajax 〜DBに登録したデータを受信する〜
  3. Google Maps API PHP連携 〜マップ情報をDBに登録する〜
  4. PHP Image File 〜iPhoneやAndroidでの画像送受信の問題〜
  5. AngularJS Routing 〜PHPをWeb APIにする〜
  6. WordPress PHPカスタム〜根本的に見た目を変える〜
  7. WordPress PHPカスタム〜根本的に見た目を変える2〜
  8. Eclipse PHPプラグイン 〜ElipseでWordPress環境を構築〜
  9. WordPress テスト実装 〜heade-test.phpを表示〜
  10. AngularJS + PHP 〜WordPressと連携する〜
  11. AngularJS + PHP 〜AngularJSの実装〜
  12. AngularJS + PHP 〜AngularJSの実装2〜
  13. WordPress 処理解析 ~index.phpを眺める~



PHP PDO 〜MySQLにアクセスする〜

イントロダクション

現在、GoogleMapを使用したブラウザアプリの作成中です(2019-07-11)。
実装中につまづいたのでメモがてらに記載します。
<作成プログラム概要>

  • JSでのGoogleMap表示
  • PHPでの入力データをDBに登録

こんな感じです。

PDO to MySql

確認するポイント

  • phpinfo()でPDOの使用が可能か確認

そして確認ができたらMySQLでのPDOのインストール方法(使用可能か確かめる)とDPDO使用方法を参照して使い方を理解する。

<作成したコード>

// DBアクセス
$dns = 'mysql:host=localhost;dbname=test_dbname';
$username = DB_USER;
$password = DB_PASS;
$driver_options = [
    PDO::MYSQL_ATTR_INIT_COMMAND => 'SET NAMES utf8',
    PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION,
    PDO::ATTR_EMULATE_PREPARES => false,
];
$insertQuery = "INSERT INTO AREA_INFO(AREA_ID, INFO_NAME, INFO_URL, INFO_IMAGE, INFO_LAT, INFO_LNG, OWNER_ID, UPDATE_DATE) VALUES(?, ?, ?, ?, ?, ?, ?, ?)";

try {
    $pdo = new PDO($dns, $username, $password, $driver_options);
echo "tee";
    $pdo->prepare($insertQuery);
    $pdo->bind(1, 1);
    $pdo->bind(2, $name);
    $pdo->bind(3, $url);
    $pdo->bind(4, $lat);
    $pdo->bind(5, $lng);
    $pdo->bind(6, $imgTmp, PDO::PARAM_LOB);
    $pdo->bind(7, 1);

} catch(Exception $e) {
    print($e->getTraceAsString());
}

PreparedStatement

SQLを実行するときによく使うのがプリペアードステートメント(PreparedStatement)です。
早い話が、SQLの値部分(?)にパラメータを渡してやるものです。
Sample

  • INSERT INTO A_TBL(COL_A, COL_B) VALUES(?, ?);

というSQLクエリを実行(execute)しようとしたときに下のようにコードを書きました。

    $pdo->prepare($insertQuery);
    $pdo->bind(1, 1);
    $pdo->bind(2, $name);
    $pdo->bind(3, $url);
    $pdo->bind(4, $lat);
    $pdo->bind(5, $lng);
    $pdo->bind(6, $imgTmp, PDO::PARAM_LOB);
    $pdo->bind(7, 1);

エラリました。。。
マニュアルを見ると「bind」なんてメソッドはありませんでした。。。
なのでマニュアルに習い以下のように書き換えました。

try {
    $pdo = new PDO($dns, $username, $password, $driver_options);
echo "tee";
    $statement = $pdo->prepare($insertQuery);
    $statement->bindParam(":id", $id);
    $statement->bindParam(":name", $name);
    $statement->bindParam(":url", $url);
    $statement->bindParam(":img", $imgTmp, PDO::PARAM_LOB);
    $statement->bindParam(":lat", $lat);
    $statement->bindParam(":lng", $lng);
    $statement->bindParam(":owner", $ownerId);

    $statement->execute();

} catch(Exception $e) {
    print($e->getTraceAsString());
}

これでDBにデータの登録ができるようになりました。作成した画面はこちらです。

ちなみにSELECT文などは「query()」が使える。

try {
    $pdo = new PDO($dns, $username, $password, $driver_options);

    foreach ($pdo->query($selectQuery) as $row) {
        $tags = $tags . '<div visible="hidden" data-name="' . $row['NFO_NAME'] . '" '
                . 'data-url="' . $row['INFO_URL'] . '"'
                . 'data-url="' . $row['INFO_LAT'] . '"'
                . 'data-url="' . $row['INFO_LNG'] . '">'
                . 'img src="data:image/jpg;base64,' . $row['INFO_IMAGE'] . '" alt="写真"'
                . '/div';
    }
    // コネクションの解放
    $pdo = null;
} catch(Exception $e) {
    print($e->getTraceAsString());
}
// レスポンスに出力
print($tags);

でわでわ。。。

WordPress Pluginを作った時の動画です。