Issue[557] File Upload for Application Form & Google Drive Integration#907
Issue[557] File Upload for Application Form & Google Drive Integration#907shuwangs wants to merge 12 commits into
Conversation
- integrate Google Drive API for file upload - implement login and callback routes for authorization - add PKCE (code_verifier) for secure token exchange - store and get credentials using session - upload one hardcoded file to drive
- add helper function to query Google Drive for an existing folder by user identifier\n - create a new folder under the root folder if none exists\n - currently uses email as folder name for testing purposes
- replace MediaFileUpload with MediaIoBaseUpload to support in-memory file uploads\n - save user email to session in application form for downstream use\n - create or retrieve user-specific Google Drive folder in household POST route\n - upload income and net worth documents to the user's folder \n - use --no-verify due to the conflicts of black and isort
- update form action to POST \n - implement POST handling in route and upload typing screenshot and fcc screenshot to folder\n - comment out formValidate at the bottom to allow POST\n - use --no-verify due to conflict
|
@shuwangs Please put front end validation back as this PR could not be released with validation commented out and should be tested with front end validation to ensure that validation still functions correctly with uploading documents. Thanks! Also, does this require new libraries? If so please add a pip install to your instructions |
- previously form could only route to next step without POSTing data - add shouldSubmit flag to distinguish between navigation and submission - ensure data is submitted only when intended
…ion vs navigation
…e form drive_service_Oauth
Hi Monikka, thanks for the feedback! I’ve added the frontend validation back and confirmed that it works correctly with the file upload flow, in 79ac8c0 and 7c86dc2 Updated the requirements in 3b45adf |
| SCOPES = ["https://www.googleapis.com/auth/drive"] | ||
| CLIENT_SECRETS_FILE = os.getenv("CLIENT_SECRETS_FILE") | ||
| GOOGLE_DRIVE_FOLDER_ID = os.getenv("GOOGLE_DRIVE_FOLDER_ID") | ||
| REDIRECT_URI = "http://127.0.0.1:5000/oauth2callback" |
There was a problem hiding this comment.
Should this be in .env file? Likely okay for development. I'd be cautious about adding this to production.
| return folder.get("id") | ||
|
|
||
|
|
||
| def upload(credentials_dict, user_folder_id, file_to_upload, custom_name=None): |
There was a problem hiding this comment.
Consider adding a max file limit size. Something like MAX_FILE_SIZE = 50 * 1000 * 1000 (equals to 50 MB)
|
|
Hi @monikkaelyse and @daaimah123 Another issue I’d like to discuss is the file upload flow in the multi-step form. Right now, in both the household form and the additional form, clicking “save” immediately creates a dedicated subfolder in Google Drive and uploads the files. The concern is that if an applicant never finishes or submits the application, we may end up with orphaned files/folders left in Drive. I’m thinking about two possible alternatives: Store files temporarily (for example in IndexedDB) and defer the Google Drive upload until final submission. I’d love any thoughts on which direction seems more appropriate. |
For the file uploads, I would suggest first uploading in Google in a temp folder, then upon completion of the form they get moved to the permanent folder. The application process would most likely utilize the database, so that when a user starts an application the information gets written to the db with a status of "in progress" or something, then when they submit the status would change to "submitted". Perhaps later there is a clean up process that will delete any old applications that have not been submitted, and part of that cleanup would be to delete their files from the temp folder. This db process is out of scope for this ticket but if there is no ticket for this, we should make one. For the Google account issue, @daaimah123 is it best if there's a shared folder in Techtonica's drive for testing / deploying this? Just ping me if you have any questions or if you'd like to move forward with this plan, just ping me when changes are made and you're ready for review. Thanks! |
- revert validateSubmitForm - use FormData to upload files separately from the full form - send user_email along with upload requests - keep uploads in the temp Google Drive folder - stop sending OAuth callback to the old upload test flow - switch Google Drive uploads to use the temp folder env var
|
Hey @shuwangs doing my round of check-ins for the repo, will you be able to update this PR with latest from mvp branch and address the requests for changes? |
Thanks for checking in, I’ve started working on the file upload flow and currently have files being saved to a temporary folder. |
- keep multi-step file uploads on the frontend with FormData - upload household and additional files to a temp Google Drive folder - submit the final application through a dedicated submit endpoint - move uploaded files from the temp folder to the permanent folder on submit
|
Updated this PR with the latest changes. The upload flow now uses a temp Google Drive folder during the multi-step process, and files are moved to the permanent folder on final submit. Still out of scope for this PR:
Would appreciate another review when you have a chance. |
|
@shuwangs I have a question about the security of the Google Drive setup. If we have one set of credentials and give it access to our drive, then we specify certain folders in our .env file, does that mean potentially with these credentials they could have access to any folder specified in the .env (assuming it exists)? Is the Google drive folder we create in our main Google Drive or is this a Project specific Google Drive location? Or can we lock down these credentials to these specific folders? I would worry that in theory someone could gain access to everything in the drive if they knew where to look. Additionally, do your Google drive setup instructions need to change now that there are two folders (temp and permanent)? |
Thanks for your question, the folder IDs in .env are mainly used as destination references, not as access restrictions themselves. Th actual security boundary comes from the OAuth scopes and the Google account being used for the integration. If the configured Drive scope is broad, then technically the authenticated account could access other Drive content that account has permission to access (Drive Scope. From my understanding Google Drive OAuth isnot designed as folder-specific access authorization. I think a safer approach would be to use a dedicated Google Drive account for this, or potentially a service account setup where access is limited to only the intended upload folders. And, I already added the separate temp/permanent env vars, but the setup instructions should also be updated to clarify that two Google Drive folders are now required,I have updated in the PR. |
Thanks for clarifying, I am a bit hesitant to enable this for testing in my own personal Google drive given this security issue. I will dig a little bit to see what the best testing solution is going forward since we will need to be able to test this frequently and pass credentials to various developers working on this in the future. I can potentially make a techtonica testing google account for now and see if that will work, but I know you ran into issues with this previously? Since this flow only uploads files created by the application form, can we avoid full https://www.googleapis.com/auth/drive and use drive.file instead? We may need the app to create the temp/permanent root folders itself, or add a setup step where the tester explicitly grants access to those folders. That would better match the upload-only use case and avoid broad access to a tester’s entire Drive. |
📝 Description
This PR implements a Google Drive-based file upload flow for the application process using OAuth 2.0. Applicant files are uploaded into a temporary Google Drive folder during the multi-step application flow, and then moved into a permanent folder when the final submission is completed.
Demo
🔂 Changes Made
⚙️ Related Issue
🍏 Type of Change
Notes
Next Steps
🎁 Acceptance Criteria
/app-householdand/app-additionalforms are successfully stored in the correct user folder🧰 New Environment Variables or Requirements
The following environment variables are required:
CLIENT_SECRETS_FILE
Path to the Google OAuth 2.0 client secrets JSON file.
GOOGLE_DRIVE_FOLDER_TEMP_ID
The root Google Drive folder ID used for temporary uploads.
GOOGLE_DRIVE_FOLDER_PERMANENT_ID
The root Google Drive folder ID used for finalized application files.
REDIRECT_URI
OAuth callback URI for local development.
Additional requirements:
🧪 How to test
🔐 Google Drive Setup
This project uses Google OAuth 2.0 and the Google Drive API to upload applicant files.
1. Create Google Cloud Project
2. Enable Google Drive API
3. Configure OAuth Consent Screen
4. Create OAuth Credentials
5. Create Google Drive Root Folders
Create two folders in Google Drive:
One folder for temporary uploads during the multi-step application flow
Techtonica_Uploads_TempGOOGLE_DRIVE_FOLDER_TEMP_IDOne folder for finalized application files after final submission
Techtonica_Uploads_PermanentGOOGLE_DRIVE_FOLDER_PERMANENT_IDCopy each folder ID from the folder URL:
Example:
https://drive.google.com/drive/folders/<your_root_folder_id>6. Set Environment Variables
✅ Checklist