Skip to content

feat: 홈 화면 '지금 뜨는 글'#885

Open
devfeijoa wants to merge 9 commits into
developfrom
feat/881
Open

feat: 홈 화면 '지금 뜨는 글'#885
devfeijoa wants to merge 9 commits into
developfrom
feat/881

Conversation

@devfeijoa
Copy link
Copy Markdown
Contributor

@devfeijoa devfeijoa commented May 27, 2026

📌𝘐𝘴𝘴𝘶𝘦𝘴

📎𝘞𝘰𝘳𝘬 𝘋𝘦𝘴𝘤𝘳𝘪𝘱𝘵𝘪𝘰𝘯

  • 홈 화면 중 지끔 뜨는 글 부분을 기능추가 및 변경

작업 내용

홈 화면의 지금 뜨는 글 컴포넌트를 변경된 피그마 디자인과 요구사항에 맞게 수정했습니다.

  • 지금 뜨는 글을 한 페이지당 최대 2개씩 노출하도록 변경
  • 각 피드 카드 전체를 터치 영역으로 유지하고, 해당 피드 상세로 이동하도록 처리
  • /feeds/popular 응답만으로 부족한 작품 제목/공개 여부/작품 연결 정보를 피드 상세 조회로 보강
  • 작품이 연결되어 있고 공개 상태인 인기 피드만 노출되도록 필터링
  • 스포일러 글은 본문을 노출하지 않고 스포일러가 포함된 글 보기 문구로 표시
  • 썸네일 우측 하단에 장르 프레임과 장르 이미지를 함께 노출
  • 피그마 기준으로 제목/본문 스타일, 간격, 썸네일 크기, 카드 높이를 반영

고려한 점

/feeds/popular 응답에 작품 제목이 없어, 임시로 feedContent를 제목처럼 사용하는 방식은 피하고 피드 상세 API를 통해 작품 제목이 보이도록 했습니다.
또한 작품 연결 여부에 따른 지금 뜨는 글 노출 여부와 스포일러 공개 여부는 앱에서 필터링하도록 처리했습니다.

Repository는 상세 정보가 보강된 인기 피드 목록만 반환하도록 하고, 홈에서 한 페이지에 2개씩 묶는 UI 정책은 HomeViewModel에서 처리하도록 책임을 분리했습니다.

📷𝘚𝘤𝘳𝘦𝘦𝘯𝘴𝘩𝘰𝘵

Screenshot_20260528_160429

💬𝘛𝘰 𝘙𝘦𝘷𝘪𝘦𝘸𝘦𝘳𝘴

Summary by CodeRabbit

  • New Features

    • 인기 피드에 소설 메타데이터(제목, 이미지, 장르 이미지) 및 공개 여부 표시가 추가되었습니다.
    • 인기 피드 상세 병렬 조회로 더 풍부한 콘텐츠가 로드됩니다.
  • UI/UX 개선

    • 홈 인기 피드가 3→2 슬롯으로 단순화되고 카드 레이아웃/높이가 조정되었습니다.
    • 썸네일 로딩, 장르 오버레이, 제목 길이 제한 및 스포일러 표시가 개선되었습니다.
  • Bug Fixes

    • 응답의 null/빈 값에 대한 기본값 처리와 필터링 로직으로 데이터 안정성이 향상되었습니다.

Review Change Stack

