Skip to content

Commit 2027ec7

Browse files
committed
Add KMZ support
1 parent 79d2779 commit 2027ec7

File tree

2 files changed

+76
-29
lines changed

2 files changed

+76
-29
lines changed

export-to-office/Code.gs

Lines changed: 73 additions & 28 deletions
Original file line numberDiff line numberDiff line change
@@ -14,11 +14,6 @@ function exportToOffice() {
1414
const now = new Date();
1515
const description = "#ExportedToOffice";
1616
const conversions = [
17-
[
18-
"application/vnd.google-apps.spreadsheet",
19-
"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",
20-
".xslx",
21-
],
2217
[
2318
"application/vnd.google-apps.document",
2419
"application/vnd.openxmlformats-officedocument.wordprocessingml.document",
@@ -29,6 +24,16 @@ function exportToOffice() {
2924
"application/vnd.openxmlformats-officedocument.presentationml.presentation",
3025
".pptx",
3126
],
27+
[
28+
"application/vnd.google-apps.map",
29+
"application/vnd.google-earth.kmz",
30+
".kmz",
31+
],
32+
[
33+
"application/vnd.google-apps.spreadsheet",
34+
"application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",
35+
".xslx",
36+
],
3237
];
3338
const folders = DriveApp.getRootFolder().getFoldersByName(folderName);
3439
if (!folders.hasNext()) {
@@ -41,10 +46,17 @@ function exportToOffice() {
4146
const oldFiles = folder.getFiles();
4247
while (oldFiles.hasNext()) {
4348
const oldFile = oldFiles.next();
44-
if (oldFile.getDescription() === description) {
49+
if (
50+
oldFile.getDescription() !== null &&
51+
oldFile.getDescription().indexOf(description) > -1
52+
) {
4553
if (oldFile.getDateCreated() - now > expiry) {
46-
console.log('Deleting obsolete file "' + oldFile.getName() + '"');
54+
console.log('Deleting orphaned file "' + oldFile.getName() + '"');
4755
oldFile.setTrashed(true);
56+
/*
57+
To support a large number of files, this script is to be run once an hour and on each run it
58+
it will export approximatly 1/24th of the files.
59+
*/
4860
} else if (oldFile.getName().charCodeAt(0) % 24 === modulo) {
4961
console.log('Deleting file "' + oldFile.getName() + '"');
5062
oldFile.setTrashed(true);
@@ -57,17 +69,35 @@ function exportToOffice() {
5769
const files = DriveApp.getFilesByType(conversion[0]);
5870
while (files.hasNext()) {
5971
const file = files.next();
60-
if (file.isTrashed()) {
61-
console.log('Skipping trashed file "' + file.getName() + '"');
62-
continue;
63-
}
64-
if (
65-
file.getAccess(Session.getActiveUser()) !== DriveApp.Permission.OWNER
66-
) {
67-
console.log('Skipping shared file "' + file.getName() + '"');
68-
continue;
69-
}
72+
/*
73+
To support a large number of files, this script is to be run once an hour and on each run it
74+
it will export approximatly 1/24th of the files.
75+
*/
7076
if (file.getName().charCodeAt(0) % 24 === modulo) {
77+
if (file.isTrashed()) {
78+
console.log('Skipping trashed file "' + file.getName() + '"');
79+
continue;
80+
}
81+
if (
82+
file.getDescription() !== null &&
83+
file.getDescription().indexOf(description) > -1
84+
) {
85+
console.log('Skipping ignored file "' + file.getName() + '"');
86+
continue;
87+
}
88+
if (
89+
file.getAccess(Session.getActiveUser()) !== DriveApp.Permission.OWNER
90+
) {
91+
console.log('Skipping shared file "' + file.getName() + '"');
92+
continue;
93+
}
94+
if (conversion[0] === "application/vnd.google-apps.map") {
95+
console.log('Sharing "' + file.getName() + '"');
96+
file.setSharing(
97+
DriveApp.Access.ANYONE_WITH_LINK,
98+
DriveApp.Permission.VIEW,
99+
);
100+
}
71101
console.log('Converting "' + file.getName() + '"');
72102
const blob = getFileAsBlob(file.getId(), conversion[1]);
73103
const newFile = folder.createFile(blob);
@@ -79,16 +109,31 @@ function exportToOffice() {
79109
}
80110

81111
function getFileAsBlob(fileId, mimeType) {
82-
const response = UrlFetchApp.fetch(
83-
"https://www.googleapis.com/drive/v3/files/" +
84-
fileId +
85-
"/export?mimeType=" +
86-
encodeURIComponent(mimeType),
87-
{
88-
headers: {
89-
Authorization: "Bearer " + ScriptApp.getOAuthToken(),
112+
if (mimeType === "application/vnd.google-earth.kmz") {
113+
const response = UrlFetchApp.fetch(
114+
"https://mapsengine.google.com/map/kml?mid=" + fileId,
115+
{
116+
headers: {
117+
Authorization: "Bearer " + ScriptApp.getOAuthToken(),
118+
Accept: mimeType,
119+
},
120+
compressed: true,
121+
"Accept-Encoding": "gzip",
90122
},
91-
},
92-
);
93-
return response.getBlob();
123+
);
124+
return response.getBlob();
125+
} else {
126+
const response = UrlFetchApp.fetch(
127+
"https://www.googleapis.com/drive/v3/files/" +
128+
fileId +
129+
"/export?mimeType=" +
130+
encodeURIComponent(mimeType),
131+
{
132+
headers: {
133+
Authorization: "Bearer " + ScriptApp.getOAuthToken(),
134+
},
135+
},
136+
);
137+
return response.getBlob();
138+
}
94139
}

export-to-office/README.md

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,12 @@
11
# Export To Office
22

3-
Export all Google Docs, Google Spreasheets and Google Slides to Microsoft Word, Microsoft Excel and Microsoft Powerpoint format (respectively).
3+
Export all Google Docs, Google Spreasheets, Google Slides and Google My Maps to Microsoft Word, Microsoft Excel, Microsoft Powerpoint and Keyhole Markup Language (KMZ) format (respectively).
44

55
Since Apps Scripts have a 6-minute runtime limite, I run this script hourly using a [standalone script](https://developers.google.com/apps-script/guides/standalone) with [time-driven trigger](https://developers.google.com/apps-script/guides/triggers/installable#time-driven_triggers). Each run exports 1/24th of the files in Google Drive so at the end of each day, all files should have been exported.
66

77
The script has two optional [script properties](https://developers.google.com/apps-script/guides/properties#manage_script_properties_manually):
88

99
- folder: the name of the Google Drive folder to save the converted files (default is 'Export'). This folder must be at the root of your Google Drive (to avoid name collisions).
1010
- expiry: the number of days after which an orphan exported file gets deleted (default is 30).
11+
12+
Note that in order to be able to export My Maps file, the script needs to allow read-only access to everyone with the private map link.

0 commit comments

Comments
 (0)