Skip to content
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
1 change: 1 addition & 0 deletions .eslintrc.js
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ module.exports = {
'unused-imports/no-unused-imports': 'error',
// emotion css props
'react/no-unknown-property': ['error', { ignore: ['css'] }],
'react/prop-types': 'off',
},
overrides: [
{
Expand Down
2 changes: 0 additions & 2 deletions Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -16,8 +16,6 @@ COPY .nx ./

RUN pnpm install

RUN pnpm add -w sharp

ENV NEXT_TELEMETRY_DISABLED=1

RUN pnpm nextjs:build
Expand Down
50 changes: 49 additions & 1 deletion services/ahhachul.com/src/apis/request/complaint.ts
Original file line number Diff line number Diff line change
@@ -1 +1,49 @@
export {};
import { appendFilesToFormData, createJsonBlob, extractFormData } from '@ahhachul/utils';

import axiosInstance from '@/apis/fetcher';
import type { ApiResponse, CommentList, PaginatedList, WithPostId } from '@/types';
import type {
ComplaintForm,
ComplaintListParams,
ComplaintPost,
ComplaintPostDetail,
} from '@/types/complaint';

export const fetchComplaintList = async (req: ComplaintListParams) => {
const { data } = await axiosInstance.get<ApiResponse<PaginatedList<ComplaintPost>>>(
'/complaint-posts',
{
params: {
...req,
pageSize: 10,
},
},
);
return data;
};

export const createComplaint = async (req: ComplaintForm) => {
const formData = new FormData();
const formDataWithoutImages = extractFormData(req, 'images');
const jsonBlob = createJsonBlob(formDataWithoutImages);

formData.append('content', jsonBlob);

if (req.images?.length) {
appendFilesToFormData(formData, req.images);
}

const { data } = await axiosInstance.post<ApiResponse<WithPostId>>('/complaint-posts', formData, {
headers: {
'Content-Type': 'multipart/form-data',
},
});

return data;
};

export const fetchComplaintDetail = (id: number) =>
axiosInstance.get<ApiResponse<ComplaintPostDetail>>(`/complaint-posts/${id}`);

export const fetchComplaintCommentList = (id: number) =>
axiosInstance.get<ApiResponse<CommentList>>(`/complaint-posts/${id}/comments`);
1 change: 1 addition & 0 deletions services/ahhachul.com/src/apis/request/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,3 +3,4 @@ export * from './user';
export * from './token';
export * from './lostFound';
export * from './community';
export * from './complaint';
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
11 changes: 11 additions & 0 deletions services/ahhachul.com/src/assets/icons/complaint/ic_hit.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
5 changes: 5 additions & 0 deletions services/ahhachul.com/src/assets/icons/complaint/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
export { default as ArrowMiniIcon } from './ic_arrow.svg?react';
export { default as EmergencyIcon } from './ic_emergency.svg?react';
export { default as HitIcon } from './ic_hit.svg?react';
export { default as MetroIcon } from './ic_metro.svg?react';
export { default as TreeIcon } from './ic_tree.svg?react';
6 changes: 6 additions & 0 deletions services/ahhachul.com/src/assets/icons/system/ic_list.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
1 change: 1 addition & 0 deletions services/ahhachul.com/src/assets/icons/system/index.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
export { default as DotIcon } from './ic_dot.svg?react';
export { default as MicIcon } from './ic_mic.svg?react';
export { default as BellIcon } from './ic_bell.svg?react';
export { default as ListIcon } from './ic_list.svg?react';
export { default as TalkIcon } from './ic_talk.svg?react';
export { default as InfoIcon } from './ic_info.svg?react';
export { default as LogoIcon } from './ic_logo.svg?react';
Expand Down
Original file line number Diff line number Diff line change
@@ -1,13 +1,15 @@
import { css } from '@emotion/react';
import styled from '@emotion/styled';

import { isWebView } from '@/constants';

export const FloatButton = styled.button`
${({ theme }) => css`
${theme.fonts.bodyLarge};

position: fixed;
right: 20px;
bottom: 80px;
bottom: ${isWebView() ? '112px' : '80px'};

width: max-content;
height: 44px;
Expand Down
Original file line number Diff line number Diff line change
@@ -1,25 +1,37 @@
import { PlusIcon } from '@/assets/icons/system';
import { ListIcon, PlusIcon } from '@/assets/icons/system';
import { UiComponent } from '@/components';
import { useAuth } from '@/contexts';
import { type TypeActivities, useFlow } from '@/stackflow';
import type { KeyOf } from '@/types';

type NewBtnType = 'new' | 'list';

interface NewBtnProps {
activityName: KeyOf<TypeActivities>;
label?: string;
type?: NewBtnType;
replace?: boolean;
}

const NewBtn = ({ activityName }: NewBtnProps) => {
const { push } = useFlow();
const NewBtn = ({ activityName, label = '글쓰기', type = 'new', replace = false }: NewBtnProps) => {
const { push, replace: replacePage } = useFlow();
const { authService } = useAuth();

const onClick = () => {
push(authService.isAuthenticated ? activityName : 'SignInPage', {});
const action = replace ? replacePage : push;
action(
authService.isAuthenticated ? activityName : 'SignInPage',
{},
{
animate: !replace,
},
);
};

return (
<UiComponent.FloatButton onClick={onClick}>
<PlusIcon />
<span>글쓰기</span>
{type === 'new' ? <PlusIcon /> : <ListIcon />}
<span>{label}</span>
</UiComponent.FloatButton>
);
};
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ export const ErrorMessage = styled.div`
color: ${({ theme }) => theme.colors.red};
gap: 6px;

& > div > svg > path {
& > svg > path {
fill: #e02020;
stroke: #ffffff;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,8 @@ import { Controller, Path, RegisterOptions, FieldValues, useFormContext } from '

import { FormComponent } from '@/components';

import * as S from './Select.styled';

import { SelectMolecules } from '../../molecules';

interface SelectFieldProps<T extends FieldValues> {
Expand Down Expand Up @@ -43,7 +45,7 @@ const SelectField = <T extends FieldValues>({
/>
)}
/>
<FormComponent.ErrorMessage errMsg={errorMsg} />
<FormComponent.ErrorMessage errMsg={errorMsg} css={S.errorStyle} />
</FormComponent.FormSection>
);
};
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
import { css } from '@emotion/react';

export const errorStyle = css`
margin-top: 12px;
padding-left: 20px;
`;
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import { FormProvider } from 'react-hook-form';

import { FormComponent } from '@/components';
import { lostFoundTypeOptions } from '@/constants';
import { communityTypeFormOptions } from '@/constants';
import { useEditCommunityForm } from '@/hooks/domain/community';
import { useFetchCommunityDetail } from '@/services/community';
import { useActivity } from '@/stackflow';
Expand Down Expand Up @@ -41,7 +41,7 @@ const EditCommunity = ({ id }: WithPostId) => {
onDeleteImg={handleImageDelete}
onImgChange={handleImageUpload}
/>
<FormComponent.Select name="categoryType" options={lostFoundTypeOptions} />
<FormComponent.Select name="categoryType" options={communityTypeFormOptions} />
<FormComponent.SubwayLine name="subwayLineId" />
<FormComponent.Title name="title" />
<FormComponent.Content name="content" initialState={post.content} />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@ const CommunityHeaderActions = ({ id, createdBy }: CommunityHeaderActionsProps)
? [
{
label: '수정하기',
onClick: () => push('EditLostFoundPage', { id }),
onClick: () => push('EditCommunityPage', { id }),
},
{
label: '삭제하기',
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export { default as ComplaintPanel } from './panel/ComplaintPanel.component';
export * from './postDetail';
export * from './searchResults';
Original file line number Diff line number Diff line change
Expand Up @@ -8,11 +8,7 @@ import { KeyOf, ValueOf } from '@/types';

import * as S from './ComplaintPanel.styled';

interface ComplaintPanelProps {
layoutCss: ReturnType<typeof css>;
}

const ComplaintPanel = ({ layoutCss }: ComplaintPanelProps) => {
const ComplaintPanel = () => {
const topCards = objectEntries(complaintsContentList).slice(0, 4);

const bottomCards = objectEntries(complaintsContentList).slice(4, 7);
Expand All @@ -22,39 +18,30 @@ const ComplaintPanel = ({ layoutCss }: ComplaintPanelProps) => {
styleCss: ReturnType<typeof css>,
) => (
<ul css={styleCss}>
{items.map(
([
key,
{
// icon,
label,
desc,
},
]) => (
<li key={key}>
<StackFlow.Link activityName={'NewComplaintPage'} activityParams={{ slug: key }}>
{/* <S.Card> */}
{items.map(([key, { icon, label, desc }]) => (
<li key={key}>
<StackFlow.Link activityName={'NewComplaintPage'} activityParams={{ slug: key }}>
<S.Card>
<span>{label}</span>
<p>{desc}</p>
{/* {icon} */}
{/* </S.Card> */}
</StackFlow.Link>
</li>
),
)}
{icon}
</S.Card>
</StackFlow.Link>
</li>
))}
</ul>
);

return (
<S.Panel css={layoutCss}>
<div>
{/* <S.Label>지하철 환경</S.Label> */}
<S.Panel>
<S.Cell>
<S.Label>지하철 환경</S.Label>
{renderComplaintCards(topCards, S.topSection)}
</div>
<div>
{/* <S.Label>긴급민원 요청</S.Label> */}
</S.Cell>
<S.Cell>
<S.Label>긴급민원 요청</S.Label>
{renderComplaintCards(bottomCards, S.bottomSection)}
</div>
</S.Cell>
</S.Panel>
);
};
Expand Down
Loading
Loading