Skip to content

Commit c60c7ac

Browse files
committed
Add DataStudio samples from DevSite.
1 parent 5ba3a1e commit c60c7ac

File tree

9 files changed

+543
-0
lines changed

9 files changed

+543
-0
lines changed

data-studio/appsscript.json

+22
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,22 @@
1+
{
2+
"dataStudio": {
3+
"name": "Nucleus by Hooli",
4+
"company": "Hooli Inc.",
5+
"companyUrl": "https://hooli.xyz",
6+
"logoUrl": "https://hooli.xyz/middle-out-optimized/nucleus/logo.png",
7+
"addonUrl": "https://hooli.xyz/data-studio-connector",
8+
"supportUrl": "https://hooli.xyz/data-studio-connector/support",
9+
"description": "Nucleus by Hooli connector lets you connect to your data in Data Studio using Nucleus middle out optimization. You will need an account on hooli.xyz to use this connector. Create your account at https://hooli.xyz/signup",
10+
"shortDescription": "Connect to your data using Nucleus middle out optimization",
11+
"authType": ["NONE"],
12+
"feeType": ["PAID"],
13+
"sources": ["HOOLI_CHAT_LOG", "ENDFRAME_SERVER_STREAM", "RETINABYTE_USER_ANALYTICS"],
14+
"templates": {
15+
"default": "872223s89f5fdkjnd983kjf"
16+
}
17+
},
18+
"urlFetchWhitelist": [
19+
"https://api.hooli.xyz/",
20+
"https://hooli.xyz/"
21+
]
22+
}

data-studio/appsscript2.json

+12
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
{
2+
"dataStudio": {
3+
"name": "npm Downloads - Build Guide",
4+
"logoUrl": "https://raw.githubusercontent.com/npm/logos/master/%22npm%22%20lockup/npm-logo-simplifed-with-white-space.png",
5+
"company": "Build Guide User",
6+
"companyUrl": "https://developers.google.com/datastudio/",
7+
"addonUrl": "https://github.com/google/datastudio/tree/master/community-connectors/npm-downloads",
8+
"supportUrl": "https://github.com/google/datastudio/issues",
9+
"description": "Get npm package download counts.",
10+
"sources": ["npm"]
11+
}
12+
}

data-studio/auth.gs

