Google apps script create authentication - google-apps-script

I have an application Google apps script and i have more than 3 users in this application i want to create an interface for authentication for this application, and according to any user i will open the interface Appropriate to every user.
Some can Help me with an article or with some code please.Thank you.

The approach I used was:
Set up a group "authed" containing the users that are allowed to use the script which allows easy change of authorised people through existing cpanel interface and saves creating a separate store of authorised people
Set the script to run as owner
In the script,
a. Get the active user
b. Get the groups for that user
c. If that group array contains the "authed" group then go ahead otherwise fail gracefully

Related

How to get the user property for the "active user" in google apps script custom function

I've published a Google Apps Script standalone spreadsheet add-on, while I met some problem using PropertiesService.getUserProperties() in a custom function.
If User A has installed the add-on and saved some data in the user property.
Then User A shared the spreadsheet to User B. When user B run the custom function, he can get the saved data in user property for user A. This is not what I suppose user Property works. Both User A and B should get their own saved data.
So what is the active user for a shared spreadsheet? I don't want all the spreadsheet viewers to get the saved data for the spreadsheet creator. Is there anything I'm doing wrong in code or "Cloud Platform project" option?
In other words, how can I get different data saved in user properties for different viewers in a shared spreadsheet?
I tried to get the active user email in a custom function, but it does not work.
Please note, I can't use Session.getActiveUser in the custom function, because Google Apps Script Custom function does not support Session service. It will get an invalid permission exception.
https://developers.google.com/apps-script/guides/sheets/functions#Advanced
Thanks,
After writing tons of code to test different scenarios, I believe it has no way to solve the above problem.
So I will use a workaround to achieve the goal. In case someone also run into the trouble. I will put down my test results here.
If Google account A shared spreadsheet to Google account B.
In custom function, they all get A's user property.
From a webpage, call into server function via script.run, both A and B can
get their own user property.
Custom functions can't access PropertiesServices.userProperties() (maybe the exception is the spreadsheet owner).
According to https://developers.google.com/apps-script/guides/sheets/functions
Unlike most other types of Apps Scripts, custom functions never ask users to authorize access to personal data. Consequently, they can only call services that do not have access to personal data, specifically the following:
While Properties is included on the list and there isn't any note for this service, since the custom function doesn't ask users to authorize to access personal data it should not return PropertiesServices.userProperties() as it potentially store user personal data.

Google Apps Script - get/assign user unique identifier

I am developing a Google Docs Add-on and need to know if the user currently using the add-on has used it before in the current document or any document. I can't figure out which service gives me some kind of unique identifier for the current user that I can use to identify the current user.
The base service's User.getEmail is not good enough as it doesn't give access to the email under certain conditions and is not reliable.
Thoughts on best way to do this?
Unfortunately, there is no such service. Google wants users' personal information to remain private, so AFAIK you won't usually get even user's email, unless your script is written for Google Apps domain and the user is in the same domain as the script's author.
The only thing you can do in the situation is use something like DocumentApp.getActiveDocument().getId() and check if the script was used in this document, but of course this won't give you an idea if user has used your script in other documents or not.
Also you can show a Prompt Dialog to user, asking him to enter email, but of course there is no way you can check if he entered his real email.
Unique user identifier you can get for apps script is Session.getEffectiveUser().getEmail()
This will return the email of user for which the script run. This is better than ActiveUser because if you use trigger EffectiveUser will well return the email of the user who install the script.
I use that for several apps to identify license assignment and it works great.
It looks like the best solution is to roll your own solution using the following to set the userId at an appropriate time:
PropertiesService.getUserProperties().setProperty("userId",<someGeneratedUId>)
then whenever you want to look up if this user is a recognizable user,
var userId = PropertiesServices.getUserProperties().getProperty("userId")
Looks like once set, the UserProperties thus set is available to this particular user (per user) running this add-on everywhere (i.e. all docs, not just the current on) that have this particular add-on enabled/running.
I'll validate this further but seems like this works in my tests.

Triggering a google apps script for all the users except administrators

How do i configure a google apps trigger for all the domain level users except administratos. Is there any global level configuration available ? or do i need to go individual users account and manually configure the same ?
It's not possible to have an Apps Script run for all users of a domain. Each user must run the code individually. If you wish to run a script for all users in a domain, consider using another platform / programming language and take advantage of service accounts.

