1
0
mirror of https://github.com/bpatrik/pigallery2.git synced 2024-12-25 02:04:15 +02:00

implementing client side login

This commit is contained in:
Braun Patrik 2016-03-13 11:28:29 +01:00
parent df717f55e1
commit 60df6caf4a
15 changed files with 259 additions and 24 deletions

27
backend/NetworkManager.ts Normal file
View File

@ -0,0 +1,27 @@
///<reference path="../typings/tsd.d.ts"/>
import * as _socketIo from 'socket.io';
import {MessageTypes} from "../common/MessageTypes";
import {User} from "../common/entities/User";
import {LoginCredential} from "../common/entities/LoginCredential";
import * as _debug from 'debug';
var debug = _debug("PiGallery2:NetworkManager");
export class NetworkManager{
private socketIo:SocketIO.Server;
constructor(http){
this.socketIo = _socketIo(http);
this.socketIo.on('connection', function(socket:SocketIO.Server){
debug("Client Connected");
socket.on(MessageTypes.Client.Login.Authenticate,(credential:LoginCredential) =>{
debug("Message: " + MessageTypes.Client.Login.Authenticate);
socket.emit(MessageTypes.Server.Login.Authenticated,new User("Dummy user","dummy@mail.com","password"));
});
});
}
}

View File

