Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/olive-seahorses-complain.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
"tinacms": patch
---

Fix branch exists error detection with case-insensitive matching
16 changes: 13 additions & 3 deletions packages/tinacms/src/internalClient/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,10 @@ interface TinaSearchConfig {
fuzzyOptions?: FuzzySearchOptions;
}
import gql from 'graphql-tag';
import { EDITORIAL_WORKFLOW_STATUS } from '../toolkit/form-builder/editorial-workflow-constants';
import {
EDITORIAL_WORKFLOW_STATUS,
EditorialWorkflowErrorDetails,
} from '../toolkit/form-builder/editorial-workflow-constants';
import { AsyncData, asyncPoll } from './asyncPoll';
import { LocalAuthProvider, TinaCloudAuthProvider } from './authProvider';
import { TinaCloudProject } from './types';
Expand Down Expand Up @@ -643,9 +646,16 @@ mutation addPendingDocumentMutation(

if (!res.ok) {
console.error('There was an error starting editorial workflow.');
throw new Error(
const error = new Error(
responseBody?.message || 'Failed to start editorial workflow'
);
) as EditorialWorkflowErrorDetails;
if (responseBody?.errorCode) {
error.errorCode = responseBody.errorCode;
}
if (responseBody?.conflictingBranch) {
error.conflictingBranch = responseBody.conflictingBranch;
}
throw error;
}

const requestId = responseBody.requestId;
Expand Down
40 changes: 34 additions & 6 deletions packages/tinacms/src/toolkit/form-builder/create-branch-modal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,11 @@ import {
PopupModal,
} from '../react-modals';
import { FieldLabel } from '@toolkit/fields';
import { EDITORIAL_WORKFLOW_STATUS } from './editorial-workflow-constants';
import {
EDITORIAL_WORKFLOW_STATUS,
EDITORIAL_WORKFLOW_ERROR,
EditorialWorkflowErrorDetails,
} from './editorial-workflow-constants';
import {
CREATE_DOCUMENT_GQL,
DELETE_DOCUMENT_GQL,
Expand Down Expand Up @@ -207,12 +211,36 @@ export const CreateBranchModal = ({
}

close();
} catch (e) {
} catch (e: unknown) {
console.error(e);
const errorMessage =
e.message && e.message.includes('Branch already exists')
? 'Branch already exists'
: 'Branch operation failed, please try again. If the problem persists please contact support.';
let errorMessage =
'Branch operation failed, please try again. If the problem persists please contact support.';

const err = e as EditorialWorkflowErrorDetails;

// Check for structured error codes from the API
if (err.errorCode) {
switch (err.errorCode) {
case EDITORIAL_WORKFLOW_ERROR.BRANCH_EXISTS:
errorMessage = 'A branch with this name already exists';
break;
case EDITORIAL_WORKFLOW_ERROR.BRANCH_HIERARCHY_CONFLICT:
errorMessage =
err.message || 'Branch name conflicts with an existing branch';
break;
case EDITORIAL_WORKFLOW_ERROR.VALIDATION_FAILED:
errorMessage = err.message || 'Invalid branch name';
break;
}
} else if (err.message) {
// Fallback to message parsing for backwards compatibility
if (err.message.toLowerCase().includes('already exists')) {
errorMessage = 'A branch with this name already exists';
} else if (err.message.toLowerCase().includes('conflict')) {
errorMessage = err.message;
}
}

setErrorMessage(errorMessage);
setDisabled(false);
setIsExecuting(false);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,3 +18,24 @@ export const EDITORIAL_WORKFLOW_STATUS = {

export type EditorialWorkflowStatus =
(typeof EDITORIAL_WORKFLOW_STATUS)[keyof typeof EDITORIAL_WORKFLOW_STATUS];

/**
* Editorial Workflow Error Codes
* These match the server-side constants in tinacloud/common/src/editorial-workflow-constants.ts
*/
export const EDITORIAL_WORKFLOW_ERROR = {
BRANCH_EXISTS: 'BRANCH_EXISTS',
BRANCH_HIERARCHY_CONFLICT: 'BRANCH_HIERARCHY_CONFLICT',
VALIDATION_FAILED: 'VALIDATION_FAILED',
} as const;

export type EditorialWorkflowError =
(typeof EDITORIAL_WORKFLOW_ERROR)[keyof typeof EDITORIAL_WORKFLOW_ERROR];

/**
* Error type for editorial workflow operations with additional error details
*/
export type EditorialWorkflowErrorDetails = Error & {
errorCode?: string;
conflictingBranch?: string;
};
Loading