Google Apps Script - communication between script

HiMy problem is following: I would like to create small web page, on which it will be possible to create event in Google Calendar, but with some restrictions. In my case this calendar could be edited by my flatmates to reserve washing machine. This reservation cannot overlap and also all of us has limited number of days when we can use it. I have created private calendar, and I have created script which validate requests, and if everything is ok add event to calendar. This script is executed as me (because only I have permission to edit this calendar).
But I have problem with fetching information which user execute this script (me or one of my flatmate). Class Session contains 2 methods getActiveUser() and getEffectiveUser() but active user does not work (I guess because privacy protection policy). But if I create another script which is executed as user accessing the web I can get active user.
Does anybody know if is it possible to communicate somehow between this 2 scripts embedeed on the same site? I want to pass email of active user from one script to another. Or maybe do you know better solution how to solve this problem?
Regards
Adam
As you noticed, you need to set the script to run as the user accessing it to get his email. Then, instead of accessing the calendar directly (which you obviously can't) you can call another script published, but running as yourself allowing anonymous access that will receive this request from the "viewing" script and create the calendar events for it.
After you publish this "background" script, get its url and use it on a UrlfetchApp.fetch call to it. Then pass the parameters as url paremeters (or on payload if you prefer to use post instead of get).
The background script may even use ContentService to give nice return values to the calling script.
Sure, you can do so, but it's not as simple as you'd like. Make your admin level script run a web service that responds to the other script. It can probably be hacked as you can't authenticate the users, but comon, this is a washing macine!

Session.getActiveUser().getEmail() workaround for distributing grades from a spreadsheet

My students all have a Google account, but use different emails (like john#hotmail.com).I tried to write a webapp that would get from my grade spreadsheet the row with the webapp's user's email address, so that each student would only see his or her grades. That webapp uses: Session.getActiveUser().getEmail()
This only works for users in the same domain as the script, I have to run the script as the webapp user (which is ok -- my students trust me that far!). Here is that restriction:
Returns a User object describing the current user. In
limited-privilege executions (such as in response to onOpen or
onEdit), we only return the identity of the active user if both the
user and the script owner are part of the same domain. This is to
protect the privacy of consumer users, who may not want their email
address exposed.
My script works, but I have to put the table of grades directly in the script and update the webapp each time I update my spreadsheet. Yeck!
I can't share my grade spreadsheet because then they would see each other's grades. So now I am brainstorming other workarounds.
Here is one example:
Share a second spreadsheet, copy the grades from my spreadsheet with an update function that encrypts the grades. The webapp sucks up the data from the shared spreadsheet and decrypts. Now a simple update of a spreadsheet is all that is needed -- the webapp doesn't need to be republished. (There are some simple encryption options, like base64encode with maybe a little scrambling...?)
Find a way to automatically update the webapp and republish. (Don't know how to do that.)
????
Any suggestions?
PS: if 1 seems feasible, some suggestions for simple encryption code?
There are some simple encryption options, like base64encode with maybe a little scrambling...?
Yes, the GAS has functions to encode/decode using the Base64 algorithm - Utilities.base64Encode, Utilities.base64Decode, but I think, it is not an option even with a little scrambling. Students are very clever. My opinion is to use a JavaScript implementation of a encryption algorithm, for instance the Blowfish. There are a number of its implementations on JavaScript (here and here). These implementations should work in the GAS environment without any changes or with small modifications. It is should be sufficient to copy and paste the source code to the GAS Editor.
I dont understand why you say "My script works, but I have to put the table of grades directly in the script and update the webapp each time I update my spreadsheet"
It is very easy to create a webapp that shows a part of a spreadsheet using a flextable for example. Each instance of the app will have a user related content automatically and you will only have to update your master spreadsheet to get what you want. I don't know why you want to encode data for this... I think the user identification through the google login should be enough, don't you ?
Here is an example of such a webapp, the numbers you see are taken from a specific column in a master spreadsheet (for this public copy I set the app as running as "me" to avoid the authorization process but in real every user is identified and sees only his data).
The Spreadsheet itself and the code are viewable here, do not hesitate to come back if you need further information.
Is it an option to sync your sheet with a scriptDB?
And then query the DB where user=loginID