@ -4,6 +4,7 @@ import * as _express from 'express';
import * as _debug from 'debug';
import * as _http from 'http';
import * as path from 'path';
import {NetworkManager} from "./NetworkManager";
export class Server {
@ -46,6 +47,7 @@ export class Server {
this.server.on('error', this.onError);
this.server.on('listening', this.onListening);
new NetworkManager(this.server);
}

10
common/common-classes.d.ts vendored Normal file
View File

@ -0,0 +1,10 @@
///<reference path="event/Event.ts"/>
///<reference path="event/Event2Args.ts"/>
///<reference path="event/EventLimit.ts"/>
///<reference path="MessageTypes.ts"/>
///<reference path="entities/Error.ts"/>
///<reference path="entities/LoginCredential.ts"/>
///<reference path="entities/User.ts"/>
///<reference path="entities/Message.ts"/>

32
common/event/Event.ts Normal file
View File

@ -0,0 +1,32 @@
///<reference path="../../typings/tsd.d.ts"/>
function isFunction(functionToCheck) {
var getType = {};
return functionToCheck && getType.toString.call(functionToCheck) === '[object Function]';
}
export class Event<T> {
private handlers: { (data?: T): void; }[] = [];
public on(handler: { (data?: T): void }) {
if(!isFunction(handler)){
throw new Error("Handler is not a function");
}
this.handlers.push(handler);
}
public off(handler: { (data?: T): void }) {
this.handlers = this.handlers.filter(h => h !== handler);
}
public allOff() {
this.handlers = [];
}
public trigger(data?: T) {
if (this.handlers) {
this.handlers.slice(0).forEach(h => h(data));
}
}
}

View File

@ -0,0 +1,23 @@
///<reference path="../../typings/tsd.d.ts"/>
export class Event2Args<T,M> {
private handlers: { (data?: T,data2?: M): void; }[] = [];
public on(handler: { (data?: T,data2?: M): void }) {
this.handlers.push(handler);
}
public off(handler: { (data?: T,data2?: M): void }) {
this.handlers = this.handlers.filter(h => h !== handler);
}
public allOff() {
this.handlers = [];
}
public trigger(data?: T,data2?: M) {
if (this.handlers) {
this.handlers.slice(0).forEach(h => h(data,data2));
}
}
}

View File

@ -0,0 +1,72 @@
///<reference path="../../typings/tsd.d.ts"/>
export class EventLimit<T> {
private lastTriggerValue:T = null;
private handlers:Array<EventLimitHandler<T>> = [];
public on(limit:T, handler:{ (data?:T): void }) {
this.handlers.push(new EventLimitHandler(limit, handler));
if (this.lastTriggerValue != null) {
this.trigger(this.lastTriggerValue);
}
}
public onSingle(limit:T, handler:{ (data?:T): void }) {
this.handlers.push(new SingleFireEventLimitHandler(limit, handler));
if (this.lastTriggerValue != null) {
this.trigger(this.lastTriggerValue);
}
}
public off(limit:T, handler:{ (data?:T): void }) {
this.handlers = this.handlers.filter(h => h.handler !== handler && h.limit !== limit);
}
public allOff() {
this.handlers = [];
}
public trigger = (data?:T) => {
if (this.handlers) {
this.handlers.slice(0).forEach(h => {
if (h.limit <= data && (h.lastTriggerValue < h.limit || h.lastTriggerValue == null)) {
h.fire(data);
}
h.lastTriggerValue = data;
});
this.handlers = this.handlers.filter(h => h.isValid());
}
this.lastTriggerValue = data;
};
}
class EventLimitHandler<T> {
public lastTriggerValue:T = null;
constructor(public limit:T, public handler:{ (data?:T): void }) {
}
public fire(data?: T){
this.handler(data);
}
public isValid():boolean{
return true;
}
}
class SingleFireEventLimitHandler<T> extends EventLimitHandler<T>{
public fired = false;
constructor(public limit:T, public handler:{ (data?:T): void }) {
super(limit,handler);
}
public fire(data?: T){
if(this.fired == false) {
this.handler(data);
}
this.fired = true
}
public isValid():boolean{
return this.fired === false;
}
}

View File

@ -5,6 +5,11 @@ import { RouteConfig, ROUTER_DIRECTIVES, ROUTER_PROVIDERS } from 'angular2/route
import {LoginComponent} from "./login/login.component";
import {NetworkService} from "./model/network.service";
import {LoginService} from "./login/login.service";
import {AuthenticationService} from "./model/authentication.service";
import {GalleryComponent} from "./gallery/gallery.component";
import {OnInit} from "angular2/core";
import {User} from "../../common/entities/User";
import {Router} from "angular2/router";
@ -16,6 +21,7 @@ import {LoginService} from "./login/login.service";
providers: [
ROUTER_PROVIDERS,
NetworkService,
AuthenticationService,
LoginService
]
})
@ -25,10 +31,22 @@ import {LoginService} from "./login/login.service";
name: 'Login',
component: LoginComponent,
useAsDefault: true
},
{
path: '/gallery',
name: 'Gallery',
component: GalleryComponent
}
])
export class AppComponent {
constructor(){
export class AppComponent implements OnInit{
constructor(private _router: Router ,private _authenticationService: AuthenticationService){
}
ngOnInit() {
this._authenticationService.OnAuthenticated.on((user:User) =>
{
this._router.navigate(["Gallery"]);
});
}
}

View File

@ -0,0 +1 @@
<h1>Gallery</h1>

View File

@ -0,0 +1,11 @@
///<reference path="../../../typings/tsd.d.ts"/>
import { Component } from 'angular2/core';
@Component({
selector: 'gallery',
templateUrl: 'app/gallery/gallery.component.html'
})
export class GalleryComponent{
}

View File

@ -1,13 +1,13 @@
<form>
<div class="group">
<input type="text" [(ngModel)]="user.username"><span class="highlight"></span><span class="bar"></span>
<input type="text" [(ngModel)]="user.username" required><span class="highlight"></span><span class="bar"></span>
<label *ngIf="!user.username">Username (or e-mail)</label>
</div>
<div class="group">
<input type="password" [(ngModel)]="user.password"><span class="highlight"></span><span class="bar"></span>
<input type="password" [(ngModel)]="user.password" required><span class="highlight"></span><span class="bar"></span>
<label *ngIf="!user.password">Password</label>
</div>
<button type="button" class="button buttonBlue">Login
<button type="button" class="button buttonBlue" (click)="onLogin()">Login
<div class="ripples buttonRipples"><span class="ripplesCircle"></span></div>
</button>
</form>

View File

@ -14,5 +14,9 @@ export class LoginComponent{
constructor(private _loginService: LoginService) {
this.user = new LoginCredential();
}
onLogin(){
this._loginService.login(this.user);
}
}

View File

@ -4,30 +4,18 @@ import {Injectable} from 'angular2/core';
import {NetworkService} from "../model/network.service";
import {OnInit} from "angular2/core";
import {MessageTypes} from "../../../common/MessageTypes";
import {Utils} from "../../../common/Utils";
import {LoginCredential} from "../../../common/entities/LoginCredential";
import {User} from "../../../common/entities/User";
import {Message} from "../../../common/entities/Message";
@Injectable()
export class LoginService implements OnInit{
export class LoginService {
private _authenticating:LoginCredential;
constructor(private _networkService: NetworkService){
}
ngOnInit() {
this._networkService.socketIO.on(MessageTypes.Server.Login.Authenticated, (message:Message<User>) => {
if(message.result.name == this._authenticating.username || message.result.email == this._authenticating.username){
}
});
}
public login(user:LoginCredential):Promise<User> {
this._networkService.socketIO.emit(MessageTypes.Client.Login.Authenticate, user);
this._authenticating = Utils.clone(user);
public login(credential:LoginCredential) {
this._networkService.login(credential);
}

View File

@ -0,0 +1,28 @@
///<reference path="../../../typings/tsd.d.ts"/>
import * as io from 'socket.io-client';
import {Injectable} from 'angular2/core';
import {OnInit} from "angular2/core";
import {NetworkService} from "./network.service";
import {User} from "../../../common/entities/User";
import {Event} from "../../../common/event/Event";
@Injectable()
export class AuthenticationService{
private _user:User;
public OnAuthenticated:Event<User>;
constructor(private _networkService: NetworkService){
this.OnAuthenticated = new Event();
this._networkService.OnAuthenticated.on(this.onAuthenticated);
}
private onAuthenticated = (user:User) => {
this._user=user;
this.OnAuthenticated.trigger(this._user);
}
}

View File

@ -3,18 +3,37 @@
import * as io from 'socket.io-client';
import {Injectable} from 'angular2/core';
import {OnInit} from "angular2/core";
import {LoginCredential} from "../../../common/entities/LoginCredential";
import {MessageTypes} from "../../../common/MessageTypes";
import {Event} from "../../../common/event/Event";
import {User} from "../../../common/entities/User";
import {Message} from "../../../common/entities/Message";
@Injectable()
export class NetworkService implements OnInit{
export class NetworkService{
private _socketIO: SocketIOClient.Socket;
ngOnInit() {
public OnAuthenticated:Event<User>;
constructor(){
this._socketIO = io();
this.OnAuthenticated = new Event();
this._subscribeMessages();
}
get socketIO():SocketIOClient.Socket {
return this._socketIO;
public login(credential:LoginCredential){
this._socketIO.emit(MessageTypes.Client.Login.Authenticate,credential);
}
private _subscribeMessages(){
this._socketIO.on(MessageTypes.Server.Login.Authenticated, (message:Message<User>) =>{
if(message.error){
//TODO: Handle error
}else{
this.OnAuthenticated.trigger(message.result);
}
});
}
}