PluginProbe
Yatra – Travel Booking & Tour Operator Software / 3.0.4
Yatra – Travel Booking & Tour Operator Software v3.0.4
3.0.16 3.0.15 3.0.14 3.0.14.1 3.0.14.2 3.0.12 3.0.13 3.0.11 3.0.10 3.0.9 3.0.8 3.0.7 3.0.6 3.0.5 3.0.5.1 3.0.4 3.0.3 3.0.2.9 3.0.2.7 3.0.2.8 3.0.2.6 trunk 1.0.0 2.0.0 2.0.1 All 84 releases
yatra / resources / js / hooks / useModules.ts

useModules.ts in Yatra – Travel Booking & Tour Operator Software 3.0.4, at resources/js/hooks/useModules.ts

287 lines 9.9 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 import {
2 useQuery,
3 UseQueryOptions,
4 useMutation,
5 useQueryClient,
6 } from "@tanstack/react-query";
7 import { apiClient } from "../lib/api-client";
8 import { __ } from "../lib/i18n";
9 import { useToast } from "../components/ui/toast";
10
11 export interface ModuleDefinition {
12 slug: string;
13 name: string;
14 description?: string;
15 category?: string;
16 version?: string;
17 docs_url?: string;
18 is_core?: boolean;
19 is_premium?: boolean;
20 is_available?: boolean;
21 requires_pro?: boolean;
22 purchase_url?: string;
23 video_url?: string;
24 enabled: boolean;
25 tags?: string[];
26 updated_at?: string | null;
27 settings_page?: string;
28 }
29
30 interface ModulesResponse {
31 data?: ModuleDefinition[];
32 }
33
34 const fetchModules = async (): Promise<ModuleDefinition[]> => {
35 const response: ModulesResponse = await apiClient.get("/modules");
36 if (Array.isArray(response)) {
37 return response;
38 }
39 if (Array.isArray(response?.data)) {
40 return response.data;
41 }
42 return [];
43 };
44
45 export const useModulesQuery = (
46 options?: Partial<UseQueryOptions<ModuleDefinition[], Error>>,
47 ) => {
48 return useQuery<ModuleDefinition[], Error>({
49 queryKey: ["modules"],
50 queryFn: fetchModules,
51 staleTime: 0,
52 ...options,
53 });
54 };
55
56 interface TogglePayload {
57 slug: string;
58 enabled: boolean;
59 name?: string;
60 }
61
62 const formatNamesList = (names: string[]) => {
63 if (names.length <= 2) {
64 return names.join(", ");
65 }
66 return `${names.slice(0, 2).join(", ")} ${__("and", "yatra")} ${names.length - 2} ${__("more", "yatra")}`;
67 };
68
69 export const useToggleModule = () => {
70 const queryClient = useQueryClient();
71 const { showToast } = useToast();
72
73 return useMutation({
74 mutationFn: async ({ slug, enabled }: TogglePayload) => {
75 const response: ModulesResponse = await apiClient.post(
76 `/modules/${slug}/toggle`,
77 { enabled },
78 );
79 return Array.isArray(response?.data) ? response.data : [];
80 },
81 onSuccess: (data, variables) => {
82 queryClient.setQueryData(["modules"], data);
83
84 // Update global admin variables for navigation
85 if (window.yatraAdmin) {
86 // Update module-specific flags based on the enabled modules
87 const enabledModules = data.filter((m) => m.enabled);
88
89 // Check for specific modules that affect navigation
90 window.yatraAdmin.emailAutomationEnabled = enabledModules.some(
91 (m) => m.slug === "email_automation" || m.slug === "email-automation",
92 );
93 window.yatraAdmin.tripConsentEnabled = enabledModules.some(
94 (m) => m.slug === "trip_consent" || m.slug === "trip-consent",
95 );
96 window.yatraAdmin.additionalServicesEnabled = enabledModules.some(
97 (m) =>
98 m.slug === "additional_services" ||
99 m.slug === "additional-services",
100 );
101 window.yatraAdmin.abandonedBookingRecoveryEnabled = enabledModules.some(
102 (m) =>
103 m.slug === "abandoned_booking_recovery" ||
104 m.slug === "abandoned-booking-recovery",
105 );
106 window.yatraAdmin.dynamicPricingEnabled = enabledModules.some(
107 (m) => m.slug === "dynamic_pricing" || m.slug === "dynamic-pricing",
108 );
109 window.yatraAdmin.flexiblePaymentsEnabled = enabledModules.some(
110 (m) => m.slug === "flexible_payments",
111 );
112 window.yatraAdmin.dynamicFormFieldEnabled = enabledModules.some(
113 (m) => m.slug === "dynamic_form_field",
114 );
115 window.yatraAdmin.customLandingPagesModuleEnabled = enabledModules.some(
116 (m) => m.slug === "custom_landing_pages",
117 );
118 window.yatraAdmin.showGoogleCalendarSettingsUI = enabledModules.some(
119 (m) => m.slug === "google_calendar" || m.slug === "google-calendar",
120 );
121 window.yatraAdmin.advancedDiscountEnabled = enabledModules.some(
122 (m) =>
123 m.slug === "advanced_discount" || m.slug === "advanced-discount",
124 );
125 // Add flags for Pro feature modules
126 window.yatraAdmin.showMailchimpSettingsUI = enabledModules.some(
127 (m) => m.slug === "mailchimp",
128 );
129 window.yatraAdmin.showFacebookPixelSettingsUI = enabledModules.some(
130 (m) => m.slug === "facebook_pixel",
131 );
132 window.yatraAdmin.showGoogleAnalyticsSettingsUI = enabledModules.some(
133 (m) => m.slug === "google_analytics",
134 );
135 // Note: availabilityModuleEnabled and departuresModuleEnabled removed - now FREE features
136
137 // Trigger a navigation refresh by updating a custom event
138 window.dispatchEvent(
139 new CustomEvent("yatra-modules-updated", {
140 detail: {
141 enabledModules: enabledModules,
142 updatedModule: variables,
143 },
144 }),
145 );
146
147 // Force a layout re-render by updating the URL key
148 const urlKey = (window as any).__yatraUrlKey || 0;
149 (window as any).__yatraUrlKey = urlKey + 1;
150 window.dispatchEvent(new CustomEvent("yatra-force-nav-refresh"));
151 }
152
153 const label = variables.name || variables.slug;
154 showToast(
155 variables.enabled
156 ? __("{module} enabled successfully.", "yatra").replace(
157 "{module}",
158 label,
159 )
160 : __("{module} disabled successfully.", "yatra").replace(
161 "{module}",
162 label,
163 ),
164 "success",
165 );
166 },
167 onError: (error: Error) => {
168 showToast(
169 error.message || __("Failed to update module.", "yatra"),
170 "error",
171 );
172 },
173 });
174 };
175
176 export const useBulkToggleModules = () => {
177 const queryClient = useQueryClient();
178 const { showToast } = useToast();
179
180 return useMutation({
181 mutationFn: async (items: TogglePayload[]) => {
182 const response: ModulesResponse = await apiClient.post(
183 "/modules/bulk-toggle",
184 { items },
185 );
186 return Array.isArray(response?.data) ? response.data : [];
187 },
188 onSuccess: (data, variables = [], context) => {
189 queryClient.setQueryData(["modules"], data);
190
191 // Check if there's a partial success message (some modules blocked)
192 const response = context as any;
193 if (response?.message) {
194 // Show partial success message with warning
195 showToast(response.message, "warning");
196 }
197
198 // Update global admin variables for navigation
199 if (window.yatraAdmin && data) {
200 // Update module-specific flags based on the enabled modules
201 const enabledModules = data.filter((m) => m.enabled);
202
203 // Check for specific modules that affect navigation
204 window.yatraAdmin.emailAutomationEnabled = enabledModules.some(
205 (m) => m.slug === "email_automation" || m.slug === "email-automation",
206 );
207 window.yatraAdmin.tripConsentEnabled = enabledModules.some(
208 (m) => m.slug === "trip_consent" || m.slug === "trip-consent",
209 );
210 window.yatraAdmin.additionalServicesEnabled = enabledModules.some(
211 (m) =>
212 m.slug === "additional_services" ||
213 m.slug === "additional-services",
214 );
215 window.yatraAdmin.abandonedBookingRecoveryEnabled = enabledModules.some(
216 (m) =>
217 m.slug === "abandoned_booking_recovery" ||
218 m.slug === "abandoned-booking-recovery",
219 );
220 window.yatraAdmin.dynamicPricingEnabled = enabledModules.some(
221 (m) => m.slug === "dynamic_pricing" || m.slug === "dynamic-pricing",
222 );
223 window.yatraAdmin.flexiblePaymentsEnabled = enabledModules.some(
224 (m) => m.slug === "flexible_payments",
225 );
226 window.yatraAdmin.dynamicFormFieldEnabled = enabledModules.some(
227 (m) => m.slug === "dynamic_form_field",
228 );
229 window.yatraAdmin.customLandingPagesModuleEnabled = enabledModules.some(
230 (m) => m.slug === "custom_landing_pages",
231 );
232 window.yatraAdmin.showGoogleCalendarSettingsUI = enabledModules.some(
233 (m) => m.slug === "google_calendar" || m.slug === "google-calendar",
234 );
235 window.yatraAdmin.advancedDiscountEnabled = enabledModules.some(
236 (m) =>
237 m.slug === "advanced_discount" || m.slug === "advanced-discount",
238 );
239 // Add flags for Pro feature modules
240 window.yatraAdmin.showMailchimpSettingsUI = enabledModules.some(
241 (m) => m.slug === "mailchimp",
242 );
243 window.yatraAdmin.showFacebookPixelSettingsUI = enabledModules.some(
244 (m) => m.slug === "facebook_pixel",
245 );
246 window.yatraAdmin.showGoogleAnalyticsSettingsUI = enabledModules.some(
247 (m) => m.slug === "google_analytics",
248 );
249 // Note: availabilityModuleEnabled and departuresModuleEnabled removed - now FREE features
250
251 // Trigger a navigation refresh by updating a custom event
252 window.dispatchEvent(
253 new CustomEvent("yatra-modules-updated", {
254 detail: {
255 enabledModules: enabledModules,
256 updatedModules: variables || [],
257 },
258 }),
259 );
260
261 // Force a layout re-render by updating the URL key
262 const urlKey = (window as any).__yatraUrlKey || 0;
263 (window as any).__yatraUrlKey = urlKey + 1;
264 window.dispatchEvent(new CustomEvent("yatra-force-nav-refresh"));
265 }
266
267 // Only show success message if there wasn't a partial success message
268 if (!response?.message && variables.length > 0) {
269 const names = variables.map((item) => item.name || item.slug);
270 const summary = formatNamesList(names);
271 const message = variables[0].enabled
272 ? __("Enabled: {modules}", "yatra").replace("{modules}", summary)
273 : __("Disabled: {modules}", "yatra").replace("{modules}", summary);
274 showToast(message, "success");
275 } else if (!response?.message) {
276 showToast(__("Modules updated successfully.", "yatra"), "success");
277 }
278 },
279 onError: (error: Error) => {
280 showToast(
281 error.message || __("Failed to update modules.", "yatra"),
282 "error",
283 );
284 },
285 });
286 };
287