Implantação de aplicativo no Laravel 7 em Ubuntu & Nginx

Implantação de aplicativo em Laravel 7 no Ubuntu & Nginx

Decidi criar meu portfólio em Laravel 7. O objetivo é que a página principal seja um landing page, onde toda a informação possa ser alterada através do painel de administração. Mas não é isso o que importa. Cheguei na parte do deploy. Encontrei alguns tutoriais bons sobre como fazer isso em um servidor completo, com todas as complicações. Eu não sou muito forte em deploy, sou mais front-end do que full stack. E, se eu consigo programar e testar em PHP, ainda não cheguei à parte de gerenciar servidores e afins. Mas precisei aprender.

Agora vamos passar por todas as etapas, começando com o acesso via SSH e terminando com o site em funcionamento. Tentaremos evitar todas as armadilhas.

Você pode encontrar instruções semelhantes na internet. Afinal, eu também encontrei. Porém, não em um só lugar, não sem a ajuda do StackOverflow e provavelmente não em russo. Eu enfrentei algumas dificuldades. Por isso, decidi simplificar a sua vida.

Faremos tudo isso com um droplet na DigitalOcean. Isso, claro, não é obrigatório, escolha qualquer hospedagem. Quando chegar a um servidor Ubuntu funcionando, volte aqui. Para aqueles que decidiram usar a DigitalOcean, também haverá dicas sobre configuração de domínio. Além disso, um link de referência para 100$.

Todas as etapas específicas para a DigitalOcean serão apresentadas em notas similares.

Vamos começar.

TL;DR (apenas os comandos principais)

Criamos o usuário

  • ssh root@[IP-do-seu-droplet]
  • adduser laravel
  • usermod -aG sudo laravel
  • su laravel

Adicionamos o SSH para ele

  • mkdir ~/.ssh
  • chmod 700 ~/.ssh
  • vim ~/.ssh/authorized_keys
  • Cole a chave pública
  • chmod 600 ~/.ssh/authorized_keys

Firewall

  • sudo ufw allow OpenSSH
  • sudo ufw enable
  • sudo ufw status

Nginx

  • sudo apt update
  • sudo apt install -y nginx
  • sudo ufw allow 'Nginx HTTP'
  • sudo ufw status

MySQL

  • sudo apt install -y mysql-server
  • sudo mysql_secure_installation, NYNNY
  • sudo mysql
  • ALTER USER 'root'@'localhost' IDENTIFIED WITH mysql_native_password BY '';
  • SELECT user,authentication_string,plugin,host FROM mysql.user;
  • FLUSH PRIVILEGES;
  • sigreturn

PHP

  • sudo apt update

  • sudo apt install -y curl wget gnupg2 ca-certificates lsb-release apt-transport-https

  • sudo apt-add-repository ppa:ondrej/php

  • sudo apt update

  • 7.3: sudo apt install -y php7.3-fpm php7.3-mysql

  • 7.4: sudo apt install -y php7.4-fpm php7.4-mysql

  • sudo vim /etc/nginx/sites-available/

Configuração básica:

server {
        listen 80;
        root /var/www/html;
        index index.php index.html index.htm index.nginx-debian.html;
        server_name ;

        location / {
                try_files $uri $uri/ =404;
        }

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

        location ~ /.ht {
                deny all;
        }
}

Apenas a configuração HTTP para Laravel:

servidor {
    escute 80;
    escute [::]:80;

    root /var/www/html/<Nome do projeto>/public;
    index index.php index.html index.htm index.nginx-debian.html;

    server_name <Seu domínio ou IP>;

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

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

    location ~ /.ht {
        negar tudo;
    }
}

Configuração HTTPS para Laravel:

servidor {
    escute 80;
    escute [::]:80;

    server_name <Seu domínio> www.<Seu domínio>;
    return 301 https://$server_name$request_uri;
}

