<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Fernando da Silva Sousa</title>
    <description>The latest articles on DEV Community by Fernando da Silva Sousa (@naaando).</description>
    <link>https://dev.to/naaando</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F406138%2Fb6c653c8-8efa-4c40-85f8-8ed323bd56c4.jpeg</url>
      <title>DEV Community: Fernando da Silva Sousa</title>
      <link>https://dev.to/naaando</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/naaando"/>
    <language>en</language>
    <item>
      <title>Projeto Planning poker realtime com Laravel</title>
      <dc:creator>Fernando da Silva Sousa</dc:creator>
      <pubDate>Fri, 24 Nov 2023 04:02:40 +0000</pubDate>
      <link>https://dev.to/naaando/como-eu-fiz-um-planning-poker-realtime-com-laravel-56h1</link>
      <guid>https://dev.to/naaando/como-eu-fiz-um-planning-poker-realtime-com-laravel-56h1</guid>
      <description>&lt;p&gt;Como desenvolvi um planning poker com &lt;strong&gt;Laravel&lt;/strong&gt;, &lt;strong&gt;Ably&lt;/strong&gt;, &lt;strong&gt;InertiaJS&lt;/strong&gt;, &lt;strong&gt;Tailwind&lt;/strong&gt; e &lt;strong&gt;Vuejs&lt;/strong&gt;.&lt;/p&gt;

&lt;p&gt;&lt;a href="//planningpoker.fssoftware.com.br"&gt;Link para planning poker&lt;/a&gt;&lt;/p&gt;


&lt;div class="ltag-github-readme-tag"&gt;
  &lt;div class="readme-overview"&gt;
    &lt;h2&gt;
      &lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--A9-wwsHG--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://dev.to/assets/github-logo-5a155e1f9a670af7944dd5e12375bc76ed542ea80224905ecaf878b9157cdefc.svg" alt="GitHub logo"&gt;
      &lt;a href="https://github.com/naaando"&gt;
        naaando
      &lt;/a&gt; / &lt;a href="https://github.com/naaando/planningpoker"&gt;
        planningpoker
      &lt;/a&gt;
    &lt;/h2&gt;
    &lt;h3&gt;
      Planning poker
    &lt;/h3&gt;
  &lt;/div&gt;
  &lt;div class="ltag-github-body"&gt;
    
