I am building a Cordova App by myself and i need to create a new folder to store images in phone's internal storage. I have visited a lot of articles online and everyone is giving the same solution but it is not working for me.
Following is the code i am using in OnDeviceReady event but it is not working.
var new_directory = 'TEST';
window.requestFileSystem(LocalFileSystem.PERSISTENT, 0, function(fileSystem) {
fileSystem.root.getDirectory(new_directory, { create: true }, function (file) {
alert("got the file: "+ file.name + ', ' + file.fullPath);
});
}, function(error) {
alert("can't even get the file system: " + error.code);
});
For Debugging i have also tried to alert
cordova.file
object but it is shown as undefined.
I have tried writing simple file request statement even its is not working
window.requestFileSystem(LocalFileSystem.PERSISTENT, 0, alert('success'), alert('failed'));
also the rest of the javascript code does not work when i write above code.
Please help me to get on with this.
Have you been asked to grant the proper permissions when you try to save the file? A window like this should have appeared:
If this is not the case, you are using an obsolete plugin version. Otherwise, there is something wrong with your code, sorry but I can't help you with that.
Related
I'm running a function which I've written in JavaScript inside a nodejs/Electron client.
This function is meant to copy a file from the users flash drive to their c:/Windows/System32 (The file is being copied there so that it can be ran from Command Prompt manually next time the computer is touched without having to switch directories)
The problem is, the files are not being copied, and copyFileSync is not throwing an error.
Here is the code I'm specifically having a problem with:
try {
console.log('copying t.bat');
fs.copyFileSync(remote.app.getAppPath() + '\\app\\files\\scripts\\files\\t.bat', 'C:\\Windows\\System32\\t.bat');
} catch(err) {
console.log('could not copy t.bat', err);
$('#mfail_title').text('Could not copy t.bat file');
$('#mfail_data').text(err);
UIkit.modal("#master_fail").show();
return false;
}
As you can see, I have copyFileSync inside a TRY CATCH block. I know this code is running because in the console I get copying t.bat, but nothing else.
How can I get my files to copy, or at least throw an error when it cannot?
This client is running inside OOBE mode on various Windows 10 machines, therefore always has administrator access.
I've tried updating to the async version of copyFile, but I'm having the same issue. Here is my code
var source = remote.app.getAppPath() + '\\app\\files\\scripts\\files\\t.bat';
var destination = 'C:\\Windows\\System32\\t.bat';
fs.copyFile(source, destination, (err) => {
if (err) {
console.log(err);
} else {
source = remote.app.getAppPath() + '\\app\\files\\scripts\\files\\p.bat';
destination = 'C:\\Windows\\System32\\p.bat';
fs.copyFile(source, destination, (err) => {
if (err) {
console.log(err);
} else {
source = remote.app.getAppPath() + '\\app\\files\\scripts\\files\\p.bat';
destination = 'C:\\Windows\\System32\\p.bat';
child = spawn("powershell.exe",['-ExecutionPolicy', 'ByPass', '-File', remote.app.getAppPath() + '\\app\\files\\scripts\\' + type + '.ps1']);
}
});
}
});
This should copy a file, then when it's complete it should copy another file, once that is complete, it should run a powershell script.
Each copyFile checks for an error before moving on, but it never throws an error, and the file is never copied.
I had a similar issue earlier, In which an Antivirus(Comodo) was not allowing electron app to access the hard drive.
Copy and other file operations were successful in that case as well, because electron in such case access the corresponding sandbox
Please check this is not the case with you.
You can actually access 'fs' in console from electron and check other things in the file system.
Looks to me as if you're using fs on then renderer process (client side) which will not work (assuming that your fs is the node.js fs module and (*)). Your first script seems to use jQuery (hints for renderer) and the second one uses remote in the first line.
fs can only (*) be used on the main process and you'll need to create an IRC channel and do something like:
ircRenderer.sendSync('copy-file-sync', {from: '/from/path', to: '/to/path'})
and, of course, implement the handler for that quickly invented 'copy-file' channel on the main process.
(*) Edit: I haven't played around a lot with nodeIntegration = true, so fs may or may not work on the renderer process with that flag set on the BrowserWindow. But the irc messaging should definitely work and if not, the problem is outside electron, probably related to file permissions.
I am struggling with getting Codova-Plugin-File to work.
the set up is like this:
function listDir(path) {
alert("in Listing Func with path: " + path);
window.resolveLocalFileSystemURL(path,
function (fileSystem) {
var reader = fileSystem.createReader();
reader.readEntries(
function (entries) {
alert("the right functions");
var textString = "";
for (var i = 0; i < entries.length; i++) {
textString = textString + entries[i];
}
alert(textString);
},
function (err) {
console.log(err);
}
);
}, function (err) {
console.log(err);
}
);
}
function findCampaignFolders() {
alert("in find folder codova: " + cordova.file);
listDir(cordova.file.applicationDirectory + "www");
alert("Did you see Files");
}
The alert is what I'm using in to see the data clearly at points.
when findCampaignFolders() is called the alerts are called like this
in find folder codova: Object[Object]
in Listing Func with path: nullwww
Did you see Files
form the nullwww, it seems as if the cordova-plugin-file is not working. I also get no prediction from VS2017, which leads me to be the cause.
I haven't done programming in a long time and the was C++.
I think I'm missing something obvious. Yes, the plugin installed on the project config.xml like so:
<plugin name="cordova-plugin-file" spec="~4.3.3" />
in the html cordova is first script called like <script type="text/javascript" src="cordova.js"></script>
And last of all when I try to navigate to the definition to see where the problem might come up, windows tells me
cannot navigate to symbol under caret
my only assumptions are that I not set it up correctly and if not what have I done wrong.
or visual studio 2017 hasn't actually installed the files, which I'm not sure how to really find that out.
VisualStudio2017 looks like this to show the plugin location
Any help would be grand or if there another way to use a filesystem on mobile I'm happy to hear about it
Since i wrote this I have been trying to shift through the code of the cordova i can get at to see what i can figure out , it a little above my head. But i found
interface CordovaPlugins {}
I feel like i should be adding something into this Interface like cordova-plugins-file or something. It is found in a file called index.d.ts
Also it seems corodva missing the functionality VS2017 can only see:
enter image description here
For around 3 weeks I've been working on an Electron app and finally decided to get around to adding update checking. For my research, the standard way to do this in Electron (using Squirrel) requires the user to physically install the application onto their computer. I would rather not do this, and keep everything as portable as possible. I then decided to try making my own update script by having the program download the update.zip, and extract it to overwrite the existing files. This works well, up until the very end. At the very end of the extraction, I receive a Invalid package error, and the actual app.asar file is missing, rendering the application useless.
I am using this to download and extract the updates:
function downloadFile(url, target, fileName, cb) { // Downloads
var req = request({
method: 'GET',
uri: url
});
var out = fs.createWriteStream(target+'/'+fileName);
req.pipe(out);
req.on('end', function() {
unzip(target+'/'+fileName, target, function() {
if (cb) {
cb();
}
});
});
}
function unzip(file, target, cb) { // Unzips
var out = fs.createReadStream(file);
out.pipe(unzipper.Extract({ path: target })).on('finish', function () {
dialog.showMessageBox({
type: 'question',
message: 'Finished extracting to `'+target+'`'
});
if (cb) {
cb();
}
});
}
And call it with:
downloadFile('http://example.com/update.zip', path.join(__dirname, './'), 'update.zip', function() { // http://example.com/update.zip is not the real source
app.relaunch();
app.quit();
});
And I use the unzipper NPM package (https://www.npmjs.com/package/unzipper).
The code works perfectly for all other zips, but it fails when trying to extract a zip containing an Electron app.
Anything I'm doing wrong, or maybe a different package that properly supports extracting zips with .asar files?
Edit 1
I just found https://www.npmjs.com/package/electron-basic-updater, which does not throw the same JavaScript error however it still does not extract the .asar files correctly, and will throw it's own error. Since the .asar is still missing, the app is still useless after the "update"
Thanks to your link to electron-basic-updater, I have found this issue mentioned there: https://github.com/TamkeenLMS/electron-basic-updater/issues/4.
They refer to the issue in the electron app: https://github.com/electron/electron/issues/9304.
Finally, in the end of the second topic there's a solution:
This is due to the electron fs module treating asar files as directories rather than files. To make the unzip process work you need to do one of two things:
Set process.noAsar = true
Use original-fs instead of fs
I have seen the people working with original-fs. But it looked like a big trouble to me.
So I tried setting process.noAsar = true (and then process.noAsar = false after unzipping) - and that worked like a charm.
to make my question short and simple:
How can I access the mediaFile generated by cordova-plugin-media-capture's function capture.captureVideo() and convert it with gifShot JS' createGIF()function into a GIF on an Android device?
I ran into the problem, that neither the fullPath (file:/URI), nor the localURL (cdvfile://) of the generated mediaFile are permitted for the use, if I directly give one of them as path for the video file for gifshot, I receive following message:
Cross-origin image load denied by Cross-Origin Resource Sharing policy.
I know that the file plugin successfully creates the videos (I can see them in the galery, so they are saved on the device permanently).
And I also know that gifShot works with mp4 videos as I already created a folder inside the project directory containing a video which it rendered correctly. I also know that sadly JavaScript normally is not permitted to gain access to files on a device/PC, but isn't there a workaround provided with Cordova?
Can someone briefly explain me, how I could access the saved file? Do I need the cordova plugins "cordova-plugin-file" and "cordova-plugin-file-transfer" and how do I use them?
My code:
Javascript:
import gifshot from 'gifshot';
Template.gifshotTest.rendered = function () {
var $$ = Dom7;
var myapp = new Framework7();
};
Template.gifshotTest.events({
'click .gifShotUpload': function () {
Meteor.call("console", "Button clicked");
// capture callback
var captureSuccess = function (mediaFiles) {
path = mediaFiles[0].localURL;
Meteor.call("console", mediaFiles[0]);
gifshot.createGIF({video: path}, function(obj) {
Meteor.call("console", "---> gifshot obj:");
Meteor.call("console", obj);
if (!obj.error) {
var image = obj.image;
$('.giffy').attr("src", image);
Meteor.call("console", image);
}
});
};
// capture error callback
var captureError = function (error) {
navigator.notification.alert('Error code: ' + error.code, null, 'Capture Error');
};
// start video capture
navigator.device.capture.captureVideo(captureSuccess, captureError, {limit: 1, duration: 5, quality: 1});
}
});
Console logs
I20160421-15:25:36.283(2)? Button clicked
I20160421-15:25:42.158(2)? null
I20160421-15:25:42.166(2)? { name: 'VID_20160421_152544.mp4',
I20160421-15:25:42.167(2)? localURL: 'cdvfile://localhost/sdcard/DCIM/Camera/VID_20160421_152544.mp4',
I20160421-15:25:42.167(2)? type: 'video/mp4',
I20160421-15:25:42.168(2)? lastModified: null,
I20160421-15:25:42.168(2)? lastModifiedDate: 1461245147000,
I20160421-15:25:42.169(2)? size: 461498,
I20160421-15:25:42.169(2)? start: 0,
I20160421-15:25:42.169(2)? end: 0,
I20160421-15:25:42.170(2)? fullPath: 'file:/storage/emulated/0/DCIM/Camera/VID_20160421_152544.mp4' }
I20160421-15:25:44.656(2) (android:http://localhost:12680/:0) Cross-origin image load denied by Cross-Origin Resource Sharing policy.
Included Cordova Plugins (Cordova Version 3.8.3):
cordova-plugin-file#4.1.1
cordova-plugin-file-transfer#1.5.1
cordova-plugin-media-capture#1.2.0
Thanks to everyone who helps me understanding the way Cordova and other libraries handle files on a device.
If the file is successfully stored in device, you can open the same use using cordova-fileopener-plugin. I would also suggest you to update your cordova version as the one you are using is too old
I know this question was asked many times before but I cannot figure it out anyhow.
I'm able to write a text file to a directory on the sdcard (android 4), but no way to read it back again, using this code:
function get_file () {
window.requestFileSystem(LocalFileSystem.PERSISTENT, 0, getFilesystem, fail);
}
function getFilesystem(fs) {
alert("getFilesystem -> backup.txt"); // OK !
// alert("filesystem.name: "+fileSystem.name); // = persistent
// alert("filesystem.root.name: "+fileSystem.root.name); // = long number
//
fs.root.getFile("../../../../../../sdcard/test/backup.txt", {create: false, exclusive: false},
function(fileEntry) {
alert(fileEntry.fullPath); // shows that my path is appended to "data/.."
fileEntry.file(function(file) {
var reader = new FileReader();
reader.onloadend = function(evt) {
alert(+evt.target.result); // NOT SHOWING !
};
reader.readAsText(file);
}, fail);
}, fail);
}
I wrote the file using the writer function into the directory sdcard/test using this sequence of ../ - this is an ugly code but working !
But fs.root.getFile does not work in the same way - the fullPath information it returns shows that my path given is APPENDED to "/data/data/com.appname/files" but does not replace it !
The onloadend function obviously isn't working since i never got the alert message, neither did I get an error message.
Change of path to "file:///sdcard/test" or "sdcard/test" has no effect either.
Any help is highly appreciated - thank you in advance !
Chris
Please refer PHONEGAP DOCUMENT
From this you will get working example of getting file from sdcard.
And if you have problem in downloading a file please refer LINK
I think in Place of "/sdcard/backup.txt" try to use only "backup.txt".
It seems to work fine.
PhoneGap takes care of the details of the path ,also works with directories.
So finally I could figure it out:
To access the directory (on Android 4.0, Samsung Note 8) I had to go up literally all directories from /data/data/com.app-name/files/apps/(random no.)/ back to the sdcard by choosing:
fs.root.getFile("../../../../../../sdcard/test/backup.txt", ...
in mosync Reload client.
"Compiling" the app with mosync apk would require only 4 times "../" because the file hierarchy there is lower than in the Reload Client. In any case have to check in file explorer (root access required).
Different from that is when you compile in the cloud with phonegap - then indeed the root path is sdcard ! You then cannot go to the data directory as far as I could find out.
This path works with write and read in mosync - my mistake was that I had line break character "\n" inside the text file. In this case I could write it, but the reader stops without error message.
Hope that will help someone else as well !
Chris