Angular Guidline
Setup
-
Install Node.js and npm: Ensure you have Node.js version 14 or higher installed on your machine. You can download it from nodejs.org.
-
Create a new project directory: Open your terminal or command prompt and create a new directory for your Angular project.
mkdir my-angular-project
cd my-angular-project -
Install Angular CLI: Use npm to install the Angular CLI globally.
npm install -g @angular/cli -
Create a new Angular application: Run the following command to generate a new Angular application.
ng new my-angular-app -
Navigate into your project directory:
cd my-angular-app -
Serve the application to see it running locally.
ng serve -
Run the development server: This will start a local development server at
http://localhost:4200/, where you can view your Angular application. -
Develop and test your application: Use your preferred code editor to develop your Angular components, services, and other features. You can also use tools like Visual Studio Code or WebStorm for an enhanced coding experience.
-
Build and deploy the application: Once your application is ready, you can build it for production using:
ng build --prod
This will generate a build directory with optimized files suitable for deployment.
Additional Tips
-
Use Angular Material or Bootstrap: If you need more components and styles, consider integrating an Angular Material library or using Bootstrap.
-
Version Control: Use Git to manage your project files. Initialize a new repository and commit your changes as needed.
-
Linter and Formatter: Set up linting tools like ESLint and Prettier for consistent code formatting.
-
Testing: Use Angular's built-in testing utilities, along with Cypress or Jest for unit and integration tests.
-
Environment Variables: Consider using environment variables to manage sensitive information such as API keys or database URLs.
By following these steps, you should have a solid foundation to start building your Angular application.
-
simple, long‑term style guide you can apply across list/add/edit.
simple, long‑term style guide you can apply across list/add/edit.
Core Pattern (Recommended for your project)
- Use rxResource() for fetching data.
- Use signal() for form fields and UI state.
- Use computed() for derived state like loading.
- Use effect() only for side effects (snackbar, logging).
- Use lastValueFrom() (or firstValueFrom()) for mutations (add/update/delete) so you can await.
1. List Page Pattern
const listResource = rxResource({
stream: () => api.getContact()
});
const deleting = signal(false);
const loading = computed(() => listResource.isLoading() || deleting());
const showError = effect(() => {
const err = listResource.error();
if (err) snackbar.open(err.message, 'Close', { duration: 3000 });
});
2. Add Page Pattern
const firstName = signal('');
const lastName = signal('');
const phone = signal<number | null>(null);
const email = signal('');
const saving = signal(false);
async function onSave() {
saving.set(true);
await lastValueFrom(api.addContact({ firstName: firstName(), ... }));
saving.set(false);
router.navigate(['/doc/crud']);
}
3) Edit Page Pattern
const id = signal(route.snapshot.paramMap.get('id') ?? '');
const contactResource = rxResource({
params: id,
stream: ({ params }) => api.getContactId(params)
});
// keep form values synced with fetched data but editable
const firstName = linkedSignal(() => contactResource.value()?.firstName ?? '');
const lastName = linkedSignal(() => contactResource.value()?.lastName ?? '');
const phone = linkedSignal(() => contactResource.value()?.phoneNumber ?? '');
const email = linkedSignal(() => contactResource.value()?.email ?? '');
const saving = signal(false);
const loading = computed(() => contactResource.isLoading() || saving());
signal
A piece of reactive state. Read with signal() and write with signal.set(value).
computed
A derived signal that re-calculates automatically when dependencies change. Example: loading = computed(() => resource.isLoading() || saving()).
effect
Runs a side effect when its dependencies change. Example: showError runs when contactsResource.error() changes.
linkedSignal
A signal that syncs from a source (like a resource or input) but stays editable. In your edit form, it starts from fetched contact fields but can be edited by the user.
toSignal
Converts an Observable into a signal. Example pattern: const user = toSignal(api.getUser()). You import it in edit-contact but don’t use it yet.
rxResource
Wraps an Observable stream into a resource with built-in value(), error(), isLoading(), reload(). It’s ideal when you want declarative data fetching that “feels like” signals. Observable
RxJS stream of async values (HTTP, events, etc). They are lazy and don’t do work until subscribed. rxResource and lastValueFrom are both ways to subscribe.
Input form
onchange : run when an input's value changed and then commited