Skip to content

Conversation

@saseungmin
Copy link
Member

@saseungmin saseungmin commented Jun 15, 2025

Summary by CodeRabbit

  • New Features

    • Introduced a web version of the YouTube player component for embedding and controlling YouTube videos in web environments.
    • Added a reusable wrapper component for consistent player styling and layout.
    • Included comprehensive TypeScript type definitions for the YouTube IFrame Player API.
  • Refactor

    • Improved performance and stability by memoizing event handlers in the app.
    • Refactored the player component structure for clearer separation of concerns.
  • Bug Fixes

    • Removed the modestbranding option from player settings to align with updated requirements.
  • Chores

    • Broadened linter and formatter file inclusion patterns.
    • Enhanced linting rules to warn when using explicit any types.
    • Updated TypeScript configuration to support DOM APIs.

@coderabbitai
Copy link

coderabbitai bot commented Jun 15, 2025

Caution

Review failed

The pull request is closed.

Walkthrough

The changes introduce a web implementation of the YouTube player component, add supporting types for the YouTube IFrame API, and refactor the player wrapper for consistent styling. The modestbranding option is removed throughout the codebase. Linting and formatting configurations are broadened, and TypeScript settings are updated to include DOM types.

Changes

File(s) Change Summary
biome.json Broadened file inclusion patterns for linting/formatting; added rule to warn on explicit any types.
tsconfig.json Updated lib to include "DOM" and "DOM.Iterable" for broader type support.
src/types/iframe.d.ts Added new TypeScript declarations for YouTube IFrame Player API types and interfaces.
src/types/youtube.ts Removed modestbranding property from YoutubePlayerVars type.
src/hooks/useCreateLocalPlayerHtml.ts Removed all logic and parameter references to modestbranding.
src/YoutubePlayer.tsx Replaced outer View with new YoutubePlayerWrapper; removed modestbranding from playerVars; cleaned up state and imports.
src/YoutubePlayerWrapper.tsx Added new wrapper component for consistent player container styling.
src/YoutubePlayer.web.tsx Added new web implementation of the YouTube player using the IFrame Player API; exposes imperative controls and event handling.
example/src/App.tsx Memoized event handlers using useCallback; removed modestbranding from playerVars.

Sequence Diagram(s)

sequenceDiagram
    participant App
    participant YoutubePlayerWrapper
    participant YoutubePlayer (.tsx/.web.tsx)
    participant YouTube IFrame API

    App->>YoutubePlayerWrapper: Render with width, height, style
    YoutubePlayerWrapper->>YoutubePlayer: Render as child
    YoutubePlayer->>YouTube IFrame API: Initialize player (web) or native logic (native)
    App->>YoutubePlayer: Pass event handlers (memoized with useCallback)
    YouTube IFrame API-->>YoutubePlayer: Player events (ready, stateChange, error, etc.)
    YoutubePlayer-->>App: Invoke corresponding callbacks
    App->>YoutubePlayer: Use imperative controls via ref
Loading

Possibly related PRs

  • feat: support youtube iframe for web #1: Introduces similar removal of modestbranding, adds YoutubePlayerWrapper and a web YouTube player component with imperative controls, indicating a direct code-level relationship.

Poem

In a wrapper snug and neat,
The player finds its seat.
No more modest branding here—
The bunny hops with cheer!
Web and native, side by side,
With types and hooks to guide.
Code carrots for all to eat! 🥕


📜 Recent review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 325a29e and d666bba.

📒 Files selected for processing (1)
  • src/types/iframe.d.ts (1 hunks)
✨ Finishing Touches
  • 📝 Generate Docstrings

🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Explain this complex logic.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query. Examples:
    • @coderabbitai explain this code block.
    • @coderabbitai modularize this function.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read src/utils.ts and explain its main purpose.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.
    • @coderabbitai help me debug CodeRabbit configuration file.

Support

Need help? Create a ticket on our support page for assistance with any issues or questions.

Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments.

CodeRabbit Commands (Invoked using PR comments)

  • @coderabbitai pause to pause the reviews on a PR.
  • @coderabbitai resume to resume the paused reviews.
  • @coderabbitai review to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
  • @coderabbitai full review to do a full review from scratch and review all the files again.
  • @coderabbitai summary to regenerate the summary of the PR.
  • @coderabbitai generate docstrings to generate docstrings for this PR.
  • @coderabbitai generate sequence diagram to generate a sequence diagram of the changes in this PR.
  • @coderabbitai resolve resolve all the CodeRabbit review comments.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

