Commit ecc30837 authored by Thodoris Nestoridis's avatar Thodoris Nestoridis

trying tabe

parent 48f8ff50
{
// Use IntelliSense to learn about possible attributes.
// Hover to view descriptions of existing attributes.
// For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387
"version": "0.2.0",
"configurations": [
{
"type": "pwa-chrome",
"request": "launch",
"name": "Launch Chrome against localhost",
"url": "http://155.207.131.19:8081/login",
"webRoot": "${workspaceFolder}"
}
]
}
\ No newline at end of file
This source diff could not be displayed because it is too large. You can view the blob instead.
This diff is collapsed.
......@@ -15,7 +15,7 @@ import { PrefixDetailsComponent } from './components/prefix-details/prefix-detai
import { AddPrefixComponent } from './components/add-prefix/add-prefix.component';*/
const routes: Routes = [
{ path: '', redirectTo: 'login', pathMatch: 'full' },
{ path: ' ', redirectTo: 'login', pathMatch: 'full' },
{ path: 'login', component: LoginComponent },
{ path: 'signup', component: SignupComponent },
{ path: 'boilerplates', component: BoilerplateListComponent, canActivate: [AuthGuard] },
......
<mat-sidenav-container>
<mat-sidenav #sidenav role="navigation">
<!--this is a place for us to add side-nav code-->
<app-sidenav-list (sidenavClose)="sidenav.close()"></app-sidenav-list>
</mat-sidenav>
<mat-sidenav-content>
<!--in here all the content must reside. We will add a navigation header as well-->
<mat-sidenav-content>
<app-header (sidenavToggle)="sidenav.toggle()"></app-header>
<main>
<router-outlet></router-outlet>
</main>
<div *ngIf="!LoggedIn()"> <router-outlet></router-outlet> </div>
<div *ngIf="LoggedIn()">
<mat-sidenav-container>
<mat-sidenav #sidenav role="navigation">
<app-sidenav-list (sidenavClose)="sidenav.close()"></app-sidenav-list>
</mat-sidenav>
<mat-sidenav-content>
<mat-sidenav-content>
<app-header (sidenavToggle)="sidenav.toggle()"></app-header>
<main>
<router-outlet></router-outlet>
</main>
</mat-sidenav-content>
</mat-sidenav-content>
</mat-sidenav-content>
</mat-sidenav-container>
</mat-sidenav-container>
</div>
<notifier-container></notifier-container>
\ No newline at end of file
import { Component } from '@angular/core';
import { Component, Output, EventEmitter } from '@angular/core';
import { AuthService } from './services/auth.service';
@Component({
selector: 'app-root',
templateUrl: './app.component.html',
styleUrls: ['./app.component.scss']
})
export class AppComponent {
constructor(private authService: AuthService){}
title = 'ReqmanAngular11';
LoggedIn() {
return this.authService.isLoggedIn();
}
};
\ No newline at end of file
......@@ -6,7 +6,7 @@ import {NgbModule} from '@ng-bootstrap/ng-bootstrap';
import { AppRoutingModule } from './app-routing.module';
import { AppComponent } from './app.component';
import { FormsModule } from '@angular/forms';
import { FormsModule, ReactiveFormsModule } from '@angular/forms';
import { HttpClientModule, HTTP_INTERCEPTORS } from '@angular/common/http';
import { AuthService, AuthInterceptor, AuthGuard } from './services/auth.service';
......@@ -46,6 +46,7 @@ import { SidenavListComponent } from './navigation/sidenav-list/sidenav-list.com
imports: [
BrowserModule,
AppRoutingModule,
ReactiveFormsModule,
FormsModule,
HttpClientModule,
NgbModule,
......
......@@ -19,6 +19,7 @@
</div>
</div>
</div>
<!--
<div class="col-md-6">
<h4>Boilerplate List</h4>
<ul class="list-group">
......@@ -57,6 +58,40 @@
</div>
<div>
<button class="btn btn-success" routerLink="/add-boilerplate">Add</button>
</div>
</div>-->
</div>
\ No newline at end of file
<table mat-table [dataSource]="dataSource" class="mat-elevation-z8">
<!-- Position Column -->
<ng-container matColumnDef="id">
<th mat-header-cell *matHeaderCellDef> No. </th>
<td mat-cell *matCellDef="let element"> {{element.id}} </td>
</ng-container>
<!-- Name Column -->
<ng-container matColumnDef="title">
<th mat-header-cell *matHeaderCellDef> Title </th>
<td mat-cell *matCellDef="let element"> {{element.title}} </td>
</ng-container>
<!-- Weight Column -->
<ng-container matColumnDef="has_prefix">
<th mat-header-cell *matHeaderCellDef> Prefix </th>
<td mat-cell *matCellDef="let element"> {{element.has_prefix}} </td>
</ng-container>
<!-- Symbol Column -->
<ng-container matColumnDef="has_main">
<th mat-header-cell *matHeaderCellDef> Main </th>
<td mat-cell *matCellDef="let element"> {{element.has_main}} </td>
</ng-container>
<!-- Symbol Column -->
<ng-container matColumnDef="has_suffix">
<th mat-header-cell *matHeaderCellDef> Suffix </th>
<td mat-cell *matCellDef="let element"> {{element.has_suffix}} </td>
</ng-container>
<tr mat-header-row *matHeaderRowDef="displayedColumns"></tr>
<tr mat-row *matRowDef="let row; columns: displayedColumns;"></tr>
</table>
......@@ -3,4 +3,7 @@
max-width: 750px;
margin: auto;
}
\ No newline at end of file
table {
width: 100%;
}
\ No newline at end of file
......@@ -2,18 +2,32 @@ import { Component, OnInit } from '@angular/core';
import { Boilerplate } from 'src/app/models/boilerplate.model';
import { BoilerplateService } from 'src/app/services/boilerplate.service';
export interface PeriodicElement {
id: number;
title: string;
has_prefix: boolean;
has_main: boolean;
has_suffix: boolean;
}
const ELEMENT_DATA: PeriodicElement[] = [{id: 5, title:"ss", has_prefix: false, has_main:true, has_suffix:true},
{id: 6, title:"s222s", has_prefix: false, has_main:true, has_suffix:true}];
@Component({
selector: 'app-boilerplate-list',
templateUrl: './boilerplate-list.component.html',
styleUrls: ['./boilerplate-list.component.scss']
})
export class BoilerplateListComponent implements OnInit {
boilerplates?: Boilerplate[];
currentBoilerplate?: Boilerplate;
currentIndex = -1;
title = '';
displayedColumns: string[] = ['id', 'title', 'has_prefix', 'has_main', 'has_suffix'];
dataSource = ELEMENT_DATA;
constructor(private boilerplateService: BoilerplateService) { }
ngOnInit(): void {
......@@ -25,7 +39,9 @@ export class BoilerplateListComponent implements OnInit {
.subscribe(
data => {
this.boilerplates = data;
console.log(data);
//this.boilerplates = this.dataSource;
data.forEach(val => this.dataSource.push(Object.assign(val)));
console.log(this.dataSource);
},
error => {
console.log(error);
......
......@@ -12,39 +12,37 @@
<!-- Default form login -->
<form class="text-center border border-light p-5">
<p class="h4 mb-4">Sign in</p>
<!-- Email -->
<input #email type="email" id="defaultLoginFormEmail" class="form-control mb-4" placeholder="E-mail">
<!-- Password -->
<input #password type="password" id="defaultLoginFormPassword" class="form-control mb-4" placeholder="Password">
<div class="d-flex justify-content-around">
<div>
<!-- Remember me -->
<input
class="form-check-input"
type="checkbox"
value=""
id="flexCheckDefault"
/>
</div>
<div>
<!-- Forgot password -->
<a href="">Forgot password?</a>
</div>
</div>
<div class="main-wrapper" fxLayout="row" fxLayoutAlign="center center">
<mat-card class="box">
<mat-card-header>
<mat-card-title>Sign In</mat-card-title>
</mat-card-header>
<form class="example-form">
<!-- Email -->
<mat-card-content>
<mat-form-field class="example-full-width">
<mat-label>Enter your email</mat-label>
<input matInput placeholder="pat@example.com" [formControl]="email" required>
<mat-error *ngIf="email.invalid">{{getErrorMessage()}}</mat-error>
</mat-form-field>
<!-- Password -->
<mat-form-field aclass="example-full-width">
<mat-label>Enter your password</mat-label>
<input matInput [type]="hide ? 'password' : 'text'" [formControl]="password" required>
<button mat-icon-button matSuffix (click)="hide = !hide" [attr.aria-label]="'Hide password'" [attr.aria-pressed]="hide">
<mat-icon>{{hide ? 'visibility_off' : 'visibility'}}</mat-icon>
</button>
</mat-form-field>
</mat-card-content>
<!-- Sign in button -->
<button mdbBtn color="info" block="true" class="my-4" type="submit" (click)="login(email.value, password.value)">Log in</button>
<button mat-stroked-button color="primary" class="btn-block" type="submit" (click)="login(email.value, password.value)">Log in</button>
<!-- Register -->
<p>Not a member?
<a href="">Register</a>
<a href="#">Register</a>
</p>
</form>
</mat-card>
</div>
<!-- Default form login -->
\ No newline at end of file
.app-header {
justify-content: space-between;
position: fixed;
top: 0;
left: 0;
right: 0;
z-index: 2;
box-shadow: 0 3px 5px -1px rgba(0, 0, 0, .2), 0 6px 10px 0 rgba(0, 0, 0, .14), 0 1px 18px 0 rgba(0, 0, 0, .12);
}
.main-wrapper {
height: 100%;
}
.positronx {
text-decoration: none;
color: #ffffff;
}
.box {
position: relative;
top: 0;
opacity: 1;
float: left;
padding: 60px 50px 40px 50px;
width: 100%;
background: #fff;
border-radius: 10px;
transform: scale(1);
-webkit-transform: scale(1);
-ms-transform: scale(1);
z-index: 5;
max-width: 330px;
}
.box.back {
transform: scale(.95);
-webkit-transform: scale(.95);
-ms-transform: scale(.95);
top: -20px;
opacity: .8;
z-index: -1;
}
.box:before {
content: "";
width: 100%;
height: 30px;
border-radius: 10px;
position: absolute;
top: -10px;
background: rgba(255, 255, 255, .6);
left: 0;
transform: scale(.95);
-webkit-transform: scale(.95);
-ms-transform: scale(.95);
z-index: -1;
}
.main-wrapper .example-form {
min-width: 100%;
max-width: 300px;
width: 100%;
padding: 20px ;
}
.main-wrapper .example-full-width,
.main-wrapper .btn-block {
width: 100%;
}
.main-wrapper mat-card-header {
text-align: center;
width: 100%;
display: block;
font-weight: 700;
}
.main-wrapper mat-card-header mat-card-title {
font-size: 30px;
margin: 0;
}
.main-wrapper .mat-card {
padding: center;
}
.main-wrapper .mat-stroked-button {
border: 1px solid currentColor;
line-height: 54px;
background: #FFF7FA;
}
.main-wrapper .mat-form-field-appearance-legacy .mat-form-field-infix {
padding: 0.8375em 0;
}
\ No newline at end of file
import { Component, OnInit } from '@angular/core';
import { Router } from '@angular/router';
import { AuthService } from './../../services/auth.service';
import { NotifierService } from "angular-notifier";
import {FormControl, Validators} from '@angular/forms';
@Component({
selector: 'app-login',
......@@ -8,13 +10,25 @@ import { AuthService } from './../../services/auth.service';
styleUrls: ['./login.component.scss']
})
export class LoginComponent implements OnInit {
error: any;
private readonly notifier: NotifierService;
constructor(
private authService: AuthService,
private router: Router,
) { }
notifierService: NotifierService,
) {this.notifier = notifierService; }
hide = true;
email = new FormControl('', [Validators.required, Validators.email]);
password = new FormControl('');
getErrorMessage() {
if (this.email.hasError('required')) {
return 'You must enter a value';
}
return this.email.hasError('email') ? 'Not a valid email' : '';
}
ngOnInit() {
}
......@@ -22,7 +36,7 @@ export class LoginComponent implements OnInit {
login(email: string, password: string) {
this.authService.login(email, password).subscribe(
success => this.router.navigate(['boilerplates']),
error => this.error = error
error => this.notifier.notify("warning",(JSON.stringify("You have entered an invalid username or password")))
);
}
......
......@@ -13,7 +13,7 @@
<a routerLink="/add-boilerplate">Add Boilepate</a>
</li>
<li>
<a routerLink="/account">Account Actions</a>
<button mat-menu-item (click)="LogOut()">Log out</button>
</li>
</ul>
</div>
......
import { Component, OnInit, Output, EventEmitter} from '@angular/core';
import { AuthService } from './../../services/auth.service';
@Component({
selector: 'app-header',
......@@ -9,11 +10,15 @@ export class HeaderComponent implements OnInit {
@Output() public sidenavToggle = new EventEmitter();
constructor() { }
constructor(private authService: AuthService){}
ngOnInit(): void {
}
public onToggleSidenav = () => {
this.sidenavToggle.emit();
}
LogOut() {
return this.authService.logout();
}
}
......@@ -3,7 +3,7 @@ import { HttpClient, HttpInterceptor, HttpRequest, HttpHandler, HttpEvent } from
import { CanActivate, Router } from '@angular/router';
import { Observable } from 'rxjs';
import { tap, shareReplay } from 'rxjs/operators';
import { tap, shareReplay, combineAll } from 'rxjs/operators';
import jwtDecode from 'jwt-decode';
import * as moment from 'moment';
......@@ -18,7 +18,7 @@ export class AuthService {
private apiRoot = 'http://155.207.131.19:8000/auth/';
constructor(private http: HttpClient) { }
constructor(private http: HttpClient, private router:Router) { }
private setSession(authResult: any) {
const token = authResult.token;
......@@ -29,7 +29,7 @@ export class AuthService {
localStorage.setItem('expires_at', JSON.stringify(expiresAt.valueOf()));
}
get token(): string {
get_token(): string {
return JSON.parse(localStorage.getItem('currentUser') || '{}');
}
......@@ -48,15 +48,22 @@ export class AuthService {
}
logout() {
const token = localStorage.getItem('token');
this.http.post(
this.apiRoot.concat('logout/'),
{ token: token }
);
localStorage.removeItem('token');
localStorage.removeItem('expires_at');
this.router.navigate(['/login']);
}
refreshToken() {
const token = localStorage.getItem('token');
if (moment().isBetween(this.getExpiration().subtract(1, 'days'), this.getExpiration())) {
return this.http.post(
this.apiRoot.concat('refresh-token/'),
{ token: this.token }
{ token: token }
).pipe(
tap(response => this.setSession(response)),
shareReplay(),
......@@ -66,15 +73,18 @@ export class AuthService {
}
getExpiration() {
const expiration = JSON.parse(localStorage.getItem('expires_at') || '{}');
const expiresAt = JSON.parse(expiration);
try {
const expiration = JSON.parse(localStorage.getItem('expires_at') || '{}');
const expiresAt = JSON.parse(expiration);
return moment(expiresAt);
return moment(expiresAt);
} catch(e){
return moment(0);}
}
isLoggedIn() {
return moment().isBefore(this.getExpiration());
}
return moment().isBefore(this.getExpiration());
}
isLoggedOut() {
return !this.isLoggedIn();
......
......@@ -47,6 +47,7 @@ INSTALLED_APPS = [
# 3rd party apps
"rest_framework",
'corsheaders',
'rest_framework_jwt.blacklist',
# our apps
"reqman.apps.common.apps.CommonConfig",
"reqman.apps.account.apps.AccountConfig",
......
......@@ -17,6 +17,7 @@ from django.contrib import admin
from django.conf import settings
from django.urls import path, include, re_path
from rest_framework_jwt.views import obtain_jwt_token, refresh_jwt_token
from rest_framework_jwt.blacklist.views import BlacklistView
urlpatterns = [
......@@ -24,6 +25,7 @@ urlpatterns = [
path('api-auth/', include('reqman.apps.reqtool.rest_api.urls')),
path('auth/login/', obtain_jwt_token),
path('auth/refresh-token/', refresh_jwt_token),
path("auth/logout/", BlacklistView.as_view({"post": "create"}))
#re_path(r'api/(?P<version>[v1|v2]+)/', include('reqman.apps.reqtool.rest_api.urls')),
#path('api/', include('reqman.apps.reqtool.rest_api.urls'))
]
......
......@@ -67,6 +67,7 @@ rdflib==5.0.0
sparqlwrapper==1.8.5
django-jsonfield==1.4.1
djangorestframework-jwt==1.5.2
drf-jwt==1.17.3
# The following packages are considered to be unsafe in a requirements file:
# setuptools==41.2.0 # via ipdb, ipython
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment