insertImage via getFilebyID suddenly stopped working - google-apps-script

I wrote a script months ago and it worked just fine but 2 days ago it stopped placing images. The var name with "url" is misleading seeing I am not using a URL by getting the file by ID.
That part of the script goes is suddenly haywire is:
var icon = finalDisplayArray[i][0]; (Im looping to place the images in this array.)
var iconURL = DriveApp.getFileById(icon);
//Logger.log tells me the above code does give me the valid name of the .jpg file here so it appears Google has the image ready to go
// THE BELOW IS WHERE IT BUGS OUT
ssDisplay.insertImage(iconURL, columnCounter, rowCounter);
// ERROR MSG: Exception: The image could not be inserted. Please verify it is valid and try again.
I haven't been using GAS for that long but is it normal for a program to suddenly quit working like this when it worked fine for months? The "columncounter", etc, is just me placing smaller icons in a row and then columsn if the row gets too long. Thought it might be since I'm using my company's email and the permissions maybe reset but all the file sharing, etc, is what it's always been.

Related

Opening a downloaded mht file from Selenium (Help needed)

Long story short, I'm not a coder.
My team used to have this coder who created this Python/Selenium code to extract some information from chrome browser (Echocardiography reports) and/or downloaded mht file (also Echocardiography reports).
This code was working fine until recently, it stopped working.
The program still successfully downloads the mht file via chrome.
However, it fails to open the file and hence, code continues without extracting any information - resulting in empty extractions.
This is the part I need help figuring out
driver.get('chrome://downloads')
# driver.get('file:///C:/Users/name/Downloads/')
root1 = driver.find_element_by_tag_name('downloads-manager')
shadow_root1 = expand_shadow_element(root1)
time.sleep(2)
root2 = shadow_root1.find_element_by_css_selector('downloads-item')
shadow_root2 = expand_shadow_element(root2)
time.sleep(1.5)
openEchoFileButton = shadow_root2.find_element_by_id('file-link')
mhtFileName = openEchoFileButton.text
driver.get('file:///C:/Users/name/Downloads/' + mhtFileName) # go to web page
try:
echoDateElement = WebDriverWait(driver, delay).until(
EC.presence_of_element_located((By.XPATH, '/html/body/div[3]/p[1]/span[3]')))
except TimeoutException:
print("Loading page took too much time!")
I'm trying to figure out why it suddenly fails to open the downloaded mht files.
Last time our team tried using this code is back in 2020 and was successful.
Were there any updates to Chrome perhaps?
Help would be immensely appreciated.
Thank you so much in advance.
There are three obvious weaknesses in this code. The first two are the use of time.sleep() to wait for the element to appear and be manipulable. What if the machine is busy doing something else, and 1.5 seconds isn't enough? The right way to do that is to repeatedly check for the element to be ready. You've got a great example of how to do that using WebDriverWait() in this code already. The third weakness is the locator used in that presence_of_element_located() call. XPath locators rooted at "/html" are notoriously fragile, subject to breakage by small changes to the web page. Try to find something in the page that you can check via a more stable locator - ideally, an element with an ID= attribute.

Script suddenly stops working but works in other sheets

Been using getFileById & insertImage in a sheet/program for months with no problem but it suddenly stopped working two days ago. In order to solve the issue I created a fresh sheet and did this simple code:
function myFunction() {
var picId = "1x2jkgSQvVKAIOg6DQ0rss82YhTQl918c";
var picToPlace = DriveApp.getFileById(picId);
SpreadsheetApp.getActiveSpreadsheet().insertImage(picToPlace,1,1);
}
It works just like it should however if I stick the same code into my main sheet I get "Exception: The image could not be inserted. Please verify it is valid and try again."
Why is this happening? I'm not doing anything different, the function is sitting by itself. Been building this sheet/program for months. Have I overloaded the sheet somehow? Again, if I make a fresh, plain sheet, stick this code in it, it works fine, but if I go back to my main sheet, stick in the same function, it just refuses to work. Its in its own function, nothing else is happening w/in it, it's the only thing I'm calling. I'm at a lost trying to figure out why insertImage has completely stopped working in this sheet. There are thousands and thousands lines of code, over 15K rows of data in some tabs, it's referencing hundreds and hundreds of pictures I've uploaded to a server, and processing various aspects of thousands of people I've inputted into this program. Did I overload this sheet somehow or is Google just over me right now (ie, does it not like me trying to use insertImage, for example, 100 times in one call..) Sorry, I've put so much effort into this and the "insertImage" function suddenly not working is a major blow to it when it is NOT the code that is malfunctioning. If it was the code at least I could fix it.
What's odd is I was running the program 2 days ago. Would look up, for example, 100 people and then have it show me all the pics on one page. Ran this a few times and in the middle one of the outputs it suddenly stopped working. I re-ran a query, asked it to show me pictures and it started placing like 20 of them and then just refused to show any more at all. This really seems like Google telling me to f8ck off.

