LlamaFinetuneGGUF commited on
Commit
a2acc77
·
1 Parent(s): 42ebd3d

fix: clean up

Browse files

fix: typecheck / lint

.github/{actions/setup-and-build → workflows}/commit.yaml RENAMED
@@ -21,12 +21,12 @@ jobs:
21
 
22
  - name: Update commit file
23
  run: |
24
- echo "{ \"commit\": \"$COMMIT_HASH\" }" > commit.json
25
 
26
  - name: Commit and push the update
27
  run: |
28
  git config --global user.name "github-actions[bot]"
29
  git config --global user.email "github-actions[bot]@users.noreply.github.com"
30
- git add commit.json
31
  git commit -m "chore: update commit hash to $COMMIT_HASH"
32
  git push
 
21
 
22
  - name: Update commit file
23
  run: |
24
+ echo "{ \"commit\": \"$COMMIT_HASH\" }" > app/commit.json
25
 
26
  - name: Commit and push the update
27
  run: |
28
  git config --global user.name "github-actions[bot]"
29
  git config --global user.email "github-actions[bot]@users.noreply.github.com"
30
+ git add app/commit.json
31
  git commit -m "chore: update commit hash to $COMMIT_HASH"
32
  git push
app/commit.json ADDED
@@ -0,0 +1 @@
 
 
1
+ { "commit": "228cf1f34fd64b6960460f84c9db47bd7ef03150" }
app/components/chat/BaseChat.tsx CHANGED
@@ -89,6 +89,7 @@ export const BaseChat = React.forwardRef<HTMLDivElement, BaseChatProps>(
89
  const TEXTAREA_MAX_HEIGHT = chatStarted ? 400 : 200;
90
  const [apiKeys, setApiKeys] = useState<Record<string, string>>(() => {
91
  const savedKeys = Cookies.get('apiKeys');
 
92
  if (savedKeys) {
93
  try {
94
  return JSON.parse(savedKeys);
@@ -97,6 +98,7 @@ export const BaseChat = React.forwardRef<HTMLDivElement, BaseChatProps>(
97
  return {};
98
  }
99
  }
 
100
  return {};
101
  });
102
  const [modelList, setModelList] = useState(MODEL_LIST);
@@ -108,15 +110,17 @@ export const BaseChat = React.forwardRef<HTMLDivElement, BaseChatProps>(
108
  // Load enabled providers from cookies
109
  const [enabledProviders, setEnabledProviders] = useState(() => {
110
  const savedProviders = Cookies.get('providers');
 
111
  if (savedProviders) {
112
  try {
113
  const parsedProviders = JSON.parse(savedProviders);
114
- return PROVIDER_LIST.filter(p => parsedProviders[p.name]);
115
  } catch (error) {
116
  console.error('Failed to parse providers from cookies:', error);
117
  return PROVIDER_LIST;
118
  }
119
  }
 
120
  return PROVIDER_LIST;
121
  });
122
 
@@ -124,10 +128,11 @@ export const BaseChat = React.forwardRef<HTMLDivElement, BaseChatProps>(
124
  useEffect(() => {
125
  const updateProvidersFromCookies = () => {
126
  const savedProviders = Cookies.get('providers');
 
127
  if (savedProviders) {
128
  try {
129
  const parsedProviders = JSON.parse(savedProviders);
130
- setEnabledProviders(PROVIDER_LIST.filter(p => parsedProviders[p.name]));
131
  } catch (error) {
132
  console.error('Failed to parse providers from cookies:', error);
133
  }
@@ -135,7 +140,9 @@ export const BaseChat = React.forwardRef<HTMLDivElement, BaseChatProps>(
135
  };
136
 
137
  updateProvidersFromCookies();
 
138
  const interval = setInterval(updateProvidersFromCookies, 1000);
 
139
  return () => clearInterval(interval);
140
  }, [PROVIDER_LIST]);
141
 
@@ -228,23 +235,6 @@ export const BaseChat = React.forwardRef<HTMLDivElement, BaseChatProps>(
228
  }
229
  };
230
 
231
- const updateApiKey = (provider: string, key: string) => {
232
- try {
233
- const updatedApiKeys = { ...apiKeys, [provider]: key };
234
- setApiKeys(updatedApiKeys);
235
-
236
- // Save updated API keys to cookies with 30 day expiry and secure settings
237
- Cookies.set('apiKeys', JSON.stringify(updatedApiKeys), {
238
- expires: 30, // 30 days
239
- secure: true, // Only send over HTTPS
240
- sameSite: 'strict', // Protect against CSRF
241
- path: '/', // Accessible across the site
242
- });
243
- } catch (error) {
244
- console.error('Error saving API keys to cookies:', error);
245
- }
246
- };
247
-
248
  const handleFileUpload = () => {
249
  const input = document.createElement('input');
250
  input.type = 'file';
 
89
  const TEXTAREA_MAX_HEIGHT = chatStarted ? 400 : 200;
90
  const [apiKeys, setApiKeys] = useState<Record<string, string>>(() => {
91
  const savedKeys = Cookies.get('apiKeys');
92
+
93
  if (savedKeys) {
94
  try {
95
  return JSON.parse(savedKeys);
 
98
  return {};
99
  }
100
  }
101
+
102
  return {};
103
  });
104
  const [modelList, setModelList] = useState(MODEL_LIST);
 
110
  // Load enabled providers from cookies
111
  const [enabledProviders, setEnabledProviders] = useState(() => {
112
  const savedProviders = Cookies.get('providers');
113
+
114
  if (savedProviders) {
115
  try {
116
  const parsedProviders = JSON.parse(savedProviders);
117
+ return PROVIDER_LIST.filter((p) => parsedProviders[p.name]);
118
  } catch (error) {
119
  console.error('Failed to parse providers from cookies:', error);
120
  return PROVIDER_LIST;
121
  }
122
  }
123
+
124
  return PROVIDER_LIST;
125
  });
126
 
 
128
  useEffect(() => {
129
  const updateProvidersFromCookies = () => {
130
  const savedProviders = Cookies.get('providers');
131
+
132
  if (savedProviders) {
133
  try {
134
  const parsedProviders = JSON.parse(savedProviders);
135
+ setEnabledProviders(PROVIDER_LIST.filter((p) => parsedProviders[p.name]));
136
  } catch (error) {
137
  console.error('Failed to parse providers from cookies:', error);
138
  }
 
140
  };
141
 
142
  updateProvidersFromCookies();
143
+
144
  const interval = setInterval(updateProvidersFromCookies, 1000);
145
+
146
  return () => clearInterval(interval);
147
  }, [PROVIDER_LIST]);
148
 
 
235
  }
236
  };
237
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
238
  const handleFileUpload = () => {
239
  const input = document.createElement('input');
240
  input.type = 'file';
app/components/chat/ModelSelector.tsx CHANGED
@@ -24,15 +24,17 @@ export const ModelSelector = ({
24
  // Load enabled providers from cookies
25
  const [enabledProviders, setEnabledProviders] = useState(() => {
26
  const savedProviders = Cookies.get('providers');
 
27
  if (savedProviders) {
28
  try {
29
  const parsedProviders = JSON.parse(savedProviders);
30
- return providerList.filter(p => parsedProviders[p.name]);
31
  } catch (error) {
32
  console.error('Failed to parse providers from cookies:', error);
33
  return providerList;
34
  }
35
  }
 
36
  return providerList;
37
  });
38
 
@@ -41,19 +43,21 @@ export const ModelSelector = ({
41
  // Function to update providers from cookies
42
  const updateProvidersFromCookies = () => {
43
  const savedProviders = Cookies.get('providers');
 
44
  if (savedProviders) {
45
  try {
46
  const parsedProviders = JSON.parse(savedProviders);
47
- const newEnabledProviders = providerList.filter(p => parsedProviders[p.name]);
48
  setEnabledProviders(newEnabledProviders);
49
 
50
  // If current provider is disabled, switch to first enabled provider
51
  if (provider && !parsedProviders[provider.name] && newEnabledProviders.length > 0) {
52
  const firstEnabledProvider = newEnabledProviders[0];
53
  setProvider?.(firstEnabledProvider);
54
-
55
  // Also update the model to the first available one for the new provider
56
- const firstModel = modelList.find(m => m.provider === firstEnabledProvider.name);
 
57
  if (firstModel) {
58
  setModel?.(firstModel.name);
59
  }
@@ -77,7 +81,8 @@ export const ModelSelector = ({
77
  return (
78
  <div className="mb-2 p-4 rounded-lg border border-bolt-elements-borderColor bg-bolt-elements-prompt-background text-bolt-elements-textPrimary">
79
  <p className="text-center">
80
- No providers are currently enabled. Please enable at least one provider in the settings to start using the chat.
 
81
  </p>
82
  </div>
83
  );
 
24
  // Load enabled providers from cookies
25
  const [enabledProviders, setEnabledProviders] = useState(() => {
26
  const savedProviders = Cookies.get('providers');
27
+
28
  if (savedProviders) {
29
  try {
30
  const parsedProviders = JSON.parse(savedProviders);
31
+ return providerList.filter((p) => parsedProviders[p.name]);
32
  } catch (error) {
33
  console.error('Failed to parse providers from cookies:', error);
34
  return providerList;
35
  }
36
  }
37
+
38
  return providerList;
39
  });
40
 
 
43
  // Function to update providers from cookies
44
  const updateProvidersFromCookies = () => {
45
  const savedProviders = Cookies.get('providers');
46
+
47
  if (savedProviders) {
48
  try {
49
  const parsedProviders = JSON.parse(savedProviders);
50
+ const newEnabledProviders = providerList.filter((p) => parsedProviders[p.name]);
51
  setEnabledProviders(newEnabledProviders);
52
 
53
  // If current provider is disabled, switch to first enabled provider
54
  if (provider && !parsedProviders[provider.name] && newEnabledProviders.length > 0) {
55
  const firstEnabledProvider = newEnabledProviders[0];
56
  setProvider?.(firstEnabledProvider);
57
+
58
  // Also update the model to the first available one for the new provider
59
+ const firstModel = modelList.find((m) => m.provider === firstEnabledProvider.name);
60
+
61
  if (firstModel) {
62
  setModel?.(firstModel.name);
63
  }
 
81
  return (
82
  <div className="mb-2 p-4 rounded-lg border border-bolt-elements-borderColor bg-bolt-elements-prompt-background text-bolt-elements-textPrimary">
83
  <p className="text-center">
84
+ No providers are currently enabled. Please enable at least one provider in the settings to start using the
85
+ chat.
86
  </p>
87
  </div>
88
  );
app/components/ui/Settings.tsx CHANGED
@@ -1,14 +1,14 @@
1
  import * as RadixDialog from '@radix-ui/react-dialog';
2
  import { motion } from 'framer-motion';
3
- import { useState, useEffect }from 'react';
4
  import { classNames } from '~/utils/classNames';
5
- import { Dialog, DialogTitle, dialogVariants, dialogBackdropVariants } from './Dialog';
6
  import { IconButton } from './IconButton';
7
  import { providersList } from '~/lib/stores/settings';
8
  import { db, getAll, deleteById } from '~/lib/persistence';
9
  import { toast } from 'react-toastify';
10
  import { useNavigate } from '@remix-run/react';
11
- import commit from '../../../commit.json';
12
  import Cookies from 'js-cookie';
13
 
14
  interface SettingsProps {
@@ -31,6 +31,7 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
31
  // Load base URLs from cookies
32
  const [baseUrls, setBaseUrls] = useState(() => {
33
  const savedUrls = Cookies.get('providerBaseUrls');
 
34
  if (savedUrls) {
35
  try {
36
  return JSON.parse(savedUrls);
@@ -43,6 +44,7 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
43
  };
44
  }
45
  }
 
46
  return {
47
  Ollama: 'http://localhost:11434',
48
  LMStudio: 'http://localhost:1234',
@@ -51,9 +53,10 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
51
  });
52
 
53
  const handleBaseUrlChange = (provider: string, url: string) => {
54
- setBaseUrls(prev => {
55
  const newUrls = { ...prev, [provider]: url };
56
  Cookies.set('providerBaseUrls', JSON.stringify(newUrls));
 
57
  return newUrls;
58
  });
59
  };
@@ -62,46 +65,52 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
62
  { id: 'chat-history', label: 'Chat History', icon: 'i-ph:book' },
63
  { id: 'providers', label: 'Providers', icon: 'i-ph:key' },
64
  { id: 'features', label: 'Features', icon: 'i-ph:star' },
65
- ...(isDebugEnabled ? [{ id: 'debug', label: 'Debug Tab', icon: 'i-ph:bug' }] : []),
66
  ];
67
 
68
  // Load providers from cookies on mount
69
  const [providers, setProviders] = useState(() => {
70
  const savedProviders = Cookies.get('providers');
 
71
  if (savedProviders) {
72
  try {
73
  const parsedProviders = JSON.parse(savedProviders);
 
74
  // Merge saved enabled states with the base provider list
75
- return providersList.map(provider => ({
76
  ...provider,
77
- isEnabled: parsedProviders[provider.name] || false
78
  }));
79
  } catch (error) {
80
  console.error('Failed to parse providers from cookies:', error);
81
  }
82
  }
 
83
  return providersList;
84
  });
85
 
86
  const handleToggleProvider = (providerName: string) => {
87
  setProviders((prevProviders) => {
88
  const newProviders = prevProviders.map((provider) =>
89
- provider.name === providerName ? { ...provider, isEnabled: !provider.isEnabled } : provider
90
  );
91
-
92
  // Save to cookies
93
- const enabledStates = newProviders.reduce((acc, provider) => ({
94
- ...acc,
95
- [provider.name]: provider.isEnabled
96
- }), {});
 
 
 
97
  Cookies.set('providers', JSON.stringify(enabledStates));
98
-
99
  return newProviders;
100
  });
101
  };
102
 
103
  const filteredProviders = providers
104
- .filter(provider => provider.name.toLowerCase().includes(searchTerm.toLowerCase()))
105
  .sort((a, b) => a.name.localeCompare(b.name));
106
 
107
  const handleCopyToClipboard = () => {
@@ -141,11 +150,12 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
141
 
142
  try {
143
  setIsDeleting(true);
 
144
  const allChats = await getAll(db);
145
-
146
  // Delete all chats one by one
147
- await Promise.all(allChats.map(chat => deleteById(db!, chat.id)));
148
-
149
  toast.success('All chats deleted successfully');
150
  navigate('/', { replace: true });
151
  } catch (error) {
@@ -168,7 +178,7 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
168
  chats: allChats,
169
  exportDate: new Date().toISOString(),
170
  };
171
-
172
  downloadAsJson(exportData, `all-chats-${new Date().toISOString()}.json`);
173
  toast.success('Chats exported successfully');
174
  } catch (error) {
@@ -207,9 +217,7 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
207
  onClick={() => setActiveTab(tab.id)}
208
  className={classNames(
209
  'w-full flex items-center gap-2 px-4 py-3 rounded-lg text-left text-sm transition-all mb-2',
210
- activeTab === tab.id
211
- ? 'bg-blue-600 text-white'
212
- : 'bg-gray-600 text-gray-200 hover:bg-blue-500'
213
  )}
214
  >
215
  <div className={tab.icon} />
@@ -239,7 +247,7 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
239
  <div className="flex-1 flex flex-col p-8">
240
  <DialogTitle className="flex-shrink-0 text-lg font-semibold text-white">Settings</DialogTitle>
241
  <div className="flex-1 overflow-y-auto">
242
- {activeTab === 'chat-history' && (
243
  <div className="p-4">
244
  <h3 className="text-lg font-medium text-white mb-4">Chat History</h3>
245
  <button
@@ -248,7 +256,7 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
248
  >
249
  Export All Chats
250
  </button>
251
-
252
  <div className="bg-red-500 text-white rounded-lg p-4 mb-4">
253
  <h4 className="font-semibold">Danger Area</h4>
254
  <p className="mb-2">This action cannot be undone!</p>
@@ -256,8 +264,8 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
256
  onClick={handleDeleteAllChats}
257
  disabled={isDeleting}
258
  className={classNames(
259
- "bg-red-700 text-white rounded-lg px-4 py-2 transition-colors duration-200",
260
- isDeleting ? "opacity-50 cursor-not-allowed" : "hover:bg-red-800"
261
  )}
262
  >
263
  {isDeleting ? 'Deleting...' : 'Delete All Chats'}
@@ -297,7 +305,7 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
297
  ></div>
298
  </label>
299
  </div>
300
-
301
  {/* Base URL input for configurable providers */}
302
  {URL_CONFIGURABLE_PROVIDERS.includes(provider.name) && provider.isEnabled && (
303
  <div className="mt-2">
@@ -334,9 +342,7 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
334
  ></div>
335
  </label>
336
  </div>
337
- <div className="feature-row">
338
- {/* Your feature content here */}
339
- </div>
340
  </div>
341
  )}
342
  {activeTab === 'debug' && isDebugEnabled && (
@@ -348,7 +354,7 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
348
  >
349
  Copy to Clipboard
350
  </button>
351
-
352
  <h4 className="text-md font-medium text-white">System Information</h4>
353
  <p className="text-white">OS: {navigator.platform}</p>
354
  <p className="text-white">Browser: {navigator.userAgent}</p>
@@ -358,7 +364,9 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
358
  {providers
359
  .filter((provider) => provider.isEnabled)
360
  .map((provider) => (
361
- <li key={provider.name} className="text-white">{provider.name}</li>
 
 
362
  ))}
363
  </ul>
364
 
@@ -384,4 +392,4 @@ export const Settings = ({ open, onClose }: SettingsProps) => {
384
  </RadixDialog.Portal>
385
  </RadixDialog.Root>
386
  );
387
- };
 
1
  import * as RadixDialog from '@radix-ui/react-dialog';
2
  import { motion } from 'framer-motion';
3
+ import { useState } from 'react';
4
  import { classNames } from '~/utils/classNames';
5
+ import { DialogTitle, dialogVariants, dialogBackdropVariants } from './Dialog';
6
  import { IconButton } from './IconButton';
7
  import { providersList } from '~/lib/stores/settings';
8
  import { db, getAll, deleteById } from '~/lib/persistence';
9
  import { toast } from 'react-toastify';
10
  import { useNavigate } from '@remix-run/react';
11
+ import commit from '~/commit.json';
12
  import Cookies from 'js-cookie';
13
 
14
  interface SettingsProps {
 
31
  // Load base URLs from cookies
32
  const [baseUrls, setBaseUrls] = useState(() => {
33
  const savedUrls = Cookies.get('providerBaseUrls');
34
+
35
  if (savedUrls) {
36
  try {
37
  return JSON.parse(savedUrls);
 
44
  };
45
  }
46
  }
47
+
48
  return {
49
  Ollama: 'http://localhost:11434',
50
  LMStudio: 'http://localhost:1234',
 
53
  });
54
 
55
  const handleBaseUrlChange = (provider: string, url: string) => {
56
+ setBaseUrls((prev: Record<string, string>) => {
57
  const newUrls = { ...prev, [provider]: url };
58
  Cookies.set('providerBaseUrls', JSON.stringify(newUrls));
59
+
60
  return newUrls;
61
  });
62
  };
 
65
  { id: 'chat-history', label: 'Chat History', icon: 'i-ph:book' },
66
  { id: 'providers', label: 'Providers', icon: 'i-ph:key' },
67
  { id: 'features', label: 'Features', icon: 'i-ph:star' },
68
+ ...(isDebugEnabled ? [{ id: 'debug' as TabType, label: 'Debug Tab', icon: 'i-ph:bug' }] : []),
69
  ];
70
 
71
  // Load providers from cookies on mount
72
  const [providers, setProviders] = useState(() => {
73
  const savedProviders = Cookies.get('providers');
74
+
75
  if (savedProviders) {
76
  try {
77
  const parsedProviders = JSON.parse(savedProviders);
78
+
79
  // Merge saved enabled states with the base provider list
80
+ return providersList.map((provider) => ({
81
  ...provider,
82
+ isEnabled: parsedProviders[provider.name] || false,
83
  }));
84
  } catch (error) {
85
  console.error('Failed to parse providers from cookies:', error);
86
  }
87
  }
88
+
89
  return providersList;
90
  });
91
 
92
  const handleToggleProvider = (providerName: string) => {
93
  setProviders((prevProviders) => {
94
  const newProviders = prevProviders.map((provider) =>
95
+ provider.name === providerName ? { ...provider, isEnabled: !provider.isEnabled } : provider,
96
  );
97
+
98
  // Save to cookies
99
+ const enabledStates = newProviders.reduce(
100
+ (acc, provider) => ({
101
+ ...acc,
102
+ [provider.name]: provider.isEnabled,
103
+ }),
104
+ {},
105
+ );
106
  Cookies.set('providers', JSON.stringify(enabledStates));
107
+
108
  return newProviders;
109
  });
110
  };
111
 
112
  const filteredProviders = providers
113
+ .filter((provider) => provider.name.toLowerCase().includes(searchTerm.toLowerCase()))
114
  .sort((a, b) => a.name.localeCompare(b.name));
115
 
116
  const handleCopyToClipboard = () => {
 
150
 
151
  try {
152
  setIsDeleting(true);
153
+
154
  const allChats = await getAll(db);
155
+
156
  // Delete all chats one by one
157
+ await Promise.all(allChats.map((chat) => deleteById(db!, chat.id)));
158
+
159
  toast.success('All chats deleted successfully');
160
  navigate('/', { replace: true });
161
  } catch (error) {
 
178
  chats: allChats,
179
  exportDate: new Date().toISOString(),
180
  };
181
+
182
  downloadAsJson(exportData, `all-chats-${new Date().toISOString()}.json`);
183
  toast.success('Chats exported successfully');
184
  } catch (error) {
 
217
  onClick={() => setActiveTab(tab.id)}
218
  className={classNames(
219
  'w-full flex items-center gap-2 px-4 py-3 rounded-lg text-left text-sm transition-all mb-2',
220
+ activeTab === tab.id ? 'bg-blue-600 text-white' : 'bg-gray-600 text-gray-200 hover:bg-blue-500',
 
 
221
  )}
222
  >
223
  <div className={tab.icon} />
 
247
  <div className="flex-1 flex flex-col p-8">
248
  <DialogTitle className="flex-shrink-0 text-lg font-semibold text-white">Settings</DialogTitle>
249
  <div className="flex-1 overflow-y-auto">
250
+ {activeTab === 'chat-history' && (
251
  <div className="p-4">
252
  <h3 className="text-lg font-medium text-white mb-4">Chat History</h3>
253
  <button
 
256
  >
257
  Export All Chats
258
  </button>
259
+
260
  <div className="bg-red-500 text-white rounded-lg p-4 mb-4">
261
  <h4 className="font-semibold">Danger Area</h4>
262
  <p className="mb-2">This action cannot be undone!</p>
 
264
  onClick={handleDeleteAllChats}
265
  disabled={isDeleting}
266
  className={classNames(
267
+ 'bg-red-700 text-white rounded-lg px-4 py-2 transition-colors duration-200',
268
+ isDeleting ? 'opacity-50 cursor-not-allowed' : 'hover:bg-red-800',
269
  )}
270
  >
271
  {isDeleting ? 'Deleting...' : 'Delete All Chats'}
 
305
  ></div>
306
  </label>
307
  </div>
308
+
309
  {/* Base URL input for configurable providers */}
310
  {URL_CONFIGURABLE_PROVIDERS.includes(provider.name) && provider.isEnabled && (
311
  <div className="mt-2">
 
342
  ></div>
343
  </label>
344
  </div>
345
+ <div className="feature-row">{/* Your feature content here */}</div>
 
 
346
  </div>
347
  )}
348
  {activeTab === 'debug' && isDebugEnabled && (
 
354
  >
355
  Copy to Clipboard
356
  </button>
357
+
358
  <h4 className="text-md font-medium text-white">System Information</h4>
359
  <p className="text-white">OS: {navigator.platform}</p>
360
  <p className="text-white">Browser: {navigator.userAgent}</p>
 
364
  {providers
365
  .filter((provider) => provider.isEnabled)
366
  .map((provider) => (
367
+ <li key={provider.name} className="text-white">
368
+ {provider.name}
369
+ </li>
370
  ))}
371
  </ul>
372
 
 
392
  </RadixDialog.Portal>
393
  </RadixDialog.Root>
394
  );
395
+ };
app/components/ui/SettingsButton.tsx CHANGED
@@ -15,4 +15,4 @@ export const SettingsButton = memo(({ onClick }: SettingsButtonProps) => {
15
  className="text-[#666] hover:text-bolt-elements-textPrimary hover:bg-bolt-elements-item-backgroundActive/10 transition-colors"
16
  />
17
  );
18
- });
 
15
  className="text-[#666] hover:text-bolt-elements-textPrimary hover:bg-bolt-elements-item-backgroundActive/10 transition-colors"
16
  />
17
  );
18
+ });
app/components/ui/SettingsSlider.tsx CHANGED
@@ -26,24 +26,24 @@ export const SettingsSlider = memo(<T,>({ selected, options, setSelected }: Sett
26
  <motion.div
27
  className={classNames(
28
  'absolute h-full bg-green-500 transition-all duration-300 rounded-lg',
29
- isLeftSelected ? 'left-0 w-1/2' : 'right-0 w-1/2'
30
  )}
31
  initial={false}
32
  animate={{
33
  x: isLeftSelected ? 0 : '100%',
34
- opacity: 0.2
35
  }}
36
  transition={{
37
  type: 'spring',
38
  stiffness: 300,
39
- damping: 30
40
  }}
41
  />
42
  <button
43
  onClick={() => setSelected?.(options.left.value)}
44
  className={classNames(
45
  'relative z-10 flex-1 p-2 rounded-lg text-sm transition-colors duration-200',
46
- isLeftSelected ? 'text-white' : 'text-bolt-elements-textSecondary hover:text-bolt-elements-textPrimary'
47
  )}
48
  >
49
  {options.left.text}
@@ -52,11 +52,11 @@ export const SettingsSlider = memo(<T,>({ selected, options, setSelected }: Sett
52
  onClick={() => setSelected?.(options.right.value)}
53
  className={classNames(
54
  'relative z-10 flex-1 p-2 rounded-lg text-sm transition-colors duration-200',
55
- !isLeftSelected ? 'text-white' : 'text-bolt-elements-textSecondary hover:text-bolt-elements-textPrimary'
56
  )}
57
  >
58
  {options.right.text}
59
  </button>
60
  </div>
61
  );
62
- });
 
26
  <motion.div
27
  className={classNames(
28
  'absolute h-full bg-green-500 transition-all duration-300 rounded-lg',
29
+ isLeftSelected ? 'left-0 w-1/2' : 'right-0 w-1/2',
30
  )}
31
  initial={false}
32
  animate={{
33
  x: isLeftSelected ? 0 : '100%',
34
+ opacity: 0.2,
35
  }}
36
  transition={{
37
  type: 'spring',
38
  stiffness: 300,
39
+ damping: 30,
40
  }}
41
  />
42
  <button
43
  onClick={() => setSelected?.(options.left.value)}
44
  className={classNames(
45
  'relative z-10 flex-1 p-2 rounded-lg text-sm transition-colors duration-200',
46
+ isLeftSelected ? 'text-white' : 'text-bolt-elements-textSecondary hover:text-bolt-elements-textPrimary',
47
  )}
48
  >
49
  {options.left.text}
 
52
  onClick={() => setSelected?.(options.right.value)}
53
  className={classNames(
54
  'relative z-10 flex-1 p-2 rounded-lg text-sm transition-colors duration-200',
55
+ !isLeftSelected ? 'text-white' : 'text-bolt-elements-textSecondary hover:text-bolt-elements-textPrimary',
56
  )}
57
  >
58
  {options.right.text}
59
  </button>
60
  </div>
61
  );
62
+ });
commit.json DELETED
@@ -1 +0,0 @@
1
- { "commit": "228cf1f34fd64b6960460f84c9db47bd7ef03150" }