74
Sebastian Springer @basti_springer Wednesday, June 26, 13

Einführung in AngularJS

Embed Size (px)

Citation preview

Page 1: Einführung in AngularJS

Sebastian Springer@basti_springer

Wednesday, June 26, 13

Page 2: Einführung in AngularJS

WER BIN ICH?

• Sebastian Springer

• https://github.com/sspringer82

• @basti_springer

• Teamlead @ Mayflower

Wednesday, June 26, 13

Page 3: Einführung in AngularJS

INHALT

• Bootstrap

• Scope

• Controller

• Model

• View

• Direktiven

• Filter

• Dependency Injection

• Module

• Testing

Wednesday, June 26, 13

Page 4: Einführung in AngularJS

ANGULAR?

• Open Source MVC Framework

• von Google

• sehr gut erweiterbar

• jQuery lite bundled

• ng-* Direktiven

Wednesday, June 26, 13

Page 5: Einführung in AngularJS

INDEX.HTML

Wednesday, June 26, 13

Page 6: Einführung in AngularJS

BOOTSTRAP

<!DOCTYPE html><html ng-app> <head> <title>Movie Database</title> <script src="/js/lib/angular.js"></script> </head> <body> Hello {{ 'World!' }} </body></html>

Wednesday, June 26, 13

Page 7: Einführung in AngularJS

BOOTSTRAP

Wednesday, June 26, 13

Page 8: Einführung in AngularJS

Wednesday, June 26, 13

Page 9: Einführung in AngularJS

CONTROLLER

• Funktionen

• Kontrolliert das Verhalten der Applikation

• Verbindet Models und Views

• Scope als Verbindungselement

Wednesday, June 26, 13

Page 10: Einführung in AngularJS

INDEX.HTML

Wednesday, June 26, 13

Page 11: Einführung in AngularJS

CONTROLLER<!DOCTYPE html><html data-ng-app> <head> <title>Movie Database</title> <script src="/js/lib/angular.js"></script> <script src="/js/controllers.js"></script> </head> <body ng-controller="MovieListCtrl">

{{ name }}

</body></html>

Wednesday, June 26, 13

Page 12: Einführung in AngularJS

CONTROLLER<!DOCTYPE html><html data-ng-app> <head> <title>Movie Database</title> <script src="/js/lib/angular.js"></script> <script src="/js/controllers.js"></script> </head> <body ng-controller="MovieListCtrl">

{{ name }}

</body></html>

Wednesday, June 26, 13

Page 13: Einführung in AngularJS

JS/CONTROLLERS.JS

Wednesday, June 26, 13

Page 14: Einführung in AngularJS

CONTROLLER

function MovieListCtrl($scope) {

$scope.name = 'Matrix';

}

Wednesday, June 26, 13

Page 15: Einführung in AngularJS

SCOPE

• Änderungen in Models erkennen

• Ausführungskontext

• An Controller gebunden

Wednesday, June 26, 13

Page 16: Einführung in AngularJS

function MovieListCtrl($scope) {

$scope.name = 'Matrix';

}

SCOPE

Wednesday, June 26, 13

Page 17: Einführung in AngularJS

<!DOCTYPE html><html data-ng-app> <head> <title>Movie Database</title> <script src="/js/lib/angular.js"></script> <script src="/js/controllers.js"></script> </head> <body ng-controller="MovieListCtrl">

{{ name }}

</body></html>

SCOPE

Wednesday, June 26, 13

Page 18: Einführung in AngularJS

Wednesday, June 26, 13

Page 19: Einführung in AngularJS

DATA-BINDING

• Das Model hält die Daten

• Die View erhält die Daten und stellt sie dar

• Scope als Verbindungsstück

Wednesday, June 26, 13

Page 20: Einführung in AngularJS

TWO-WAY-DATA-BINDING

• Controller gibt den Wert für das Model vor

• Über das Model kann der Wert geändert werden