Suddenly moveActiveSheet returns an error - Google Apps Script

I am getting the following error:
Exception: Service Spreadsheets failed while accessing document with
id . . .
when I try to execute a script on a Google sheet.
The script worked fine until today.
I believe the problem occurs between these two lines:
var newTab = sheet.duplicateActiveSheet();
sheet.moveActiveSheet(1);
because at the time of the error the duplicate sheet has been created
but has not yet been moved to the first position.
Is it possible that the "moveActiveSheet" command suddenly can not
find the new active sheet that has just been created?
If so, is there some other way to do this?
There seems to be a bug and it has already been reported.
The issue has been already reported today (15th of December) in the IssueTracker by 13 users (as of now).
Click on the star ⭐ icon to the top/upper-left corner of the webpage to make the issue more popular in order for Google to fix it sooner.
This workaround solution might be useful, I haven't tested it, but you can give it a try.
The problem is an internal error in the moveActiveSheet line.
I have found a work around for the problem.
In the script comment out the moveActiveSheet line as shown here:
var newTab = sheet.duplicateActiveSheet();
// sheet.moveActiveSheet(1);
sheet.renameActiveSheet(newTabName);
This will result in the new tab being misplaced.
You can manually move it to the first position.
Google claims to be working on a fix for this problem.
See https://issuetracker.google.com/issues/175625775
The bug occurs when pos in sheet.moveActiveSheet(pos) is 1
While the bug is being fixed, as a workaround, instead of e.g. moving the second sheet to the first position, you can move the first sheet to the second position.
Because
sheet.moveActiveSheet(2);
still works.

Why does my file download link seem to work, but is unable to find the file?