devfeijoa added 4 commits May 26, 2026 13:04
- 작품 연결이 되어있지 않는 글을 뜨지 않게 하기 위해 null 허용으로 전환
- 지금 뜨는 글 피드 슬롯 구성을 3개에서 2개로 변경
- 피드 상세 정보(제목, 썸네일, 장르) 표시를 위한 UI 레이아웃 대폭 수정
- `HomeViewModel`에서 피드 상세 정보를 함께 조회하도록 데이터 가공 로직 추가
- `PopularFeedsViewHolder`에서 썸네일(Coil 사용) 및 제목 생략 처리 등 바인딩 로직 고도화
- `FeedRepository`에 단일 피드 조회(`fetchFeed`) 메서드 추가
- `PopularFeedsAdapter`의 리스트 비교(`DiffUtil`) 로직 수정
- `HomeViewModel`에 있던 인기 피드 가공 로직(`toHomePopularFeeds`)을 `FeedRepository`의 `fetchHomePopularFeeds` 메서드로 이관
- `FeedRepository`에서 인기 피드 목록 조회 시 각 피드의 상세 정보를 병렬로 호출하여 데이터(내용, 스포일러 여부, 작품 정보 등)를 보충하도록 수정
- 공개 상태이며 작품 제목과 이미지가 유효한 피드만 필터링하고 페이지 사이즈(2개)에 맞춰 청킹(Chunk) 처리하는 로직 추가
- `HomeViewModel`의 데이터 로딩 로직을 `runCatching`과 `async/await`을 활용해 예외 처리 및 가독성 개선
- 공통 에러 핸들링을 위한 `handleFailureState` 메서드 추출 및 적용
@devfeijoa devfeijoa requested review from Sadturtleman, m6z1 and s9hn May 27, 2026 02:37
@devfeijoa devfeijoa self-assigned this May 27, 2026
@devfeijoa devfeijoa added 🍯 [FEAT] 새로운 기능을 개발합니다. [👸 공주 은영] labels May 27, 2026
@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented May 27, 2026

워크스루

API/엔티티 확장, DTO→Entity 매핑 기본값 적용, 저장소의 인기 피드 상세 병렬 조회 추가, 뷰모델 동시성 리팩터링, 2-슬롯 UI 및 레이아웃·이미지 로딩 변경을 포함한 홈 인기 피드 기능 전체 경로 변경.

변경 사항

홈 화면 지금 뜨는 글 기능 구현

Layer / File(s) 요약
API 응답 스키마 및 데이터 모델 확장
app/src/main/java/.../PopularFeedsResponseDto.kt, app/src/main/java/.../PopularFeedsEntity.kt
DTO의 feedContent를 nullable로 변경하고 isPublic, title, novelTitle, novelImage, novelThumbnailImage, novelGenreImage를 추가. Entity에 isPublic, novelTitle, novelImage, novelGenreImage 필드 추가.
매핑 로직 및 저장소 병렬 상세 조회
app/src/main/java/.../FeedMapper.kt, app/src/main/java/.../FeedRepository.kt
Mapper에서 null/빈값에 대한 기본값(orEmpty(), true) 및 대체값(feed.title, novelThumbnailImage)을 적용. Repository에 fetchPopularFeedsWithDetails()를 추가하여 인기 피드 목록 기준으로 상세를 async 병렬 조회·병합·필터링함.
뷰모델 동시성 및 상태 관리
app/src/main/java/.../HomeViewModel.kt
fetchUserHomeData·fetchGuestDatacoroutineScope+async+runCatching 패턴으로 리팩터링, 공통 handleFailureState() 추가, HOME_POPULAR_FEED_PAGE_SIZE = 2 상수 도입 및 인기 피드 chunk 처리 변경.
어댑터/뷰홀더 렌더링 및 레이아웃 조정
app/src/main/java/.../PopularFeedsAdapter.kt, app/src/main/java/.../PopularFeedsViewHolder.kt, app/src/main/res/layout/fragment_home.xml, app/src/main/res/layout/item_popular_feed.xml, app/src/main/res/layout/item_popular_feed_slot.xml
Adapter의 areItemsTheSame을 전체 feedId 시퀀스 비교로 변경. ViewHolder를 3→2 슬롯으로 축소하고 각 슬롯의 제목 ellipsize, 스포일러 표시, 코일 기반 썸네일(라운딩/에러 처리), 장르 이미지 SVG 로딩 및 toImageUrl()/ellipsizeByLength() 헬퍼 추가. 관련 레이아웃 높이·구성 조정.

예상 코드 리뷰 시간

🎯 4 (Complex) | ⏱️ ~60 minutes

Possibly related PRs

제안 레이블

🏹 궁사 명지

제안 검토자

  • s9hn
  • m6z1
  • Sadturtleman

