Chuyển đến nội dung chính

Angular 22: Tìm hiểu Standalone Components – Từ NgModule đến kiến trúc hiện đại

1. Giới thiệu

Nếu đã từng làm việc với Angular phiên bản cũ, bạn có thể quen thuộc với việc phải tạo một NgModule để khai báo các component, directive và pipe trước khi sử dụng chúng.

Ví dụ, khi tạo một component mới, chúng ta thường phải khai báo nó trong declarations của một NgModule.

Đây là cách tổ chức ứng dụng Angular truyền thống. Tuy nhiên, từ Angular 14, Angular đã giới thiệu một cách tiếp cận mới mang tên Standalone Components.

Standalone giúp component có thể tự quản lý các dependency cần thiết cho template của mình mà không cần phải khai báo trong một NgModule.

Đến Angular 19, Standalone đã trở thành mặc định. Vì vậy, khi tạo một project mới bằng Angular 22, chúng ta có thể phát triển ứng dụng mà không cần tự tạo AppModule như trước đây.

Trong bài viết này, chúng ta sẽ tìm hiểu:

  • Standalone Components là gì?
  • Vì sao Angular chuyển sang Standalone?
  • Tạo project Angular 22.
  • Xây dựng một Homepage sử dụng Standalone Components.
  • Tạo một component theo cách truyền thống với NgModule.
  • So sánh hai cách tiếp cận.

2. Standalone Components là gì?

Trong Angular, Component là đơn vị cơ bản để xây dựng giao diện người dùng. Mỗi component thường bao gồm:

  • TypeScript: xử lý logic và dữ liệu.
  • HTML: định nghĩa giao diện.
  • SCSS/CSS: định nghĩa giao diện trình bày.

Trước Angular 14, một component thông thường phải thuộc về một NgModule. NgModule chịu trách nhiệm khai báo và quản lý các component, directive, pipe liên quan.

Ví dụ kiến trúc truyền thống:

flowchart TD
    A["AppModule"] --> B["AppComponent"]
    A --> C["HomeComponent"]
    A --> D["HeaderComponent"]
    A --> E["FooterComponent"]
    style A fill:#dbeafe,stroke:#2563eb

Với Standalone Components, mỗi component có thể tự khai báo dependency của mình thông qua thuộc tính imports trong @Component.

Ví dụ:

import { Component } from '@angular/core';

@Component({
  selector: 'app-home',
  imports: [],
  templateUrl: './home.html',
  styleUrl: './home.scss'
})
export class HomeComponent {
}

Bạn có thể nhận thấy component không cần khai báo trong một NgModule nào cả.

Lưu ý về lịch sử:

  • Angular 14: giới thiệu Standalone Components.
  • Angular 15: Standalone Components trở thành stable.
  • Angular 19: Standalone trở thành mặc định cho component, directive và pipe.
  • Angular 22: tiếp tục sử dụng Standalone làm cách tiếp cận mặc định cho ứng dụng mới.

Điều đó có nghĩa là khi sử dụng Angular 22, chúng ta không cần khai báo standalone: true trong decorator nữa. Nếu muốn tạo component theo cách cũ, chúng ta phải khai báo rõ standalone: false.

3. Standalone Components có lợi thế gì?

3.1. Giảm sự phụ thuộc vào NgModule

Trong kiến trúc truyền thống, khi tạo một component mới, chúng ta thường phải thực hiện thêm bước khai báo trong NgModule.

Ví dụ:

@NgModule({
  declarations: [
    HomeComponent,
    HeaderComponent,
    FooterComponent
  ],
  imports: [
    CommonModule
  ]
})
export class HomeModule {
}

Với Standalone, component có thể được sử dụng trực tiếp mà không cần bước khai báo này.

3.2. Dependency rõ ràng hơn

Một component Standalone khai báo trực tiếp những component, directive hoặc pipe mà nó sử dụng trong template.

Ví dụ:

@Component({
  selector: 'app-home',
  imports: [
    HeaderComponent,
    FooterComponent,
    ReadingStatsComponent
  ],
  templateUrl: './home.html'
})
export class HomeComponent {
}

Khi đọc component, chúng ta có thể biết ngay nó đang phụ thuộc vào những thành phần nào.

3.3. Hỗ trợ Lazy Loading

Standalone kết hợp rất tốt với Angular Router. Chúng ta có thể tải một component khi người dùng truy cập vào route tương ứng.

import { Routes } from '@angular/router';

