Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

refactor(RSS-ECOMM-5_21): implement separate page for addresses #365

Merged
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions src/app/App/model/AppModel.ts
Original file line number Diff line number Diff line change
Expand Up @@ -68,6 +68,12 @@ class AppModel {
);
return new RegistrationPageModel(this.appView.getHTML());
},
[PAGE_ID.USER_ADDRESSES_PAGE]: async (): Promise<Page> => {
const { default: UserAddressesPageModel } = await import(
'@/pages/UserAddressesPage/model/UserAddressesPageModel.ts'
);
return new UserAddressesPageModel(this.appView.getHTML());
},
[PAGE_ID.USER_PROFILE_PAGE]: async (): Promise<Page> => {
const { default: UserProfilePageModel } = await import('@/pages/UserProfilePage/model/UserProfilePageModel.ts');
return new UserProfilePageModel(this.appView.getHTML());
Expand Down
3 changes: 2 additions & 1 deletion src/app/styles/variables.scss
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,8 @@
// fonts
--small-font: 400 0.625rem 'Cerapro', sans-serif; // 10px
--regular-font: 400 0.8125rem 'Cerapro', sans-serif; // 13px
--extra-regular-font: 400 1.5rem 'Cerapro', sans-serif; // 24px
--basic-regular-font: 400 1.125rem 'Cerapro', sans-serif; // 18px
--extra-regular-font: 500 1.5rem 'Cerapro', sans-serif; // 24px
--medium-font: 500 1.25rem 'Cerapro', sans-serif; // 20px
--extra-medium-font: 500 1.875rem 'Cerapro', sans-serif; // 30px
--bold-font: 700 1rem 'Cerapro', sans-serif; // 16px
Expand Down
11 changes: 1 addition & 10 deletions src/entities/UserAddress/model/UserAddressModel.ts
Original file line number Diff line number Diff line change
Expand Up @@ -19,21 +19,13 @@ import { showErrorMessage, showSuccessMessage } from '@/shared/utils/userMessage
import UserAddressView from '../view/UserAddressView.ts';

class UserAddressModel {
private callback: (isDisabled: boolean) => void;

private currentAddress: Address;

private labels: Map<HTMLDivElement, { inactive?: boolean; type: AddressTypeType }>;

private view: UserAddressView;

constructor(
address: Address,
activeTypes: AddressTypeType[],
callback: (isDisabled: boolean) => void,
inactiveTypes?: AddressTypeType[],
) {
this.callback = callback;
constructor(address: Address, activeTypes: AddressTypeType[], inactiveTypes?: AddressTypeType[]) {
this.currentAddress = address;
this.view = new UserAddressView(address, activeTypes, inactiveTypes);
this.labels = this.view.getLabels();
Expand Down Expand Up @@ -87,7 +79,6 @@ class UserAddressModel {
private async labelClickHandler(activeType: AddressTypeType, inactive?: boolean): Promise<void> {
const loader = new LoaderModel(LOADER_SIZE.MEDIUM);
loader.setAbsolutePosition();
this.callback(true);
this.view.toggleState(true);
this.getHTML().append(loader.getHTML());
try {
Expand Down
6 changes: 3 additions & 3 deletions src/entities/UserAddress/view/userAddressView.module.scss
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,9 @@
display: grid;
align-items: center;
border-radius: var(--medium-br);
padding: var(--extra-small-offset);
padding: var(--small-offset);
background: var(--white-tr);
gap: var(--tiny-offset);
gap: var(--extra-small-offset) var(--tiny-offset);
}

.labelsWrapper {
Expand Down Expand Up @@ -114,7 +114,7 @@
.streetNameSpan,
.postalCodeSpan,
.countrySpan {
font: var(--regular-font);
font: var(--basic-regular-font);
letter-spacing: var(--one);
word-break: break-all;
color: var(--steam-green-400);
Expand Down
2 changes: 1 addition & 1 deletion src/features/WishlistButton/view/WishlistButtonView.ts
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ class WishlistButtonView {
});

const svg = document.createElementNS(SVG_DETAILS.SVG_URL, 'svg');
svg.append(createSVGUse(SVG_DETAILS.FILL_HEART));
svg.append(createSVGUse(SVG_DETAILS.HEART));
this.switchToWishListButton.getHTML().append(svg);

return this.switchToWishListButton;
Expand Down
54 changes: 54 additions & 0 deletions src/pages/UserAddressesPage/model/UserAddressesPageModel.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
import type { Page } from '@/shared/types/page.ts';

import RouterModel from '@/app/Router/model/RouterModel.ts';
import getCustomerModel from '@/shared/API/customer/model/CustomerModel.ts';
import getStore from '@/shared/Store/Store.ts';
import { setCurrentPage } from '@/shared/Store/actions.ts';
import { SERVER_MESSAGE_KEYS } from '@/shared/constants/messages.ts';
import { PAGE_ID } from '@/shared/constants/pages.ts';
import createBaseElement from '@/shared/utils/createBaseElement.ts';
import { showErrorMessage } from '@/shared/utils/userMessage.ts';
import UserAddressesModel from '@/widgets/UserAddresses/model/UserAddressesModel.ts';

import UserAddressesPageView from '../view/UserAddressesPageView.ts';

class UserAddressesPageModel implements Page {
private addresses: UserAddressesModel | null = null;

private view: UserAddressesPageView | null = null;

constructor(parent: HTMLDivElement) {
const { isUserLoggedIn } = getStore().getState();
if (!isUserLoggedIn) {
RouterModel.getInstance().navigateTo(PAGE_ID.LOGIN_PAGE);
showErrorMessage(SERVER_MESSAGE_KEYS.NEED_LOGIN);
} else {
this.view = new UserAddressesPageView(parent);
this.init().catch(showErrorMessage);
}
}

private async init(): Promise<void> {
try {
const user = await getCustomerModel().getCurrentUser();
if (user) {
this.addresses = new UserAddressesModel(user);
this.view?.getHTML().append(this.addresses.getHTML());
getStore().dispatch(setCurrentPage(PAGE_ID.USER_ADDRESSES_PAGE));
}
} catch (error) {
showErrorMessage(SERVER_MESSAGE_KEYS.NEED_LOGIN);
}
}

public getHTML(): HTMLDivElement {
if (this.view) {
return this.view.getHTML();
}
return createBaseElement({
tag: 'div',
});
}
}

export default UserAddressesPageModel;
33 changes: 33 additions & 0 deletions src/pages/UserAddressesPage/view/UserAddressesPageView.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,33 @@
import clearOutElement from '@/shared/utils/clearOutElement.ts';
import createBaseElement from '@/shared/utils/createBaseElement.ts';

import styles from './userAddressesPageView.module.scss';

class UserAddressesPageView {
private page: HTMLDivElement;

private parent: HTMLDivElement;

constructor(parent: HTMLDivElement) {
this.parent = parent;
clearOutElement(this.parent);
this.page = this.createHTML();
window.scrollTo(0, 0);
}

private createHTML(): HTMLDivElement {
this.page = createBaseElement({
cssClasses: [styles.userAddressesPage],
tag: 'div',
});

this.parent.append(this.page);

return this.page;
}

public getHTML(): HTMLDivElement {
return this.page;
}
}
export default UserAddressesPageView;
26 changes: 26 additions & 0 deletions src/pages/UserAddressesPage/view/userAddressesPageView.module.scss
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
@import 'src/app/styles/mixins';

.userAddressesPage {
position: relative;
display: block;
margin: 0 auto;
width: 65%;
animation: show 0.2s ease-out forwards;

@media (max-width: 768px) {
margin: 0;
padding: var(--extra-small-offset);
width: 100%;
}
}

@keyframes show {
0% {
opacity: 0;
}

100% {
display: block;
opacity: 1;
}
}
45 changes: 2 additions & 43 deletions src/pages/UserProfilePage/model/UserProfilePageModel.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,19 +3,16 @@ import type { Page } from '@/shared/types/page.ts';
import RouterModel from '@/app/Router/model/RouterModel.ts';
import getCustomerModel from '@/shared/API/customer/model/CustomerModel.ts';
import getStore from '@/shared/Store/Store.ts';
import { setAuthToken, setCurrentPage, switchIsUserLoggedIn } from '@/shared/Store/actions.ts';
import { setCurrentPage } from '@/shared/Store/actions.ts';
import { SERVER_MESSAGE_KEYS } from '@/shared/constants/messages.ts';
import { PAGE_ID } from '@/shared/constants/pages.ts';
import createBaseElement from '@/shared/utils/createBaseElement.ts';
import { showErrorMessage } from '@/shared/utils/userMessage.ts';
import UserAddressesModel from '@/widgets/UserAddresses/model/UserAddressesModel.ts';
import UserInfoModel from '@/widgets/UserInfo/model/UserInfoModel.ts';

import UserProfilePageView from '../view/UserProfilePageView.ts';

class UserProfilePageModel implements Page {
private addresses: UserAddressesModel | null = null;

private userInfo: UserInfoModel | null = null;

private view: UserProfilePageView | null = null;
Expand All @@ -31,57 +28,19 @@ class UserProfilePageModel implements Page {
}
}

private addressesLinkHandler(): void {
this.userInfo?.hide();
this.addresses?.show();
}

private async init(): Promise<void> {
this.setAddressesLinkHandler();
this.setPersonalInfoLinkHandler();
try {
const user = await getCustomerModel().getCurrentUser();

if (user) {
this.userInfo = new UserInfoModel(user);
this.addresses = new UserAddressesModel(user);
this.view?.getUserProfileWrapper().append(this.userInfo.getHTML(), this.addresses.getHTML());
this.setAccountLogoutButtonHandler();
this.view?.getUserProfileWrapper().append(this.userInfo.getHTML());
getStore().dispatch(setCurrentPage(PAGE_ID.USER_PROFILE_PAGE));
}
} catch (error) {
showErrorMessage(SERVER_MESSAGE_KEYS.NEED_LOGIN);
}
}

private logoutHandler(): void {
localStorage.clear();
getStore().dispatch(setAuthToken(null));
getStore().dispatch(switchIsUserLoggedIn(false));
getCustomerModel().logout().catch(showErrorMessage);
RouterModel.getInstance().navigateTo(PAGE_ID.LOGIN_PAGE);
}

private personalInfoLinkHandler(): void {
this.addresses?.hide();
this.userInfo?.show();
}

private setAccountLogoutButtonHandler(): void {
const logoutButton = this.view?.getAccountLogoutButton();
logoutButton?.getHTML().addEventListener('click', () => this.logoutHandler());
}

private setAddressesLinkHandler(): void {
const addressesLink = this.view?.getAddressesLink();
addressesLink?.getHTML().addEventListener('click', () => this.addressesLinkHandler());
}

private setPersonalInfoLinkHandler(): void {
const personalInfoLink = this.view?.getPersonalInfoLink();
personalInfoLink?.getHTML().addEventListener('click', () => this.personalInfoLinkHandler());
}

public getHTML(): HTMLDivElement {
if (this.view) {
return this.view.getHTML();
Expand Down
Loading