Wednesday, June 26, 13

Page 21: Einführung in AngularJS

TWO-WAY-DATA-BINDINGfunction LoginCtrl($scope) {

$scope.username = 'stranger';

$scope.login = function () { if ($scope.username === 'admin' && $scope.password === 'test') { $scope.user = 'Administrator'; } }

}

Wednesday, June 26, 13

Page 22: Einführung in AngularJS

Wednesday, June 26, 13

Page 23: Einführung in AngularJS

MODEL

Wednesday, June 26, 13

Page 24: Einführung in AngularJS

MODEL

• Daten zur Darstellung in der View

• keinerlei Vorgaben hinsichtlich des Aufbaus

Wednesday, June 26, 13

Page 25: Einführung in AngularJS

MODEL

Wednesday, June 26, 13

Page 26: Einführung in AngularJS

MODEL

function MovieListCtrl($scope) {

$scope.name = 'Matrix';

}

Wednesday, June 26, 13

Page 27: Einführung in AngularJS

VIEW

Wednesday, June 26, 13

Page 28: Einführung in AngularJS

VIEW

• Darstellung der Modeldaten

• Zeigt Änderungen des Models sofort an

• Zugriff auf den Scope über {{ }}

Wednesday, June 26, 13

Page 29: Einführung in AngularJS

VIEW

Wednesday, June 26, 13

Page 30: Einführung in AngularJS

VIEW<!DOCTYPE html><html data-ng-app> <head> <title>Movie Database</title> <script src="/js/lib/angular.js"></script> <script src="/js/controllers.js"></script> </head> <body ng-controller="MovieListCtrl">

{{ name }}

</body></html>

Wednesday, June 26, 13

Page 31: Einführung in AngularJS

DIREKTIVEN

Wednesday, June 26, 13

Page 32: Einführung in AngularJS

DIREKTIVEN

• HTML Attribute

• Verhalten oder DOM Transformation

• Built-ins und eingene Direktiven

• Eigene Direktiven

• z.B. ngApp, ngController, ngRepeat

Wednesday, June 26, 13

Page 33: Einführung in AngularJS

DIREKTIVEN

Wednesday, June 26, 13

Page 34: Einführung in AngularJS

JS/CONTROLLERS.JS

Wednesday, June 26, 13

Page 35: Einführung in AngularJS

DIREKTIVEN

function MovieListCtrl($scope) {

$scope.films = [ {name: 'Matrix', year: 2005, genre: 'Sci-Fi'}, {name: 'Avatar', year: 2009, genre: 'Sci-Fi'}, {name: 'Gran Torino', year: 2008, genre: 'Drama'} ];}

Wednesday, June 26, 13

Page 36: Einführung in AngularJS

INDEX.HTML

Wednesday, June 26, 13

Page 37: Einführung in AngularJS

<table> <thead> <tr> <th>Name</th><th>Jahr</th><th>Genre</th> </tr> </thead>

<tbody>

<tr ng-repeat="film in films"> <td>{{film.name}}</td> <td>{{film.year}}</td> <td>{{film.genre}}</td> </tr>

</tbody></table>

Wednesday, June 26, 13

Page 38: Einführung in AngularJS

Wednesday, June 26, 13

Page 39: Einführung in AngularJS

FILTER

Wednesday, June 26, 13

Page 40: Einführung in AngularJS

• Datentransformation

• Verbindung über das Pipe-Symbol

• Eigene Filter

• z.B. uppercase, json

FILTER

Wednesday, June 26, 13

Page 41: Einführung in AngularJS

{{ 'Hello World' | uppercase }}

<input ng-model="search">

<table> <thead> <tr> <th>Name</th><th>Jahr</th><th>Genre</th> </tr> </thead>

<tbody> <tr ng-repeat="film in films | filter: search"> <td>{{film.name}}</td> <td>{{film.year}}</td> <td>{{film.genre}}</td> </tr> </tbody></table>

