export type Subscription = { [key: string]: boolean } export type Subscriber = (value: V) => void export type IsEqual = (a: any, b: any) => boolean export interface AnyObject { [key: string]: any } export interface ValidationErrors extends AnyObject {} export interface SubmissionErrors extends AnyObject {} export interface FormSubscription { active?: boolean dirty?: boolean dirtyFields?: boolean dirtyFieldsSinceLastSubmit?: boolean dirtySinceLastSubmit?: boolean error?: boolean errors?: boolean hasSubmitErrors?: boolean hasValidationErrors?: boolean initialValues?: boolean invalid?: boolean modified?: boolean pristine?: boolean submitError?: boolean submitErrors?: boolean submitFailed?: boolean submitting?: boolean submitSucceeded?: boolean touched?: boolean valid?: boolean validating?: boolean values?: boolean visited?: boolean } export interface FormState { // by default: all values are subscribed. if subscription is specified, some values may be undefined active: undefined | string dirty: boolean dirtyFields: { [key: string]: boolean } dirtyFieldsSinceLastSubmit: { [key: string]: boolean } dirtySinceLastSubmit: boolean error: any errors: ValidationErrors hasSubmitErrors: boolean hasValidationErrors: boolean initialValues: FormValues invalid: boolean modified?: { [key: string]: boolean } pristine: boolean submitError: any submitErrors: SubmissionErrors submitFailed: boolean submitSucceeded: boolean submitting: boolean touched?: { [key: string]: boolean } valid: boolean validating: boolean values: FormValues visited?: { [key: string]: boolean } } export type FormSubscriber = Subscriber> export interface FieldState { active?: boolean blur: () => void change: (value: any) => void data?: AnyObject dirty?: boolean dirtySinceLastSubmit?: boolean error?: any focus: () => void initial?: FieldValue invalid?: boolean length?: number modified?: boolean name: string pristine?: boolean submitError?: any submitFailed?: boolean submitSucceeded?: boolean submitting?: boolean touched?: boolean valid?: boolean validating?: boolean value?: FieldValue visited?: boolean } export interface FieldSubscription { active?: boolean data?: boolean dirty?: boolean dirtySinceLastSubmit?: boolean error?: boolean initial?: boolean invalid?: boolean length?: boolean modified?: boolean pristine?: boolean submitError?: boolean submitFailed?: boolean submitSucceeded?: boolean submitting?: boolean touched?: boolean valid?: boolean validating?: boolean value?: boolean visited?: boolean } export type FieldSubscriber = Subscriber> export type Subscribers = { index: number entries: { [key: number]: { subscriber: Subscriber subscription: Subscription notified: boolean } } } export type Unsubscribe = () => void type FieldValidator = ( value: FieldValue, allValues: object, meta?: FieldState ) => any | Promise type GetFieldValidator = () => | FieldValidator | undefined export interface FieldConfig { afterSubmit?: () => void beforeSubmit?: () => void | false data?: any defaultValue?: any getValidator?: GetFieldValidator initialValue?: any isEqual?: IsEqual validateFields?: string[] } export type RegisterField = ( name: string, subscriber: FieldSubscriber, subscription: FieldSubscription, config?: FieldConfig ) => Unsubscribe export interface InternalFieldState { active: boolean blur: () => void change: (value: any) => void data: AnyObject focus: () => void isEqual: IsEqual lastFieldState?: FieldState length?: any modified: boolean name: string touched: boolean validateFields?: string[] validators: { [index: number]: GetFieldValidator } valid: boolean validating: boolean visited: boolean } export interface InternalFormState { active?: string dirtySinceLastSubmit: boolean error?: any errors: ValidationErrors initialValues?: object lastSubmittedValues?: object pristine: boolean submitError?: any submitErrors?: object submitFailed: boolean submitSucceeded: boolean submitting: boolean valid: boolean validating: number values: object } type ConfigKey = keyof Config export interface FormApi { batch: (fn: () => void) => void blur: (name: string) => void change: (name: string, value?: any) => void destroyOnUnregister: boolean focus: (name: string) => void initialize: (data: FormValues | ((values: FormValues) => FormValues)) => void isValidationPaused: () => boolean getFieldState: (field: string) => FieldState | undefined getRegisteredFields: () => string[] getState: () => FormState mutators: { [key: string]: (...args: any[]) => any } pauseValidation: () => void registerField: RegisterField reset: (initialValues?: object) => void resetFieldState: (name: string) => void resumeValidation: () => void setConfig: ( name: K, value: Config[K] ) => void submit: () => Promise | undefined subscribe: ( subscriber: FormSubscriber, subscription: FormSubscription ) => Unsubscribe } export type DebugFunction = ( state: FormState, fieldStates: { [key: string]: FieldState } ) => void export interface MutableState { fieldSubscribers: { [key: string]: Subscribers> } fields: { [key: string]: InternalFieldState } formState: InternalFormState lastFormState?: FormState } export type GetIn = (state: object, complexKey: string) => any export type SetIn = (state: object, key: string, value: any) => object export type ChangeValue = ( state: MutableState, name: string, mutate: (value: any) => any ) => void export type RenameField = ( state: MutableState, from: string, to: string ) => void export interface Tools { changeValue: ChangeValue getIn: GetIn renameField: RenameField resetFieldState: (name: string) => void setIn: SetIn shallowEqual: IsEqual } export type Mutator = ( args: any, state: MutableState, tools: Tools ) => any export interface Config { debug?: DebugFunction destroyOnUnregister?: boolean initialValues?: FormValues keepDirtyOnReinitialize?: boolean mutators?: { [key: string]: Mutator } onSubmit: ( values: FormValues, form: FormApi, callback?: (errors?: SubmissionErrors) => void ) => | SubmissionErrors | Promise | undefined | void validate?: ( values: FormValues ) => ValidationErrors | Promise | undefined validateOnBlur?: boolean } export type Decorator = ( form: FormApi ) => Unsubscribe export function createForm( config: Config ): FormApi export const fieldSubscriptionItems: string[] export const formSubscriptionItems: string[] export const ARRAY_ERROR: 'FINAL_FORM/array-error' export const FORM_ERROR: 'FINAL_FORM/form-error' export function getIn(state: object, complexKey: string): any export function setIn(state: object, key: string, value: any): object export const version: string export const configOptions: ConfigKey[]