Hello I made this script to export the data from a column to a .txt on my google drive
function createOrAppendFile() {
var ss = SpreadsheetApp.getActive();
var sheet = ss.getActiveSheet();
var range = sheet.getRange('G3:G50');
var rows = range.getValues();
var fileName="test.txt";
var folderName="Videos";
var data = rows.splice(0);
var str = data.map(function(e) {return e.join()}).join("\n");
var content = str;
// get list of folders with matching name
var folderList = DriveApp.getFoldersByName(folderName);
if (folderList.hasNext()) {
// found matching folder
var folder = folderList.next();
// search for files with matching name
var fileList = folder.getFilesByName(fileName);
if (fileList.hasNext()) {
// found matching file - append text
var file = fileList.next();
var combinedContent = content;
file.setContent(combinedContent);
}
else {
// file not found - create new
folder.createFile(fileName, content);
}
}
}
The problem is that when I export the data its exporting with the empty lines and on the .txt shows up empty lines that i dont want to have, how i can make it? So I only export the lines that have content.
This is what the .txt looks like https://i.stack.imgur.com/wplZL.png
I think that the reason of your issue might be due to sheet.getRange('G3:G50'). In this case, even when the empty rows are included below the data range in the range of G3:G50, range.getValues() retrieves all rows of G3:G50. If you want to retrieve the values with the data range, how about the following modification?
From:
var range = sheet.getRange('G3:G50');
To:
var range = sheet.getRange('G3:G' + sheet.getLastRow());
And, when you want to remove all empty rows of the column "G", you can also use the following modification.
From:
var range = sheet.getRange('G3:G50');
var rows = range.getValues();
To:
var range = sheet.getRange('G3:G' + sheet.getLastRow());
var values = range.getValues().filter(([g]) => g.toString() != "");
References:
getLastRow()
filter()
Related
Please help me:
I have a sheet file with 2 columns
Column A is the keyword, column B is the link to insert the keyword. Eg:
Column A Column B
Key1 Link1
Key2 Link2
... ...
How to automatically find keywords in the DOCS file and then insert Link?
Here is my idea, but it doesn't work
function insertLink() {
var file,files,folder,folders,newestFileID;
var filethaythe = DriveApp.getFilesByName('Set Link');
var ss = SpreadsheetApp.open(filethaythe.next());//ID sheet thư viện thay thế
SpreadsheetApp.setActiveSpreadsheet(ss);
SpreadsheetApp.setActiveSheet(ss.getSheets()[0]);
var sh = SpreadsheetApp.getActiveSpreadsheet().getSheetByName('Trang tính1');
var sheet = ss.getSheetByName('Trang tính1');
var values = sheet.getDataRange().getValues();
folders = DriveApp.getFoldersByName('test3');
while (folders.hasNext()) {
folder = folders.next();
files = folder.getFilesByType("application/vnd.google-apps.document");
while (files.hasNext()){
file = files.next();
var newestFileID = file.getId();
Utilities.sleep(500);
var currentDoc = DocumentApp.openById(newestFileID);
var dongcuoi= sh.getLastRow();
var dc = dongcuoi +1;
var rgtxt = currentDoc.getBody();
var rgrep = ss.getSheets()[0].getRange("A1:B"+dc);
var repA = rgrep.getValues().filter(r => r.every(c => c.toString()));
repA.forEach(e => rgtxt.setLinkUrl(...e));
currentDoc.saveAndClose();
break
}
};
}
I believe your goal as follows.
You want to set the hyperlink to the word on Google Document.
The words and hyperlinks are retrieved from Google Spreadsheet.
In this case, how about the following modification?
Modified script:
function insertLink() {
// 1. Retrieve values from Spreadsheet.
var file,files,folder,folders,newestFileID;
var filethaythe = DriveApp.getFilesByName('Set Link');
var ss = SpreadsheetApp.open(filethaythe.next());
var sheet = ss.getSheetByName('Trang tính1');
var values = sheet.getDataRange().getValues();
// 2. Retrieve Google Document.
folders = DriveApp.getFoldersByName('test3');
while (folders.hasNext()) {
folder = folders.next();
files = folder.getFilesByType("application/vnd.google-apps.document");
while (files.hasNext()) {
file = files.next();
var newestFileID = file.getId();
// 3. Search words and set hyperlinks on Google Document.
var currentDoc = DocumentApp.openById(newestFileID);
var rgtxt = currentDoc.getBody();
values.forEach(([a, b]) => {
var s = rgtxt.findText(a);
while (s) {
var start = s.getStartOffset();
s.getElement().asText().setLinkUrl(start, start + a.length - 1, b);
s = rgtxt.findText(a, s);
}
});
currentDoc.saveAndClose();
break
}
}
}
In order to search the word, the method of findText is used. And, the method of setLinkUrl sets the hyperlink to the searched word.
References:
findText(searchPattern, from)
setLinkUrl(startOffset, endOffsetInclusive, url)
I created a code that merges different g sheet files together into a master spreadsheet from a given folder. Now I'd like to create a filter in the code which filters column 71 (BT) for only criteria "ABC" and merges the data into one. Would you guys help a brother out?
function myFunction() {
var folder = DriveApp.getFolderById("id");
var filesInterator = folder.getFiles();
var file;
var fileType;
var ssID;
var combinedData = [];
var data;
while(filesInterator.hasNext()){
file = filesInterator.next();
fileType = file.getMimeType();
if(fileType === "application/vnd.google-apps.spreadsheet"){
ssID = file.getId();
data = getDataFromSpreadsheet(ssID);
combinedData = combinedData.concat(data);
} // if ends here
} // while loops ends here
//Logger.log(combinedData.length);
var ws = SpreadsheetApp.getActiveSpreadsheet().getSheetByName("QwERTY");
ws.getRange("A2:BK").clearContent();
ws.getRange(2,1,combinedData.length,combinedData[0].length).setValues(combinedData);
}
function getDataFromSpreadsheet(ssID) {
var ss = SpreadsheetApp.openById(ssID);
var ws = ss.getSheetByName("XYZ");
var data = ws.getRange("A2:KB" + ws.getLastRow()).getValues().filter(r => r[0] != '');
return data;
}
You can add the following lines of code:
let filterCriteria = SpreadsheetApp
.newFilterCriteria()
.whenTextContains("ABC")
.build();
let filter = ws.getRange(1, 71).createFilter();
filter.setColumnFilterCriteria(71, filterCriteria).sort(71, true);
Assuming, that ws is your working sheet and the criteria you're looking for is when text contains "ABC", then the snippet above will create a filter on the ws sheet on the BT1 cell.
However, please bear in mind that depending on the exact criteria of your filter you can modify the current one by taking a look at the methods available for the FilterCriteriaBuilder Class here.
Reference
Apps Script FilterCriteriaBuilder Class;
Apps Script Filter Class;
Apps Script FilterCriteria Class.
I have 100 Google Sheet files in one folder of Google Drive. Each Google sheet file has 10 sheets (A,B,C,D,E,F,G,H,I,J). I wanted to append all 100 Google Sheet files into one Google Sheet appending data from "B" sheets of all the 100 files. But the sheets with name "B" will not be in 2nd place always. All the sheets has same columns. I have the below code which appends the sheets from multiple files only if those sheets are in 2nd place in the order in each sheet. 1) It has to pick the sheet name instead of the 2nd sheet 2) This code is including even the blank rows if any in the sheets. it has to skip the blank rows from the sheets.
function myFunction() {
var myFolder = DriveApp.getFolderById("1ZtxfMNDn3uFhCcdcp5unfmTwUIJ_3fZK");
var spreadSheets = myFolder.getFilesByType("application/vnd.google-apps.spreadsheet");
var master_files = DriveApp.getFilesByName("MergedNew")
if (master_files.hasNext()){
var master_file=master_files.next();
var newSpreadSheet = SpreadsheetApp.openById(master_file.getId());
}
else {
var newSpreadSheet = SpreadsheetApp.create("MergedNew");
newSpreadSheet.getSheets()[0].setName('B data');
}
var bSheet = newSpreadSheet.getSheetByName('B data');
while(spreadSheets.hasNext())
{
var sheet = spreadSheets.next();
var spreadSheet = SpreadsheetApp.openById(sheet.getId());
var sh = spreadSheet.getSheets()[1];
var data = sh.getRange(2,1,sh.getMaxRows(),sh.getMaxColumns()).getValues();
if (bSheet.getLastRow() == 0){
var headers = sh.getRange(1,1,1,sh.getMaxColumns()).getValues();
bSheet.getRange(1,1,1,sh.getMaxColumns()).setValues(headers);
}
bSheet.getRange(bSheet.getLastRow()+1,1,data.length,data[0].length).setValues(data);
}
}
Explanation:
But the sheets with name "B" will not be in 2nd place always
Then replace this:
var sh = spreadSheet.getSheets()[1];
with:
var sh = spreadSheet.getSheetByName('B');
or:
var sh = spreadSheet.getSheetByName('B data');
depending upon how you named the B sheets.
It has to skip the blank rows from the sheets
Then you can filter out the blank rows as follows:
var filtered_data = data.filter(function (row) {
return row[0] != ""; //
});
Solution:
function myFunction() {
var myFolder = DriveApp.getFolderById("1ZtxfMNDn3uFhCcdcp5unfmTwUIJ_3fZK");
var spreadSheets = myFolder.getFilesByType("application/vnd.google-apps.spreadsheet");
var master_files = DriveApp.getFilesByName("MergedNew")
if (master_files.hasNext()){
var master_file=master_files.next();
var newSpreadSheet = SpreadsheetApp.openById(master_file.getId());
}
else {
var newSpreadSheet = SpreadsheetApp.create("MergedNew");
newSpreadSheet.getSheets()[0].setName('B data');
}
var bSheet = newSpreadSheet.getSheetByName('B data');
while(spreadSheets.hasNext())
{
var sheet = spreadSheets.next();
var spreadSheet = SpreadsheetApp.openById(sheet.getId());
var sh = spreadSheet.getSheetByName('B');
var data = sh.getRange(2,1,sh.getMaxRows(),sh.getMaxColumns()).getValues();
var filtered_data = data.filter(function (row) {
return row[0] != ""; //
});
if (bSheet.getLastRow() == 0){
var headers = sh.getRange(1,1,1,sh.getMaxColumns()).getValues();
bSheet.getRange(1,1,1,sh.getMaxColumns()).setValues(headers);
}
bSheet.getRange(bSheet.getLastRow()+1,1,filtered_data.length,filtered_data[0].length).setValues(filtered_data);
}
}
Pick sheet B, not second sheet:
In order to retrieve a sheet with a certain name, and not with a certain index, you need to use getSheetByName(name) instead of getSheets(). Replace this:
var sh = spreadSheet.getSheets()[1];
With this:
var sh = spreadSheet.getSheetByName("{your_sheet_name}");
Remove blank rows:
You don't want to copy the blank rows to the new sheet, so you should filter them out from your source data. You can use filter and some (or every) for that. Add this line after retrieving data from the source sheet:
data = data.filter(row => row.some(value => value != ""));
I'm trying to figure out how to tell the script to print to a specific sheet named 'Creative' and starting in cell B2. Instead of printing to The code, I'm using the code below. Thanks so much for any help you can offer.
function getFileArray(folderId){
var folder = DriveApp.getFolderById(folderId);
var files = folder.getFiles();
var fileList = [];
//Loop though files and add names and urls to the array
while (files.hasNext()){
var file = files.next();
var fileName = file.getName();
var fileUrl = file.getUrl();
fileList = fileList.concat([[fileName, fileUrl]]);
}
//See returned fileList in a log
//Logger.log( fileList ) //Preview Returned Array
return fileList
}
//Prints any 2D array to a range that starts with the selected cell
function printArrayToSelection(twoDimArr){
var firstCell = SS.getActiveCell();
var lastCell = firstCell.offset(twoDimArr.length - 1, twoDimArr[0].length - 1);
var destinationRange = SS.getActiveSheet().getRange(
firstCell.getA1Notation() + ':' + lastCell.getA1Notation());
destinationRange.setValues(twoDimArr);
}
//Print the actual data
function printFileArray(){
printArrayToSelection(getFileArray('FOLDERIDHERE'));
}
To specify the sheet for the destination range, you can use the getSheetByName method and pass "Creative" as an argument.
To get the destination range, I would recommend using the getRange method and passing the row, column, number of rows, and number of columns as arguments. For your case, this would be 2, 2, twoDimArr.length, twoDimArr[0].length
The documentation for this method can be found here:
https://developers.google.com/apps-script/reference/spreadsheet/sheet#getRange(Integer,Integer,Integer,Integer)
function printArrayToSelection(twoDimArr){
var firstCell = SS.getActiveCell();
var lastCell = firstCell.offset(twoDimArr.length - 1, twoDimArr[0].length - 1);
var destinationRange = SS.getSheetByName("Creative").getRange(2, 2, twoDimArr.length, twoDimArr[0].length);
destinationRange.setValues(twoDimArr);
}
I use Google Sheets (spreadsheet) to combine article data for different sources for my Gambio shop.
To import the data I need the pipe symbol as delimiter / separator and " as text delimiter in a .csv file.
In the Google Sheets menu for exporting to .csv there are no Options.
Is there a way to export to .csv with pipe separators in Google Sheets?
There are several ways to export a spreadsheet and/or a sheet from Google Sheets. Exporting a sheet as a csv file is built-in to Google Sheets (File, Download, CSV).
In this case, the OP introduces two complications that are not catered for by the "standard" methods.
1) the fields to be delimited by the 'pipe' character (|), and
2) all string fields to be enclosed in double quotes.
There are several scripts on GitHub that offer automation of the process of saving a sheet as csv. export-named-sheet-as-csv.gs by Michael Derazon (https://gist.github.com/mderazon/9655893) is an example, and I used this as a basis for this code. However, these scripts follow the "normal" rules of using a comma as the field delimiter, and no special treatment of strings.
The following code will save the active sheet as a csv file, and provides for pipe field delimiters and double quotes around strings. These parameters can be dictated by the user by editing fields on the Parameters sheet as seen in this screenshot.
The script uses typeof to identify strings, and a function isValidDate noted by Dmytro Shevchenko in Detecting an “invalid date” Date instance in JavaScript.
/*
* script to export data in all sheets in the current spreadsheet as individual csv files
* files will be named according to the name of the sheet
* author: Michael Derazon
* source: https://gist.github.com/mderazon/9655893
* adapted by Ted Bell for https://stackoverflow.com/questions/49248498/how-can-i-export-to-csv-with-pipe-delimiter
*/
function onOpen() {
var ss = SpreadsheetApp.getActiveSpreadsheet();
var csvMenuEntries = [{
name: "export as csv file",
functionName: "saveAsCSV"
}];
ss.addMenu("CSV Export", csvMenuEntries);
};
function saveAsCSV() {
var ss = SpreadsheetApp.getActiveSpreadsheet();
var ssname = ss.getName();
var sheet = ss.getActiveSheet();
var sheetname = sheet.getSheetName();
//Logger.log("DEBUG: the name of the spreadsheet is "+ssname);//DEBUG
//Logger.log("DEBUG: the sheet name is "+sheetname);// DEBUG
//// create a folder from the name of the spreadsheet
var folder = DriveApp.createFolder(ssname.toLowerCase() + '_' + sheetname.toLowerCase().replace(/ /g, '_') + '_csv_' + new Date().getTime());
//Logger.log("DEBUG: the folder name is "+folder);//DEBUG
// append ".csv" extension to the sheet name
var fileName = ssname + '_' + sheetname + ".csv";
// convert all available sheet data to csv format
var csvFile = so_4225484202(fileName);
// create a file in the Docs List with the given name and the csv data
folder.createFile(fileName, csvFile);
Browser.msgBox('Files are waiting in a folder named ' + folder.getName());
}
function isValidDate(date) {
return date && Object.prototype.toString.call(date) === "[object Date]" && !isNaN(date);
}
function so_4225484202(filename) {
var ss = SpreadsheetApp.getActiveSpreadsheet();
var sheet = ss.getActiveSheet();
var paramsheet = ss.getSheetByName("Parameters");
var linearray = [];
var rowdata = [];
var csv = "";
var fieldvalue = "";
var param = paramsheet.getRange(2, 2, 2);
var paramValues = param.getValues();
//Logger.log("DEBUG: parameters = "+param.getA1Notation());//DEBUG
var fieldDelimiter = paramValues[0][0];
var textDelimiter = paramValues[1][0];
//Logger.log("DEBUG: field delimiter: "+fieldDelimiter+", text delim: "+textDelimiter);//DEBUG
var rangeData = sheet.getDataRange();
var lastColumn = rangeData.getLastColumn();
var lastRow = rangeData.getLastRow();
//Logger.log("DEBUG: lastColumn: "+lastColumn+", lastRow: "+lastRow);//DEBUG
// Get array of values in the Data Range
var rangeValues = rangeData.getValues();
// Loop through array and build values for csv
for (i = 0; i < lastRow; i++) {
for (j = 0; j < lastColumn; j++) {
var value = rangeValues[i][j];
var theType = typeof value;
if (theType === "object") {
var testdate = isValidDate(value);
//Logger.log("if typeof is object: testdate: "+testdate);//DEBUG
var testtype = typeof testdate;
if (testtype === "boolean") {
// variable is a boolean
//Logger.log("Its a date");//DEBUG
theType = "date";
} else {
//Logger.log("Its not a date");//DEBUG
}
}
if (theType === "string") {
value = textDelimiter + value + textDelimiter;
}
rowdata.push([value]);
};
//Logger.log("DEBUG: rowdata: "+rowdata);//DEBUG
csv += rowdata.join(fieldDelimiter) + "\n";
var rowdata = [];
};
//Logger.log("DEBUG: csv: "+csv);//DEBUG
return csv;
}
This spreadsheet contains sample data.
A sheet containing almost 1,000 records is processed and saved in about 5 seconds.
I actually didn't make it happen inside the Google world.
My workaround is to use an editor like Sublime Text to mark all pipe delimiters and replace them with semicolon to import in sheets.