Wednesday, June 26, 13

Page 42: Einführung in AngularJS

{{ 'Hello World' | uppercase }}

<input ng-model="search">

<table> <thead> <tr> <th>Name</th><th>Jahr</th><th>Genre</th> </tr> </thead>

<tbody> <tr ng-repeat="film in films | filter: search"> <td>{{film.name}}</td> <td>{{film.year}}</td> <td>{{film.genre}}</td> </tr> </tbody></table>

Wednesday, June 26, 13

Page 43: Einführung in AngularJS

Wednesday, June 26, 13

Page 44: Einführung in AngularJS

DEPENDENCY INJECTION

Wednesday, June 26, 13

Page 45: Einführung in AngularJS

DEPENDENCY INJECTION

• Strukturierung - Komponenten für Model, View, Controller

• Lose Kopplung - DI löst Abhängigkeiten auf

• DI stellt Services zur Verfügung

• Caching Mechanismus

Wednesday, June 26, 13

Page 46: Einführung in AngularJS

DEPENDENCY INJECTION

Wednesday, June 26, 13

Page 47: Einführung in AngularJS

DEPENDENCY INJECTION

function MovieListCtrl($scope, $http) {

$http.get('/movies').success(function(data) { $scope.films = data; });

}

Wednesday, June 26, 13

Page 48: Einführung in AngularJS

DEPENDENCY INJECTION

function MovieListCtrl($scope, $http) {

$http.get('/movies').success(function(data) { $scope.films = data; });

}

Wednesday, June 26, 13

Page 49: Einführung in AngularJS

MODULE

Wednesday, June 26, 13

Page 50: Einführung in AngularJS

• Geben den Bootstrap-Prozess einer Applikation vor

• Service Modul

• Directive Modul

• Filter Modul

• Application Modul

MODULE

Wednesday, June 26, 13

Page 51: Einführung in AngularJS

MODULEvar myApp = angular.module('myApp', []);

myApp.controller('MovieListCtrl', ['$scope', '$http', function ($scope, $http) {

$http.get('/movies').success(function(data) { $scope.films = data; });

}]);

Wednesday, June 26, 13

Page 52: Einführung in AngularJS

MODULEvar myApp = angular.module('myApp', []);

myApp.controller('MovieListCtrl', ['$scope', '$http', function ($scope, $http) {

$http.get('/movies').success(function(data) { $scope.films = data; });

}]);

Wednesday, June 26, 13

Page 53: Einführung in AngularJS

TESTING

Wednesday, June 26, 13

Page 54: Einführung in AngularJS

TESTS

• Karma als Testrunner

• sudo npm install -g karma

• Angular setzt auf Jasmine

• Zwei Arten von Tests

• Unittests

• E2E-Tests

Wednesday, June 26, 13

Page 55: Einführung in AngularJS

UNITTESTS

Wednesday, June 26, 13

Page 56: Einführung in AngularJS

UNITTESTS

• Testen Units of Code

• Grundlage für TDD