export const routes: Routes = [
  {
    path: 'dashboard',
    loadComponent: () =>
      import('./pages/dashboard/dashboard')
        .then(m => m.DashboardComponent)
  },
  {
    path: 'books',
    loadComponent: () =>
      import('./pages/books/books')
        .then(m => m.BooksComponent)
  }
];

Thay vì phải tải tất cả giao diện ngay từ đầu, Angular có thể tải component theo nhu cầu.

Lưu ý: Lazy Loading không phải chỉ Standalone mới hỗ trợ. NgModule cũng hỗ trợ Lazy Loading thông qua loadChildren. Điểm thuận lợi của Standalone là có thể tải trực tiếp một component bằng loadComponent.

3.4. Dễ tổ chức và tái sử dụng

Mỗi component có thể hoạt động độc lập và được import vào nhiều component khác nhau.

Điều này giúp việc chia nhỏ giao diện, phát triển theo feature và bảo trì ứng dụng trở nên thuận tiện hơn.

4. Tạo project Angular 22

4.1. Kiểm tra môi trường

Trước tiên, chúng ta cần cài đặt Node.js và Angular CLI.

Kiểm tra phiên bản Node.js:

node -v
npm -v

Tham khảo yêu cầu Node.js hiện hành trong tài liệu Angular 22 trước khi cài đặt. Tài liệu cài đặt Angular hiện yêu cầu Node.js 22.22.3 trở lên.

Cài Angular CLI phiên bản 22:

npm install -g @angular/cli@22

Kiểm tra Angular CLI:

ng version

4.2. Khởi tạo project

Chúng ta sẽ xây dựng một ứng dụng nhỏ có tên ReadingDashboard, dùng để theo dõi mục tiêu đọc sách.

ng new reading-dashboard --style=scss

Angular CLI sẽ hỏi một số tùy chọn khi tạo project. Chúng ta có thể chọn cấu hình mặc định, sử dụng Standalone và không cần bật SSR cho bài thực hành này.

Sau khi tạo project thành công:

cd reading-dashboard
ng serve --open

Trình duyệt sẽ mở ứng dụng tại:

http://localhost:4200

4.3. Cấu trúc project

Với cấu hình Angular CLI hiện đại, cấu trúc thư mục có thể trông như sau:

reading-dashboard/
├── public/
├── src/
│   ├── app/
│   │   ├── app.config.ts
│   │   ├── app.routes.ts
│   │   ├── app.ts
│   │   ├── app.html
│   │   └── app.scss
│   ├── index.html
│   ├── main.ts
│   └── styles.scss
├── angular.json
├── package.json
└── tsconfig.json

Một điểm cần lưu ý: Angular CLI phiên bản mới có thể sử dụng cách đặt tên file ngắn như app.ts, thay vì app.component.ts như các phiên bản hoặc cấu hình cũ.

Đây chỉ là sự khác biệt về quy ước đặt tên file, không làm thay đổi bản chất của Component.

5. Xây dựng Homepage với Standalone Components

🧭 Tư duy cấu trúc luồng chạy: Index → App → Home → Sub-components

Trước khi tạo code, hãy làm rõ một thắc mắc phổ biến: "Một trang Homepage trong Angular sẽ chạy và phân rã cấu trúc như thế nào?"

Câu trả lời là một luồng khởi tạo và phân cấp Component (Component Tree) gồm 4 tầng:

  1. Tầng 1: index.html (HTML Shell)

    Trình duyệt nạp file index.html, chứa thẻ gốc <app-root></app-root>. Đây là vị trí Angular sẽ render Root Component vào DOM.

  2. Tầng 2: AppComponent (Root Layout)

    Angular khởi tạo AppComponent thông qua bootstrapApplication(AppComponent) trong main.ts.

    Với cấu hình selector: 'app-root', Angular xác định vị trí render component tương ứng trong index.html.

    Đây là nơi quản lý bộ khung toàn cục của ứng dụng như Header, Footer và <router-outlet /> để hiển thị các trang theo URL.

  3. Tầng 3: HomePageComponent (Page Component)

    Đây là component đại diện cho toàn bộ nội dung trang chủ.

    Nếu sử dụng Angular Router, khi người dùng truy cập URL trang chủ, Router sẽ render HomePageComponent thông qua <router-outlet /> trong AppComponent.

    Nếu chưa sử dụng Router, AppComponent cũng có thể import và gọi trực tiếp <app-home-page />.

  4. Tầng 4: Sub-components (Feature Blocks)

    Để tránh HomePageComponent trở nên quá lớn, chúng ta chia giao diện thành những component nhỏ, độc lập theo chức năng:

    • ReadingStatsComponent: Hiển thị thống kê số liệu.
    • WeeklyGoalComponent: Hiển thị tiến độ mục tiêu.

    HomePageComponent đóng vai trò điều phối bố cục, khai báo các component con trong mảng imports: [...] và sử dụng selector tương ứng trong template.

