- {timeSlots.map((time, timeIndex) => (
+ {timeSlots.map((time, _timeIndex) => (
{time}
diff --git a/extensions/general/calendar/components/DayDetailModal.tsx b/extensions/general/calendar/components/DayDetailModal.tsx
index 1340583b..e0d4066e 100644
--- a/extensions/general/calendar/components/DayDetailModal.tsx
+++ b/extensions/general/calendar/components/DayDetailModal.tsx
@@ -10,7 +10,7 @@ import {
import { Badge } from '@/components/ui/badge'
import { Button } from '@/components/ui/button'
import { Invoice, Deadline } from '@/types'
-import { formatCurrency, formatDate } from '@/lib/utils'
+import { formatCurrency } from '@/lib/utils'
import {
isInvoiceOverdue,
isDeadlineOverdue,
diff --git a/extensions/general/receipt-ocr/components/ReceiptDashboard.tsx b/extensions/general/receipt-ocr/components/ReceiptDashboard.tsx
index 7f9046b3..bcc28202 100644
--- a/extensions/general/receipt-ocr/components/ReceiptDashboard.tsx
+++ b/extensions/general/receipt-ocr/components/ReceiptDashboard.tsx
@@ -1,6 +1,6 @@
'use client'
-import { Card, CardContent, CardHeader, CardTitle } from '@/components/ui/card'
+import { Card, CardContent } from '@/components/ui/card'
import { Button } from '@/components/ui/button'
import { Badge } from '@/components/ui/badge'
import { Flame, Receipt, CreditCard, Camera, ArrowRight } from 'lucide-react'
diff --git a/extensions/general/receipt-ocr/components/TransactionMatcher.tsx b/extensions/general/receipt-ocr/components/TransactionMatcher.tsx
index a929b606..fb75c56a 100644
--- a/extensions/general/receipt-ocr/components/TransactionMatcher.tsx
+++ b/extensions/general/receipt-ocr/components/TransactionMatcher.tsx
@@ -1,13 +1,13 @@
'use client'
import { useState, useEffect } from 'react'
-import { Card, CardContent, CardHeader, CardTitle } from '@/components/ui/card'
+import { Card, CardContent } from '@/components/ui/card'
import { Button } from '@/components/ui/button'
import { Badge } from '@/components/ui/badge'
import { Skeleton } from '@/components/ui/skeleton'
import { formatCurrency, formatDate } from '@/lib/utils'
import { X, Check, Link2, AlertCircle, Search, Loader2 } from 'lucide-react'
-import type { Receipt, ReceiptMatchCandidate, Transaction } from '@/types'
+import type { Receipt, ReceiptMatchCandidate } from '@/types'
interface TransactionMatcherProps {
receipt: Receipt
diff --git a/extensions/general/receipt-ocr/lib/receipt-categorizer.ts b/extensions/general/receipt-ocr/lib/receipt-categorizer.ts
index 0649bc29..62b0afe7 100644
--- a/extensions/general/receipt-ocr/lib/receipt-categorizer.ts
+++ b/extensions/general/receipt-ocr/lib/receipt-categorizer.ts
@@ -5,7 +5,7 @@
* using pattern matching and AI-suggested categories.
*/
-import type { TransactionCategory, ReceiptLineItem, ExtractedLineItem } from '@/types'
+import type { TransactionCategory, ExtractedLineItem } from '@/types'
import { getTemplateById } from '@/lib/bookkeeping/booking-templates'
// Category mappings from suggested category to TransactionCategory
diff --git a/extensions/general/receipt-ocr/lib/receipt-pipeline.ts b/extensions/general/receipt-ocr/lib/receipt-pipeline.ts
index e63510b1..2e80592f 100644
--- a/extensions/general/receipt-ocr/lib/receipt-pipeline.ts
+++ b/extensions/general/receipt-ocr/lib/receipt-pipeline.ts
@@ -9,7 +9,7 @@
import 'server-only'
import type { SupabaseClient } from '@supabase/supabase-js'
-import type { Receipt, ReceiptMatchCandidate, ReceiptExtractionResult } from '@/types'
+import type { Receipt, ReceiptExtractionResult } from '@/types'
import { analyzeReceipt } from './receipt-analyzer'
import { processLineItems, getDefaultClassification } from './receipt-categorizer'
import { autoMatchReceipts } from './receipt-matcher'
diff --git a/extensions/general/receipt-ocr/pages/ReceiptsPage.tsx b/extensions/general/receipt-ocr/pages/ReceiptsPage.tsx
index e7023ba2..8902de25 100644
--- a/extensions/general/receipt-ocr/pages/ReceiptsPage.tsx
+++ b/extensions/general/receipt-ocr/pages/ReceiptsPage.tsx
@@ -1,7 +1,7 @@
'use client'
import { useState, useEffect, useCallback } from 'react'
-import { Card, CardContent, CardHeader, CardTitle } from '@/components/ui/card'
+import { Card, CardContent } from '@/components/ui/card'
import { Button } from '@/components/ui/button'
import { Badge } from '@/components/ui/badge'
import { Skeleton } from '@/components/ui/skeleton'
diff --git a/lib/ai/document-analyzer.ts b/lib/ai/document-analyzer.ts
index 17db1433..2c817247 100644
--- a/lib/ai/document-analyzer.ts
+++ b/lib/ai/document-analyzer.ts
@@ -451,7 +451,7 @@ function validateVatBreakdown(data: any): VatBreakdownItem[] {
*/
export function validateExtractionConsistency(
extraction: ReceiptExtractionResult | InvoiceExtractionResult,
- // eslint-disable-next-line @typescript-eslint/no-unused-vars
+
_type: 'receipt' | 'invoice'
): ConsistencyResult {
const issues: string[] = []
diff --git a/lib/api/schemas.ts b/lib/api/schemas.ts
index 28597c71..162366bd 100644
--- a/lib/api/schemas.ts
+++ b/lib/api/schemas.ts
@@ -13,9 +13,6 @@ const isoDate = z.string().regex(/^\d{4}-\d{2}-\d{2}$/, 'Expected YYYY-MM-DD dat
/** BAS account number — always a string of 4 digits */
const accountNumber = z.string().regex(/^\d{4}$/, 'Account number must be exactly 4 digits')
-/** Positive monetary amount (> 0) */
-const positiveAmount = z.number().positive()
-
/** Non-negative monetary amount (>= 0) */
const nonNegativeAmount = z.number().nonnegative()
diff --git a/lib/bookkeeping/account-descriptions.ts b/lib/bookkeeping/account-descriptions.ts
index 9fffb944..f0e8101d 100644
--- a/lib/bookkeeping/account-descriptions.ts
+++ b/lib/bookkeeping/account-descriptions.ts
@@ -1,3 +1,5 @@
+import { getBASReference, ACCOUNT_CLASS_LABELS } from './bas-reference'
+
export type AccountType = 'asset' | 'liability' | 'equity' | 'revenue' | 'expense' | 'untaxed_reserves'
export interface AccountDescription {
@@ -332,8 +334,6 @@ export function getAccountDescription(accountNumber: string): AccountDescription
// Fall back to BAS reference data for accounts not in the hardcoded list
try {
- // Dynamic import avoided — use lazy require pattern
- const { getBASReference, ACCOUNT_CLASS_LABELS } = require('./bas-reference')
const ref = getBASReference(accountNumber)
if (ref) {
const classLabel = ACCOUNT_CLASS_LABELS[ref.account_class] || ''
diff --git a/lib/bookkeeping/currency-revaluation.ts b/lib/bookkeeping/currency-revaluation.ts
index 2c1ef123..5e04be34 100644
--- a/lib/bookkeeping/currency-revaluation.ts
+++ b/lib/bookkeeping/currency-revaluation.ts
@@ -173,10 +173,8 @@ export async function previewCurrencyRevaluation(
let credit1510 = 0 // Receivable loss (revalue down)
let debit2440 = 0 // Payable gain (liability shrank)
let credit2440 = 0 // Payable loss (liability grew)
- let debit3960 = 0 // Placeholder — we won't debit 3960
let credit3960 = 0 // Gains
let debit7960 = 0 // Losses
- let credit7960 = 0 // Placeholder — we won't credit 7960
for (const item of items) {
if (item.type === 'receivable') {
diff --git a/lib/bookkeeping/invoice-entries.ts b/lib/bookkeeping/invoice-entries.ts
index b1a7d94e..666d8ae2 100644
--- a/lib/bookkeeping/invoice-entries.ts
+++ b/lib/bookkeeping/invoice-entries.ts
@@ -1,6 +1,6 @@
import { createJournalEntry, findFiscalPeriod } from './engine'
import { resolveSekAmount, buildCurrencyMetadata } from './currency-utils'
-import { generateSalesVatLines, generateReverseChargeLines } from './vat-entries'
+import { generateSalesVatLines } from './vat-entries'
import { getVatTreatmentForRate } from '@/lib/invoices/vat-rules'
import { createLogger } from '@/lib/logger'
import type { SupabaseClient } from '@supabase/supabase-js'
diff --git a/lib/bookkeeping/mapping-engine.ts b/lib/bookkeeping/mapping-engine.ts
index b2db7de7..584ac5f0 100644
--- a/lib/bookkeeping/mapping-engine.ts
+++ b/lib/bookkeeping/mapping-engine.ts
@@ -2,14 +2,11 @@ import type { SupabaseClient } from '@supabase/supabase-js'
import {
generateInputVatLine,
generateReverseChargeLines,
- extractNetAmount,
- extractVatAmount,
} from './vat-entries'
import { findMatchingTemplates, buildMappingResultFromTemplate } from './booking-templates'
import type {
MappingRule,
MappingResult,
- RiskLevel,
Transaction,
EntityType,
VatJournalLine,
diff --git a/lib/bookkeeping/transaction-entries.ts b/lib/bookkeeping/transaction-entries.ts
index 4be60f64..8edc4818 100644
--- a/lib/bookkeeping/transaction-entries.ts
+++ b/lib/bookkeeping/transaction-entries.ts
@@ -1,6 +1,6 @@
import { createJournalEntry, findFiscalPeriod } from './engine'
import { resolveSekAmount, buildCurrencyMetadata } from './currency-utils'
-import { generateInputVatLine, generateReverseChargeLines, extractNetAmount, extractVatAmount } from './vat-entries'
+import { extractNetAmount, extractVatAmount } from './vat-entries'
import { createLogger } from '@/lib/logger'
import type { SupabaseClient } from '@supabase/supabase-js'
import type {
diff --git a/lib/core/documents/document-service.ts b/lib/core/documents/document-service.ts
index 2a4fe893..362a4165 100644
--- a/lib/core/documents/document-service.ts
+++ b/lib/core/documents/document-service.ts
@@ -1,7 +1,7 @@
import type { SupabaseClient } from '@supabase/supabase-js'
import { createServiceClient } from '@/lib/supabase/server'
import { eventBus } from '@/lib/events'
-import type { DocumentAttachment, CreateDocumentAttachmentInput, DocumentUploadSource } from '@/types'
+import type { DocumentAttachment, DocumentUploadSource } from '@/types'
/**
* Document Service - WORM-style document archive
diff --git a/lib/documents/__tests__/document-matcher.test.ts b/lib/documents/__tests__/document-matcher.test.ts
index da8b5dda..50863faa 100644
--- a/lib/documents/__tests__/document-matcher.test.ts
+++ b/lib/documents/__tests__/document-matcher.test.ts
@@ -1,7 +1,7 @@
import { describe, it, expect, vi, beforeEach } from 'vitest'
import { matchDocumentToTransactions } from '../document-matcher'
import { makeInvoiceInboxItem, makeTransaction } from '@/tests/helpers'
-import type { InvoiceExtractionResult, ReceiptExtractionResult, Transaction } from '@/types'
+import type { InvoiceExtractionResult, ReceiptExtractionResult } from '@/types'
describe('matchDocumentToTransactions', () => {
const mockSupabase = {} as never // Not used when candidateTransactions is provided
diff --git a/lib/extensions/__tests__/ai-consent.test.ts b/lib/extensions/__tests__/ai-consent.test.ts
index 81bc6a88..46f16855 100644
--- a/lib/extensions/__tests__/ai-consent.test.ts
+++ b/lib/extensions/__tests__/ai-consent.test.ts
@@ -1,3 +1,4 @@
+/* eslint-disable @typescript-eslint/no-explicit-any */
import { describe, it, expect, vi, beforeEach } from 'vitest'
import { createMockSupabase } from '@/tests/helpers'
import {
diff --git a/lib/extensions/__tests__/sectors.test.ts b/lib/extensions/__tests__/sectors.test.ts
index 2da84e51..90224143 100644
--- a/lib/extensions/__tests__/sectors.test.ts
+++ b/lib/extensions/__tests__/sectors.test.ts
@@ -1,4 +1,4 @@
-import { resolve, join, dirname } from 'path'
+import { resolve, join } from 'path'
import { readdirSync, readFileSync } from 'fs'
/**
@@ -74,6 +74,7 @@ describe('sectors registry', () => {
})
it('getSector returns undefined for unknown slug', () => {
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
const sector = getSector('invalid' as any)
expect(sector).toBeUndefined()
})
diff --git a/lib/import/sie-import.ts b/lib/import/sie-import.ts
index a2f2b6fa..f5d773f6 100644
--- a/lib/import/sie-import.ts
+++ b/lib/import/sie-import.ts
@@ -355,7 +355,7 @@ async function importVouchers(
p_series: voucherSeries,
})
- let currentVoucherNumber = (startNumber as number) || 1
+ const currentVoucherNumber = (startNumber as number) || 1
// Batch insert journal entries (in chunks of 100)
const BATCH_SIZE = 100
diff --git a/lib/reports/__tests__/ar-ledger.test.ts b/lib/reports/__tests__/ar-ledger.test.ts
index 2f1ac1d2..bb4174ac 100644
--- a/lib/reports/__tests__/ar-ledger.test.ts
+++ b/lib/reports/__tests__/ar-ledger.test.ts
@@ -20,6 +20,7 @@ function makeBuilder() {
function makeClient() {
return {
from: vi.fn().mockImplementation(() => makeBuilder()),
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
} as any
}
diff --git a/lib/reports/__tests__/ar-reconciliation.test.ts b/lib/reports/__tests__/ar-reconciliation.test.ts
index 03b7923c..d6a3f951 100644
--- a/lib/reports/__tests__/ar-reconciliation.test.ts
+++ b/lib/reports/__tests__/ar-reconciliation.test.ts
@@ -20,6 +20,7 @@ function makeBuilder() {
function makeClient() {
return {
from: vi.fn().mockImplementation(() => makeBuilder()),
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
} as any
}
diff --git a/lib/reports/__tests__/balance-sheet.test.ts b/lib/reports/__tests__/balance-sheet.test.ts
index fa00e2fc..7efefa0a 100644
--- a/lib/reports/__tests__/balance-sheet.test.ts
+++ b/lib/reports/__tests__/balance-sheet.test.ts
@@ -10,6 +10,7 @@ import type { TrialBalanceRow } from '@/types'
const mockTrialBalance = vi.mocked(generateTrialBalance)
+// eslint-disable-next-line @typescript-eslint/no-explicit-any
const supabase = {} as any
beforeEach(() => {
diff --git a/lib/reports/__tests__/full-archive-export.test.ts b/lib/reports/__tests__/full-archive-export.test.ts
index 70031e02..5e6d18e3 100644
--- a/lib/reports/__tests__/full-archive-export.test.ts
+++ b/lib/reports/__tests__/full-archive-export.test.ts
@@ -1,3 +1,4 @@
+/* eslint-disable @typescript-eslint/no-explicit-any */
import { describe, it, expect, vi, beforeEach } from 'vitest'
import JSZip from 'jszip'
import { generateFullArchive } from '../full-archive-export'
diff --git a/lib/reports/__tests__/general-ledger.test.ts b/lib/reports/__tests__/general-ledger.test.ts
index dcda4be7..628a1b2d 100644
--- a/lib/reports/__tests__/general-ledger.test.ts
+++ b/lib/reports/__tests__/general-ledger.test.ts
@@ -21,6 +21,7 @@ function makeClient() {
return {
from: vi.fn().mockImplementation(() => makeBuilder()),
rpc: vi.fn().mockImplementation(async () => results[resultIdx++] ?? { data: null, error: null }),
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
} as any
}
diff --git a/lib/reports/__tests__/income-statement.test.ts b/lib/reports/__tests__/income-statement.test.ts
index 7b40e4e2..3f583135 100644
--- a/lib/reports/__tests__/income-statement.test.ts
+++ b/lib/reports/__tests__/income-statement.test.ts
@@ -10,6 +10,7 @@ import type { TrialBalanceRow } from '@/types'
const mockTrialBalance = vi.mocked(generateTrialBalance)
+// eslint-disable-next-line @typescript-eslint/no-explicit-any
const supabase = {} as any
beforeEach(() => {
diff --git a/lib/reports/__tests__/journal-register.test.ts b/lib/reports/__tests__/journal-register.test.ts
index c3b2329a..5a2cd567 100644
--- a/lib/reports/__tests__/journal-register.test.ts
+++ b/lib/reports/__tests__/journal-register.test.ts
@@ -20,6 +20,7 @@ function makeBuilder() {
function makeClient() {
return {
from: vi.fn().mockImplementation(() => makeBuilder()),
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
} as any
}
diff --git a/lib/reports/__tests__/sie-export.test.ts b/lib/reports/__tests__/sie-export.test.ts
index e6d6e918..4359caac 100644
--- a/lib/reports/__tests__/sie-export.test.ts
+++ b/lib/reports/__tests__/sie-export.test.ts
@@ -20,6 +20,7 @@ function makeBuilder() {
function makeClient() {
return {
from: vi.fn().mockImplementation(() => makeBuilder()),
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
} as any
}
diff --git a/lib/reports/__tests__/supplier-ledger.test.ts b/lib/reports/__tests__/supplier-ledger.test.ts
index dd53a23f..cefc51b0 100644
--- a/lib/reports/__tests__/supplier-ledger.test.ts
+++ b/lib/reports/__tests__/supplier-ledger.test.ts
@@ -20,6 +20,7 @@ function makeBuilder() {
function makeClient() {
return {
from: vi.fn().mockImplementation(() => makeBuilder()),
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
} as any
}
diff --git a/lib/reports/__tests__/supplier-reconciliation.test.ts b/lib/reports/__tests__/supplier-reconciliation.test.ts
index c60b60a5..dc5ef35b 100644
--- a/lib/reports/__tests__/supplier-reconciliation.test.ts
+++ b/lib/reports/__tests__/supplier-reconciliation.test.ts
@@ -20,6 +20,7 @@ function makeBuilder() {
function makeClient() {
return {
from: vi.fn().mockImplementation(() => makeBuilder()),
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
} as any
}
diff --git a/lib/reports/__tests__/trial-balance.test.ts b/lib/reports/__tests__/trial-balance.test.ts
index 14444fa8..7dd9beac 100644
--- a/lib/reports/__tests__/trial-balance.test.ts
+++ b/lib/reports/__tests__/trial-balance.test.ts
@@ -21,6 +21,7 @@ function makeClient() {
return {
from: vi.fn().mockImplementation(() => makeBuilder()),
rpc: vi.fn().mockImplementation(async () => results[resultIdx++] ?? { data: null, error: null }),
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
} as any
}
diff --git a/lib/reports/__tests__/vat-declaration.test.ts b/lib/reports/__tests__/vat-declaration.test.ts
index 47325085..0c0a962f 100644
--- a/lib/reports/__tests__/vat-declaration.test.ts
+++ b/lib/reports/__tests__/vat-declaration.test.ts
@@ -20,6 +20,7 @@ function makeBuilder() {
function makeClient() {
return {
from: vi.fn().mockImplementation(() => makeBuilder()),
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
} as any
}
diff --git a/lib/reports/ink2/__tests__/ink2-engine.test.ts b/lib/reports/ink2/__tests__/ink2-engine.test.ts
index d0878208..c31801fb 100644
--- a/lib/reports/ink2/__tests__/ink2-engine.test.ts
+++ b/lib/reports/ink2/__tests__/ink2-engine.test.ts
@@ -1,6 +1,6 @@
import { describe, it, expect } from 'vitest'
import { INK2_ACCOUNT_MAPPINGS, isAccountInMapping } from '../ink2-engine'
-import type { INK2AccountMapping, INK2SRUCode } from '../types'
+import type { INK2SRUCode } from '../types'
/**
* Helper to find which SRU code an account maps to
diff --git a/lib/reports/ne-bilaga/__tests__/ne-engine.test.ts b/lib/reports/ne-bilaga/__tests__/ne-engine.test.ts
index c52a29c5..eee7a977 100644
--- a/lib/reports/ne-bilaga/__tests__/ne-engine.test.ts
+++ b/lib/reports/ne-bilaga/__tests__/ne-engine.test.ts
@@ -1,6 +1,5 @@
import { describe, it, expect } from 'vitest'
import { NE_ACCOUNT_MAPPINGS } from '../ne-engine'
-import type { NEAccountMapping } from '@/lib/reports/ne-bilaga/types'
/**
* Helper to check if an account falls into a specific ruta
diff --git a/lib/tax/calculator.ts b/lib/tax/calculator.ts
index 6f8afc42..a74f76e4 100644
--- a/lib/tax/calculator.ts
+++ b/lib/tax/calculator.ts
@@ -137,8 +137,6 @@ export function calculateABTax(
// Arbetsgivaravgifter on salaries (already included in salary costs usually)
// This is just for reference
- const arbetsgivaravgifter = salaryCostsYTD * TAX_RATES.arbetsgivaravgifter
-
const totalTax = bolagsskatt + momsFromUnpaidInvoices
return {
diff --git a/lib/tax/deadline-config.ts b/lib/tax/deadline-config.ts
index 16b7f54a..60bdb5f7 100644
--- a/lib/tax/deadline-config.ts
+++ b/lib/tax/deadline-config.ts
@@ -214,7 +214,6 @@ export const TAX_DEADLINE_CONFIGS: TaxDeadlineConfig[] = [
const dl = getDeadline(fyEndYear)
if (dl.year === year) {
// Compute the FY start year
- const fyStartYear = fyEndMonth === 12 ? fyEndYear : fyEndYear - (fyEndMonth < settings.fiscal_year_start_month ? 0 : 0)
const fyStart = fyEndMonth === 12 ? fyEndYear : fyEndYear
const periodLabel = fyEndMonth === 12
? `${fyEndYear}`
@@ -249,14 +248,12 @@ export const TAX_DEADLINE_CONFIGS: TaxDeadlineConfig[] = [
// 7 months after FY end per ÅRL 8:3
// Deadline month (0-indexed): ((fyEndMonth - 1) + 7) % 12
- const deadlineMonth0 = ((fyEndMonth - 1) + 7) % 12
// Last day of the deadline month
// Determine which year the deadline falls in
- const wrapsYear = fyEndMonth > 5 // Jun+ wraps into next year
+ const _wrapsYear = fyEndMonth > 5 // Jun+ wraps into next year
// For calendar year (Dec end): deadline Jul 31 same year+1
// The FY ending in `year` produces a deadline:
- const fyEndYear = year - 1 // By default we show deadline for the FY that ended in year-1
- const deadlineYear = wrapsYear ? fyEndYear + 1 + 1 : fyEndYear + 1
+ const _fyEndYear = year - 1 // By default we show deadline for the FY that ended in year-1
// Simpler: compute from a concrete FY end date
// FY ends: fyEndMonth (1-indexed), last day, in some year.
// We want the deadline that falls in `year`.
diff --git a/lib/tax/deadline-generator.ts b/lib/tax/deadline-generator.ts
index 32f2f9ab..dfbdb2cd 100644
--- a/lib/tax/deadline-generator.ts
+++ b/lib/tax/deadline-generator.ts
@@ -4,11 +4,10 @@
import { SupabaseClient } from '@supabase/supabase-js'
import { createLogger } from '@/lib/logger'
-import type { TaxDeadlineType, DeadlineStatus, CreateDeadlineInput } from '@/types'
+import type { TaxDeadlineType, DeadlineStatus } from '@/types'
const log = createLogger('deadline-generator')
import {
- TAX_DEADLINE_CONFIGS,
getApplicableDeadlineConfigs,
type CompanySettingsForDeadlines,
type DeadlineInstance,
@@ -180,7 +179,7 @@ export async function generateTaxDeadlinesForUser(
*/
function createLinkedReportPeriod(
instance: DeadlineInstance,
- type: TaxDeadlineType
+ _type: TaxDeadlineType
): Record | null {
const period = instance.period
diff --git a/public/docs/arkivplan-mall.md b/public/docs/arkivplan-mall.md
new file mode 100644
index 00000000..99581389
--- /dev/null
+++ b/public/docs/arkivplan-mall.md
@@ -0,0 +1,146 @@
+# Arkivplan
+
+**Mall for användare av erp-base**
+Upprättad i enlighet med BFNAR 2013:2 punkt 8.3
+
+---
+
+## Instruktioner
+
+Denna mall ska fyllas i av dig som kund och sparas som del av din systemdokumentation. Bokföringsnämndens allmänna råd (BFNAR 2013:2) kräver att varje bokföringsskyldig upprättar en arkivplan som beskriver vilken räkenskapsinformation som finns, var den förvaras, och vem som ansvarar för arkiveringen.
+
+Fyll i de markerade fälten. Radera denna instruktionssektion innan du arkiverar dokumentet.
+
+---
+
+## 1. Företagsuppgifter
+
+| Fält | Uppgift |
+|---|---|
+| Företagsnamn | [FÖRETAGSNAMN] |
+| Organisationsnummer | [ORG-NR] |
+| Företagsform | [ ] Enskild firma [ ] Aktiebolag |
+| Räkenskapsår | [STARTMÅNAD] - [SLUTMÅNAD] |
+| Bokföringsmetod | [ ] Faktureringsmetoden [ ] Kontantmetoden |
+| Momsredovisningsperiod | [ ] Månadsvis [ ] Kvartalsvis [ ] Årsvis |
+| Ansvarig för bokföringen | [NAMN, ROLL] |
+
+## 2. Bokföringssystem
+
+| Fält | Uppgift |
+|---|---|
+| Programvara | erp-base ([DOMÄN]) |
+| Leverantör | [BOLAGSNAMN], org.nr [ORG-NR] |
+| Lagringsplats | Molnbaserad tjänst, data lagrat inom EU (Supabase/AWS) |
+| Åtkomst | Via webbläsare, inloggning med magic link (e-post) |
+| Kontoplan | BAS 2025/2026 (konfigurerad i erp-base) |
+
+## 3. Förteckning över räkenskapsinformation
+
+Tabellen nedan anger vilken räkenskapsinformation som finns, i vilken form den förvaras, var, och arkiveringstid.
+
+### 3.1 Löpande bokföring
+
+| Räkenskapsinformation | Form | Lagringsplats | Arkiveringstid |
+|---|---|---|---|
+| Grundbokföring (registreringsordning) | Elektronisk | erp-base databas | 7 år efter räkenskapsårets utgång |
+| Huvudbokföring (systematisk ordning) | Elektronisk | erp-base databas | 7 år efter räkenskapsårets utgång |
+| Verifikationer (journalposter) | Elektronisk | erp-base databas | 7 år efter räkenskapsårets utgång |
+
+### 3.2 Verifikationsunderlag
+
+| Räkenskapsinformation | Form | Lagringsplats | Arkiveringstid | Anmärkning |
+|---|---|---|---|---|
+| Kundfakturor (utgående) | Elektronisk (PDF) | erp-base dokumentarkiv | 7 år | Genereras i erp-base |
+| Leverantörsfakturor (inkommande) | Elektronisk (PDF/bild) | erp-base dokumentarkiv | 7 år | Uppladdade/skannade |
+| Kvitton | Elektronisk (foto/PDF) | erp-base dokumentarkiv | 7 år | Fotograferade via appen |
+| Bankutdrag/kontoutdrag | Elektronisk | erp-base via PSD2-koppling | 7 år | Synkroniserade via Enable Banking |
+| Avtal och övriga underlag | [Elektronisk/Papper] | [erp-base / Fysisk pärm] | 7 år | [Ange var dessa förvaras] |
+
+### 3.3 Årsbokslut och årsredovisning
+
+| Räkenskapsinformation | Form | Lagringsplats | Arkiveringstid |
+|---|---|---|---|
+| Resultaträkning | Elektronisk | erp-base rapportmodul | 7 år |
+| Balansräkning | Elektronisk | erp-base rapportmodul | 7 år |
+| Årsredovisning (AB) / Årsbokslut (EF) | [Elektronisk/Papper] | [erp-base / Bolagsverket / Fysisk pärm] | 7 år (10 år rekommenderat) |
+| NE-bilaga (EF) | Elektronisk | erp-base rapportmodul | 7 år |
+| SIE-filer (export) | Elektronisk | [Ange var exporterade filer sparas] | 7 år |
+
+### 3.4 Skattedeklarationer och momsrapporter
+
+| Räkenskapsinformation | Form | Lagringsplats | Arkiveringstid |
+|---|---|---|---|
+| Momsdeklarationer | Elektronisk | erp-base rapportmodul + Skatteverket | 7 år |
+| SRU-filer | Elektronisk | erp-base rapportmodul | 7 år |
+| Inkomstdeklaration | [Elektronisk/Papper] | [Skatteverket / Egen kopia] | 7 år |
+
+### 3.5 Systemdokumentation
+
+| Dokument | Form | Lagringsplats | Arkiveringstid |
+|---|---|---|---|
+| Systemdokumentation | Elektronisk | [erp-base / Egen lagring] | Samma som den räkenskapsinformation den avser |
+| Behandlingshistorik | Elektronisk | erp-base (automatiskt genererad) | Samma som den räkenskapsinformation den avser |
+| Denna arkivplan | [Elektronisk/Papper] | [Ange lagringsplats] | Samma som den räkenskapsinformation den avser |
+
+## 4. Pappersoriginal
+
+4.1. Räkenskapsinformation som tagits emot i pappersform (kvitton, fakturor) och som har överförts till elektronisk form genom skanning eller fotografering ska bevaras i sin ursprungliga pappersform i minst tre (3) år efter utgången av det kalenderår då räkenskapsåret avslutades, i enlighet med 7 kap. 6 § BFL.
+
+*Notering: Lagändring trädde i kraft 1 juli 2024 som möjliggör omedelbar förstöring av pappersoriginal efter överföring till elektronisk form, under förutsättning att överföringen sker på ett betryggande sätt och att inga uppgifter går förlorade. Se BFNAR 2024:1 och uppdaterad vägledning (2024-09-16) for detaljer om vilka krav som gäller vid sådan överföring.*
+
+4.2. Dokument som tas emot elektroniskt (e-fakturor, digitala kvitton) arkiveras i elektronisk form. Inget pappersoriginal finns.
+
+4.3. Förvaring av pappersoriginal:
+- Plats: [ANGE PLATS, t.ex. kontor, bankfack]
+- Ansvarig: [NAMN]
+
+## 5. Säkerhetskopiering och redundans
+
+5.1. erp-base sköter automatisk daglig säkerhetskopiering av databasen via Supabase-infrastrukturen.
+
+5.2. Kunden rekommenderas att regelbundet exportera SIE4-filer och spara dessa på en separat lagringsplats som kompletterande säkerhetskopia.
+
+Kundens kompletterande säkerhetskopiering:
+- Frekvens: [t.ex. månadsvis, kvartalsvis]
+- Lagringsplats: [t.ex. extern hårddisk, molnlagring]
+- Ansvarig: [NAMN]
+
+## 6. Åtkomst efter avslutad prenumeration
+
+6.1. Vid uppsägning av erp-base-kontot har Kunden nittio (90) dagar att exportera all räkenskapsinformation i enlighet med Användarvillkoren avsnitt 8.
+
+6.2. Räkenskapsinformation som omfattas av sjuårig arkiveringsskyldighet bevaras i skrivskyddat läge av erp-base, alternativt tillhandahålls som fullständig dataexport.
+
+6.3. Det är Kundens ansvar att planera för dataportabilitet och säkerställa tillgång till räkenskapsinformation under hela arkiveringsperioden, oavsett om Tjänsten fortfarande används.
+
+## 7. Geografisk lagring
+
+7.1. All data i erp-base lagras inom EU/EES via Supabase (AWS-infrastruktur, region eu-central eller eu-west).
+
+7.2. Viss behandling sker hos underbiträden i USA (se Personuppgiftsbiträdesavtalet, avsnitt 6.2) med stöd av EU-U.S. Data Privacy Framework eller standardavtalsklausuler.
+
+7.3. I enlighet med 7 kap. 3a § BFL får räkenskapsinformation i elektronisk form förvaras i annat EU-land under förutsättning att detta har anmälts till Skatteverket.
+
+**Anmälan till Skatteverket:** [ ] Har gjorts [ ] Behöver göras [ ] Ej tillämpligt (data lagras i Sverige)
+
+## 8. Ansvar och kontakt
+
+| Roll | Namn | Kontakt |
+|---|---|---|
+| Bokföringsansvarig | [NAMN] | [E-POST / TELEFON] |
+| Extern redovisningskonsult (om tillämpligt) | [NAMN / BYRÅ] | [E-POST / TELEFON] |
+| Revisor (om tillämpligt) | [NAMN / BYRÅ] | [E-POST / TELEFON] |
+
+## 9. Uppdatering av arkivplanen
+
+Denna arkivplan ska granskas och vid behov uppdateras minst en gång per räkenskapsår, samt vid byte av bokföringsprogram, ändring av företagsform, eller ändring av lagringsrutiner.
+
+| Datum | Ändring | Utförd av |
+|---|---|---|
+| [DATUM] | Första version upprättad | [NAMN] |
+| | | |
+
+---
+
+*Denna arkivplan uppfyller kraven i BFNAR 2013:2 punkt 8.3 och Exempel 8.1 i vägledningen. Anpassa innehållet till ditt företags specifika förhållanden. Platshållare markerade med hakparenteser ska fyllas i.*
diff --git a/public/docs/systemdokumentation-mall.md b/public/docs/systemdokumentation-mall.md
new file mode 100644
index 00000000..cbe0f1df
--- /dev/null
+++ b/public/docs/systemdokumentation-mall.md
@@ -0,0 +1,259 @@
+# Systemdokumentation
+
+**Mall for användare av erp-base**
+Upprättad i enlighet med 5 kap. 11 § BFL och BFNAR 2013:2 kapitel 9
+
+---
+
+## Instruktioner
+
+Varje bokföringsskyldig ska upprätta en systemdokumentation som beskriver bokföringssystemets organisation och uppbyggnad. Dokumentationen ska göra det möjligt att utan svårighet överblicka systemet och förstå hur bokföringen är organiserad (BFNAR 2013:2 punkt 9.1).
+
+Denna mall är förifylld med uppgifter som gäller för erp-base. Avsnitt markerade med hakparenteser ska anpassas till ditt företags förhållanden. Radera denna instruktionssektion innan du arkiverar dokumentet.
+
+Systemdokumentationen ska förvaras tillsammans med övrig räkenskapsinformation under hela arkiveringsperioden (7 år).
+
+---
+
+## 1. Företagsuppgifter
+
+| Fält | Uppgift |
+|---|---|
+| Företagsnamn | [FÖRETAGSNAMN] |
+| Organisationsnummer | [ORG-NR] |
+| Företagsform | [ ] Enskild firma [ ] Aktiebolag |
+| Räkenskapsår | [STARTMÅNAD] - [SLUTMÅNAD] |
+| Tillämpat K-regelverk | [ ] K1 (förenklat årsbokslut, EF under 3 MSEK) [ ] K2 (årsredovisning, mindre AB) [ ] K3 (årsredovisning, huvudregelverk) |
+
+## 2. Bokföringsprogram
+
+| Fält | Uppgift |
+|---|---|
+| Programnamn | erp-base |
+| Version | [ANGE VERSION, t.ex. 1.0] |
+| Leverantör | [BOLAGSNAMN], org.nr [ORG-NR] |
+| Webbplats | [DOMÄN] |
+| Typ | Molnbaserad SaaS-tjänst (webbläsarbaserad) |
+| Databasplattform | PostgreSQL via Supabase (AWS, EU-region) |
+| Autentisering | Magic link via e-post (lösenordsfri) |
+
+## 3. Kontoplan (BFNAR 2013:2 punkt 9.2)
+
+3.1. Kontoplanen bygger på BAS-kontoplanen (BAS 2025/2026) utgiven av BAS-intressenternas Förening.
+
+3.2. Kontona är indelade i klasser enligt BAS-standard:
+
+| Klass | Beskrivning | Exempel på konton |
+|---|---|---|
+| 1 | Tillgångar | 1510 Kundfordringar, 1930 Företagskonto |
+| 2 | Eget kapital och skulder | 2013 Egna uttag (EF), 2440 Leverantörsskulder, 2611-2631 Utgående moms, 2641 Ingående moms |
+| 3 | Intäkter | 3001 Försäljning 25%, 3002 Försäljning 12%, 3003 Försäljning 6%, 3305 Exportförsäljning |
+| 4-7 | Kostnader | Konfigureras efter verksamhet |
+| 8 | Finansiella poster och skatt | Konfigureras efter verksamhet |
+
+3.3. Kontoplanen kan ses och exporteras i erp-base under Inställningar > Kontoplan.
+
+3.4. Företagsspecifika anpassningar av kontoplanen:
+[BESKRIV EVENTUELLA TILLAGDA ELLER BORTTAGNA KONTON, t.ex. "Konto 4010 Inköp varor, 5010 Lokalhyra har lagts till. Inga standardkonton har tagits bort."]
+
+## 4. Samlingsplan (BFNAR 2013:2 punkt 9.3-9.5)
+
+Samlingsplanen beskriver hur bokföringen är organiserad i form av delsystem, grundbokföring och huvudbokföring.
+
+### 4.1 Översikt
+
+```
+Affärshändelse
+ |
+ v
+Verifikation skapas (manuellt eller automatiskt)
+ |
+ v
+Journalpost registreras (grundbokföring, registreringsordning)
+ |
+ v
+Konteras på BAS-konton (huvudbokföring, systematisk ordning)
+ |
+ v
+Status: Utkast (draft)
+ |
+ v
+Bekräftas av användaren
+ |
+ v
+Status: Bokförd (posted), verifikationsnummer tilldelas
+```
+
+### 4.2 Grundbokföring (registreringsordning)
+
+Samtliga affärshändelser registreras kronologiskt i erp-base journalen. Varje post innehåller:
+- Verifikationsnummer (sekventiellt, tilldelat automatiskt vid bokföring)
+- Registreringsdatum (datum då posten skapades i systemet)
+- Bokföringsdatum (datum för affärshändelsen)
+- Beskrivning
+- Konteringsrader med konto, debet, kredit
+
+Grundbokföringen kan visas under Bokföring > Journal i erp-base.
+
+### 4.3 Huvudbokföring (systematisk ordning)
+
+Huvudbokföringen presenterar affärshändelserna sorterade per konto. Varje konto visar ingående saldo, periodens transaktioner och utgående saldo.
+
+Huvudbokföringen kan visas och exporteras under Rapporter > Huvudbok i erp-base.
+
+### 4.4 Delsystem
+
+Följande delsystem matar journalen:
+
+| Delsystem | Beskrivning | Automatisk kontering |
+|---|---|---|
+| Kundfakturering | Utgående fakturor med per-rad momssats | Debet 1510, kredit 30xx + 26xx |
+| Kundbetalningar | Inbetalningar mot fakturor | Debet 1930, kredit 1510 |
+| Leverantörsfakturor | Inkommande fakturor, registrering och betalning | Debet kostnadskonto + 2641, kredit 2440 |
+| Leverantörsbetalningar | Utbetalningar mot leverantörsfakturor | Debet 2440, kredit 1930 |
+| Banktransaktioner | Synkroniserade via PSD2 (Enable Banking) | Kontering via kategoriseringsregler |
+| Kvittohantering | OCR-bearbetade kvitton | Kontering efter granskning |
+| Kreditnotor | Kreditering av utgående fakturor | Omvänd kontering av originalfaktura |
+
+### 4.5 Avstämningsordning
+
+Bankkonto 1930 avstäms via erp-base bankavstämningsmodul (4-stegs matchning: exakt belopp+datum, referensmatchning, datumintervall, fuzzy-matchning).
+
+## 5. Verifikationer (BFNAR 2013:2 punkt 9.6-9.8)
+
+### 5.1 Verifikationsnumrering
+
+Verifikationsnummer tilldelas sekventiellt av systemet vid bokföring. Numreringen är unik per räkenskapsår och användare. Numren tilldelas via databas-RPC (concurrent-safe) och kan inte sättas manuellt.
+
+En enda verifikationsnummerserie används: [A1, A2, A3, ...].
+
+[OM FÖRETAGET ANVÄNDER FLERA SERIER, BESKRIV HÄR.]
+
+### 5.2 Verifikationens innehåll
+
+Varje verifikation i erp-base innehåller:
+- Verifikationsnummer
+- Bokföringsdatum (affärshändelsens datum)
+- Registreringsdatum (datum då posten skapades)
+- Beskrivning av affärshändelsen
+- Konteringsrader (konto, debet, kredit)
+- Referens till underlag (bifogat dokument, fakturanummer, etc.)
+- Status (utkast / bokförd / reverserad)
+- Vid rättelse: referens till reverserad/reverserande verifikation
+
+### 5.3 Underlag
+
+Underlag kopplas till verifikationer som bifogade dokument (PDF, bild). Dokumenten lagras i erp-base dokumentarkiv med SHA-256 checksumma for integritetskontroll.
+
+Typer av underlag:
+- Kundfakturor (genererade i systemet)
+- Leverantörsfakturor (uppladdade)
+- Kvitton (fotograferade/skannade)
+- Bankbekräftelser (synkroniserade)
+- Övriga avtal och dokument (uppladdade)
+
+## 6. Rättelser (BFNAR 2013:2 punkt 9.9)
+
+6.1. Bokförda verifikationer (status: posted) kan inte ändras eller raderas. Detta upprätthålls av databastriggrar i enlighet med bokföringslagens krav på oföränderlighet.
+
+6.2. Rättelse sker genom stornobokning: en ny verifikation skapas som reverserar den felaktiga posten (byter debet/kredit). Den nya verifikationen länkas till originalet via referens (reverses_id / reversed_by_id).
+
+6.3. Därefter skapas en ny korrekt verifikation vid behov.
+
+6.4. Rättelseverifikationen innehåller uppgift om vilken verifikation som rättats, när rättelsen gjordes, och vem som utförde rättelsen (BFNAR 2013:2 punkt 2.17).
+
+## 7. Periodavstängning
+
+7.1. Räkenskapsperioder kan stängas (låsas) i erp-base. En låst period tillåter inte nya bokföringsposter. Periodlåsning upprätthålls av databastriggrar (enforce_period_lock).
+
+7.2. Årsbokslut registreras som bokföringsposter i systemet.
+
+## 8. Momshantering
+
+8.1. Följande momssatser hanteras:
+
+| Momssats | Beskrivning | Utgående moms-konto | Ingående moms-konto |
+|---|---|---|---|
+| 25 % | Standardsats | 2611 | 2641 |
+| 12 % | Reducerad (livsmedel, hotell m.m.) | 2621 | 2641 |
+| 6 % | Reducerad (böcker, tidningar, kultur m.m.) | 2631 | 2641 |
+| 0 % (export) | Varuexport utanför EU | - | 2641 |
+| 0 % (omvänd skattskyldighet) | Försäljning med omvänd skattskyldighet | - | 2641/2645 |
+| Momsfri | Undantagna transaktioner | - | - |
+
+*Notering: Livsmedel sänks till 6 % från 1 april 2026 t.o.m. 31 december 2027.*
+
+8.2. Fakturor stödjer blandade momssatser (per fakturarad).
+
+8.3. Momsrapport genereras under Rapporter > Momsdeklaration och mappas till Skatteverkets rutor.
+
+## 9. Behandlingshistorik (BFNAR 2013:2 punkt 9.16)
+
+9.1. erp-base registrerar automatiskt en behandlingshistorik som inkluderar:
+- Registreringsdatum och tidpunkt for varje journalpost
+- Tidpunkt för statusändring (utkast till bokförd)
+- Vem som utförde bokningen (användar-ID kopplat till e-postadress)
+- Stornobokningar med referens till originalverifikation
+- Tidpunkt och utförare av periodlåsning
+
+9.2. Behandlingshistoriken genereras automatiskt av systemet och kan inte ändras av användaren.
+
+9.3. Behandlingshistoriken kan exporteras under Rapporter > Audit trail.
+
+## 10. Import och export
+
+| Funktion | Format | Beskrivning |
+|---|---|---|
+| SIE-import | SIE4 | Import av bokföringsdata från annat system |
+| Bankfil-import | CSV (10 svenska bankformat) | Import av banktransaktioner |
+| SIE-export | SIE4 | Export av komplett bokföring per räkenskapsår |
+| Huvudbok | PDF/skärm | Export av huvudbok |
+| Resultaträkning | PDF/skärm | Export av resultaträkning |
+| Balansräkning | PDF/skärm | Export av balansräkning |
+| Momsdeklaration | PDF/skärm | Underlag för momsdeklaration |
+| SRU-export | SRU | Export for inkomstdeklaration |
+| NE-bilaga | PDF/skärm | Bilaga till inkomstdeklaration (EF) |
+| Verifikationsunderlag | PDF/bild | Nedladdning av bifogade dokument |
+
+## 11. Integrationer
+
+| Integration | Beskrivning | Dataflöde |
+|---|---|---|
+| Enable Banking (PSD2) | Bankkontosynkronisering | Bank -> erp-base (läsning av transaktioner och saldon) |
+| Anthropic API | AI-kategorisering av transaktioner, OCR | erp-base -> Anthropic -> erp-base (transaktionsdata skickas, kategoriseringsförslag returneras) |
+| OpenAI API | Embeddingar for likhetsmatchning | erp-base -> OpenAI -> erp-base (transaktionsbeskrivningar skickas, vektorer returneras) |
+| Resend | E-postutskick | erp-base -> Resend -> mottagare (fakturor, påminnelser) |
+
+[ANGE YTTERLIGARE INTEGRATIONER OM TILLÄMPLIGT]
+
+## 12. Behörigheter och åtkomstkontroll
+
+12.1. Varje konto i erp-base är isolerat via Row Level Security (RLS) i databasen. En användare kan enbart se och redigera sin egen data.
+
+12.2. Nuvarande behörighetsstruktur:
+
+| Roll | Beskrivning |
+|---|---|
+| Kontoägare | Full åtkomst till all data och funktionalitet |
+
+[OM YTTERLIGARE ROLLER FINNS, BESKRIV HÄR]
+
+12.3. Ansvarig for att tilldela och granska behörigheter: [NAMN]
+
+## 13. Uppdatering av systemdokumentationen
+
+Systemdokumentationen ska uppdateras vid:
+- Byte eller uppgradering av bokföringsprogram
+- Ändringar i kontoplan
+- Ändringar i momshantering
+- Nya integrationer eller delsystem
+- Minst en gång per räkenskapsår
+
+| Datum | Ändring | Utförd av |
+|---|---|---|
+| [DATUM] | Första version upprättad | [NAMN] |
+| | | |
+
+---
+
+*Denna systemdokumentation uppfyller kraven i 5 kap. 11 § BFL och BFNAR 2013:2 kapitel 9 (punkterna 9.1-9.16) samt Exempel 9.1-9.4 i vägledningen. Anpassa innehållet till ditt företags specifika förhållanden.*
diff --git a/public/gnubokiceon-removebg-preview.png b/public/gnubokiceon-removebg-preview.png
new file mode 100644
index 00000000..9126809b
Binary files /dev/null and b/public/gnubokiceon-removebg-preview.png differ