CodeRabbit Configuration File (.coderabbit.yaml)

  • You can programmatically configure CodeRabbit by adding a .coderabbit.yaml file to the root of your repository.
  • Please see the configuration documentation for more information.
  • If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: # yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json

Documentation and Community

  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

@saseungmin saseungmin changed the title feat: support youtube ifram for web feat: support youtube iframe for web Jun 15, 2025
Copy link

@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: 4

🔭 Outside diff range comments (1)
src/hooks/useCreateLocalPlayerHtml.ts (1)

24-27: ⚠️ Potential issue

Undefined origin becomes literal 'undefined' in iframe URL.

When origin is falsy, escapeHtml(origin) returns the string 'undefined', triggering the ternary safeOrigin ? … branch and injecting an invalid origin param.

-const safeOrigin = escapeHtml(origin);
+const safeOrigin = origin ? escapeHtml(origin) : '';

Then keep the existing ternary.

🧹 Nitpick comments (5)
biome.json (1)

9-12: Broader include-glob may slow linting & surface noise.

"src/**/*" matches every file (images, JSON, build artefacts, etc.).
Consider narrowing the glob (e.g. src/**/*.{js,jsx,ts,tsx}) or adding an "exclude" for asset folders to avoid needless lint/format passes and spurious warnings.

src/YoutubePlayerWrapper.tsx (1)

10-12: Prop-driven size can be unintentionally overridden by style prop.

style is placed after { width, height } in the array, so callers can silently overwrite the explicit width/height you expose. If the wrapper’s contract is “width/height win”, invert the order:

-return <View style={[styles.container, { width, height }, style]}>{children}</View>;
+return <View style={[styles.container, style, { width, height }]}>{children}</View>;
src/types/iframe.d.ts (1)

162-164: Constructor overload misses HTMLElement signature.

YouTube’s IFrame API allows passing an HTMLElement. Add an overload to prevent false-errors when callers already have the element reference.

-Player: { new (elementId: string, options: Options): YouTubePlayer };
+Player: {
+  new (elementId: string, options: Options): YouTubePlayer;
+  new (element: HTMLElement, options: Options): YouTubePlayer;
+};
src/YoutubePlayer.tsx (2)

107-108: Consider using a generic type instead of any.

The biome-ignore comment suppresses the any type warning, but a generic type would provide better type safety.