📌 Kết luận: Luồng khởi tạo và hiển thị

index.html → main.ts → AppComponent → Angular Router → HomePageComponent → Sub-components.

Lưu ý: Angular Router là thành phần tùy chọn. Nếu ứng dụng không sử dụng Router, Root Component có thể gọi trực tiếp Page Component.

Chúng ta sẽ xây dựng một trang Personal Reading Dashboard với những chức năng cơ bản:

  • Hiển thị tổng số sách đã đọc.
  • Hiển thị số sách đang đọc.
  • Theo dõi mục tiêu đọc sách trong tuần.
  • Hiển thị danh sách sách đang đọc.

Giao diện sẽ được chia thành các component nhỏ để dễ quản lý.

5.1. Thiết kế component tree

flowchart TD
    A["AppComponent"] --> B["HomePageComponent"]
    B --> C["ReadingStatsComponent"]
    B --> D["WeeklyGoalComponent"]
    B --> E["Book List"]
    B --> F["LegacyNoticeComponent"]
    E --> G["Book Item"]
    style A fill:#dbeafe,stroke:#2563eb
    style B fill:#dcfce7,stroke:#16a34a

Trong ví dụ này, HomePageComponent sẽ là component điều phối giao diện. Các component con chịu trách nhiệm hiển thị từng phần nội dung.

5.2. Tạo các component

Chúng ta đứng tại thư mục gốc của project Angular và chạy các lệnh:

ng generate component pages/home-page
ng generate component components/reading-stats
ng generate component components/weekly-goal
Hoặc dùng câu lệnh rút gọn tạo Home page
ng g c pages/home
pages/home: Angular sẽ tự tạo một thư mục con src/app/pages/home chứa 4 file tương ứng (.ts, .html, .scss, .spec.ts).

Vì Angular 22 mặc định tạo Standalone Component nên chúng ta không cần thêm --standalone.

Ví dụ cấu trúc thư mục:

src/app/
├── components/
│   ├── reading-stats/
│   │   ├── reading-stats.ts
│   │   ├── reading-stats.html
│   │   └── reading-stats.scss
│   └── weekly-goal/
│       ├── weekly-goal.ts
│       ├── weekly-goal.html
│       └── weekly-goal.scss
├── pages/
│   └── home-page/
│       ├── home-page.html
│       ├── home-page.scss
│       ├── home-page.spec.ts
│       └── home-page.ts
├── app.ts
└── app.html

Tên file thực tế có thể khác nếu project sử dụng cấu hình naming convention khác.

5.3. Tạo ReadingStatsComponent

Component này chịu trách nhiệm hiển thị thống kê đọc sách.

reading-stats.ts

import { Component } from '@angular/core';

@Component({
  selector: 'app-reading-stats',
  imports: [],
  templateUrl: './reading-stats.html',
  styleUrl: './reading-stats.scss'
})
export class ReadingStatsComponent {
  totalBooks = 24;
  currentlyReading = 3;
  readingHours = 42;
}

reading-stats.html

<section>
  <h2>Reading Statistics</h2>

  <div>
    <h3>{{ totalBooks }}</h3>
    <p>Books Completed</p>
  </div>

  <div>
    <h3>{{ currentlyReading }}</h3>
    <p>Currently Reading</p>
  </div>

  <div>
    <h3>{{ readingHours }}</h3>
    <p>Reading Hours</p>
  </div>
</section>

Ở đây, component sử dụng dữ liệu nội bộ để hiển thị thống kê. Trong ứng dụng thực tế, dữ liệu có thể được truyền từ component cha hoặc lấy từ service/API.

5.4. Tạo WeeklyGoalComponent

Component này hiển thị tiến độ mục tiêu đọc sách hàng tuần.

weekly-goal.ts

import { Component } from '@angular/core';

@Component({
  selector: 'app-weekly-goal',
  imports: [],
  templateUrl: './weekly-goal.html',
  styleUrl: './weekly-goal.scss'
})
export class WeeklyGoalComponent {
  weeklyTarget = 5;
  booksRead = 3;

