• Categories
    Category
    {{ postCtrl.tags }}
    • {{ category.tag_type }}

      • {{tag.tag_name}}
      • View more
  • Categories
    Category
    {{ postCtrl.tags }}
    • {{ category.tag_type }}

      • {{tag.tag_name}}
      • View more
  • News
  • Tutorials
  • Forums
  • Tags
  • Users
Tutorial News Comments FAQ Related Articles

How to install LEMP Stack on Ubuntu 22.04

  • 00:49 lsb_release -a
  • 01:02 sudo apt update
  • 01:25 sudo apt install nginx
  • 02:22 sudo ufw allow "Nginx Full"
  • 02:47 sudo apt install mariadb-server
  • 03:23 sudo mysql_secure_installation
  • 04:09 mysql -u root -p
  • 04:30 sudo apt install php8.1-fpm php8.1-mysql php8.1-gd php8.1-bcmath php8.1-cli php8.1-curl php8.1-mbstring php 8.1-zip php8.1-opcache php8.1-xml
  • 05:06 php -v
  • 05:26 vim /etc/nginx/sites-enabled/default
  • 08:06 sudo nginx -t
  • 08:17 sudo systemctl restart nginx
  • 08:58 echo "" | sudo tee /var/www/html/test.php
{{postValue.id}}

How to install LEMP Stack on Ubuntu 22.04

Introduction

LEMP is an open-source web application stack utilized for developing web applications. The acronym LEMP stands for Linux Operating System (L), Nginx web server (E, pronounced as "engine-x"), MySQL database (M), and PHP scripting language (P). A LAMP stack, similarly, consists of a combination of four distinct software technologies that developers employ to create websites and web applications.

Procedure

Step 1: Check the OS version using the below command

root@linuxhelp:~# lsb_release -a
No LSB modules are available.
Distributor ID:	Ubuntu
Description:	Ubuntu 22.04.3 LTS
Release:	22.04
Codename:	jammy

Step 2: Update the package list using the below command

root@linuxhelp:~# sudo apt update
Hit:1 http://in.archive.ubuntu.com/ubuntu jammy InRelease
Get:2 http://in.archive.ubuntu.com/ubuntu jammy-updates InRelease [128 kB]
Get:3 http://security.ubuntu.com/ubuntu jammy-security InRelease [129 kB]
Get:4 http://in.archive.ubuntu.com/ubuntu jammy-backports InRelease [127 kB]
Get:5 http://in.archive.ubuntu.com/ubuntu jammy-updates/main i386 Packages [673 kB]
Get:19 http://security.ubuntu.com/ubuntu jammy-security/universe amd64 Packages [886 kB]                                                                                              
Get:20 http://security.ubuntu.com/ubuntu jammy-security/universe Translation-en [173 kB]                                                                                              
Fetched 14.7 MB in 7s (2,093 kB/s)                                                                                                                                                    
Reading package lists... 31%
Reading package lists... Done
Building dependency tree... Done
Reading state information... Done
339 packages can be upgraded. Run 'apt list --upgradable' to see them.

Step 3: Install Nginx using the below command

root@linuxhelp:~# sudo apt install nginx
Reading package lists... Done
Building dependency tree... Done
Reading state information... Done
The following packages were automatically installed and are no longer required:
  libflashrom1 libftdi1-2 libllvm13
Use 'sudo apt autoremove' to remove them.
The following additional packages will be installed:
  libnginx-mod-http-geoip2 libnginx-mod-http-image-filter libnginx-mod-http-xslt-filter libnginx-mod-mail libnginx-mod-stream libnginx-mod-stream-geoip2 nginx-common nginx-core
Suggested packages:
  fcgiwrap nginx-doc
The following NEW packages will be installed:
  libnginx-mod-http-geoip2 libnginx-mod-http-image-filter libnginx-mod-http-xslt-filter libnginx-mod-mail libnginx-mod-stream libnginx-mod-stream-geoip2 nginx nginx-common
  nginx-core