&lt;div id="readme" class="md"&gt;
&lt;p&gt;&lt;a href="https://codecov.io/gh/naaando/planningpoker" rel="nofollow"&gt;&lt;img src="https://camo.githubusercontent.com/faf0a4594990bc47c54e3c0cd37bb138276a175cab84722396a4f42e8a6414d5/68747470733a2f2f636f6465636f762e696f2f67682f6e6161616e646f2f706c616e6e696e67706f6b65722f67726170682f62616467652e7376673f7374796c653d666f722d7468652d626164676526746f6b656e3d4338434c393355543756" alt="codecov"&gt;&lt;/a&gt;
&lt;a rel="noopener noreferrer nofollow" href="https://camo.githubusercontent.com/3c5a3f3fde2742f3f78ed5a6531b80bd12bcd49bc05ba6c47b25a73a31abada7/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f6c61726176656c2d2532334646324432302e7376673f6c6f676f3d6c61726176656c266c6f676f436f6c6f723d7768697465"&gt;&lt;img src="https://camo.githubusercontent.com/3c5a3f3fde2742f3f78ed5a6531b80bd12bcd49bc05ba6c47b25a73a31abada7/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f6c61726176656c2d2532334646324432302e7376673f6c6f676f3d6c61726176656c266c6f676f436f6c6f723d7768697465" alt="Laravel"&gt;&lt;/a&gt;
&lt;a rel="noopener noreferrer nofollow" href="https://camo.githubusercontent.com/c8b5b30a4c76809b3f38e1f0c0264f5b59d0da4aabe9dafb4280346ff8e5b637/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f7461696c77696e646373732d2532333338423241432e7376673f6c6f676f3d7461696c77696e642d637373266c6f676f436f6c6f723d7768697465"&gt;&lt;img src="https://camo.githubusercontent.com/c8b5b30a4c76809b3f38e1f0c0264f5b59d0da4aabe9dafb4280346ff8e5b637/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f7461696c77696e646373732d2532333338423241432e7376673f6c6f676f3d7461696c77696e642d637373266c6f676f436f6c6f723d7768697465" alt="TailwindCSS"&gt;&lt;/a&gt;
&lt;a rel="noopener noreferrer nofollow" href="https://camo.githubusercontent.com/40553b1f17d56efbe6b6db78d8a3338cb00bcad284ce270b61ae14c284020cf7/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f7675656a732d2532333335343935652e7376673f6c6f676f3d767565646f746a73266c6f676f436f6c6f723d253233344643303844"&gt;&lt;img src="https://camo.githubusercontent.com/40553b1f17d56efbe6b6db78d8a3338cb00bcad284ce270b61ae14c284020cf7/68747470733a2f2f696d672e736869656c64732e696f2f62616467652f7675656a732d2532333335343935652e7376673f6c6f676f3d767565646f746a73266c6f676f436f6c6f723d253233344643303844" alt="Vue.js"&gt;&lt;/a&gt;&lt;/p&gt;
&lt;h1&gt;
Planning Poker&lt;/h1&gt;
&lt;h2&gt;
Overview&lt;/h2&gt;
&lt;p&gt;This is a Planning Poker project developed using Laravel as the backend framework, Vue.js for the frontend, Inertia.js for the middle layer, and Ably for real-time communication.&lt;/p&gt;
&lt;h2&gt;
Usage&lt;/h2&gt;
&lt;div class="table-wrapper-paragraph"&gt;&lt;table&gt;
&lt;thead&gt;
&lt;tr&gt;
&lt;th&gt;Welcome&lt;/th&gt;
&lt;th&gt;Playing&lt;/th&gt;
&lt;/tr&gt;
&lt;/thead&gt;
&lt;tbody&gt;
&lt;tr&gt;
&lt;td&gt;&lt;a rel="noopener noreferrer" href="https://github.com/naaando/planningpoker/resources/images/first-time.png"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--BuuCxQRn--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://github.com/naaando/planningpoker/resources/images/first-time.png" alt="First time"&gt;&lt;/a&gt;&lt;/td&gt;
&lt;td&gt;&lt;a rel="noopener noreferrer" href="https://github.com/naaando/planningpoker/resources/images/playing.png"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--1tT41Gys--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://github.com/naaando/planningpoker/resources/images/playing.png" alt="Playing"&gt;&lt;/a&gt;&lt;/td&gt;
&lt;/tr&gt;
&lt;/tbody&gt;
&lt;/table&gt;&lt;/div&gt;
&lt;h2&gt;
Technologies Used&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href="https://laravel.com/" rel="nofollow"&gt;Laravel&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://vuejs.org/" rel="nofollow"&gt;Vue.js&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://inertiajs.com/" rel="nofollow"&gt;Inertia.js&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://github.com/naaando/planningpokerably.com/"&gt;Ably&lt;/a&gt;&lt;/li&gt;
&lt;/ul&gt;
&lt;h2&gt;
Requirements&lt;/h2&gt;
&lt;ul&gt;
&lt;li&gt;&lt;a href="https://www.docker.com/" rel="nofollow"&gt;Docker&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;&lt;a href="https://docs.docker.com/compose/" rel="nofollow"&gt;Docker Compose&lt;/a&gt;&lt;/li&gt;
&lt;li&gt;Database (e.g., MySQL)&lt;/li&gt;
&lt;/ul&gt;
&lt;h2&gt;
Installation&lt;/h2&gt;
&lt;ol&gt;
&lt;li&gt;Clone the repository:&lt;/li&gt;
&lt;/ol&gt;
&lt;div class="snippet-clipboard-content notranslate position-relative overflow-auto"&gt;&lt;pre class="notranslate"&gt;&lt;code&gt;git clone https://github.com/naaando/planningpoker.git
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;ol start="2"&gt;
&lt;li&gt;Copy the environment file:&lt;/li&gt;
&lt;/ol&gt;
&lt;div class="snippet-clipboard-content notranslate position-relative overflow-auto"&gt;&lt;pre class="notranslate"&gt;&lt;code&gt;cp .env.example .env
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;ol start="3"&gt;
&lt;li&gt;Configure the environment file:&lt;/li&gt;
&lt;/ol&gt;
&lt;p&gt;Open the &lt;code&gt;.env&lt;/code&gt; file at the root of the project and configure your environment variables, including the database configuration and Ably credentials.&lt;/p&gt;
&lt;ol start="4"&gt;
&lt;li&gt;Start the project with Sail:&lt;/li&gt;
&lt;/ol&gt;
&lt;div class="snippet-clipboard-content notranslate position-relative overflow-auto"&gt;&lt;pre class="notranslate"&gt;&lt;code&gt;./vendor/bin/sail up -d
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;ol start="5"&gt;
&lt;li&gt;Install PHP dependencies:&lt;/li&gt;
&lt;/ol&gt;
&lt;div class="snippet-clipboard-content notranslate position-relative overflow-auto"&gt;&lt;pre class="notranslate"&gt;&lt;code&gt;./vendor/bin/sail composer install
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;ol start="6"&gt;
&lt;li&gt;Generate the application key:&lt;/li&gt;
&lt;/ol&gt;
&lt;div class="snippet-clipboard-content notranslate position-relative overflow-auto"&gt;&lt;pre class="notranslate"&gt;&lt;code&gt;./vendor/bin/sail artisan key:generate
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;ol start="7"&gt;
&lt;li&gt;Run database migrations:&lt;/li&gt;
&lt;/ol&gt;
&lt;div class="snippet-clipboard-content notranslate position-relative overflow-auto"&gt;&lt;pre class="notranslate"&gt;&lt;code&gt;./vendor/bin/sail artisan migrate
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;ol start="8"&gt;
&lt;li&gt;Install Node.js dependencies:&lt;/li&gt;
&lt;/ol&gt;
&lt;div class="snippet-clipboard-content notranslate position-relative overflow-auto"&gt;&lt;pre class="notranslate"&gt;&lt;code&gt;./vendor/bin/sail npm install
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;ol start="9"&gt;
&lt;li&gt;Compile assets:&lt;/li&gt;
&lt;/ol&gt;
&lt;div class="snippet-clipboard-content notranslate position-relative overflow-auto"&gt;&lt;pre class="notranslate"&gt;&lt;code&gt;./vendor/bin/sail npm run dev
&lt;/code&gt;&lt;/pre&gt;&lt;/div&gt;
&lt;h2&gt;
Contributing&lt;/h2&gt;
&lt;p&gt;Contributions are welcome! Please follow the instructions in &lt;a href="https://github.com/naaando/planningpokerCONTRIBUTING.md"&gt;CONTRIBUTING.md&lt;/a&gt;.&lt;/p&gt;
&lt;h2&gt;
License&lt;/h2&gt;
&lt;p&gt;This project is licensed under the &lt;a href="https://github.com/naaando/planningpokerLICENSE"&gt;MIT License&lt;/a&gt;.&lt;/p&gt;
&lt;/div&gt;