servidor {
    escute 443 ssl http2;
    escute [::]:443 ssl http2;
    server_name <Seu domínio> www.<Seu domínio>;
    root /var/www/html/<Nome do projeto>/public;

    ssl_certificate /etc/letsencrypt/live/<Seu domínio>/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/<Seu domínio>/privkey.pem;

    ssl_protocols TLSv1.2;
    ssl_ciphers ECDHE-RSA-AES256-GCM-SHA512:DHE-RSA-AES256-GCM-SHA512:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-SHA384;
    ssl_prefer_server_ciphers on;

    add_header X-Frame-Options "SAMEORIGIN";
    add_header X-XSS-Protection "1; mode=block";
    add_header X-Content-Type-Options "nosniff";

    index index.php index.html index.htm index.nginx-debian.html;

    charset utf-8;

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

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

    location ~ /.ht {
            negar tudo;
    }

    location ~ /.well-known {
            permitir tudo;
    }
}

  • sudo ln -s /etc/nginx/sites-available/<Seu domínio> /etc/nginx/sites-enabled/
  • sudo unlink /etc/nginx/sites-enabled/default
  • sudo nginx -t
  • sudo systemctl reload nginx

Laravel

  • 7.3: sudo apt install -y php7.3-mbstring php7.3-xml composer unzip

  • 7.4: sudo apt install -y php7.4-mbstring php7.4-xml composer unzip

  • mysql -u root -p

  • CRIE O BANCO DE DADOS laravel DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci;

  • CONCEDA TODAS AS PERMISSÕES NO laravel.* PARA 'root'@'localhost' IDENTIFICADO POR '<Sua senha do MySQL>;

  • FLUSH PRIVILEGES;

  • sigreturn

  • cd /var/www/html

  • sudo mkdir -p <Nome do projeto>

  • sudo chown laravel:laravel <Nome do projeto>

  • cd ./<Nome do projeto>

  • git clone <link do projeto> . / git clone -b <nome do ramo> --single-branch <link do projeto> .

  • composer install

  • vim .env

APP_NAME=Laravel
APP_ENV=production
APP_KEY=
APP_DEBUG=false
APP_URL=http://<Seu domínio>

LOG_CHANNEL=stack

DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=laravel
DB_USERNAME=root
DB_PASSWORD=<Sua senha do MySQL>

  • php artisan migrate

  • php artisan key:generate

  • sudo chown -R $USER:www-data storage

  • sudo chown -R $USER:www-data bootstrap/cache

  • chmod -R 775 storage

  • chmod -R 775 bootstrap/cache

HTTPS

  • sudo add-apt-repository ppa:certbot/certbot

  • sudo apt install -y python-certbot-nginx

  • sudo certbot certonly --webroot --webroot-path=/var/www/html/<Nome do projeto>/public -d <Seu domínio> -d www.<Seu domínio>

  • sudo nginx -t

  • sudo ufw allow 'Nginx HTTPS'

  • sudo ufw status

  • sudo systemctl reload nginx

Criando um droplet na DigitalOcean e registrando uma nova chave SSH

Acredito sinceramente que você conseguirá se registrar na DigitalOcean. Não é fácil, tem muita verificação e outras complicações. Se você estiver enfrentando um erro de rede com a verificação de documentos, tente fazer tudo através de VPN, deve ajudar.

No menu superior, clique em Criar->Droplets. Selecione Ubuntu.

Assim que você se registrar, receberá 100$ na conta. Mas não se anime muito. Você tem apenas 60 dias para gastá-los. E isso é muito pouco. Você pode, como eu, querer usar um plano mais caro, para depois, quando o dinheiro real começar a entrar, mudar para um mais barato. De antemão, digo que não vai funcionar. Você pode aumentar, mas não pode diminuir. É assim que funciona. Eu escolho Padrão->$5.

Eu escolho a região mais próxima de nós Frankfurt. Rede VPC->default-fra1

Faremos a autenticação imediatamente via SSH. Clique em Nova Chave SSH. Se você não tem SSH, há um guia muito simples à direita. Abra o terminal bash, cole ssh-keygen. Em seguida, entre no arquivo com a chave pública /Users/<Ваше имя пользователя>/.ssh/id_rsa.pub (ou apenas cat ~/\.ssh/id_rsa.pub), copie o conteúdo e cole na janela à esquerda. O nome pode ser qualquer um.

Criamos um hostname para o droplet.

Clique em Criar Droplet

Criamos um novo usuário

  • ssh root@[IP-do-seu-droplet]
  • Você tem certeza de que deseja continuar conectando (sim/não/[impressão digital])? sim
  • Digite sua senha do SSH
  • Criamos o usuário laravel: adduser laravel
  • Digite a senha e outras informações (eu só coloco o Nome Completo)
  • Adicionamos o usuário ao grupo sudo: usermod -aG sudo laravel

SSH para o novo usuário

  • Trocamos para o novo usuário: su laravel

