mirror of
https://github.com/AutoMaker-Org/automaker.git
synced 2026-03-18 22:33:08 +00:00
- Add feature mutations (create, update, delete with optimistic updates) - Add auto-mode mutations (start, stop, approve plan) - Add worktree mutations (create, delete, checkout, switch branch) - Add settings mutations (update global/project, validate API keys) - Add GitHub mutations (create PR, validate PR) - Add cursor permissions mutations (apply profile, copy config) - Add spec mutations (generate, update, save) - Add pipeline mutations (toggle, update config) - Add session mutations with cache invalidation Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
97 lines
2.6 KiB
TypeScript
97 lines
2.6 KiB
TypeScript
/**
|
|
* Cursor Permissions Mutation Hooks
|
|
*
|
|
* React Query mutations for managing Cursor CLI permissions.
|
|
*/
|
|
|
|
import { useMutation, useQueryClient } from '@tanstack/react-query';
|
|
import { getHttpApiClient } from '@/lib/http-api-client';
|
|
import { queryKeys } from '@/lib/query-keys';
|
|
import { toast } from 'sonner';
|
|
|
|
interface ApplyProfileInput {
|
|
profileId: 'strict' | 'development';
|
|
scope: 'global' | 'project';
|
|
}
|
|
|
|
/**
|
|
* Apply a Cursor permission profile
|
|
*
|
|
* @param projectPath - Optional path to the project (required for project scope)
|
|
* @returns Mutation for applying permission profiles
|
|
*
|
|
* @example
|
|
* ```tsx
|
|
* const applyMutation = useApplyCursorProfile(projectPath);
|
|
* applyMutation.mutate({ profileId: 'development', scope: 'project' });
|
|
* ```
|
|
*/
|
|
export function useApplyCursorProfile(projectPath?: string) {
|
|
const queryClient = useQueryClient();
|
|
|
|
return useMutation({
|
|
mutationFn: async (input: ApplyProfileInput) => {
|
|
const { profileId, scope } = input;
|
|
const api = getHttpApiClient();
|
|
const result = await api.setup.applyCursorPermissionProfile(
|
|
profileId,
|
|
scope,
|
|
scope === 'project' ? projectPath : undefined
|
|
);
|
|
|
|
if (!result.success) {
|
|
throw new Error(result.error || 'Failed to apply profile');
|
|
}
|
|
|
|
return result;
|
|
},
|
|
onSuccess: (result) => {
|
|
// Invalidate permissions cache
|
|
queryClient.invalidateQueries({
|
|
queryKey: queryKeys.cursorPermissions.permissions(projectPath),
|
|
});
|
|
toast.success(result.message || 'Profile applied');
|
|
},
|
|
onError: (error) => {
|
|
toast.error('Failed to apply profile', {
|
|
description: error instanceof Error ? error.message : 'Unknown error',
|
|
});
|
|
},
|
|
});
|
|
}
|
|
|
|
/**
|
|
* Copy Cursor example config to clipboard
|
|
*
|
|
* @returns Mutation for copying config
|
|
*
|
|
* @example
|
|
* ```tsx
|
|
* const copyMutation = useCopyCursorConfig();
|
|
* copyMutation.mutate('development');
|
|
* ```
|
|
*/
|
|
export function useCopyCursorConfig() {
|
|
return useMutation({
|
|
mutationFn: async (profileId: 'strict' | 'development') => {
|
|
const api = getHttpApiClient();
|
|
const result = await api.setup.getCursorExampleConfig(profileId);
|
|
|
|
if (!result.success || !result.config) {
|
|
throw new Error(result.error || 'Failed to get config');
|
|
}
|
|
|
|
await navigator.clipboard.writeText(result.config);
|
|
return result;
|
|
},
|
|
onSuccess: () => {
|
|
toast.success('Config copied to clipboard');
|
|
},
|
|
onError: (error) => {
|
|
toast.error('Failed to copy config', {
|
|
description: error instanceof Error ? error.message : 'Unknown error',
|
|
});
|
|
},
|
|
});
|
|
}
|