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

[WEB-1116] feat: pages realtime sync #5057

Merged
merged 27 commits into from
Jul 22, 2024
Merged

Conversation

aaryan610
Copy link
Collaborator

@aaryan610 aaryan610 commented Jul 5, 2024

Realtime sync for Pages

Live server:

Created a new NodeJS server to handle web socket connection using Hocuspocus.

Editor refactoring:

  1. New collaboration hooks-
    • useCollaborationEditor- for editable collaborative editors.
    • useCollaborationReadOnlyEditor- for read only collaborative editors.
  2. Removed old custom CollaborationProvider.

Summary by CodeRabbit

  • New Features

    • Enhanced error handling across multiple endpoints using centralized error codes for improved clarity and maintainability.
    • Introduced new collaborative editing capabilities with the addition of components and hooks for real-time document editing.
    • Added functionalities for managing page descriptions in a collaborative environment.
    • Implemented robust authentication for collaborative document editing, ensuring secure access.
  • Bug Fixes

    • Improved response structure for API errors, providing detailed error messages and codes to aid in debugging.
  • Documentation

    • Updated various configuration files to reflect recent changes and improve the setup process for developers.
  • Chores

    • Added TypeScript configuration and bundler setup files to streamline the development process.

live/src/index.ts Outdated Show resolved Hide resolved
live/src/page.ts Outdated Show resolved Hide resolved
@aaryan610 aaryan610 marked this pull request as ready for review July 15, 2024 09:12
@aaryan610 aaryan610 marked this pull request as draft July 16, 2024 09:04
@sriramveeraghanta sriramveeraghanta changed the base branch from preview to develop July 16, 2024 09:13
@aaryan610 aaryan610 changed the base branch from develop to preview July 16, 2024 11:06
@aaryan610 aaryan610 marked this pull request as ready for review July 16, 2024 12:44
Copy link
Contributor

coderabbitai bot commented Jul 19, 2024

Important

Review skipped

Auto reviews are disabled on base/target branches other than the default branch.

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Walkthrough

This update enhances error handling in the API by introducing structured error codes, improving clarity and maintainability. A new WebSocket server has been established for collaborative editing, along with various optimizations across editor components. These changes streamline functionalities, ensuring robust management of pages and user interactions, enriching both the development workflow and the user experience in collaborative environments.

Changes

Files Change Summary
apiserver/.../page/base.py, apiserver/utils/error_codes.py Enhanced error handling with structured responses and centralized error codes.
live/index.ts, live/page.ts Established a WebSocket server for collaborative editing with integrated authentication and document management.
packages/editor/... Restructured editor components for better collaboration, updating hooks and exports for improved functionality.
docker-compose-local.yml, live/.env.example, live/Dockerfile.dev, live/Dockerfile.channel Added new services and environment configurations to support live development and testing.
setup.sh, turbo.json Introduced commands for environment setup and new environment variables for configuration improvements.

Sequence Diagram(s)

sequenceDiagram
    participant User
    participant WebApp
    participant API
    participant ErrorHandler

    User->>WebApp: Initiate Edit
    WebApp->>API: Send Edit Request
    API->>ErrorHandler: Validate Input
    alt If valid
        ErrorHandler-->>API: Proceed with Edit
        API-->>WebApp: Success Response
        WebApp-->>User: Update UI
    else If invalid
        ErrorHandler-->>API: Return Error Code
        API-->>WebApp: Error Response
        WebApp-->>User: Show Error Message
    end
Loading

🐇 "In a world of code so fine,
We hop with joy, a change divine!
With error codes now neat and clear,
Our coding bunnies leap with cheer.
Collaborative dreams now take flight,
As we code through day and night!" 🐇


Thank you for using CodeRabbit. We offer it for free to the OSS community and would appreciate your support in helping us grow. If you find it useful, would you consider giving us a shout-out on your favorite social media?

Share
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>.
    • Generate unit testing code for this file.
    • 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 generate unit testing code for this file.
    • @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 generate interesting stats about this repository and render them as a table.
    • @coderabbitai show all the console.log statements in this repository.
    • @coderabbitai read src/utils.ts and generate unit testing code.
    • @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.

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 as 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 resolve resolve all the CodeRabbit review comments.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Additionally, you can add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.

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.

Copy link
Contributor

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

Outside diff range, codebase verification and nitpick comments (13)
packages/editor/tsup.config.ts (1)

4-4: Issues found with the integration of src/lib.ts entry point.

The addition of src/lib.ts as an entry point in tsup.config.ts is not accompanied by any references or imports in the codebase, indicating a potential incomplete integration.

  • packages/editor/tsup.config.ts: entry: ["src/index.ts", "src/lib.ts"]

Please review and ensure that src/lib.ts is properly integrated and utilized within the codebase.

Analysis chain

Verify the integration of src/lib.ts entry point.

The addition of src/lib.ts expands the scope of files processed during the build. Ensure that the new entry point is necessary and correctly integrated.

Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify the integration of `src/lib.ts` entry point in the codebase.

# Test: Search for the usage of `src/lib.ts`. Expect: Proper integration and usage.
rg --type python -A 5 $'src/lib.ts'

Length of output: 65


Script:

#!/bin/bash
# Description: Verify the integration of `src/lib.ts` entry point in the codebase.

# Test: Search for the usage of `src/lib.ts`. Expect: Proper integration and usage.
rg --type ts -A 5 'src/lib.ts'

Length of output: 355


Script:

#!/bin/bash
# Description: Verify the integration of `src/lib.ts` entry point in the codebase.

# Test: Search for imports or references to `src/lib.ts`. Expect: Proper integration and usage.
rg 'src/lib.ts' --type ts

Length of output: 97

live/Dockerfile.channel (1)

8-11: package-lock.json is missing

The package-lock.json file is not present in the ./channel/ directory. This file is essential for locking dependency versions to ensure consistency across different environments. Please add and maintain the package-lock.json file to avoid potential dependency issues.

Analysis chain

Verify the presence and currency of package-lock.json.

Ensure that package-lock.json is present and up-to-date to avoid potential dependency issues.

Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify the presence and currency of `package-lock.json`.

# Test: Check if `package-lock.json` exists and is up-to-date.
if [ -f ./channel/package-lock.json ]; then
  echo "package-lock.json is present."
else
  echo "package-lock.json is missing."
fi

Length of output: 109

live/package.json (1)

2-4: Fill in the metadata fields.

The description and author fields are empty. Consider providing meaningful values for better project identification and maintainability.

-  "description": "",
-  "author": "",
+  "description": "Real-time synchronization server for collaborative editing",
+  "author": "Your Name <your.email@example.com>",

Also applies to: 13-14

live/src/services/api.service.ts (2)

1-3: Consider importing only the necessary parts from axios.

To reduce the bundle size, consider importing only the necessary parts from axios instead of the entire library.

- import axios, { AxiosInstance } from "axios";
+ import { create } from "axios";

39-41: Clarify the data parameter in the delete method.

The data parameter in the delete method is optional, but its usage might be unclear. Consider adding a comment or renaming the parameter for better clarity.

