001/** 002 * Copyright (C) 2006-2025 Talend Inc. - www.talend.com 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 */ 016package org.talend.sdk.component.tools.validator; 017 018import static java.util.function.Function.identity; 019import static java.util.stream.Collectors.groupingBy; 020import static java.util.stream.Collectors.joining; 021import static java.util.stream.Collectors.toList; 022import static java.util.stream.Collectors.toMap; 023 024import java.util.ArrayList; 025import java.util.HashSet; 026import java.util.List; 027import java.util.Map; 028import java.util.Objects; 029import java.util.Set; 030import java.util.stream.Collectors; 031import java.util.stream.Stream; 032 033import org.apache.xbean.finder.AnnotationFinder; 034import org.talend.sdk.component.api.configuration.action.Checkable; 035import org.talend.sdk.component.api.configuration.type.DataStore; 036import org.talend.sdk.component.api.service.Service; 037import org.talend.sdk.component.api.service.healthcheck.HealthCheck; 038import org.talend.sdk.component.tools.validator.Validators.ValidatorHelper; 039 040public class DataStoreValidator implements Validator { 041 042 private final Validators.ValidatorHelper helper; 043 044 public DataStoreValidator(final ValidatorHelper helper) { 045 this.helper = helper; 046 } 047 048 @Override 049 public Stream<String> validate(final AnnotationFinder finder, final List<Class<?>> components) { 050 List<String> errors = new ArrayList<>(); 051 final List<Class<?>> datastoreClasses = finder.findAnnotatedClasses(DataStore.class); 052 053 final List<String> datastores = 054 datastoreClasses.stream().map(d -> d.getAnnotation(DataStore.class).value()).collect(toList()); 055 056 Set<String> uniqueDatastores = new HashSet<>(datastores); 057 if (datastores.size() != uniqueDatastores.size()) { 058 errors 059 .add("Duplicated DataStore found : " + datastores 060 .stream() 061 .collect(groupingBy(identity())) 062 .entrySet() 063 .stream() 064 .filter(e -> e.getValue().size() > 1) 065 .map(Map.Entry::getKey) 066 .collect(joining(", "))); 067 } 068 069 final List<Class<?>> checkableClasses = finder.findAnnotatedClasses(Checkable.class); 070 errors 071 .addAll(checkableClasses 072 .stream() 073 .filter(d -> !d.isAnnotationPresent(DataStore.class)) 074 .map(c -> c.getName() + " has @Checkable but is not a @DataStore") 075 .sorted() 076 .collect(Collectors.toList())); 077 078 final Map<String, String> checkableDataStoresMap = checkableClasses 079 .stream() 080 .filter(d -> d.isAnnotationPresent(DataStore.class)) 081 .collect(toMap(d -> d.getAnnotation(DataStore.class).value(), 082 d -> d.getAnnotation(Checkable.class).value())); 083 084 final Set<String> healthchecks = finder 085 .findAnnotatedMethods(HealthCheck.class) 086 .stream() 087 .filter(h -> h.getDeclaringClass().isAnnotationPresent(Service.class)) 088 .map(m -> m.getAnnotation(HealthCheck.class).value()) 089 .collect(Collectors.toSet()); 090 errors 091 .addAll(checkableDataStoresMap 092 .entrySet() 093 .stream() 094 .filter(e -> !healthchecks.contains(e.getValue())) 095 .map(e -> "No @HealthCheck for dataStore: '" + e.getKey() + "' with checkable: '" + e.getValue() 096 + "'") 097 .sorted() 098 .collect(Collectors.toList())); 099 100 errors 101 .addAll(datastoreClasses 102 .stream() 103 .map(clazz -> this.helper 104 .validateFamilyI18nKey(clazz, 105 "${family}.datastore." + clazz.getAnnotation(DataStore.class).value() 106 + "._displayName")) 107 .filter(Objects::nonNull) 108 .collect(toList())); 109 110 return errors.stream(); 111 112 } 113}