&lt;/div&gt;
&lt;br&gt;
  &lt;div class="gh-btn-container"&gt;&lt;a class="gh-btn" href="https://github.com/naaando/planningpoker"&gt;View on GitHub&lt;/a&gt;&lt;/div&gt;
&lt;br&gt;
&lt;/div&gt;
&lt;br&gt;


&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--CC4Awc97--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/52tks4k49x8w4gec96ja.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--CC4Awc97--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/52tks4k49x8w4gec96ja.png" alt="Roda de poker do Planning poker" width="800" height="560"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Meu time de utiliza scrum na gestão dos projetos, uma parte desse fluxo de trabalho envolve estimar o tempo gasto nas atividades, e para isso utilizamos um jogo chamado planning poker para fazer as votações das estimativas.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;Já existem diversos produtos prontos para esse propósito na forma de sistemas web então decidi criar mais um.&lt;/p&gt;
&lt;/blockquote&gt;

&lt;h3&gt;
  
  
  Login
&lt;/h3&gt;

&lt;p&gt;A utilização de sistema de login foi descartada por se tratar de um sistema simples em que um sistema de login poderia atrapalhar a adesão dos usuários e gerar mais complexidade que o necessário, os nomes dos usuários são passados na hora do voto no payload.&lt;/p&gt;

