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

Angular 9 support #3537

Closed
9 tasks done
maxokorokov opened this issue Jan 9, 2020 · 12 comments
Closed
9 tasks done

Angular 9 support #3537

maxokorokov opened this issue Jan 9, 2020 · 12 comments

Comments

@maxokorokov
Copy link
Member

maxokorokov commented Jan 9, 2020


Update: published 6.0.0-rc.0, final version should be coming next week

@maxokorokov maxokorokov added this to the 6.0 milestone Jan 9, 2020
@Zwergenpunk
Copy link

Do you have any timeline for support of ng 9?

@maxokorokov
Copy link
Member Author

@Zwergenpunk, rc should be released later this week.

Though we're not aware of any issues with ivy support at the moment, and there are no actual component code changes planned for 6.0.0. So even the latest 5.2.x should work with ivy and NG 9 (despite installation/dependency warnings of course).

@Zwergenpunk
Copy link

Thanks for the info and your work :)

@maxokorokov maxokorokov changed the title Chore for 6.0.0 Angular 9 support Feb 13, 2020
@maxokorokov maxokorokov pinned this issue Feb 13, 2020
@bcmedeiros
Copy link

I'm using Angular 9 since release, no issues so far. If you need any tests, I might be able to help, just let me know.

@ghost
Copy link

ghost commented Feb 14, 2020

Hello. With enabled Ivy, Angular requires to install @angular/localize because of some module in ng-boostrap. I don't use i18n in my application and want to decrease bundle size as much as possible. Is it possible to avoid importing @angular/localize?

image

Used ng-bootstrap modules in my app: NgbDropdownModule, NgbPopoverModule, NgbCollapseModule, NgbTooltipModule, NgbModalModule

@maxokorokov
Copy link
Member Author

maxokorokov commented Feb 14, 2020

@nseni, we haven't updated the docs/release notes yet, but there are indeed 2 new peer dependencies:

  • tslib → it was a dependency before, we just followed Angular here → Tslib as peerDependency angular/angular#32167
  • @angular/localize, because we're using Angular i18n in the library. And it is one of the breaking changes for ivy.

So you're actually kind of using i18n... via ng-bootstrap, because all our labels are translated with i18n. You can read more here → https://angular.io/guide/migration-localize


I'm not 100% sure how i18n is supposed to work with ivy and haven't really been following this, but if I understand correctly, it works this way (@pkozlowski-opensource, please correct me if I'm wrong):

Let's take our alert as an example.

  1. We have an aria-label="Close" i18n-aria-label="@@ngb.alert.close" somewhere in our ng-bootstrap alert template. And component templates are just strings when ng-bootstrap is distributed as a view engine (not ivy) library (look into your node_modules/@ng-bootstrap/...).
  2. When you serve/test/build your app, ng-bootstrap goes through ivy ngcc (result ends up in node_modules/@ng-bootstrap/.../__ivy__ngcc) and our label in the template gets compiled to:
var I18N_1;
if (typeof ngI18nClosureMode !== "undefined" && ngI18nClosureMode) {
    const MSG_EXTERNAL_ngb_alert_close$$FESM2015_NG_BOOTSTRAP_JS__2 = goog.getMsg("Close");
    I18N_1 = MSG_EXTERNAL_ngb_alert_close$$FESM2015_NG_BOOTSTRAP_JS__2;
}
else {
    I18N_1 = $localize `:@@ngb.alert.close␟f4e529ae5ffd73001d1ff4bbdeeb0a72e342e5c8␟7819314041543176992:Close`;
}
const _c3 = ["aria-label", I18N_1];

So you have this global $localize function now.

  1. If you look at this $localize function in source code, you'll see that there are 3 possible scenarios to what happens with this function.

For example, if you just ng build --prod your app, you'll end up with this $localize function in polyfills:

Roughly this:

    "N/DB": function(e, t) {
        const n = "undefined" != typeof globalThis && globalThis
          , o = "undefined" != typeof window && window
          , r = "undefined" != typeof self && "undefined" != typeof WorkerGlobalScope && self instanceof WorkerGlobalScope && self
          , s = "undefined" != typeof global && global
          , a = function(e, ...t) {
            if (a.translate) {
                const n = a.translate(e, t);
                e = n[0],
                t = n[1]
            }
            let n = i(e[0], e.raw[0]);
            for (let o = 1; o < e.length; o++)
                n += t[o - 1] + i(e[o], e.raw[o]);
            return n
        };
        function i(e, t) {
            return ":" === t.charAt(0) ? e.substring(function(e, t) {
                for (let n = 1, o = 1; n < e.length; n++,
                o++)
                    if ("\\" === t[o])
                        o++;
                    else if (":" === e[n])
                        return n;
                throw new Error(`Unterminated $localize metadata block in "${t}".`)
            }(e, t) + 1) : e
        }
        (n || s || o || r).$localize = a
    },

And the actual code where this aria-label is set, would look like this:

const uu = ["aria-label", $localize`:@@ngb.alert.close␟f4e529ae5ffd73001d1ff4bbdeeb0a72e342e5c8␟7819314041543176992:Close`];

So "almost" no overhead here, I wouldn't worry about it.

However if you ng build --prod --localize, this $localize function will be compiled out completely and you'll end up with:

const Uc = ["aria-label", "Close"];

But you'll have to mange locales for your app.

I'm not sure, if it is possible to inline these i18n strings any other way and completely avoid overhead.

But hey, you'll get dynamic i18n if necessary now :)

@stevethemacguy
Copy link

stevethemacguy commented Feb 21, 2020

I'm having a change detection issue with the datepicker when building with IVY. I will submit an issue with a minimal repo on Monday, but just wanted to give a heads-up. If I dynamically add a class to a custom dayTemplate, the class is not added in the HTML until I trigger change detection on the datepicker in some other way (e.g. by hovering over the calendar). Might be related to #3257 and #3438.

@maxokorokov
Copy link
Member Author

maxokorokov commented Feb 21, 2020

@stevethemacguy please do open an issue with the reproduction scenario. Please add the Stackblitz (even though they use view engine, and not ivy at the moment)

EDIT: for ivy you could also use https://ng-run.com/

@maxokorokov
Copy link
Member Author

Closing as 6.0.0 was released, please open new issues if necessary.

@maxokorokov maxokorokov unpinned this issue Feb 21, 2020
@stevethemacguy
Copy link

@maxokorokov Unfortunately 6.0.0 didn't fix my issue, but thanks for the ng-run link. I'll see if I can reproduce.

@stevethemacguy
Copy link

@maxokorokov Is there a way to share the ng-run project? I have a StackBlitz version done too, but I'm curious. Thank you.

@stevethemacguy
Copy link

stevethemacguy commented May 13, 2020

I confirmed that Angular version 9.1.5 fixed my datepicker change detection issue when building with IVY. (see angular/angular#35400).

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

4 participants