Todas as ações a seguir, até o final do artigo, serão realizadas em nome do usuário laravel. Portanto, se você eventualmente se desconectar, entre novamente e digite su laravel

  • mkdir ~/.ssh
  • chmod 700 ~/.ssh
  • vim ~/.ssh/authorized_keys

Abrimos o arquivo no Vim. Se você não está familiarizado com ele, pode trabalhar no Nano, é sua escolha.

Os comandos mais básicos do Vim

Para utilizar o editor Vim ao longo do artigo, você precisa saber o seguinte.

  • No Vim, existem diferentes modos: o modo normal, onde você insere comandos e seleciona outros modos.
  • Para sair de qualquer modo e voltar ao modo normal, basta pressionar Esc
  • Mover-se: você pode usar as setas
  • Sair sem salvar <Normal mode>: :q!
  • Sair e salvar <Normal mode>: :wq
  • Entrar no modo de inserção de texto <Normal mode>: i (da inglês. inserir)
  • Cole nossa chave pública (que fizemos acima)
  • Protegemos contra alterações: chmod 600 ~/.ssh/authorized_keys

Instalamos o firewall

  • Veja todas as configurações disponíveis: sudo ufw app list
  • Permitimos OpenSSH (caso contrário, seremos bloqueados): sudo ufw allow OpenSSH
  • Iniciamos o firewall: sudo ufw enable, y
  • Verificamos: sudo ufw status

Status: ativo

Para                         Ação      De
--                         ------      ----
OpenSSH                    PERMITIR    Em qualquer lugar
OpenSSH (v6)               PERMITIR    Em qualquer lugar (v6)

Tudo está certo.

Instalamos o Nginx

Durante a instalação, às vezes perguntará 'Você tem certeza?'. Responda y (bem, apenas se tiver certeza).

  • sudo apt update
  • sudo apt install nginx

Adicionamos o Nginx às configurações do firewall

  • sudo ufw app list
  • sudo ufw allow 'Nginx HTTP'
  • sudo ufw status

Status: ativo

Para                         Ação      De
--                         ------      ----
OpenSSH                    PERMITIR       Qualquer lugar
Nginx HTTP                 PERMITIR       Qualquer lugar
OpenSSH (v6)               PERMITIR       Qualquer lugar (v6)
Nginx HTTP (v6)            PERMITIR       Qualquer lugar (v6)

Acesse seu IP. Se tudo estiver certo, você deverá ver o seguinte.

Implantação de aplicativo em Laravel 7 no Ubuntu & Nginx

Instalando o MySQL

  • sudo apt install mysql-server
  • Executando o script automático de proteção sudo mysql_secure_installation

Responda às perguntas apresentadas. Se você não souber o que responder, aqui estão as opções recomendadas:

  • Validar plugin de senha — N

  • Remover usuários anônimos? — Y

  • Proibir login remoto do root? — N

  • Remover banco de dados de teste e acesso a ele? — N

  • Recarregar tabelas de privilégios agora? — Y

  • Acessando o MySQL: sudo mysql

  • Verificando os métodos de acesso: SELECT user,authentication_string,plugin,host FROM mysql.user;

  • Definindo senha para o root: ALTER USER 'root'@'localhost' IDENTIFIED WITH mysql_native_password BY '';

  • Verificando os métodos de acesso novamente: SELECT user,authentication_string,plugin,host FROM mysql.user;

  • Aplicando as alterações e saindo do MySQL: FLUSH PRIVILEGES; e sigreturn

  • Agora, para entrar no MySQL, você precisa usar mysql -u root -p e digitar a senha

Instalando o PHP

Utilizaremos um repositório de terceiros de Ondřej Surý

  • sudo apt update
  • sudo apt install -y curl wget gnupg2 ca-certificates lsb-release apt-transport-https
  • sudo apt-add-repository ppa:ondrej/php
  • sudo apt update

Agora, vamos escolher. Para Laravel 7, você pode escolher PHP 7.3 ou 7.4. A diferença será apenas nos números 3 e 4.

  • 7.3: sudo apt install -y php7.3-fpm php7.3-mysql
  • 7.4: sudo apt install -y php7.4-fpm php7.4-mysql

O PHP FastCGI Process Manager (fpm) trabalha com requisições PHP. O mysql, é claro, é para trabalhar com MySQL.

A partir daqui, farei tudo na versão 7.4.

Configurando o Nginx

  • sudo vim /etc/nginx/sites-available/

