Skip to content

File Upload Plugin ​

The File Upload Plugin provides comprehensive file upload and management capabilities for the on-CodeMerge editor, supporting file uploads, downloads, and integration with external storage services.

Features ​

  • File Upload: Upload files with drag & drop support
  • File Download: Download uploaded files with one click
  • File Type Validation: Configurable allowed file types
  • File Size Limits: Customizable maximum file size
  • Server Integration: Real server endpoints or emulation mode
  • File Links: Insert clickable file links in content
  • Progress Tracking: Upload progress indication
  • Error Handling: Comprehensive error management
  • Toolbar Integration: Easy access via toolbar button
  • Keyboard Shortcuts: Quick upload commands

Install and CSS: see Editor API — Getting Started.

Basic Usage ​

javascript
import { Editor, FileUploadPlugin } from 'on-codemerge';

const editor = new Editor(container, {
  plugins: [FileUploadPlugin()],
});

Demo ​


Public API (v2) ​

Factory: FileUploadPlugin(config?) — options: Partial<UploadConfig> & PluginToolbarOpts.

Command
insertFileeditor.command('insertFile')

Keyboard shortcuts ​

ShortcutCommand
Mod-Alt-uinsertFile

Modal: stage a file (name / size) then Upload & insert, or pick from Gallery when endpoints.list is set. Gallery supports delete when endpoints.delete is set (DELETE {delete}/{id}). Upload uses POST multipart file with optional headers. Without endpoints.upload (or with useEmulation: true) uploads stay in-memory for demos.

ts
FileUploadPlugin({
  endpoints: {
    upload: '/api/files/upload',
    download: '/api/files/download', // GET {download}/{id}
    list: '/api/files', // optional gallery
    delete: '/api/files', // optional DELETE {delete}/{id}
  },
  headers: { Authorization: 'Bearer …' },
  maxFileSize: 10 * 1024 * 1024,
  useEmulation: false,
});

Contracts

  • GET list → { items: [{ id, name, url, size?, mime?, thumbUrl? }] }
  • POST upload → { id, name, url, size?, mime? }
  • GET download/{id} → file body

Note: Command insertFile (not insertFileLink).

Supported File Types ​

