multermate 1.0.2 → 1.0.4

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.
Files changed (5) hide show
  1. package/LICENSE +21 -21
  2. package/index.js +208 -197
  3. package/package.json +9 -2
  4. package/readme.md +259 -0
  5. package/README.md +0 -159
package/LICENSE CHANGED
@@ -1,21 +1,21 @@
1
- MIT License
2
-
3
- Copyright (c) 2024 Wasim Zaman
4
-
5
- Permission is hereby granted, free of charge, to any person obtaining a copy
6
- of this software and associated documentation files (the "Software"), to deal
7
- in the Software without restriction, including without limitation the rights
8
- to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
- copies of the Software, and to permit persons to whom the Software is
10
- furnished to do so, subject to the following conditions:
11
-
12
- The above copyright notice and this permission notice shall be included in all
13
- copies or substantial portions of the Software.
14
-
15
- THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
- IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
- FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
- AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
- LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
- OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
- SOFTWARE.
1
+ MIT License
2
+
3
+ Copyright (c) 2024 Wasim Zaman
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/index.js CHANGED
@@ -1,197 +1,208 @@
1
- const path = require("path");
2
- const multer = require("multer");
3
- const { v4: uuidv4 } = require("uuid");
4
-
5
- // Constants for allowed MIME types
6
- const ALLOWED_MIME_TYPES = {
7
- images: ["image/jpeg", "image/jpg", "image/png", "image/gif"],
8
- videos: ["video/mp4", "video/mpeg", "video/ogg", "video/webm", "video/avi"],
9
- pdfs: ["application/pdf"],
10
- all: [
11
- "image/jpeg",
12
- "image/jpg",
13
- "image/png",
14
- "image/gif",
15
- "video/mp4",
16
- "video/mpeg",
17
- "video/ogg",
18
- "video/webm",
19
- "video/avi",
20
- "application/pdf",
21
- ],
22
- };
23
-
24
- /**
25
- * Function to configure storage for Multer.
26
- *
27
- * @param {string} destination - The destination folder where files will be stored. Default is "uploads".
28
- * @returns {object} - Multer storage configuration object.
29
- */
30
- const configureStorage = (destination) => {
31
- return multer.diskStorage({
32
- destination: (req, file, cb) => {
33
- cb(null, destination || "uploads"); // Default folder is "uploads" if none is provided.
34
- },
35
- filename: (req, file, cb) => {
36
- const sanitizedFilename = file.originalname.replace(/\\/g, "/");
37
- const extension = path.extname(sanitizedFilename);
38
- const fieldName = file.fieldname || "file"; // Use the field name as part of the filename.
39
- const uniqueName = uuidv4(); // Generate a unique name using uuid.
40
- let fileName = `${uniqueName}-${fieldName}${extension}`;
41
-
42
- // Replace backslashes with forward slashes in the final filename
43
- fileName = fileName.replace(/\\/g, "/");
44
-
45
- cb(null, fileName); // Set the final filename.
46
- },
47
- });
48
- };
49
-
50
- /**
51
- * Function to configure file filter for Multer.
52
- *
53
- * @param {Array} allowedMimeTypes - Array of allowed MIME types.
54
- * @returns {function} - File filter function for Multer.
55
- */
56
- const configureFileFilter = (allowedMimeTypes) => {
57
- return (req, file, cb) => {
58
- if (allowedMimeTypes.includes(file.mimetype)) {
59
- cb(null, true); // Allow the file if its MIME type is allowed.
60
- } else {
61
- cb(
62
- new Error("Invalid file type. Only specified file types are allowed."),
63
- false
64
- ); // Reject the file if its MIME type is not allowed.
65
- }
66
- };
67
- };
68
-
69
- /**
70
- * Function to configure Multer with the provided options.
71
- *
72
- * @param {object} options - Configuration options for Multer.
73
- * @param {string} [options.destination] - Destination folder for files. Default is "uploads".
74
- * @param {string} [options.filename] - Custom filename template for saved files.
75
- * @param {Array<string>} [options.fileTypes] - Array of file types to allow (e.g., ['images', 'videos']).
76
- * @param {Array<string>} [options.customMimeTypes] - Array of custom MIME types to allow.
77
- * @param {number} [options.fileSizeLimit] - Maximum file size allowed (in bytes). Default is 50MB.
78
- * @param {boolean} [options.preservePath] - Preserve the full path of files. Default is false.
79
- * @returns {object} - Multer instance configured with the provided options.
80
- */
81
- const configureMulter = ({
82
- destination,
83
- filename,
84
- fileTypes = [],
85
- customMimeTypes = [],
86
- fileSizeLimit,
87
- preservePath = false,
88
- }) => {
89
- const storage = configureStorage(destination);
90
-
91
- // Combine allowed MIME types based on fileTypes array
92
- let allowedMimeTypes = [];
93
-
94
- if (customMimeTypes.length > 0) {
95
- // Use custom MIME types if provided
96
- allowedMimeTypes = customMimeTypes;
97
- } else {
98
- // Use default MIME types for specified fileTypes
99
- fileTypes.forEach((type) => {
100
- if (ALLOWED_MIME_TYPES[type]) {
101
- allowedMimeTypes = allowedMimeTypes.concat(ALLOWED_MIME_TYPES[type]);
102
- }
103
- });
104
-
105
- // If no specific file types are provided, use all allowed MIME types
106
- if (allowedMimeTypes.length === 0) {
107
- allowedMimeTypes = ALLOWED_MIME_TYPES.all;
108
- }
109
- }
110
-
111
- const fileFilter = configureFileFilter(allowedMimeTypes);
112
-
113
- return multer({
114
- storage,
115
- fileFilter,
116
- limits: { fileSize: fileSizeLimit || 1024 * 1024 * 50 }, // Default 50MB file size limit
117
- preservePath,
118
- });
119
- };
120
-
121
- /**
122
- * Function to handle multiple fields in a single form submission.
123
- *
124
- * @param {Array} fields - Array of field configurations, each containing:
125
- * @param {string} fields.name - The name of the form field.
126
- * @param {number} [fields.maxCount=10] - The maximum number of files to accept per field.
127
- * @param {Array<string>} [fields.fileTypes] - Array of file types to allow for this field (e.g., ['images']).
128
- * @returns {function} - Multer instance configured to handle multiple fields.
129
- */
130
- const uploadFields = (fields) => {
131
- const fieldConfigs = fields.map((field) => ({
132
- name: field.name,
133
- maxCount: field.maxCount || 10, // Default maxCount is 10 if not specified.
134
- }));
135
-
136
- let allowedFileTypes = [];
137
-
138
- fields.forEach((field) => {
139
- const types = field.fileTypes || [];
140
- types.forEach((type) => {
141
- if (ALLOWED_MIME_TYPES[type]) {
142
- allowedFileTypes = allowedFileTypes.concat(ALLOWED_MIME_TYPES[type]);
143
- }
144
- });
145
- });
146
-
147
- const multerInstance = configureMulter({
148
- fileTypes: allowedFileTypes,
149
- customMimeTypes: [],
150
- fileSizeLimit: fields[0]?.fileSizeLimit, // Assuming all fields share the same limit.
151
- });
152
-
153
- return multerInstance.fields(fieldConfigs);
154
- };
155
-
156
- // Export functions to configure multer and available file types
157
- module.exports = {
158
- /**
159
- * Function to handle a single file upload.
160
- *
161
- * @param {object} options - Configuration options for the single file upload.
162
- * @param {string} [options.destination] - Destination folder for the uploaded file.
163
- * @param {string} [options.filename] - Custom filename template for the uploaded file.
164
- * @param {Array<string>} [options.fileTypes] - Array of file types to allow (e.g., ['images']).
165
- * @param {Array<string>} [options.customMimeTypes] - Array of custom MIME types to allow.
166
- * @param {number} [options.fileSizeLimit] - Maximum file size allowed (in bytes). Default is 50MB.
167
- * @param {boolean} [options.preservePath] - Preserve the full path of the uploaded file. Default is false.
168
- * @returns {function} - Multer instance configured for single file upload.
169
- */
170
- uploadSingle: (options = {}) => {
171
- const multerInstance = configureMulter(options);
172
- return multerInstance.single(options.filename || "file");
173
- },
174
-
175
- /**
176
- * Function to handle multiple file uploads across multiple fields.
177
- *
178
- * @param {object} options - Configuration options for multiple file uploads.
179
- * @param {Array<object>} options.fields - Array of field configurations for multiple file uploads.
180
- * @param {string} [options.destination] - Destination folder for the uploaded files.
181
- * @param {Array<string>} [options.customMimeTypes] - Array of custom MIME types to allow.
182
- * @param {number} [options.fileSizeLimit] - Maximum file size allowed (in bytes). Default is 50MB.
183
- * @param {boolean} [options.preservePath] - Preserve the full path of the uploaded files. Default is false.
184
- * @returns {function} - Multer instance configured for multiple file uploads.
185
- */
186
- uploadMultiple: (options = {}) => {
187
- const multerInstance = configureMulter(options);
188
- return multerInstance.fields(options.fields || []);
189
- },
190
-
191
- /**
192
- * Export the allowed file types for reference.
193
- *
194
- * @type {Array<string>}
195
- */
196
- ALLOWED_FILE_TYPES: Object.keys(ALLOWED_MIME_TYPES),
197
- };
1
+ const path =
2
+ typeof require !== "undefined"
3
+ ? require("path")
4
+ : (await import("path")).default;
5
+ const multer =
6
+ typeof require !== "undefined"
7
+ ? require("multer")
8
+ : (await import("multer")).default;
9
+ const { v4: uuidv4 } =
10
+ typeof require !== "undefined" ? require("uuid") : await import("uuid");
11
+ const fs =
12
+ typeof require !== "undefined"
13
+ ? require("fs/promises")
14
+ : await import("fs/promises");
15
+
16
+ // Constants for allowed MIME types
17
+ const ALLOWED_MIME_TYPES = {
18
+ images: ["image/jpeg", "image/jpg", "image/png", "image/gif"],
19
+ videos: ["video/mp4", "video/mpeg", "video/ogg", "video/webm", "video/avi"],
20
+ pdfs: ["application/pdf"],
21
+ all: [
22
+ "image/jpeg",
23
+ "image/jpg",
24
+ "image/png",
25
+ "image/gif",
26
+ "video/mp4",
27
+ "video/mpeg",
28
+ "video/ogg",
29
+ "video/webm",
30
+ "video/avi",
31
+ "application/pdf",
32
+ ],
33
+ };
34
+
35
+ /**
36
+ * Function to configure storage for Multer.
37
+ *
38
+ * @param {string} destination - The destination folder where files will be stored. Default is "uploads".
39
+ * @returns {object} - Multer storage configuration object.
40
+ */
41
+ const configureStorage = (destination) => {
42
+ return multer.diskStorage({
43
+ destination: (req, file, cb) => {
44
+ cb(null, destination || "uploads"); // Default folder is "uploads" if none is provided.
45
+ },
46
+ filename: (req, file, cb) => {
47
+ const sanitizedFilename = file.originalname.replace(/\\/g, "/");
48
+ const extension = path.extname(sanitizedFilename);
49
+ const fieldName = file.fieldname || "file"; // Use the field name as part of the filename.
50
+ const uniqueName = uuidv4(); // Generate a unique name using uuid.
51
+ let fileName = `${uniqueName}-${fieldName}${extension}`;
52
+
53
+ // Replace backslashes with forward slashes in the final filename
54
+ fileName = fileName.replace(/\\/g, "/");
55
+
56
+ cb(null, fileName); // Set the final filename.
57
+ },
58
+ });
59
+ };
60
+
61
+ /**
62
+ * Function to configure file filter for Multer.
63
+ *
64
+ * @param {Array} allowedMimeTypes - Array of allowed MIME types.
65
+ * @returns {function} - File filter function for Multer.
66
+ */
67
+ const configureFileFilter = (allowedMimeTypes) => {
68
+ return (req, file, cb) => {
69
+ if (allowedMimeTypes.includes(file.mimetype)) {
70
+ cb(null, true); // Allow the file if its MIME type is allowed.
71
+ } else {
72
+ cb(
73
+ new Error("Invalid file type. Only specified file types are allowed."),
74
+ false
75
+ ); // Reject the file if its MIME type is not allowed.
76
+ }
77
+ };
78
+ };
79
+
80
+ /**
81
+ * Function to configure Multer with the provided options.
82
+ *
83
+ * @param {object} options - Configuration options for Multer.
84
+ * @param {string} [options.destination] - Destination folder for files. Default is "uploads".
85
+ * @param {string} [options.filename] - Custom filename template for saved files.
86
+ * @param {Array<string>} [options.fileTypes] - Array of file types to allow (e.g., ['images', 'videos']).
87
+ * @param {Array<string>} [options.customMimeTypes] - Array of custom MIME types to allow.
88
+ * @param {number} [options.fileSizeLimit] - Maximum file size allowed (in bytes). Default is 50MB.
89
+ * @param {boolean} [options.preservePath] - Preserve the full path of files. Default is false.
90
+ * @returns {object} - Multer instance configured with the provided options.
91
+ */
92
+ const configureMulter = ({
93
+ destination,
94
+ filename,
95
+ fileTypes = [],
96
+ customMimeTypes = [],
97
+ fileSizeLimit,
98
+ preservePath = false,
99
+ }) => {
100
+ const storage = configureStorage(destination);
101
+
102
+ // Combine allowed MIME types based on fileTypes array
103
+ let allowedMimeTypes = [];
104
+
105
+ if (customMimeTypes.length > 0) {
106
+ // Use custom MIME types if provided
107
+ allowedMimeTypes = customMimeTypes;
108
+ } else {
109
+ // Use default MIME types for specified fileTypes
110
+ fileTypes.forEach((type) => {
111
+ if (ALLOWED_MIME_TYPES[type]) {
112
+ allowedMimeTypes = allowedMimeTypes.concat(ALLOWED_MIME_TYPES[type]);
113
+ }
114
+ });
115
+
116
+ // If no specific file types are provided, use all allowed MIME types
117
+ if (allowedMimeTypes.length === 0) {
118
+ allowedMimeTypes = ALLOWED_MIME_TYPES.all;
119
+ }
120
+ }
121
+
122
+ const fileFilter = configureFileFilter(allowedMimeTypes);
123
+
124
+ return multer({
125
+ storage,
126
+ fileFilter,
127
+ limits: { fileSize: fileSizeLimit || 1024 * 1024 * 50 }, // Default 50MB file size limit
128
+ preservePath,
129
+ });
130
+ };
131
+
132
+ /**
133
+ * Function to handle multiple fields in a single form submission.
134
+ *
135
+ * @param {Array} fields - Array of field configurations, each containing:
136
+ * @param {string} fields.name - The name of the form field.
137
+ * @param {number} [fields.maxCount=10] - The maximum number of files to accept per field.
138
+ * @param {Array<string>} [fields.fileTypes] - Array of file types to allow for this field (e.g., ['images']).
139
+ * @returns {function} - Multer instance configured to handle multiple fields.
140
+ */
141
+ const uploadFields = (fields) => {
142
+ const fieldConfigs = fields.map((field) => ({
143
+ name: field.name,
144
+ maxCount: field.maxCount || 10, // Default maxCount is 10 if not specified.
145
+ }));
146
+
147
+ let allowedFileTypes = [];
148
+
149
+ fields.forEach((field) => {
150
+ const types = field.fileTypes || [];
151
+ types.forEach((type) => {
152
+ if (ALLOWED_MIME_TYPES[type]) {
153
+ allowedFileTypes = allowedFileTypes.concat(ALLOWED_MIME_TYPES[type]);
154
+ }
155
+ });
156
+ });
157
+
158
+ const multerInstance = configureMulter({
159
+ fileTypes: allowedFileTypes,
160
+ customMimeTypes: [],
161
+ fileSizeLimit: fields[0]?.fileSizeLimit, // Assuming all fields share the same limit.
162
+ });
163
+
164
+ return multerInstance.fields(fieldConfigs);
165
+ };
166
+
167
+ /**
168
+ * Utility function to delete a file from the filesystem
169
+ *
170
+ * @param {string} filePath - The path to the file that needs to be deleted
171
+ * @returns {Promise<boolean>} - Returns true if deletion was successful, false otherwise
172
+ */
173
+ const deleteFile = async (filePath) => {
174
+ try {
175
+ await fs.unlink(filePath);
176
+ return true;
177
+ } catch (error) {
178
+ console.error(`Error deleting file: ${error.message}`);
179
+ return false;
180
+ }
181
+ };
182
+
183
+ const exportObject = {
184
+ uploadSingle: (options = {}) => {
185
+ const multerInstance = configureMulter(options);
186
+ return multerInstance.single(options.filename || "file");
187
+ },
188
+
189
+ uploadMultiple: (options = {}) => {
190
+ const multerInstance = configureMulter(options);
191
+ return multerInstance.fields(options.fields || []);
192
+ },
193
+
194
+ ALLOWED_FILE_TYPES: Object.keys(ALLOWED_MIME_TYPES),
195
+ deleteFile,
196
+ };
197
+
198
+ // Dual export support
199
+ if (typeof module !== "undefined" && module.exports) {
200
+ module.exports = exportObject;
201
+ } else {
202
+ Object.assign(globalThis, {
203
+ uploadSingle: exportObject.uploadSingle,
204
+ uploadMultiple: exportObject.uploadMultiple,
205
+ ALLOWED_FILE_TYPES: exportObject.ALLOWED_FILE_TYPES,
206
+ deleteFile: exportObject.deleteFile,
207
+ });
208
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "multermate",
3
- "version": "1.0.2",
3
+ "version": "1.0.4",
4
4
  "description": "A flexible and customizable npm package for configuring Multer",
5
5
  "main": "index.js",
6
6
  "scripts": {
@@ -26,5 +26,12 @@
26
26
  "bugs": {
27
27
  "url": "https://github.com/Wasim-Zaman/multermate/issues"
28
28
  },
29
- "homepage": "https://github.com/Wasim-Zaman/multermate#readme"
29
+ "homepage": "https://github.com/Wasim-Zaman/multermate#readme",
30
+ "type": "commonjs",
31
+ "exports": {
32
+ ".": {
33
+ "require": "./index.js",
34
+ "import": "./index.js"
35
+ }
36
+ }
30
37
  }
package/readme.md ADDED
@@ -0,0 +1,259 @@
1
+ # Multer Mate
2
+
3
+ A robust and flexible file upload utility built on top of Multer, providing advanced file handling capabilities for Node.js applications.
4
+
5
+ ## Features
6
+
7
+ - 📁 Flexible file storage configuration
8
+ - 🔒 Built-in file type validation
9
+ - 📦 Single and multiple file uploads
10
+ - 🎯 Field-specific file type restrictions
11
+ - 🗑️ File deletion utility
12
+ - ⚡ Configurable file size limits
13
+ - 🎨 Custom MIME type support
14
+ - 🔄 Unique file naming with UUID
15
+ - 🛡️ Path sanitization
16
+ - 📝 Comprehensive error handling
17
+
18
+ ## Installation
19
+
20
+ ```bash
21
+ npm install multermate
22
+ ```
23
+
24
+ ## Basic Usage
25
+
26
+ ```javascript
27
+ // CommonJS
28
+ const { uploadSingle, uploadMultiple, deleteFile } = require("multermate");
29
+
30
+ // ES Modules
31
+ import { uploadSingle, uploadMultiple, deleteFile } from "multermate";
32
+ ```
33
+
34
+ ## Upload Configurations
35
+
36
+ ### Single File Upload
37
+
38
+ ```javascript
39
+ // Basic single file upload
40
+ app.post("/upload", uploadSingle(), (req, res) => {
41
+ res.json({ file: req.file });
42
+ });
43
+
44
+ // Advanced single file upload
45
+ app.post(
46
+ "/upload/advanced",
47
+ uploadSingle({
48
+ destination: "uploads/images",
49
+ filename: "profile",
50
+ fileTypes: ["images"],
51
+ fileSizeLimit: 5 * 1024 * 1024, // 5MB
52
+ preservePath: false,
53
+ }),
54
+ (req, res) => {
55
+ res.json({ file: req.file });
56
+ }
57
+ );
58
+ ```
59
+
60
+ ### Multiple Files Upload
61
+
62
+ ```javascript
63
+ // Multiple fields with different configurations
64
+ app.post(
65
+ "/upload/multiple",
66
+ uploadMultiple({
67
+ fields: [
68
+ {
69
+ name: "avatar",
70
+ maxCount: 1,
71
+ fileTypes: ["images"],
72
+ },
73
+ {
74
+ name: "documents",
75
+ maxCount: 5,
76
+ fileTypes: ["pdfs"],
77
+ },
78
+ {
79
+ name: "media",
80
+ maxCount: 3,
81
+ fileTypes: ["images", "videos"],
82
+ },
83
+ ],
84
+ destination: "uploads/mixed",
85
+ fileSizeLimit: 10 * 1024 * 1024, // 10MB per file
86
+ }),
87
+ (req, res) => {
88
+ res.json({ files: req.files });
89
+ }
90
+ );
91
+ ```
92
+
93
+ ### Custom MIME Types
94
+
95
+ ```javascript
96
+ app.post(
97
+ "/upload/custom",
98
+ uploadSingle({
99
+ destination: "uploads/custom",
100
+ customMimeTypes: [
101
+ "application/vnd.ms-excel",
102
+ "application/json",
103
+ "text/csv",
104
+ ],
105
+ fileSizeLimit: 1024 * 1024, // 1MB
106
+ })
107
+ );
108
+ ```
109
+
110
+ ### File Deletion
111
+
112
+ ```javascript
113
+ // Simple file deletion
114
+ app.delete("/files/:filename", async (req, res) => {
115
+ const isDeleted = await deleteFile(`uploads/${req.params.filename}`);
116
+ res.json({ success: isDeleted });
117
+ });
118
+
119
+ // Advanced file deletion with error handling
120
+ app.delete("/files/:type/:filename", async (req, res) => {
121
+ try {
122
+ const filePath = path.join("uploads", req.params.type, req.params.filename);
123
+ const isDeleted = await deleteFile(filePath);
124
+
125
+ if (isDeleted) {
126
+ res.json({
127
+ success: true,
128
+ message: "File deleted successfully",
129
+ });
130
+ } else {
131
+ res.status(404).json({
132
+ success: false,
133
+ message: "File not found or unable to delete",
134
+ });
135
+ }
136
+ } catch (error) {
137
+ res.status(500).json({
138
+ success: false,
139
+ message: error.message,
140
+ });
141
+ }
142
+ });
143
+ ```
144
+
145
+ ## API Reference
146
+
147
+ ### uploadSingle(options)
148
+
149
+ Configures single file upload with the following options:
150
+
151
+ | Option | Type | Default | Description |
152
+ | --------------- | -------- | --------- | ---------------------- |
153
+ | destination | string | 'uploads' | Upload directory path |
154
+ | filename | string | 'file' | Form field name |
155
+ | fileTypes | string[] | ['all'] | Allowed file types |
156
+ | customMimeTypes | string[] | [] | Custom MIME types |
157
+ | fileSizeLimit | number | 50MB | Max file size in bytes |
158
+ | preservePath | boolean | false | Preserve original path |
159
+
160
+ ### uploadMultiple(options)
161
+
162
+ Configures multiple file uploads with the following options:
163
+
164
+ | Option | Type | Default | Description |
165
+ | --------------- | -------- | --------- | -------------------- |
166
+ | fields | Field[] | [] | Field configurations |
167
+ | destination | string | 'uploads' | Upload directory |
168
+ | customMimeTypes | string[] | [] | Custom MIME types |
169
+ | fileSizeLimit | number | 50MB | Max file size |
170
+ | preservePath | boolean | false | Preserve paths |
171
+
172
+ #### Field Configuration
173
+
174
+ | Option | Type | Default | Description |
175
+ | --------- | -------- | ------- | --------------------- |
176
+ | name | string | - | Field name (required) |
177
+ | maxCount | number | 10 | Max files per field |
178
+ | fileTypes | string[] | ['all'] | Allowed types |
179
+
180
+ ### deleteFile(filePath)
181
+
182
+ Deletes a file from the filesystem:
183
+
184
+ | Parameter | Type | Description |
185
+ | --------- | ---------------- | ---------------- |
186
+ | filePath | string | Path to file |
187
+ | Returns | Promise<boolean> | Deletion success |
188
+
189
+ ### Supported File Types
190
+
191
+ ```javascript
192
+ const ALLOWED_FILE_TYPES = {
193
+ images: ["jpeg", "jpg", "png", "gif"],
194
+ videos: ["mp4", "mpeg", "ogg", "webm", "avi"],
195
+ pdfs: ["pdf"],
196
+ };
197
+ ```
198
+
199
+ ## Error Handling
200
+
201
+ ```javascript
202
+ app.post("/upload", uploadSingle(), (req, res) => {
203
+ try {
204
+ // File size validation
205
+ if (req.fileValidationError) {
206
+ return res.status(400).json({
207
+ error: req.fileValidationError,
208
+ });
209
+ }
210
+
211
+ // File existence check
212
+ if (!req.file) {
213
+ return res.status(400).json({
214
+ error: "No file uploaded",
215
+ });
216
+ }
217
+
218
+ // Success response
219
+ res.json({
220
+ success: true,
221
+ file: {
222
+ filename: req.file.filename,
223
+ path: req.file.path,
224
+ size: req.file.size,
225
+ mimetype: req.file.mimetype,
226
+ },
227
+ });
228
+ } catch (error) {
229
+ res.status(500).json({
230
+ error: error.message,
231
+ });
232
+ }
233
+ });
234
+ ```
235
+
236
+ ## Best Practices
237
+
238
+ 1. Always implement proper error handling
239
+ 2. Set appropriate file size limits
240
+ 3. Validate file types on the server
241
+ 4. Use custom storage destinations for different file types
242
+ 5. Implement file cleanup mechanisms
243
+ 6. Consider implementing file type verification beyond MIME types
244
+
245
+ ## License
246
+
247
+ MIT
248
+
249
+ ## Contributing
250
+
251
+ Contributions are welcome! Please feel free to submit issues and pull requests.
252
+
253
+ ## Author
254
+
255
+ Wasim Zaman
256
+
257
+ ## Support
258
+
259
+ For support, please open an issue in the GitHub repository.
package/README.md DELETED
@@ -1,159 +0,0 @@
1
- # Multer Mate
2
-
3
- `multermate` is a flexible and customizable npm package for configuring Multer, a Node.js middleware for handling `multipart/form-data` (file uploads). This package allows you to easily configure Multer for various use cases, including storing files in different directories and specifying allowed file types.
4
-
5
- ## Features
6
-
7
- - Customizable storage destinations
8
- - Unique file naming using `uuid`
9
- - Support for various file types (images, videos, PDFs, etc.)
10
- - Configurable file size limits
11
- - Single and multiple file uploads
12
- - Specify custom MIME types within broader categories
13
- - Default behavior for allowing all MIME types if none specified
14
-
15
- ## Installation
16
-
17
- Install the package using npm:
18
-
19
- ```bash
20
- npm install multermate
21
- ```
22
-
23
- ## Usage
24
-
25
- ### Import the package
26
-
27
- ```javascript
28
- const {
29
- uploadSingle,
30
- uploadMultiple,
31
- ALLOWED_FILE_TYPES,
32
- } = require("multermate");
33
- ```
34
-
35
- ### Single File Upload
36
-
37
- ```javascript
38
- const express = require("express");
39
- const { uploadSingle } = require("multermate");
40
-
41
- const app = express();
42
-
43
- app.post(
44
- "/upload/single",
45
- uploadSingle({
46
- destination: "uploads/images",
47
- filename: "image",
48
- fileTypes: ["images"],
49
- fileSizeLimit: 1024 * 1024 * 10, // 10MB limit
50
- }),
51
- (req, res) => {
52
- res.send("Single file uploaded!");
53
- }
54
- );
55
-
56
- app.listen(3000, () => {
57
- console.log("Server started on http://localhost:3000");
58
- });
59
- ```
60
-
61
- ### Multiple Files Upload (Mixed File Types)
62
-
63
- ```javascript
64
- const express = require("express");
65
- const { uploadMultiple } = require("multermate");
66
-
67
- const app = express();
68
-
69
- app.post(
70
- "/upload/multiple",
71
- uploadMultiple({
72
- fields: [
73
- { name: "media", maxCount: 1, fileTypes: ["images", "videos"] },
74
- { name: "pdf", maxCount: 1, fileTypes: ["pdfs"] },
75
- ],
76
- }),
77
- (req, res) => {
78
- res.send("Multiple files uploaded!");
79
- }
80
- );
81
-
82
- app.listen(3000, () => {
83
- console.log("Server started on http://localhost:3000");
84
- });
85
- ```
86
-
87
- ### Custom MIME Types (e.g., Only PNGs and PDFs)
88
-
89
- ```javascript
90
- const express = require("express");
91
- const { uploadSingle, uploadMultiple } = require("multermate");
92
-
93
- const app = express();
94
-
95
- // Single PNG or PDF file upload
96
- app.post(
97
- "/upload-custom",
98
- uploadSingle({
99
- destination: "uploads/custom",
100
- customMimeTypes: ["image/png", "application/pdf"],
101
- fileSizeLimit: 1024 * 1024 * 15, // 15MB limit
102
- }),
103
- (req, res) => {
104
- res.send("PNG or PDF file uploaded!");
105
- }
106
- );
107
-
108
- // Multiple PNGs or PDFs upload
109
- app.post(
110
- "/upload-custom-multiple",
111
- uploadMultiple({
112
- fields: [
113
- { name: "images", maxCount: 5, customMimeTypes: ["image/png"] },
114
- { name: "pdfs", maxCount: 2, customMimeTypes: ["application/pdf"] },
115
- ],
116
- }),
117
- (req, res) => {
118
- res.send("PNG images and PDF files uploaded!");
119
- }
120
- );
121
-
122
- app.listen(3000, () => {
123
- console.log("Server started on http://localhost:3000");
124
- });
125
- ```
126
-
127
- ### Default Behavior (Allow All MIME Types)
128
-
129
- ```javascript
130
- const express = require("express");
131
- const { uploadSingle, uploadMultiple } = require("multermate");
132
-
133
- const app = express();
134
-
135
- // Single file upload (default behavior allows all MIME types)
136
- app.post("/upload", uploadSingle(), (req, res) => {
137
- res.send("File uploaded!");
138
- });
139
-
140
- // Multiple files upload (default behavior allows all MIME types)
141
- app.post("/upload-multiple", uploadMultiple(), (req, res) => {
142
- res.send("Files uploaded!");
143
- });
144
-
145
- app.listen(3000, () => {
146
- console.log("Server started on http://localhost:3000");
147
- });
148
- ```
149
-
150
- ### Exported Constants
151
-
152
- ```javascript
153
- const { ALLOWED_FILE_TYPES } = require("multermate");
154
- console.log(ALLOWED_FILE_TYPES); // ['images', 'videos', 'pdfs', 'all']
155
- ```
156
-
157
- ## Conclusion
158
-
159
- multermate provides a flexible and easy-to-use configuration for handling file uploads in Node.js applications. Whether you need to handle single or multiple file uploads, restrict uploads to certain file types, or specify custom MIME types, this package has you covered.