@spaceinvoices/react-ui 0.1.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -0
- package/README.md +340 -0
- package/cli/dist/index.js +922 -0
- package/package.json +87 -0
- package/registry.json +600 -0
- package/spaceinvoices.schema.json +47 -0
- package/src/app.tsx +25 -0
- package/src/common/autocomplete.tsx +135 -0
- package/src/components/activities/activity-timeline.tsx +160 -0
- package/src/components/activities/index.ts +1 -0
- package/src/components/activities/locales/de.ts +30 -0
- package/src/components/activities/locales/sl.ts +30 -0
- package/src/components/advance-invoices/advance-invoices.hooks.ts +75 -0
- package/src/components/advance-invoices/create/create-advance-invoice-form.tsx +702 -0
- package/src/components/advance-invoices/create/locales/de.ts +29 -0
- package/src/components/advance-invoices/create/locales/sl.ts +25 -0
- package/src/components/advance-invoices/create/prepare-advance-invoice-submission.ts +74 -0
- package/src/components/advance-invoices/index.ts +5 -0
- package/src/components/advance-invoices/list/index.ts +3 -0
- package/src/components/advance-invoices/list/list-row-actions.tsx +119 -0
- package/src/components/advance-invoices/list/list-table.tsx +178 -0
- package/src/components/advance-invoices/list/locales/de.ts +32 -0
- package/src/components/advance-invoices/list/locales/sl.ts +32 -0
- package/src/components/advance-invoices/list/use-advance-invoice-download.ts +63 -0
- package/src/components/button-loader.tsx +11 -0
- package/src/components/combobox.tsx +96 -0
- package/src/components/company-registry/company-registry-autocomplete.tsx +151 -0
- package/src/components/company-registry/company-registry.hooks.ts +67 -0
- package/src/components/company-registry/index.ts +7 -0
- package/src/components/credit-notes/create/create-credit-note-form.tsx +332 -0
- package/src/components/credit-notes/create/index.ts +1 -0
- package/src/components/credit-notes/create/locales/de.ts +69 -0
- package/src/components/credit-notes/create/locales/sl.ts +67 -0
- package/src/components/credit-notes/credit-notes.hooks.ts +22 -0
- package/src/components/credit-notes/index.ts +10 -0
- package/src/components/credit-notes/list/index.ts +3 -0
- package/src/components/credit-notes/list/list-row-actions.tsx +116 -0
- package/src/components/credit-notes/list/list-table.tsx +183 -0
- package/src/components/credit-notes/list/locales/de.ts +33 -0
- package/src/components/credit-notes/list/locales/sl.ts +33 -0
- package/src/components/credit-notes/list/use-credit-note-download.ts +65 -0
- package/src/components/customers/create-customer-form/create-customer-form.tsx +134 -0
- package/src/components/customers/create-customer-form/locales/de.ts +20 -0
- package/src/components/customers/create-customer-form/locales/sl.ts +20 -0
- package/src/components/customers/customer-autocomplete.tsx +173 -0
- package/src/components/customers/customer-combobox.tsx +130 -0
- package/src/components/customers/customer-list-table/customer-list-row-actions.tsx +48 -0
- package/src/components/customers/customer-list-table/customer-list-table.tsx +124 -0
- package/src/components/customers/customer-list-table/index.ts +2 -0
- package/src/components/customers/customer-list-table/locales/de.ts +16 -0
- package/src/components/customers/customer-list-table/locales/sl.ts +16 -0
- package/src/components/customers/customers.hooks.test.ts +348 -0
- package/src/components/customers/customers.hooks.ts +57 -0
- package/src/components/customers/index.ts +5 -0
- package/src/components/dashboard/chart-empty-state.tsx +29 -0
- package/src/components/dashboard/collection-rate-card/collection-rate-card.tsx +80 -0
- package/src/components/dashboard/collection-rate-card/index.ts +4 -0
- package/src/components/dashboard/collection-rate-card/locales/sl.ts +3 -0
- package/src/components/dashboard/collection-rate-card/use-collection-rate.ts +74 -0
- package/src/components/dashboard/index.ts +54 -0
- package/src/components/dashboard/invoice-status-chart/index.ts +4 -0
- package/src/components/dashboard/invoice-status-chart/invoice-status-chart.tsx +130 -0
- package/src/components/dashboard/invoice-status-chart/locales/sl.ts +9 -0
- package/src/components/dashboard/invoice-status-chart/use-invoice-status.ts +105 -0
- package/src/components/dashboard/loading-card.tsx +19 -0
- package/src/components/dashboard/payment-methods-chart/index.ts +4 -0
- package/src/components/dashboard/payment-methods-chart/locales/sl.ts +12 -0
- package/src/components/dashboard/payment-methods-chart/payment-methods-chart.tsx +152 -0
- package/src/components/dashboard/payment-methods-chart/use-payment-methods.ts +50 -0
- package/src/components/dashboard/payment-trend-chart/index.ts +4 -0
- package/src/components/dashboard/payment-trend-chart/locales/sl.ts +5 -0
- package/src/components/dashboard/payment-trend-chart/payment-trend-chart.tsx +137 -0
- package/src/components/dashboard/payment-trend-chart/use-payment-trend.ts +92 -0
- package/src/components/dashboard/revenue-card.tsx +49 -0
- package/src/components/dashboard/revenue-trend-chart/index.ts +4 -0
- package/src/components/dashboard/revenue-trend-chart/locales/sl.ts +5 -0
- package/src/components/dashboard/revenue-trend-chart/revenue-trend-chart.tsx +137 -0
- package/src/components/dashboard/revenue-trend-chart/use-revenue-trend.ts +93 -0
- package/src/components/dashboard/shared/index.ts +5 -0
- package/src/components/dashboard/shared/use-revenue-data.ts +160 -0
- package/src/components/dashboard/shared/use-stats-counts.ts +89 -0
- package/src/components/dashboard/shared/use-stats-query.ts +38 -0
- package/src/components/dashboard/stat-card.tsx +41 -0
- package/src/components/dashboard/tax-collected-card/index.ts +2 -0
- package/src/components/dashboard/tax-collected-card/tax-collected-card.tsx +77 -0
- package/src/components/dashboard/tax-collected-card/use-tax-collected.ts +145 -0
- package/src/components/dashboard/top-customers-chart/index.ts +4 -0
- package/src/components/dashboard/top-customers-chart/locales/sl.ts +5 -0
- package/src/components/dashboard/top-customers-chart/top-customers-chart.tsx +130 -0
- package/src/components/dashboard/top-customers-chart/use-top-customers.ts +72 -0
- package/src/components/documents/create/document-add-item-form.tsx +379 -0
- package/src/components/documents/create/document-add-item-tax-rate-field.tsx +120 -0
- package/src/components/documents/create/document-details-section.tsx +597 -0
- package/src/components/documents/create/document-items-section.tsx +133 -0
- package/src/components/documents/create/document-recipient-section.tsx +101 -0
- package/src/components/documents/create/form-types.ts +36 -0
- package/src/components/documents/create/index.ts +9 -0
- package/src/components/documents/create/live-preview.tsx +235 -0
- package/src/components/documents/create/mark-as-paid-section.tsx +82 -0
- package/src/components/documents/create/prepare-document-submission.test.ts +132 -0
- package/src/components/documents/create/prepare-document-submission.ts +187 -0
- package/src/components/documents/create/prepare-preview-data.test.ts +155 -0
- package/src/components/documents/create/prepare-preview-data.ts +16 -0
- package/src/components/documents/create/smart-code-insert-button.tsx +139 -0
- package/src/components/documents/create/use-document-customer-form.ts +161 -0
- package/src/components/documents/document-preview.tsx +13 -0
- package/src/components/documents/documents.hooks.ts +146 -0
- package/src/components/documents/index.ts +23 -0
- package/src/components/documents/shared/document-preview-display.tsx +172 -0
- package/src/components/documents/shared/index.ts +3 -0
- package/src/components/documents/shared/scaled-document-preview.tsx +70 -0
- package/src/components/documents/shared/use-a4-scaling.ts +62 -0
- package/src/components/documents/types.ts +61 -0
- package/src/components/documents/view/document-actions-bar.tsx +328 -0
- package/src/components/documents/view/document-details-card.tsx +179 -0
- package/src/components/documents/view/document-payments-list.tsx +256 -0
- package/src/components/documents/view/index.ts +4 -0
- package/src/components/documents/view/locales/de.ts +85 -0
- package/src/components/documents/view/locales/sl.ts +84 -0
- package/src/components/documents/view/use-document-download.ts +125 -0
- package/src/components/entities/create-entity-form.tsx +105 -0
- package/src/components/entities/entities.hooks.ts +50 -0
- package/src/components/entities/entity-settings-form/email-template-variables-info.tsx +103 -0
- package/src/components/entities/entity-settings-form/entity-settings-form.tsx +1326 -0
- package/src/components/entities/entity-settings-form/image-upload-with-crop.tsx +222 -0
- package/src/components/entities/entity-settings-form/index.ts +2 -0
- package/src/components/entities/entity-settings-form/input-with-preview.tsx +190 -0
- package/src/components/entities/entity-settings-form/locales/de.ts +192 -0
- package/src/components/entities/entity-settings-form/locales/sl.ts +188 -0
- package/src/components/entities/furs-settings-form/furs-settings-form.tsx +410 -0
- package/src/components/entities/furs-settings-form/furs-settings.hooks.ts +320 -0
- package/src/components/entities/furs-settings-form/index.ts +3 -0
- package/src/components/entities/furs-settings-form/locales/de.ts +233 -0
- package/src/components/entities/furs-settings-form/locales/en.ts +194 -0
- package/src/components/entities/furs-settings-form/locales/sl.ts +196 -0
- package/src/components/entities/furs-settings-form/sections/certificate-settings-section.tsx +242 -0
- package/src/components/entities/furs-settings-form/sections/enable-fiscalization-section.tsx +139 -0
- package/src/components/entities/furs-settings-form/sections/general-settings-section.tsx +252 -0
- package/src/components/entities/furs-settings-form/sections/premises-management-section.tsx +370 -0
- package/src/components/entities/furs-settings-form/sections/register-premise-dialog.tsx +420 -0
- package/src/components/entities/keys.ts +2 -0
- package/src/components/entities/settings/branding-settings-form.tsx +274 -0
- package/src/components/entities/settings/company-settings-form.tsx +256 -0
- package/src/components/entities/settings/defaults-settings-form.tsx +501 -0
- package/src/components/entities/settings/email-settings-form.tsx +288 -0
- package/src/components/entities/settings/eslog-settings-form.tsx +113 -0
- package/src/components/entities/settings/index.ts +8 -0
- package/src/components/entities/settings/number-format-settings-form.tsx +244 -0
- package/src/components/entities/settings/pdf-template-selector/demo-invoice-data.ts +164 -0
- package/src/components/entities/settings/pdf-template-selector/index.ts +2 -0
- package/src/components/entities/settings/pdf-template-selector/locales/de.ts +18 -0
- package/src/components/entities/settings/pdf-template-selector/locales/sl.ts +18 -0
- package/src/components/entities/settings/pdf-template-selector/pdf-template-cards.tsx +49 -0
- package/src/components/entities/settings/settings-footer.tsx +16 -0
- package/src/components/entities/settings/tax-rules-settings-form.tsx +346 -0
- package/src/components/estimates/create/create-estimate-form.tsx +384 -0
- package/src/components/estimates/create/locales/de.ts +64 -0
- package/src/components/estimates/create/locales/sl.ts +63 -0
- package/src/components/estimates/create/prepare-estimate-submission.ts +39 -0
- package/src/components/estimates/create/use-estimate-customer-form.ts +5 -0
- package/src/components/estimates/estimates.hooks.ts +15 -0
- package/src/components/estimates/index.ts +6 -0
- package/src/components/estimates/list/index.ts +3 -0
- package/src/components/estimates/list/list-row-actions.tsx +103 -0
- package/src/components/estimates/list/list-table.tsx +171 -0
- package/src/components/estimates/list/locales/de.ts +26 -0
- package/src/components/estimates/list/locales/sl.ts +26 -0
- package/src/components/estimates/list/use-estimate-download.ts +63 -0
- package/src/components/export/document-export-form.tsx +288 -0
- package/src/components/export/index.ts +2 -0
- package/src/components/form/form-input.tsx +89 -0
- package/src/components/form/index.ts +1 -0
- package/src/components/invoices/create/create-invoice-form.tsx +852 -0
- package/src/components/invoices/create/eslog-validation.test.ts +242 -0
- package/src/components/invoices/create/eslog-validation.ts +208 -0
- package/src/components/invoices/create/locales/de.ts +118 -0
- package/src/components/invoices/create/locales/sl.ts +114 -0
- package/src/components/invoices/create/prepare-invoice-submission.test.ts +777 -0
- package/src/components/invoices/create/prepare-invoice-submission.ts +79 -0
- package/src/components/invoices/create/use-invoice-customer-form.ts +5 -0
- package/src/components/invoices/index.ts +9 -0
- package/src/components/invoices/invoices-furs.hooks.ts +28 -0
- package/src/components/invoices/invoices.hooks.ts +110 -0
- package/src/components/invoices/list/index.ts +3 -0
- package/src/components/invoices/list/list-row-actions.tsx +132 -0
- package/src/components/invoices/list/list-table.tsx +165 -0
- package/src/components/invoices/list/locales/de.ts +33 -0
- package/src/components/invoices/list/locales/sl.ts +33 -0
- package/src/components/invoices/list/use-invoice-download.ts +62 -0
- package/src/components/invoices/send-email-dialog/index.ts +1 -0
- package/src/components/invoices/send-email-dialog/locales/de.ts +18 -0
- package/src/components/invoices/send-email-dialog/locales/sl.ts +17 -0
- package/src/components/invoices/send-email-dialog/send-email-dialog.tsx +289 -0
- package/src/components/invoices/send-email-dialog.tsx +2 -0
- package/src/components/invoices/shared/index.ts +2 -0
- package/src/components/invoices/shared/scaled-document-preview.tsx +32 -0
- package/src/components/invoices/shared/use-a4-scaling.tsx +39 -0
- package/src/components/invoices/view/eslog-info-display.tsx +160 -0
- package/src/components/invoices/view/furs-info-display.tsx +213 -0
- package/src/components/items/create-item-form/create-item-form.tsx +155 -0
- package/src/components/items/create-item-form/locales/de.ts +14 -0
- package/src/components/items/create-item-form/locales/en.ts +9 -0
- package/src/components/items/create-item-form/locales/sl.ts +14 -0
- package/src/components/items/item-combobox.tsx +147 -0
- package/src/components/items/item-list-table/item-list-header.tsx +33 -0
- package/src/components/items/item-list-table/item-list-row-actions.tsx +48 -0
- package/src/components/items/item-list-table/item-list-row.tsx +32 -0
- package/src/components/items/item-list-table/item-list-table.tsx +76 -0
- package/src/components/items/item-list-table/locales/de.ts +10 -0
- package/src/components/items/item-list-table/locales/en.ts +10 -0
- package/src/components/items/item-list-table/locales/sl.ts +10 -0
- package/src/components/items/items.hooks.ts +63 -0
- package/src/components/loading-spinner.tsx +24 -0
- package/src/components/payments/create-payment-form/create-payment-form.tsx +222 -0
- package/src/components/payments/create-payment-form/locales/de.ts +20 -0
- package/src/components/payments/create-payment-form/locales/sl.ts +20 -0
- package/src/components/payments/edit-payment-form/edit-payment-form.tsx +230 -0
- package/src/components/payments/edit-payment-form/index.ts +1 -0
- package/src/components/payments/edit-payment-form/locales/de.ts +20 -0
- package/src/components/payments/edit-payment-form/locales/sl.ts +20 -0
- package/src/components/payments/index.ts +4 -0
- package/src/components/payments/list/index.ts +2 -0
- package/src/components/payments/list/list-row-actions.tsx +98 -0
- package/src/components/payments/list/list-table.tsx +186 -0
- package/src/components/payments/list/locales/de.ts +19 -0
- package/src/components/payments/list/locales/sl.ts +19 -0
- package/src/components/payments/payments.hooks.ts +15 -0
- package/src/components/request-logs/index.ts +3 -0
- package/src/components/request-logs/request-log-detail.tsx +242 -0
- package/src/components/request-logs/request-log-list-table.tsx +266 -0
- package/src/components/request-logs/request-logs-page.tsx +10 -0
- package/src/components/table/README.md +410 -0
- package/src/components/table/data-table.tsx +251 -0
- package/src/components/table/date-cell.tsx +35 -0
- package/src/components/table/filter-bar.tsx +114 -0
- package/src/components/table/filter-panel.tsx +407 -0
- package/src/components/table/hooks/use-table-fetch.ts +17 -0
- package/src/components/table/hooks/use-table-query.ts +36 -0
- package/src/components/table/hooks/use-table-state.ts +293 -0
- package/src/components/table/index.ts +35 -0
- package/src/components/table/search-input.tsx +85 -0
- package/src/components/table/sortable-header.tsx +56 -0
- package/src/components/table/table-empty-state.tsx +40 -0
- package/src/components/table/table-no-results.tsx +41 -0
- package/src/components/table/table-pagination.tsx +42 -0
- package/src/components/table/table-skeleton.tsx +54 -0
- package/src/components/table/types.ts +136 -0
- package/src/components/tax-reports/index.ts +1 -0
- package/src/components/tax-reports/kir-export-form.tsx +172 -0
- package/src/components/taxes/create-tax-form/create-tax-form.tsx +112 -0
- package/src/components/taxes/create-tax-form/locales/de.ts +8 -0
- package/src/components/taxes/create-tax-form/locales/en.ts +7 -0
- package/src/components/taxes/create-tax-form/locales/sl.ts +8 -0
- package/src/components/taxes/tax-list-table/locales/de.ts +11 -0
- package/src/components/taxes/tax-list-table/locales/en.ts +10 -0
- package/src/components/taxes/tax-list-table/locales/sl.ts +11 -0
- package/src/components/taxes/tax-list-table/tax-list-header.tsx +29 -0
- package/src/components/taxes/tax-list-table/tax-list-row-actions.tsx +43 -0
- package/src/components/taxes/tax-list-table/tax-list-row.tsx +46 -0
- package/src/components/taxes/tax-list-table/tax-list-table.tsx +59 -0
- package/src/components/taxes/taxes.hooks.ts +35 -0
- package/src/components/ui/alert-dialog.tsx +61 -0
- package/src/components/ui/alert.tsx +72 -0
- package/src/components/ui/badge.tsx +48 -0
- package/src/components/ui/breadcrumb.tsx +132 -0
- package/src/components/ui/button.tsx +61 -0
- package/src/components/ui/calendar.tsx +213 -0
- package/src/components/ui/card.tsx +94 -0
- package/src/components/ui/chart.tsx +380 -0
- package/src/components/ui/checkbox.tsx +27 -0
- package/src/components/ui/collapsible.tsx +56 -0
- package/src/components/ui/command.tsx +187 -0
- package/src/components/ui/dialog.tsx +187 -0
- package/src/components/ui/drawer.tsx +123 -0
- package/src/components/ui/dropdown-menu.tsx +291 -0
- package/src/components/ui/form.tsx +166 -0
- package/src/components/ui/input-group.tsx +149 -0
- package/src/components/ui/input.tsx +20 -0
- package/src/components/ui/label.tsx +18 -0
- package/src/components/ui/loading-spinner.tsx +16 -0
- package/src/components/ui/popover.tsx +108 -0
- package/src/components/ui/radio-group.tsx +37 -0
- package/src/components/ui/select.tsx +200 -0
- package/src/components/ui/separator.tsx +23 -0
- package/src/components/ui/sheet.tsx +145 -0
- package/src/components/ui/sidebar.tsx +771 -0
- package/src/components/ui/skeleton.tsx +13 -0
- package/src/components/ui/sonner.tsx +60 -0
- package/src/components/ui/spinner.tsx +10 -0
- package/src/components/ui/sticky-form-footer.tsx +55 -0
- package/src/components/ui/switch.tsx +30 -0
- package/src/components/ui/table.tsx +101 -0
- package/src/components/ui/tabs.tsx +80 -0
- package/src/components/ui/textarea.tsx +18 -0
- package/src/components/ui/tooltip.tsx +89 -0
- package/src/components/wl-subscription/index.ts +2 -0
- package/src/components/wl-subscription/locked-feature.tsx +173 -0
- package/src/components/wl-subscription/upgrade-modal.tsx +209 -0
- package/src/frontend.tsx +28 -0
- package/src/generate-schemas.ts +265 -0
- package/src/generated/schemas/advanceinvoice.ts +177 -0
- package/src/generated/schemas/creditnote.ts +187 -0
- package/src/generated/schemas/customer.ts +29 -0
- package/src/generated/schemas/entity.ts +252 -0
- package/src/generated/schemas/estimate.ts +159 -0
- package/src/generated/schemas/furssettings.ts +25 -0
- package/src/generated/schemas/index.ts +24 -0
- package/src/generated/schemas/invoice.ts +167 -0
- package/src/generated/schemas/item.ts +38 -0
- package/src/generated/schemas/payment.ts +44 -0
- package/src/generated/schemas/previewadvanceinvoice_body.ts +354 -0
- package/src/generated/schemas/previewestimate_body.ts +309 -0
- package/src/generated/schemas/registerfursmovablepremise_body.ts +22 -0
- package/src/generated/schemas/registerfursrealestatepremise_body.ts +32 -0
- package/src/generated/schemas/renderdocument_body.ts +594 -0
- package/src/generated/schemas/sendemail_body.ts +26 -0
- package/src/generated/schemas/startpdfexport_body.ts +20 -0
- package/src/generated/schemas/tax.ts +48 -0
- package/src/generated/schemas/uploadfile_body.ts +23 -0
- package/src/generated/schemas/uploadfurscertificate_body.ts +20 -0
- package/src/generated/schemas/userfurssettings.ts +19 -0
- package/src/hooks/create-resource-hooks.test.ts +483 -0
- package/src/hooks/create-resource-hooks.ts +300 -0
- package/src/hooks/use-debounce.ts +12 -0
- package/src/hooks/use-duplicate-document.ts +185 -0
- package/src/hooks/use-media-query.tsx +19 -0
- package/src/hooks/use-mobile.ts +39 -0
- package/src/hooks/use-next-document-number.ts +57 -0
- package/src/hooks/use-resource-mutation.ts +118 -0
- package/src/hooks/use-vies-check.ts +130 -0
- package/src/index.css +11 -0
- package/src/index.html +13 -0
- package/src/index.tsx +12 -0
- package/src/lib/auth.ts +4 -0
- package/src/lib/browser-cookies.ts +70 -0
- package/src/lib/constants.ts +287 -0
- package/src/lib/cookies.ts +36 -0
- package/src/lib/schemas/advance-invoice.ts +43 -0
- package/src/lib/schemas/credit-note.ts +32 -0
- package/src/lib/schemas/estimate.ts +31 -0
- package/src/lib/schemas/index.ts +18 -0
- package/src/lib/schemas/invoice.ts +43 -0
- package/src/lib/schemas/shared.ts +79 -0
- package/src/lib/translation.ts +38 -0
- package/src/lib/utils.ts +6 -0
- package/src/providers/entities-context.tsx +41 -0
- package/src/providers/entities-provider.tsx +201 -0
- package/src/providers/form-footer-context.tsx +72 -0
- package/src/providers/sdk-provider.tsx +164 -0
- package/src/providers/white-label-provider.tsx +91 -0
- package/src/providers/wl-subscription-provider.tsx +277 -0
- package/src/utils/string-helpers.ts +111 -0
package/src/app.tsx
ADDED
|
@@ -0,0 +1,25 @@
|
|
|
1
|
+
import { Card, CardContent } from "@/ui/components/ui/card";
|
|
2
|
+
|
|
3
|
+
import "./index.css";
|
|
4
|
+
|
|
5
|
+
export function App() {
|
|
6
|
+
return (
|
|
7
|
+
<div className="container relative z-10 mx-auto p-8 text-center">
|
|
8
|
+
<div className="mb-8 flex items-center justify-center gap-8">{/* Logo */}</div>
|
|
9
|
+
|
|
10
|
+
<Card className="border-muted bg-card/50 backdrop-blur-sm">
|
|
11
|
+
<CardContent>
|
|
12
|
+
<h1 className="mb-4 font-bold text-5xl leading-tight">Space Invoices React UI kit</h1>
|
|
13
|
+
|
|
14
|
+
<p>
|
|
15
|
+
This is a simple UI kit for React. It is a work in progress and will be updated as we add more components.
|
|
16
|
+
</p>
|
|
17
|
+
|
|
18
|
+
{/* Place components here for preview */}
|
|
19
|
+
</CardContent>
|
|
20
|
+
</Card>
|
|
21
|
+
</div>
|
|
22
|
+
);
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
export default App;
|
|
@@ -0,0 +1,135 @@
|
|
|
1
|
+
import { Popover } from "@base-ui/react/popover";
|
|
2
|
+
import * as React from "react";
|
|
3
|
+
import { Command, CommandEmpty, CommandGroup, CommandItem, CommandList } from "@/ui/components/ui/command";
|
|
4
|
+
import { Input } from "@/ui/components/ui/input";
|
|
5
|
+
import { cn } from "@/ui/lib/utils";
|
|
6
|
+
|
|
7
|
+
export type AutocompleteOption = {
|
|
8
|
+
value: string;
|
|
9
|
+
label: string | React.ReactNode;
|
|
10
|
+
};
|
|
11
|
+
|
|
12
|
+
type AutocompleteProps = {
|
|
13
|
+
options: AutocompleteOption[];
|
|
14
|
+
value?: string;
|
|
15
|
+
onValueChange?: (value: string) => void;
|
|
16
|
+
onBlur?: (event: React.FocusEvent<HTMLInputElement>) => void; // Added onBlur prop
|
|
17
|
+
placeholder?: string;
|
|
18
|
+
emptyText?: string;
|
|
19
|
+
className?: string;
|
|
20
|
+
disabled?: boolean;
|
|
21
|
+
loading?: boolean;
|
|
22
|
+
onSearch?: (value: string) => void;
|
|
23
|
+
searchValue?: string;
|
|
24
|
+
displayValue?: string;
|
|
25
|
+
};
|
|
26
|
+
|
|
27
|
+
export function Autocomplete({
|
|
28
|
+
options,
|
|
29
|
+
value,
|
|
30
|
+
onValueChange,
|
|
31
|
+
onBlur: onBlurProp, // Destructure the new onBlur prop
|
|
32
|
+
placeholder = "Type to search...",
|
|
33
|
+
emptyText = "No results found.",
|
|
34
|
+
className,
|
|
35
|
+
disabled,
|
|
36
|
+
loading,
|
|
37
|
+
onSearch,
|
|
38
|
+
searchValue: externalSearchValue,
|
|
39
|
+
displayValue,
|
|
40
|
+
}: AutocompleteProps) {
|
|
41
|
+
const [open, setOpen] = React.useState(false);
|
|
42
|
+
const [internalSearchValue, setInternalSearchValue] = React.useState("");
|
|
43
|
+
const inputRef = React.useRef<HTMLInputElement>(null);
|
|
44
|
+
|
|
45
|
+
const searchValue = externalSearchValue ?? internalSearchValue;
|
|
46
|
+
// Show displayValue when not typing, otherwise show what user is typing
|
|
47
|
+
const inputValue = searchValue || displayValue;
|
|
48
|
+
|
|
49
|
+
const handleInputChange = (e: React.ChangeEvent<HTMLInputElement>) => {
|
|
50
|
+
const value = e.target.value;
|
|
51
|
+
setInternalSearchValue(value);
|
|
52
|
+
onSearch?.(value);
|
|
53
|
+
|
|
54
|
+
// Open popover when user starts typing
|
|
55
|
+
if (!open) {
|
|
56
|
+
setOpen(true);
|
|
57
|
+
}
|
|
58
|
+
};
|
|
59
|
+
|
|
60
|
+
const handleSelect = (selectedValue: string) => {
|
|
61
|
+
onValueChange?.(selectedValue);
|
|
62
|
+
setOpen(false);
|
|
63
|
+
};
|
|
64
|
+
|
|
65
|
+
const handleInputFocus = () => {
|
|
66
|
+
// Only open popover on focus if there's no displayValue (no customer selected)
|
|
67
|
+
if (!displayValue && options.length > 0) {
|
|
68
|
+
setOpen(true);
|
|
69
|
+
}
|
|
70
|
+
};
|
|
71
|
+
|
|
72
|
+
const handleInputBlur = (e: React.FocusEvent<HTMLInputElement>) => {
|
|
73
|
+
// Don't close if clicking inside the popover
|
|
74
|
+
const relatedTarget = e.relatedTarget as HTMLElement;
|
|
75
|
+
if (relatedTarget?.closest('[role="dialog"]')) {
|
|
76
|
+
return;
|
|
77
|
+
}
|
|
78
|
+
// Close after a short delay to allow click events to fire
|
|
79
|
+
setTimeout(() => setOpen(false), 200);
|
|
80
|
+
|
|
81
|
+
onBlurProp?.(e); // Call the passed onBlur prop after internal logic
|
|
82
|
+
};
|
|
83
|
+
|
|
84
|
+
// Handle popover open/close - prevent closing when input is focused
|
|
85
|
+
const handleOpenChange = (newOpen: boolean) => {
|
|
86
|
+
if (!newOpen && document.activeElement === inputRef.current) {
|
|
87
|
+
// Don't close if the input still has focus (user clicked on input)
|
|
88
|
+
return;
|
|
89
|
+
}
|
|
90
|
+
setOpen(newOpen);
|
|
91
|
+
};
|
|
92
|
+
|
|
93
|
+
return (
|
|
94
|
+
<Popover.Root open={open} onOpenChange={handleOpenChange}>
|
|
95
|
+
<Input
|
|
96
|
+
ref={inputRef}
|
|
97
|
+
value={inputValue}
|
|
98
|
+
onChange={handleInputChange}
|
|
99
|
+
onFocus={handleInputFocus}
|
|
100
|
+
onBlur={handleInputBlur}
|
|
101
|
+
placeholder={placeholder}
|
|
102
|
+
className={className}
|
|
103
|
+
disabled={disabled}
|
|
104
|
+
autoComplete="off"
|
|
105
|
+
/>
|
|
106
|
+
<Popover.Portal>
|
|
107
|
+
<Popover.Positioner anchor={inputRef} align="start" sideOffset={4} className="isolate z-50">
|
|
108
|
+
<Popover.Popup
|
|
109
|
+
initialFocus={false}
|
|
110
|
+
className="flex flex-col rounded-md bg-popover p-0 text-popover-foreground shadow-md outline-hidden ring-1 ring-foreground/10"
|
|
111
|
+
style={{ width: inputRef.current?.offsetWidth }}
|
|
112
|
+
>
|
|
113
|
+
<Command shouldFilter={false}>
|
|
114
|
+
<CommandList>
|
|
115
|
+
<CommandEmpty>{loading ? "Loading..." : emptyText}</CommandEmpty>
|
|
116
|
+
<CommandGroup>
|
|
117
|
+
{options.map((option) => (
|
|
118
|
+
<CommandItem
|
|
119
|
+
key={option.value}
|
|
120
|
+
value={option.value}
|
|
121
|
+
onSelect={() => handleSelect(option.value)}
|
|
122
|
+
className={cn(value === option.value && "font-bold")}
|
|
123
|
+
>
|
|
124
|
+
{option.label}
|
|
125
|
+
</CommandItem>
|
|
126
|
+
))}
|
|
127
|
+
</CommandGroup>
|
|
128
|
+
</CommandList>
|
|
129
|
+
</Command>
|
|
130
|
+
</Popover.Popup>
|
|
131
|
+
</Popover.Positioner>
|
|
132
|
+
</Popover.Portal>
|
|
133
|
+
</Popover.Root>
|
|
134
|
+
);
|
|
135
|
+
}
|
|
@@ -0,0 +1,160 @@
|
|
|
1
|
+
import type { Activity } from "@spaceinvoices/js-sdk";
|
|
2
|
+
import { CheckCircle2, Circle, Clock, Mail, Pencil, Receipt, RefreshCw, Trash2, XCircle } from "lucide-react";
|
|
3
|
+
import { Card, CardContent, CardHeader, CardTitle } from "@/ui/components/ui/card";
|
|
4
|
+
import type { ComponentTranslationProps } from "@/ui/lib/translation";
|
|
5
|
+
import { createTranslation } from "@/ui/lib/translation";
|
|
6
|
+
import de from "./locales/de";
|
|
7
|
+
import sl from "./locales/sl";
|
|
8
|
+
|
|
9
|
+
const translations = { de, sl } as const;
|
|
10
|
+
|
|
11
|
+
// Re-export for convenience
|
|
12
|
+
export type { Activity };
|
|
13
|
+
|
|
14
|
+
interface ActivityTimelineProps extends ComponentTranslationProps {
|
|
15
|
+
activities: Activity[];
|
|
16
|
+
isLoading?: boolean;
|
|
17
|
+
}
|
|
18
|
+
|
|
19
|
+
/**
|
|
20
|
+
* Get icon and color for activity action type
|
|
21
|
+
*/
|
|
22
|
+
function getActivityIcon(action: string) {
|
|
23
|
+
const iconMap: Record<string, { icon: typeof Circle; color: string }> = {
|
|
24
|
+
created: { icon: CheckCircle2, color: "text-green-500" },
|
|
25
|
+
updated: { icon: Pencil, color: "text-blue-500" },
|
|
26
|
+
deleted: { icon: Trash2, color: "text-red-500" },
|
|
27
|
+
voided: { icon: XCircle, color: "text-gray-500" },
|
|
28
|
+
sent: { icon: Mail, color: "text-purple-500" },
|
|
29
|
+
exported: { icon: Receipt, color: "text-orange-500" },
|
|
30
|
+
synced: { icon: RefreshCw, color: "text-cyan-500" },
|
|
31
|
+
fiscalized: { icon: CheckCircle2, color: "text-emerald-500" },
|
|
32
|
+
};
|
|
33
|
+
return iconMap[action] || { icon: Circle, color: "text-gray-400" };
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
/**
|
|
37
|
+
* Format relative time
|
|
38
|
+
*/
|
|
39
|
+
function formatRelativeTime(date: Date | string, t: (key: string) => string): string {
|
|
40
|
+
const d = typeof date === "string" ? new Date(date) : date;
|
|
41
|
+
const now = new Date();
|
|
42
|
+
const diffMs = now.getTime() - d.getTime();
|
|
43
|
+
const diffMins = Math.floor(diffMs / 60000);
|
|
44
|
+
const diffHours = Math.floor(diffMs / 3600000);
|
|
45
|
+
const diffDays = Math.floor(diffMs / 86400000);
|
|
46
|
+
|
|
47
|
+
if (diffMins < 1) return t("just now");
|
|
48
|
+
if (diffMins < 60) return `${diffMins} ${t("minutes ago")}`;
|
|
49
|
+
if (diffHours < 24) return `${diffHours} ${t("hours ago")}`;
|
|
50
|
+
return `${diffDays} ${t("days ago")}`;
|
|
51
|
+
}
|
|
52
|
+
|
|
53
|
+
/**
|
|
54
|
+
* Get display label for actor
|
|
55
|
+
*/
|
|
56
|
+
function getActorLabel(activity: Activity, t: (key: string) => string): string {
|
|
57
|
+
if (activity.actor_label) return activity.actor_label;
|
|
58
|
+
if (activity.actor_type === "user") return t("user");
|
|
59
|
+
if (activity.actor_type === "system") return t("system");
|
|
60
|
+
if (activity.actor_type === "cron") return t("cron");
|
|
61
|
+
if (activity.actor_type === "webhook") return t("webhook");
|
|
62
|
+
return activity.actor_type;
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
/**
|
|
66
|
+
* Activity Timeline Component
|
|
67
|
+
*
|
|
68
|
+
* Displays a chronological list of activities for a resource.
|
|
69
|
+
* Shows icon, action, actor, and relative timestamp.
|
|
70
|
+
*/
|
|
71
|
+
export function ActivityTimeline({ activities, isLoading, ...i18nProps }: ActivityTimelineProps) {
|
|
72
|
+
const t = createTranslation({ translations, ...i18nProps });
|
|
73
|
+
|
|
74
|
+
if (isLoading) {
|
|
75
|
+
return (
|
|
76
|
+
<Card>
|
|
77
|
+
<CardHeader className="pb-3">
|
|
78
|
+
<CardTitle className="text-lg">{t("Activity")}</CardTitle>
|
|
79
|
+
</CardHeader>
|
|
80
|
+
<CardContent>
|
|
81
|
+
<div className="space-y-4">
|
|
82
|
+
{[1, 2, 3].map((i) => (
|
|
83
|
+
<div key={i} className="flex animate-pulse items-start gap-3">
|
|
84
|
+
<div className="mt-0.5 h-5 w-5 rounded-full bg-muted" />
|
|
85
|
+
<div className="flex-1 space-y-2">
|
|
86
|
+
<div className="h-4 w-24 rounded bg-muted" />
|
|
87
|
+
<div className="h-3 w-16 rounded bg-muted" />
|
|
88
|
+
</div>
|
|
89
|
+
</div>
|
|
90
|
+
))}
|
|
91
|
+
</div>
|
|
92
|
+
</CardContent>
|
|
93
|
+
</Card>
|
|
94
|
+
);
|
|
95
|
+
}
|
|
96
|
+
|
|
97
|
+
if (!activities.length) {
|
|
98
|
+
return (
|
|
99
|
+
<Card>
|
|
100
|
+
<CardHeader className="pb-3">
|
|
101
|
+
<CardTitle className="text-lg">{t("Activity")}</CardTitle>
|
|
102
|
+
</CardHeader>
|
|
103
|
+
<CardContent>
|
|
104
|
+
<div className="flex items-center gap-2 text-muted-foreground text-sm">
|
|
105
|
+
<Clock className="h-4 w-4" />
|
|
106
|
+
<span>{t("No activities yet for this resource")}</span>
|
|
107
|
+
</div>
|
|
108
|
+
</CardContent>
|
|
109
|
+
</Card>
|
|
110
|
+
);
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
return (
|
|
114
|
+
<Card>
|
|
115
|
+
<CardHeader className="pb-3">
|
|
116
|
+
<CardTitle className="text-lg">{t("Activity")}</CardTitle>
|
|
117
|
+
</CardHeader>
|
|
118
|
+
<CardContent>
|
|
119
|
+
<div className="relative">
|
|
120
|
+
{/* Timeline line */}
|
|
121
|
+
<div className="absolute top-3 bottom-3 left-2.5 w-px bg-border" />
|
|
122
|
+
|
|
123
|
+
{/* Activity items */}
|
|
124
|
+
<div className="space-y-4">
|
|
125
|
+
{activities.map((activity) => {
|
|
126
|
+
const { icon: Icon, color } = getActivityIcon(activity.action);
|
|
127
|
+
return (
|
|
128
|
+
<div key={activity.id} className="relative flex items-start gap-3 pl-0">
|
|
129
|
+
{/* Icon */}
|
|
130
|
+
<div className={`relative z-10 bg-background ${color}`}>
|
|
131
|
+
<Icon className="h-5 w-5" />
|
|
132
|
+
</div>
|
|
133
|
+
|
|
134
|
+
{/* Content */}
|
|
135
|
+
<div className="min-w-0 flex-1">
|
|
136
|
+
<div className="flex items-center gap-2">
|
|
137
|
+
<span className="font-medium text-sm">{t(activity.action)}</span>
|
|
138
|
+
<span className="text-muted-foreground text-xs">{getActorLabel(activity, t)}</span>
|
|
139
|
+
</div>
|
|
140
|
+
<div className="mt-0.5 text-muted-foreground text-xs">
|
|
141
|
+
{formatRelativeTime(activity.created_at, t)}
|
|
142
|
+
</div>
|
|
143
|
+
{/* Details if available */}
|
|
144
|
+
{activity.details && Object.keys(activity.details).length > 0 && (
|
|
145
|
+
<div className="mt-1 text-muted-foreground text-xs">
|
|
146
|
+
{activity.action === "sent" && (activity.details as { to?: string }).to && (
|
|
147
|
+
<span>to {(activity.details as { to: string }).to}</span>
|
|
148
|
+
)}
|
|
149
|
+
</div>
|
|
150
|
+
)}
|
|
151
|
+
</div>
|
|
152
|
+
</div>
|
|
153
|
+
);
|
|
154
|
+
})}
|
|
155
|
+
</div>
|
|
156
|
+
</div>
|
|
157
|
+
</CardContent>
|
|
158
|
+
</Card>
|
|
159
|
+
);
|
|
160
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export { type Activity, ActivityTimeline } from "./activity-timeline";
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
export default {
|
|
2
|
+
// Header
|
|
3
|
+
Activity: "Aktivitaet",
|
|
4
|
+
|
|
5
|
+
// Actions
|
|
6
|
+
created: "Erstellt",
|
|
7
|
+
updated: "Aktualisiert",
|
|
8
|
+
deleted: "Geloescht",
|
|
9
|
+
voided: "Storniert",
|
|
10
|
+
sent: "Gesendet",
|
|
11
|
+
exported: "Exportiert",
|
|
12
|
+
synced: "Synchronisiert",
|
|
13
|
+
fiscalized: "Fiskalisiert",
|
|
14
|
+
|
|
15
|
+
// Actor types
|
|
16
|
+
user: "Benutzer",
|
|
17
|
+
system: "System",
|
|
18
|
+
cron: "Geplante Aufgabe",
|
|
19
|
+
webhook: "Webhook",
|
|
20
|
+
|
|
21
|
+
// Empty state
|
|
22
|
+
"No activities": "Keine Aktivitaeten",
|
|
23
|
+
"No activities yet for this resource": "Noch keine Aktivitaeten fuer diese Ressource",
|
|
24
|
+
|
|
25
|
+
// Time
|
|
26
|
+
"just now": "gerade eben",
|
|
27
|
+
"minutes ago": "Minuten her",
|
|
28
|
+
"hours ago": "Stunden her",
|
|
29
|
+
"days ago": "Tage her",
|
|
30
|
+
} as const;
|
|
@@ -0,0 +1,30 @@
|
|
|
1
|
+
export default {
|
|
2
|
+
// Header
|
|
3
|
+
Activity: "Aktivnost",
|
|
4
|
+
|
|
5
|
+
// Actions
|
|
6
|
+
created: "Ustvarjeno",
|
|
7
|
+
updated: "Posodobljeno",
|
|
8
|
+
deleted: "Izbrisano",
|
|
9
|
+
voided: "Stornirano",
|
|
10
|
+
sent: "Poslano",
|
|
11
|
+
exported: "Izvozeno",
|
|
12
|
+
synced: "Sinhronizirano",
|
|
13
|
+
fiscalized: "Davčno potrjeno",
|
|
14
|
+
|
|
15
|
+
// Actor types
|
|
16
|
+
user: "Uporabnik",
|
|
17
|
+
system: "Sistem",
|
|
18
|
+
cron: "Načrtovano opravilo",
|
|
19
|
+
webhook: "Webhook",
|
|
20
|
+
|
|
21
|
+
// Empty state
|
|
22
|
+
"No activities": "Ni aktivnosti",
|
|
23
|
+
"No activities yet for this resource": "Za ta vir še ni aktivnosti",
|
|
24
|
+
|
|
25
|
+
// Time
|
|
26
|
+
"just now": "pravkar",
|
|
27
|
+
"minutes ago": "minut nazaj",
|
|
28
|
+
"hours ago": "ur nazaj",
|
|
29
|
+
"days ago": "dni nazaj",
|
|
30
|
+
} as const;
|
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
import type { CreateAdvanceInvoice201, CreateAdvanceInvoiceBody } from "@spaceinvoices/js-sdk";
|
|
2
|
+
import { useMutation, useQueryClient } from "@tanstack/react-query";
|
|
3
|
+
import { NEXT_DOCUMENT_NUMBER_CACHE_KEY } from "@/ui/hooks/use-next-document-number";
|
|
4
|
+
import { useSDK } from "@/ui/providers/sdk-provider";
|
|
5
|
+
|
|
6
|
+
// Define constants for cache keys
|
|
7
|
+
export const ADVANCE_INVOICES_CACHE_KEY = "advance-invoices";
|
|
8
|
+
|
|
9
|
+
// ============================================================================
|
|
10
|
+
// Create Advance Invoice Hook
|
|
11
|
+
// ============================================================================
|
|
12
|
+
|
|
13
|
+
type UseCreateAdvanceInvoiceOptions = {
|
|
14
|
+
entityId: string;
|
|
15
|
+
onSuccess?: (data: CreateAdvanceInvoice201) => void;
|
|
16
|
+
onError?: (error: unknown) => void;
|
|
17
|
+
};
|
|
18
|
+
|
|
19
|
+
export function useCreateAdvanceInvoice({ entityId, onSuccess, onError }: UseCreateAdvanceInvoiceOptions) {
|
|
20
|
+
const { sdk } = useSDK();
|
|
21
|
+
const queryClient = useQueryClient();
|
|
22
|
+
|
|
23
|
+
return useMutation({
|
|
24
|
+
mutationFn: async (data: CreateAdvanceInvoiceBody) => {
|
|
25
|
+
return sdk.advanceInvoices.create(data, { entity_id: entityId });
|
|
26
|
+
},
|
|
27
|
+
onSuccess: (data) => {
|
|
28
|
+
// Invalidate advance invoices list cache
|
|
29
|
+
queryClient.invalidateQueries({ queryKey: [ADVANCE_INVOICES_CACHE_KEY] });
|
|
30
|
+
// Invalidate next number cache (shared cache key)
|
|
31
|
+
queryClient.invalidateQueries({ queryKey: [NEXT_DOCUMENT_NUMBER_CACHE_KEY] });
|
|
32
|
+
onSuccess?.(data);
|
|
33
|
+
},
|
|
34
|
+
onError,
|
|
35
|
+
});
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
// ============================================================================
|
|
39
|
+
// FURS Last-Used Combo (localStorage) - Reuse from invoices
|
|
40
|
+
// ============================================================================
|
|
41
|
+
|
|
42
|
+
const FURS_ADV_LAST_USED_KEY = "si:furs:adv:last-used";
|
|
43
|
+
|
|
44
|
+
export type FursCombo = {
|
|
45
|
+
business_premise_name: string;
|
|
46
|
+
electronic_device_name: string;
|
|
47
|
+
};
|
|
48
|
+
|
|
49
|
+
/**
|
|
50
|
+
* Get last-used FURS premise/device combo from localStorage for advance invoices
|
|
51
|
+
* @param entityId - Entity ID (combos are stored per-entity)
|
|
52
|
+
*/
|
|
53
|
+
export function getLastUsedFursCombo(entityId: string): FursCombo | null {
|
|
54
|
+
if (typeof window === "undefined") return null;
|
|
55
|
+
try {
|
|
56
|
+
const stored = localStorage.getItem(`${FURS_ADV_LAST_USED_KEY}:${entityId}`);
|
|
57
|
+
return stored ? JSON.parse(stored) : null;
|
|
58
|
+
} catch {
|
|
59
|
+
return null;
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
/**
|
|
64
|
+
* Save last-used FURS premise/device combo to localStorage for advance invoices
|
|
65
|
+
* @param entityId - Entity ID
|
|
66
|
+
* @param combo - FURS premise/device combo
|
|
67
|
+
*/
|
|
68
|
+
export function setLastUsedFursCombo(entityId: string, combo: FursCombo): void {
|
|
69
|
+
if (typeof window === "undefined") return;
|
|
70
|
+
try {
|
|
71
|
+
localStorage.setItem(`${FURS_ADV_LAST_USED_KEY}:${entityId}`, JSON.stringify(combo));
|
|
72
|
+
} catch {
|
|
73
|
+
// Ignore localStorage errors (quota exceeded, etc.)
|
|
74
|
+
}
|
|
75
|
+
}
|