  get progress(): number {
    return Math.round(
      (this.booksRead / this.weeklyTarget) * 100
    );
  }
}

weekly-goal.html

<section>
  <h2>Weekly Reading Goal</h2>

  <p>
    {{ booksRead }} / {{ weeklyTarget }} books completed
  </p>

  <p>Progress: {{ progress }}%</p>

  <p>
    Keep going! You are making great progress.
  </p>
</section>

5.5. Tạo HomePageComponent

Đây là component quan trọng nhất trong ví dụ. Nó sẽ kết hợp các component con thành một trang hoàn chỉnh.

home-page.ts

import { Component, signal } from '@angular/core';
import { ReadingStatsComponent } from
  '../../components/reading-stats/reading-stats';
import { WeeklyGoalComponent } from
  '../../components/weekly-goal/weekly-goal';

interface Book {
  id: number;
  title: string;
  author: string;
  status: string;
}

@Component({
  selector: 'app-home-page',
  imports: [
    ReadingStatsComponent,
    WeeklyGoalComponent
  ],
  templateUrl: './home-page.html',
  styleUrl: './home-page.scss'
})
export class HomePageComponent {

  books = signal<Book[]>([
    {
      id: 1,
      title: 'Atomic Habits',
      author: 'James Clear',
      status: 'Reading'
    },
    {
      id: 2,
      title: 'Deep Work',
      author: 'Cal Newport',
      status: 'Reading'
    },
    {
      id: 3,
      title: 'The Psychology of Money',
      author: 'Morgan Housel',
      status: 'Reading'
    }
  ]);
}

home-page.html

<main>

  <header>
    <h1>My Reading Dashboard</h1>
    <p>Track your reading journey and build better habits.</p>
  </header>

  <app-reading-stats />

  <app-weekly-goal />

  <section>
    <h2>Currently Reading</h2>

    @for (book of books(); track book.id) {
      <article>
        <h3>{{ book.title }}</h3>
        <p>Author: {{ book.author }}</p>
        <p>Status: {{ book.status }}</p>
      </article>
    } @empty {
      <p>No books found.</p>
    }

  </section>

</main>

Chúng ta có thể thấy một số điểm đáng chú ý:

  • imports khai báo hai component con mà Homepage sử dụng.
  • signal() quản lý danh sách sách có thể thay đổi.
  • @for duyệt qua danh sách sách.
  • track book.id giúp Angular nhận diện từng phần tử trong danh sách.
  • @empty hiển thị nội dung khi danh sách không có dữ liệu.

Đây là cú pháp Control Flow hiện đại của Angular, không cần import CommonModule chỉ để sử dụng vòng lặp này.

5.6. Kết nối Homepage với AppComponent

Bây giờ chúng ta cần hiển thị Homepage trong component gốc của ứng dụng.

app.ts

import { Component } from '@angular/core';
import { HomePageComponent } from
  './pages/home-page/home-page';

@Component({
  selector: 'app-root',
  imports: [HomePageComponent],
  templateUrl: './app.html',
  styleUrl: './app.scss'
})
export class App {
}

app.html

<app-home-page />

Như vậy, chúng ta đã hoàn thành một Homepage được xây dựng từ nhiều Standalone Components.

5.7. Kết quả kiến trúc

flowchart TD
    A["App"] --> B["HomePage"]
    B --> C["ReadingStats"]
    B --> D["WeeklyGoal"]
    B --> E["Currently Reading"]
    E --> F["Book 1"]
    E --> G["Book 2"]
    E --> H["Book 3"]

Điểm quan trọng là mỗi component có thể được phát triển và kiểm thử tương đối độc lập. HomePage chỉ cần import những thành phần mà nó thực sự sử dụng.

6. Tạo một component thông thường với NgModule

Để hiểu rõ sự khác biệt giữa Standalone và cách tiếp cận truyền thống, chúng ta sẽ tạo thêm một component không phải Standalone.

Trong Angular 22, muốn tạo component theo cách cũ, chúng ta phải khai báo:

standalone: false

6.1. Tạo LegacyNoticeComponent

Chạy lệnh:

ng generate component legacy/legacy-notice --standalone=false

legacy-notice.ts

import { Component } from '@angular/core';

@Component({
  selector: 'app-legacy-notice',
  standalone: false,
  templateUrl: './legacy-notice.html',
  styleUrl: './legacy-notice.scss'
})
export class LegacyNoticeComponent {
  message = 'Welcome to the Reading Dashboard!';
}

