Podejście do walidacji.

1

Jestem ciekawy waszego podejścia co do walidacji parametrów. Załóżmy że mamy sobie serwis który przyjmuje m.in. mape Map<String,String> filters. Te filtry mają posłużyć do złożenia sqla. No ale może się zdarzyć że do tej metody serwisowej ktoś przekaże pustą mapę. I teraz możemy podejść do tego tak że w serwisie walidujemy return filters.isEmpty() ? dao.fetchWithoutFilters(filters) : dao.fetchWithFilters().

Albo możemy przekazywać po prostu mapę i w dao robić ify które weryfikują dane parametry. No i teraz pytanie jakie macie do tego podejście? Nasuwa mi się taka myśl że jakbyśmy mieli wszędzie weryfikować parametry to jest to bez sensu i musimy gdzieś założyć że to co wchodzi jest bez błędów.

0
Karol191PL napisał(a):

Nasuwa mi się taka myśl że jakbyśmy mieli wszędzie weryfikować parametry to jest to bez sensu i musimy gdzieś założyć że to co wchodzi jest bez błędów.

Najwcześniej jak się da należy zrobić walidację. Potem na podstawie tego buduje się obiekt domenowy który zawsze jest poprawny i już nie trzeba sprawdzać walidacji

1

Wszystko zależy od wymagań biznesowych. Jeśli jest założenie, że pusta mapa jest wartością poprawną to tu nie ma co walidować (zakładając, że ta mapa nie może być nullem). Jednak jeśli tak nie jest, to zapewne już na samym początku życia requestu dołożyłbym walidacje przychodzących parametrów, a potem zapewne używał NonEmptyMap (mówię z perspektywy Scali, w Javie pewnie nadal byłaby to zwykła mapa bądź jakiś wrapper). Oprócz tego pewnie pozamieniałbym Stringi w mapie na coś, co ma jakiekolwiek znaczenie biznesowe.

3
Karol191PL napisał(a):

I teraz możemy podejść do tego tak że w serwisie walidujemy return filters.isEmpty() ? dao.fetchWithoutFilters(filters) : dao.fetchWithFilters().

To nie jest "walidacja", tylko po prostu obsłużenie obu możliwości (jako poprawnych).

Swoją drogą przykład wygląda na błędny, powinno chyba być odwrotnie: dao.fetchWithoutFilters() : dao.fetchWithFilters(filters).

Aczkolwiek jeśli brak filtrów jest poprawny (na zasadzie *.*), to spodziewałbym się, że powinna go obsłużyć jedna metoda fetchWithFilters, i nie potrzeba robić osobnej fetchWithoutFilters. Tak samo jak nie ma potrzeby, żeby obok println(string) była osobna printEmptyLn(), jeżeli println może "wydrukować" pustego stringa i nic złego się przez to nie dzieje.

W (standardowej) Javie nie ma typów kolekcji, które by gwarantowały, na poziomie samego typu, że nie są puste. Jeśli jakaś metoda przyjmuje zatem kolekcję, to powinna ją obsłużyć bez względu na liczbę elementów.

Jeśli natomiast brak filtrów jest nieprawidłowy z zasady, to stworzyłbym klasę Filters, która byłaby opakowaniem na mapę, ale nie można by stworzyć obiektu Filters, który nie zawierałby żadnych danych. Inaczej mówiąc, obiekt Filters zawierający pustą mapę to jest coś, co fizycznie nie ma prawa zaistnieć.

A wtedy nie ma dylematów dotyczących tego, "gdzie zwalidować mapę", która (jeśli tego nie zrobimy) porusza się po naszym kodzie z taką jakby niewidzialną właściwością - czy jestem już zwalidowana, czy nie jestem? Której jednak nie widać, i nie można jej łatwo sprawdzić.

Naturalnym miejscem walidacji staje się to, i tylko to miejsce, w którym tworzona jest instancja Filters. I można je łatwo znaleźć w kodzie - po prostu wyszukując, gdzie obiekty Filters są instancjonowane.

musimy gdzieś założyć że to co wchodzi jest bez błędów.

To właśnie będzie owo "gdzieś". Granica, w której anonimowa mapa, sama z siebie nie gwarantująca dotrzymania żadnego kontraktu, przeistacza się w nasz obiekt domenowy, nad którego kontraktem mamy kontrolę.

1 użytkowników online, w tym zalogowanych: 0, gości: 1