세금계산서 리스트 및 상세
This commit is contained in:
@@ -0,0 +1,29 @@
|
||||
import axios from 'axios';
|
||||
import { API_URL_VAT_RETURN } from '@/shared/api/api-url-vat-return';
|
||||
import { resultify } from '@/shared/lib/resultify';
|
||||
import { CBDCAxiosError } from '@/shared/@types/error';
|
||||
import {
|
||||
VatReturnDetailParams,
|
||||
VatReturnDetailResponse
|
||||
} from '../model/types';
|
||||
import {
|
||||
useMutation,
|
||||
UseMutationOptions
|
||||
} from '@tanstack/react-query';
|
||||
|
||||
export const vatReturnDetail = (params: VatReturnDetailParams) => {
|
||||
return resultify(
|
||||
axios.post<VatReturnDetailResponse>(API_URL_VAT_RETURN.vatReturnDetail(), params),
|
||||
);
|
||||
};
|
||||
|
||||
export const useVatReturnDetailMutation = (options?: UseMutationOptions<VatReturnDetailResponse, CBDCAxiosError, VatReturnDetailParams>) => {
|
||||
const mutation = useMutation<VatReturnDetailResponse, CBDCAxiosError, VatReturnDetailParams>({
|
||||
...options,
|
||||
mutationFn: (params: VatReturnDetailParams) => vatReturnDetail(params),
|
||||
});
|
||||
|
||||
return {
|
||||
...mutation,
|
||||
};
|
||||
};
|
||||
29
src/entities/vat-return/api/use-vat-return-list-mutation.ts
Normal file
29
src/entities/vat-return/api/use-vat-return-list-mutation.ts
Normal file
@@ -0,0 +1,29 @@
|
||||
import axios from 'axios';
|
||||
import { API_URL_VAT_RETURN } from '@/shared/api/api-url-vat-return';
|
||||
import { resultify } from '@/shared/lib/resultify';
|
||||
import { CBDCAxiosError } from '@/shared/@types/error';
|
||||
import {
|
||||
VatReturnListResponse,
|
||||
VatReturnListParams,
|
||||
} from '../model/types';
|
||||
import {
|
||||
useMutation,
|
||||
UseMutationOptions
|
||||
} from '@tanstack/react-query';
|
||||
|
||||
export const vatReturnList = (params: VatReturnListParams) => {
|
||||
return resultify(
|
||||
axios.post<VatReturnListResponse>(API_URL_VAT_RETURN.vatReturnList(), params),
|
||||
);
|
||||
};
|
||||
|
||||
export const useVatReturnListMutation = (options?: UseMutationOptions<VatReturnListResponse, CBDCAxiosError, VatReturnListParams>) => {
|
||||
const mutation = useMutation<VatReturnListResponse, CBDCAxiosError, VatReturnListParams>({
|
||||
...options,
|
||||
mutationFn: (params: VatReturnListParams) => vatReturnList(params),
|
||||
});
|
||||
|
||||
return {
|
||||
...mutation,
|
||||
};
|
||||
};
|
||||
81
src/entities/vat-return/model/types.ts
Normal file
81
src/entities/vat-return/model/types.ts
Normal file
@@ -0,0 +1,81 @@
|
||||
import { DefaulResponsePagination, DefaultRequestPagination } from '@/entities/common/model/types';
|
||||
|
||||
|
||||
export enum VatReturnTabKeys {
|
||||
List = 'List',
|
||||
VatReference = 'VatReference',
|
||||
};
|
||||
export interface VatReturnTabProps {
|
||||
activeTab: VatReturnTabKeys;
|
||||
};
|
||||
export enum VatReturnReceiptType {
|
||||
ALL = 'ALL',
|
||||
RECEIPT = 'RECEIPT',
|
||||
BILL = 'BILL '
|
||||
};
|
||||
export enum VatReturnTargetType {
|
||||
ALL = 'ALL',
|
||||
GENERAL = 'GENERAL',
|
||||
DIFFERENCE_COLLECTION = 'DIFFERENCE_COLLECTION',
|
||||
REFUND_SETTLEMENT = 'REFUND_SETTLEMENT',
|
||||
};
|
||||
|
||||
export interface VatReturnListParams {
|
||||
mid: string;
|
||||
startDate?: string;
|
||||
endDate?: string;
|
||||
receiptType?: VatReturnReceiptType;
|
||||
targetType?: VatReturnTargetType;
|
||||
pagination?: DefaultRequestPagination;
|
||||
};
|
||||
|
||||
|
||||
export interface VatReturnListResponse extends DefaulResponsePagination {
|
||||
content: Array<VatReturnListContent>;
|
||||
};
|
||||
|
||||
export interface VatReturnListContent {
|
||||
id?: number
|
||||
companyName?: string;
|
||||
mid?: string;
|
||||
issueDate?: string;
|
||||
paymentMethod?: string;
|
||||
amount?: number;
|
||||
};
|
||||
|
||||
export interface ListDateGroupProps {
|
||||
date?: string;
|
||||
items?: Array<VatReturnListContent>
|
||||
}
|
||||
export interface ListItemProps {
|
||||
id?: number;
|
||||
companyName?: string;
|
||||
mid?: string;
|
||||
issueDate?: string;
|
||||
paymentMethod?: string;
|
||||
amount?: number;
|
||||
}
|
||||
export interface VatReturnDetailParams {
|
||||
taxInvoiceNumber?: string;
|
||||
};
|
||||
|
||||
export interface VatReturnDetailResponse {
|
||||
id?: number;
|
||||
totalAmount?: number;
|
||||
supplyAmount?: number;
|
||||
vatAmount?: number;
|
||||
mid?: string;
|
||||
targetBusinessStartDate?: string;
|
||||
targetBusinessEndDate?: string;
|
||||
issueDate?: string;
|
||||
subject?: string;
|
||||
targetType?: VatReturnTargetType;
|
||||
receiptType?: VatReturnReceiptType;
|
||||
email?: string;
|
||||
receiverBusinessRegistrationNumber?: string;
|
||||
receiverCompanyName?: string;
|
||||
receiverCeoName?: string;
|
||||
supplierBusinessRegistrationNumber?: string;
|
||||
supplierCompanyName?: string;
|
||||
supplierCeoName?: string;
|
||||
};
|
||||
46
src/entities/vat-return/ui/list-date-group.tsx
Normal file
46
src/entities/vat-return/ui/list-date-group.tsx
Normal file
@@ -0,0 +1,46 @@
|
||||
import moment from 'moment';
|
||||
import 'moment/dist/locale/ko';
|
||||
import { ListDateGroupProps } from '../model/types';
|
||||
import { ListItem } from './list-item';
|
||||
|
||||
export const ListDateGroup = ({
|
||||
date,
|
||||
items
|
||||
}: ListDateGroupProps) => {
|
||||
moment.locale('ko');
|
||||
const getStateDate = () => {
|
||||
let stateDate = moment(date).format('YY.MM');
|
||||
return stateDate;
|
||||
};
|
||||
|
||||
const getListItem = () => {
|
||||
let rs = [];
|
||||
if(!!items && items.length>0){
|
||||
for(let i=0;i<items.length;i++){
|
||||
let key = 'ListItem-'+i;
|
||||
rs.push(
|
||||
<ListItem
|
||||
key={ key }
|
||||
id={ items[i]?.id || 0 }
|
||||
companyName={ items[i]?.companyName || '' }
|
||||
mid={ items[i]?.mid || '' }
|
||||
issueDate={ items[i]?.issueDate || '' }
|
||||
paymentMethod={ items[i]?.paymentMethod || '' }
|
||||
amount={ items[i]?.amount || 0 }
|
||||
></ListItem>
|
||||
)
|
||||
}
|
||||
}
|
||||
|
||||
return rs;
|
||||
};
|
||||
|
||||
return (
|
||||
<>
|
||||
<div className="date-group">
|
||||
<div className="date-header">{ getStateDate() }</div>
|
||||
{ getListItem() }
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
};
|
||||
166
src/entities/vat-return/ui/list-filter.tsx
Normal file
166
src/entities/vat-return/ui/list-filter.tsx
Normal file
@@ -0,0 +1,166 @@
|
||||
import { motion } from 'framer-motion';
|
||||
import { IMAGE_ROOT } from '@/shared/constants/common';
|
||||
import { VatReturnReceiptType, VatReturnTargetType } from '../model/types';
|
||||
import { FilterMotionDuration, FilterMotionStyle, FilterMotionVariants } from '@/entities/common/model/constant';
|
||||
|
||||
export interface ListFilterProps {
|
||||
filterOn: boolean;
|
||||
setFilterOn: (filterOn: boolean) => void;
|
||||
mid: string;
|
||||
startDate: string;
|
||||
endDate: string;
|
||||
receiptType: VatReturnReceiptType;
|
||||
targetType: VatReturnTargetType;
|
||||
setMid: (mid: string) => void;
|
||||
setStartDate: (date: string) => void;
|
||||
setEndDate: (date: string) => void;
|
||||
setReceiptType: (receiptType: VatReturnReceiptType) => void;
|
||||
setTargetType: (targetType: VatReturnTargetType) => void;
|
||||
};
|
||||
|
||||
export const ListFilter = ({
|
||||
filterOn,
|
||||
setFilterOn,
|
||||
mid,
|
||||
startDate,
|
||||
endDate,
|
||||
receiptType,
|
||||
targetType,
|
||||
setMid,
|
||||
setStartDate,
|
||||
setEndDate,
|
||||
setReceiptType,
|
||||
setTargetType
|
||||
}: ListFilterProps) => {
|
||||
const variants = {
|
||||
hidden: { x: '100%' },
|
||||
visible: { x: '0%' },
|
||||
};
|
||||
|
||||
const onClickToClose = () => {
|
||||
setFilterOn(false);
|
||||
};
|
||||
return (
|
||||
<>
|
||||
<motion.div
|
||||
id="fullMenuModal"
|
||||
className="full-menu-modal"
|
||||
initial="hidden"
|
||||
animate={ (filterOn)? 'visible': 'hidden' }
|
||||
variants={ FilterMotionVariants }
|
||||
transition={ FilterMotionDuration }
|
||||
style={ FilterMotionStyle }
|
||||
>
|
||||
<div className="full-menu-container">
|
||||
<div className="full-menu-header">
|
||||
<div className="full-menu-title center">필터</div>
|
||||
<div className="full-menu-actions">
|
||||
<button
|
||||
className="full-menu-close"
|
||||
onClick={ () => onClickToClose() }
|
||||
>
|
||||
<img
|
||||
src={ IMAGE_ROOT + '/ico_close.svg' }
|
||||
alt="닫기"
|
||||
/>
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="option-list pb-120">
|
||||
<div className="opt-field">
|
||||
<div className="opt-label">가맹점</div>
|
||||
<div className="opt-controls">
|
||||
<select className="flex-1">
|
||||
<option>nictest001m</option>
|
||||
</select>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="opt-field mt_top">
|
||||
<div className="opt-label">발행월</div>
|
||||
<div className="opt-controls col below h36">
|
||||
<div className="chip-row">
|
||||
<span className="keyword-tag active">당월</span>
|
||||
<span className="keyword-tag">2개월</span>
|
||||
<span className="keyword-tag">3개월</span>
|
||||
<span className="keyword-tag">직접입력</span>
|
||||
</div>
|
||||
<div className="range-row">
|
||||
<div className="input-wrapper date">
|
||||
<input
|
||||
className="date-input"
|
||||
type="text"
|
||||
placeholder="날짜 선택"
|
||||
value="2025.06.08"
|
||||
readOnly={ true }
|
||||
/>
|
||||
<button
|
||||
className="date-btn"
|
||||
type="button"
|
||||
>
|
||||
<img
|
||||
src={ IMAGE_ROOT + '/ico_date.svg' }
|
||||
alt="날짜 선택"
|
||||
/>
|
||||
</button>
|
||||
</div>
|
||||
<span className="beetween">~</span>
|
||||
<div className="input-wrapper date">
|
||||
<input
|
||||
className="date-input"
|
||||
type="text"
|
||||
placeholder="날짜 선택"
|
||||
value="2025.06.08"
|
||||
readOnly={ true }
|
||||
/>
|
||||
<button
|
||||
className="date-btn"
|
||||
type="button"
|
||||
>
|
||||
<img
|
||||
src={ IMAGE_ROOT + '/ico_date.svg' }
|
||||
alt="날짜 선택"
|
||||
/>
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="opt-field">
|
||||
<div className="opt-label">영수 구분</div>
|
||||
<div className="opt-controls col below h36">
|
||||
<div className="chip-row">
|
||||
<span className="keyword-tag active">전체</span>
|
||||
<span className="keyword-tag">영수</span>
|
||||
<span className="keyword-tag">청구</span>
|
||||
<span
|
||||
className="keyword-tag"
|
||||
style={{ visibility: 'hidden' }}
|
||||
></span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="opt-field">
|
||||
<div className="opt-label">발행 대상</div>
|
||||
<div className="opt-controls col below h36">
|
||||
<div className="chip-row">
|
||||
<span className="keyword-tag active">전체</span>
|
||||
<span className="keyword-tag">일반</span>
|
||||
<span className="keyword-tag">차액정산</span>
|
||||
<span className="keyword-tag">환급정산</span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
<div className="apply-row">
|
||||
<button className="btn-50 btn-blue flex-1">적용</button>
|
||||
</div>
|
||||
</div>
|
||||
</motion.div>
|
||||
</>
|
||||
);
|
||||
};
|
||||
53
src/entities/vat-return/ui/list-item.tsx
Normal file
53
src/entities/vat-return/ui/list-item.tsx
Normal file
@@ -0,0 +1,53 @@
|
||||
import { NumericFormat } from 'react-number-format';
|
||||
import { PATHS } from '@/shared/constants/paths';
|
||||
import { useNavigate } from '@/shared/lib/hooks/use-navigate';
|
||||
import { ListItemProps } from '../model/types';
|
||||
import moment from 'moment';
|
||||
|
||||
export const ListItem = ({
|
||||
id,
|
||||
companyName,
|
||||
mid,
|
||||
issueDate,
|
||||
paymentMethod,
|
||||
amount
|
||||
}: ListItemProps) => {
|
||||
const { navigate } = useNavigate();
|
||||
|
||||
const onClickToNavigate = () => {
|
||||
navigate(PATHS.vatReturn.detail, {
|
||||
state: {
|
||||
taxInvoiceNumber: id
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
return (
|
||||
<>
|
||||
<div
|
||||
className="transaction-item approved"
|
||||
onClick={ () => onClickToNavigate() }
|
||||
>
|
||||
<div className="transaction-status">
|
||||
<div className="status-dot blue"></div>
|
||||
</div>
|
||||
<div className="transaction-content">
|
||||
<div className="transaction-title">{ companyName } ({ mid })</div>
|
||||
<div className="transaction-details">
|
||||
<span>{ moment(issueDate).format('YYYY.MM.DD') }</span>
|
||||
<span className="separator">|</span>
|
||||
<span>{ paymentMethod }</span>
|
||||
</div>
|
||||
</div>
|
||||
<div className="transaction-amount">
|
||||
<NumericFormat
|
||||
value={ amount }
|
||||
thousandSeparator
|
||||
displayType="text"
|
||||
suffix='원'
|
||||
></NumericFormat>
|
||||
</div>
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
};
|
||||
144
src/entities/vat-return/ui/list-wrap.tsx
Normal file
144
src/entities/vat-return/ui/list-wrap.tsx
Normal file
@@ -0,0 +1,144 @@
|
||||
import moment from 'moment';
|
||||
|
||||
import { useEffect, useState } from 'react';
|
||||
import { IMAGE_ROOT } from '@/shared/constants/common';
|
||||
import { ListFilter } from './list-filter';
|
||||
import { SortOptionsBox } from '@/entities/common/ui/sort-options-box';
|
||||
import { SortByKeys } from '@/entities/common/model/types';
|
||||
import { DEFAULT_PAGE_PARAM } from '@/entities/common/model/constant';
|
||||
import {
|
||||
VatReturnListContent,
|
||||
VatReturnListParams,
|
||||
VatReturnReceiptType,
|
||||
VatReturnTargetType
|
||||
} from '../model/types';
|
||||
import { useVatReturnListMutation } from '../api/use-vat-return-list-mutation';
|
||||
import { ListDateGroup } from './list-date-group';
|
||||
|
||||
export const ListWrap = () => {
|
||||
const [filterOn, setFilterOn] = useState<boolean>(false);
|
||||
const [sortBy, setSortBy] = useState<SortByKeys>(SortByKeys.New);
|
||||
const [listItems, setListItems] = useState<Record<string, Array<VatReturnListContent>>>({});
|
||||
const [pageParam, setPageParam] = useState(DEFAULT_PAGE_PARAM);
|
||||
const [mid, setMid] = useState<string>('nictest00m');
|
||||
const [startDate, setStartDate] = useState(moment().subtract(1, 'month').format('YYYY-MM-DD'));
|
||||
const [endDate, setEndDate] = useState(moment().format('YYYY-MM-DD'));
|
||||
const [receiptType, setReceiptType] = useState<VatReturnReceiptType>(VatReturnReceiptType.ALL);
|
||||
const [targetType, setTargetType] = useState<VatReturnTargetType>(VatReturnTargetType.ALL);
|
||||
|
||||
const { mutateAsync: vatReturnList } = useVatReturnListMutation();
|
||||
|
||||
const callList = () => {
|
||||
let params: VatReturnListParams = {
|
||||
mid: mid,
|
||||
startDate: startDate,
|
||||
endDate: endDate,
|
||||
receiptType: receiptType,
|
||||
targetType: targetType,
|
||||
};
|
||||
vatReturnList(params).then((rs) => {
|
||||
setListItems(assembleData(rs.content));
|
||||
});
|
||||
|
||||
};
|
||||
|
||||
const onClickToOpenFIlter = () => {
|
||||
setFilterOn(true);
|
||||
};
|
||||
const onClickToSort = (sort: SortByKeys) => {
|
||||
setSortBy(sort);
|
||||
};
|
||||
|
||||
useEffect(() => {
|
||||
callList();
|
||||
}, []);
|
||||
|
||||
const getListDateGroup = () => {
|
||||
let rs = [];
|
||||
if(Object.keys(listItems).length > 0){
|
||||
for (const [key, value] of Object.entries(listItems)) {
|
||||
rs.push(
|
||||
<ListDateGroup
|
||||
key={ key }
|
||||
date={ key }
|
||||
items={ value }
|
||||
></ListDateGroup>
|
||||
);
|
||||
}
|
||||
}
|
||||
return rs;
|
||||
};
|
||||
|
||||
const assembleData = (content: Array<VatReturnListContent>) => {
|
||||
let data: any = {};
|
||||
if(content && content.length > 0){
|
||||
for(let i=0;i<content?.length;i++){
|
||||
let groupDate = moment(content[i]?.issueDate).format('YYYYMMDD');
|
||||
if(!!groupDate && !data.hasOwnProperty(groupDate)){
|
||||
data[groupDate] = [];
|
||||
}
|
||||
if(!!groupDate && data.hasOwnProperty(groupDate)){
|
||||
data[groupDate].push(content[i]);
|
||||
}
|
||||
}
|
||||
}
|
||||
return data;
|
||||
};
|
||||
return (
|
||||
<>
|
||||
<div className="summary-section pt-30">
|
||||
<div className="credit-controls">
|
||||
<div>
|
||||
<input
|
||||
type="text"
|
||||
className="credit-period"
|
||||
value={moment(startDate).format('YYYY.MM.DD') + '-' + moment(endDate).format('YYYY.MM.DD')}
|
||||
readOnly={ true }
|
||||
/>
|
||||
<button
|
||||
className="filter-btn"
|
||||
onClick={ () => onClickToOpenFIlter() }
|
||||
>
|
||||
<img
|
||||
src={ IMAGE_ROOT + '/ico_setting.svg' }
|
||||
alt="검색옵션"
|
||||
/>
|
||||
</button>
|
||||
</div>
|
||||
<button className="download-btn">
|
||||
<img
|
||||
src={ IMAGE_ROOT + '/ico_download.svg' }
|
||||
alt="다운로드"
|
||||
/>
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
<div className="filter-section mt-10">
|
||||
<SortOptionsBox
|
||||
sortBy={ sortBy }
|
||||
onClickToSort={ onClickToSort }
|
||||
></SortOptionsBox>
|
||||
</div>
|
||||
<div className="transaction-list">
|
||||
{ getListDateGroup() }
|
||||
</div>
|
||||
<div className="apply-row bottom-padding">
|
||||
<button className="btn-50 btn-blue flex-1">수기발행</button>
|
||||
</div>
|
||||
<ListFilter
|
||||
filterOn={ filterOn }
|
||||
setFilterOn={ setFilterOn }
|
||||
mid={ mid }
|
||||
startDate={ startDate }
|
||||
endDate={ endDate }
|
||||
receiptType={ receiptType }
|
||||
targetType={ targetType }
|
||||
setMid={ setMid }
|
||||
setStartDate={ setStartDate }
|
||||
setEndDate={ setEndDate }
|
||||
setReceiptType={ setReceiptType }
|
||||
setTargetType={ setTargetType }
|
||||
></ListFilter>
|
||||
</>
|
||||
);
|
||||
};
|
||||
85
src/entities/vat-return/ui/section/amount-section.tsx
Normal file
85
src/entities/vat-return/ui/section/amount-section.tsx
Normal file
@@ -0,0 +1,85 @@
|
||||
import moment from 'moment';
|
||||
import { VatReturnDetailResponse } from '../../model/types';
|
||||
import { SectionTitleArrow } from '@/entities/common/ui/section-title-arrow';
|
||||
import { NumericFormat } from 'react-number-format';
|
||||
import SlideDown from 'react-slidedown';
|
||||
import 'react-slidedown/lib/slidedown.css';
|
||||
import { useState } from 'react';
|
||||
|
||||
export interface AmountSectionProps {
|
||||
detail: VatReturnDetailResponse;
|
||||
};
|
||||
|
||||
export const AmountSection = ({
|
||||
detail
|
||||
}: AmountSectionProps) => {
|
||||
const [isOpen, setIsOpen] = useState<boolean>(false);
|
||||
|
||||
const openSection = () => {
|
||||
const status = !isOpen;
|
||||
setIsOpen(status);
|
||||
};
|
||||
return (
|
||||
<>
|
||||
<div className="txn-num-group">
|
||||
<div className="txn-amount">
|
||||
<div className="value">
|
||||
<NumericFormat
|
||||
value={ detail.totalAmount }
|
||||
thousandSeparator
|
||||
displayType="text"
|
||||
></NumericFormat>
|
||||
<span className="unit">원</span>
|
||||
</div>
|
||||
<button
|
||||
className="chip-btn"
|
||||
type="button"
|
||||
onClick={ () => openSection() }
|
||||
>
|
||||
<span>금액상세</span> <SectionTitleArrow isOpen={ isOpen }></SectionTitleArrow>
|
||||
</button>
|
||||
</div>
|
||||
<SlideDown className={'my-dropdown-slidedown'}>
|
||||
{ isOpen &&
|
||||
<div className="amount-expand">
|
||||
<ul className="amount-list">
|
||||
<li className="amount-item">
|
||||
<span className="label">· 공급가액</span>
|
||||
<span className="value">
|
||||
<NumericFormat
|
||||
value={ detail.supplyAmount }
|
||||
thousandSeparator
|
||||
displayType="text"
|
||||
suffix='원'
|
||||
></NumericFormat>
|
||||
</span>
|
||||
</li>
|
||||
<li className="amount-item">
|
||||
<span className="label">· VAT</span>
|
||||
<span className="value">
|
||||
<NumericFormat
|
||||
value={ detail.vatAmount }
|
||||
thousandSeparator
|
||||
displayType="text"
|
||||
suffix='원'
|
||||
></NumericFormat>
|
||||
</span>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
}
|
||||
</SlideDown>
|
||||
<div className="txn-mid">
|
||||
<span className="value">{ detail.mid }</span>
|
||||
</div>
|
||||
<div className="txn-mid">
|
||||
<span className="value">{ moment(detail.issueDate).format('YYYY.MM.DD') }</span>
|
||||
</div>
|
||||
<div className="txn-doc">
|
||||
<button className="doc-btn" type="button">세금계산서</button>
|
||||
<button className="doc-btn" type="button">상세자료</button>
|
||||
</div>
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
};
|
||||
49
src/entities/vat-return/ui/section/issue-section.tsx
Normal file
49
src/entities/vat-return/ui/section/issue-section.tsx
Normal file
@@ -0,0 +1,49 @@
|
||||
import moment from 'moment';
|
||||
import { VatReturnDetailResponse } from '../../model/types';
|
||||
|
||||
export interface IssueSectionProps {
|
||||
detail: VatReturnDetailResponse
|
||||
};
|
||||
|
||||
export const IssueSection = ({
|
||||
detail
|
||||
}: IssueSectionProps) => {
|
||||
|
||||
return (
|
||||
<>
|
||||
<div className="txn-section">
|
||||
<div className="section-title">발행 정보</div>
|
||||
<ul className="kv-list">
|
||||
<li className="kv-row">
|
||||
<span className="k">MID</span>
|
||||
<span className="v">{ detail.mid }</span>
|
||||
</li>
|
||||
<li className="kv-row">
|
||||
<span className="k">발행대상일자</span>
|
||||
<span className="v">{ moment(detail.targetBusinessStartDate).format('YYYY.MM.DD') } ~ { moment(detail.targetBusinessEndDate).format('YYYY.MM.DD') }</span>
|
||||
</li>
|
||||
<li className="kv-row">
|
||||
<span className="k">발행일자</span>
|
||||
<span className="v">{ moment(detail.issueDate).format('YYYY.MM.DD') }</span>
|
||||
</li>
|
||||
<li className="kv-row">
|
||||
<span className="k">적요</span>
|
||||
<span className="v">{ detail.subject }</span>
|
||||
</li>
|
||||
<li className="kv-row">
|
||||
<span className="k">발행대상</span>
|
||||
<span className="v">{ detail.targetType }</span>
|
||||
</li>
|
||||
<li className="kv-row">
|
||||
<span className="k">영수구분</span>
|
||||
<span className="v">{ detail.receiptType }</span>
|
||||
</li>
|
||||
<li className="kv-row">
|
||||
<span className="k">Email</span>
|
||||
<span className="v">{ detail.email }</span>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
};
|
||||
32
src/entities/vat-return/ui/section/receiver-section.tsx
Normal file
32
src/entities/vat-return/ui/section/receiver-section.tsx
Normal file
@@ -0,0 +1,32 @@
|
||||
import { VatReturnDetailResponse } from '../../model/types';
|
||||
|
||||
export interface ReceiverSectionProps {
|
||||
detail: VatReturnDetailResponse
|
||||
};
|
||||
|
||||
export const ReceiverSection = ({
|
||||
detail
|
||||
}: ReceiverSectionProps) => {
|
||||
|
||||
return (
|
||||
<>
|
||||
<div className="txn-section">
|
||||
<div className="section-title">공급받는 자 정보</div>
|
||||
</div>
|
||||
<ul className="kv-list">
|
||||
<li className="kv-row">
|
||||
<span className="k">사업자등록번호</span>
|
||||
<span className="v">{ detail.receiverBusinessRegistrationNumber }</span>
|
||||
</li>
|
||||
<li className="kv-row">
|
||||
<span className="k">상호명</span>
|
||||
<span className="v">{ detail.receiverCompanyName }</span>
|
||||
</li>
|
||||
<li className="kv-row">
|
||||
<span className="k">대표자명</span>
|
||||
<span className="v">{ detail.receiverCeoName }</span>
|
||||
</li>
|
||||
</ul>
|
||||
</>
|
||||
);
|
||||
};
|
||||
32
src/entities/vat-return/ui/section/supplier-section.tsx
Normal file
32
src/entities/vat-return/ui/section/supplier-section.tsx
Normal file
@@ -0,0 +1,32 @@
|
||||
import { VatReturnDetailResponse } from '../../model/types';
|
||||
|
||||
export interface SupplierSectionProps {
|
||||
detail: VatReturnDetailResponse
|
||||
};
|
||||
|
||||
export const SupplierSection = ({
|
||||
detail
|
||||
}: SupplierSectionProps) => {
|
||||
|
||||
return (
|
||||
<>
|
||||
<div className="txn-section">
|
||||
<div className="section-title">공급자 정보</div>
|
||||
</div>
|
||||
<ul className="kv-list">
|
||||
<li className="kv-row">
|
||||
<span className="k">사업자등록번호</span>
|
||||
<span className="v">{ detail.supplierBusinessRegistrationNumber }</span>
|
||||
</li>
|
||||
<li className="kv-row">
|
||||
<span className="k">상호명</span>
|
||||
<span className="v">{ detail.supplierCompanyName }</span>
|
||||
</li>
|
||||
<li className="kv-row">
|
||||
<span className="k">대표자명</span>
|
||||
<span className="v">{ detail.supplierCeoName }</span>
|
||||
</li>
|
||||
</ul>
|
||||
</>
|
||||
);
|
||||
};
|
||||
26
src/entities/vat-return/ui/var-reference-req-fail.tsx
Normal file
26
src/entities/vat-return/ui/var-reference-req-fail.tsx
Normal file
@@ -0,0 +1,26 @@
|
||||
export const VatReferenceReqFail = () => {
|
||||
|
||||
return (
|
||||
<>
|
||||
<div className="success-page">
|
||||
<div className="success-body">
|
||||
<div className="error-icon" aria-hidden="true"></div>
|
||||
<h1 className="success-title">
|
||||
<span>부가세 참고 자료</span>
|
||||
<br/>
|
||||
<span>신청 실패하였습니다</span>
|
||||
</h1>
|
||||
<div className="success-result">
|
||||
<p className="result-text align-left position_label">
|
||||
<span>결과 :</span>
|
||||
<span>[9997] 키인가맹점이 아닙니다.<br/>NICEPAY로 문의하세요.</span>
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
<div className="apply-row">
|
||||
<button className="btn-50 btn-blue flex-1">확인</button>
|
||||
</div>
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
};
|
||||
29
src/entities/vat-return/ui/vat-reference-req-success.tsx
Normal file
29
src/entities/vat-return/ui/vat-reference-req-success.tsx
Normal file
@@ -0,0 +1,29 @@
|
||||
export const VatReferenceReqSuccess = () => {
|
||||
|
||||
return (
|
||||
<>
|
||||
<div className="success-page">
|
||||
<div className="success-body">
|
||||
<div className="success-icon" aria-hidden="true"></div>
|
||||
<h1 className="success-title">
|
||||
<span>부가세 참고 자료</span>
|
||||
<br/>
|
||||
<span>신청이 완료되었습니다.</span>
|
||||
</h1>
|
||||
<p className="success-subtitle">파일은 선택한 수령 방법으로 제공됩니다.</p>
|
||||
<div className="success-result">
|
||||
<p className="result-text">
|
||||
<span>신청일 :</span> <span>2025.06.04</span>
|
||||
<br/>
|
||||
<span>메일주소 :</span> <span>TEST@NICEPAY.CO.KR</span>
|
||||
</p>
|
||||
</div>
|
||||
<p className="success-note dot">참고용 자료이므로 반드시 내부 회계자료 등과<br/>비교 후 사용해 주세요.</p>
|
||||
</div>
|
||||
<div className="apply-row">
|
||||
<button className="btn-50 btn-blue flex-1">확인</button>
|
||||
</div>
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
};
|
||||
8
src/entities/vat-return/ui/vat-reference-wrap.tsx
Normal file
8
src/entities/vat-return/ui/vat-reference-wrap.tsx
Normal file
@@ -0,0 +1,8 @@
|
||||
export const VatReferenceWrap = () => {
|
||||
|
||||
return (
|
||||
<>
|
||||
|
||||
</>
|
||||
)
|
||||
};
|
||||
37
src/entities/vat-return/ui/vat-return-tab.tsx
Normal file
37
src/entities/vat-return/ui/vat-return-tab.tsx
Normal file
@@ -0,0 +1,37 @@
|
||||
import { PATHS } from '@/shared/constants/paths';
|
||||
import { useNavigate } from '@/shared/lib/hooks/use-navigate';
|
||||
import {
|
||||
VatReturnTabKeys,
|
||||
VatReturnTabProps
|
||||
} from '../model/types';
|
||||
|
||||
export const VatReturnTab = ({
|
||||
activeTab
|
||||
}: VatReturnTabProps) => {
|
||||
const { navigate } = useNavigate();
|
||||
|
||||
const onClickToNavigation = (tab: VatReturnTabKeys) => {
|
||||
if(activeTab !== tab){
|
||||
if(tab === VatReturnTabKeys.List){
|
||||
navigate(PATHS.vatReturn.list);
|
||||
}
|
||||
else if(tab === VatReturnTabKeys.VatReference){
|
||||
navigate(PATHS.vatReturn.vatReference);
|
||||
}
|
||||
}
|
||||
};
|
||||
return(
|
||||
<>
|
||||
<div className="subTab">
|
||||
<button
|
||||
className={`subtab-btn ${(activeTab === VatReturnTabKeys.List)? 'active': ''}` }
|
||||
onClick={ () => onClickToNavigation(VatReturnTabKeys.List) }
|
||||
>세금 계산서</button>
|
||||
<button
|
||||
className={`subtab-btn ${(activeTab === VatReturnTabKeys.VatReference)? 'active': ''}` }
|
||||
onClick={ () => onClickToNavigation(VatReturnTabKeys.VatReference) }
|
||||
>부가세 참고</button>
|
||||
</div>
|
||||
</>
|
||||
);
|
||||
};
|
||||
Reference in New Issue
Block a user