0 upgraded, 9 newly installed, 0 to remove and 339 not upgraded.
Need to get 697 kB of archives.
After this operation, 2,395 kB of additional disk space will be used.
Do you want to continue? [Y/n] y
Get:1 http://in.archive.ubuntu.com/ubuntu jammy-updates/main amd64 nginx-common all 1.18.0-6ubuntu14.4 [40.0 kB]
Get:2 http://in.archive.ubuntu.com/ubuntu jammy-updates/main amd64 libnginx-mod-http-geoip2 amd64 1.18.0-6ubuntu14.4 [11.9 kB]
Get:6 http://in.archive.ubuntu.com/ubuntu jammy-updates/main amd64 libnginx-mod-stream amd64 1.18.0-6ubuntu14.4 [72.9 kB]
Get:7 http://in.archive.ubuntu.com/ubuntu jammy-updates/main amd64 libnginx-mod-stream-geoip2 amd64 1.18.0-6ubuntu14.4 [10.1 kB]
Get:8 http://in.archive.ubuntu.com/ubuntu jammy-updates/main amd64 nginx-core amd64 1.18.0-6ubuntu14.4 [484 kB]
Get:9 http://in.archive.ubuntu.com/ubuntu jammy-updates/main amd64 nginx amd64 1.18.0-6ubuntu14.4 [3,872 B]
Fetched 697 kB in 2s (348 kB/s)
Preconfiguring packages ...
Selecting previously unselected package nginx-common.
(Reading database ... 203969 files and directories currently installed.)
Preparing to unpack .../0-nginx-common_1.18.0-6ubuntu14.4_all.deb ...
Unpacking nginx-common (1.18.0-6ubuntu14.4) ...
Selecting previously unselected package libnginx-mod-http-geoip2.
Preparing to unpack .../1-libnginx-mod-http-geoip2_1.18.0-6ubuntu14.4_amd64.deb ...
Unpacking libnginx-mod-http-geoip2 (1.18.0-6ubuntu14.4) ...
Selecting previously unselected package libnginx-mod-http-image-filter.
Unpacking nginx (1.18.0-6ubuntu14.4) ...
Setting up nginx-common (1.18.0-6ubuntu14.4) ...
Created symlink /etc/systemd/system/multi-user.target.wants/nginx.service → /lib/systemd/system/nginx.service.
Setting up libnginx-mod-http-xslt-filter (1.18.0-6ubuntu14.4) ...
Setting up libnginx-mod-http-geoip2 (1.18.0-6ubuntu14.4) ...
Setting up libnginx-mod-mail (1.18.0-6ubuntu14.4) ...
Setting up libnginx-mod-http-image-filter (1.18.0-6ubuntu14.4) ...
Setting up libnginx-mod-stream (1.18.0-6ubuntu14.4) ...
Setting up libnginx-mod-stream-geoip2 (1.18.0-6ubuntu14.4) ...
Setting up nginx-core (1.18.0-6ubuntu14.4) ...
 * Upgrading binary nginx                                                                                                                                                       [ OK ] 
Setting up nginx (1.18.0-6ubuntu14.4) ...
Processing triggers for man-db (2.10.2-1) ...
Processing triggers for ufw (0.36.1-4ubuntu0.1) ...

Step 4: Install MySQL using the below command

root@linuxhelp:~# sudo apt install mariadb-server
Reading package lists... Done
Building dependency tree... Done
Reading state information... Done
The following packages were automatically installed and are no longer required:
  libflashrom1 libftdi1-2 libllvm13
Use 'sudo apt autoremove' to remove them.
Suggested packages:
  gawk-doc libmldbm-perl libnet-daemon-perl libsql-statement-perl libipc-sharedcache-perl mailx mariadb-test
The following NEW packages will be installed:
  galera-4 gawk libcgi-fast-perl libcgi-pm-perl libconfig-inifiles-perl libdbd-mysql-perl libdbi-perl libfcgi-bin libfcgi-perl libfcgi0ldbl libhtml-template-perl libmariadb3
  libmysqlclient21 libsigsegv2 libsnappy1v5 libterm-readkey-perl mariadb-client-10.6 mariadb-client-core-10.6 mariadb-common mariadb-server mariadb-server-10.6
  mariadb-server-core-10.6 mysql-common socat
