@zaamx/netme-pos 0.0.15 → 0.0.18
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/.medusa/server/src/admin/index.js +216 -216
- package/.medusa/server/src/admin/index.mjs +220 -220
- package/.medusa/server/src/api/admin/orders/sales/pending-by-location/route.js +152 -0
- package/.medusa/server/src/api/admin/orders/sales/route.js +398 -0
- package/.medusa/server/src/api/middlewares.js +168 -1
- package/.medusa/server/src/api/store/netme-pos/draft-orders/[id]/convert-to-order/route.js +37 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/[id]/edit/confirm/route.js +20 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/[id]/edit/items/[action_id]/route.js +74 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/[id]/edit/items/item/[item_id]/route.js +41 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/[id]/edit/items/route.js +31 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/[id]/edit/promotions/route.js +31 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/[id]/edit/request/route.js +16 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/[id]/edit/route.js +32 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/[id]/edit/shipping-methods/[action_id]/route.js +32 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/[id]/edit/shipping-methods/method/[method_id]/route.js +30 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/[id]/edit/shipping-methods/route.js +19 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/[id]/route.js +63 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/guards.js +77 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/helpers.js +19 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/pricing.js +136 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/query-config.js +60 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/route.js +140 -0
- package/.medusa/server/src/api/store/netme-pos/draft-orders/validators.js +217 -0
- package/.medusa/server/src/api/store/netme-pos/fulfillment-validators.js +74 -0
- package/.medusa/server/src/api/store/netme-pos/payment-collections/[id]/mark-as-paid/route.js +34 -0
- package/.medusa/server/src/api/store/netme-pos/payment-collections/[id]/payment-sessions/route.js +28 -0
- package/.medusa/server/src/api/store/netme-pos/payment-collections/guards.js +27 -0
- package/.medusa/server/src/api/store/netme-pos/products/[id]/route.js +10 -0
- package/.medusa/server/src/api/store/netme-pos/products/route.js +14 -0
- package/.medusa/server/src/api/store/netme-pos/scope.js +106 -0
- package/.medusa/server/src/api/store/netme-pos/shipping-options/route.js +100 -0
- package/.medusa/server/src/api/store/netme-pos/stock-locations/route.js +45 -0
- package/.medusa/server/src/links/agent-draft-order.js +31 -0
- package/.medusa/server/src/workflows/ensure-agent-can-act-for/index.js +36 -0
- package/package.json +1 -1
|
@@ -1,11 +1,11 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { jsx, jsxs, Fragment } from "react/jsx-runtime";
|
|
2
2
|
import { defineRouteConfig } from "@medusajs/admin-sdk";
|
|
3
|
-
import {
|
|
4
|
-
import {
|
|
3
|
+
import { EllipsisHorizontal, PencilSquare, ShieldCheck, Trash, Users, CurrencyDollar, XMark, ChevronUpDown, ArrowUturnLeft, Spinner, ArrowLeft, Buildings, ChannelsSolid, Tag } from "@medusajs/icons";
|
|
4
|
+
import { toast, Drawer, Label, Input, Text, Button, Prompt, DropdownMenu, IconButton, FocusModal, createDataTableColumnHelper, useDataTable, DataTable, Container, Heading, Select, Badge, Popover, clx, Checkbox, Switch } from "@medusajs/ui";
|
|
5
5
|
import { useState, useMemo, useEffect, useRef } from "react";
|
|
6
|
-
import {
|
|
7
|
-
import { Link, useNavigate, useParams } from "react-router-dom";
|
|
6
|
+
import { useQueryClient, useMutation, useQuery } from "@tanstack/react-query";
|
|
8
7
|
import Medusa from "@medusajs/js-sdk";
|
|
8
|
+
import { useNavigate, Link, useParams } from "react-router-dom";
|
|
9
9
|
const sdk = new Medusa({
|
|
10
10
|
// @ts-ignore
|
|
11
11
|
baseUrl: "/",
|
|
@@ -15,187 +15,6 @@ const sdk = new Medusa({
|
|
|
15
15
|
type: "session"
|
|
16
16
|
}
|
|
17
17
|
});
|
|
18
|
-
const POS_ROLES = [
|
|
19
|
-
{ value: "cashier", label: "Cajero" },
|
|
20
|
-
{ value: "supervisor", label: "Supervisor" },
|
|
21
|
-
{ value: "manager", label: "Gerente" }
|
|
22
|
-
];
|
|
23
|
-
const CAPABILITY_GROUPS = [
|
|
24
|
-
{
|
|
25
|
-
title: "Venta / carrito",
|
|
26
|
-
items: [
|
|
27
|
-
{ key: "cancel_sale", label: "Cancelar venta", description: "Botón que borra el draft" },
|
|
28
|
-
{ key: "pause_sale", label: "Pausar venta", description: "Guardar para después" },
|
|
29
|
-
{ key: "remove_item", label: "Eliminar ítems del carrito" },
|
|
30
|
-
{ key: "edit_quantity", label: "Cambiar cantidades" },
|
|
31
|
-
{ key: "apply_promotion", label: "Aplicar / quitar cupón" },
|
|
32
|
-
{ key: "apply_manual_discount", label: "Descuento manual (override de precio)", description: "Acción sensible" }
|
|
33
|
-
]
|
|
34
|
-
},
|
|
35
|
-
{
|
|
36
|
-
title: "Configuración de la sesión",
|
|
37
|
-
items: [
|
|
38
|
-
{ key: "change_region", label: "Cambiar región" },
|
|
39
|
-
{ key: "change_sales_channel", label: "Cambiar canal de venta" },
|
|
40
|
-
{ key: "change_location", label: "Cambiar ubicación de surtido" }
|
|
41
|
-
]
|
|
42
|
-
},
|
|
43
|
-
{
|
|
44
|
-
title: "Pago",
|
|
45
|
-
items: [
|
|
46
|
-
{ key: "pay_cash", label: "Cobrar en caja (efectivo)" },
|
|
47
|
-
{ key: "pay_card", label: "Cobrar con tarjeta (Stripe)" },
|
|
48
|
-
{ key: "use_store_credit", label: "Pagar con Monedero (store credit)" },
|
|
49
|
-
{ key: "capture_payment", label: "Capturar pago" },
|
|
50
|
-
{ key: "capture_without_docs", label: "Capturar sin documentación", description: "Acción sensible" }
|
|
51
|
-
]
|
|
52
|
-
},
|
|
53
|
-
{
|
|
54
|
-
title: "Envío / dirección",
|
|
55
|
-
items: [
|
|
56
|
-
{ key: "edit_shipping", label: "Elegir / cambiar método de envío" },
|
|
57
|
-
{ key: "edit_customer_address", label: "Editar dirección de envío del cliente" }
|
|
58
|
-
]
|
|
59
|
-
},
|
|
60
|
-
{
|
|
61
|
-
title: "Ventas pendientes",
|
|
62
|
-
items: [
|
|
63
|
-
{ key: "view_pending_drafts", label: "Ver ventas pendientes (/pos-drafts)" },
|
|
64
|
-
{ key: "recover_draft", label: "Recuperar / cargar un draft" }
|
|
65
|
-
]
|
|
66
|
-
}
|
|
67
|
-
];
|
|
68
|
-
const CAPABILITY_KEYS = CAPABILITY_GROUPS.flatMap(
|
|
69
|
-
(g) => g.items.map((i) => i.key)
|
|
70
|
-
);
|
|
71
|
-
const allTrue = () => CAPABILITY_KEYS.reduce(
|
|
72
|
-
(acc, key) => ({ ...acc, [key]: true }),
|
|
73
|
-
{}
|
|
74
|
-
);
|
|
75
|
-
const ROLE_PRESETS = {
|
|
76
|
-
cashier: {
|
|
77
|
-
...allTrue(),
|
|
78
|
-
cancel_sale: false,
|
|
79
|
-
apply_manual_discount: false,
|
|
80
|
-
change_region: false,
|
|
81
|
-
change_sales_channel: false,
|
|
82
|
-
capture_payment: false,
|
|
83
|
-
capture_without_docs: false,
|
|
84
|
-
view_pending_drafts: false,
|
|
85
|
-
recover_draft: false
|
|
86
|
-
},
|
|
87
|
-
supervisor: {
|
|
88
|
-
...allTrue(),
|
|
89
|
-
capture_without_docs: false
|
|
90
|
-
},
|
|
91
|
-
manager: {
|
|
92
|
-
...allTrue()
|
|
93
|
-
}
|
|
94
|
-
};
|
|
95
|
-
const presetForRole = (role) => {
|
|
96
|
-
if (role && ROLE_PRESETS[role]) {
|
|
97
|
-
return ROLE_PRESETS[role];
|
|
98
|
-
}
|
|
99
|
-
return allTrue();
|
|
100
|
-
};
|
|
101
|
-
const resolveCapabilities = (role, stored) => {
|
|
102
|
-
const preset = presetForRole(role);
|
|
103
|
-
return CAPABILITY_KEYS.reduce((acc, key) => {
|
|
104
|
-
const storedValue = stored && typeof stored[key] === "boolean" ? stored[key] : void 0;
|
|
105
|
-
acc[key] = storedValue ?? preset[key] ?? true;
|
|
106
|
-
return acc;
|
|
107
|
-
}, {});
|
|
108
|
-
};
|
|
109
|
-
const columnHelper$2 = createDataTableColumnHelper();
|
|
110
|
-
const roleLabel = (role) => {
|
|
111
|
-
var _a;
|
|
112
|
-
return ((_a = POS_ROLES.find((r) => r.value === role)) == null ? void 0 : _a.label) || null;
|
|
113
|
-
};
|
|
114
|
-
const scopeSummary = (ids) => Array.isArray(ids) ? `${ids.length} seleccionada${ids.length === 1 ? "" : "s"}` : "Todas";
|
|
115
|
-
const useColumns$2 = () => useMemo(
|
|
116
|
-
() => [
|
|
117
|
-
columnHelper$2.accessor("first_name", {
|
|
118
|
-
header: "Nombre",
|
|
119
|
-
cell: ({ row }) => `${row.original.first_name ?? ""} ${row.original.last_name ?? ""}`.trim() || "—"
|
|
120
|
-
}),
|
|
121
|
-
columnHelper$2.accessor("email", {
|
|
122
|
-
header: "Email"
|
|
123
|
-
}),
|
|
124
|
-
columnHelper$2.display({
|
|
125
|
-
id: "role",
|
|
126
|
-
header: "Rol POS",
|
|
127
|
-
cell: ({ row }) => {
|
|
128
|
-
var _a;
|
|
129
|
-
const label = roleLabel((_a = row.original.metadata) == null ? void 0 : _a.pos_role);
|
|
130
|
-
return label ? /* @__PURE__ */ jsx(Badge, { size: "2xsmall", color: "blue", children: label }) : /* @__PURE__ */ jsx(Text, { size: "small", className: "text-ui-fg-muted", children: "Sin rol" });
|
|
131
|
-
}
|
|
132
|
-
}),
|
|
133
|
-
columnHelper$2.display({
|
|
134
|
-
id: "locations",
|
|
135
|
-
header: "Ubicaciones",
|
|
136
|
-
cell: ({ row }) => {
|
|
137
|
-
var _a;
|
|
138
|
-
return /* @__PURE__ */ jsx(Text, { size: "small", children: scopeSummary((_a = row.original.metadata) == null ? void 0 : _a.pos_stock_location_ids) });
|
|
139
|
-
}
|
|
140
|
-
}),
|
|
141
|
-
columnHelper$2.display({
|
|
142
|
-
id: "actions",
|
|
143
|
-
cell: ({ row }) => /* @__PURE__ */ jsx("div", { className: "flex justify-end", children: /* @__PURE__ */ jsx(Button, { asChild: true, size: "small", variant: "secondary", children: /* @__PURE__ */ jsx(Link, { to: `/pos-permissions/${row.original.id}`, children: "Editar permisos" }) }) })
|
|
144
|
-
})
|
|
145
|
-
],
|
|
146
|
-
[]
|
|
147
|
-
);
|
|
148
|
-
const PosPermissionsPage = () => {
|
|
149
|
-
const [searchValue, setSearchValue] = useState("");
|
|
150
|
-
const [pagination, setPagination] = useState({
|
|
151
|
-
pageIndex: 0,
|
|
152
|
-
pageSize: 15
|
|
153
|
-
});
|
|
154
|
-
const limit = pagination.pageSize;
|
|
155
|
-
const offset = pagination.pageIndex * limit;
|
|
156
|
-
const { data, isLoading } = useQuery({
|
|
157
|
-
queryFn: () => sdk.client.fetch("/admin/operators", {
|
|
158
|
-
query: {
|
|
159
|
-
limit,
|
|
160
|
-
offset,
|
|
161
|
-
q: searchValue || void 0
|
|
162
|
-
}
|
|
163
|
-
}),
|
|
164
|
-
queryKey: ["operators", "pos-permissions", limit, offset, searchValue],
|
|
165
|
-
placeholderData: (previousData) => previousData
|
|
166
|
-
});
|
|
167
|
-
const columns = useColumns$2();
|
|
168
|
-
const table = useDataTable({
|
|
169
|
-
data: (data == null ? void 0 : data.operators) || [],
|
|
170
|
-
columns,
|
|
171
|
-
getRowId: (row) => row.id,
|
|
172
|
-
rowCount: (data == null ? void 0 : data.count) || 0,
|
|
173
|
-
isLoading,
|
|
174
|
-
search: {
|
|
175
|
-
state: searchValue,
|
|
176
|
-
onSearchChange: setSearchValue
|
|
177
|
-
},
|
|
178
|
-
pagination: {
|
|
179
|
-
state: pagination,
|
|
180
|
-
onPaginationChange: setPagination
|
|
181
|
-
}
|
|
182
|
-
});
|
|
183
|
-
return /* @__PURE__ */ jsxs(Container, { className: "flex flex-col items-stretch overflow-hidden p-0", children: [
|
|
184
|
-
/* @__PURE__ */ jsx("div", { className: "flex items-center justify-between border-b border-ui-border-base px-6 py-4", children: /* @__PURE__ */ jsxs("div", { className: "flex flex-col gap-y-1", children: [
|
|
185
|
-
/* @__PURE__ */ jsx(Heading, { level: "h2", children: "Permisos POS" }),
|
|
186
|
-
/* @__PURE__ */ jsx(Text, { size: "small", className: "text-ui-fg-subtle", children: "Define el alcance (ubicaciones, canales, regiones) y las capacidades de cada operador del Punto de Venta." })
|
|
187
|
-
] }) }),
|
|
188
|
-
/* @__PURE__ */ jsxs(DataTable, { instance: table, children: [
|
|
189
|
-
/* @__PURE__ */ jsx(DataTable.Toolbar, { children: /* @__PURE__ */ jsx("div", { className: "flex w-full items-center justify-end", children: /* @__PURE__ */ jsx(DataTable.Search, { placeholder: "Buscar operador..." }) }) }),
|
|
190
|
-
/* @__PURE__ */ jsx(DataTable.Table, {}),
|
|
191
|
-
/* @__PURE__ */ jsx(DataTable.Pagination, {})
|
|
192
|
-
] })
|
|
193
|
-
] });
|
|
194
|
-
};
|
|
195
|
-
const config$2 = defineRouteConfig({
|
|
196
|
-
label: "Permisos POS",
|
|
197
|
-
icon: ShieldCheck
|
|
198
|
-
});
|
|
199
18
|
const EditOperatorDrawer = ({
|
|
200
19
|
operator,
|
|
201
20
|
open,
|
|
@@ -502,24 +321,24 @@ const CreateOperatorModal = () => {
|
|
|
502
321
|
] }) }) })
|
|
503
322
|
] });
|
|
504
323
|
};
|
|
505
|
-
const columnHelper$
|
|
506
|
-
const useColumns$
|
|
324
|
+
const columnHelper$2 = createDataTableColumnHelper();
|
|
325
|
+
const useColumns$2 = () => {
|
|
507
326
|
return useMemo(
|
|
508
327
|
() => [
|
|
509
|
-
columnHelper$
|
|
328
|
+
columnHelper$2.accessor("first_name", {
|
|
510
329
|
header: "First Name"
|
|
511
330
|
}),
|
|
512
|
-
columnHelper$
|
|
331
|
+
columnHelper$2.accessor("last_name", {
|
|
513
332
|
header: "Last Name"
|
|
514
333
|
}),
|
|
515
|
-
columnHelper$
|
|
334
|
+
columnHelper$2.accessor("email", {
|
|
516
335
|
header: "Email"
|
|
517
336
|
}),
|
|
518
|
-
columnHelper$
|
|
337
|
+
columnHelper$2.accessor("created_at", {
|
|
519
338
|
header: "Date Added",
|
|
520
339
|
cell: ({ getValue }) => new Date(getValue()).toLocaleDateString()
|
|
521
340
|
}),
|
|
522
|
-
columnHelper$
|
|
341
|
+
columnHelper$2.display({
|
|
523
342
|
id: "actions",
|
|
524
343
|
cell: ({ row }) => /* @__PURE__ */ jsx(OperatorActions, { operator: row.original })
|
|
525
344
|
})
|
|
@@ -546,7 +365,7 @@ const OperatorTable = () => {
|
|
|
546
365
|
queryKey: ["operators", limit, offset, searchValue],
|
|
547
366
|
placeholderData: (previousData) => previousData
|
|
548
367
|
});
|
|
549
|
-
const columns = useColumns$
|
|
368
|
+
const columns = useColumns$2();
|
|
550
369
|
const table = useDataTable({
|
|
551
370
|
data: (data == null ? void 0 : data.operators) || [],
|
|
552
371
|
columns,
|
|
@@ -577,7 +396,7 @@ const OperatorsPage = () => {
|
|
|
577
396
|
/* @__PURE__ */ jsx(OperatorTable, {})
|
|
578
397
|
] });
|
|
579
398
|
};
|
|
580
|
-
const config$
|
|
399
|
+
const config$2 = defineRouteConfig({
|
|
581
400
|
label: "Operators",
|
|
582
401
|
icon: Users
|
|
583
402
|
});
|
|
@@ -913,7 +732,7 @@ const PaymentOptionActions = ({
|
|
|
913
732
|
)
|
|
914
733
|
] });
|
|
915
734
|
};
|
|
916
|
-
const columnHelper = createDataTableColumnHelper();
|
|
735
|
+
const columnHelper$1 = createDataTableColumnHelper();
|
|
917
736
|
const formatAmount = (value) => {
|
|
918
737
|
const n = Number(value ?? 0);
|
|
919
738
|
return n.toLocaleString("es-MX", {
|
|
@@ -944,10 +763,10 @@ const statusColor = (status) => {
|
|
|
944
763
|
return "grey";
|
|
945
764
|
}
|
|
946
765
|
};
|
|
947
|
-
const useColumns = () => {
|
|
766
|
+
const useColumns$1 = () => {
|
|
948
767
|
return useMemo(
|
|
949
768
|
() => [
|
|
950
|
-
columnHelper.accessor("order_display_id", {
|
|
769
|
+
columnHelper$1.accessor("order_display_id", {
|
|
951
770
|
header: "Orden",
|
|
952
771
|
cell: ({ row }) => {
|
|
953
772
|
const displayId = row.original.order_display_id;
|
|
@@ -972,19 +791,19 @@ const useColumns = () => {
|
|
|
972
791
|
);
|
|
973
792
|
}
|
|
974
793
|
}),
|
|
975
|
-
columnHelper.accessor("reference_code", {
|
|
794
|
+
columnHelper$1.accessor("reference_code", {
|
|
976
795
|
header: "Folio / Referencia",
|
|
977
796
|
cell: ({ getValue }) => getValue() || "—"
|
|
978
797
|
}),
|
|
979
|
-
columnHelper.accessor("payment_method", {
|
|
798
|
+
columnHelper$1.accessor("payment_method", {
|
|
980
799
|
header: "Método",
|
|
981
800
|
cell: ({ getValue }) => getValue() || "—"
|
|
982
801
|
}),
|
|
983
|
-
columnHelper.accessor("amount", {
|
|
802
|
+
columnHelper$1.accessor("amount", {
|
|
984
803
|
header: "Monto",
|
|
985
804
|
cell: ({ getValue }) => formatAmount(getValue())
|
|
986
805
|
}),
|
|
987
|
-
columnHelper.accessor("status", {
|
|
806
|
+
columnHelper$1.accessor("status", {
|
|
988
807
|
header: "Estatus",
|
|
989
808
|
cell: ({ getValue }) => {
|
|
990
809
|
const status = getValue();
|
|
@@ -994,15 +813,15 @@ const useColumns = () => {
|
|
|
994
813
|
return /* @__PURE__ */ jsx(Badge, { size: "2xsmall", color: statusColor(status), children: status });
|
|
995
814
|
}
|
|
996
815
|
}),
|
|
997
|
-
columnHelper.accessor("concept", {
|
|
816
|
+
columnHelper$1.accessor("concept", {
|
|
998
817
|
header: "Concepto",
|
|
999
818
|
cell: ({ getValue }) => getValue() || "—"
|
|
1000
819
|
}),
|
|
1001
|
-
columnHelper.accessor("created_at", {
|
|
820
|
+
columnHelper$1.accessor("created_at", {
|
|
1002
821
|
header: "Fecha",
|
|
1003
822
|
cell: ({ getValue }) => new Date(getValue()).toLocaleString()
|
|
1004
823
|
}),
|
|
1005
|
-
columnHelper.display({
|
|
824
|
+
columnHelper$1.display({
|
|
1006
825
|
id: "actions",
|
|
1007
826
|
cell: ({ row }) => /* @__PURE__ */ jsx(PaymentOptionActions, { paymentOption: row.original })
|
|
1008
827
|
})
|
|
@@ -1029,7 +848,7 @@ const PaymentOptionTable = () => {
|
|
|
1029
848
|
queryKey: ["payment-options", limit, offset, searchValue],
|
|
1030
849
|
placeholderData: (previousData) => previousData
|
|
1031
850
|
});
|
|
1032
|
-
const columns = useColumns();
|
|
851
|
+
const columns = useColumns$1();
|
|
1033
852
|
const table = useDataTable({
|
|
1034
853
|
data: (data == null ? void 0 : data.payment_options) || [],
|
|
1035
854
|
columns,
|
|
@@ -1066,10 +885,191 @@ const PaymentOptionsPage = () => {
|
|
|
1066
885
|
/* @__PURE__ */ jsx(PaymentOptionTable, {})
|
|
1067
886
|
] });
|
|
1068
887
|
};
|
|
1069
|
-
const config = defineRouteConfig({
|
|
888
|
+
const config$1 = defineRouteConfig({
|
|
1070
889
|
label: "Notas de pago",
|
|
1071
890
|
icon: CurrencyDollar
|
|
1072
891
|
});
|
|
892
|
+
const POS_ROLES = [
|
|
893
|
+
{ value: "cashier", label: "Cajero" },
|
|
894
|
+
{ value: "supervisor", label: "Supervisor" },
|
|
895
|
+
{ value: "manager", label: "Gerente" }
|
|
896
|
+
];
|
|
897
|
+
const CAPABILITY_GROUPS = [
|
|
898
|
+
{
|
|
899
|
+
title: "Venta / carrito",
|
|
900
|
+
items: [
|
|
901
|
+
{ key: "cancel_sale", label: "Cancelar venta", description: "Botón que borra el draft" },
|
|
902
|
+
{ key: "pause_sale", label: "Pausar venta", description: "Guardar para después" },
|
|
903
|
+
{ key: "remove_item", label: "Eliminar ítems del carrito" },
|
|
904
|
+
{ key: "edit_quantity", label: "Cambiar cantidades" },
|
|
905
|
+
{ key: "apply_promotion", label: "Aplicar / quitar cupón" },
|
|
906
|
+
{ key: "apply_manual_discount", label: "Descuento manual (override de precio)", description: "Acción sensible" }
|
|
907
|
+
]
|
|
908
|
+
},
|
|
909
|
+
{
|
|
910
|
+
title: "Configuración de la sesión",
|
|
911
|
+
items: [
|
|
912
|
+
{ key: "change_region", label: "Cambiar región" },
|
|
913
|
+
{ key: "change_sales_channel", label: "Cambiar canal de venta" },
|
|
914
|
+
{ key: "change_location", label: "Cambiar ubicación de surtido" }
|
|
915
|
+
]
|
|
916
|
+
},
|
|
917
|
+
{
|
|
918
|
+
title: "Pago",
|
|
919
|
+
items: [
|
|
920
|
+
{ key: "pay_cash", label: "Cobrar en caja (efectivo)" },
|
|
921
|
+
{ key: "pay_card", label: "Cobrar con tarjeta (Stripe)" },
|
|
922
|
+
{ key: "use_store_credit", label: "Pagar con Monedero (store credit)" },
|
|
923
|
+
{ key: "capture_payment", label: "Capturar pago" },
|
|
924
|
+
{ key: "capture_without_docs", label: "Capturar sin documentación", description: "Acción sensible" }
|
|
925
|
+
]
|
|
926
|
+
},
|
|
927
|
+
{
|
|
928
|
+
title: "Envío / dirección",
|
|
929
|
+
items: [
|
|
930
|
+
{ key: "edit_shipping", label: "Elegir / cambiar método de envío" },
|
|
931
|
+
{ key: "edit_customer_address", label: "Editar dirección de envío del cliente" }
|
|
932
|
+
]
|
|
933
|
+
},
|
|
934
|
+
{
|
|
935
|
+
title: "Ventas pendientes",
|
|
936
|
+
items: [
|
|
937
|
+
{ key: "view_pending_drafts", label: "Ver ventas pendientes (/pos-drafts)" },
|
|
938
|
+
{ key: "recover_draft", label: "Recuperar / cargar un draft" }
|
|
939
|
+
]
|
|
940
|
+
}
|
|
941
|
+
];
|
|
942
|
+
const CAPABILITY_KEYS = CAPABILITY_GROUPS.flatMap(
|
|
943
|
+
(g) => g.items.map((i) => i.key)
|
|
944
|
+
);
|
|
945
|
+
const allTrue = () => CAPABILITY_KEYS.reduce(
|
|
946
|
+
(acc, key) => ({ ...acc, [key]: true }),
|
|
947
|
+
{}
|
|
948
|
+
);
|
|
949
|
+
const ROLE_PRESETS = {
|
|
950
|
+
cashier: {
|
|
951
|
+
...allTrue(),
|
|
952
|
+
cancel_sale: false,
|
|
953
|
+
apply_manual_discount: false,
|
|
954
|
+
change_region: false,
|
|
955
|
+
change_sales_channel: false,
|
|
956
|
+
capture_payment: false,
|
|
957
|
+
capture_without_docs: false,
|
|
958
|
+
view_pending_drafts: false,
|
|
959
|
+
recover_draft: false
|
|
960
|
+
},
|
|
961
|
+
supervisor: {
|
|
962
|
+
...allTrue(),
|
|
963
|
+
capture_without_docs: false
|
|
964
|
+
},
|
|
965
|
+
manager: {
|
|
966
|
+
...allTrue()
|
|
967
|
+
}
|
|
968
|
+
};
|
|
969
|
+
const presetForRole = (role) => {
|
|
970
|
+
if (role && ROLE_PRESETS[role]) {
|
|
971
|
+
return ROLE_PRESETS[role];
|
|
972
|
+
}
|
|
973
|
+
return allTrue();
|
|
974
|
+
};
|
|
975
|
+
const resolveCapabilities = (role, stored) => {
|
|
976
|
+
const preset = presetForRole(role);
|
|
977
|
+
return CAPABILITY_KEYS.reduce((acc, key) => {
|
|
978
|
+
const storedValue = stored && typeof stored[key] === "boolean" ? stored[key] : void 0;
|
|
979
|
+
acc[key] = storedValue ?? preset[key] ?? true;
|
|
980
|
+
return acc;
|
|
981
|
+
}, {});
|
|
982
|
+
};
|
|
983
|
+
const columnHelper = createDataTableColumnHelper();
|
|
984
|
+
const roleLabel = (role) => {
|
|
985
|
+
var _a;
|
|
986
|
+
return ((_a = POS_ROLES.find((r) => r.value === role)) == null ? void 0 : _a.label) || null;
|
|
987
|
+
};
|
|
988
|
+
const scopeSummary = (ids) => Array.isArray(ids) ? `${ids.length} seleccionada${ids.length === 1 ? "" : "s"}` : "Todas";
|
|
989
|
+
const useColumns = () => useMemo(
|
|
990
|
+
() => [
|
|
991
|
+
columnHelper.accessor("first_name", {
|
|
992
|
+
header: "Nombre",
|
|
993
|
+
cell: ({ row }) => `${row.original.first_name ?? ""} ${row.original.last_name ?? ""}`.trim() || "—"
|
|
994
|
+
}),
|
|
995
|
+
columnHelper.accessor("email", {
|
|
996
|
+
header: "Email"
|
|
997
|
+
}),
|
|
998
|
+
columnHelper.display({
|
|
999
|
+
id: "role",
|
|
1000
|
+
header: "Rol POS",
|
|
1001
|
+
cell: ({ row }) => {
|
|
1002
|
+
var _a;
|
|
1003
|
+
const label = roleLabel((_a = row.original.metadata) == null ? void 0 : _a.pos_role);
|
|
1004
|
+
return label ? /* @__PURE__ */ jsx(Badge, { size: "2xsmall", color: "blue", children: label }) : /* @__PURE__ */ jsx(Text, { size: "small", className: "text-ui-fg-muted", children: "Sin rol" });
|
|
1005
|
+
}
|
|
1006
|
+
}),
|
|
1007
|
+
columnHelper.display({
|
|
1008
|
+
id: "locations",
|
|
1009
|
+
header: "Ubicaciones",
|
|
1010
|
+
cell: ({ row }) => {
|
|
1011
|
+
var _a;
|
|
1012
|
+
return /* @__PURE__ */ jsx(Text, { size: "small", children: scopeSummary((_a = row.original.metadata) == null ? void 0 : _a.pos_stock_location_ids) });
|
|
1013
|
+
}
|
|
1014
|
+
}),
|
|
1015
|
+
columnHelper.display({
|
|
1016
|
+
id: "actions",
|
|
1017
|
+
cell: ({ row }) => /* @__PURE__ */ jsx("div", { className: "flex justify-end", children: /* @__PURE__ */ jsx(Button, { asChild: true, size: "small", variant: "secondary", children: /* @__PURE__ */ jsx(Link, { to: `/pos-permissions/${row.original.id}`, children: "Editar permisos" }) }) })
|
|
1018
|
+
})
|
|
1019
|
+
],
|
|
1020
|
+
[]
|
|
1021
|
+
);
|
|
1022
|
+
const PosPermissionsPage = () => {
|
|
1023
|
+
const [searchValue, setSearchValue] = useState("");
|
|
1024
|
+
const [pagination, setPagination] = useState({
|
|
1025
|
+
pageIndex: 0,
|
|
1026
|
+
pageSize: 15
|
|
1027
|
+
});
|
|
1028
|
+
const limit = pagination.pageSize;
|
|
1029
|
+
const offset = pagination.pageIndex * limit;
|
|
1030
|
+
const { data, isLoading } = useQuery({
|
|
1031
|
+
queryFn: () => sdk.client.fetch("/admin/operators", {
|
|
1032
|
+
query: {
|
|
1033
|
+
limit,
|
|
1034
|
+
offset,
|
|
1035
|
+
q: searchValue || void 0
|
|
1036
|
+
}
|
|
1037
|
+
}),
|
|
1038
|
+
queryKey: ["operators", "pos-permissions", limit, offset, searchValue],
|
|
1039
|
+
placeholderData: (previousData) => previousData
|
|
1040
|
+
});
|
|
1041
|
+
const columns = useColumns();
|
|
1042
|
+
const table = useDataTable({
|
|
1043
|
+
data: (data == null ? void 0 : data.operators) || [],
|
|
1044
|
+
columns,
|
|
1045
|
+
getRowId: (row) => row.id,
|
|
1046
|
+
rowCount: (data == null ? void 0 : data.count) || 0,
|
|
1047
|
+
isLoading,
|
|
1048
|
+
search: {
|
|
1049
|
+
state: searchValue,
|
|
1050
|
+
onSearchChange: setSearchValue
|
|
1051
|
+
},
|
|
1052
|
+
pagination: {
|
|
1053
|
+
state: pagination,
|
|
1054
|
+
onPaginationChange: setPagination
|
|
1055
|
+
}
|
|
1056
|
+
});
|
|
1057
|
+
return /* @__PURE__ */ jsxs(Container, { className: "flex flex-col items-stretch overflow-hidden p-0", children: [
|
|
1058
|
+
/* @__PURE__ */ jsx("div", { className: "flex items-center justify-between border-b border-ui-border-base px-6 py-4", children: /* @__PURE__ */ jsxs("div", { className: "flex flex-col gap-y-1", children: [
|
|
1059
|
+
/* @__PURE__ */ jsx(Heading, { level: "h2", children: "Permisos POS" }),
|
|
1060
|
+
/* @__PURE__ */ jsx(Text, { size: "small", className: "text-ui-fg-subtle", children: "Define el alcance (ubicaciones, canales, regiones) y las capacidades de cada operador del Punto de Venta." })
|
|
1061
|
+
] }) }),
|
|
1062
|
+
/* @__PURE__ */ jsxs(DataTable, { instance: table, children: [
|
|
1063
|
+
/* @__PURE__ */ jsx(DataTable.Toolbar, { children: /* @__PURE__ */ jsx("div", { className: "flex w-full items-center justify-end", children: /* @__PURE__ */ jsx(DataTable.Search, { placeholder: "Buscar operador..." }) }) }),
|
|
1064
|
+
/* @__PURE__ */ jsx(DataTable.Table, {}),
|
|
1065
|
+
/* @__PURE__ */ jsx(DataTable.Pagination, {})
|
|
1066
|
+
] })
|
|
1067
|
+
] });
|
|
1068
|
+
};
|
|
1069
|
+
const config = defineRouteConfig({
|
|
1070
|
+
label: "Permisos POS",
|
|
1071
|
+
icon: ShieldCheck
|
|
1072
|
+
});
|
|
1073
1073
|
const MultiSelect = ({
|
|
1074
1074
|
options,
|
|
1075
1075
|
value,
|
|
@@ -1694,10 +1694,6 @@ const i18nTranslations0 = {};
|
|
|
1694
1694
|
const widgetModule = { widgets: [] };
|
|
1695
1695
|
const routeModule = {
|
|
1696
1696
|
routes: [
|
|
1697
|
-
{
|
|
1698
|
-
Component: PosPermissionsPage,
|
|
1699
|
-
path: "/pos-permissions"
|
|
1700
|
-
},
|
|
1701
1697
|
{
|
|
1702
1698
|
Component: OperatorsPage,
|
|
1703
1699
|
path: "/operators"
|
|
@@ -1706,6 +1702,10 @@ const routeModule = {
|
|
|
1706
1702
|
Component: PaymentOptionsPage,
|
|
1707
1703
|
path: "/payment-options"
|
|
1708
1704
|
},
|
|
1705
|
+
{
|
|
1706
|
+
Component: PosPermissionsPage,
|
|
1707
|
+
path: "/pos-permissions"
|
|
1708
|
+
},
|
|
1709
1709
|
{
|
|
1710
1710
|
Component: PosPermissionEditorPage,
|
|
1711
1711
|
path: "/pos-permissions/:id"
|
|
@@ -1715,25 +1715,25 @@ const routeModule = {
|
|
|
1715
1715
|
const menuItemModule = {
|
|
1716
1716
|
menuItems: [
|
|
1717
1717
|
{
|
|
1718
|
-
label: config.label,
|
|
1719
|
-
icon: config.icon,
|
|
1720
|
-
path: "/
|
|
1718
|
+
label: config$2.label,
|
|
1719
|
+
icon: config$2.icon,
|
|
1720
|
+
path: "/operators",
|
|
1721
1721
|
nested: void 0,
|
|
1722
1722
|
rank: void 0,
|
|
1723
1723
|
translationNs: void 0
|
|
1724
1724
|
},
|
|
1725
1725
|
{
|
|
1726
|
-
label: config$
|
|
1727
|
-
icon: config$
|
|
1728
|
-
path: "/
|
|
1726
|
+
label: config$1.label,
|
|
1727
|
+
icon: config$1.icon,
|
|
1728
|
+
path: "/payment-options",
|
|
1729
1729
|
nested: void 0,
|
|
1730
1730
|
rank: void 0,
|
|
1731
1731
|
translationNs: void 0
|
|
1732
1732
|
},
|
|
1733
1733
|
{
|
|
1734
|
-
label: config
|
|
1735
|
-
icon: config
|
|
1736
|
-
path: "/
|
|
1734
|
+
label: config.label,
|
|
1735
|
+
icon: config.icon,
|
|
1736
|
+
path: "/pos-permissions",
|
|
1737
1737
|
nested: void 0,
|
|
1738
1738
|
rank: void 0,
|
|
1739
1739
|
translationNs: void 0
|