Showing posts with label Angular code reusability. Show all posts
Showing posts with label Angular code reusability. Show all posts

Saturday, November 8, 2025

🧩 Best Practices for Angular 16+ with .NET Core

 

🔹 1. Code Reusability in Angular

Reusable code saves time, reduces duplication, and improves maintainability.

✅ Best Practices:

a. Use Shared Modules

Create a dedicated SharedModule for commonly used components, directives, and pipes.

// shared/shared.module.ts import { NgModule } from '@angular/core'; import { CommonModule } from '@angular/common'; import { FormsModule } from '@angular/forms'; import { HighlightDirective } from './highlight.directive'; import { DateFormatPipe } from './date-format.pipe'; @NgModule({ declarations: [HighlightDirective, DateFormatPipe], imports: [CommonModule, FormsModule], exports: [CommonModule, FormsModule, HighlightDirective, DateFormatPipe] }) export class SharedModule {}

Then import it in feature modules:

@NgModule({ imports: [SharedModule], }) export class EmployeeModule {}

b. Reusable Components

Create generic UI components like modals, dropdowns, and tables.

// shared/components/confirm-dialog/confirm-dialog.component.ts @Component({ selector: 'app-confirm-dialog', template: ` <h3>{{title}}</h3> <p>{{message}}</p> <button (click)="onConfirm()">OK</button> <button (click)="onCancel()">Cancel</button> ` }) export class ConfirmDialogComponent { @Input() title = ''; @Input() message = ''; @Output() confirm = new EventEmitter<boolean>(); onConfirm() { this.confirm.emit(true); } onCancel() { this.confirm.emit(false); } }

🔹 2. Caching for Performance

Caching reduces API calls and improves responsiveness.

✅ Best Practices:

a. Use Angular HTTP Interceptors for Caching

// core/interceptors/cache.interceptor.ts @Injectable() export class CacheInterceptor implements HttpInterceptor { private cache = new Map<string, any>(); intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> { if (req.method !== 'GET') return next.handle(req); const cachedResponse = this.cache.get(req.url); if (cachedResponse) return of(cachedResponse); return next.handle(req).pipe( tap(event => { if (event instanceof HttpResponse) this.cache.set(req.url, event); }) ); } }

Add it in providers:

providers: [ { provide: HTTP_INTERCEPTORS, useClass: CacheInterceptor, multi: true } ]

b. Leverage Browser Storage

Use localStorage or IndexedDB to persist data.

localStorage.setItem('user', JSON.stringify(user)); const user = JSON.parse(localStorage.getItem('user')!);

🔹 3. Performance Improvements

✅ Best Practices:

a. Use OnPush Change Detection

For performance-sensitive components:

@Component({ selector: 'app-user-card', templateUrl: './user-card.component.html', changeDetection: ChangeDetectionStrategy.OnPush }) export class UserCardComponent { @Input() user!: User; }

b. Lazy Loading Modules

Split large apps into lazy-loaded modules.

// app-routing.module.ts const routes: Routes = [ { path: 'employee', loadChildren: () => import('./employee/employee.module').then(m => m.EmployeeModule) } ];

c. Use trackBy in ngFor

Reduces DOM re-rendering:

<tr *ngFor="let emp of employees; trackBy: trackById"> <td>{{emp.name}}</td> </tr>
trackById(index: number, item: any) { return item.id; }

d. Minimize API Calls

Use RxJS shareReplay() for shared observables:

employees$ = this.http.get<Employee[]>('/api/employees').pipe(shareReplay(1));

e. Server-Side Pagination & Filtering

Instead of loading all data:

// .NET Core API [HttpGet] public async Task<IActionResult> GetEmployees(int page = 1, int size = 10) { var data = await _context.Employees.Skip((page-1)*size).Take(size).ToListAsync(); return Ok(data); }

🔹 4. Security Best Practices

✅ a. JWT Authentication

Use short-lived JWT tokens for secure API calls.

.NET Core (Backend)

services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme) .AddJwtBearer(options => { options.TokenValidationParameters = new TokenValidationParameters { ValidateIssuer = true, ValidateAudience = true, ValidIssuer = Configuration["Jwt:Issuer"], ValidAudience = Configuration["Jwt:Audience"], ValidateLifetime = true, IssuerSigningKey = new SymmetricSecurityKey( Encoding.UTF8.GetBytes(Configuration["Jwt:Key"]) ) }; });

Angular (Frontend)

// core/interceptors/auth.interceptor.ts @Injectable() export class AuthInterceptor implements HttpInterceptor { intercept(req: HttpRequest<any>, next: HttpHandler) { const token = localStorage.getItem('token'); const cloned = req.clone({ setHeaders: { Authorization: `Bearer ${token}` } }); return next.handle(cloned); } }

✅ b. Sanitize User Input

Use Angular’s built-in sanitization:

this.safeHtml = this.sanitizer.bypassSecurityTrustHtml(userInput);

✅ c. Avoid Sensitive Data in Client Storage

Never store passwords or API keys in localStorage.

✅ d. Enable HTTPS and CORS Properly

app.UseHttpsRedirection(); app.UseCors(builder => builder.WithOrigins("https://your-angular-app.com") .AllowAnyHeader() .AllowAnyMethod());

🔹 5. Architecture Best Practices

✅ a. Organize Project Structure

/src /app /core /services /interceptors /shared /components /pipes /features /employee /products

✅ b. Use Interfaces and Models

export interface Employee { id: number; name: string; email: string; }

✅ c. Follow SOLID Principles

Keep components small and service-driven.


🔹 6. Example: Angular + .NET Core Integration

Angular Service

@Injectable({ providedIn: 'root' }) export class EmployeeService { private apiUrl = environment.apiBaseUrl + '/employees'; constructor(private http: HttpClient) {} getEmployees(page = 1, size = 10): Observable<Employee[]> { return this.http.get<Employee[]>(`${this.apiUrl}?page=${page}&size=${size}`); } }

.NET Core Controller

[ApiController] [Route("api/[controller]")] public class EmployeesController : ControllerBase { private readonly AppDbContext _context; public EmployeesController(AppDbContext context) => _context = context; [HttpGet] public async Task<IEnumerable<Employee>> GetEmployees(int page = 1, int size = 10) => await _context.Employees.Skip((page - 1) * size).Take(size).ToListAsync(); }

🔹 7. Tools and Optimization Tips

  • Angular CLI commands for performance:

    ng build --configuration production
  • Enable Ahead-of-Time (AOT) compilation

  • Use ngx-translate for i18n

  • Use Service Workers for offline caching (PWA)


✨ Conclusion

Building enterprise-grade apps using Angular 16+ and .NET Core requires balancing performance, maintainability, and security.
By following the above best practices — shared modules, lazy loading, caching, and JWT security — you can achieve high scalability and efficient app delivery.

Don't Copy

Protected by Copyscape Online Plagiarism Checker

Pages