Skip to content

Comments

feat: Implement project templates feature#13

Open
pqhung3007 wants to merge 4 commits intopreviewfrom
claude/implement-project-templates-0191Gy3Hz5LDsksyoo8z84dE
Open

feat: Implement project templates feature#13
pqhung3007 wants to merge 4 commits intopreviewfrom
claude/implement-project-templates-0191Gy3Hz5LDsksyoo8z84dE

Conversation

@pqhung3007
Copy link
Owner

This commit adds a comprehensive project templates feature that allows users to create, manage, and use reusable project templates.

Backend Changes:

  • Add ProjectTemplate model with fields for template configuration, optional features, and content
  • Create serializers for template CRUD operations with validation
  • Implement API views for template management (list, create, update, delete, use)
  • Add URL routes for template endpoints at /api/workspaces/{slug}/project-templates/
  • Create database migration for project_templates table with unique constraints

Frontend Changes:

  • Add TypeScript types for IProjectTemplate and related interfaces
  • Create ProjectTemplateService for API interactions
  • Implement MobX store (ProjectTemplateStore) for state management
  • Add templates route to workspace settings navigation
  • Create templates page with list view, search, and empty state
  • Build ProjectTemplateCard component for displaying templates
  • Implement CreateProjectTemplateModal for template creation

Features:

  • Create reusable project templates with customizable properties
  • Configure optional features (modules, cycles, pages, issue types, etc.)
  • Support for custom states, labels, issue types, and initial work items
  • Track template usage statistics
  • Search and filter templates
  • Delete templates with confirmation
  • Professional empty states and UI components

This implementation follows the existing codebase patterns for consistency and maintainability.

Description

Type of Change

  • Bug fix (non-breaking change which fixes an issue)
  • Feature (non-breaking change which adds functionality)
  • Improvement (change that would cause existing functionality to not work as expected)
  • Code refactoring
  • Performance improvements
  • Documentation update

Screenshots and Media (if applicable)

Test Scenarios

References

This commit adds a comprehensive project templates feature that allows users to create, manage, and use reusable project templates.

Backend Changes:
- Add ProjectTemplate model with fields for template configuration, optional features, and content
- Create serializers for template CRUD operations with validation
- Implement API views for template management (list, create, update, delete, use)
- Add URL routes for template endpoints at /api/workspaces/{slug}/project-templates/
- Create database migration for project_templates table with unique constraints

Frontend Changes:
- Add TypeScript types for IProjectTemplate and related interfaces
- Create ProjectTemplateService for API interactions
- Implement MobX store (ProjectTemplateStore) for state management
- Add templates route to workspace settings navigation
- Create templates page with list view, search, and empty state
- Build ProjectTemplateCard component for displaying templates
- Implement CreateProjectTemplateModal for template creation

Features:
- Create reusable project templates with customizable properties
- Configure optional features (modules, cycles, pages, issue types, etc.)
- Support for custom states, labels, issue types, and initial work items
- Track template usage statistics
- Search and filter templates
- Delete templates with confirmation
- Professional empty states and UI components

This implementation follows the existing codebase patterns for consistency and maintainability.
status=status.HTTP_409_CONFLICT,
)
return Response(
{"error": str(e)},

Check warning

Code scanning / CodeQL

Information exposure through an exception Medium

Stack trace information
flows to this location and may be exposed to an external user.

Copilot Autofix

AI 3 months ago

To fix the problem, we need to stop exposing the raw error message (str(e)) from IntegrityError exceptions to the API client in the default case. Instead, we should return a generic, non-descript message (such as "A database error occurred") for any unhandled database errors, and optionally log the real error on the server side for debugging/tracing. No change is needed to error cases already handled (such as unique constraints or workspace existence). This requires:

  • Updating the except IntegrityError as e block to return a generic message for unhandled cases (line 102), instead of relaying str(e) to users.
  • Optionally, adding a server-side log message (using either print or Python’s logging module; choose logging if not shown otherwise).
  • No new imports needed — logging is in the standard library, and the rest of the code does not show a preferred logging approach.

All changes are restricted to apps/api/plane/api/views/project_template.py, specifically the relevant lines in the post method of ProjectTemplateListCreateAPIEndpoint.

Suggested changeset 1
apps/api/plane/api/views/project_template.py

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/apps/api/plane/api/views/project_template.py b/apps/api/plane/api/views/project_template.py
--- a/apps/api/plane/api/views/project_template.py
+++ b/apps/api/plane/api/views/project_template.py
@@ -98,8 +98,10 @@
                     {"name": "A template with this name already exists"},
                     status=status.HTTP_409_CONFLICT,
                 )
