To create custom attr :
class InstallData implements InstallDataInterface
{
private $customerSetupFactory;
public function __construct(CustomerSetupFactory $customerSetupFactory)
{
$this->customerSetupFactory = $customerSetupFactory;
}
public function install(ModuleDataSetupInterface $setup, ModuleContextInterface $context)
{
$installer = $setup;
$installer->startSetup();
$customerSetup = $this->customerSetupFactory->create(['setup' => $setup]);
$customerSetup->addAttribute(
\Magento\Customer\Model\Customer::ENTITY,
'custom_file',
[
'type' => 'varchar',
'label' => 'Custom File',
'input' => 'file',
'position' => 1000,
'visible' => true,
'required' => false,
'system' => false,
'user_defined' => true,
'position' => 1000,
'is_used_in_grid' => true,
'is_visible_in_grid' => false,
'is_filterable_in_grid' => true,
'is_searchable_in_grid' => false
]
);
$customFileAttribute = $customerSetup->getEavConfig()->getAttribute(\Magento\Customer\Model\Customer::ENTITY, 'custom_file');
$customFileAttribute->setData('used_in_forms', ['adminhtml_customer']);
$customFileAttribute->save();
$installer->endSetup();
}
}
Define field in checkout_index_index.xml :
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
<body>
<referenceBlock name="checkout.root">
<arguments>
<argument name="jsLayout" xsi:type="array">
<item name="components" xsi:type="array">
<item name="checkout" xsi:type="array">
<item name="children" xsi:type="array">
<item name="steps" xsi:type="array">
<item name="children" xsi:type="array">
<item name="shipping-step" xsi:type="array">
<item name="children" xsi:type="array">
<item name="shippingAddress" xsi:type="array">
<item name="children" xsi:type="array">
<item name="shippingAdditional" xsi:type="array">
<item name="children" xsi:type="array">
<item name="custom-file-upload" xsi:type="array">
<item name="component" xsi:type="string">Custom_Module/js/view/checkout/shipping/custom-file-upload</item>
</item>
</item>
</item>
</item>
</item>
</item>
</item>
</item>
</item>
</item>
</item>
</item>
</argument>
</arguments>
</referenceBlock>
</body>
</page>
Add js file in module :
define([
'uiComponent'
], function (Component) {
'use strict';
return Component.extend({
defaults: {
template: 'Custom_Module/checkout/shipping/custom-file-upload'
},
initialize: function () {
this._super();
// add your initialization logic here
}
});
});
Create html file as per define in js file :
<input type="file" data-bind="
attr: {
'id': 'custom-file-upload',
'name': 'custom_file'
},
value: customFile"
/>
And Add uploaded file after order in custom table with order id.
class InstallSchema implements InstallSchemaInterface
{
public function install(SchemaSetupInterface $setup, ModuleContextInterface $context)
{
$installer = $setup;
$installer->startSetup();
$table = $installer->getConnection()->newTable(
$installer->getTable('custom_module_uploaded_files')
)->addColumn(
'file_id',
\Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
null,
['identity' => true, 'nullable' => false, 'primary' => true],
'File ID'
)->addColumn(
'order_id',
\Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
null,
['nullable' => false],
'Order ID'
)->addColumn(
'file_path',
\Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
255,
['nullable' => true],
'File Path'
)->addIndex(
$installer->getIdxName('custom_module_uploaded_files', ['order_id']),
['order_id']
)->addForeignKey(
$installer->getFkName('custom_module_uploaded_files', 'order_id', 'sales_order', 'entity_id'),
'order_id',
$installer->getTable('sales_order'),
'entity_id',
\Magento\Framework\DB\Ddl\Table::ACTION_CASCADE
)->setComment(
'Custom Module Uploaded Files'
);
$installer->getConnection()->createTable($table);
$installer->endSetup();
}
}
Add below file to save data :
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
<type name="Magento\Sales\Api\OrderRepositoryInterface">
<plugin name="custom_module_save_image_data" type="Custom\Module\Plugin\OrderRepositoryPlugin" sortOrder="1" disabled="false" />
</type>
</config>
Add plugin class :
class OrderRepositoryPlugin
{
public function beforeSave(OrderRepositoryInterface $subject, OrderInterface $order, $saveOptions = false)
{
$customImageData = $this->getCustomImageData();
$order->setCustomImageData($customImageData);
return [$order, $saveOptions];
}
private function getCustomImageData()
{
..
}
}