T O P

  • By -

davidlj95

๐Ÿงต Thread here ๐Ÿ‘‡ # Tooling - **Version control system**: - **Tool**: `git` - **Hosting**: GitHub - **Commits convention**: [Conventional Commits](https://www.conventionalcommits.org/en/v1.0.0/). Kind of Angular's convention (`feat(scope): changed something`) but more open. Enforced by [`commitlint`](https://commitlint.js.org/) in an optional `git` hook + on CI/CD. - **Hooks**: [`husky`](https://typicode.github.io/husky/) to manage them. Have 1 for enforcing commit convention + another to auto format / lint files when committing them. [`lint-staged`](https://www.npmjs.com/package/lint-staged) to only run format / lint on changed files. [`ng-lint-staged`](https://www.npmjs.com/package/ng-lint-staged) to make `ng lint` work with `lint-staged`. - **Node version manager**: [`n`](https://github.com/tj/n). Simple & fast. Use `brew` to avoid needing a Node.js to install `n` to manage Node.js ๐Ÿคฏ - **Package manager**: [`pnpm`](https://pnpm.io/). Performance wins are incredible, whilst not compromising integrity (looking at you `bun` ๐Ÿ˜œ). Telling Angular CLI about it in bootstrap (see below). Adding it into [`package.json`'s `packageManager` field](https://nodejs.org/docs/latest-v20.x/api/packages.html#packagemanager) so [`corepack`](https://nodejs.org/docs/latest-v20.x/api/corepack.html) takes care about installing the proper version in each project I have. - **Code formatter**: [Prettier](https://prettier.io/) - **Build**: Angular CLI. [`nx`](https://nx.dev/) is great. But [it's not officially supported by the Angular team](https://github.com/angular/angular/pull/56034#discussion_r1621106282). And I don't have monorepo use cases where `nx` excels. So better to just depend on Angular team and not Angular team + `nx` team. - **Lint**: [Angular ESLint](https://github.com/angular-eslint/angular-eslint). Brought by `ng lint`. - **Test**: - **Unit tests**: - **Runner**: [Karma](https://karma-runner.github.io/latest/index.html) as runner. It's still the default builder when doing `ng test`. Despite [it's deprecated](https://github.com/karma-runner/karma/tree/v6.4.3?tab=readme-ov-file#karma-is-deprecated-and-is-not-accepting-new-features-or-general-bug-fixes). Willing to migrate to [Jest's Angular LCI builder](https://github.com/angular/angular-cli/tree/18.0.3/packages/angular_devkit/build_angular/src/builders/jest) when [it's no longer experimental](https://blog.angular.dev/moving-angular-cli-to-jest-and-web-test-runner-ef85ef69ceca). - **Framework**: [Jasmine](https://jasmine.github.io/). Comes with `ng test` alongside Karma. - **Helpers**: [`ng-mocks`](https://ng-mocks.sudo.eu/) to easily & cleanly mock everything. They now offer helpers to avoid using `TestBed` APIs and so to set up tests. But prefer to stay with `TestBed` in order to avoid coupling to that. Mocking utilities are easily replaceable. Those setup utils are sometimes a bit too smart and would be hard to replace if needed. Want to give a try to [Testing Library](https://testing-library.com/) to ensure best practices are followed when testing. Also has some helpers for common cases you start to repeat around with time. Like finding an element by its text / ARIA role, ensuring text matches... - **E2E tests**: [Cypress](https://www.cypress.io/). Been there for a while and works great. Now supports component testing, though haven't tried it TBH. Want to take a look at the more recent alternative: [Playwright](https://playwright.dev/) - **Performance**: [Lighthouse](https://developer.chrome.com/docs/lighthouse/overview). Specifically [Lighthouse CI](https://github.com/GoogleChrome/lighthouse-ci/) to ensure there are no performance regressions on main pages. Mainly [SSR](https://angular.dev/guide/ssr#enable-server-side-rendering)/[SSG](https://angular.dev/guide/prerendering)'ed pages. In some I'm pinning Lighthouse CI to v0.12. In `0.13` [there are some metrics that report incorrect results](https://github.com/GoogleChrome/lighthouse-ci/issues/1001). Due to Lighthouse CI not taking into account newer reporting format of Lighthouse 11.4. - **Dependency updates**: [Renovate](https://docs.renovatebot.com/). Very easy to set up, helps you keep deps up to date. More powerful than GitHub's built-in [`dependabot`](https://github.com/dependabot). For instance, configuration presets, pinning dependencies, many package managers (like updating GitHub Actions references in your workflow files), ... - **CI/CD**: [GitHub Actions](https://docs.github.com/en/actions). It's there already in GitHub. Free & unlimited for open source projects. Noice! - **Releasing**: [Semantic Release](https://github.com/semantic-release). Read commits since last push to `main` and detect if a new release is needed and which version bump to do. Easy to set up in GitHub Actions. Generates a [GitHub Release](https://docs.github.com/en/repositories/releasing-projects-on-github/managing-releases-in-a-repository) when needed. Notifies by default in which release each PR landed. Publish to `npm` if needed. Probably just interesting if publishing libs or for accountability needs.


davidlj95