0 upgraded, 24 newly installed, 0 to remove and 339 not upgraded.
Need to get 18.7 MB of archives.
After this operation, 165 MB of additional disk space will be used.
Do you want to continue? [Y/n] y
Get:1 http://in.archive.ubuntu.com/ubuntu jammy/main amd64 libsigsegv2 amd64 2.13-1ubuntu3 [14.6 kB]
Get:2 http://in.archive.ubuntu.com/ubuntu jammy-updates/main amd64 gawk amd64 1:5.1.0-1ubuntu0.1 [447 kB]
Get:3 http://in.archive.ubuntu.com/ubuntu jammy/main amd64 mysql-common all 5.8+1.0.8 [7,212 B]
Get:4 http://in.archive.ubuntu.com/ubuntu jammy-updates/universe amd64 mariadb-common all 1:10.6.18-0ubuntu0.22.04.1 [16.5 kB]
Get:5 http://in.archive.ubuntu.com/ubuntu jammy/universe amd64 galera-4 amd64 26.4.9-1build1 [720 kB]
Get:22 http://in.archive.ubuntu.com/ubuntu jammy/main amd64 libhtml-template-perl all 2.97-1.1 [59.1 kB]
Get:23 http://in.archive.ubuntu.com/ubuntu jammy/main amd64 libterm-readkey-perl amd64 2.38-1build4 [25.2 kB]
Get:24 http://in.archive.ubuntu.com/ubuntu jammy-updates/universe amd64 mariadb-server all 1:10.6.18-0ubuntu0.22.04.1 [11.8 kB]
Fetched 18.7 MB in 5s (3,885 kB/s)          
Setting up libsnappy1v5:amd64 (1.1.8-1build3) ...
Setting up socat (1.7.4.1-3ubuntu4) ...
Setting up libmariadb3:amd64 (1:10.6.18-0ubuntu0.22.04.1) ...
Setting up libfcgi-perl:amd64 (0.82+ds-1build1) ...
Setting up libterm-readkey-perl (2.38-1build4) ...
Setting up libdbi-perl:amd64 (1.643-3build3) ...
Setting up mariadb-server-core-10.6 (1:10.6.18-0ubuntu0.22.04.1) ...
Setting up libcgi-fast-perl (1:2.15-1) ...
Setting up mariadb-client-core-10.6 (1:10.6.18-0ubuntu0.22.04.1) ...
Setting up libdbd-mysql-perl:amd64 (4.050-5ubuntu0.22.04.1) ...
Setting up mariadb-client-10.6 (1:10.6.18-0ubuntu0.22.04.1) ...
Setting up mariadb-server-10.6 (1:10.6.18-0ubuntu0.22.04.1) ...
Created symlink /etc/systemd/system/multi-user.target.wants/mariadb.service → /lib/systemd/system/mariadb.service.
Setting up mariadb-server (1:10.6.18-0ubuntu0.22.04.1) ...
Processing triggers for man-db (2.10.2-1) ...
Processing triggers for libc-bin (2.35-0ubuntu3.1) ...

Step 5: Secure the MySQL using the below command

root@linuxhelp:~# sudo mysql_secure_installation
NOTE: RUNNING ALL PARTS OF THIS SCRIPT IS RECOMMENDED FOR ALL MariaDB
      SERVERS IN PRODUCTION USE!  PLEASE READ EACH STEP CAREFULLY!
In order to log into MariaDB to secure it, we'll need the current
password for the root user. If you've just installed MariaDB, and
haven't set the root password yet, you should just press enter here.
Enter current password for root (enter for none): 
OK, successfully used password, moving on...
Setting the root password or using the unix_socket ensures that nobody
can log into the MariaDB root user without the proper authorisation.
You already have your root account protected, so you can safely answer 'n'.
Switch to unix_socket authentication [Y/n] y
Enabled successfully!
Reloading privilege tables..
 ... Success!
You already have your root account protected, so you can safely answer 'n'.
Change the root password? [Y/n] y
New password: 
Re-enter new password: 
Password updated successfully!
Reloading privilege tables..
 ... Success!


