Skip to content
This repository has been archived by the owner on Sep 27, 2023. It is now read-only.

[DO NOT MERGE] Propose refined sample format #154

Closed
wants to merge 2 commits into from
Closed

Conversation

jmdobry
Copy link
Contributor

@jmdobry jmdobry commented Oct 10, 2018

New format based on recent discussions on sample best practices.

Format examples:

Notable changes

  • Each sample is now in its own file (lends itself well to auto-generated samples).
  • Added Node.js v8+ features such as spread, array destructuring, and async/await.
    • Adding async/await necessitated adding a wrapper function inside the sample.
  • The most important variables (i.e. those that can't be hardcoded and must be set by the user) are commented out at the top of the sample.
  • The less important variables (request options with valid default values) are inlined into the request object.
  • Stripped out the yargs CLI wrapper in lieu of a simple ...process.argv.slice(2) which gets passed to the main so the sample can still be invoked from the command-line.
    • Auto-generated samples could add back in Yargs if they want

Structure of samples

  1. Outside region tag:
    1. Copyright header
    2. 'use strict';
  2. Inside region tag (everything in here is what the user sees on cloud.google.com):
    1. (If applicable) Setup variables, e.g. if given filepath, read in the file's bytes into a variable to be added to the request object.
    2. Import statements
    3. Instantiate client library
    4. async function usefulFunctionNameHere():
      1. Construct request
        1. Includes inline comments about what the options are for
      2. Make API call
      3. Print interesting stuff to console, then return the response.
      4. Handle error (print error then re-throw)
    5. Call the usefulFunctionNameHere function, passing in the variables in 2i.
  3. Outside region tag:
    1. Call the wrapping main function, passing in ...process.argv.slice(2)

Notes

  • If proposed format is acceptable, this would serve as a template for updating all Node.js samples.
  • Why did I pick the two samples that I picked? One is a very basic sample, only the projectId can't be hard-coded. The second is a more complicated sample that requires a filepath (which subsequently requires the file's bytes be read into memory)

