#topicpath
----


#contents

**RESTのデータをキャッシュする [#w87c22e5]
一度RESTでとったデータをキャッシュしておく方法について。

 angular.module('uiRouterSampleApp')
   .controller('Menu6Ctrl', function (sampleRestService, $scope) {
     // 同期っぽく、値をセットする
     var result = sampleRestService.getWeather();
     console.log(result);
 
 
     // 非同期っぽく、callbackで値をセットする
     sampleRestService.getWeather().$promise.then(function (data) {
       $scope.result = data;
       console.log(data);
     });
   })
   .factory('sharedService', function () {
     // Public API here
     return {
       isEmpty: function () {
         return this._data1 == null;
       },
 
       get cacheData() {
         console.log('getter!!');
         return this._data1;
       },
       set cacheData(val) {
         console.log('setter!!');
         this._data1 = val;
       }
     };
   })
   .factory('sampleRestService', function ($resource, sharedService) {
     // Public API here
     return {
       getWeather: function () {
         if (!sharedService.isEmpty()) {
           console.log('キャッシュから返す');
           return sharedService.cacheData;
         } else {
           console.log('サーバからとって返す.そのときキャッシュにも詰める');
           return $resource("/api/weather1.json").get(function (result) {
             sharedService.cacheData = result;
           });
         }
       }
     };
   });

こんな感じで、実行結果を保持しておいて次回以降それを返すなんて事ができそうです。


**HTTPの通信エラーを一網打尽に対応する [#wa40c8fe]
 angular
    .module("hoge", [])
    .config(['$httpProvider', function ($httpProvider) {
        $httpProvider.interceptors.push(
            ['$q', '$timeout', '$window', function ($q, $timeout, $window) {
                return {
                    responseError: function (rejection) {
                        var message = '';
                        if (400 == rejection.status) {
                            message = '不正なリクエスト';
                        }
                        if (401 == rejection.status) {
                            message = '認証エラーです。';
                        }
                        if (404 == rejection.status) {
                            message = 'そのリソースは存在しません';
                        }
                        if (405 == rejection.status) {
                            message = 'そのリクエストは許可されていません。';
                        }
                        if (409 == rejection.status) {
                            message = '登録しようとしたリソースはすでに存在するようです。';
                        }
                        if (500 == rejection.status) {
                            message = '予期しないエラーが発生しました。';
                        }
                        $timeout(function () {
                            $window.alert(message + ": [" + rejection.status + "]");
                        })
                        return $q.reject(rejection);
                    }
                };
            }]
        );
    }]);

**クエリパラメタから値を取り出す [#l41ce7bf]
 /xxx/xxx.html?key=hogehoge
ってURLで画面を表示したときに、
 var key = $location.search()["key"];
hogehogeが取得できます。
 

**getter/setterでフィールドにアクセスする [#qa056160]
JavaBeansみたいに。。
 angular.module(APP_NAME)
   .factory('getsetservice', function () {
     // Public API here
     return {
       get data1() {
         console.log('getter!!');
         return this._data1;
       },
       set data1(val) {
         console.log('setter!!');
         this._data1 = val;
       }
     };
   });

Controller側はこちら;
 angular.module(APP_NAME)
   .controller('Menu5Ctrl', function ($scope, getsetservice) {
        getsetservice.data1 = 'kino';
        console.log('data1: ' + getsetservice.data1);
        console.log('_data1: ' + getsetservice._data1);    <- これでアクセスできちゃうのはご愛敬 :-)
     }
   });

プロパティに直接セットしているように見えるけど実はアクセッサ経由。。ストア先をメモリ上でなくてlocalStorageに変更しよう、とかなっても利用側は変更不要にできそうですね。。

**保存先をWebStorageに変更してみた [#o4c78690]
  angular.module(APP_NAME)
   .factory('getsetservice', function ($localStorage, $sessionStorage) {
     // Public API here
     return {
       get localData1() {
         console.log('local storage getter!!');
         return $localStorage._localData1;
       },
       set localData1(val) {
         console.log('local storage setter!!');
         $localStorage._localData1 = val;
       },
       get sessionData1() {
         console.log('session storage getter!!');
         return $sessionStorage._sessionData1;
       },
       set sessionData1(val) {
         console.log('session storage setter!!');
         $sessionStorage._sessionData1 = val;
       }
     };
   });

こうしておけば、ストア先をWebStorage(session/localどちらでも) にすることができます。

あ、AngularJSでWebStorageを使う場合は
 bower install ngstorage --save
でngstorageをインストールし、
 angular.module(APP_NAME, [
    ..... 
    'ui.router',
    'ngStorage'
  ]);
でngStorageを依存モジュールに定義しておきます



**ControllerからWebStorageをつかう [#i76b1881]

 angular.module(APP_NAME)
   .controller('Menu5Ctrl', function ($scope, $localStorage, $sessionStorage) {
     // デフォルト値とともに変数の定義
     $scope.$storage1 = $localStorage.$default({
       ctrl_localData2: 'localDef'
     });
     $scope.$storage2 = $sessionStorage.$default({
       ctrl_sessionData2: 'sessionDef'
     });
 
     $scope.onClick = function () {
       $scope.$storage1.ctrl_localData2 = $scope.localData1;
       $scope.$storage2.ctrl_sessionData2 = $scope.sessionData1;
     }
   });




**ng-modelで紐付けたオブジェクトの構造 [#ce15274c]
たとえば以下のように ng-modelでオブジェクトをバインドした場合
 <form class="form-horizontal" role="form" ng-submit="addRow()">
     <div class="form-group">
         <label class="col-md-2 control-label">param1</label>
         <div class="col-md-4">
             <input type="text" class="form-control" name="postData.param1"
                    ng-model="postData.param1" />
         </div>
     </div>
     <div class="form-group">
         <label class="col-md-2 control-label">param2</label>
         <div class="col-md-4">
             <input type="text" class="form-control" name="postData.param2"
                    ng-model="postData.param2" />
         </div>
     </div>
     <div class="form-group">
         <div style="padding-left:110px">
             <input type="submit" value="Submit" class="btn btn-primary"/>
         </div>
     </div>
 </form>
$scope.postDataは
 {
   param1="aaa",
   param2="bbbbb"
 }
のようなオブジェクトが格納されます。$httpとかに
 $http({
   method: method,
   url: url,
   data: postData  ←ココ
 });
こんな感じでそのまま渡せてとても便利。。





** YeomanでAngularJSの Scaffoldをつくる [#ue186960]
 sudo npm install -g yo bower grunt-cli
 sudo npm install -g generator-angular
 sudo npm install -g generator-karma karma
がインストール済みだとして、
 yo angular
でOK


**YeomanでServiceを追加する [#uce89538]
 yo angular:factory weatherService
weatherservice.jsに weatherServiceというfactoryが追加され、さらにindex.htmlに
 <script src="scripts/services/weatherservices.js"></script>
が自動挿入されます。


**YeomanでControllerを追加する [#h87c832a]
 yo angular:controller menu5
menu5.jsに Menu5CtrlというControllerが追加され、さらにindex.htmlに
 <script src="scripts/controllers/menu5.js"></script>
が自動挿入されます。


**関連リンク [#l5ff47b0]
-[[The web's scaffolding tool for modern webapps | Yeoman>http://yeoman.io/]]

-[[AngularJSの$resourceの意外なハマりポイント | I am mitsuruog>http://blog.mitsuruog.info/2014/12/pitfall-at-angular-resource.html]]
-[[AngularJSのfactory内でHTTPリクエストサンプル - Qiita>http://qiita.com/tkc24@github/items/8a66369632dec767e027]]
-[[AngularJS: API: $http>https://docs.angularjs.org/api/ng/service/$http]]
-[[AngularJS と UI Bootstrapで$modalを使う場合のメモ - Qiita>http://qiita.com/nogson/items/41c6f3720701399d4b2a]]

----
この記事は
#vote(おもしろかった,そうでもない)

#comment

#topicpath

SIZE(10){現在のアクセス:&counter;}

トップ   編集 差分 バックアップ 添付 複製 名前変更 リロード   新規 一覧 単語検索 最終更新   ヘルプ   最終更新のRSS