+179
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,179 @@
1+
/**
2+
* Copyright Google LLC
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* https://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
// [START apps_script_data_studio_reset_auth_oauth2]
18+
// [END apps_script_data_studio_reset_auth_oauth2]
19+
20+
21+
22+
23+
24+
// [START apps_script_data_studio_get_auth_type_oauth2]
25+
function getAuthType() {
26+
return {
27+
"type": "OAUTH2"
28+
};
29+
}
30+
// [END apps_script_data_studio_get_auth_type_oauth2]
31+
32+
// [START apps_script_data_studio_get_auth_type_user_pass]
33+
function getAuthType() {
34+
return {
35+
"type": "USER_PASS"
36+
};
37+
}
38+
// [END apps_script_data_studio_get_auth_type_user_pass]
39+
40+
// [START apps_script_data_studio_get_auth_type_key]
41+
function getAuthType() {
42+
return {
43+
"type": "KEY"
44+
};
45+
}
46+
// [END apps_script_data_studio_get_auth_type_key]
47+
48+
// [START apps_script_data_studio_get_auth_type_none]
49+
function getAuthType() {
50+
return {
51+
"type": "NONE"
52+
};
53+
}
54+
// [END apps_script_data_studio_get_auth_type_none]
55+
56+
// [START apps_script_data_studio_auth_reset_oauth2]
57+
function resetAuth() {
58+
getOAuthService().reset();
59+
}
60+
// [END apps_script_data_studio_auth_reset_oauth2]
61+
62+
// [START apps_script_data_studio_auth_reset_user]
63+
function resetAuth() {
64+
var userProperties = PropertiesService.getUserProperties();
65+
userProperties.deleteProperty('dscc.username');
66+
userProperties.deleteProperty('dscc.password');
67+
}
68+
// [END apps_script_data_studio_auth_reset_user]
69+
70+
// [START apps_script_data_studio_auth_reset_key]
71+
function resetAuth() {
72+
var userProperties = PropertiesService.getUserProperties();
73+
userProperties.deleteProperty('dscc.key');
74+
}
75+
// [END apps_script_data_studio_auth_reset_key]
76+
77+
// [START apps_script_data_studio_auth_valid_oauth2]
78+
function isAuthValid() {
79+
return getOAuthService().hasAccess();
80+
}
81+
// [END apps_script_data_studio_auth_valid_oauth2]
82+
83+
// [START apps_script_data_studio_auth_valid_user_pass]
84+
function isAuthValid() {
85+
var userProperties = PropertiesService.getUserProperties();
86+
var userName = userProperties.getProperty('dscc.username');
87+
var password = userProperties.getProperty('dscc.password');
88+
// This assumes you have a validateCredentials function that
89+
// can validate if the userName and password are correct.
90+
return validateCredentials(userName, password);
91+
}
92+
// [END apps_script_data_studio_auth_valid_user_pass]
93+
94+
// [START apps_script_data_studio_auth_valid_key]
95+
function isAuthValid() {
96+
var userProperties = PropertiesService.getUserProperties();
97+
var key = userProperties.getProperty('dscc.key');
98+
// This assumes you have a validateKey function that can validate
99+
// if the key is valid.
100+
return validateKey(key);
101+
}
102+
// [END apps_script_data_studio_auth_valid_key]
103+
104+
// [START apps_script_data_studio_auth_library]
105+
function getOAuthService() {
106+
return OAuth2.createService('exampleService')
107+
.setAuthorizationBaseUrl('...')
108+
.setTokenUrl('...')
109+
.setClientId('...')
110+
.setClientSecret('...')
111+
.setPropertyStore(PropertiesService.getUserProperties())
112+
.setCallbackFunction('authCallback')
113+
.setScope('...');
114+
};
115+
// [END apps_script_data_studio_auth_library]
116+
117+
// [START apps_script_data_studio_auth_callback]
118+
function authCallback(request) {
119+
var authorized = getOAuthService().handleCallback(request);
120+
if (authorized) {
121+
return HtmlService.createHtmlOutput('Success! You can close this tab.');
122+
} else {
123+
return HtmlService.createHtmlOutput('Denied. You can close this tab');
124+
};
125+
};
126+
// [END apps_script_data_studio_auth_callback]
127+
128+
// [START apps_script_data_studio_auth_urls]
129+
function get3PAuthorizationUrls() {
130+
return getOAuthService().getAuthorizationUrl();
131+
}
132+
// [END apps_script_data_studio_auth_urls]
133+
134+
// [START apps_script_data_studio_auth_set_credentials_user_pass]
135+
function setCredentials(request) {
136+
var creds = request.userPass;
137+
var username = creds.username;
138+
var password = creds.password;
139+
140+
// Optional
141+
// Check if the provided username and password are valid through a
142+
// call to your service. You would have to have a `checkForValidCreds`
143+
// function defined for this to work.
144+
var validCreds = checkForValidCreds(username, password);
145+
if (!validCreds) {
146+
return {
147+
errorCode: "INVALID_CREDENTIALS"
148+
};
149+
}
150+
var userProperties = PropertiesService.getUserProperties();
151+
userProperties.setProperty('dscc.username', username);
152+
userProperties.setProperty('dscc.password', password);
153+
return {
154+
errorCode: "NONE"
155+
};
156+
}
157+
// [END apps_script_data_studio_auth_set_credentials_user_pass]
158+
159+
// [START apps_script_data_studio_auth_set_credentials_key]
160+
function setCredentials(request) {
161+
var key = request.key;
162+
163+
// Optional
164+
// Check if the provided key is valid through a call to your service.
165+
// You would have to have a `checkForValidKey` function defined for
166+
// this to work.
167+
var validKey = checkForValidKey(key);
168+
if (!validKey) {
169+
return {
170+
errorCode: "INVALID_CREDENTIALS"
171+
};
172+
}
173+
var userProperties = PropertiesService.getUserProperties();
174+
userProperties.setProperty('dscc.key', key);
175+
return {
176+
errorCode: "NONE"
177+
};
178+
}
179+
// [END apps_script_data_studio_auth_set_credentials_key]

data-studio/build.gs

+124
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,124 @@
1+
/**
2+
* Copyright Google LLC
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* https://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
// [START apps_script_data_studio_build_get_config]
18+
function getConfig() {
19+
var cc = DataStudioApp.createCommunityConnector();
20+
var config = cc.getConfig();
21+
22+
config.newInfo()
23+
.setId('instructions')
24+
.setText('Enter npm package names to fetch their download count.');
25+
26+
config.newTextInput()
27+
.setId('package')
28+
.setName('Enter a single package name.')
29+
.setHelpText('for example, googleapis or lighthouse')
30+
.setPlaceholder('googleapis')
31+
.setAllowOverride(true);
32+
33+
config.setDateRangeRequired(true);
34+
35+
return config.build();
36+
}
37+
// [END apps_script_data_studio_build_get_config]
38+
39+
// [START apps_script_data_studio_build_get_fields]
40+
function getFields() {
41+
var cc = DataStudioApp.createCommunityConnector();
42+
var fields = cc.getFields();
43+
var types = cc.FieldType;
44+
var aggregations = cc.AggregationType;
45+
46+
fields.newDimension()
47+
.setId('packageName')
48+
.setName('Package Name')
49+
.setType(types.TEXT);
50+
51+
fields.newDimension()
52+
.setId('day')
53+
.setName('Day')
54+
.setType(types.YEAR_MONTH_DAY);
55+
56+
fields.newMetric()
57+
.setId('downloads')
58+
.setName('Downloads')
59+
.setType(types.NUMBER)
60+
.setAggregation(aggregations.SUM);
61+
62+
return fields;
63+
64+
}
65+
66+
function getSchema(request) {
67+
var fields = getFields().build();
68+
return { 'schema': fields };
69+
}
70+
// [END apps_script_data_studio_build_get_fields]
71+
72+
// [START apps_script_data_studio_build_get_data]
73+
function responseToRows(requestedFields, response, packageName) {
74+
// Transform parsed data and filter for requested fields
75+
return response.map(function(dailyDownload) {
76+
var row = [];
77+
requestedFields.asArray().forEach(function (field) {
78+
switch (field.getId()) {
79+
case 'day':
80+
return row.push(dailyDownload.day.replace(/-/g, ''));
81+
case 'downloads':
82+
return row.push(dailyDownload.downloads);
83+
case 'packageName':
84+
return row.push(packageName);
85+
default:
86+
return row.push('');
87+
}
88+
});
89+
return { values: row };
90+
});
91+
}
92+
93+
function getData(request) {
94+
var requestedFieldIds = request.fields.map(function(field) {
95+
return field.name;
96+
});
97+
var requestedFields = getFields().forIds(requestedFieldIds);
98+
99+
// Fetch and parse data from API
100+
var url = [
101+
'https://api.npmjs.org/downloads/range/',
102+
request.dateRange.startDate,
103+
':',
104+
request.dateRange.endDate,
105+
'/',
106+
request.configParams.package
107+
];
108+
var response = UrlFetchApp.fetch(url.join(''));
109+
var parsedResponse = JSON.parse(response).downloads;
110+
var rows = responseToRows(requestedFields, parsedResponse, request.configParams.package);
111+
112+
return {
113+
schema: requestedFields.build(),
114+
rows: rows
115+
};
116+
}
117+
// [END apps_script_data_studio_build_get_data]
118+
119+
// [START apps_script_data_studio_build_get_auth_type]
120+
function getAuthType() {
121+
var response = { type: 'NONE' };
122+
return response;
123+
}
124+
// [END apps_script_data_studio_build_get_auth_type]

data-studio/data-source.gs

+55
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,55 @@
1+
/**
2+
* Copyright Google LLC
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* https://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
// [START apps_script_data_studio_params]
18+
var configParams = [
19+
{
20+
type:'TEXTINPUT',
21+
name: 'ZipCode',
22+
displayName: 'ZIP Code',
23+
parameterControl: {
24+
allowOverride: true
25+
}
26+
},
27+
{
28+
type: "SELECT_SINGLE",
29+
name: "units",
30+
displayName: "Units",
31+
parameterControl: {
32+
allowOverride: true
33+
},
34+
options: [
35+
{
36+
label: "Metric",
37+
value: "metric"
38+
},
39+
{
40+
label: "Imperial",
41+
value: "imperial"
42+
},
43+
{
44+
label: "Kelvin",
45+
value: "kelvin"
46+
}
47+
]
48+
},
49+
{
50+
type:'TEXTINPUT',
51+
name: 'Days',
52+
displayName: 'Days to forecast'
53+
}
54+
];
55+
// [END apps_script_data_studio_params]

0 commit comments

Comments
 (0)