如何将存储在 Google 驱动器上的 Google 文档文件(文档模板)转换为 PDF 并下载?
How do I convert Google Docs file (Template for Document) Stored on Google Drive to PDF and download it?
现在卡在这个问题上几个小时了。我有一个可以用 python 编辑的模板。这个想法是复制、编辑、转换、下载然后从驱动器中删除文件,只留下空模板。我通读了文档并尝试了不同的方法,但我无法弄清楚。
编辑:
到目前为止我的代码
SCOPES = ['https://www.googleapis.com/auth/drive']
DOCUMENT_ID = '1ZgaYCra-7m_oWIBWK9RoMssYNTAsQLa1ELI1vyBB73c'
def main():
creds = None
# The file token.pickle stores the user's access and refresh tokens, and is
# created automatically when the authorization flow completes for the first
# time.
if os.path.exists('token.pickle'):
with open('token.pickle', 'rb') as token:
creds = pickle.load(token)
# If there are no (valid) credentials available, let the user log in.
if not creds or not creds.valid:
if creds and creds.expired and creds.refresh_token:
creds.refresh(Request())
else:
flow = InstalledAppFlow.from_client_secrets_file(
'credentials.json', SCOPES)
creds = flow.run_local_server(port=0)
# Save the credentials for the next run
with open('token.pickle', 'wb') as token:
pickle.dump(creds, token)
service = build('docs', 'v1', credentials=creds)
text1 = 'test'
requests1 = [
{
'insertText': {
'location': {
'index': 110,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 98,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 83,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 72,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 49,
},
'text': text1
}
},
]
result = service.documents().batchUpdate(
documentId=DOCUMENT_ID, body={'requests': requests1}).execute()
if name == 'main':
主要()
我相信你的现状和你的目标如下。
- 您有一个 Google 文档作为模板文档。
- 您想使用 python 的 googleapis 实现以下流程。
- 复制模板文档。
- 更新复制的文档。
- 将更新后的文档下载为 PDF 文件。
- 删除复制的文档。
修改点:
- 您的脚本更新了现有的 Google 文档。所以为了达到你的目的,还需要准备其他流程。
- 为了复制模板文档,将文档下载为PDF文件并删除文档,驱动器API使用如下。并且,当文档更新时,使用 Docs API。
- 复制模板文档。
- 在这种情况下,使用驱动器 API。
- 更新复制的文档。
- 在这种情况下,使用 Docs API 并且使用 yoru 脚本中的脚本。
- 将更新后的文档下载为 PDF 文件。
- 在这种情况下,使用驱动器 API。
- 删除复制的文档。
- 在这种情况下,使用驱动器 API。
当你的脚本修改后,变成如下。
修改后的脚本:
在这个修改后的脚本中,它假定您的脚本使用了 credentials=creds
中的 creds
。并且,在使用此脚本之前,请设置变量。
templateDocumentId = '###' # Please set the Document ID.
outputPDFFilename = 'sample.pdf' # Please set the output PDF filename.
drive = build('drive', 'v3', credentials=creds)
docs = build('docs', 'v1', credentials=creds)
# 1. Copy template Document.
copiedDoc = drive.files().copy(fileId=templateDocumentId, body={'name': 'copiedTemplateDocument'}).execute()
copiedDocId = copiedDoc.get('id')
print('Done: 1. Copy template Document.')
# 2. Update copied Document.
text1 = 'test'
requests1 = [
{
'insertText': {
'location': {
'index': 110,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 98,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 83,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 72,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 49,
},
'text': text1
}
},
]
result = docs.documents().batchUpdate(documentId=copiedDocId, body={'requests': requests1}).execute()
print('Done: 2. Update copied Document.')
# 3. Download the updated Document as PDF file.
request = drive.files().export_media(fileId=copiedDocId, mimeType='application/pdf')
fh = io.FileIO(outputPDFFilename, mode='wb')
downloader = MediaIoBaseDownload(fh, request)
done = False
while done is False:
status, done = downloader.next_chunk()
print('Download %d%%.' % int(status.progress() * 100))
print('Done: 3. Download the updated Document as PDF file.')
# 4. Delete the copied Document.
drive.files().delete(fileId=copiedDocId).execute()
print('Done: 4. Delete the copied Document.')
注:
- 为了下载文件,还使用了
import io
和from googleapiclient.http import MediaIoBaseDownload
。
- 在这个答案中,它假设您的
requests1
for service.documents().batchUpdate(documentId=DOCUMENT_ID, body={'requests': requests1}).execute()
的请求正文按您预期的那样工作正常。所以请注意这一点。
参考文献:
现在卡在这个问题上几个小时了。我有一个可以用 python 编辑的模板。这个想法是复制、编辑、转换、下载然后从驱动器中删除文件,只留下空模板。我通读了文档并尝试了不同的方法,但我无法弄清楚。
编辑: 到目前为止我的代码
SCOPES = ['https://www.googleapis.com/auth/drive']
DOCUMENT_ID = '1ZgaYCra-7m_oWIBWK9RoMssYNTAsQLa1ELI1vyBB73c'
def main():
creds = None
# The file token.pickle stores the user's access and refresh tokens, and is
# created automatically when the authorization flow completes for the first
# time.
if os.path.exists('token.pickle'):
with open('token.pickle', 'rb') as token:
creds = pickle.load(token)
# If there are no (valid) credentials available, let the user log in.
if not creds or not creds.valid:
if creds and creds.expired and creds.refresh_token:
creds.refresh(Request())
else:
flow = InstalledAppFlow.from_client_secrets_file(
'credentials.json', SCOPES)
creds = flow.run_local_server(port=0)
# Save the credentials for the next run
with open('token.pickle', 'wb') as token:
pickle.dump(creds, token)
service = build('docs', 'v1', credentials=creds)
text1 = 'test'
requests1 = [
{
'insertText': {
'location': {
'index': 110,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 98,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 83,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 72,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 49,
},
'text': text1
}
},
]
result = service.documents().batchUpdate(
documentId=DOCUMENT_ID, body={'requests': requests1}).execute()
if name == 'main': 主要()
我相信你的现状和你的目标如下。
- 您有一个 Google 文档作为模板文档。
- 您想使用 python 的 googleapis 实现以下流程。
- 复制模板文档。
- 更新复制的文档。
- 将更新后的文档下载为 PDF 文件。
- 删除复制的文档。
修改点:
- 您的脚本更新了现有的 Google 文档。所以为了达到你的目的,还需要准备其他流程。
- 为了复制模板文档,将文档下载为PDF文件并删除文档,驱动器API使用如下。并且,当文档更新时,使用 Docs API。
- 复制模板文档。
- 在这种情况下,使用驱动器 API。
- 更新复制的文档。
- 在这种情况下,使用 Docs API 并且使用 yoru 脚本中的脚本。
- 将更新后的文档下载为 PDF 文件。
- 在这种情况下,使用驱动器 API。
- 删除复制的文档。
- 在这种情况下,使用驱动器 API。
- 复制模板文档。
当你的脚本修改后,变成如下。
修改后的脚本:
在这个修改后的脚本中,它假定您的脚本使用了 credentials=creds
中的 creds
。并且,在使用此脚本之前,请设置变量。
templateDocumentId = '###' # Please set the Document ID.
outputPDFFilename = 'sample.pdf' # Please set the output PDF filename.
drive = build('drive', 'v3', credentials=creds)
docs = build('docs', 'v1', credentials=creds)
# 1. Copy template Document.
copiedDoc = drive.files().copy(fileId=templateDocumentId, body={'name': 'copiedTemplateDocument'}).execute()
copiedDocId = copiedDoc.get('id')
print('Done: 1. Copy template Document.')
# 2. Update copied Document.
text1 = 'test'
requests1 = [
{
'insertText': {
'location': {
'index': 110,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 98,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 83,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 72,
},
'text': text1
}
},
{
'insertText': {
'location': {
'index': 49,
},
'text': text1
}
},
]
result = docs.documents().batchUpdate(documentId=copiedDocId, body={'requests': requests1}).execute()
print('Done: 2. Update copied Document.')
# 3. Download the updated Document as PDF file.
request = drive.files().export_media(fileId=copiedDocId, mimeType='application/pdf')
fh = io.FileIO(outputPDFFilename, mode='wb')
downloader = MediaIoBaseDownload(fh, request)
done = False
while done is False:
status, done = downloader.next_chunk()
print('Download %d%%.' % int(status.progress() * 100))
print('Done: 3. Download the updated Document as PDF file.')
# 4. Delete the copied Document.
drive.files().delete(fileId=copiedDocId).execute()
print('Done: 4. Delete the copied Document.')
注:
- 为了下载文件,还使用了
import io
和from googleapiclient.http import MediaIoBaseDownload
。 - 在这个答案中,它假设您的
requests1
forservice.documents().batchUpdate(documentId=DOCUMENT_ID, body={'requests': requests1}).execute()
的请求正文按您预期的那样工作正常。所以请注意这一点。