nkjmkzk.net

powered by Kazuki Nakajima

AngularJSではじめるHTML5開発 – Part5 データの更新

Part4の続きです。

今回はデータの更新をおこないます。

まずは今回開発する部分をデモでみてみましょう。

デモ

それでは実装へ。

レコードを更新する関数を作成する

レコードを取得する関数と同様に更新する関数を作成します。

RemoteTKにはupdate()というレコード更新のためのメソッドが用意されていますのでこれを利用します。
 

		$scope.updateGuest = function(){
			var guest = angular.copy($scope.guest);
			delete guest.attributes;
			$scope.force.update(
				"guest__c",
				$scope.guest.Id,
				guest,
				function(result){
					alert("レコードが更新されました。");
				},
					function(result){
					console.log(result);
				}
			);
		}

第一引数にオブジェクト名のguest__c、第二引数にレコードIDの$scope.guest.Id、第三引数に更新するデータをオブジェクトで指定します。

第三引数のデータは、本当なら$scope.guestをそのまま渡してあげたいところですが、実はこのオブジェクトには元々のguest__c オブジェクトには存在しないattributesというプロパティが追加されており、これをそのままRemoteTKのupdateに渡すと「そんな項目ないよ」というエラーになってしまいます。したがって、事前にこのプロパティを消す必要があります。

ただし、一応元のオブジェクトはそのまま維持しておくために一旦オブジェクトを更新専用オブジェクトにコピーしてから削除しています。
 

			var guest = angular.copy($scope.guest);
			delete guest.attributes;

angular.copy()はオブジェクトまたは配列のDeep Copyをおこなうメソッドです。これでコピーして更新専用オブジェクトguestを作成し、このguestからattributesを削除しています。

これでレコードを更新する関数ができました。

更新ボタンを設置する

更新を実行するためのボタンを設置します。
 

				<form role="form">
					<div class="form-group">
						<label>ゲスト名</label>
						<input ng-model="guest.Name" type="text" class="form-control" placeholder="ゲスト名" />
					</div>
					<div class="form-group">
						<label>Email</label>
						<input ng-model="guest.email__c" type="email" class="form-control" placeholder="Email" />
					</div>
					<div class="form-group">
						<button class="btn btn-success" ng-click="updateGuest()">更新</button>
					</div>
				</form>

クラスのbtnおよびbtn-successはBootstrapのスタイルを適用させているだけです。

重要なのはng-clickでクリック時に先ほど作成したupdateGuest()を実行しているところですね。

さて、実際にプレビューしてみましょう。任意のレコードをクリックし、Emailを入力して「更新」をクリックしてください。

udpate guest

「レコードを更新されました。」というアラートが表示されれば成功です。

ただし、このデータ更新の仕組み、まだまだ改善の余地があります。

まず、アラートが表示されるまでの間、処理が実行されているのかどうか、またその経過がわかりません。

また、Emailではなくゲスト名を更新してみるとわかりますが、更新が完了したにも関わらずサイドバーのゲスト名は古いままの表示になっています。

ということで次回はこのAjax処理中(更新処理中)の経過をユーザーに表示しつつ、重複送信等の誤操作を防止する仕組みを実装したいと思います。

例によって最後に現時点でのindexファイルの全ソースを掲載しておきます。

<apex:page showHeader="false" standardStyleSheets="false" applyBodyTag="false" applyHtmlTag="false" docType="html-5.0" >
   
<html ng-app="ngbootcamp">
<head>
    <link rel="stylesheet" type="text/css" href="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/3.1.0/css/bootstrap.min.css"></link>
    <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/jquery/2.0.3/jquery.min.js"></script>
    <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/twitter-bootstrap/3.1.0/js/bootstrap.min.js"></script>
    <script type="text/javascript" src="https://cdnjs.cloudflare.com/ajax/libs/angular.js/1.2.10/angular.min.js"></script>
    <c:RemoteTK />
    <script>
    var ngbootcamp = angular.module('ngbootcamp', []);
    
    ngbootcamp.controller('guestCtl', function($scope){
        $scope.updateGuest = function(){
            var guest = angular.copy($scope.guest);
            delete guest.attributes;
            $scope.force.update(
                "guest__c",
                $scope.guest.Id,
                guest,
                function(result){
                    alert("レコードが更新されました。");
                },
                    function(result){
                    console.log(result);
                }
            );
        }
 
        $scope.getGuest = function(recordId){
            $scope.force.retrieve(
                "guest__c",
                recordId,
                "Id,Name,email__c",
                function(result){
                    $scope.guest = result;
                    $scope.$apply();
                },
                    function(result){
                    console.log(result);
                }
            );
        }
 
        $scope.getGuests = function(){
            var soql = "select Id, Name, CreatedDate from guest__c";
            $scope.force.query(
                soql,
                function(result){
                    $scope.guests = result.records;
                    $scope.$apply();
                },
                    function(result){
                    console.log(result);
                }
            );
        }
 
        $scope.force = new remotetk.Client();
        $scope.getGuests();
    });
    </script>
</head>
<body ng-controller="guestCtl">
    <div class="container" style="margin-top:20px;">
        <div class="row">
            <div class="col-md-4">
                <div class="panel panel-default">
                    <div class="panel-heading">
                        ゲスト
                    </div>
                    <div class="list-group">
                        <a class="list-group-item" href="#" ng-click="getGuest(guest.Id)" ng-repeat="guest in guests">{{guest.Name}}</a>
                    </div>
                </div>
            </div>
            <div class="col-md-8">
                <h1>{{guest.Name}}</h1>
                <form role="form">
                    <div class="form-group">
                        <label>ゲスト名</label>
                        <input ng-model="guest.Name" type="text" class="form-control" placeholder="ゲスト名" />
                    </div>
                    <div class="form-group">
                        <label>Email</label>
                        <input ng-model="guest.email__c" type="email" class="form-control" placeholder="Email" />
                    </div>
                    <div class="form-group">
                        <button class="btn btn-success" ng-click="updateGuest()">更新</button>
                    </div>
                </form>
            </div>
        </div>
    </div>
</body>
</html>
   
</apex:page>

 

関連情報

without comments

Written by 中嶋 一樹

2月 9th, 2014 at 6:54 pm

Leave a Reply