Substitua "" pelo domínio (por exemplo, mysite.ru), que você deseja usar no futuro. Se você ainda não tiver um, escreva qualquer um, depois basta repetir as ações nesta seção para seu domínio, quando o escolher.

Digite o seguinte:

server {
        listen 80;
        root /var/www/html;
        index index.php index.html index.htm index.nginx-debian.html;
        server_name ;

        location / {
                try_files $uri $uri/ =404;
        }

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

        location ~ /.ht {
                deny all;
        }
}

Se você escolheu a versão 7.3 em vez de php7.4-fpm.sock digite php7.4-fpm.sock.

Escutamos a porta 80 em server_name, quando uma requisição chega na raiz /var/www/html pegamos o arquivo index. Se houver algo após server_name procuramos tal arquivo. Se não encontrarmos, retornamos 404. Se terminar em .php, passamos pelo fpm. Se existir .ht, proibimos (403).

  • Fazemos um link de sites-available em para: sudo ln -s /etc/nginx/sites-available/<Seu domínio> /etc/nginx/sites-enabled/
  • sites-enabled padrão: sudo unlink /etc/nginx/sites-enabled/default
  • Removemos o link para sudo nginx -t
  • Verificamos por erros: sudo systemctl reload nginx

Reiniciamos:

  • sudo vim /var/www/html/info.php
  • Escrevemos: <?php phpinfo();
  • Navegamos para /info.php

Você deve ver algo parecido:

Implantação de aplicativo em Laravel 7 no Ubuntu & Nginx

Agora, este arquivo pode ser removido: sudo rm /var/www/html/info.php

Instalamos o Laravel

  • 7.3: sudo apt install php7.3-mbstring php7.3-xml composer unzip

  • 7.4: sudo apt install php7.4-mbstring php7.4-xml composer unzip

  • Acessando o MySQL: mysql -u root -p

  • Criamos um banco de dados chamado laravel: CRIE O BANCO DE DADOS laravel DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci;

  • Damos acesso root a laravel: CONCEDA TODAS AS PERMISSÕES NO laravel.* PARA 'root'@'localhost' IDENTIFICADO POR '<Sua senha do MySQL>;

  • FLUSH PRIVILEGES;

  • sigreturn

  • cd /var/www/html

  • Criamos uma pasta para o projeto: sudo mkdir -p <Nome do projeto>

  • Concedemos ao usuário laravel permissões para o projeto: sudo chown laravel:laravel <Nome do projeto>

A seguir, precisamos transferir o projeto. Por exemplo, clonando do Github.

  • cd ./<Nome do projeto>
  • git clone <link do projeto> .

Vale lembrar que, se você não salvou arquivos estáticos (por exemplo, de /public) no Github, você, naturalmente, não os terá. Por exemplo, para resolver isso, eu criei uma branch separada deploy, da qual já clonei: git clone -b <nome do ramo> --single-branch <link do projeto> ..

  • Instalando dependências: composer install
  • Criando .env: vim .env

A versão básica dele é assim:

APP_NAME=Laravel
APP_ENV=production
APP_KEY=
APP_DEBUG=false
APP_URL=http://<Seu domínio>

LOG_CHANNEL=stack

DB_CONNECTION=mysql
DB_HOST=127.0.0.1
DB_PORT=3306
DB_DATABASE=laravel
DB_USERNAME=root
DB_PASSWORD=<Sua senha do MySQL>

Se você copiar seu .env, substitua APP_ENV por production, APP_DEBUG por false e insira as configurações corretas para MySQL.

  • Migrando o banco de dados: php artisan migrate
  • Gerando código: php artisan key:generate

Alterando permissões:

  • sudo chown -R $USER:www-data storage
  • sudo chown -R $USER:www-data bootstrap/cache
  • chmod -R 775 storage
  • chmod -R 775 bootstrap/cache

A última coisa que resta é reconfigurar o Nginx para o Laravel:

sudo vim /etc/nginx/sites-available/

servidor {
    escute 80;
    escute [::]:80;

    root /var/www/html/<Nome do projeto>/public;
    index index.php index.html index.htm index.nginx-debian.html;

    server_name <Seu domínio ou IP>;

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

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

    location ~ /.ht {
        negar tudo;
    }
}

Como da última vez, se você escolheu a versão 7.3 em vez de php7.4-fpm.sock digite php7.4-fpm.sock.

