Enabling File Uploads in Web Components for HarmonyOS Next
Overview
The Web component in HarmonyOS Next provides robust support for file upload functionality on the frontend page. This feature allows application developers to handle file upload requests directly from the frontend using the onShowFileSelector()
interface. If developers do not implement custom handling, the Web component will provide a default behavior to manage file uploads. This guide will walk you through the process of enabling and customizing file uploads in your HarmonyOS Next application.
Example: Handling File Upload Requests
In the following example, when a user clicks the file upload button on the frontend page, the application receives a file upload request in the onShowFileSelector()
interface. Here, the developer sets the local file path for the upload to the frontend page.
Application-Side Code
// xxx.ets
import { webview } from '@kit.ArkWeb';
import { BusinessError } from '@kit.BasicServicesKit';
import { picker } from '@kit.CoreFileKit';
@Entry
@Component
struct WebComponent {
controller: webview.WebviewController = new webview.WebviewController();
build() {
Column() {
Web({ src: $rawfile('local.html'), controller: this.controller })
.onShowFileSelector((event) => {
console.log('onShowFileSelector invoked');
const documentSelectOptions = new picker.DocumentSelectOptions();
let uri: string | null = null;
const documentViewPicker = new picker.DocumentViewPicker();
documentViewPicker.select(documentSelectOptions).then((documentSelectResult) => {
uri = documentSelectResult[0];
console.info('documentViewPicker.select succeeded, uri is: ' + uri);
if (event) {
event.result.handleFileList([uri]);
}
}).catch((err: BusinessError) => {
console.error(`Invoke documentViewPicker.select failed, code is ${err.code}, message is ${err.message}`);
});
return true;
})
}
}
}
Frontend Page Code (local.html
)
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8">
<title>Document</title>
</head>
<body>
<!-- Click to upload file -->
<input type="file" value="file"><br>
<meta name="viewport" content="width=device-width" />
</body>
</html>
Explanation
- onShowFileSelector(): This interface is called when the frontend page requests a file upload. Developers can use this interface to customize the file selection process and set the selected file path for the frontend page.
-
DocumentViewPicker: This class is used to open a file picker dialog for the user to select a file. The selected file's URI is then passed back to the frontend page using the
handleFileList
method.
Detailed Steps
-
Setting Up the Web Component:
- Import the necessary modules from
@kit.ArkWeb
,@kit.BasicServicesKit
, and@kit.CoreFileKit
. - Create a
WebviewController
instance to manage the Web component.
- Import the necessary modules from
-
Handling File Upload Requests:
- Use the
onShowFileSelector()
interface to intercept file upload requests from the frontend page. - Create an instance of
DocumentSelectOptions
to configure the file picker. - Use the
DocumentViewPicker
class to open a file picker dialog and allow the user to select a file. - Capture the selected file's URI and pass it back to the frontend page using the
handleFileList
method.
- Use the
Additional Considerations
- Error Handling: Implement robust error handling to manage scenarios where the file picker fails or the user cancels the selection.
- Customization: Customize the file picker options to filter file types or limit the number of files that can be selected.
- Security: Ensure that the application handles file uploads securely, validating the file type and size to prevent potential security issues.
Example with Custom File Picker Options
// xxx.ets
import { webview } from '@kit.ArkWeb';
import { BusinessError } from '@kit.BasicServicesKit';
import { picker } from '@kit.CoreFileKit';
@Entry
@Component
struct WebComponent {
controller: webview.WebviewController = new webview.WebviewController();
build() {
Column() {
Web({ src: $rawfile('local.html'), controller: this.controller })
.onShowFileSelector((event) => {
console.log('onShowFileSelector invoked');
const documentSelectOptions = new picker.DocumentSelectOptions();
documentSelectOptions.fileType = ['image/jpeg', 'image/png']; // Limit to image files
documentSelectOptions.maxCount = 1; // Allow only one file to be selected
let uri: string | null = null;
const documentViewPicker = new picker.DocumentViewPicker();
documentViewPicker.select(documentSelectOptions).then((documentSelectResult) => {
uri = documentSelectResult[0];
console.info('documentViewPicker.select succeeded, uri is: ' + uri);
if (event) {
event.result.handleFileList([uri]);
}
}).catch((err: BusinessError) => {
console.error(`Invoke documentViewPicker.select failed, code is ${err.code}, message is ${err.message}`);
});
return true;
})
}
}
}
Top comments (0)