Claus Ibsen created CAMEL-24752:
-----------------------------------

             Summary: camel-core - generate a name to artifact table (like 
SensitiveUtils) so unknown component, language, data format and bean errors say 
which jar to add
                 Key: CAMEL-24752
                 URL: https://issues.apache.org/jira/browse/CAMEL-24752
             Project: Camel
          Issue Type: Improvement
          Components: camel-core, build system
            Reporter: Claus Ibsen


The runtime cannot tell which jar a missing component, language, data format or 
built-in bean is in: the metadata that knows (the catalog JSON, or the 
META-INF/services/org/apache/camel/*.json files) ships inside the jar that is 
absent. So the errors are generic, or guess:

* unknown component scheme (AbstractCamelContext.doGetEndpoint -> 
NoSuchEndpointException): {{No endpoint could be found for: foo://bar, please 
check your classpath contains the needed Camel component jar.}} - no jar named, 
no nearest scheme
* unknown language (NoSuchLanguageException): {{... e.g. camel-<name>}} - a 
guess that is wrong for 14 of the 28 languages (xquery -> camel-saxon, spel -> 
camel-spring, java -> camel-joor, js -> camel-javascript, hl7terser -> 
camel-hl7, xtokenize -> camel-stax, simple/header/... -> camel-core-languages)
* data format jar missing (DataFormatReifier.createDataFormat): {{Data format 
'jaxb' could not be created. Ensure ... present on the classpath}} - no jar
* built-in bean jar missing (PojoBeanHelper from CAMEL-24709): generic hint, as 
the bean metadata is in the missing jar
* YAML {{Unknown expression with id: ...}} - no nearest name, no jar

Measured against the catalog, {{camel-<name>}} is the wrong artifact for 103 of 
407 component schemes (aws2-ddbstream -> camel-aws2-ddb, caffeine-cache -> 
camel-caffeine, class -> camel-bean, coaps -> camel-coap, avro -> 
camel-avro-rpc, ...), 14 of 28 languages and 25 of 56 data formats, so a guess 
is not good enough.

Proposal: do what {{SensitiveUtils}} does. A new {{update-artifact-helper}} 
goal next to {{update-sensitive-helper}} in catalog/camel-catalog reads the 
catalog JSON and rewrites a generated class in core/camel-util (e.g. 
{{CamelArtifactUtils}}) between START/END tokens, with four blocks: components 
(scheme -> artifactId, incl. alternative schemes), languages, dataformats, 
beans (simple name -> javaType, interfaceType, artifactId). Plus small 
hand-written methods: artifactOf(kind, name), names(kind) and closest(kind, 
name) (edit distance; camel-util has none today and YamlValidator and 
EditDistanceSuggestionStrategy each keep a private copy that could move here).

A Java class rather than a resource file so camel-api can use it (camel-api 
already depends on camel-util), it is GraalVM native safe without resource 
registration, and it matches the existing pattern. ~560 entries, well within 
limits. The table version equals the runtime version by construction, which is 
better than the camel-jbang catalog that may be another version.

Consumers (one line at each throw site):
# NoSuchLanguageException: known name -> {{add camel-saxon to the classpath}}; 
unknown -> {{not a Camel language (did you mean 'xquery'?)}}; replaces the guess
# NoSuchEndpointException / AbstractCamelContext unknown scheme: {{the 
aws2-ddbstream component is in camel-aws2-ddb, add it to the classpath}} or 
{{did you mean 'kafka'?}}
# DataFormatReifier (model based and by ref): same two forms
# PojoBeanHelper.classNotFoundHint: classpath scan first (covers third-party 
beans built with the plugin), table as fallback -> {{ZipAggregationStrategy is 
in camel-zipfile, add it to the classpath}}
# YAML Unknown expression with id: nearest name + jar

Runtime flavour: the artifact is camel-saxon-starter on Spring Boot and 
camel-quarkus-saxon on Quarkus; the message can say {{add camel-saxon 
(camel-saxon-starter on Spring Boot, camel-quarkus-saxon on Quarkus)}} 
unconditionally, as core cannot cheaply tell the runtime.

Notes:
* two-pass build like SensitiveUtils: adding a component needs a rebuild to 
refresh the table; the CI uncommitted-changes check enforces it
* third-party or camel-quarkus-only components are not in the table; the hint 
falls back to the generic text
* NoSuchLanguageException / NoSuchEndpointException texts are asserted with 
contains() in a few tests; append after the existing sentence

Found while working on CAMEL-24709 (PR 26455), where naming the missing 
artifact turned out to be impossible from classpath metadata alone.



--
This message was sent by Atlassian Jira
(v8.20.10#820010)

Reply via email to