Package: django-gsheets-roymo
django-gsheetsDjango app for keeping models and google sheets syncedPurposedjango-gsheets is a pluggable Django app that adds functionality (via mixins) to models allowing them to sync data to and from Google Sheets. The app errs on the side of caution in that deletions from your DB won't propagate to the sheet and visa versa.InstallationInstall django-gsheetspip install django-gsheetsAdd django-gsheets to INSTALLED_APPSINSTALLED_APPS=[...'gsheets',...]After adding, make sure to runmigrateCreate a Google Cloud Project and Download OAuth Client SecretsGoogle has a good guide for thathere(you only need to do Step 1).Update Project SettingsUpdate your project settings to tell django-gsheets where the downloaded credentials are. You should just need the following:GSHEETS={'CLIENT_SECRETS':'<PATH TO DOWNLOADED CREDS>'}Add GSheets URLS to the ProjectUpdate your project URLs to include django-gsheets paths.urlpatterns=[...path('',include('gsheets.urls')),]UsageAdd the SheetSyncableMixin to a ModelIn order to provide two-way sync capability to a models' data, all you need to do is add theSheetSyncableMixinto it and tell the model what sheet to use. For example:fromdjango.dbimportmodelsfromgsheetsimportmixinsfromuuidimportuuid4classPerson(mixins.SheetSyncableMixin,models.Model):spreadsheet_id='18F_HLftNtaouHgA3fmfT2M1Va9oO-YWTBw2EDsuz8V4'model_id_field='guid'guid=models.CharField(primary_key=True,max_length=255,default=uuid4)first_name=models.CharField(max_length=127)last_name=models.CharField(max_length=127)email=models.CharField(max_length=127,null=True,blank=True,default=None)phone=models.CharField(max_length=127,null=True,blank=True,default=None)def__str__(self):returnf'{self.first_name}{self.last_name}//{self.email}({self.guid})'To two-way sync sheet data, simply runPerson.sync_sheet().If you want to be more fine-grained and have models that either just push to Google Sheets or just pull, you can swapSheetSyncableMixinforSheetPushableMixinorSheetPullableMixin(respectively).Authorize Google SheetsBefore your first usage, you'll need to authorize the app to perform operations on your Google Sheets. To do so, access/gsheets/authorize/on your application and go through the standard oauth flow.Further ConfigurationYou can further configure the functionality of sheet sync by specifying any of the following fields on the model.FieldDefaultDescriptionspreadsheet_idNonedesignates the Google Sheet to syncsheet_nameSheet1the name of the sheet in the Google Sheetdata_rangeA1:Zthe range of data in the sheet to keep synced. First row must contain field names that match model fields.model_id_fieldidthe name of the model field storing a unique ID for each rowsheet_id_fieldDjango GUIDthe name of the field in the synced sheet that will store model instance IDsbatch_size500(internal) the batch size to use when updating sheets with progressmax_rows30000(internal) used for internal calculations, don't change unless you know what you're doingmax_colZ(internal) used for internal calculations, don't change unless you know what you're doingPostprocessingYou can hook into the postprocessing step of row pulling to perform operations like tying the model instance to a related object. For example, the following demonstrates using thesheet_row_processedsignal to update a Car with it's owner information based on a field calledowner_last_namein the spreadsheetfromdjango.dispatchimportreceiverfromdjango.core.exceptionsimportObjectDoesNotExistfromgsheets.signalsimportsheet_row_processedfrom.modelsimportCar,Person@receiver(sheet_row_processed,sender=Car)deftie_car_to_owner(instance=None,created=None,row_data=None,**kwargs):try:instance.owner=Person.objects.get(last_name__iexact=row_data['owner_last_name'])instance.save()except(ObjectDoesNotExist,KeyError):passManagement CommandsIf you don't want to manually sync data to and from models to gsheets,django-gsheetsships with a handy management command that automatically discovers all models mixing in one ofSheetPullableMixin,SheetPushableMixin, orSheetSyncableMixinand runs the appropriate sync command. To execute, simply runpython manage.py syncgsheets.Known LimitationsNo support for Related fieldsDevelopmentAny and all contributions welcome. To get started with a development environment, simply pull down a copy of this repo and bring up the environment withdocker-compose up -d. Before doing so, however, you should have the following in place:A google project setup (notes on that in theInstallationsection above). After setting up, download the client credentials JSON file to thecredsfolder in this repo. This folder is volume mounted into the running application container at/creds.An ngrok (or similar) server set up to proxy an https connection to your local dev environment. You'll need this because Google OAuth2 only supports https redirect URIs.