Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat(cdk): construct.uniqueId and relax construct id constraints #556

Merged
merged 1 commit into from
Aug 14, 2018

Conversation

eladb
Copy link
Contributor

@eladb eladb commented Aug 14, 2018

Adds a property uniqueId to Construct which returns an alphanumeric 255-length-limited tree-unique identity for a construct.

Relax constraints for construct id (previously known as "name") to only restrict the usage of the path separator. Otherwise, all characters are allowed. This will allow using the construct id for a wider range of purposes, but since logical IDs (and uniqueId now) are alpha-safe, it's okay.

Deprecate construct.name in favor of construct.id.

By submitting this pull request, I confirm that my contribution is made under the terms of the Apache-2.0 license.

Adds a property `uniqueId` to Construct which returns an 
alphanumeric 255-length-limited tree-unique identity for a construct.

Relax constraints for construct id (previously known as "name") to only
restrict the usage of the path separator. Otherwise, all characters are
allowed. This will allow using the construct id for a wider range of
purposes, but since logical IDs (and uniqueId now) are alpha-safe, it's 
okay.

Deprecate `construct.name` in favor of `construct.id`.
@eladb eladb requested a review from rix0rrr August 14, 2018 06:26
@eladb eladb merged commit 0efe25b into master Aug 14, 2018
@eladb eladb deleted the benisrae/construct-unique-id branch August 14, 2018 07:36
@@ -1,11 +1,7 @@
import { makeUniqueId } from '../util/uniqueid';
import { StackElement } from "./stack";
Copy link
Contributor

Choose a reason for hiding this comment

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

Update to use single quotes.

/**
* Returns the parent of this node or undefined if this is a root node.
*/
public readonly parent?: Construct;

/**
* The name of this construct
* @deprecated use `id`
Copy link
Contributor

Choose a reason for hiding this comment

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

Yeahhhhhh that's a poor deprecation message. You want to explain why id is better.

Copy link
Contributor

Choose a reason for hiding this comment

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

Also a good idea to mention when it was deprecated, so we can assess when it is safe to drop.

Copy link
Contributor

Choose a reason for hiding this comment

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

Finally, why are you so careful in not breaking usage of .name? I feel like this is probably not common place... Would have dropped.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

okay, removed!

*/
public readonly name: string;

/**
* The subtree-local id of the construct.
* This id is unique within the subtree. To obtain a tree-unique id, use `uniqueId`.
Copy link
Contributor

Choose a reason for hiding this comment

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

Define subtree... The construct may be accessible from several parts of the tree, but I suppose the subtree in question is the one it's attached to, not the one you're accessing from...

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Changed description to:

    /**
     * The local id of the construct.
     * This id is unique amongst its siblings.
     * To obtain a tree-global unique id for this construct, use `uniqueId`.
     */
    public readonly id: string;


