readAsDataUrl function no output - ionic-framework

i am using ionic 5 & capacitor.
For some reason, the readAsDataURL isnt working and it isnt showing me an error message either.
the path & file name seem fine, they are :
filePath: file:///storage/emulated/0/Android/data/io.ionic.starter/cache/1763816379-cropped.jpg
path : file:///storage/emulated/0/Android/data/io.ionic.starter/cache/
fileName: 1763816379-cropped.jpg
showCroppedImage(ImagePath) {
var filePath = ImagePath;
let fileName = filePath.split("/").pop();
let path = filePath.substring(0, filePath.lastIndexOf("/") + 1);
alert(filePath);
alert(fileName);
alert(path);
alert("works till here");
this.file
.readAsDataURL(path, fileName)
.then((base64) => {
alert(base64);
})
.catch((err) => {
console.log(err);
alert(err);
});
}

this.file.createFile(
this.file.externalDataDirectory,
"base64string.txt",
true
);
this.file.readAsText(this.file.externalDataDirectory, "base64string.txt");
this.blob = new Blob([this.base64string]);
this.file
.writeFile(
this.file.externalDataDirectory,
"base64string.txt",
this.blob,
{ replace: true, append: false }
)
.then(() => {
alert("File saved in internal storage/android/data/io.starter.ionic/");
});
}
Earlier, my file was getting saved in an internal directory which was not accessible by a user. So i used the externalDataDirectory function, which fixed my issue. It stores the file in an external directory which is accessible by the user.
The file is stored in "internal storage/android/data/#app_id#/"

I ended up sorting the problem for my application and I have included it below:
/** #desc crop the selected image */
async cropImage(fileUrl: any) {
this.show_spinner = true;
await this.ionLoader.showLoader('Cropping Image...');
this.crop.crop(fileUrl, {
quality: 75,
targetHeight: 320,
targetWidth: 240
})
.then(
async (newImage) => {
this.show_spinner = false;
await this.ionLoader.hideLoader();
this.showCroppedImage(newImage.split('?')[0]);
},
async (error: IonicResultMessageInterface) => {
this.show_spinner = false;
await this.ionLoader.hideLoader();
console.error('Error cropping image', error);
console.log(error);
this.setUserProfileImage();
this.toasterService.showToast(error.message, 'failure');
}
);
}
/** #desc show the image after it has been cropped */
async showCroppedImage(ImagePath: string) {
console.log(ImagePath);
this.show_spinner = true;
const copyPath = ImagePath;
const splitPath = copyPath.split('/');
const imageName = splitPath[splitPath.length - 1];
const file_ext = imageName.substr(imageName.lastIndexOf('.') + 1);
try {
const base64 = await Filesystem.readFile({ path: ImagePath});
if (base64) {
console.log(base64);
this.userImageUrl = 'data:image/' + file_ext + ';base64,' + base64.data;
this.show_spinner = false;
await this.updateProfilePictureMethod();
} else {
this.show_spinner = false;
console.log('Error in the showCroppedImage File method');
console.log('Unexpected Error');
this.setUserProfileImage();
this.toasterService.showToast('Unexpected Error Occurred in the showCroppedImage File', 'failure');
}
} catch (error) {
this.show_spinner = false;
console.log('Error in the showCroppedImage File method');
console.log('Unexpected Error');
this.setUserProfileImage();
this.toasterService.showToast(error.message, 'failure');
}
}

Related

about vscode api for executeCommand("explorer.newFolder")