+            import logging
+            logging.exception("Database integrity error occurred while creating project template")
             return Response(
-                {"error": str(e)},
+                {"error": "A database error occurred. Please try again later."},
                 status=status.HTTP_400_BAD_REQUEST,
             )
         except Workspace.DoesNotExist:
EOF
@@ -98,8 +98,10 @@
{"name": "A template with this name already exists"},
status=status.HTTP_409_CONFLICT,
)
import logging
logging.exception("Database integrity error occurred while creating project template")
return Response(
{"error": str(e)},
{"error": "A database error occurred. Please try again later."},
status=status.HTTP_400_BAD_REQUEST,
)
except Workspace.DoesNotExist:
Copilot is powered by AI and may make mistakes. Always verify output.
)
except Exception as e:
return Response(
{"error": str(e)},

Check warning

Code scanning / CodeQL

Information exposure through an exception Medium

Stack trace information
flows to this location and may be exposed to an external user.

Copilot Autofix

AI 3 months ago

To fix the issue, we should avoid returning stringified exceptions directly to the user for unexpected errors, and instead return a generic error message that reveals no internal details. Specific, non-sensitive error messages for expected exceptions like IntegrityError and Workspace.DoesNotExist should be kept. For the generic Exception catch block (lines 110-114), modify the response so it returns a generic error message (e.g., "An internal server error occurred.") instead of the actual exception message. Optionally, log the actual exception (not shown in the snippet), but do not expose the details in the API response.

The changes needed are:

  • Edit the except Exception as e: block (lines 110-114) to return a generic error message in the response.

No new imports are needed as we are not adding logging or other custom behavior.


Suggested changeset 1
apps/api/plane/api/views/project_template.py

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/apps/api/plane/api/views/project_template.py b/apps/api/plane/api/views/project_template.py
--- a/apps/api/plane/api/views/project_template.py
+++ b/apps/api/plane/api/views/project_template.py
@@ -109,7 +109,7 @@
             )
         except Exception as e:
             return Response(
-                {"error": str(e)},
+                {"error": "An internal server error occurred."},
                 status=status.HTTP_500_INTERNAL_SERVER_ERROR,
             )
 
EOF
@@ -109,7 +109,7 @@
)
except Exception as e:
return Response(
{"error": str(e)},
{"error": "An internal server error occurred."},
status=status.HTTP_500_INTERNAL_SERVER_ERROR,
)

Copilot is powered by AI and may make mistakes. Always verify output.
status=status.HTTP_409_CONFLICT,
)
return Response(
{"error": str(e)},

Check warning

Code scanning / CodeQL

Information exposure through an exception Medium

Stack trace information
flows to this location and may be exposed to an external user.

Copilot Autofix

AI 3 months ago

To fix this issue in apps/api/plane/api/views/project_template.py (specifically in the patch method), the error response at line 182 should be made generic and not include the string representation of the integrity error. Instead of returning {"error": str(e)}, respond with a generic message such as {"error": "Invalid request"} or another appropriate, non-revealing message. Also, ensure proper server-side logging is present to retain the exception details for debugging (if logging is implemented locally). No new imports are required. Only the error response in the patch method under generic IntegrityError needs to be changed.

Suggested changeset 1
apps/api/plane/api/views/project_template.py

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/apps/api/plane/api/views/project_template.py b/apps/api/plane/api/views/project_template.py
--- a/apps/api/plane/api/views/project_template.py
+++ b/apps/api/plane/api/views/project_template.py
@@ -179,7 +179,7 @@
                     status=status.HTTP_409_CONFLICT,
                 )
             return Response(
-                {"error": str(e)},
+                {"error": "Invalid request."},
                 status=status.HTTP_400_BAD_REQUEST,
             )
 
