From 65024fe5ecaae3fa2e6ebb177b0530e6bc842ac5 Mon Sep 17 00:00:00 2001 From: Anmol Singh Bhatia <121005188+anmolsinghbhatia@users.noreply.github.com> Date: Thu, 29 Feb 2024 16:12:34 +0530 Subject: [PATCH 01/18] chore: priority icon none state hover state added (#3840) --- web/components/dropdowns/priority.tsx | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/web/components/dropdowns/priority.tsx b/web/components/dropdowns/priority.tsx index 5cacefb3f..e0677c843 100644 --- a/web/components/dropdowns/priority.tsx +++ b/web/components/dropdowns/priority.tsx @@ -58,7 +58,7 @@ const BorderButton = (props: ButtonProps) => { high: "bg-orange-500/20 text-orange-950 border-orange-500", medium: "bg-yellow-500/20 text-yellow-950 border-yellow-500", low: "bg-custom-primary-100/20 text-custom-primary-950 border-custom-primary-100", - none: "bg-custom-background-80 border-custom-border-300", + none: "hover:bg-custom-background-80 border-custom-border-300", }; return ( @@ -197,7 +197,7 @@ const TransparentButton = (props: ButtonProps) => { high: "text-orange-950", medium: "text-yellow-950", low: "text-blue-950", - none: "", + none: "hover:text-custom-text-300", }; return ( From d1087820f6d5e3c75e13ba49d2281c408f3e8c69 Mon Sep 17 00:00:00 2001 From: guru_sainath Date: Thu, 29 Feb 2024 17:18:03 +0530 Subject: [PATCH 02/18] [web-599] ui: kanban layout UI consistency enhancement for grouped display filters (#3841) * ui: UI inconsistancy in kanban layout when we grouped and sub grouped display filters. * ui: width update in the kanban block --- .../issue-layouts/kanban/base-kanban-root.tsx | 44 ++++++++++--------- .../issues/issue-layouts/kanban/block.tsx | 2 +- .../issues/issue-layouts/kanban/default.tsx | 4 +- .../issue-layouts/kanban/kanban-group.tsx | 4 +- .../issues/issue-layouts/kanban/swimlanes.tsx | 4 +- 5 files changed, 29 insertions(+), 29 deletions(-) diff --git a/web/components/issues/issue-layouts/kanban/base-kanban-root.tsx b/web/components/issues/issue-layouts/kanban/base-kanban-root.tsx index 0d7a984b1..7bdaf282d 100644 --- a/web/components/issues/issue-layouts/kanban/base-kanban-root.tsx +++ b/web/components/issues/issue-layouts/kanban/base-kanban-root.tsx @@ -291,27 +291,29 @@ export const BaseKanBanRoot: React.FC = observer((props: IBas - +
+ +
diff --git a/web/components/issues/issue-layouts/kanban/block.tsx b/web/components/issues/issue-layouts/kanban/block.tsx index 8446e7328..be27f7706 100644 --- a/web/components/issues/issue-layouts/kanban/block.tsx +++ b/web/components/issues/issue-layouts/kanban/block.tsx @@ -141,7 +141,7 @@ export const KanbanIssueBlock: React.FC = memo((props) => { >
= observer((props) => { const isGroupByCreatedBy = group_by === "created_by"; return ( -
+
{groupList && groupList.length > 0 && groupList.map((_list: IGroupByColumn) => { const groupByVisibilityToggle = visibilityGroupBy(_list); return ( -
+
{sub_group_by === null && (
{ {(provided: any, snapshot: any) => (
diff --git a/web/components/issues/issue-layouts/kanban/swimlanes.tsx b/web/components/issues/issue-layouts/kanban/swimlanes.tsx index 7b57752f2..44715cf62 100644 --- a/web/components/issues/issue-layouts/kanban/swimlanes.tsx +++ b/web/components/issues/issue-layouts/kanban/swimlanes.tsx @@ -38,11 +38,11 @@ const SubGroupSwimlaneHeader: React.FC = ({ kanbanFilters, handleKanbanFilters, }) => ( -
+
{list && list.length > 0 && list.map((_list: IGroupByColumn) => ( -
+
Date: Thu, 29 Feb 2024 17:19:13 +0530 Subject: [PATCH 03/18] fix: project sidebar favorite list logic updated (#3842) --- web/store/project/project.store.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/web/store/project/project.store.ts b/web/store/project/project.store.ts index c9aa826fe..176c3a364 100644 --- a/web/store/project/project.store.ts +++ b/web/store/project/project.store.ts @@ -148,7 +148,7 @@ export class ProjectStore implements IProjectStore { projects = sortBy(projects, "created_at"); const projectIds = projects - .filter((project) => project.workspace === currentWorkspace.id && project.is_favorite) + .filter((project) => project.workspace === currentWorkspace.id && project.is_member && project.is_favorite) .map((project) => project.id); return projectIds; } From 5d7c0a2a64d1d1681918da46f4e5b5d31876138d Mon Sep 17 00:00:00 2001 From: guru_sainath Date: Thu, 29 Feb 2024 17:19:51 +0530 Subject: [PATCH 04/18] [WEB-600] fix: fixed sub-group-by issue count display in kanban layout header (#3843) * fix: fixed subgroupby issue count at the header in kanban layout * chore: code beautification --- .../issues/issue-layouts/kanban/swimlanes.tsx | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/web/components/issues/issue-layouts/kanban/swimlanes.tsx b/web/components/issues/issue-layouts/kanban/swimlanes.tsx index 7b57752f2..1102cdcd6 100644 --- a/web/components/issues/issue-layouts/kanban/swimlanes.tsx +++ b/web/components/issues/issue-layouts/kanban/swimlanes.tsx @@ -30,6 +30,15 @@ interface ISubGroupSwimlaneHeader { kanbanFilters: TIssueKanbanFilters; handleKanbanFilters: (toggle: "group_by" | "sub_group_by", value: string) => void; } + +const getSubGroupHeaderIssuesCount = (issueIds: TSubGroupedIssues, groupById: string) => { + let headerCount = 0; + Object.keys(issueIds).map((groupState) => { + headerCount = headerCount + (issueIds?.[groupState]?.[groupById]?.length || 0); + }); + return headerCount; +}; + const SubGroupSwimlaneHeader: React.FC = ({ issueIds, sub_group_by, @@ -49,7 +58,7 @@ const SubGroupSwimlaneHeader: React.FC = ({ column_id={_list.id} icon={_list.icon} title={_list.name} - count={(issueIds as TGroupedIssues)?.[_list.id]?.length || 0} + count={getSubGroupHeaderIssuesCount(issueIds as TSubGroupedIssues, _list?.id)} kanbanFilters={kanbanFilters} handleKanbanFilters={handleKanbanFilters} issuePayload={_list.payload} From f183e389eab48937e9e389a7c656bbc90cb12ddd Mon Sep 17 00:00:00 2001 From: Anmol Singh Bhatia <121005188+anmolsinghbhatia@users.noreply.github.com> Date: Thu, 29 Feb 2024 17:20:17 +0530 Subject: [PATCH 05/18] fix: module sidebar description duplicacy (#3844) --- web/components/modules/sidebar.tsx | 6 ------ 1 file changed, 6 deletions(-) diff --git a/web/components/modules/sidebar.tsx b/web/components/modules/sidebar.tsx index 53d7eff4c..c8c55321c 100644 --- a/web/components/modules/sidebar.tsx +++ b/web/components/modules/sidebar.tsx @@ -368,12 +368,6 @@ export const ModuleDetailsSidebar: React.FC = observer((props) => {
- {moduleDetails.description && ( - - {moduleDetails.description} - - )} -
From e4988ee9406fa6ea8d90e5f21a2068ed5186dd84 Mon Sep 17 00:00:00 2001 From: Anmol Singh Bhatia <121005188+anmolsinghbhatia@users.noreply.github.com> Date: Thu, 29 Feb 2024 19:40:46 +0530 Subject: [PATCH 06/18] fix: issue sidebar and peek overview cycle select improvement (#3845) --- web/components/issues/issue-detail/cycle-select.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/web/components/issues/issue-detail/cycle-select.tsx b/web/components/issues/issue-detail/cycle-select.tsx index fb8449d6f..84dccefac 100644 --- a/web/components/issues/issue-detail/cycle-select.tsx +++ b/web/components/issues/issue-detail/cycle-select.tsx @@ -50,7 +50,7 @@ export const IssueCycleSelect: React.FC = observer((props) => buttonVariant="transparent-with-text" className="w-full group" buttonContainerClassName="w-full text-left" - buttonClassName={`text-sm ${issue?.cycle_id ? "" : "text-custom-text-400"}`} + buttonClassName={`text-sm justify-between ${issue?.cycle_id ? "" : "text-custom-text-400"}`} placeholder="No cycle" hideIcon dropdownArrow From 5cfebb8dae33191fba9f2fbffeea3e762ca271d5 Mon Sep 17 00:00:00 2001 From: guru_sainath Date: Thu, 29 Feb 2024 19:41:30 +0530 Subject: [PATCH 07/18] fix: issue description on last draft issue (#3846) --- web/components/issues/issue-modal/modal.tsx | 3 ++- web/components/workspace/sidebar-quick-action.tsx | 3 ++- 2 files changed, 4 insertions(+), 2 deletions(-) diff --git a/web/components/issues/issue-modal/modal.tsx b/web/components/issues/issue-modal/modal.tsx index dc73bc77a..1da02f0ac 100644 --- a/web/components/issues/issue-modal/modal.tsx +++ b/web/components/issues/issue-modal/modal.tsx @@ -100,8 +100,9 @@ export const CreateUpdateIssueModal: React.FC = observer((prop const fetchIssueDetail = async (issueId: string | undefined) => { if (!workspaceSlug) return; + if (!projectId || issueId === undefined) { - setDescription("

"); + setDescription(data?.description_html || "

"); return; } const response = await fetchIssue(workspaceSlug, projectId, issueId, isDraft ? "DRAFT" : "DEFAULT"); diff --git a/web/components/workspace/sidebar-quick-action.tsx b/web/components/workspace/sidebar-quick-action.tsx index 38d3e6b6a..dd2dd5c68 100644 --- a/web/components/workspace/sidebar-quick-action.tsx +++ b/web/components/workspace/sidebar-quick-action.tsx @@ -58,6 +58,7 @@ export const WorkspaceSidebarQuickAction = observer(() => { const draftIssues = storedValue ?? {}; if (workspaceSlug && draftIssues[workspaceSlug]) delete draftIssues[workspaceSlug]; setValue(draftIssues); + return Promise.resolve(); }; return ( @@ -66,7 +67,7 @@ export const WorkspaceSidebarQuickAction = observer(() => { isOpen={isDraftIssueModalOpen} onClose={() => setIsDraftIssueModalOpen(false)} data={workspaceDraftIssue ?? {}} - // storeType={storeType} + onSubmit={() => removeWorkspaceDraftIssue()} isDraft={true} /> From e6f33eb26252b69055c12ffb885e1c6bccbb693d Mon Sep 17 00:00:00 2001 From: guru_sainath Date: Thu, 29 Feb 2024 20:29:02 +0530 Subject: [PATCH 08/18] [WEB-609] fix: header text overflow issue in kanban layout (#3848) * fix: kanban header text overflow * chore: updated condition --- .../issues/issue-layouts/kanban/default.tsx | 11 +++++++++-- .../issue-layouts/kanban/headers/group-by-card.tsx | 14 +++++++++++--- 2 files changed, 20 insertions(+), 5 deletions(-) diff --git a/web/components/issues/issue-layouts/kanban/default.tsx b/web/components/issues/issue-layouts/kanban/default.tsx index 7aac11c6f..3cbab589f 100644 --- a/web/components/issues/issue-layouts/kanban/default.tsx +++ b/web/components/issues/issue-layouts/kanban/default.tsx @@ -101,8 +101,15 @@ const GroupByKanBan: React.FC = observer((props) => { const groupList = showEmptyGroup ? list : groupWithIssues; - const visibilityGroupBy = (_list: IGroupByColumn) => - sub_group_by ? false : kanbanFilters?.group_by.includes(_list.id) ? true : false; + const visibilityGroupBy = (_list: IGroupByColumn) => { + if (sub_group_by) { + if (kanbanFilters?.sub_group_by.includes(_list.id)) return true; + return false; + } else { + if (kanbanFilters?.group_by.includes(_list.id)) return true; + return false; + } + }; const isGroupByCreatedBy = group_by === "created_by"; diff --git a/web/components/issues/issue-layouts/kanban/headers/group-by-card.tsx b/web/components/issues/issue-layouts/kanban/headers/group-by-card.tsx index 440b379b8..f49af2922 100644 --- a/web/components/issues/issue-layouts/kanban/headers/group-by-card.tsx +++ b/web/components/issues/issue-layouts/kanban/headers/group-by-card.tsx @@ -106,13 +106,21 @@ export const HeaderGroupByCard: FC = observer((props) => { {icon ? icon : }
-
+
{title}
-
+
{count || 0}
From bc6e48fcd6f64aa364f7a5f7fd2cfeeba6e18259 Mon Sep 17 00:00:00 2001 From: Bavisetti Narayan <72156168+NarayanBavisetti@users.noreply.github.com> Date: Fri, 1 Mar 2024 13:33:23 +0530 Subject: [PATCH 09/18] chore: issue comment PATCH changes (#3850) --- apiserver/plane/api/views/issue.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/apiserver/plane/api/views/issue.py b/apiserver/plane/api/views/issue.py index 0905ae1f7..bf3313779 100644 --- a/apiserver/plane/api/views/issue.py +++ b/apiserver/plane/api/views/issue.py @@ -716,9 +716,9 @@ class IssueCommentAPIEndpoint(WebhookMixin, BaseAPIView): # Validation check if the issue already exists if ( - str(request.data.get("external_id")) + request.data.get("external_id") and (issue_comment.external_id != str(request.data.get("external_id"))) - and Issue.objects.filter( + and IssueComment.objects.filter( project_id=project_id, workspace__slug=slug, external_source=request.data.get( From d39f2526a28169a763f48ecf41b5f31353b4777f Mon Sep 17 00:00:00 2001 From: sriram veeraghanta Date: Fri, 1 Mar 2024 13:49:50 +0530 Subject: [PATCH 10/18] chore: removing unnecessary lines --- web/layouts/app-layout/layout.tsx | 21 --------------------- 1 file changed, 21 deletions(-) diff --git a/web/layouts/app-layout/layout.tsx b/web/layouts/app-layout/layout.tsx index 2a788e761..07ec9711d 100644 --- a/web/layouts/app-layout/layout.tsx +++ b/web/layouts/app-layout/layout.tsx @@ -6,11 +6,6 @@ import { CommandPalette } from "components/command-palette"; import { AppSidebar } from "./sidebar"; import { observer } from "mobx-react-lite"; -// FIXME: remove this later -import { useIssues } from "hooks/store/use-issues"; -import { EIssuesStoreType } from "constants/issue"; -import useSWR from "swr"; - export interface IAppLayout { children: ReactNode; header: ReactNode; @@ -20,22 +15,6 @@ export interface IAppLayout { export const AppLayout: FC = observer((props) => { const { children, header, withProjectWrapper = false } = props; - const workspaceSlug = "plane-demo"; - const projectId = "b16907a9-a55f-4f5b-b05e-7065a0869ba6"; - - const { issues, issuesFilter } = useIssues(EIssuesStoreType.ARCHIVED); - - useSWR( - workspaceSlug && projectId ? `PROJECT_ARCHIVED_ISSUES_V3_${workspaceSlug}_${projectId}` : null, - async () => { - if (workspaceSlug && projectId) { - await issuesFilter?.fetchFilters(workspaceSlug, projectId); - // await issues?.fetchIssues(workspaceSlug, projectId, issues?.groupedIssueIds ? "mutation" : "init-loader"); - } - }, - { revalidateIfStale: false, revalidateOnFocus: false } - ); - return ( <> From e4bccea82447974f38de10e1fb3079259126fd87 Mon Sep 17 00:00:00 2001 From: Anmol Singh Bhatia <121005188+anmolsinghbhatia@users.noreply.github.com> Date: Fri, 1 Mar 2024 17:20:36 +0530 Subject: [PATCH 11/18] fix: multiple issue comment (#3854) --- .../issue-detail/issue-activity/comments/comment-create.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/web/components/issues/issue-detail/issue-activity/comments/comment-create.tsx b/web/components/issues/issue-detail/issue-activity/comments/comment-create.tsx index f666b6c1d..af4732808 100644 --- a/web/components/issues/issue-detail/issue-activity/comments/comment-create.tsx +++ b/web/components/issues/issue-detail/issue-activity/comments/comment-create.tsx @@ -74,7 +74,7 @@ export const IssueCommentCreate: FC = (props) => { return (
{ - if (e.key === "Enter" && !e.shiftKey && !isEmpty) { + if (e.key === "Enter" && !e.shiftKey && !isEmpty && !isSubmitting) { handleSubmit(onSubmit)(e); } }} From 4b706437d71732b8ab10dad50751c6407b817a18 Mon Sep 17 00:00:00 2001 From: Anmol Singh Bhatia <121005188+anmolsinghbhatia@users.noreply.github.com> Date: Fri, 1 Mar 2024 17:23:26 +0530 Subject: [PATCH 12/18] [WEB-619] fix: workspace all issue quick action (#3853) * chore: custom menu dropdown menu items classname prop added * fix: issue layout quick action z index fix --- packages/ui/src/dropdowns/custom-menu.tsx | 3 ++- packages/ui/src/dropdowns/helper.tsx | 1 + .../issues/issue-layouts/quick-action-dropdowns/all-issue.tsx | 1 + .../issue-layouts/quick-action-dropdowns/archived-issue.tsx | 1 + .../issue-layouts/quick-action-dropdowns/cycle-issue.tsx | 1 + .../issue-layouts/quick-action-dropdowns/module-issue.tsx | 1 + .../issue-layouts/quick-action-dropdowns/project-issue.tsx | 1 + 7 files changed, 8 insertions(+), 1 deletion(-) diff --git a/packages/ui/src/dropdowns/custom-menu.tsx b/packages/ui/src/dropdowns/custom-menu.tsx index cdfccbb4e..d1623dddf 100644 --- a/packages/ui/src/dropdowns/custom-menu.tsx +++ b/packages/ui/src/dropdowns/custom-menu.tsx @@ -27,6 +27,7 @@ const CustomMenu = (props: ICustomMenuDropdownProps) => { noBorder = false, noChevron = false, optionsClassName = "", + menuItemsClassName = "", verticalEllipsis = false, portalElement, menuButtonOnClick, @@ -70,7 +71,7 @@ const CustomMenu = (props: ICustomMenuDropdownProps) => { useOutsideClickDetector(dropdownRef, closeDropdown); let menuItems = ( - +
void; + menuItemsClassName?: string; onMenuClose?: () => void; closeOnSelect?: boolean; portalElement?: Element | null; diff --git a/web/components/issues/issue-layouts/quick-action-dropdowns/all-issue.tsx b/web/components/issues/issue-layouts/quick-action-dropdowns/all-issue.tsx index 1d0472454..20d21dc5f 100644 --- a/web/components/issues/issue-layouts/quick-action-dropdowns/all-issue.tsx +++ b/web/components/issues/issue-layouts/quick-action-dropdowns/all-issue.tsx @@ -96,6 +96,7 @@ export const AllIssueQuickActions: React.FC = observer((props storeType={EIssuesStoreType.PROJECT} /> = (props) => onSubmit={handleDelete} /> = observer((pro storeType={EIssuesStoreType.CYCLE} /> = observer((pr storeType={EIssuesStoreType.MODULE} /> = observer((p isDraft={isDraftIssue} /> Date: Fri, 1 Mar 2024 17:29:30 +0530 Subject: [PATCH 13/18] [WEB-616] fix: inbox issue navigation issue title and description event propagation (#3851) * fix: inbox issue navigation issue title and description event propagation * fix: inbox issue navigation issue title and description event propagation --- web/components/inbox/inbox-issue-actions.tsx | 2 ++ 1 file changed, 2 insertions(+) diff --git a/web/components/inbox/inbox-issue-actions.tsx b/web/components/inbox/inbox-issue-actions.tsx index 8a3bb4261..48d9157c6 100644 --- a/web/components/inbox/inbox-issue-actions.tsx +++ b/web/components/inbox/inbox-issue-actions.tsx @@ -131,6 +131,8 @@ export const InboxIssueActionsHeader: FC = observer((p const handleInboxIssueNavigation = useCallback( (direction: "next" | "prev") => { if (!inboxIssues || !inboxIssueId) return; + const activeElement = document.activeElement as HTMLElement; + if (activeElement && (activeElement.classList.contains("tiptap") || activeElement.id === "title-input")) return; const nextIssueIndex = direction === "next" ? (currentIssueIndex + 1) % inboxIssues.length From 6eb7014ea42b637dd46dc4374e821013f832420e Mon Sep 17 00:00:00 2001 From: Vihar Kurama Date: Mon, 4 Mar 2024 20:06:53 +0530 Subject: [PATCH 14/18] chore: update github readme - content edits to feature section, new screenshots and added repo activity, contributors. (#3870) * update github readme, add new features and deployment options * add new product screenshots * add contributors section to readme * chore: update formatting --- README.md | 151 +++++++++++++++++++++++++++++++++++------------------- 1 file changed, 98 insertions(+), 53 deletions(-) diff --git a/README.md b/README.md index b509fd6f6..52ccda474 100644 --- a/README.md +++ b/README.md @@ -7,7 +7,7 @@

Plane

-

Flexible, extensible open-source project management

+

Open-source project management that unlocks customer value.

@@ -16,6 +16,13 @@ Commit activity per month

+

+ Website • + Releases • + Twitter • + Documentation +

+

-Meet [Plane](https://plane.so). An open-source software development tool to manage issues, sprints, and product roadmaps with peace of mind 🧘‍♀️. +Meet [Plane](https://plane.so). An open-source software development tool to manage issues, sprints, and product roadmaps with peace of mind. 🧘‍♀️ > Plane is still in its early days, not everything will be perfect yet, and hiccups may happen. Please let us know of any suggestions, ideas, or bugs that you encounter on our [Discord](https://discord.com/invite/A92xrEGCge) or GitHub issues, and we will use your feedback to improve on our upcoming releases. -The easiest way to get started with Plane is by creating a [Plane Cloud](https://app.plane.so) account. Plane Cloud offers a hosted solution for Plane. If you prefer to self-host Plane, please refer to our [deployment documentation](https://docs.plane.so/docker-compose). -## ⚡️ Contributors Quick Start -### Prerequisite +## ⚡ Installation -Development system must have docker engine installed and running. +The easiest way to get started with Plane is by creating a [Plane Cloud](https://app.plane.so) account where we offer a hosted solution for users. -### Steps +If you want more control over your data prefer to self-host Plane, please refer to our [deployment documentation](https://docs.plane.so/docker-compose). -Setting up local environment is extremely easy and straight forward. Follow the below step and you will be ready to contribute +| Installation Methods | Documentation Link | +|-----------------|----------------------------------------------------------------------------------------------------------| +| Docker | [![Docker](https://img.shields.io/badge/docker-%230db7ed.svg?style=for-the-badge&logo=docker&logoColor=white)](https://docs.plane.so/docker-compose) | +| Kubernetes | [![Kubernetes](https://img.shields.io/badge/kubernetes-%23326ce5.svg?style=for-the-badge&logo=kubernetes&logoColor=white)](https://docs.plane.so/kubernetes) | -1. Clone the code locally using `git clone https://github.com/makeplane/plane.git` -1. Switch to the code folder `cd plane` -1. Create your feature or fix branch you plan to work on using `git checkout -b ` -1. Open terminal and run `./setup.sh` -1. Open the code on VSCode or similar equivalent IDE -1. Review the `.env` files available in various folders. Visit [Environment Setup](./ENV_SETUP.md) to know about various environment variables used in system -1. Run the docker command to initiate various services `docker compose -f docker-compose-local.yml up -d` - -You are ready to make changes to the code. Do not forget to refresh the browser (in case id does not auto-reload) - -Thats it! - -## 🍙 Self Hosting - -For self hosting environment setup, visit the [Self Hosting](https://docs.plane.so/docker-compose) documentation page +`Instance admin` can configure instance settings using our [God-mode](https://docs.plane.so/instance-admin) feature. ## 🚀 Features -- **Issue Planning and Tracking**: Quickly create issues and add details using a powerful rich text editor that supports file uploads. Add sub-properties and references to issues for better organization and tracking. -- **Issue Attachments**: Collaborate effectively by attaching files to issues, making it easy for your team to find and share important project-related documents. -- **Layouts**: Customize your project view with your preferred layout - choose from List, Kanban, or Calendar to visualize your project in a way that makes sense to you. -- **Cycles**: Plan sprints with Cycles to keep your team on track and productive. Gain insights into your project's progress with burn-down charts and other useful features. -- **Modules**: Break down your large projects into smaller, more manageable modules. Assign modules between teams to easily track and plan your project's progress. +- **Issues**: Quickly create issues and add details using a powerful, rich text editor that supports file uploads. Add sub-properties and references to problems for better organization and tracking. + +- **Cycles** + Keep up your team's momentum with Cycles. Gain insights into your project's progress with burn-down charts and other valuable features. + +- **Modules**: Break down your large projects into smaller, more manageable modules. Assign modules between teams to track and plan your project's progress easily. + - **Views**: Create custom filters to display only the issues that matter to you. Save and share your filters in just a few clicks. -- **Pages**: Plane pages function as an AI-powered notepad, allowing you to easily document issues, cycle plans, and module details, and then synchronize them with your issues. -- **Command K**: Enjoy a better user experience with the new Command + K menu. Easily manage and navigate through your projects from one convenient location. -- **GitHub Sync**: Streamline your planning process by syncing your GitHub issues with Plane. Keep all your issues in one place for better tracking and collaboration. + +- **Pages**: Plane pages, equipped with AI and a rich text editor, let you jot down your thoughts on the fly. Format your text, upload images, hyperlink, or sync your existing ideas into an actionable item or issue. + +- **Analytics**: Get insights into all your Plane data in real-time. Visualize issue data to spot trends, remove blockers, and progress your work. + +- **Drive** (*coming soon*): The drive helps you share documents, images, videos, or any other files that make sense to you or your team and align on the problem/solution. + + + +## 🛠️ Contributors Quick Start + +> Development system must have docker engine installed and running. + +Setting up local environment is extremely easy and straight forward. Follow the below step and you will be ready to contribute + +1. Clone the code locally using: + ``` + git clone https://github.com/makeplane/plane.git + ``` +2. Switch to the code folder: + ``` + cd plane + ``` +3. Create your feature or fix branch you plan to work on using: + ``` + git checkout -b + ``` +4. Open terminal and run: + ``` + ./setup.sh + ``` +5. Open the code on VSCode or similar equivalent IDE. +6. Review the `.env` files available in various folders. + Visit [Environment Setup](./ENV_SETUP.md) to know about various environment variables used in system. +7. Run the docker command to initiate services: + ``` + docker compose -f docker-compose-local.yml up -d + ``` + +You are ready to make changes to the code. Do not forget to refresh the browser (in case it does not auto-reload). + +Thats it! + +## ❤️ Community + +The Plane community can be found on [GitHub Discussions](https://github.com/orgs/makeplane/discussions), and our [Discord server](https://discord.com/invite/A92xrEGCge). Our [Code of conduct](https://github.com/makeplane/plane/blob/master/CODE_OF_CONDUCT.md) applies to all Plane community chanels. + +Ask questions, report bugs, join discussions, voice ideas, make feature requests, or share your projects. + +### Repo Activity +![Plane Repo Activity](https://repobeats.axiom.co/api/embed/2523c6ed2f77c082b7908c33e2ab208981d76c39.svg "Repobeats analytics image") ## 📸 Screenshots

Plane Views @@ -91,8 +135,7 @@ For self hosting environment setup, visit the [Self Hosting](https://docs.plane.

Plane Issue Details @@ -100,7 +143,7 @@ For self hosting environment setup, visit the [Self Hosting](https://docs.plane.

Plane Cycles and Modules @@ -109,7 +152,7 @@ For self hosting environment setup, visit the [Self Hosting](https://docs.plane.

Plane Analytics @@ -118,7 +161,7 @@ For self hosting environment setup, visit the [Self Hosting](https://docs.plane.

Plane Pages @@ -128,7 +171,7 @@ For self hosting environment setup, visit the [Self Hosting](https://docs.plane.

Plane Command Menu @@ -136,20 +179,22 @@ For self hosting environment setup, visit the [Self Hosting](https://docs.plane.

-## 📚Documentation - -For full documentation, visit [docs.plane.so](https://docs.plane.so/) - -To see how to Contribute, visit [here](https://github.com/makeplane/plane/blob/master/CONTRIBUTING.md). - -## ❤️ Community - -The Plane community can be found on GitHub Discussions, where you can ask questions, voice ideas, and share your projects. - -To chat with other community members you can join the [Plane Discord](https://discord.com/invite/A92xrEGCge). - -Our [Code of Conduct](https://github.com/makeplane/plane/blob/master/CODE_OF_CONDUCT.md) applies to all Plane community channels. - ## ⛓️ Security -If you believe you have found a security vulnerability in Plane, we encourage you to responsibly disclose this and not open a public issue. We will investigate all legitimate reports. Email engineering@plane.so to disclose any security vulnerabilities. +If you believe you have found a security vulnerability in Plane, we encourage you to responsibly disclose this and not open a public issue. We will investigate all legitimate reports. + +Email squawk@plane.so to disclose any security vulnerabilities. + +## ❤️ Contribute + +There are many ways to contribute to Plane, including: +- Submitting [bugs](https://github.com/makeplane/plane/issues/new?assignees=srinivaspendem%2Cpushya22&labels=%F0%9F%90%9Bbug&projects=&template=--bug-report.yaml&title=%5Bbug%5D%3A+) and [feature requests](https://github.com/makeplane/plane/issues/new?assignees=srinivaspendem%2Cpushya22&labels=%E2%9C%A8feature&projects=&template=--feature-request.yaml&title=%5Bfeature%5D%3A+) for various components. +- Reviewing [the documentation](https://docs.plane.so/) and submitting [pull requests](https://github.com/makeplane/plane), from fixing typos to adding new features. +- Speaking or writing about Plane or any other ecosystem integration and [letting us know](https://discord.com/invite/A92xrEGCge)! +- Upvoting [popular feature requests](https://github.com/makeplane/plane/issues) to show your support. + +### We couldn't have done this without you. + +
+ + \ No newline at end of file From d99529b109fea50d4c74e7fbe7c61b4a23b7bef3 Mon Sep 17 00:00:00 2001 From: "M. Palanikannan" <73993394+Palanikannan1437@users.noreply.github.com> Date: Mon, 4 Mar 2024 20:33:16 +0530 Subject: [PATCH 15/18] fix: crash while updating link text on the last node (#3871) --- .../src/ui/components/links/link-edit-view.tsx | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/packages/editor/document-editor/src/ui/components/links/link-edit-view.tsx b/packages/editor/document-editor/src/ui/components/links/link-edit-view.tsx index 136d04e01..971915439 100644 --- a/packages/editor/document-editor/src/ui/components/links/link-edit-view.tsx +++ b/packages/editor/document-editor/src/ui/components/links/link-edit-view.tsx @@ -40,9 +40,11 @@ export const LinkEditView = ({ const [positionRef, setPositionRef] = useState({ from: from, to: to }); const [localUrl, setLocalUrl] = useState(viewProps.url); - const linkRemoved = useRef(); + const linkRemoved = useRef(); const getText = (from: number, to: number) => { + if (to >= editor.state.doc.content.size) return ""; + const text = editor.state.doc.textBetween(from, to, "\n"); return text; }; @@ -72,10 +74,12 @@ export const LinkEditView = ({ const url = isValidUrl(localUrl) ? localUrl : viewProps.url; + if (to >= editor.state.doc.content.size) return; + editor.view.dispatch(editor.state.tr.removeMark(from, to, editor.schema.marks.link)); editor.view.dispatch(editor.state.tr.addMark(from, to, editor.schema.marks.link.create({ href: url }))); }, - [localUrl] + [localUrl, editor, from, to, viewProps.url] ); const handleUpdateText = (text: string) => { From af70722e34ceeb09cf2c1bee04a69ce89e7d7791 Mon Sep 17 00:00:00 2001 From: Henit Chobisa Date: Tue, 5 Mar 2024 13:02:13 +0530 Subject: [PATCH 16/18] chore: added workflow for checking version before merge to master (#3847) --- .github/workflows/check-version.yml | 45 +++++++++++++++++++++++++++++ 1 file changed, 45 insertions(+) create mode 100644 .github/workflows/check-version.yml diff --git a/.github/workflows/check-version.yml b/.github/workflows/check-version.yml new file mode 100644 index 000000000..ca8b6f8b3 --- /dev/null +++ b/.github/workflows/check-version.yml @@ -0,0 +1,45 @@ +name: Version Change Before Release + +on: + pull_request: + branches: + - master + +jobs: + check-version: + runs-on: ubuntu-latest + steps: + - name: Checkout repository + uses: actions/checkout@v4 + with: + ref: ${{ github.head_ref }} + fetch-depth: 0 + + - name: Setup Node.js + uses: actions/setup-node@v4 + with: + node-version: '18' + + - name: Get PR Branch version + run: echo "PR_VERSION=$(node -p "require('./package.json').version")" >> $GITHUB_ENV + + - name: Fetch base branch + run: git fetch origin master:master + + - name: Get Master Branch version + run: | + git checkout master + echo "MASTER_VERSION=$(node -p "require('./package.json').version")" >> $GITHUB_ENV + + - name: Get master branch version and compare + run: | + echo "Comparing versions: PR version is $PR_VERSION, Master version is $MASTER_VERSION" + if [ "$PR_VERSION" == "$MASTER_VERSION" ]; then + echo "Version in PR branch is the same as in master. Failing the CI." + exit 1 + else + echo "Version check passed. Versions are different." + fi + env: + PR_VERSION: ${{ env.PR_VERSION }} + MASTER_VERSION: ${{ env.MASTER_VERSION }} From f8f9dd33311686e94c2386cfe94af14569662d90 Mon Sep 17 00:00:00 2001 From: Henit Chobisa Date: Tue, 5 Mar 2024 13:14:00 +0530 Subject: [PATCH 17/18] [CHANG-8] chore: Upgraded Build Pull Request CI for Faster Parallel Build with Linting Capabilities (#3838) * chore: upgraded build pull request ci for multi stage parallel builds * Update build-test-pull-request.yml --- .github/workflows/build-test-pull-request.yml | 111 +++++++++++++----- 1 file changed, 84 insertions(+), 27 deletions(-) diff --git a/.github/workflows/build-test-pull-request.yml b/.github/workflows/build-test-pull-request.yml index 83ed41625..e0014f696 100644 --- a/.github/workflows/build-test-pull-request.yml +++ b/.github/workflows/build-test-pull-request.yml @@ -1,27 +1,19 @@ -name: Build Pull Request Contents +name: Build and Lint on Pull Request on: + workflow_dispatch: pull_request: types: ["opened", "synchronize"] jobs: - build-pull-request-contents: - name: Build Pull Request Contents - runs-on: ubuntu-20.04 - permissions: - pull-requests: read - + get-changed-files: + runs-on: ubuntu-latest + outputs: + apiserver_changed: ${{ steps.changed-files.outputs.apiserver_any_changed }} + web_changed: ${{ steps.changed-files.outputs.web_any_changed }} + space_changed: ${{ steps.changed-files.outputs.deploy_any_changed }} steps: - - name: Checkout Repository to Actions - uses: actions/checkout@v3.3.0 - with: - token: ${{ secrets.ACCESS_TOKEN }} - - - name: Setup Node.js 18.x - uses: actions/setup-node@v2 - with: - node-version: 18.x - + - uses: actions/checkout@v3 - name: Get changed files id: changed-files uses: tj-actions/changed-files@v41 @@ -31,17 +23,82 @@ jobs: - apiserver/** web: - web/** + - packages/** + - 'package.json' + - 'yarn.lock' + - 'tsconfig.json' + - 'turbo.json' deploy: - space/** + - packages/** + - 'package.json' + - 'yarn.lock' + - 'tsconfig.json' + - 'turbo.json' - - name: Build Plane's Main App - if: steps.changed-files.outputs.web_any_changed == 'true' - run: | - yarn - yarn build --filter=web + lint-apiserver: + needs: get-changed-files + runs-on: ubuntu-latest + if: needs.get-changed-files.outputs.apiserver_changed == 'true' + steps: + - uses: actions/checkout@v3 + - name: Set up Python + uses: actions/setup-python@v4 + with: + python-version: '3.x' # Specify the Python version you need + - name: Install Pylint + run: python -m pip install ruff + - name: Install Apiserver Dependencies + run: cd apiserver && pip install -r requirements.txt + - name: Lint apiserver + run: ruff check --fix apiserver - - name: Build Plane's Deploy App - if: steps.changed-files.outputs.deploy_any_changed == 'true' - run: | - yarn - yarn build --filter=space + lint-web: + needs: get-changed-files + if: needs.get-changed-files.outputs.web_changed == 'true' + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v3 + - name: Setup Node.js + uses: actions/setup-node@v2 + with: + node-version: 18.x + - run: yarn install + - run: yarn lint --filter=web + + lint-space: + needs: get-changed-files + if: needs.get-changed-files.outputs.space_changed == 'true' + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v3 + - name: Setup Node.js + uses: actions/setup-node@v2 + with: + node-version: 18.x + - run: yarn install + - run: yarn lint --filter=space + + build-web: + needs: lint-web + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v3 + - name: Setup Node.js + uses: actions/setup-node@v2 + with: + node-version: 18.x + - run: yarn install + - run: yarn build --filter=web + + build-space: + needs: lint-space + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v3 + - name: Setup Node.js + uses: actions/setup-node@v2 + with: + node-version: 18.x + - run: yarn install + - run: yarn build --filter=space From d07dd650222706aaf305b470bf2f6fee0c178b21 Mon Sep 17 00:00:00 2001 From: Manish Gupta <59428681+mguptahub@users.noreply.github.com> Date: Wed, 6 Mar 2024 12:57:14 +0530 Subject: [PATCH 18/18] feat: feature preview deploys for web and space nextjs applications (#3881) * feature preview deploy * chore: variable name changes --------- Co-authored-by: sriram veeraghanta --- .github/workflows/feature-deployment.yml | 73 ++++++++++++++++++++++++ 1 file changed, 73 insertions(+) create mode 100644 .github/workflows/feature-deployment.yml diff --git a/.github/workflows/feature-deployment.yml b/.github/workflows/feature-deployment.yml new file mode 100644 index 000000000..2220a7a84 --- /dev/null +++ b/.github/workflows/feature-deployment.yml @@ -0,0 +1,73 @@ +name: Feature Preview + +on: + workflow_dispatch: + inputs: + web-build: + required: true + type: boolean + default: true + space-build: + required: true + type: boolean + default: false + +jobs: + feature-deploy: + name: Feature Deploy + runs-on: ubuntu-latest + env: + KUBE_CONFIG_FILE: ${{ secrets.KUBE_CONFIG }} + BUILD_WEB: ${{ (github.event.inputs.web-build == '' && true) || github.event.inputs.web-build }} + BUILD_SPACE: ${{ (github.event.inputs.space-build == '' && false) || github.event.inputs.space-build }} + + steps: + - name: Tailscale + uses: tailscale/github-action@v2 + with: + oauth-client-id: ${{ secrets.TAILSCALE_OAUTH_CLIENT_ID }} + oauth-secret: ${{ secrets.TAILSCALE_OAUTH_SECRET }} + tags: tag:ci + + - name: Kubectl Setup + run: | + curl -LO "https://dl.k8s.io/release/${{secrets.KUBE_VERSION}}/bin/linux/amd64/kubectl" + chmod +x kubectl + + mkdir -p ~/.kube + echo "$KUBE_CONFIG_FILE" > ~/.kube/config + chmod 600 ~/.kube/config + + - name: HELM Setup + run: | + curl -fsSL -o get_helm.sh https://raw.githubusercontent.com/helm/helm/main/scripts/get-helm-3 + chmod 700 get_helm.sh + ./get_helm.sh + + - name: App Deploy + run: | + helm --kube-insecure-skip-tls-verify repo add feature-preview ${{ secrets.FEATURE_PREVIEW_HELM_CHART_URL }} + GIT_BRANCH=${{ github.ref_name }} + APP_NAMESPACE=${{ secrets.FEATURE_PREVIEW_NAMESPACE }} + + METADATA=$(helm install feature-preview/${{ secrets.FEATURE_PREVIEW_HELM_CHART_NAME }} \ + --kube-insecure-skip-tls-verify \ + --generate-name \ + --namespace $APP_NAMESPACE \ + --set shared_config.git_repo=${{ github.repositoryUrl }} \ + --set shared_config.git_branch="$GIT_BRANCH" \ + --set web.enabled=${{ env.BUILD_WEB }} \ + --set space.enabled=${{ env.BUILD_SPACE }} \ + --output json \ + --timeout 1000s) + + APP_NAME=$(echo $METADATA | jq -r '.name') + + INGRESS_HOSTNAME=$(kubectl get ingress -n feature-builds --insecure-skip-tls-verify \ + -o jsonpath='{.items[?(@.metadata.annotations.meta\.helm\.sh\/release-name=="'$APP_NAME'")]}' | \ + jq -r '.spec.rules[0].host') + + echo "****************************************" + echo "APP NAME ::: $APP_NAME" + echo "INGRESS HOSTNAME ::: $INGRESS_HOSTNAME" + echo "****************************************"