&lt;h3&gt;
  
  
  Mecânica
&lt;/h3&gt;

&lt;p&gt;A mecânica de um jogo desses não é complicada, você tem &lt;strong&gt;salas&lt;/strong&gt;, onde ocorrem &lt;strong&gt;partidas&lt;/strong&gt; e nas partidas são feitos os &lt;strong&gt;votos&lt;/strong&gt;. &lt;/p&gt;

&lt;p&gt;O trabalho da &lt;strong&gt;sala&lt;/strong&gt; é manter um guardar a partida atual, assim pode ser utilizado o mesmo link em vários jogos e os usuários sempre vão conseguir acessar a partida certa. &lt;/p&gt;

&lt;p&gt;A &lt;strong&gt;partida&lt;/strong&gt; tem informações de inicio, fim, e o vínculo com a sala, por regra de negócio só pode ter uma partida aberta na sala.&lt;/p&gt;

&lt;p&gt;Os &lt;strong&gt;votos&lt;/strong&gt; possuem nome do usuário e valor (atualmente em fibonacci), como não tem usuário logado, o nome é necessário no voto para se ter o contexto.&lt;/p&gt;

&lt;h3&gt;
  
  
  Modelagem relacional
&lt;/h3&gt;

&lt;p&gt;A modelagem relacional foi algo feito a contragosto já que não vejo necessidade de armazenar esse tipo de informação e queria simplificar ao máximo, mas dada a integração do &lt;strong&gt;eloquent ORM&lt;/strong&gt; optei por utilizar uma modelagem com &lt;strong&gt;Postgres&lt;/strong&gt;, mas algum sistema de dados em memória como &lt;strong&gt;Redis&lt;/strong&gt; seria melhor aproveitado.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Modelagem&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--Tt6AnZ2I--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/yodnvrauf8wl0ahvcxsj.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--Tt6AnZ2I--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/yodnvrauf8wl0ahvcxsj.png" alt="Modelagem do banco de dados" width="800" height="511"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;A modelagem pensada de forma relacional para se integrar com uma infra de &lt;strong&gt;postgres,&lt;/strong&gt; mas poderia estar estruturada direto com redis em memória para otimizar performance.&lt;/p&gt;

&lt;h3&gt;
  
  
  Realtime
&lt;/h3&gt;

&lt;p&gt;Um dos requisitos de um sistema de planning poker é funcionar em tempo real, dada a forma que os runtimes de PHP funcionam, existem poucas alternativas de websockets utilizando, a prática comum é a utilização de um serviço especializado na comunicação via websockets, como pusher, soketi, ably.&lt;/p&gt;

&lt;p&gt;Aproveitando as integrações do Laravel eu utilizei o sistema de &lt;strong&gt;broadcasts do Laravel&lt;/strong&gt; e o driver do &lt;strong&gt;Ably.&lt;/strong&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Fluxo
&lt;/h3&gt;

&lt;p&gt;Aqui o fluxo completo do aplicação, o usuário deve inserir o nome ao acessar a aplicação, pode entrar em uma sala através de link ou criar.&lt;/p&gt;

&lt;p&gt;Os eventos que ocorrem na API (backend) são enviados para a Ably que encaminha as mensagens por websocket para os usuários que estão escutando os eventos da sala. &lt;/p&gt;

&lt;p&gt;Cada um desses eventos de websocket é tratado na interface e a cada alteração no estado da partida e das votações reflete imediatamente na interface.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--ipq4O7O7--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/vjx4ctk6hh8r5gqjcnuy.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--ipq4O7O7--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/vjx4ctk6hh8r5gqjcnuy.png" alt="Fluxo detalhado" width="800" height="1108"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;h3&gt;
  
  
  Layout