Configurando o domínio na DigitalOcean

Na verdade, tudo é muito simples. Você compra um domínio (onde quiser), vai para a DigitalOcean em Criar->Domains/DNS. No campo Adicionar um domínio você insere esse domínio e clica em adicionar. Em seguida, vá para as configurações do domínio e no campo NOME DO HOST você insere @. Escolha o projeto e clique em Criar registro.
Agora vá para o site onde comprou o domínio, encontre "Servidores DNS" (ou algo parecido) e insira os servidores da DigitalOcean (ou seja, ns1.digitalocean.com, ns2.digitalocean.com, ns3.digitalocean.com). Agora é necessário esperar um pouco (ou muito) até que essas configurações sejam aceitas. Pronto!
O único problema é que seu site será acessível apenas como HTTP. Para ter HTTPS, siga para a próxima parte.

Configurando HTTPS

Instalamos o certbot e fornecemos o nome do domínio (no formato mysite.ru) e o nome do domínio com www (www.mysite.ru).

  • sudo add-apt-repository ppa:certbot/certbot
  • sudo apt install python-certbot-nginx
  • sudo certbot certonly --webroot --webroot-path=/var/www/html/<Nome do projeto>/public -d <Seu domínio> -d www.<Seu domínio>

Agora precisamos reconfigurar o Nginx (não esqueça de substituir pelos seus valores):

servidor {
    escute 80;
    escute [::]:80;

    server_name <Seu domínio> www.<Seu domínio>;
    return 301 https://$server_name$request_uri;
}

servidor {
    escute 443 ssl http2;
    escute [::]:443 ssl http2;
    server_name <Seu domínio> www.<Seu domínio>;
    root /var/www/html/<Nome do projeto>/public;

    ssl_certificate /etc/letsencrypt/live/<Seu domínio>/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/<Seu domínio>/privkey.pem;

    ssl_protocols TLSv1.2;
    ssl_ciphers ECDHE-RSA-AES256-GCM-SHA512:DHE-RSA-AES256-GCM-SHA512:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-GCM-SHA384:ECDHE-RSA-AES256-SHA384;
    ssl_prefer_server_ciphers on;

    add_header X-Frame-Options "SAMEORIGIN";
    add_header X-XSS-Protection "1; mode=block";
    add_header X-Content-Type-Options "nosniff";

    index index.php index.html index.htm index.nginx-debian.html;

    charset utf-8;

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

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

    location ~ /.ht {
            negar tudo;
    }

    location ~ /.well-known {
            permitir tudo;
    }
}

Acho que você já entendeu o que precisa mudar para PHP 7.3.

Aqui, na verdade, tudo é simples. Nós apenas redirecionamos todas as requisições de HTTP (porta 80) para HTTPS (porta 443). E fazemos tudo o que já fazíamos antes, mas agora com criptografia.

Falta definir as permissões no firewall:

  • sudo nginx -t
  • sudo ufw app list
  • sudo ufw allow 'Nginx HTTPS'
  • sudo ufw status
  • sudo systemctl reload nginx

Agora tudo deve funcionar como deveria.

[Дополнительно] Установка Node.js

Se por acaso você precisar rodar comandos npm diretamente no servidor, você precisa instalar o Node.js.

  • sudo apt update
  • sudo apt install -y nodejs npm
  • nodejs -v

Isso é tudo, eu parei nessa etapa. Na verdade, o resultado me agrada. Pode ser que eu mude da DigitalOcean para um lugar mais perto da Rússia e mais barato. Mas como já passei por todos os processos de verificação no site e fiz tudo lá, mostrei pelo exemplo deles. Além disso, seus primeiros 100 dólares são uma ótima base para treinos.

P.S. Agradecimento especial ao autor deste gist, que serviu de base para todas as ações mencionadas acima. Ele não funciona em alguns pontos para Laravel 7, eu corrigi isso.

P.P.S. Se você é um engenheiro de alto nível que pensa em comandos de bash, por favor, não seja muito crítico. Pode ser que o nível deste artigo pareça baixo para você, mas eu ficaria feliz em ter encontrado algo assim quando precisei. Se tiver sugestões de melhorias, estou totalmente a favor.

Fonte: habr.com

Compre hospedagem confiável para sites com proteção contra DDoS, servidores VPS VDS 🔥 Compre hospedagem confiável para sites com proteção contra DDoS, servidores VPS VDS | ProHoster