{"id":16761490,"url":"https://github.com/gustavofreze/financial","last_synced_at":"2026-01-22T05:03:31.103Z","repository":{"id":104270954,"uuid":"414017610","full_name":"gustavofreze/financial","owner":"gustavofreze","description":"POC de uma aplicação de domínio financeiro.","archived":false,"fork":false,"pushed_at":"2025-12-22T16:47:32.000Z","size":44759,"stargazers_count":76,"open_issues_count":0,"forks_count":3,"subscribers_count":5,"default_branch":"main","last_synced_at":"2025-12-24T04:53:07.624Z","etag":null,"topics":["clean-architecture","cqrs","domain-driven-design","event-sourcing","financial","hexagonal-architecture","kafka","kotlin","poc","proof-of-concept"],"latest_commit_sha":null,"homepage":"","language":"Kotlin","has_issues":false,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/gustavofreze.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2021-10-06T00:15:52.000Z","updated_at":"2025-12-22T16:46:36.000Z","dependencies_parsed_at":"2023-11-25T23:15:07.550Z","dependency_job_id":null,"html_url":"https://github.com/gustavofreze/financial","commit_stats":null,"previous_names":[],"tags_count":1,"template":false,"template_full_name":null,"purl":"pkg:github/gustavofreze/financial","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gustavofreze%2Ffinancial","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gustavofreze%2Ffinancial/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gustavofreze%2Ffinancial/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gustavofreze%2Ffinancial/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/gustavofreze","download_url":"https://codeload.github.com/gustavofreze/financial/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/gustavofreze%2Ffinancial/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28655038,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-01-22T01:17:37.254Z","status":"online","status_checked_at":"2026-01-22T02:00:07.137Z","response_time":144,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["clean-architecture","cqrs","domain-driven-design","event-sourcing","financial","hexagonal-architecture","kafka","kotlin","poc","proof-of-concept"],"created_at":"2024-10-13T04:42:44.358Z","updated_at":"2026-01-22T05:03:31.091Z","avatar_url":"https://github.com/gustavofreze.png","language":"Kotlin","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Financial\n\n[![License](https://img.shields.io/badge/license-MIT-green)](LICENSE)\n\n* [Overview](#overview)\n    - [Domínio](#domain)\n    - [Arquitetura](#architecture)\n    - [Organização da aplicação](#organization)\n    - [Casos de uso](#use_cases)\n* [Instalação](#installation)\n    - [Repositório](#repository)\n    - [Configuração](#settings)\n* [Roadmap](#roadmap)\n    - [Verificando o ambiente](#checking)\n    - [Executando os casos de uso](#run_use_cases)\n* [Testes](#tests)\n* [Úteis](#useful)\n\n\u003cdiv id=\"overview\"\u003e\u003c/div\u003e \n\n## Overview\n\nA ideia deste projeto é aplicar o conteúdo estudado sobre **Clean Architecture**, **Hexagonal Architecture**,\n**Domain-Driven Design**, **Event Sourcing**, **CQRS** e **Kafka**.\n\n\u003cdiv id='domain'\u003e\u003c/div\u003e \n\n### Domínio\n\nO domínio da aplicação é **financial**, que possui um subdomínio **accounting**. Dentro do subdomínio, temos dois\ncontextos, **account** e **bookkeeping**.\n\n\u003c!--suppress HtmlDeprecatedAttribute --\u003e\n\u003cp align=\"center\"\u003e\n    \u003cimg src=\"doc/images/overview/financial-domain.png\" alt=\"Representação do domínio.\"/\u003e\n    \u003cbr /\u003e\n    \u003ctl\u003eRepresentação do domínio.\u003c/tl\u003e\n\u003c/p\u003e\n\n#### Accounting\n\nO **Accounting** (contabilidade) é o processo de registro de transações financeiras pertencentes a uma empresa.\n\n**Account**\n\nO contexto de account nada mais é do que uma conta contábil, que contém contas nas quais as informações sobre as\ntransações de débitos e créditos são classificadas e resumidas.\n\n**Bookkeeping**\n\nO contexto de bookkeeping é o registro das transações financeiras, e envolve a preparação de documentos de origem para\ntodas as transações, operações e outros eventos de uma empresa. As transações incluem compras, vendas, recebimentos e\npagamentos por uma pessoa individual ou uma organização.\n\n\n\u003cdiv id='architecture'\u003e\u003c/div\u003e \n\n### Arquitetura\n\nA arquitetura da aplicação está dividida em alguns pilares, os quais delimitam os contextos.\n\n\u003c!--suppress HtmlDeprecatedAttribute --\u003e\n\u003cp align=\"center\"\u003e\n    \u003cimg src=\"doc/images/overview/financial-architecture.png\" alt=\"Arquitetura do Financial.\"/\u003e\n    \u003cbr /\u003e\n    \u003ctl\u003eArquitetura do Financial.\u003c/tl\u003e\n\u003c/p\u003e\n\n\n\u003c!--suppress HtmlDeprecatedAttribute --\u003e\n\u003cp align=\"center\"\u003e\n    \u003cimg src=\"doc/images/overview/financial-architecture-flow.png\" alt=\"Fluxo da aplicação.\"/\u003e\n    \u003cbr /\u003e\n    \u003ctl\u003eFluxo da aplicação.\u003c/tl\u003e\n\u003c/p\u003e\n\n- **Command**\n\n  Um comando é uma ordem para execução de algum caso de uso de negócio, eles geralmente resultam em eventos sendo\n  emitidos.\n\n\n- **Core**\n\n  É o núcleo da aplicação. Os objetos desta camada contém a lógica para manipular os casos de uso, que são específicos\n  do próprio domínio. O core é independente dos processos de negócio que acionam essa lógica, são independentes e\n  desconhecem completamente outras camadas.\n\n\n- **Driven**\n\n  No driven estão os adaptadores de acionamento, os quais implementam as interfaces de saída da aplicação. Isso permite\n  que o núcleo da aplicação exponha funcionalidades para o exterior.\n\n\n- **Driver**\n\n  No driver estão os adaptadores primários que envolvem uma porta e a usam para informar ao core o que fazer. Eles\n  traduzem tudo o que vem de um mecanismo de entrega em uma chamada de método no core.\n\n\n- **Query**\n\n  Implementações das recuperações dos modelos de leitura.\n\n\u003cdiv id=\"organization\"\u003e\u003c/div\u003e \n\n### Organização da aplicação\n\nDe forma geral, a aplicação está separada em quatro módulos:\n\n```\napplication\n┣ 📂account\n┣ 📂bookkeeping\n┣ 📂shared\n┗ 📂starter\n```\n\n**Account**: Possui a lógica/regra de negócio do contexto de account.\n\n**Bookkeeping**: Possui a lógica/regra de negócio do contexto de bookkeeping.\n\n**Shared**: Possui implementações e interfaces comuns, que não detém lógica/regra de negócio. O conteúdo desse módulo\npode ser convertido em várias bibliotecas.\n\n**Starter**: Possui a inicialização dos componentes de plataforma usados pela aplicação, e as configurações de\ndependências da aplicação.\n\n\u003cdiv id='use_cases'\u003e\u003c/div\u003e \n\n### Casos de uso\n\n**Bookkeeping**\n\nNo contexto de bookkeeping, quando uma operação contábil é registrada a partir de um comando\n`RegisterFinancialTransaction`, então um evento de `TransactionRegistered` ocorre, e é registrado no\ntópico `financial.accounting.bookkeeping.transaction-registered`. Apenas transações com valores maiores que **R$ 0,00**\nsão registradas.\n\nO streaming dos dados é realizado usando o Kafka, onde foi utilizado o método\nde [CDC](https://en.wikipedia.org/wiki/Change_data_capture), implementando uma abordagem utilizando logs.\n\n\u003c!--suppress HtmlDeprecatedAttribute --\u003e\n\u003cp align=\"center\"\u003e\n    \u003cimg src=\"doc/images/overview/financial-kafka-cdc.png\" alt=\"Fluxo de CDC com o Kafka.\"/\u003e\n    \u003cbr /\u003e\n    \u003ctl\u003eFluxo de CDC com o Kafka.\u003c/tl\u003e\n\u003c/p\u003e\n\n**Account**\n\nNo contexto de account, uma política reage ao evento `TransactionRegistered` emitido pelo contexto de bookkeeping, o que\nresulta em um comando `AdjustBalance`, que faz a atualização dos saldos das contas.\n\n\u003c!--suppress HtmlDeprecatedAttribute --\u003e\n\u003cp align=\"center\"\u003e\n    \u003cimg src=\"doc/images/overview/financial-kafka-flow-macro.png\" alt=\"Fluxo de produção e consumo do evento.\"/\u003e\n    \u003cbr /\u003e\n    \u003ctl\u003eFluxo de produção e consumo do evento.\u003c/tl\u003e\n\u003c/p\u003e\n\n\u003cdiv id='installation'\u003e\u003c/div\u003e \n\n## Instalação\n\n\u003cdiv id='repository'\u003e\u003c/div\u003e \n\n### Repositório\n\nPara clonar o repositório usando a linha de comando, execute:\n\n```bash\ngit clone https://github.com/gustavofreze/financial.git\n```\n\n\u003cdiv id='settings'\u003e\u003c/div\u003e \n\n### Configuração\n\nVerifique se algum processo usa as portas: **2181**, **5432**, **8080**, **8081**, **8083**, **9000**, **9001**\ne **9021**. Se alguma das portas descritas estiver em uso, ela deve ser “liberada”.\n\nPara instalar e configurar o projeto, execute na raiz do projeto:\n\n```bash\nmake configure\n```\n\n\u003cdiv id='roadmap'\u003e\u003c/div\u003e \n\n## Roadmap\n\n\u003cdiv id='checking'\u003e\u003c/div\u003e \n\n### Verificando o ambiente\n\nPara executar os casos de uso, basta estar com o ambiente docker inicializado.\n\nVocê pode conferir executando:\n\n```bash\ndocker ps --format \"table {{.Names}}\\t{{.Status}}\"\n```\n\n\u003c!--suppress HtmlDeprecatedAttribute --\u003e\n\u003cp align=\"center\"\u003e\n    \u003cimg src=\"doc/images/roadmap/containers-status.png\" alt=\"Containers inicializados.\"/\u003e\n    \u003cbr /\u003e\n    \u003ctl\u003eContainers inicializados.\u003c/tl\u003e\n\u003c/p\u003e\n\nE posteriormente verifique a aplicação executando:\n\n```bash\ndocker logs -f app\n```\n\n\u003c!--suppress HtmlDeprecatedAttribute --\u003e\n\u003cp align=\"center\"\u003e\n    \u003cimg src=\"doc/images/roadmap/app-status.png\" alt=\"Aplicação pronta para executar os casos de uso.\"/\u003e\n    \u003cbr /\u003e\n    \u003ctl\u003eAplicação pronta para executar os casos de uso.\u003c/tl\u003e\n\u003c/p\u003e\n\n\n\u003cdiv id='run_use_cases'\u003e\u003c/div\u003e \n\n### Executando os casos de uso\n\nO primeiro comando a ser executado, pertence ao contexto de account. O comando `ShowBalance` exibe o saldo de todas as\ncontas.\n\n```bash\nmake show-balance\n```\n\n\u003c!--suppress HtmlDeprecatedAttribute --\u003e\n\u003cp align=\"center\"\u003e\n    \u003cimg src=\"doc/images/roadmap/opening-balance.png\" alt=\"Saldo inicial das contas.\"/\u003e\n    \u003cbr /\u003e\n    \u003ctl\u003eSaldo inicial das contas.\u003c/tl\u003e\n\u003c/p\u003e\n\nO segundo comando a ser executado, pertence ao contexto de bookkeeping. O comando `RegisterFinancialTransaction`\nregistra uma transação financeira.\n\n```bash\nmake register-financial-transaction\n```\n\n\u003c!--suppress HtmlDeprecatedAttribute --\u003e\n\u003cp align=\"center\"\u003e\n    \u003cimg src=\"doc/images/roadmap/register-financial-transaction.png\" alt=\"Transação financeira registrada.\"/\u003e\n    \u003cbr /\u003e\n    \u003ctl\u003eTransação financeira registrada.\u003c/tl\u003e\n\u003c/p\u003e\n\nApós o comando `RegisterFinancialTransaction` ter sido executado, um evento `TransactionRegistered` é gerado, e enviado\npara o tópico no Kafka, através do processo de CDC, conforme explicado anteriormente.\n\nNo contexto de account, a política irá reagir ao evento `TransactionRegistered`, o que resulta na execução do\ncomando `AdjustBalance`. O saldo é atualizado realizando uma operação de débito e crédito respectivamente. Mesmo se uma\nconta estiver com saldo de **R$ 0,00** ou **negativo**, a operação é realizada.\n\nPara conferir se o saldo foi atualizado, basta executar novamente o comando `ShowBalance`.\n\n```bash\nmake show-balance\n```\n\n\u003c!--suppress HtmlDeprecatedAttribute --\u003e\n\u003cp align=\"center\"\u003e\n    \u003cimg src=\"doc/images/roadmap/updated-balance.png\" alt=\"Saldo atualizado das contas.\"/\u003e\n    \u003cbr /\u003e\n    \u003ctl\u003eSaldo atualizado das contas.\u003c/tl\u003e\n\u003c/p\u003e\n\nAinda no contexto de account, caso ocorra uma falha ao executar uma política, o evento desta política vai para uma fila\nde solução de problemas, de forma que é possível tentar novamente sua execução.\n\nEssa fila de solução de problemas, é uma junção dos conceitos\nde [troubleshooting](https://en.wikipedia.org/wiki/Troubleshooting)\ne [DLQ](https://en.wikipedia.org/wiki/Dead_letter_queue).\n\nPara demonstrar na prática, existe um registro previamente registrado na fila troubleshooting. Para executar a política\nnovamente a partir da fila de troubleshooting, é necessário executar o comando `SolveFailures`.\n\n```bash\nmake solve-failures\n```\n\n\u003c!--suppress HtmlDeprecatedAttribute --\u003e\n\u003cp align=\"center\"\u003e\n    \u003cimg src=\"doc/images/roadmap/solve-failures.png\" alt=\"Execução da fila de troubleshooting.\"/\u003e\n    \u003cbr /\u003e\n    \u003ctl\u003eExecução da fila de troubleshooting.\u003c/tl\u003e\n\u003c/p\u003e\n\nCom a política de atualizar saldo executada, o saldo das contas foi mais uma vez atualizado.\n\nPara conferir se o saldo foi atualizado, basta executar novamente o comando `ShowBalance`.\n\n```bash\nmake show-balance\n```\n\n\u003c!--suppress HtmlDeprecatedAttribute --\u003e\n\u003cp align=\"center\"\u003e\n    \u003cimg src=\"doc/images/roadmap/updated-balance-by-failure.png\" alt=\"Saldo atualizado das contas, após a execução da política na fila de troubleshooting.\"/\u003e\n    \u003cbr /\u003e\n    \u003ctl\u003eSaldo atualizado das contas, após a execução da política na fila de troubleshooting.\u003c/tl\u003e\n\u003c/p\u003e\n\n\u003cdiv id=\"tests\"\u003e\u003c/div\u003e \n\n## Testes\n\n- Executa todos os testes:\n\n  ```bash\n  make test\n  ```\n\n- Executa os testes unitários:\n\n  ```bash\n  make unit-test\n  ```\n\n- Executa os testes de integração:\n\n  ```bash\n  make integration-test\n  ```\n\n\u003cdiv id=\"useful\"\u003e\u003c/div\u003e \n\n## Úteis\n\n- Para todos os containers do projeto:\n\n  ```bash\n  make stop\n  ```\n\n- Remove todos os containers e networks criados pelo projeto:\n\n  ```bash\n  make clean\n  ```\n\n- Remove todos os containers, networks e imagens criados pelo projeto:\n\n  ```bash\n  make clean-all\n  ```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgustavofreze%2Ffinancial","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fgustavofreze%2Ffinancial","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fgustavofreze%2Ffinancial/lists"}