@zauru-sdk/components 2.0.220 → 2.0.222

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -3,6 +3,22 @@
3
3
  All notable changes to this project will be documented in this file.
4
4
  See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
5
5
 
6
+ ## [2.0.222](https://github.com/intuitiva/zauru-typescript-sdk/compare/v2.0.221...v2.0.222) (2025-06-04)
7
+
8
+ **Note:** Version bump only for package @zauru-sdk/components
9
+
10
+
11
+
12
+
13
+
14
+ ## [2.0.221](https://github.com/intuitiva/zauru-typescript-sdk/compare/v2.0.220...v2.0.221) (2025-06-02)
15
+
16
+ **Note:** Version bump only for package @zauru-sdk/components
17
+
18
+
19
+
20
+
21
+
6
22
  ## [2.0.220](https://github.com/intuitiva/zauru-typescript-sdk/compare/v2.0.219...v2.0.220) (2025-05-30)
7
23
 
8
24
  **Note:** Version bump only for package @zauru-sdk/components
@@ -1,2 +1,2 @@
1
1
  import type { NavBarProps } from "./NavBar.types.js";
2
- export declare const NavBar: ({ title, loggedIn, items, selectedColor, version, }: NavBarProps) => import("react/jsx-runtime").JSX.Element;
2
+ export declare const NavBar: ({ title, loggedIn, items, selectedColor, version, reloadCatalogsOption, }: NavBarProps) => import("react/jsx-runtime").JSX.Element;
@@ -7,6 +7,7 @@ export type NavBarItem = {
7
7
  color?: ColorInterface;
8
8
  childrens?: Exclude<NavBarItem, "loggedIn">[];
9
9
  reduxNotificationBadge?: (state: any) => string | number;
10
+ hide?: boolean;
10
11
  };
11
12
  export type NavBarProps = {
12
13
  title: string;
@@ -15,6 +16,7 @@ export type NavBarProps = {
15
16
  selectedColor: "pink" | "purple" | "slate" | "green" | "yellow" | "red" | "sky";
16
17
  LinkComponent?: any;
17
18
  version?: string;
19
+ reloadCatalogsOption?: boolean;
18
20
  };
19
21
  export type NavBarStateProps = {
20
22
  NavBarOpen: boolean;
@@ -1,5 +1,5 @@
1
1
  import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
2
- import React, { useState, useEffect } from "react";
2
+ import React, { useState, useEffect, useMemo } from "react";
3
3
  import { DropDownArrowSvgIcon, LogoutDropDownSvgIcon, MenuAlt4Svg, OpcionButtonSvgIcon, } from "@zauru-sdk/icons";
4
4
  import { COLORS } from "./NavBar.utils.js";
5
5
  import { Link, useNavigate, useLocation } from "@remix-run/react";
@@ -30,7 +30,7 @@ const NavItem = ({ name, link, icon, selectedColor, childrens = [], reduxNotific
30
30
  // De lo contrario, usamos el color normal (bg700)
31
31
  className: `${isActive ? specialColor.bg900 : specialColor.bg700} container text-white w-full sm:w-auto h-10 text-sm py-1 uppercase shadow hover:shadow-lg outline-none rounded-full focus:outline-none my-auto sm:my-0 sm:mr-1 mb-1 ease-linear transition-all duration-150`, children: _jsxs(Link, { className: "px-3 flex items-center text-xs leading-snug text-white uppercase hover:opacity-75 relative", to: link, children: [_jsxs("div", { className: "mx-auto pt-2", children: [icon, _jsx("span", { children: name })] }), notificationBadge !== undefined && (_jsx("span", { className: "absolute -top-2 -right-2 bg-red-500 text-white text-xs font-bold rounded-full flex items-center justify-center w-5 h-5", children: notificationBadge }))] }) }) }));
32
32
  };
