multiple FileUpload display file path as text [duplicate] - javascript

This question already has answers here:
How to get full path of selected file on change of <input type=‘file’> using javascript, jquery-ajax?
(14 answers)
Closed 6 years ago.
I have a select choice of files to upload can be single or multiple
as I select I would like to have a text below stated the path of the files I have selected.
<form action="mymethod" enctype="multipart/form-data" method="Post" id="submitForm">
<input id="file" name="file[]" multiple type="file">
Upon selecting the file let say its 3:
it will show on the screen:
however currently it is showing:
here is my script:
<script>
var selDiv = "";
document.addEventListener("DOMContentLoaded", init,
false);
function init() {
document.querySelector('#file').addEventListener(
'change', handleFileSelect, false);
selDiv = document.querySelector("#selectedFiles");
}
function handleFileSelect(e) {
if (!e.target.files)
return;
selDiv.innerHTML = "";
var files = e.target.files;
for ( var i = 0; i < files.length; i++) {
var f = files[i];
selDiv.innerHTML += f.name + "<br/>";
}
}
</script>
Prehaps you guys could give me suggestion on how I would tackle this issue?

You won't be able to access this via JavaScript; as a security precaution the browser will expose the file name to you, but nothing else about the local file system.
This is a built in security measure by the browser creators, so private information about local file paths cannot be seen.

Related

Javascript: Use <input type="file"/> to compute SHA256 file hash

Motivation: I want to make a browser-based hashing utility so users can compute file hashes without installing software.
The approach I'm considering is a static page with "a file upload button" (except no upload takes place): the user picks a file, and the script computes and displays its hash.
So let's say we have this element on the page:
<input id="file-hasher" type="file" />
This creates a button that allows the users of the web page to select a file via an OS "File open..." dialog in the browser.
Let's say the user clicks said button, selects a file in the dialog, then clicks the "Ok" button to close the dialog.
The selected file name is now stored in:
document.getElementById("file-hasher").value
Here, I'm hoping to use a library like https://github.com/bitwiseshiftleft/sjcl/ to compute the hash of the chosen file. Is there a way to do this or does the browser's security model get in the way?
Yes, you can select a file using the file element, and take a hash of the file locally, 'in-browser', using javascript. The browser's security model does not prevent this; and the hash function from the native Web Crypto API can be used, so there is no need for any external crypto libraries.
Here is a working example:
function hashfile() {
readbinaryfile(fileselector.files[0])
.then(function(result) {
result = new Uint8Array(result);
return window.crypto.subtle.digest('SHA-256', result);
}).then(function(result) {
result = new Uint8Array(result);
var resulthex = Uint8ArrayToHexString(result);
divresult.innerText = 'result: ' + resulthex;
});
}
function readbinaryfile(file) {
return new Promise((resolve, reject) => {
var fr = new FileReader();
fr.onload = () => {
resolve(fr.result)
};
fr.readAsArrayBuffer(file);
});
}
function Uint8ArrayToHexString(ui8array) {
var hexstring = '',
h;
for (var i = 0; i < ui8array.length; i++) {
h = ui8array[i].toString(16);
if (h.length == 1) {
h = '0' + h;
}
hexstring += h;
}
var p = Math.pow(2, Math.ceil(Math.log2(hexstring.length)));
hexstring = hexstring.padStart(p, '0');
return hexstring;
}
<h2>File Hash</h2>
<div>
Select file to take hash of:
<br/>
<input type="file" id="fileselector" onchange="javascript:hashfile();">
</div>
<br/>
<div id="divresult"></div>
The standard browser security model allows you to have the user pick a file and do what you will with it. I'm an older guy and thought surely this kinda mingling with a user's parts would require additional hoops/consent. So #ceving 's answer was best: "Do it and you will see."
Here's a link to a good article: https://humanwhocodes.com/blog/2012/05/08/working-with-files-in-javascript-part-1/
Apologies for not trying first before posting.

How just select directory not file?

