question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Regression - Decorators

See original GitHub issue

Currently, we cannot upgrade to Angular 9.0 Ivy because of the regressions introduced by the Ivy compiler. If #35464 is not merged, we will have to stop upgrading Angular and leave it at version 9.0 indefinitely.

I am sharing this issue primarily so the Angular team can see how users are using Custom Decorators in the wild. I suspect I’m not the only one doing something like this.

Description

We develop an Nx workspace app, with multiple shared libraries powering both a Desktop, and Mobile application - responsive design doesn’t cut it for our use case. In addition, we also have separate administrator views, and client libraries which are all generated from the same source code.

As such, dependency injection doesn’t always meet our use case, even with the @Optonal decorator. Many of our components end up being shared between Mobile and Desktop, User and Administrator contexts, and as much as we can simplify their logic, we try to do so.

Currently, we use custom decorators to wire components in to pieces of the application which may, or may not be present. A great example is how we integrate with the map; In the Desktop application, a large on-screen map is available to most components. When users are entering addresses, they can click on the map, drag the pin around, etc. When on the Mobile application, this is not available.

The following code is how we connect the pin to the map in our application:


@Component({
    selector: 'app-foo',
    template: `
The origin pin is at {{orig?.lat}}, {{orig?.lng}}.
<button (click)="centerOnEmpireStateBuilding()">Center</button>
<button (click)="removePin()">Hide Pin</button>
`
})
// Wires up necesary parts, Object.defineProperty etc. on `ngOnInit`
@MapConnectedComponent()
export class FooComponent {
    
     // Actually connects this property to the map in a two-way databinding
    @MapConnectedAddress('orig')
    pin: {lat:number; lng: number;}

   centerOnEmpireStateBuilding() {
      // This will move the pin on the map to the appropriate location as well.
      this.pin = {lat: 40.7484, lng:-73.9857};
   }

  removePin() {
      // This will remove the pin
    this.pin = null;
  }
}

Because we have a small team of mostly junior developers, we try to focus on our developer experience heavily. Custom Decorators like this provide many benefits, chiefly among them:

  1. Declarative vs. Imperative programming
  2. Easy instruction for Jr developers - practically self documenting code.
  3. Free adherence to the Open / Closed principle, without need for inheritence.

Conclusion

#35464 is a blocker for us; We really don’t want to unravel all the custom decorators we’ve developed (this is just one of the examples) just so that Angular can have a minuscule benefit in start up performance.

With Angular 8.0 I was able to achieve a very concise, easy to explain process. Before the decorators, each address which needed to be connected to the map, required 8 - 10 lines of code, not to mention injecting the right service, etc. Now, it’s two decorators.

I hope this has been illuminating in how Metaprogramming is used in the wild, and helps you understand the user base better.

Issue Analytics

  • State:closed
  • Created 3 years ago
  • Reactions:2
  • Comments:5 (1 by maintainers)

github_iconTop GitHub Comments

2reactions
bryanridesharkcommented, May 15, 2020

@pkozlowski-opensource , are we having to wait for Angular 10 for #35464 to be merged? Or Angular 11? Or can we expect this to land in a point release for Angular 9, say 9.2?

I would love to be able to upgrade our application to Ivy - everything else worked, except for this.

0reactions
angular-automatic-lock-bot[bot]commented, Jun 20, 2020

This issue has been automatically locked due to inactivity. Please file a new issue if you are encountering a similar or related problem.

Read more about our automatic conversation locking policy.

This action has been performed automatically by a bot.

Read more comments on GitHub >

github_iconTop Results From Across the Web

Decorators in Python - How to enhance functions without ...
Decorators in python allow you to dynamically change the functionality of another function, without altering it's code.
Read more >
ReFrame Programming APIs — ReFrame 3.1 (rev: 8332e984 ...
This page provides a reference guide of the ReFrame API for writing regression tests covering all the relevant details. Internal data structures and...
Read more >
Regression on form rebuild and wrong decorator pattern ...
Problem/Motivation The overridden file system introduced in [#3058063] presents a regression in file upload widgets using ajax (e.g., ...
Read more >
Decorating Tasks - Flyte
A simple way of modifying the behavior of tasks is by using decorators to wrap your task functions. In order to make sure...
Read more >
Decorating my Kawaii/AgeRe Room + GIVEAWAY! - YouTube
Decorating my Kawaii/AgeRe Room + GIVEAWAY! | Age Regression. 5.4K views 1 year ago. Soft Princess. Soft Princess. 5.08K subscribers.
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found