33
- export const NavBar = ({ title, loggedIn, items, selectedColor, version, }) => {
33
+ export const NavBar = ({ title, loggedIn, items, selectedColor, version, reloadCatalogsOption, }) => {
34
34
  const color = COLORS[selectedColor];
35
35
  const [NavBarOpen, setNavBarOpen] = useState(false);
36
36
  const [currentVersion, setCurrentVersion] = useState(version);
@@ -48,8 +48,14 @@ export const NavBar = ({ title, loggedIn, items, selectedColor, version, }) => {
48
48
  return { ...x };
49
49
  }) }, index));
50
50
  }) }));
51
- const options = (_jsxs(_Fragment, { children: [_jsx("ul", { className: "w-full lg:flex lg:items-center", children: renderNavItems(items.filter((item) => item.loggedIn === loggedIn)) }), _jsx("ul", { className: "sm:flex sm:flex-col lg:flex-row ml-auto", children: loggedIn && (_jsx(OptionsDropDownButton, { color: color, options: [
52
- _jsx(Link, { className: `block px-4 py-3 text-sm text-gray-600 capitalize transition-colors duration-200 transform dark:text-gray-300 hover:bg-red-100 dark:hover:bg-gray-700 dark:hover:text-white`, to: "/logout", children: _jsxs("div", { className: "mx-auto pt-2", children: [_jsx(LogoutDropDownSvgIcon, {}), _jsx("span", { children: "Cerrar sesi\u00F3n" })] }) }, "cerrar-sesion"),
53
- ] })) })] }));
51
+ const hiddenItemsChange = useMemo(() => items.filter((item) => item.hide === true), [items]);
52
+ const options = useMemo(() => {
53
+ return (_jsxs(_Fragment, { children: [_jsx("ul", { className: "w-full lg:flex lg:items-center", children: renderNavItems(items
54
+ .filter((item) => item.loggedIn === loggedIn)
55
+ .filter((item) => item.hide !== true)) }), _jsx("ul", { className: "sm:flex sm:flex-col lg:flex-row ml-auto", children: loggedIn && (_jsx(OptionsDropDownButton, { color: color, options: [
56
+ reloadCatalogsOption && (_jsx(Link, { className: `block px-4 py-3 text-sm text-gray-600 capitalize transition-colors duration-200 transform dark:text-gray-300 hover:bg-red-100 dark:hover:bg-gray-700 dark:hover:text-white`, to: "/reload-catalogs", children: _jsxs("div", { className: "mx-auto pt-2", children: [_jsxs("svg", { className: `h-5 w-5 mr-1`, width: "24", height: "24", fill: "none", stroke: "currentColor", strokeWidth: "1.5", viewBox: "0 0 24 24", strokeLinecap: "round", strokeLinejoin: "round", xmlns: "http://www.w3.org/2000/svg", children: [_jsx("path", { d: "M20.5 8c-1.392-3.179-4.823-5-8.522-5C7.299 3 3.453 6.552 3 11.1" }), _jsx("path", { d: "M16.489 8.4h3.97A.54.54 0 0 0 21 7.86V3.9M3.5 16c1.392 3.179 4.823 5 8.522 5 4.679 0 8.525-3.552 8.978-8.1" }), _jsx("path", { d: "M7.511 15.6h-3.97a.54.54 0 0 0-.541.54v3.96" })] }), _jsx("span", { children: "Recargar cat\u00E1logos" })] }) }, "recargar-catalogos")),
57
+ _jsx(Link, { className: `block px-4 py-3 text-sm text-gray-600 capitalize transition-colors duration-200 transform dark:text-gray-300 hover:bg-red-100 dark:hover:bg-gray-700 dark:hover:text-white`, to: "/logout", children: _jsxs("div", { className: "mx-auto pt-2", children: [_jsx(LogoutDropDownSvgIcon, {}), _jsx("span", { children: "Cerrar sesi\u00F3n" })] }) }, "cerrar-sesion"),
58
+ ] })) })] }));
59
+ }, [items, loggedIn, hiddenItemsChange]);
54
60
  return (_jsx("nav", { className: `py-3 ${color.bg600}`, children: _jsxs("div", { className: "flex items-center justify-between ml-5 mr-5", children: [_jsxs("div", { className: "flex justify-between items-center w-full lg:w-auto", children: [_jsxs(Link, { className: "text-sm font-bold leading-relaxed inline-block mr-4 py-2 whitespace-nowrap uppercase text-white", to: "/home", children: [_jsx("div", { className: "inline-block mr-2 mb-2 align-middle", children: _jsx("img", { className: "w-auto h-7", src: "/logo.png", alt: "logo-zauru" }) }), title] }), version !== currentVersion && (_jsx("button", { className: `ml-2 px-2 py-1 text-xs text-white ${color.bg700} rounded-full hover:${color.bg900} transition-colors duration-200`, onClick: refreshPage, children: "\uD83D\uDD04 Actualizar versi\u00F3n" })), _jsx("button", { className: `rounded lg:hidden focus:outline-none focus:ring focus:${color.ring600} focus:ring-opacity-50`, "aria-label": "Toggle mobile menu", type: "button", onClick: () => setNavBarOpen(!NavBarOpen), children: _jsx(MenuAlt4Svg, { open: NavBarOpen }) })] }), _jsx("div", { className: `lg:hidden fixed top-0 left-0 z-50 w-64 h-full ${color.bg700} dark:bg-gray-900 shadow-lg transform ${NavBarOpen ? "translate-x-0" : "-translate-x-full"} transition-transform duration-300 ease-in-out overflow-y-auto`, children: _jsx("div", { className: "p-4", children: options }) }), _jsx("div", { className: "hidden lg:flex lg:items-center w-full lg:w-auto", children: options })] }) }));
