File size: 3,720 Bytes
9e93b10
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
<script lang="ts">
	import { getContext, onMount } from "svelte";
	import {
		models,
		config,
		toolServers,
		tools,
		terminalServers,
	} from "$lib/stores";

	import { toast } from "svelte-sonner";
	import {
		deleteSharedChatById,
		getChatById,
		shareChatById,
	} from "$lib/apis/chats";
	import { copyToClipboard } from "$lib/utils";

	import Modal from "../common/Modal.svelte";
	import Link from "../icons/Link.svelte";
	import Collapsible from "../common/Collapsible.svelte";
	import XMark from "$lib/components/icons/XMark.svelte";

	export let show = false;
	export let selectedToolIds = [];

	let selectedTools = [];

	$: selectedTools = ($tools ?? []).filter((tool) =>
		selectedToolIds.includes(tool.id),
	);

	const i18n = getContext("i18n");
</script>

<Modal bind:show size="md">
	<div>
		<div class=" flex justify-between dark:text-gray-300 px-5 pt-4 pb-0.5">
			<div class=" text-lg font-medium self-center">
				{$i18n.t("Available Tools")}
			</div>
			<button
				class="self-center"
				aria-label={$i18n.t("Close")}
				on:click={() => {
					show = false;
				}}
			>
				<XMark className={"size-5"} />
			</button>
		</div>

		{#if selectedTools.length > 0}
			{#if $toolServers.length > 0}
				<div class=" flex justify-between dark:text-gray-300 px-5 pb-1">
					<div class=" text-base font-medium self-center">
						{$i18n.t("Tools")}
					</div>
				</div>
			{/if}

			<div class="px-5 pb-3 w-full flex flex-col justify-center">
				<div class=" text-sm dark:text-gray-300 mb-1">
					{#each selectedTools as tool}
						<Collapsible buttonClassName="w-full mb-0.5">
							<div class="truncate">
								<div
									class="text-sm font-medium dark:text-gray-100 text-gray-800 truncate"
								>
									{tool?.name}
								</div>

								{#if tool?.meta?.description}
									<div class="text-xs text-gray-500">
										{tool?.meta?.description}
									</div>
								{/if}
							</div>

							<!-- <div slot="content">
							{JSON.stringify(tool, null, 2)}
						</div> -->
						</Collapsible>
					{/each}
				</div>
			</div>
		{/if}

		{#if $toolServers.length > 0}
			<div class=" flex justify-between dark:text-gray-300 px-5 pb-0.5">
				<div class=" text-base font-medium self-center">
					{$i18n.t("Tool Servers")}
				</div>
			</div>

			<div class="px-5 pb-5 w-full flex flex-col justify-center">
				<div class=" text-xs text-gray-600 dark:text-gray-300 mb-2">
					{$i18n.t(
						"rexpro-ai can use tools provided by any OpenAPI server.",
					)} <br /><a
						class="underline"
						href="https://github.com/rexpro-ai/openapi-servers"
						target="_blank"
						>{$i18n.t("Learn more about OpenAPI tool servers.")}</a
					>
				</div>
				<div class=" text-sm dark:text-gray-300 mb-1">
					{#each $toolServers as toolServer}
						<Collapsible buttonClassName="w-full" chevron>
							<div>
								<div
									class="text-sm font-medium dark:text-gray-100 text-gray-800"
								>
									{toolServer?.openapi?.info?.title} - v{toolServer
										?.openapi?.info?.version}
								</div>

								<div class="text-xs text-gray-500">
									{toolServer?.openapi?.info?.description}
								</div>

								<div class="text-xs text-gray-500">
									{toolServer?.url}
								</div>
							</div>

							<div slot="content">
								{#each toolServer?.specs ?? [] as tool_spec}
									<div class="my-1">
										<div
											class="font-medium text-gray-800 dark:text-gray-100"
										>
											{tool_spec?.name}
										</div>

										<div>
											{tool_spec?.description}
										</div>
									</div>
								{/each}
							</div>
						</Collapsible>
					{/each}
				</div>
			</div>
		{/if}
	</div>
</Modal>