Nguon: Microsoft Learn · .NET 8.0

Sử dụng Grunt trong ASP.NET Core

Nguồn: Use Grunt in ASP.NET Core

Grunt là một trình chạy tác vụ JavaScript (JavaScript task runner) tự động hóa việc minification script, biên dịch TypeScript, các công cụ kiểm tra chất lượng code "lint", CSS pre-processors, và hầu hết các tác vụ lặp đi lặp lại cần thiết để hỗ trợ phát triển client. Grunt được hỗ trợ đầy đủ trong Visual Studio.

Ví dụ này sử dụng một dự án ASP.NET Core rỗng làm điểm bắt đầu, để chỉ cách tự động hóa quy trình build client từ đầu.

Ví dụ hoàn chỉnh sẽ dọn sạch thư mục triển khai đích, kết hợp các file JavaScript, kiểm tra chất lượng code, nén nội dung file JavaScript và triển khai ra thư mục gốc của ứng dụng web. Chúng ta sẽ sử dụng các gói sau:

Chuẩn bị ứng dụng

Để bắt đầu, hãy thiết lập một ứng dụng web trống mới và thêm các file TypeScript mẫu. Các file TypeScript được tự động biên dịch thành JavaScript bằng cài đặt mặc định của Visual Studio và sẽ là nguyên liệu thô để xử lý bằng Grunt.

  1. Trong Visual Studio, tạo một ASP.NET Web Application mới.
  2. Trong hộp thoại New ASP.NET Project, chọn template Empty của ASP.NET Core và nhấn OK.
  3. Trong Solution Explorer, xem lại cấu trúc dự án. Thư mục \src bao gồm các node wwwrootDependencies trống.

!empty web solution

  1. Thêm thư mục mới tên TypeScript vào thư mục dự án.
  2. Trước khi thêm file, hãy đảm bảo Visual Studio có tùy chọn 'compile on save' (biên dịch khi lưu) cho file TypeScript được bật. Điều hướng đến Tools > Options > Text Editor > Typescript > Project:

!options setting auto compilation of TypeScript files

  1. Nhấp chuột phải vào thư mục TypeScript và chọn Add > New Item từ menu ngữ cảnh. Chọn mục JavaScript file và đặt tên file là Tastes.ts (lưu ý phần mở rộng \*.ts). Sao chép dòng code TypeScript dưới đây vào file (khi bạn lưu, một file Tastes.js mới sẽ xuất hiện với source JavaScript).

``typescript enum Tastes { Sweet, Sour, Salty, Bitter } ``

  1. Thêm file thứ hai vào thư mục TypeScript và đặt tên là Food.ts. Sao chép code dưới đây vào file.

```typescript class Food { constructor(name: string, calories: number) { this._name = name; this._calories = calories; }

private _name: string; get Name() { return this._name; }

private _calories: number; get Calories() { return this._calories; }

private _taste: Tastes; get Taste(): Tastes { return this._taste } set Taste(value: Tastes) { this._taste = value; } } ```

Cấu hình npm

Tiếp theo, cấu hình npm để tải xuống grunt và grunt-tasks.

  1. Trong Solution Explorer, nhấp chuột phải vào dự án và chọn Add > New Item từ menu ngữ cảnh. Chọn mục npm Configuration File, giữ tên mặc định package.json, và nhấn nút Add.
  2. Trong file package.json, bên trong dấu ngoặc nhọn của object devDependencies, nhập "grunt". Chọn grunt từ danh sách IntelliSense và nhấn Enter. Visual Studio sẽ đặt tên gói grunt trong dấu nháy và thêm dấu hai chấm. Ở bên phải dấu hai chấm, chọn phiên bản ổn định mới nhất của gói từ đầu danh sách IntelliSense (nhấn Ctrl-Space nếu IntelliSense không hiện).

!grunt Intellisense

> Lưu ý: npm sử dụng semantic versioning để tổ chức các dependency (phụ thuộc). Semantic versioning, còn được gọi là SemVer, xác định các gói với sơ đồ đánh số <major>.<minor>.<patch>. IntelliSense đơn giản hóa semantic versioning bằng cách chỉ hiển thị một vài lựa chọn phổ biến. Mục đầu tiên trong danh sách IntelliSense (0.4.5 trong ví dụ trên) được coi là phiên bản ổn định mới nhất. Ký hiệu dấu mũ (^) khớp với phiên bản major mới nhất và dấu ngã (~) khớp với phiên bản minor mới nhất.

  1. Thêm nhiều dependency hơn để tải các gói grunt-contrib-\ cho clean, jshint, concat, uglify, và watch* như trong ví dụ dưới đây. Các phiên bản không cần phải khớp với ví dụ.

