-
-
Notifications
You must be signed in to change notification settings - Fork 38
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Security Vulnerability in Apps Script API #156
Comments
@JeelRajodiya @benjagm please assign this issue to me. |
For local development for others users we can provide them SECRET_KEY for testing purpose sheet while for production we can use the main one. In this way it follows the open source structure. Thanks |
@AQIB-NAWAB If we store the secret key in the frontend, don't you think anyone can view our repo and see that secret key as well? |
We will store the secret key in env file |
For development purpose we provide only TEST_SECRET_KEY. |
Here is sample code which follows the development as well as production guidelines const SECRET_KEY = "OUR_SECRET_KEY";
const postData = JSON.parse(e.postData.contents);
const receivedSecret = postData.secret_key;
// Check if the secret key is provided and matches
if (!receivedSecret) {
return ContentService.createTextOutput(
JSON.stringify({ status: "error", message: "Unauthorized access , Please provide the SECRET KEY" })
).setMimeType(ContentService.MimeType.JSON);
}
let sheet=null;
if(receivedSecret=="TEST_SECRET_KEY"){
sheet = SpreadsheetApp.openById("TEST_SHEET_ID");
}else if(receivedSecret==SECRET_KEY){
sheet = SpreadsheetApp.openById("SHEET_ID");
}else{
return ContentService.createTextOutput(
JSON.stringify({ status: "error", message: "Unauthorized access , Please provide the correct SECRET KEY" })
).setMimeType(ContentService.MimeType.JSON);
} |
Our project is client side only, anything we store in the env file will eventually reflect in the build code. I am aware of this issue, but it is not likely anyone will spam the app script api. if we want to solve this we need a better solution rather than sending a secret from the client (you can know the secret key if you inspect the tour code in network tab). I am not sure how storing a key in client can make it more secure, if you have any example where a project is storing a key in the client to the server to verify the request was sent by the dedicated client, please share. |
We can enhance our security by sending the secret key through request headers, similar to how cookies are used for authentication in many projects. During deployment, our environment variables will be injected into the application, ensuring that these keys do not appear in the build code. This approach helps to keep our secret keys secure while still allowing the necessary authentication between the client and the server. |
There is another approach to solve this problem is validating the domain of client for the request. If it is from tour.json.com |
"During deployment, our environment variables will be injected into the application, ensuring that these keys do not appear in the build code" Can you elaborate this more please, I am unable to understand what is the difference between application and build code? |
This sounds good, how can we validate the domain of the client request? |
Here is function that return sheet according to domain of client side. we can extract the domain from the headers.Referer.
Another approach is that we can have our own backend which contains all the secrets and our client side made request to backend and forward it google app script. |
It is like saving envs in deployment platforms as secrets. For example in Vercel , Cloudflare.But we still ending up exposing the SECRET from client side. |
exactly, we can't put any secrets in our project since it is client side only. Vercel keeps exposes those secrets to the |
Anyone can put custom headers and pretend to be from our domain, Can we think of a better approach? |
How about IP address or using the JWT token same as we do for authentication. |
@JeelRajodiya @benjagm I have another approach. We can make an API request from the frontend using Next.js API routes. The request will include the user's name and email: POST In the API route, we'll call another backend endpoint while keeping the secret key stored in environment variables. This way, all logic is handled on our custom backend server, and secrets remain secure since they won’t be exposed in network requests. |
Our project is hosted on github pages, we can't implement backend or any api endpoints. |
Right now, anyone who knows the API URL can send a request and add data to our Google Sheet. This means unauthorized users could add fake or incorrect data just by making a POST request.
Why is this happening?
The API doesn’t have any security checks in place. There’s nothing stopping someone from sending data, even if they’re not supposed to.
Solution
Here is the code to solve the problem
Here is the video of current behavior
Screencast.from.2025-03-22.19-41-24.webm
The text was updated successfully, but these errors were encountered: