Tags are essentially labels or keywords that can help identify and organize the running of your playbooks. So if your are going to install a program in a section in your playbook you can give it a tag which can be any name to identify it. Then you can run the playbook with –tags. Tags can be named anything but you should add a tag to identify what that part of the playbook is doing.
Below is a example
sudo nano tags-install.yml
---
- hosts: webservers
become: true
tasks:
- name: install apache2 on Ubuntu
tags: always
apt:
name: apache2
state: latest
when: ansible_distribution == 'Ubuntu'
- hosts: fileservers
become: true
tasks:
- name: install samba on Centos
tags: samba,fileserver
dnf:
name: samba
state: latest
when: ansible_distribution == 'CentOS'
- hosts: dbservers
become: true
tasks:
- name: install vlc and apache2 Ubuntu
apt:
name:
- vlc
- apache2
state: latest
when: ansible_distribution == 'Ubuntu'
My inventory.ini file looks like this
[fileservers]
#centos
192.168.1.151
#Ubuntu
[webservers]
#ubuntu
192.168.1.128
[dbservers]
#ubuntu
192.168.1.130
[workstations]
#centos
192.168.1.150
Here we have three examples, in one tag: always means it will always run, ‘samba’ and ‘fileserver’ tags either can be used or both too, last one doesn’t have tag so it will be skipped if I use a tag in my playbook command.
ansible-playbook --list-tags tags-install.yml
ansible-playbook --tags fileserver tags-install.yml --ask-become-pass
ansible-playbook --tags "fileserver,samba" tags-install.yml --ask-become-pass
My outputs

It ignored the 192.168.1.130 which is a dbserver which in my playbook doesn’t have a tag.

This playbook I ran with two tags, but didn’t do anything because everything is already installed.

Below is the screen shot from the servers targeted (managed nodes) First command show it was NOT installed, then after the playbook ran it installed.


commands
#ubuntu
sudo apt list --installed | grep apache2
#centos
sudo dnf list --installed | grep samba