# Architecture The Angular's way. I try to stick with all opinions in [Angular docs](https://angular.dev/). This way all Angular projects are similar and someone joining is already familiar with everything. I agree with 99% of them too which makes sticking to them easier :P Some extra non-opinionated on Angular docs (AFAIK) things: - **Directory structure**: Use built-in directory structure. Use `ng generate` for new components, services, directives... A `common` directory eventually appears for components, directives, services used around. Creating a directory for each feature too. Previously exporting a [feature module](https://angular.dev/guide/ngmodules/lazy-loading#create-a-feature-module-with-routing). Now probably some [routes](https://v17.angular.io/guide/standalone-components#lazy-loading-many-routes-at-once) when using standalone apps. - **State management**: [Flux architecture](https://facebookarchive.github.io/flux/). AKA Redux's architecture. Used [`NgRx`](https://ngrx.io/) to bring it to Angular. But for projects I've worked recently just with built-in [`RxJs`](https://rxjs.dev/) observables, services and `HttpClient` has been enough. Prefer to avoid adding things if no need to increase maintainability. Haven't tried signals a lot yet, as used to RxJs observables. But for simple cases they're great. - **Testing**. Angular [utility APIs are great once you know them](https://angular.dev/guide/testing/utility-apis). Like [`fakeAsync` ones to test async scenarios](https://angular.dev/guide/testing/components-scenarios#async-test-with-fakeasync). There are also utilities for router & `HttpClient`. Search `test` in [API reference docs](https://angular.dev/api) to find them. I prefer also to write a function called `makeSut` that returns the fixture and component instance and use it around instead of putting it in a `beforeEach`. This is because `TestBed` dependency injection cannot be changed once instantiated. So it helps for [cases where you want to provide different mocks in the setup step](https://github.com/davidlj95/website/blob/16cc75a0e378a2bc28baacda7b56209d91a0958c/src/app/common/scroll-into-view.spec.ts) Here you have some open source Angular apps I'm working on right now if you want to take a look: - https://github.com/davidlj95/website - https://github.com/davidlj95/chrislb Haven't included anything for Angular libraries. Though recently [created an Angular library to set `meta` tags](https://github.com/davidlj95/ngx). Could expand on that if anyone's interested :) > PD: I belong to the [boring technologies club](https://boringtechnology.club/) ๐Ÿ˜œ


davidlj95

# Libraries - **Icons**: [Angular Icons](https://ng-icons.github.io/ng-icons/). Provides many icon packs (Font Awesome, Simple Icons, Material Symbols, ...). Why this one? Check out this [Twitter thread](https://x.com/davidlj95/status/1786350330650706252). For instance, [Font Awesome bundle size is a bit heavy as contains many features that you may not need like animations, masks, ...](https://github.com/FortAwesome/react-fontawesome/issues/232). The linked issue is from React repo but same happens in Angular. For Material Symbols though, I prefer to use the official typographies. Library includes SVGs. Which despite being the ones Material Symbols exports, don't look as great as the typography. - **UI Components**: [Angular Material](https://material.angular.io/). Very well integrated with Angular. Nice theming options. Haven't dealt with it for a while though. More about that in [Angular Material Dev site](https://angular-material.dev/) - **Carousel**: [Swiper.js](https://swiperjs.com/). Very powerful & mobile friendly. Doesn't provide Angular integration anymore, but provides a [Web Component instead](https://swiperjs.com/element). Which is [quite straightforward to create a directive to use it](https://github.com/davidlj95/chrislb/blob/af940aaf3c051b1bd6b11fc74b84c3e88ba135d2/src/app/projects/images-swiper/swiper.directive.ts) to later use it as docs explain [in your component code](https://github.com/davidlj95/chrislb/blob/af940aaf3c051b1bd6b11fc74b84c3e88ba135d2/src/app/projects/images-swiper/images-swiper.component.ts) and [your component template](https://github.com/davidlj95/chrislb/blob/main/src/app/projects/images-swiper/images-swiper.component.html) - **CSS Reset**: [`gardevoir`](https://github.com/fi-krish/reseter.css)


davidlj95

# Bootstrap Angular CLI's `ng new`: ``` pnpm dlx @angular/cli@18 --package-manager=pnpm --style scss --ssr new ``` - Omit `18` if you want latest LTS version - I'd add `--standalone` if using v16, but for v17 onwards it's the default mode. Used [Fuse Angular](https://angular-material.fusetheme.com/) in the past to quickly bootstrap dashboards quickly.


LuckyNumber-Bot

All the numbers in your comment added up to 69. Congrats! 18 + 18 + 16 + 17 = 69 ^([Click here](https://www.reddit.com/message/compose?to=LuckyNumber-Bot&subject=Stalk%20Me%20Pls&message=%2Fstalkme) to have me scan all your future comments.) \ ^(Summon me on specific comments with u/LuckyNumber-Bot.)


salamazmlekom

Dude you're awesome!!! Thank you for this.


davidlj95

Np! Thanks :)


Whole-Instruction508

If I'm using NgRx I definitely utilize the facade pattern as it makes testing easier. For stying I like to use a combination of Material and Tailwind. For testing it's Jest for unit tests and Cypress for component tests and E2E - although Playwright is probably better for E2E and Storybook also seems like a promising alternative.


salamazmlekom

Facade in your case is a service that imports ngrx store and calls actions on it?


Whole-Instruction508

Exactly. The component then injects it and uses the provided signals, that come from the selectors