feature/research-di #1

Merged
behnam merged 37 commits from feature/research-di into develop 2024-11-21 15:50:19 +00:00
17 changed files with 64 additions and 52 deletions
Showing only changes of commit 43a622851d - Show all commits

2
.gitignore vendored
View File

@ -9,7 +9,7 @@
!.yarn/plugins
!.yarn/releases
!.yarn/versions
.vscode
# testing
/coverage

View File

@ -1,10 +1,10 @@
import fetchSummaryInfoUsecase from '@/feature/core/summary-info/domain/usecase/fetch-summary-info-usecase';
import {
BanknotesIcon,
ClockIcon,
UserGroupIcon,
InboxIcon,
} from '@heroicons/react/24/outline';
import { fetchCardData } from '@/app/lib/data';
const iconMap = {
collected: BanknotesIcon,
@ -14,21 +14,16 @@ const iconMap = {
};
export default async function CardWrapper() {
const {
numberOfInvoices,
numberOfCustomers,
totalPaidInvoices,
totalPendingInvoices,
} = await fetchCardData();
const {customersNumber, invoicesNumber, invoicesSummary } = await fetchSummaryInfoUsecase();
return (
<>
<Card title="Collected" value={totalPaidInvoices} type="collected" />
<Card title="Pending" value={totalPendingInvoices} type="pending" />
<Card title="Total Invoices" value={numberOfInvoices} type="invoices" />
<Card title="Collected" value={invoicesSummary.paid} type="collected" />
<Card title="Pending" value={invoicesSummary.pending} type="pending" />
<Card title="Total Invoices" value={invoicesNumber} type="invoices" />
<Card
title="Total Customers"
value={numberOfCustomers}
value={customersNumber}
type="customers"
/>
</>

View File

@ -1,9 +1,9 @@
import fetchCustomerInvoicesUsecase from '@/feature/core/customer-invoice/domain/usecase/fetch-customer-invoices-usecase';
import { ArrowPathIcon } from '@heroicons/react/24/outline';
import clsx from 'clsx';
import Image from 'next/image';
import { fetchLatestInvoices } from '@/app/lib/data';
export default async function LatestInvoices() {
const latestInvoices = await fetchLatestInvoices();
const latestInvoices = await fetchCustomerInvoicesUsecase();
return (
<div className="flex w-full flex-col md:col-span-4">
@ -26,25 +26,25 @@ export default async function LatestInvoices() {
>
<div className="flex items-center">
<Image
src={invoice.image_url}
alt={`${invoice.name}'s profile picture`}
src={invoice.customerImageUrl}
alt={`${invoice.customerName}'s profile picture`}
className="mr-4 rounded-full"
width={32}
height={32}
/>
<div className="min-w-0">
<p className="truncate text-sm font-semibold md:text-base">
{invoice.name}
{invoice.customerName}
</p>
<p className="hidden text-sm text-gray-500 sm:block">
{invoice.email}
{invoice.customerEmail}
</p>
</div>
</div>
<p
className="truncate text-sm font-medium md:text-base"
>
{invoice.amount}
{invoice.invoicesAmount}
</p>
</div>
);

View File

@ -1,9 +1,9 @@
import { generateYAxis } from '@/app/lib/utils';
import fetchRevenuesUsecase from '@/feature/core/revenue/domain/usecase/fetch-revenues-usecase';
import { CalendarIcon } from '@heroicons/react/24/outline';
import { fetchRevenue } from '@/app/lib/data';
export default async function RevenueChart() {
const revenue = await fetchRevenue();
const revenue = await fetchRevenuesUsecase();
const chartHeight = 350;

View File

@ -0,0 +1,27 @@
import di from "@/bootstrap/di/init-di"
import fetchCustomerInvoicesUsecase from "@/feature/core/customer-invoice/domain/usecase/fetch-customer-invoices-usecase";
import fetchCustomersUsecase from "@/feature/core/customer/domain/usecase/fetch-customers-usecase";
import fetchAllInvoicesAmountUsecase from "@/feature/core/invoice/domain/usecase/fetch-all-invoices-amount-usecase";
import fetchRevenuesUsecase from "@/feature/core/revenue/domain/usecase/fetch-revenues-usecase";
export default function dashboardAppModule() {
const dashboardDi = di.createChildContainer()
dashboardDi.register(fetchCustomersUsecase.name, {
useValue: fetchCustomersUsecase
})
dashboardDi.register(fetchAllInvoicesAmountUsecase.name, {
useValue: fetchAllInvoicesAmountUsecase
})
dashboardDi.register(fetchAllInvoicesAmountUsecase.name, {
useValue: fetchAllInvoicesAmountUsecase
})
dashboardDi.register(fetchCustomerInvoicesUsecase.name, {
useValue: fetchCustomerInvoicesUsecase
})
dashboardDi.register(fetchRevenuesUsecase.name, {
useValue: fetchRevenuesUsecase
})
return dashboardDi
}

View File

@ -12,7 +12,10 @@ import getSummaryInfoDi from "@/feature/core/summary-info/data/module/summary-in
import { revenueModuleKey } from "@/feature/core/revenue/domain/revenue-module-key";
import getRevenueDi from "@/feature/core/revenue/data/module/revenue-di";
const memoizedDis: Record<string, DependencyContainer> = {}
export default function serverDi(module: string): DependencyContainer {
if (memoizedDis[module]) return memoizedDis[module]
const getDi = {
[testModuleKey]: getTestModule,
[customerKey]: getCustomerDi,
@ -24,5 +27,7 @@ export default function serverDi(module: string): DependencyContainer {
if (!getDi) throw new Error("Server Di didn't found for module: " + module)
return getDi()
const di = getDi()
memoizedDis[module] = di
return di
}

View File

@ -1,16 +1,11 @@
import di from "@/bootstrap/di/init-di";
import CustomerInvoiceDbRepo from "@/feature/core/customer-invoice/data/repo/customer-invoice-db-repo";
import { customerInvoiceRepoKey } from "@/feature/core/customer-invoice/domain/i-repo/customer-invoice-repo";
import fetchCustomerInvoicesUsecase from "@/feature/core/customer-invoice/domain/usecase/fetch-customer-invoices-usecase";
import CustomerDbRepo from "@/feature/core/customer/data/repo/customer-db-repo";
import { DependencyContainer } from "tsyringe";
export default function getCustomerInvoiceDi(): DependencyContainer {
const customerInvoiceDi = di.createChildContainer()
customerInvoiceDi.register(fetchCustomerInvoicesUsecase.name, {
useValue: fetchCustomerInvoicesUsecase
})
customerInvoiceDi.register(customerInvoiceRepoKey, CustomerDbRepo)
customerInvoiceDi.register(customerInvoiceRepoKey, CustomerInvoiceDbRepo)
return customerInvoiceDi
}

View File

@ -2,7 +2,6 @@ import { formatCurrency } from "@/app/lib/utils";
import { sql } from "@/bootstrap/db/db";
import CustomerInvoice from "@/feature/core/customer-invoice/domain/entity/customer-invoice";
import CustomerInvoiceRepo from "@/feature/core/customer-invoice/domain/i-repo/customer-invoice-repo";
import { connection } from "next/server";
import postgres from "postgres";
type customerInvoiceDbResponse = {
@ -13,11 +12,8 @@ type customerInvoiceDbResponse = {
amount: string;
}
export default class CustomerDbRepo implements CustomerInvoiceRepo {
export default class CustomerInvoiceDbRepo implements CustomerInvoiceRepo {
async fetchList(): Promise<CustomerInvoice[]> {
// This is equivalent to in fetch(..., {cache: 'no-store'}).
connection()
try {
const data = await sql`
SELECT invoices.amount, customers.name, customers.image_url, customers.email, invoices.id

View File

@ -3,9 +3,10 @@ import serverDi from "@/feature/common/server-di";
import CustomerInvoice from "@/feature/core/customer-invoice/domain/entity/customer-invoice";
import CustomerInvoiceRepo, { customerInvoiceRepoKey } from "@/feature/core/customer-invoice/domain/i-repo/customer-invoice-repo";
import { customerInvoiceModuleKey } from "@/feature/core/customer-invoice/invoice-module-key";
import { connection } from "next/server";
export default function fetchCustomerInvoicesUsecase(): Promise<CustomerInvoice[]> {
export default async function fetchCustomerInvoicesUsecase(): Promise<CustomerInvoice[]> {
connection()
const repo = serverDi(customerInvoiceModuleKey).resolve<CustomerInvoiceRepo>(customerInvoiceRepoKey)
return repo.fetchList()
}

View File

@ -1,16 +1,11 @@
import di from "@/bootstrap/di/init-di";
import CustomerDbRepo from "@/feature/core/customer/data/repo/customer-db-repo";
import { customerRepoKey } from "@/feature/core/customer/domain/i-repo/customer-repo";
import fetchCustomersUsecase from "@/feature/core/customer/domain/usecase/fetch-customers-usecase";
import { DependencyContainer } from "tsyringe";
export default function getCustomerDi(): DependencyContainer {
const customerDi = di.createChildContainer()
customerDi.register(fetchCustomersUsecase.name, {
useValue: fetchCustomersUsecase
})
customerDi.register(customerRepoKey, CustomerDbRepo)
return customerDi
}

View File

@ -2,7 +2,7 @@ import serverDi from "@/feature/common/server-di";
import { customerKey } from "@/feature/core/customer/customer-key";
import CustomerRepo, { customerRepoKey } from "@/feature/core/customer/domain/i-repo/customer-repo";
export default function fetchCustomersAmountUsecase(): Promise<number> {
export default async function fetchCustomersAmountUsecase(): Promise<number> {
const repo = serverDi(customerKey).resolve<CustomerRepo>(customerRepoKey)
return repo.fetchCustomersAmount()
}

View File

@ -5,7 +5,7 @@ import { customerKey } from "@/feature/core/customer/customer-key";
import Customer from "@/feature/core/customer/domain/entity/customer";
import CustomerRepo, { customerRepoKey } from "@/feature/core/customer/domain/i-repo/customer-repo";
export default function fetchCustomersUsecase(query: string): Promise<Customer[]> {
export default async function fetchCustomersUsecase(query: string): Promise<Customer[]> {
const repo = serverDi(customerKey).resolve<CustomerRepo>(customerRepoKey)
return repo.fetchList(query)

View File

@ -3,7 +3,7 @@ import serverDi from "@/feature/common/server-di";
import InvoiceRepo, { invoiceRepoKey } from "@/feature/core/invoice/domain/i-repo/invoice-repo";
import { invoiceModuleKey } from "@/feature/core/invoice/invoice-module-key";
export default function fetchAllInvoicesAmountUsecase(): Promise<number> {
export default async function fetchAllInvoicesAmountUsecase(): Promise<number> {
const repo = serverDi(invoiceModuleKey).resolve<InvoiceRepo>(invoiceRepoKey)
return repo.fetchAllInvoicesAmount()

View File

@ -3,7 +3,7 @@ import InvoiceRepo, { invoiceRepoKey } from "@/feature/core/invoice/domain/i-rep
import InvoiceStatusSummary from "@/feature/core/invoice/domain/value-object/invoice-status";
import { invoiceModuleKey } from "@/feature/core/invoice/invoice-module-key";
export default function fetchInvoicesStatusSummary(): Promise<InvoiceStatusSummary> {
export default async function fetchInvoicesStatusSummary(): Promise<InvoiceStatusSummary> {
const repo = serverDi(invoiceModuleKey).resolve<InvoiceRepo>(invoiceRepoKey)
return repo.fetchInvoicesStatusSummary()
}

View File

@ -11,7 +11,6 @@ export type RevenueDbResponse = {
export default class RevenueDbRepo implements RevenueRepo {
async fetchRevenues(): Promise<Revenue[]> {
// This is equivalent to in fetch(..., {cache: 'no-store'}).
connection()
try {
// Artificially delay a response for demo purposes.
// Don't do this in production :)

View File

@ -1,9 +1,9 @@
import serverDi from "@/feature/common/server-di";
import Revenue from "@/feature/core/revenue/domain/entity/revenue";
import RevenueRepo from "@/feature/core/revenue/domain/i-repo/revenue-repo";
import RevenueRepo, { revenueRepoKey } from "@/feature/core/revenue/domain/i-repo/revenue-repo";
import { revenueModuleKey } from "@/feature/core/revenue/domain/revenue-module-key";
export default function fetchRevenuesUsecase(): Promise<Revenue[]> {
const repo = serverDi(revenueModuleKey).resolve<RevenueRepo>(revenueModuleKey)
export default async function fetchRevenuesUsecase(): Promise<Revenue[]> {
const repo = serverDi(revenueModuleKey).resolve<RevenueRepo>(revenueRepoKey)
return repo.fetchRevenues()
}

View File

@ -2,7 +2,6 @@ import di from "@/bootstrap/di/init-di"
import fetchCustomersAmountUsecase from "@/feature/core/customer/domain/usecase/fetch-customers-amount-usecase"
import fetchAllInvoicesAmountUsecase from "@/feature/core/invoice/domain/usecase/fetch-all-invoices-amount-usecase"
import fetchInvoicesStatusSummary from "@/feature/core/invoice/domain/usecase/fetch-invoices-status-summary"
import fetchSummaryInfoUsecase from "@/feature/core/summary-info/domain/usecase/fetch-summary-info-usecase"
export default function getSummaryInfoDi() {
const summaryInfoDi = di.createChildContainer()
@ -14,7 +13,7 @@ export default function getSummaryInfoDi() {
useValue: fetchCustomersAmountUsecase
})
summaryInfoDi.register(fetchInvoicesStatusSummary.name, {
useValue: fetchSummaryInfoUsecase
useValue: fetchInvoicesStatusSummary
})
return summaryInfoDi
}