@bluemarble/bm-components 0.0.93 → 0.0.95

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/dist/index.mjs CHANGED
@@ -52,6 +52,26 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
52
52
  isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
53
53
  mod
54
54
  ));
55
+ var __async = (__this, __arguments, generator) => {
56
+ return new Promise((resolve, reject) => {
57
+ var fulfilled = (value) => {
58
+ try {
59
+ step(generator.next(value));
60
+ } catch (e) {
61
+ reject(e);
62
+ }
63
+ };
64
+ var rejected = (value) => {
65
+ try {
66
+ step(generator.throw(value));
67
+ } catch (e) {
68
+ reject(e);
69
+ }
70
+ };
71
+ var step = (x) => x.done ? resolve(x.value) : Promise.resolve(x.value).then(fulfilled, rejected);
72
+ step((generator = generator.apply(__this, __arguments)).next());
73
+ });
74
+ };
55
75
 
56
76
  // node_modules/prop-types/node_modules/react-is/cjs/react-is.production.min.js
57
77
  var require_react_is_production_min = __commonJS({
@@ -3815,19 +3835,338 @@ function BaseGrid({
3815
3835
  );
3816
3836
  }
3817
3837
 
3818
- // src/components/hooks/useGrid.ts
3819
- import { useMemo as useMemo3, useState as useState4 } from "react";
3838
+ // src/components/Modal/index.tsx
3839
+ import React24 from "react";
3840
+ import {
3841
+ Box as Box4,
3842
+ Modal as MuiModal
3843
+ } from "@mui/material";
3844
+ var Modal = (_a) => {
3845
+ var _b = _a, { open, onClose } = _b, rest = __objRest(_b, ["open", "onClose"]);
3846
+ return /* @__PURE__ */ React24.createElement(MuiModal, __spreadValues({ open, onClose, disableEnforceFocus: true }, rest), /* @__PURE__ */ React24.createElement(
3847
+ Box4,
3848
+ {
3849
+ sx: {
3850
+ outline: "none",
3851
+ backgroundColor: "white",
3852
+ position: "absolute",
3853
+ top: "50%",
3854
+ left: "50%",
3855
+ transform: "translate(-50%, -50%)",
3856
+ borderRadius: 1
3857
+ }
3858
+ },
3859
+ /* @__PURE__ */ React24.createElement(React24.Fragment, null, rest.children)
3860
+ ));
3861
+ };
3862
+
3863
+ // src/components/utils/GetInputLabel.ts
3864
+ function GetInputLabel(columns) {
3865
+ return (columnName) => {
3866
+ const column = columns.find((column2) => column2.name === columnName);
3867
+ return { label: column.label, name: column.name };
3868
+ };
3869
+ }
3870
+
3871
+ // src/components/Dialog/index.tsx
3872
+ import React25 from "react";
3873
+ import {
3874
+ Box as Box5,
3875
+ Dialog as DefaultDialog,
3876
+ DialogContentText,
3877
+ DialogActions,
3878
+ DialogTitle,
3879
+ Button as Button3,
3880
+ CircularProgress as CircularProgress2
3881
+ } from "@mui/material";
3882
+ var Dialog = (_a) => {
3883
+ var _b = _a, {
3884
+ open,
3885
+ title,
3886
+ loading,
3887
+ body,
3888
+ options
3889
+ } = _b, rest = __objRest(_b, [
3890
+ "open",
3891
+ "title",
3892
+ "loading",
3893
+ "body",
3894
+ "options"
3895
+ ]);
3896
+ return /* @__PURE__ */ React25.createElement(DefaultDialog, __spreadValues({ open }, rest), /* @__PURE__ */ React25.createElement(Box5, { sx: { p: 2 } }, /* @__PURE__ */ React25.createElement(DialogTitle, { sx: { fontWeight: "bold" } }, title), /* @__PURE__ */ React25.createElement(DialogContentText, { sx: { px: "10px", textAlign: "center", mb: 2 } }, body), /* @__PURE__ */ React25.createElement(DialogActions, null, options.map((option, index) => {
3897
+ return /* @__PURE__ */ React25.createElement(
3898
+ Button3,
3899
+ {
3900
+ key: index,
3901
+ onClick: () => option.cb(option.label),
3902
+ variant: option.focus ? "contained" : "text",
3903
+ sx: {
3904
+ fontWeight: option.focus ? "bold" : "normal",
3905
+ color: option.focus ? "#fff" : "primary.main"
3906
+ },
3907
+ disableElevation: true,
3908
+ disabled: loading
3909
+ },
3910
+ loading && option.focus ? /* @__PURE__ */ React25.createElement(CircularProgress2, { size: 25, color: "inherit" }) : /* @__PURE__ */ React25.createElement(React25.Fragment, null, option.label)
3911
+ );
3912
+ }))));
3913
+ };
3914
+
3915
+ // src/errors/HttpError.ts
3916
+ var HttpError = class extends Error {
3917
+ constructor(status, message) {
3918
+ super(message);
3919
+ this.message = message;
3920
+ this.stack = `HttpError: ${message}`;
3921
+ this.status = status;
3922
+ }
3923
+ };
3924
+
3925
+ // src/helpers/apiHelper/index.ts
3926
+ var ApiHelper = class _ApiHelper {
3927
+ onFinally() {
3928
+ }
3929
+ constructor(props) {
3930
+ this.middlewares = (props == null ? void 0 : props.middlewares.reverse()) || [];
3931
+ this.onFinally = props.onFinally;
3932
+ }
3933
+ setMiddlewares(middlewares) {
3934
+ this.middlewares = middlewares.reverse();
3935
+ return this;
3936
+ }
3937
+ createMethods(methods) {
3938
+ return (req, res) => __async(this, null, function* () {
3939
+ const currentMethod = methods[req.method];
3940
+ try {
3941
+ if (!currentMethod)
3942
+ throw new HttpError(405, "M\xE9todo inv\xE1lido");
3943
+ const methodWithMiddlewares = this.middlewares.reduce(
3944
+ (acc, fn) => fn(acc),
3945
+ currentMethod
3946
+ );
3947
+ yield methodWithMiddlewares(req, res);
3948
+ } catch (error) {
3949
+ if (error instanceof HttpError)
3950
+ return res.status(error.status).json(error.message);
3951
+ if (process.env.NODE_ENV === "production")
3952
+ return res.status(500).json({
3953
+ code: "internal.error",
3954
+ error: "Erro interno do servidor",
3955
+ details: error
3956
+ });
3957
+ throw new Error(error);
3958
+ } finally {
3959
+ this.onFinally();
3960
+ }
3961
+ });
3962
+ }
3963
+ static parserErrorWrapper(body, parser) {
3964
+ try {
3965
+ const object = parser.parse(body);
3966
+ return object;
3967
+ } catch (error) {
3968
+ throw new HttpError(400, {
3969
+ code: "invalid.body",
3970
+ error: "Dados inv\xE1lidos",
3971
+ details: error
3972
+ });
3973
+ }
3974
+ }
3975
+ static parseQueyFilters(filters) {
3976
+ return Object.entries(filters).reduce((acc, [key, value]) => {
3977
+ if (value)
3978
+ acc[key] = value;
3979
+ return acc;
3980
+ }, {});
3981
+ }
3982
+ static create({ onFinally }) {
3983
+ return new _ApiHelper({
3984
+ onFinally
3985
+ });
3986
+ }
3987
+ };
3988
+
3989
+ // src/hooks/useFormHelper.ts
3990
+ import axios from "axios";
3991
+ import { useEffect as useEffect5, useRef as useRef4 } from "react";
3992
+
3993
+ // src/hooks/useAlert.ts
3994
+ import { useContext as useContext2 } from "react";
3995
+
3996
+ // src/contexts/AlertContext.tsx
3997
+ import React27 from "react";
3998
+ import { createContext as createContext2, useState as useState3 } from "react";
3999
+
4000
+ // src/components/Toast/index.tsx
4001
+ import React26 from "react";
4002
+ import { Alert, IconButton as IconButton4, Snackbar } from "@mui/material";
4003
+ import { MdClose as MdClose2 } from "react-icons/md";
4004
+ var Toast = ({ open, onClose, severity, message }) => {
4005
+ return /* @__PURE__ */ React26.createElement(React26.Fragment, null, /* @__PURE__ */ React26.createElement(
4006
+ Snackbar,
4007
+ {
4008
+ open,
4009
+ autoHideDuration: 6e3,
4010
+ anchorOrigin: { vertical: "top", horizontal: "right" },
4011
+ sx: { zIndex: 99999999 }
4012
+ },
4013
+ /* @__PURE__ */ React26.createElement(
4014
+ Alert,
4015
+ {
4016
+ severity,
4017
+ elevation: 2,
4018
+ sx: { mb: 2 },
4019
+ action: /* @__PURE__ */ React26.createElement(
4020
+ IconButton4,
4021
+ {
4022
+ "aria-label": "close",
4023
+ color: "inherit",
4024
+ size: "small",
4025
+ onClick: onClose
4026
+ },
4027
+ /* @__PURE__ */ React26.createElement(MdClose2, { fontSize: "inherit" })
4028
+ )
4029
+ },
4030
+ message
4031
+ )
4032
+ ));
4033
+ };
4034
+
4035
+ // src/contexts/AlertContext.tsx
4036
+ var AlertContext = createContext2({});
4037
+ var AlertProvider = ({ children }) => {
4038
+ const [severity, setSeverity] = useState3("info");
4039
+ const [message, setMessage] = useState3("");
4040
+ const [isVisible, setIsVisible] = useState3(false);
4041
+ const createAlert = (newMessage, severity2) => {
4042
+ setMessage(newMessage);
4043
+ setSeverity(severity2);
4044
+ setIsVisible(true);
4045
+ };
4046
+ function onCloseToast() {
4047
+ setIsVisible(false);
4048
+ }
4049
+ return /* @__PURE__ */ React27.createElement(AlertContext.Provider, { value: { createAlert } }, children, /* @__PURE__ */ React27.createElement(
4050
+ Toast,
4051
+ {
4052
+ open: isVisible,
4053
+ onClose: onCloseToast,
4054
+ severity,
4055
+ message
4056
+ }
4057
+ ));
4058
+ };
4059
+
4060
+ // src/hooks/useAlert.ts
4061
+ var useAlert = () => {
4062
+ return useContext2(AlertContext);
4063
+ };
4064
+
4065
+ // src/hooks/useLoading.ts
4066
+ import { useState as useState4 } from "react";
4067
+ function useLoading() {
4068
+ const [state, setState] = useState4([]);
4069
+ const isLoading = (prop) => state.includes(prop);
4070
+ const setLoading = (prop, remove) => {
4071
+ if (remove)
4072
+ setState((prevState) => prevState.filter((state2) => state2 !== prop));
4073
+ else
4074
+ setState((prevState) => [...prevState, prop]);
4075
+ };
4076
+ return { isLoading, setLoading };
4077
+ }
4078
+
4079
+ // src/hooks/useFormHelper.ts
4080
+ function useFormHelper({ formatErrorMessage, api }) {
4081
+ const alertProps = useAlert();
4082
+ const loadingProps = useLoading();
4083
+ const { createAlert } = alertProps;
4084
+ const { setLoading } = loadingProps;
4085
+ const sourceRef = useRef4();
4086
+ function onSubmitWrapper(fn, { name }) {
4087
+ return (fields, methods) => __async(this, null, function* () {
4088
+ const LOADING_NAME = name;
4089
+ setLoading(LOADING_NAME);
4090
+ try {
4091
+ yield fn(fields, methods);
4092
+ } catch (error) {
4093
+ errorHandler(error, methods.setErrors);
4094
+ } finally {
4095
+ setLoading(LOADING_NAME, true);
4096
+ }
4097
+ });
4098
+ }
4099
+ function onRequestWrapper(fn, { name }) {
4100
+ return (...params) => __async(this, null, function* () {
4101
+ if (name.includes("get:"))
4102
+ sourceRef.current = axios.CancelToken.source();
4103
+ const LOADING_NAME = name;
4104
+ setLoading(LOADING_NAME);
4105
+ api.interceptors.request.use(
4106
+ (config) => {
4107
+ var _a;
4108
+ if (!config.cancelToken && sourceRef.current && config.method === "get") {
4109
+ config.cancelToken = (_a = sourceRef.current) == null ? void 0 : _a.token;
4110
+ }
4111
+ return config;
4112
+ },
4113
+ (error) => {
4114
+ console.log("[middleware]");
4115
+ return Promise.reject(error);
4116
+ }
4117
+ );
4118
+ try {
4119
+ const response = yield fn(...params);
4120
+ return response;
4121
+ } catch (error) {
4122
+ errorHandler(error);
4123
+ } finally {
4124
+ setLoading(LOADING_NAME, true);
4125
+ }
4126
+ });
4127
+ }
4128
+ function errorHandler(error, callback) {
4129
+ if ((error == null ? void 0 : error.message) === "cancel.navigation")
4130
+ return;
4131
+ if (callback) {
4132
+ if (error.response.data.code === "invalid.body") {
4133
+ const errors = error.response.data.details.issues;
4134
+ const currentErrors = errors.reduce((acc, item) => {
4135
+ acc[item.path.join(".")] = item.message;
4136
+ return acc;
4137
+ }, {});
4138
+ callback(currentErrors);
4139
+ }
4140
+ }
4141
+ createAlert(formatErrorMessage(error), "error");
4142
+ }
4143
+ useEffect5(() => {
4144
+ return () => {
4145
+ var _a;
4146
+ (_a = sourceRef.current) == null ? void 0 : _a.cancel("cancel.navigation");
4147
+ };
4148
+ }, []);
4149
+ return __spreadProps(__spreadValues(__spreadValues({}, alertProps), loadingProps), {
4150
+ onSubmitWrapper,
4151
+ onRequestWrapper
4152
+ });
4153
+ }
4154
+
4155
+ // src/hooks/useGrid.ts
4156
+ import { useMemo as useMemo3, useState as useState6 } from "react";
4157
+
4158
+ // src/hooks/useFilter.ts
4159
+ import moment2 from "moment";
4160
+ import { useState as useState5 } from "react";
3820
4161
 
3821
4162
  // src/components/utils/getObjectValue.ts
3822
4163
  function getObjectValue(obj) {
3823
4164
  return (prop) => prop.split(".").reduce((o, k) => o[k], obj);
3824
4165
  }
3825
4166
 
3826
- // src/components/hooks/useFilter.ts
3827
- import moment2 from "moment";
3828
- import { useState as useState3 } from "react";
4167
+ // src/hooks/useFilter.ts
3829
4168
  function useFilter() {
3830
- const [selectedFilters, setSelectedFilters] = useState3([]);
4169
+ const [selectedFilters, setSelectedFilters] = useState5([]);
3831
4170
  const filterBy = (newFilter) => {
3832
4171
  const propToCompare = newFilter.id ? "id" : "prop";
3833
4172
  function removeRepeatedFilters(filter) {
@@ -3897,18 +4236,18 @@ function createFilter(filters) {
3897
4236
  };
3898
4237
  }
3899
4238
 
3900
- // src/components/hooks/useGrid.ts
4239
+ // src/hooks/useGrid.ts
3901
4240
  function useGrid({
3902
4241
  columns,
3903
4242
  filters = [],
3904
4243
  search,
3905
4244
  rowsPerPageOptions = [30, 60, 100]
3906
4245
  }) {
3907
- const [defaultData, setDefaultData] = useState4([]);
3908
- const [sortedBy, setSortedBy] = useState4("");
3909
- const [sortedDirection, setSortedDirection] = useState4("desc");
3910
- const [currentPage, setCurrentPage] = useState4(0);
3911
- const [rowsPerPage, setRowsPerPage] = useState4(rowsPerPageOptions[0]);
4246
+ const [defaultData, setDefaultData] = useState6([]);
4247
+ const [sortedBy, setSortedBy] = useState6("");
4248
+ const [sortedDirection, setSortedDirection] = useState6("desc");
4249
+ const [currentPage, setCurrentPage] = useState6(0);
4250
+ const [rowsPerPage, setRowsPerPage] = useState6(rowsPerPageOptions[0]);
3912
4251
  const toggleSortedDirection = () => {
3913
4252
  if (sortedDirection === "desc")
3914
4253
  setSortedDirection("asc");
@@ -4030,108 +4369,20 @@ function createSearch(options) {
4030
4369
  };
4031
4370
  }
4032
4371
 
4033
- // src/components/hooks/useEvent.ts
4034
- import { useEffect as useEffect5 } from "react";
4372
+ // src/hooks/useEvent.ts
4373
+ import { useEffect as useEffect6 } from "react";
4035
4374
  function useEvent(event, handler, passive = false) {
4036
- useEffect5(() => {
4375
+ useEffect6(() => {
4037
4376
  window.addEventListener(event, handler, passive);
4038
4377
  return function cleanup() {
4039
4378
  window.removeEventListener(event, handler);
4040
4379
  };
4041
4380
  });
4042
4381
  }
4043
-
4044
- // src/components/hooks/useLoading.ts
4045
- import { useState as useState5 } from "react";
4046
- function useLoading() {
4047
- const [state, setState] = useState5([]);
4048
- const isLoading = (prop) => state.includes(prop);
4049
- const setLoading = (prop, remove) => {
4050
- if (remove)
4051
- setState((prevState) => prevState.filter((state2) => state2 !== prop));
4052
- else
4053
- setState((prevState) => [...prevState, prop]);
4054
- };
4055
- return { isLoading, setLoading };
4056
- }
4057
-
4058
- // src/components/Modal/index.tsx
4059
- import React25 from "react";
4060
- import {
4061
- Box as Box4,
4062
- Modal as MuiModal
4063
- } from "@mui/material";
4064
- var Modal = (_a) => {
4065
- var _b = _a, { open, onClose } = _b, rest = __objRest(_b, ["open", "onClose"]);
4066
- return /* @__PURE__ */ React25.createElement(MuiModal, __spreadValues({ open, onClose, disableEnforceFocus: true }, rest), /* @__PURE__ */ React25.createElement(
4067
- Box4,
4068
- {
4069
- sx: {
4070
- outline: "none",
4071
- backgroundColor: "white",
4072
- position: "absolute",
4073
- top: "50%",
4074
- left: "50%",
4075
- transform: "translate(-50%, -50%)",
4076
- borderRadius: 1
4077
- }
4078
- },
4079
- /* @__PURE__ */ React25.createElement(React25.Fragment, null, rest.children)
4080
- ));
4081
- };
4082
-
4083
- // src/components/utils/GetInputLabel.ts
4084
- function GetInputLabel(columns) {
4085
- return (columnName) => {
4086
- const column = columns.find((column2) => column2.name === columnName);
4087
- return { label: column.label, name: column.name };
4088
- };
4089
- }
4090
-
4091
- // src/components/Dialog/index.tsx
4092
- import React26 from "react";
4093
- import {
4094
- Box as Box5,
4095
- Dialog as DefaultDialog,
4096
- DialogContentText,
4097
- DialogActions,
4098
- DialogTitle,
4099
- Button as Button3,
4100
- CircularProgress as CircularProgress2
4101
- } from "@mui/material";
4102
- var Dialog = (_a) => {
4103
- var _b = _a, {
4104
- open,
4105
- title,
4106
- loading,
4107
- body,
4108
- options
4109
- } = _b, rest = __objRest(_b, [
4110
- "open",
4111
- "title",
4112
- "loading",
4113
- "body",
4114
- "options"
4115
- ]);
4116
- return /* @__PURE__ */ React26.createElement(DefaultDialog, __spreadValues({ open }, rest), /* @__PURE__ */ React26.createElement(Box5, { sx: { p: 2 } }, /* @__PURE__ */ React26.createElement(DialogTitle, { sx: { fontWeight: "bold" } }, title), /* @__PURE__ */ React26.createElement(DialogContentText, { sx: { px: "10px", textAlign: "center", mb: 2 } }, body), /* @__PURE__ */ React26.createElement(DialogActions, null, options.map((option, index) => {
4117
- return /* @__PURE__ */ React26.createElement(
4118
- Button3,
4119
- {
4120
- key: index,
4121
- onClick: () => option.cb(option.label),
4122
- variant: option.focus ? "contained" : "text",
4123
- sx: {
4124
- fontWeight: option.focus ? "bold" : "normal",
4125
- color: option.focus ? "#fff" : "primary.main"
4126
- },
4127
- disableElevation: true,
4128
- disabled: loading
4129
- },
4130
- loading && option.focus ? /* @__PURE__ */ React26.createElement(CircularProgress2, { size: 25, color: "inherit" }) : /* @__PURE__ */ React26.createElement(React26.Fragment, null, option.label)
4131
- );
4132
- }))));
4133
- };
4134
4382
  export {
4383
+ AlertContext,
4384
+ AlertProvider,
4385
+ ApiHelper,
4135
4386
  Autocomplete2 as Autocomplete,
4136
4387
  BaseGrid,
4137
4388
  Checkbox,
@@ -4139,6 +4390,7 @@ export {
4139
4390
  EditableTableCell,
4140
4391
  GetInputLabel,
4141
4392
  Grid_default as Grid,
4393
+ HttpError,
4142
4394
  Input,
4143
4395
  InputMask2 as InputMask,
4144
4396
  LargeButton,
@@ -4152,8 +4404,10 @@ export {
4152
4404
  createFilter,
4153
4405
  filterData,
4154
4406
  getTabProps,
4407
+ useAlert,
4155
4408
  useEvent,
4156
4409
  useFilter,
4410
+ useFormHelper,
4157
4411
  useGrid,
4158
4412
  useLoading
4159
4413
  };