Compare commits

...

7 Commits

Author SHA1 Message Date
Gregory Schier
6f50f35519 Bump Tauri to fix macOS 13 launch issue 2024-10-15 09:54:21 -07:00
Gregory Schier
4e775b2b49 Undo minimumSystemVersion 2024-10-15 07:49:27 -07:00
Gregory Schier
e77a9e5d44 Rebuild plugins 2024-10-15 07:48:26 -07:00
Gregory Schier
a381e44d8c Prevent stale content flash after editing request name 2024-10-15 07:32:00 -07:00
Gregory Schier
4acf0969e8 Only sync models from active workspace 2024-10-15 07:31:42 -07:00
Gregory Schier
30c4178269 Disable autocomplete/correct/etc in plain input 2024-10-14 21:46:48 -07:00
Gregory Schier
dffe6e0a16 Intelligent readonly editor updates, to preserve scroll 2024-10-14 10:40:09 -07:00
18 changed files with 206 additions and 76 deletions

88
package-lock.json generated
View File

@@ -18,7 +18,7 @@
"src-web"
],
"devDependencies": {
"@tauri-apps/cli": "^2.0.2",
"@tauri-apps/cli": "^2.0.3",
"@typescript-eslint/eslint-plugin": "^8.5.0",
"@typescript-eslint/parser": "^8.5.0",
"eslint": "^8",
@@ -2689,9 +2689,9 @@
}
},
"node_modules/@tauri-apps/cli": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli/-/cli-2.0.2.tgz",
"integrity": "sha512-R4ontHZvXORArERAHIidp5zRfZEshZczTiK+poslBv7AGKpQZoMw+E49zns7mOmP64i2Cq9Ci0pJvi4Rm8Okzw==",
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli/-/cli-2.0.3.tgz",
"integrity": "sha512-JwEyhc5BAVpn4E8kxzY/h7+bVOiXQdudR1r3ODMfyyumZBfgIWqpD/WuTcPq6Yjchju1BSS+80jAE/oYwI/RKg==",
"dev": true,
"license": "Apache-2.0 OR MIT",
"bin": {
@@ -2705,22 +2705,22 @@
"url": "https://opencollective.com/tauri"
},
"optionalDependencies": {
"@tauri-apps/cli-darwin-arm64": "2.0.2",
"@tauri-apps/cli-darwin-x64": "2.0.2",
"@tauri-apps/cli-linux-arm-gnueabihf": "2.0.2",
"@tauri-apps/cli-linux-arm64-gnu": "2.0.2",
"@tauri-apps/cli-linux-arm64-musl": "2.0.2",
"@tauri-apps/cli-linux-x64-gnu": "2.0.2",
"@tauri-apps/cli-linux-x64-musl": "2.0.2",
"@tauri-apps/cli-win32-arm64-msvc": "2.0.2",
"@tauri-apps/cli-win32-ia32-msvc": "2.0.2",
"@tauri-apps/cli-win32-x64-msvc": "2.0.2"
"@tauri-apps/cli-darwin-arm64": "2.0.3",
"@tauri-apps/cli-darwin-x64": "2.0.3",
"@tauri-apps/cli-linux-arm-gnueabihf": "2.0.3",
"@tauri-apps/cli-linux-arm64-gnu": "2.0.3",
"@tauri-apps/cli-linux-arm64-musl": "2.0.3",
"@tauri-apps/cli-linux-x64-gnu": "2.0.3",
"@tauri-apps/cli-linux-x64-musl": "2.0.3",
"@tauri-apps/cli-win32-arm64-msvc": "2.0.3",
"@tauri-apps/cli-win32-ia32-msvc": "2.0.3",
"@tauri-apps/cli-win32-x64-msvc": "2.0.3"
}
},
"node_modules/@tauri-apps/cli-darwin-arm64": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-darwin-arm64/-/cli-darwin-arm64-2.0.2.tgz",
"integrity": "sha512-B+/a8Q6wAqmB4A4HVeK0oQP5TdQGKW60ZLOI9O2ktH2HPr9ETr3XkwXPuJ2uAOuGEgtRZHBgFOIgG000vMnKlg==",
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-darwin-arm64/-/cli-darwin-arm64-2.0.3.tgz",
"integrity": "sha512-jIsbxGWS+As1ZN7umo90nkql/ZAbrDK0GBT6UsgHSz5zSwwArICsZFFwE1pLZip5yoiV5mn3TGG2c1+v+0puzQ==",
"cpu": [
"arm64"
],
@@ -2735,9 +2735,9 @@
}
},
"node_modules/@tauri-apps/cli-darwin-x64": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-darwin-x64/-/cli-darwin-x64-2.0.2.tgz",
"integrity": "sha512-kaurhn6XT4gAVCPAQSSHl/CHFxTS0ljc47N7iGTSlYJ03sCWPRZeNuVa/bn6rolz9MA2JfnRnFqB1pUL6jzp9Q==",
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-darwin-x64/-/cli-darwin-x64-2.0.3.tgz",
"integrity": "sha512-ROITHtLTA1muyrwgyuwyasmaLCGtT4as/Kd1kerXaSDtFcYrnxiM984ZD0+FDUEDl5BgXtYa/sKKkKQFjgmM0A==",
"cpu": [
"x64"
],
@@ -2752,9 +2752,9 @@
}
},
"node_modules/@tauri-apps/cli-linux-arm-gnueabihf": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-arm-gnueabihf/-/cli-linux-arm-gnueabihf-2.0.2.tgz",
"integrity": "sha512-bVrofjlacMxmGMcqK18iBW05tsZXOd19/MnqruFFcHSVjvkGGIXHMtUbMXnZNXBPkHDsnfytNtkY9SZGfCFaBA==",
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-arm-gnueabihf/-/cli-linux-arm-gnueabihf-2.0.3.tgz",
"integrity": "sha512-bQ3EZwCFfrLg/ZQ2I8sLuifSxESz4TP56SleTkKsPtTIZgNnKpM88PRDz4neiRroHVOq8NK0X276qi9LjGcXPw==",
"cpu": [
"arm"
],
@@ -2769,9 +2769,9 @@
}
},
"node_modules/@tauri-apps/cli-linux-arm64-gnu": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-arm64-gnu/-/cli-linux-arm64-gnu-2.0.2.tgz",
"integrity": "sha512-7XCBn0TTBVQGnV42dXcbHPLg/9W8kJoVzuliIozvNGyRWxfXqDbQYzpI48HUQG3LgHMabcw8+pVZAfGhevLrCA==",
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-arm64-gnu/-/cli-linux-arm64-gnu-2.0.3.tgz",
"integrity": "sha512-aLfAA8P9OTErVUk3sATxtXqpAtlfDPMPp4fGjDysEELG/MyekGhmh2k/kG/i32OdPeCfO+Nr37wJksARJKubGw==",
"cpu": [
"arm64"
],
@@ -2786,9 +2786,9 @@
}
},
"node_modules/@tauri-apps/cli-linux-arm64-musl": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-arm64-musl/-/cli-linux-arm64-musl-2.0.2.tgz",
"integrity": "sha512-1xi2SreGVlpAL68MCsDUY63rdItUdPZreXIAcOVqvUehcJRYOa1XGSBhrV0YXRgZeh0AtKC19z6PRzcv4rosZA==",
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-arm64-musl/-/cli-linux-arm64-musl-2.0.3.tgz",
"integrity": "sha512-I4MVD7nf6lLLRmNQPpe5beEIFM6q7Zkmh77ROA5BNu/+vHNL5kiTMD+bmd10ZL2r753A6pO7AvqkIxcBuIl0tg==",
"cpu": [
"arm64"
],
@@ -2803,9 +2803,9 @@
}
},
"node_modules/@tauri-apps/cli-linux-x64-gnu": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-x64-gnu/-/cli-linux-x64-gnu-2.0.2.tgz",
"integrity": "sha512-WVjwYzPWFqZVg1fx6KSU5w47Q0VbMyaCp34qs5EcS8EIU0/RnofdzqUoOYqvgGVgNgoz7Pj5dXK2SkS8BHXMmA==",
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-x64-gnu/-/cli-linux-x64-gnu-2.0.3.tgz",
"integrity": "sha512-C6Jkx2zZGKkoi+sg5FK9GoH/0EvAaOgrZfF5azV5EALGba46g7VpWcZgp9zFUd7K2IzTi+0OOY8TQ2OVfKZgew==",
"cpu": [
"x64"
],
@@ -2820,9 +2820,9 @@
}
},
"node_modules/@tauri-apps/cli-linux-x64-musl": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-x64-musl/-/cli-linux-x64-musl-2.0.2.tgz",
"integrity": "sha512-h5miE2mctgaQNn/BbG9o1pnJcrx+VGBi2A6JFqGu934lFgSV5+s28M8Gc8AF2JgFH4hQV4IuMkeSw8Chu5Dodg==",
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-linux-x64-musl/-/cli-linux-x64-musl-2.0.3.tgz",
"integrity": "sha512-qi4ghmTfSAl+EEUDwmwI9AJUiOLNSmU1RgiGgcPRE+7A/W+Am9UnxYySAiRbB/gJgTl9sj/pqH5Y9duP1/sqHg==",
"cpu": [
"x64"
],
@@ -2837,9 +2837,9 @@
}
},
"node_modules/@tauri-apps/cli-win32-arm64-msvc": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-win32-arm64-msvc/-/cli-win32-arm64-msvc-2.0.2.tgz",
"integrity": "sha512-2b8oO0+dYonahG5PfA/zoq0zlafLclfmXgqoWDZ++UiPtQHJNpNeEQ8GWbSFKGHQ494Jo6jHvazOojGRE1kqAg==",
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-win32-arm64-msvc/-/cli-win32-arm64-msvc-2.0.3.tgz",
"integrity": "sha512-UXxHkYmFesC97qVmZre4vY7oDxRDtC2OeKNv0bH+iSnuUp/ROxzJYGyaelnv9Ybvgl4YVqDCnxgB28qMM938TA==",
"cpu": [
"arm64"
],
@@ -2854,9 +2854,9 @@
}
},
"node_modules/@tauri-apps/cli-win32-ia32-msvc": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-win32-ia32-msvc/-/cli-win32-ia32-msvc-2.0.2.tgz",
"integrity": "sha512-axgICLunFi0To3EibdCBgbST5RocsSmtM4c04+CbcX8WQQosJ9ziWlCSrrOTRr+gJERAMSvEyVUS98f6bWMw9A==",
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-win32-ia32-msvc/-/cli-win32-ia32-msvc-2.0.3.tgz",
"integrity": "sha512-D+xoaa35RGlkXDpnL5uDTpj29untuC5Wp6bN9snfgFDagD0wnFfC8+2ZQGu16bD0IteWqDI0OSoIXhNvy+F+wg==",
"cpu": [
"ia32"
],
@@ -2871,9 +2871,9 @@
}
},
"node_modules/@tauri-apps/cli-win32-x64-msvc": {
"version": "2.0.2",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-win32-x64-msvc/-/cli-win32-x64-msvc-2.0.2.tgz",
"integrity": "sha512-JR17cM6+DyExZRgpXr2/DdqvcFYi/EKvQt8dI5R1/uQoesWd8jeNnrU7c1FG1Zmw9+pTzDztsNqEKsrNq2sNIg==",
"version": "2.0.3",
"resolved": "https://registry.npmjs.org/@tauri-apps/cli-win32-x64-msvc/-/cli-win32-x64-msvc-2.0.3.tgz",
"integrity": "sha512-eWV9XWb4dSYHXl13OtYWLjX1JHphUEkHkkGwJrhr8qFBm7RbxXxQvrsUEprSi51ug/dwJenjJgM4zR8By4htfw==",
"cpu": [
"x64"
],

View File

@@ -31,7 +31,7 @@
"tauri-before-dev": "npm run --workspaces --if-present dev"
},
"devDependencies": {
"@tauri-apps/cli": "^2.0.2",
"@tauri-apps/cli": "^2.0.3",
"@typescript-eslint/eslint-plugin": "^8.5.0",
"@typescript-eslint/parser": "^8.5.0",
"eslint": "^8",

12
src-tauri/Cargo.lock generated
View File

@@ -6095,9 +6095,9 @@ checksum = "61c41af27dd6d1e27b1b16b489db798443478cef1f06a660c96db617ba5de3b1"
[[package]]
name = "tauri"
version = "2.0.3"
version = "2.0.4"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "fd96d46534b10765ce0c6208f9451d98ea38636364a41b272d3610c70dd0e4c3"
checksum = "44438500b50708bfc1e6083844e135d1b516325aae58710dcd8fb67e050ae87c"
dependencies = [
"anyhow",
"bytes",
@@ -6406,9 +6406,9 @@ dependencies = [
[[package]]
name = "tauri-runtime-wry"
version = "2.1.0"
version = "2.1.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "aaac63b65df8e85570993eaf93ae1dd73a6fb66d8bd99674ce65f41dc3c63e7d"
checksum = "1431602bcc71f2f840ad623915c9842ecc32999b867c4a787d975a17a9625cc6"
dependencies = [
"gtk",
"http 1.1.0",
@@ -7848,9 +7848,9 @@ dependencies = [
[[package]]
name = "wry"
version = "0.46.0"
version = "0.46.1"
source = "registry+https://github.com/rust-lang/crates.io-index"
checksum = "469a3765ecc3e8aa9ccdf3c5a52c82697ec03037cd60494488763880d31a1b3a"
checksum = "2f8c948dc5f7c23bd93ba03b85b7f679852589bb78e150424d993171e4ef7b73"
dependencies = [
"base64 0.22.1",
"block2",

View File

@@ -66,4 +66,4 @@ eventsource-client = { git = "https://github.com/yaakapp/rust-eventsource-client
yaak_models = { path = "yaak_models" }
yaak_plugin_runtime = { path = "yaak_plugin_runtime" }
tauri-plugin-shell = "2.0.1"
tauri = { version = "2.0.3", features = ["devtools", "protocol-asset"] }
tauri = { version = "2.0.4", features = ["devtools", "protocol-asset"] }

View File

@@ -288,7 +288,8 @@ var SUPPORTED_ARGS = [
// Request method
DATA_FLAGS
].flatMap((v) => v);
function pluginHookImport(ctx, rawData) {
var BOOL_FLAGS = ["G", "get", "digest"];
function pluginHookImport(_ctx, rawData) {
if (!rawData.match(/^\s*curl /)) {
return null;
}
@@ -359,10 +360,11 @@ function importCommand(parseEntries, workspaceId) {
}
let value;
const nextEntry = parseEntries[i + 1];
const hasValue = !BOOL_FLAGS.includes(name);
if (isSingleDash && name.length > 1) {
value = name.slice(1);
name = name.slice(0, 1);
} else if (typeof nextEntry === "string" && !nextEntry.startsWith("-")) {
} else if (typeof nextEntry === "string" && hasValue && !nextEntry.startsWith("-")) {
value = nextEntry;
i++;
} else {

View File

@@ -0,0 +1,55 @@
"use strict";
var __create = Object.create;
var __defProp = Object.defineProperty;
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
var __getOwnPropNames = Object.getOwnPropertyNames;
var __getProtoOf = Object.getPrototypeOf;
var __hasOwnProp = Object.prototype.hasOwnProperty;
var __export = (target, all) => {
for (var name in all)
__defProp(target, name, { get: all[name], enumerable: true });
};
var __copyProps = (to, from, except, desc) => {
if (from && typeof from === "object" || typeof from === "function") {
for (let key of __getOwnPropNames(from))
if (!__hasOwnProp.call(to, key) && key !== except)
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
}
return to;
};
var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
// If the importer is in node compatibility mode or this is not an ESM
// file that has been converted to a CommonJS file using a Babel-
// compatible transform (i.e. "__esModule" has not been set), then set
// "default" to the CommonJS "module.exports" for node compatibility.
isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
mod
));
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
// src/index.ts
var src_exports = {};
__export(src_exports, {
plugin: () => plugin
});
module.exports = __toCommonJS(src_exports);
var import_node_fs = __toESM(require("node:fs"));
var plugin = {
templateFunctions: [{
name: "fs.readFile",
description: "Read the contents of a file as utf-8",
args: [{ title: "Select File", type: "file", name: "path", label: "File" }],
async onRender(_ctx, args) {
if (!args.values.path) return null;
try {
return import_node_fs.default.promises.readFile(args.values.path, "utf-8");
} catch (err) {
return null;
}
}
}]
};
// Annotate the CommonJS export names for ESM import in node:
0 && (module.exports = {
plugin
});

View File

@@ -0,0 +1,9 @@
{
"name": "@yaakapp/template-function-fs",
"private": true,
"version": "0.0.1",
"scripts": {
"build": "yaakcli build ./src/index.ts",
"dev": "yaakcli dev ./src/index.js"
}
}

View File

@@ -28,6 +28,7 @@ var algorithms = ["md5", "sha1", "sha256", "sha512"];
var plugin = {
templateFunctions: algorithms.map((algorithm) => ({
name: `hash.${algorithm}`,
description: "Hash a value to its hexidecimal representation",
args: [
{
name: "input",

View File

@@ -26,24 +26,21 @@ module.exports = __toCommonJS(src_exports);
var plugin = {
templateFunctions: [{
name: "prompt.text",
description: "Prompt the user for input when sending a request",
args: [
{ type: "text", name: "title", label: "Title" },
{ type: "text", name: "label", label: "Label", optional: true },
{ type: "text", name: "defaultValue", label: "Default Value", optional: true },
{ type: "text", name: "placeholder", label: "Placeholder", optional: true }
],
async onRender(ctx, args) {
console.log("PROMPT", args);
if (args.purpose !== "send") return null;
const value = await ctx.prompt.text({
return await ctx.prompt.text({
id: `prompt-${args.values.label}`,
label: args.values.label ?? "",
label: args.values.title ?? "",
title: args.values.title ?? "",
defaultValue: args.values.defaultValue,
placeholder: args.values.placeholder
});
console.log("VALUE", value);
return value;
}
}]
};

View File

@@ -8837,6 +8837,7 @@ var plugin = {
templateFunctions: [
{
name: "response.header",
description: "Read the value of a response header, by name",
args: [
requestArg,
{
@@ -8863,6 +8864,7 @@ var plugin = {
},
{
name: "response.body.path",
description: "Access a field of the response body using JsonPath or XPath",
aliases: ["response"],
args: [
requestArg,
@@ -8901,6 +8903,34 @@ var plugin = {
}
return null;
}
},
{
name: "response.body.raw",
description: "Access the entire response body, as text",
aliases: ["response"],
args: [
requestArg,
behaviorArg
],
async onRender(ctx, args) {
if (!args.values.request) return null;
const response = await getResponse(ctx, {
requestId: args.values.request,
purpose: args.purpose,
behavior: args.values.behavior ?? null
});
if (response == null) return null;
if (response.bodyPath == null) {
return null;
}
let body;
try {
body = (0, import_node_fs.readFileSync)(response.bodyPath, "utf-8");
} catch (_) {
return null;
}
return body;
}
}
]
};

View File

@@ -1,10 +1,6 @@
import { lazy } from 'react';
import { createBrowserRouter, Navigate, RouterProvider, useParams } from 'react-router-dom';
import { routePaths, useAppRoutes } from '../hooks/useAppRoutes';
import { useGenerateThemeCss } from '../hooks/useGenerateThemeCss';
import { useSyncFontSizeSetting } from '../hooks/useSyncFontSizeSetting';
import { useSyncModelStores } from '../hooks/useSyncModelStores';
import { useSyncZoomSetting } from '../hooks/useSyncZoomSetting';
import { DefaultLayout } from './DefaultLayout';
import { RedirectToLatestWorkspace } from './RedirectToLatestWorkspace';
import RouteError from './RouteError';
@@ -54,12 +50,6 @@ const router = createBrowserRouter([
]);
export function AppRouter() {
// Add some global hooks that should remain persistent
useSyncModelStores();
useSyncZoomSetting();
useSyncFontSizeSetting();
useGenerateThemeCss();
return <RouterProvider router={router} />;
}

View File

@@ -2,6 +2,7 @@ import { emit } from '@tauri-apps/api/event';
import type { PromptTextRequest, PromptTextResponse } from '@yaakapp-internal/plugin';
import { useEnsureActiveCookieJar } from '../hooks/useActiveCookieJar';
import { useActiveWorkspaceChangedToast } from '../hooks/useActiveWorkspaceChangedToast';
import {useGenerateThemeCss} from "../hooks/useGenerateThemeCss";
import { useHotKey } from '../hooks/useHotKey';
import { useListenToTauriEvent } from '../hooks/useListenToTauriEvent';
import { useNotificationToast } from '../hooks/useNotificationToast';
@@ -10,10 +11,18 @@ import { useRecentCookieJars } from '../hooks/useRecentCookieJars';
import { useRecentEnvironments } from '../hooks/useRecentEnvironments';
import { useRecentRequests } from '../hooks/useRecentRequests';
import { useRecentWorkspaces } from '../hooks/useRecentWorkspaces';
import {useSyncFontSizeSetting} from "../hooks/useSyncFontSizeSetting";
import {useSyncModelStores} from "../hooks/useSyncModelStores";
import { useSyncWorkspaceChildModels } from '../hooks/useSyncWorkspaceChildModels';
import {useSyncZoomSetting} from "../hooks/useSyncZoomSetting";
import { useToggleCommandPalette } from '../hooks/useToggleCommandPalette';
export function GlobalHooks() {
useSyncModelStores();
useSyncZoomSetting();
useSyncFontSizeSetting();
useGenerateThemeCss();
// Include here so they always update, even if no component references them
useRecentWorkspaces();
useRecentEnvironments();

View File

@@ -702,11 +702,11 @@ function SidebarItem({
useScrollIntoView(ref.current, isActive);
const handleSubmitNameEdit = useCallback(
(el: HTMLInputElement) => {
async (el: HTMLInputElement) => {
if (itemModel === 'http_request') {
updateHttpRequest.mutate({ id: itemId, update: (r) => ({ ...r, name: el.value }) });
await updateHttpRequest.mutateAsync({ id: itemId, update: (r) => ({ ...r, name: el.value }) });
} else if (itemModel === 'grpc_request') {
updateGrpcRequest.mutate({ id: itemId, update: (r) => ({ ...r, name: el.value }) });
await updateGrpcRequest.mutateAsync({ id: itemId, update: (r) => ({ ...r, name: el.value }) });
}
setEditing(false);
},

View File

@@ -8,12 +8,12 @@ import classNames from 'classnames';
import { EditorView } from 'codemirror';
import type { MutableRefObject, ReactNode } from 'react';
import {
useEffect,
Children,
cloneElement,
forwardRef,
isValidElement,
useCallback,
useEffect,
useImperativeHandle,
useMemo,
useRef,
@@ -343,6 +343,33 @@ export const Editor = forwardRef<EditorView | undefined, EditorProps>(function E
[forceUpdateKey],
);
// For read-only mode, update content when `defaultValue` changes
useEffect(() => {
if (!readOnly || cm.current?.view == null || defaultValue == null) return;
// Replace codemirror contents
const currentDoc = cm.current.view.state.doc.toString();
if (defaultValue.startsWith(currentDoc)) {
// If we're just appending, append only the changes. This preserves
// things like scroll position.
cm.current.view.dispatch({
changes: cm.current.view.state.changes({
from: currentDoc.length,
insert: defaultValue.slice(currentDoc.length),
}),
});
} else {
// If we're replacing everything, reset the entire content
cm.current.view.dispatch({
changes: cm.current.view.state.changes({
from: 0,
to: currentDoc.length,
insert: currentDoc,
}),
});
}
}, [defaultValue, readOnly]);
// Add bg classes to actions, so they appear over the text
const decoratedActions = useMemo(() => {
const results = [];

View File

@@ -128,6 +128,9 @@ export const PlainInput = forwardRef<HTMLInputElement, PlainInputProps>(function
type={type === 'password' && !obscured ? 'text' : type}
defaultValue={defaultValue}
placeholder={placeholder}
autoComplete="off"
autoCapitalize="off"
autoCorrect="off"
onChange={(e) => handleChange(e.target.value)}
onPaste={(e) => onPaste?.(e.clipboardData.getData('Text'))}
className={inputClassName}

View File

@@ -90,7 +90,6 @@ function ActualEventStreamViewer({ response }: Props) {
) : (
<Editor
readOnly
forceUpdateKey={activeEvent.id ?? activeEvent.data}
defaultValue={tryFormatJson(activeEvent.data)}
language={language}
/>

View File

@@ -160,7 +160,6 @@ export function TextViewer({
<Editor
readOnly
className={className}
forceUpdateKey={body}
defaultValue={body}
language={language}
actions={actions}

View File

@@ -4,6 +4,7 @@ import type { AnyModel } from '@yaakapp-internal/models';
import { useSetAtom } from 'jotai/index';
import { extractKeyValue } from '../lib/keyValueStore';
import { modelsEq } from '../lib/model_util';
import {useActiveWorkspace} from "./useActiveWorkspace";
import { cookieJarsAtom } from './useCookieJars';
import { environmentsAtom } from './useEnvironments';
import { foldersAtom } from './useFolders';
@@ -25,6 +26,7 @@ export interface ModelPayload {
}
export function useSyncModelStores() {
const activeWorkspace = useActiveWorkspace();
const queryClient = useQueryClient();
const { wasUpdatedExternally } = useRequestUpdateKey(null);
@@ -48,10 +50,17 @@ export function useSyncModelStores() {
? keyValueQueryKey(model)
: null;
// TODO: Move this logic to useRequestEditor() hook
if (model.model === 'http_request' && windowLabel !== getCurrentWebviewWindow().label) {
wasUpdatedExternally(model.id);
}
// Only sync models that belong to this workspace, if a workspace ID is present
if ('workspaceId' in model && model.workspaceId !== activeWorkspace?.id) {
return;
}
// Mark these models as DESC instead of ASC
const pushToFront = (['http_response', 'grpc_connection'] as AnyModel['model'][]).includes(
model.model,
);