55
61
  };
@@ -9,6 +9,6 @@ export const LoadingWindow = ({ loadingItems = [], description = "Por favor, esp
9
9
  if (!hasMounted) {
10
10
  return null;
11
11
  }
12
- return (_jsx("div", { className: "min-h-screen bg-gray-200 flex flex-col justify-center items-center", children: _jsxs(motion.div, { initial: { opacity: 0, y: -20 }, animate: { opacity: 1, y: 0 }, transition: { duration: 0.5 }, className: "text-center flex flex-col items-center", children: [_jsx("img", { src: "/logo.png", alt: "Zauru Logo", className: "mb-8 h-20" }), _jsx("h1", { className: "text-3xl font-bold text-gray-800 mb-4", children: "Cargando..." }), _jsx("p", { className: "text-gray-600 mb-4", children: description }), loadingItems && (_jsx("ul", { className: "text-left mb-4", children: loadingItems.map((item, index) => (_jsxs("li", { className: "flex items-center mb-2", children: [_jsx("svg", { className: `${item.loading ? "" : "hidden"} w-5 h-5 text-blue-500 mr-2 animate-spin loading-spinner`, fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: _jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M4 4v5h.582m15.356 2A8.001 8.001 0 004.582 9m0 0H9m11 11v-5h-.581m0 0a8.003 8.003 0 01-15.357-2m15.357 2H15" }) }), _jsx("svg", { className: `${item.loading ? "hidden" : ""} w-5 h-5 text-green-500 mr-2 check-mark`, fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: _jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M5 13l4 4L19 7" }) }), _jsx("span", { children: item.name })] }, index))) })), _jsx(motion.div, { animate: { rotate: 360 }, transition: { duration: 2, repeat: Infinity, ease: "linear" }, className: "mt-8", children: _jsx("svg", { className: "w-12 h-12 text-blue-500", fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: _jsx(motion.path, { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M4 4v5h.582m15.356 2A8.001 8.001 0 004.582 9m0 0H9m11 11v-5h-.581m0 0a8.003 8.003 0 01-15.357-2m15.357 2H15", animate: { rotate: 360 }, transition: { duration: 2, repeat: Infinity, ease: "linear" } }) }) })] }) }));
12
+ return (_jsxs("div", { className: "min-h-screen bg-gray-200 flex flex-col justify-center items-center", children: [_jsxs(motion.div, { initial: { opacity: 0, y: -20 }, animate: { opacity: 1, y: 0 }, transition: { duration: 0.5 }, className: "text-center flex flex-col items-center", children: [_jsx("img", { src: "/logo.png", alt: "Zauru Logo", className: "mb-8 h-20" }), _jsx("h1", { className: "text-3xl font-bold text-gray-800 mb-4", children: loadingItems.some((x) => x.loading) ? "Cargando..." : "Cargado" }), _jsx("p", { className: "text-gray-600 mb-4", children: description }), loadingItems && (_jsx("ul", { className: "text-left mb-4", children: loadingItems.map((item, index) => (_jsxs("li", { className: "flex items-center mb-2", children: [_jsx("svg", { className: `${item.loading ? "" : "hidden"} w-5 h-5 text-blue-500 mr-2 animate-spin loading-spinner`, fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: _jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M4 4v5h.582m15.356 2A8.001 8.001 0 004.582 9m0 0H9m11 11v-5h-.581m0 0a8.003 8.003 0 01-15.357-2m15.357 2H15" }) }), _jsx("svg", { className: `${item.loading ? "hidden" : ""} w-5 h-5 text-green-500 mr-2 check-mark`, fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: _jsx("path", { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M5 13l4 4L19 7" }) }), _jsx("span", { children: item.name })] }, index))) }))] }), _jsx("div", { className: "flex flex-col items-center", children: loadingItems.some((x) => x.loading) ? (_jsx(motion.div, { animate: { rotate: 360 }, transition: { duration: 2, repeat: Infinity, ease: "linear" }, className: "mt-8", children: _jsx("svg", { className: "w-12 h-12 text-blue-500", fill: "none", viewBox: "0 0 24 24", stroke: "currentColor", children: _jsx(motion.path, { strokeLinecap: "round", strokeLinejoin: "round", strokeWidth: 2, d: "M4 4v5h.582m15.356 2A8.001 8.001 0 004.582 9m0 0H9m11 11v-5h-.581m0 0a8.003 8.003 0 01-15.357-2m15.357 2H15", animate: { rotate: 360 }, transition: { duration: 2, repeat: Infinity, ease: "linear" } }) }) })) : (_jsx("span", { className: "text-green-500", children: "\u2705" })) })] }));
13
13
  };
14
14
  export default LoadingWindow;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@zauru-sdk/components",
3
- "version": "2.0.220",
3
+ "version": "2.0.222",
4
4
  "description": "Componentes reutilizables en las WebApps de Zauru.",
5
5
  "main": "./dist/esm/index.js",
6
6
  "module": "./dist/esm/index.js",
@@ -35,11 +35,11 @@
35
35
  "@rails/activestorage": "^8.0.200",
36
36
  "@reduxjs/toolkit": "^2.2.1",
37
37
  "@remix-run/react": "^2.8.1",
38
- "@zauru-sdk/common": "^2.0.220",
39
- "@zauru-sdk/hooks": "^2.0.220",
38
+ "@zauru-sdk/common": "^2.0.221",
39
+ "@zauru-sdk/hooks": "^2.0.221",
40
40
  "@zauru-sdk/icons": "^2.0.188",
41
- "@zauru-sdk/types": "^2.0.220",
42
- "@zauru-sdk/utils": "^2.0.220",
41
+ "@zauru-sdk/types": "^2.0.221",
42
+ "@zauru-sdk/utils": "^2.0.222",
43
43
  "browser-image-compression": "^2.0.2",
44
44
  "framer-motion": "^11.7.0",
45
45
  "jsonwebtoken": "^9.0.2",
@@ -52,5 +52,5 @@
52
52
  "styled-components": "^5.3.5",
53
53
  "zod": "^3.23.8"
54
54
  },
55
- "gitHead": "c8ca154d7c11e35c916f2e7f7bfc27f5ba2c14f1"
55
+ "gitHead": "6d2aeab534dc2248f8cd2a355f35cfd42626f38e"
56
56
  }
@@ -1,4 +1,4 @@
1
- import React, { useState, useEffect } from "react";
1
+ import React, { useState, useEffect, useMemo } from "react";
2
2
  import {
3
3
  DropDownArrowSvgIcon,
4
4
  LogoutDropDownSvgIcon,
@@ -127,6 +127,7 @@ export const NavBar = ({
127
127
  items,
128
128
  selectedColor,
129
129
  version,
130
+ reloadCatalogsOption,
130
131
  }: NavBarProps) => {
131
132
  const color: ColorInterface = COLORS[selectedColor];
132
133
  const [NavBarOpen, setNavBarOpen] = useState(false);
@@ -165,33 +166,71 @@ export const NavBar = ({
165
166
  </div>
166
167
  );
167
168
 
168
- const options = (
169
- <>
170
- <ul className="w-full lg:flex lg:items-center">
171
- {renderNavItems(items.filter((item) => item.loggedIn === loggedIn))}
172
- </ul>
173
- <ul className="sm:flex sm:flex-col lg:flex-row ml-auto">
174
- {loggedIn && (
175
- <OptionsDropDownButton
176
- color={color}
177
- options={[
178
- <Link
179
- key="cerrar-sesion"
180
- className={`block px-4 py-3 text-sm text-gray-600 capitalize transition-colors duration-200 transform dark:text-gray-300 hover:bg-red-100 dark:hover:bg-gray-700 dark:hover:text-white`}
181
- to="/logout"
182
- >
183
- <div className="mx-auto pt-2">
184
- {<LogoutDropDownSvgIcon />}
185
- <span>Cerrar sesión</span>
186
- </div>
187
- </Link>,
188
- ]}
189
- />
190
- )}
191
- </ul>
192
- </>
169
+ const hiddenItemsChange = useMemo(
170
+ () => items.filter((item) => item.hide === true),
171
+ [items]
193
172
  );
194
173
 
174
+ const options = useMemo(() => {
175
+ return (
176
+ <>
177
+ <ul className="w-full lg:flex lg:items-center">
178
+ {renderNavItems(
179
+ items
180
+ .filter((item) => item.loggedIn === loggedIn)
181
+ .filter((item) => item.hide !== true)
182
+ )}
183
+ </ul>
184
+ <ul className="sm:flex sm:flex-col lg:flex-row ml-auto">
185
+ {loggedIn && (
186
+ <OptionsDropDownButton
187
+ color={color}
188
+ options={[
189
+ reloadCatalogsOption && (
190
+ <Link
191
+ key="recargar-catalogos"
192
+ className={`block px-4 py-3 text-sm text-gray-600 capitalize transition-colors duration-200 transform dark:text-gray-300 hover:bg-red-100 dark:hover:bg-gray-700 dark:hover:text-white`}
193
+ to="/reload-catalogs"
194
+ >
195
+ <div className="mx-auto pt-2">
196
+ <svg
197
+ className={`h-5 w-5 mr-1`}
198
+ width="24"
199
+ height="24"
200
+ fill="none"
201
+ stroke="currentColor"
202
+ strokeWidth="1.5"
203
+ viewBox="0 0 24 24"
204
+ strokeLinecap="round"
205
+ strokeLinejoin="round"
206
+ xmlns="http://www.w3.org/2000/svg"
207
+ >
208
+ <path d="M20.5 8c-1.392-3.179-4.823-5-8.522-5C7.299 3 3.453 6.552 3 11.1" />
209
+ <path d="M16.489 8.4h3.97A.54.54 0 0 0 21 7.86V3.9M3.5 16c1.392 3.179 4.823 5 8.522 5 4.679 0 8.525-3.552 8.978-8.1" />
210
+ <path d="M7.511 15.6h-3.97a.54.54 0 0 0-.541.54v3.96" />
211
+ </svg>
212
+ <span>Recargar catálogos</span>
213
+ </div>
214
+ </Link>
215
+ ),
216
+ <Link
217
+ key="cerrar-sesion"
218
+ className={`block px-4 py-3 text-sm text-gray-600 capitalize transition-colors duration-200 transform dark:text-gray-300 hover:bg-red-100 dark:hover:bg-gray-700 dark:hover:text-white`}
219
+ to="/logout"
220
+ >
221
+ <div className="mx-auto pt-2">
222
+ {<LogoutDropDownSvgIcon />}
223
+ <span>Cerrar sesión</span>
224
+ </div>
225
+ </Link>,
226
+ ]}
227
+ />
228
+ )}
229
+ </ul>
230
+ </>
231
+ );
232
+ }, [items, loggedIn, hiddenItemsChange]);
233
+
195
234
  return (
196
235
  <nav className={`py-3 ${color.bg600}`}>
197
236
  <div className="flex items-center justify-between ml-5 mr-5">
@@ -14,6 +14,7 @@ export type NavBarItem = {
14
14
  color?: ColorInterface;
15
15
  childrens?: Exclude<NavBarItem, "loggedIn">[];
16
16
  reduxNotificationBadge?: (state: any) => string | number;
17
+ hide?: boolean;
17
18
  };
18
19
 
19
20
  export type NavBarProps = {
@@ -30,6 +31,7 @@ export type NavBarProps = {
30
31
  | "sky";
31
32
  LinkComponent?: any;
32
33
  version?: string;
34
+ reloadCatalogsOption?: boolean;
33
35
  };
34
36
 
35
37
  export type NavBarStateProps = {
@@ -34,7 +34,9 @@ export const LoadingWindow: React.FC<LoadingWindowProps> = ({
34
34
  className="text-center flex flex-col items-center"
35
35
  >
36
36
  <img src="/logo.png" alt="Zauru Logo" className="mb-8 h-20" />
37
- <h1 className="text-3xl font-bold text-gray-800 mb-4">Cargando...</h1>
37
+ <h1 className="text-3xl font-bold text-gray-800 mb-4">
38
+ {loadingItems.some((x) => x.loading) ? "Cargando..." : "Cargado"}
39
+ </h1>
38
40
  <p className="text-gray-600 mb-4">{description}</p>
39
41
  {loadingItems && (
40
42
  <ul className="text-left mb-4">
@@ -75,28 +77,34 @@ export const LoadingWindow: React.FC<LoadingWindowProps> = ({
75
77
  ))}
76
78
  </ul>
77
79
  )}
78
- <motion.div
79
- animate={{ rotate: 360 }}
80
- transition={{ duration: 2, repeat: Infinity, ease: "linear" }}
81
- className="mt-8"
82
- >
83
- <svg
84
- className="w-12 h-12 text-blue-500"
85
- fill="none"
86
- viewBox="0 0 24 24"
87
- stroke="currentColor"
88
- >
89
- <motion.path
90
- strokeLinecap="round"
91
- strokeLinejoin="round"
92
- strokeWidth={2}
93
- d="M4 4v5h.582m15.356 2A8.001 8.001 0 004.582 9m0 0H9m11 11v-5h-.581m0 0a8.003 8.003 0 01-15.357-2m15.357 2H15"
94
- animate={{ rotate: 360 }}
95
- transition={{ duration: 2, repeat: Infinity, ease: "linear" }}
96
- />
97
- </svg>
98
- </motion.div>
99
80
  </motion.div>
81
+ <div className="flex flex-col items-center">
82
+ {loadingItems.some((x) => x.loading) ? (
83
+ <motion.div
84
+ animate={{ rotate: 360 }}
85
+ transition={{ duration: 2, repeat: Infinity, ease: "linear" }}
86
+ className="mt-8"
87
+ >
88
+ <svg
89
+ className="w-12 h-12 text-blue-500"
90
+ fill="none"
91
+ viewBox="0 0 24 24"
92
+ stroke="currentColor"
93
+ >
94
+ <motion.path
95
+ strokeLinecap="round"
96
+ strokeLinejoin="round"
97
+ strokeWidth={2}
98
+ d="M4 4v5h.582m15.356 2A8.001 8.001 0 004.582 9m0 0H9m11 11v-5h-.581m0 0a8.003 8.003 0 01-15.357-2m15.357 2H15"
99
+ animate={{ rotate: 360 }}
100
+ transition={{ duration: 2, repeat: Infinity, ease: "linear" }}
101
+ />
102
+ </svg>
103
+ </motion.div>
104
+ ) : (
105
+ <span className="text-green-500">✅</span>
106
+ )}
107
+ </div>
100
108
  </div>
101
109
  );
102
110
  };