contentoh-components-library 21.6.35 → 21.6.37

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.
@@ -39,6 +39,7 @@ import { ImageDataTable } from "../../organisms/ImageDataTable";
39
39
  import { ImagePreviewer } from "../../organisms/ImagePreviewer";
40
40
  import { InputGroup } from "../../organisms/InputGroup";
41
41
  import { LinkVariantsModal } from "../../organisms/LinkVariantsModal";
42
+ import { UnlinkVariantModal } from "../../organisms/UnlinkVariantModal";
42
43
  import { PropagateChangesModal } from "../../organisms/PropagateChangesModal";
43
44
  import { readPayload } from "../../organisms/LinkVariantsModal/api";
44
45
  import { ProductImageModal } from "../../organisms/ProductImageModal";
@@ -781,8 +782,8 @@ const ProviderProductEditionView = ({
781
782
  productos no son familia, y una llamada por ficha para no mostrar nada es
782
783
  peso que paga todo el mundo por el caso de unos pocos.
783
784
  */
784
- const loadFamily = async () => {
785
- if (family) return family;
785
+ const loadFamily = async (forzar = false) => {
786
+ if (family && !forzar) return family;
786
787
  try {
787
788
  const res = await axios.post(
788
789
  `${process.env.REACT_APP_VARIANTS_ENDPOINT}/family`,
@@ -875,6 +876,71 @@ const ProviderProductEditionView = ({
875
876
  }
876
877
  };
877
878
 
879
+ /*
880
+ Qué vínculo se está por romper, o null si no hay diálogo abierto.
881
+
882
+ Guarda al HIJO, porque la relación vive en él (`article.parent_article_id`)
883
+ y es lo que pide la acción `unlink`. `mode` solo cambia el texto: no es lo
884
+ mismo soltarse de un padre que soltar a un hijo, aunque por dentro sea la
885
+ misma llamada.
886
+ */
887
+ const [porDesvincular, setPorDesvincular] = useState(null);
888
+
889
+ /*
890
+ Después de desvincular, esta ficha cambia de forma.
891
+
892
+ Si el producto se soltó de su padre, deja de ser hijo y vuelve a poder ligar
893
+ —el botón reaparece—. Si soltó a un hijo, pierde uno de la cuenta. En los dos
894
+ casos hay que repreguntar la familia: lo que se ve en la lista ya no es lo
895
+ que hay en el servidor.
896
+ */
897
+ const handleOnUnlinked = (result) => {
898
+ if (!result) return;
899
+
900
+ const updatedProduct =
901
+ result.mode === "self"
902
+ ? { ...state.product, parentArticleId: null, variantsCount: 0 }
903
+ : {
904
+ ...state.product,
905
+ variantsCount: Math.max((state.product?.variantsCount ?? 1) - 1, 0),
906
+ };
907
+
908
+ dispatch({ type: "SET_PRODUCT", payload: updatedProduct });
909
+
910
+ try {
911
+ sessionStorage.setItem("productSelected", JSON.stringify(updatedProduct));
912
+
913
+ const productEdit = JSON.parse(sessionStorage.getItem("productEdit"));
914
+ if (productEdit) {
915
+ sessionStorage.setItem(
916
+ "productEdit",
917
+ JSON.stringify({ ...productEdit, product: updatedProduct })
918
+ );
919
+ }
920
+ } catch (error) {
921
+ console.error("unlinkVariant/sessionStorage: ", error);
922
+ }
923
+
924
+ /*
925
+ Si ya no queda familia, se cierra el desplegable: su botón desaparece con
926
+ el vínculo, y dejarlo abierto pinta una caja que dice «no tiene hijos» y
927
+ que nadie puede cerrar.
928
+ */
929
+ if (
930
+ !updatedProduct.parentArticleId &&
931
+ (updatedProduct.variantsCount ?? 0) === 0
932
+ ) {
933
+ setShowFamily(false);
934
+ }
935
+
936
+ loadFamily(true);
937
+
938
+ // Y los servicios: al desvincular, el servidor pone `is_overridden = 0` en
939
+ // todas las versiones, así que los chips de herencia tienen que dejar de
940
+ // dibujarse. Sin esto la ficha sigue mostrándolos hasta que se recarga.
941
+ setLinkNonce((n) => n + 1);
942
+ };
943
+
878
944
  const openVariant = async (articleId) => {
879
945
  setLoadingVariant(articleId);
880
946
  try {
@@ -950,8 +1016,14 @@ const ProviderProductEditionView = ({
950
1016
  };
951
1017
 
952
1018
  dispatch({ type: "SET_PRODUCT", payload: updatedProduct });
953
- // La lista cacheada quedó vieja: se descarta para que vuelva a pedirse.
954
- setFamily(null);
1019
+ /*
1020
+ Se vuelve a pedir, no se vacía.
1021
+
1022
+ `setFamily(null)` invalidaba la caché, pero la lista solo se pide al pulsar
1023
+ el desplegable: si estaba abierto al ligar, se quedaba en «Cargando
1024
+ familia…» para siempre, porque ya nadie iba a volver a pedirla.
1025
+ */
1026
+ loadFamily(true);
955
1027
  // Y los servicios, para que los chips reflejen la herencia recién creada.
956
1028
  setLinkNonce((n) => n + 1);
957
1029
 
@@ -1513,6 +1585,14 @@ const ProviderProductEditionView = ({
1513
1585
  onLinked={handleOnLinkedVariants}
1514
1586
  />
1515
1587
  )}
1588
+ {porDesvincular && (
1589
+ <UnlinkVariantModal
1590
+ {...porDesvincular}
1591
+ token={token}
1592
+ onClose={() => setPorDesvincular(null)}
1593
+ onUnlinked={handleOnUnlinked}
1594
+ />
1595
+ )}
1516
1596
  {showModal && (
1517
1597
  <ProductImageModal
1518
1598
  images={state.images_values}
@@ -1759,43 +1839,92 @@ const ProviderProductEditionView = ({
1759
1839
  </p>
1760
1840
  )}
1761
1841
 
1842
+ {/* Desvincular se ofrece donde se ve el vínculo, y solo en
1843
+ la dirección que corresponde a esta ficha: desde un hijo,
1844
+ sobre su padre —«me suelto»—; desde un padre, sobre cada
1845
+ hijo. A un hermano no: para eso se abre su ficha, donde la
1846
+ acción dice lo que de verdad va a pasar. */}
1762
1847
  {family?.parent && (
1763
- <button
1764
- type="button"
1765
- className="family-row parent"
1766
- disabled={loadingVariant !== null}
1767
- onClick={() => openVariant(family.parent.articleId)}
1768
- >
1769
- <span className="role">
1770
- {loadingVariant === family.parent.articleId
1771
- ? "Abriendo…"
1772
- : "Producto padre"}
1773
- </span>
1774
- <span className="name">{family.parent.name}</span>
1775
- <span className="upc">{family.parent.upc}</span>
1776
- </button>
1848
+ <div className="family-item">
1849
+ <button
1850
+ type="button"
1851
+ className="family-row parent"
1852
+ disabled={loadingVariant !== null}
1853
+ onClick={() => openVariant(family.parent.articleId)}
1854
+ >
1855
+ <span className="role">
1856
+ {loadingVariant === family.parent.articleId
1857
+ ? "Abriendo…"
1858
+ : "Producto padre"}
1859
+ </span>
1860
+ <span className="name">{family.parent.name}</span>
1861
+ <span className="upc">{family.parent.upc}</span>
1862
+ </button>
1863
+
1864
+ <button
1865
+ type="button"
1866
+ className="desvincular"
1867
+ title="Dejar de ser hijo de este producto"
1868
+ onClick={() =>
1869
+ setPorDesvincular({
1870
+ mode: "self",
1871
+ childArticleId: state.product?.id_article,
1872
+ childName: state.product?.name,
1873
+ childUpc: state.product?.upc,
1874
+ parentName: family.parent.name,
1875
+ parentUpc: family.parent.upc,
1876
+ })
1877
+ }
1878
+ >
1879
+ Desvincular
1880
+ </button>
1881
+ </div>
1777
1882
  )}
1778
1883
 
1779
1884
  {family?.variants?.map((variant) => (
1780
- <button
1781
- key={variant.articleId}
1782
- type="button"
1783
- className={`family-row${
1784
- variant.isCurrent ? " current" : ""
1785
- }`}
1786
- disabled={variant.isCurrent || loadingVariant !== null}
1787
- onClick={() => openVariant(variant.articleId)}
1788
- >
1789
- <span className="role">
1790
- {loadingVariant === variant.articleId
1791
- ? "Abriendo…"
1792
- : variant.isCurrent
1793
- ? "Estás aquí"
1794
- : "Hijo"}
1795
- </span>
1796
- <span className="name">{variant.name}</span>
1797
- <span className="upc">{variant.upc}</span>
1798
- </button>
1885
+ <div className="family-item" key={variant.articleId}>
1886
+ <button
1887
+ type="button"
1888
+ className={`family-row${
1889
+ variant.isCurrent ? " current" : ""
1890
+ }`}
1891
+ disabled={variant.isCurrent || loadingVariant !== null}
1892
+ onClick={() => openVariant(variant.articleId)}
1893
+ >
1894
+ <span className="role">
1895
+ {loadingVariant === variant.articleId
1896
+ ? "Abriendo…"
1897
+ : variant.isCurrent
1898
+ ? "Estás aquí"
1899
+ : "Hijo"}
1900
+ </span>
1901
+ <span className="name">{variant.name}</span>
1902
+ <span className="upc">{variant.upc}</span>
1903
+ </button>
1904
+
1905
+ {/* Solo cuando esta ficha ES el padre: si hay `parent`, lo
1906
+ que se lista son hermanos y este producto no manda
1907
+ sobre su vínculo. */}
1908
+ {!family.parent && !variant.isCurrent && (
1909
+ <button
1910
+ type="button"
1911
+ className="desvincular"
1912
+ title="Desvincular este hijo"
1913
+ onClick={() =>
1914
+ setPorDesvincular({
1915
+ mode: "child",
1916
+ childArticleId: variant.articleId,
1917
+ childName: variant.name,
1918
+ childUpc: variant.upc,
1919
+ parentName: state.product?.name,
1920
+ parentUpc: state.product?.upc,
1921
+ })
1922
+ }
1923
+ >
1924
+ Desvincular
1925
+ </button>
1926
+ )}
1927
+ </div>
1799
1928
  ))}
1800
1929
 
1801
1930
  {family && !family.error && !family.variants?.length && (
@@ -208,6 +208,36 @@ export const Container = styled.div`
208
208
  color: ${GlobalColors.gray};
209
209
  }
210
210
 
211
+ /* La fila es un botón que navega; desvincular tiene que quedar FUERA de
212
+ él —un botón dentro de otro no es HTML válido y el clic se confunde—. */
213
+ .family-item {
214
+ display: flex;
215
+ align-items: center;
216
+ gap: 4px;
217
+ }
218
+
219
+ .family-item .family-row {
220
+ flex: 1;
221
+ min-width: 0;
222
+ }
223
+
224
+ .desvincular {
225
+ flex-shrink: 0;
226
+ border: none;
227
+ background: none;
228
+ padding: 4px 6px;
229
+ cursor: pointer;
230
+ font-family: ${FontFamily.Raleway_500};
231
+ font-size: 10px;
232
+ color: ${GlobalColors.gray};
233
+ text-decoration: underline;
234
+ white-space: nowrap;
235
+ }
236
+
237
+ .desvincular:hover {
238
+ color: ${PINK};
239
+ }
240
+
211
241
  .family-row {
212
242
  display: flex;
213
243
  align-items: baseline;
@@ -51,6 +51,7 @@ import { ProductImageModal } from "../../organisms/ProductImageModal";
51
51
  import { VersionSelector } from "../../organisms/VersionSelector";
52
52
  import { Modal } from "../../organisms/Modal";
53
53
  import { LinkVariantsModal } from "../../organisms/LinkVariantsModal";
54
+ import { UnlinkVariantModal } from "../../organisms/UnlinkVariantModal";
54
55
  import { PropagateChangesModal } from "../../organisms/PropagateChangesModal";
55
56
  import { readPayload } from "../../organisms/LinkVariantsModal/api";
56
57
 
@@ -186,6 +187,9 @@ const RetailerProductEditionView = ({
186
187
  const [family, setFamily] = useState(null);
187
188
  const [showFamily, setShowFamily] = useState(false);
188
189
  const [loadingVariant, setLoadingVariant] = useState(null);
190
+ // Qué vínculo se está por romper, o null si no hay diálogo abierto. Guarda al
191
+ // HIJO, que es quien lleva la relación y lo que pide la acción `unlink`.
192
+ const [porDesvincular, setPorDesvincular] = useState(null);
189
193
  // Por qué un salto no se pudo hacer. Vive aparte de `family.error` porque no
190
194
  // es un fallo al leer la familia, sino al abrir uno de sus miembros.
191
195
  const [avisoFamilia, setAvisoFamilia] = useState(null);
@@ -858,6 +862,69 @@ const RetailerProductEditionView = ({
858
862
  En ese caso no hay nada que abrir aquí, y se dice en vez de navegar a una
859
863
  pantalla que mostraría el producto equivocado.
860
864
  */
865
+ /*
866
+ Después de desvincular, esta ficha cambia de forma: si se soltó de su padre
867
+ vuelve a poder ligar, y si soltó a un hijo pierde uno de la cuenta. En esta
868
+ pantalla el bloque de parentesco se decide con `family`, así que hay que
869
+ repreguntarla —vaciarla lo haría desaparecer, que es el error que ya se
870
+ cometió una vez aquí—.
871
+ */
872
+ const handleOnUnlinked = (result) => {
873
+ if (!result) return;
874
+
875
+ const updatedProduct =
876
+ result.mode === "self"
877
+ ? { ...state.product, parentArticleId: null, variantsCount: 0 }
878
+ : {
879
+ ...state.product,
880
+ variantsCount: Math.max((state.product?.variantsCount ?? 1) - 1, 0),
881
+ };
882
+
883
+ dispatch({ type: "SET_PRODUCT", payload: updatedProduct });
884
+
885
+ // Se PARCHEA lo guardado: ahí vive el producto con la forma del listado
886
+ // —`article` anidado, servicios, cadenas— y escribir encima la versión
887
+ // aplanada de esta pantalla lo dejaría mutilado en el siguiente F5.
888
+ try {
889
+ const guardado = JSON.parse(
890
+ sessionStorage.getItem("productSelected") ?? "null"
891
+ );
892
+
893
+ if (guardado) {
894
+ sessionStorage.setItem(
895
+ "productSelected",
896
+ JSON.stringify({
897
+ ...guardado,
898
+ variantsCount: updatedProduct.variantsCount,
899
+ parentArticleId: updatedProduct.parentArticleId ?? null,
900
+ })
901
+ );
902
+ }
903
+ } catch (error) {
904
+ console.error("unlinkVariant/sessionStorage: ", error);
905
+ }
906
+
907
+ /*
908
+ Si ya no queda familia, se cierra el desplegable: su botón desaparece con
909
+ el vínculo, y dejarlo abierto pinta una caja que dice «no tiene hijos» y
910
+ que nadie puede cerrar.
911
+ */
912
+ if (
913
+ !updatedProduct.parentArticleId &&
914
+ (updatedProduct.variantsCount ?? 0) === 0
915
+ ) {
916
+ setShowFamily(false);
917
+ }
918
+
919
+ loadFamily(true);
920
+
921
+ // Al desvincular el servidor pone `is_overridden = 0` en todas las
922
+ // versiones, así que los chips de herencia tienen que dejar de dibujarse.
923
+ // Sin `enableLoading` para no parpadear el esqueleto encima de una pantalla
924
+ // que ya está pintada.
925
+ loadData(false);
926
+ };
927
+
861
928
  const openFamilyMember = async (articleId) => {
862
929
  setLoadingVariant(articleId);
863
930
  setAvisoFamilia(null);
@@ -1064,17 +1131,73 @@ const RetailerProductEditionView = ({
1064
1131
  await saveDescriptions(token);
1065
1132
  break;
1066
1133
  case "Ficha técnica": {
1067
- // Guardar un padre con hijos abre la decisión de propagar. Sin este
1068
- // paso el cambio se queda solo en el padre y los hijos se van
1069
- // separando de él sin que nadie lo note.
1070
- const esPadre = hijosDelProducto > 0;
1071
1134
  const cambios = cambiosDeFichaTecnica();
1072
1135
 
1073
- if (esPadre && cambios.length > 0) {
1074
- setPreparandoPropagacion(true);
1075
- loadFamily()
1076
- .then(() => setPendingPropagation({ cambios }))
1077
- .finally(() => setPreparandoPropagacion(false));
1136
+ if (cambios.length === 0) {
1137
+ await saveDatasheets(token);
1138
+ break;
1139
+ }
1140
+
1141
+ /*
1142
+ Guardar un padre con hijos abre la decisión de propagar. Sin este paso
1143
+ el cambio se queda solo en el padre y los hijos se van separando de él
1144
+ sin que nadie lo note.
1145
+
1146
+ Si tiene hijos se resuelve AQUÍ, esperando la respuesta, en vez de
1147
+ mirar la copia en memoria. `family` es una consulta asíncrona: si
1148
+ todavía no llegó, o si falló, `hijosDelProducto` vale 0 — o sea que
1149
+ «todavía no sé» se leía igual que «no tiene hijos», y el padre se
1150
+ guardaba sin ofrecer la propagación. En silencio, que es lo peor: el
1151
+ usuario creía haber bajado el cambio a los hijos.
1152
+
1153
+ La ficha de la aplicación de clientes no tiene el problema porque ahí
1154
+ `state.product.variantsCount` viene del listado; aquí el producto sale
1155
+ del endpoint de reportes, que no trae el parentesco.
1156
+ */
1157
+ setPreparandoPropagacion(true);
1158
+ let familia = null;
1159
+ try {
1160
+ familia = await loadFamily(true);
1161
+ } finally {
1162
+ setPreparandoPropagacion(false);
1163
+ }
1164
+
1165
+ // No se pudo saber si tiene hijos. Guardar de todas formas repetiría el
1166
+ // defecto que se está corrigiendo, así que se dice y se deja la decisión.
1167
+ if (!familia || familia.error) {
1168
+ dispatch({
1169
+ type: "SET_MODAL",
1170
+ payload: {
1171
+ show: true,
1172
+ title: "No se pudo consultar la familia",
1173
+ message:
1174
+ "No pudimos saber si este producto tiene hijos, así que no sabemos si hay que bajarles el cambio. Vuelve a intentar el guardado; si sigue fallando, guarda y revisa los hijos a mano.",
1175
+ image: warningIcon,
1176
+ buttons: [
1177
+ {
1178
+ text: "Entendido",
1179
+ buttonType: "general-white-button",
1180
+ action: () =>
1181
+ dispatch({ type: "SET_MODAL", payload: { show: false } }),
1182
+ },
1183
+ {
1184
+ text: "Guardar solo este producto",
1185
+ buttonType: "general-button-default",
1186
+ action: () => {
1187
+ dispatch({ type: "SET_MODAL", payload: { show: false } });
1188
+ saveDatasheets(token);
1189
+ },
1190
+ },
1191
+ ],
1192
+ },
1193
+ });
1194
+ return;
1195
+ }
1196
+
1197
+ const hijos = (familia.variants ?? []).filter((v) => !v.isCurrent);
1198
+
1199
+ if (hijos.length > 0) {
1200
+ setPendingPropagation({ cambios });
1078
1201
  return;
1079
1202
  }
1080
1203
 
@@ -1857,6 +1980,14 @@ const RetailerProductEditionView = ({
1857
1980
  onLinked={handleOnLinkedVariants}
1858
1981
  />
1859
1982
  )}
1983
+ {porDesvincular && (
1984
+ <UnlinkVariantModal
1985
+ {...porDesvincular}
1986
+ token={token}
1987
+ onClose={() => setPorDesvincular(null)}
1988
+ onUnlinked={handleOnUnlinked}
1989
+ />
1990
+ )}
1860
1991
  {showRejectModal && (
1861
1992
  <Modal
1862
1993
  title={
@@ -2117,43 +2248,90 @@ const RetailerProductEditionView = ({
2117
2248
  </p>
2118
2249
  )}
2119
2250
 
2251
+ {/* Desvincular se ofrece donde se ve el vínculo, y solo en la
2252
+ dirección que corresponde a esta ficha: desde un hijo, sobre
2253
+ su padre; desde un padre, sobre cada hijo. A un hermano no:
2254
+ para eso se abre su ficha. */}
2120
2255
  {family?.parent && (
2121
- <button
2122
- type="button"
2123
- className="family-row parent"
2124
- disabled={loadingVariant !== null}
2125
- onClick={() => openFamilyMember(family.parent.articleId)}
2126
- >
2127
- <span className="role">
2128
- {loadingVariant === family.parent.articleId
2129
- ? "Abriendo…"
2130
- : "Producto padre"}
2131
- </span>
2132
- <span className="name">{family.parent.name}</span>
2133
- <span className="upc">{family.parent.upc}</span>
2134
- </button>
2256
+ <div className="family-item">
2257
+ <button
2258
+ type="button"
2259
+ className="family-row parent"
2260
+ disabled={loadingVariant !== null}
2261
+ onClick={() => openFamilyMember(family.parent.articleId)}
2262
+ >
2263
+ <span className="role">
2264
+ {loadingVariant === family.parent.articleId
2265
+ ? "Abriendo…"
2266
+ : "Producto padre"}
2267
+ </span>
2268
+ <span className="name">{family.parent.name}</span>
2269
+ <span className="upc">{family.parent.upc}</span>
2270
+ </button>
2271
+
2272
+ <button
2273
+ type="button"
2274
+ className="desvincular"
2275
+ title="Dejar de ser hijo de este producto"
2276
+ onClick={() =>
2277
+ setPorDesvincular({
2278
+ mode: "self",
2279
+ childArticleId: state.product?.id_article,
2280
+ childName: state.product?.name,
2281
+ childUpc: state.product?.upc,
2282
+ parentName: family.parent.name,
2283
+ parentUpc: family.parent.upc,
2284
+ })
2285
+ }
2286
+ >
2287
+ Desvincular
2288
+ </button>
2289
+ </div>
2135
2290
  )}
2136
2291
 
2137
2292
  {family?.variants?.map((variant) => (
2138
- <button
2139
- key={variant.articleId}
2140
- type="button"
2141
- className={`family-row${
2142
- variant.isCurrent ? " current" : ""
2143
- }`}
2144
- disabled={variant.isCurrent || loadingVariant !== null}
2145
- onClick={() => openFamilyMember(variant.articleId)}
2146
- >
2147
- <span className="role">
2148
- {loadingVariant === variant.articleId
2149
- ? "Abriendo…"
2150
- : variant.isCurrent
2151
- ? "Estás aquí"
2152
- : "Hijo"}
2153
- </span>
2154
- <span className="name">{variant.name}</span>
2155
- <span className="upc">{variant.upc}</span>
2156
- </button>
2293
+ <div className="family-item" key={variant.articleId}>
2294
+ <button
2295
+ type="button"
2296
+ className={`family-row${
2297
+ variant.isCurrent ? " current" : ""
2298
+ }`}
2299
+ disabled={variant.isCurrent || loadingVariant !== null}
2300
+ onClick={() => openFamilyMember(variant.articleId)}
2301
+ >
2302
+ <span className="role">
2303
+ {loadingVariant === variant.articleId
2304
+ ? "Abriendo…"
2305
+ : variant.isCurrent
2306
+ ? "Estás aquí"
2307
+ : "Hijo"}
2308
+ </span>
2309
+ <span className="name">{variant.name}</span>
2310
+ <span className="upc">{variant.upc}</span>
2311
+ </button>
2312
+
2313
+ {/* Solo cuando esta ficha ES el padre: si hay `parent`, lo
2314
+ que se lista son hermanos. */}
2315
+ {!family.parent && !variant.isCurrent && (
2316
+ <button
2317
+ type="button"
2318
+ className="desvincular"
2319
+ title="Desvincular este hijo"
2320
+ onClick={() =>
2321
+ setPorDesvincular({
2322
+ mode: "child",
2323
+ childArticleId: variant.articleId,
2324
+ childName: variant.name,
2325
+ childUpc: variant.upc,
2326
+ parentName: state.product?.name,
2327
+ parentUpc: state.product?.upc,
2328
+ })
2329
+ }
2330
+ >
2331
+ Desvincular
2332
+ </button>
2333
+ )}
2334
+ </div>
2157
2335
  ))}
2158
2336
 
2159
2337
  {family && !family.error && !family.variants?.length && (
@@ -215,6 +215,36 @@ export const Container = styled.div`
215
215
  color: ${GlobalColors.gray};
216
216
  }
217
217
 
218
+ /* La fila es un botón que navega; desvincular tiene que quedar FUERA de
219
+ él —un botón dentro de otro no es HTML válido y el clic se confunde—. */
220
+ .family-item {
221
+ display: flex;
222
+ align-items: center;
223
+ gap: 4px;
224
+ }
225
+
226
+ .family-item .family-row {
227
+ flex: 1;
228
+ min-width: 0;
229
+ }
230
+
231
+ .desvincular {
232
+ flex-shrink: 0;
233
+ border: none;
234
+ background: none;
235
+ padding: 4px 6px;
236
+ cursor: pointer;
237
+ font-family: ${FontFamily.Raleway_500};
238
+ font-size: 10px;
239
+ color: ${GlobalColors.gray};
240
+ text-decoration: underline;
241
+ white-space: nowrap;
242
+ }
243
+
244
+ .desvincular:hover {
245
+ color: ${PINK};
246
+ }
247
+
218
248
  .family-row {
219
249
  display: flex;
220
250
  align-items: baseline;
package/src/index.js CHANGED
@@ -89,6 +89,7 @@ export * from "./components/organisms/ImagesGroup/index";
89
89
  export * from "./components/organisms/InputGroup/index";
90
90
  export * from "./components/organisms/LinkVariantsModal/index";
91
91
  export * from "./components/organisms/PropagateChangesModal/index";
92
+ export * from "./components/organisms/UnlinkVariantModal/index";
92
93
  export * from "./components/organisms/ProductImageModal/index";
93
94
  export * from "./components/organisms/Chat/index";
94
95
  export * from "./components/organisms/Modal/index";