&lt;/h3&gt;

&lt;p&gt;A parte de layout foi a mais dificil, eu não tinha pensado sobre a complexidade do layout, acreditei que seria mais simples mas ao me deparar com várias alternativas (flexbox, grid, table, position absolute) de implementação, cada uma com seus problemas (e evitando usar js para não aumentar a complexidade).&lt;/p&gt;

&lt;p&gt;Acabei optando depois de alguns testes, pela visualização com uma table e divs nas células posicionando os cartões, não fica muito adequado nas pontas mas foi o que ficou mais semelhante ao formato que eu buscava (formato de mesa de poker oval).&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--QrRhe6fG--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/vhrus8i0kjhbnwaze27p.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--QrRhe6fG--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/vhrus8i0kjhbnwaze27p.png" alt="Imagem do layout completo" width="800" height="392"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;O responsivo ficou para ser implementado posteriormente e foi dada pouca atenção ao design da aplicação, pois o foco era em velocidade de entrega e funcionalidade.&lt;/p&gt;

&lt;h3&gt;
  
  
  Finalização e deploy
&lt;/h3&gt;

&lt;p&gt;O deploy inicial foi preparado em uma VPS da Digital Ocean com Ubuntu, docker e PostgreSQL.&lt;/p&gt;

&lt;p&gt;Preparei as &lt;strong&gt;actions do GitHub&lt;/strong&gt; para &lt;strong&gt;validar os testes automatizados&lt;/strong&gt; e &lt;strong&gt;fazer a imagem docker&lt;/strong&gt; a partir do php oficial com apache.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--i1920jIW--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/u284tdn8r7g4urghc6hj.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--i1920jIW--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_800/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/u284tdn8r7g4urghc6hj.png" alt="Github actions" width="767" height="304"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;O deploy continua manual mas é um script simples, então também pode ficar para uma melhoria futura.&lt;/p&gt;

&lt;h3&gt;
  
  
  Primeiro uso
&lt;/h3&gt;

&lt;p&gt;Invés de lustrar muito eu quis mostrar o projeto conforme o que eu tinha conseguido produzir no período que eu me propus para não virar um projeto imaginário.&lt;/p&gt;

&lt;p&gt;Aconteceram alguns problemas durante o test drive:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;&lt;p&gt;Durante a primeira votação meu sistema morreu e não levantou mais, tinha esquecido de habilitar o docker restart, outro agravante é que eu não preparei o monitoramento então nem acompanhei o log de crash.&lt;/p&gt;&lt;/li&gt;
&lt;li&gt;&lt;p&gt;O sistema foi feito usando o Firefox, quando foram executar pelo Chrome o layout ficou quebrado.&lt;/p&gt;&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Mas já deu pra ter uma dimensão do que eu preciso corrigir e espero que em breve já esteja dando para utilizar como ferramenta principal para nosso planning poker.&lt;/p&gt;

&lt;p&gt;O código está publicado no github com licensa MIT&lt;br&gt;
&lt;a href="https://github.com/naaando/planningpoker"&gt;https://github.com/naaando/planningpoker&lt;/a&gt;&lt;/p&gt;

</description>
      <category>laravel</category>
      <category>scrum</category>
      <category>beginners</category>
      <category>webdev</category>
    </item>
    <item>
      <title>O elefante na sala (gerenciando produtos de software em PHP)</title>
      <dc:creator>Fernando da Silva Sousa</dc:creator>
      <pubDate>Wed, 15 Nov 2023 18:35:01 +0000</pubDate>
      <link>https://dev.to/naaando/o-elefante-na-sala-gerenciando-produtos-de-software-em-php-4afd</link>
      <guid>https://dev.to/naaando/o-elefante-na-sala-gerenciando-produtos-de-software-em-php-4afd</guid>
      <description>&lt;p&gt;Neste texto busco auxiliar lideranças na gestão de produtos de software em PHP, abordando o fenômeno que conhecemos como legado de software, insights sobre estratégias e como podemos implementar processos e ferramentas de qualidade com PHP. Se trata sobre minha experiência empírica e em bases de autores de gestão de projetos e processos ágeis.&lt;/p&gt;