legacy-notice.html

<section>
  <h2>Reading Reminder</h2>
  <p>{{ message }}</p>
</section>

Khác với Standalone Component, component này không thể được import trực tiếp vào imports của một Standalone Component.

Nó phải được khai báo trong một NgModule.

6.2. Tạo LegacyUiModule

Tạo file legacy-ui.module.ts trong thư mục legacy.

import { NgModule } from '@angular/core';
import { CommonModule } from '@angular/common';

import { LegacyNoticeComponent } from
  './legacy-notice/legacy-notice';

@NgModule({
  declarations: [
    LegacyNoticeComponent
  ],
  imports: [
    CommonModule
  ],
  exports: [
    LegacyNoticeComponent
  ]
})
export class LegacyUiModule {
}

Giải thích:

  • declarations: khai báo component không phải Standalone thuộc module này.
  • imports: import các module mà component trong module cần sử dụng.
  • exports: cho phép module khác sử dụng component được export.

6.3. Sử dụng component truyền thống trong Homepage

Điều thú vị là chúng ta vẫn có thể sử dụng component truyền thống trong một ứng dụng Standalone.

Chỉ cần import NgModule chứa component đó.

Cập nhật home-page.ts:

import { Component, signal } from '@angular/core';

import { ReadingStatsComponent } from
  '../../components/reading-stats/reading-stats';

import { WeeklyGoalComponent } from
  '../../components/weekly-goal/weekly-goal';

import { LegacyUiModule } from
  '../../legacy/legacy-ui.module';

@Component({
  selector: 'app-home-page',
  imports: [
    ReadingStatsComponent,
    WeeklyGoalComponent,
    LegacyUiModule
  ],
  templateUrl: './home-page.html',
  styleUrl: './home-page.scss'
})
export class HomePageComponent {
  // Giữ nguyên phần dữ liệu books
}

Sau đó thêm component vào home-page.html:

<main>

  <app-legacy-notice />

  <app-reading-stats />

  <app-weekly-goal />

  <!-- Các nội dung còn lại -->

</main>

Như vậy, ứng dụng Angular hiện đại vẫn có thể sử dụng lại các component cũ thông qua NgModule.

Đây là một điểm rất quan trọng khi làm việc với các dự án Angular đã tồn tại nhiều năm.

7. So sánh Standalone Component và NgModule Component

Đến đây, chúng ta đã thực hành cả hai cách tiếp cận.

Bảng dưới đây tổng hợp những điểm khác biệt chính:

Tiêu chí Standalone NgModule-based
standalone Mặc định true từ Angular 19 Phải khai báo false trong Angular 19+
NgModule Không bắt buộc Bắt buộc có module khai báo component
Dependency Khai báo trong imports của component Quản lý thông qua NgModule
Sử dụng component Import trực tiếp component Import NgModule chứa component
Lazy Loading Hỗ trợ loadComponent Thường dùng loadChildren
Phù hợp Ứng dụng mới Dự án legacy hoặc module-based

7.1. So sánh code trực tiếp

Cách 1: Standalone Component


@Component({
  selector: 'app-dashboard',
  imports: [
    ReadingStatsComponent,
    WeeklyGoalComponent
  ],
  templateUrl: './dashboard.html'
})
export class DashboardComponent {
}

Chúng ta chỉ cần import trực tiếp các component mà Dashboard sử dụng.

Cách 2: NgModule Component

@Component({
  selector: 'app-dashboard',
  standalone: false,
  templateUrl: './dashboard.html'
})
export class DashboardComponent {
}

Sau đó phải khai báo trong module:

@NgModule({
  declarations: [
    DashboardComponent
  ],
  imports: [
    CommonModule,
    ReadingModule
  ]
})
export class DashboardModule {
}

Nhìn vào hai ví dụ, chúng ta có thể thấy Standalone giảm bớt một lớp tổ chức trung gian và làm dependency rõ ràng hơn ở cấp component.

8. Standalone có làm ứng dụng chạy nhanh hơn không?

Đây là một câu hỏi khá phổ biến.

Câu trả lời là: Standalone không tự động làm ứng dụng nhanh hơn chỉ vì chúng ta không sử dụng NgModule.

Lợi thế lớn hơn nằm ở cách tổ chức code, dependency và khả năng phân chia ứng dụng.

Ví dụ, khi kết hợp Standalone với Lazy Loading:

