{"id":23918324,"url":"https://github.com/sahilk-027/angular-journey","last_synced_at":"2025-07-08T12:03:48.386Z","repository":{"id":210503516,"uuid":"725960311","full_name":"SahilK-027/Angular-Journey","owner":"SahilK-027","description":"All Angular 16 learning","archived":false,"fork":false,"pushed_at":"2023-12-18T04:55:34.000Z","size":34,"stargazers_count":2,"open_issues_count":0,"forks_count":0,"subscribers_count":1,"default_branch":"main","last_synced_at":"2025-01-05T13:13:46.931Z","etag":null,"topics":["angular","angular-learning"],"latest_commit_sha":null,"homepage":"","language":null,"has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/SahilK-027.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2023-12-01T08:30:03.000Z","updated_at":"2024-04-26T04:49:23.000Z","dependencies_parsed_at":"2025-01-05T13:13:32.112Z","dependency_job_id":null,"html_url":"https://github.com/SahilK-027/Angular-Journey","commit_stats":null,"previous_names":["sahilk-027/angular-journey"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/SahilK-027%2FAngular-Journey","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/SahilK-027%2FAngular-Journey/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/SahilK-027%2FAngular-Journey/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/SahilK-027%2FAngular-Journey/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/SahilK-027","download_url":"https://codeload.github.com/SahilK-027/Angular-Journey/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":240372480,"owners_count":19791008,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["angular","angular-learning"],"created_at":"2025-01-05T13:13:27.467Z","updated_at":"2025-02-23T20:21:10.212Z","avatar_url":"https://github.com/SahilK-027.png","language":null,"funding_links":[],"categories":[],"sub_categories":[],"readme":"# Angular Journey SK027\n\n## How Angular project works ?\n\n### Create Angular Project and start development\n\n- Creates a new Angular workspace.\n\n```bash\nng new [project_name]  # [aliases: n]\n```\n\n- Builds and serves your application, rebuilding on file changes.\n\n```bash\nng serve [project]  #[aliases: s]\n```\n\n- Theory\n\nAngular CLI saves the compile Angular application in the memory \u0026 directly starts it. If we make any changes to our Angular app, Angular CLI will recompile \u0026 update the file. Angular CLI uses Webpack to traverse through our Angular app \u0026 it bundles IS \u0026 other files into one or more bundles. Then Angular CLI also injects the bundled JavaScript \u0026 CSS files in the index.html.\n\nWhen the index.html file is loaded, Angular core libraries \u0026 third party libraries are also loaded by that time. Now Angular needs to locate the main entry point. So it analyzes angular.json (get the main file).\n\n```json\n\"options\":{\n    \"outputPath\": \"dist/angular-ekart\",\n    \"index\": \"src/index.html\",\n    \"main\": \"src/main.ts\",\n    \"polyfills\": [\"zone.js\"]\n}\n```\n\n- Flow\n  Angular Project -\u003e index.html -\u003e angular.json (get the main file) -\u003e main.ts -\u003e AppModule -\u003e AppComponent -\u003e View Template(app. component. html)\n\n## Types of Component Selector\n\n- Like HTML tag: selector : \"app-nav\"\n- Like HTML attribute: selector : \"[app-nav]\"\n- Like HTML class: selector : \".app-nav\"\n\n## Data Binding\n\nData Binding in Angular allows us to communicate between a component class (Typescript) and its corresponding view template (Html) \u0026 vice-versa.\n\nComponent \u003c---------------------------------\u003e View Template\n(UI logic) (HTML Page)\n\n- Example: How data binding is done in between component and template\n- Component UI logic\n\n```typescript\nexport class MyComponent{\n    title = \"dummy title';\n    message = 'SK LEARNS ANGULAR';\n    display = false;\n    onclick(){\n        this.display = true;\n    }\n}\n```\n\n- View Template\n\n```html\n\u003cdiv class=\"header\"\u003e\n  \u003cdiv\u003e{{ title }}\u003c/div\u003e\n  \u003cdiv\u003e{{ message }}\u003c/div\u003e\n  \u003cbutton （click）=\"onclick()\"\u003eClick Me\u003c/button\u003e\n  \u003cdiv [hidden]=\"display\"\u003e\n    \u003cp\u003eDisplay this content\u003c/p\u003e\n  \u003c/div\u003e\n\u003c/div\u003e\n```\n\n### Advantages and disadvantages of angular over react.\nAngular: \n- Two-way data binding by default using ngModel.\n- Angular's built-in dependency injection system makes it easier to manage and organize components, services, and other application parts.\n- Angular applications may have larger initial bundle sizes compared to React, which can impact page load times. However, Angular provides tools to optimize and reduce bundle sizes.\n- More strict and better error handling.\n\nRect: Unidirectional data flow, but supports two-way binding using state management libraries (e.g., Redux).\n\n### Types of Data Binding in Angular\n\n- Type 1: One Way Data Binding\n  Component to View OR View to Component\n\nOne-way data binding is when, data can be access from component into its corresponding view or vice versa.\n\n    - Type 1.1: Component to View\n                  Data flow from component to class view template\n        Component ------------------------------------------------------------------\u003e View Template\n                  String interpolation: {{data}}\n                  Property binding: [property] = data\n\n    - Type 1.2: View to Component\n                    Data flow from view template to component class\n        Component \u003c------------------------------------------------------------------ View Template\n                  Event binding:: (data)=\"expression\"\n\n#### String interpolation\n\nExample:\n\n```typescript\nexport class ProductListComponent {\n  product = {\n    name: \"iPhone XR\",\n    price: 789,\n    color: \"Black\",\n    discount: 5.5,\n  };\n\n  getDiscountedPrice(): number {\n    return (\n      this.product.price - (this.product.price * this.product.discount) / 100\n    );\n  }\n}\n```\n\n```html\n\u003cp\u003eProduct name: {{product.name}}\u003c/p\u003e\n\u003cp\u003eOriginal price: {{product.price}}\u003c/p\u003e\n\u003cp\u003eProduct color: {{product.color}}\u003c/p\u003e\n\u003cp\u003eDiscounted price: {{getDiscountedPrice()}}\u003c/p\u003e\n```\n\n#### Property Binding\n\nProperty binding lets us bind a property of a DOM object, for example the hidden property, to some data value. This can let us show or hide a DOM element, or manipulate the DOM in some other way.\n\nExample:\n\n```typescript\nexport class ProductListComponent {\n  product = {\n    name: \"iPhone XR\",\n    price: 789,\n    color: \"Black\",\n    discount: 5.5,\n    pImage: \"/assets/images/iphoneXR.png\",\n  };\n\n  getDiscountedPrice(): number {\n    return (\n      this.product.price - (this.product.price * this.product.discount) / 100\n    );\n  }\n}\n```\n\n```html\n\u003c!-- we can do it with string interpolation like this --\u003e\n\u003c!-- \u003cimg src = {{product.pImage}}\u003e --\u003e\n\n\u003c!-- we can do it with property binding like this\nInside \"\" you can write any typescript expression --\u003e\n\u003cimg [src]=\"product.pImage\" /\u003e\n\u003cimg bind-src=\"product.pImage\" /\u003e\n\u003c!-- Another syntax for property binding --\u003e\n\n\u003cp\u003eProduct name: {{product.name}}\u003c/p\u003e\n\u003cp\u003eOriginal price: {{product.price}}\u003c/p\u003e\n\u003cp\u003eProduct color: {{product.color}}\u003c/p\u003e\n\u003cp\u003eDiscounted price: {{getDiscountedPrice()}}\u003c/p\u003e\n```\n\nNote: If we can do same stuff with string interpolation why do we need property binding?\nAns: For html attributes like hidden, Disabled, Checked we need to use property binding only there string interpolation won't work.\n\n#### Event Binding\n\nIn Angular, event binding is a mechanism that allows you to respond to user events, such as clicks, key presses, mouse movements, etc. It's a way to capture and handle events raised by the user or by other components in your application.\n\nFor event binding wrap the event with (). Angular supports a variety of events such as (click), (keyup), (change), etc\n\nIn Angular, the (change) event binding is used to capture and respond to changes in an input element, such as text inputs, checkboxes, and select dropdowns. The (change) event is triggered when the user interacts with the input, and the value of the input changes.\n\n- Example\n\n```typescript\nexport class AppComponent {\n  // Initial value for the dynamicName\n  dynamicName: string = \"Not entered name\";\n\n  // Method to be called on input change\n  onNameChange(newName: string): void {\n    // Update dynamicName with the new value\n    this.dynamicName = newName;\n  }\n}\n```\n\n```html\n\u003c!-- Input tag with event binding for input event --\u003e\n\u003cinput\n  placeholder=\"Enter your name\"\n  (input)=\"onNameChange($event.target.value)\"\n/\u003e\n\n\u003c!-- Paragraph with string interpolation --\u003e\n\u003cp\u003e{{ dynamicName }}\u003c/p\u003e\n```\n\n- Type 2: `Two Way Data Binding`\n  Component to View View to Component\n\nTwo-way data binding binds data from component class to view template and view template to component class. It is a combination of property binding \u0026 event binding.\n\nTwo-way data binding in Angular is commonly achieved using [(ngModel)]. `ngModel` is the directive that provides two-way data binding in Angular forms.\n\nEnsure that you have the FormsModule imported in your Angular module. The FormsModule is required for using ngModel for two-way data binding.\n\n- Use [(ngModel)] in HTML:\n\nYou can use [(ngModel)] within your template to create two-way data binding. It's often used in conjunction with form controls like input elements.\n\n```html\n\u003c!-- app.component.html --\u003e\n\n\u003cinput [(ngModel)]=\"username\" placeholder=\"Enter your username\" /\u003e\n\n\u003c!-- The value of the input is bound to the 'username' property of the component --\u003e\n```\n\n- Use in component\n\nIn your component TypeScript file, you should have a property (e.g., username) that you bind to in the template.\n\n```typescript\n// app.component.ts\n\nimport { Component } from \"@angular/core\";\n\n@Component({\n  selector: \"app-root\",\n  templateUrl: \"./app.component.html\",\n  styleUrls: [\"./app.component.css\"],\n})\nexport class AppComponent {\n  // The 'username' property is bound to the input value using [(ngModel)]\n  username: string = \"\";\n}\n```\n\n#### Property Binding + Event Binding\n\nTwo-way data binding in Angular is a combination of property binding and event binding. It allows data to flow in both directions: from the component class to the view template (property binding) and from the view template to the component class (event binding). This is often used with [(ngModel)], which is a built-in directive in Angular.\n\nHere's an example demonstrating two-way data binding:\n\n```typescript\nexport class AppComponent {\n  // Initial value for the dynamicName\n  dynamicName: string = \"Not entered name\";\n\n  // Method to be called on input change\n  onNameChange(newName: string): void {\n    // Update dynamicName with the new value\n    this.dynamicName = newName;\n  }\n}\n```\n\n```html\n\u003c!-- Input tag with event binding for input event --\u003e\n\u003c!-- one way\n\u003cinput\n  placeholder=\"Enter your name\"\n  (input)=\"onNameChange($event.target.value)\"\n/\u003e --\u003e\n\n\u003c!-- Or the other --\u003e\n\u003cinput placeholder=\"Enter your name\" [(ngModel)]=\"dynamicName\" /\u003e\n\n\u003c!-- Paragraph with string interpolation --\u003e\n\u003cp\u003e{{ dynamicName }}\u003c/p\u003e\n```\n\n[(ngModel)]=\"dynamicName\" is Angular's two-way data binding syntax. It binds the value of the input element to the dynamicName property in the component class.\n\nAs the user types in the input field, the dynamicName property is updated automatically, and the paragraph below reflects the changes instantly.\n\nTwo-way data binding is a powerful feature in Angular as it simplifies the synchronization of data between the component and the view. It enhances the developer experience by reducing the need for explicit event handling for input changes. However, it's essential to note that for two-way data binding to work, you need to import the FormsModule from @angular/forms in your Angular module.\n\n## Angular Directives\n\nIn Angular, directives are a category of functionalities that allow you to extend the behavior of HTML elements or create reusable components. They are markers on a DOM element that tell Angular to do something to that element or its content. Angular provides several built-in directives, and you can also create custom directives.\n\n1. Component Directives:\n\nComponent: The most common type of directive. It allows you to create reusable, encapsulated components with their own logic, templates, and styles. Components are the building blocks of Angular applications.\n\n2.  Structural Directives:\n\n    - \\*ngFor\n      ngFor is a structural directive in Angular that is used for rendering a template for each item in a collection. It's commonly used for iterating over arrays or lists to generate dynamic content in the view.\n\n    - Example:\n      Simple\n\n    ```html\n    \u003cdiv *ngFor=\"let fruit of ['Apple', 'Mango', 'orange', 'grapes']\"\u003e\n      \u003cp\u003eFruit name: {{ fruit }}\u003c/p\u003e\n    \u003c/div\u003e\n    ```\n\n    TypeScript + HTML\n\n    ```typescript\n    export class AppComponent {\n      // Initial value for the dynamicName\n      listOfFruits: string[] = [\"Apple\", \"Mango\", \"orange\", \"grapes\"];\n    }\n    ```\n\n    ```html\n    \u003cdiv *ngFor=\"let fruit of listOfFruits\"\u003e\n      \u003cp\u003eFruit name: {{ fruit }}\u003c/p\u003e\n    \u003c/div\u003e\n    ```\n\n    - *ngIf\n      *ngIf directive, it is a structural directive in Angular. This directive is used to conditionally render or remove elements from the DOM (Document Object Model) based on a certain expression's truthiness.\n\n      Here's a basic example of how you might use `*ngIf` in an Angular component\n\n      - Simple example\n\n      ```html\n      \u003cdiv *ngIf=\"isConditionTrue\"\u003e\n        This content will only be displayed if isConditionTrue is true.\n      \u003c/div\u003e\n      ```\n\n      You can also use \\*ngIf with an \"else\" clause:\n\n      ```html\n      \u003cdiv *ngIf=\"isConditionTrue; else elseBlock\"\u003e\n        This content will be displayed if isConditionTrue is true.\n      \u003c/div\u003e\n      \u003cng-template #elseBlock\u003e\n        This content will be displayed if isConditionTrue is false.\n      \u003c/ng-template\u003e\n      ```\n\n3.  Attribute Directives:\n\n    - [ngStyle]\n\n    The ngStyle directive in Angular is another structural directive that allows you to dynamically set inline styles for HTML elements based on expressions in your component. It gives you the flexibility to conditionally apply styles depending on certain conditions or dynamic data.\n\n        - Example:\n\n        ```html\n        \u003c!-- app.component.html --\u003e\n        \u003cdiv [ngStyle]=\"{ 'color': isConditionTrue ? 'green' : 'red' }\"\u003e\n        {{isConditionTrue ? 'True' : 'False'}}\n        \u003c/div\u003e\n        ```\n\n    - [ngClass]\n\n    The [ngClass] directive in Angular is used to conditionally apply CSS classes to HTML elements based on certain conditions or expressions. It provides a way to dynamically manage the classes of an element.\n\n        - Example:\n\n        ```html\n        \u003c!-- app.component.html --\u003e\n        \u003cbutton\n        [ngClass]=\"{ 'disabled-button': isButtonDisabled }\"\n        [disabled]=\"isButtonDisabled\"\n        \u003e\n        Click me\n        \u003c/button\u003e\n        ```\n\n        ```typescript\n        export class AppComponent {\n            isButtonDisabled: boolean = false;\n\n            // Some logic to determine when the button should be disabled\n            updateButtonState() {\n                // Example: Disable the button if a condition is met\n                this.isButtonDisabled = /* some condition */;\n            }\n        }\n\n    ```\n\n    In this example:\n\n    - If isButtonDisabled is true, the CSS class disabled-button will be applied to the button, providing a visual indication that it is disabled.\n    - The [disabled] attribute is bound to the isButtonDisabled variable, so if isButtonDisabled is true, the button will be disabled; otherwise, it will be enabled.\n\n    ```\n\n4.  Custom Directives:\n\nYou can create your own custom directives to encapsulate behavior and reuse it across your application.\n\n## Custom Property binding\n\n### Parent component to child component communication (use @Input() decorator)\n\n#### @Input() Decorator\n\n                    Custom property binding\n\nParent Component ---------------------------------------------------\u003e Child Compo\n@Input() decorator\n\nParent Compo\n\n```html\n\u003cparent *ngFor=\"let fruit of listOfFruits\" [fruit]=\"fruit\"\u003e \u003c/parent\u003e\n```\n\nChild Compo\n\n```typescript\nexport class ChildComponent {\n  // Initial value for the dynamicName\n  @input() fruit;\n}\n```\n\n### Child component to parent component communication (use @output())\n\nIn Angular, you can achieve communication from a child component to a parent component using the @Output() decorator along with an EventEmitter. This allows the child component to emit events that the parent component can listen to.\n\n- Example\n\nChild Component (child.component.ts)\n\n```typescript\nimport { Component, EventEmitter, Output } from \"@angular/core\";\n\n@Component({\n  selector: \"app-child\",\n  template: ` \u003cbutton (click)=\"sendMessage()\"\u003eSend Message to Parent\u003c/button\u003e `,\n})\nexport class ChildComponent {\n  @Output() messageEvent = new EventEmitter\u003cstring\u003e();\n\n  sendMessage() {\n    const message = \"Hello from the child component!\";\n    this.messageEvent.emit(message);\n  }\n}\n```\n\n- The @Output() decorator is used to create an EventEmitter named messageEvent. This EventEmitter will emit events that the parent component can subscribe to.\n- The sendMessage() method is triggered when the button is clicked. It emits a message using this.messageEvent.emit(message).\n\nParent Component (parent.component.ts)\n\n```typescript\nimport { Component } from \"@angular/core\";\n\n@Component({\n  selector: \"app-parent\",\n  template: `\n    \u003capp-child (messageEvent)=\"receiveMessage($event)\"\u003e\u003c/app-child\u003e\n    \u003cp\u003e{{ receivedMessage }}\u003c/p\u003e\n  `,\n})\nexport class ParentComponent {\n  receivedMessage: string = \"\";\n\n  receiveMessage(message: string) {\n    this.receivedMessage = message;\n  }\n}\n```\n\n- The ParentComponent listens for the (messageEvent) emitted by the ChildComponent.\n- When the event is received, the receiveMessage($event) method is called, which updates the receivedMessage property in the parent component.\n\n### Communication between non related components\n\n\u003cimg width=\"1437\" alt=\"Screenshot 2023-12-02 at 7 15 20 PM\" src=\"https://github.com/SahilK-027/Angular-Journey/assets/104154041/cfe6b846-0d42-47a6-87b2-e3a800ac7494\"\u003e\n\n\u003e **Note**\n\u003e We can achieve this by much simpler way using Services in Angular\n\n## Template reference variables\n\nTemplate reference variables in Angular allow you to create a reference to an element in the template and then use that reference in the component code. They are denoted by a hash symbol (#) followed by a name.\n\nTemplate reference variables in Angular allow you to create a reference to an element in the template and then use that reference in the component code. They are denoted by a hash symbol (#) followed by a name.\n\nHere's a basic example:\n\n```html\n\u003c!-- app.component.html --\u003e\n\u003cinput type=\"text\" #myInput /\u003e\n\u003cbutton (click)=\"logInputValue(myInput.value)\"\u003eLog Input Value\u003c/button\u003e\n```\n\nIn this example:\n\n- #myInput is a template reference variable assigned to the input element.\n- When the button is clicked, the (click) event triggers the logInputValue method in the component, passing the value of the input using myInput.value.\n\n## Components vs Directives\n\n| Feature              | Components                                                       | Directives                                  |\n| -------------------- | ---------------------------------------------------------------- | ------------------------------------------- |\n| **Definition**       | Represent a UI control or a view                                 | Extend the behavior of elements in the DOM  |\n| **Encapsulation**    | Have their own template, styles, and logic                       | Do not have their own template or styles    |\n| **Usage**            | Used as custom elements in templates                             | Used to change the behavior of elements     |\n| **Creation**         | Created using the `@Component` decorator                         | Created using the `@Directive` decorator    |\n| **Metadata**         | Use `@Component` metadata                                        | Use `@Directive` metadata                   |\n| **Selector**         | Identified by an HTML element selector                           | Identified by an attribute selector         |\n| **Template**         | Has its own template                                             | Can modify the template of the host element |\n| **Example**          | `\u003capp-example\u003e\u003c/app-example\u003e`                                    | `\u003cdiv appExample\u003e\u003c/div\u003e`                    |\n| **Controller/Class** | Has a class with properties and methods                          | Has a class with properties and methods     |\n| **Purpose**          | Encapsulate a behavior or feature                                | Add behavior or manipulate DOM elements     |\n| **Example Use Case** | Creating a login form component                                  | Creating a custom validation directive      |\n| **Two-Way Binding**  | Supports two-way data binding (via `ngModel`)                    | Typically used for one-way binding          |\n| **Lifecycle Hooks**  | Has a set of lifecycle hooks (e.g., `ngOnInit`, `ngOnChanges`)   | Can use lifecycle hooks but has fewer       |\n| **Communication**    | Can communicate with other components through services or events | Often used for DOM manipulation or styling  |\n\n## @ViewChild() in Angular\n\nThe ViewChild decorator is used to query and get a reference of the DOM element in the component. It returns the first matching element.\n\nApply the @ViewChild decorator to a property in your component class.\n\n```typescript\n@ViewChild(SomeComponent) someComponentRef: SomeComponent;\n```\n\n## ng-template\n\n```html\n\u003ch2\u003eLearn NG Template\u003c/h2\u003e\n\u003cng-template #myTemplate\u003e\n\u003ch3\u003eThis is a template\u003c/h3\u003e\n‹p›This is an example paragraph to understand ng-template\u003c/p\u003e\n\u003c/ng-template\u003e\n\n‹!--ngTemplate@Outlet Directive--›\n\u003cdiv *ngTemplateOutlet=\"myTemplate\"\u003e\u003c/₫iv\u003e I\n```\n\nIn this example, SomeComponent is the type of the child component you want to reference, and someComponentRef is the property that will hold the reference to the child component.\n\n## Lifecycle Hooks in Angular\n\nIn Angular, lifecycle hooks are methods that allow you to tap into the lifecycle of a component, directive, or service. These hooks provide points in the lifecycle where you can perform operations or respond to changes.\n\n### The change detection cycle\n\nIn Angular, change detection is a mechanism that ensures the view reflects the current state of the application data. The change detection cycle is the process by which Angular determines what changes have occurred in the application state and updates the view accordingly. It's an essential part of Angular's architecture to maintain a responsive and synchronized user interface.\n\n- When change detection occurs?\n  - Whenever the @input property of a component changes\n  - Whenever a DOM event happens. E.g. Click or Change\n  - Whenever a timer events happens using setTimeOut () OR setInterval().\n  - Whenever an HTTP request is made.\n\n#### ngOnChanges Lifecycle Hook:\n\nIn Angular, the ngOnChanges lifecycle hook is part of the lifecycle hooks that a component can implement. This hook is called whenever there is a change in the `input properties` of the component. It provides a way for the component to respond to changes in its input properties and take appropriate actions.\n\n- Ex.\n\n```typescript\nimport { Component, Input, OnChanges, SimpleChanges } from \"@angular/core\";\n\n@Component({\n  selector: \"app-example\",\n  template: \"\u003cp\u003e{{ inputData }}\u003c/p\u003e\",\n})\nexport class ExampleComponent implements OnChanges {\n  @Input() inputData: string;\n\n  ngOnChanges(changes: SimpleChanges): void {\n    if (changes.inputData) {\n      console.log(\"InputData changed:\", changes.inputData);\n      // Perform actions based on the changes to inputData\n    }\n  }\n}\n```\n\n#### ngOnInit Lifecycle Hook:\n\nThe ngOnInit lifecycle hook in Angular is a method that is called after the Angular component has been initialized. It is part of the Angular component lifecycle and provides a hook for developers to perform initialization logic for the component.\n\n-Example\n\n```typescript\nimport { Component, OnInit } from \"@angular/core\";\n\n@Component({\n  selector: \"app-example\",\n  template: \"\u003cp\u003e{{ message }}\u003c/p\u003e\",\n})\nexport class ExampleComponent implements OnInit {\n  message: string;\n\n  ngOnInit(): void {\n    this.message = \"Component initialized\";\n    // Perform other initialization tasks here\n  }\n}\n```\n\nIn the example above, the ngOnInit hook is used to set the message property of the component to 'Component initialized'. This is a simple example, but in a real-world scenario, you might use this hook to make HTTP requests, set up subscriptions, or perform other tasks necessary for the component's operation.\n\nThe ngOnInit hook is called once after the component is created, making it a suitable place for tasks that should happen only once during the component's lifecycle. Keep in mind that it is called after the constructor but before the ngOnChanges hook.\n\n#### ngDoCheck Lifecycle Hook:\n\nThe ngDoCheck lifecycle hook in Angular provides a mechanism for developers to implement custom change detection for a component. Unlike other lifecycle hooks, ngDoCheck is called during every change detection cycle, giving you an opportunity to check for changes and perform custom logic.\n\n-Example:\n\n```typescript\nimport { Component, DoCheck } from \"@angular/core\";\n\n@Component({\n  selector: \"app-example\",\n  template: \"\u003cp\u003e{{ data }}\u003c/p\u003e\",\n})\nexport class ExampleComponent implements DoCheck {\n  data: string = \"Initial Data\";\n\n  ngDoCheck(): void {\n    // Perform custom change detection logic\n    console.log(\"ngDoCheck triggered\");\n  }\n}\n```\n\nKeep in mind that using ngDoCheck requires careful consideration, as it is called frequently. Overusing or performing heavy operations in this hook can have performance implications. It is often used in conjunction with the ChangeDetectorRef service to manually trigger change detection when needed.\n\nTypically, for most scenarios, Angular's default change detection is sufficient. However, ngDoCheck provides a way to implement custom change detection logic when necessary.\n\n### Lifecycle hooks sequence\n\n\u003cdiv align=\"center\"\u003e\n\u003cimg width=\"472\" alt=\"Screenshot 2023-12-03 at 11 02 00 AM\" src=\"https://github.com/SahilK-027/Angular-Journey/assets/104154041/ecf440e1-02d5-4092-915b-27641dcc8161\"\u003e\n\u003c/div\u003e\n\n## Services\n\nIn Angular, services are a way to organize and share code across components. They are singleton objects that can be injected into components, directives, or other services to provide functionality that is independent of any particular component. Let's explore some real-life use cases for Angular services:\n\n1. Data Sharing and Communication:\n\n- Use Case: Imagine you have a shopping cart component and a product list component. When a user adds a product to the cart, you need a way to update the cart information in real-time and reflect those changes in the product list.\n- Service Role: You can create a CartService that holds the cart data and provides methods for updating and retrieving the cart information. Both the shopping cart component and the product list component can inject and use this service to communicate and share data.\n\n2. HTTP Requests and API Integration:\n\n- Use Case: When you need to interact with a backend API to fetch or send data, you don't want to handle HTTP requests directly in your components. You want a centralized service to manage API calls.\n- Service Role: Create an ApiService that encapsulates the HTTP requests. Components can then inject and use this service to make API calls, and the service can handle error handling, request/response transformations, and other related tasks.\n\n3. User Authentication:\n\n- Use Case: Implementing user authentication involves handling login, logout, and checking the user's authentication status across multiple components.\n- Service Role: Create an AuthService that manages user authentication state. Components can use methods like login, logout, and isLoggedIn provided by this service. The service can also emit events when the authentication state changes.\n\n4. Caching and State Management:\n\n- Use Case: Suppose you have an application that fetches a large dataset from the server, and you want to cache this data locally to improve performance and reduce redundant server calls.\n- Service Role: Create a CacheService that stores and retrieves data. Components can use this service to check if data is already available locally before making a new request to the server. This helps in optimizing the application's performance.\n\n5. Global Event Handling:\n\n- Use Case: You might need a way for components to communicate indirectly, for example, to trigger a specific action when a user interacts with one component and have another component respond to that action.\n- Service Role: Create an EventService that allows components to publish and subscribe to events. Components can use this service to announce events, and other components interested in those events can subscribe to them.\n\nBelow is a simple example of an Angular service that handles click events and logs a message to the console. In this example, we won't use dependency injection, and the service will be a plain JavaScript object.\n\n```typescript\n// subscribe-event.service.ts\n\nexport class SubscribeService = {\n  onSubscribeClick(){\n    console.log('Thank you for subscription');\n  }\n};\n```\n\nThis service is a simple JavaScript object (SubscribeService) iyt contains onSubscribeClick method to log a message to the console whenever a click occurs.\n\nYou can use this service in your components like this:\n\n```typescript\n// example.component.ts\n\nimport { SubscribeService } from \"./click-event.service\";\n\nexport class ExampleComponent {\n  onSubscribeClick() {\n    let subService = new SubscribeService();\n    subService.onSubscribeClick();\n  }\n}\n```\n\nIn your template:\n\n```html\n\u003c!-- example.component.html --\u003e\n\u003cbutton (click)=\"onSubscribeClick()\"\u003eClick me\u003c/button\u003e\n```\n\nNote: This example is intentionally simple and doesn't follow Angular's recommended practices for creating services using dependency injection. In a real Angular application, you would typically use Angular's dependency injection system to create services for better maintainability, testability, and flexibility.\n\n## Disadvantages of using simple Services \u0026 (Why to use Dependency Injection?)\n\n- Without dependency injection, a class (component) is tightly coupled with its dependency (service). This makes a class non-flexible. Any change in dependency forces us to change the class implementation.\n\n- It makes testing of class difficult. Because if the dependency changes, the class has to change. And when the class changes, the unit test mock code also has to change.\n\n- How to do the same above thing using Dependency Injection?\n\nYou can use the service in your components like this:\n\n```typescript\n// example.component.ts\n\nimport { SubscribeService } from \"./click-event.service\";\n\n@Component({\n  selector: \"\",\n  templateUrl: \"\",\n\n  // What to provide?\n  providers: [SubscribeService],\n})\nexport class ExampleComponent {\n  // How to provide dependency\n  constructor(private subService: SubscribeService) {}\n  onSubscribeClick() {\n    this.subService.onSubscribeClick();\n  }\n}\n```\n\n# Angular testing with Jasmine Framework\n\nJasmine is used to write the actual test cases for your Angular components, services, and other code.\n\nKarma is responsible for running these tests in a controlled environment, such as real browsers or headless browsers, and reporting the results.\n\nIn the context of testing, a \"specification\" and a \"test suite\" are terms often associated with testing frameworks like Jasmine. Let's define each term:\n\n## Specification\n\nA specification refers to a single unit test or test case that describes a specific behavior or functionality of your code. A specification is typically defined using the it function in Jasmine.\n\n```typescript\ndescribe(\"MyComponent\", () =\u003e {\n  // It block represents a specification\n  it(\"should do something when a condition is met\", () =\u003e {});\n\n  it(\"should handle another scenario correctly\", () =\u003e {});\n});\n```\n\n## Test Suite\n\nA test suite is a collection of related test specifications or test cases. It is created using the describe function in Jasmine. A test suite helps organize and group related tests, making it easier to manage and run them.\n\n```typescript\n// Suit 1\ndescribe(\"MyComponent\", () =\u003e {\n  it(\"should do something when a condition is met\", () =\u003e {\n    // Test code goes here\n  });\n\n  it(\"should handle another scenario correctly\", () =\u003e {\n    // Test code goes here\n  });\n});\n\n// Suit 2\ndescribe(\"AnotherComponent\", () =\u003e {\n  it(\"should have a default value\", () =\u003e {\n    // Test code goes here\n  });\n\n  it(\"should handle a specific event\", () =\u003e {\n    // Test code goes here\n  });\n});\n```\n\nNote: How to create a component without spec file\n\n```bash\nng g c Component --skip-tests\n```\n\n## Simple Test In Jasmine\n\n```typescript\nimport { Injectable } from \"@angular/core\";\n\n@Injectable({\n  providedIn: \"root\",\n})\nexport class CalcService {\n  multiply(a: number, b: number): number {\n    return a * b;\n  }\n}\n```\n\n```typescript\ndescribe(\"Testing CalcService\", () =\u003e {\n  it(\"Should correctly multiply two numbers\", () =\u003e {\n    const calc = new CalcService();\n    const result = calc.multiply(3, 4);\n    expect(result).toBe(3 * 4);\n  });\n});\n```\n\n## spyOn\n\nIn Jasmine, the `spyOn` method is used to create spies, which are a way to mock or `spy on the behavior of functions, methods, or properties in your code` during testing. Spies are particularly useful for verifying that certain functions are called, checking the number of times they are called, and capturing the arguments passed to them. In the context of Angular testing, spyOn is commonly used with services, component methods, and external dependencies.\n\n- Syntax:\n\n```typescript\nspyOn(object, methodName);\n```\n\nobject: The object that contains the method you want to spy on.\nmethodName: The name of the method you want to spy on.\n\nChecking Method Arguments:\n\nUse `toHaveBeenCalledWith` to verify that a method was called with specific arguments.\n\nAs spyOn takes two arguments one for object and other for method, for passing object we need to instantiate it and while instantiating the object the constructor is called automatically. So, to avoid calling the constructor we must avoid creating the actual instance of the object to pass to the spyOn method. How can we do that?\n\nUsing `jasmine.createSpyObj(\"service/component\", [\"method\"]);`\n\n## BeforeEach in jasmine\n\nIn Jasmine, beforeEach is a function provided by the testing framework to set up preconditions or shared state before each test spec (it block) is executed. This is particularly useful for reducing redundancy in your test suite and ensuring a consistent starting point for each test.\n\n```typescript\ndescribe(\"My test suite\", () =\u003e {\n  let sharedVariable;\n\n  // beforeEach is used to set up preconditions before each it block\n  beforeEach(() =\u003e {\n    // Initialization or setup code goes here\n    sharedVariable = 10;\n  });\n\n  it(\"should do something\", () =\u003e {\n    // Test code that uses the sharedVariable\n    expect(sharedVariable).toBe(10);\n  });\n\n  it(\"should do something else\", () =\u003e {\n    // Test code that also uses the sharedVariable\n    sharedVariable = 20;\n    expect(sharedVariable).toBe(20);\n  });\n});\n```\n\nYou can use beforeEach to perform various setup tasks, such as initializing variables, creating objects, or setting up a test environment. It ensures that the specified code is executed before each test in the suite.\n\n`TestBud` : TestBed is a utility in Angular's testing infrastructure that is used to configure and create instances of components, services, and other Angular elements within a testing environment. It provides a testing module environment where you can configure the dependencies and settings for testing Angular components, services, and directives.\n\n```typescript\nTestBed.configureTestingModule({\n  declarations: [MyComponent],\n  providers: [MyService],\n});\n```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsahilk-027%2Fangular-journey","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fsahilk-027%2Fangular-journey","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fsahilk-027%2Fangular-journey/lists"}