I using js to create my form, my problem is how to just select directory, not file?
Belows is my coding:
const realFileBtn = document.getElementById("real-file");
const customBtn = document.getElementById("custom-button");
const customTxt = document.getElementById("custom-text");
customBtn.addEventListener("click", function() {
realFileBtn.click();
});
realFileBtn.addEventListener("change", function() {
if (realFileBtn.value) {
customTxt.innerHTML = realFileBtn.value;
} else {
customTxt.innerHTML = "No file chosen, yet.";
}
});
<input type="file" id="real-file" hidden="hidden" />
<button type="button" id="custom-button">CHOOSE A FILE</button>
<span id="custom-text">No file chosen, yet.</span>
Below is my output:
Actually I want the output not to select the file, just select the folder, because the next step I need store file in this folder directory.
If success the output is folder directory name is:
C:\Staff Import Folder\Source
Hope someone can help me solve this problem. Thanks.
In newest browsers, you can select a directory content with the webkitdirectory attribute of the <input type="file"> element, as being defined by Files and Directories entries API, but I fear this will be deceptive to you since it will only select all the files in this directory (and its sub-folders). There is currently no way to navigate this directory from here.
We should be able to navigate such directory, by looking at the webkitEntries IDL attribute, but currently browsers only populate this from a drop event. You can see a demo in this Q.A.
inp.onchange = (e) => {
console.log( inp.webkitEntries ); // []
console.log( [...inp.files].map( file => file.name ) );
};
<input type="file" webkitdirectory id="inp">
But even then, while you'll be able to navigate that directory, you still won't be able to set anything on the FileSystem. Web scripts simply don't have the authorization to write anything on the disk, except in sand-boxed areas like IndexedDB.
https://developer.mozilla.org/en-US/docs/Web/API/HTMLInputElement/webkitdirectory
document.getElementById("filepicker").addEventListener("change", function(event) {
let output = document.getElementById("listing");
let files = event.target.files;
for (let i = 0; i < files.length; i++) {
let item = document.createElement("li");
item.innerHTML = files[i].webkitRelativePath;
output.appendChild(item);
};
}, false);
<input type="file" id="filepicker" name="fileList" webkitdirectory multiple />
<ul id="listing"></ul>

Sync a FileReader in a for loop: Javascript

I am trying to implement a JavaScript program to read a bunch of CSV files from a particular directory containing sub-directories. To do so, I am thinking of using Javascript to read multiple files using webkitdirectory and reading the files and then using java to push them.
HTML Form
<input id="csv" type="file" multiple webkitdirectory directory>
<input type="button" onclick="readCSV()" value="Submit">
JavaScript to Read Files
function readCSV(){
var fileInput = document.getElementById("csv");
var fileCount = fileInput.files.length;
if( fileCount != 0) {
alert(fileCount);
var reader;
for (var i = 0; i < fileCount; i++) {
reader = new FileReader();
reader.onload = function () {
document.getElementById('out').innerHTML = reader.result;
// Once the file is read, Send it to JavaServlet to save on server.
};
reader.readAsBinaryString(fileInput.files[i]);
}
} else {
alert("Select a File");
}
}
The problem I am facing here is that the code runs successfully when only one file is selected but breaks when multiple files are selected. I think the problem is in sync read. But I couldn't find a way to either sync read or pause the loop while the reader object completely reads the file.

Handling multiple files from an input element in an array with Google Apps Script

I have a form, which allows to select an item from a dropdown list and upload a file. The name and the ID of the item are saved in a Spreadsheet document. Works with one file...but I want to upload multiple files. Could you help me fixing the script?
The HTML part looks like this
<div class="col-md-4 col-sm-6 ">
<div class="caption">
<h3>Bildauswahl</h3>
<p align="center"><input type="file" name="myFiles[]" id="myFiles" multiple></p>
</div>
</div>
My script, which is not working, is the following:
var dropBoxId = "XYZ";
var logSheetId = "ABC";
function doGet(e) {
return HtmlService.createHtmlOutputFromFile('InputForm.html');
}
function uploadFiles(formObject) {
try {
// Create a file in Drive from the one provided in the form
var folder = DriveApp.getFolderById(dropBoxId);
var input = document.getElementById('myFiles');
for (i = 0; i<input.files.length; i++) {
var blob = input.files[i];
var file = folder.createFile(blob);
var ss = SpreadsheetApp.openById(logSheetId);
var sheet = ss.getSheets()[0];
sheet.appendRow([file.getName(), file.getUrl(), formObject.myName]);
}
// Return the new file Drive URL so it can be put in the web app output
return file.getUrl();
} catch (error) {
return error.toString();
}
}
Thanks.
As of right now you have to use a work around to work with multiple files. The multiple attribute only works in IFRAME mode, but file inputs are broken in IFRAME mode.
To see this workaround take a look at the bug submission for this issue:
https://code.google.com/p/google-apps-script-issues/issues/detail?id=4610
Also in your code you have some mixing of server side and client side code that will not work:
var folder = DriveApp.getFolderById(dropBoxId); //server side
var input = document.getElementById('myFiles'); //client side
You will need to do your multiple file processing on the client side
I came up with a nice solution for multi-file uploading. Limitations are files must be under 10 MB.
CODE.GS
function doGet() {
return HtmlService.createHtmlOutputFromFile('index').setSandboxMode(HtmlService.SandboxMode.IFRAME);
}
function saveFile(data,name,folderId) {
var contentType = data.substring(5,data.indexOf(';'));
var file = Utilities.newBlob(Utilities.base64Decode(data.substr(data.indexOf('base64,')+7)), contentType, name);
DriveApp.getFolderById(folderId).createFile(file);
}
index.html
<div>
<input type="file" id="myFiles" name="myFiles" multiple/>
<input type="button" value="Submit" onclick="SaveFiles()" />
</div>
<script>
var reader = new FileReader();
var files;
var fileCounter = 0;
var folderId = "";
reader.onloadend = function () {
google.script.run
.withSuccessHandler(function(){
fileCounter++;
postNextFile();
}).saveFile(reader.result,files[fileCounter].name,folderId);
}
function SaveFiles(){
var folderSelect = document.getElementById("folderSelectId");
folderId = folderSelect.options[e.selectedIndex].value;
files = document.getElementById("myFiles").files;
postNextFile();
}
function postNextFile(){if(fileCounter < files.length){reader.readAsDataURL(files[fileCounter]);}else{fileCounter=0;alert("upload done")}}
</script>

