Skip to content

Commit

Permalink
♻️ (typescript) migrate parts of ImportTransactionModal to TS (#3570)
Browse files Browse the repository at this point in the history
  • Loading branch information
MatissJanis authored Oct 9, 2024
1 parent 79f640c commit 23de23b
Show file tree
Hide file tree
Showing 15 changed files with 260 additions and 87 deletions.
4 changes: 3 additions & 1 deletion packages/desktop-client/src/components/forms.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -64,7 +64,9 @@ export const FormField = ({ style, children }: FormFieldProps) => {

// Custom inputs

type CheckboxProps = ComponentProps<'input'>;
type CheckboxProps = ComponentProps<'input'> & {
style?: CSSProperties;
};

export const Checkbox = (props: CheckboxProps) => {
return (
Expand Down
Original file line number Diff line number Diff line change
@@ -1,17 +1,26 @@
import React from 'react';
import React, { type ComponentProps, type ReactNode } from 'react';

import { theme } from '../../../style';
import { type CSSProperties, theme } from '../../../style';
import { View } from '../../common/View';
import { Checkbox } from '../../forms';

type CheckboxOptionProps = {
id: string;
checked?: ComponentProps<typeof Checkbox>['checked'];
disabled?: ComponentProps<typeof Checkbox>['disabled'];
onChange?: ComponentProps<typeof Checkbox>['onChange'];
children: ReactNode;
style?: CSSProperties;
};

export function CheckboxOption({
id,
checked,
disabled,
onChange,
children,
style,
}) {
}: CheckboxOptionProps) {
return (
<View
style={{
Expand All @@ -33,7 +42,7 @@ export function CheckboxOption({
htmlFor={id}
style={{
userSelect: 'none',
color: disabled ? theme.pageTextSubdued : null,
color: disabled ? theme.pageTextSubdued : undefined,
}}
>
{children}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,14 +4,25 @@ import { Select } from '../../common/Select';
import { View } from '../../common/View';
import { SectionLabel } from '../../forms';

import { dateFormats } from './utils';
import {
dateFormats,
type ImportTransaction,
type FieldMapping,
} from './utils';

type DateFormatSelectProps = {
transactions: ImportTransaction[];
fieldMappings: FieldMapping;
parseDateFormat?: string;
onChange: (newValue: string) => void;
};

export function DateFormatSelect({
transactions,
fieldMappings,
parseDateFormat,
onChange,
}) {
}: DateFormatSelectProps) {
// We don't actually care about the delimiter, but we try to render
// it based on the data we have so far. Look in a transaction and
// try to figure out what delimiter the date is using, and default
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,23 +6,44 @@ import { SectionLabel } from '../../forms';

import { SelectField } from './SelectField';
import { SubLabel } from './SubLabel';
import { stripCsvImportTransaction } from './utils';
import {
stripCsvImportTransaction,
type FieldMapping,
type ImportTransaction,
} from './utils';

type FieldMappingsProps = {
transactions: ImportTransaction[];
mappings?: FieldMapping;
onChange: (field: keyof FieldMapping, newValue: string) => void;
splitMode: boolean;
inOutMode: boolean;
hasHeaderRow: boolean;
};

export function FieldMappings({
transactions,
mappings,
mappings = {
date: null,
amount: null,
payee: null,
notes: null,
inOut: null,
category: null,
outflow: null,
inflow: null,
},
onChange,
splitMode,
inOutMode,
hasHeaderRow,
}) {
}: FieldMappingsProps) {
if (transactions.length === 0) {
return null;
}

const trans = stripCsvImportTransaction(transactions[0]);
const options = Object.keys(trans);
mappings = mappings || {};

return (
<View>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,13 +5,21 @@ import { View } from '../../common/View';

import { CheckboxOption } from './CheckboxOption';

type InOutOptionProps = {
inOutMode: boolean;
outValue: string;
disabled: boolean;
onToggle: () => void;
onChangeText: (newValue: string) => void;
};

export function InOutOption({
inOutMode,
outValue,
disabled,
onToggle,
onChangeText,
}) {
}: InOutOptionProps) {
return (
<View style={{ flexDirection: 'row', gap: 10, height: 28 }}>
<CheckboxOption
Expand Down
Original file line number Diff line number Diff line change
@@ -1,16 +1,23 @@
import React from 'react';
import React, { type ComponentProps } from 'react';

import { Input } from '../../common/Input';
import { View } from '../../common/View';

import { CheckboxOption } from './CheckboxOption';

type MultiplierOptionProps = {
multiplierEnabled: boolean;
multiplierAmount: string;
onToggle: ComponentProps<typeof CheckboxOption>['onChange'];
onChangeAmount: (newValue: string) => void;
};

export function MultiplierOption({
multiplierEnabled,
multiplierAmount,
onToggle,
onChangeAmount,
}) {
}: MultiplierOptionProps) {
return (
<View style={{ flexDirection: 'row', gap: 10, height: 28 }}>
<CheckboxOption
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,17 @@ import { Text } from '../../common/Text';

import { formatDate, parseDate } from './utils';

export function ParsedDate({ parseDateFormat, dateFormat, date }) {
type ParsedDateProps = {
parseDateFormat?: Parameters<typeof parseDate>[1];
dateFormat: Parameters<typeof parseDate>[1];
date?: string;
};

export function ParsedDate({
parseDateFormat,
dateFormat,
date,
}: ParsedDateProps) {
const parsed =
date &&
formatDate(
Expand Down

This file was deleted.

Original file line number Diff line number Diff line change
@@ -0,0 +1,42 @@
import React from 'react';

import { type CSSProperties } from '../../../style';
import { Select } from '../../common/Select';

type SelectFieldProps = {
style?: CSSProperties;
options: string[];
value: null | string;
onChange: (newValue: string) => void;
hasHeaderRow: boolean;
firstTransaction: Record<string, unknown>;
};

export function SelectField({
style,
options,
value,
onChange,
hasHeaderRow,
firstTransaction,
}: SelectFieldProps) {
return (
<Select
options={[
['choose-field', 'Choose field...'],
...options.map(
option =>
[
option,
hasHeaderRow
? option
: `Column ${parseInt(option) + 1} (${firstTransaction[option]})`,
] as const,
),
]}
value={value === null ? 'choose-field' : value}
onChange={onChange}
style={style}
/>
);
}
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,11 @@ import React from 'react';
import { theme } from '../../../style';
import { Text } from '../../common/Text';

export function SubLabel({ title }) {
type SubLabelProps = {
title: string;
};

export function SubLabel({ title }: SubLabelProps) {
return (
<Text style={{ fontSize: 13, marginBottom: 3, color: theme.pageText }}>
{title}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import React, { useMemo } from 'react';
import React, { type ComponentProps, useMemo } from 'react';

import { amountToCurrency } from 'loot-core/src/shared/util';
import { type CategoryEntity } from 'loot-core/types/models';

import { SvgDownAndRightArrow } from '../../../icons/v2';
import { theme, styles } from '../../../style';
Expand All @@ -11,7 +12,29 @@ import { Checkbox } from '../../forms';
import { Row, Field } from '../../table';

import { ParsedDate } from './ParsedDate';
import { applyFieldMappings, formatDate, parseAmountFields } from './utils';
import {
applyFieldMappings,
type FieldMapping,
formatDate,
type ImportTransaction,
parseAmountFields,
} from './utils';

type TransactionProps = {
transaction: ImportTransaction;
fieldMappings: FieldMapping;
showParsed: boolean;
parseDateFormat: ComponentProps<typeof ParsedDate>['parseDateFormat'];
dateFormat: ComponentProps<typeof ParsedDate>['dateFormat'];
splitMode: boolean;
inOutMode: boolean;
outValue: number;
flipAmount: boolean;
multiplierAmount: string;
categories: CategoryEntity[];
onCheckTransaction: (transactionId: string) => void;
reconcile: boolean;
};

export function Transaction({
transaction: rawTransaction,
Expand All @@ -27,7 +50,7 @@ export function Transaction({
categories,
onCheckTransaction,
reconcile,
}) {
}: TransactionProps) {
const categoryList = categories.map(category => category.name);
const transaction = useMemo(
() =>
Expand All @@ -37,23 +60,34 @@ export function Transaction({
[rawTransaction, fieldMappings],
);

let amount, outflow, inflow;
if (rawTransaction.isMatchedTransaction) {
amount = rawTransaction.amount;
if (splitMode) {
outflow = amount < 0 ? -amount : 0;
inflow = amount > 0 ? amount : 0;
const { amount, outflow, inflow } = useMemo(() => {
if (rawTransaction.isMatchedTransaction) {
const amount = rawTransaction.amount;

return {
amount,
outflow: splitMode ? (amount < 0 ? -amount : 0) : null,
inflow: splitMode ? (amount > 0 ? amount : 0) : null,
};
}
} else {
({ amount, outflow, inflow } = parseAmountFields(

return parseAmountFields(
transaction,
splitMode,
inOutMode,
outValue,
flipAmount,
multiplierAmount,
));
}
);
}, [
rawTransaction,
transaction,
splitMode,
inOutMode,
outValue,
flipAmount,
multiplierAmount,
]);

return (
<Row
Expand Down Expand Up @@ -214,7 +248,11 @@ export function Transaction({
<Field
width={90}
contentStyle={{ textAlign: 'left', ...styles.tnum }}
title={transaction.inOut}
title={
transaction.inOut === undefined
? undefined
: String(transaction.inOut)
}
>
{transaction.inOut}
</Field>
Expand Down
Loading

0 comments on commit 23de23b

Please sign in to comment.