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

Chore: Fix an issue with property renaming in polymer #6401

Merged
merged 19 commits into from
Dec 15, 2023

Conversation

rileyajones
Copy link
Contributor

@rileyajones rileyajones commented May 22, 2023

Motivation for features / changes

We keep the property renaming compiler flag turned off because of the many issues it causes with polymer. This should bring us one step closer towards enabling it.
b/281726974

Googlers, see that this imports correctly cl/585788456

Technical description of changes

The hack of creating custom elements and then referencing properties on them doesn't really work with property renaming turned on because the portions of the code which reference the properties are often not being changed. To get around this while still maintaining the binary seperation I am updating the code to write properties to window

Screenshots of UI changes (or N/A)

Properties are not being renamed
image

@rileyajones rileyajones requested a review from bmd3k May 22, 2023 22:06
Copy link
Contributor

@bmd3k bmd3k left a comment

Choose a reason for hiding this comment

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

This breaks the boundary between the polymer and angular binaries. This is currently forbidden by policy and an internal test. Is there a way to accomplish this without breaking that boundary?

Is it possible, for example, for the polymer code to define some symbols on the window object ?

@rileyajones rileyajones requested a review from bmd3k May 25, 2023 18:38
@rileyajones rileyajones marked this pull request as ready for review May 25, 2023 18:38
tensorboard/webapp/deeplink/hash.ts Outdated Show resolved Hide resolved
tensorboard/webapp/deeplink/hash.ts Outdated Show resolved Hide resolved
tensorboard/webapp/deeplink/hash.ts Outdated Show resolved Hide resolved
@@ -23,25 +23,28 @@ const TAB = '__tab__';

