Skip to content

Commit 537294e

Browse files
refactor
1 parent 445e26b commit 537294e

12 files changed

+566
-524
lines changed

example/lib/password_benchmark.dart

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import 'package:benchmark_harness/benchmark_harness.dart';
22
import 'package:form_builder_validators/form_builder_validators.dart';
3-
import 'package:form_builder_validators/new_api_prototype.dart'
3+
import 'package:form_builder_validators/new_api_prototype/new_api_prototype.dart'
44
show isReq, password;
55

66
import 'package:flutter/material.dart';

lib/form_builder_validators.dart

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -31,7 +31,7 @@ export 'localization/intl/messages_tr.dart';
3131
export 'localization/intl/messages_uk.dart';
3232
export 'localization/intl/messages_zh.dart';
3333
export 'localization/l10n.dart';
34-
export 'new_api_prototype.dart'; // This is the new api prototype
34+
export 'new_api_prototype/new_api_prototype.dart'; // This is the new api prototype
3535
export 'src/base_validator.dart';
3636
export 'src/bool/bool.dart';
3737
export 'src/collection/collection.dart';
Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
import '../localization/l10n.dart';
2+
import 'constants.dart';
3+
4+
Validator<T> minLength<T extends Object>(int minLength,
5+
{String Function(int)? minLengthMsg}) {
6+
return (value) {
7+
// I think it makes more sense to say that scalar objects has length 1 instead of 0.
8+
int valueLength = 1;
9+
10+
if (value is String) valueLength = value.length;
11+
if (value is Iterable) valueLength = value.length;
12+
if (value is Map) valueLength = value.length;
13+
14+
return valueLength < minLength
15+
? minLengthMsg?.call(minLength) ??
16+
FormBuilderLocalizations.current.minLengthErrorText(minLength)
17+
: null;
18+
};
19+
}
20+
21+
Validator<T> maxLength<T extends Object>(int maxLength,
22+
{String Function(int)? maxLengthMsg}) {
23+
return (value) {
24+
// I think it makes more sense to say that scalar objects has length 1 instead of 0.
25+
int valueLength = 1;
26+
27+
if (value is String) valueLength = value.length;
28+
if (value is Iterable) valueLength = value.length;
29+
if (value is Map) valueLength = value.length;
30+
31+
return valueLength > maxLength
32+
? maxLengthMsg?.call(maxLength) ??
33+
FormBuilderLocalizations.current.maxLengthErrorText(maxLength)
34+
: null;
35+
};
36+
}
Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
// Composition validators
2+
import 'constants.dart';
3+
4+
Validator<T> and<T extends Object>(
5+
List<Validator<T>> validators, {
6+
bool printErrorAsSoonAsPossible = true,
7+
}) {
8+
return (T value) {
9+
final errorMessageBuilder = <String>[];
10+
for (final validator in validators) {
11+
final errorMessage = validator(value);
12+
if (errorMessage != null) {
13+
if (printErrorAsSoonAsPossible) {
14+
return errorMessage;
15+
}
16+
errorMessageBuilder.add(errorMessage);
17+
}
18+
}
19+
if (errorMessageBuilder.isNotEmpty) {
20+
return errorMessageBuilder.join(' AND ');
21+
}
22+
23+
return null;
24+
};
25+
}
26+
27+
Validator<T> or<T extends Object>(List<Validator<T>> validators) {
28+
return (T value) {
29+
final errorMessageBuilder = <String>[];
30+
for (final validator in validators) {
31+
final errorMessage = validator(value);
32+
if (errorMessage == null) {
33+
return null;
34+
}
35+
errorMessageBuilder.add(errorMessage);
36+
}
37+
return errorMessageBuilder.join(' OR ');
38+
};
39+
}
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
typedef Validator<T extends Object?> = String? Function(T);
Lines changed: 120 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,120 @@
1+
import '../localization/l10n.dart';
2+
import 'constants.dart';
3+
4+
Validator<T> containsElement<T extends Object>(
5+
List<T> values, {
6+
String? containsElementMsg,
7+
}) {
8+
return (T value) {
9+
return values.contains(value)
10+
? null
11+
: containsElementMsg ??
12+
FormBuilderLocalizations.current.containsElementErrorText;
13+
};
14+
}
15+
16+
Validator<T> isEqual<T extends Object?>(T value,
17+
{String Function(String)? equalMsg}) {
18+
return (input) {
19+
final valueString = value.toString();
20+
return value == input
21+
? null
22+
: equalMsg?.call(valueString) ??
23+
FormBuilderLocalizations.current.equalErrorText(valueString);
24+
};
25+
}
26+
27+
/// Returns a [Validator] function that checks if its `T` input is a `true`
28+
/// boolean or a [String] parsable to a `true` boolean. If the input satisfies
29+
/// this condition, the validator returns `null`. Otherwise, it returns the
30+
/// default error message
31+
/// `FormBuilderLocalizations.current.mustBeTrueErrorText`, if [isTrueMsg]
32+
/// is not provided.
33+
///
34+
/// # Parsing rules
35+
/// If the input of the validator is a [String], it will be parsed using
36+
/// the rules specified by the combination of [caseSensitive] and [trim].
37+
/// [caseSensitive] indicates whether the lowercase must be considered equal to
38+
/// uppercase or not, and [trim] indicates whether whitespaces from both sides
39+
/// of the string will be ignored or not.
40+
///
41+
/// The default behavior is to ignore leading and trailing whitespaces and be
42+
/// case insensitive.
43+
///
44+
/// # Examples
45+
/// ```dart
46+
/// // The following examples must pass:
47+
/// assert(isTrue()(' true ') == null);
48+
/// assert(isTrue(trim:false)(' true ') != null);
49+
/// assert(isTrue()('TRue') == null);
50+
/// assert(isTrue(caseSensitive:true)('TRue') != null);
51+
/// ```
52+
Validator<T> isTrue<T extends Object>(
53+
{String? isTrueMsg, bool caseSensitive = false, bool trim = true}) {
54+
return (value) {
55+
final (isValid, typeTransformedValue) = _isBoolValidateAndConvert(
56+
value,
57+
caseSensitive: caseSensitive,
58+
trim: trim,
59+
);
60+
if (isValid && typeTransformedValue! == true) {
61+
return null;
62+
}
63+
return isTrueMsg ?? FormBuilderLocalizations.current.mustBeTrueErrorText;
64+
};
65+
}
66+
67+
/// Returns a [Validator] function that checks if its `T` input is a `false`
68+
/// boolean or a [String] parsable to a `false` boolean. If the input satisfies
69+
/// this condition, the validator returns `null`. Otherwise, it returns the
70+
/// default error message
71+
/// `FormBuilderLocalizations.current.mustBeFalseErrorText`, if [isFalseMsg]
72+
/// is not provided.
73+
///
74+
/// # Parsing rules
75+
/// If the input of the validator is a [String], it will be parsed using
76+
/// the rules specified by the combination of [caseSensitive] and [trim].
77+
/// [caseSensitive] indicates whether the lowercase must be considered equal to
78+
/// uppercase or not, and [trim] indicates whether whitespaces from both sides
79+
/// of the string will be ignored or not.
80+
///
81+
/// The default behavior is to ignore leading and trailing whitespaces and be
82+
/// case insensitive.
83+
///
84+
/// # Examples
85+
/// ```dart
86+
/// // The following examples must pass:
87+
/// assert(isFalse()(' false ') == null);
88+
/// assert(isFalse(trim:false)(' false ') != null);
89+
/// assert(isFalse()('FAlse') == null);
90+
/// assert(isFalse(caseSensitive:true)('FAlse') != null);
91+
/// ```
92+
Validator<T> isFalse<T extends Object>(
93+
{String? isFalseMsg, bool caseSensitive = false, bool trim = true}) {
94+
return (value) {
95+
final (isValid, typeTransformedValue) = _isBoolValidateAndConvert(
96+
value,
97+
caseSensitive: caseSensitive,
98+
trim: trim,
99+
);
100+
if (isValid && typeTransformedValue! == false) {
101+
return null;
102+
}
103+
return isFalseMsg ?? FormBuilderLocalizations.current.mustBeFalseErrorText;
104+
};
105+
}
106+
107+
(bool, bool?) _isBoolValidateAndConvert<T extends Object>(T value,
108+
{bool caseSensitive = false, bool trim = true}) {
109+
if (value is bool) {
110+
return (true, value);
111+
}
112+
if (value is String) {
113+
final bool? candidateValue = bool.tryParse(trim ? value.trim() : value,
114+
caseSensitive: caseSensitive);
115+
if (candidateValue != null) {
116+
return (true, candidateValue);
117+
}
118+
}
119+
return (false, null);
120+
}
Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,8 @@
1+
export 'composition_validators.dart';
2+
export 'constants.dart';
3+
export 'generic_type_validators.dart';
4+
export 'numeric_validators.dart';
5+
export 'override_error_msg.dart';
6+
export 'required_validators.dart';
7+
export 'string_validators.dart';
8+
export 'type_validators.dart';

0 commit comments

Comments
 (0)