``json "devDependencies": { "grunt": "0.4.5", "grunt-contrib-clean": "0.6.0", "grunt-contrib-jshint": "0.11.0", "grunt-contrib-concat": "0.5.1", "grunt-contrib-uglify": "0.8.0", "grunt-contrib-watch": "0.6.1" } ``

  1. Lưu file package.json.

Các gói cho mỗi mục devDependencies sẽ được tải xuống, cùng với các file mà mỗi gói yêu cầu. Bạn có thể tìm thấy các file gói trong thư mục node\_modules bằng cách bật nút Show All Files trong Solution Explorer.

!grunt node_modules

Lưu ý: Nếu cần, bạn có thể khôi phục các dependency thủ công trong Solution Explorer bằng cách nhấp chuột phải vào Dependencies\npm và chọn tùy chọn menu Restore Packages.

Cấu hình Grunt

Grunt được cấu hình bằng một file manifest (tệp kê khai) tên Gruntfile.js để định nghĩa, tải và đăng ký các tác vụ có thể chạy thủ công hoặc được cấu hình để chạy tự động dựa trên các sự kiện trong Visual Studio.

  1. Nhấp chuột phải vào dự án và chọn Add > New Item. Chọn template mục JavaScript File, đổi tên thành Gruntfile.js, và nhấn nút Add.
  2. Thêm code sau vào Gruntfile.js. Hàm initConfig đặt các tùy chọn cho mỗi gói, và phần còn lại của module tải và đăng ký các tác vụ.

``javascript module.exports = function (grunt) { grunt.initConfig({ }); }; ``

  1. Bên trong hàm initConfig, thêm các tùy chọn cho tác vụ clean như trong ví dụ Gruntfile.js dưới đây. Tác vụ clean chấp nhận một mảng các chuỗi thư mục. Tác vụ này xóa các file từ wwwroot/lib và xóa toàn bộ thư mục /temp.

``javascript module.exports = function (grunt) { grunt.initConfig({ clean: ["wwwroot/lib/*", "temp/"], }); }; ``

  1. Bên dưới hàm initConfig, thêm lời gọi đến grunt.loadNpmTasks. Điều này sẽ làm cho tác vụ có thể chạy từ Visual Studio.

``javascript grunt.loadNpmTasks("grunt-contrib-clean"); ``

  1. Lưu Gruntfile.js.
  2. Nhấp chuột phải vào Gruntfile.js và chọn Task Runner Explorer từ menu ngữ cảnh. Cửa sổ Task Runner Explorer sẽ mở ra.
  3. Xác minh rằng clean hiển thị dưới Tasks trong Task Runner Explorer.
  4. Nhấp chuột phải vào tác vụ clean và chọn Run từ menu ngữ cảnh. Một cửa sổ lệnh hiển thị tiến trình của tác vụ.
  5. Trong hàm initConfig, thêm một entry cho concat bằng code dưới đây.

Mảng thuộc tính src liệt kê các file cần kết hợp, theo thứ tự chúng nên được kết hợp. Thuộc tính dest gán đường dẫn đến file kết hợp được tạo ra.

``javascript concat: { all: { src: ['TypeScript/Tastes.js', 'TypeScript/Food.js'], dest: 'temp/combined.js' } }, ``

  1. Thêm tác vụ jshint bằng code dưới đây.

Tiện ích jshint code-quality được chạy trên mọi file JavaScript tìm thấy trong thư mục temp.

``javascript jshint: { files: ['temp/*.js'], options: { '-W069': false, } }, ``

> Lưu ý: Tùy chọn "-W069" là một lỗi do jshint tạo ra khi JavaScript sử dụng cú pháp dấu ngoặc vuông để gán thuộc tính thay vì ký hiệu chấm, Tastes["Sweet"] thay vì Tastes.Sweet. Tùy chọn này tắt cảnh báo để cho phép phần còn lại của quá trình tiếp tục.

  1. Thêm tác vụ uglify bằng code dưới đây.