By default, a MariaDB installation has an anonymous user, allowing anyone
to log into MariaDB without having to have a user account created for
them.  This is intended only for testing, and to make the installation
go a bit smoother.  You should remove them before moving into a
production environment.

Remove anonymous users? [Y/n] y
 ... Success!

Normally, root should only be allowed to connect from 'localhost'.  This
ensures that someone cannot guess at the root password from the network.

Disallow root login remotely? [Y/n] y
 ... Success!

By default, MariaDB comes with a database named 'test' that anyone can
access.  This is also intended only for testing, and should be removed
before moving into a production environment.

Remove test database and access to it? [Y/n] y
 - Dropping test database...
 ... Success!
 - Removing privileges on test database...
 ... Success!

Reloading the privilege tables will ensure that all changes made so far
will take effect immediately.

Reload privilege tables now? [Y/n] y
 ... Success!

Cleaning up...

All done!  If you've completed all of the above steps, your MariaDB
installation should now be secure.
Thanks for using MariaDB!

Step 6: Login to MariaDB using the below command and enter the password:

root@linuxhelp:~# mysql -u root -p
Enter password: 
Welcome to the MariaDB monitor.  Commands end with ; or \g.
Your MariaDB connection id is 42
Server version: 10.6.18-MariaDB-0ubuntu0.22.04.1 Ubuntu 22.04
Copyright (c) 2000, 2018, Oracle, MariaDB Corporation Ab and others.
Type 'help;' or '\h' for help. Type '\c' to clear the current input statement.
MariaDB [(none)]> 
MariaDB [(none)]> 
MariaDB [(none)]> 
MariaDB [(none)]> exit
Bye

Step 7: Install PHP with its common extensions using the below command

root@linuxhelp:~# sudo apt install php8.1-fpm php8.1-mysql php8.1-gd php8.1-bcmath php8.1-cli php8.1-curl php8.1-mbstring php8.1-zip  php8.1-opcache php8.1-xml
Reading package lists... Done
Building dependency tree... Done
Reading state information... Done
The following packages were automatically installed and are no longer required:
  libflashrom1 libftdi1-2 libllvm13
Use 'sudo apt autoremove' to remove them.
The following additional packages will be installed:
  libonig5 libzip4 php-common php8.1-common php8.1-readline
Suggested packages:
  php-pear
The following NEW packages will be installed:
  libonig5 libzip4 php-common php8.1-bcmath php8.1-cli php8.1-common php8.1-curl php8.1-fpm php8.1-gd php8.1-mbstring php8.1-mysql php8.1-opcache php8.1-readline php8.1-xml
  php8.1-zip