@Injectable()
export class HashDeepLinker implements DeepLinkerInterface {
Copy link
Contributor

Choose a reason for hiding this comment

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

Can we expand this PR to the point where we are accessing tf_global and tf_storage consistently in the Angular part of the app? Basically get to the point where we can delete TfStorageElement and TfGlobalsElement types. The inconsistency in how we access these types is going to hurt somebody's head in the future.

Alternatively: Perhaps the additional cleanup work can be done in a followup PR is you'd like to keep this PR smaller.

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 think I have addressed this, but I'm going to let you resolve this to be sure

@rileyajones rileyajones requested a review from bmd3k November 21, 2023 22:43
@@ -0,0 +1,10 @@
load("//tensorboard/defs:defs.bzl", "tf_ts_library")
Copy link
Contributor

@bmd3k bmd3k Nov 22, 2023

Choose a reason for hiding this comment

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

We already have tb_polymer_interop_types. No need to redeclare the abstractions here.

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 was trying to keep functionality out of a "types" file, but thinking about it more, that does make sense


// Note: `migrateLegacyURLScheme()` must be called before `setUseHash`, so
// that tfStorage reads from the actual URL, not the fake hash for tests
// only.
tfGlobals.tf_globals.setUseHash(true);
this.tfStorage.tf_storage.migrateLegacyURLScheme();
getGlobals('setUseHash')?.(true);
Copy link
Contributor

Choose a reason for hiding this comment

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

There should be minimal or no changes to this file, as long as the polymer binary properly attaches the api to the TFGlobals object.

tensorboard/components/tf_globals/globals-polymer.ts Outdated Show resolved Hide resolved
@rileyajones rileyajones requested a review from bmd3k November 22, 2023 20:55
@@ -41,7 +40,8 @@ export class PluginCoreApiHostImpl {
const result: {
[key: string]: string;
} = {};
const urlDict = tfStorage.tf_storage.getUrlHashDict();

const urlDict = window['tensorboard']['tf_storage']['getUrlHashDict']?.();
Copy link
Contributor

Choose a reason for hiding this comment

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

Whatever you're doing here is probably not going to impress the readability team. You should be able to continue to rely on proper JS/TS objects in the polymer code. (and elsewhere in the polymer code).

Copy link
Contributor Author

Choose a reason for hiding this comment

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

With property renaming enabled the two binaries will check different properties. Something akin to this is necessary to enable them to communicate.

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 can definitely see why the readability team wouldn't love this though

// Note: `migrateLegacyURLScheme()` must be called before `setUseHash`, so
// that tfStorage reads from the actual URL, not the fake hash for tests
// only.
tfGlobals.tf_globals.setUseHash(true);
this.tfStorage.tf_storage.migrateLegacyURLScheme();
window['tensorboard']['tf_storage']['migrateLegacyURLScheme']?.();
Copy link
Contributor

Choose a reason for hiding this comment

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

If you properly declared the API interface for the Angular binary then shouldn't this be tensorboard.tf_storage.migrateLegacyURLScheme?

It should be unnecessary to access the API like this (and I don't think it'll impress the readability team).

Copy link
Contributor Author

Choose a reason for hiding this comment

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

With property renaming enabled the polymer binary will not store this as window.tensorboard.tf_storage.migrateLegacyURLScheme, it will be something like window.AB.CD.EF, then the angular binary will attempt to check a different property, say window.CD.DE.FG. I found string indexes to be the cleanest way to ensure the same properties are accessed.

Copy link
Contributor

Choose a reason for hiding this comment

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

Spoke offline. Riley to look into how to fix this, possibly using typings, possibly using some internal examples of interactions with thirdparty js binaries as motivation.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

This was tricky to solve given that both property renaming and definition files work differently internally and externally. Fortunately I did figure it out with the only compromise being the need to declare window.tensorboard in both the definitions file and the types file.

@rileyajones rileyajones requested a review from bmd3k November 27, 2023 19:51
override _template = null;
tf_globals = tf_globals;
}
window.tensorboard.tf_globals = tf_globals;
Copy link
Contributor

Choose a reason for hiding this comment

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

Cool, it does seem to work. This is how it looks with property renaming turned on:

image

tensorboard/components/tf_globals/globals-polymer.ts Outdated Show resolved Hide resolved
tensorboard/webapp/tb_polymer_interop_types.ts Outdated Show resolved Hide resolved
tensorboard/components/tf_globals/globals-polymer.ts Outdated Show resolved Hide resolved
@@ -15,12 +15,12 @@ limitations under the License.
/**
* Implements core plugin APIs.
*/
import '../../../webapp/tb_polymer_interop_types';
Copy link
Contributor

Choose a reason for hiding this comment

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

PR description hygiene: You include a couple screenshots that IMO are not very valuable. I think you're trying to tell me how you tested your changes but you could probably just use words for that.

A more valuable screenshot would be one that actually shows how the new code is resilient to variable renaming (perhaps a similar screenshot to the one I posted where you see how window.tensorboard.tf_globals appears in the console).

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Prior to my changes those pages never loaded because an error was thrown. I was attempting to highlight that the page at least loads now.
I definitely see your point though so I've updated my description to just include a screenshot of the console

Copy link
Contributor

Choose a reason for hiding this comment

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

I don't understand. TimeSeries and Scalars pages have always loaded successfully. (except for the occasional P0 outage, I guess).

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 didn't load with property renaming enabled

tensorboard/webapp/widgets/histogram/BUILD Outdated Show resolved Hide resolved

export declare interface TfGlobalsElement extends HTMLElement {
tf_globals: TfGlobals;
interface Window {
Copy link
Contributor

Choose a reason for hiding this comment

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

Is this redundant with tb_polymer_interop_type_definitions?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

For some reason the polymer binary doesn't recognize the global definition (this is why it needs to import tb_polymer_interop_types). That means that without this definition here the polymer binary doesn't recognize that this type exists.

Copy link
Contributor

Choose a reason for hiding this comment

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

I patched in your PR locally and deleted this interface Window block. Everything seems to compile and run. I didn't try importing it internally, though. If you still think there is some reason to duplicate it here, best leave a comment.

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 take it you made the change to the OSS project? This works fine there but internally you'll see this error
https://screenshot.googleplex.com/8A2L2M3shUuMu29

I'll add a comment

tensorboard/webapp/deeplink/hash_test.ts Outdated Show resolved Hide resolved
tensorboard/webapp/deeplink/hash.ts Outdated Show resolved Hide resolved
@rileyajones rileyajones requested a review from bmd3k December 6, 2023 23:56
Copy link
Contributor

@bmd3k bmd3k left a comment

Choose a reason for hiding this comment

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

The changes look very good now. Thanks for persisting at it.

Would you consider doing this for any remaining Angular/Polymer interop types? Would that be enough to turn on property renaming?

@@ -15,12 +15,12 @@ limitations under the License.
/**
* Implements core plugin APIs.
*/
import '../../../webapp/tb_polymer_interop_types';
Copy link
Contributor

Choose a reason for hiding this comment

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

I don't understand. TimeSeries and Scalars pages have always loaded successfully. (except for the occasional P0 outage, I guess).

tensorboard/webapp/deeplink/hash.ts Outdated Show resolved Hide resolved
tensorboard/webapp/deeplink/hash.ts Outdated Show resolved Hide resolved
tensorboard/webapp/deeplink/hash_test.ts Outdated Show resolved Hide resolved

export declare interface TfGlobalsElement extends HTMLElement {
tf_globals: TfGlobals;
interface Window {
Copy link
Contributor

Choose a reason for hiding this comment

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

I patched in your PR locally and deleted this interface Window block. Everything seems to compile and run. I didn't try importing it internally, though. If you still think there is some reason to duplicate it here, best leave a comment.

@rileyajones
Copy link
Contributor Author

The changes look very good now. Thanks for persisting at it.

Would you consider doing this for any remaining Angular/Polymer interop types? Would that be enough to turn on property renaming?

It would be nice to get this fully working. As far as I can tell the main issue remaining after this is with some of the dependencies used by the polymer binary. Specifically dagre and THREE. That could be solvable and might make for an interesting on duty task.

@rileyajones rileyajones merged commit d0c5860 into tensorflow:master Dec 15, 2023
13 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants