### Example Render Function for Users Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/GENERICLIST_COMPONENT.md Provides an example of a `renderItem` function for displaying user data. It shows how to conditionally render content for mobile cards versus desktop table rows, and how to handle click events. ```jsx const renderUserItem = (user, index, isMobileCard, handleClick) => { if (isMobileCard) { // Mobile Card View - return full card content return (

{user.full_name}

{user.email}

); } // Desktop Table Row - return only td elements return ( <> {user.full_name} {user.email} ); }; ``` -------------------------------- ### Complete Example: Users Page Pattern with SearchFilterBar (React) Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/SEARCHFILTERBAR_COMPONENT.md This example demonstrates the complete implementation of the Users page using the SearchFilterBar component. It includes state management for search terms and roles, dynamic role filter options based on user roles, and navigation to a user creation page. Dependencies include React hooks and context providers. ```jsx import { useState, useContext } from "react"; import { useNavigate } from "react-router-dom"; import SearchFilterBar from "../../component/ui/SearchFilterBar"; import AuthContext from "../../context/AuthContext"; import { useLocale } from "../../contexts/LocaleContext"; function Users() { const [searchTerm, setSearchTerm] = useState(""); const [role, setRole] = useState(""); const navigate = useNavigate(); const { user } = useContext(AuthContext); const { t } = useLocale(); // Get available role options based on current user's role const getRoleFilterOptions = () => { const allRoles = [ { value: "", label: t('userFilter.all') }, { value: "User", label: t('userFilter.user') }, { value: "Seller", label: t('userFilter.seller') }, { value: "Admin", label: t('userFilter.admin') } ]; if (user?.role === 'admin') { return allRoles; } else if (user?.role === 'seller') { return [allRoles[0], allRoles[1]]; } return [allRoles[0]]; }; return (
navigate("/users/create"), className: "py-3 px-10 bg-success-300 text-white font-bold rounded-lg hover:bg-success-400 transition-all" } ]} /> {/* Rest of your page content */}
); } ``` -------------------------------- ### GenericList Usage Example (Projects) - React Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/GENERICLIST_COMPONENT.md Illustrates how to use the GenericList component for displaying a list of projects. This example defines a custom render function for project items and configures the component with an API endpoint, filters, selection handler, table columns, sorting, items per page, and entity name. ```jsx const renderProjectItem = (project, index, isMobileCard, handleClick) => { return ( handleClick(project)} isMobileCard={isMobileCard} /> ); }; ``` -------------------------------- ### Environment Configuration and API Setup (JavaScript) Source: https://context7.com/sjperalta/fintera-ui-react/llms.txt Sets up environment variables and API configuration for different deployment environments using Vite. It demonstrates how to define API URLs and application environments in .env files and how to import and use these variables in JavaScript components. Includes a helper function for retrieving authentication tokens from local storage. ```javascript // config.js export const API_URL = import.meta.env.VITE_API_URL; // .env file VITE_API_URL=http://localhost:3001/api/v1 VITE_APP_ENV=development // Production .env VITE_API_URL=https://api.fintera.com/api/v1 VITE_APP_ENV=production // Usage in components import { API_URL } from '../config'; const response = await fetch(`${API_URL}/api/v1/projects`); // Token retrieval helper (auth.js) export const getToken = () => { return localStorage.getItem('token'); }; ``` -------------------------------- ### Smart Pagination Logic Example Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/PAGINATION_IMPLEMENTATION.md Illustrates different display patterns for pagination controls based on the total number of pages and the current page. This logic aims to provide a user-friendly experience by showing relevant page numbers and using ellipsis for large page counts. ```javascript // Example pagination display patterns: // Total ≤ 5 pages: [1] [2] [3] [4] [5] // At start (page 2): [1] [2] [3] [4] ... [20] // In middle (page 10): [1] ... [9] [10] [11] ... [20] // At end (page 19): [1] ... [17] [18] [19] [20] ``` -------------------------------- ### Migration Example: UserFilter to SearchFilterBar (React) Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/SEARCHFILTERBAR_COMPONENT.md Illustrates the code changes required when migrating from the older `UserFilter` component to the new `SearchFilterBar` component. This highlights the updated prop names and the new `actions` prop for configuring buttons, demonstrating a more flexible and reusable approach. ```jsx ### Before ```jsx ``` ### After ```jsx navigate("/users/create") } ]} /> ``` ``` -------------------------------- ### Manage Payments using Payments API Source: https://context7.com/sjperalta/fintera-ui-react/llms.txt Provides examples for fetching payments with filtering, retrieving payment statistics, and performing actions like approving, registering extra payments, undoing transactions, and applying capital repayments. ```javascript // Fetch payments with filtering const response = await fetch( `${API_URL}/api/v1/payments?status=submitted&search_term=John&start_date=2024-01-01&end_date=2024-12-31&sort=updated_at-desc&page=1&per_page=20`, { headers: { "Content-Type": "application/json", Authorization: `Bearer ${token}`, }, } ); // Response: { payments: [...], pagination: {...} } // Get payment statistics const response = await fetch(`${API_URL}/api/v1/payments/stats`, { headers: { "Content-Type": "application/json", Authorization: `Bearer ${token}`, }, }); // Response: { pending_this_month, collected_this_month, total_overdue } // Approve a payment await fetch(`${API_URL}/api/v1/payments/${paymentId}/approve`, { method: "POST", headers: { "Content-Type": "application/json", Authorization: `Bearer ${token}`, }, body: JSON.stringify({ amount: 1000.00, interest: 50.00 }), }); // Register extra payment await fetch(`${API_URL}/api/v1/payments/${paymentId}/extra_payment`, { method: "POST", headers: { "Content-Type": "application/json", Authorization: `Bearer ${token}`, }, body: JSON.stringify({ amount: 300.00 }), }); // Undo a payment transaction await fetch(`${API_URL}/api/v1/payments/${paymentId}/undo`, { method: "POST", headers: { Authorization: `Bearer ${token}` }, }); // Apply capital repayment await fetch( `${API_URL}/api/v1/projects/${projectId}/lots/${lotId}/contracts/${contractId}/capital_repayment`, { method: "POST", headers: { "Content-Type": "application/json", Authorization: `Bearer ${token}`, }, body: JSON.stringify({ amount: 500.00 }), } ); ``` -------------------------------- ### SearchFilterBar with Action Buttons (React) Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/SEARCHFILTERBAR_COMPONENT.md Shows the integration of action buttons within the SearchFilterBar component. This example demonstrates how to define and pass an array of action objects, each with a label, click handler, and styling. ```jsx import SearchFilterBar from "../../component/ui/SearchFilterBar"; import { useNavigate } from "react-router-dom"; function MyPage() { const [searchTerm, setSearchTerm] = useState(""); const navigate = useNavigate(); return ( navigate("/users/create"), className: "py-3 px-10 bg-success-300 text-white font-bold rounded-lg hover:bg-success-400 transition-all" }, { label: "Export", onClick: () => handleExport(), className: "py-3 px-10 bg-blue-500 text-white font-bold rounded-lg hover:bg-blue-600 transition-all" } ] /> ); } ``` -------------------------------- ### Example Item Component Structure (React) Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/GENERICLIST_COMPONENT.md Demonstrates the structure of an item component that can render differently based on the `isMobileCard` prop, supporting both mobile card views and desktop table row views. This component is designed to be used with the GenericList component. ```jsx function UserData({ userInfo, index, token, onClick, isMobileCard = false }) { if (isMobileCard) { // Mobile Card View return (
{/* Full card content */}
); } // Desktop Table Row View return ( <> {/* Cell 1 */} {/* Cell 2 */} {/* Cell 3 */} ); } ``` -------------------------------- ### Payments API Source: https://context7.com/sjperalta/fintera-ui-react/llms.txt Tracks installment payments, extra payments, and capital repayments for contracts. ```APIDOC ## GET /api/v1/payments ### Description Fetches a list of payments with optional filtering and sorting. ### Method GET ### Endpoint /api/v1/payments ### Parameters #### Query Parameters - **status** (string) - Optional - Filter by payment status (e.g., 'submitted'). - **search_term** (string) - Optional - Search term for filtering payments. - **start_date** (string) - Optional - Filter by start date (YYYY-MM-DD). - **end_date** (string) - Optional - Filter by end date (YYYY-MM-DD). - **sort** (string) - Optional - Sorting order (e.g., 'updated_at-desc'). - **page** (integer) - Optional - Page number for pagination. - **per_page** (integer) - Optional - Number of items per page. ### Response #### Success Response (200) - **payments** (array) - An array of payment objects. - **pagination** (object) - Pagination details. #### Response Example ```json { "payments": [ { "id": "paymentId1", "contract_id": "contractId1", "amount": "1000.00", "status": "submitted", "payment_date": "2024-07-27" } ], "pagination": { "page": 1, "pages": 5, "count": 100 } } ``` ## GET /api/v1/payments/stats ### Description Retrieves statistics for payments. ### Method GET ### Endpoint /api/v1/payments/stats ### Response #### Success Response (200) - **pending_this_month** (integer) - Number of pending payments this month. - **collected_this_month** (integer) - Number of collected payments this month. - **total_overdue** (integer) - Total number of overdue payments. #### Response Example ```json { "pending_this_month": 15, "collected_this_month": 75, "total_overdue": 5 } ``` ## POST /api/v1/payments/{paymentId}/approve ### Description Approves a specific payment. ### Method POST ### Endpoint /api/v1/payments/{paymentId}/approve ### Parameters #### Path Parameters - **paymentId** (string) - Required - The ID of the payment to approve. #### Request Body - **amount** (number) - Required - The approved amount. - **interest** (number) - Required - The interest amount. ### Response #### Success Response (200) - **message** (string) - Success message. #### Response Example ```json { "message": "Payment approved successfully." } ``` ## POST /api/v1/payments/{paymentId}/extra_payment ### Description Registers an extra payment for a specific payment. ### Method POST ### Endpoint /api/v1/payments/{paymentId}/extra_payment ### Parameters #### Path Parameters - **paymentId** (string) - Required - The ID of the payment. #### Request Body - **amount** (number) - Required - The amount of the extra payment. ### Response #### Success Response (200) - **message** (string) - Success message. #### Response Example ```json { "message": "Extra payment registered successfully." } ``` ## POST /api/v1/payments/{paymentId}/undo ### Description Undoes a payment transaction. ### Method POST ### Endpoint /api/v1/payments/{paymentId}/undo ### Parameters #### Path Parameters - **paymentId** (string) - Required - The ID of the payment to undo. ### Response #### Success Response (200) - **message** (string) - Success message. #### Response Example ```json { "message": "Payment transaction undone successfully." } ``` ## POST /api/v1/projects/{projectId}/lots/{lotId}/contracts/{contractId}/capital_repayment ### Description Applies a capital repayment to a contract. ### Method POST ### Endpoint /api/v1/projects/{projectId}/lots/{lotId}/contracts/{contractId}/capital_repayment ### Parameters #### Path Parameters - **projectId** (string) - Required - The ID of the project. - **lotId** (string) - Required - The ID of the lot. - **contractId** (string) - Required - The ID of the contract. #### Request Body - **amount** (number) - Required - The amount to apply as capital repayment. ### Response #### Success Response (200) - **message** (string) - Success message. #### Response Example ```json { "message": "Capital repayment applied successfully." } ``` ``` -------------------------------- ### GenericList Basic Usage (Users Page) - React Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/GENERICLIST_COMPONENT.md Demonstrates the basic usage of the GenericList component to display a list of users. It configures the endpoint, item rendering function, filters, selection handler, table columns, sorting, items per page, custom messages, and entity name. This example utilizes React hooks and custom components like UserData. ```jsx import GenericList from "../../component/ui/GenericList"; import UserData from "../../component/user/UserData"; import { getToken } from "../../../auth"; function Users() { const [searchTerm, setSearchTerm] = useState(""); const [role, setRole] = useState(""); const [selectedUser, setSelectedUser] = useState(null); const { t } = useLocale(); const token = getToken(); // Define table columns const columns = [ { label: t('users.user'), align: "left" }, { label: t('common.status'), align: "center" }, { label: t('common.actions'), align: "left" } ]; // Define render function const renderUserItem = (user, index, isMobileCard, handleClick) => { return ( handleClick(user)} isMobileCard={isMobileCard} /> ); }; return ( ); } ``` -------------------------------- ### GET Contract(s) API Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/BANK_RESERVATION_MAX_PAYMENT_DATE.md Retrieves contract details. Returns the 'max_payment_date' if it exists on the contract. ```APIDOC ## GET Contract(s) API ### Description Retrieves one or more contract details. If the contract uses 'bank' or 'cash' financing, the 'max_payment_date' will be included in the response. ### Method GET ### Endpoint `/api/v1/projects/:project_id/lots/:lot_id/contracts/:id` or `/api/v1/projects/:project_id/lots/:lot_id/contracts` ### Parameters #### Path Parameters - **project_id** (string) - Required - The ID of the project. - **lot_id** (string) - Required - The ID of the lot. - **id** (string) - Required (for single contract retrieval) - The ID of the contract. #### Query Parameters None ### Response #### Success Response (200 OK) - **max_payment_date** (string) - The maximum payment date in ISO format or 'YYYY-MM-DD', if present on the contract. #### Response Example ```json { "id": "contract_abc123", "financing_type": "bank", "max_payment_date": "2026-06-30T00:00:00.000Z" } ``` ``` -------------------------------- ### Create and Fetch Contracts using Contracts API Source: https://context7.com/sjperalta/fintera-ui-react/llms.txt Demonstrates how to create a new contract reservation with associated user information and documents. It also shows how to fetch a list of contracts with various filtering and sorting options, and retrieve contract statistics. ```javascript // Create a new contract/reservation const handleSubmit = async () => { const formData = new FormData(); formData.append("contract[payment_term]", 12); // months formData.append("contract[financing_type]", "direct"); // direct|bank|cash formData.append("contract[reserve_amount]", "5000.00"); formData.append("contract[down_payment]", "10000.00"); formData.append("contract[max_payment_date]", "2025-06-30"); // for bank/cash formData.append("contract[note]", "Client notes here"); formData.append("contract[applicant_user_id]", userId); // User info (creates new user if applicant_user_id is empty) formData.append("user[full_name]", "John Doe"); formData.append("user[phone]", "+504 9999-9999"); formData.append("user[identity]", "0801-1990-12345"); formData.append("user[email]", "john@example.com"); // Attach documents documents.forEach((doc, index) => { formData.append(`documents[${index}]`, doc); }); const response = await fetch( `${API_URL}/api/v1/projects/${projectId}/lots/${lotId}/contracts`, { method: "POST", headers: { Authorization: `Bearer ${token}` }, body: formData, } ); }; // Fetch contracts list with filtering const response = await fetch( `${API_URL}/api/v1/contracts?status=approved&search_term=John&start_date=2024-01-01&end_date=2024-12-31&sort=contracts.created_at-desc&page=1&per_page=12`, { headers: { "Content-Type": "application/json", Authorization: `Bearer ${token}`, }, } ); // Response: { contracts: [...], pagination: {...} } // Get contract statistics const response = await fetch(`${API_URL}/api/v1/contracts/stats`, { headers: { Authorization: `Bearer ${token}` }, }); // Response: { total, pending, approved, rejected } ``` -------------------------------- ### GET /api/v1/users/:user_id/payment_history Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/PAGINATION_IMPLEMENTATION.md Retrieves a paginated list of user payment history. Supports filtering by search term, status, payment type, and date range. ```APIDOC ## GET /api/v1/users/:user_id/payment_history ### Description Retrieves a paginated list of user payment history. Supports filtering by search term, status, payment type, and date range. ### Method GET ### Endpoint `/api/v1/users/:user_id/payment_history` ### Parameters #### Path Parameters - **user_id** (string) - Required - The ID of the user whose payment history is being requested. #### Query Parameters - **page** (number) - Required - The current page number for pagination. - **per_page** (number) - Required - The number of items to display per page. - **search_term** (string) - Optional - A search term to filter payment history. - **status** (string) - Optional - Filters payments by status (e.g., 'paid', 'pending', 'submitted', 'rejected'). - **payment_type** (string) - Optional - Filters payments by type (e.g., 'reserve', 'down_payment', 'installment', 'capital_repayment'). - **date_range** (string) - Optional - Filters payments by date range (e.g., 'all', 'month', 'quarter', 'year'). ### Request Example ``` GET /api/v1/users/123/payment_history?page=2&per_page=10&status=paid&date_range=month ``` ### Response #### Success Response (200) - **payments** (array) - An array of payment objects. - **total** (number) - The total amount of payments. - **balance** (number) - The current balance. - **overdue_amount** (number) - The amount that is overdue. - **payment_count** (number) - The total count of payments. - **count_paid_done** (number) - The count of payments marked as 'paid'. - **meta** (object) - Metadata for pagination. - **current_page** (number) - The current page number. - **total_pages** (number) - The total number of pages available. - **per_page** (number) - The number of items per page. - **total_count** (number) - The total number of items across all pages. #### Response Example ```json { "payments": [ { "id": "pay_1", "amount": 100.00, "status": "paid", "date": "2023-10-26" } ], "total": 150000.00, "balance": 50000.00, "overdue_amount": 10000.00, "payment_count": 45, "count_paid_done": 30, "meta": { "current_page": 2, "total_pages": 5, "per_page": 10, "total_count": 45 } } ``` ``` -------------------------------- ### Projects Page SearchFilterBar Usage (JSX) Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/SEARCHFILTERBAR_REFACTORING.md An example of using the SearchFilterBar component on a Projects page. It shows how to configure search, filter options, placeholders, and action buttons specific to project management. ```jsx navigate("/projects/create") } ]} /> ``` -------------------------------- ### Manage Users with Users API Source: https://context7.com/sjperalta/fintera-ui-react/llms.txt Illustrates how to search for users with various filters such as search term, role, and status. It also includes the structure of a user object and how to filter for a seller's own clients. ```javascript // Search users const response = await fetch( `${API_URL}/api/v1/users?search_term=John&role=user&status=active&page=1&per_page=12`, { method: "GET", headers: { Authorization: `Bearer ${token}`, "Content-Type": "application/json", }, } ); // Response: { users: [...], pagination: { page, pages, count } } // User object structure: // { // id, full_name, email, phone, identity, rtn, role, // status, credit_score, must_change_password, locale // } // Roles: "admin", "seller", "user" // Statuses: "active", "inactive" // Filter for seller's own clients const response = await fetch( `${API_URL}/api/v1/users?my_clients=1&role=user`, { headers: { Authorization: `Bearer ${token}` } } ); ``` -------------------------------- ### Contracts Page SearchFilterBar Usage (JSX) Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/SEARCHFILTERBAR_REFACTORING.md Demonstrates the implementation of the SearchFilterBar component on a Contracts page. This example highlights custom filter options and multiple action buttons for contract management tasks. ```jsx navigate("/contracts/create") }, { label: "Export", onClick: handleExport } ]} /> ``` -------------------------------- ### Basic SearchFilterBar Usage (React) Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/SEARCHFILTERBAR_COMPONENT.md Demonstrates the basic implementation of the SearchFilterBar component with only search functionality. It shows how to manage the search term state and handle changes, with the filter dropdown hidden. ```jsx import SearchFilterBar from "../../component/ui/SearchFilterBar"; function MyPage() { const [searchTerm, setSearchTerm] = useState(""); return ( ); } ``` -------------------------------- ### Projects API Integration (JavaScript) Source: https://context7.com/sjperalta/fintera-ui-react/llms.txt Manages real estate projects, supporting CRUD operations, filtering, sorting, pagination, and CSV imports. It requires an authorization token for requests and interacts with the `/api/v1/projects` endpoint. Responses include project data and pagination details. ```javascript // Fetch projects with pagination and filtering const fetchProjects = async () => { const url = new URL(`${API_URL}/api/v1/projects`); url.searchParams.set("search_term", "Park View"); url.searchParams.set("sort", "name-asc"); url.searchParams.set("page", 1); url.searchParams.set("per_page", 20); const response = await fetch(url.toString(), { method: "GET", headers: { "Content-Type": "application/json", Authorization: `Bearer ${token}`, }, }); const data = await response.json(); // Response: { projects: [...], pagination: { page, pages, count } } }; // Import projects from CSV const handleImportCSV = async (file) => { const formData = new FormData(); formData.append("file", file); formData.append("options[update_existing]", "1"); formData.append("options[skip_duplicates]", "0"); const response = await fetch(`${API_URL}/api/v1/projects/import`, { method: "POST", headers: { Authorization: `Bearer ${token}` }, body: formData, }); // Returns success/error status }; // Fetch single project details const response = await fetch(`${API_URL}/api/v1/projects/${projectId}`, { headers: { "Content-Type": "application/json", Authorization: `Bearer ${token}`, }, }); // Response: { project: { id, name, address, interest_rate, delivery_date, commission_rate_direct, ... } } ``` -------------------------------- ### Lots API Integration (JavaScript) Source: https://context7.com/sjperalta/fintera-ui-react/llms.txt Manages individual lots within a project, providing details on pricing, dimensions, and status. It requires a project ID and an authorization token. The API supports fetching lists of lots with pagination and sorting, as well as retrieving details for a specific lot. ```javascript // Fetch lots for a project const response = await fetch( `${API_URL}/api/v1/projects/${projectId}/lots?page=1&per_page=20&sort=name-asc`, { headers: { "Content-Type": "application/json", Authorization: `Bearer ${token}`, }, } ); // Response: { lots: [...], pagination: {...}, total: number } // Fetch single lot details const response = await fetch( `${API_URL}/api/v1/projects/${projectId}/lots/${lotId}`, { headers: { "Content-Type": "application/json", Authorization: `Bearer ${token}`, }, } ); // Response: { // lot: { // id, name, price, effective_price, length, width, area, // measurement_unit, status, address // } // } // Lot statuses: "available", "reserved", "sold" ``` -------------------------------- ### Defining Columns for GenericList Table View (React) Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/GENERICLIST_COMPONENT.md Provides an example of how to define the `columns` array, a prop for `GenericList` when used in a table view. Each object in the array specifies the `label` and `align` properties for a table column, contributing to the structured display of data. ```jsx const columns = [ { label: t('users.user'), align: "left" }, { label: t('common.status'), align: "center" }, { label: t('common.actions'), align: "left" } ]; ``` -------------------------------- ### Translation Keys for Pagination UI (Spanish) Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/PAGINATION_IMPLEMENTATION.md Provides Spanish translations for common pagination UI elements, including 'First Page', 'Last Page', and 'Items per page'. This ensures multi-language support for the pagination features. ```json { "common": { "firstPage": "Primera Página", "lastPage": "Última Página", "itemsPerPage": "Elementos por página" } } ``` -------------------------------- ### Projects API Source: https://context7.com/sjperalta/fintera-ui-react/llms.txt Manages real estate projects, supporting CRUD operations, filtering, sorting, and CSV import. ```APIDOC ## GET /api/v1/projects ### Description Retrieves a list of projects with support for pagination, filtering, and sorting. ### Method GET ### Endpoint /api/v1/projects ### Parameters #### Query Parameters - **search_term** (string) - Optional - Term to search for in project names or addresses - **sort** (string) - Optional - Sorting order (e.g., `name-asc`, `delivery_date-desc`) - **page** (integer) - Optional - Page number for pagination (defaults to 1) - **per_page** (integer) - Optional - Number of items per page (defaults to 20) ### Response #### Success Response (200) - **projects** (array) - Array of project objects - **pagination** (object) - Pagination details (`page`, `pages`, `count`) #### Response Example ```json { "projects": [ { "id": "proj-1", "name": "Park View", "address": "123 Main St", "interest_rate": 5.5, "delivery_date": "2024-12-31", "commission_rate_direct": 3.0 } ], "pagination": { "page": 1, "pages": 10, "count": 200 } } ``` ## POST /api/v1/projects/import ### Description Imports projects from a CSV file. Supports options for updating existing projects and skipping duplicates. ### Method POST ### Endpoint /api/v1/projects/import ### Parameters #### Request Body - **file** (file) - Required - The CSV file containing project data - **options[update_existing]** (integer) - Optional - Set to `1` to update existing projects, `0` otherwise - **options[skip_duplicates]** (integer) - Optional - Set to `1` to skip duplicate entries, `0` otherwise ### Request Example ``` // Using FormData in JavaScript const formData = new FormData(); formData.append("file", file); formData.append("options[update_existing]", "1"); formData.append("options[skip_duplicates]", "0"); ``` ### Response #### Success Response (200) - Status indicating success or failure of the import operation. #### Response Example ```json { "status": "success", "message": "Projects imported successfully." } ``` ## GET /api/v1/projects/{projectId} ### Description Retrieves detailed information for a specific project. ### Method GET ### Endpoint /api/v1/projects/{projectId} ### Parameters #### Path Parameters - **projectId** (string) - Required - The ID of the project to retrieve ### Response #### Success Response (200) - **project** (object) - Detailed project object #### Response Example ```json { "project": { "id": "proj-1", "name": "Park View", "address": "123 Main St", "interest_rate": 5.5, "delivery_date": "2024-12-31", "commission_rate_direct": 3.0 } } ``` ``` -------------------------------- ### Migrating from Old List Components to GenericList (React) Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/GENERICLIST_COMPONENT.md Illustrates the transformation required when migrating from older, specific list components (like `UsersList`) to the more generic `GenericList` component. This includes updating the component usage and defining necessary props like `endpoint`, `renderItem`, and `columns`. ```jsx /* Before (UsersList.jsx) */ /* After (GenericList) */ ``` -------------------------------- ### Render Contract List with GenericList Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/GENERICLIST_COMPONENT.md Demonstrates how to use the GenericList component to fetch and display a list of contracts. It configures the endpoint, item rendering function, filters, selection handler, column definitions, sorting, pagination, and messages for empty or loading states. ```jsx const renderContractItem = (contract, index, isMobileCard, handleClick) => { return ( handleClick(contract)} isMobileCard={isMobileCard} /> ); }; ``` -------------------------------- ### Translation Keys for Pagination UI (English) Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/PAGINATION_IMPLEMENTATION.md Defines English text for common pagination elements such as 'First Page', 'Last Page', and 'Items per page'. These keys are used within the application's localization system. ```json { "common": { "firstPage": "First Page", "lastPage": "Last Page", "itemsPerPage": "Items per page" } } ``` -------------------------------- ### Lots API Source: https://context7.com/sjperalta/fintera-ui-react/llms.txt Manages individual lots within a project, including pricing, dimensions, status, and availability. ```APIDOC ## GET /api/v1/projects/{projectId}/lots ### Description Retrieves a list of lots for a specific project, with pagination and sorting options. ### Method GET ### Endpoint /api/v1/projects/{projectId}/lots ### Parameters #### Path Parameters - **projectId** (string) - Required - The ID of the project containing the lots #### Query Parameters - **page** (integer) - Optional - Page number for pagination (defaults to 1) - **per_page** (integer) - Optional - Number of items per page (defaults to 20) - **sort** (string) - Optional - Sorting order (e.g., `name-asc`) ### Response #### Success Response (200) - **lots** (array) - Array of lot objects - **pagination** (object) - Pagination details (`page`, `pages`, `count`) - **total** (integer) - Total number of lots #### Response Example ```json { "lots": [ { "id": "lot-101", "name": "Lot A1", "price": 150000, "effective_price": 145000, "length": 30, "width": 15, "area": 450, "measurement_unit": "sqm", "status": "available", "address": "123 Main St, Lot A1" } ], "pagination": { "page": 1, "pages": 5, "count": 100 }, "total": 100 } ``` ## GET /api/v1/projects/{projectId}/lots/{lotId} ### Description Retrieves detailed information for a specific lot within a project. ### Method GET ### Endpoint /api/v1/projects/{projectId}/lots/{lotId} ### Parameters #### Path Parameters - **projectId** (string) - Required - The ID of the project containing the lot - **lotId** (string) - Required - The ID of the lot to retrieve ### Response #### Success Response (200) - **lot** (object) - Detailed lot object #### Response Example ```json { "lot": { "id": "lot-101", "name": "Lot A1", "price": 150000, "effective_price": 145000, "length": 30, "width": 15, "area": 450, "measurement_unit": "sqm", "status": "available", "address": "123 Main St, Lot A1" } } ``` ### Lot Statuses - `available` - `reserved` - `sold` ``` -------------------------------- ### Rollback to Old UsersList Component (JSX) Source: https://github.com/sjperalta/fintera-ui-react/blob/main/documentation/GENERICLIST_IMPLEMENTATION.md This code demonstrates how to quickly revert to the previous UsersList component if issues arise with the new GenericList integration. It involves importing the UsersList component and replacing the GenericList instance with it, passing the necessary props for search and role filtering. ```jsx // In src/pages/users/index.jsx import UsersList from "../../component/user/UsersList"; // Replace GenericList with UsersList ``` -------------------------------- ### Localization System with LocaleContext (React JSX) Source: https://context7.com/sjperalta/fintera-ui-react/llms.txt This system enables internationalization (i18n) within the React application using `LocaleContext`. It supports multiple languages (English and Spanish demonstrated), handles automatic parameter replacement in translations, and persists the selected locale using localStorage. The `LocaleProvider` should wrap the application, and the `useLocale` hook provides access to translation functions and locale management. ```jsx import { useLocale, LocaleProvider } from "./contexts/LocaleContext"; // Wrap app with provider function App() { return ( ); } // Use translations in components function MyComponent() { const { t, locale, setLocale, getSupportedLocales } = useLocale(); return (
{/* Simple translation */}

{t('header.pageTitle.dashboard')}

{/* Translation with parameters */}

{t('payments.noPaymentsFound', { searchTerm: 'John', status: 'pending' })}

{/* Change locale */} {/* Current locale */} Current: {locale}
); } // Translation file structure (src/locales/en.json): // { // "header": { // "pageTitle": { "dashboard": "Dashboard", "contracts": "Contracts" } // }, // "payments": { // "noPaymentsFound": "No payments found for {searchTerm} with status {status}" // } // } ``` -------------------------------- ### Authentication API Integration (JavaScript) Source: https://context7.com/sjperalta/fintera-ui-react/llms.txt Handles user login, token storage, and automatic token refresh using JWT. It relies on the API_URL configuration and interacts with localStorage for token persistence. The AuthContext provides hooks for accessing user data and authentication functions. ```javascript import { API_URL } from '../../config'; // Login request const login = async (email, password) => { const response = await fetch(`${API_URL}/api/v1/auth/login`, { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ email, password }) }); const data = await response.json(); if (response.ok && data.token && data.user) { // Store tokens localStorage.setItem('token', data.token); localStorage.setItem('user', JSON.stringify(data.user)); localStorage.setItem('refresh_token', data.refresh_token); return { success: true, user: data.user }; } return { success: false, error: data.errors || 'Login failed' }; }; // Token refresh const refresh = async (storedRefreshToken) => { const response = await fetch(`${API_URL}/api/v1/auth/refresh`, { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ refresh_token: storedRefreshToken }) }); const data = await response.json(); // Returns { token, user, refresh_token } }; // Usage in components import AuthContext from './contexts/AuthContext'; const { user, token, login, logout } = useContext(AuthContext); ```