I added this HTML to a page that I render via a REST call:
StringBuilder builder = new StringBuilder();
. . .
builder.Append("<p></p>");
builder.Append("<a href=\"/App_Data/MinimalSpreadsheetLight.xlsx\" download>");
builder.Append("<p></p>");
. . .
return builder.ToString();
My ASP.NET Web API project has a folder named "App_Data" which does contain a file named "MinimalSpreadsheetLight.xlsx"
The download link is indeed rendered on the page, and clicking it does appear, at first, to download the file (it has the Excel icon, and it bears the file name), but beneath that it says "Failed - No file":
Is the problem with my HTML, or the path I'm using, or file permissions, or what?
I've only tested this with Chrome, so far, BTW. IOW, it's not an IE issue.
UPDATE
I tried it with a leading squiggly, too:
builder.Append("<a href=\"~/App_Data/MinimalSpreadsheetLight.xlsx\" download=\"Spreadsheet file\">");
...yet, alas, to no avail.
UPDATE 2
I changed the pertinent line of HTML to this:
builder.Append("<a href=\"App_Data/MinimalSpreadsheetLight.xlsx\" download=\"Minimal Spreadsheet file\">");
...and it displays in the source like so (with some context):
<p>(Invoice Count excludes credits and re-delivery invoices)</p><p></p><p></p><a href="App_Data/MinimalSpreadsheetLight.xlsx" download="Minimal Spreadsheet file">
...but the link does not appear at all.
UPDATE 3
I was misled by this reference, which showed no text being added; I changed the code to this:
builder.Append("Spreadsheet file");
...(adding "Spreadsheet file" and closing out the anchor tag), and now the link appears; however, I still get the "Failed - No file" msg, and 2-clicking the "downloaded file" does nothing.
UPDATE 4
I tried two other permutations of what's seen in Update 3, namely with the forward whack reintroduced prior to "App_Data":
builder.Append("Spreadsheet file");
...and with both the squiggly prepended and the forward whack:
builder.Append("Spreadsheet file");
...but the results are the same in any of these permutations ("Failed - no file").
UPDATE 5
I also tried it without the "App_Data" at all, on the off change that is not needed:
builder.Append("Spreadsheet file");
...but the same "Failed - No file" is the result of that attempt, too.
UPDATE 6
Okay, so I tried this, too (single quotes):
builder.Append("<a href='/App_Data/MinimalSpreadsheetLight.xlsx' download='Minimal Spreadsheet file'>Spreadsheet file</a>");
...but no change. The file is there:
...so why is it not seen or accessible?
UPDATE 7
This:
string fullPath = HttpContext.Server.MapPath("~/App_Data/MinimalSpreadsheetLight.xlsx");
... (which I got from here) fails to compile with, "An object reference is required for the non-static field, method, or property 'System.Web.HttpContext.Server.get'
2-clicking the err msg highlights just "Server"
UPDATE 8
This (which I got from the same place as what I tried in Update 7):
string justDataDir = AppDomain.CurrentDomain.GetData("DataDirectory").ToString();
string url2 = string.Format("Spreadsheet file</button>", justDataDir);
builder.Append(url2);
...does nothing; clicking the link doesn't even give me a fake/failed download now...
justDataDir is:
C:\Projects\ProActWebReports\ProActWebReports\App_Data
url2 is:
Spreadsheet file</button>
UPDATE 9
I noticed on further fine-tooth-combing that url2 had a forward whack in it; I changed it so that all the whacks were back, but it made no difference to Update 8's results: clicking the link does nothing whatsoever.
If somebody solves this, it will definitely get bountified after the fact.
UPDATE 10
Maybe what I really need to do is, instead of the simple html, add some jQuery that will download the file. But the question is, can jQuery access the App_Data folder any better than raw/simple html can?
The app_data folder is used by iis and asp.net as a private area in which to put database files which can only be accessed by code running on the server.
If you try to access the folder directly via your browser you will get a permissions error.
In order to make the files available for download, move them the a folder under 'Content' (if you have an mvc site) and ensure that your web.config allows the .xlsx exention to be downloaded.
It may depend on what version of iis you are using.
Downloading Docx from IE - Setting MIME Types in IIS

Google Drive watching for new files

I'm considering using Google Drive push notification in order to replace our currently pulling process.
I started playing with it, but I have 2 major problems:
Watching changes:
When watching for drive changes, I get notification with the new change id. But when I try to query it using: driveService.changes().get(changeId), I intermittently get 404. Am I doing something wrong here?
Watching files:
When watching for file changes, in case of a folder, I want to know about new files added to that folder, so I expected that when adding/removing files from this folder, the "x-goog-resource-state" will hold "add/remove" value while "x-goog-changed" will contain "children".
In reality, the "x-goog-changed" does contain "children", but the "x-goog-resource-state" is always "update", and there is no extra information about the added/deleted file.
Regarding deleted files, I know can get it by watching the file once I have it, but is there a way I can get updated about new files in a certain folder?
I was working on a similar project a few months ago. There are two things you can do to monitor changes on Google Drive :
Set Notification Push using : changes().watch()
Set Notification Push using : files().watch()
The 1st case sends you a request for everything that happens on the Drive you are monitoring, with very little information on what exactly has changed.
The 2nd case is less 'spamming', and you get to decide which folder to monitor.
However the tags on the change type are not accurate. when I was using files().watch() I tested all the use-cases, and I compared the headers of each case.
My conclusions are:
for a new file (or folder) creation inside yourfolder (yourfolder/newfile) the headers contain:
'X-Goog-Changed': 'properties'
'X-Goog-Resource-State': 'update'
which is the same when you move a file to yourfolder, or when you start following an existing file in your folder.
you get 'X-Goog-Resource-State': 'add' when you share with a user
as you can see, the header tags are not accurate/unique.
Also, note that the push-notification channel will not send you requests for files inside a folder inside yourfolder (yourfolder/folder/files). And the channel will expire at some point.
If you still have any questions, or want to know how to implement the code, let me know : )