&lt;p&gt;O PHP é uma linguagem amplamente usada, muito pela sua simplicidade, com servidor HTTP e camada de view abstraídos, com pouco conhecimento se pode fazer coisas realmente interessantes, é um processo diferente de linguagens fortemente tipadas, com compilação, estrutura, orientação a objetos obrigatória, etc. &lt;/p&gt;

&lt;p&gt;Funciona muito bem para hobby e desenvolvimento rápido de produtos simples, conforme a aplicação evolui precisa de uma arquitetura mais adequada, idealmente seguindo ou documentando padrões, aplicações web já foram feitas tantas vezes que emergiram padrões para nos auxiliar.&lt;/p&gt;

&lt;h1&gt;
  
  
  A origem do legado
&lt;/h1&gt;

&lt;p&gt;Muitos sistemas são construído na mentalidade de projeto, mas sistemas são mais parecidos com serviços, eles interagem com protocolos, com ecossistemas, bibliotecas e serviços, além de melhorias na própria plataforma em que foram desenvolvidos, eventualmente algum desses pontos precisa de atualização.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Os motivos principais para um sistema ser considerado legado são&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Dependências descontinuada&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;É a possibilidade mais remota, a não ser que uma tecnologia exótica com pouquíssimos usuários, se o planejamento foi bem feito durante a construção esse risco já deveria estar previsto. &lt;/p&gt;

&lt;p&gt;Trabalhar com sistemas open source também mitiga bem esse risco, usualmente outros provedores desse serviço também costumam emergir para ocupar o lugar e em ultima instância você pode incorporar a rotina de manutenção desse sistema por conta própria.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Descaso com atualizações&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Os softwares sempre tem novas versões, e existem razões para se preocupar em atualizá-los. A medida que a atualização de um sistema vai sendo postergada existe um efeito na segurança e outro pouco visível na produtividade, novas versões trazem novas soluções para os problemas, as documentações e tutoriais na internet começam a focar nas novidades.&lt;/p&gt;

&lt;p&gt;Qualquer sistema com a versão abaixo da LTS deveria ser tratado como um risco de segurança e impacto de performance.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Aumento na complexidade do projeto&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Existe na literatura técnica diversos registros de que ocorre um aumento exponencial da complexidade ao adicionar novos recursos a um sistema existente quando ele não possui uma boa arquitetura e seus débitos são acumulados.&lt;/p&gt;

&lt;p&gt;Um projeto pode ter sido concebido de forma mal estruturada ou pode ter ficado assim após os autores originais terem saído. De qualquer forma não houve atenção e habilidade suficientes para acompanhar as agendas de atualizações dos sistemas.&lt;/p&gt;

&lt;h1&gt;
  
  
  Dividir para fracassar
&lt;/h1&gt;

&lt;p&gt;A maioria dos sistemas não devem e não podem ser reescritos do zero. Qualidade não é um programa que pode ser instalado de maneira simples. Seu projeto chegou nesse estado e pode acontecer de novo até mesmo na fase inicial da instalação de um framework, desenvolvedores ruins costumam se escorar nessa solução e existe o risco de fazer um sistema pior que o primeiro.&lt;/p&gt;

&lt;p&gt;É uma ideia comum pensar em abandonar a tecnologia atual e apostar na escrita de um sistema novo, e na teoria é uma tarefa trivial pois é possível fazer alguns CRUDs por dia, então supõem que é possível parar de dar manutenção e funcionalidades ao sistema antigo e começar um sistema novo. Um projeto isolado para substituir no final, a medida que o tempo passa mais demandas vão sendo impostas sobre o sistema antigo, então começa a briga por recursos de desenvolvimento.&lt;/p&gt;

&lt;p&gt;Você incorre em dois problemas principais, você precisa entregar funcionalidades com a metade do contingente no sistema antigo, que é lento para implementar as coisas, e o novo sistema ainda não está pronto para produção.&lt;/p&gt;

&lt;h1&gt;
  
  
  &lt;strong&gt;Elevando os padrões&lt;/strong&gt;
&lt;/h1&gt;

&lt;p&gt;O maior efeito perceptível de incremento de qualidade é quando existe um consenso sobre. Satisfação dos desenvolvedores ao desenvolver, da gerencia sobre a produtividade e dos usuários quanto a confiabilidade, funcionalidade e performance do sistema.&lt;/p&gt;

&lt;p&gt;&lt;em&gt;Alguns pontos chave para tratar da qualidade da aplicação&lt;/em&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Revisão de código&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Os processos de revisão de código são de certo a parte mais importante pois é a partir da entrada de novos códigos que melhoramos ou pioramos o que existe, é preciso bloquear commits diretos para master/main, mesmo os desenvolvedores mais experientes não devem ter esse tipo de permissão. É necessário que outros desenvolvedores experientes na base de código avaliem, também é importante observar que se a nenhuma revisão aponta problemas e melhorias, a revisão não está sendo feita corretamente.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Implementação de pipelines&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Pipelines integram nos eventos do repositório e podem executar ações para validar se testes automáticos da qualidade do sistema continuam passando, validam se a forma de escrita está de acordo com a definição da equipe (via linters), executam implantações em servidores de teste e produção.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Monitoramento de defeitos e exceções&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;Não basta esperar a crítica dos clientes, é necessário fazer um monitoramento proativo de problemas e reportar para os clientes antes que eles precisem comunicar o problema, isso estabelece uma confiança na ferramenta, ferramentas como Sentry, Bugsnag, Datadog, Raygun, etc. conseguem sumarizar os erros tanto do frontend quanto do backend para que o problema possa ser corrigido o mais rápido possível, também é importante tratar dos falso positivos para que não tire a visibilidade dos problemas reais.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Estilização de código&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;O PHP tem um padrão de estilização de código definido pela &lt;strong&gt;PSR-12&lt;/strong&gt;, é uma boa prática segui-lo, mas também existem os padrões do Laravel, Symfony, e outros. É possível automatizar com o &lt;strong&gt;ecs&lt;/strong&gt; ou &lt;strong&gt;phpcs&lt;/strong&gt;, e no caso do Laravel, com o &lt;strong&gt;Laravel Pint&lt;/strong&gt;. &lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Análise estática e refatoração automatizada&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;O PHP é uma linguagem interpretada, isso implica em só saber que um código está com problema (seja sintático ou lógico) durante a execução. IDEs mais recentes introduzem algum tipo de validação sintática através do &lt;a href="https://langserver.org/"&gt;Language Server Protocol&lt;/a&gt;, também existem ferramentas para conseguir fazer essa análise de forma estática como &lt;strong&gt;PHPStan&lt;/strong&gt; e &lt;strong&gt;PSalm&lt;/strong&gt; que podem aprimorar a qualidade do código e evita bugs antes mesmo de entrar em produção.&lt;/p&gt;

&lt;p&gt;Para refatoração automatizada de código existem ferramentas  como Rector e Phabric, com o Rector é possível migrar automaticamente entre versões do PHP e bases de código legada para os padrões mais recentes usando regras personalizadas, frameworks também costumam criar regras para o Rector facilitando a atualização.&lt;/p&gt;

&lt;h1&gt;
  
  
  Conclusão
&lt;/h1&gt;

&lt;p&gt;O PHP é uma linguagem acessível mas exige uma atenção com qualidade assim como qualquer outra tecnologia para que seja produtiva e atenda as necessidade dos consumidores, ao atentar para se manter atualizado garantimos entregas, segurança e performance nos mantendo produtivos e competitivos mediante o mercado. Também é importante lembrar que assim como na engenharia tradicional, grandes saltos de produtividade advém de novas ferramentas e é importante incorporar o uso delas para se beneficiar.&lt;/p&gt;

</description>
      <category>management</category>
      <category>php</category>
      <category>legacy</category>
      <category>webdev</category>
    </item>
  </channel>
</rss>