- delete(url: string, data?: any, config = {}) {
-   return this.axiosInstance.delete(url, { data, ...config });
+ delete(url: string, data?: any, config = {}) {
+   // Note: The data parameter is optional and used for sending a request body with DELETE requests.
+   return this.axiosInstance.delete(url, { data, ...config });
packages/editor/src/core/components/editors/document/read-only-editor.tsx (1)

45-46: Consider logging when the editor is not available.

Returning null when the editor is not available might make debugging difficult. Consider adding a log statement to indicate why the editor is not rendered.

- if (!editor) return null;
+ if (!editor) {
+   console.warn("Editor is not available.");
+   return null;
+ }
packages/editor/src/core/components/editors/document/collaborative-read-only-editor.tsx (1)

13-51: LGTM! Consider adding PropTypes for better type checking.

The function is well-structured and correctly uses the props and hooks.

+ CollaborativeDocumentReadOnlyEditor.propTypes = {
+   containerClassName: PropTypes.string,
+   editorClassName: PropTypes.string,
+   embedHandler: PropTypes.object,
+   forwardedRef: PropTypes.object,
+   handleEditorReady: PropTypes.func,
+   id: PropTypes.string.isRequired,
+   mentionHandler: PropTypes.func,
+   realtimeConfig: PropTypes.object.isRequired,
+   user: PropTypes.object.isRequired,
+ };
live/src/services/page.service.ts (3)

11-29: Consider adding more detailed error handling.

The method is well-structured, but adding more detailed error handling can improve robustness.

- .catch((error) => {
-   throw error?.response?.data;
- });
+ .catch((error) => {
+   if (error.response) {
+     // Request made and server responded
+     console.error('Error response:', error.response.data);
+     throw error.response.data;
+   } else if (error.request) {
+     // Request made but no response received
+     console.error('Error request:', error.request);
+     throw new Error('No response received from server');
+   } else {
+     // Something happened in setting up the request
+     console.error('Error message:', error.message);
+     throw new Error(error.message);
+   }
+ });

31-51: Consider adding more detailed error handling.

The method is well-structured, but adding more detailed error handling can improve robustness.

- .catch((error) => {
-   throw error?.response?.data;
- });
+ .catch((error) => {
+   if (error.response) {
+     // Request made and server responded
+     console.error('Error response:', error.response.data);
+     throw error.response.data;
+   } else if (error.request) {
+     // Request made but no response received
+     console.error('Error request:', error.request);
+     throw new Error('No response received from server');
+   } else {
+     // Something happened in setting up the request
+     console.error('Error message:', error.message);
+     throw new Error(error.message);
+   }
+ });

53-77: Consider adding more detailed error handling.

The method is well-structured, but adding more detailed error handling can improve robustness.

- .catch((error) => {
-   throw error;
- });
+ .catch((error) => {
+   if (error.response) {
+     // Request made and server responded
+     console.error('Error response:', error.response.data);
+     throw error.response.data;
+   } else if (error.request) {
+     // Request made but no response received
+     console.error('Error request:', error.request);
+     throw new Error('No response received from server');
+   } else {
+     // Something happened in setting up the request
+     console.error('Error message:', error.message);
+     throw new Error(error.message);
+   }
+ });
live/src/page.ts (3)

59-61: Improve error logging.

Include more detailed error information in the log to facilitate debugging.

-  console.error("Update error:", error);
+  console.error("Update error:", error.message, error.stack);

97-99: Improve error logging.

Include more detailed error information in the log to facilitate debugging.

-  console.error("Error while transforming from HTML to Uint8Array", error);
+  console.error("Error while transforming from HTML to Uint8Array", error.message, error.stack);

135-137: Improve error logging.

Include more detailed error information in the log to facilitate debugging.

-  console.error("Fetch error:", error);
+  console.error("Fetch error:", error.message, error.stack);
Review details

Configuration used: CodeRabbit UI
Review profile: CHILL

Commits

Files that changed from the base of the PR and between 075b8ef and 0d9b346.

Files ignored due to path filters (1)
  • yarn.lock is excluded by !**/yarn.lock, !**/*.lock
Files selected for processing (51)
  • apiserver/plane/app/views/issue/archive.py (3 hunks)
  • apiserver/plane/app/views/issue/bulk_operations.py (4 hunks)
  • apiserver/plane/app/views/page/base.py (3 hunks)
  • apiserver/plane/utils/error_codes.py (1 hunks)
  • docker-compose-local.yml (1 hunks)
  • live/.env.example (1 hunks)
  • live/Dockerfile.channel (1 hunks)
  • live/Dockerfile.dev (1 hunks)
  • live/package.json (1 hunks)
  • live/src/authentication.ts (1 hunks)
  • live/src/index.ts (1 hunks)
  • live/src/page.ts (1 hunks)
  • live/src/services/api.service.ts (1 hunks)
  • live/src/services/page.service.ts (1 hunks)
  • live/src/services/user.service.ts (1 hunks)
  • live/src/types/common.d.ts (1 hunks)
  • live/tsconfig.json (1 hunks)
  • live/tsup.config.ts (1 hunks)
  • package.json (1 hunks)
  • packages/editor/package.json (2 hunks)
  • packages/editor/src/core/components/editors/document/collaborative-editor.tsx (5 hunks)
  • packages/editor/src/core/components/editors/document/collaborative-read-only-editor.tsx (1 hunks)
  • packages/editor/src/core/components/editors/document/index.ts (1 hunks)
  • packages/editor/src/core/components/editors/document/read-only-editor.tsx (1 hunks)
  • packages/editor/src/core/extensions/code/without-props.tsx (1 hunks)
  • packages/editor/src/core/extensions/core-without-props.tsx (4 hunks)
  • packages/editor/src/core/extensions/custom-link/extension.tsx (1 hunks)
  • packages/editor/src/core/extensions/index.ts (1 hunks)
  • packages/editor/src/core/extensions/mentions/extension.tsx (1 hunks)
  • packages/editor/src/core/extensions/mentions/mentions-without-props.tsx (2 hunks)
  • packages/editor/src/core/helpers/common.ts (1 hunks)
  • packages/editor/src/core/hooks/use-collaborative-editor.ts (3 hunks)
  • packages/editor/src/core/hooks/use-editor.ts (5 hunks)
  • packages/editor/src/core/hooks/use-read-only-collaborative-editor.ts (1 hunks)
  • packages/editor/src/core/hooks/use-read-only-editor.ts (1 hunks)
  • packages/editor/src/core/types/editor.ts (4 hunks)
  • packages/editor/src/index.ts (2 hunks)
  • packages/editor/src/lib.ts (1 hunks)
  • packages/editor/tsup.config.ts (1 hunks)
  • packages/ui/package.json (3 hunks)
  • packages/ui/tsup.config.ts (1 hunks)
  • setup.sh (1 hunks)
  • turbo.json (1 hunks)
  • web/app/[workspaceSlug]/(projects)/projects/(detail)/[projectId]/pages/(detail)/header.tsx (3 hunks)
  • web/core/components/pages/editor/editor-body.tsx (7 hunks)
  • web/core/components/pages/editor/header/extra-options.tsx (2 hunks)
  • web/core/components/pages/editor/header/mobile-root.tsx (3 hunks)
  • web/core/components/pages/editor/header/options-dropdown.tsx (3 hunks)
  • web/core/components/pages/editor/header/root.tsx (3 hunks)
  • web/core/components/pages/editor/page-root.tsx (4 hunks)
  • web/helpers/common.helper.ts (1 hunks)
Files skipped from review due to trivial changes (6)
  • apiserver/plane/utils/error_codes.py
  • live/.env.example
  • live/src/types/common.d.ts
  • packages/editor/src/core/helpers/common.ts
  • packages/editor/src/lib.ts
  • turbo.json
Additional context used
Biome
web/core/components/pages/editor/page-root.tsx

[error] 28-28: Unnecessary use of boolean literals in conditional expression.

Simplify your code by directly assigning the result without using a ternary operator.
If your goal is negation, you may use the logical NOT (!) or double NOT (!!) operator for clearer and concise code.
Check for more details about NOT operator.
Unsafe fix: Remove the conditional expression with

(lint/complexity/noUselessTernary)

live/src/index.ts

[error] 57-66: Promise executor functions should not be async.

(lint/suspicious/noAsyncPromiseExecutor)


[error] 82-86: Promise executor functions should not be async.

(lint/suspicious/noAsyncPromiseExecutor)

Additional comments not posted (137)
packages/editor/src/core/components/editors/document/index.ts (2)

1-1: Verify the integration of collaborative-editor.

The export change aligns with the shift towards collaborative editing functionality. Ensure that the new export is properly integrated and tested within the application.


2-2: Verify the integration of collaborative-read-only-editor.

The export change aligns with the shift towards collaborative editing functionality. Ensure that the new export is properly integrated and tested within the application.

packages/editor/tsup.config.ts (1)

7-7: LGTM!

The change to the clean property ensures that previous build artifacts are removed before generating new ones, reducing the risk of stale files affecting the build.

live/tsup.config.ts (7)

4-4: LGTM!

The entry property is correctly set to src/index.ts, which is necessary for the build process.


5-5: LGTM!

The format property is correctly set to ["cjs", "esm"], ensuring compatibility with different module systems.


6-6: LGTM!

The dts property is correctly set to true, ensuring that TypeScript declaration files are generated.


7-7: LGTM!

The clean property is set to false, which might be necessary for the live service to retain previous build artifacts.


8-8: LGTM!

The external property is correctly set to ["react"], ensuring that react is treated as an external dependency.


9-9: LGTM!

The injectStyle property is correctly set to true, ensuring that styles are injected during the build process.


10-11: LGTM!

The spread operator ensures that any additional options passed to the configuration are included.

packages/ui/tsup.config.ts (1)

1-11: Verify the clean option in the tsup configuration.

The clean option is set to false. This might lead to outdated build artifacts if not handled elsewhere. Ensure that this is intentional and that build artifacts are managed properly.

live/Dockerfile.dev (4)

1-2: LGTM!

The base image node:18-alpine and the installation of libc6-compat are appropriate for a Node.js application.


3-4: LGTM!

Setting the working directory to /app is a standard practice.


7-9: Verify the necessity of installing Turbo globally.

Installing Turbo globally might not be necessary if it's included in the project dependencies. Consider using the local version if available.


10-13: LGTM!

Exposing port 3003 and running the development server with yarn dev is appropriate. The volume setup ensures that node_modules are shared.

setup.sh (1)

12-12: LGTM!

The addition of the line to copy the environment example file for the live directory is appropriate and follows the existing pattern.

live/Dockerfile.channel (3)

16-19: LGTM!

The TypeScript installation and application file copying steps are correct.


22-25: LGTM!

The TypeScript compilation and port exposure steps are correct.


28-28: LGTM!

The command to start the Node.js server is correct.

packages/editor/src/core/extensions/index.ts (1)

Line range hint 1-17:
Verify the impact of removing document-without-props.

The removal of the export statement for document-without-props might impact other parts of the codebase that rely on this module. Ensure that all dependencies on this module are updated accordingly.

Verification successful

No impact from removing document-without-props found.

The verification process did not find any instances of document-without-props being used or imported in the codebase. Therefore, its removal does not affect other parts of the project.

  • No occurrences of document-without-props found in TypeScript files.
  • No import statements for document-without-props found.
Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify the impact of removing `document-without-props`.

# Test: Search for the usage of `document-without-props`. Expect: No occurrences.
rg --type ts -A 5 $'document-without-props'

Length of output: 42


Script:

#!/bin/bash
# Description: Verify the impact of removing `document-without-props` by searching across all file types.

# Test: Search for the usage of `document-without-props` in the entire codebase. Expect: No occurrences.
rg -A 5 'document-without-props'

Length of output: 32


Script:

#!/bin/bash
# Description: Verify the impact of removing `document-without-props` by searching for import statements.

# Test: Search for import statements that include `document-without-props`. Expect: No occurrences.
rg 'import.*document-without-props'

Length of output: 37

live/tsconfig.json (17)

2-3: LGTM!

The schema and display name settings are correct.


5-5: LGTM!

The allowJs option is correctly set to true.


6-6: LGTM!

The allowSyntheticDefaultImports option is correctly set to true.


7-7: LGTM!

The baseUrl option is correctly set to ".".


8-8: LGTM!

The esModuleInterop option is correctly set to true.


9-9: LGTM!

The forceConsistentCasingInFileNames option is correctly set to true.


10-11: LGTM!

The module and moduleResolution options are correctly set to NodeNext.


12-12: LGTM!

The noImplicitAny option is correctly set to true.


13-13: LGTM!

The outDir option is correctly set to "dist".


14-16: LGTM!

The paths option is correctly set for aliasing.


17-17: LGTM!

The removeComments option is correctly set to true.


18-18: LGTM!

The resolveJsonModule option is correctly set to true.


19-19: LGTM!

The skipLibCheck option is correctly set to true.


20-20: LGTM!

The sourceMap option is correctly set to true.


21-21: LGTM!

The strict option is correctly set to true.


22-22: LGTM!

The target option is correctly set to ES2022.


24-24: LGTM!

The exclude option settings are correct.

package.json (1)

10-10: Addition of "live" workspace.

The addition of "live" to the workspaces array suggests a new environment or module is being integrated. Ensure that the new workspace is correctly configured and does not introduce any dependency or build issues.

packages/editor/src/index.ts (1)

10-11: Updated exports for collaborative editors.

The export statements have been updated to reflect the new collaborative editor components. Ensure that the new components are correctly implemented and integrated.

packages/editor/src/core/extensions/mentions/mentions-without-props.tsx (3)

2-2: Importing MentionOptions.

The import statement includes MentionOptions from the @tiptap/extension-mention, indicating a shift towards utilizing this type for the extended options. Ensure that the imported type is correctly used in the interface.


4-4: Importing IMentionHighlight.

The import statement includes IMentionHighlight from @/types, suggesting the use of this type for mention highlights. Ensure that the imported type is correctly used in the interface.


6-9: Extended CustomMentionOptions interface.

The CustomMentionOptions interface has been extended to include two new properties: mentionHighlights, which is a function returning a promise that resolves to an array of IMentionHighlight, and readonly, which is a boolean. Ensure that these new properties are correctly used and integrated within the mention functionality.

live/package.json (3)

6-10: LGTM!

The scripts section is correctly configured for building, starting, and developing the project.


15-30: LGTM!

The dependencies are relevant and necessary for the project's functionality.


32-40: LGTM!

The devDependencies are relevant and necessary for TypeScript development.

live/src/services/user.service.ts (1)

11-15: LGTM!

The currentUserConfig method is correctly implemented.

web/helpers/common.helper.ts (1)

12-13: LGTM!

The new constant LIVE_BASE_URL is correctly implemented.

packages/editor/src/core/components/editors/document/collaborative-read-only-editor.tsx (2)

1-11: LGTM! Imports are appropriate.

The imports are necessary for the functionality of the component and are correctly used.


53-62: LGTM! Ref forwarding is correctly implemented.

The function correctly forwards the ref and sets the display name.

live/src/services/page.service.ts (2)

1-4: LGTM! Imports are appropriate.

The imports are necessary for the functionality of the service and are correctly used.


6-9: LGTM! Class structure is appropriate.

The class is well-structured and correctly extends APIService.

web/core/components/pages/editor/header/mobile-root.tsx (3)

Line range hint 1-8: LGTM! Imports are appropriate.

The imports are necessary for the functionality of the component and are correctly used.


Line range hint 10-20: LGTM! Type definition is appropriate.

The type definition is well-structured and the removal of handleSaveDescription is correctly reflected.


Line range hint 22-46: LGTM! Function implementation is appropriate.

The function is well-structured and the removal of handleSaveDescription is correctly reflected.

packages/ui/package.json (3)

9-9: Impact of adding "type": "module".

Adding "type": "module" shifts the project to ECMAScript modules, affecting module resolution strategy. Ensure all imports/exports are updated accordingly.


16-17: Simplification of build and development scripts.

The build and development scripts have been simplified to use tsup directly. Ensure the default configurations provided by tsup align with the project's requirements.


53-53: Addition of "@types/lodash" and update of tsup version.

  • The addition of "@types/lodash" enhances type safety and developer experience when using Lodash.
  • Updating tsup to ^7.2.0 may introduce new features or optimizations. Review the tsup changelog for any breaking changes or new features.

Also applies to: 68-68

packages/editor/package.json (2)

18-22: Enhancement of module export capabilities.

The new entry for ./lib in exports improves compatibility and usability for consumers of the package by supporting various module loading contexts.


38-38: Addition of new dependency "@hocuspocus/provider".

The addition of "@hocuspocus/provider" with version ^2.13.5 expands the functionality or features of the package. Ensure this dependency aligns with the project's requirements and review its documentation for proper integration.

packages/editor/src/core/hooks/use-read-only-collaborative-editor.ts (6)

1-10: LGTM! Imports and type definitions are appropriate.

The imports and type definitions are necessary for the functionality of the read-only collaborative editor hook.


12-24: LGTM! Comprehensive type definition.

The type definition for ReadOnlyCollaborativeEditorProps is comprehensive and covers all necessary properties for the read-only collaborative editor.


38-56: LGTM! Proper initialization and cleanup of HocuspocusProvider.

The initialization and cleanup of the HocuspocusProvider are handled correctly, ensuring proper resource management.


57-63: LGTM! Integration of IndexeddbPersistence for offline support.

The integration of IndexeddbPersistence enhances the functionality of the read-only collaborative editor by providing offline support.


65-77: LGTM! Appropriate usage of useReadOnlyEditor hook.

The usage of useReadOnlyEditor to initialize the editor with the provided properties is appropriate and aligns with the requirements of the read-only collaborative editor.


79-80: LGTM! Clear return statement.

The return statement provides the editor instance and a boolean indicating if IndexedDB is synced, which is necessary for the consumers of the hook.

packages/editor/src/core/components/editors/document/collaborative-editor.tsx (5)

4-5: LGTM! Imports for collaborative editing are correctly added.

The new imports for IssueWidget, useCollaborativeEditor, and ICollaborativeDocumentEditor are necessary for the new collaborative editing functionality.

Also applies to: 9-9, 11-11


Line range hint 13-26:
LGTM! Component definition and props destructuring are correct.

The component CollaborativeDocumentEditor is correctly defined, and the props are appropriately destructured to include new properties for collaborative editing.


Line range hint 28-35:
LGTM! State and helper function definitions are correct.

The state for hideDragHandleOnMouseLeave and the helper function setHideDragHandleFunction are correctly implemented and utilized.


36-43: LGTM! Extensions array and conditional inclusion of IssueWidget are correct.

The extensions array is correctly defined, and IssueWidget is conditionally included based on embedHandler.issue.


Line range hint 46-88:
LGTM! Use of useCollaborativeEditor hook and rendering logic are correct.

The useCollaborativeEditor hook is correctly used, and the rendering logic is appropriately updated.

packages/editor/src/core/extensions/core-without-props.tsx (3)

9-15: LGTM! Imports for new extensions are correctly added.

The new imports for CustomCodeBlockExtensionWithoutProps and IssueWidgetWithoutProps are necessary for the new extension configurations.


78-78: LGTM! Updates to CoreEditorExtensionsWithoutProps are correct.

The function is correctly updated to include CustomCodeBlockExtensionWithoutProps and remove certain other extensions.


86-86: LGTM! Addition of DocumentEditorExtensionsWithoutProps is correct.

The new function DocumentEditorExtensionsWithoutProps is correctly implemented to include IssueWidgetWithoutProps.

packages/editor/src/core/hooks/use-read-only-editor.ts (1)

14-14: LGTM! Making initialValue optional is correct.

The change to make the initialValue property optional in the CustomReadOnlyEditorProps interface is correctly implemented.

web/core/components/pages/editor/header/root.tsx (2)

Line range hint 14-14:
Verify the removal of handleSaveDescription.

Ensure that all references to handleSaveDescription have been removed from the codebase to avoid potential runtime errors.

Verification successful

Verify the removal of handleSaveDescription.

All references to handleSaveDescription have been removed from the root.tsx file, and it does not affect the functionality of the component. The references found in use-auto-save.tsx are not related to root.tsx.

  • web/core/hooks/use-auto-save.tsx
Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify the removal of `handleSaveDescription`.

# Test: Search for any remaining references to `handleSaveDescription`. Expect: No occurrences.
rg --type tsx 'handleSaveDescription'

Length of output: 65


Script:

#!/bin/bash
# Description: Verify the removal of `handleSaveDescription`.

# Test: Search for any remaining references to `handleSaveDescription`. Expect: No occurrences.
rg 'handleSaveDescription' --glob '*.ts' --glob '*.tsx' --glob '*.jsx'

Length of output: 815


Script:

#!/bin/bash
# Description: Verify the usage of `useAutoSave`.

# Test: Search for any references to `useAutoSave`. Expect: Determine if it is used in `root.tsx` or other relevant files.
rg 'useAutoSave' --glob '*.ts' --glob '*.tsx' --glob '*.jsx'

Length of output: 260


Line range hint 16-54:
LGTM! Verify the functionality of PageEditorHeaderRoot.

The code changes are approved.

However, ensure that the PageEditorHeaderRoot component still functions as intended without the handleSaveDescription prop.

web/core/components/pages/editor/header/extra-options.tsx (2)

26-26: Verify the removal of handleSaveDescription.

Ensure that all references to handleSaveDescription have been removed from the codebase to avoid potential runtime errors.


Line range hint 29-67:
LGTM! Verify the functionality of PageExtraOptions.

The code changes are approved.

However, ensure that the PageExtraOptions component still functions as intended without the handleSaveDescription prop.

web/core/components/pages/editor/page-root.tsx (1)

Line range hint 1-67:
LGTM! Verify the functionality of PageRoot.

The code changes are approved.

However, ensure that the PageRoot component still functions as intended without the removed functionalities.


<details>
<summary>Tools</summary>

<details>
<summary>Biome</summary><blockquote>

[error] 28-28: Unnecessary use of boolean literals in conditional expression.

Simplify your code by directly assigning the result without using a ternary operator.
If your goal is negation, you may use the logical NOT (!) or double NOT (!!) operator for clearer and concise code.
 Check for more details about NOT operator.
Unsafe fix: Remove the conditional expression with


(lint/complexity/noUselessTernary)

</blockquote></details>

</details>

</blockquote></details>
<details>
<summary>live/src/index.ts (5)</summary><blockquote>

`1-11`: **LGTM! Imports and initial setup are appropriate.**

The imports cover necessary modules for setting up a real-time collaboration server.

---

`13-40`: **LGTM! Server configuration and authentication handling are robust.**

The authentication logic handles missing credentials and unsuccessful attempts effectively.

---

`41-87`: **LGTM! Database extension configuration is appropriate.**

The `fetch` and `store` functions handle page descriptions effectively, using cookies and request parameters for authentication.

<details>
<summary>Tools</summary>

<details>
<summary>Biome</summary><blockquote>

[error] 57-66: Promise executor functions should not be `async`.



(lint/suspicious/noAsyncPromiseExecutor)

---

[error] 82-86: Promise executor functions should not be `async`.



(lint/suspicious/noAsyncPromiseExecutor)

</blockquote></details>

</details>

---

`91-95`: **LGTM! Server and WebSocket setup are correct.**

The server handles WebSocket connections on the `/collaboration` route effectively.

---

`97-97`: **LGTM! Server listening setup is correct.**

The server listens on port 3003 as expected.

</blockquote></details>
<details>
<summary>packages/editor/src/core/types/editor.ts (5)</summary><blockquote>

`8-8`: **LGTM! Imports are appropriate.**

The imports cover necessary types for defining collaborative editing features.

---

`53-60`: **LGTM! `ICollaborativeDocumentEditor` interface is well-defined.**

The interface includes necessary properties for real-time collaboration and embedded content handling.

---

`77-83`: **LGTM! `ICollaborativeDocumentReadOnlyEditor` interface is well-defined.**

The interface includes necessary properties for real-time collaboration and embedded content handling in a read-only context.

---

`85-88`: **LGTM! `IDocumentReadOnlyEditor` interface is well-defined.**

The interface includes necessary properties for embedded content handling in a read-only context.

---

`90-101`: **LGTM! `TUserDetails` and `TRealtimeConfig` types are well-defined.**

The types include necessary properties for user details and real-time configuration settings.

</blockquote></details>
<details>
<summary>packages/editor/src/core/hooks/use-collaborative-editor.ts (6)</summary><blockquote>

`1-16`: **LGTM! Imports and initial setup are appropriate.**

The imports cover necessary modules and types for setting up a collaborative editor hook.

---

Line range hint `18-35`: 
**LGTM! `CollaborativeEditorProps` type is well-defined.**

The type includes necessary properties for the collaborative editor hook.

---

`38-65`: **LGTM! `useCollaborativeEditor` hook initialization is correct.**

The hook initializes the Hocuspocus provider with necessary parameters for real-time collaboration.

---

`67-81`: **LGTM! Effect hooks for provider lifecycle management are well-implemented.**

The hooks ensure proper destruction, disconnection, and setup for IndexedDB persistence.

---

Line range hint `83-105`: 
**LGTM! Editor configuration is correct.**

The hook configures the editor with necessary extensions, handlers, and properties for collaborative editing.

---

`106-106`: **LGTM! Return statement of the hook is correct.**

The hook returns the configured editor object as expected.

</blockquote></details>
<details>
<summary>docker-compose-local.yml (5)</summary><blockquote>

`89-92`: **LGTM! The build attribute is correctly configured.**

The `build` attribute is set up to use the specified Dockerfile for the `live` service.

---

`93-93`: **LGTM! The restart attribute is correctly configured.**

The `restart` attribute ensures the service restarts unless explicitly stopped.

---

`94-95`: **LGTM! The networks attribute is correctly configured.**

The `networks` attribute connects the service to the `dev_env` network.

---

`96-97`: **LGTM! The volumes attribute is correctly configured.**

The `volumes` attribute maps the local `./live` directory to `/app/live` within the container.

---

`98-101`: **LGTM! The depends_on attribute is correctly configured.**

The `depends_on` attribute ensures that the `live` service starts only after the `api`, `worker`, and `web` services are up and running.

</blockquote></details>
<details>
<summary>packages/editor/src/core/extensions/code/without-props.tsx (4)</summary><blockquote>

`13-31`: **LGTM! The Tab keyboard shortcut handler is correctly implemented.**

The handler correctly checks the selection state and inserts a tab character. Error handling is implemented using a try-catch block.

---

`33-66`: **LGTM! The ArrowUp keyboard shortcut handler is correctly implemented.**

The handler correctly checks the cursor position and inserts a new paragraph if necessary. Error handling is implemented using a try-catch block.

---

`68-107`: **LGTM! The ArrowDown keyboard shortcut handler is correctly implemented.**

The handler correctly checks the cursor position and exits the code block if necessary. Error handling is implemented using a try-catch block.

---

`111-115`: **LGTM! The configure method is correctly implemented.**

The configuration options are correctly set up to use lowlight and specify default language and exit options.

</blockquote></details>
<details>
<summary>packages/editor/src/core/extensions/mentions/extension.tsx (10)</summary><blockquote>

Line range hint `17-19`: 
**LGTM! The addStorage method is correctly implemented.**

The method correctly initializes the storage with `mentionsOpen` set to `false`.

---

Line range hint `20-38`: 
**LGTM! The addAttributes method is correctly implemented.**

The method correctly defines attributes with default values.

---

Line range hint `39-41`: 
**LGTM! The addNodeView method is correctly implemented.**

The method correctly returns a `ReactNodeViewRenderer` for the `MentionNodeView`.

---

Line range hint `42-46`: 
**LGTM! The parseHTML method is correctly implemented.**

The method correctly defines the HTML tag for the mention component.

---

Line range hint `47-49`: 
**LGTM! The renderHTML method is correctly implemented.**

The method correctly returns the HTML representation of the mention component.

---

Line range hint `50-52`: 
**LGTM! The HTMLAttributes configuration option is correctly implemented.**

The option correctly sets the class attribute for the mention component.

---

Line range hint `53-53`: 
**LGTM! The readonly configuration option is correctly implemented.**

The option correctly sets the readonly state for the extension.

---

Line range hint `54-54`: 
**LGTM! The mentionHighlights configuration option is correctly implemented.**

The option correctly sets the function to fetch mention highlights.

---

Line range hint `55-108`: 
**LGTM! The suggestion configuration option is correctly implemented.**

The option correctly sets the rendering logic for mention suggestions, including handling start, update, keydown, and exit events.

---

`10-10`: **Verify the impact of making CustomMentionOptions non-exported.**

The `CustomMentionOptions` interface is no longer exported, which might impact external modules that rely on this interface.

<details>
<summary>Verification successful</summary>



---

<!-- [monologue]
[task review_file_3/3 interface_1/1] Continue verifying the impact of making `CustomMentionOptions` non-exported.
[observations] The search results show no export statements involving `CustomMentionOptions`.
[analysis] The absence of export statements confirms that `CustomMentionOptions` was not exported and thus not used externally. This means making it non-exported should not impact any external modules.
[actions] Conclude the verification process and generate the final response.
-->

**The `CustomMentionOptions` interface is not exported and is only used internally. Therefore, making it non-exported will not impact any external modules.**

- No export statements involving `CustomMentionOptions` were found in the codebase.



</details>


<details>
<summary>Scripts executed</summary>

The following scripts were executed for the analysis:

Script:

```shell
#!/bin/bash
# Description: Verify the impact of making CustomMentionOptions non-exported.

# Test: Search for the usage of CustomMentionOptions in the codebase. Expect: No external usage.
rg --type ts 'CustomMentionOptions'

Length of output: 491


Script:

#!/bin/bash
# Description: Verify if CustomMentionOptions was ever exported.

# Test: Search for any export statements involving CustomMentionOptions. Expect: No export statements.
rg --type ts 'export .*CustomMentionOptions'

Length of output: 46

web/core/components/pages/editor/header/options-dropdown.tsx (4)

24-24: LGTM!

The code changes are approved.


119-119: LGTM!

The code changes are approved.


126-126: LGTM!

The code changes are approved.


133-133: LGTM!

The code changes are approved.

packages/editor/src/core/extensions/custom-link/extension.tsx (1)

139-139: LGTM!

The code changes are approved.

web/app/[workspaceSlug]/(projects)/projects/(detail)/[projectId]/pages/(detail)/header.tsx (2)

32-34: Verify the removal of isContentEditable and isSubmitting properties.

The removal of isContentEditable and isSubmitting properties from the usePage hook suggests a significant change in how the component manages these states. Ensure that the new state management approach is consistent and that these properties are no longer required.


Line range hint 138-182: Verify the removal of the save button.

The removal of the conditional Button for saving changes indicates a significant change in functionality. Ensure that the ability to save changes has been appropriately handled elsewhere in the application.

web/core/components/pages/editor/editor-body.tsx (4)

1-11: LGTM! Collaborative editor components imported.

The import statements have been updated to include new collaborative editor components, indicating a shift towards real-time collaborative features.


18-19: LGTM! New import for LIVE_BASE_URL.

The LIVE_BASE_URL constant is imported from common.helper, likely used for configuring the real-time collaboration URL.


92-102: LGTM! Real-time collaboration configuration.

The realtimeConfig object created with useMemo enhances the component's ability to manage real-time updates based on the current workspace and project context.


Line range hint 138-182: LGTM! Integration of collaborative editor components.

The collaborative editor components are integrated with the new realtimeConfig and user data, enabling real-time collaboration features.

packages/editor/src/core/hooks/use-editor.ts (3)

58-62: LGTM! Improved state and ref organization.

The savedSelection state and its corresponding ref are now declared earlier in the hook, improving the clarity of state management.


Line range hint 92-92: Verify the removal of the provider parameter.

The removal of the provider parameter and related functionality indicates a shift in how the editor manages state related to collaborative editing. Ensure that the new approach aligns with the overall design and functionality requirements.


Line range hint 138-138: LGTM! Streamlined flow and readability improvements.

The overall flow of the useEditor hook has been streamlined, with redundant lines removed, enhancing readability and maintainability.

apiserver/plane/app/views/issue/bulk_operations.py (4)

24-24: Import statement for ERROR_CODES looks good.

The import statement is correctly added and aligns with the changes mentioned in the summary.


63-76: Use of ERROR_CODES for invalid issue dates is appropriate.

The change replaces a hard-coded error code with a value from the ERROR_CODES dictionary, improving maintainability.


134-136: Use of ERROR_CODES for invalid issue start date is appropriate.

The change replaces a hard-coded error code with a value from the ERROR_CODES dictionary, improving maintainability.


170-172: Use of ERROR_CODES for invalid issue target date is appropriate.

The change replaces a hard-coded error code with a value from the ERROR_CODES dictionary, improving maintainability.

apiserver/plane/app/views/issue/archive.py (2)

49-49: Import statement for ERROR_CODES looks good.

The import statement is correctly added and aligns with the changes mentioned in the summary.


345-348: Use of ERROR_CODES for invalid archive state group is appropriate.

The change replaces a hard-coded error code with a value from the ERROR_CODES dictionary, improving maintainability.

apiserver/plane/app/views/page/base.py (3)

36-36: Import statement for ERROR_CODES looks good.

The import statement is correctly added and aligns with the changes mentioned in the summary.


475-479: Use of ERROR_CODES for locked page error is appropriate.

The change replaces a hard-coded error code with a value from the ERROR_CODES dictionary, improving maintainability.


484-488: Use of ERROR_CODES for archived page error is appropriate.

The change replaces a hard-coded error code with a value from the ERROR_CODES dictionary, improving maintainability.

live/src/services/user.service.ts Show resolved Hide resolved
live/src/services/user.service.ts Show resolved Hide resolved
Comment on lines +8 to +18
export abstract class APIService {
protected baseURL: string;
private axiosInstance: AxiosInstance;

constructor(baseURL: string) {
this.baseURL = baseURL;
this.axiosInstance = axios.create({
baseURL,
withCredentials: true,
});
}
Copy link
Contributor

Choose a reason for hiding this comment

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

Consider adding error handling for axios instance creation.

While creating the axios instance, consider adding error handling to manage any potential issues during initialization.

- this.axiosInstance = axios.create({
+ try {
+   this.axiosInstance = axios.create({
    baseURL,
    withCredentials: true,
  });
+ } catch (error) {
+   console.error("Failed to create axios instance:", error);
+   throw error;
+ }
Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
export abstract class APIService {
protected baseURL: string;
private axiosInstance: AxiosInstance;
constructor(baseURL: string) {
this.baseURL = baseURL;
this.axiosInstance = axios.create({
baseURL,
withCredentials: true,
});
}
constructor(baseURL: string) {
this.baseURL = baseURL;
try {
this.axiosInstance = axios.create({
baseURL,
withCredentials: true,
});
} catch (error) {
console.error("Failed to create axios instance:", error);
throw error;
}
}


config();

export const API_BASE_URL = process.env.API_BASE_URL ?? "";
Copy link
Contributor

Choose a reason for hiding this comment

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

Ensure API_BASE_URL is set.

If API_BASE_URL is not set, an empty string will be used, which might lead to unexpected behavior. Consider adding a warning or error if the environment variable is not set.

- export const API_BASE_URL = process.env.API_BASE_URL ?? "";
+ export const API_BASE_URL = process.env.API_BASE_URL;
+ if (!API_BASE_URL) {
+   console.warn("API_BASE_URL is not set. Defaulting to an empty string.");
+ }
Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
export const API_BASE_URL = process.env.API_BASE_URL ?? "";
export const API_BASE_URL = process.env.API_BASE_URL;
if (!API_BASE_URL) {
console.warn("API_BASE_URL is not set. Defaulting to an empty string.");
}

live/src/page.ts Outdated Show resolved Hide resolved
live/src/authentication.ts Outdated Show resolved Hide resolved
live/src/authentication.ts Show resolved Hide resolved
live/src/authentication.ts Outdated Show resolved Hide resolved
web/core/components/pages/editor/page-root.tsx Outdated Show resolved Hide resolved
Comment on lines +57 to +66
return new Promise(async (resolve) => {
if (documentType === "project_page") {
const fetchedData = await fetchPageDescriptionBinary(
params,
pageId,
cookie,
);
resolve(fetchedData);
}
});
Copy link
Contributor

Choose a reason for hiding this comment

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

Avoid using async functions inside Promise executor functions.

Using async functions inside Promise executor functions can lead to unexpected behavior. Refactor the code to avoid this pattern.

-        return new Promise(async (resolve) => {
+        return new Promise((resolve) => {
           (async () => {
             if (documentType === "project_page") {
               const fetchedData = await fetchPageDescriptionBinary(
                 params,
                 pageId,
                 cookie,
               );
               resolve(fetchedData);
             }
           })();
         });

-        return new Promise(async () => {
+        return new Promise((resolve) => {
           (async () => {
             if (documentType === "project_page") {
               await updatePageDescription(params, pageId, state, cookie);
               resolve();
             }
           })();
         });

Also applies to: 82-86

Tools
Biome

[error] 57-66: Promise executor functions should not be async.

(lint/suspicious/noAsyncPromiseExecutor)

Copy link
Contributor

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

Review details

Configuration used: CodeRabbit UI
Review profile: CHILL

Commits

Files that changed from the base of the PR and between 0d9b346 and b354547.

Files selected for processing (6)
  • apiserver/plane/app/views/page/base.py (3 hunks)
  • live/src/index.ts (1 hunks)
  • live/src/page.ts (1 hunks)
  • packages/editor/src/core/extensions/core-without-props.tsx (4 hunks)
  • packages/editor/src/core/hooks/use-collaborative-editor.ts (3 hunks)
  • packages/editor/src/core/hooks/use-editor.ts (5 hunks)
Files skipped from review as they are similar to previous changes (2)
  • apiserver/plane/app/views/page/base.py
  • live/src/page.ts
Additional context used
Biome
live/src/index.ts

[error] 57-66: Promise executor functions should not be async.

(lint/suspicious/noAsyncPromiseExecutor)


[error] 82-86: Promise executor functions should not be async.

(lint/suspicious/noAsyncPromiseExecutor)

Additional comments not posted (12)
packages/editor/src/core/extensions/core-without-props.tsx (3)

9-17: LGTM!

The new import statements for various custom extensions are correct and necessary for the changes made in the file.


86-86: LGTM!

The new function DocumentEditorExtensionsWithoutProps is correctly implemented.


Line range hint 19-84: Ensure the removal of old extensions is intentional.

The new configuration of CoreEditorExtensionsWithoutProps looks good. However, verify that the removal of CustomKeymap, CustomTypographyExtension, and CustomCodeBlockExtension is intentional and does not affect the functionality.

Verification successful

The removal of old extensions appears to be intentional and does not affect the functionality.

  • No usage of CustomKeymap, CustomTypographyExtension, and CustomCodeBlockExtension was found in the codebase.
Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify the removal of old extensions is intentional and does not affect the functionality.

# Test: Search for the old extensions in the codebase. Expect: No usage of the removed extensions.
rg --type javascript 'CustomKeymap|CustomTypographyExtension|CustomCodeBlockExtension'

Length of output: 123


Script:

#!/bin/bash
# Description: Verify the removal of old extensions is intentional and does not affect the functionality.

# Test: Search for the old extensions in the codebase. Expect: No usage of the removed extensions.
rg --type js 'CustomKeymap|CustomTypographyExtension|CustomCodeBlockExtension'

Length of output: 80

live/src/index.ts (2)

1-11: LGTM!

The new import statements for various modules required for the server setup are correct and necessary for the changes made in the file.


13-40: Ensure proper error handling in authentication.

The server configuration looks good. However, ensure that proper error handling is in place for the authentication process to avoid potential security issues.

Verification successful

Proper error handling is in place in the authentication process.

The handleAuthentication function includes appropriate error handling mechanisms, ensuring that various failure scenarios are addressed correctly.

  • Token mismatch: throw Error("Token doesn't match");
  • Incomplete query params: throw Error("Incomplete query params, workspaceSlug or projectId missing");
  • Invalid document type: throw Error("Invalid document type provided");
Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify proper error handling in the authentication process.

# Test: Search for error handling in the authentication process. Expect: Proper error handling in place.
rg --type javascript 'handleAuthentication'

Length of output: 78


Script:

#!/bin/bash
# Description: Verify proper error handling in the authentication process.

# Test: Search for error handling in the authentication process. Expect: Proper error handling in place.
rg --type typescript 'handleAuthentication'

Length of output: 78


Script:

#!/bin/bash
# Description: Verify proper error handling in the authentication process.

# Test: Search for error handling in the authentication process. Expect: Proper error handling in place.
rg 'handleAuthentication' --glob '*.ts'

Length of output: 259


Script:

#!/bin/bash
# Description: Extract and inspect the handleAuthentication function for proper error handling.

# Extract the handleAuthentication function from live/src/authentication.ts
ast-grep --lang typescript --pattern $'export const handleAuthentication = async ($_: Props) => {
  $$$
}' live/src/authentication.ts

Length of output: 2575

packages/editor/src/core/hooks/use-collaborative-editor.ts (3)

1-16: LGTM!

The new import statements for various modules required for the collaborative editor are correct and necessary for the changes made in the file.


Line range hint 18-36: LGTM!

The new type definition CollaborativeEditorProps is correct and does not introduce any issues.


Line range hint 38-107: Ensure proper cleanup of resources.

The new implementation of useCollaborativeEditor looks good. However, ensure that proper cleanup of resources is in place to avoid potential memory leaks.

Verification successful

Proper cleanup of resources confirmed.

The useCollaborativeEditor function includes appropriate cleanup logic within the useEffect and useLayoutEffect hooks to ensure that resources are properly managed and potential memory leaks are avoided.

  • The useEffect hook destroys and disconnects the provider on unmount.
  • The useLayoutEffect hook destroys the localProvider on unmount.
Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify proper cleanup of resources in the useCollaborativeEditor function.

# Test: Search for resource cleanup in the function. Expect: Proper cleanup of resources in place.
rg --type javascript 'useCollaborativeEditor'

Length of output: 80


Script:

#!/bin/bash
# Description: Verify proper cleanup of resources in the useCollaborativeEditor function.

# Search for useEffect and useLayoutEffect hooks in the specific file to check for cleanup logic.
rg 'useEffect|useLayoutEffect' packages/editor/src/core/hooks/use-collaborative-editor.ts

Length of output: 191


Script:

#!/bin/bash
# Description: Extract the full content of useEffect and useLayoutEffect hooks to review the cleanup logic.

# Extract the content of useEffect and useLayoutEffect hooks.
rg -A 10 'useEffect|useLayoutEffect' packages/editor/src/core/hooks/use-collaborative-editor.ts

Length of output: 997

packages/editor/src/core/hooks/use-editor.ts (4)

62-66: LGTM!

The adjustments in the organization of state and refs within the useEditor hook improve the clarity of state management.


Line range hint 88-104:
LGTM!

The adjustments in the useEffect hook for syncing SWR data improve the handling of the value prop, ensuring that the editor content is synced correctly with the external value.


Line range hint 32-48:
Verify the impact of removing the provider property.

The removal of the provider property from the CustomEditorProps interface simplifies the interface but might affect other parts of the codebase that relied on this property.


Line range hint 50-66:
Verify the impact of removing the provider parameter.

The removal of the provider parameter from the useEditor hook simplifies the hook but might affect other parts of the codebase that relied on this parameter.

Verification successful

Verify the impact of removing the provider parameter.

The removal of the provider parameter from the useEditor hook does not impact the rest of the codebase, as there are no remaining references to this parameter.

  • No occurrences of useEditor with provider parameter were found.
Scripts executed

The following scripts were executed for the analysis:

Script:

#!/bin/bash
# Description: Verify the impact of removing the `provider` parameter from the `useEditor` hook.

# Test: Search for the usage of the `useEditor` hook with the `provider` parameter. Expect: No occurrences of `useEditor` with `provider` parameter.
rg --type typescript --type tsx --type javascript --type jsx -A 5 $'useEditor({ provider:'

Length of output: 198


Script:

#!/bin/bash
# Description: Verify the impact of removing the `provider` parameter from the `useEditor` hook.

# Test 1: Search for the `useEditor` function definition to confirm the removal of the `provider` parameter.
rg --type typescript --type tsx --type javascript --type jsx 'useEditor' -A 10

# Test 2: Search for the usage of the `useEditor` hook with the `provider` parameter.
rg --type typescript --type tsx --type javascript --type jsx -A 5 'useEditor\(\{[^}]*provider:'

Length of output: 246


Script:

#!/bin/bash
# Description: Verify the impact of removing the `provider` parameter from the `useEditor` hook.

# Test 1: Search for the `useEditor` function definition to confirm the removal of the `provider` parameter.
rg --type ts --type tsx --type js --type jsx 'useEditor' -A 10

# Test 2: Search for the usage of the `useEditor` hook with the `provider` parameter.
rg --type ts --type tsx --type js --type jsx -A 5 'useEditor\(\{[^}]*provider:'

Length of output: 200


Script:

#!/bin/bash
# Description: Verify the impact of removing the `provider` parameter from the `useEditor` hook.

# Find all relevant files
fd -e ts -e tsx -e js -e jsx > files.txt

# Test 1: Search for the `useEditor` function definition to confirm the removal of the `provider` parameter.
rg 'useEditor' -A 10 -f files.txt

# Test 2: Search for the usage of the `useEditor` hook with the `provider` parameter.
rg -A 5 'useEditor\(\{[^}]*provider:' -f files.txt

Length of output: 235


Script:

#!/bin/bash
# Description: Verify the impact of removing the `provider` parameter from the `useEditor` hook.

# Test 1: Search for the `useEditor` function definition to confirm the removal of the `provider` parameter.
fd -e ts -e tsx -e js -e jsx | xargs rg 'useEditor' -A 10

# Test 2: Search for the usage of the `useEditor` hook with the `provider` parameter.
fd -e ts -e tsx -e js -e jsx | xargs rg -A 5 'useEditor\(\{[^}]*provider:'

Length of output: 10069

Comment on lines +41 to +87
extensions: [
new Logger(),
new Database({
fetch: async ({
documentName: pageId,
requestHeaders,
requestParameters,
}) => {
// request headers
const cookie = requestHeaders.cookie?.toString();
// query params
const params = requestParameters;
const documentType = params.get("documentType")?.toString() as
| TDocumentTypes
| undefined;

return new Promise(async (resolve) => {
if (documentType === "project_page") {
const fetchedData = await fetchPageDescriptionBinary(
params,
pageId,
cookie,
);
resolve(fetchedData);
}
});
},
store: async ({
state,
documentName: pageId,
requestHeaders,
requestParameters,
}) => {
// request headers
const cookie = requestHeaders.cookie?.toString();
// query params
const params = requestParameters;
const documentType = params.get("documentType")?.toString() as
| TDocumentTypes
| undefined;

return new Promise(async () => {
if (documentType === "project_page") {
await updatePageDescription(params, pageId, state, cookie);
}
});
},
Copy link
Contributor

Choose a reason for hiding this comment

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

Avoid using async functions inside Promise executor functions.

Using async functions inside Promise executor functions can lead to unexpected behavior. Refactor the code to avoid this pattern.

-        return new Promise(async (resolve) => {
+        return new Promise((resolve) => {
           (async () => {
             if (documentType === "project_page") {
               const fetchedData = await fetchPageDescriptionBinary(
                 params,
                 pageId,
                 cookie,
               );
               resolve(fetchedData);
             }
           })();
         });

-        return new Promise(async () => {
+        return new Promise((resolve) => {
           (async () => {
             if (documentType === "project_page") {
               await updatePageDescription(params, pageId, state, cookie);
               resolve();
             }
           })();
         });
Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
extensions: [
new Logger(),
new Database({
fetch: async ({
documentName: pageId,
requestHeaders,
requestParameters,
}) => {
// request headers
const cookie = requestHeaders.cookie?.toString();
// query params
const params = requestParameters;
const documentType = params.get("documentType")?.toString() as
| TDocumentTypes
| undefined;
return new Promise(async (resolve) => {
if (documentType === "project_page") {
const fetchedData = await fetchPageDescriptionBinary(
params,
pageId,
cookie,
);
resolve(fetchedData);
}
});
},
store: async ({
state,
documentName: pageId,
requestHeaders,
requestParameters,
}) => {
// request headers
const cookie = requestHeaders.cookie?.toString();
// query params
const params = requestParameters;
const documentType = params.get("documentType")?.toString() as
| TDocumentTypes
| undefined;
return new Promise(async () => {
if (documentType === "project_page") {
await updatePageDescription(params, pageId, state, cookie);
}
});
},
return new Promise((resolve) => {
(async () => {
if (documentType === "project_page") {
const fetchedData = await fetchPageDescriptionBinary(
params,
pageId,
cookie,
);
resolve(fetchedData);
}
})();
});
return new Promise((resolve) => {
(async () => {
if (documentType === "project_page") {
await updatePageDescription(params, pageId, state, cookie);
resolve();
}
})();
});
Tools
Biome

[error] 57-66: Promise executor functions should not be async.

(lint/suspicious/noAsyncPromiseExecutor)


[error] 82-86: Promise executor functions should not be async.

(lint/suspicious/noAsyncPromiseExecutor)

Copy link
Contributor

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

Review details

Configuration used: CodeRabbit UI
Review profile: CHILL

Commits

Files that changed from the base of the PR and between b354547 and f38fd54.

Files selected for processing (3)
  • live/src/authentication.ts (1 hunks)
  • live/src/page.ts (1 hunks)
  • web/core/components/pages/editor/page-root.tsx (4 hunks)
Files skipped from review as they are similar to previous changes (3)
  • live/src/authentication.ts
  • live/src/page.ts
  • web/core/components/pages/editor/page-root.tsx

@aaryan610 aaryan610 changed the base branch from preview to develop July 22, 2024 09:54
@SatishGandham SatishGandham merged commit 2ea5077 into develop Jul 22, 2024
13 of 14 checks passed
@SatishGandham SatishGandham deleted the feat-realtime-sync branch July 22, 2024 13:13
sriramveeraghanta added a commit that referenced this pull request Jul 26, 2024
* init: live server for editor realtime sync

* chore: authentication added

* chore: updated logic to convert html to binary for old pages

* chore: added description json on page update

* chore: made all functions generic

* chore: save description in json and html formats

* refactor: document editor components

* chore: uncomment ui package components

* fix: without props extensions refactor

* fix: merge conflicts resolved from preview

* chore: init docker compose

* chore: pages custom error codes

* chore: add health check endpoint to the live server

* chore: update without props extensions type

* chore: better error handling

* chore: update react-hook-form versions

---------

Co-authored-by: NarayanBavisetti <narayan3119@gmail.com>
Co-authored-by: sriram veeraghanta <veeraghanta.sriram@gmail.com>
sriramveeraghanta added a commit that referenced this pull request Sep 2, 2024
* [WEB-1116] feat: pages realtime sync (#5057)

* init: live server for editor realtime sync

* chore: authentication added

* chore: updated logic to convert html to binary for old pages

* chore: added description json on page update

* chore: made all functions generic

* chore: save description in json and html formats

* refactor: document editor components

* chore: uncomment ui package components

* fix: without props extensions refactor

* fix: merge conflicts resolved from preview

* chore: init docker compose

* chore: pages custom error codes

* chore: add health check endpoint to the live server

* chore: update without props extensions type

* chore: better error handling

* chore: update react-hook-form versions

---------

Co-authored-by: NarayanBavisetti <narayan3119@gmail.com>
Co-authored-by: sriram veeraghanta <veeraghanta.sriram@gmail.com>

* fix: docker related fixes

* fix: module type fixes

* fix: nginx update

* fix: adding live server workflow

* fix: workflow fixes

* fix: docker compose fixes

* fix: workflow fixes

* fix: path config

* fix: docker compose warnings

* fix: nginx port forwarding

* fix: update docker compose with new env

* fix: env var fixes

* fix: error handling

* fix: docker compose env var

* fix: compose fixes

* chore: update server start message

* chore: handle errors

* fix: build errors

* chore: update port

* chore: update server port

* chore: show error on authentication fail

* chore: show error on authentication fail

* feat: add redis extension

* chore: updated restore version logic

---------

Co-authored-by: NarayanBavisetti <narayan3119@gmail.com>
Co-authored-by: sriram veeraghanta <veeraghanta.sriram@gmail.com>
Co-authored-by: Palanikannan M <akashmalinimurugu@gmail.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants