Deployment 24.4

- Edit Category
- Verify oobCode before reset pass
- Change invoice -> account, delete account in User
This commit is contained in:
Nguyen Ha Khue
2023-04-24 17:01:16 +07:00
parent 2bcc84f3ff
commit fe41791608
22 changed files with 328 additions and 175 deletions
+2 -3
View File
@@ -17,7 +17,7 @@ import { MenusModule } from './components/menus/menus.module';
import { VendorsModule } from './components/vendors/vendors.module';
import { UsersModule } from './components/users/users.module';
import { LocalizationModule } from './components/localization/localization.module';
import { InvoiceModule } from './components/invoice/invoice.module';
import { AccountModule } from './components/account/account.module';
import { SettingModule } from './components/setting/setting.module';
import { ReportsModule } from './components/reports/reports.module';
import { AuthModule } from './components/auth/auth.module';
@@ -28,7 +28,6 @@ import { AngularFireModule } from "@angular/fire/compat";
import { environment } from "../environments/environment";
import { FirebaseService } from "./shared/service/firebase.service";
import { AuthInterceptor } from "./shared/inceptor/auth-interceptor";
import { NgImageSliderModule } from 'ng-image-slider'
@NgModule({
declarations: [
@@ -39,7 +38,7 @@ import { NgImageSliderModule } from 'ng-image-slider'
BrowserModule.withServerTransition({ appId: 'serverApp' }),
AppRoutingModule,
DashboardModule,
InvoiceModule,
AccountModule,
SettingModule,
ReportsModule,
AuthModule,
@@ -1,15 +1,17 @@
import { NgModule } from '@angular/core';
import { Routes, RouterModule } from '@angular/router';
import { InvoiceComponent } from './invoice.component';
import { AccountComponent } from './account.component';
import { AdminGuard } from 'src/app/shared/guard/admin-guard.service';
const routes: Routes = [
{
path: '',
component: InvoiceComponent,
canActivate: [AdminGuard],
component: AccountComponent,
data: {
title: "Invoice",
breadcrumb: "Invoice"
title: "Tài khoản",
breadcrumb: "Danh sách"
}
},
];
@@ -0,0 +1,105 @@
<!-- Container-fluid starts-->
<div class="container-fluid">
<div class="card">
<!-- <div class="card-header">
<h5>User Details</h5>
</div> -->
<div class="card-body">
<div class="btn-popup pull-left">
<input [(ngModel)]="searchName" (change)="searchUser()" class="form-control" type="text"
placeholder="Tìm kiếm" />
</div>
<div id="batchDelete" class="category-table custom-datatable transcation-datatable user-image">
<div class="table-responsive" *ngIf="users.length">
<table class="table table-striped">
<thead>
<tr>
<th scope="col">#</th>
<th scope="col">Ảnh đại diện</th>
<th scope="col"><a (click)="onSort('fullName')">Họ và tên</a></th>
<th scope="col"><a (click)="onSort('email')">Email</a></th>
<th scope="col"><a (click)="onSort('phoneNumber')">Số điện thoại</a></th>
<th scope="col">Vai trò</th>
<th scope="col"></th>
</tr>
</thead>
<tbody>
<tr *ngFor="let user of users; let i = index">
<th>{{i + 1}}</th>
<td scope="row">
<img [src]="user.imageUrl" class="imgTable" style="width: 20px">
</td>
<td>
{{user.fullName}}
</td>
<td>{{user.email}}</td>
<td>{{user.phoneNumber}}</td>
<td>
<a *ngIf="user.role.roleName == 'ROLE_ADMIN'">Quản trị viên</a>
<a *ngIf="user.role.roleName == 'ROLE_USER'">Người dùng</a>
<a *ngIf="user.role.roleName == 'ROLE_SHOP'">Người bán hàng</a>
<a *ngIf="user.role.roleName == 'ROLE_SHIPPER'">Shipper</a>
</td>
<td>
<a style="cursor: pointer" href="javascript:void(0)"><i
class='fa fa-edit f-12'></i></a>&nbsp;
<a style="cursor: pointer" (click)="openModal(user, confirmDelete)"><i
class="fa fa-trash-o"></i></a>
</td>
</tr>
</tbody>
</table>
<!-- Pagination -->
<div class="d-flex justify-content-center p-2">
<select [(ngModel)]="role" class="form-select" style="width: auto" name="pageSize"
(change)="listAllUsers()">
<option [selected]="true" [ngValue]="'ALL'">Tất cả</option>
<option [ngValue]="'ROLE_ADMIN'">Quản trị viên</option>
<option [value]="'ROLE_USER'" [ngValue]="'ROLE_USER'">Người dùng</option>
<option [ngValue]="'ROLE_SHOP'">Người bán hàng</option>
<option [ngValue]="'ROLE_SHIPPER'">Shipper</option>
</select>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
<ngb-pagination [(page)]="thePageNumber" [pageSize]="thePageSize"
[collectionSize]="theTotalElements" [maxSize]="5" (pageChange)="listAllUsers()">
</ngb-pagination>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
<select [(ngModel)]="thePageSize" class="form-select" style="width: auto" name="pageSize"
(change)="listAllUsers()">
<option [value]="10" [selected]="true" [ngValue]="10">10 tài khoản / trang</option>
<option [ngValue]="20">20 tài khoản / trang</option>
<option [ngValue]="30">30 tài khoản / trang</option>
</select>
</div>
</div>
<div class="table-responsive" *ngIf="!users.length">
<div class="d-flex justify-content-center p-2">
<img src="../../../../assets/images/error/no-user.png" alt="">
</div>
<div class="d-flex justify-content-center p-2">
<h4 style="color: #FF8084;">Không tìm thấy tài khoản</h4>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- Container-fluid Ends-->
<ng-template #confirmDelete>
<div class="modal-body text-center">
<h5 class="text-dark font-weight-bold mb-4">Bạn chắc chắn muốn xoá người dùng này ?</h5>
<button type="button" class="btn btn-primary" (click)="confirmDeleted(deleteSuccess)">Tiếp
tục</button>&nbsp;&nbsp;
<button type="button" class="btn btn-secondary" (click)="closeLayer1()">Quay lại</button>
</div>
</ng-template>
<ng-template #deleteSuccess>
<div class="modal-body text-center">
<h5 class="text-dark font-weight-bold mb-4">Xoá người dùng thành công</h5>
<button type="button" class="btn btn-primary" (click)="closeLayer1()">Tiếp tục</button>
</div>
</ng-template>
@@ -0,0 +1,110 @@
import { DecimalPipe } from '@angular/common';
import { Component, OnInit, TemplateRef } from '@angular/core';
import { Observable } from 'rxjs';
import { TableService } from 'src/app/shared/service/table.service';
import { BsModalRef, BsModalService } from 'ngx-bootstrap/modal';
import { User } from 'src/app/shared/tables/user';
import { UserService } from 'src/app/shared/service/user.service';
import { FormBuilder } from '@angular/forms';
import { FirebaseService } from 'src/app/shared/service/firebase.service';
@Component({
selector: 'app-invoice',
templateUrl: './account.component.html',
styleUrls: ['./account.component.scss'],
providers: [TableService, DecimalPipe]
})
export class AccountComponent implements OnInit {
users: User[] = [];
userDel: User
searchName: string = '';
//Pagination Properties
role: string = 'ALL'
thePageNumber = 1;
thePageSize = 10;
sortBy = 'id';
sortDir = 'asc';
theTotalElements = 0;
isSearch: boolean = false;
constructor(
private userService: UserService,
private formBuilder: FormBuilder,
private firebaseService: FirebaseService,
private modalService: BsModalService) {
}
ngOnInit() {
this.listAllUsers()
}
listAllUsers() {
if (this.role != 'ALL') {
this.userService.getAllUsersByRole(this.role, this.thePageNumber - 1, this.thePageSize, this.sortBy, this.sortDir).subscribe(this.processResult());
}
else {
this.userService.getAllUsers(this.thePageNumber - 1, this.thePageSize, this.sortBy, this.sortDir).subscribe(this.processResult());
}
}
searchUser() {
if (this.searchName.trim() !== '') {
if (this.role != 'ALL') {
this.userService.getAllUsersByRoleAndEmailOrPhoneNumber(this.searchName, this.role, this.thePageNumber - 1, this.thePageSize, this.sortBy, this.sortDir).subscribe(this.processResult());
}
else {
this.userService.getAllUsersByEmailOrPhoneNumber(this.searchName, this.thePageNumber - 1, this.thePageSize, this.sortBy, this.sortDir).subscribe(this.processResult());
}
}
else {
this.listAllUsers();
}
}
processResult() {
return (data: any) => {
this.users = data.users;
this.thePageNumber = data.page.pageNo + 1;
this.thePageSize = data.page.pageSize;
this.theTotalElements = data.page.totalElements;
}
}
onSort(sortItem: string) {
if (this.sortDir == 'asc') {
this.sortBy = sortItem;
this.sortDir = 'desc';
}
else {
this.sortDir = 'asc'
}
this.listAllUsers();
}
//Modal
layer1: BsModalRef;
openModal(user: User, template: TemplateRef<any>) {
this.userDel = user;
this.layer1 = this.modalService.show(template, { class: 'modal-sm' });
}
confirmDeleted(success: TemplateRef<any>) {
this.userService.deleteUserById(this.userDel.id).subscribe();
this.firebaseService.deleteUserByEmail(this.userDel.email).subscribe(() => {
this.listAllUsers();
this.layer1.hide();
this.layer1 = this.modalService.show(success, { class: 'modal-sm' });
});
}
closeLayer1() {
this.layer1.hide();
}
}
@@ -1,18 +1,21 @@
import { NgModule } from '@angular/core';
import { CommonModule } from '@angular/common';
import { InvoiceRoutingModule } from './invoice-routing.module';
import { InvoiceComponent } from './invoice.component';
import { InvoiceRoutingModule } from './account-routing.module';
import { AccountComponent } from './account.component';
import { SharedModule } from 'src/app/shared/shared.module';
import { NgbModule } from '@ng-bootstrap/ng-bootstrap';
import { FormsModule, ReactiveFormsModule } from '@angular/forms';
@NgModule({
declarations: [InvoiceComponent],
declarations: [AccountComponent],
imports: [
CommonModule,
InvoiceRoutingModule,
FormsModule,
SharedModule,
ReactiveFormsModule,
NgbModule
]
})
export class InvoiceModule { }
export class AccountModule { }
@@ -4,6 +4,8 @@ import { FirebaseService } from "../../../shared/service/firebase.service";
import { ActivatedRoute, Router } from '@angular/router';
import { Validation } from 'src/app/constants/Validation';
import { BsModalRef, BsModalService } from 'ngx-bootstrap/modal';
import { AngularFireAuth } from '@angular/fire/compat/auth';
import { error } from 'console';
@Component({
selector: "app-reset-password",
@@ -27,6 +29,7 @@ export class ResetPasswordComponent {
private formBuilder: UntypedFormBuilder,
private activatedRoute: ActivatedRoute,
private firebaseService: FirebaseService,
private firebaseAuth: AngularFireAuth,
private modalService: BsModalService,
private router: Router
) {
@@ -57,6 +60,13 @@ export class ResetPasswordComponent {
//Get Token from link
this.oobCode = this.activatedRoute.snapshot.queryParamMap.get('oobCode');
this.action = this.activatedRoute.snapshot.queryParamMap.get('mode');
this.resetPasswordForm = this.formBuilder.group({
password: new FormControl("", [Validators.required, Validators.pattern(Validation.Regex.Password)]),
confirmPassword: new FormControl("", [Validators.required, Validators.pattern(Validation.Regex.Password)]),
},
{
validator: this.ConfirmedValidator("password", "confirmPassword"),
})
if (this.action == 'verifyEmail') {
this.firebaseService.confirmVerifyEmail(this.oobCode)
@@ -64,13 +74,11 @@ export class ResetPasswordComponent {
}
if (this.oobCode) {
this.resetPasswordForm = this.formBuilder.group({
password: new FormControl("", [Validators.required, Validators.pattern(Validation.Regex.Password)]),
confirmPassword: new FormControl("", [Validators.required, Validators.pattern(Validation.Regex.Password)]),
},
{
validator: this.ConfirmedValidator("password", "confirmPassword"),
})
this.firebaseAuth.checkActionCode(this.oobCode).then((info) => {
}).catch(error => {
this.router.navigate(['/auth/forbidden']);
})
}
else {
this.router.navigate(['/auth/forbidden']);
@@ -176,8 +176,15 @@
<ng-template #sendMailCompleted>
<div class="modal-body text-center">
<p>Đã gửi đường dẫn thay đổi mật khẩu đến email của bạn</p>
<p>Vui lòng kiểm tra hòm thư</p>
<button type="button" class="btn btn-primary" (click)="gmail()">Gmail</button>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
<button type="button" class="btn btn-secondary" (click)="closeLayer1()">Đóng</button>
<p>Vui lòng kiểm tra hòm thư của bạn</p>
<!-- <button type="button" class="btn btn-primary" (click)="gmail()">Gmail</button>&nbsp;&nbsp;&nbsp;&nbsp;&nbsp; -->
<button type="button" class="btn btn-primary" (click)="closeLayer1()">Đóng</button>
</div>
</ng-template>
<ng-template #emailNotExisted>
<div class="modal-body text-center">
<p>Tài khoản này không tồn tại trong hệ thống. Vui lòng kiểm tra lại địa chỉ email</p>
<button type="button" class="btn btn-primary" (click)="closeLayer1()">Đóng</button>
</div>
</ng-template>
@@ -4,6 +4,7 @@ import { FirebaseService } from "../../../shared/service/firebase.service";
import { Router } from "@angular/router";
import { Validation } from "src/app/constants/Validation";
import { BsModalRef, BsModalService } from "ngx-bootstrap/modal";
import { AuthService } from "src/app/shared/service/auth.service";
@Component({
selector: "app-send-email",
@@ -19,10 +20,12 @@ export class SendEmailComponent {
public active = 1;
@ViewChild('sendMailCompleted') sendMailCompleted: TemplateRef<any>
@ViewChild('emailNotExisted') emailNotExisted: TemplateRef<any>
constructor(
private formBuilder: UntypedFormBuilder,
private firebaseService: FirebaseService,
private authService: AuthService,
private modalService: BsModalService,
private router: Router
) {
@@ -62,8 +65,19 @@ export class SendEmailComponent {
this.sendEmailForm.markAllAsTouched();
return;
}
this.firebaseService.resetPassword(this.email.value);
this.layer1 = this.modalService.show(this.sendMailCompleted, { class: "modal-sm" });
this.authService.checkEmailInDB(this.email.value).subscribe({
next: (response) => {
if (response.isTrue == true) {
this.firebaseService.resetPassword(this.email.value);
this.layer1 = this.modalService.show(this.sendMailCompleted, { class: "modal-sm" });
}
else {
this.layer1 = this.modalService.show(this.emailNotExisted, { class: "modal-sm" })
}
}
})
}
gmail() {
@@ -1,57 +0,0 @@
<!-- Container-fluid starts-->
<div class="container-fluid">
<div class="row">
<div class="col-sm-12">
<div class="card">
<div class="card-header">
<h5>Invoice List</h5>
</div>
<div class="card-body">
<div id="batchDelete" class="custom-datatable">
<div class="table-responsive">
<table class="table table-striped">
<thead>
<tr>
<th scope="col" sortable="no">No</th>
<th scope="col" sortable="invoice">Invoice</th>
<th scope="col" sortable="name" >Date</th>
<th scope="col" sortable="name" >Shipping</th>
<th scope="col" sortable="name" >Amount</th>
<th scope="col" sortable="name" >Tax</th>
<th scope="col" sortable="name" >Total</th>
<th scope="col" sortable="name" >Actions</th>
</tr>
</thead>
<tbody>
<tr *ngFor="let item of tableItem$ | async ">
<td scope="row">
<span>{{item.no}}</span>
</td>
<td>
{{item.invoice}}
</td>
<td>{{item.date}}</td>
<td>{{item.shipping}}</td>
<td>{{item.amount}}</td>
<td>{{item.tax}}</td>
<td>{{item.total}}</td>
<td>
<a href="javascript:void(0)"><i class='fa fa-edit f-12'></i></a>&nbsp;
<a href="javascript:void(0)"><i class="fa fa-trash-o"></i></a>
</td>
</tr>
</tbody>
</table>
<div class="d-flex justify-content-center p-2">
<ngb-pagination
[collectionSize]="(total$ | async)!" [(page)]="service.page" [pageSize]="service.pageSize">
</ngb-pagination>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
</div>
<!-- Container-fluid Ends-->
@@ -1,45 +0,0 @@
import { DecimalPipe } from '@angular/common';
import { Component, OnInit, QueryList, ViewChildren } from '@angular/core';
import { Observable } from 'rxjs';
import { NgbdSortableHeader, SortEvent } from 'src/app/shared/directives/NgbdSortableHeader';
import { TableService } from 'src/app/shared/service/table.service';
import { InvoiceDB, INVOICEDB } from '../../shared/tables/invoice';
@Component({
selector: 'app-invoice',
templateUrl: './invoice.component.html',
styleUrls: ['./invoice.component.scss'],
providers: [TableService, DecimalPipe]
})
export class InvoiceComponent implements OnInit {
public tableItem$: Observable<InvoiceDB[]>;
public searchText;
total$: Observable<number>;
constructor(public service: TableService) {
this.tableItem$ = service.tableItem$;
this.total$ = service.total$;
this.service.setUserData(INVOICEDB)
}
@ViewChildren(NgbdSortableHeader) headers: QueryList<NgbdSortableHeader>;
onSort({ column, direction }: SortEvent) {
// resetting other headers
this.headers.forEach((header) => {
if (header.sortable !== column) {
header.direction = '';
}
});
this.service.sortColumn = column;
this.service.sortDirection = direction;
}
ngOnInit() {
}
}
@@ -3,7 +3,7 @@
<div class="col-sm-12">
<div class="card">
<div class="card-header">
<h5>Product Lists</h5>
<h5>Danh sách sản phẩm</h5>
</div>
<div class="card-body">
<div id="batchDelete" class="custom-datatable">
@@ -36,11 +36,12 @@
</tr>
</tbody>
</table>
<div class="d-flex justify-content-between p-2">
<div class="d-flex justify-content-center p-2">
<ngb-pagination [collectionSize]="theTotalElements" [(page)]="thePageNumber"
[maxSize]="5" [pageSize]="thePageSize" [rotate]="true" [boundaryLinks]="true"
(pageChange)="getProductByCategories()">
</ngb-pagination>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;
<select class="form-select" style="width: auto" name="pageSize"
(change)="getProductByCategories()" [(ngModel)]="thePageSize">
<option [value]="10" [selected]="true" [ngValue]="10">10 sản phẩm / trang</option>
@@ -10,6 +10,7 @@ import { ProductService } from 'src/app/shared/service/product.service';
})
export class CategoryDetailComponent implements OnInit {
products = [];
catName: string = '';
categories: number[] = [];
//Pagination Properties
@@ -28,7 +29,7 @@ export class CategoryDetailComponent implements OnInit {
}
getProductByCategories() {
const id = +this.route.snapshot.paramMap.get('id')
const id = +this.route.snapshot.paramMap.get('id');
this.categories.push(id)
this.productService.getProductsByCategoryIds(this.categories, this.thePageNumber - 1, this.thePageSize).subscribe(
this.processResult()
@@ -41,6 +42,7 @@ export class CategoryDetailComponent implements OnInit {
this.thePageNumber = data.page.pageNo + 1;
this.thePageSize = data.page.pageSize;
this.theTotalElements = data.page.totalElements;
this.catName = this.products[0].categories.name;
}
}
}
@@ -7,29 +7,15 @@
<h5>Thể loại sản phẩm</h5>
</div>
<div class="card-body">
<!-- <div class="btn-popup pull-right">-->
<!-- <button-->
<!-- type="button" class="btn btn-primary" data-toggle="modal" data-original-title="test"-->
<!-- data-target="#exampleModal" (click)="open(content)">Add Category-->
<!-- </button>-->
<!-- </div>-->
<div id="batchDelete" class="category-table custom-datatable">
<div class="table-responsive">
<!-- <form>
<div class="mb-3 row">
<label for="table-complete-search" class="col-xs-3 col-sm-auto col-form-label">Full text search:</label>
<div class="col-xs-3 col-sm-auto">
<input id="table-complete-search" type="text" class="form-control" name="searchTerm" [(ngModel)]="searchText" autocomplete="off">
</div>
</div>
</form> -->
<table class="table table-striped">
<thead>
<tr>
<th scope="col">#</th>
<th scope="col">STT</th>
<th class="d-flex justify-content-center align-items-center" scope="col">
<span>Ảnh</span></th>
<span>Ảnh</span>
</th>
<th scope="col">Tên loại</th>
<th scope="col"></th>
</tr>
@@ -40,7 +26,8 @@
<div>{{ i + 1 }}</div>
</th>
<td class="d-flex justify-content-center align-items-center ">
<img [src]="category.imageUrl" class="imgTable" style="width: 20px"
<img [src]="category.imageUrl" class="imgTable"
style="width: 20px; cursor: pointer;"
[routerLink]="['/products','category',category.id]">
</td>
<td>{{ category.name }}</td>
@@ -48,8 +35,7 @@
<a style="cursor: pointer;"
[routerLink]="['/products','category',category.id]"><i
style="color: lightseagreen;" class='fa fa-eye f-12'></i></a>&nbsp;
<a style="cursor: pointer;"
(click)="editCategory(productCategoryTemplate, category)"><i
<a style="cursor: pointer;" (click)="editCategory(category)"><i
class='fa fa-edit f-12'></i></a>&nbsp;
<a style="cursor: pointer;"
(click)="openModal(deleteCategory, category.id)"><i
@@ -72,7 +58,7 @@
<!-- Container-fluid Ends-->
<ng-template #productCategoryTemplate>
<form formGroup="categoryForm">
<form [formGroup]="categoryForm">
<div class="modal-header">
<h5 class="modal-title f-w-600" id="exampleModalLabel">Edit Product Category</h5>
<button type="button" class="close" aria-label="Close" (click)="decline()">
@@ -83,13 +69,13 @@
<div>
<div class="form-group">
<label for="validationCustom01" class="mb-1">Tên loại :</label>
<input class="form-control" id="validationCustom01" type="text"
[formControl]="categoryForm.controls['categoryName']" required>
<input class="form-control" id="validationCustom01" type="text" formControlName="categoryName"
required>
</div>
<div class="form-group mb-0">
<label for="image" class="mb-1">Ảnh :</label>
<input class="form-control" id="image" [formControl]="categoryForm.controls['categoryImage']"
type="file" autocomplete="off" (change)="onFileSelected($event)">
<input class="form-control" id="image" type="file" autocomplete="off"
(change)="onFileSelected($event)">
</div>
</div>
<div class="modal-footer">
@@ -1,4 +1,4 @@
import { Component, OnInit, TemplateRef } from '@angular/core';
import { Component, OnInit, TemplateRef, ViewChild } from '@angular/core';
import { DecimalPipe } from '@angular/common';
import { TableService } from 'src/app/shared/service/table.service';
import { CategoryService } from 'src/app/shared/service/category.service';
@@ -7,7 +7,6 @@ import { FormBuilder, FormGroup } from '@angular/forms';
import { Category } from 'src/app/shared/tables/category';
import { AngularFireStorage } from '@angular/fire/compat/storage';
import { finalize, Observable } from 'rxjs';
import { resolve } from 'path';
import { Router } from '@angular/router';
@Component({
@@ -24,11 +23,15 @@ export class CategoryComponent implements OnInit {
categories: Category[];
categoryId: number;
isChanged: boolean = false;
//File
imageFile: File;
imageUrl;
downloadURL: Observable<string>;
@ViewChild('productCategoryTemplate') editCategoryModal: TemplateRef<any>
constructor(
private categoryService: CategoryService,
private modalService: BsModalService,
@@ -36,8 +39,7 @@ export class CategoryComponent implements OnInit {
private storage: AngularFireStorage,
private router: Router) {
this.categoryForm = this.formBuilder.group({
categoryName: [''],
categoryImage: ['']
categoryName: ['']
})
}
@@ -71,19 +73,30 @@ export class CategoryComponent implements OnInit {
this.modalRef.hide();
}
editCategory(template: TemplateRef<any>, category: Category) {
editCategory(category: Category) {
this.categoryId = category.id
this.imageUrl = category.imageUrl;
this.categoryForm.patchValue({
categoryName: category.name,
categoryImage: category.imageUrl
categoryName: category?.name
})
this.modalRef = this.modalService.show(template, { class: 'modal-md' });
this.modalRef = this.modalService.show(this.editCategoryModal, { class: 'modal-md' });
}
onSaveCategory(event, template: TemplateRef<any>) {
this.uploadImage().then(() => {
if (this.isChanged == true) {
this.uploadImage().then(() => {
const category = new Category()
category.name = this.categoryName
category.imageUrl = this.imageUrl;
this.categoryService.editCategoryById(this.categoryId, category).subscribe()
this.modalRef.hide();
this.modalRef = this.modalService.show(template, { class: 'modal-md' });
})
}
else {
const category = new Category()
category.name = this.categoryName
category.imageUrl = this.imageUrl;
@@ -91,7 +104,8 @@ export class CategoryComponent implements OnInit {
this.categoryService.editCategoryById(this.categoryId, category).subscribe()
this.modalRef.hide();
this.modalRef = this.modalService.show(template, { class: 'modal-md' });
})
}
}
success(): void {
@@ -101,6 +115,7 @@ export class CategoryComponent implements OnInit {
}
onFileSelected(event) {
this.isChanged = true;
this.imageFile = event.target.files[0];
}
@@ -220,7 +220,7 @@
<label for="validationCustom03" class="mb-0">Id shop</label>
</div>
<div class="col-xl-8 col-sm-7">
<input class="form-control" id="validationCustom03"
<input readonly class="form-control" id="validationCustom03"
[formControl]="editProductForm.controls['shopId']">
<div *ngIf="productShopId?.invalid && (productShopId?.dirty || productShopId?.touched)"
class="alert alert-danger mt-1">
@@ -39,8 +39,8 @@ const routes: Routes = [
canActivate: [AdminGuard],
component: CategoryDetailComponent,
data: {
title: "Danh sách sản phẩm",
breadcrumb: "Thể loại"
title: "Chi tiết thể loại",
breadcrumb: "Chi tiết"
}
},
{
-1
View File
@@ -22,7 +22,6 @@ import { ListAccountComponent } from './list-account/list-account.component';
SharedModule,
FormsModule,
ReactiveFormsModule,
ReactiveFormsModule,
UsersRoutingModule
]
})
+2 -2
View File
@@ -84,8 +84,8 @@ export const content: Routes = [
}
},
{
path: 'invoice',
loadChildren: () => import('../../components/invoice/invoice.module').then(m => m.InvoiceModule),
path: 'account',
loadChildren: () => import('../../components/account/account.module').then(m => m.AccountModule),
data: {
breadcrumb: "Hoá đơn"
}
+4
View File
@@ -35,4 +35,8 @@ export class AuthService {
checkEmailOrPhoneNumberExist(userDto: User) {
return this.httpClient.post<StringBoolObject>(this.baseUrl + `/check`, userDto);
}
checkEmailInDB(email: string) {
return this.httpClient.get<StringBoolObject>(this.baseUrl + `/check-email?email=${email}`)
}
}
+5 -6
View File
@@ -112,11 +112,13 @@ export class NavService {
// { path: '/menus/create-menu', title: 'Create Menu', type: 'link' },
// ]
// },
{
title: 'Tài khoản', path: '/account', icon: 'user', type: 'link', active: false
},
{
title: 'Người dùng', icon: 'user-plus', type: 'sub', active: false, children: [
{ path: '/users/list', title: 'Danh sách', type: 'link' },
{ path: '/users/create', title: 'Tạo người dùng', type: 'link' },
{ path: '/users/accounts/list', title: 'Tài khoản', type: 'link' },
{ path: '/users/create', title: 'Tạo người dùng', type: 'link' }
]
},
{
@@ -136,7 +138,7 @@ export class NavService {
{ path: '/utilities/list-address', title: 'Địa chỉ', type: 'link' },
{ path: '/utilities/list-slider', title: 'Slider', type: 'link' }
]
}
},
// {
// title: 'Localization', icon: 'chrome', type: 'sub', children: [
// {path: '/localization/translations', title: 'Translations', type: 'link'},
@@ -148,9 +150,6 @@ export class NavService {
// title: 'Báo cáo', path: '/reports', icon: 'bar-chart', type: 'link', active: false
// },
// {
// title: 'Hoá đơn', path: '/invoice', icon: 'archive', type: 'link', active: false
// },
// {
// title: 'Cài đặt', icon: 'settings', type: 'sub', children: [
// { path: '/settings/profile', title: 'Trang cá nhân', type: 'link' },
// ]
+1
View File
@@ -4,6 +4,7 @@
export const environment = {
production: false,
// foodOrderingBaseApiUrl: 'http://localhost:8080/api',
foodOrderingBaseApiUrl: 'https://foodify-backend-production.up.railway.app/api',
firebaseConfig: {
apiKey: 'AIzaSyAZFFIuXkbgdp2F-Em4CK2z8kVJ2L4p_UU',