Skip to content

Commit e9c0f92

Browse files
Ace Nassrijmdobry
Ace Nassri
authored andcommitted
Add sample for Natural Language 1.1 launch (#352)
* Fix NL tests * Add analyzeEntitySentiment sample * Fix failing tests * Add NL 1.0 features * Update dependencies
1 parent f8f7e62 commit e9c0f92

File tree

3 files changed

+179
-25
lines changed

3 files changed

+179
-25
lines changed

cloud-language/snippets/analyze.js

+134-15
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ function analyzeSentimentOfText (text) {
2121
const Language = require('@google-cloud/language');
2222

2323
// Instantiates a client
24-
const language = Language();
24+
const language = Language({ apiVersion: 'v1beta2' });
2525

2626
// The text to analyze, e.g. "Hello, world!"
2727
// const text = 'Hello, world!';
@@ -32,9 +32,17 @@ function analyzeSentimentOfText (text) {
3232
// Detects the sentiment of the document
3333
document.detectSentiment()
3434
.then((results) => {
35-
const sentiment = results[0];
36-
console.log(`Score: ${sentiment.score}`);
37-
console.log(`Magnitude: ${sentiment.magnitude}`);
35+
const sentiment = results[1].documentSentiment;
36+
console.log(`Document sentiment:`)
37+
console.log(` Score: ${sentiment.score}`);
38+
console.log(` Magnitude: ${sentiment.magnitude}`);
39+
40+
const sentences = results[1].sentences;
41+
sentences.forEach((sentence) => {
42+
console.log(`Sentence: ${sentence.text.content}`);
43+
console.log(` Score: ${sentence.sentiment.score}`);
44+
console.log(` Magnitude: ${sentence.sentiment.magnitude}`);
45+
});
3846
})
3947
.catch((err) => {
4048
console.error('ERROR:', err);
@@ -49,7 +57,7 @@ function analyzeSentimentInFile (bucketName, fileName) {
4957
const Storage = require('@google-cloud/storage');
5058

5159
// Instantiates the clients
52-
const language = Language();
60+
const language = Language({ apiVersion: 'v1beta2' });
5361
const storage = Storage();
5462

5563
// The name of the bucket where the file resides, e.g. "my-bucket"
@@ -67,9 +75,17 @@ function analyzeSentimentInFile (bucketName, fileName) {
6775
// Detects the sentiment of the document
6876
document.detectSentiment()
6977
.then((results) => {
70-
const sentiment = results[0];
71-
console.log(`Score: ${sentiment.score}`);
72-
console.log(`Magnitude: ${sentiment.magnitude}`);
78+
const sentiment = results[1].documentSentiment;
79+
console.log(`Document sentiment:`)
80+
console.log(` Score: ${sentiment.score}`);
81+
console.log(` Magnitude: ${sentiment.magnitude}`);
82+
83+
const sentences = results[1].sentences;
84+
sentences.forEach((sentence) => {
85+
console.log(`Sentence: ${sentence.text.content}`);
86+
console.log(` Score: ${sentence.sentiment.score}`);
87+
console.log(` Magnitude: ${sentence.sentiment.magnitude}`);
88+
});
7389
})
7490
.catch((err) => {
7591
console.error('ERROR:', err);
@@ -83,7 +99,7 @@ function analyzeEntitiesOfText (text) {
8399
const Language = require('@google-cloud/language');
84100

85101
// Instantiates a client
86-
const language = Language();
102+
const language = Language({ apiVersion: 'v1beta2' });
87103

88104
// The text to analyze, e.g. "Hello, world!"
89105
// const text = 'Hello, world!';
@@ -94,12 +110,15 @@ function analyzeEntitiesOfText (text) {
94110
// Detects entities in the document
95111
document.detectEntities()
96112
.then((results) => {
97-
const entities = results[0];
113+
const entities = results[1].entities;
98114

99115
console.log('Entities:');
100116
entities.forEach((entity) => {
101117
console.log(entity.name);
102118
console.log(` - Type: ${entity.type}, Salience: ${entity.salience}`);
119+
if (entity.metadata && entity.metadata.wikipedia_url) {
120+
console.log(` - Wikipedia URL: ${entity.metadata.wikipedia_url}$`);
121+
}
103122
});
104123
})
105124
.catch((err) => {
@@ -115,7 +134,7 @@ function analyzeEntitiesInFile (bucketName, fileName) {
115134
const Storage = require('@google-cloud/storage');
116135

117136
// Instantiates the clients
118-
const language = Language();
137+
const language = Language({ apiVersion: 'v1beta2' });
119138
const storage = Storage();
120139

121140
// The name of the bucket where the file resides, e.g. "my-bucket"
@@ -139,6 +158,9 @@ function analyzeEntitiesInFile (bucketName, fileName) {
139158
entities.forEach((entity) => {
140159
console.log(entity.name);
141160
console.log(` - Type: ${entity.type}, Salience: ${entity.salience}`);
161+
if (entity.metadata && entity.metadata.wikipedia_url) {
162+
console.log(` - Wikipedia URL: ${entity.metadata.wikipedia_url}$`);
163+
}
142164
});
143165
})
144166
.catch((err) => {
@@ -153,7 +175,7 @@ function analyzeSyntaxOfText (text) {
153175
const Language = require('@google-cloud/language');
154176

155177
// Instantiates a client
156-
const language = Language();
178+
const language = Language({ apiVersion: 'v1beta2' });
157179

158180
// The text to analyze, e.g. "Hello, world!"
159181
// const text = 'Hello, world!';
@@ -168,7 +190,8 @@ function analyzeSyntaxOfText (text) {
168190

169191
console.log('Parts of speech:');
170192
syntax.forEach((part) => {
171-
console.log(`${part.partOfSpeech.tag}:\t ${part.text.content}`);
193+
console.log(`${part.partOfSpeech.tag}: ${part.text.content}`);
194+
console.log(`Morphology:`, part.partOfSpeech);
172195
});
173196
})
174197
.catch((err) => {
@@ -184,7 +207,7 @@ function analyzeSyntaxInFile (bucketName, fileName) {
184207
const Storage = require('@google-cloud/storage');
185208

186209
// Instantiates the clients
187-
const language = Language();
210+
const language = Language({ apiVersion: 'v1beta2' });
188211
const storage = Storage();
189212

190213
// The name of the bucket where the file resides, e.g. "my-bucket"
@@ -206,7 +229,8 @@ function analyzeSyntaxInFile (bucketName, fileName) {
206229

207230
console.log('Parts of speech:');
208231
syntax.forEach((part) => {
209-
console.log(`${part.partOfSpeech.tag}:\t ${part.text.content}`);
232+
console.log(`${part.partOfSpeech.tag}: ${part.text.content}`);
233+
console.log(`Morphology:`, part.partOfSpeech);
210234
});
211235
})
212236
.catch((err) => {
@@ -215,6 +239,87 @@ function analyzeSyntaxInFile (bucketName, fileName) {
215239
// [END language_syntax_file]
216240
}
217241

242+
function analyzeEntitySentimentOfText (text) {
243+
// [START language_entity_sentiment_string]
244+
// Imports the Google Cloud client library
245+
const Language = require('@google-cloud/language').v1beta2();
246+
247+
// Instantiates a client
248+
const language = Language.languageServiceClient();
249+
250+
// The text to analyze, e.g. "Hello, world!"
251+
// const text = 'Hello, world!';
252+
253+
// Configure a request containing a string
254+
const request = {
255+
document: {
256+
type: 'PLAIN_TEXT',
257+
content: text
258+
}
259+
};
260+
261+
// Detects sentiment of entities in the document
262+
language.analyzeEntitySentiment(request)
263+
.then((results) => {
264+
const entities = results[0].entities;
265+
266+
console.log(`Entities and sentiments:`)
267+
entities.forEach((entity) => {
268+
console.log(` Name: ${entity.name}`);
269+
console.log(` Type: ${entity.type}`);
270+
console.log(` Score: ${entity.sentiment.score}`);
271+
console.log(` Magnitude: ${entity.sentiment.magnitude}`);
272+
});
273+
})
274+
.catch((err) => {
275+
console.error('ERROR:', err);
276+
});
277+
// [END language_entity_sentiment_string]
278+
}
279+
280+
function analyzeEntitySentimentInFile (bucketName, fileName) {
281+
// [START language_entity_sentiment_file]
282+
// Imports the Google Cloud client libraries
283+
const Language = require('@google-cloud/language').v1beta2();
284+
const Storage = require('@google-cloud/storage');
285+
286+
// Instantiates the clients
287+
const language = Language.languageServiceClient();
288+
const storage = Storage();
289+
290+
// The name of the bucket where the file resides, e.g. "my-bucket"
291+
// const bucketName = 'my-bucket';
292+
293+
// The name of the file to analyze, e.g. "file.txt"
294+
// const fileName = 'file.txt';
295+
296+
// Configure a request containing a string
297+
const request = {
298+
document: {
299+
type: 'PLAIN_TEXT',
300+
gcsContentUri: `gs://${bucketName}/${fileName}`
301+
}
302+
};
303+
304+
// Detects sentiment of entities in the document
305+
language.analyzeEntitySentiment(request)
306+
.then((results) => {
307+
const entities = results[0].entities;
308+
309+
console.log(`Entities and sentiments:`)
310+
entities.forEach((entity) => {
311+
console.log(` Name: ${entity.name}`);
312+
console.log(` Type: ${entity.type}`);
313+
console.log(` Score: ${entity.sentiment.score}`);
314+
console.log(` Magnitude: ${entity.sentiment.magnitude}`);
315+
});
316+
})
317+
.catch((err) => {
318+
console.error('ERROR:', err);
319+
});
320+
// [END language_entity_sentiment_file]
321+
}
322+
218323
require(`yargs`)
219324
.demand(1)
220325
.command(
@@ -253,12 +358,26 @@ require(`yargs`)
253358
{},
254359
(opts) => analyzeSyntaxInFile(opts.bucketName, opts.fileName)
255360
)
361+
.command(
362+
`entity-sentiment-text <text>`,
363+
`Detects sentiment of the entities in a string.`,
364+
{},
365+
(opts) => analyzeEntitySentimentOfText(opts.text)
366+
)
367+
.command(
368+
`entity-sentiment-file <bucketName> <fileName>`,
369+
`Detects sentiment of the entities in a file in Google Cloud Storage.`,
370+
{},
371+
(opts) => analyzeEntitySentimentInFile(opts.bucketName, opts.fileName)
372+
)
256373
.example(`node $0 sentiment-text "President Obama is speaking at the White House."`)
257374
.example(`node $0 sentiment-file my-bucket file.txt`, `Detects sentiment in gs://my-bucket/file.txt`)
258375
.example(`node $0 entities-text "President Obama is speaking at the White House."`)
259376
.example(`node $0 entities-file my-bucket file.txt`, `Detects entities in gs://my-bucket/file.txt`)
260377
.example(`node $0 syntax-text "President Obama is speaking at the White House."`)
261378
.example(`node $0 syntax-file my-bucket file.txt`, `Detects syntax in gs://my-bucket/file.txt`)
379+
.example(`node $0 entity-sentiment-text "President Obama is speaking at the White House."`)
380+
.example(`node $0 entity-sentiment-file my-bucket file.txt`, `Detects sentiment of entities in gs://my-bucket/file.txt`)
262381
.wrap(120)
263382
.recommendCommands()
264383
.epilogue(`For more information, see https://cloud.google.com/natural-language/docs`)

cloud-language/snippets/package.json

+3-3
Original file line numberDiff line numberDiff line change
@@ -8,9 +8,9 @@
88
"test": "cd ..; npm run st -- --verbose language/system-test/*.test.js"
99
},
1010
"dependencies": {
11-
"@google-cloud/language": "0.10.2",
12-
"@google-cloud/storage": "1.0.0",
13-
"yargs": "7.0.2"
11+
"@google-cloud/language": "0.10.3",
12+
"@google-cloud/storage": "1.1.0",
13+
"yargs": "7.1.0"
1414
},
1515
"engines": {
1616
"node": ">=4.3.2"

cloud-language/snippets/system-test/analyze.test.js

+42-7
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,7 @@ const bucketName = `nodejs-docs-samples-test-${uuid.v4()}`;
2727
const fileName = `text.txt`;
2828
const localFilePath = path.join(__dirname, `../resources/text.txt`);
2929
const text = `President Obama is speaking at the White House.`;
30+
const germanText = `Willkommen bei München`;
3031

3132
test.before(async () => {
3233
const [bucket] = await storage.createBucket(bucketName);
@@ -43,16 +44,20 @@ test.after.always(async () => {
4344
test.beforeEach(stubConsole);
4445
test.afterEach.always(restoreConsole);
4546

46-
test(`should run sync recognize`, async (t) => {
47+
test(`should analyze sentiment in text`, async (t) => {
4748
const output = await runAsync(`${cmd} sentiment-text "${text}"`, cwd);
48-
t.true(output.includes(`Score: 0.`));
49-
t.true(output.includes(`Magnitude: 0.`));
49+
t.true(output.includes(`Document sentiment:`));
50+
t.true(output.includes(`Sentence: ${text}`));
51+
t.true(output.includes(`Score: 0`));
52+
t.true(output.includes(`Magnitude: 0`));
5053
});
5154

5255
test(`should analyze sentiment in a file`, async (t) => {
5356
const output = await runAsync(`${cmd} sentiment-file ${bucketName} ${fileName}`, cwd);
54-
t.true(output.includes(`Score: 0.`));
55-
t.true(output.includes(`Magnitude: 0.`));
57+
t.true(output.includes(`Document sentiment:`));
58+
t.true(output.includes(`Sentence: ${text}`));
59+
t.true(output.includes(`Score: 0`));
60+
t.true(output.includes(`Magnitude: 0`));
5661
});
5762

5863
test(`should analyze entities in text`, async (t) => {
@@ -61,6 +66,7 @@ test(`should analyze entities in text`, async (t) => {
6166
t.true(output.includes(`Type: PERSON`));
6267
t.true(output.includes(`White House`));
6368
t.true(output.includes(`Type: LOCATION`));
69+
t.true(output.includes(`/wiki/Barack_Obama`));
6470
});
6571

6672
test('should analyze entities in a file', async (t) => {
@@ -70,21 +76,50 @@ test('should analyze entities in a file', async (t) => {
7076
t.true(output.includes(`Type: PERSON`));
7177
t.true(output.includes(`White House`));
7278
t.true(output.includes(`Type: LOCATION`));
79+
t.true(output.includes(`/wiki/Barack_Obama`));
7380
});
7481

7582
test(`should analyze syntax in text`, async (t) => {
7683
const output = await runAsync(`${cmd} syntax-text "${text}"`, cwd);
7784
t.true(output.includes(`Parts of speech:`));
7885
t.true(output.includes(`NOUN:`));
7986
t.true(output.includes(`President`));
80-
t.true(output.includes(`NOUN:`));
8187
t.true(output.includes(`Obama`));
88+
t.true(output.includes(`Morphology:`));
89+
t.true(output.includes(`tag: 'NOUN'`));
8290
});
8391

8492
test('should analyze syntax in a file', async (t) => {
8593
const output = await runAsync(`${cmd} syntax-file ${bucketName} ${fileName}`, cwd);
8694
t.true(output.includes(`NOUN:`));
8795
t.true(output.includes(`President`));
88-
t.true(output.includes(`NOUN:`));
8996
t.true(output.includes(`Obama`));
97+
t.true(output.includes(`Morphology:`));
98+
t.true(output.includes(`tag: 'NOUN'`));
99+
});
100+
101+
test('should analyze syntax in a 1.1 language (German)', async (t) => {
102+
const output = await runAsync(`${cmd} syntax-text "${germanText}"`, cwd);
103+
t.true(output.includes(`Parts of speech:`));
104+
t.true(output.includes(`ADV: Willkommen`));
105+
t.true(output.includes(`ADP: bei`));
106+
t.true(output.includes(`NOUN: München`));
107+
});
108+
109+
test(`should analyze entity sentiment in text`, async (t) => {
110+
const output = await runAsync(`${cmd} entity-sentiment-text "${text}"`, cwd);
111+
t.true(output.includes(`Entities and sentiments:`));
112+
t.true(output.includes(`Obama`));
113+
t.true(output.includes(`PERSON`));
114+
t.true(output.includes(`Score: 0`));
115+
t.true(output.includes(`Magnitude: 0`));
116+
});
117+
118+
test('should analyze entity sentiment in a file', async (t) => {
119+
const output = await runAsync(`${cmd} entity-sentiment-file ${bucketName} ${fileName}`, cwd);
120+
t.true(output.includes(`Entities and sentiments:`));
121+
t.true(output.includes(`Obama`));
122+
t.true(output.includes(`PERSON`));
123+
t.true(output.includes(`Score: 0`));
124+
t.true(output.includes(`Magnitude: 0`));
90125
});

0 commit comments

Comments
 (0)