@googlebot googlebot added the cla: yes This human has signed the Contributor License Agreement. label Oct 10, 2018
@ghost ghost assigned jmdobry Oct 10, 2018
samples/dlp_inspect_file.js Outdated Show resolved Hide resolved
samples/dlp_inspect_file.js Outdated Show resolved Hide resolved
const output = await tools.runAsync(
`${cmd} string "I'm Gary and my email is gary@example.com"`,
`node dlp_inspect_string.js ${PROJECT_ID} "I'm Gary and my email is gary@example.com"`,

This comment was marked as spam.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

All the sample tests in this repo have that problem.

@fhinkel
Copy link
Contributor

fhinkel commented Nov 8, 2018

If we use this for how Node samples should look like, we need to replace ava with mocha and semistandard with prettier and eslint.

@sduskis
Copy link

sduskis commented Jan 22, 2019

@jmdobry, what's the status of this PR?

@jmdobry
Copy link
Contributor Author

jmdobry commented Jan 22, 2019

We'll be finalizing it end of February at a team summit.

@JustinBeckwith JustinBeckwith added the do not merge Indicates a pull request not ready for merge, due to either quality or timing. label Jan 26, 2019
@yoshi-automation yoshi-automation added the 🚨 This issue needs some love. label Feb 7, 2019
@JustinBeckwith JustinBeckwith added the status: blocked Resolving the issue is dependent on other work. label Feb 8, 2019
@yoshi-automation yoshi-automation removed the 🚨 This issue needs some love. label Feb 8, 2019
@codecov
Copy link

codecov bot commented Feb 27, 2019

Codecov Report

Merging #154 into master will not change coverage.
The diff coverage is n/a.

Impacted file tree graph

@@          Coverage Diff          @@
##           master   #154   +/-   ##
=====================================
  Coverage     100%   100%           
=====================================
  Files           1      1           
  Lines           4      4           
=====================================
  Hits            4      4

Continue to review full report at Codecov.

Legend - Click here to learn more
Δ = absolute <relative> (impact), ø = not affected, ? = missing data
Powered by Codecov. Last update 1f1d069...47f8669. Read the comment docs.

samples/.eslintrc.yml Outdated Show resolved Hide resolved
samples/dlp_inspect_image_file.js Outdated Show resolved Hide resolved
samples/dlp_inspect_image_file.js Outdated Show resolved Hide resolved
samples/dlp_inspect_image_file.js Outdated Show resolved Hide resolved
const fs = require('fs');

export async function inspectImageFile(
projectId = 'YOUR_PROJECT_ID',
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We should never require the projectId. Best practice is to leverage the metadata server present on all GCP runtimes.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

DLP is somewhat special as the request needs the project ID, users should not pass it in though but use dlp.getProjectId(), https://github.com/googleapis/nodejs-dlp/blob/master/src/v2/dlp_service_client.js#L268.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It's not actually that special, quite a few APIs require project ID in path parameters to specify the resource owner for billing (different from the inferred project ID used for authentication). Current guidance from the sample working group is to make project ID explicit in the case where it's a required value in the request body. For almost all samples however, the project ID used for authentication should be inferred from the environment (hence the use of const dlp = new DLP.DlpServiceClient(); in the sample)

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

OK

@jmdobry jmdobry changed the title [DO NOT MERGE] Propose new sample format. [DO NOT MERGE] Propose refined sample format Mar 5, 2019
@jmdobry
Copy link
Contributor Author

jmdobry commented Mar 5, 2019

Note: The failing test is not related to this PR.

// [END dlp_inspect_image_file]
}

main(...process.argv.slice(2));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

there's been discussion in the Node.js tooling working group about providing a slightly higher level abstraction on process.argv; potentially Node.js would provide an object.

I agree with the decision to drop yargs so that folks don't have a dependency, but I've definitely found it can be a bit confusing for folks as to why they need to perform a slice operation.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, I made this as simple as possible here while still allowing the sample to be runnable from the command-line. Users on cloud.google.com won't see the slice, they'll just be copying the code between the START and END blocks. I imagine @beccasaurus and co. might auto-generate a more interesting/helpful CLI wrapper.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yep, we use yargs with --input_param="value" flags for all sample input parameters

Copy link
Contributor

@bcoe bcoe left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I really like this work to modernize code samples, especially the fact that you've broken everything out into its own files -- as you say this will be great for auto generation.

@jmdobry jmdobry force-pushed the sample-proposal branch 2 times, most recently from bac400f to cf6666f Compare March 12, 2019 03:29
samples/dlp_delete_job.js Outdated Show resolved Hide resolved
Copy link
Contributor

@fhinkel fhinkel left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

👍

@@ -0,0 +1,47 @@
/**

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This should be samples/dlp-delete-job.js per recent @JustinBeckwith PR changes request

All files _ --> -

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

what's the reason for that? seems it would be easier for our tooling to have the filename be the exact region tag string

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A few things!

  1. JavaScript developers tend to prefer dashes to underscores
  2. The previous file names were really long and had duplicate data (like the project name...) in them
  3. I am generally nervous about encoding metadata inside of file names

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

  1. So that's why lodash is more popular than underscore.js 😛 I feel this could be answered with BigQuery
  2. What previous file names?
  3. The cloud.google.com use case for our samples (where filename doesn't matter) far outweighs the use case where the filename even matters, so we're making things harder for our tooling without much benefit. But if e.g. for Java we already have to have logic to translate region tags to pascal-cased file names, we might as well have more logic to translate region tags to kebab-cased file names for Node.js.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah to be clear - this ain't a hill I want to die on. With no other constraints, I would prefer dashes and not encoding metadata in the file name. If that's a ton of extra work - then I'm not gonna raise a fuss. I trust y'all :)

'use strict';

const {assert} = require('chai');
const dlp = require('@google-cloud/dlp');

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should the test use this style...

const {DlpServiceClient} = require('@google-cloud/dlp');

@@ -0,0 +1,59 @@
/**

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

s/system-test/test/g

We should now have tests in ./samples/test and deprecate the phrase system-test for our sample tests.

( I think? ) => this is a refactor that @JustinBeckwith did today

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

( fwiw – I think ./samples/test is clean. and people understand it. it's idiomatic. )

( when I read "system-test" my brain takes a moment to wonder "what types of tests are these?" )

( i would support this 🙈 )

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Yeah, I tend to just switch these to test as I go.

@jmdobry
Copy link
Contributor Author

jmdobry commented May 15, 2019

Canonical samples have been documented elsewhere. Thanks for review!

@jmdobry jmdobry closed this May 15, 2019
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
cla: yes This human has signed the Contributor License Agreement. do not merge Indicates a pull request not ready for merge, due to either quality or timing. status: blocked Resolving the issue is dependent on other work.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

9 participants