0 upgraded, 15 newly installed, 0 to remove and 339 not upgraded.
Need to get 6,268 kB of archives.
After this operation, 24.8 MB of additional disk space will be used.
Do you want to continue? [Y/n] y
Get:1 http://in.archive.ubuntu.com/ubuntu jammy/main amd64 libonig5 amd64 6.9.7.1-2build1 [172 kB]
Get:2 http://in.archive.ubuntu.com/ubuntu jammy/universe amd64 libzip4 amd64 1.7.3-1ubuntu2 [55.0 kB]
Get:3 http://in.archive.ubuntu.com/ubuntu jammy/main amd64 php-common all 2:92ubuntu1 [12.4 kB]
Get:4 http://in.archive.ubuntu.com/ubuntu jammy-updates/main amd64 php8.1-common amd64 8.1.2-1ubuntu2.18 [1,126 kB]
Get:5 http://in.archive.ubuntu.com/ubuntu jammy-updates/universe amd64 php8.1-bcmath amd64 8.1.2-1ubuntu2.18 [16.5 kB]
Get:6 http://in.archive.ubuntu.com/ubuntu jammy-updates/main amd64 php8.1-opcache amd64 8.1.2-1ubuntu2.18 [365 kB]
Get:14 http://in.archive.ubuntu.com/ubuntu jammy-updates/main amd64 php8.1-xml amd64 8.1.2-1ubuntu2.18 [120 kB]
Get:15 http://in.archive.ubuntu.com/ubuntu jammy-updates/universe amd64 php8.1-zip amd64 8.1.2-1ubuntu2.18 [27.1 kB]
Fetched 6,268 kB in 3s (1,954 kB/s)    
Selecting previously unselected package libonig5:amd64.
(Reading database ... 204902 files and directories currently installed.)
Preparing to unpack .../00-libonig5_6.9.7.1-2build1_amd64.deb ...
Preparing to unpack .../08-php8.1-curl_8.1.2-1ubuntu2.18_amd64.deb ...
Unpacking php8.1-curl (8.1.2-1ubuntu2.18) ...
Selecting previously unselected package php8.1-fpm.
Preparing to unpack .../09-php8.1-fpm_8.1.2-1ubuntu2.18_amd64.deb ...
Unpacking php8.1-fpm (8.1.2-1ubuntu2.18) ...
Selecting previously unselected package php8.1-gd.
Preparing to unpack .../10-php8.1-gd_8.1.2-1ubuntu2.18_amd64.deb ...
Unpacking php8.1-gd (8.1.2-1ubuntu2.18) ...
Selecting previously unselected package php8.1-mbstring.
Preparing to unpack .../11-php8.1-mbstring_8.1.2-1ubuntu2.18_amd64.deb ...
Unpacking php8.1-mbstring (8.1.2-1ubuntu2.18) ...
Selecting previously unselected package php8.1-mysql.
Preparing to unpack .../12-php8.1-mysql_8.1.2-1ubuntu2.18_amd64.deb ...
Unpacking php8.1-mysql (8.1.2-1ubuntu2.18) ...
Selecting previously unselected package php8.1-xml.
Preparing to unpack .../13-php8.1-xml_8.1.2-1ubuntu2.18_amd64.deb ...
Unpacking php8.1-xml (8.1.2-1ubuntu2.18) ...
Selecting previously unselected package php8.1-zip.
Preparing to unpack .../14-php8.1-zip_8.1.2-1ubuntu2.18_amd64.deb ...
Unpacking php8.1-zip (8.1.2-1ubuntu2.18) ...
Setting up php-common (2:92ubuntu1) ...
Created symlink /etc/systemd/system/timers.target.wants/phpsessionclean.timer → /lib/systemd/system/phpsessionclean.timer.
Setting up php8.1-common (8.1.2-1ubuntu2.18) ...

Creating config file /etc/php/8.1/mods-available/calendar.ini with new version

Creating config file /etc/php/8.1/mods-available/ctype.ini with new version

Creating config file /etc/php/8.1/mods-available/exif.ini with new version

Creating config file /etc/php/8.1/cli/php.ini with new version
Setting up php8.1-fpm (8.1.2-1ubuntu2.18) ...
Creating config file /etc/php/8.1/fpm/php.ini with new version
Created symlink /etc/systemd/system/multi-user.target.wants/php8.1-fpm.service → /lib/systemd/system/php8.1-fpm.service.
Processing triggers for man-db (2.10.2-1) ...
Processing triggers for libc-bin (2.35-0ubuntu3.1) ...
Processing triggers for php8.1-cli (8.1.2-1ubuntu2.18) ...
Processing triggers for php8.1-fpm (8.1.2-1ubuntu2.18) ...

Step 8: Check the version of PHP using the below command

root@linuxhelp:~# php -v
PHP 8.1.2-1ubuntu2.18 (cli) (built: Jun 14 2024 15:52:55) (NTS)
Copyright (c) The PHP Group
Zend Engine v4.1.2, Copyright (c) Zend Technologies

Step 9: Configure Nginx to use PHP processor, open the default server block file in a text editor using the following command.

root@linuxhelp:~# vim /etc/nginx/sites-enabled/default

configuration changes:
     
 
        index index.html index.htm index.nginx-debian.html;

        server_name _;

        location / {
                try_files $uri $uri/ /index.php?$args;
        }
 

        # deny access to .htaccess files, if Apache's document root
        # concurs with nginx's one
        #
        #location ~ /\.ht {
        #       deny all;
        #}

        location ~ \.php$ {
        include snippets/fastcgi-php.conf;
        fastcgi_pass unix:/var/run/php/php8.1-fpm.sock;
        }
}

