<?xml version="1.0" encoding="UTF-8"?><rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Blog da Alice Tech</title>
	<atom:link href="https://alice.com.br/tech/feed/" rel="self" type="application/rss+xml" />
	<link>https://alice.com.br/tech/</link>
	<description>Acompanhe conteúdos sobre tecnologia, IA e inovação na saúde e descubra como a Alice transforma o cuidado diário em uma rotina mais humanizada.</description>
	<lastBuildDate>Thu, 19 Feb 2026 18:43:50 +0000</lastBuildDate>
	<language>pt-BR</language>
	<sy:updatePeriod>
	hourly	</sy:updatePeriod>
	<sy:updateFrequency>
	1	</sy:updateFrequency>
		<item>
		<title>Autorização com OPA: Open Policy Agent</title>
		<link>https://alice.com.br/tech/autorizacao-com-opa-open-policy-agent/</link>
		
		<dc:creator><![CDATA[Alice]]></dc:creator>
		<pubDate>Thu, 20 Mar 2025 19:41:09 +0000</pubDate>
				<category><![CDATA[Alice]]></category>
		<guid isPermaLink="false">https://alice.com.br/tech/?p=225</guid>

					<description><![CDATA[<p>Como os times de engenharia da Alice trabalharam para lidar com os problemas relativos a Autorização e como a solução que escolhemos nos ajuda a resolvê-los.</p>
<p>O post <a href="https://alice.com.br/tech/autorizacao-com-opa-open-policy-agent/">Autorização com OPA: Open Policy Agent</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>A Alice é uma empresa de tecnologia com o propósito de tornar o mundo mais saudável. Mas, como toda empresa de tecnologia, precisa lidar com desafios comuns e decidir como vai endereçá-los. Este artigo explica um pouco dos problemas relativos a Autorização que enfrentamos, passa pelas alternativas que consideramos e mostra como a solução que escolhemos resolve esses problemas (e inevitavelmente acaba criando outros).</p>
<h2>O que é Autorização? Qual a diferença de Autenticação?</h2>
<p>Antes de entrar nos detalhes do tema, é importante relembrar a diferença entre Autenticação e Autorização, dois conceitos que muitas vezes andam juntos mas são fundamentalmente diferentes.</p>

<p>Em resumo, <strong>Autenticação</strong> é o processo de Identificação de um usuário, que garante que ele é quem diz ser. Já <strong>Autorização</strong> é o processo que indica se um usuário identificado (ou não) tem a permissão para realizar determinadas ações dentro do sistema.</p>

<p>Soluções e Frameworks que temos disponíveis para usar podem lidar com um ou ambos aspectos, e é importante saber disso porque pode inviabilizar uma escolha. Você pode, por exemplo, ser obrigado a usar o aspecto de Autenticação da solução para que o aspecto de Autorização funcione e, dependendo do caso (como foi na Alice), isso pode não ser desejado.</p>

<h2>Tipos comuns de Autorização</h2>
<p>Temos alguns tipos diferentes de Autorização, que cobrem a maior parte das necessidades comuns dos sistemas de mercado. Aqui descrevo os principais:</p>

<ul>
<li><strong>Role-Based Access Control (RBAC)</strong>: o tipo mais comum de controle de acesso, consiste em atribuir papéis (roles) aos usuários e definir o que cada papel pode fazer. A ideia é que papéis possam ser atribuídos ou revogados a qualquer momento, e o sistema possa mudar seu comportamento imediatamente após os papéis mudarem. Os papéis costumam ser uma informação curta, que pode ser facilmente trafegada dentro de Tokens JWT por conveniência.
<ul>
<li>Exemplo: Joãozinho assume o papel de analista de Operações e ganha a capacidade de editar quaisquer Membros (como chamamos os pacientes da Alice) no sistema.</li>
</ul>
</li>
</ul>

<ul>
<li><strong>Attribute-Based Access Control (ABAC)</strong>: controle de acesso baseado em atributos do usuário e / ou do recurso sendo acessado.
<ul>
<li>Exemplo: Joãozinho pode editar um Membro do sistema se seu atributo do usuário isAdmin = true, ou se o membro tem o atributo isPublic = true.</li>
</ul>
</li>
</ul>

<ul>
<li><strong>Relationship-Based Access Control (ReBAC)</strong>: caso específico de ABAC onde uma permissão é concedida se há um relacionamento específico entre o usuário e o recurso sendo acessado.
<ul>
<li>Exemplo: Joãozinho pode editar os dados de um Membro se o registro representar ele mesmo ou um dependente dele.</li>
</ul>
</li>
</ul>

<p>Seu sistema pode ter necessidades de Autorização em qualquer um dos níveis. No caso, as regras que a Alice precisa suportar são RBAC em sua maioria, com alguns casos de ABAC e ReBAC. Isso significa que a solução escolhida precisa também suportar esses modelos de autorização; somente RBAC não é suficiente (ou envolveria muito improviso para fazer).</p>

<h2>Nossa abordagem original de Autorização</h2>
<p>Sendo uma empresa de saúde, a Alice evidentemente tem muito contato com informações pessoais e de saúde. Portanto, um mecanismo de Autorização é essencial para garantir que dados não sejam acessados ou modificados por pessoas não autorizadas, sejam médicos, enfermeiros ou até o time de atendimento operacional.</p>
<p>Inicialmente optamos por manter a camada de Autorização junto à nossa camada compartilhada de acesso a dados (Data-Layer), que já realiza outras atribuições, como tokenização dos registros, de-identificação e afins. Através de uma DSL fluida, avaliamos quatro parâmetros essenciais para tomar uma decisão de Autorização:</p>
<ul>
<li><strong>Root Service</strong>: o serviço do qual se originou a solicitação. Isso é importante pois um mesmo usuário pode ter permissões distintas em sistemas diferentes.</li>
<li><strong>Subject</strong>: o usuário atual.</li>
<li><strong>Resource</strong>: o recurso que se deseja acessar.</li>
<li><strong>Action</strong>: a ação que o usuário deseja realizar no recurso. No contexto de acesso a dados, consideramos as ações CRUD (Create, Read, Update, Delete).</li>
</ul>

<p>Também partimos do princípio de “<strong>Least Privilege</strong>”, o que significa que qualquer acesso precisa necessariamente ser liberado via a escrita de Policies, ou regras de autorização, na DSL supracitada. Caso contrário, o acesso por padrão é negado. Essas regras são deployadas junto ao Data-Layer, e toda alteração das mesmas exige uma nova versão em produção para ser efetiva e impactar os usuários finais.</p>

<h2>Problemas</h2>
<p>A abordagem que inicialmente escolhemos nos permite grande liberdade na tomada de decisões de Autorização, mas vem com os seguintes contrapontos:</p>
<ul>
<li><strong>Acoplamento com o Data-Layer</strong>: não podemos alterar policies sem redeployar o serviço; regras de certos domínios acessam diretamente dados de outros domínios sem passar pelo serviço correspondente, quebrando o encapsulamento. Gera acoplamento da própria camada de dados com os modelos servidos por ela.</li>
<li><strong>Testes</strong>: não é trivial escrever testes das policies e é comum haver erros em tempo de desenvolvimento descobrindo que esquecemos de incluir uma policy necessária.</li>
<li><strong>Isolamento (“siloing”)</strong>: a alteração de policies é altamente técnica e só pode ser feita por desenvolvedores back-end. Não há UI ou facilitador para isso.</li>
<li><strong>Escopo</strong>: limitado somente à camada de acesso a dados; isso significa que, com esse mecanismo, não temos capacidade de tomar decisões de exibição de itens visuais no front-end de acordo com o perfil do usuário, por exemplo.</li>
</ul>

<p>Com esses aspectos em mente, olhamos para o mercado procurando por uma solução de Autorização que suportasse as nossas necessidades, ao mesmo tempo que mitigasse a maior parte possível desses problemas.</p>

<h2>Alternativas consideradas</h2>
<p>Um ponto importante na hora de elencar a solução: não tínhamos a intenção de mudar o mecanismo de Autenticação utilizado atualmente, o que significa que soluções que fazem a “venda casada” com Autorização (por exemplo, <a href="https://www.keycloak.org/">keycloak</a> e <a href="https://www.aserto.com/">aserto</a>) não resolveriam nosso problema.</p>

<p>Assim sendo, encontramos duas alternativas mais em linha com o que buscávamos:</p>
<ul>
<li><a href="https://www.osohq.com/docs">Oso Cloud</a></li>
<li><a href="https://www.openpolicyagent.org/">Open Policy Agent</a> (OPA)</li>
</ul>

<p>Após uma análise minuciosa, preferimos seguir com o OPA, em vez do Oso Cloud, devido a alguns fatores:</p>
<ul>
<li>o Oso é menos flexível e a migração das nossas policies atuais seria mais trabalhosa.</li>
<li>o Oso é um SaaS e tem um custo associado; com nosso volume de requests esse custo pode ser bem significativo.</li>
<li>o Oso tem uma UI para edição de policies, mas para escrever ABAC / ReBAC é preciso escrever as regras na linguagem Polar.</li>
</ul>

<p>Por outro lado, o OPA tem várias características que o tornam uma boa opção para a gente. É open-source, utilizado por algumas grandes empresas, flexível e orientado à nuvem. É escrito em Golang, altamente performático e capaz de responder a um grande volume de requests de Autorização na casa dos milissegundos – característica essencial para nosso caso, pois teríamos que externalizar as chamadas de autorização, já pagando o custo de latência de rede.</p>
<p>Outra característica que tornava o OPA mais atrativo era que as regras são escritas na linguagem <a href="https://www.openpolicyagent.org/docs/latest/policy-language/">Rego</a> , que apesar de não ser tão simples é flexível o bastante para implementar RBAC, ABAC, ReBAC e outros tipos de controle de acesso. As regras e dados de autorização são alimentados no serviço e ficam disponíveis em memória, e podem ser substituídos em tempo de execução.</p>
<p>Além disso, o usuário do OPA é quem define o formato do input (os dados de autorização relativos a um dado request) e o formato do output (quais permissões são calculadas e retornadas), então ele pode ser usado em mais de um contexto.</p>

<p>Além de tudo isso, há um forte <a href="https://www.openpolicyagent.org/ecosystem/">ecossistema</a> em torno do OPA, com várias ferramentas construídas para facilitar sua adoção em escala, e até mesmo uma versão <a href="https://www.styra.com/enterprise-opa/">Enterprise</a>.</p>

<h2>Como o OPA endereça nossos problemas</h2>
<ul>
<li><strong>Acoplamento com o Data-Layer</strong>: o deploy de novas policies é feito diretamente no OPA e não precisa nem redeployar o serviço, pois ele tem suporte a hot-reload (apontando para um bucket do S3, por exemplo). O OPA pode também ter uma base de dados de Autorização, que torna mais simples a implementação de ReBAC em vez de ficar buscando esses dados em real-time no momento do request.</li>
<li><strong>Testes</strong>: toda policy pode e deve ser testada unitariamente; os testes são rápidos e podem ser incluídos na sua pipe de CI. Em termos de garantir que os dados esperados são efetivamente enviados para o OPA, essa responsabilidade fica com os testes do seu sistema.</li>
<li><strong>Isolamento (“siloing”)</strong>: infelizmente o OPA não resolve este ponto muito bem, pois é necessário escrever código e não há UI que facilite o processo. Mas um ponto positivo é que quem cuida das policies não precisa ser o mesmo time dono dos dados, pode ser um time focado nisso.</li>
<li><strong>Escopo</strong>: dependendo de como forem escritas as regras, pode-se usar um mesmo servidor do OPA para atender a requests de Autorização de várias fontes. Na Alice, conseguimos escrever de uma forma que a mesma regra calcula permissões para o front-end (quando tenho dados somente do usuário acessando) e para o back-end (quando tenho as demais informações de recurso e ação, por exemplo).</li>
</ul>

<h2>Conclusão</h2>
<p>Apesar de ser um problema bastante comum no desenvolvimento de sistemas, pode ser desafiador encontrar uma solução de Autorização que case bem com as suas necessidades. É importante estudar com calma as alternativas, realizar Provas de Conceito em escopos menores e ter um bom plano de migração quando já há bastante coisa construída no esquema atual.</p>

<p>Esse é o tipo de problema que faz muito sentido ser endereçado pelo <strong>time de Plataforma,</strong> pois causa um grande impacto ao longo de todas as camadas de desenvolvimento, e precisa de grande apoio das lideranças para efetivamente sair do papel.</p>

<h1>&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;&#8212;-</h1>

<p>Alice is a technology company with the mission of making the world healthier. But like any tech company, it faces common challenges and must decide how to address them. This article explains some of the authorization-related problems we encountered, explores the alternatives we considered, and shows how the solution we chose solves these problems (while inevitably creating others as well ).</p>
<h2><b>What is Authorization? How is it Different from Authentication?</b></h2>
<p>Before diving into the details, it’s important to recall the difference between Authentication and Authorization—two concepts that often go together but are fundamentally different.</p>
<p>In short, <b>Authentication</b> is the process of identifying a user, ensuring that they are who they claim to be. <b>Authorization</b>, on the other hand, is the process of determining whether an identified (or even unidentified) user has permission to perform certain actions within the system.</p>
<p>The solutions and frameworks available may handle one or both aspects, which is important to consider when making a choice. You might, for example, be forced to use a solution’s Authentication component just to make its Authorization component work. Depending on the case (as was true for Alice), this may not be desirable.</p>
<h2><b>Common Types of Authorization</b></h2>
<p>There are several types of Authorization, covering most of the common needs of modern systems. Here are the main ones:</p>
<ul>
<li><b>Role-Based Access Control (RBAC)</b>: The most common type of access control, in which roles are assigned to users, defining what each role can do. Roles can be assigned or revoked at any time, and the system adjusts behavior accordingly.
<ul>
<li><i>Example</i>: Bob is assigned the role of Operations Analyst and gains the ability to edit any Member (as we call the patients here in Alice) in the system.</li>
</ul>
</li>
</ul>

<ul>
<li><b>Attribute-Based Access Control (ABAC)</b>: Access control based on user attributes and/or the attributes of the resource being accessed.
<ul>
<li><i>Example</i>: Bob can edit a Member in the system if his user attribute isAdmin = true, or if the Member has the attribute isPublic = true.</li>
</ul>
</li>
</ul>

<ul>
<li><b>Relationship-Based Access Control (ReBAC)</b>: A specific case of ABAC where permission is granted based on a specific relationship between the user and the accessed resource.
<ul>
<li><i>Example</i>: Bob can edit a Member’s data if the record represents himself or one of his dependents.</li>
</ul>
</li>
</ul>

<p>A system may require Authorization at any of these levels. In Alice’s case, most rules follow RBAC, with some cases requiring ABAC and ReBAC. This means the chosen solution must support these Authorization models—RBAC alone wouldn’t be sufficient (or would require excessive workarounds).</p>
<h2><b>Our Initial Approach to Authorization</b></h2>
<p>As a healthcare company, Alice deals extensively with personal and medical information, making a robust Authorization mechanism essential to ensure that data is accessed or modified only by authorized individuals—whether doctors, nurses, or operational support teams.</p>
<p>Initially, we decided to implement Authorization within our shared Data-Layer, which already handled tasks like tokenizing records, de-identifying data, and other privacy and security measures. Using a fluid Domain Specific Language (code homebrewed for this purpose), we evaluated four key parameters to make Authorization decisions:</p>
<ul>
<li><b>Root service</b>: The service where the request originated (important because a user might have different permissions in different systems).</li>
<li><b>Subject</b>: The current user.</li>
<li><b>Resource</b>: The resource being accessed.</li>
<li><b>Action</b>: The action the user wants to perform on the resource (CRUD: Create, Read, Update, Delete).</li>
</ul>
<p>We also followed the <b>Least Privilege</b> principle, meaning access must be explicitly granted via written Policies in the DSL—otherwise, access is denied by default. These rules were deployed alongside the Data-Layer, requiring a new production release for any changes to take effect.</p>
<h2><b>Problems</b></h2>
<p>While this approach gave us flexibility in Authorization decisions, it also introduced some drawbacks:</p>
<ul>
<li><b>Tight coupling with the Data-Layer</b>: Policies could not be changed without redeploying the service; some domain rules accessed data from other domains directly, breaking encapsulation.</li>
<li><b>Testing challenges</b>: Writing tests for policies wasn’t trivial, leading to frequent runtime errors when missing a necessary policy.</li>
<li><b>Expertise</b>: Policy modifications were highly technical and could only be done by backend developers—there was no UI or other tooling to facilitate this.</li>
<li><b>Scope limitations</b>: The mechanism only covered data access, meaning we couldn’t use it for UI-based authorization (e.g., controlling which UI elements should be displayed based on a user’s role).</li>
</ul>
<p>With these challenges in mind, we looked for an Authorization solution that met our needs while mitigating as many of these issues as possible.</p>
<h2><b>Considered Alternatives</b></h2>
<p>A key requirement in our search: we had no intention of changing our existing Authentication mechanism. This meant solutions that bundled Authentication and Authorization together (such as <a href="https://www.keycloak.org/">Keycloak</a> or <a href="https://www.aserto.com/">Aserto</a>) wouldn’t work for us.</p>
<p>Instead, we found two alternatives that better aligned with our needs:</p>
<ul>
<li><a href="https://www.osohq.com/docs"><b>Oso Cloud</b></a></li>
<li><a href="https://www.openpolicyagent.org/"><b>Open Policy Agent (OPA)</b></a></li>
</ul>
<p>After a thorough analysis, we decided to go with OPA instead of Oso Cloud for several reasons:</p>
<ul>
<li>Oso is less flexible, and migrating our existing policies would be more complex.</li>
<li>Oso is a SaaS solution with associated costs, which could be significant given our request volume.</li>
<li>Oso provides a UI for policy editing, but writing ABAC/ReBAC rules still requires using the Polar language.</li>
</ul>
<p>On the other hand, OPA has several characteristics that make it a great option for us. It is open-source, used by some large companies, flexible, and cloud-oriented. It is written in Golang, highly performant, and capable of handling a high volume of authorization requests in milliseconds—an essential feature for our case since we needed to externalize authorization calls while already accounting for network latency costs.</p>
<p>Policies are written in the <a href="https://www.openpolicyagent.org/docs/latest/policy-language/">Rego</a> language, which, although not the simplest, is flexible enough to implement RBAC, ABAC, ReBAC, and other access control models. Authorization rules and data are fed into the service, stored in memory, and can be replaced at runtime.</p>
<p>OPA users define the input format (the authorization data related to a given request) and the output format (which permissions are calculated and returned), allowing it to be used in multiple contexts.</p>
<p>Beyond all this, OPA has a strong <a href="https://www.openpolicyagent.org/ecosystem/">ecosystem</a>, with various tools built to facilitate large-scale adoption and even an <a href="https://www.styra.com/enterprise-opa/">Enterprise</a> version.</p>
<h2><b>How OPA Solves Our Problems</b></h2>
<ul>
<li><b>Decoupling from the Data-Layer</b>: Policies are deployed directly to OPA, eliminating the need to redeploy the service. OPA also supports an Authorization database, making it easier to implement ReBAC without real-time data lookups.</li>
<li><b>Improved Testing</b>: Policies can and should be unit tested, with fast execution that integrates into CI pipelines. Ensuring the right data reaches OPA remains the responsibility of system tests.</li>
<li><b>Less Expertise</b>: While OPA still requires writing code (lacking a UI for policy management), policy ownership and authoring can be assigned to a dedicated team rather than the teams managing the data itself.</li>
<li><b>Expanded Scope</b>: A single OPA instance can handle Authorization requests from multiple sources. At Alice, we structured our policies so the same rule could determine permissions for both the frontend (based on user attributes) and the backend (considering additional resource and action information).</li>
</ul>
<h2><b>Conclusion</b></h2>
<p>Despite being a common challenge in system development, finding an Authorization solution that fits your needs can be difficult. It&#8217;s crucial to carefully study alternatives, run Proofs of Concept in limited scopes, and have a solid migration plan when transitioning from an existing system.</p>
<p>This is the kind of problem that makes sense to be handled by a <b>Platform Team</b>, as it impacts all layers of development and requires strong leadership support to be successfully implemented.</p>


<p>O post <a href="https://alice.com.br/tech/autorizacao-com-opa-open-policy-agent/">Autorização com OPA: Open Policy Agent</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>Migrar para Next.js e SSR: desafios e aprendizados</title>
		<link>https://alice.com.br/tech/os-desafios-de-migrar-para-uma-stack-de-next-js-stencil-e-ssr/</link>
		
		<dc:creator><![CDATA[Alice]]></dc:creator>
		<pubDate>Mon, 25 Nov 2024 19:58:43 +0000</pubDate>
				<category><![CDATA[Alice]]></category>
		<guid isPermaLink="false">https://alice.com.br/tech/?p=216</guid>

					<description><![CDATA[<p>Como os times de engenharia da Alice trabalharam para implementar nova stack no site que melhorou o carregamento da página em 50% e elevou a experiência do usuário.</p>
<p>O post <a href="https://alice.com.br/tech/os-desafios-de-migrar-para-uma-stack-de-next-js-stencil-e-ssr/">Migrar para Next.js e SSR: desafios e aprendizados</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>O site da Alice, assim como o da maior parte das empresas de tecnologia hoje, nasceu como uma página estática. Mas, ao longo do tempo, incorporou uma gama de funcionalidades que refletem nossos diferenciais como healthtech. Viabilizar essa transição, no entanto, exigiu migrar toda sua base de código para um novo framework, um projeto árduo que gerou melhora substancial na experiência do usuário, na performance do site e reduziu os custos de manutenção.</p>
<p>Hoje, o projeto faz uso do Next.js, num contexto de Server-Side Rendering (SSR) e um design system baseado em Stencil. Essa migração, porém, gerou desafios técnicos importantes que exigiram mudanças mais amplas em nossa arquitetura.</p>
<p>Neste artigo, exploramos os problemas e desafios que enfrentamos ao adotar essa stack, com foco em &#8220;piscas&#8221; na interface com o usuário final, e como os solucionamos e garantimos a melhor experiência e funcionalidades para quem está na ponta.</p>
<h2>Next.js, Stencil e SSR</h2>
<p>Quando criamos o site adotamos o Nuxt 2 como framework. Foi a escolha apropriada para o momento da empresa e as opções disponíveis à época. À medida que a Alice se desenvolveu, porém, o projeto foi crescendo em complexidade. Em poucos anos, implementamos subprodutos no site como uma <a href="https://alice.com.br/calculadora-de-saude">calculadora de saúde</a>, um <a href="https://www.alice.com.br/simulador">simulador de planos</a> e um sistema de consulta à nossa <a href="https://alice.com.br/rede-credenciada">rede credenciada</a>.</p>
<p>Migrar para o Nuxt 3 se provou uma opção indevida – tratava-se de um framework ainda imaturo que, por características de nossa base de código, exigiria tanto esforço quanto o necessário para migrar para outro framework. Em vez disso, optamos pelo Next.js.</p>
<p>Qualquer migração, porém, traz desafios. No nosso caso, precisávamos integrar perfeitamente uma aplicação em Next.js em SSR com o design system da Alice, baseado em Stencil.js, que exporta <a href="https://developer.mozilla.org/en-US/docs/Web/API/Web_components">web components</a> que podem ser encapsulados para React.</p>
<p>Imediatamente, enfrentamos problemas: um constante &#8220;pisca&#8221; na tela, que afetava negativamente a experiência do usuário, prejudicava as métricas do Core Web Vitals e reduzia a performance de nossas páginas em buscas no Google.</p>
<p>Uma investigação revelou que esse problema, conhecido como &#8220;flash of unstyled content&#8221; (FOUC), resultava da interação entre nosso design system, em Stencil.js, com projetos em SSR, como o Next.js. Mais especificamente, tratava-se de problemas na etapa de hidratação da página.</p>
<h2>Hidratação</h2>
<p>Vamos comparar a construção de uma página web com a montagem de uma casa. Inicialmente, você organiza a casa com móveis essenciais e decoração, preparando-a para receber visitas. Esse processo se assemelha à pré-renderização de uma página no Next.js, onde a estrutura básica é montada no lado servidor antes de qualquer interação do usuário.</p>
<p>Quando alguém visita a casa, não se limita a observar os móveis; interage com o ambiente, abre portas ou acende luzes. Na web, essa interação é possível graças à &#8220;hidratação&#8221;. Após a página ser carregada, os elementos se tornam interativos, permitindo ao usuário realizar ações como cliques e toques.</p>
<h2>Como era em uma stack baseada em Nuxt 2</h2>
<p>Numa stack baseada em Nuxt 2 já conseguíamos utilizar os Web components do design system encapsulados para Vue, mas eles eram considerados como client components. Ou seja, toda a hidratação e construção da página era feita do lado do cliente/navegador, prejudicando assim o tempo total de carregamento e, consequentemente, as notas do Core Web Vitals do site como um todo.</p>
<p>O projeto já tinha outros problemas relacionados a performance e experiência de desenvolvimento, pois era muito desafiador escalar páginas mantendo uma boa performance combinado com uma boa experiência de codificação e implementação de testes (unitários e e2e).</p>
<p>Um dos pontos que identificamos como defasado no projeto era a versão do Vue utilizada pelo Nuxt 2, pois o framework estava travado na versão 2.6.14 do Vue, que já era considerada legado. Isso nos impedia de atualizar em relação a outras soluções, como por exemplo o testing-library, cypress, design system, storybook, node, etc.</p>
<p>Além disso, identificamos também outros problemas de experiência de desenvolvimento como auto importação de arquivos em testes, mock de endpoints e store, tempo elevado de execução de build, test e lint.</p>
<h2>Como a página operava no Next.js</h2>
<p>No entanto, no Next.js, apesar de não passarmos pelos problemas citados acima, ainda precisávamos resolver a questão da hidratação dos componentes do Design System com o Next server.</p>
<p>Tecnicamente, a hidratação vincula o HTML pré-renderizado ao JavaScript necessário para tornar a página interativa. Então, quando o navegador carrega a página, o JavaScript é executado, permitindo interações – e esse processo é conhecido como hidratação. Ele inicializa a aplicação no lado do cliente após o carregamento, reativando event handlers e estados previamente definidos no HTML estático.</p>
<p>Em um aplicativo Next.js, a página é parcialmente pré-renderizada no servidor e entregue como HTML estático. Em seguida, o JavaScript necessário para sua interatividade é enviado e executado pelo navegador. Durante essa execução, ocorre a hidratação, onde o React reconecta os manipuladores de eventos e estados à estrutura de componentes já renderizada. Esse intervalo de tempo foi o que causou o &#8220;pisca&#8221; em nossa página.</p>
<p>Embora o Stencil já esteja implementando suporte dos web components para SSR, não poderíamos esperar o lançamento dessa funcionalidade, então por meio de uma série de estudos e benchmarking, conseguimos encontrar uma solução entre SSR e client web components.</p>
<p>A ideia principal era garantir que os web components do design system chegassem no cliente final totalmente hidratados e, para isso, criamos um servidor customizado em node e substituímos pelo Next server padrão onde combinamos recursos de renderização do Next com a hidratação do Stencil nos componentes do design system antes mesmo da resposta chegar no navegador.</p>
<p>Essa camada funciona especificamente para páginas com conteúdos totalmente estáticos, então também precisávamos encontrar uma solução para páginas dinâmicas. Para isso, usamos um conceito de Provider, que se trata da injeção de um componente em React responsável por hidratar os componentes do design system. Tudo isso foi feito de forma transparente para o usuário final, justamente na camada de Layout, ou seja, uma camada que age logo depois da resposta do servidor no navegador e antes do usuário receber a página totalmente renderizada.</p>
<p>Observação importante: A proposta final do Stencil é usarmos os web components como server components. Esse suporte foi disponibilizado recentemente e estamos realizando uma série de testes para consolidar de vez o Stencil + Nextjs + SSR.</p>
<h2>Resultados</h2>
<p>Os resultados foram observados imediatamente. Nossos Core Web Vitals subiram de 72 para 90 na comparação com a implementação em Nuxt 2, com os escores de SEO saltando de 61 para 100.</p>
<p>Em média, o tempo de carregamento foi reduzido em 50%.</p>
<h2>A logística da migração</h2>
<p>Encontrar a solução técnica é, porém, apenas metade do caminho. Só conseguiríamos extrair valor dessa iniciativa quando implementássemos a nova stack em toda nossa base de código, um processo trabalhoso e arriscado.</p>
<p>Dois times se dedicaram a realizar a migração: o squad de engenharia de produto de vendas, que é formalmente responsável pelo site, além de uma série de outros sistemas e entregas; e o time de plataforma em engenharia.</p>
<p>A primeira grande decisão a ser tomada era entre migrar de uma só vez ou reescrever gradualmente o projeto. Ambas as abordagens exigiriam esforço significativo. No entanto, a reescrita gradual permitiria que realizássemos em paralelo a transição para o Next.js com as entregas regulares do squad de vendas. Além disso, poderíamos monitorar a performance e os resultados da migração de cada funcionalidade, gerando aprendizados contínuos e refinamentos a cada página.</p>
<p>Optamos, então, por reescrever gradualmente todo o projeto, começando pela página inicial, avaliando métricas relevantes como conversão e performance por meio de testes A/B. O resultado foi uma implementação suave, acelerada e bem-sucedida, demarcando o modelo para migrações semelhantes no futuro.</p>

<h2><b>____________________________________________________________________</b></h2>
<h2>The challenges of migrating to a Next.js, Stencil and SSR stack</h2>
<p><i>How Alice&#8217;s engineering teams implemented a new technology stack for our website, improving load times by 50% and enhancing user experience.</i></p>
<p>Alice&#8217;s website, like many technology companies today, started as a static page. As we evolved, we integrated several functionalities that highlight our unique position as a healthtech company. To support this transition, we migrated the entire codebase to a new framework, a taxing project that yielded substantial improvements in user experience, website performance, and slashed maintenance costs.</p>
<p>Our current tech stack is based on Next.js with Server-Side Rendering (SSR) and a design system powered by Stencil. This migration involved significant technical challenges that necessitated broader architectural changes.</p>
<p>In this article, we delve into the specific problems and challenges we encountered while adopting this stack, with a particular focus on addressing &#8220;flashes&#8221; in the interface. We&#8217;ll discuss how we overcame these issues to ensure the best possible experience and functionality for our end-users.</p>
<h3>Next.js, Stencil and SSR</h3>
<p>When we started the website, we adopted the Nuxt 2 framework. It was a suitable choice given the company&#8217;s stage and the available options at the time. As Alice evolved, however, the project&#8217;s complexity increased. Within a few years, we implemented subproducts into the website including a <a href="https://alice.com.br/calculadora-de-saude">health calculator</a>, a <a href="https://www.alice.com.br/simulador">plan simulator</a> and a system allowing users to browse our accredited network of <a href="https://alice.com.br/rede-credenciada">health community</a>.</p>
<p>Migrating to Nuxt 3 proved insufficient &#8211; it was a framework still in its early stages, and due to specificities in our codebase, it would require as much effort to implement as a migration to another framework. Instead, we opted for Next.js.</p>
<p>Any migration, however, bears challenges. In our case, we needed to perfectly integrate an application based on Next.js in SSR with Alice&#8217;s design system, oriented around Stencil.js, that exports web components that can be encapsulated for React.</p>
<p>We immediately faced a significant challenge: a constant screen flashing, which negatively impacted user experience, depressed Core Web Vitals, and reduced the website&#8217;s performance in Google search results.</p>
<p>An investigation revealed that this issue, known as ‘Flash of Unstyled Content’ (FOUC), was a consequence of the interaction between our Stencil.js design system and SSR projects such as Next.js. More specifically, it was a problem during the page&#8217;s hydration step.</p>
<h3>Hydration</h3>
<p>Creating a webpage is somewhat like setting up your home. First, you organize your living room with essential furniture and decoration, preparing it to host visits. This process is similar to prerendering a Next.js page, where its basic structure is built on the server before any user interaction.</p>
<p>When someone visits that apartment, they don&#8217;t just look at the furniture; they interact with their surroundings, turning on lights, opening doors, and so on. On the web, these interactions are made possible by &#8216;hydration&#8217;. Once the page loads, all elements become interactive, allowing users to click, tap, and more.</p>
<h3>Using a Nuxt 2 stack</h3>
<p>In a Nuxt2 stack, we were able to utilize web components from the design system encapsulated for Vue, but they were considered client components. The whole hydration and construction of the web page happened at the client side, hampering overall load times and, consequently, the whole website&#8217;s Core Web Vitals.</p>
<p>We had already identified other problems related to performance and development experience. It was very challenging to scale up pages maintaining good performance, an effective coding experience and implementing e2e and unit tests.</p>
<p>One of the main improvement points was the version of Vue used by Nuxt 2: we were still stuck with Vue&#8217;s legacy 2.6.14 version. That prevented us from updating other solutions, such as testing-library, cypress, design system, storybook, node, etc.</p>
<p>We also identified other developer experience problems such as auto-importing of test files, endpoint mocks and store, and overly long times for executing build, test, and lint.</p>
<h3>How the page operated under Next.js</h3>
<p>Under Next.js, though we didn&#8217;t encounter the same issues, we still needed to solve the problems involved in hydrating the design system components with the Next server.</p>
<p>Technically, the hydrating step connects a pre-rendered HTML with the JavaScript needed to make the page interactive. In other words, when the browser loads the webpage, it executes the JavaScript, allowing for interactions – and this process is known as hydration. It starts the application in the client side after loading, reactivating event handlers and states previously defined in the static HTML.</p>
<p>In a Next.js application, the page is partially pre-rendered on the server and delivered as static HTML. Subsequently, the necessary JavaScript for interactivity is sent and executed by the browser. During this execution, hydration occurs, where React reconnects event handlers and state to the already rendered component structure. This time interval caused the flash on our page.</p>
<p>Although Stencil was developing SSR support for web components, we couldn&#8217;t wait for the launch. Through research and benchmarking, we found a solution between SSR and client web components.</p>
<p>Our primary goal was to ensure fully hydrated design system components on the client side. To make it happen, we created a custom Node.js server to replace the standard Next server, combining Next&#8217;s rendering resources with Stencil&#8217;s hydration in the design system components before the response reached the browser.</p>
<p>That layer worked well for fully static pages, but we also needed to find a solution for dynamic pages. So, we implemented a Provider concept, injecting a React component responsible for hydrating design system components. All that happened in the Layout layer, that is, a layer activated as soon as the server responds to the browser and before the end user receives the fully rendered webpage.</p>
<p>It&#8217;s worth noting that Stencil&#8217;s final proposal involves using web components as server components. While this feature is now available, we&#8217;re currently conducting several tests to fully integrate Stencil, Next.js and SSR.</p>
<h3>Results</h3>
<p>Results were observed immediately. Our Core Web Vitals rose from 72 to 90 compared to the Nuxt 2 implementation, with SEO scores jumping from 61 to 100.</p>
<p>Loading improved 50% on average.</p>
<h3>Migration logistics</h3>
<p>Finding a technical solution is, however, only half the trouble. We could only generate value from this initiative once we had implemented the new stack throughout our codebase &#8211; a long and risky endeavor.</p>
<p>Two teams were tasked with the migration: the engineering team in the sales squad, formally responsible for the website as well as other systems; and the engineering platform team.</p>
<p>The first big decision was whether to migrate the entire project at once or to gradually refactor it. While both approaches required substantial effort, a gradual refactoring would allow us to parallelize the transition with the sales squad&#8217;s ongoing work. Besides, we could monitor performance and results for each functionality, enabling continuous learning and refining at every step.</p>
<p>Ultimately, we chose to gradually refactor the entire project, starting with the homepage, assessing relevant metrics such as conversion and performance through A/B tests. The end result was a smooth, quick, and successful implementation, setting the standard for future migrations.</p>
<p>O post <a href="https://alice.com.br/tech/os-desafios-de-migrar-para-uma-stack-de-next-js-stencil-e-ssr/">Migrar para Next.js e SSR: desafios e aprendizados</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>IA aplicada ao customer experience na Alice</title>
		<link>https://alice.com.br/tech/inteligencia-artificial-aplicada-no-customer-experience/</link>
		
		<dc:creator><![CDATA[Alice]]></dc:creator>
		<pubDate>Tue, 01 Oct 2024 18:49:33 +0000</pubDate>
				<category><![CDATA[Alice]]></category>
		<guid isPermaLink="false">https://alice.com.br/tech/?p=202</guid>

					<description><![CDATA[<p>Como a Alice utiliza inteligência artificial para elevar a qualidade do atendimento ao cliente.</p>
<p>O post <a href="https://alice.com.br/tech/inteligencia-artificial-aplicada-no-customer-experience/">IA aplicada ao customer experience na Alice</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>O setor de saúde vai muito além de hospitais com equipe médica e time de enfermagem. Em volta desse sistema, há uma enorme estrutura responsável por cuidar de tarefas essenciais do dia a dia dos pacientes, como pagamentos, autorizações de procedimentos, esclarecimento de dúvidas administrativas e cobranças. Otimizar isso tudo e garantir segurança e customer experience de excelência é um desafio.</p>
<p>Neste artigo, vamos mostrar como a Alice está utilizando inteligência artificial (IA) para elevar ainda mais a qualidade do atendimento dos nossos membros &#8211; como chamamos os clientes aqui na Alice.</p>
<p>Entre todas as áreas do nosso negócio, o ecossistema administrativo é um dos que mais podem gerar frustrações para os usuários. Em um <a href="https://www1.folha.uol.com.br/equilibrioesaude/2024/04/queixas-sobre-rescisoes-unilaterais-de-planos-de-saude-coletivos-sobem-99.shtml" target="_blank" rel="nofollow noopener">setor que está entre os menos populares no Brasil</a>, queremos garantir que nossos membros tenham todo o suporte necessário para lidar com questões burocráticas. Por isso, a colaboração do time de Design, responsável por cuidar da experiência nos sistemas da Alice e criar uma jornada simples e eficiente, foi essencial para aprimorar um dos aspectos mais desafiadores do mercado de planos de saúde.</p>
<h2>Como a Alice lida com problemas administrativos</h2>
<p>Quando um membro da Alice enfrenta alguma dificuldade com seu plano, ele usa nosso chat proprietário para entrar em contato com uma equipe essencial: os Navegs &#8211; nosso time de atendimento ao cliente. Eles são responsáveis por apoiar nossos membros e ajudar a resolver dúvidas e problemas.</p>
<p>Atualmente, pagamentos e gestão de planos são os temas que geram mais acionamentos do time de atendimento quando falamos de assuntos administrativos. Dentro dessa categoria, boletos e a composição da mensalidade são as dúvidas mais frequentes. Os cenários variam: pode ser desde uma empresa que precisa apenas baixar um boleto, renegociar um pagamento, até um pedido de mudança na data de vencimento do boleto. Cada uma dessas situações exige uma abordagem diferente.</p>
<p>Por serem questões tão recorrentes, mas de baixa complexidade de execução, enxergamos uma excelente oportunidade para criar automação por meio de chat de inteligência artificial. Dessa forma, o atendimento poderia ser expandido para 24h por dia, 7 dias por semana, e os Navegs, por sua vez, poderiam focar em atendimentos mais complexos.</p>
<p>Ser um Navegs não é uma tarefa fácil. Esse time lida com vários atendimentos simultâneos, com chamados que são abertos automaticamente, e precisa fazer uma triagem antes de resolver o problema do membro. Um desafio comum dele é manter o tempo de espera curto enquanto gerencia várias ocorrências ao mesmo tempo. Garantir essa velocidade na resposta é fundamental para que o customer experience seja bom.</p>
<p>O atendimento na Alice pode ser dividido em quatro etapas:<figure class="wp-attachment-209" ><img fetchpriority="high" decoding="async" class="aligncenter wp-image-209 size-full" src="https://alice.com.br/tech/wp-content/uploads/2024/10/frame-1000002098.jpg" alt="" width="4260" height="1128" srcset="https://alice.com.br/tech/wp-content/uploads/2024/10/frame-1000002098.jpg 4260w, https://alice.com.br/tech/wp-content/uploads/2024/10/frame-1000002098-300x79.jpg 300w, https://alice.com.br/tech/wp-content/uploads/2024/10/frame-1000002098-768x203.jpg 768w" sizes="(max-width: 4260px) 100vw, 4260px" /></figure></p>
<p>Etapa 1 : Triagem (Definição, classificação e investigação do problema)</p>
<p>Etapa 2 : Definição (Identificação da melhor forma de resolver o problema)</p>
<p>Etapa 3 : Execução (Implementação da solução escolhida)</p>
<p>Etapa 4 : Devolutiva (Comunicação da solução ao membro)</p>
<p>Antes da iniciativa de chats de inteligência artificial, todas essas etapas do atendimento eram realizadas por pessoas. Agora, a inteligência artificial entrará em ação no momento que o membro abrir um chamado. Para isso ser possível, utilizamos dois agentes de IA, que nada mais são do que programas que coletam e utilizam dados estruturados para realizar tarefas predeterminadas.</p>
<p>Um primeiro agente, conhecido como “Classificador”, consulta nosso banco de dados para coletar informações e classificar o tema abordado. Em seguida, o segundo agente, chamado de “Explorador”, faz perguntas ao membro para entender melhor sobre o problema. Com base nas respostas, o agente cria um resumo do atendimento e passa para o Navegs que, por fim, inicia o atendimento pessoal.</p>
<p>Em resumo, os agentes de IA coletam os dados e só depois transferem o atendimento para um humano, já com um resumo do problema e a triagem realizada. Dessa forma, reduzimos o tempo na primeira etapa do atendimento, e o Navegs pode focar na segunda etapa (definição da solução) e dali em diante.</p>
<p>Com a implementação dessa automação, reduzimos a quantidade de telas que o membro precisa acessar no app até iniciar o atendimento de fato. No caso de dúvidas sobre gestão de planos, reduzimos de 4 para 3 telas e, em pagamentos, de 5 para 3 telas.</p>
<p><figure class="wp-attachment-210" ><img decoding="async" class="aligncenter wp-image-210 size-full" src="https://alice.com.br/tech/wp-content/uploads/2024/10/to-be.gif" alt="" width="374" height="810" /></figure></p>
<h2>Aprendizados em Design</h2>
<p>No time de Design da Alice, temos princípios que são fundamentais em qualquer trabalho que executamos. Colaboração e resolutividade são os que consideramos como principais neste projeto. Falaremos sobre cada um deles a seguir.</p>
<ul>
<li><b>Colaboração:</b> Uma parte essencial dessa iniciativa tem relação com testar os prompts (tarefas que a IA precisa executar), ou seja, garantir que a IA responda corretamente de acordo com regras predefinidas. Há um equilíbrio entre automatizar cenários comuns e entender que alguns casos específicos podem não ser resolvidos pela IA de imediato. Reunimos pessoas de diferentes áreas – incluindo Design, Engenharia, Product Management e Operações – para testar os prompts. A diversidade de perspectivas foi fundamental para identificar erros e propor melhorias.</li>
<li><b>Resolutividade: </b>Como esse é um experimento recente e sem histórico de referência, é crucial entender o impacto dessa iniciativa. Hoje utilizamos a métrica de CSAT (Customer Satisfaction Score) para avaliar a satisfação do membro em nossas entregas. Vamos continuar acompanhando essa métrica ao longo dos próximos meses para considerar melhorias futuras.</li>
</ul>
<h2>Reflexões para o Futuro</h2>
<p>A aplicação de inteligência artificial nos negócios é um tópico relativamente novo e cheio de desafios. Sabemos que estamos todos aprendendo juntos, e esses novos métodos de trabalho devem sempre ser explorados com uma perspectiva centrada nas pessoas que usam o nosso produto, no caso, nossos membros.</p>
<p>Assim, pensando nos próximos passos para desenvolver ainda mais soluções que melhorem nosso customer experience e o dia a dia dos nossos membros, disponibilizaremos uma documentação que será compartilhada com os times da Alice para que todos tenham autonomia para criar os seus próprios projetos de IA. Para mantermos uma padronização nesse processo, o time de UX Writing será fundamental para garantir a consistência de linguagem e tom de voz adequado.</p>
<p>Essa iniciativa foi apenas uma entre muitas baseadas na aplicação de IA por toda a Alice. Ela ilustra o papel estratégico que a nova geração de modelos de linguagem tem para o nosso negócio e os esforços para difundir seu uso em toda a companhia.</p>
<p>_____________________________________________________________________________________________________________________________________</p>
<h2>Artificial Intelligence applied to customer experience</h2>
<p><em>How Alice is using AI to improve client support</em></p>
<p>The healthcare sector encompasses much more than hospitals with their medical and nursing teams. Throughout the system, there is an enormous structure that handles essential day-to-day tasks for patients, such as payments, procedure authorizations, bureaucratic questions and financial charges. Optimizing this structure and ensuring safety and an excellent customer experience is a challenge.</p>
<p>In this article, we will discuss how Alice has been using artificial intelligence (AI) to raise the quality of customer service for our members – how we call Alice’s clients.</p>
<p>Health insurance plans&#8217; users often find the administrative ecosystem one of the most frustrating areas of this business. In a sector that ranks among the least popular in Brazil, we want to ensure that our members have all necessary support to handle bureaucratic matters. The collaboration of our Design team, which is responsible for safeguarding customer experience across all systems in Alice, was essential to improve one of the most challenging aspects of the healthcare market.</p>
<h3>How Alice handles administrative matters</h3>
<p>When a member faces some sort of difficulty with his/her plan, he/she uses our proprietary chat to contact an essential team: Navigators – our customer service team. They are in charge of supporting our members and helping to solve doubts and problems.</p>
<p>Payments and plan management are currently the most frequent issues addressed by our members. Under these categories, invoices and the composition of monthly bills are the most common themes. These range from a company that needs to download an invoice or renegotiate a payment to a request for changing the maturity date on the invoice. Each of these situations requires a different approach.</p>
<p>Because these are recurring, low-complexity matters, we saw an excellent opportunity for automation using AI. Doing so would allow us to extend service 24/7, and the Navigators, in turn, could focus on more complex cases. The Design team played a key role in finding a solution, since it is tasked with understanding member demands and creating a simple and efficient journey.</p>
<h3>Reformulating journeys</h3>
<p>Navigators face a complex task. They juggle multiple concurrent support requests, including auto-generated tickets, and must triage them efficiently. A key challenge is reducing members’ wait time while managing a high volume of tickets. Timely responses are essential to deliver a superior customer experience.</p>
<p>Their journey can be summarized in four steps:</p>
<p>1: Screening (Defining, classifying and investigating the problem)</p>
<p>2: Definition (Identifying the best way of solving the problem)</p>
<p>3: Execution (Implementing the chosen solution)</p>
<p>4: Feedback (Communicating the solution to the member)</p>
<p>Before the AI initiative, human beings were tasked with all these steps. Now, the AI will step up when members get in touch. We make use of two AI agents – programs that collect and make use of structured data to take on predetermined tasks.</p>
<p>A first agent, known as &#8220;Classifier&#8221;, browses Alice’s database to collect information and classify the member&#8217;s complaint under one of several themes. Then, a second agent, known as an &#8220;Explorer&#8221;, poses questions to the member to better understand the matter. Based on the answers, the agent generates a summary that is sent to the Navigator, which, finally, begins the one-on-one interaction.</p>
<p>AI agents collect data and only then hand the member over to a human, having finished a screening process and delivering a complaint summary. This reduces the time spent in the first step, allowing the Navigator to focus on the second to fourth steps.</p>
<p>With this implementation, we reduced the amount of screens the member has to move through until he reaches the actual interaction with a Navigator. For plan management matters, this number fell to 3 from 4 and, for payments, to 3 from 5.</p>
<h3>Design learnings</h3>
<p>In Alice&#8217;s design team, we hold a few principles as fundamental to all of our work and this feature exemplifies this. In particular, we believe this project showcased our focus on Collaboration and Resolutivity.</p>
<ul>
<li>Collaboration: An essential part of this initiative was testing prompts (tasks that the AI executes) – that is, ensuring that the AI answers correctly based on predefined rules. There&#8217;s a tradeoff between automatizing common scenarios and understanding that some specific cases cannot be solved immediately by the AI. Several different areas at Alice – including Design, Engineering, Product and Operations – collaborated in testing those prompts. Having a diversity of views was essential to identifying errors and proposing improvements.</li>
<li>Resolutivity: Because this is a recent experiment with no prior history, it is crucial to understand its impact. Currently, we focus on CSAT (Consumer Satisfaction Score) and will be tracking that performance indicator in order to iterate on the agents.</li>
</ul>
<h3>Looking forward</h3>
<p>Deploying AI to solve business problems is a relatively new topic that is full of challenges. We are learning collectively, and new ways of working must always be explored  with a client-centric approach.</p>
<p>For the next steps in developing even more solutions that improve customer experience and day-to-day experience, we will develop documentation that will be shared with all teams at Alice so that all are able to autonomously take on AI projects. Our UX Writing team will be key in ensuring language consistency and an adequate voice.</p>
<p>This initiative is one among many based on implementing AI solutions throughout Alice. It highlights the strategic role that the new LLM generation plays in our business and efforts to democratize its use across the company.</p>
<p>O post <a href="https://alice.com.br/tech/inteligencia-artificial-aplicada-no-customer-experience/">IA aplicada ao customer experience na Alice</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>Cultura de IA: como a Alice inova no dia a dia</title>
		<link>https://alice.com.br/tech/como-a-alice-esta-construindo-uma-cultura-de-ia-no-seu-dia-a-dia/</link>
		
		<dc:creator><![CDATA[Bruno Federowski]]></dc:creator>
		<pubDate>Tue, 30 Jul 2024 19:45:54 +0000</pubDate>
				<category><![CDATA[Software]]></category>
		<guid isPermaLink="false">https://alice.com.br/tech/?p=194</guid>

					<description><![CDATA[<p>Todo time em uma empresa de tecnologia deveria usar AI cotidianamente. Como fazemos isso acontecer?</p>
<p>O post <a href="https://alice.com.br/tech/como-a-alice-esta-construindo-uma-cultura-de-ia-no-seu-dia-a-dia/">Cultura de IA: como a Alice inova no dia a dia</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>A Alice acredita que inteligência artificial (IA) deve  permear tudo que fazemos. Como garantimos que isso acontece? Essa é a parte complexa.</p>
<p>Com avanços em IA surgindo diariamente, fica cada vez mais evidente o seu impacto disruptivo. A IA vai transformar indústrias, gerar novas oportunidades, impulsionar a produtividade ao longo de todos os setores e abrir as portas para uma nova era das empresas de tecnologia.</p>
<p>Enquanto startups que têm IA em seu DNA nascem todo dia, companhias de setores tradicionais precisam se adaptar rapidamente a esse novo contexto. É um desafio análogo ao nascimento dos primeiros computadores, e realizar uma mudança cultural tão importante exige um esforço imenso.</p>
<h2><b>A Alice e IA</b></h2>
<p>A Alice é um plano de saúde para empresas que permite que os seus membros (clientes) naveguem pelo sistema de saúde de forma coordenada entre os três diferentes níveis de atenção: primária, secundária e terciária. Fazemos isso direcionando os nossos membros aos agentes mais custo-efetivos do sistema de saúde – membros com condições simples podem ser tratados por enfermeiras e médicos de família, enquanto aqueles com sintomas graves deveriam rapidamente se consultar com os especialistas.</p>
<p>Abordagens baseadas em machine learning e dados sempre foram centrais para essa missão. Quando a Alice foi fundada, isso significava modelos proprietários construídos por nosso time interno de cientistas de dados, e um grande foco em análise de dados.</p>
<p>Mas a ascensão da IA generativa mudou isso. Em vez de depender de um time específico, a nova geração de produtos permite que todo funcionário da Alice faça uso de modelos no estado da arte. Seja incorporando modelos de terceiros diretamente em nossos produtos – para, por exemplo, resumir dados médicos baseados em transcrições de consultas em áudio – ou por aplicações de dia-a-dia que nos permitem reduzir burocracia, a IA deveria ter uma presença constante em como trabalhamos.</p>
<p>Um <a href="https://static1.squarespace.com/static/5d35e72fcff15f0001b48fc2/t/668d08608a0d4574b039bdea/1720518756159/chatgpt-full.pdf">estudo recente</a> mostrou que a adoção do ChatGPT foi ampla, mas desigual. Muitos funcionários precisam de treinamento e direcionamento para aproveitar completamente os aumentos de produtividade, e muitos são prejudicados por restrições das empresas em que trabalham.</p>
<p>Não cair nessas armadilhas exige uma mudança cultural importante. Product managers (PMs) e times operacionais deveriam enxergar a IA como a primeira solução para todo problema com que se deparam. Isso também significa que o uso de IA deveria ser tão simples quanto possível e não exigir expertise técnica.</p>
<h2><b>Transformação cultural</b></h2>
<p>Para fortalecer a ideia de que recorrer à IA é simples e esperado, organizamos eventos que chamamos de &#8220;AI Day&#8221;, envolvendo toda a empresa.</p>
<p>Durante todo um dia de trabalho, times de todas as áreas se reuniram em nosso escritório e trabalharam em implementar vários protótipos de aplicações de IA. Esses protótipos poderiam ser lançados no mesmo dia, ou poderiam ser um ponto de partida para um ciclo normal de desenvolvimento. Os times contaram com o apoio de membros de nossas equipes de engenharia e dados, assim como outros funcionários da Alice que já haviam adotado IA como uma ferramenta de trabalho cotidiano.</p>
<p>Antes desses eventos, os participantes levantaram ideias para vários protótipos em uma planilha comum, a serem validados por aqueles que lideraram a iniciativa. Esses projetos variavam dos mais simples, como classificar dados de exames com base em texto não estruturado, aos mais complexos, como gerar um banco de dados com uma ferramenta de busca usando todo o histórico médico de membros.</p>
<p>Fornecemos uma conta no ChatGPT aos participantes com acesso a assistants. No fim de cada dia, eles apresentaram seus projetos a todo mundo presente no evento.</p>
<p>Tivemos três objetivos com essa iniciativa: ensinar a todos como usar IA numa base cotidiana e incorporar essa possibilidade em seu raciocínio; aumentar o ritmo de geração de novas aplicações de IA; e identificar que ferramentas nosso time de engenharia deveria desenvolver para incentivar a adoção de IA.</p>
<p>Esses esforços foram em grande parte bem-sucedidos. Vários dos protótipos desenvolvidos em nosso primeiro AI Day se tornaram projetos completos, e muitos outros foram implementados imediatamente. Temos visto times que não são tradicionalmente de tech usando IA em seu dia a dia, e geramos um novo roadmap para o time de Foundation em engenharia com entregáveis claros que vão impulsionar a produtividade daqueles que trabalham com IA.</p>
<p>Com isso, vieram aprendizados importantes:</p>
<ul>
<li>Depois que a porteira está aberta, é difícil segurar a boiada. Um dos principais fatores que levam times fora de tecnologia a relutarem em usar IA é que eles precisam adaptar seu pensamento a uma nova ferramenta. Quebrar essa barreira rapidamente leva a um uso acelerado;</li>
<li>Transicionar para um modelo em que IA é uma parte central de como trabalhamos exige quebrar dependências. Se funcionários da Alice precisam contatar os times de dado ou engenharias para usar IA, isso significa que estamos fazendo algo errado;</li>
<li>IA pode ser transformador com produtos de larga escala, sim, mas uma parte importante do valor vem da soma de muitas aplicações pequenas. Aumentar eficiência em todos os lados da companhia pode ser tão impactante quanto desenvolver um novo produto de IA.</li>
</ul>
<h2><b>IA como plataforma</b></h2>
<p>Nossa experiência com os AI Days nos fez dividir nossos esforços para facilitar o uso de IA em duas frentes: primeiro, precisávamos simplificar o teste de novas aplicações; segundo, precisávamos fazer com que lançar novos produtos de IA fosse tão fácil quanto possível, sem abrir mão de qualidade, controle de custo ou privacidade.</p>
<p>Na primeira frente, nosso time de Foundation em engenharia começou a desenvolver uma plataforma de testes que permitirá que nossos usuários cumpram várias tarefas que hoje são difíceis em um ambiente no-code:</p>
<ul>
<li>Rodar prompts de IA que são dinamicamente atrelados a dados de teste em batch. Por exemplo, um usuário pode subir um arquivo com comentários do NPS e pedir que a plataforma rode um prompt, atribuindo a cada um deles uma classificação;</li>
<li>Otimizar prompts em escala comparando o resultado de diferentes prompts sobre um conjunto de arquivos; diferentes contextos sobre um único prompt; etc.</li>
<li>Conectar diretamente a nossa camada analítica pelo Metabase, garantindo que usuários não precisam inserir manualmente dados de teste;</li>
<li>Gerar workflows de diferentes modelos de IA. Por exemplo, transcrever um áudio e em seguida enviar essa transcrição a um modelo de texto;</li>
<li>Controles de custo e acesso por meio de uma estrutura de times que atribui orçamentos específicos para cada unidade;</li>
<li>Salvar e comentar em experimentos passados, permitindo que usuários mantenham um histórico dos últimos testes de seu time;</li>
<li>Fazer uso de nossa infraestrutura de anonimização e privacidade para garantir que respeitemos nossas regras de governança.</li>
</ul>
<p>Adotamos a estratégia de lançar iterações da plataforma rapidamente e testar com usuários. Representantes de produto, operações e até nossa equipe médica foram os clientes e tiveram a responsabilidade de validar nossos planos e evangelizar seus times.</p>
<p>Enquanto isso, também precisávamos facilitar o deploy de aplicações que se conectassem diretamente a nossos produtos. Por sorte, trabalhar com a nova geração de LLMs é simples, e nos concentramos em garantir que os dados inseridos e gerados por esses modelos passem pelos mesmos processos que nossos dados em produção.</p>
<h2><b>O futuro</b></h2>
<p>A Alice acredita que IA é o futuro, e que ocupamos uma posição única que nos permite nos beneficiar de novos desenvolvimentos. Como um payvidor que atua em toda a jornada de saúde e tem acesso a dados de fontes muito diversas, produtos de dados deveriam ser tão centrais para nós quanto nossa operação médica.</p>
<p>Em uma publicação futura, vamos explorar os detalhes da arquitetura descrita nas últimas sessões. Mas já demos passos largos em adotar uma cultura que coloca IA no centro com nossos esforços institucionais para educar os times e com o desenvolvimento rápido de ferramentas para incentivar a adoção. O futuro é animador e há muito mais a ser feito, tanto em termos dos planos da própria Alice quanto do desenvolvimento de LLMs como um todo.</p>
<hr>
<h2>How Alice is building a culture of &#8216;AI as a go-to solution&#8217;</h2>
<p>Alice believes that AI should permeate every aspect of what we do. How do we make sure that this is the case? That&#8217;s the hard part.</p>
<p>As advances in AI technology pop up daily, claims of its transformative impact pile up. AI is set to disrupt established industries, foster new opportunities, drive up productivity across the board and usher in a new era for tech companies.</p>
<p>While startups that make AI as part of their DNA are born everyday, incumbents in traditional sectors have to quickly adapt to the new environment. That is a challenge analogous to the advent of the first computers, and bringing about such a major culture change requires major effort.</p>
<h3><b>Alice and AI</b></h3>
<p>Alice is a healthcare company that provides direct access to our own primary care physicians as well as third-party secondary and tertiary care. We do this by directing members to the most cost-effective agent in the healthcare chain – members with simple conditions can be treated by nurses and family doctors, while those with aggravated symptoms should be rapidly attended on by specialists.</p>
<p>Machine learning and data-based approaches have always been core to how we accomplish that mission. Back when we were founded, this meant proprietary models built by our in-house data scientists and a strong reliance on analytics.</p>
<p>But the ascent of generative AI has changed this. Instead of relying on a specific team, the new generation of products allows every single Alice employee to make use of state-of-the-art models. Whether it is by embedding third-party models directly into our products, such as by summarizing medical data based on consultation audio transcripts, or by day-to-day applications that allow us to reduce bureaucratic work, AI should play a constant role in how we work.</p>
<p>A <a href="https://static1.squarespace.com/static/5d35e72fcff15f0001b48fc2/t/668d08608a0d4574b039bdea/1720518756159/chatgpt-full.pdf">recent paper</a> showed that adoption of ChatGPT has been widespread, but has been unequal. Many workers require training and guidance to fully benefit from productivity increases, and many are hindered by company restrictions.</p>
<p>Not falling into those traps requires a major culture change. Product managers and operational teams should see AI as the number one go-to solution for every problem that arises. It also means that the use of AI should be as hassle-free as possible and does not require much technical expertise.</p>
<h3>Culture change</h3>
<p>In order to establish the idea that tapping into AI is easy and expected, we ran company-wide events known as &#8220;AI Days&#8221;.</p>
<p>For a whole working day, teams from across the company would gather in our office and work on implementing several POCs of AI applications that could either be rolled out on the same day or would kickstart a regular development cycle. They would be supported by members of the engineering and data teams, as well as other Alice employees who had already adopted AI as a day-to-day working tool.</p>
<p>Before those events, participants would brainstorm possible POCs in a common spreadsheet to be validated by those leading the initiative. These would range from the simplest, such as tagging exam data based on unstructured text, to the more complex, like generating a searchable database based on members&#8217; full medical history.</p>
<p>Participants would be provided with a ChatGPT account that granted them access to assistants. At the end of each day, they would present their accomplishments to the whole event.</p>
<p>Our objectives with this initiative were threefold: teaching employees how to work with AI on a daily basis and ingraining that possibility into their thinking; increasing the pace of generation of new AI applications; and identifying what tools our engineering team should develop to ensure that AI adoption soars.</p>
<p>Those efforts were largely successful. Several of the POCs developed on our first AI Day event went on to become full-fledged projects, and many others were implemented from the get-go. We&#8217;ve seen teams that are not traditionally tech-savvy increasingly rely on AI in their day-to-day work. They also led to a new roadmap for our Engineering Foundation team with clear deliverables that will greatly boost the productivity of those working with AI applications.</p>
<p>All in all, the AI Day events led to significant learnings:</p>
<ul>
<li>Once the floodgates are open, the water is hard to stop. One of the main issues that prevent non-tech teams from using AI is that they have to adapt their thinking to a new tool. Breaching that barrier quickly leads to accelerated use;</li>
<li>Successfully transitioning to a model where AI is a core part of how we work means breaking down dependencies. If Alice employees need to contact data or engineering to make use of AI, that means that there&#8217;s something wrong;</li>
<li>AI can be transformative through large-scale products, yes, but a large swath of its value comes from the sum of a lot of tiny, day-to-day applications. Increasing efficiency across all levels of the company can be as impactful as developing one major new AI product.</li>
</ul>
<h3><b>AI as a platform</b></h3>
<p>Our experience with AI Days led us to divide our efforts to ease use of AI in two fronts: first, we needed to facilitate testing of new applications throughout the company; second, we should make deploying new AI products as easy as possible while maintaining a high level of quality in our infrastructure, cost control and privacy policies.</p>
<p>In the first front, our Engineering Foundation team began development of a testing platform that will allow users to undertake several different tasks that are as of now hard to achieve in a no-code environment:</p>
<ul>
<li>Running AI prompts that are dynamically attached to testing data in batches. For instance, a user can upload a file with NPS comments and then request the platform run a prompt on them, asking it to classify each of the entries between a few different tags;</li>
<li>Optimizing prompts at scale by comparing the results of different prompts over a single batch of files; different contexts over a single prompt; etc.</li>
<li>Connecting directly to our analytical layer through Metabase, ensuring that users do not need to manually input testing data;</li>
<li>Setting up workflows of different AI models. For example, by transcribing an audio, then sending that transcription to a text-based model;</li>
<li>Access and cost controls through a team-based structure that carries specific budgets for each unit;</li>
<li>Saving and commenting on past experiments and allowing users to keep a history of their team&#8217;s previous attempts;</li>
<li>Using our own anonymization and privacy infrastructure to ensure that we are not breaching our rules of governance.</li>
</ul>
<p>We adopted a strategy of rolling out quick iterations of the platform and testing it with users. With representatives of product, operations and even our medical staff as stakeholders, tasked with validating our roadmap and evangelizing their teams, development is running smoothly.</p>
<p>Meanwhile, we also needed to facilitate deployment for those applications that would connect directly with our products. Fortunately, the new generation of LLMs are easy to deal with and we were able to focus on ensuring that data inputted and outputted by those models go through the same processes as those of our production data.</p>
<h3><b>The future</b></h3>
<p>Alice believes that AI is the future, and that it is uniquely positioned to take advantage of new developments. Being a payvidor that acts on the whole healthcare journey and has access to data from a wide range of sources, data products should be as core to us as our medical operations.</p>
<p>In an upcoming post, we will explore the details of the architecture described in the previous sections. But we have taken long strides already in adopting an AI-centric culture by pursuing institutional efforts to educate our teams as well as quick development of tools that boost adoption. The future is bright and there is much more to be done both in terms of Alice&#8217;s efforts and the development of LLMs as a whole.</p>
<p>O post <a href="https://alice.com.br/tech/como-a-alice-esta-construindo-uma-cultura-de-ia-no-seu-dia-a-dia/">Cultura de IA: como a Alice inova no dia a dia</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>How we extract data for our DW</title>
		<link>https://alice.com.br/tech/how-we-extract-data-for-our-dw/</link>
		
		<dc:creator><![CDATA[Bruno Federowski]]></dc:creator>
		<pubDate>Sat, 20 Jul 2024 20:23:39 +0000</pubDate>
				<category><![CDATA[Software]]></category>
		<guid isPermaLink="false">https://alice.com.br/tech/sem-categoria/how-we-extract-data-for-our-dw/</guid>

					<description><![CDATA[<p>About a year ago I arrived at Alice with the compromise to make the world healthier. We had less than 100 employees and living from series A, which means short money. A big challen</p>
<p>O post <a href="https://alice.com.br/tech/how-we-extract-data-for-our-dw/">How we extract data for our DW</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></description>
										<content:encoded><![CDATA[<h4>A long long time ago…</h4>
<p>About a year ago I arrived at Alice with the compromise to make the world healthier. We had less than 100 employees and living from series A, which means short money. A big challenge and a lot of work to do!</p>
<h4>The first challenges</h4>
<p>As a data engineer, my responsibility was to provide data for everybody. The team was very small (actually just me and half the time of my boss) and the systems were changing very fast.</p>
<p>Facing the situation, the plan needed to be as simple and direct as possible:</p>
<ul>
<li>Use a relational database as the data warehouse. We choose PostgreSQL hosted in AWS RDS. Easy to configure and maintain.</li>
<li>Use a simple tool to schedule the ETL pipelines. The choice was Airflow since it&#8217;s a very stable, well know tool and we had experience with it (and we love Python).</li>
<li>A visualization interface. Metabase was the winner for many motives: Free, previous experience with it, easy to install and configure, self-service, very stable and users usually like it.</li>
</ul>
<p>OK…. That&#8217;s something we can make happen! I reused some previous code I wrote in the past to copy data from one place to another and data started to flow! Great! Mission accomplished!</p>
<h4>Problems always happen!</h4>
<p>BUT…. almost every day I had dags broken and had to add a table, fix some table structure, re-run dags, and deploy emergency PRs. The problem was for every new column, every modification in size or type, even the order of some selects could break something. How to solve it?</p>
<h4>For every problem, a solution!</h4>
<p>At that point, I started to work on an Airflow plugin for a smarter extractor which was baptized, given my total lack of imagination, &#8220;SmartTransfer&#8221;. The main idea was to check the existence and structure of the table in the destination stage area and automatically create or re-create as needed.</p>
<p>The intention was to be really easy to be called, with minimal parameters. Below is a real example of a very simple dag with it:</p>
<p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/7faf4916b61074e1a251a48b55577003/href">https://medium.com/media/7faf4916b61074e1a251a48b55577003/href</a></iframe></p>
<p><em>(all code is available at </em><a href="https://github.com/alice-health/airflow_plugins">https://github.com/alice-health/airflow_plugins</a> <em>)</em></p>
<p>So, how does it work? No big secret, but there are some steps in the process.</p>
<p>First, we need to check the structure of the source table. We run a query and get one row from the source table and analyze the columns.</p>
<p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/aa1ad187358be8b92f52a8ba5fd8d6c5/href">https://medium.com/media/aa1ad187358be8b92f52a8ba5fd8d6c5/href</a></iframe></p>
<p>From the table, we can create build the &#8216;create table&#8217; statement.</p>
<p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/612364fbe3b882fca211d453c0fa7964/href">https://medium.com/media/612364fbe3b882fca211d453c0fa7964/href</a></iframe></p>
<p>We used the &#8216;unlogged table&#8217; PostgreSQL feature because it should be, in principle, faster. Unlogged tables are faster but not crash-free, so be careful! Since staging is just a copy of production, it&#8217;s not a problem to lose data. <a href="https://www.postgresql.org/docs/11/sql-createtable.html">You can learn more about PostgreSQL here</a>. We didn&#8217;t notice much difference but we have only a few gigabytes. We will benchmark again in the future as our database grows.</p>
<p>Everything set, the logic is quite straightforward:</p>
<ul>
<li>If the destination table doesn&#8217;t exist, create it</li>
<li>If the destination table exists but the structure is different, drop it and recreate it</li>
<li>If tables have the same structure, same primary keys, just keep the table</li>
</ul>
<p>It&#8217;s important to remember in the case of (re)creating the destination table we need to do a full import, so we set the flag &#8220;need_full_import&#8221; to True</p>
<p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/2bfb41b76b83a85411afcbaf739329d5/href">https://medium.com/media/2bfb41b76b83a85411afcbaf739329d5/href</a></iframe></p>
<p>Finally, transfer the data. The first step is to know if we are going to do a full import or an incremental import:</p>
<p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/aaa4f0613d2923850568eed527c52622/href">https://medium.com/media/aaa4f0613d2923850568eed527c52622/href</a></iframe></p>
<p>and prepare the insert statements. The syntax is PostgreSQL specific, with &#8220;<em>ON CONFLICT DO UPDATE&#8221;</em> to create a mixed insert/update statement:</p>
<p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/538289ba2b8b9bcd3fb07634be08bca1/href">https://medium.com/media/538289ba2b8b9bcd3fb07634be08bca1/href</a></iframe></p>
<p>The main loop makes the data transfer. The most important part here is the grouper function: It lazily consumes the source_cursor, keeping in memory only the data will be sent in the current block</p>
<p><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/aca4c1f9af8fe1c23f37b2fd81b3a271/href">https://medium.com/media/aca4c1f9af8fe1c23f37b2fd81b3a271/href</a></iframe><iframe src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/e52079bf806612b757bf4497fb89a7b4/href">https://medium.com/media/e52079bf806612b757bf4497fb89a7b4/href</a></iframe></p>
<p>More details of installing, using, and testing SmartTransfer are in the README file in the official repository at <a href="https://github.com/alice-health/airflow_plugins">https://github.com/alice-health/airflow_plugins</a>.</p>
<h4>Conclusion</h4>
<p>I tried to cover the most important (and interesting) parts of the code and show how we solved the problem of moving, not hundred of terabytes with 100 people, but a couple of gigabytes with two people, in a way to automatize all table synchronization and copying process to minimize the data engineer manual work.</p>
<p>O post <a href="https://alice.com.br/tech/how-we-extract-data-for-our-dw/">How we extract data for our DW</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>Como fazemos microbenchmarks em Kotlin</title>
		<link>https://alice.com.br/tech/como-fazemos-microbenchmarks-em-kotlin/</link>
		
		<dc:creator><![CDATA[Bruno Federowski]]></dc:creator>
		<pubDate>Sat, 20 Jul 2024 20:23:39 +0000</pubDate>
				<category><![CDATA[Software]]></category>
		<guid isPermaLink="false">https://alice.com.br/tech/sem-categoria/como-fazemos-microbenchmarks-em-kotlin/</guid>

					<description><![CDATA[<p>As vezes precisamos fazer alguns testes de performance ou de benchmark, a fim de ter um melhor embasamento na hora de tomar nossas decisões.</p>
<p>O post <a href="https://alice.com.br/tech/como-fazemos-microbenchmarks-em-kotlin/">Como fazemos microbenchmarks em Kotlin</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>As vezes precisamos fazer alguns testes de performance ou de benchmark, a fim de ter um melhor embasamento na hora de <a href="https://medium.com/alice-tech/como-tomamos-decis%C3%B5es-860121def07f">tomar nossas decisões</a>. Dado que não existe muito material sobre o assunto com essa stack específica, pensamos em descrever aqui como fizemos nossa aplicação simples para benchmarks.</p>
<h3>Afinal, o que é um microbenchmark?</h3>
<p>Um microbenchmark é um teste projetado para medir o desempenho de uma unidade muito pequena: o tempo para chamar um método sincronizado versus um método não sincronizado; a sobrecarga na criação de um encadeamento versus o uso de um conjunto de encadeamentos; o tempo para executar um algoritmo aritmético versus uma implementação alternativa; e assim por diante.</p>
<p>É uma forma bem interessante de verificar se algum fluxo que estamos fazemos está consumindo muito ou pouco tempo ou recursos (CPU, memória, rede, disco, etc). Porém deve ser feito com cautela.</p>
<p>Muitos fatores podem interferir na execução e aferição de um benchmark, como capacidade de processamento do computador, memória disponível, versão do framework, entre outros. Por conta disso, deve ser feito para testes isolados de unidades bem específicas.</p>
<h3>Testando uso de reflections para nossos logs</h3>
<p>Há alguns meses atrás, o time <a href="https://alice.com.br/blog/conheca-a-alice/alice-e-a-empresa-mais-inovadora-da-america-latina-segundo-fast-company/">Alice</a> estudou a necessidade do uso de <em>Reflection</em> para identificar a função e a classe exata de onde o log foi gerado.</p>
<p>Nossa hipótese era que a utilização de <em>Reflection</em> poderia aumentar o consumo de recursos da função, mas não sabíamos o quanto aumentaria e se isso impactaria de verdade nossas aplicações.</p>
<h4>Importação de dependências</h4>
<p>Usamos a biblioteca JMH (the Java Microbenchmark Harness) para fazer a comparação. Utilizamos tanto o <a href="https://search.maven.org/classic/#artifactdetails%7Corg.openjdk.jmh%7Cjmh-core%7C1.19%7Cjar">JMH Core</a> quanto <a href="https://search.maven.org/classic/#artifactdetails%7Corg.openjdk.jmh%7Cjmh-generator-annprocess%7C1.19%7Cjar">JMH Annotation Processor</a>.</p>
<pre>plugins <strong>{
    </strong><em>kotlin</em>("jvm") <em>version </em>"1.4.32"
    <em>kotlin</em>("kapt") <em>version </em>"1.4.32"
    id("me.champeau.gradle.jmh") <em>version </em>"0.5.2"
    id("io.morethan.jmhreport") <em>version </em>"0.9.0"
    <em>application
</em><strong>}</strong></pre>
<p>No build.gradle.kts do projeto nós declaramos a task para rodar os testes de benchmark</p>
<pre><em>task</em>("benchmarks", type = JavaExec::class) <strong>{
  </strong><em>classpath </em>= <em>sourceSets</em>.getByName("test").<em>runtimeClasspath
  main </em>= "br.com.alice.benchmarks.BenchmarksRunnerKt"
<strong>}</strong></pre>
<p>Além disso importamos a biblioteca orgs.slf4j.Logger para criar nossos logs. A lista de dependências ficou:</p>
<pre><em>dependencies </em><strong>{
    </strong><em>kapt</em>("org.openjdk.jmh:jmh-generator-annprocess:1.25")

    <em>implementation</em>("org.openjdk.jmh:jmh-core:1.25")
    <em>implementation</em>("org.openjdk.jmh:jmh-generator-annprocess:1.25")

    <em>api</em>("ch.qos.logback:logback-classic:1.2.3")
    <em>implementation</em>("net.logstash.logback:logstash-logback-encoder:6.4")

    <em>annotationProcessor</em>("org.openjdk.jmh:jmh-generator-annprocess:1.25")

    <em>testImplementation</em>(<em>kotlin</em>("test-junit"))
<strong>}</strong></pre>
<h4>Criação da função de log</h4>
<p>Para realizar o teste, criamos uma abstração para a biblioteca orgs.slf4j.Logger . Só possui uma simples função de logar info, simulando nossa biblioteca interna para logs.</p>
<p><iframe loading="lazy" src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/e613b3205a2f958257f256880d60dc51/href">https://medium.com/media/e613b3205a2f958257f256880d60dc51/href</a></iframe></p>
<h4>Criando os casos de teste</h4>
<p>JMH suporta diferentes tipos de benchmarks: <em>Throughput,</em> <em>AverageTime,</em> <em>SampleTime</em>, and <em>SingleShotTime</em>. São configurados via annotation @BenchmarkMode .</p>
<ul>
<li><em>Throughput</em>: nesse modo, o teste é executado em um período pre determinado e é avaliado o número de vezes que o método em teste foi executado</li>
<li><em>AverageTime</em>: inverso ao <em>Throughput</em>, esse método é usado para se ter o tempo médio de cada chamada do método em teste.</li>
<li><em>SampleTime</em>: esse método também utiliza um tempo pré determinado, porém aqui algumas chamadas são selecionadas randomicamente e seu tempo avaliado.</li>
<li><em>SingleShotTime</em>: mede o tempo de uma única chamada.</li>
</ul>
<p>Para o nosso caso, utilizamos <em>AverageTime</em>, dessa forma a gente simular os nossos micro-serviços utilizando os métodos de log diversas vezes e ver o quanto isso impactaria o tempo e os recursos dos mesmos.</p>
<p>Configuramos também a unidade de medida temporal para microsegundos, também via annotation @OutputTimeUnit .</p>
<p>Usamos a annotation @Benchmark para definir uma função como <em>test case</em> do benchmarking. Criamos 3 tipos de testes:</p>
<ul>
<li>Log sem nenhuma reflection</li>
<li>Log utilizando reflection através do Throwable para receber os nomes de classe e método.</li>
<li>Log utilizando reflection através da Thread para receber os nomes de classe e método.</li>
</ul>
<p><iframe loading="lazy" src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/d4d08cafb3722fed8a0ab3599682a6db/href">https://medium.com/media/d4d08cafb3722fed8a0ab3599682a6db/href</a></iframe></p>
<h4>Configuração final do benchmark</h4>
<p>Para agrupar todos os testes, configurar saída do resultado e definir últimas configurações, nós criamos o arquivo <strong>BenchmarksRunner.kt</strong>, assim declarado no gradle.build.kts , mostrado no início do artigo.</p>
<p><iframe loading="lazy" src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/cf5835559cc5bcb2f4e16b799c9127f2/href">https://medium.com/media/cf5835559cc5bcb2f4e16b799c9127f2/href</a></iframe></p>
<p>As configurações utilizadas no OptionsBuilder:</p>
<ul>
<li>include adiciona o teste que vamos realizar. Nele indicamos qual a classe a ser executada, nesse caso o LogReflectionBenchmark .</li>
<li>forks é o número de testes paralelos que vão ser executados em cada iteração. Utilizamos 2 forks.</li>
<li>threads é o número de threads a ser utilizada para cada teste. Escolhemos duas threads. Dependendo do número de threads disponíveis na máquina, esse valor pode aumentar.</li>
<li>warmupBatchSize é o tamanho o grupo de aquecimento. Utilizamos 2 <em>batches</em>.</li>
<li>warmupIterations é o número de iterações a serem executadas antes de começar a contabilizar o tempo. Esse número é importante pois ajuda a contabilizar depois que a máquina já estiver rodando os testes. Um número muito alto pode impactar negativamente o teste, se o processo já tiver consumido bastante recurso da máquina.</li>
<li>measurementIterations é o número de iterações, agora contabilizando o tempo de cada teste. O resultado final é montado a partir a média entre as diferentes iterações.</li>
</ul>
<p>Além disso, definimos como arquivos output benchmark_output.log e benchmark_result.json . Eles vão conter as informações dos testes.</p>
<h4>Hora de rodar os testes</h4>
<p>Depois de toda a configuração, podemos rodar o BenchmarksRunner.main e aguardar os resultados. Após alguns minutos, o resultado foi mostrado no arquivo benchmark_output.log .</p>
<pre>LogReflectionBenchmark.logWithReflectionThreadGetStackTrace     avgt    4  28.860 ± 7.172  us/op
LogReflectionBenchmark.logWithReflectionThrowableGetStackTrace  avgt    4  42.075 ± 11.087  us/op
LogReflectionBenchmark.logWithoutReflection                     avgt    4  0.36028 ±  0.00035  us/op</pre>
<p>Como vocês podem ver, a utilização do log sem nenhum tipo de <em>reflection</em> foi cerca de 100x mais rápida do que com uso de qualquer <em>reflection</em>. Isso já foi necessário para que o nosso time decidisse não precisar logar o nome da função e nem da classe.</p>
<h3>Teste você mesmo</h3>
<p>Caso queira validar também em sua máquina, o código de exemplo está aberto. Você pode fazer o mesmo teste que nós fizemos, ou usar o exemplo para criar seus próprios microbenchmarks em Kotlin.</p>
<p><a href="https://github.com/alice-health/kotlin-benchmark-example">alice-health/kotlin-benchmark-example</a></p>
<p>No repositório tem a descrição de como executar os testes. E se você conseguiu testar outros <em>use cases</em>, compartilha aqui com a gente!</p>
<h3>Que tal fazer parte desse time?</h3>
<p>Estamos buscando pessoas que topem o desafio de transformar a saúde no Brasil através da tecnologia. <a href="https://www.alice.com.br/carreiras">Clica aqui</a> para saber mais das vagas que temos em aberto!</p>
<p>O post <a href="https://alice.com.br/tech/como-fazemos-microbenchmarks-em-kotlin/">Como fazemos microbenchmarks em Kotlin</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>Discovery: a forma de descobrir da Alice</title>
		<link>https://alice.com.br/tech/discovery-a-forma-de-descobrir-da-alice/</link>
		
		<dc:creator><![CDATA[Bruno Federowski]]></dc:creator>
		<pubDate>Sat, 20 Jul 2024 20:23:39 +0000</pubDate>
				<category><![CDATA[Development]]></category>
		<guid isPermaLink="false">https://alice.com.br/tech/sem-categoria/discovery-a-forma-de-descobrir-da-alice/</guid>

					<description><![CDATA[<p>E então perguntei: vocês sabem o que é discovery?</p>
<p>O post <a href="https://alice.com.br/tech/discovery-a-forma-de-descobrir-da-alice/">Discovery: a forma de descobrir da Alice</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></description>
										<content:encoded><![CDATA[<h2><strong>Café Legal</strong></h2>
<figure><img decoding="async" src="https://cdn-images-1.medium.com/max/400/1*t0_9EPYSGJhHhXC0Z0Fh6w.png" alt="" /></figure>
<p>Certo dia fui surpreendida por um evento na minha agenda: “Café Legal.”</p>
<p>Era um convite de duas pessoas do Time de <em>Legal</em> da Alice para um café. Dentre outras coisas, elas queriam entender mais sobre a Área de Produto e como elas poderiam contribuir de forma ativa com as nossas tomadas de decisão.</p>
<p>Falamos sobre amenidades, eu expliquei um pouco sobre as Áreas de Produto e Tecnologia e quando me questionaram sobre como poderiam ser mais participativas nos nossos processos, eu inconscientemente respondi: “precisamos inserir vocês nos nossos <em>discoveries</em>.”</p>
<p>Falei isso com certa naturalidade e fiz uma pausa. Elas me olharam com cara de “quê?”. E então perguntei: <strong>vocês sabem o que é <em>discovery</em>?</strong></p>
<p>Elas não sabiam. E isso, de forma alguma, é um demérito. Nós, que trabalhamos com produtos digitais, estamos muito acostumados com determinados termos, que acabamos utilizando com pessoas que não lidam diretamente com o nosso universo.</p>
<p>Expliquei para elas o que vou resumir aqui:</p>
<p><em>Discovery</em>, como o nome já indica<em>, </em>é um <strong>processo de <em>descoberta</em>: </strong>existe um problema, existem hipóteses de como resolver esse problema e, baseado nessas hipóteses, existem as possíveis soluções.</p>
<p>No <em>discovery</em>, buscamos encontrar a melhor solução para um problema sob três pilares: <strong>usuário</strong> (UX), <strong>tecnologia</strong> (viabilidade) e <strong>negócios</strong> (alinhamento estratégico).</p>
<figure><img decoding="async" src="https://cdn-images-1.medium.com/max/1024/1*EohLLpe-GqmPLa9TKeV2wg.png" alt="" /></figure>
<p>E, embora o <em>discovery</em> seja, muitas vezes, liderado por uma pessoa de produto (PM), ele é executado em conjunto com Product Designers e pessoas de desenvolvimento (tech), que têm papel fundamental para se obter um bom resultado.</p>
<h2><strong>Como estamos descobrindo a melhor forma de “descobrir” na Alice</strong></h2>
<p>Somos uma empresa <em>early stage</em> e sempre estamos descobrindo a melhor forma de fazer alguma coisa.</p>
<p>Uma das nossas virtudes é: <strong>“Subimos a barra, evoluímos todos os dias”</strong>. E para o processo de <em>discovery</em> não é diferente.</p>
<figure><img decoding="async" src="https://cdn-images-1.medium.com/max/250/1*lMWGPx6QJKPoCzPPv05dDw.gif" alt="" /></figure>
<p>Iniciamos no melhor modelo <em>free style</em>.</p>
<p>Cada PM, com sua experiência e bagagem de aprendizados, iniciou e concluiu diversos processos de <em>discovery</em>. E os resultados, naturalmente, tiveram méritos, falhas e novos aprendizados.</p>
<p>Decidimos nos reunir para unificar esse processo, juntar nossas forças para preencher as lacunas de cada processo individualizado.</p>
<p>E chegamos a um <em>framework</em> que vou detalhar a seguir.</p>
<h2><strong><em>Framework</em> de <em>Discovery</em> da Alice</strong></h2>
<p>Para apresentar o <em>framework</em>, vamos usar um suposto problema como exemplo:</p>
<p>Muitas pessoas do Time de Saúde estão reportando baixa adesão dos membros ao plano de ação.</p>
<blockquote><p>Plano de ação é uma lista de tarefas que o Time de Saúde estabelece com o membro com o objetivo de tornar sua vida mais saudável. As tarefas podem variar entre: iniciar uma atividade física, realizar um exame, se consultar com um especialista, tomar um medicamento, fazer acompanhamento com Nutricionista, entre outras coisas.</p></blockquote>
<p>Esse <em>framework</em> está dividido em <strong>2 grandes etapas</strong>:</p>
<ol>
<li>Entendimento do <strong>problema</strong> e levantamento de <strong>hipóteses</strong>;</li>
<li><strong>Validação</strong> ou redução do grau de incerteza das hipóteses e proposta de <strong>solução</strong>;</li>
</ol>
<p>Cada uma dessas etapas é marcada por um evento que reúne as pessoas envolvidas com o tema central do <em>discovery</em>.</p>
<h3><strong>1ª Etapa: entendimento do problema e levantamento de hipóteses</strong></h3>
<p>Ser PM é fazer escolhas, sempre —<strong> </strong>ser humano é fazer escolhas<strong>, </strong>sempre!</p>
<p>Como PM precisamos escolher <strong>qual problema resolver primeiro</strong>. Isso porque existem recursos limitados para desenvolver soluções. Essa etapa tem dois objetivos principais:</p>
<ol>
<li>Responder se o problema é relevante (qual é o impacto dele) e se existe alinhamento estratégico para priorizar a solução desse problema;</li>
<li>Levantar hipóteses para solucionar esse problema;</li>
</ol>
<p>É sempre importante frisar que <strong>hipóteses não são soluções</strong>. As hipóteses estão mais relacionadas a “o que deve ser feito” para se obter determinado resultado, enquanto as soluções estão relacionadas a <strong>“como isso deve ser feito”</strong>.</p>
<p>Eu sugiro escrever as hipóteses utilizando esse modelo<strong>: se [<em>variável</em>], então [<em>resultado</em>], porque [<em>racional</em>]</strong>.</p>
<p><strong>Utilizando o problema de exemplo:</strong> se [<em>as pessoas tivessem uma maneira mais fácil de agendar seus exames</em>], então [<em>o engajamento delas com o plano iria aumentar</em>], porque [<em>verificamos que + de 45% das pessoas demoram mais de 15 dias para agendar seus exames e aproximadamente 25% das pessoas não realizam o agendamento</em>].</p>
<p>A hipótese aqui: as pessoas têm dificuldades para agendar exames.</p>
<p>A solução a gente deixa para a segunda etapa.</p>
<figure><img decoding="async" src="https://cdn-images-1.medium.com/max/304/1*tKDCtUduKpDtO4QM0d3KTQ.gif" alt="" /></figure>
<p>Nessa primeira etapa vamos a fundo no <strong>entendimento do problema</strong>. Entre outras coisas, fazemos entrevistas com as pessoas envolvidas, <em>shadowings</em> (passar um tempo acompanhando a rotina dessas pessoas ou, até mesmo, assumir esses papéis), análise de dados, análise da evolução do produto, etc…</p>
<p>Como resultado dessas ações, temos um documento contendo:</p>
<p>[x] Descrição do problema<br />
[x] Descrição do impacto do problema<br />
[x] Evidências (quali/quanti) do problema a ser resolvido<br />
[x] Impacto no OKR<br />
[x] Proposta de hipóteses</p>
<p>Essa etapa é marcada pelo evento <em>Discovery</em> <em>Kick-off</em>, onde reunimos os principais <em>stakeholders</em> para <strong>apresentar o problema e as hipóteses de solução</strong>. Nesse evento buscamos o <em>buy-in</em> dos envolvidos para seguir para próxima etapa.</p>
<p>Ou seja<strong>,</strong> baseado no que sabemos até aqui: podemos afirmar que o problema é relevante, e o desenvolvimento de uma solução — agora — está alinhado estrategicamente com a empresa?</p>
<p><strong>Se sim, <em>next </em></strong>(se não, re-prioriza)</p>
<h3><strong>2ª Etapa: validação das hipóteses e proposta de solução</strong></h3>
<p>Ótimo. Já conhecemos a fundo o problema e já temos em mãos algumas hipóteses de como solucioná-lo. Mas como saber se essas são hipóteses válidas? Existem algumas formas.</p>
<p><strong>Vamos usar como exemplo a hipótese descrita na primeira etapa:</strong> se [<em>as pessoas tivessem uma maneira mais fácil de agendar seus exames</em>], então [<em>o engajamento delas com o plano iria aumentar</em>], porque [<em>verificamos que + de 45% das pessoas demoram mais de 15 dias para agendar seus exames, e aproximadamente 25% das pessoas não realizam o agendamento</em>].</p>
<p>Aqui o problema é o baixo engajamento ao plano e a hipótese é que isso se deve à dificuldade de agendamento de exames.</p>
<figure><img decoding="async" src="https://cdn-images-1.medium.com/max/320/1*G6SdMHqkJYdhw5P46ynq6A.gif" alt="" /></figure>
<p>Uma das formas de validar as hipóteses é <strong>entrevistar as pessoas</strong> que possuem baixa adesão ao plano. Nessas entrevistas, perguntamos a elas se aumentaria a probabilidade de adesão ao plano se houvesse uma forma mais fácil de agendar os exames.</p>
<p>Perguntamos também sobre outras hipóteses de solução a fim de entender quais são mais aderentes.</p>
<p>Outra forma complementar a essa, é <strong>simular um cenário</strong> onde enviamos um formulário para o membro para coletar informações sobre o melhor dia/horário de realização de exames e fazemos o agendamento pela pessoa.</p>
<p>Ao final desta simulação, comparamos se o engajamento ao plano dessas pessoas aumentou em comparação às demais.</p>
<p><strong>Sim? Sinal de que estamos no caminho certo!<br />
</strong>Entrevistas, cenários simulados e <em>benchmarks</em> são algumas formas de reduzir incertezas em relação às hipóteses.</p>
<p>Nesse momento algumas hipóteses serão validadas, outras terão seu grau de incerteza reduzido, e outras cairão.</p>
<p>Com base nas hipóteses validadas, partimos para o desenho da solução.</p>
<figure><img decoding="async" src="https://cdn-images-1.medium.com/max/1024/1*33khN9zpFCMWnF8pLqeVTQ.png" alt="" /></figure>
<p>Utilizando o mesmo exemplo, o que fazemos aqui é propor qual é a melhor forma de facilitar o agendamento de exames.</p>
<p>Podemos ter como solução, uma funcionalidade de agendamento de exames no app da Alice. Sendo assim, criamos um protótipo dessa funcionalidade e selecionamos pessoas para testarem a solução.</p>
<p>Minha sugestão é, se possível, desenvolver <strong>protótipos navegáveis de alta fidelidade</strong>.</p>
<p>Isso ajuda muito a ter resultados de testes mais assertivos, e, não menos importante, é uma documentação bastante robusta para posterior alinhamento com todos os envolvidos.</p>
<p>Com o protótipo em mãos, partimos para os testes, e inicia-se o famoso ciclo — teste &gt; feedback &gt; iteração — até chegarmos à solução final.</p>
<p>Aqui na Alice usamos e abusamos do <a href="https://maze.co/"><strong>Maze</strong></a> para testes de usabilidade. É uma ferramenta incrível, que nos ajuda a ter mais alcance, e resultados mais estruturados.</p>
<p>Ah, e sabe o Time de <em>Legal</em>?</p>
<p>Então, esse é um ótimo momento para envolvê-lo se você entender que a solução proposta pode ter algum <strong>impacto jurídico</strong>.</p>
<figure><img decoding="async" src="https://cdn-images-1.medium.com/max/200/1*f59vUogpdf9FA8MVIPb49g.gif" alt="" /></figure>
<p>Ou apenas para pegar a opinião deles, porque eles são “legal” — (<em>tudumtss</em>).</p>
<p>Ao final dessa etapa complementamos nosso documento de <em>discovery</em> com mais esse checklist preenchido.</p>
<p><strong>[x]</strong> Descrição da solução (fluxograma, protótipo, casos de uso, etc.)<br />
<strong>[x]</strong> Evidências de validação / invalidação das hipóteses<br />
<strong>[x]</strong> Validação da solução com <em>users<br />
</em><strong>[x]</strong> <em>Roadmap<br />
</em><strong>[x]</strong> Métricas de sucesso<br />
<strong>[ ]</strong> Alinhamento com <em>stakeholders</em></p>
<p>Para coroar, convidamos os <em>stakeholders</em> envolvidos para um evento que chamamos de <em>Discovery Sign-off</em>, apresentamos a <strong>solução final</strong> e nos alinhamos sobre os <strong>próximos passos</strong>.</p>
<p><strong>[x]</strong> Alinhamento com <em>stakeholders</em></p>
<figure><img decoding="async" src="https://cdn-images-1.medium.com/max/400/1*fkpeTX3xgb25idItqUh20A.png" alt="" /></figure>
<h2><strong>Para finalizar…</strong></h2>
<p>Todo esse <em>framework</em> pode dar, à primeira vista, a impressão de excesso de burocracia. Mas ele é só uma trilha, e não um trilho — parafraseando o Time de Saúde da Alice em relação aos protocolos de saúde. Cumprir todas essas etapas, ou apenas parte delas, depende da complexidade e impacto do problema e do grau de incerteza em relação às hipóteses.</p>
<p>O <em>discovery</em> ajuda a validar hipóteses, mas dificilmente será possível reduzir a zero o grau de incerteza em relação a elas.</p>
<p><strong>Muitas vezes é importante arriscar</strong>. A verdade é que uma hipótese somente será 100% validada quando a solução derivada dela estiver em uso.</p>
<p>Muito embora o <em>discovery</em> seja uma importante ferramenta para <strong>evitar custos que são evitáveis</strong> com a implementação de uma solução que tem grandes chances de não funcionar, ele é, também, um processo que custa caro. <strong>É preciso escolher quais batalhas lutar!</strong></p>
<p>O post <a href="https://alice.com.br/tech/discovery-a-forma-de-descobrir-da-alice/">Discovery: a forma de descobrir da Alice</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>JSON: integrando Back-end e Front-end na prática</title>
		<link>https://alice.com.br/tech/json-como-integrar-back-end-e-front-end-com-padroes-diferentes/</link>
		
		<dc:creator><![CDATA[Bruno Federowski]]></dc:creator>
		<pubDate>Sat, 20 Jul 2024 20:23:39 +0000</pubDate>
				<category><![CDATA[Development]]></category>
		<guid isPermaLink="false">https://alice.com.br/tech/sem-categoria/json-como-integrar-back-end-e-front-end-com-padroes-diferentes/</guid>

					<description><![CDATA[<p>Como padrão, no Javascript utilizamos o camelCase para nomenclatura de variáveis ​​e funções. E aqui na Alice, nós também seguimos esse padrão para os projetos de Front-end.</p>
<p>O post <a href="https://alice.com.br/tech/json-como-integrar-back-end-e-front-end-com-padroes-diferentes/">JSON: integrando Back-end e Front-end na prática</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></description>
										<content:encoded><![CDATA[<h3>O Problema</h3>
<p>Como padrão, no Javascript utilizamos o <strong>camelCase </strong>para nomenclatura de variáveis ​​e funções, e é possível encontrar essa definição nos principais guias de estilo de JS, como o <a href="https://standardjs.com/rules.html">standardjs</a> ou o <a href="https://github.com/airbnb/javascript#naming--camelCase">airbnb</a>. E aqui na <a href="https://alice.com.br/carreiras">Alice</a>, nós também seguimos esse padrão para os projetos de Front-end.</p>
<p>Uma das <a href="https://medium.com/alice-tech/como-tomamos-decis%C3%B5es-860121def07f">decisões que tomamos</a> ao definir o padrão para nossas APIs é que usaríamos JSON com <strong>snake_case </strong>pois consideramos que para a leitura de logs por humanos, esse formato é mais legível do que <strong>camelCase</strong>. No nosso Back-end, feito em <a href="https://kotlinlang.org/">Kotlin</a>, utilizamos a biblioteca em java, <a href="https://github.com/google/gson">GSON</a>. Ela transforma os objetos JAVA em uma representação em JSON e vice-versa. Para que a serialização/deserialização funcionasse com <strong>snake_case</strong> foi necessário passar o parâmetro <em>FieldNamingPolicy</em> com o valor <em>LOWER_CASE_WITH_UNDERSCORES </em>na configuração do client do GSON. (Imagem abaixo)</p>
<figure><img decoding="async" src="https://cdn-images-1.medium.com/max/840/1*8xkzcdPXNLHMqnJOgwI2dw.png" alt="" /></figure>
<p>Dessa forma ficamos com o padrão <strong>snake_case</strong> no Back-end em todas as nossas APIs e <strong>camelCase</strong> em todos os projetos de Front-end, ou seja, o corpo de nossas requisições e respostas HTTP são formados por um <strong>JSON com padrão snake_case</strong>.</p>
<p>Com isso temos o seguinte problema: Como utilizar <strong>camelCase</strong> no Front-end, sendo que todas as solicitação para as nossas APIs HTTP teriam que ser feitas com <strong>snake_case</strong>?</p>
<h3>A Solução</h3>
<p>Para realizar nossas chamadas HTTP no Front-end, utilizamos a <a href="https://github.com/sindresorhus/ky">biblioteca ky</a> ( ), que adiciona algumas funcionalidades da <a href="https://developer.mozilla.org/pt-BR/docs/Web/API/Fetch_API">fetch API</a>, entre elas, os <a href="https://github.com/sindresorhus/ky#hooks">hooks</a> que permitem modificações da requisição e de seu <em>payload</em> durante o ciclo de vida dessa chamada.</p>
<p>Conseguimos então, resolver esse problema criando um conversor, antes das requisições e após as respostas, utilizando os hooks <strong>beforeRequest</strong> (que permite modificar a requisição antes dela ser enviada) e <strong>afterResponse </strong>(que permite alterar a resposta da requisição):</p>
<ul>
<li><strong>beforeRequest: </strong>Vamos converter o corpo da nossa requisição de <strong>camelCase</strong> para <strong>snake_case</strong><em>.</em></li>
<li><strong>afterResponse: </strong>Vamos converter o corpo da nossa resposta de <strong>snake_case</strong> para <strong>camelCase</strong><em>.</em></li>
</ul>
<p>O código JS ficaria da seguinte forma:</p>
<p><iframe loading="lazy" src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/c6890799daa387f4bc862d605eae4e86/href">https://medium.com/media/c6890799daa387f4bc862d605eae4e86/href</a></iframe></p>
<h3>Esse código é open source</h3>
<p>Criamos um pacote para permitir essa e outras alterações de <em>case </em>em nossas requisições, e decidimos abrir o código dessa solução:</p>
<p><a href="https://github.com/alice-health/ky-hooks-change-case">alice-health/ky-hooks-change-case</a></p>
<p>Inclusive, esse pacote foi adicionado como biblioteca relacionada no <a href="https://github.com/sindresorhus/ky#related">repositório oficial do KY</a>. Sinta-se a vontade para abrir <em>pull requests</em> com melhorias, correções ou mandar qualquer comentário. Já utilizou o <em>ky </em>e/ou<em> hooks</em> para outros casos de uso? Compartilhe com a gente aqui nos comentários quais  .</p>
<p>Kudos e agradecimentos à <a href="https://medium.com/u/da63b77d6dcb">Diego Leme</a> pela contribuição na biblioteca e início desse post.</p>
<h3>Que tal fazer parte desse time?</h3>
<p>Estamos buscando pessoas que topem o desafio de transformar a saúde no Brasil através da tecnologia. <a href="https://www.alice.com.br/carreiras">Clica aqui</a> para saber mais das vagas que temos em aberto!</p>
<p>O post <a href="https://alice.com.br/tech/json-como-integrar-back-end-e-front-end-com-padroes-diferentes/">JSON: integrando Back-end e Front-end na prática</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>Melhor forma de escrever CSS no Vue</title>
		<link>https://alice.com.br/tech/qual-a-melhor-forma-de-escrever-css-no-vue/</link>
		
		<dc:creator><![CDATA[Bruno Federowski]]></dc:creator>
		<pubDate>Sat, 20 Jul 2024 20:23:39 +0000</pubDate>
				<category><![CDATA[Software]]></category>
		<guid isPermaLink="false">https://alice.com.br/tech/sem-categoria/qual-a-melhor-forma-de-escrever-css-no-vue/</guid>

					<description><![CDATA[<p>Vamos lá, CSS não é a coisa mais fácil do mundo.</p>
<p>O post <a href="https://alice.com.br/tech/qual-a-melhor-forma-de-escrever-css-no-vue/">Melhor forma de escrever CSS no Vue</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>Vamos lá, CSS não é a coisa mais fácil do mundo. Existem diversas formas de resolver o mesmo problema, os browsers nem sempre possuem o mesmo comportamento, já chegamos num nível onde é impossível saber todas as regras que existem, etc. Na expectativa de ajudar o desenvolvimento, temos pré-processadores, pós-processadores, variáveis e metodologias para organização das classes, para citar alguns exemplos das ferramentas que temos para facilitar o uso do CSS.</p>
<p>Mas é claro, como quase tudo no mundo do frontend, as opções não param por ai. Dependendo do framework que você usa, também existem algumas alternativas diferentes para escrever CSS <em>{como se já não fosse complexo o suficiente haha, mas vamos falar disso depois}</em>.</p>
<p>Aqui na Alice, <a href="https://medium.com/alice-tech/h%C3%A1-1-ano-escolhemos-o-vue-js-419cf6c82c1d">nós usamos o Vue</a> e durante algumas semanas no nosso chapter de frontend, discutimos qual seria o padrão que iríamos adotar. Antes de tomar uma decisão, nós testamos as opções mais comuns e algumas obscuras que a comunidade ainda não está usando tanto. Como o nosso chapter de frontends não é muito grande, é importante para nós termos um padrão bem definido <em>{já que cada pessoa está em um time diferente}</em> e que seja fácil para quem não trabalha com frontend <em>{já que nem todo time tem alguém com esse foco}</em>.</p>
<p>No decorrer desse artigo, junto com os pontos que levantamos, tem algumas implementações básicas de um componente de botão <em>{que chamei ele de base-button}</em> que tem algumas propriedades: <em>tamanho</em>, <em>ícone</em> e <em>loading </em>que são as responsáveis por mudar o comportamento/CSS.</p>
<p>Então aperte o cinto que vamos seguir numa jornada do que nós encontramos em cada uma das possibilidades ✨</p>
<h2>Mas antes, uma leve introdução ao vue file</h2>
<p>Para quem nunca trabalhou com o Vue antes, é possível criar componentes usando arquivos <em>.vue</em>, que possuem o HTML dentro do &lt;template&gt;, o JS dentro de &lt;script&gt; e o CSS dentro de &lt;style&gt;.</p>
<p>Focando no assunto desse post, na parte de CSS nós temos algumas alternativas: escrever o CSS puro <em>{assim como vemos da linha 16 a 18}</em>, ou escrever com algum pré-processador.</p>
<p>Escolhendo a segunda o opção, tudo que nós precisamos fazer é adicionar um atributo <em>lang</em> na linha 15 com o nome da <em>&#8220;linguagem&#8221;</em> que queremos <em>{Aqui na Alice nós usamos o </em><a href="https://sass-lang.com/"><em>SASS</em></a><em> com a sintaxe scss, então a maioria dos exemplos daqui pra frente terão o CSS escrito dessa forma}</em>.</p>
<p>Sabendo disso vamos começar falando de uma das nossas opções de escrever CSS, que não depende de estar usando ou não um pré-processador:</p>
<h3>BEM</h3>
<p>Acredito que essa seja uma das formas mais comum de escrever CSS. Por ser uma metodologia, não tem grandes segredos, mas não significa que seja fácil. Pensar no nome das coisas provavelmente é a parte mais difícil do desenvolvimento de software <em>{risos}</em>, e com o <a href="http://getbem.com/introduction/">BEM</a> é preciso pensar com carinho no nome das classes para que a estrutura faça sentido.</p>
<p>Para quem nunca trabalhou com a metodologia antes, vamos a uma explicação rápida:</p>
<figure><img decoding="async" src="https://cdn-images-1.medium.com/max/670/1*2obrsDtnpAfExJALr3ROpQ.png" alt="" /><figcaption><a href="https://keepinguptodate.com/pages/2020/05/bem-visually-explained/">BEM Visually Explained</a> — By Jon Keeping</figcaption></figure>
<p>Nós basicamente dividimos uma classe em três pedaços:</p>
<ul>
<li>O <em>Block</em> representa o bloco que vai ser estilizado <em>{normalmente algum elemento que esteja envolvendo outros elementos/outras tags}.</em></li>
<li>O <em>Element</em> é algum elemento ou tag que esteja dentro desse bloco, e para identificarmos ele facilmente, é separado por dois <em>underscores</em>.</li>
<li>O <em>Modifier</em> significa que o estado daquele elemento mudou, o que significa que o nosso layout vai mudar graças; a separação dele é por dois <em>dashes</em>.</li>
</ul>
<p>Isso significa que em uma classe eu posso ter dois <em>elements</em>? Ou dois <em>modifiers</em>? Não. A estrutura do BEM espera que você tenha um de cada, por isso para pessoas que não estão familiarizadas com a metologia, pode ser bem confuso como criar uma classe nova. <em>{</em><a href="https://keepinguptodate.com/pages/2020/05/bem-visually-explained/"><em>Nesse artigo</em></a><em> tem uma explicação detalhada do uso do BEM e erros comuns, vale a leitura!}</em></p>
<p>De qualquer forma, se usado corretamente vários problemas de CSS são resolvidos, além de termos uma boa organização.</p>

<p>Agora vamos para a aplicação dessa metologia no Vue.</p>
<p>Começando pelas linhas 4, 5, 6, 7 — aqui nós temos classes condicionais baseadas em alguns atributos <em>{que no nosso exemplo são props declaradas nas linhas 28 e 29}</em>, uma coisa que podemos ver é que por serem condicionais, usamos o <em>modifier</em> para alterar visualmente o layout de cada uma delas <em>{já que elas representam um estado do nosso botão}</em>.</p>
<p>Na linha 12, temos uma classe com um <em>element</em>, pois esse componente de icone representa um elemento no nosso bloco <em>{que nesse exemplo é o botão}</em>.</p>
<p>Por fim, na linha 34 temos a declaração da lang, que como é importante dizer que só vai funcionar se o projeto está preparado para o pré-processador declarado. Se você começar um projeto usando o <a href="https://cli.vuejs.org/">Vue CLI</a> é uma das coisas que você pode ou não escolher. Se você quiser mudar o lang, na <a href="https://vue-loader.vuejs.org/guide/pre-processors.html">documentação do Vue</a> tem um passo-a-passo.</p>
<h3>Scoped CSS</h3>
<p>Você pode se perguntar: por quê exatamente eu preciso do BEM? Não é só sair espalhando minhas classes por ai e tudo bem?</p>
<p>Conforme você vai escrevendo o seu CSS, no final das contas o Vue vai pegar o CSS de todos os componentes sendo usados naquela página e jogar ele no &lt;head&gt;. O que significa que qualquer componente vai ser afetado por qualquer regra definida em um componente. O BEM tenta resolver isso tendo classes especificas que não vão afetar outro componente tão facilmente.</p>
<p>É ai que entra o <a href="https://vue-loader.vuejs.org/guide/scoped-css.html">scoped CSS</a>. Ele nos ajuda a resolver esse problema de escopo adicionando um atributo a mais nas nossas tags HTML para deixar as classes específicas para aquele componente.</p>
<p>Tudo o que precisamos para isso funcione é adicionar o atributo <em>scoped</em> à declaração de &lt;style&gt;, assim como na linha 34 do exemplo.</p>
<p><iframe loading="lazy" src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/4c1cc874afea1ff0fbbb82cd2134220d/href">https://medium.com/media/4c1cc874afea1ff0fbbb82cd2134220d/href</a></iframe></p>
<p>Para entender melhor vamos pegar a classe na linha 5.</p>
<p>O Vue vai transformar ela em algo como: .<em>loading[data-v-763db97b]</em>. Esse atributo novo sempre vai começar com <em>data-v </em>e vai terminar com uma <em>hash </em>aleatória, o que ajuda caso tenhamos classes iguais <em>{elas não vão colidir graças ao hash} </em>e impede que um componente distante seja afetado.</p>
<p>O problema dessa solução é que mesmo com esse atributo a mais na tag HTML, as regras afetam os componentes filhos. Olhando no exemplo ao lado, se o &lt;base-icon&gt; tivesse a classe<em> &#8220;icon&#8221;</em> e removêssemos a linha 12, as regras de CSS dessa classe afetariam o componente filho mesmo assim.</p>
<p>Podemos resolver isso facilmente evitando seletores iguais <em>{até mesmo usando uma metologia como o BEM que vimos anteriomente}</em>, para não correr o risco de herdar regras que não gostaríamos.</p>
<h3>CSS Modules</h3>
<p>Assim como a solução anterior, o <a href="https://vue-loader.vuejs.org/guide/css-modules.html#usage">CSS Modules</a> tenta nos ajudar com esse problema de conflitar regras de CSS ou herdar regras que não gostariamos.</p>
<p>A diferença dele para o <em>scoped</em>, é que não teremos um atributo novo no HTML e sim uma classe gerada pelo Vue, composta pelo nome do componente + o nome da classe que nós colocamos no CSS + uma hash aleatória.</p>
<p>Para que essa solução funcione, precisamos adicionar o atributo <em>module</em> à declaração de &lt;style&gt;, assim como na linha 35 do exemplo.</p>
<p><iframe loading="lazy" src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/835a20022087c3a3aa6756877efde63d/href">https://medium.com/media/835a20022087c3a3aa6756877efde63d/href</a></iframe></p>
<p>Uma das coisas mais importantes aqui é que a sintaxe de declarar uma classe sempre vai ser <em>:class=&#8221;$style.xpto&#8221; </em>e com o nome da classe sempre em <em>camelCase</em>. E no caso de classes condicionais como na linha 5, 6 e 7, precisamos usar a classe dentro de colchetes.</p>
<p>Para entender melhor, vamos pegar a linha 5 de exemplo. No fim das contas o Vue vai gerar uma classe parecida com <em>BaseButton_loading_1VuSe</em>. Isso vai resolver o nosso problema de conflito de regras e não é algo que interfere nos filhos.</p>
<p>Mas <em>e se</em> você quisesse que isso acontecesse? Até agora pontuei que um componente filho herdar as regras do pai era uma coisa ruim, mas dependendo da situação é exatamente isso que nós queremos para não repetir código.</p>
<p>Nesse caso, você pode passar as classes como <em>prop</em> para o componente filho, ou usar <a href="https://sass-lang.com/documentation/at-rules/mixin">mixins</a> de um pré-processador e importar nos dois componentes.</p>
<figure><img decoding="async" src="https://cdn-images-1.medium.com/max/1024/0*zmhmFWohYMyOXc0X" alt="" /><figcaption>Photo by <a href="https://unsplash.com/@alistairmacrobert?utm_source=medium&amp;utm_medium=referral">Alistair MacRobert</a> on <a href="https://unsplash.com?utm_source=medium&amp;utm_medium=referral">Unsplash</a></figcaption></figure>
<h3>Achou que tinha acabado?</h3>
<p>Achou errado!</p>
<p>As três soluções que vimos até agora, são as formas oficiais do Vue de definir CSS, mas a partir daqui vamos entrar no mundo obscuro das formas alternativas.</p>
<p>Nós separamos duas para testar e ambas são frameworks <a href="https://cssinjs.org/?v=v10.5.1">CSS-in-JS</a>, o que significa que nós escrevemos o CSS no JS e não precisamos mais da tag &lt;style&gt; nos nossos componentes.</p>
<h3>Aphrodite</h3>
<p>Começando pelo <a href="https://github.com/Khan/aphrodite">Aphrodite</a> <em>{que não tem muita coisa sobre o uso dele com o Vue na internet e eu usei </em><a href="https://medium.com/@nicholasbaroni/styling-vue-components-with-aphrodite-dd53bc2fa9d8"><em>esse artigo</em></a><em> como referência para a minha implementação}</em>.</p>
<p><iframe loading="lazy" src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/15e50f0ad53bdfef0f348b7478f076a7/href">https://medium.com/media/15e50f0ad53bdfef0f348b7478f076a7/href</a></iframe></p>
<p>Inicialmente, nós precisamos importar duas coisas do framework: o <em>StyleSheet</em> e o <em>css {como vemos na linha 8}</em>.</p>
<p>O <em>StyleSheet </em>vai ser o responsável por gerar as nossas regras de CSS baseado na estrutura de objeto com o nome da classe sendo a chave, e o valor sendo os atributos de CSS <em>{linha 10 à 19}</em>.</p>
<p>E para que nós possamos usar essas classes no HTML, primeiro precisamos expor elas no JS <em>{como vemos da linha 22 à 24} </em>e usamos o <em>css </em>na linha 2 <em>{separando os nomes das classes por vírgula se necessário}</em>.</p>
<p>Agora vamos voltar o mesmo componente de botão dos exemplos anteriores, mas dessa vez usando Aphrodite:</p>
<p><iframe loading="lazy" src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/c19aebfbe771d7f29025293b5708c073/href">https://medium.com/media/c19aebfbe771d7f29025293b5708c073/href</a></iframe></p>
<p>Temos algumas limitações com essa solução, e de cara o que mais me incomodou foi que por padrão todas as regras são geradas com<em> !important</em>. A linha 18 poderia estar importando só de <em>&#8216;aphoridite&#8217;</em>, mas para não ter o comportamento de <em>!important</em>, eu acabei importando as dependências necessárias de outro pacote.</p>
<p>Também não existe um jeito oficial de definir classes aninhados <em>{ou seja, uma classe dentro de outra classe}</em>, com isso precisamos ter classes diferentes para um estado específico de um elemento, como por exemplo na linha 27 e 28, onde o componente de ícone que nos exemplos anteriores só tinha uma classe, aqui nós precisamos de duas.</p>
<p>Com essa implementação, as classes geradas são completamente aleatórias <em>{algo parecido com _w3twfb}</em>, o que dificulta um pouco encontrar onde que essas regras foram definidas, mas tem a vantagem de serem nomes curtos.</p>
<p>Por fim, a implementação de exemplo não é a mais otimizada possível, dá para criar um plugin que importe o Aphrodite em todos os nossos componentes.</p>
<h3>Styled Components</h3>
<p>Por fim chegamos na última opção da nossa lista, o <a href="https://github.com/styled-components/vue-styled-components">Styled Components</a>, que nos permite criar componentes estilizados.</p>
<p><iframe loading="lazy" src="" width="0" height="0" frameborder="0" scrolling="no"><a href="https://medium.com/media/ec9dd6c8f4bca0bdc59cb46af4576e02/href">https://medium.com/media/ec9dd6c8f4bca0bdc59cb46af4576e02/href</a></iframe></p>
<p>Na linha 22 e 33 temos dois componentes sendo definidos usando o <em>styled</em> importado do framework. O primeiro parâmetro é a tag HTML que vai ser renderizada, o segundo são as <em>props</em> daquele componente. A partir dai é possível retornar todas as regras de CSS necessárias<em> {e condicionar elas dependendo de uma propriedade, o que nos dá muita liberdade}</em>.</p>
<p>Por mais diferente que essa implementação seja, esses dois componentes são iguais a qualquer outro definido por um arquivo vue <em>{claro, com as suas limitações, ele é um componente puramente visual, então não vamos ter métodos ou outros tipos de atributos nele} </em>e precisa ser declarado como na linha 42 para ser usado pelo HTML.</p>
<p>Eles também não precisavam estar dentro do <em>vue file</em> <em>{só coloquei aqui para facilitar o exemplo rs}.</em> Por serem componentes normais, poderiam estar em arquivos separados para serem importados pelo base-button.</p>
<p>É uma solução simples para componentes básicos.</p>
<figure><img decoding="async" src="https://cdn-images-1.medium.com/max/1024/0*U_Hpbae9C1fL-0mi" alt="" /><figcaption>Photo by <a href="https://unsplash.com/@sagarapher?utm_source=medium&amp;utm_medium=referral">Sagar Rana</a> on <a href="https://unsplash.com?utm_source=medium&amp;utm_medium=referral">Unsplash</a></figcaption></figure>
<h2>Conclusão</h2>
<p>Depois de muita discussão e uni-duni-tê, nós escolhemos usar o <strong>CSS Modules</strong> como padrão aqui na Alice <em>{pessoalmente, eu ainda prefiro usar o BEM, mas vamos manter isso entre eu e vc, blz? haha}</em>.</p>
<p>Pelas nossas conversas, foi a opção que mais fez sentido para o nosso momento e para os nossos produtos, onde muitas pessoas precisam mexer. Mesmo sendo uma sintaxe <em>diferente do normal</em>, é algo rápido de aprender/entender e ganhamos uma certa liberdade com qual nome de classes vamos colocar <em>{além de impedir certos problemas de herdar regras desnecessárias/ter seletores de tag HTML}</em>.</p>
<p>Mas por que fizemos essa escolha? As outras opções são ruins?</p>
<p>Particularmente as soluções não oficiais não me agradam, pois é uma dependência a mais que precisamos colocar no projeto, temos uma curva de aprendizado para escrever o CSS dentro do JS, e do meu ponto de vista não é mais vantajoso do que usar uma solução oficial do Vue.</p>
<p>Porém, não existe solução perfeita, não tem uma forma melhor do que a outra, no fim das contas é necessário considerar o que mais faz sentido para o projeto e para as pessoas que vão dar manutenção no código.</p>
<p>Hoje o <em>CSS Modules</em> faz sentido pra gente, mas quem sabe daqui um tempo não faça mais. É importante ter a mente aberta para qualquer solução, e do meu ponto de vista, manter o mais simples possível. 🙂</p>
<h3>Que tal fazer parte desse time?</h3>
<p>Estamos buscando pessoas que topem o desafio de transformar a saúde no Brasil através da tecnologia. <a href="https://www.alice.com.br/carreiras">Clica aqui</a> para saber mais das vagas que temos em aberto! 🙂</p>
<p>O post <a href="https://alice.com.br/tech/qual-a-melhor-forma-de-escrever-css-no-vue/">Melhor forma de escrever CSS no Vue</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></content:encoded>
					
		
		
			</item>
		<item>
		<title>Privacidade em healthtechs: como a Alice garante segurança</title>
		<link>https://alice.com.br/tech/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar/</link>
		
		<dc:creator><![CDATA[Bruno Federowski]]></dc:creator>
		<pubDate>Sat, 20 Jul 2024 20:23:39 +0000</pubDate>
				<category><![CDATA[Development]]></category>
		<guid isPermaLink="false">https://alice.com.br/tech/sem-categoria/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar/</guid>

					<description><![CDATA[<p>Quando entrei na Alice para ajudar a desenhar o programa de Data Privacy da empresa, eu mal sabia o que dizia a LGPD e como ela iria impactar praticamente todas as empresas do Bras</p>
<p>O post <a href="https://alice.com.br/tech/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar/">Privacidade em healthtechs: como a Alice garante segurança</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></description>
										<content:encoded><![CDATA[<p>Quando entrei na Alice para ajudar a desenhar o programa de Data Privacy da empresa, 5 meses atrás, eu mal sabia o que dizia a <a href="http://www.planalto.gov.br/ccivil_03/_ato2015-2018/2018/lei/L13709compilado.htm">Lei Geral de Proteção de Dados</a> e como ela iria impactar praticamente todas as empresas do Brasil quando entrasse em vigor.</p>
<p>Pode até não parecer, mas eu fiz questão de deixar isso claro durante todo o meu processo de contratação, e o fato da Alice ter me dado esse voto de confiança já diz muito sobre a empresa: aqui, estamos mais interessados no brilho nos olhos e na vontade de aprender de cada um do que nas qualificações técnicas ou o conhecimento de ferramentas específicas.</p>
<p>Logo no começo da minha jornada por aqui, entrei para o <em>squad</em> de Privacidade que temos, que envolve pessoas das mais diversas áreas dentro da empresa <em>{como Produto, Engenharia, Jurídico, TI, Financeiro…}</em> e marquei conversas individuais com cada um como forma de entender um pouco sobre o que já tínhamos feito até o momento e qual a nossa visão para o futuro. Foi assim que tive dimensão do desafio e de sua importância para a Alice.</p>
<h2>A importância da privacidade para a Alice</h2>
<p>Aqui na Alice, a gente lida com dados muito sensíveis sobre a saúde dos nossos membros, o que inclui nossos funcionários e o que chamamos de membros “externos”, que são as pessoas que compraram nosso produto <em>{e são apaixonadas por ele}</em>.</p>
<p>Para uma empresa como a nossa, não preciso nem dizer o quão importante é conseguirmos garantir a segurança e a privacidade dos dados que coletamos.</p>
<p>Um possível ataque ou vazamento de dados, como vimos recentemente acontecer com o STJ <em>{que </em><a href="https://thehack.com.br/stj-e-vitima-de-ransomware-e-tem-seus-dados-e-os-backups-criptografados/"><em>teve seus sistemas criptografados por um ransomware</em></a><em>} </em>ou com o Ministério da Saúde <em>{que acabou tendo a </em><a href="https://saude.estadao.com.br/noticias/geral,nova-falha-do-ministerio-da-saude-expoe-dados-pessoais-de-mais-de-200-milhoes,70003536340"><em>chave para acesso a dados de mais de 200 milhões de brasileiros divulgada</em></a><em>}</em> pode prejudicar não só a reputação e marca da Alice, como acarretar em multas e, pior, na perda da confiança dos nossos membros.</p>
<p>Para aumentar o tamanho do desafio <em>{ainda bem, porque se fosse fácil eu nem estaria aqui pra contar essa história}</em>, o produto oferecido pela Alice é um produto que depende do compartilhamento de dados de saúde entre diferentes profissionais e instituições.</p>
<p>Esse compartilhamento existe para que possamos fazer o que chamamos de “coordenação de cuidados”, que nada mais é que um termo bonito para dizer que, aqui, queremos que nossos membros tenham experiências mágicas, do tipo:</p>
<ul>
<li>Chegar numa consulta com um especialista que já te recebe pelo nome, sabe todo o seu histórico e o motivo do atendimento</li>
<li>Depois da consulta, conversar com o seu Time de Saúde <em>{o time de médicos, enfermeiros, preparadores físicos e nutricionistas que cuida de cada membro Alice}</em> e perceber que eles já sabem o que foi discutido e quais foram as recomendações do especialista</li>
<li>Ir ao laboratório fazer um exame e, ao se identificar <em>{só com o CPF, nada de códigos e carteirinhas}</em>, já ser atendido por alguém que tem todo o seu encaminhamento e contexto dos pedidos</li>
</ul>
<p>Por esse motivo, desde a sua concepção, a Alice tem a privacidade dos membros como um dos seus pilares. Mas como fazemos isso quando dependemos tanto justamente do compartilhamento de informações sensíveis para entregarmos mais saúde aos nossos membros?</p>
<h2>Cultura e tecnologia como ferramentas para entregar privacidade</h2>
<p>A resposta para essa pergunta <em>{como garantir privacidade em uma empresa cujo business model parte da premissa do compartilhamento de dados sensíveis?}</em> passa por duas principais alavancas: a criação de uma forte cultura de segurança de dados e respeito à privacidade dos membros e a utilização da tecnologia como ferramenta viabilizadora para a execução de melhorias nos produtos e processos da empresa.</p>
<h3>Cultura</h3>
<figure class="wp-attachment-165" ><img loading="lazy" decoding="async" class="wp-image-165 size-large" src="https://alice.com.br/tech/wp-content/uploads/2024/07/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar-2-1024x768.jpg" alt="" width="1024" height="768" srcset="https://alice.com.br/tech/wp-content/uploads/2024/07/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar-2-1024x768.jpg 1024w, https://alice.com.br/tech/wp-content/uploads/2024/07/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar-2-300x225.jpg 300w, https://alice.com.br/tech/wp-content/uploads/2024/07/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar-2-768x576.jpg 768w" sizes="auto, (max-width: 1024px) 100vw, 1024px" /></figure>
<p>Um dos conceitos mais importantes que temos como mantra aqui na Alice é o de <em>Privacy by Design</em>. De forma bem simplificada, <em>Privacy by Design</em> é uma forma de abordar e resolver desafios de privacidade logo na concepção de um produto, e não após o produto ser lançado e o risco ser identificado.</p>
<p>Isso significa, por exemplo, que os PMs <em>{Product Managers}</em> e desenvolvedores da Alice têm uma atuação proativa para entender a melhor forma de criar uma nova ferramenta que já nasça adequada à proteção da privacidade dos nossos membros. Não preciso nem dizer que essa forma de desenvolver produtos é muito mais eficiente e segura do que se, no futuro, tivéssemos que adaptar ferramentas já existentes para adequá-las do ponto de vista de privacidade.</p>
<p>Inclusive, para uma empresa que cresce de forma tão acelerada, como é o caso da Alice, lançando novos produtos e funcionalidades semanalmente, ter os conceitos de <em>Privacy by Design</em> embutidos na cultura dos times é essencial para garantir que não estejamos sempre correndo atrás do prejuízo e fazendo remendos em nossas ferramentas e produtos, e consigamos manter a agilidade necessária e esperada de uma startup com ambições tão grandes quanto as nossas.</p>
<p>Além dos princípios do <em>Privacy by Design</em>, uma forte cultura de privacidade ajuda a garantir que os funcionários da Alice sigam outras boas práticas de privacidade, como por exemplo:</p>
<ul>
<li>A não exposição de dados pessoais de membros em canais de comunicação internos com muitos colaboradores <em>{por aqui, usamos o Slack}</em></li>
<li>A utilização da mínima quantidade de dados pessoais possível em determinado processo ou fluxo de informações</li>
<li>A garantia de que softwares utilizados para o tratamento de dados pessoais possuam determinados requisitos de segurança e proteção à privacidade <em>{no caso de dados de saúde, temos também a exigência de que todos os softwares sejam </em><a href="https://en.wikipedia.org/wiki/Health_Insurance_Portability_and_Accountability_Act"><em>HIPAA</em></a><em>-compliant}</em></li>
</ul>
<p>Ainda falando sobre a importância da cultura nesse processo, uma das principais virtudes que temos na Alice é a <em>transparência</em> com nossos membros, parceiros e também entre nossos times. A união da transparência com a cultura de privacidade da Alice resultou na <a href="https://www.alice.com.br/footer/politica-de-privacidade">Política de Privacidade</a> mais incrível desse Brasilzão — nela, nossos membros podem tirar todas as suas dúvidas a respeito do que fazemos com seus dados e quais são seus direitos sobre eles.</p>
<p>Para se manter e fortalecer essa cultura de proteção à privacidade de dados, não existe atalho ou segredo: é muito importante que existam sessões de treinamento recorrentes, com o suporte das lideranças da empresa, e que o assunto seja sempre abordado em fóruns públicos em que todos poderão se educar e tirar suas dúvidas sobre o tema.</p>
<h3>Tecnologia</h3>
<figure class="wp-attachment-167" ><img loading="lazy" decoding="async" class="size-large wp-image-167" src="https://alice.com.br/tech/wp-content/uploads/2024/07/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar-3-1024x684.jpg" alt="" width="1024" height="684" srcset="https://alice.com.br/tech/wp-content/uploads/2024/07/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar-3-1024x684.jpg 1024w, https://alice.com.br/tech/wp-content/uploads/2024/07/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar-3-300x200.jpg 300w, https://alice.com.br/tech/wp-content/uploads/2024/07/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar-3-768x513.jpg 768w" sizes="auto, (max-width: 1024px) 100vw, 1024px" /></figure>
<p>A Alice é, antes de mais nada, uma <em>healthtech</em>. Aqui, acreditamos que a tecnologia é fundamental para conseguirmos entregar mais saúde aos nossos membros.</p>
<p>É graças a ela que conseguimos escalar soluções de coordenação de cuidados <em>{como eu expliquei lá atrás}</em>, realizar o contato proativo com os nossos membros exatamente nos momentos adequados ou garantir que estejamos sempre a um clique de distância através do Alice Agora <em>{nossa ferramenta de chat instantâneo entre o membro e nossos Times de Saúde}.</em></p>
<p>Além de acreditarmos na tecnologia para a entrega de saúde, entendemos que ela é também peça essencial para a promoção da privacidade dos membros. Através dela, nós implementamos medidas como:</p>
<ul>
<li>A separação entre os dados de saúde <em>{não identificados}</em> e os dados pessoais dos nossos membros em duas estruturas de bases de dados separadas, com uma terceira base <em>{guardada a sete chaves}</em> funcionando como a chave para identificar os dados de saúde. Assim, protegemos a identidade dos nossos membros caso ocorra um possível vazamento <em>{toc, toc, toc}</em> da base com dados sensíveis</li>
<li>A de-identificação dos dados dos nossos membros <em>{o uso de um código interno nas nossas rotinas operacionais, ao invés de usarmos nomes ou CPFs}</em></li>
<li>A automatização do envio e recebimento de dados de saúde para/dos nossos especialistas <em>{lembra que, ao realizarem um atendimento, eles já têm todo o contexto e histórico médico de quem estão atendendo?}</em></li>
<li>A disponibilização dos resultados de exames diretamente no nosso app <em>{assim, os membros não precisam ficar enviando PDFs por e-mail para o seu Time de Saúde, que consegue acessar os resultados de forma automática}</em></li>
<li>A restrição do acesso às nossas bases e sistemas apenas às pessoas essenciais</li>
</ul>
<h2>E agora? O que vem a seguir?</h2>
<p><figure class="wp-attachment-168" ><img loading="lazy" decoding="async" class="aligncenter size-large wp-image-168" src="https://alice.com.br/tech/wp-content/uploads/2024/07/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar-4-1024x683.jpg" alt="" width="1024" height="683" srcset="https://alice.com.br/tech/wp-content/uploads/2024/07/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar-4-1024x683.jpg 1024w, https://alice.com.br/tech/wp-content/uploads/2024/07/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar-4-300x200.jpg 300w, https://alice.com.br/tech/wp-content/uploads/2024/07/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar-4-768x512.jpg 768w" sizes="auto, (max-width: 1024px) 100vw, 1024px" /></figure></p>
<p>Apesar de já termos percorrido um bom caminho para chegarmos até aqui, sabemos que o trabalho de promoção da segurança e privacidade dos dados na Alice <em>{e em qualquer empresa}</em> é um que nunca acabará: sempre teremos novos fluxos de dados para serem mapeados <em>{já contei que é muito importante termos um mapa de tudo o que acontece com os dados pessoais na empresa? só assim podemos priorizar o desenvolvimento de melhorias nos diferentes fluxos}</em>, novos colaboradores com quem compartilharmos nossa visão de como executar privacidade <em>{e aprendermos no processo!}</em> e novas demandas de funcionalidades para quebrarmos a cabeça durante seu desenho <em>{lembra do Privacy by Design?}</em>.</p>
<p>Dito isso, tenho confiança de que a Alice já é, e será cada vez mais, referência na forma como pensamos em privacidade em saúde. E fico muito feliz de fazer parte de tudo isso.</p>
<h2>Que tal fazer parte desse time?</h2>
<p>Estamos buscando pessoas que topem o desafio de transformar a saúde no Brasil através da tecnologia. <a href="https://www.alice.com.br/carreiras">Clica aqui</a> para saber mais das vagas que temos em aberto!</p>
<p>O post <a href="https://alice.com.br/tech/construindo-uma-healthtech-que-coloca-a-privacidade-de-seus-usuarios-em-primeiro-lugar/">Privacidade em healthtechs: como a Alice garante segurança</a> apareceu primeiro em <a href="https://alice.com.br/tech">Blog da Alice Tech</a>.</p>
]]></content:encoded>
					
		
		
			</item>
	</channel>
</rss>