🐰 뜨는 글을 찾는 토끼가 말하네,
API는 넉넉히, 매핑은 깔끔히,
병렬로 달려와 이미지를 불러오니,
두 칸에 담긴 이야기 반짝이고,
홈 화면이 오늘도 빛나네. ✨

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed 제목은 홈 화면의 '지금 뜨는 글' 기능 추가/변경을 명확하게 나타내며, 변경사항의 핵심을 잘 요약하고 있습니다.
Linked Issues check ✅ Passed PR의 코드 변경사항이 #881 이슈의 '지금 뜨는 글' 기능 추가/변경 요구사항을 충족하고 있습니다.
Out of Scope Changes check ✅ Passed 모든 코드 변경사항이 '지금 뜨는 글' 기능 개선 및 관련 UI/데이터 처리에 집중하고 있으며, 범위를 벗어난 변경은 없습니다.
Description check ✅ Passed PR 설명이 필수 항목들을 포함하고 있으며, 작업 내용과 고려사항이 명확하게 작성되어 있습니다.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/881

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

🧹 Nitpick comments (2)
app/src/main/res/layout/item_popular_feed_slot.xml (2)

64-64: 💤 Low value

썸네일 marginStart가 의도한 간격인지 확인하세요.

Line 64의 android:layout_marginStart="20dp"FrameLayout에 적용되어 있지만, 제목/본문 텍스트와 썸네일 사이의 간격을 제어합니다. 만약 제목을 제약 기반 레이아웃(0dp)으로 변경한다면, 제목의 marginEnd로 이 간격을 관리하는 것이 더 명확합니다.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@app/src/main/res/layout/item_popular_feed_slot.xml` at line 64, 썸네일의 간격 제어가
현재 FrameLayout의 android:layout_marginStart="20dp"에 의해 이뤄지고 있는데, 제목(TextView 등)이
제약 기반으로 변경되어 width=0dp로 동작할 경우 간격 관리는 제목의 marginEnd로 하는 것이 명확합니다;
item_popular_feed_slot.xml에서 썸네일을 감싼 FrameLayout(썸네일 뷰)에서 layout_marginStart를
제거하고 대신 제목을 정의한 TextView(혹은 제목 관련 뷰)의 android:layout_marginEnd="20dp"로 동일한 간격을
적용하도록 변경하세요.

18-18: ⚡ Quick win

고정 너비(195dp) 대신 제약 기반 레이아웃 사용을 고려하세요.

제목, 본문, 스포일러 텍스트에 하드코딩된 195dp 너비는 다양한 화면 크기에서 반응형으로 동작하지 않습니다. 0dp(match_constraint)와 layout_constraintEnd_toStartOf를 사용하면 썸네일과의 간격을 유지하면서 화면 크기에 맞게 조정됩니다.

♻️ 제약 기반 레이아웃 제안
     <TextView
         android:id="@+id/tv_popular_feed_title"
-        android:layout_width="195dp"
+        android:layout_width="0dp"
+        android:layout_marginEnd="20dp"
         android:layout_height="wrap_content"
         android:ellipsize="end"
         android:maxLines="1"
         android:textAppearance="`@style/title3`"
         android:textColor="`@color/black`"
         app:layout_constraintEnd_toStartOf="`@id/fl_popular_feed_thumbnail`"
         app:layout_constraintStart_toStartOf="parent"
         app:layout_constraintTop_toTopOf="parent"
-        app:layout_constraintHorizontal_bias="0"
         tools:text="피폐 역하렘 남주들의 막내 처제가..." />
 
     <TextView
         android:id="@+id/tv_popular_feed_content"
-        android:layout_width="195dp"
+        android:layout_width="0dp"
         android:layout_height="wrap_content"
         android:layout_marginTop="4dp"
         android:ellipsize="end"
         android:maxLines="3"
         android:textAppearance="`@style/body5`"
         android:textColor="`@color/black`"
         app:layout_constraintEnd_toEndOf="`@id/tv_popular_feed_title`"
         app:layout_constraintStart_toStartOf="`@id/tv_popular_feed_title`"
         app:layout_constraintTop_toBottomOf="`@id/tv_popular_feed_title`"
         tools:text="이름이 나여주입니다ㅋㅋㅋ읽던 소설이 세계멸망엔딩나서 댓글달았다가 그 세계의 본인에게 빙의하게 되었는데 S급 힐..." />
 
     <TextView
         android:id="@+id/tv_popular_feed_content_spoiler"
-        android:layout_width="195dp"
+        android:layout_width="0dp"
         android:layout_height="wrap_content"
         android:layout_marginTop="8dp"
         android:ellipsize="end"
         android:maxLines="1"
         android:text="`@string/home_popular_feed_spoiler`"
         android:textAppearance="`@style/body5`"
         android:textColor="`@color/secondary_100_FF675D`"
         android:visibility="gone"
         app:layout_constraintEnd_toEndOf="`@id/tv_popular_feed_title`"
         app:layout_constraintStart_toStartOf="`@id/tv_popular_feed_title`"
         app:layout_constraintTop_toBottomOf="`@id/tv_popular_feed_title`"
         tools:visibility="visible" />

참고: 제목에서 layout_constraintHorizontal_bias="0"도 함께 제거했습니다(start 제약만 있을 때 불필요).

Also applies to: 32-32, 46-46

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@app/src/main/res/layout/item_popular_feed_slot.xml` at line 18, Replace the
fixed width (android:layout_width="195dp") on the feed slot text views with a
constraint-based width so the items are responsive: set
android:layout_width="0dp" (match_constraint) for the title/body/spoiler
TextViews and add a layout_constraintEnd_toStartOf pointing to the thumbnail
ImageView (and keep their start constraint to the parent or other anchor), and
remove any unnecessary layout_constraintHorizontal_bias="0" on the title; apply
the same change for the other occurrences (the identical fixed-width attributes
at the other two locations noted in the comment).
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@app/src/main/java/com/into/websoso/data/mapper/FeedMapper.kt`:
- Line 118: The mapping in FeedMapper (the line setting isPublic = feed.isPublic
?: true) uses a default of true which may expose private content; change the
default to false so that when feed.isPublic is null it is treated as non-public.
Locate the mapping method in FeedMapper (the function that constructs the mapped
Feed/DTO and assigns isPublic) and replace the null-coalescing default from true
to false, ensuring all callers still expect a non-null Boolean afterward.

In `@app/src/main/java/com/into/websoso/ui/main/home/HomeViewModel.kt`:
- Around line 147-151: The success-state updates using _uiState.value =
uiState.value?.copy(... popularNovels = popularNovels.popularNovels,
popularFeeds = popularFeeds) (and the similar update at the second success
branch around the other copy at lines noted) do not reset the error flag; modify
both uiState.value?.copy calls to include error = false so a prior error state
is cleared when successful data arrives (update both occurrences where
popularNovels/popularFeeds are assigned).

In `@app/src/main/res/layout/item_popular_feed.xml`:
- Line 36: slot2의 top 제약(layout_constraintTop_toBottomOf)이 현재
`@id/item_popular_fees_slot1로` 되어 있어 divider_1(`@id/divider_1`)이 slot1 바로 아래로 배치된
설정과 충돌합니다; slot2의 top 제약을 divider_1의 아래로 변경하여 중첩을 제거하세요 — 즉
item_popular_feed.xml에서 slot2의 layout_constraintTop_toBottomOf 속성값을
`@id/item_popular_divider_1`(또는 실제 divider_1 ID)로 바꿔 divider_1과 slot1 사이의 순서를
보장하도록 수정하세요.

---

Nitpick comments:
In `@app/src/main/res/layout/item_popular_feed_slot.xml`:
- Line 64: 썸네일의 간격 제어가 현재 FrameLayout의 android:layout_marginStart="20dp"에 의해
이뤄지고 있는데, 제목(TextView 등)이 제약 기반으로 변경되어 width=0dp로 동작할 경우 간격 관리는 제목의 marginEnd로
하는 것이 명확합니다; item_popular_feed_slot.xml에서 썸네일을 감싼 FrameLayout(썸네일 뷰)에서
layout_marginStart를 제거하고 대신 제목을 정의한 TextView(혹은 제목 관련 뷰)의
android:layout_marginEnd="20dp"로 동일한 간격을 적용하도록 변경하세요.
- Line 18: Replace the fixed width (android:layout_width="195dp") on the feed
slot text views with a constraint-based width so the items are responsive: set
android:layout_width="0dp" (match_constraint) for the title/body/spoiler
TextViews and add a layout_constraintEnd_toStartOf pointing to the thumbnail
ImageView (and keep their start constraint to the parent or other anchor), and
remove any unnecessary layout_constraintHorizontal_bias="0" on the title; apply
the same change for the other occurrences (the identical fixed-width attributes
at the other two locations noted in the comment).
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 992b4eed-8a16-4f50-861f-b60934dfcc8d

📥 Commits

Reviewing files that changed from the base of the PR and between 1c9fd79 and a43ef50.

📒 Files selected for processing (10)
  • app/src/main/java/com/into/websoso/data/mapper/FeedMapper.kt
  • app/src/main/java/com/into/websoso/data/model/PopularFeedsEntity.kt
  • app/src/main/java/com/into/websoso/data/remote/response/PopularFeedsResponseDto.kt
  • app/src/main/java/com/into/websoso/data/repository/FeedRepository.kt
  • app/src/main/java/com/into/websoso/ui/main/home/HomeViewModel.kt
  • app/src/main/java/com/into/websoso/ui/main/home/adpater/PopularFeedsAdapter.kt
  • app/src/main/java/com/into/websoso/ui/main/home/adpater/PopularFeedsViewHolder.kt
  • app/src/main/res/layout/fragment_home.xml
  • app/src/main/res/layout/item_popular_feed.xml
  • app/src/main/res/layout/item_popular_feed_slot.xml

Comment thread app/src/main/java/com/into/websoso/data/mapper/FeedMapper.kt Outdated
Comment thread app/src/main/java/com/into/websoso/ui/main/home/HomeViewModel.kt
Comment thread app/src/main/res/layout/item_popular_feed.xml Outdated
devfeijoa added 3 commits May 28, 2026 15:37
- `FeedRepository`의 `fetchHomePopularFeeds` 메서드명을 `fetchPopularFeedsWithDetails`로 변경
- `HomeViewModel`에서 변경된 메서드명을 참조하도록 수정 및 반영
- `FeedRepository`에서 수행하던 인기 피드 리스트 chunk(페이징) 처리를 `HomeViewModel`로 이동
- `FeedRepository.fetchPopularFeedsWithDetails`의 반환 타입을 `List<List<...>>`에서 `List<...>`로 변경
- `HomeViewModel`에 `HOME_POPULAR_FEED_PAGE_SIZE` 상수 추가 및 UI 상태 업데이트 시 데이터 가공 로직 반영
- `FeedMapper`에서 `isPublic` 필드의 기본값을 `true`에서 `false`로 변경
Copy link
Copy Markdown

@coderabbitai coderabbitai Bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (2)
app/src/main/java/com/into/websoso/data/repository/FeedRepository.kt (1)

46-61: ⚠️ Potential issue | 🟠 Major | ⚡ Quick win

상세 조회 전체 실패를 성공으로 삼키지 마세요.

여기서 상세 API 예외를 전부 null로 바꾸면, 원본 인기 피드가 있어도 fetchPopularFeedsWithDetails()가 빈 리스트로 정상 반환될 수 있습니다. 그러면 HomeViewModel의 실패 처리 경로가 타지 않아 홈 화면에서 섹션이 조용히 사라집니다. 최소한 원본 목록이 비어 있지 않은데 상세 조회가 전부 실패한 경우에는 예외를 다시 올리거나, 실패 신호를 함께 반환하도록 바꿔주세요.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@app/src/main/java/com/into/websoso/data/repository/FeedRepository.kt` around
lines 46 - 61, The current mapping in fetchPopularFeedsWithDetails() uses async
+ runCatching { feedApi.getFeed(feed.feedId)... }.getOrNull(), which swallows
all exceptions and can silently return an empty list; instead return
success/failure info per item (e.g., Result<Feed> or a sealed wrapper) from each
async so you can detect global failure; after awaitAll examine the collected
results and if the input popular feeds list was non-empty but all detail lookups
failed, rethrow an appropriate exception (or return a failure result) rather
than returning an empty list; reference feedApi.getFeed(feed.feedId) and
fetchPopularFeedsWithDetails() when making the change.
app/src/main/java/com/into/websoso/ui/main/home/HomeViewModel.kt (1)