Tác vụ minify file combined.js tìm thấy trong thư mục temp và tạo file kết quả trong wwwroot/lib theo quy ước đặt tên chuẩn <tên file>.min.js.

``javascript uglify: { all: { src: ['temp/combined.js'], dest: 'wwwroot/lib/combined.min.js' } }, ``

  1. Dưới lời gọi đến grunt.loadNpmTasks tải grunt-contrib-clean, hãy thêm lời gọi tương tự cho jshint, concat, và uglify bằng code dưới đây.

``javascript grunt.loadNpmTasks('grunt-contrib-jshint'); grunt.loadNpmTasks('grunt-contrib-concat'); grunt.loadNpmTasks('grunt-contrib-uglify'); ``

  1. Lưu Gruntfile.js.
  2. Lưu ý rằng danh sách Tasks của Task Runner Explorer bao gồm các tác vụ clean, concat, jshintuglify. Chạy từng tác vụ theo thứ tự và quan sát kết quả trong Solution Explorer. Mỗi tác vụ sẽ chạy không có lỗi.

Tác vụ concat tạo một file combined.js mới và đặt nó vào thư mục temp. Tác vụ jshint đơn giản chạy và không tạo ra output. Tác vụ uglify tạo một file combined.min.js mới và đặt nó vào wwwroot/lib.

Kết hợp tất cả lại

Sử dụng phương thức registerTask() của Grunt để chạy một loạt tác vụ theo một trình tự cụ thể. Ví dụ, để chạy các bước ví dụ trên theo thứ tự clean -> concat -> jshint -> uglify, thêm code dưới đây vào module. Code nên được thêm ở cùng cấp với các lời gọi loadNpmTasks(), bên ngoài initConfig.

javascript
grunt.registerTask("all", ['clean', 'concat', 'jshint', 'uglify']);

Tác vụ mới xuất hiện trong Task Runner Explorer dưới Alias Tasks. Bạn có thể nhấp chuột phải và chạy nó giống như các tác vụ khác. Tác vụ all sẽ chạy clean, concat, jshintuglify, theo thứ tự.

!alias grunt tasks

Theo dõi các thay đổi

Tác vụ watch theo dõi file và thư mục. watch kích hoạt các tác vụ tự động nếu phát hiện thay đổi. Thêm code dưới đây vào initConfig để theo dõi các thay đổi với file \*.js trong thư mục TypeScript. Nếu một file JavaScript bị thay đổi, watch sẽ chạy tác vụ all.

javascript
watch: {
  files: ["TypeScript/*.js"],
  tasks: ["all"]
}

Thêm lời gọi đến loadNpmTasks() để hiển thị tác vụ watch trong Task Runner Explorer.

javascript
grunt.loadNpmTasks('grunt-contrib-watch');

Nhấp chuột phải vào tác vụ watch trong Task Runner Explorer và chọn Run từ menu ngữ cảnh. Cửa sổ lệnh hiển thị tác vụ watch đang chạy sẽ hiển thị thông báo "Waiting…". Mở một trong các file TypeScript, thêm một khoảng trắng, sau đó lưu file. Điều này sẽ kích hoạt tác vụ watch và kích hoạt các tác vụ khác chạy theo thứ tự.

Liên kết đến các sự kiện Visual Studio

Trừ khi bạn muốn khởi động tác vụ thủ công mỗi lần làm việc trong Visual Studio, hãy liên kết các tác vụ với các sự kiện Before Build, After Build, Clean, và Project Open.

Liên kết watch để nó chạy mỗi khi Visual Studio mở. Trong Task Runner Explorer, nhấp chuột phải vào tác vụ watch và chọn Bindings > Project Open từ menu ngữ cảnh.

!bind a task to the project opening

Unload và reload dự án. Khi dự án tải lại, tác vụ watch bắt đầu chạy tự động.

Tóm tắt

Grunt là một trình chạy tác vụ mạnh mẽ có thể được sử dụng để tự động hóa hầu hết các tác vụ build client. Grunt tận dụng npm để cung cấp các gói và có tích hợp công cụ với Visual Studio. Task Runner Explorer của Visual Studio phát hiện các thay đổi đối với file cấu hình và cung cấp giao diện thuận tiện để chạy tác vụ, xem các tác vụ đang chạy và liên kết các tác vụ với các sự kiện Visual Studio.