flowchart TD
    A["Application Start"] --> B["Load Home Page"]
    B --> C{"User navigates?"}
    C -->|Books| D["Load Books Component"]
    C -->|Reports| E["Load Reports Component"]
    C -->|Settings| F["Load Settings Component"]

Angular có thể chỉ tải phần code cần thiết khi người dùng truy cập vào từng chức năng.

Điều này có thể giúp giảm lượng JavaScript cần tải ban đầu, tùy thuộc vào cách chúng ta tổ chức và build ứng dụng.

Vì vậy, nên xem Standalone là một cải tiến về kiến trúc và trải nghiệm phát triển, chứ không phải một giải pháp tăng performance tự động.

9. Khi nào nên sử dụng Standalone?

Với một project mới sử dụng Angular 22, chúng ta nên ưu tiên Standalone Components.

Một số nguyên tắc có thể áp dụng:

  • Sử dụng Standalone cho các component mới.
  • Chia giao diện thành các component nhỏ theo chức năng.
  • Khai báo dependency trực tiếp trong imports của component.
  • Sử dụng Angular Router và loadComponent khi phù hợp.
  • Sử dụng NgModule khi cần tích hợp các component hoặc thư viện legacy.
  • Không cần tạo NgModule chỉ để tuân theo thói quen từ các phiên bản Angular cũ.

Nếu đang làm việc với một ứng dụng Angular cũ, chúng ta cũng không cần chuyển đổi toàn bộ sang Standalone ngay lập tức. Angular hỗ trợ migration từng bước.

10. Tổng kết

Qua bài thực hành, chúng ta đã hiểu cách Standalone Components thay đổi cách tổ chức một ứng dụng Angular.

Trước đây, NgModule đóng vai trò trung tâm trong việc khai báo và quản lý component. Với Standalone, mỗi component có thể tự quản lý các dependency của mình.

Những điểm cần ghi nhớ:

  • Standalone được giới thiệu từ Angular 14, stable từ Angular 15.
  • Từ Angular 19, Standalone là mặc định.
  • Angular 22 tiếp tục ưu tiên kiến trúc Standalone.
  • Standalone Component có thể import trực tiếp các component, directive, pipe khác.
  • Component truyền thống vẫn có thể được sử dụng thông qua NgModule.
  • Hai cách tiếp cận có thể cùng tồn tại trong một ứng dụng.

Nếu bắt đầu một dự án Angular mới, hãy ưu tiên Standalone. Đây là cách tiếp cận đơn giản và phù hợp với hướng phát triển hiện đại của Angular.

11. Tài liệu tham khảo

Happy Coding!

Nhận xét

Bài đăng phổ biến từ blog này

[ASP.NET MVC] Authentication và Authorize

Một trong những vấn đề bảo mật cơ bản nhất là đảm bảo những người dùng hợp lệ truy cập vào hệ thống. ASP.NET đưa ra 2 khái niệm: Authentication và Authorize Authentication xác nhận bạn là ai. Ví dụ: Bạn có thể đăng nhập vào hệ thống bằng username và password hoặc bằng ssh. Authorization xác nhận những gì bạn có thể làm. Ví dụ: Bạn được phép truy cập vào website, đăng thông tin lên diễn đàn nhưng bạn không được phép truy cập vào trang mod và admin.

Tổng hợp một số kiến thức lập trình về Amibroker

Giới thiệu về Amibroker Amibroker theo developer Tomasz Janeczko được xây dựng dựa trên ngôn ngữ C. Vì vậy bộ code Amibroker Formula Language sử dụng có syntax khá tương đồng với C, ví dụ như câu lệnh #include để import hay cách gói các object, hàm trong các block {} và kết thúc câu lệnh bằng dấu “;”. AFL trong Amibroker là ngôn ngữ xử lý mảng (an array processing language). Nó hoạt động dựa trên các mảng (các dòng/vector) số liệu, khá giống với cách hoạt động của spreadsheet trên excel.

ASP.NET MVC: Cơ bản về Validation

Validation (chứng thực) là một tính năng quan trọng trong ASP.NET MVC và được phát triển trong một thời gian dài. Validation vắng mặt trong phiên bản đầu tiên của asp.net mvc và thật khó để tích hợp 1 framework validation của một bên thứ 3 vì không có khả năng mở rộng. ASP.NET MVC2 đã hỗ trợ framework validation do Microsoft phát triển, tên là Data Annotations. Và trong phiên bản 3, framework validation đã hỗ trợ tốt hơn việc xác thực phía máy khách, và đây là một xu hướng của việc phát triển ứng dụng web ngày nay.