/**
* The full path of this construct in the tree.
* Components are separated by '/'.
Copy link
Contributor

Choose a reason for hiding this comment

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

In other words:

So we had this jolly good array of strings that represent a path in the tree. We could have exposed it as a ReadonlyArray<string>, but we though - oh the hell, we can .join('/') this so in case you're interested in the array, you'll always have to .split('/') it. There there, we fixed it.

Copy link
Contributor

Choose a reason for hiding this comment

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

Yes, I know not every language supports ReadonlyArray<T>, but they could code-generate a copy-on-read and be good with it.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

The reason this is a string is because I think that in most cases, when people need the path, they want the string version of it and not the components. Optimize for the common case.

public readonly path: string;

/**
* A tree-unique alpha-numeric identifier for this construct.
Copy link
Contributor

Choose a reason for hiding this comment

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

Hmm'kay. I feel tree is maybe over-used and maybe too generic.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Tree represents the entire construct tree. Added "global"

const hash = pathHash(components);
const human = removeDupes(components)
.map(removeNonAlpha)
.filter(x => x !== HIDDEN_FROM_HUMAN_ID)
Copy link
Contributor

Choose a reason for hiding this comment

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

Do you not want to do this one before removeNonAlpha? I feel that Re-source shouldn't be considered as === 'Resource'.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Done

/**
* Removes all non-alphanumeric characters in a string.
*/
function removeNonAlpha(s: string) {
Copy link
Contributor

Choose a reason for hiding this comment

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

Rename to removeNonAlphanumeric. The name is, otherwise, a lie.

* Removes all non-alphanumeric characters in a string.
*/
function removeNonAlpha(s: string) {
return s.replace(/[^A-Za-z0-9]/g, '');
Copy link
Contributor

Choose a reason for hiding this comment

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

Can make this return s.replace(/[^a-z0-9]/ig, '');

Copy link
Contributor Author

Choose a reason for hiding this comment

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

I prefer this

/**
* Remove duplicate "terms" from the path list
*
* If a component name is completely the same as the suffix of
Copy link
Contributor

Choose a reason for hiding this comment

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

Very convoluted phrasing:

completely the same as the suffix of the previous comment name

How about

If the previous path component name ends with this component name, skip the current component.

<MyConstruct name='child1' prop1='hi' prop2={21} >
<MyConstruct name='child11' prop1='there' />
<MyConstruct name='child12' prop1='boo' />
<MyConstruct id='child1' prop1='hi' prop2={21} >
Copy link
Contributor

Choose a reason for hiding this comment

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

That sure is one place where id looks so much better! 👌🏻

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Agreed

eladb pushed a commit that referenced this pull request Aug 14, 2018
* Use node.js "crypto" module instead of md5
* Remove `construct.name` (and fix all dependencies)
* Remove non-alphanumeric after "Resource" is omitted

BREAKING CHANGE: `construct.name` => `construct.id`
eladb pushed a commit that referenced this pull request Aug 14, 2018
* Use node.js "crypto" module instead of md5
* Remove `construct.name` (and fix all dependencies)
* Remove non-alphanumeric after "Resource" is omitted

BREAKING CHANGE: `construct.name` => `construct.id`
rix0rrr added a commit that referenced this pull request Aug 15, 2018
### Features

* __@aws-cdk/cdk__: Tokens can now be transparently embedded into
  strings and encoded into JSON without losing their semantics. This
  makes it possible to treat late-bound (deploy-time) values as if they
  were regular strings ([@rix0rrr] in
  [#518](#518)).
* __@aws-cdk/aws-s3__: add support for bucket notifications to Lambda,
  SNS, and SQS targets ([@eladb] in
  [#201](#201),
  [#560](#560),
  [#561](#561),
  [#564](#564))
* __@aws-cdk/cdk__: non-alphanumeric characters can now be used as
  construct identifiers ([@eladb] in
  [#556](#556))
* __@aws-cdk/aws-iam__: add support for `maxSessionDuration` for Roles
  ([@eladb] in [#545](#545)).

### Changes

* __@aws-cdk/aws-lambda__ (_**BREAKING**_): most classes renamed to be
  shorter and more in line with official service naming (`Lambda`
  renamed to `Function` or ommitted) ([@eladb] in
  [#550](#550))
* __@aws-cdk/aws-codepipeline__ (_**BREAKING**_): move all CodePipeline
  actions from `@aws-cdk/aws-xxx-codepipeline` packages into the regular
  `@aws-cdk/aws-xxx` service packages ([@skinny85] in
  [#459](#459)).
* __@aws-cdk/aws-custom-resources__ (_**BREAKING**_): package was
  removed, and the Custom Resource construct added to the
  __@aws-cdk/aws-cloudformation__ package ([@rix0rrr] in
  [#513](#513))

### Fixes

* __@aws-cdk/aws-lambda__: Lambdas that are triggered by CloudWatch
  Events now show up in the console, and can only be triggered the
  indicated Event Rule. _**BREAKING**_ for middleware writers (as this
  introduces an API change), but transparent to regular consumers
  ([@eladb] in [#558](#558))
* __@aws-cdk/aws-codecommit__: fix a bug where `pollForSourceChanges`
  could not be set to `false` ([@maciejwalkowiak] in
  [#534](#534))
* __aws-cdk__: don't fail if the `~/.aws/credentials` file is missing
  ([@RomainMuller] in
  [#541](#541))
* __@aws-cdk/aws-cloudformation__: fix a bug in the CodePipeline actions
  to correctly support TemplateConfiguration ([@mindstorms6] in
  [#571](#571)).
* __@aws-cdk/aws-cloudformation__: fix a bug in the CodePipeline actions
  to correctly support ParameterOverrides ([@mindstorms6] in
  [#574](#574)).

### Known Issues

* `cdk init` will try to init a `git` repository and fail if no global
  `user.name` and `user.email` have been configured.
@NGL321 NGL321 added the contribution/core This is a PR that came from AWS. label Sep 27, 2019
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
contribution/core This is a PR that came from AWS.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants