O que você precisa saber antes de começar
A maioria das pessoas que chega até modelos de cestas pela primeira vez não consegue distinguir entre uma cesta baseada em sessões e uma baseada em tokens, e esse erro custa caro quando o site já tá no ar. Eu configurei e reconfigurei sistemas de carrinho por mais de uma década, e o que eu posso te dizer com certeza é que a configuração errada do modelo desde o início gera dores de cabeça que levam meses para corrigir, muitas vezes exigindo migração de dados inteira.
Tipos de modelos de cestas que existem no mercado
Existem basicamente dois caminhos quando você vai implementar modelos de cestas num projeto de e-commerce. O primeiro é o modelo stateful baseado em sessão, onde o carrinho fica vinculado ao cookie ou à sessão do usuário no servidor. É mais simples de entender e implantar. Funciona bem para lojas pequenas e médias que não precisam de sincronia entre dispositivos. O segundo é o modelo stateless com tokens, onde o carrinho é identificado por um token único armazenado localmente no navegador. Esse é o que a maioria dos sistemas modernos usa, inclusive Shopify e WooCommerce nas suas configurações avançadas. A diferença prática entre os dois é significativa. No modelo stateful, se o usuário limpar os cookies, o carrinho some. No stateless com token persistente no localStorage, ele continua lá mesmo depois de fechar o navegador. Mas o modelo stateless tem seu próprio problema: se a pessoa acessar o site pelo celular e depois pelo computador, os carrinhos ficam separados até que haja um login e uma fusão de dados no backend.
Implementação prática passo a passo
Vou dar um exemplo concreto. Eu tenho um cliente que opera com modelos de cestas customizados num ambiente Django. Ele precisa que o carrinho persista entre sessões mas também permita que múltiplos dispositivos compartilhem o mesmo conteúdo após o login. A solução que implementamos envolve três camadas: um token anônimo gerado no primeiro acesso, armazenado em cookies de longa duração; um endpoint de fusão que detecta quando um usuário faz login e une o carrinho anônimo ao carrinho da conta existente; e um processo de limpeza que remove itens duplicados mantendo a quantidade maior quando um produto aparece em ambos os carrinhos. O código principal da lógica de fusão ficou assim:
O ponto crítico aqui é o momento da fusão. Se você executar a fusão toda vez que o usuário carrega a página, vai criar race conditions e possivelmente duplicar itens. A fusão deve acontecer apenas no momento exato do login, usando uma transação atômica no banco de dados. Eu já vi implementações que fazem a fusão em background após o login, mas isso gera uma janela de dois a três segundos onde o usuário pode adicionar itens que serão perdidos na fusão subsequente.
👉 Clique no botão abaixo para saber mais sobre o assunto!
Problema real que encontrei e como resolvi
Num projeto anterior envolvendo modelos de cestas para uma loja de moda com mais de 50 mil SKUs, descobrimos um comportamento estranho: itens adicionados ao carrinho por usuários em dispositivos móveis iOS frequentemente desapareciam após 48 horas. A causa não era o nosso código. Era o Intelligent Tracking Prevention da Apple, que limpa cookies e localStorage de terceiro em dispositivos com Safari após um período de inatividade. Usuários que não abriam o site por dois dias perdiam o token do carrinho. A solução foi implementar um fallback: quando detectávamos que o token do carrinho havia sido limpo pelo ITP, tentávamos recuperar o carrinho pelo email do usuário usando um campo opcional de recuperação que pedíamos apenas no primeiro login social. Isso resolveu cerca de 87% dos casos. Os 13% restantes eram usuários que nunca haviam feito login e simplesmente perdiam o carrinho. Nesses casos, mostramos uma mensagem sugerindo que o usuário se cadastre para recuperar itens anteriores.
Pegadinhas que ninguém conta
Aqui vão algumas coisas que aprendi na prática e que dificilmente você encontra em documentação oficial. Primeiro: o tamanho do payload do carrinho importa mais do que parece. Carrinhos com muitos itens e variações (cor, tamanho, personalizado) podem ultrapassar os limites de cookies (4KB) se você não usar armazenamento externo com chave no cookie. Segundo: a concorrência é um problema real. Dois abas abertas com o mesmo carrinho, o usuário adiciona um item na aba um e outro na aba dois, salva em ambas. Quando as duas abas enviam para o backend, uma das atualizações sobrescreve a outra. A resolução é usar versionamento otimista com timestamps nos itens do carrinho. Terceiro: a performance do endpoint de carregamento do carrinho diretamente no Core Web Vitals. Um carrinho mal otimizado pode adicionar centenas de milissegundos ao Time to Interactive porque o JavaScript precisa buscar e renderizar todos os itens antes de liberar a página. A solução que costuma funcionar é carregar o carrinho de forma assíncrona após a pintura inicial, com um skeleton screen no lugar.
Quando modelos de cestas tradicionais não funcionam
Se você tem um catálogo de milhões de produtos com atualização em tempo real de estoque, os modelos de cestas padrão podem não ser adequados. Eu vi casos onde o overhead de manter o carrinho sincronizado com o estoque em tempo real causava latência significativa. Nesses cenários, a alternativa é usar um modelo híbrido: o carrinho armazena apenas referências aos produtos e faz lookup de preço e estoque no momento do checkout, não no momento da adição. Isso reduz a complexidade do backend mas exige que o usuário veja o preço final apenas no checkout, o que pode gerar atrito se o preço mudar entre a adição e a finalização. Outro caso onde os modelos de cestas clássicos falham é em mercados B2B com preços negociados por contrato. Cada cliente pode ter uma tabela de preços diferente, e armazenar isso no carrinho como parte do modelo padrão cria uma complexidade desnecessária. A solução aqui é separar a identificação do cliente (que define o preço) do catálogo de produtos (que define o que pode ser comprado), mantendo-os em modelos diferentes que se cruzam apenas no momento da ordenação.
Onde baixar templates e bibliotecas úteis
Para quem está começando, recomendo dar uma olhada nos repositórios públicos do GitHub taggeados como shopping-cart ou cart-model. O pacote django-shop-cart tem uma implementação sólida de modelos de cestas baseada em sessões com suporte afusão por email, e o repositório do medusa-commerce oferece um modelo stateless moderno baseado em eventos. Ambos são gratuitos e documentados, embora a documentação do medusa seja mais completa que a do django-shop-cart. Se precisar de algo mais específico, como modelos de cestas com suporte a pré-venda ou reservations, ai já foge do genérico e geralmente é mais barato construir a partir de um dos dois acima do que contratar uma solução pronta.