mirror of
https://github.com/Kong/insomnia.git
synced 2026-04-20 14:17:29 -04:00
feat(Git Sync): UX improvements (#8524)
* fix loading state in commit and commit and push buttons * use yaml when parsing open api specs in the app * improve error message for pushing to a remote with extra commits * improve buttons ux on repo settings modal * check for response.errors * fix error issue
This commit is contained in:
@@ -147,7 +147,7 @@ function getApiSpec(file: InsomniaFile): [WithExportType<ApiSpec>] | [] {
|
||||
_type: EXPORT_TYPE_API_SPEC,
|
||||
fileName: 'file' in file.spec ? file.spec.file : '',
|
||||
contentType: 'json',
|
||||
contents: 'contents' in file.spec && file.spec.contents ? JSON.stringify(file.spec.contents) : '',
|
||||
contents: 'contents' in file.spec && file.spec.contents ? stringify(file.spec.contents) : '',
|
||||
parentId: file.meta?.id || '__WORKSPACE_ID__',
|
||||
}];
|
||||
}
|
||||
|
||||
@@ -1408,9 +1408,17 @@ export const pushToGitRemoteAction = async ({
|
||||
});
|
||||
await database.flushChanges(bufferId);
|
||||
} catch (err: unknown) {
|
||||
if (err instanceof Errors.PushRejectedError && err.data.reason === 'not-fast-forward') {
|
||||
return {
|
||||
errors: ['Push Rejected. It seems that the remote repository has changes that you do not have locally. Please pull the changes and try again.'],
|
||||
gitRepository,
|
||||
};
|
||||
}
|
||||
|
||||
if (err instanceof Errors.HttpError) {
|
||||
return {
|
||||
errors: [`${err.message}, ${err.data.response}`],
|
||||
gitRepository,
|
||||
};
|
||||
}
|
||||
const errorMessage = err instanceof Error ? err.message : 'Unknown Error';
|
||||
|
||||
@@ -656,23 +656,36 @@ export class GitVCS {
|
||||
|
||||
async push(gitCredentials?: GitCredentials | null, force = false) {
|
||||
console.log(`[git] Push remote=origin force=${force ? 'true' : 'false'}`);
|
||||
// eslint-disable-next-line no-unreachable
|
||||
const response: git.PushResult = await git.push({
|
||||
|
||||
const response = await git.push({
|
||||
...this._baseOpts,
|
||||
...gitCallbacks(gitCredentials),
|
||||
remote: 'origin',
|
||||
force,
|
||||
});
|
||||
|
||||
// @ts-expect-error -- TSCONVERSION git errors are not handled correctly
|
||||
if (response.errors?.length) {
|
||||
if (response.error) {
|
||||
console.log('[git] Push rejected', response);
|
||||
// @ts-expect-error -- TSCONVERSION git errors are not handled correctly
|
||||
throw new Error(
|
||||
`Push rejected with errors: ${response.error}.\n\nGo to View > Toggle DevTools > Console for more information.`
|
||||
);
|
||||
}
|
||||
|
||||
if ('errors' in response && response.errors && Array.isArray(response.errors)) {
|
||||
console.log('[git] Push failed with errors', response.errors);
|
||||
const errorsString = JSON.stringify(response.errors);
|
||||
throw new Error(
|
||||
`Push rejected with errors: ${errorsString}.\n\nGo to View > Toggle DevTools > Console for more information.`
|
||||
);
|
||||
}
|
||||
|
||||
// NOTE: Response can be ok and have errors so we check this in the end to make sure we throw an error if there are any.
|
||||
if (response.ok) {
|
||||
console.log('[git] Push successful');
|
||||
return;
|
||||
}
|
||||
|
||||
throw new Error('Push failed with unknown error. Please try again.');
|
||||
}
|
||||
|
||||
async _hasUncommittedChanges() {
|
||||
@@ -896,9 +909,15 @@ export class GitVCS {
|
||||
oursBranch,
|
||||
theirsBranch,
|
||||
);
|
||||
} else {
|
||||
throw err;
|
||||
}
|
||||
|
||||
if (err instanceof git.Errors.MergeNotSupportedError) {
|
||||
const errorMessage = 'Merges with additions are not supported yet.';
|
||||
|
||||
throw new Error(errorMessage);
|
||||
}
|
||||
|
||||
throw err;
|
||||
},
|
||||
);
|
||||
}
|
||||
|
||||
@@ -103,8 +103,8 @@ export const GitProjectStagingModal: FC<{ onClose: () => void }> = ({
|
||||
|
||||
const { Form, formAction, state, data } = useFetcher<{ errors?: string[] }>();
|
||||
|
||||
const isCreatingSnapshot = state === 'loading' && formAction === '/organization/:organizationId/project/:projectId/workspace/:workspaceId/git/commit';
|
||||
const isPushing = state === 'loading' && formAction === '/organization/:organizationId/project/:projectId/workspace/:workspaceId/git/commit-and-push';
|
||||
const isCreatingSnapshot = state !== 'idle' && formAction === `/organization/${organizationId}/project/${projectId}/git/commit`;
|
||||
const isPushing = state !== 'idle' && formAction === `/organization/${organizationId}/project/${projectId}/git/commit-and-push`;
|
||||
const previewDiffItem = diffChangesFetcher.data && 'diff' in diffChangesFetcher.data ? diffChangesFetcher.data : null;
|
||||
|
||||
const allChanges = [...changes.staged, ...changes.unstaged];
|
||||
|
||||
@@ -30,12 +30,10 @@ function getDefaultOAuthProvider(credentials?: GitCredentials | null): OauthProv
|
||||
return 'custom';
|
||||
}
|
||||
|
||||
export const GitProjectRepositorySettingsModal = (props: ModalProps & {
|
||||
export const GitProjectRepositorySettingsModal = ({ gitRepository, ...modalProps }: ModalProps & {
|
||||
gitRepository?: GitRepository;
|
||||
}) => {
|
||||
const { organizationId, projectId } = useParams() as { organizationId: string; projectId: string; workspaceId: string };
|
||||
const { gitRepository } = props;
|
||||
|
||||
const modalRef = useRef<ModalHandle>(null);
|
||||
const updateGitRepositoryFetcher = useFetcher();
|
||||
const deleteGitRepositoryFetcher = useFetcher();
|
||||
@@ -89,7 +87,7 @@ export const GitProjectRepositorySettingsModal = (props: ModalProps & {
|
||||
|
||||
return (
|
||||
<OverlayContainer>
|
||||
<Modal ref={modalRef} {...props}>
|
||||
<Modal ref={modalRef} {...modalProps}>
|
||||
<ModalHeader>
|
||||
Repository Settings{' '}
|
||||
<HelpTooltip>
|
||||
@@ -159,7 +157,7 @@ export const GitProjectRepositorySettingsModal = (props: ModalProps & {
|
||||
>
|
||||
<button
|
||||
className="btn"
|
||||
disabled={!gitRepository}
|
||||
disabled={!hasGitRepository}
|
||||
onClick={() => {
|
||||
deleteGitRepositoryFetcher.submit({}, {
|
||||
action: `/organization/${organizationId}/project/${projectId}/git/reset`,
|
||||
@@ -169,15 +167,26 @@ export const GitProjectRepositorySettingsModal = (props: ModalProps & {
|
||||
>
|
||||
Reset
|
||||
</button>
|
||||
<button
|
||||
type="submit"
|
||||
disabled={isLoading}
|
||||
form={selectedTab}
|
||||
className="btn"
|
||||
data-testid="git-repository-settings-modal__sync-btn"
|
||||
>
|
||||
Sync
|
||||
</button>
|
||||
{hasGitRepository ? (
|
||||
<button
|
||||
type="button"
|
||||
onClick={() => modalRef.current?.hide()}
|
||||
className="btn"
|
||||
data-testid="git-repository-settings-modal__sync-btn-close"
|
||||
>
|
||||
Close
|
||||
</button>
|
||||
) : (
|
||||
<button
|
||||
type="submit"
|
||||
disabled={isLoading}
|
||||
form={selectedTab}
|
||||
className="btn"
|
||||
data-testid="git-repository-settings-modal__sync-btn"
|
||||
>
|
||||
Sync
|
||||
</button>
|
||||
)}
|
||||
</div>
|
||||
</ModalFooter>
|
||||
</Modal>
|
||||
|
||||
@@ -30,11 +30,10 @@ function getDefaultOAuthProvider(credentials?: GitCredentials | null): OauthProv
|
||||
return 'custom';
|
||||
}
|
||||
|
||||
export const GitRepositorySettingsModal = (props: ModalProps & {
|
||||
export const GitRepositorySettingsModal = ({ gitRepository, ...modalProps }: ModalProps & {
|
||||
gitRepository?: GitRepository;
|
||||
}) => {
|
||||
const { organizationId, projectId, workspaceId } = useParams() as { organizationId: string; projectId: string; workspaceId: string };
|
||||
const { gitRepository } = props;
|
||||
const modalRef = useRef<ModalHandle>(null);
|
||||
const updateGitRepositoryFetcher = useFetcher();
|
||||
const deleteGitRepositoryFetcher = useFetcher();
|
||||
@@ -88,7 +87,7 @@ export const GitRepositorySettingsModal = (props: ModalProps & {
|
||||
|
||||
return (
|
||||
<OverlayContainer>
|
||||
<Modal ref={modalRef} {...props}>
|
||||
<Modal ref={modalRef} {...modalProps}>
|
||||
<ModalHeader>
|
||||
Repository Settings{' '}
|
||||
<HelpTooltip>
|
||||
@@ -158,7 +157,7 @@ export const GitRepositorySettingsModal = (props: ModalProps & {
|
||||
>
|
||||
<button
|
||||
className="btn"
|
||||
disabled={!gitRepository}
|
||||
disabled={!hasGitRepository}
|
||||
onClick={() => {
|
||||
deleteGitRepositoryFetcher.submit({}, {
|
||||
action: `/organization/${organizationId}/project/${projectId}/workspace/${workspaceId}/git/reset`,
|
||||
|
||||
@@ -95,18 +95,18 @@ export const GitStagingModal: FC<{ onClose: () => void }> = ({
|
||||
const {
|
||||
changes,
|
||||
} = gitChangesFetcher.data || {
|
||||
changes: {
|
||||
staged: [],
|
||||
unstaged: [],
|
||||
},
|
||||
changes: {
|
||||
staged: [],
|
||||
unstaged: [],
|
||||
},
|
||||
branch: '',
|
||||
statusNames: {},
|
||||
};
|
||||
|
||||
const { Form, formAction, state, data } = useFetcher<{ errors?: string[]; gitRepository: GitRepository }>();
|
||||
|
||||
const isCreatingSnapshot = state === 'loading' && formAction === '/organization/:organizationId/project/:projectId/workspace/:workspaceId/git/commit';
|
||||
const isPushing = state === 'loading' && formAction === '/organization/:organizationId/project/:projectId/workspace/:workspaceId/git/commit-and-push';
|
||||
const isCreatingSnapshot = state !== 'idle' && formAction === `/organization/${organizationId}/project/${projectId}/workspace/:workspaceId/git/commit`;
|
||||
const isPushing = state !== 'idle' && formAction === `/organization/${organizationId}/project/${projectId}/workspace/${workspaceId}/git/commit-and-push`;
|
||||
|
||||
const previewDiffItem = diffChangesFetcher.data && 'diff' in diffChangesFetcher.data ? diffChangesFetcher.data : null;
|
||||
|
||||
|
||||
Reference in New Issue
Block a user