EOF
@@ -179,7 +179,7 @@
status=status.HTTP_409_CONFLICT,
)
return Response(
{"error": str(e)},
{"error": "Invalid request."},
status=status.HTTP_400_BAD_REQUEST,
)

Copilot is powered by AI and may make mistakes. Always verify output.
This commit significantly enhances the project templates feature with a full multi-step
configuration interface that matches the project creation experience.

Enhanced Features:
- Multi-step modal with 5 steps: Basic Info, Features, States, Labels, Work Items
- Visual progress indicator showing current step
- Navigation between steps with Previous/Next buttons

Template Configuration Options:
1. Basic Information:
   - Template name (required)
   - Description
   - Default visibility (Public/Secret)

2. Features Configuration:
   - Toggle for Cycles
   - Toggle for Modules
   - Toggle for Views
   - Toggle for Pages
   - Toggle for Intake
   - Toggle for Issue Types
   - Toggle for Time Tracking

3. States Configuration:
   - Enable/disable custom states
   - Pre-populated with 5 default states (Backlog, Todo, In Progress, Done, Cancelled)
   - Add/remove custom states
   - Configure state name, color, and group (backlog, unstarted, started, completed, cancelled)

4. Labels Configuration:
   - Enable/disable labels
   - Add/remove custom labels
   - Configure label name and color

5. Work Items Configuration:
   - Enable/disable initial work items
   - Add/remove work items
   - Configure work item name and description

UI Improvements:
- Edit functionality integrated into template cards
- Full template details fetched when editing
- Professional multi-step modal with progress tracking
- Consistent styling with the existing project creation flow
- Color pickers for states and labels
- Removed simple modal in favor of enhanced version

This implementation ensures consistency with the existing project creation workflow
and provides a comprehensive template management experience.
This commit integrates project templates into the project creation workflow,
allowing users to start new projects from pre-configured templates.

New Features:
1. Template Selection Step:
   - Added new TEMPLATE_SELECTION step to project creation modal
   - Created ProjectTemplateSelector component with:
     - Search functionality for templates
     - "Blank Project" option to start from scratch
     - Visual template cards showing emoji/icon, name, description, and usage count
     - Selected state indication with checkmark
     - Skip option to bypass template selection

2. Template Integration:
   - Templates automatically apply configured settings:
     - Network visibility (Public/Secret)
     - Feature toggles (cycles, modules, views, pages, intake, issue types, time tracking)
   - Template data is merged with any existing project data
   - Optional showTemplateSelector prop to enable/disable template selection

3. User Experience:
   - Professional template cards with hover effects
   - Visual selection indicators
   - Search to filter templates by name
   - Usage statistics displayed on each template
   - Clean navigation with Continue/Skip buttons

Flow:
1. User opens project creation modal
2. Template selection screen shows all available templates
3. User can select a template or choose "Blank Project"
4. Selected template pre-fills project settings
5. User proceeds to project creation form with pre-configured values
6. Features are automatically enabled based on template

This creates a seamless project creation experience where users can leverage
pre-configured templates to quickly set up new projects with consistent settings.
This commit restructures the Templates page to display three separated
categories using a clean tabbed navigation interface.

Template Categories:
1. Project templates - Fully implemented with all CRUD operations
2. Work item templates - Coming soon (empty state placeholder)
3. Page templates - Coming soon (empty state placeholder)

UI/UX Improvements:
- Added tabbed navigation with icons for each category:
  - Layout icon for Project templates
  - ListTodo icon for Work item templates
  - FileText icon for Page templates
- Active tab highlighting with custom primary color border
- Category descriptions below tabs to explain each template type
- Smooth tab switching with transition animations
- Coming soon empty states for work item and page templates
- Updated page description to cover all template types

Benefits:
- Clear separation of template types
- Scalable structure ready for future template implementations
- Consistent navigation pattern
- Professional tabbed interface matching Plane's design system
- Easy to extend with work item and page templates in the future

The project templates tab remains fully functional with all existing
features (create, edit, delete, search, use templates).
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