how to retrieve filename from input type=file value

I have this function for validating image files uploaded through this:
<input accept="image/*" type="file" name="temp_picture" id="temp_picture">
//onchange
validate($(this).attr('name')); //I had to use the attribute name in some other function
And then I have this checker in a function if it is a valid jpeg/jpg file
function validate(pictureId){
var fileExtension = document.getElementById(pictureId).value.split('.').pop().toLowerCase();
//etc
}
The problem is, I could not get the image filename from value. The code below returns an empty string:
console.log(document.getElementById(pictureId).value);
Your code uses the undefined identifier pictureId. Use the string '#temp_picture' instead.
If you actually had var pictureId = '#temp_picture' but forgot to include it in the code you posted, the odds are that the code is being executed before the user made any selection. It works if you execute the code e.g. in an onchange even handler.
Note that the name returned is usually not the true pathname of the file but could be e.g. C:\fakepath\foo.png. This is a security measure, intended to prevent pages from inspecting the file system of the user’s computer. Here it does not matter, since you apparently want to look just at the last few characters of the name.
write the following function on the click event of button or something you are going to use
function checkvalid()
{
var file_name = document.getElementById("temp_picture").value;
var file_extn=file_name.split('.').pop().toLowerCase();
switch(file_extn) {
//if .jpg/.gif/.png do something
case 'jpg': case 'gif': case 'png':
/* handle */
break;
//if .zip/.rar do something else
case 'zip': case 'rar':
/* handle */`enter code here`
break;
//if .pdf do something else
case 'pdf':
/* handle */
break;
}
}
You have given your id wrong in the function..Thats the main problem for the error message.
I am attaching a demo here satisfying your requirements.Do check.
http://plnkr.co/edit/QlGMSL6xJulxBSPBbB1f?p=preview
Take a look at how I did it, it takes into consideration of the \fakepath\, it also fetches both the extension and the filename:
document.getElementById("temp_picture").onchange=function(){
var removeFakePath = this.value.split("\\"); // For the browser that add a fake path
var getFileWithExt = removeFakePath[removeFakePath.length - 1];
var splitExtension = getFileWithExt.split(".");
var filename = splitExtension[0];
var extension = splitExtension[1];
alert("Filename:" + filename + "\n\rExtension:" + extension);
};
Fiddle Example
Check out below code for your help:
It check s the file size and file type
<!DOCTYPE html>
<html>
<body>
<input type="file" name="image_file" id="image_file" onchange="fileSelected();">`
`<script>
var iMaxFilesize = 1048576; // 1MB
function fileSelected()
{
// get selected file element
var oFile = document.getElementById('image_file').files[0];
// filter for image files
var rFilter = /^(image\/bmp|image\/gif|image\/jpeg|image\/png|image\/tiff)$/i;
if (! rFilter.test(oFile.type)) {
alert("Not a proper file format");
return;
}
// little test for filesize
if (oFile.size > iMaxFilesize) {
alert("File size exceeded");
return;
}
alert("success = "+oFile.name);
}
</script>
</body>
</html>
You could try using the "filelist" api, like this:
var file = document.getElementById( 'temp_picture' ).files[0];
alert(file.name);
https://developer.mozilla.org/en-US/docs/Web/API/FileList
HTML
----
<form id='bob'>
<input accept="image/*" type="file" name="temp_picture" id="temp_picture" multiple>
<div id='output'></div>
</form>
Javascript
----------
function getvalues(){
var output=document.getElementById('output');
var input=document.getElementById('temp_picture');
input.onchange=function(e){
var files=input.files;
for( var i=0; i < files.length; i++ ) {
createNode( 'pre',{ innerHTML:'Name='+files[i].name+'<br />Size='+files[i].size+'<br />Type='+files[i].type, style:'margin:3em' }, output );
}
}
}
/*
There is a function here called 'createNode' - basically it uses document.createElement but also adds attributes to newly generated nodes. I have not included it for reasons of brevity.
*/
window.onload=getvalues;

Categories