I want callback for after newFolder,
executeCommand("explorer.newFolder").then(value => console.log(value))
but The value is not the value of folderName.
I analyzed the code of the command you executed.
The explorer.newFolder command is defined as NEW_FOLDER_COMMAND_ID, and is connected with the openExplorerAndCreate handler. (The result is received through the handler of CommndsRegistry.)
The return of the openExplorerAndCreateis a callback function (Promise).
When i look closely inside,, if the input parameter is not isFolder, that is, if it is a file, a callback function is provided by the return commandService.executeCommand(NEW_UNTITLED_FILE_COMMAND_ID); command.\
but if it is a folder, there is no return value. That is undifined.
in vscode API documentation
return type of executeCommand() is Thenable<T | undefined>. That is, in the case of the corresponding command, it is returned as undefined, not Thenable<T>. If an error is not thrown and undefined is returned, it can be determined that it has been normally executed.
// src/vs/workbench/contrib/files/browser/fileAction.ts
...
export const NEW_FOLDER_COMMAND_ID = 'explorer.newFolder';
...
CommandsRegistry.registerCommand({
id: NEW_FOLDER_COMMAND_ID,
handler: async (accessor) => {
await openExplorerAndCreate(accessor, true);
}
});
...
async function openExplorerAndCreate(accessor: ServicesAccessor, isFolder: boolean): Promise<void> {
const explorerService = accessor.get(IExplorerService);
const fileService = accessor.get(IFileService);
const editorService = accessor.get(IEditorService);
const viewsService = accessor.get(IViewsService);
const notificationService = accessor.get(INotificationService);
const commandService = accessor.get(ICommandService);
const wasHidden = !viewsService.isViewVisible(VIEW_ID);
const view = await viewsService.openView(VIEW_ID, true);
if (wasHidden) {
// Give explorer some time to resolve itself #111218
await timeout(500);
}
if (!view) {
// Can happen in empty workspace case (https://github.com/microsoft/vscode/issues/100604)
if (isFolder) {
throw new Error('Open a folder or workspace first.');
}
return commandService.executeCommand(NEW_UNTITLED_FILE_COMMAND_ID);
}
const stats = explorerService.getContext(false);
const stat = stats.length > 0 ? stats[0] : undefined;
let folder: ExplorerItem;
if (stat) {
folder = stat.isDirectory ? stat : (stat.parent || explorerService.roots[0]);
} else {
folder = explorerService.roots[0];
}
if (folder.isReadonly) {
throw new Error('Parent folder is readonly.');
}
const newStat = new NewExplorerItem(fileService, folder, isFolder);
folder.addChild(newStat);
const onSuccess = async (value: string): Promise<void> => {
try {
const resourceToCreate = resources.joinPath(folder.resource, value);
await explorerService.applyBulkEdit([new ResourceFileEdit(undefined, resourceToCreate, { folder: isFolder })], {
undoLabel: nls.localize('createBulkEdit', "Create {0}", value),
progressLabel: nls.localize('creatingBulkEdit', "Creating {0}", value)
});
await refreshIfSeparator(value, explorerService);
if (isFolder) {
await explorerService.select(resourceToCreate, true);
} else {
await editorService.openEditor({ resource: resourceToCreate, options: { pinned: true } });
}
} catch (error) {
onErrorWithRetry(notificationService, error, () => onSuccess(value));
}
};
await explorerService.setEditable(newStat, {
validationMessage: value => validateFileName(newStat, value),
onFinish: async (value, success) => {
folder.removeChild(newStat);
await explorerService.setEditable(newStat, null);
if (success) {
onSuccess(value);
}
}
});
}

How to fix "_filePath.includes is not a function. ( In '_filePath.includes('&'), '_filePath.includes' is undefined)" in React Native?