• Pfad: test/unit/*

• Konfiguration: config/karma.conf.js

Wednesday, June 26, 13

Page 57: Einführung in AngularJS

TEST/UNIT/CONTROLLERSPEC.JS

Wednesday, June 26, 13

Page 58: Einführung in AngularJS

describe('movieListCtrl', function(){

var scope, ctrl, $httpBackend;

beforeEach(inject(function(_$httpBackend_, $rootScope, $controller) { $httpBackend = _$httpBackend_; $httpBackend.expectGET('data/movies.json').respond( [{"name": "Matrix", "year": 2005, "genre": "Sci-Fi"}] ); scope = $rootScope.$new(); ctrl = $controller(movieListCtrl, {$scope: scope}); }));

Wednesday, June 26, 13

Page 59: Einführung in AngularJS

it ("should fetch a list with one movie", function () { expect(scope.films).toBeUndefined();

$httpBackend.flush();

expect(scope.films).toEqual( [{"name": "Matrix", "year": 2005, "genre": "Sci-Fi"}] ); });

Wednesday, June 26, 13

Page 60: Einführung in AngularJS

UNITTESTS

$ ./scripts/test.sh

Starting Karma Server (http://karma-runner.github.io)-------------------------------------------------------------------INFO [karma]: Karma server started at http://localhost:9876/INFO [launcher]: Starting browser ChromeINFO [launcher]: Starting browser FirefoxINFO [Firefox 21.0 (Mac)]: Connected on socket id 8lw9q3ZBbNpAb7rc3RpSINFO [Chrome 27.0 (Mac)]: Connected on socket id KI5wy1rfgkIU32cP3RpRFirefox 21.0 (Mac): Executed 4 of 4 SUCCESS (0.134 secs / 0.037 secs)Chrome 27.0 (Mac): Executed 4 of 4 SUCCESS (0.157 secs / 0.044 secs)TOTAL: 8 SUCCESS

Wednesday, June 26, 13

Page 61: Einführung in AngularJS

UNITTESTS

Wednesday, June 26, 13

Page 62: Einführung in AngularJS

UNITTESTS

INFO [watcher]: Changed file "/srv/angularMovieDB/app/js/controllers.js".

Watcher

Wednesday, June 26, 13

Page 63: Einführung in AngularJS

E2E

Wednesday, June 26, 13

Page 64: Einführung in AngularJS

E2E

• Testen zusammenhängende Units

• DOM-Manipulationen

• Pfad: test/e2e

• Konfiguration: config/karma-e2e.conf.js

Wednesday, June 26, 13

Page 65: Einführung in AngularJS

TEST/E2E/SCENARIOS.JS

Wednesday, June 26, 13

Page 66: Einführung in AngularJS

E2E

describe('Movie List', function() {

beforeEach(function() { browser().navigateTo('../../app/index.html'); });

it('should display 3 movies', function() { expect(repeater('table tbody tr').count()).toBe(3); });});

Wednesday, June 26, 13

Page 67: Einführung in AngularJS

E2E

• Webserver ausführen

•./scripts/web-server.js

• Tests ausführen

•./scripts/e2e-test.sh

Wednesday, June 26, 13

Page 68: Einführung in AngularJS

E2E

./scripts/e2e-test.sh

Starting Karma Server (http://karma-runner.github.io)-------------------------------------------------------------------[2013-06-22 10:26:07.404] [WARN] config - "/" is proxied, you should probably change urlRoot to avoid conflictsINFO [karma]: Karma server started at http://localhost:9876/INFO [launcher]: Starting browser ChromeINFO [Chrome 27.0 (Mac)]: Connected on socket id 4YaYP4NBBNKlOgDS_YbAChrome 27.0 (Mac): Executed 1 of 1 SUCCESS (0.385 secs / 0.189 secs)

Wednesday, June 26, 13

Page 69: Einführung in AngularJS

E2E

• http://docs.angularjs.org/guide/dev_guide.e2e-testing

Wednesday, June 26, 13

Page 70: Einführung in AngularJS

ANGULAR-SEED

Wednesday, June 26, 13

Page 71: Einführung in AngularJS

ANGULAR-SEED

• Basisstruktur für Projekte

• https://github.com/angular/angular-seed

Wednesday, June 26, 13

Page 72: Einführung in AngularJS

TIPPS & TRICKS

• Setzt Module ein

• Nutzt den Router

• Achtet auf den Scope

• Nutzt die Direktiven

• Schreibt Tests

Wednesday, June 26, 13

Page 73: Einführung in AngularJS

FRAGEN?

Wednesday, June 26, 13

Page 74: Einführung in AngularJS

KONTAKT

Sebastian [email protected]

Mayflower GmbHMannhardtstr. 680538 MünchenDeutschland

@basti_springer

https://github.com/sspringer82

Wednesday, June 26, 13