feat: google drive initial bringup
This commit is contained in:
parent
f1b3f58806
commit
a23dc0a749
9 changed files with 332 additions and 3 deletions
|
|
@ -76,7 +76,7 @@ def get_bootinfo():
|
|||
bootinfo.calendars = sorted(frappe.get_hooks("calendars"))
|
||||
bootinfo.treeviews = frappe.get_hooks("treeviews") or []
|
||||
bootinfo.lang_dict = get_lang_dict()
|
||||
bootinfo.gsuite_enabled = get_gsuite_status()
|
||||
bootinfo.google_drive_enabled = get_google_drive_status()
|
||||
bootinfo.success_action = get_success_action()
|
||||
bootinfo.update(get_email_accounts(user=frappe.session.user))
|
||||
bootinfo.energy_points_enabled = is_energy_point_enabled()
|
||||
|
|
@ -258,8 +258,8 @@ def get_unseen_notes():
|
|||
(select user from `tabNote Seen By` nsb
|
||||
where nsb.parent=`tabNote`.name)''', (frappe.utils.now(), frappe.session.user), as_dict=True)
|
||||
|
||||
def get_gsuite_status():
|
||||
return (frappe.get_value('Gsuite Settings', None, 'enable') == '1')
|
||||
def get_google_drive_status():
|
||||
return True if frappe.db.exists("Google Drive", {"enable": 1}) else False
|
||||
|
||||
def get_success_action():
|
||||
return frappe.get_all("Success Action", fields=["*"])
|
||||
|
|
|
|||
0
frappe/integrations/doctype/google_drive/__init__.py
Normal file
0
frappe/integrations/doctype/google_drive/__init__.py
Normal file
30
frappe/integrations/doctype/google_drive/google_drive.js
Normal file
30
frappe/integrations/doctype/google_drive/google_drive.js
Normal file
|
|
@ -0,0 +1,30 @@
|
|||
// Copyright (c) 2019, Frappe Technologies and contributors
|
||||
// For license information, please see license.txt
|
||||
|
||||
frappe.ui.form.on('Google Drive', {
|
||||
refresh: function(frm) {
|
||||
if (frm.is_new()) {
|
||||
frm.dashboard.set_headline(__("To use Google Drive, enable <a href='#Form/Google Settings'>Google Settings</a>."));
|
||||
}
|
||||
},
|
||||
authorize_google_drive_access: function(frm) {
|
||||
let reauthorize = 0;
|
||||
if(frm.doc.authorization_code) {
|
||||
reauthorize = 1;
|
||||
}
|
||||
|
||||
frappe.call({
|
||||
method: "frappe.integrations.doctype.google_drive.google_drive.authorize_access",
|
||||
args: {
|
||||
"g_drive": frm.doc.name,
|
||||
"reauthorize": reauthorize
|
||||
},
|
||||
callback: function(r) {
|
||||
if(!r.exc) {
|
||||
frm.save();
|
||||
window.open(r.message.url);
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
});
|
||||
94
frappe/integrations/doctype/google_drive/google_drive.json
Normal file
94
frappe/integrations/doctype/google_drive/google_drive.json
Normal file
|
|
@ -0,0 +1,94 @@
|
|||
{
|
||||
"autoname": "format:{folder_name}-{reference_doctype}",
|
||||
"creation": "2019-08-08 13:16:06.783138",
|
||||
"doctype": "DocType",
|
||||
"engine": "InnoDB",
|
||||
"field_order": [
|
||||
"enable",
|
||||
"sb_00",
|
||||
"user",
|
||||
"folder_name",
|
||||
"authorize_google_drive_access",
|
||||
"authorization_code",
|
||||
"refresh_token"
|
||||
],
|
||||
"fields": [
|
||||
{
|
||||
"default": "0",
|
||||
"fieldname": "enable",
|
||||
"fieldtype": "Check",
|
||||
"label": "Enable"
|
||||
},
|
||||
{
|
||||
"depends_on": "enable",
|
||||
"fieldname": "sb_00",
|
||||
"fieldtype": "Section Break",
|
||||
"label": "Google Drive"
|
||||
},
|
||||
{
|
||||
"fieldname": "user",
|
||||
"fieldtype": "Link",
|
||||
"in_list_view": 1,
|
||||
"label": "User",
|
||||
"options": "User",
|
||||
"reqd": 1
|
||||
},
|
||||
{
|
||||
"depends_on": "eval:!doc.__islocal",
|
||||
"fieldname": "authorize_google_drive_access",
|
||||
"fieldtype": "Button",
|
||||
"label": "Authorize Google Drive Access"
|
||||
},
|
||||
{
|
||||
"fieldname": "folder_name",
|
||||
"fieldtype": "Data",
|
||||
"in_list_view": 1,
|
||||
"label": "Folder Name",
|
||||
"reqd": 1,
|
||||
"set_only_once": 1,
|
||||
"unique": 1
|
||||
},
|
||||
{
|
||||
"fieldname": "authorization_code",
|
||||
"fieldtype": "Password",
|
||||
"label": "Authorization Code"
|
||||
},
|
||||
{
|
||||
"fieldname": "refresh_token",
|
||||
"fieldtype": "Password",
|
||||
"label": "Refresh Token"
|
||||
}
|
||||
],
|
||||
"modified": "2019-08-09 18:20:58.169056",
|
||||
"modified_by": "Administrator",
|
||||
"module": "Integrations",
|
||||
"name": "Google Drive",
|
||||
"owner": "Administrator",
|
||||
"permissions": [
|
||||
{
|
||||
"create": 1,
|
||||
"delete": 1,
|
||||
"email": 1,
|
||||
"print": 1,
|
||||
"read": 1,
|
||||
"role": "System Manager",
|
||||
"share": 1,
|
||||
"write": 1
|
||||
},
|
||||
{
|
||||
"create": 1,
|
||||
"delete": 1,
|
||||
"email": 1,
|
||||
"export": 1,
|
||||
"print": 1,
|
||||
"read": 1,
|
||||
"report": 1,
|
||||
"role": "All",
|
||||
"share": 1,
|
||||
"write": 1
|
||||
}
|
||||
],
|
||||
"sort_field": "modified",
|
||||
"sort_order": "ASC",
|
||||
"track_changes": 1
|
||||
}
|
||||
133
frappe/integrations/doctype/google_drive/google_drive.py
Normal file
133
frappe/integrations/doctype/google_drive/google_drive.py
Normal file
|
|
@ -0,0 +1,133 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
# Copyright (c) 2019, Frappe Technologies and contributors
|
||||
# For license information, please see license.txt
|
||||
|
||||
from __future__ import unicode_literals
|
||||
import frappe
|
||||
import requests
|
||||
import googleapiclient.discovery
|
||||
import google.oauth2.credentials
|
||||
|
||||
from frappe import _
|
||||
from frappe.model.document import Document
|
||||
from frappe.utils import get_request_site_address
|
||||
from six.moves.urllib.parse import quote
|
||||
from apiclient.http import MediaFileUpload
|
||||
|
||||
SCOPES = "https://www.googleapis.com/auth/drive"
|
||||
|
||||
class GoogleDrive(Document):
|
||||
|
||||
def get_access_token(self):
|
||||
google_settings = frappe.get_doc("Google Settings")
|
||||
|
||||
if not google_settings.enable:
|
||||
frappe.throw(_("Google Integration is disabled."))
|
||||
|
||||
if not self.refresh_token:
|
||||
button_label = frappe.bold(_("Allow Google Drive Access"))
|
||||
raise frappe.ValidationError(_("Click on {0} to generate Refresh Token.").format(button_label))
|
||||
|
||||
data = {
|
||||
"client_id": google_settings.client_id,
|
||||
"client_secret": google_settings.get_password(fieldname="client_secret", raise_exception=False),
|
||||
"refresh_token": self.get_password(fieldname="refresh_token", raise_exception=False),
|
||||
"grant_type": "refresh_token",
|
||||
"scope": SCOPES
|
||||
}
|
||||
|
||||
try:
|
||||
r = requests.post("https://www.googleapis.com/oauth2/v4/token", data=data).json()
|
||||
except requests.exceptions.HTTPError:
|
||||
button_label = frappe.bold(_("Allow Google Drive Access"))
|
||||
frappe.throw(_("Something went wrong during the token generation. Click on {0} to generate a new one.").format(button_label))
|
||||
|
||||
return r.get("access_token")
|
||||
|
||||
@frappe.whitelist()
|
||||
def authorize_access(g_drive, reauthorize=None):
|
||||
"""
|
||||
If no Authorization code get it from Google and then request for Refresh Token.
|
||||
Google Contact Name is set to flags to set_value after Authorization Code is obtained.
|
||||
"""
|
||||
|
||||
google_settings = frappe.get_doc("Google Settings")
|
||||
google_drive = frappe.get_doc("Google Drive", g_drive)
|
||||
|
||||
redirect_uri = get_request_site_address(True) + "?cmd=frappe.integrations.doctype.google_drive.google_drive.google_callback"
|
||||
|
||||
if not google_drive.authorization_code or reauthorize:
|
||||
frappe.cache().hset("google_drive", "google_drive", google_drive.name)
|
||||
return get_authentication_url(client_id=google_settings.client_id, redirect_uri=redirect_uri)
|
||||
else:
|
||||
try:
|
||||
data = {
|
||||
"code": google_drive.authorization_code,
|
||||
"client_id": google_settings.client_id,
|
||||
"client_secret": google_settings.get_password(fieldname="client_secret", raise_exception=False),
|
||||
"redirect_uri": redirect_uri,
|
||||
"grant_type": "authorization_code"
|
||||
}
|
||||
r = requests.post("https://www.googleapis.com/oauth2/v4/token", data=data).json()
|
||||
|
||||
if "refresh_token" in r:
|
||||
frappe.db.set_value("Google Drive", google_drive.name, "refresh_token", r.get("refresh_token"))
|
||||
frappe.db.commit()
|
||||
|
||||
frappe.local.response["type"] = "redirect"
|
||||
frappe.local.response["location"] = "/desk#Form/{0}/{1}".format(quote("Google Drive"), quote(google_drive.name))
|
||||
|
||||
frappe.msgprint(_("Google Drive has been configured."))
|
||||
except Exception as e:
|
||||
frappe.throw(e)
|
||||
|
||||
def get_authentication_url(client_id, redirect_uri):
|
||||
return {
|
||||
"url": "https://accounts.google.com/o/oauth2/v2/auth?access_type=offline&response_type=code&prompt=consent&client_id={}&include_granted_scopes=true&scope={}&redirect_uri={}".format(client_id, SCOPES, redirect_uri)
|
||||
}
|
||||
|
||||
@frappe.whitelist()
|
||||
def google_callback(code=None):
|
||||
"""
|
||||
Authorization code is sent to callback as per the API configuration
|
||||
"""
|
||||
google_drive = frappe.cache().hget("google_drive", "google_drive")
|
||||
frappe.db.set_value("Google Drive", google_drive, "authorization_code", code)
|
||||
frappe.db.commit()
|
||||
|
||||
authorize_access(google_drive)
|
||||
|
||||
def get_google_drive_object(g_drive):
|
||||
"""
|
||||
Returns an object of Google Drive.
|
||||
"""
|
||||
google_settings = frappe.get_doc("Google Settings")
|
||||
account = frappe.get_doc("Google Drive", g_drive)
|
||||
|
||||
credentials_dict = {
|
||||
"token": account.get_access_token(),
|
||||
"refresh_token": account.get_password(fieldname="refresh_token", raise_exception=False),
|
||||
"token_uri": "https://www.googleapis.com/oauth2/v4/token",
|
||||
"client_id": google_settings.client_id,
|
||||
"client_secret": google_settings.get_password(fieldname="client_secret", raise_exception=False),
|
||||
"scopes": "https://www.googleapis.com/auth/drive/v3"
|
||||
}
|
||||
|
||||
credentials = google.oauth2.credentials.Credentials(**credentials_dict)
|
||||
google_drive = googleapiclient.discovery.build("drive", "v3", credentials=credentials)
|
||||
|
||||
return google_calendar
|
||||
|
||||
@frappe.whitelist()
|
||||
def upload_document(doctype, docname, g_drive):
|
||||
from frappe.utils.print_format import download_pdf
|
||||
|
||||
google_drive = get_google_drive_object(g_drive)
|
||||
download_pdf(doctype=doctype, docname=docname, format="pdf")
|
||||
file_metadata = {"name": frappe.local.response.filename}
|
||||
media = MediaFileUpload(frappe.local.response.filename, mimetype="application/pdf")
|
||||
|
||||
file = google_drive.files().create(body=file_metadata, media_body=media, fields='id').execute()
|
||||
|
||||
|
||||
# frappe.local.response.filecontent
|
||||
|
|
@ -0,0 +1,10 @@
|
|||
# -*- coding: utf-8 -*-
|
||||
# Copyright (c) 2019, Frappe Technologies and Contributors
|
||||
# See license.txt
|
||||
from __future__ import unicode_literals
|
||||
|
||||
# import frappe
|
||||
import unittest
|
||||
|
||||
class TestGoogleDrive(unittest.TestCase):
|
||||
pass
|
||||
|
|
@ -205,6 +205,7 @@
|
|||
"public/js/frappe/ui/toolbar/toolbar.js",
|
||||
"public/js/frappe/ui/toolbar/notifications.js",
|
||||
"public/js/frappe/views/communication.js",
|
||||
"public/js/frappe/views/google_drive_uploader.js",
|
||||
"public/js/frappe/views/translation_manager.js",
|
||||
|
||||
"public/js/frappe/ui/sort_selector.html",
|
||||
|
|
|
|||
|
|
@ -125,6 +125,15 @@ frappe.ui.form.Toolbar = Class.extend({
|
|||
}
|
||||
}
|
||||
|
||||
//Google Drive
|
||||
if(frappe.boot.google_drive_enabled){
|
||||
this.page.add_menu_item(__("Google Drive Upload"), function() {
|
||||
new frappe.views.GoogleDriveUploader(me.frm);}, true);
|
||||
this.print_icon = this.page.add_action_icon("fa fa-google", function() {
|
||||
new frappe.views.GoogleDriveUploader(me.frm);
|
||||
});
|
||||
}
|
||||
|
||||
// email
|
||||
if(frappe.model.can_email(null, me.frm) && me.frm.doc.docstatus < 2) {
|
||||
this.page.add_menu_item(__("Email"), function() {
|
||||
|
|
|
|||
52
frappe/public/js/frappe/views/google_drive_uploader.js
Normal file
52
frappe/public/js/frappe/views/google_drive_uploader.js
Normal file
|
|
@ -0,0 +1,52 @@
|
|||
frappe.views.GoogleDriveUploader = Class.extend({
|
||||
init: function(opts) {
|
||||
$.extend(this, opts);
|
||||
this.make();
|
||||
},
|
||||
make: function() {
|
||||
let me = this;
|
||||
let uploader = new frappe.ui.Dialog({
|
||||
title: __("Upload File to Google Drive"),
|
||||
fields: [
|
||||
{
|
||||
fieldtype: "Link",
|
||||
fieldname: "google_drive",
|
||||
options: "Google Drive",
|
||||
label: __("Google Drive"),
|
||||
reqd: 1,
|
||||
get_query: function() {
|
||||
return {
|
||||
"filters": {
|
||||
"owner": frappe.session.user,
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
],
|
||||
primary_action_label: __("Submit"),
|
||||
primary_action: (d) => {
|
||||
frappe.show_alert({
|
||||
indicator: "red",
|
||||
message: __("Uploading to Google Drive.")
|
||||
});
|
||||
uploader.hide();
|
||||
frappe.call({
|
||||
method: "frappe.integrations.doctype.google_drive.google_drive.upload_document",
|
||||
args: {
|
||||
doctype: me.doctype,
|
||||
docname: me.docname,
|
||||
g_drive: d.google_drive,
|
||||
},
|
||||
callback: function(r) {
|
||||
frappe.show_alert({
|
||||
indicator: "green",
|
||||
message: __("Document uploaded to Google Drive.")
|
||||
});
|
||||
uploader.hide();
|
||||
}
|
||||
})
|
||||
}
|
||||
});
|
||||
uploader.show();
|
||||
}
|
||||
})
|
||||
Loading…
Add table
Reference in a new issue