73-90: ⚠️ Potential issue | 🟠 Major | ⚡ Quick win

CancellationException을 runCatching으로 잡아 error UI로 전환될 수 있습니다.

fetchUserHomeData()/fetchGuestData()async { runCatching { ... } }CancellationException까지 Result로 감싸고, exceptionOrNull() != null이면 handleFailureState()로 가서 error = true를 설정합니다(취소는 취소로 전파되어야 합니다). updateFeed()/updateNovel()도 동일 패턴이라 함께 개선 필요합니다.

수정 방향
+import kotlinx.coroutines.CancellationException
+
+private suspend inline fun <T> suspendResultOf(
+    crossinline block: suspend () -> T,
+): Result<T> =
+    try {
+        Result.success(block())
+    } catch (e: CancellationException) {
+        throw e
+    } catch (t: Throwable) {
+        Result.failure(t)
+    }
+
-                val popularFeedsDeferred =
-                    async { runCatching { feedRepository.fetchPopularFeedsWithDetails() } }
+                val popularFeedsDeferred =
+                    async { suspendResultOf { feedRepository.fetchPopularFeedsWithDetails() } }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@app/src/main/java/com/into/websoso/ui/main/home/HomeViewModel.kt` around
lines 73 - 90, The current async { runCatching { ... } } pattern in
fetchUserHomeData()/fetchGuestData() (and similarly in
updateFeed()/updateNovel()) is wrapping CancellationException into a Result and
causing cancelled coroutines to be treated as failures; change each async block
to explicitly rethrow CancellationException before wrapping other exceptions
(e.g. replace async { runCatching { ... } } with async { try {
Result.success(...) } catch (e: CancellationException) { throw e } catch (t:
Throwable) { Result.failure(t) } } ) so cancellations propagate, and keep the
subsequent failure check (exceptionOrNull) unchanged.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Outside diff comments:
In `@app/src/main/java/com/into/websoso/data/repository/FeedRepository.kt`:
- Around line 46-61: The current mapping in fetchPopularFeedsWithDetails() uses
async + runCatching { feedApi.getFeed(feed.feedId)... }.getOrNull(), which
swallows all exceptions and can silently return an empty list; instead return
success/failure info per item (e.g., Result<Feed> or a sealed wrapper) from each
async so you can detect global failure; after awaitAll examine the collected
results and if the input popular feeds list was non-empty but all detail lookups
failed, rethrow an appropriate exception (or return a failure result) rather
than returning an empty list; reference feedApi.getFeed(feed.feedId) and
fetchPopularFeedsWithDetails() when making the change.

In `@app/src/main/java/com/into/websoso/ui/main/home/HomeViewModel.kt`:
- Around line 73-90: The current async { runCatching { ... } } pattern in
fetchUserHomeData()/fetchGuestData() (and similarly in
updateFeed()/updateNovel()) is wrapping CancellationException into a Result and
causing cancelled coroutines to be treated as failures; change each async block
to explicitly rethrow CancellationException before wrapping other exceptions
(e.g. replace async { runCatching { ... } } with async { try {
Result.success(...) } catch (e: CancellationException) { throw e } catch (t:
Throwable) { Result.failure(t) } } ) so cancellations propagate, and keep the
subsequent failure check (exceptionOrNull) unchanged.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro

Run ID: 8110d88b-2f7d-4aa6-9c6c-d1259f68f5d9

📥 Commits

Reviewing files that changed from the base of the PR and between a43ef50 and d3f492d.

📒 Files selected for processing (2)
  • app/src/main/java/com/into/websoso/data/repository/FeedRepository.kt
  • app/src/main/java/com/into/websoso/ui/main/home/HomeViewModel.kt

devfeijoa added 2 commits May 28, 2026 15:56
- 인기 피드 슬롯의 높이를 고정값(122dp)에서 `0dp`로 변경하여 영역을 가변적으로 차지하도록 수정
- 구분선(divider)을 중앙에 배치하고, 이를 기준으로 슬롯 1과 2가 상하로 균등하게 배치되도록 제약 조건 조정
- `HomeViewModel`에서 인기 작품 및 인기 피드 데이터 로드 성공 시 `error` 상태를 `false`로 변경하도록 수정
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

[👸 공주 은영] 🍯 [FEAT] 새로운 기능을 개발합니다.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

feat: 홈 화면 '지금 뜨는 글'

1 participant