Step 10: Test modified Nginx configuration for syntax error using the below command

root@linuxhelp:~# sudo nginx -t
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful

Step 11 : Restart Nginx to take effect , restart using the below command

root@linuxhelp:~#  sudo systemctl restart nginx

Step 12: To test our PHP setup , create PHP test file in web root directory using the below command

root@linuxhelp:~# echo "<?php phpinfo(); ?>" | sudo tee /var/www/html/test.php
<?php phpinfo(); ?>

Conclusion:

We have reached the end of this article. In this guide, we have walked you through the steps required to install LEMP Stack on Ubuntu 22.04.Your feedback is much welcome.

Tags:
michael
Author: 

Comments ( 0 )

No comments available

Add a comment
{{postCtrl.cmtErrMsg}}

Frequently asked questions ( 5 )

Q

1.What is the LEMP Stack?

A

The LEMP Stack is a combination of four open-source technologies used to build a web server:
L- Linux (operating system)
E-Nginx (web server and reverse proxy)
M-MySQL (relational database management system)
P-PHP (server-side scripting language)

Q

2. What is the purpose of each component in the LEMP Stack?

A

Linux: Provides a solid foundation for running the other components.Nginx: Acts as a web server, reverse proxy, and load balancer. It serves static files, handles HTTPrequests, and directs traffic to other servers if needed. MySQL: A relational database management system that stores and manages data for your web applications.PHP : A server-side scripting language used to create dynamic web pages, interact with the MySQL database,and perform various tasks.

Q

3.What are the advantages of using the LEMP Stack?

A

Nginx is known for its high performance and ability to handle a large number of concurrent connections.The LEMP stack is highly scalable, making it suitable for large-scale web applications.Each component has built-in security features, such as Linux's secure permissions, Nginx's URLrewriting and access control, MySQL's robust authentication and encryption, and PHP's secure coding practices.

Q

4.What are some common use cases for the LEMP Stack?

A

Build custom web applications using PHP and MySQL, with Nginx serving as a web server. : Use the LEMP stack with popular CMS platforms like WordPress or Joomla.Content management systems (CMS).Use the LEMP stack with popular CMS platforms like WordPress or Joomla. Create online stores using e-commerce platforms like Magento or Prestashop, built on top of the LEMP stack.

Q

5.Are there any potential drawbacks to using the LEMP stack?

A

Steeper learning curve: Each component has its own unique configuration options, which can be overwhelmingfor new users.
Resource-intensive: The LEMP stack requires significant system resources (CPU, memory, disk space) to runefficiently.
Complexity : With multiple components involved, troubleshooting and debugging issues can be more challenging.

Back To Top!
Rank
User
Points

Top Contributers

userNamenaveelansari
135850

Top Contributers

userNameayanbhatti
92510

Top Contributers

userNamehamzaahmed
32150

Top Contributers

1
userNamelinuxhelp
31040

Top Contributers

userNamemuhammadali
24500
Can you help Jayce ?
What are the types of table used in IPtables

What are the various types of table used in IPtables and how to use that for my server security?

Networking
  • Routing
  • trunk
  • Netmask
  • Packet Capture
  • domain
  • HTTP Proxy
Server Setup
  • NFS
  • KVM
  • Memory
  • Sendmail
  • WebDAV
  • LXC
Shell Commands
  • Cloud commander
  • Command line archive tools
  • last command
  • Shell
  • terminal
  • Throttle
Desktop Application
  • Linux app
  • Pithos
  • Retrospect
  • Scribe
  • TortoiseHg
  • 4Images
Monitoring Tool
  • Monit
  • Apache Server Monitoring
  • EtherApe 
  • Arpwatch Tool
  • Auditd
  • Barman
Web Application
  • Nutch
  • Amazon VPC
  • FarmWarDeployer
  • Rukovoditel
  • Mirror site
  • Chef
Contact Us | Terms of Use| Privacy Policy| Disclaimer
© 2025 LinuxHelp.com All rights reserved. Linux™ is the registered trademark of Linus Torvalds. This site is not affiliated with linus torvalds in any way.