I am trying to upload an image to Firebase Storage, however, ref.putfile() leads to the error in the tittle
I didn't find any appropriate resource related to this error
This is where I get image from user:
openPicker = () => {
// More info on all the options is below in the API Reference... just some common use cases shown here
const options = {
title: 'Fotoğraf Seç',
storageOptions: {
skipBackup: true,
path: 'images',
},
};
ImagePicker.showImagePicker(options, (response) => {
console.log('Response = ', response);
if (response.didCancel) {
console.log('User cancelled image picker');
}
else if (response.error) {
console.log('ImagePicker Error: ', response.error);
}
else if (response.customButton) {
console.log('User tapped custom button: ', response.customButton);
}
else {
const source = { uri: response.uri}
this.setState({
imageMessageSrc: source
});
this.uploadImage();
}
});
}
Then I try to uploadImage to firebase
uploadImage = () => {
console.log("Here");
const filename = this.randIDGenerator// Generate unique name
firebase
.storage()
.ref(`${firebase.auth().currentUser.uid}/sentPictures/${filename}`)
.putFile(this.state.imageMessageSrc)
.then(() => {
console.log("Here1");
})
.catch((error) => {
console.log(error);
})
When I delete putFile, error is gone, but obviously nothing happens to database.
Problem is related to the difference between filePath and fileUri. So, the solution is as below:
openPicker = () => {
const options = {
title: 'Fotoğraf Seç',
storageOptions: {
skipBackup: true,
path: 'images',
allowsEditing: true,
},
};
ImagePicker.showImagePicker(options, (response) => {
console.log('Response = ', response);
if (response.didCancel) {
console.log('User cancelled image picker');
}
else if (response.error) {
console.log('ImagePicker Error: ', response.error);
}
else if (response.customButton) {
console.log('User tapped custom button: ',response.customButton);
}
else {
var path = '';
if (Platform.OS == 'ios')
path = response.uri.toString();
else {
path = response.path.toString();
}
const image= {
image: response.uri.toString(),
path: path
};
this.uploadImage(image);
}
});
}
uploadImage = (image) => {
firebase.storage().ref(uploadUrl).putFile(image.path);
}
I realized that Firebase Storage putFile function doesn't work with image uri, instead it should be supplied with filePath. I used uri of this image to directly show image on the screen even before upload.

How to upload multiple images into mongoDB?

I successfully coded to upload a image upload into the MongoDB. But now i want to upload multiple images into database. i used gridFS and multer. Can someone help me out to solve this problem
// Create Storage engine
var storage = new GridFsStorage({
url: Mongo,
file: (req, file) => {
return new Promise((resolve, reject) => {
crypto.randomBytes(16, (err, buf) => {
if (err) {
return reject(err);
}
const filename = buf.toString('hex') + path.extname(file.originalname);
const fileInfo = {
filename: filename,
bucketName: 'uploads',
metadata: {'username': req.body.username}
};
resolve(fileInfo);
});
});
}
});
const upload = multer({ storage });
/*--------------------------------------------------------*/
app.get('/',(req,res)=>{
gfs.files.find().toArray((err,files)=>{
// Check if Files
if(!files || files.length ===0)
{
res.render('index',{files:false});
} else{
files.map(file=>{
if(file.contentType === 'image/jpeg' || file.contentType ===
'image/png')
{
file.isImage = true;
} else {
file.isImage = false;
}
});
res.render('index',{files:files});
}
});
});
/*----------------------------------------------------*/
// Display Image
app.get('/image/:filename', (req,res)=>{
gfs.files.findOne({filename: req.params.filename}, (req,file) =>{
// Check if File
if(!file || file.length ===0)
{
return res.status(404).json({
err: 'No files exist'
});
}
// Check if image
if(file.contentType === 'image/jpeg' || file.contentType === 'image/png')
{
// Read output tp browser
var readstream = gfs.createReadStream(file.filename);
readstream.pipe(res);
}
else
{
res.status(404).json({
err: 'Not an image'
});
}
});
});
i attached code section which is related to image upload. please check this code and give a good trick to upload multiple images to mongoDB

Ionic Camera Uploading to S3

I am having a problem taking a picture and uploading it to an S3 bucket when using FILE_URI for the camera.DestinationType. When using this same process with the DATA_URL DestinationType it works fine.
When using FILE_URI the file that gets uploaded to the S3 bucket says it's corrupt. I did notice the file size is much smaller (~100B) than an actual image.
Here are the versions I am using:
Ionic Framework 3.9.2 and cordova-plugin-camera 4.0.2
Here is the code I'm using:
const options: CameraOptions = {
quality: 100,
correctOrientation: true,
destinationType: this.camera.DestinationType.FILE_URI,
encodingType: this.camera.EncodingType.JPEG,
mediaType: this.camera.MediaType.PICTURE,
sourceType: this.camera.PictureSourceType.CAMERA,
}
this.camera.getPicture(options).then((imageData) => {
console.log(imageData);
let base64data = 'data:image/jpeg;base64,' + imageData;
this.bigImg = base64data;
// imageData is either a base64 encoded string or a file URI
// If it's base64:
this.selectedPhoto = this.dataURItoBlob(this.bigImg);
}, (err) => {
// Handle error
console.log("Get Image Error: " + err);
});
this.sub = AWS.config.credentials.identityId;
let uploadMessage = "Uploading Image...";
let photoName = "testPic";
this.upload(this.selectedPhoto, uploadMessage, photoName)
.then(data => {
// Change active page to list
this.navCtrl.setRoot(TabsPage).then(() => {
});
});
dataURItoBlob(dataURI) {
// code adapted from: http://stackoverflow.com/questions/33486352/cant-upload-image-to-aws-s3-from-ionic-camera
let binary = atob(dataURI.split(',')[1]);
let array = [];
for (let i = 0; i < binary.length; i++) {
array.push(binary.charCodeAt(i));
}
return new Blob([new Uint8Array(array)], {type: 'image/jpeg'});
};
upload(selectedPhoto, uploadMessage, photoName) {
return new Promise((resolve, reject) => {
let loading = this.loadingCtrl.create({
content: uploadMessage
});
loading.present();
if (selectedPhoto) {
this.s3.upload({
'Key': 'protected/' + this.sub + '/' + photoName,
'Body': selectedPhoto,
'ContentType': 'image/jpeg'
}).promise().then((data) => {
this.data2 = data;
console.log('upload complete:', JSON.stringify(data));
loading.dismiss();
resolve(data);
}, err => {
console.log('upload failed....', JSON.stringify(err));
loading.dismiss();
reject(err);
});
} else {
loading.dismiss();
reject("upload failed");
}
});

Uploading hundreds of photos (almost a thousand) using ionic

I've been struggling for months to do this but it seems impossible.
I am creating an app using ionic framework which uploads hundreds of photos.
This app is used to generate reports which contains a lot of photos.
The APIs work perfectly on a local server but when I tried using our cloud server much photos are not getting uploaded, the app shows success but when I check the server only few photos are getting uploaded (less than a hundred).
Any ideas about what should I do to make this work?
Thanks.
EDIT:
here's the code for capturing photos cameraservice.js
app.factory('cameraService', function ($rootScope, $q, $http, $location, $timeout, $cordovaCamera,$cordovaFile,$cordovaFileTransfer, apiUrl) {
var settings = {
saveToPhotoAlbum: true,
correctOrientation: true,
quality: 10,
targetWidth: 720,
targetHeight: 720,
};
return {
getPicture: function(){
var d = $q.defer();
let options = {
popoverOptions: CameraPopoverOptions
};
angular.extend(options, settings)
$cordovaCamera.getPicture(options).then(function(imageData) {
let namePath = imageData.substr(0, imageData.lastIndexOf('/') + 1);
let filename = imageData.replace(/^.*[\\\/]/, '');
$cordovaFile.moveFile(namePath, filename, cordova.file.dataDirectory, filename)
.then(function (res) {
d.resolve({ filename: res.name });
}, function (error) {
console.log(error)
});
}, function(err) {
console.log(err)
});
return d.promise;
}
}
})
and here's my uploadservice.js
app.factory('imageUploadService', function ($cordovaFileTransfer) {
var settings = {
fileKey: "file",
chunkedMode: false,
mimeType: "multipart/form-data",
headers : {
Connection:"close"
}
};
return {
upload: function(url, filename, options){
let filePath = cordova.file.dataDirectory + filename;
angular.extend(options, settings);
console.log(url, filePath, options)
return $cordovaFileTransfer.upload(url, filePath, options);
}
}
});
this is how I use the APIs sendservice.js
app.factory('sendService', function ($http, $q, imageUploadService, $timeout, apiUrl) {
return {
photos: function(id, data){
let d = $q.defer();
var url = apiUrl + "/api/senddescription"
var api = apiUrl + "/api/senddetailedphoto";
let q = [];
angular.forEach(data, (item, index)=>{
angular.forEach(item.photos, (i)=>{
let origName = i.image;
var options = {
filename: i.image,
params : {
report_no : id,
label: i.label,
photo_count: index,
photo_label: i.label
},
chunkedMode: false,
headers : {
Connection : "close"
}
};
setTimeout(function(){
q.push(imageUploadService.upload(api, origName, options))
},15000);
})
let data = {
report_no: id,
photo_count: index,
product_description: item.product_description
}
q.push($http.post(url, data));
$q.all(q).then(res=>{
d.resolve(res);
}, err=>{
d.reject(err);
})
})
return d.promise;
}
}
});
These are my APIs
/api/senddescription
public function sendPhotoDescription(Request $request){
$desc = DetailedPhotoDescription::where('report_number',$request->input('report_no'))->where('photo_count',$request->input('photo_count'))->first();
if (!$desc) {
$desc = new DetailedPhotoDescription();
$desc->report_number = $request->input('report_no');
}
$desc->photo_count = $request->input('photo_count');
$desc->product_description = $request->input('product_description');
if ($desc->save()) {
return response()->json([
'message'=>'OK'
],200);
}else{
return response()->json([
'message'=>'Error submitting photo. Please resend the report!'
],500);
}
}
/api/senddetailedphoto
public function sendDetailedPhoto(Request $request){
$file = $request->file('file');
//set a unique file name
$filename = uniqid() . '.' . $file->getClientOriginalExtension();
// //move the files to the correct folder
if ($file->move('images/reports/'. $request->input('report_no').'/detailedPhoto'.'/'.$request->input('photo_count').'/', $filename)) {
$detailed = new DetailedPhoto();
$detailed->report_number = $request->input('report_no');
$detailed->photo_count = $request->input('photo_count');
$detailed->photo_label = $request->input('photo_label');
$detailed->image_data = $filename;
if ($detailed->save()) {
return response()->json([
'message' => 'OK'
],200);
}else{
return response()->json([
'message' => 'Error saving detailed photos. Please resend the report!'
],500);
}
}else{
return response()->json([
'message' => 'Error uploading detailed photos. Please resend the report!'
],500);
}
}