medusa-shiprocket-fulfillment-sbl 0.0.1
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 +105 -0
- package/.medusa/server/src/admin/index.mjs +106 -0
- package/.medusa/server/src/jobs/refresh-shiprocket-token.js +32 -0
- package/.medusa/server/src/providers/shiprocket/client/handle-error.js +27 -0
- package/.medusa/server/src/providers/shiprocket/client/index.js +327 -0
- package/.medusa/server/src/providers/shiprocket/client/methods/authenticate.js +38 -0
- package/.medusa/server/src/providers/shiprocket/client/types/index.js +3 -0
- package/.medusa/server/src/providers/shiprocket/index.js +8 -0
- package/.medusa/server/src/providers/shiprocket/service.js +246 -0
- package/.medusa/server/src/providers/shiprocket/types/index.js +3 -0
- package/.medusa/server/src/providers/shiprocket/utils/index.js +25 -0
- package/README.md +183 -0
- package/package.json +85 -0
|
@@ -0,0 +1,105 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
const jsxRuntime = require("react/jsx-runtime");
|
|
3
|
+
const adminSdk = require("@medusajs/admin-sdk");
|
|
4
|
+
const ui = require("@medusajs/ui");
|
|
5
|
+
const ShiprocketTrackingWidget = ({ data: order }) => {
|
|
6
|
+
var _a;
|
|
7
|
+
if (!(order == null ? void 0 : order.id) || !(order == null ? void 0 : order.fulfillments)) return null;
|
|
8
|
+
const activeShipments = (_a = order.fulfillments) == null ? void 0 : _a.filter(
|
|
9
|
+
(f) => {
|
|
10
|
+
var _a2;
|
|
11
|
+
return !f.canceled_at && f.data.awb && f.data.shipment_id && ((_a2 = f.provider) == null ? void 0 : _a2.id) === "shiprocket_shiprocket";
|
|
12
|
+
}
|
|
13
|
+
);
|
|
14
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(ui.Container, { className: "p-6 rounded-lg shadow-lg border border-neutral-700", children: [
|
|
15
|
+
/* @__PURE__ */ jsxRuntime.jsx("header", { className: "mb-6", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Heading, { level: "h2", className: "font-semibold text-lg text-white", children: "Shiprocket Printables" }) }),
|
|
16
|
+
(activeShipments == null ? void 0 : activeShipments.length) === 0 ? /* @__PURE__ */ jsxRuntime.jsx(ui.Text, { className: "text-sm italic text-gray-400", children: "No active shipments" }) : /* @__PURE__ */ jsxRuntime.jsx("ul", { className: "space-y-6", children: activeShipments.map((fulfillment) => {
|
|
17
|
+
var _a2, _b, _c, _d, _e, _f, _g;
|
|
18
|
+
return /* @__PURE__ */ jsxRuntime.jsxs(
|
|
19
|
+
"li",
|
|
20
|
+
{
|
|
21
|
+
className: "bg-neutral-900/10 rounded-xl shadow-none p-5 flex flex-col gap-4 border border-neutral-900/10",
|
|
22
|
+
children: [
|
|
23
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex justify-between items-center", children: [
|
|
24
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Text, { className: "text-sm text-gray-300 font-normal", children: [
|
|
25
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: "text-xs font-normal text-white", children: "Shipment ID:" }),
|
|
26
|
+
" ",
|
|
27
|
+
((_a2 = fulfillment.data) == null ? void 0 : _a2.shipment_id) || "No AWB found"
|
|
28
|
+
] }),
|
|
29
|
+
/* @__PURE__ */ jsxRuntime.jsx("span", { className: `
|
|
30
|
+
px-2 py-1 rounded-lg shadow-none text-[9px] font-semibold uppercase select-none
|
|
31
|
+
${fulfillment.status === "delivered" ? "bg-green-500 text-black" : fulfillment.status === "pending" ? "bg-yellow-400 text-black" : "bg-red-700 text-white"}
|
|
32
|
+
min-w-[4.5rem] text-center`, children: fulfillment.status || "Cancelled" })
|
|
33
|
+
] }),
|
|
34
|
+
JSON.stringify(fulfillment, null, 2),
|
|
35
|
+
/* @__PURE__ */ jsxRuntime.jsxs("div", { className: "flex justify-center items-center gap-3 mt-4", children: [
|
|
36
|
+
((_b = fulfillment.labels) == null ? void 0 : _b.label_url) && /* @__PURE__ */ jsxRuntime.jsx(
|
|
37
|
+
"a",
|
|
38
|
+
{
|
|
39
|
+
href: `${(_c = fulfillment.labels) == null ? void 0 : _c.label_url}`,
|
|
40
|
+
target: "_blank",
|
|
41
|
+
rel: "noopener noreferrer",
|
|
42
|
+
className: "flex-1 px-4 py-1 text-xs bg-neutral-900/60 font-medium hover:bg-neutral-900/90 rounded-lg transition-colors text-center",
|
|
43
|
+
"aria-disabled": "false",
|
|
44
|
+
children: "Label"
|
|
45
|
+
}
|
|
46
|
+
),
|
|
47
|
+
((_d = fulfillment.labels) == null ? void 0 : _d.manifest_url) && /* @__PURE__ */ jsxRuntime.jsx(
|
|
48
|
+
"a",
|
|
49
|
+
{
|
|
50
|
+
href: `${(_e = fulfillment.labels) == null ? void 0 : _e.manifest_url}`,
|
|
51
|
+
target: "_blank",
|
|
52
|
+
rel: "noopener noreferrer",
|
|
53
|
+
className: "flex-1 px-4 py-1 text-xs bg-neutral-900/60 font-medium hover:bg-neutral-900/90 rounded-lg transition-colors text-center",
|
|
54
|
+
"aria-disabled": "false",
|
|
55
|
+
children: "Manifest"
|
|
56
|
+
}
|
|
57
|
+
),
|
|
58
|
+
((_f = fulfillment.labels) == null ? void 0 : _f.invoice_url) && /* @__PURE__ */ jsxRuntime.jsx(
|
|
59
|
+
"a",
|
|
60
|
+
{
|
|
61
|
+
href: `${(_g = fulfillment.labels) == null ? void 0 : _g.invoice_url}`,
|
|
62
|
+
target: "_blank",
|
|
63
|
+
rel: "noopener noreferrer",
|
|
64
|
+
className: "flex-1 px-4 py-1 text-xs bg-neutral-900/60 font-medium hover:bg-neutral-900/90 rounded-lg transition-colors text-center",
|
|
65
|
+
"aria-disabled": "false",
|
|
66
|
+
children: "Invoice"
|
|
67
|
+
}
|
|
68
|
+
)
|
|
69
|
+
] })
|
|
70
|
+
]
|
|
71
|
+
},
|
|
72
|
+
fulfillment.id
|
|
73
|
+
);
|
|
74
|
+
}) })
|
|
75
|
+
] });
|
|
76
|
+
};
|
|
77
|
+
adminSdk.defineWidgetConfig({
|
|
78
|
+
zone: "order.details.side.after"
|
|
79
|
+
});
|
|
80
|
+
const widgetModule = { widgets: [
|
|
81
|
+
{
|
|
82
|
+
Component: ShiprocketTrackingWidget,
|
|
83
|
+
zone: ["order.details.side.after"]
|
|
84
|
+
}
|
|
85
|
+
] };
|
|
86
|
+
const routeModule = {
|
|
87
|
+
routes: []
|
|
88
|
+
};
|
|
89
|
+
const menuItemModule = {
|
|
90
|
+
menuItems: []
|
|
91
|
+
};
|
|
92
|
+
const formModule = { customFields: {} };
|
|
93
|
+
const displayModule = {
|
|
94
|
+
displays: {}
|
|
95
|
+
};
|
|
96
|
+
const i18nModule = { resources: {} };
|
|
97
|
+
const plugin = {
|
|
98
|
+
widgetModule,
|
|
99
|
+
routeModule,
|
|
100
|
+
menuItemModule,
|
|
101
|
+
formModule,
|
|
102
|
+
displayModule,
|
|
103
|
+
i18nModule
|
|
104
|
+
};
|
|
105
|
+
module.exports = plugin;
|
|
@@ -0,0 +1,106 @@
|
|
|
1
|
+
import { jsxs, jsx } from "react/jsx-runtime";
|
|
2
|
+
import { defineWidgetConfig } from "@medusajs/admin-sdk";
|
|
3
|
+
import { Container, Heading, Text } from "@medusajs/ui";
|
|
4
|
+
const ShiprocketTrackingWidget = ({ data: order }) => {
|
|
5
|
+
var _a;
|
|
6
|
+
if (!(order == null ? void 0 : order.id) || !(order == null ? void 0 : order.fulfillments)) return null;
|
|
7
|
+
const activeShipments = (_a = order.fulfillments) == null ? void 0 : _a.filter(
|
|
8
|
+
(f) => {
|
|
9
|
+
var _a2;
|
|
10
|
+
return !f.canceled_at && f.data.awb && f.data.shipment_id && ((_a2 = f.provider) == null ? void 0 : _a2.id) === "shiprocket_shiprocket";
|
|
11
|
+
}
|
|
12
|
+
);
|
|
13
|
+
return /* @__PURE__ */ jsxs(Container, { className: "p-6 rounded-lg shadow-lg border border-neutral-700", children: [
|
|
14
|
+
/* @__PURE__ */ jsx("header", { className: "mb-6", children: /* @__PURE__ */ jsx(Heading, { level: "h2", className: "font-semibold text-lg text-white", children: "Shiprocket Printables" }) }),
|
|
15
|
+
(activeShipments == null ? void 0 : activeShipments.length) === 0 ? /* @__PURE__ */ jsx(Text, { className: "text-sm italic text-gray-400", children: "No active shipments" }) : /* @__PURE__ */ jsx("ul", { className: "space-y-6", children: activeShipments.map((fulfillment) => {
|
|
16
|
+
var _a2, _b, _c, _d, _e, _f, _g;
|
|
17
|
+
return /* @__PURE__ */ jsxs(
|
|
18
|
+
"li",
|
|
19
|
+
{
|
|
20
|
+
className: "bg-neutral-900/10 rounded-xl shadow-none p-5 flex flex-col gap-4 border border-neutral-900/10",
|
|
21
|
+
children: [
|
|
22
|
+
/* @__PURE__ */ jsxs("div", { className: "flex justify-between items-center", children: [
|
|
23
|
+
/* @__PURE__ */ jsxs(Text, { className: "text-sm text-gray-300 font-normal", children: [
|
|
24
|
+
/* @__PURE__ */ jsx("span", { className: "text-xs font-normal text-white", children: "Shipment ID:" }),
|
|
25
|
+
" ",
|
|
26
|
+
((_a2 = fulfillment.data) == null ? void 0 : _a2.shipment_id) || "No AWB found"
|
|
27
|
+
] }),
|
|
28
|
+
/* @__PURE__ */ jsx("span", { className: `
|
|
29
|
+
px-2 py-1 rounded-lg shadow-none text-[9px] font-semibold uppercase select-none
|
|
30
|
+
${fulfillment.status === "delivered" ? "bg-green-500 text-black" : fulfillment.status === "pending" ? "bg-yellow-400 text-black" : "bg-red-700 text-white"}
|
|
31
|
+
min-w-[4.5rem] text-center`, children: fulfillment.status || "Cancelled" })
|
|
32
|
+
] }),
|
|
33
|
+
JSON.stringify(fulfillment, null, 2),
|
|
34
|
+
/* @__PURE__ */ jsxs("div", { className: "flex justify-center items-center gap-3 mt-4", children: [
|
|
35
|
+
((_b = fulfillment.labels) == null ? void 0 : _b.label_url) && /* @__PURE__ */ jsx(
|
|
36
|
+
"a",
|
|
37
|
+
{
|
|
38
|
+
href: `${(_c = fulfillment.labels) == null ? void 0 : _c.label_url}`,
|
|
39
|
+
target: "_blank",
|
|
40
|
+
rel: "noopener noreferrer",
|
|
41
|
+
className: "flex-1 px-4 py-1 text-xs bg-neutral-900/60 font-medium hover:bg-neutral-900/90 rounded-lg transition-colors text-center",
|
|
42
|
+
"aria-disabled": "false",
|
|
43
|
+
children: "Label"
|
|
44
|
+
}
|
|
45
|
+
),
|
|
46
|
+
((_d = fulfillment.labels) == null ? void 0 : _d.manifest_url) && /* @__PURE__ */ jsx(
|
|
47
|
+
"a",
|
|
48
|
+
{
|
|
49
|
+
href: `${(_e = fulfillment.labels) == null ? void 0 : _e.manifest_url}`,
|
|
50
|
+
target: "_blank",
|
|
51
|
+
rel: "noopener noreferrer",
|
|
52
|
+
className: "flex-1 px-4 py-1 text-xs bg-neutral-900/60 font-medium hover:bg-neutral-900/90 rounded-lg transition-colors text-center",
|
|
53
|
+
"aria-disabled": "false",
|
|
54
|
+
children: "Manifest"
|
|
55
|
+
}
|
|
56
|
+
),
|
|
57
|
+
((_f = fulfillment.labels) == null ? void 0 : _f.invoice_url) && /* @__PURE__ */ jsx(
|
|
58
|
+
"a",
|
|
59
|
+
{
|
|
60
|
+
href: `${(_g = fulfillment.labels) == null ? void 0 : _g.invoice_url}`,
|
|
61
|
+
target: "_blank",
|
|
62
|
+
rel: "noopener noreferrer",
|
|
63
|
+
className: "flex-1 px-4 py-1 text-xs bg-neutral-900/60 font-medium hover:bg-neutral-900/90 rounded-lg transition-colors text-center",
|
|
64
|
+
"aria-disabled": "false",
|
|
65
|
+
children: "Invoice"
|
|
66
|
+
}
|
|
67
|
+
)
|
|
68
|
+
] })
|
|
69
|
+
]
|
|
70
|
+
},
|
|
71
|
+
fulfillment.id
|
|
72
|
+
);
|
|
73
|
+
}) })
|
|
74
|
+
] });
|
|
75
|
+
};
|
|
76
|
+
defineWidgetConfig({
|
|
77
|
+
zone: "order.details.side.after"
|
|
78
|
+
});
|
|
79
|
+
const widgetModule = { widgets: [
|
|
80
|
+
{
|
|
81
|
+
Component: ShiprocketTrackingWidget,
|
|
82
|
+
zone: ["order.details.side.after"]
|
|
83
|
+
}
|
|
84
|
+
] };
|
|
85
|
+
const routeModule = {
|
|
86
|
+
routes: []
|
|
87
|
+
};
|
|
88
|
+
const menuItemModule = {
|
|
89
|
+
menuItems: []
|
|
90
|
+
};
|
|
91
|
+
const formModule = { customFields: {} };
|
|
92
|
+
const displayModule = {
|
|
93
|
+
displays: {}
|
|
94
|
+
};
|
|
95
|
+
const i18nModule = { resources: {} };
|
|
96
|
+
const plugin = {
|
|
97
|
+
widgetModule,
|
|
98
|
+
routeModule,
|
|
99
|
+
menuItemModule,
|
|
100
|
+
formModule,
|
|
101
|
+
displayModule,
|
|
102
|
+
i18nModule
|
|
103
|
+
};
|
|
104
|
+
export {
|
|
105
|
+
plugin as default
|
|
106
|
+
};
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.config = void 0;
|
|
7
|
+
exports.default = refreshShiprocketTokenJob;
|
|
8
|
+
const client_1 = __importDefault(require("../providers/shiprocket/client"));
|
|
9
|
+
async function refreshShiprocketTokenJob(container) {
|
|
10
|
+
const options = {
|
|
11
|
+
email: process.env.SHIPROCKET_EMAIL,
|
|
12
|
+
password: process.env.SHIPROCKET_PASSWORD,
|
|
13
|
+
};
|
|
14
|
+
const client = new client_1.default(options);
|
|
15
|
+
try {
|
|
16
|
+
await client["ensureAuthenticated"]?.();
|
|
17
|
+
// Optionally, log or store the refreshed token somewhere if needed
|
|
18
|
+
container.resolve("logger").info("Shiprocket token refreshed");
|
|
19
|
+
}
|
|
20
|
+
catch (err) {
|
|
21
|
+
// Optionally, log error
|
|
22
|
+
container.resolve("logger").error("Failed to refresh Shiprocket token", err);
|
|
23
|
+
}
|
|
24
|
+
finally {
|
|
25
|
+
client.dispose();
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
exports.config = {
|
|
29
|
+
name: "refresh-shiprocket-token",
|
|
30
|
+
schedule: "0 0 */8 * *", // every 8 days at 00:00
|
|
31
|
+
};
|
|
32
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoicmVmcmVzaC1zaGlwcm9ja2V0LXRva2VuLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vc3JjL2pvYnMvcmVmcmVzaC1zaGlwcm9ja2V0LXRva2VuLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7OztBQUlBLDRDQWdCQztBQWxCRCw0RUFBNkQ7QUFFOUMsS0FBSyxVQUFVLHlCQUF5QixDQUFDLFNBQTBCO0lBQzlFLE1BQU0sT0FBTyxHQUE0QjtRQUNyQyxLQUFLLEVBQUUsT0FBTyxDQUFDLEdBQUcsQ0FBQyxnQkFBaUI7UUFDcEMsUUFBUSxFQUFFLE9BQU8sQ0FBQyxHQUFHLENBQUMsbUJBQW9CO0tBQzdDLENBQUE7SUFDRCxNQUFNLE1BQU0sR0FBRyxJQUFJLGdCQUFnQixDQUFDLE9BQU8sQ0FBQyxDQUFBO0lBQzVDLElBQUksQ0FBQztRQUNELE1BQU0sTUFBTSxDQUFDLHFCQUFxQixDQUFDLEVBQUUsRUFBRSxDQUFBO1FBQ3ZDLG1FQUFtRTtRQUNuRSxTQUFTLENBQUMsT0FBTyxDQUFDLFFBQVEsQ0FBQyxDQUFDLElBQUksQ0FBQyw0QkFBNEIsQ0FBQyxDQUFBO0lBQ2xFLENBQUM7SUFBQyxPQUFPLEdBQUcsRUFBRSxDQUFDO1FBQ1gsd0JBQXdCO1FBQ3hCLFNBQVMsQ0FBQyxPQUFPLENBQUMsUUFBUSxDQUFDLENBQUMsS0FBSyxDQUFDLG9DQUFvQyxFQUFFLEdBQUcsQ0FBQyxDQUFBO0lBQ2hGLENBQUM7WUFBUyxDQUFDO1FBQ1AsTUFBTSxDQUFDLE9BQU8sRUFBRSxDQUFBO0lBQ3BCLENBQUM7QUFDTCxDQUFDO0FBRVksUUFBQSxNQUFNLEdBQUc7SUFDbEIsSUFBSSxFQUFFLDBCQUEwQjtJQUNoQyxRQUFRLEVBQUUsYUFBYSxFQUFFLHdCQUF3QjtDQUNwRCxDQUFBIn0=
|
|
@@ -0,0 +1,27 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.handleError = void 0;
|
|
4
|
+
const utils_1 = require("@medusajs/framework/utils");
|
|
5
|
+
const handleError = (error) => {
|
|
6
|
+
const message = error.response?.data?.message || error.message;
|
|
7
|
+
const code = error.response?.status || 500;
|
|
8
|
+
if (code === 401) {
|
|
9
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.UNAUTHORIZED, "Authentication failed with Shiprocket");
|
|
10
|
+
}
|
|
11
|
+
if (code === 429) {
|
|
12
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, "Rate limit exceeded. Please try again later.");
|
|
13
|
+
}
|
|
14
|
+
if (code === 400 && error.response?.data?.errors) {
|
|
15
|
+
const validationErrors = Object.entries(error.response.data.errors)
|
|
16
|
+
.map(([field, msgs]) => `${field}: ${Array.isArray(msgs) ? msgs.join(", ") : msgs}`)
|
|
17
|
+
.join("; ");
|
|
18
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, `Validation failed: ${validationErrors}`);
|
|
19
|
+
}
|
|
20
|
+
throw new utils_1.MedusaError(code === 404
|
|
21
|
+
? utils_1.MedusaError.Types.NOT_FOUND
|
|
22
|
+
: code === 400
|
|
23
|
+
? utils_1.MedusaError.Types.INVALID_DATA
|
|
24
|
+
: utils_1.MedusaError.Types.UNEXPECTED_STATE, message);
|
|
25
|
+
};
|
|
26
|
+
exports.handleError = handleError;
|
|
27
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaGFuZGxlLWVycm9yLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vc3JjL3Byb3ZpZGVycy9zaGlwcm9ja2V0L2NsaWVudC9oYW5kbGUtZXJyb3IudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7O0FBQUEscURBQXVEO0FBR2hELE1BQU0sV0FBVyxHQUFHLENBQUMsS0FBa0MsRUFBUyxFQUFFO0lBQ3JFLE1BQU0sT0FBTyxHQUFHLEtBQUssQ0FBQyxRQUFRLEVBQUUsSUFBSSxFQUFFLE9BQU8sSUFBSSxLQUFLLENBQUMsT0FBTyxDQUFBO0lBQzlELE1BQU0sSUFBSSxHQUFHLEtBQUssQ0FBQyxRQUFRLEVBQUUsTUFBTSxJQUFJLEdBQUcsQ0FBQTtJQUUxQyxJQUFJLElBQUksS0FBSyxHQUFHLEVBQUUsQ0FBQztRQUNmLE1BQU0sSUFBSSxtQkFBVyxDQUNqQixtQkFBVyxDQUFDLEtBQUssQ0FBQyxZQUFZLEVBQzlCLHVDQUF1QyxDQUMxQyxDQUFBO0lBQ0wsQ0FBQztJQUVELElBQUksSUFBSSxLQUFLLEdBQUcsRUFBRSxDQUFDO1FBQ2YsTUFBTSxJQUFJLG1CQUFXLENBQ2pCLG1CQUFXLENBQUMsS0FBSyxDQUFDLFlBQVksRUFDOUIsOENBQThDLENBQ2pELENBQUE7SUFDTCxDQUFDO0lBRUQsSUFBSSxJQUFJLEtBQUssR0FBRyxJQUFJLEtBQUssQ0FBQyxRQUFRLEVBQUUsSUFBSSxFQUFFLE1BQU0sRUFBRSxDQUFDO1FBQy9DLE1BQU0sZ0JBQWdCLEdBQUcsTUFBTSxDQUFDLE9BQU8sQ0FBQyxLQUFLLENBQUMsUUFBUSxDQUFDLElBQUksQ0FBQyxNQUFNLENBQUM7YUFDOUQsR0FBRyxDQUFDLENBQUMsQ0FBQyxLQUFLLEVBQUUsSUFBSSxDQUFDLEVBQUUsRUFBRSxDQUFDLEdBQUcsS0FBSyxLQUFLLEtBQUssQ0FBQyxPQUFPLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FBQyxDQUFDLElBQUksRUFBRSxDQUFDO2FBQ25GLElBQUksQ0FBQyxJQUFJLENBQUMsQ0FBQTtRQUNmLE1BQU0sSUFBSSxtQkFBVyxDQUNqQixtQkFBVyxDQUFDLEtBQUssQ0FBQyxZQUFZLEVBQzlCLHNCQUFzQixnQkFBZ0IsRUFBRSxDQUMzQyxDQUFBO0lBQ0wsQ0FBQztJQUVELE1BQU0sSUFBSSxtQkFBVyxDQUNqQixJQUFJLEtBQUssR0FBRztRQUNSLENBQUMsQ0FBQyxtQkFBVyxDQUFDLEtBQUssQ0FBQyxTQUFTO1FBQzdCLENBQUMsQ0FBQyxJQUFJLEtBQUssR0FBRztZQUNkLENBQUMsQ0FBQyxtQkFBVyxDQUFDLEtBQUssQ0FBQyxZQUFZO1lBQ2hDLENBQUMsQ0FBQyxtQkFBVyxDQUFDLEtBQUssQ0FBQyxnQkFBZ0IsRUFDeEMsT0FBTyxDQUNWLENBQUE7QUFDTCxDQUFDLENBQUE7QUFwQ1ksUUFBQSxXQUFXLGVBb0N2QiJ9
|
|
@@ -0,0 +1,327 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
const axios_1 = __importDefault(require("axios"));
|
|
7
|
+
const utils_1 = require("@medusajs/framework/utils");
|
|
8
|
+
const authenticate_1 = require("./methods/authenticate");
|
|
9
|
+
const handle_error_1 = require("./handle-error");
|
|
10
|
+
class ShiprocketClient {
|
|
11
|
+
constructor(options) {
|
|
12
|
+
this.token = null;
|
|
13
|
+
this.isDisposed = false;
|
|
14
|
+
if (!options.email || !options.password) {
|
|
15
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, "Shiprocket API credentials are required");
|
|
16
|
+
}
|
|
17
|
+
this.email = options.email;
|
|
18
|
+
this.password = options.password;
|
|
19
|
+
this.pickup_location = options.pickup_location;
|
|
20
|
+
this.axios = axios_1.default.create({
|
|
21
|
+
baseURL: "https://apiv2.shiprocket.in/v1/external",
|
|
22
|
+
headers: { "Content-Type": "application/json" },
|
|
23
|
+
timeout: 10000,
|
|
24
|
+
});
|
|
25
|
+
// Interceptor to handle 401 Unauthorized automatically
|
|
26
|
+
this.axios.interceptors.response.use((response) => response, async (error) => {
|
|
27
|
+
const originalRequest = error.config;
|
|
28
|
+
if (error.response?.status === 401 &&
|
|
29
|
+
!originalRequest._retry &&
|
|
30
|
+
!originalRequest.url?.includes("/auth/login")) {
|
|
31
|
+
originalRequest._retry = true;
|
|
32
|
+
try {
|
|
33
|
+
await this.refreshToken();
|
|
34
|
+
originalRequest.headers["Authorization"] = `Bearer ${this.token}`;
|
|
35
|
+
return this.axios(originalRequest);
|
|
36
|
+
}
|
|
37
|
+
catch (refreshError) {
|
|
38
|
+
return Promise.reject(refreshError);
|
|
39
|
+
}
|
|
40
|
+
}
|
|
41
|
+
return Promise.reject(error);
|
|
42
|
+
});
|
|
43
|
+
}
|
|
44
|
+
dispose() {
|
|
45
|
+
this.isDisposed = true;
|
|
46
|
+
this.token = null;
|
|
47
|
+
}
|
|
48
|
+
async refreshToken() {
|
|
49
|
+
if (this.isDisposed)
|
|
50
|
+
return;
|
|
51
|
+
const auth = await (0, authenticate_1.authenticate)(this.axios, this.email, this.password, this.isDisposed);
|
|
52
|
+
this.token = auth.token;
|
|
53
|
+
this.axios.defaults.headers.common["Authorization"] = `Bearer ${this.token}`;
|
|
54
|
+
}
|
|
55
|
+
async ensureToken() {
|
|
56
|
+
if (!this.token) {
|
|
57
|
+
await this.refreshToken();
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
async calculate(data) {
|
|
61
|
+
await this.ensureToken();
|
|
62
|
+
try {
|
|
63
|
+
const response = await this.axios.get("/courier/serviceability/", { params: data });
|
|
64
|
+
const availableCouriers = response.data.data.available_courier_companies;
|
|
65
|
+
if (!availableCouriers?.length) {
|
|
66
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.NOT_FOUND, "No couriers available for this route");
|
|
67
|
+
}
|
|
68
|
+
const filtered = data.allowed_courier_ids?.length
|
|
69
|
+
? availableCouriers.filter((c) => data.allowed_courier_ids.includes(c.id))
|
|
70
|
+
: availableCouriers;
|
|
71
|
+
if (!filtered?.length) {
|
|
72
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.NOT_FOUND, "No allowed couriers available for this route");
|
|
73
|
+
}
|
|
74
|
+
const cheapest = filtered.reduce((min, curr) => Number(curr.rate) < Number(min.rate) ? curr : min);
|
|
75
|
+
return Math.ceil(Number(cheapest?.rate) || 0);
|
|
76
|
+
}
|
|
77
|
+
catch (error) {
|
|
78
|
+
(0, handle_error_1.handleError)(error);
|
|
79
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.UNEXPECTED_STATE, "Rate calculation failed unexpectedly");
|
|
80
|
+
}
|
|
81
|
+
}
|
|
82
|
+
async create(fulfillment, items, order) {
|
|
83
|
+
await this.ensureToken();
|
|
84
|
+
const req = (val, name) => {
|
|
85
|
+
if (val === undefined || val === null || val === "") {
|
|
86
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, `Missing required field: ${name}`);
|
|
87
|
+
}
|
|
88
|
+
return String(val);
|
|
89
|
+
};
|
|
90
|
+
const orderItemMap = new Map();
|
|
91
|
+
if (Array.isArray(order.items)) {
|
|
92
|
+
order.items.forEach((orderItem) => {
|
|
93
|
+
orderItemMap.set(orderItem.id, orderItem);
|
|
94
|
+
});
|
|
95
|
+
}
|
|
96
|
+
let totalWeight = 0;
|
|
97
|
+
let totalLength = 0;
|
|
98
|
+
let totalBreadth = 0;
|
|
99
|
+
let totalHeight = 0;
|
|
100
|
+
try {
|
|
101
|
+
const order_date = new Date(order.created_at)
|
|
102
|
+
.toLocaleString("en-GB", {
|
|
103
|
+
day: "2-digit", month: "2-digit", year: "numeric",
|
|
104
|
+
hour: "2-digit", minute: "2-digit", hour12: false,
|
|
105
|
+
})
|
|
106
|
+
.replace(",", "")
|
|
107
|
+
.replace(/\//g, "-");
|
|
108
|
+
// Calculate totals and dimensions
|
|
109
|
+
items.forEach((item) => {
|
|
110
|
+
const orderItem = orderItemMap.get(item.line_item_id);
|
|
111
|
+
if (!orderItem) {
|
|
112
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, `Order item not found for fulfillment item: ${item.title}`);
|
|
113
|
+
}
|
|
114
|
+
const variant = orderItem.variant;
|
|
115
|
+
if (!variant) {
|
|
116
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, `Variant data missing for item: ${item.title}`);
|
|
117
|
+
}
|
|
118
|
+
const weight = Number(variant.weight || 0) / 1000;
|
|
119
|
+
const length = Number(variant.length || 0);
|
|
120
|
+
const breadth = Number(variant.width || 0);
|
|
121
|
+
const height = Number(variant.height || 0);
|
|
122
|
+
if (!weight || !length || !breadth || !height) {
|
|
123
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, `Missing dimensions/weight for item "${item.title}". Please update product variant settings.`);
|
|
124
|
+
}
|
|
125
|
+
const quantity = Number(item.quantity || item.raw_quantity?.value || 1);
|
|
126
|
+
totalWeight += weight * quantity;
|
|
127
|
+
totalLength = Math.max(totalLength, length);
|
|
128
|
+
totalBreadth = Math.max(totalBreadth, breadth);
|
|
129
|
+
totalHeight += height * quantity;
|
|
130
|
+
});
|
|
131
|
+
const shipping = order.shipping_address || fulfillment?.delivery_address || {};
|
|
132
|
+
const billing = order.billing_address || order.customer || {};
|
|
133
|
+
// Build Order Payload with STRICT validation
|
|
134
|
+
const orderData = {
|
|
135
|
+
order_id: `${order.id}-${Math.floor(Date.now() / 1000)}`, // Safer randomness
|
|
136
|
+
order_date,
|
|
137
|
+
pickup_location: this.pickup_location || "Primary",
|
|
138
|
+
billing_customer_name: req(billing.first_name, "Billing First Name"),
|
|
139
|
+
billing_last_name: billing.last_name || "",
|
|
140
|
+
billing_address: req(shipping.address_1 || billing.address_1, "Billing Address 1"),
|
|
141
|
+
billing_address_2: shipping.address_2 || billing.address_2 || "",
|
|
142
|
+
billing_city: req(shipping.city || billing.city, "Billing City"),
|
|
143
|
+
billing_pincode: Number(req(shipping.postal_code || billing.postal_code, "Billing Pincode")),
|
|
144
|
+
billing_state: req(shipping.province || billing.province, "Billing State"),
|
|
145
|
+
billing_country: req(shipping.country_code || billing.country_code || "IN", "Billing Country"),
|
|
146
|
+
billing_email: req(billing.email || order.email, "Billing Email"),
|
|
147
|
+
billing_phone: Number(req(shipping.phone || billing.phone, "Billing Phone").toString().replace(/[^0-9]/g, "")),
|
|
148
|
+
shipping_is_billing: true,
|
|
149
|
+
shipping_customer_name: req(shipping.first_name, "Shipping First Name"),
|
|
150
|
+
shipping_last_name: shipping.last_name || "",
|
|
151
|
+
shipping_address: req(shipping.address_1, "Shipping Address 1"),
|
|
152
|
+
shipping_address_2: shipping.address_2 || "",
|
|
153
|
+
shipping_city: req(shipping.city, "Shipping City"),
|
|
154
|
+
shipping_pincode: Number(req(shipping.postal_code, "Shipping Pincode")),
|
|
155
|
+
shipping_country: req(shipping.country_code || "IN", "Shipping Country"),
|
|
156
|
+
shipping_state: req(shipping.province, "Shipping State"),
|
|
157
|
+
shipping_email: req(billing.email || order.email, "Shipping Email"),
|
|
158
|
+
shipping_phone: Number(req(shipping.phone, "Shipping Phone").toString().replace(/[^0-9]/g, "")),
|
|
159
|
+
order_items: items.map((item) => {
|
|
160
|
+
const orderItem = orderItemMap.get(item.line_item_id);
|
|
161
|
+
const variant = orderItem.variant;
|
|
162
|
+
const selling_price = Math.round(Number(orderItem.unit_price || orderItem.detail?.unit_price || 0));
|
|
163
|
+
return {
|
|
164
|
+
name: item.title,
|
|
165
|
+
sku: variant.sku || orderItem.variant_sku || item.sku || item.id,
|
|
166
|
+
units: Number(item.quantity || item.raw_quantity?.value || 1),
|
|
167
|
+
selling_price,
|
|
168
|
+
discount: "",
|
|
169
|
+
tax: "",
|
|
170
|
+
hsn: Number(variant.hs_code || 0),
|
|
171
|
+
};
|
|
172
|
+
}),
|
|
173
|
+
payment_method: "Prepaid",
|
|
174
|
+
sub_total: items.reduce((sum, item) => {
|
|
175
|
+
const orderItem = orderItemMap.get(item.line_item_id);
|
|
176
|
+
const price = Number(orderItem.unit_price || orderItem.detail?.unit_price || 0);
|
|
177
|
+
const qty = Number(item.quantity || item.raw_quantity?.value || 1);
|
|
178
|
+
return sum + (price * qty);
|
|
179
|
+
}, 0),
|
|
180
|
+
length: totalLength,
|
|
181
|
+
breadth: totalBreadth,
|
|
182
|
+
height: totalHeight,
|
|
183
|
+
weight: totalWeight,
|
|
184
|
+
};
|
|
185
|
+
const orderCreated = await this.axios
|
|
186
|
+
.post("/orders/create/adhoc", orderData)
|
|
187
|
+
.catch((err) => {
|
|
188
|
+
// Extract deep error message if available
|
|
189
|
+
const apiError = err;
|
|
190
|
+
const firstError = apiError.response?.data?.errors
|
|
191
|
+
? Object.values(apiError.response.data.errors)[0][0]
|
|
192
|
+
: err.message;
|
|
193
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, `Shiprocket Error: ${firstError}`);
|
|
194
|
+
});
|
|
195
|
+
if (!orderCreated.data?.shipment_id) {
|
|
196
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, "Failed to create Shiprocket order: No shipment ID returned");
|
|
197
|
+
}
|
|
198
|
+
// Assign AWB
|
|
199
|
+
const awbCreated = await this.axios.post(`/courier/assign/awb`, {
|
|
200
|
+
shipment_id: orderCreated.data.shipment_id,
|
|
201
|
+
});
|
|
202
|
+
if (awbCreated.data.awb_assign_status !== 1) {
|
|
203
|
+
// Try to cancel if AWB fails to avoid stuck orders
|
|
204
|
+
try {
|
|
205
|
+
await this.cancel(orderCreated.data.order_id);
|
|
206
|
+
}
|
|
207
|
+
catch (e) { /* ignore */ }
|
|
208
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.NOT_ALLOWED, awbCreated.data.message || "AWB assignment failed");
|
|
209
|
+
}
|
|
210
|
+
const responseData = awbCreated.data.response.data;
|
|
211
|
+
return {
|
|
212
|
+
...orderCreated.data,
|
|
213
|
+
awb: responseData.awb_code,
|
|
214
|
+
courier_company_id: responseData.courier_company_id,
|
|
215
|
+
courier_name: responseData.courier_name || orderCreated.data.courier_name,
|
|
216
|
+
tracking_number: responseData.awb_code,
|
|
217
|
+
tracking_url: `https://shiprocket.co/tracking/${responseData.awb_code}`,
|
|
218
|
+
};
|
|
219
|
+
}
|
|
220
|
+
catch (error) {
|
|
221
|
+
(0, handle_error_1.handleError)(error);
|
|
222
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.UNEXPECTED_STATE, "Order creation failed");
|
|
223
|
+
}
|
|
224
|
+
}
|
|
225
|
+
async cancel(orderId) {
|
|
226
|
+
await this.ensureToken();
|
|
227
|
+
try {
|
|
228
|
+
await this.axios.post(`/orders/cancel`, { ids: [orderId] });
|
|
229
|
+
}
|
|
230
|
+
catch (error) {
|
|
231
|
+
// handleError expects AxiosError, but we'll let it handle the error appropriately
|
|
232
|
+
if (error && typeof error === 'object' && 'response' in error) {
|
|
233
|
+
(0, handle_error_1.handleError)(error);
|
|
234
|
+
}
|
|
235
|
+
}
|
|
236
|
+
}
|
|
237
|
+
async getTrackingInfo(trackingNumber) {
|
|
238
|
+
await this.ensureToken();
|
|
239
|
+
try {
|
|
240
|
+
const response = await this.axios.get(`/courier/track/awb/${trackingNumber}`);
|
|
241
|
+
return response.data;
|
|
242
|
+
}
|
|
243
|
+
catch (error) {
|
|
244
|
+
(0, handle_error_1.handleError)(error);
|
|
245
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.UNEXPECTED_STATE, "Tracking failed");
|
|
246
|
+
}
|
|
247
|
+
}
|
|
248
|
+
async createReturn(fulfillment) {
|
|
249
|
+
await this.ensureToken();
|
|
250
|
+
// Implementation of Return Order
|
|
251
|
+
// Note: Shiprocket Return API requires specific fields.
|
|
252
|
+
// We assume 'fulfillment' contains necessary return details linked to the original order.
|
|
253
|
+
const returnData = {
|
|
254
|
+
order_id: `${fulfillment.id}-${Math.floor(Date.now() / 1000)}`,
|
|
255
|
+
order_date: new Date().toISOString().split('T')[0],
|
|
256
|
+
cannel_id: "", // Optional
|
|
257
|
+
pickup_customer_name: fulfillment.pickup_address?.first_name,
|
|
258
|
+
pickup_last_name: fulfillment.pickup_address?.last_name || "",
|
|
259
|
+
pickup_address: fulfillment.pickup_address?.address_1,
|
|
260
|
+
pickup_address_2: fulfillment.pickup_address?.address_2 || "",
|
|
261
|
+
pickup_city: fulfillment.pickup_address?.city,
|
|
262
|
+
pickup_state: fulfillment.pickup_address?.province,
|
|
263
|
+
pickup_country: fulfillment.pickup_address?.country_code || "India",
|
|
264
|
+
pickup_pincode: fulfillment.pickup_address?.postal_code,
|
|
265
|
+
pickup_email: fulfillment.email,
|
|
266
|
+
pickup_phone: fulfillment.pickup_address?.phone,
|
|
267
|
+
order_items: (fulfillment.items || []).map((item) => ({
|
|
268
|
+
name: item.title,
|
|
269
|
+
sku: item.sku,
|
|
270
|
+
units: item.quantity,
|
|
271
|
+
selling_price: item.unit_price,
|
|
272
|
+
discount: "",
|
|
273
|
+
qc_enable: false // default false
|
|
274
|
+
})),
|
|
275
|
+
payment_method: "Prepaid",
|
|
276
|
+
total_discount: "0",
|
|
277
|
+
sub_total: fulfillment.sub_total || 0,
|
|
278
|
+
length: 10, breadth: 10, height: 10, weight: 0.5 // defaults if missing on return items
|
|
279
|
+
};
|
|
280
|
+
try {
|
|
281
|
+
const response = await this.axios.post(`/orders/create/return`, returnData);
|
|
282
|
+
return response.data;
|
|
283
|
+
}
|
|
284
|
+
catch (error) {
|
|
285
|
+
(0, handle_error_1.handleError)(error);
|
|
286
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, "Failed to create return order");
|
|
287
|
+
}
|
|
288
|
+
}
|
|
289
|
+
async createDocuments(fulfillment) {
|
|
290
|
+
await this.ensureToken();
|
|
291
|
+
const createPromise = (url, params) => this.axios.get(url, { params }).catch(() => ({ data: null })); // Return null on fail to not break all
|
|
292
|
+
const [manifestRes, labelRes, invoiceRes] = await Promise.all([
|
|
293
|
+
createPromise(`/manifests/generate`, { order_ids: [fulfillment.shipment_id] }),
|
|
294
|
+
createPromise(`/courier/generate/label`, { shipment_id: [fulfillment.shipment_id] }),
|
|
295
|
+
createPromise(`/orders/print/invoice`, { ids: [fulfillment.order_id] })
|
|
296
|
+
]);
|
|
297
|
+
const extractUrl = (res, key, checkKey, checkVal) => {
|
|
298
|
+
if (!res?.data)
|
|
299
|
+
return "";
|
|
300
|
+
const item = Array.isArray(res.data) ? res.data[0] : res.data;
|
|
301
|
+
if (checkKey && item[checkKey] !== checkVal)
|
|
302
|
+
return "";
|
|
303
|
+
return item[key] || "";
|
|
304
|
+
};
|
|
305
|
+
return {
|
|
306
|
+
manifest: extractUrl(manifestRes, "manifest_url", "status", 1),
|
|
307
|
+
label: extractUrl(labelRes, "label_url", "label_created", 1),
|
|
308
|
+
invoice: extractUrl(invoiceRes, "invoice_url", "is_invoice_created", true),
|
|
309
|
+
};
|
|
310
|
+
}
|
|
311
|
+
async generateLabel(fulfillment) {
|
|
312
|
+
await this.ensureToken();
|
|
313
|
+
const res = await this.axios.get(`/courier/generate/label`, {
|
|
314
|
+
params: { shipment_id: [fulfillment.shipment_id] }
|
|
315
|
+
});
|
|
316
|
+
return res.data?.[0]?.label_url || "";
|
|
317
|
+
}
|
|
318
|
+
async generateInvoice(fulfillment) {
|
|
319
|
+
await this.ensureToken();
|
|
320
|
+
const res = await this.axios.get(`/orders/print/invoice`, {
|
|
321
|
+
params: { ids: [fulfillment.order_id] }
|
|
322
|
+
});
|
|
323
|
+
return res.data?.[0]?.invoice_url || "";
|
|
324
|
+
}
|
|
325
|
+
}
|
|
326
|
+
exports.default = ShiprocketClient;
|
|
327
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5kZXguanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi9zcmMvcHJvdmlkZXJzL3NoaXByb2NrZXQvY2xpZW50L2luZGV4LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7O0FBQUEsa0RBQTRDO0FBQzVDLHFEQUF1RDtBQUN2RCx5REFBcUQ7QUFDckQsaURBQTRDO0FBdUg1QyxNQUFxQixnQkFBZ0I7SUFRakMsWUFBWSxPQUFnQztRQUhwQyxVQUFLLEdBQWtCLElBQUksQ0FBQTtRQUMzQixlQUFVLEdBQUcsS0FBSyxDQUFBO1FBR3RCLElBQUksQ0FBQyxPQUFPLENBQUMsS0FBSyxJQUFJLENBQUMsT0FBTyxDQUFDLFFBQVEsRUFBRSxDQUFDO1lBQ3RDLE1BQU0sSUFBSSxtQkFBVyxDQUNqQixtQkFBVyxDQUFDLEtBQUssQ0FBQyxZQUFZLEVBQzlCLHlDQUF5QyxDQUM1QyxDQUFBO1FBQ0wsQ0FBQztRQUNELElBQUksQ0FBQyxLQUFLLEdBQUcsT0FBTyxDQUFDLEtBQUssQ0FBQTtRQUMxQixJQUFJLENBQUMsUUFBUSxHQUFHLE9BQU8sQ0FBQyxRQUFRLENBQUE7UUFDaEMsSUFBSSxDQUFDLGVBQWUsR0FBRyxPQUFPLENBQUMsZUFBZSxDQUFBO1FBQzlDLElBQUksQ0FBQyxLQUFLLEdBQUcsZUFBSyxDQUFDLE1BQU0sQ0FBQztZQUN0QixPQUFPLEVBQUUseUNBQXlDO1lBQ2xELE9BQU8sRUFBRSxFQUFFLGNBQWMsRUFBRSxrQkFBa0IsRUFBRTtZQUMvQyxPQUFPLEVBQUUsS0FBSztTQUNqQixDQUFDLENBQUE7UUFFRix1REFBdUQ7UUFDdkQsSUFBSSxDQUFDLEtBQUssQ0FBQyxZQUFZLENBQUMsUUFBUSxDQUFDLEdBQUcsQ0FDaEMsQ0FBQyxRQUFRLEVBQUUsRUFBRSxDQUFDLFFBQVEsRUFDdEIsS0FBSyxFQUFFLEtBQUssRUFBRSxFQUFFO1lBQ1osTUFBTSxlQUFlLEdBQUcsS0FBSyxDQUFDLE1BQU0sQ0FBQTtZ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
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.authenticate = void 0;
|
|
4
|
+
const utils_1 = require("@medusajs/framework/utils");
|
|
5
|
+
const handle_error_1 = require("../handle-error");
|
|
6
|
+
/**
|
|
7
|
+
* Authenticates with the Shiprocket API to get a token.
|
|
8
|
+
* @param axios - The Axios instance to use for the request.
|
|
9
|
+
* @param email - The user's email.
|
|
10
|
+
* @param password - The user's password.
|
|
11
|
+
* @param isDisposed - Whether the client is disposed.
|
|
12
|
+
* @returns The authentication token and its expiry time.
|
|
13
|
+
*/
|
|
14
|
+
const authenticate = async (axios, email, password, isDisposed) => {
|
|
15
|
+
if (isDisposed) {
|
|
16
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.UNEXPECTED_STATE, "Cannot authenticate disposed client");
|
|
17
|
+
}
|
|
18
|
+
try {
|
|
19
|
+
const response = await axios.post("/auth/login", {
|
|
20
|
+
email,
|
|
21
|
+
password,
|
|
22
|
+
});
|
|
23
|
+
if (!response.data.token) {
|
|
24
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, "No token received in authentication response");
|
|
25
|
+
}
|
|
26
|
+
return {
|
|
27
|
+
token: response.data.token,
|
|
28
|
+
// Token valid for 10 days, refresh after 8
|
|
29
|
+
tokenExpiry: Date.now() + 8 * 24 * 60 * 60 * 1000,
|
|
30
|
+
};
|
|
31
|
+
}
|
|
32
|
+
catch (error) {
|
|
33
|
+
(0, handle_error_1.handleError)(error);
|
|
34
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.UNEXPECTED_STATE, "Authentication failed unexpectedly");
|
|
35
|
+
}
|
|
36
|
+
};
|
|
37
|
+
exports.authenticate = authenticate;
|
|
38
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiYXV0aGVudGljYXRlLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vLi4vLi4vLi4vLi4vc3JjL3Byb3ZpZGVycy9zaGlwcm9ja2V0L2NsaWVudC9tZXRob2RzL2F1dGhlbnRpY2F0ZS50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiOzs7QUFBQSxxREFBdUQ7QUFFdkQsa0RBQTZDO0FBRzdDOzs7Ozs7O0dBT0c7QUFDSSxNQUFNLFlBQVksR0FBRyxLQUFLLEVBQzdCLEtBQW9CLEVBQ3BCLEtBQWEsRUFDYixRQUFnQixFQUNoQixVQUFtQixFQUM0QixFQUFFO0lBQ2pELElBQUksVUFBVSxFQUFFLENBQUM7UUFDYixNQUFNLElBQUksbUJBQVcsQ0FDakIsbUJBQVcsQ0FBQyxLQUFLLENBQUMsZ0JBQWdCLEVBQ2xDLHFDQUFxQyxDQUN4QyxDQUFBO0lBQ0wsQ0FBQztJQUVELElBQUksQ0FBQztRQUNELE1BQU0sUUFBUSxHQUFHLE1BQU0sS0FBSyxDQUFDLElBQUksQ0FBeUIsYUFBYSxFQUFFO1lBQ3JFLEtBQUs7WUFDTCxRQUFRO1NBQ1gsQ0FBQyxDQUFBO1FBRUYsSUFBSSxDQUFDLFFBQVEsQ0FBQyxJQUFJLENBQUMsS0FBSyxFQUFFLENBQUM7WUFDdkIsTUFBTSxJQUFJLG1CQUFXLENBQ2pCLG1CQUFXLENBQUMsS0FBSyxDQUFDLFlBQVksRUFDOUIsOENBQThDLENBQ2pELENBQUE7UUFDTCxDQUFDO1FBRUQsT0FBTztZQUNILEtBQUssRUFBRSxRQUFRLENBQUMsSUFBSSxDQUFDLEtBQUs7WUFDMUIsMkNBQTJDO1lBQzNDLFdBQVcsRUFBRSxJQUFJLENBQUMsR0FBRyxFQUFFLEdBQUcsQ0FBQyxHQUFHLEVBQUUsR0FBRyxFQUFFLEdBQUcsRUFBRSxHQUFHLElBQUk7U0FDcEQsQ0FBQTtJQUNMLENBQUM7SUFBQyxPQUFPLEtBQUssRUFBRSxDQUFDO1FBQ2IsSUFBQSwwQkFBVyxFQUFDLEtBQUssQ0FBQyxDQUFBO1FBQ2xCLE1BQU0sSUFBSSxtQkFBVyxDQUNqQixtQkFBVyxDQUFDLEtBQUssQ0FBQyxnQkFBZ0IsRUFDbEMsb0NBQW9DLENBQ3ZDLENBQUE7SUFDTCxDQUFDO0FBQ0wsQ0FBQyxDQUFBO0FBdENZLFFBQUEsWUFBWSxnQkFzQ3hCIn0=
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5kZXguanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi8uLi9zcmMvcHJvdmlkZXJzL3NoaXByb2NrZXQvY2xpZW50L3R5cGVzL2luZGV4LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiIifQ==
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
const service_1 = __importDefault(require("./service"));
|
|
7
|
+
exports.default = service_1.default;
|
|
8
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5kZXguanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi9zcmMvcHJvdmlkZXJzL3NoaXByb2NrZXQvaW5kZXgudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7Ozs7QUFBQSx3REFBNEQ7QUFFNUQsa0JBQWUsaUJBQW9DLENBQUEifQ==
|
|
@@ -0,0 +1,246 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
const utils_1 = require("@medusajs/framework/utils");
|
|
7
|
+
const client_1 = __importDefault(require("./client"));
|
|
8
|
+
class ShipRocketFulfillmentProviderService extends utils_1.AbstractFulfillmentProviderService {
|
|
9
|
+
/**
|
|
10
|
+
* Constructs a new instance of the ShipRocketFulfillmentProviderService.
|
|
11
|
+
* @param {Logger} logger - The logger instance.
|
|
12
|
+
* @param {Options} options - The options for the Shiprocket client.
|
|
13
|
+
*/
|
|
14
|
+
constructor({ logger }, options) {
|
|
15
|
+
super();
|
|
16
|
+
this.logger_ = logger;
|
|
17
|
+
this.options_ = options;
|
|
18
|
+
this.client = new client_1.default({
|
|
19
|
+
email: options.email,
|
|
20
|
+
password: options.password,
|
|
21
|
+
pickup_location: options.pickup_location,
|
|
22
|
+
});
|
|
23
|
+
}
|
|
24
|
+
/**
|
|
25
|
+
* Returns the fulfillment options for Shiprocket.
|
|
26
|
+
* @returns An array of fulfillment options.
|
|
27
|
+
*/
|
|
28
|
+
async getFulfillmentOptions() {
|
|
29
|
+
return [
|
|
30
|
+
{
|
|
31
|
+
id: "Standard Shipping",
|
|
32
|
+
name: "Standard Shipping",
|
|
33
|
+
is_return: false,
|
|
34
|
+
},
|
|
35
|
+
{
|
|
36
|
+
id: "Return Shipping",
|
|
37
|
+
name: "Return Shipping",
|
|
38
|
+
is_return: true,
|
|
39
|
+
},
|
|
40
|
+
];
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Determines whether the fulfillment option can calculate the shipping rate.
|
|
44
|
+
* @param data - The fulfillment option data.
|
|
45
|
+
* @returns A promise that resolves to a boolean indicating whether the option can calculate the rate.
|
|
46
|
+
*/
|
|
47
|
+
async canCalculate(data) {
|
|
48
|
+
return true;
|
|
49
|
+
}
|
|
50
|
+
/**
|
|
51
|
+
* Calculates the shipping rate for a given order.
|
|
52
|
+
* @param optionData - The fulfillment option data.
|
|
53
|
+
* @param data - The fulfillment data.
|
|
54
|
+
* @param context - The fulfillment context.
|
|
55
|
+
* @returns The calculated shipping rate.
|
|
56
|
+
* @throws {Error} If either pickup or delivery postcodes are missing.
|
|
57
|
+
* @throws {Error} If weight is missing.
|
|
58
|
+
*/
|
|
59
|
+
async calculatePrice(optionData, data, context) {
|
|
60
|
+
const params = {
|
|
61
|
+
pickup_postcode: context["from_location"]?.address?.postal_code,
|
|
62
|
+
delivery_postcode: context["shipping_address"]?.postal_code,
|
|
63
|
+
weight: 0,
|
|
64
|
+
cod: (this.options_.cod === "true" || this.options_.cod === 1) ? 1 : 0,
|
|
65
|
+
};
|
|
66
|
+
// Calculate total weight
|
|
67
|
+
const items = (context["items"] || []);
|
|
68
|
+
let totalWeightGrams = 0;
|
|
69
|
+
for (const item of items) {
|
|
70
|
+
const quantity = item.quantity || 1;
|
|
71
|
+
// Medusa usually stores weight in grams. Shiprocket needs kg.
|
|
72
|
+
// Try variant weight first, then metadata, then default to 0
|
|
73
|
+
const itemWeight = (item.variant?.weight ?? item.metadata?.weight ?? 0);
|
|
74
|
+
totalWeightGrams += itemWeight * quantity;
|
|
75
|
+
}
|
|
76
|
+
// Convert to kg. If 0, default to 0.5kg to allow calculation to proceed (avoid blocking checkout for missing weights)
|
|
77
|
+
params.weight = totalWeightGrams > 0 ? totalWeightGrams / 1000 : 0.5;
|
|
78
|
+
// Ensure we have a valid pickup postcode.
|
|
79
|
+
// Note: from_location depends on Stock Location being properly configured and linked in Medusa.
|
|
80
|
+
if (!params.pickup_postcode) {
|
|
81
|
+
this.logger_.warn("Shiprocket: Missing pickup_postcode. Ensure a Stock Location with an address is linked to the Sales Channel.");
|
|
82
|
+
// We can't proceed without it, shiprocket API will fail.
|
|
83
|
+
}
|
|
84
|
+
if (!params.pickup_postcode || !params.delivery_postcode) {
|
|
85
|
+
throw new Error("Both pickup and delivery postcodes are required for rate calculation.");
|
|
86
|
+
}
|
|
87
|
+
const price = await this.client.calculate(params);
|
|
88
|
+
return {
|
|
89
|
+
calculated_amount: price,
|
|
90
|
+
is_calculated_price_tax_inclusive: true,
|
|
91
|
+
};
|
|
92
|
+
}
|
|
93
|
+
/**
|
|
94
|
+
* Creates a fulfillment in Shiprocket.
|
|
95
|
+
* @param data - The fulfillment data.
|
|
96
|
+
* @param items - The items in the fulfillment.
|
|
97
|
+
* @param order - The order associated with the fulfillment.
|
|
98
|
+
* @param fulfillment - The fulfillment data.
|
|
99
|
+
* @returns The created fulfillment data.
|
|
100
|
+
*/
|
|
101
|
+
async createFulfillment(data, items, order, fulfillment) {
|
|
102
|
+
try {
|
|
103
|
+
// Type assertions needed due to Medusa's fulfillment types being more specific
|
|
104
|
+
const fulfillmentData = fulfillment;
|
|
105
|
+
const itemsData = items;
|
|
106
|
+
const orderData = order;
|
|
107
|
+
const externalData = await this.client.create(fulfillmentData, itemsData, orderData);
|
|
108
|
+
const { label, manifest, invoice } = await this.client.createDocuments(externalData);
|
|
109
|
+
return {
|
|
110
|
+
data: {
|
|
111
|
+
...(fulfillment || {}),
|
|
112
|
+
...externalData,
|
|
113
|
+
},
|
|
114
|
+
labels: [
|
|
115
|
+
{
|
|
116
|
+
tracking_number: externalData.tracking_number || "",
|
|
117
|
+
tracking_url: externalData.tracking_url || "",
|
|
118
|
+
label_url: label || "",
|
|
119
|
+
// invoice_url: invoice || "", // types might not support this in label object, but okay to omit if not needed
|
|
120
|
+
},
|
|
121
|
+
],
|
|
122
|
+
};
|
|
123
|
+
}
|
|
124
|
+
catch (err) {
|
|
125
|
+
const error = err;
|
|
126
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, (error?.message || error?.response?.data?.message || "Failed to create fulfillment"));
|
|
127
|
+
}
|
|
128
|
+
}
|
|
129
|
+
/**
|
|
130
|
+
* Cancels a fulfillment in Shiprocket.
|
|
131
|
+
* @param data - The fulfillment data.
|
|
132
|
+
* @throws {MedusaError} If the order ID is not provided.
|
|
133
|
+
*/
|
|
134
|
+
async cancelFulfillment(data) {
|
|
135
|
+
const { order_id } = data;
|
|
136
|
+
if (!order_id) {
|
|
137
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, "Order ID is required");
|
|
138
|
+
}
|
|
139
|
+
await this.client.cancel(order_id);
|
|
140
|
+
}
|
|
141
|
+
/**
|
|
142
|
+
* Creates a return fulfillment in Shiprocket.
|
|
143
|
+
* @param fulfillment - The fulfillment data.
|
|
144
|
+
* @returns The created return fulfillment data.
|
|
145
|
+
*/
|
|
146
|
+
async createReturnFulfillment(fulfillment) {
|
|
147
|
+
try {
|
|
148
|
+
const externalData = await this.client.createReturn(fulfillment);
|
|
149
|
+
return {
|
|
150
|
+
data: {
|
|
151
|
+
...(fulfillment || {}),
|
|
152
|
+
...externalData,
|
|
153
|
+
},
|
|
154
|
+
labels: [
|
|
155
|
+
{
|
|
156
|
+
tracking_number: externalData.tracking_number || externalData.awb || "",
|
|
157
|
+
tracking_url: externalData.tracking_url || "",
|
|
158
|
+
label_url: externalData.label_url || "",
|
|
159
|
+
},
|
|
160
|
+
],
|
|
161
|
+
};
|
|
162
|
+
}
|
|
163
|
+
catch (err) {
|
|
164
|
+
const error = err;
|
|
165
|
+
throw new utils_1.MedusaError(utils_1.MedusaError.Types.INVALID_DATA, (error?.message || error?.response?.data?.message || "Failed to create return fulfillment"));
|
|
166
|
+
}
|
|
167
|
+
}
|
|
168
|
+
/**
|
|
169
|
+
* Retrieves the documents associated with a fulfillment.
|
|
170
|
+
* @param data - The fulfillment data.
|
|
171
|
+
* @returns An array of documents associated with the fulfillment.
|
|
172
|
+
*/
|
|
173
|
+
async getFulfillmentDocuments(data) {
|
|
174
|
+
try {
|
|
175
|
+
const invoice = await this.client.generateInvoice(data);
|
|
176
|
+
// Return empty array as the method signature requires never[]
|
|
177
|
+
return [];
|
|
178
|
+
}
|
|
179
|
+
catch (err) {
|
|
180
|
+
const error = err;
|
|
181
|
+
this.logger_.warn(`Failed to generate invoice: ${error?.message || "Unknown error"}`);
|
|
182
|
+
return [];
|
|
183
|
+
}
|
|
184
|
+
}
|
|
185
|
+
/**
|
|
186
|
+
* Retrieves the documents associated with a shipment.
|
|
187
|
+
* @param data - The shipment data.
|
|
188
|
+
* @returns An array of documents associated with the shipment.
|
|
189
|
+
*/
|
|
190
|
+
async getShipmentDocuments(data) {
|
|
191
|
+
try {
|
|
192
|
+
const label = await this.client.generateLabel(data);
|
|
193
|
+
// Return empty array as the method signature requires never[]
|
|
194
|
+
return [];
|
|
195
|
+
}
|
|
196
|
+
catch (err) {
|
|
197
|
+
const error = err;
|
|
198
|
+
this.logger_.warn(`Failed to generate label: ${error?.message || "Unknown error"}`);
|
|
199
|
+
return [];
|
|
200
|
+
}
|
|
201
|
+
}
|
|
202
|
+
/**
|
|
203
|
+
* Retrieves the documents associated with a return fulfillment.
|
|
204
|
+
* @param data - The return fulfillment data.
|
|
205
|
+
* @returns An empty array, as document retrieval is not supported for returns.
|
|
206
|
+
*/
|
|
207
|
+
async getReturnDocuments(data) {
|
|
208
|
+
return [];
|
|
209
|
+
}
|
|
210
|
+
/**
|
|
211
|
+
* Retrieves the documents associated with a fulfillment, given its data and the type of documents to retrieve.
|
|
212
|
+
* @param fulfillmentData - The fulfillment data.
|
|
213
|
+
* @param documentType - The type of documents to retrieve.
|
|
214
|
+
* @returns A promise that resolves once the documents have been retrieved.
|
|
215
|
+
* @remarks Document retrieval is not supported by this provider.
|
|
216
|
+
*/
|
|
217
|
+
async retrieveDocuments(fulfillmentData, documentType) {
|
|
218
|
+
this.logger_.debug("Document retrieval not supported");
|
|
219
|
+
}
|
|
220
|
+
/**
|
|
221
|
+
* Validates the fulfillment data to ensure it has the required information.
|
|
222
|
+
* If the external ID is not present, it will be generated automatically.
|
|
223
|
+
* @param optionData - The data provided by the user when creating a fulfillment option.
|
|
224
|
+
* @param data - The data provided by the user when creating a fulfillment.
|
|
225
|
+
* @param context - The context of the fulfillment.
|
|
226
|
+
* @returns A promise that resolves with the validated fulfillment data.
|
|
227
|
+
*/
|
|
228
|
+
async validateFulfillmentData(optionData, data, context) {
|
|
229
|
+
return {
|
|
230
|
+
...data,
|
|
231
|
+
external_id: `temp_${Date.now()}`,
|
|
232
|
+
};
|
|
233
|
+
}
|
|
234
|
+
/**
|
|
235
|
+
* Validates a fulfillment option to ensure it has the required information.
|
|
236
|
+
* @param data - The data provided by the user when creating a fulfillment option.
|
|
237
|
+
* @returns A promise that resolves with a boolean indicating whether the option is valid.
|
|
238
|
+
* @remarks A fulfillment option is valid if it has an external ID.
|
|
239
|
+
*/
|
|
240
|
+
async validateOption(data) {
|
|
241
|
+
return data.external_id !== undefined;
|
|
242
|
+
}
|
|
243
|
+
}
|
|
244
|
+
ShipRocketFulfillmentProviderService.identifier = "shiprocket";
|
|
245
|
+
exports.default = ShipRocketFulfillmentProviderService;
|
|
246
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoic2VydmljZS5qcyIsInNvdXJjZVJvb3QiOiIiLCJzb3VyY2VzIjpbIi4uLy4uLy4uLy4uLy4uL3NyYy9wcm92aWRlcnMvc2hpcHJvY2tldC9zZXJ2aWNlLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiI7Ozs7O0FBQUEscURBQTRGO0FBYTVGLHNEQUF3QztBQWtDeEMsTUFBTSxvQ0FBcUMsU0FBUSwwQ0FBa0M7SUFPakY7Ozs7T0FJRztJQUNILFlBQVksRUFBRSxNQUFNLEVBQXdCLEVBQUUsT0FBZ0I7UUFDMUQsS0FBSyxFQUFFLENBQUM7UUFDUixJQUFJLENBQUMsT0FBTyxHQUFHLE1BQU0sQ0FBQztRQUN0QixJQUFJLENBQUMsUUFBUSxHQUFHLE9BQU8sQ0FBQztRQUN4QixJQUFJLENBQUMsTUFBTSxHQUFHLElBQUksZ0JBQWdCLENBQUM7WUFDL0IsS0FBSyxFQUFFLE9BQU8sQ0FBQyxLQUFLO1lBQ3BCLFFBQVEsRUFBRSxPQUFPLENBQUMsUUFBUTtZQUMxQixlQUFlLEVBQUUsT0FBTyxDQUFDLGVBQWU7U0FDM0MsQ0FBQyxDQUFDO0lBQ1AsQ0FBQztJQUVEOzs7T0FHRztJQUNILEtBQUssQ0FBQyxxQkFBcUI7UUFDdkIsT0FBTztZQUNIO2dCQUNJLEVBQUUsRUFBRSxtQkFBbUI7Z0JBQ3ZCLElBQUksRUFBRSxtQkFBbUI7Z0JBQ3pCLFNBQVMsRUFBRSxLQUFLO2FBQ25CO1lBQ0Q7Z0JBQ0ksRUFBRSxFQUFFLGlCQUFpQjtnQkFDckIsSUFBSSxFQUFFLGlCQUFpQjtnQkFDdkIsU0FBUyxFQUFFLElBQUk7YUFDbEI7U0FDSixDQUFDO0lBQ04sQ0FBQztJQUdEOzs7O09BSUc7SUFDSCxLQUFLLENBQUMsWUFBWSxDQUFDLElBQTZCO1FBQzVDLE9BQU8sSUFBSSxDQUFDO0lBQ2hCLENBQUM7SUFDRDs7Ozs7Ozs7T0FRRztJQUVILEtBQUssQ0FBQyxjQUFjLENBQ2hCLFVBQXlELEVBQ3pELElBQTZDLEVBQzdDLE9BQW1EO1FBRW5ELE1BQU0sTUFBTSxHQUFHO1lBQ1gsZUFBZSxFQUFFLE9BQU8sQ0FBQyxlQUFlLENBQUMsRUFBRSxPQUFPLEVBQUUsV0FBcUI7WUFDekUsaUJBQWlCLEVBQUUsT0FBTyxDQUFDLGtCQUFrQixDQUFDLEVBQUUsV0FBcUI7WUFDckUsTUFBTSxFQUFFLENBQUM7WUFDVCxHQUFHLEVBQUUsQ0FBQyxJQUFJLENBQUMsUUFBUSxDQUFDLEdBQUcsS0FBSyxNQUFNLElBQUksSUFBSSxDQUFDLFFBQVEsQ0FBQyxHQUFHLEtBQUssQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBVztTQUNuRixDQUFDO1FBRUYseUJBQXlCO1FBQ3pCLE1BQU0sS0FBSyxHQUFHLENBQUMsT0FBTyxDQUFDLE9BQU8sQ0FBQyxJQUFJLEVBQUUsQ0FBNkIsQ0FBQztRQUNuRSxJQUFJLGdCQUFnQixHQUFHLENBQUMsQ0FBQztRQUV6QixLQUFLLE1BQU0sSUFBSSxJQUFJLEtBQUssRUFBRSxDQUFDO1lBQ3ZCLE1BQU0sUUFBUSxHQUFHLElBQUksQ0FBQyxRQUFRLElBQUksQ0FBQyxDQUFDO1lBQ3BDLDhEQUE4RDtZQUM5RCw2REFBNkQ7WUFDN0QsTUFBTSxVQUFVLEdBQUcsQ0FBQyxJQUFJLENBQUMsT0FBTyxFQUFFLE1BQU0sSUFBSSxJQUFJLENBQUMsUUFBUSxFQUFFLE1BQU0sSUFBSSxDQUFDLENBQUMsQ0FBQztZQUN4RSxnQkFBZ0IsSUFBSSxVQUFVLEdBQUcsUUFBUSxDQUFDO1FBQzlDLENBQUM7UUFFRCxzSEFBc0g7UUFDdEgsTUFBTSxDQUFDLE1BQU0sR0FBRyxnQkFBZ0IsR0FBRyxDQUFDLENBQUMsQ0FBQyxDQUFDLGdCQUFnQixHQUFHLElBQUksQ0FBQyxDQUFDLENBQUMsR0FBRyxDQUFDO1FBRXJFLDJDQUEyQztRQUMzQyxnR0FBZ0c7UUFDaEcsSUFBSSxDQUFDLE1BQU0sQ0FBQyxlQUFlLEVBQUUsQ0FBQztZQUMxQixJQUFJLENBQUMsT0FBTyxDQUFDLElBQUksQ0FBQyw4R0FBOEcsQ0FBQyxDQUFDO1lBQ2xJLHlEQUF5RDtRQUM3RCxDQUFDO1FBRUQsSUFBSSxDQUFDLE1BQU0sQ0FBQyxlQUFlLElBQUksQ0FBQyxNQUFNLENBQUMsaUJBQWlCLEVBQUUsQ0FBQztZQUN2RCxNQUFNLElBQUksS0FBSyxDQUFDLHVFQUF1RSxDQUFDLENBQUM7UUFDN0YsQ0FBQztRQUVELE1BQU0sS0FBSyxHQUFHLE1BQU0sSUFBSSxDQUFDLE1BQU0sQ0FBQyxTQUFTLENBQUMsTUFBTSxDQUFDLENBQUM7UUFFbEQsT0FBTztZQUNILGlCQUFpQixFQUFFLEtBQUs7WUFDeEIsaUNBQWlDLEVBQUUsSUFBSTtTQUMxQyxDQUFDO0lBQ04sQ0FBQztJQUdEOzs7Ozs7O09BT0c7SUFDSCxLQUFLLENBQUMsaUJBQWlCLENBQ25CLElBQTZCLEVBQzdCLEtBQXlELEVBQ3pELEtBQStDLEVBQy9DLFdBQXlEO1FBRXpELElBQUksQ0FBQztZQUNELCtFQUErRTtZQUMvRSxNQUFNLGVBQWUsR0FBRyxXQUFrRSxDQUFDO1lBQzNGLE1BQU0sU0FBUyxHQUFHLEtBQTRELENBQUM7WUFDL0UsTUFBTSxTQUFTLEdBQUcsS0FBNEQsQ0FBQztZQUMvRSxNQUFNLFlBQVksR0FBRyxNQUFNLElBQUksQ0FBQyxNQUFNLENBQUMsTUFBTSxDQUFDLGVBQWUsRUFBRSxTQUFTLEVBQUUsU0FBUyxDQUFDLENBQUM7WUFDckYsTUFBTSxFQUFFLEtBQUssRUFBRSxRQUFRLEVBQUUsT0FBTyxFQUFFLEdBQUcsTUFBTSxJQUFJLENBQUMsTUFBTSxDQUFDLGVBQWUsQ0FBQyxZQUFZLENBQUMsQ0FBQztZQUVyRixPQUFPO2dCQUNILElBQUksRUFBRTtvQkFDRixHQUFHLENBQUUsV0FBc0IsSUFBSSxFQUFFLENBQUM7b0JBQ2xDLEdBQUcsWUFBWTtpQkFDbEI7Z0JBQ0QsTUFBTSxFQUFFO29CQUNKO3dCQUNJLGVBQWUsRUFBRSxZQUFZLENBQUMsZUFBZSxJQUFJLEVBQUU7d0JBQ25ELFlBQVksRUFBRSxZQUFZLENBQUMsWUFBWSxJQUFJLEVBQUU7d0JBQzdDLFNBQVMsRUFBRSxLQUFLLElBQUksRUFBRTt3QkFDdEIsOEdBQThHO3FCQUNqSDtpQkFDSjthQUNKLENBQUM7UUFDTixDQUFDO1FBQUMsT0FBTyxHQUFZLEVBQUUsQ0FBQztZQUNwQixNQUFNLEtBQUssR0FBRyxHQUF1QixDQUFDO1lBQ3RDLE1BQU0sSUFBSSxtQkFBVyxDQUNqQixtQkFBVyxDQUFDLEtBQUssQ0FBQyxZQUFZLEVBQzlCLENBQUMsS0FBSyxFQUFFLE9BQU8sSUFBSSxLQUFLLEVBQUUsUUFBUSxFQUFFLElBQUksRUFBRSxPQUFPLElBQUksOEJBQThCLENBQUMsQ0FDdkYsQ0FBQztRQUNOLENBQUM7SUFDTCxDQUFDO0lBRUQ7Ozs7T0FJRztJQUNILEtBQUssQ0FBQyxpQkFBaUIsQ0FBQyxJQUE2QjtRQUNqRCxNQUFNLEVBQUUsUUFBUSxFQUFFLEdBQUcsSUFBNEIsQ0FBQztRQUVsRCxJQUFJLENBQUMsUUFBUSxFQUFFLENBQUM7WUFDWixNQUFNLElBQUksbUJBQVcsQ0FDakIsbUJBQVcsQ0FBQyxLQUFLLENBQUMsWUFBWSxFQUM5QixzQkFBc0IsQ0FDekIsQ0FBQztRQUNOLENBQUM7UUFFRCxNQUFNLElBQUksQ0FBQyxNQUFNLENBQUMsTUFBTSxDQUFDLFFBQVEsQ0FBQyxDQUFDO0lBQ3ZDLENBQUM7SUFFRDs7OztPQUlHO0lBQ0gsS0FBSyxDQUFDLHVCQUF1QixDQUN6QixXQUFvQztRQUVwQyxJQUFJLENBQUM7WUFDRCxNQUFNLFlBQVksR0FBRyxNQUFNLElBQUksQ0FBQyxNQUFNLENBQUMsWUFBWSxDQUFDLFdBQVcsQ0FBQyxDQUFDO1lBRXJFLE9BQU87Z0JBQ0gsSUFBSSxFQUFFO29CQUNGLEdBQUcsQ0FBRSxXQUFzQixJQUFJLEVBQUUsQ0FBQztvQkFDbEMsR0FBRyxZQUFZO2lCQUNsQjtnQkFDRCxNQUFNLEVBQUU7b0JBQ0o7d0JBQ0ksZUFBZSxFQUFFLFlBQVksQ0FBQyxlQUFlLElBQUksWUFBWSxDQUFDLEdBQUcsSUFBSSxFQUFFO3dCQUN2RSxZQUFZLEVBQUUsWUFBWSxDQUFDLFlBQVksSUFBSSxFQUFFO3dCQUM3QyxTQUFTLEVBQUUsWUFBWSxDQUFDLFNBQVMsSUFBSSxFQUFFO3FCQUMxQztpQkFDSjthQUNKLENBQUM7UUFDRixDQUFDO1FBQUMsT0FBTyxHQUFZLEVBQUUsQ0FBQztZQUNwQixNQUFNLEtBQUssR0FBRyxHQUF1QixDQUFDO1lBQ3RDLE1BQU0sSUFBSSxtQkFBVyxDQUNqQixtQkFBVyxDQUFDLEtBQUssQ0FBQyxZQUFZLEVBQzlCLENBQUMsS0FBSyxFQUFFLE9BQU8sSUFBSSxLQUFLLEVBQUUsUUFBUSxFQUFFLElBQUksRUFBRSxPQUFPLElBQUkscUNBQXFDLENBQUMsQ0FDOUYsQ0FBQztRQUNOLENBQUM7SUFDTCxDQUFDO0lBRUQ7Ozs7TUFJRTtJQUNGLEtBQUssQ0FBQyx1QkFBdUIsQ0FBQyxJQUE2QjtRQUN2RCxJQUFJLENBQUM7WUFDRCxNQUFNLE9BQU8sR0FBRyxNQUFNLElBQUksQ0FBQyxNQUFNLENBQUMsZUFBZSxDQUFDLElBQUksQ0FBQyxDQUFDO1lBQ3hELDhEQUE4RDtZQUM5RCxPQUFPLEVBQUUsQ0FBQztRQUNkLENBQUM7UUFBQyxPQUFPLEdBQVksRUFBRSxDQUFDO1lBQ3BCLE1BQU0sS0FBSyxHQUFHLEdBQXVCLENBQUM7WUFDdEMsSUFBSSxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsK0JBQStCLEtBQUssRUFBRSxPQUFPLElBQUksZUFBZSxFQUFFLENBQUMsQ0FBQztZQUN0RixPQUFPLEVBQUUsQ0FBQztRQUNkLENBQUM7SUFDTCxDQUFDO0lBRUQ7Ozs7T0FJRztJQUNILEtBQUssQ0FBQyxvQkFBb0IsQ0FBQyxJQUE2QjtRQUNwRCxJQUFJLENBQUM7WUFDRCxNQUFNLEtBQUssR0FBRyxNQUFNLElBQUksQ0FBQyxNQUFNLENBQUMsYUFBYSxDQUFDLElBQUksQ0FBQyxDQUFDO1lBQ3BELDhEQUE4RDtZQUM5RCxPQUFPLEVBQUUsQ0FBQztRQUNkLENBQUM7UUFBQyxPQUFPLEdBQVksRUFBRSxDQUFDO1lBQ3BCLE1BQU0sS0FBSyxHQUFHLEdBQXVCLENBQUM7WUFDdEMsSUFBSSxDQUFDLE9BQU8sQ0FBQyxJQUFJLENBQUMsNkJBQTZCLEtBQUssRUFBRSxPQUFPLElBQUksZUFBZSxFQUFFLENBQUMsQ0FBQztZQUNwRixPQUFPLEVBQUUsQ0FBQztRQUNkLENBQUM7SUFDTCxDQUFDO0lBRUQ7Ozs7T0FJRztJQUNILEtBQUssQ0FBQyxrQkFBa0IsQ0FBQyxJQUE2QjtRQUNsRCxPQUFPLEVBQUUsQ0FBQztJQUNkLENBQUM7SUFHRDs7Ozs7O09BTUc7SUFDSCxLQUFLLENBQUMsaUJBQWlCLENBQ25CLGVBQXdDLEVBQ3hDLFlBQW9CO1FBRXBCLElBQUksQ0FBQyxPQUFPLENBQUMsS0FBSyxDQUFDLGtDQUFrQyxDQUFDLENBQUM7SUFDM0QsQ0FBQztJQUVEOzs7Ozs7O09BT0c7SUFDSCxLQUFLLENBQUMsdUJBQXVCLENBQ3pCLFVBQW1DLEVBQ25DLElBQTZCLEVBQzdCLE9BQWdDO1FBRWhDLE9BQU87WUFDSCxHQUFHLElBQUk7WUFDUCxXQUFXLEVBQUUsUUFBUSxJQUFJLENBQUMsR0FBRyxFQUFFLEVBQUU7U0FDcEMsQ0FBQztJQUNOLENBQUM7SUFFRDs7Ozs7T0FLRztJQUNILEtBQUssQ0FBQyxjQUFjLENBQUMsSUFBNkI7UUFDOUMsT0FBTyxJQUFJLENBQUMsV0FBVyxLQUFLLFNBQVMsQ0FBQztJQUMxQyxDQUFDOztBQWhTTSwrQ0FBVSxHQUFHLFlBQVksQ0FBQztBQW1TckMsa0JBQWUsb0NBQW9DLENBQUMifQ==
|
|
@@ -0,0 +1,3 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5kZXguanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi9zcmMvcHJvdmlkZXJzL3NoaXByb2NrZXQvdHlwZXMvaW5kZXgudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IiJ9
|
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.getCheapestCourier = getCheapestCourier;
|
|
4
|
+
exports.filterAllowedCouriers = filterAllowedCouriers;
|
|
5
|
+
exports.slugify = slugify;
|
|
6
|
+
function getCheapestCourier(couriers) {
|
|
7
|
+
const validCouriers = couriers.filter((c) => !!c.rate && !isNaN(Number(c.rate)));
|
|
8
|
+
if (validCouriers.length === 0)
|
|
9
|
+
return null;
|
|
10
|
+
return validCouriers.reduce((min, curr) => {
|
|
11
|
+
return Number(curr.rate) < Number(min.rate) ? curr : min;
|
|
12
|
+
});
|
|
13
|
+
}
|
|
14
|
+
function filterAllowedCouriers(couriers, allowedCourierIds) {
|
|
15
|
+
return couriers.filter((courier) => allowedCourierIds.includes(courier.courier_company_id));
|
|
16
|
+
}
|
|
17
|
+
function slugify(str) {
|
|
18
|
+
return str
|
|
19
|
+
.toLowerCase()
|
|
20
|
+
.trim()
|
|
21
|
+
.replace(/[^a-z0-9\s-]/g, '')
|
|
22
|
+
.replace(/\s+/g, '-')
|
|
23
|
+
.replace(/-+/g, '-');
|
|
24
|
+
}
|
|
25
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoiaW5kZXguanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi8uLi8uLi8uLi8uLi8uLi9zcmMvcHJvdmlkZXJzL3NoaXByb2NrZXQvdXRpbHMvaW5kZXgudHMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6Ijs7QUFFQSxnREFVQztBQUVELHNEQU9DO0FBRUQsMEJBT0M7QUE1QkQsU0FBZ0Isa0JBQWtCLENBQUMsUUFBbUI7SUFDbEQsTUFBTSxhQUFhLEdBQUcsUUFBUSxDQUFDLE1BQU0sQ0FDakMsQ0FBQyxDQUFDLEVBQUUsRUFBRSxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsSUFBSSxJQUFJLENBQUMsS0FBSyxDQUFDLE1BQU0sQ0FBQyxDQUFDLENBQUMsSUFBSSxDQUFDLENBQUMsQ0FDNUMsQ0FBQztJQUVGLElBQUksYUFBYSxDQUFDLE1BQU0sS0FBSyxDQUFDO1FBQUUsT0FBTyxJQUFJLENBQUM7SUFFNUMsT0FBTyxhQUFhLENBQUMsTUFBTSxDQUFDLENBQUMsR0FBRyxFQUFFLElBQUksRUFBRSxFQUFFO1FBQ3RDLE9BQU8sTUFBTSxDQUFDLElBQUksQ0FBQyxJQUFJLENBQUMsR0FBRyxNQUFNLENBQUMsR0FBRyxDQUFDLElBQUksQ0FBQyxDQUFDLENBQUMsQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFDLEdBQUcsQ0FBQztJQUM3RCxDQUFDLENBQUMsQ0FBQztBQUNQLENBQUM7QUFFRCxTQUFnQixxQkFBcUIsQ0FDakMsUUFBbUIsRUFDbkIsaUJBQTJCO0lBRTNCLE9BQU8sUUFBUSxDQUFDLE1BQU0sQ0FBQyxDQUFDLE9BQU8sRUFBRSxFQUFFLENBQy9CLGlCQUFpQixDQUFDLFFBQVEsQ0FBQyxPQUFPLENBQUMsa0JBQWtCLENBQUMsQ0FDekQsQ0FBQztBQUNOLENBQUM7QUFFRCxTQUFnQixPQUFPLENBQUMsR0FBVztJQUMvQixPQUFPLEdBQUc7U0FDTCxXQUFXLEVBQUU7U0FDYixJQUFJLEVBQUU7U0FDTixPQUFPLENBQUMsZUFBZSxFQUFFLEVBQUUsQ0FBQztTQUM1QixPQUFPLENBQUMsTUFBTSxFQUFFLEdBQUcsQ0FBQztTQUNwQixPQUFPLENBQUMsS0FBSyxFQUFFLEdBQUcsQ0FBQyxDQUFDO0FBQzdCLENBQUMifQ==
|
package/README.md
ADDED
|
@@ -0,0 +1,183 @@
|
|
|
1
|
+
<p align="center">
|
|
2
|
+
<a href="https://www.shiprocket.in">
|
|
3
|
+
<img src="https://custom-icon-badges.demolab.com/badge/Shiprocket-purple?style=for-the-badge&logo=package&logoColor=white" alt="Shiprocket Logo" height="50">
|
|
4
|
+
</a>
|
|
5
|
+
</p>
|
|
6
|
+
|
|
7
|
+
<h1 align="center">Medusa Shiprocket Fulfillment Plugin</h1>
|
|
8
|
+
|
|
9
|
+
<p align="center">
|
|
10
|
+
<strong>Seamless Logistics for Medusa v2 Stores in India 🇮🇳</strong>
|
|
11
|
+
</p>
|
|
12
|
+
|
|
13
|
+
<p align="center">
|
|
14
|
+
<a href="https://www.npmjs.com/package/@medusa-shiprocket-fulfillment-plugin-sbl">
|
|
15
|
+
<img src="https://img.shields.io/npm/v/@medusa-shiprocket-fulfillment-plugin-sbl?color=blue&style=flat-square" alt="NPM Version">
|
|
16
|
+
</a>
|
|
17
|
+
<a href="https://www.npmjs.com/package/@medusa-shiprocket-fulfillment-plugin-sbl">
|
|
18
|
+
<img src="https://img.shields.io/npm/dw/@medusa-shiprocket-fulfillment-plugin-sbl?style=flat-square" alt="NPM Downloads">
|
|
19
|
+
</a>
|
|
20
|
+
<a href="https://github.com/SAM-AEL/medusa-shiprocket-fulfillment-plugin-sbl/blob/main/LICENSE">
|
|
21
|
+
<img src="https://img.shields.io/github/license/SAM-AEL/medusa-shiprocket-fulfillment-plugin-sbl?style=flat-square" alt="License">
|
|
22
|
+
</a>
|
|
23
|
+
</p>
|
|
24
|
+
|
|
25
|
+
<hr />
|
|
26
|
+
|
|
27
|
+
## 🚀 Overview
|
|
28
|
+
|
|
29
|
+
The **Medusa Shiprocket Fulfillment Plugin** integrates [Shiprocket](https://www.shiprocket.in/), India's leading logistics aggregator, directly into your [Medusa](https://medusajs.com/) store.
|
|
30
|
+
|
|
31
|
+
Streamline your shipping operations by automating rate calculations, order creation, label generation, and returns—all from within the Medusa Admin.
|
|
32
|
+
|
|
33
|
+
**Compatible with Medusa v2.0+**
|
|
34
|
+
|
|
35
|
+
## ✨ Key Features
|
|
36
|
+
|
|
37
|
+
| Feature | Description |
|
|
38
|
+
| :--- | :--- |
|
|
39
|
+
| **💵 Automated Rates** | Fetch real-time shipping rates at checkout based on pickup and delivery pin codes. |
|
|
40
|
+
| **📦 Seamless Fulfillment** | Automatically create shipments in Shiprocket when you fulfill an order in Medusa. |
|
|
41
|
+
| **📄 Document Generation** | Generate and retrieve **Shipping Labels**, **Manifests**, and **Invoices** directly. |
|
|
42
|
+
| **↩️ Returns Management** | Handle return requests and generate reverse pickup shipments effortlessly. |
|
|
43
|
+
| **🇮🇳 India-First** | Optimized for Indian addresses, GST compliance, and domestic courier networks. |
|
|
44
|
+
| **🛑 Easy Cancellation** | Cancel shipments instantly from the Medusa Admin to void labels. |
|
|
45
|
+
|
|
46
|
+
## 📋 Prerequisites
|
|
47
|
+
|
|
48
|
+
Before you begin, ensure you have:
|
|
49
|
+
|
|
50
|
+
1. A **[Medusa v2](https://docs.medusajs.com/)** server set up.
|
|
51
|
+
2. A **[Shiprocket](https://app.shiprocket.in/register)** account.
|
|
52
|
+
3. At least one **Pickup Location** configured in your Shiprocket dashboard.
|
|
53
|
+
|
|
54
|
+
## 🛠️ Installation
|
|
55
|
+
|
|
56
|
+
Install the plugin using your preferred package manager:
|
|
57
|
+
|
|
58
|
+
```bash
|
|
59
|
+
npm install @medusa-shiprocket-fulfillment-plugin-sbl
|
|
60
|
+
# or
|
|
61
|
+
yarn add @medusa-shiprocket-fulfillment-plugin-sbl
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
## ⚙️ Configuration
|
|
65
|
+
|
|
66
|
+
### 1. Environment Variables
|
|
67
|
+
|
|
68
|
+
Add your Shiprocket credentials to your `.env` file.
|
|
69
|
+
|
|
70
|
+
> [!WARNING]
|
|
71
|
+
> **Security Note**: Never commit your actual API passwords to version control (git).
|
|
72
|
+
|
|
73
|
+
```bash
|
|
74
|
+
SHIPROCKET_EMAIL="your_email@example.com"
|
|
75
|
+
SHIPROCKET_PASSWORD="your_shiprocket_password"
|
|
76
|
+
# Must match the 'Nickname' of a pickup location in your Shiprocket settings
|
|
77
|
+
SHIPROCKET_PICKUP_LOCATION="Primary"
|
|
78
|
+
```
|
|
79
|
+
|
|
80
|
+
### 2. Medusa Config
|
|
81
|
+
|
|
82
|
+
Register the plugin in your `medusa-config.js` (or `medusa-config.ts`) file. You need to add it to both the `modules` (for the fulfillment provider) and `plugins` (if you are using any admin widgets, though currently optional).
|
|
83
|
+
|
|
84
|
+
```javascript
|
|
85
|
+
module.exports = defineConfig({
|
|
86
|
+
// ... other config
|
|
87
|
+
modules: [
|
|
88
|
+
{
|
|
89
|
+
resolve: "@medusajs/medusa/fulfillment",
|
|
90
|
+
options: {
|
|
91
|
+
providers: [
|
|
92
|
+
{
|
|
93
|
+
resolve: "@medusa-shiprocket-fulfillment-plugin-sbl",
|
|
94
|
+
id: "shiprocket",
|
|
95
|
+
options: {
|
|
96
|
+
email: process.env.SHIPROCKET_EMAIL,
|
|
97
|
+
password: process.env.SHIPROCKET_PASSWORD,
|
|
98
|
+
pickup_location: process.env.SHIPROCKET_PICKUP_LOCATION,
|
|
99
|
+
/**
|
|
100
|
+
* Set "true" (string) to enable Cash on Delivery support.
|
|
101
|
+
* This maps the payment method 'cod' to Shiprocket's COD logic.
|
|
102
|
+
*/
|
|
103
|
+
cod: "false",
|
|
104
|
+
},
|
|
105
|
+
},
|
|
106
|
+
],
|
|
107
|
+
},
|
|
108
|
+
},
|
|
109
|
+
],
|
|
110
|
+
});
|
|
111
|
+
```
|
|
112
|
+
|
|
113
|
+
## 💻 Usage Guide
|
|
114
|
+
|
|
115
|
+
### Enabling the Provider
|
|
116
|
+
|
|
117
|
+
1. Log in to your **Medusa Admin**.
|
|
118
|
+
2. Go to **Settings** → **Regions**.
|
|
119
|
+
3. Select the region you want to ship to (e.g., "India").
|
|
120
|
+
4. In the **Fulfillment Providers** section, edit and ensure `shiprocket` is selected.
|
|
121
|
+
5. Save changes.
|
|
122
|
+
|
|
123
|
+
### Shipping Options
|
|
124
|
+
|
|
125
|
+
You can now create Shipping Options (e.g., "Standard Shipping") that use the **shiprocket** provider.
|
|
126
|
+
- **Calculated**: Choose "Calculated" price type to use Shiprocket's real-time rate API.
|
|
127
|
+
|
|
128
|
+
### Creating a Fulfillment (Shipment)
|
|
129
|
+
When you fulfill an order in the Medusa Admin:
|
|
130
|
+
1. The plugin creates an order in Shiprocket.
|
|
131
|
+
2. It attempts to automatically assign an AWB (Air Waybill) using Shiprocket's "adhoc" API.
|
|
132
|
+
3. If successful, the **Tracking Number** and **Tracking URL** are saved to the fulfillment in Medusa.
|
|
133
|
+
|
|
134
|
+
## 🐛 Troubleshooting
|
|
135
|
+
|
|
136
|
+
### "Rate calculation failed"
|
|
137
|
+
- Ensure both the **Store Address** (Pickup) and **Customer Address** (Delivery) have valid 6-digit Indian pincodes.
|
|
138
|
+
- Check that the `weight` is set on your Product Variants (in grams or per your Shiprocket config). Shiprocket requires weight to calculate rates.
|
|
139
|
+
|
|
140
|
+
### "Authentication failed"
|
|
141
|
+
- Double-check your `SHIPROCKET_EMAIL` and `SHIPROCKET_PASSWORD` in `.env`.
|
|
142
|
+
- The plugin auto-refreshes tokens, but invalid credentials will block this.
|
|
143
|
+
|
|
144
|
+
### Scheduled Job: Token Refresh
|
|
145
|
+
|
|
146
|
+
The plugin includes a scheduled job (`refresh-shiprocket-token`) that automatically refreshes the Shiprocket authentication token every 8 days. This job runs automatically and ensures uninterrupted service. No manual configuration is required.
|
|
147
|
+
|
|
148
|
+
## 📝 Changelog
|
|
149
|
+
|
|
150
|
+
### Version 0.0.1
|
|
151
|
+
|
|
152
|
+
- Initial release
|
|
153
|
+
- **Fixed**: Resolved TypeScript import errors for Medusa v2.11.2 compatibility
|
|
154
|
+
- **Improved**: Replaced all `any` types with proper TypeScript interfaces for better type safety
|
|
155
|
+
- **Improved**: Added comprehensive error handling to all fulfillment methods
|
|
156
|
+
- **Improved**: Enhanced error handling in document retrieval methods
|
|
157
|
+
- **Changed**: Updated Medusa framework dependencies to v2.11.2
|
|
158
|
+
- **Removed**: Unused placeholder API routes
|
|
159
|
+
- Basic fulfillment provider implementation
|
|
160
|
+
- Rate calculation support
|
|
161
|
+
- Order creation and AWB assignment
|
|
162
|
+
- Document generation (labels, manifests, invoices)
|
|
163
|
+
- Return fulfillment support
|
|
164
|
+
- Token refresh mechanism
|
|
165
|
+
|
|
166
|
+
## 🤝 Contributing
|
|
167
|
+
|
|
168
|
+
Contributions are welcome! If you find a bug or want to add a feature:
|
|
169
|
+
|
|
170
|
+
1. Fork the repository.
|
|
171
|
+
2. Create a feature branch (`git checkout -b feature/amazing-feature`).
|
|
172
|
+
3. Commit your changes.
|
|
173
|
+
4. Open a Pull Request.
|
|
174
|
+
|
|
175
|
+
## 📄 License
|
|
176
|
+
|
|
177
|
+
This project is licensed under the [MIT License](LICENSE).
|
|
178
|
+
|
|
179
|
+
---
|
|
180
|
+
|
|
181
|
+
<p align="center">
|
|
182
|
+
Built with ❤️ by <a href="https://github.com/SAM-AEL">SAM-AEL</a>
|
|
183
|
+
</p>
|
package/package.json
ADDED
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "medusa-shiprocket-fulfillment-sbl",
|
|
3
|
+
"version": "0.0.1",
|
|
4
|
+
"description": "Shiprocket Fulfillment Provider Plugin for MedusaJS 2",
|
|
5
|
+
"author": "SAM-AEL",
|
|
6
|
+
"homepage": "https://github.com/SAM-AEL",
|
|
7
|
+
"repository": "https://github.com/SAM-AEL/medusa-shiprocket-fulfillment-plugin-sbl",
|
|
8
|
+
"license": "MIT",
|
|
9
|
+
"files": [
|
|
10
|
+
".medusa/server"
|
|
11
|
+
],
|
|
12
|
+
"main": ".medusa/server/src/providers/shiprocket/index.js",
|
|
13
|
+
"exports": {
|
|
14
|
+
".": "./.medusa/server/src/providers/shiprocket/index.js",
|
|
15
|
+
"./package.json": "./package.json",
|
|
16
|
+
"./workflows": "./.medusa/server/src/workflows/index.js",
|
|
17
|
+
"./.medusa/server/src/modules/*": "./.medusa/server/src/modules/*/index.js",
|
|
18
|
+
"./modules/*": "./.medusa/server/src/modules/*/index.js",
|
|
19
|
+
"./providers/*": "./.medusa/server/src/providers/*/index.js",
|
|
20
|
+
"./*": "./.medusa/server/src/*.js",
|
|
21
|
+
"./admin": {
|
|
22
|
+
"import": "./.medusa/server/src/admin/index.mjs",
|
|
23
|
+
"require": "./.medusa/server/src/admin/index.js",
|
|
24
|
+
"default": "./.medusa/server/src/admin/index.js"
|
|
25
|
+
}
|
|
26
|
+
},
|
|
27
|
+
"keywords": [
|
|
28
|
+
"medusa",
|
|
29
|
+
"plugin",
|
|
30
|
+
"medusa-plugin",
|
|
31
|
+
"medusa-v2",
|
|
32
|
+
"medusa-plugin-shipping"
|
|
33
|
+
],
|
|
34
|
+
"scripts": {
|
|
35
|
+
"build": "medusa plugin:build",
|
|
36
|
+
"dev": "medusa plugin:develop",
|
|
37
|
+
"prepublishOnly": "medusa plugin:build"
|
|
38
|
+
},
|
|
39
|
+
"devDependencies": {
|
|
40
|
+
"@medusajs/admin-sdk": "2.11.2",
|
|
41
|
+
"@medusajs/cli": "2.11.2",
|
|
42
|
+
"@medusajs/framework": "2.11.2",
|
|
43
|
+
"@medusajs/icons": "2.11.2",
|
|
44
|
+
"@medusajs/medusa": "2.11.2",
|
|
45
|
+
"@medusajs/test-utils": "2.11.2",
|
|
46
|
+
"@medusajs/ui": "4.0.25",
|
|
47
|
+
"@mikro-orm/cli": "6.4.3",
|
|
48
|
+
"@mikro-orm/core": "6.4.3",
|
|
49
|
+
"@mikro-orm/knex": "6.4.3",
|
|
50
|
+
"@mikro-orm/migrations": "6.4.3",
|
|
51
|
+
"@mikro-orm/postgresql": "6.4.3",
|
|
52
|
+
"@swc/core": "1.5.7",
|
|
53
|
+
"@types/node": "^20.0.0",
|
|
54
|
+
"@types/react": "^18.3.2",
|
|
55
|
+
"@types/react-dom": "^18.2.25",
|
|
56
|
+
"awilix": "^8.0.1",
|
|
57
|
+
"pg": "^8.13.0",
|
|
58
|
+
"prop-types": "^15.8.1",
|
|
59
|
+
"react": "^18.2.0",
|
|
60
|
+
"react-dom": "^18.2.0",
|
|
61
|
+
"ts-node": "^10.9.2",
|
|
62
|
+
"typescript": "^5.6.2",
|
|
63
|
+
"vite": "^5.2.11",
|
|
64
|
+
"yalc": "^1.0.0-pre.53"
|
|
65
|
+
},
|
|
66
|
+
"peerDependencies": {
|
|
67
|
+
"@medusajs/admin-sdk": "2.11.2",
|
|
68
|
+
"@medusajs/cli": "2.11.2",
|
|
69
|
+
"@medusajs/framework": "2.11.2",
|
|
70
|
+
"@medusajs/icons": "2.11.2",
|
|
71
|
+
"@medusajs/medusa": "2.11.2",
|
|
72
|
+
"@medusajs/test-utils": "2.11.2",
|
|
73
|
+
"@medusajs/ui": "4.0.25",
|
|
74
|
+
"@mikro-orm/cli": "6.4.3",
|
|
75
|
+
"@mikro-orm/core": "6.4.3",
|
|
76
|
+
"@mikro-orm/knex": "6.4.3",
|
|
77
|
+
"@mikro-orm/migrations": "6.4.3",
|
|
78
|
+
"@mikro-orm/postgresql": "6.4.3",
|
|
79
|
+
"awilix": "^8.0.1",
|
|
80
|
+
"pg": "^8.13.0"
|
|
81
|
+
},
|
|
82
|
+
"engines": {
|
|
83
|
+
"node": ">=20"
|
|
84
|
+
}
|
|
85
|
+
}
|