feat: point core frontend snippets pickers at the plugin (B2)

This commit is contained in:
LukeGus committed 2026-09-23 08:59:06 -05:00
1 parent e07221eaf3
commit 1eac0f54b0
22 files changed
+170 -2968

No files matched your search

+10 -6
View File
@@ -195,7 +195,7 @@ export async function adminGetUserSnippets(
targetUserId: string,
): Promise<Record<string, unknown>> {
try {
const response = await authApi.get("/snippets", {
const response = await authApi.get("/plugin-api/snippets", {
headers: adminHeaders(targetUserId),
});
return response.data;
@@ -209,7 +209,7 @@ export async function adminCreateUserSnippet(
snippetData: Record<string, unknown>,
): Promise<Record<string, unknown>> {
try {
const response = await authApi.post("/snippets", snippetData, {
const response = await authApi.post("/plugin-api/snippets", snippetData, {
headers: adminHeaders(targetUserId),
});
return response.data;
@@ -224,9 +224,13 @@ export async function adminUpdateUserSnippet(
snippetData: Record<string, unknown>,
): Promise<Record<string, unknown>> {
try {
const response = await authApi.put(`/snippets/${snippetId}`, snippetData, {
headers: adminHeaders(targetUserId),
});
const response = await authApi.put(
`/plugin-api/snippets/${snippetId}`,
snippetData,
{
headers: adminHeaders(targetUserId),
},
);
return response.data;
} catch (error) {
throw handleApiError(error, "update user's snippet");
@@ -238,7 +242,7 @@ export async function adminDeleteUserSnippet(
snippetId: number,
): Promise<Record<string, unknown>> {
try {
const response = await authApi.delete(`/snippets/${snippetId}`, {
const response = await authApi.delete(`/plugin-api/snippets/${snippetId}`, {
headers: adminHeaders(targetUserId),
});
return response.data;
-1
View File
@@ -115,7 +115,6 @@ export interface UserPreferences {
pinAppRail?: boolean | null;
expandAppRailOnHover?: boolean | null;
showPinAppRailButton?: boolean | null;
foldersCollapsed?: boolean | null;
confirmSnippetExecution?: boolean | null;
disableUpdateCheck?: boolean | null;
confirmTabClose?: boolean | null;
-86
View File
@@ -397,47 +397,6 @@ export async function setHostAuthOverride(
}
}
// ============================================================================
// SNIPPET SHARING
// ============================================================================
export async function shareSnippet(
snippetId: number,
shareData: {
targetType: "user" | "role";
targetUserId?: string;
targetRoleId?: number;
durationHours?: number;
},
): Promise<{ success: boolean }> {
try {
const response = await rbacApi.post(
`/rbac/snippet/${snippetId}/share`,
shareData,
);
return response.data;
} catch (error) {
throw handleApiError(error, "share snippet");
}
}
export async function shareSnippetFolder(
folder: string,
targets: ShareTarget[],
durationHours?: number,
): Promise<{ success: boolean; snippetsShared: number }> {
try {
const response = await rbacApi.post("/rbac/snippet-folder/share", {
folder,
targets,
durationHours,
});
return response.data;
} catch (error) {
throw handleApiError(error, "share snippet folder");
}
}
export type CredentialPermissionLevel = "use" | "manage";
export async function shareCredential(
@@ -480,48 +439,3 @@ export async function revokeCredentialAccess(
throw handleApiError(error, "revoke credential access");
}
}
export async function getSnippetAccess(
snippetId: number,
): Promise<{ accessList: AccessRecord[] }> {
try {
const response = await rbacApi.get(`/rbac/snippet/${snippetId}/access`);
return response.data;
} catch (error) {
throw handleApiError(error, "fetch snippet access");
}
}
export async function revokeSnippetAccess(
snippetId: number,
accessId: number,
): Promise<{ success: boolean }> {
try {
const response = await rbacApi.delete(
`/rbac/snippet/${snippetId}/access/${accessId}`,
);
return response.data;
} catch (error) {
throw handleApiError(error, "revoke snippet access");
}
}
export async function getSharedSnippets(): Promise<{
sharedSnippets: Array<{
id: number;
name: string;
content: string;
description: string | null;
folder: string | null;
ownerUsername: string;
permissionLevel: string;
expiresAt: string | null;
}>;
}> {
try {
const response = await rbacApi.get("/rbac/shared-snippets");
return response.data;
} catch (error) {
handleApiError(error, "fetch shared snippets");
}
}
+8 -163
View File
@@ -3,6 +3,12 @@ import { authApi, handleApiError } from "@/main-axios";
/**
* A snippet row as the list endpoint returns it. Callers that need the full
* shape narrow it themselves; only the id is relied on across the app.
*
* Snippets themselves are owned by the snippets plugin
* (/plugin-api/snippets); this is the thin read/run surface used by a few
* core and plugin callers (the host editor's startup snippet, the command
* palette, custom keybindings, host-metrics quick actions) that cannot
* reach into the snippets plugin's own frontend code.
*/
export interface SnippetRow {
id: number;
@@ -11,54 +17,20 @@ export interface SnippetRow {
export async function getSnippets(): Promise<SnippetRow[]> {
try {
const response = await authApi.get("/snippets");
const response = await authApi.get("/plugin-api/snippets");
return response.data;
} catch (error) {
throw handleApiError(error, "fetch snippets");
}
}
export async function createSnippet(
snippetData: Record<string, unknown>,
): Promise<Record<string, unknown>> {
try {
const response = await authApi.post("/snippets", snippetData);
return response.data;
} catch (error) {
throw handleApiError(error, "create snippet");
}
}
export async function updateSnippet(
snippetId: number,
snippetData: Record<string, unknown>,
): Promise<Record<string, unknown>> {
try {
const response = await authApi.put(`/snippets/${snippetId}`, snippetData);
return response.data;
} catch (error) {
throw handleApiError(error, "update snippet");
}
}
export async function deleteSnippet(
snippetId: number,
): Promise<Record<string, unknown>> {
try {
const response = await authApi.delete(`/snippets/${snippetId}`);
return response.data;
} catch (error) {
throw handleApiError(error, "delete snippet");
}
}
export async function executeSnippet(
snippetId: number,
hostId: number,
inputValues?: Record<string, string>,
): Promise<{ success: boolean; output: string; error?: string }> {
try {
const response = await authApi.post("/snippets/execute", {
const response = await authApi.post("/plugin-api/snippets/execute", {
snippetId,
hostId,
...(inputValues ? { inputValues } : {}),
@@ -68,130 +40,3 @@ export async function executeSnippet(
throw handleApiError(error, "execute snippet");
}
}
export async function getSnippetFolders(): Promise<Record<string, unknown>> {
try {
const response = await authApi.get("/snippets/folders");
return response.data;
} catch (error) {
throw handleApiError(error, "fetch snippet folders");
}
}
export async function createSnippetFolder(folderData: {
name: string;
color?: string;
icon?: string;
}): Promise<Record<string, unknown>> {
try {
const response = await authApi.post("/snippets/folders", folderData);
return response.data;
} catch (error) {
throw handleApiError(error, "create snippet folder");
}
}
export async function updateSnippetFolderMetadata(
folderName: string,
metadata: { color?: string; icon?: string },
): Promise<Record<string, unknown>> {
try {
const response = await authApi.put(
`/snippets/folders/${encodeURIComponent(folderName)}/metadata`,
metadata,
);
return response.data;
} catch (error) {
throw handleApiError(error, "update snippet folder metadata");
}
}
export async function renameSnippetFolder(
oldName: string,
newName: string,
): Promise<{ success: boolean; oldName: string; newName: string }> {
try {
const response = await authApi.put("/snippets/folders/rename", {
oldName,
newName,
});
return response.data;
} catch (error) {
throw handleApiError(error, "rename snippet folder");
}
}
export async function deleteSnippetFolder(
folderName: string,
): Promise<{ success: boolean }> {
try {
const response = await authApi.delete(
`/snippets/folders/${encodeURIComponent(folderName)}`,
);
return response.data;
} catch (error) {
throw handleApiError(error, "delete snippet folder");
}
}
export async function reorderSnippets(
updates: Array<{ id: number; order: number; folder?: string }>,
): Promise<{ success: boolean }> {
try {
const response = await authApi.put("/snippets/reorder", {
snippets: updates,
});
return response.data;
} catch (error) {
throw handleApiError(error, "reorder snippets");
}
}
export interface SnippetExportData {
snippets: Array<{
name: string;
content: string;
description?: string | null;
folder?: string | null;
order?: number;
hostFilter?: string | null;
}>;
folders: Array<{
name: string;
color?: string | null;
icon?: string | null;
}>;
}
export async function exportSnippets(): Promise<SnippetExportData> {
try {
const response = await authApi.get("/snippets/export");
return response.data;
} catch (error) {
throw handleApiError(error, "export snippets");
}
}
export async function importSnippets(
data: SnippetExportData,
overwrite: boolean,
): Promise<{
success: boolean;
snippetsImported: number;
snippetsSkipped: number;
snippetsUpdated: number;
foldersImported: number;
foldersSkipped: number;
failed: number;
errors: string[];
}> {
try {
const response = await authApi.post("/snippets/bulk-import", {
...data,
overwrite,
});
return response.data;
} catch (error) {
throw handleApiError(error, "import snippets");
}
}