Default Configuration ​

  • Max File Size: 10MB
  • Allowed Types: All file types (*/*)
  • Mode: Emulation (local storage)

Common File Type Examples ​

javascript
// Images
allowedTypes: ['image/jpeg', 'image/png', 'image/gif', 'image/webp'];

// Documents
allowedTypes: ['application/pdf', 'text/plain', 'application/msword'];

// Archives
allowedTypes: ['application/zip', 'application/x-rar-compressed'];

// Media
allowedTypes: ['video/mp4', 'audio/mpeg', 'audio/wav'];

Examples ​

Basic File Upload ​

javascript
// Simple file upload
const fileUploadPlugin = FileUploadPlugin();
editor.use(fileUploadPlugin);

// Upload file programmatically
const fileInput = document.createElement('input');
fileInput.type = 'file';
fileInput.onchange = async (e) => {
  const file = e.target.files[0];
  if (file) {
    try {
      const uploadedFile = await fileUploader.uploadFile(file);
      console.log('File uploaded:', uploadedFile);
    } catch (error) {
      console.error('Upload failed:', error);
    }
  }
};

Server Integration ​

Custom File Validation ​

javascript
// Custom file validation
const customFileUploader = new FileUploader({
  maxFileSize: 2 * 1024 * 1024, // 2MB
  allowedTypes: ['image/jpeg', 'image/png'],
  useEmulation: true,
});

// Add custom validation
customFileUploader.validateFile = (file) => {
  if (file.name.includes('virus')) {
    throw new Error('Suspicious file name');
  }
  return true;
};

Integration Examples ​

React Integration ​

Vue Integration ​

Styling ​

Default Styles ​

css
/* File upload menu */
.file-upload-menu {
  background: white;
  border: 1px solid #e5e7eb;
  border-radius: 8px;
  box-shadow: 0 10px 15px -3px rgba(0, 0, 0, 0.1);
  padding: 20px;
  max-width: 400px;
}

/* File upload area */
.file-upload-area {
  border: 2px dashed #d1d5db;
  border-radius: 8px;
  padding: 40px 20px;
  text-align: center;
  transition: all 0.2s ease;
  cursor: pointer;
}

.file-upload-area:hover {
  border-color: #3b82f6;
  background-color: #f8fafc;
}

.file-upload-area.dragover {
  border-color: #3b82f6;
  background-color: #eff6ff;
}

/* File link */
.file-link {
  display: inline-flex;
  align-items: center;
  gap: 8px;
  padding: 8px 12px;
  background-color: #f3f4f6;
  border: 1px solid #d1d5db;
  border-radius: 6px;
  color: #374151;
  text-decoration: none;
  cursor: pointer;
  transition: all 0.2s ease;
}

.file-link:hover {
  background-color: #e5e7eb;
  border-color: #9ca3af;
}

/* Upload progress */
.upload-progress {
  background-color: #3b82f6;
  height: 4px;
  border-radius: 2px;
  transition: width 0.3s ease;
}

/* File icon */
.file-icon {
  width: 20px;
  height: 20px;
  color: #6b7280;
}

Custom File Upload Themes ​

css
/* Dark theme */
.file-upload-dark .file-upload-menu {
  background-color: #1f2937;
  border-color: #374151;
  color: #f9fafb;
}

.file-upload-dark .file-upload-area {
  border-color: #4b5563;
  background-color: #374151;
}

.file-upload-dark .file-upload-area:hover {
  border-color: #60a5fa;
  background-color: #1e3a8a;
}

/* Custom file types */
.file-link.pdf {
  background-color: #fee2e2;
  border-color: #ef4444;
  color: #991b1b;
}

.file-link.image {
  background-color: #dbeafe;
  border-color: #3b82f6;
  color: #1e40af;
}

.file-link.document {
  background-color: #fef3c7;
  border-color: #f59e0b;
  color: #92400e;
}

Responsive File Upload Styles ​

css
/* Mobile file upload styles */
@media (max-width: 768px) {
  .file-upload-menu {
    max-width: 90vw;
    margin: 0 16px;
  }

  .file-upload-area {
    padding: 30px 15px;
  }

  .file-link {
    padding: 12px 16px;
    font-size: 16px;
  }
}

/* Tablet file upload styles */
@media (min-width: 769px) and (max-width: 1024px) {
  .file-upload-menu {
    max-width: 500px;
  }
}

File Upload Structure ​

Uploaded File Object ​

javascript
interface UploadedFile {
  id: string;           // Unique file identifier
  name: string;         // Original file name
  size: number;         // File size in bytes
  type: string;         // MIME type
  data: ArrayBuffer;    // File data
}
html
<a class="file-link" data-file-id="file-123"> 📎 document.pdf (1.2 MB) </a>

Troubleshooting ​

Common Issues ​

  1. File upload not working

    • Check file size limits
    • Verify allowed file types
    • Check for JavaScript errors
    • Ensure upload endpoints are configured
  2. File download not working

    • Check if file exists in storage
    • Verify download permissions
    • Check for network errors
    • Ensure file ID is valid
  3. File type validation failing

    • Check allowedTypes configuration
    • Verify MIME type detection
    • Check file extension validation
    • Ensure wildcard patterns are correct
  4. Server integration issues

    • Check endpoint URLs
    • Verify server response format
    • Check CORS configuration
    • Ensure authentication is working

Debug Mode ​

Enable debug logging:

javascript
// Add console logging
console.log('File Upload plugin initialized');

// Check upload events
editor.on('file:upload-started', (file) => {
  console.log('Upload started:', file);
});

editor.on('file:upload-error', (error) => {
  console.error('Upload error:', error);
});

// Check file uploader
const fileUploader = new FileUploader();
console.log('File uploader created');

// Test file validation
const testFile = new File(['test'], 'test.txt', { type: 'text/plain' });
const isValid = fileUploader.isFileTypeAllowed(testFile);
console.log('File type allowed:', isValid);

Browser Support ​

  • Chrome 60+
  • Firefox 55+
  • Safari 12+
  • Edge 79+

Performance Considerations ​

  • File uploads are asynchronous
  • Large files are handled efficiently
  • Progress tracking is optimized
  • Memory usage is managed for large files

Security ​

  • File type validation prevents malicious uploads
  • File size limits prevent abuse
  • Server-side validation is recommended
  • Secure file storage practices

License ​

MIT License - see LICENSE file for details.

Released under the MIT License.