-// biome-ignore lint/suspicious/noExplicitAny: <explanation>
-(command: string, args: (string | number | boolean | undefined)[] = [], needsResult = false): Promise<any> => {
+<T = unknown>(command: string, args: (string | number | boolean | undefined)[] = [], needsResult = false): Promise<T | null> => {

193-193: Translate comment to English for consistency.

The Korean comment should be in English to maintain consistency across the codebase.

-// 모든 pending commands 정리
+// Clear all pending commands
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between e306a11 and 4aa7ef4.

📒 Files selected for processing (9)
  • biome.json (2 hunks)
  • example/src/App.tsx (4 hunks)
  • src/YoutubePlayer.tsx (3 hunks)
  • src/YoutubePlayer.web.tsx (1 hunks)
  • src/YoutubePlayerWrapper.tsx (1 hunks)
  • src/hooks/useCreateLocalPlayerHtml.ts (2 hunks)
  • src/types/iframe.d.ts (1 hunks)
  • src/types/youtube.ts (0 hunks)
  • tsconfig.json (1 hunks)
💤 Files with no reviewable changes (1)
  • src/types/youtube.ts
🧰 Additional context used
🧬 Code Graph Analysis (2)
example/src/App.tsx (1)
src/types/youtube.ts (2)
  • ProgressData (56-61)
  • YouTubeError (41-44)
src/YoutubePlayer.web.tsx (3)
src/types/youtube.ts (3)
  • PlayerControls (63-98)
  • YoutubePlayerProps (16-30)
  • ERROR_CODES (46-52)
src/types/iframe.d.ts (1)
  • YouTubePlayer (64-160)
src/index.tsx (1)
  • PlayerState (3-3)
🔇 Additional comments (8)
tsconfig.json (1)

9-9: DOM libs addition is appropriate – no further action.

Adding "DOM" and "DOM.Iterable" to lib is necessary for the new web-specific code that references browser globals. Nothing else in the file is affected – good change.

biome.json (1)

23-26: Rule set change looks safe but may flood CI with warnings.

Turning on suspicious.noExplicitAny as warn is fine if your CI treats warnings non-fatally. Verify pipelines won’t become noisy.

src/hooks/useCreateLocalPlayerHtml.ts (1)

94-104: mute playerVar is unofficial – confirm necessity.

playerVars doesn’t document mute; muting is normally done after onReady. If relying on unofficial query params, ensure they remain supported or move muting logic to onReady.

src/YoutubePlayer.tsx (1)

46-104: LGTM! Well-structured message handling.

The message handler properly handles all event types with appropriate error handling and logging.

example/src/App.tsx (1)

23-91: Good optimization with useCallback hooks!

The memoization of event handlers prevents unnecessary re-renders of the YoutubePlayer component. The empty dependency arrays are correct since these callbacks only use stable references (refs, state setters, and global functions).

src/YoutubePlayer.web.tsx (3)

49-77: Well-implemented progress tracking!

The progress tracking properly handles errors and cleans up intervals. The 1-second interval provides a good balance between accuracy and performance.


239-309: Excellent null handling in async methods!

All async control methods properly handle cases where the player might not be initialized, returning sensible defaults using nullish coalescing.


116-178: 🛠️ Refactor suggestion

Wrap player creation logic in useCallback.

Direct assignment to createPlayerRef.current outside of hooks could cause issues in React's concurrent mode.

Replace the direct assignment with:

-createPlayerRef.current = () => {
+const createPlayerFunction = useCallback(() => {
   if (!containerRef.current || !window.YT?.Player || !videoId) {
     return;
   }
   // ... rest of the function
-};
+}, [videoId, autoplay, controls, loop, startTime, endTime, playsinline, rel, onReady, onStateChange, onError, onPlaybackQualityChange, onPlaybackRateChange, onAutoplayBlocked, startProgressTracking, stopProgressTracking]);
+
+createPlayerRef.current = createPlayerFunction;

Likely an incorrect or invalid review comment.

Copy link

@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 (1)
src/types/iframe.d.ts (1)

1-2: Remove the unused YouTubeError import.

YouTubeError is imported but never referenced in this declaration file, which will trigger tsc --noUnusedLocals or ESLint errors.

-import type { ERROR_CODES, PlaybackQuality, PlayerState, YouTubeError } from './youtube';
+import type { ERROR_CODES, PlaybackQuality, PlayerState } from './youtube';
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between 4aa7ef4 and a430714.

📒 Files selected for processing (3)
  • src/YoutubePlayer.web.tsx (1 hunks)
  • src/YoutubePlayerWrapper.tsx (1 hunks)
  • src/types/iframe.d.ts (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (2)
  • src/YoutubePlayerWrapper.tsx
  • src/YoutubePlayer.web.tsx

Copy link

@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

♻️ Duplicate comments (2)
src/types/iframe.d.ts (2)

150-150: Return a named PlayerSize instead of an inline object.

Re-introduce the PlayerSize interface (width / height) for reuse and clearer IDE hints.

+export interface PlayerSize {
+  width: number;
+  height: number;
+}
...
-  setSize(width: number, height: number): Promise<{ width: number; height: number }>;
+  setSize(width: number, height: number): Promise<PlayerSize>;

30-32: ⚠️ Potential issue

Missing 2 value for playerVars.controls.

The IFrame API allows controls: 0 | 1 | 2; omitting 2 causes false-positive type errors for the “chromeless” UI.

-        controls?: 0 | 1 | undefined;
+        controls?: 0 | 1 | 2 | undefined;
🧹 Nitpick comments (1)
src/types/iframe.d.ts (1)

1-1: Remove unused YouTubeError import or leverage it in onError.

YouTubeError is imported but never referenced, which will trigger no-unused-vars / unused-imports lint rules.
Either (a) drop the identifier, or (b) switch the onError callback to the richer type:

-import type { ERROR_CODES, PlaybackQuality, PlayerState, YouTubeError } from './youtube';
+import type { ERROR_CODES, PlaybackQuality, PlayerState } from './youtube';

or

-        onError?: (event: { data: keyof typeof ERROR_CODES }) => void;
+        onError?: (event: { data: YouTubeError }) => void;
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL
Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between a430714 and 325a29e.

📒 Files selected for processing (1)
  • src/types/iframe.d.ts (1 hunks)
🧰 Additional context used
🧬 Code Graph Analysis (1)
src/types/iframe.d.ts (2)
src/index.tsx (1)
  • PlayerState (3-3)
src/types/youtube.ts (2)
  • PlaybackQuality (54-54)
  • ERROR_CODES (46-52)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants