This is an automated email from the ASF dual-hosted git repository. aldettinger pushed a commit to branch data-extraction-example in repository https://gitbox.apache.org/repos/asf/camel-quarkus-examples.git
commit 18be2dda7e5dd06b9f145ff209d5359a71af294b Author: aldettinger <aldettin...@gmail.com> AuthorDate: Thu Jul 25 18:30:03 2024 +0200 Add an example of data extraction with Quarkus LangChain4j --- data-extract-langchain4j/README.adoc | 190 ++++++++++ .../eclipse-formatter-config.xml | 276 +++++++++++++++ data-extract-langchain4j/pom.xml | 387 +++++++++++++++++++++ data-extract-langchain4j/schema.png | Bin 0 -> 97169 bytes data-extract-langchain4j/schemas-source.odp | Bin 0 -> 19800 bytes .../extraction/CustomPojoExtractionService.java | 34 ++ .../src/main/java/org/acme/extraction/Routes.java | 32 ++ .../src/main/kubernetes/kubernetes.yml | 95 +++++ .../src/main/kubernetes/openshift.yml | 122 +++++++ .../src/main/resources/application.properties | 63 ++++ .../org/acme/extraction/OllamaTestResource.java | 51 +++ .../src/test/java/org/acme/extraction/RouteIT.java | 8 + .../test/java/org/acme/extraction/RouteTest.java | 46 +++ .../src/test/resources/application.properties | 10 + .../texts/01_sarah-london-10-07-1986-satisfied.txt | 8 + .../texts/02_john-doe-01-11-2001-unsatisfied.txt | 13 + .../texts/03_kate-boss-13-08-1999-satisfied.txt | 12 + 17 files changed, 1347 insertions(+) diff --git a/data-extract-langchain4j/README.adoc b/data-extract-langchain4j/README.adoc new file mode 100644 index 0000000..33ca1eb --- /dev/null +++ b/data-extract-langchain4j/README.adoc @@ -0,0 +1,190 @@ += JPA idempotent repository: A Camel Quarkus example +:cq-example-description: An example that shows how to consume a message only once, even when the message is delivered multiple times + +{cq-description} + +TIP: Check the https://camel.apache.org/camel-quarkus/latest/first-steps.html[Camel Quarkus User guide] for prerequisites +and other general information. + +Suppose an application needs to invoke a costly API. Each time a duplicate message would be processed, then a bunch of money would be lost. In such situations, it could make sense to prevent some duplicate calls by using the https://camel.apache.org/components/latest/eips/idempotentConsumer-eip.html[idempotent consumer] EIP. +Let's see an example with the schema below: + +image::schema.png[] + +As one could see in the schema, using the idempotent consumer pattern in Camel is as simple as creating a route using the `idempotentConsumer` and `idempotentRepository` keywords. In this example, the idempotent repository is a database that is edited and read through JPA. Under the hood, this database will keep track of messages that have already been processed. + +Note that JPA is not the only option when it comes to selecting an `idempotentRepository` implementation. +Other choices are available as listed in the https://camel.apache.org/components/latest/eips/idempotentConsumer-eip.html#_idempotent_consumer_implementations[documentation]. + +In this example, let's focus on JPA and see more details about how to execute such a route in the next sections below. + +== Start in Development mode + +Let's start by executing the command below: + +[source,shell] +---- +mvn clean compile quarkus:dev +---- + +The above command compiles the project, starts the application and lets the Quarkus tooling watch for changes in your workspace. +Any modifications in your project will automatically take effect in the running application. + +TIP: Please refer to the Development mode section of +https://camel.apache.org/camel-quarkus/latest/first-steps.html#_development_mode[Camel Quarkus User guide] for more details. + +It should be possible now to see some log messages appearing on the console. +Note how some files with different content are generated `3,5,7...` +Each time such a file is consumed by the route, a costly API is called. +However, a file with content `1` is regularly generated. +This duplicate file is problematic as it will generate undue calls to the costly API too frequently. +This is where the https://camel.apache.org/components/latest/eips/idempotentConsumer-eip.html[idempotent consumer] enter the game. +The source code could be found in the source file named `src/main/java/org/acme/jpa/idempotent/repository/JpaIdempotentRoute.java`. +The camel application should produce logs as below: + +[source,shell] +---- +2023-09-15 15:47:49,477 INFO [route2] (Camel (camel-1) thread #2 - timer://createExampleInputFiles) ----------------------------------------------------------------- +2023-09-15 15:47:49,478 INFO [route2] (Camel (camel-1) thread #2 - timer://createExampleInputFiles) Creating an example input file with content 1 +2023-09-15 15:47:50,974 INFO [route1] (Camel (camel-1) thread #1 - file://target/input-files) Received an example input file having the content 1 +2023-09-15 15:47:51,167 INFO [route1] (Camel (camel-1) thread #1 - file://target/input-files) The file was not a duplicate, invoke the costly API +2023-09-15 15:47:51,230 INFO [org.acm.jpa.ide.rep.CostlyApiService] (vert.x-worker-thread-1) Costly API has been called with new content => GOOD +2023-09-15 15:47:59,475 INFO [route2] (Camel (camel-1) thread #2 - timer://createExampleInputFiles) ----------------------------------------------------------------- +2023-09-15 15:47:59,477 INFO [route2] (Camel (camel-1) thread #2 - timer://createExampleInputFiles) Creating an example input file with content 3 +2023-09-15 15:48:00,758 INFO [route1] (Camel (camel-1) thread #1 - file://target/input-files) Received an example input file having the content 3 +2023-09-15 15:48:00,761 INFO [route1] (Camel (camel-1) thread #1 - file://target/input-files) The file was not a duplicate, invoke the costly API +2023-09-15 15:48:00,765 INFO [org.acm.jpa.ide.rep.CostlyApiService] (vert.x-worker-thread-1) Costly API has been called with new content => GOOD +2023-09-15 15:48:09,475 INFO [route2] (Camel (camel-1) thread #2 - timer://createExampleInputFiles) ----------------------------------------------------------------- +2023-09-15 15:48:09,477 INFO [route2] (Camel (camel-1) thread #2 - timer://createExampleInputFiles) Creating an example input file with content 1 +2023-09-15 15:48:10,777 INFO [route1] (Camel (camel-1) thread #1 - file://target/input-files) Received an example input file having the content 1 +2023-09-15 15:48:19,475 INFO [route2] (Camel (camel-1) thread #2 - timer://createExampleInputFiles) ----------------------------------------------------------------- +2023-09-15 15:48:19,477 INFO [route2] (Camel (camel-1) thread #2 - timer://createExampleInputFiles) Creating an example input file with content 5 +2023-09-15 15:48:20,796 INFO [route1] (Camel (camel-1) thread #1 - file://target/input-files) Received an example input file having the content 5 +2023-09-15 15:48:20,801 INFO [route1] (Camel (camel-1) thread #1 - file://target/input-files) The file was not a duplicate, invoke the costly API +2023-09-15 15:48:20,804 INFO [org.acm.jpa.ide.rep.CostlyApiService] (vert.x-worker-thread-1) Costly API has been called with new content => GOOD +---- + +The idempotent consumer is storing the list of already processed messages into a MariaDB database. + +If you're wondering how the database schema was created, it happens automatically thanks to `quarkus-flyway`. On application startup, it +creates the `my-db` database and the required `CAMEL_MESSAGEPROCESSED` table. You can find the Flyway migration script at `src/main/resources/db/migration/V1.0.0__add_camel_message_processed.sql`. +You can find more information about Flyway in the https://quarkus.io/guides/flyway[Quarkus Flyway guide]. + +== Starting and initializing the MariaDB database in a container + +Before packaging and running the application in JVM mode, we need to start and initialize a MariaDB database in a container. +So, in a first shell, please launch a MariaDB database container: + +[source,shell] +---- +docker run -e MARIADB_USER=mariadb -e MARIADB_PASSWORD=mariadb -e MARIADB_DATABASE=my-db -e MARIADB_ROOT_PASSWORD=secret -p 3306:3306 docker.io/mariadb:10.11 +---- + +If successful, you should see the message `mariadbd: ready for connections` output to the console. + +=== Package and run the application + +Once you are done with developing you may want to package and run the application. + +TIP: Find more details about the JVM mode and Native mode in the Package and run section of +https://camel.apache.org/camel-quarkus/latest/first-steps.html#_package_and_run_the_application[Camel Quarkus User guide] + +==== JVM mode + +[source,shell] +---- +mvn clean package -DskipTests +java -jar target/quarkus-app/quarkus-run.jar +---- + +As mentioned above, `quarkus-flyway` will automatically create the required database and tables for you. + +==== Native mode + +IMPORTANT: Native mode requires having GraalVM and other tools installed. Please check the Prerequisites section +of https://camel.apache.org/camel-quarkus/latest/first-steps.html#_prerequisites[Camel Quarkus User guide]. + +To prepare a native executable using GraalVM, run the following commands: + +[source,shell] +---- +mvn clean package -DskipTests -Pnative +./target/*-runner +---- + +The compilation is a bit slower. Beyond that, notice how the application behaves the same way. +The only variation compared to the JVM mode is actually that the application was packaged as a native executable. + +==== Deploying to Kubernetes + +You can build a container image for the application like this. Refer to the https://quarkus.io/guides/deploying-to-kubernetes[Quarkus Kubernetes guide] for options around customizing image names, registries etc. + +[source,shell] +---- +mvn clean package -DskipTests -Dquarkus.container-image.build=true +---- + +If you are using a local development cluster like Kind or k3s, you can use host the container image on your local host. Or, with minikube, use the Docker daemon from the cluster virtual machine `eval $(minikube docker-env)`. Otherwise, you'll need to push the image to a registry of your choosing. + +Next apply the necessary resources to the cluster if needed: + +[source,shell] +---- +kubectl apply -f target/kubernetes/kubernetes.yml +---- + +TIP: You can build & deploy in one single step by doing `mvn clean package -DskipTests -Dquarkus.kubernetes.deploy=true` + +Check pods are running by executing: + +[source,shell] +---- +kubectl get pods +---- + +We expect a list of three pods similar to below. +Note that the `camel-quarkus-examples-jpa-idempotent-repository-flyway` pod will transition from `running` to `completed`, after it has completed initializing the MariaDB database. + +[source,shell] +---- +NAME READY STATUS RESTARTS AGE +camel-quarkus-examples-mariadb-database-deployment-76f6dc9bdnwwxn 1/1 Running 0 23s +camel-quarkus-examples-jpa-idempotent-repository-flyway-in2q5n5 0/1 Completed 0 23s +camel-quarkus-examples-jpa-idempotent-repository-7c74b9cf5ph68r 1/1 Running 1 (18s ago) 23s +---- + +Now, let's tail the application logs: + +[source,shell] +---- +kubectl logs -f camel-quarkus-examples-jpa-idempotent-repository-56999fcffb6qv2 +---- + +To clean up do: + +[source,shell] +---- +kubectl delete all -l app.kubernetes.io/name=camel-quarkus-examples-jpa-idempotent-repository +kubectl delete all -l job-name=camel-quarkus-examples-jpa-idempotent-repository-flyway-init +kubectl delete all -l app.kubernetes.io/name=camel-quarkus-examples-mariadb-database +---- + +[NOTE] +==== +If you need to configure container resource limits & requests, or enable the Quarkus Kubernetes client to trust self signed certificates, you can find these configuration options in `src/main/resources/application.properties`. Simply uncomment them and set your desired values. +==== + +==== Deploying to OpenShift + +In order to start a Source To Image (S2I) build and deploy the application, let's execute the command below: + +[source,shell] +---- +mvn clean package -DskipTests -Dquarkus.kubernetes.deploy=true -Dopenshift +---- + +You can check the pod status and tail logs using the commands mentioned above in the Kubernetes section. Use the `oc` binary instead of `kubectl` if preferred. + +== Feedback + +Please report bugs and propose improvements via https://github.com/apache/camel-quarkus/issues[GitHub issues of Camel Quarkus] project. diff --git a/data-extract-langchain4j/eclipse-formatter-config.xml b/data-extract-langchain4j/eclipse-formatter-config.xml new file mode 100644 index 0000000..2248b2b --- /dev/null +++ b/data-extract-langchain4j/eclipse-formatter-config.xml @@ -0,0 +1,276 @@ +<?xml version="1.0" encoding="UTF-8"?> +<!-- + + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + +--> +<profiles version="8"> + <profile name="Camel Java Conventions" version="8" kind="CodeFormatterProfile"> + <setting id="org.eclipse.jdt.core.formatter.align_type_members_on_columns" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_allocation_expression" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_enum_constant" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_explicit_constructor_call" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_method_invocation" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_arguments_in_qualified_allocation_expression" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_binary_expression" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_compact_if" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_conditional_expression" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_enum_constants" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_multiple_fields" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_parameters_in_method_declaration" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_selector_in_method_invocation" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_superclass_in_type_declaration" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_enum_declaration" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_type_declaration" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_constructor_declaration" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_method_declaration" value="16"/> + <setting id="org.eclipse.jdt.core.formatter.blank_lines_after_imports" value="1"/> + <setting id="org.eclipse.jdt.core.formatter.blank_lines_after_package" value="1"/> + <setting id="org.eclipse.jdt.core.formatter.blank_lines_before_field" value="0"/> + <setting id="org.eclipse.jdt.core.formatter.blank_lines_before_first_class_body_declaration" value="0"/> + <setting id="org.eclipse.jdt.core.formatter.blank_lines_before_imports" value="1"/> + <setting id="org.eclipse.jdt.core.formatter.blank_lines_before_member_type" value="1"/> + <setting id="org.eclipse.jdt.core.formatter.blank_lines_before_method" value="1"/> + <setting id="org.eclipse.jdt.core.formatter.blank_lines_before_new_chunk" value="1"/> + <setting id="org.eclipse.jdt.core.formatter.blank_lines_before_package" value="0"/> + <setting id="org.eclipse.jdt.core.formatter.blank_lines_between_type_declarations" value="1"/> + <setting id="org.eclipse.jdt.core.formatter.brace_position_for_annotation_type_declaration" value="end_of_line"/> + <setting id="org.eclipse.jdt.core.formatter.brace_position_for_anonymous_type_declaration" value="end_of_line"/> + <setting id="org.eclipse.jdt.core.formatter.brace_position_for_array_initializer" value="end_of_line"/> + <setting id="org.eclipse.jdt.core.formatter.brace_position_for_block" value="end_of_line"/> + <setting id="org.eclipse.jdt.core.formatter.brace_position_for_block_in_case" value="end_of_line"/> + <setting id="org.eclipse.jdt.core.formatter.brace_position_for_constructor_declaration" value="end_of_line"/> + <setting id="org.eclipse.jdt.core.formatter.brace_position_for_enum_constant" value="end_of_line"/> + <setting id="org.eclipse.jdt.core.formatter.brace_position_for_enum_declaration" value="end_of_line"/> + <setting id="org.eclipse.jdt.core.formatter.brace_position_for_method_declaration" value="end_of_line"/> + <setting id="org.eclipse.jdt.core.formatter.brace_position_for_switch" value="end_of_line"/> + <setting id="org.eclipse.jdt.core.formatter.brace_position_for_type_declaration" value="end_of_line"/> + <setting id="org.eclipse.jdt.core.formatter.comment.align_tags_names_descriptions" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.comment.align_tags_descriptions_grouped" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.comment.clear_blank_lines" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.comment.format_block_comments" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.comment.format_comments" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.comment.format_header" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.comment.format_html" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.comment.format_javadoc_comments" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.comment.format_line_comments" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.comment.format_source_code" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.comment.indent_parameter_description" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.comment.indent_return_description" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.comment.indent_root_tags" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_before_root_tags" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.comment.insert_new_line_for_parameter" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.comment.line_length" value="120"/> + <setting id="org.eclipse.jdt.core.formatter.compact_else_if" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.continuation_indentation" value="2"/> + <setting id="org.eclipse.jdt.core.formatter.continuation_indentation_for_array_initializer" value="2"/> + <setting id="org.eclipse.jdt.core.formatter.format_guardian_clause_on_one_line" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_constant_header" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_declaration_header" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_type_header" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.indent_breaks_compare_to_cases" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.indent_statements_compare_to_block" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.indent_statements_compare_to_body" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_cases" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_switch" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.indentation.size" value="8"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_parameter" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_after_opening_brace_in_array_initializer" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_at_end_of_file_if_missing" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_catch_in_try_statement" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_closing_brace_in_array_initializer" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_else_in_if_statement" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_finally_in_try_statement" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_before_while_in_do_statement" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_anonymous_type_declaration" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_block" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_constant" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_declaration" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_method_body" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_new_line_in_empty_type_declaration" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_and_in_type_parameter" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_assignment_operator" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation_type_declaration" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_binary_operator" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_arguments" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_parameters" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_brace_in_block" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_closing_paren_in_cast" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_assert" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_case" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_conditional" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_for" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_colon_in_labeled_statement" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_allocation_expression" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_annotation" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_array_initializer" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_parameters" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_throws" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_constant_arguments" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_declarations" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_explicitconstructorcall_arguments" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_increments" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_inits" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_parameters" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_throws" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_invocation_arguments" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_field_declarations" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_local_declarations" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_parameterized_type_reference" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_superinterfaces" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_arguments" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_parameters" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_ellipsis" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_parameterized_type_reference" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_arguments" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_parameters" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_brace_in_array_initializer" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_allocation_expression" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_reference" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_annotation" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_cast" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_catch" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_constructor_declaration" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_enum_constant" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_for" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_if" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_declaration" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_invocation" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_parenthesized_expression" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_switch" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_synchronized" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_while" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_postfix_operator" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_prefix_operator" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_question_in_conditional" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_question_in_wildcard" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_for" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_after_unary_operator" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_and_in_type_parameter" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_assignment_operator" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_at_in_annotation_type_declaration" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_binary_operator" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_parameterized_type_reference" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_arguments" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_parameters" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_brace_in_array_initializer" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_allocation_expression" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_reference" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_annotation" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_cast" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_catch" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_constructor_declaration" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_enum_constant" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_for" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_if" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_declaration" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_invocation" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_parenthesized_expression" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_switch" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_synchronized" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_while" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_assert" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_case" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_conditional" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_default" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_for" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_colon_in_labeled_statement" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_allocation_expression" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_annotation" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_array_initializer" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_parameters" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_throws" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_constant_arguments" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_declarations" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_explicitconstructorcall_arguments" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_increments" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_inits" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_parameters" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_throws" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_invocation_arguments" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_field_declarations" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_local_declarations" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_parameterized_type_reference" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_superinterfaces" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_arguments" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_parameters" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_ellipsis" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_parameterized_type_reference" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_arguments" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_parameters" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_annotation_type_declaration" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_anonymous_type_declaration" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_array_initializer" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_block" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_constructor_declaration" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_constant" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_declaration" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_method_declaration" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_switch" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_type_declaration" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_allocation_expression" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_reference" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_type_reference" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation_type_member_declaration" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_catch" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_constructor_declaration" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_enum_constant" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_for" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_if" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_declaration" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_invocation" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_parenthesized_expression" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_switch" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_synchronized" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_while" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_postfix_operator" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_prefix_operator" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_question_in_conditional" value="insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_question_in_wildcard" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_for" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_before_unary_operator" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_between_brackets_in_array_type_reference" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_braces_in_array_initializer" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_brackets_in_array_allocation_expression" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_annotation_type_member_declaration" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_constructor_declaration" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_enum_constant" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_declaration" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_invocation" value="do not insert"/> + <setting id="org.eclipse.jdt.core.formatter.join_lines_in_comments" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.join_wrapped_lines" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.keep_else_statement_on_same_line" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.keep_empty_array_initializer_on_one_line" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.keep_imple_if_on_one_line" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.keep_then_statement_on_same_line" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.lineSplit" value="128"/> + <setting id="org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_method_body" value="0"/> + <setting id="org.eclipse.jdt.core.formatter.number_of_empty_lines_to_preserve" value="1"/> + <setting id="org.eclipse.jdt.core.formatter.put_empty_statement_on_new_line" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.tabulation.char" value="space"/> + <setting id="org.eclipse.jdt.core.formatter.tabulation.size" value="4"/> + <setting id="org.eclipse.jdt.core.formatter.use_tabs_only_for_leading_indentations" value="false"/> + <setting id="org.eclipse.jdt.core.formatter.use_on_off_tags" value="true"/> + <setting id="org.eclipse.jdt.core.formatter.disabling_tag" value="CHECKSTYLE:OFF"/> + <setting id="org.eclipse.jdt.core.formatter.enabling_tag" value="CHECKSTYLE:ON"/> + </profile> +</profiles> diff --git a/data-extract-langchain4j/pom.xml b/data-extract-langchain4j/pom.xml new file mode 100644 index 0000000..bebd8bd --- /dev/null +++ b/data-extract-langchain4j/pom.xml @@ -0,0 +1,387 @@ +<?xml version="1.0" encoding="UTF-8"?> +<!-- + + Licensed to the Apache Software Foundation (ASF) under one or more + contributor license agreements. See the NOTICE file distributed with + this work for additional information regarding copyright ownership. + The ASF licenses this file to You under the Apache License, Version 2.0 + (the "License"); you may not use this file except in compliance with + the License. You may obtain a copy of the License at + + http://www.apache.org/licenses/LICENSE-2.0 + + Unless required by applicable law or agreed to in writing, software + distributed under the License is distributed on an "AS IS" BASIS, + WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + See the License for the specific language governing permissions and + limitations under the License. + +--> +<project xmlns="http://maven.apache.org/POM/4.0.0" + xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" + xsi:schemaLocation="http://maven.apache.org/POM/4.0.0 http://maven.apache.org/xsd/maven-4.0.0.xsd"> + <modelVersion>4.0.0</modelVersion> + + <artifactId>camel-quarkus-examples-data-extract-langchain4j</artifactId> + <groupId>org.apache.camel.quarkus.examples</groupId> + <version>3.13.0-SNAPSHOT</version> + + <name>Camel Quarkus :: Examples :: Data Extract LangChain4j Repository</name> + <description>Camel Quarkus Example :: Data Extract LangChain4j Repository</description> + + <properties> + <quarkus.platform.version>3.12.0</quarkus.platform.version> + <camel-quarkus.platform.version>3.13.0-SNAPSHOT</camel-quarkus.platform.version> + + <quarkus.platform.group-id>io.quarkus</quarkus.platform.group-id> + <quarkus.platform.artifact-id>quarkus-bom</quarkus.platform.artifact-id> + <camel-quarkus.platform.group-id>org.apache.camel.quarkus</camel-quarkus.platform.group-id> + <camel-quarkus.platform.artifact-id>camel-quarkus-bom</camel-quarkus.platform.artifact-id> + + <project.build.sourceEncoding>UTF-8</project.build.sourceEncoding> + <project.reporting.outputEncoding>UTF-8</project.reporting.outputEncoding> + <maven.compiler.target>17</maven.compiler.target> + <maven.compiler.source>17</maven.compiler.source> + <maven.compiler.testTarget>${maven.compiler.target}</maven.compiler.testTarget> + <maven.compiler.testSource>${maven.compiler.source}</maven.compiler.testSource> + + <formatter-maven-plugin.version>2.24.1</formatter-maven-plugin.version> + <groovy-maven-plugin.version>2.1.1</groovy-maven-plugin.version> + <impsort-maven-plugin.version>1.11.0</impsort-maven-plugin.version> + <license-maven-plugin.version>4.5</license-maven-plugin.version> + <maven-compiler-plugin.version>3.13.0</maven-compiler-plugin.version> + <maven-jar-plugin.version>3.4.2</maven-jar-plugin.version> + <maven-resources-plugin.version>3.3.1</maven-resources-plugin.version> + <maven-surefire-plugin.version>3.3.1</maven-surefire-plugin.version> + </properties> + + <dependencyManagement> + <dependencies> + <!-- Import BOM --> + <dependency> + <groupId>io.quarkiverse.langchain4j</groupId> + <artifactId>quarkus-langchain4j-bom</artifactId> + <version>0.16.4</version> + <type>pom</type> + <scope>import</scope> + </dependency> + <dependency> + <groupId>${quarkus.platform.group-id}</groupId> + <artifactId>${quarkus.platform.artifact-id}</artifactId> + <version>${quarkus.platform.version}</version> + <type>pom</type> + <scope>import</scope> + </dependency> + <dependency> + <groupId>${camel-quarkus.platform.group-id}</groupId> + <artifactId>${camel-quarkus.platform.artifact-id}</artifactId> + <version>${camel-quarkus.platform.version}</version> + <type>pom</type> + <scope>import</scope> + </dependency> + </dependencies> + </dependencyManagement> + + <dependencies> + <dependency> + <groupId>org.apache.camel.quarkus</groupId> + <artifactId>camel-quarkus-bean</artifactId> + </dependency> + <dependency> + <groupId>org.apache.camel.quarkus</groupId> + <artifactId>camel-quarkus-platform-http</artifactId> + </dependency> + <dependency> + <groupId>io.quarkiverse.langchain4j</groupId> + <artifactId>quarkus-langchain4j-ollama</artifactId> + </dependency> + <dependency> + <groupId>commons-io</groupId> + <artifactId>commons-io</artifactId> + </dependency> + + <!-- Test --> + <dependency> + <groupId>io.quarkus</groupId> + <artifactId>quarkus-junit5</artifactId> + <scope>test</scope> + </dependency> + <dependency> + <groupId>org.awaitility</groupId> + <artifactId>awaitility</artifactId> + <scope>test</scope> + </dependency> + <dependency> + <groupId>io.rest-assured</groupId> + <artifactId>rest-assured</artifactId> + <scope>test</scope> + </dependency> + <dependency> + <groupId>org.testcontainers</groupId> + <artifactId>testcontainers</artifactId> + <scope>test</scope> + </dependency> + </dependencies> + + <build> + <pluginManagement> + <plugins> + <plugin> + <groupId>org.codehaus.gmaven</groupId> + <artifactId>groovy-maven-plugin</artifactId> + <version>${groovy-maven-plugin.version}</version> + </plugin> + + <plugin> + <groupId>net.revelc.code.formatter</groupId> + <artifactId>formatter-maven-plugin</artifactId> + <version>${formatter-maven-plugin.version}</version> + <configuration> + <configFile>${maven.multiModuleProjectDirectory}/eclipse-formatter-config.xml</configFile> + <lineEnding>LF</lineEnding> + </configuration> + </plugin> + + <plugin> + <groupId>net.revelc.code</groupId> + <artifactId>impsort-maven-plugin</artifactId> + <version>${impsort-maven-plugin.version}</version> + <configuration> + <groups>java.,javax.,org.w3c.,org.xml.,junit.</groups> + <removeUnused>true</removeUnused> + <staticAfter>true</staticAfter> + <staticGroups>java.,javax.,org.w3c.,org.xml.,junit.</staticGroups> + </configuration> + </plugin> + + <plugin> + <groupId>org.apache.maven.plugins</groupId> + <artifactId>maven-compiler-plugin</artifactId> + <version>${maven-compiler-plugin.version}</version> + <configuration> + <showDeprecation>true</showDeprecation> + <showWarnings>true</showWarnings> + <compilerArgs> + <arg>-Xlint:unchecked</arg> + </compilerArgs> + </configuration> + </plugin> + + <plugin> + <groupId>org.apache.maven.plugins</groupId> + <artifactId>maven-surefire-plugin</artifactId> + <version>${maven-surefire-plugin.version}</version> + <configuration> + <failIfNoTests>false</failIfNoTests> + <systemPropertyVariables> + <java.util.logging.manager>org.jboss.logmanager.LogManager</java.util.logging.manager> + </systemPropertyVariables> + </configuration> + </plugin> + + <plugin> + <groupId>${quarkus.platform.group-id}</groupId> + <artifactId>quarkus-maven-plugin</artifactId> + <version>${quarkus.platform.version}</version> + </plugin> + + <plugin> + <groupId>org.apache.maven.plugins</groupId> + <artifactId>maven-failsafe-plugin</artifactId> + <version>${maven-surefire-plugin.version}</version> + </plugin> + + <plugin> + <groupId>org.apache.maven.plugins</groupId> + <artifactId>maven-jar-plugin</artifactId> + <version>${maven-jar-plugin.version}</version> + </plugin> + + <plugin> + <groupId>com.mycila</groupId> + <artifactId>license-maven-plugin</artifactId> + <version>${license-maven-plugin.version}</version> + <configuration> + <failIfUnknown>true</failIfUnknown> + <header>${maven.multiModuleProjectDirectory}/header.txt</header> + <excludes> + <exclude>**/*.adoc</exclude> + <exclude>**/*.odp</exclude> + <exclude>**/*.txt</exclude> + <exclude>**/LICENSE.txt</exclude> + <exclude>**/LICENSE</exclude> + <exclude>**/NOTICE.txt</exclude> + <exclude>**/NOTICE</exclude> + <exclude>**/README</exclude> + <exclude>**/pom.xml.versionsBackup</exclude> + </excludes> + <mapping> + <java>SLASHSTAR_STYLE</java> + <properties>CAMEL_PROPERTIES_STYLE</properties> + <kt>SLASHSTAR_STYLE</kt> + </mapping> + <headerDefinitions> + <headerDefinition>${maven.multiModuleProjectDirectory}/license-properties-headerdefinition.xml</headerDefinition> + </headerDefinitions> + </configuration> + </plugin> + </plugins> + </pluginManagement> + + <plugins> + <plugin> + <groupId>${quarkus.platform.group-id}</groupId> + <artifactId>quarkus-maven-plugin</artifactId> + <executions> + <execution> + <id>build</id> + <goals> + <goal>build</goal> + </goals> + </execution> + </executions> + </plugin> + + <plugin> + <groupId>net.revelc.code.formatter</groupId> + <artifactId>formatter-maven-plugin</artifactId> + <executions> + <execution> + <id>format</id> + <goals> + <goal>format</goal> + </goals> + <phase>process-sources</phase> + </execution> + </executions> + </plugin> + + <plugin> + <groupId>net.revelc.code</groupId> + <artifactId>impsort-maven-plugin</artifactId> + <executions> + <execution> + <id>sort-imports</id> + <goals> + <goal>sort</goal> + </goals> + <phase>process-sources</phase> + </execution> + </executions> + </plugin> + + <plugin> + <groupId>org.codehaus.gmaven</groupId> + <artifactId>groovy-maven-plugin</artifactId> + <executions> + <execution> + <id>sync-k8s-resource-versions</id> + <inherited>false</inherited> + <goals> + <goal>execute</goal> + </goals> + <phase>process-sources</phase> + <configuration> + <source> + import java.util.regex.Matcher + import java.util.regex.Pattern + + Pattern pattern = Pattern.compile("app.kubernetes.io/version: .*") + + ["kubernetes", "openshift"].each { k8sResource -> + String sanitizedBasedir = project.basedir.path.replace('\\', '/') + File file = new File("${sanitizedBasedir}/src/main/kubernetes/${k8sResource}.yml") + String content = file.text + Matcher matcher = pattern.matcher(content) + + if (matcher.find()) { + String updatedContent = matcher.replaceAll("app.kubernetes.io/version: ${project.version}") + if (updatedContent != content) { + log.info("Updating app.kubernetes.io/version label to ${project.version} in ${file.path}") + file.write(updatedContent) + } + } + } + </source> + </configuration> + </execution> + </executions> + </plugin> + </plugins> + </build> + + <profiles> + <profile> + <id>native</id> + <activation> + <property> + <name>native</name> + </property> + </activation> + <properties> + <quarkus.native.enabled>true</quarkus.native.enabled> + </properties> + <build> + <plugins> + <plugin> + <groupId>org.apache.maven.plugins</groupId> + <artifactId>maven-failsafe-plugin</artifactId> + <executions> + <execution> + <goals> + <goal>integration-test</goal> + <goal>verify</goal> + </goals> + </execution> + </executions> + </plugin> + </plugins> + </build> + </profile> + <profile> + <id>kubernetes</id> + <activation> + <activeByDefault>true</activeByDefault> + <property> + <name>kubernetes</name> + </property> + </activation> + <dependencies> + <dependency> + <groupId>io.quarkus</groupId> + <artifactId>quarkus-kubernetes</artifactId> + </dependency> + <dependency> + <groupId>io.quarkus</groupId> + <artifactId>quarkus-container-image-jib</artifactId> + </dependency> + </dependencies> + </profile> + <profile> + <id>openshift</id> + <activation> + <property> + <name>openshift</name> + </property> + </activation> + <dependencies> + <dependency> + <groupId>io.quarkus</groupId> + <artifactId>quarkus-openshift</artifactId> + </dependency> + </dependencies> + </profile> + <profile> + <id>skip-testcontainers-tests</id> + <activation> + <property> + <name>skip-testcontainers-tests</name> + </property> + </activation> + <properties> + <skipTests>true</skipTests> + </properties> + </profile> + </profiles> + +</project> diff --git a/data-extract-langchain4j/schema.png b/data-extract-langchain4j/schema.png new file mode 100644 index 0000000..0252310 Binary files /dev/null and b/data-extract-langchain4j/schema.png differ diff --git a/data-extract-langchain4j/schemas-source.odp b/data-extract-langchain4j/schemas-source.odp new file mode 100644 index 0000000..0c40e43 Binary files /dev/null and b/data-extract-langchain4j/schemas-source.odp differ diff --git a/data-extract-langchain4j/src/main/java/org/acme/extraction/CustomPojoExtractionService.java b/data-extract-langchain4j/src/main/java/org/acme/extraction/CustomPojoExtractionService.java new file mode 100644 index 0000000..e3916aa --- /dev/null +++ b/data-extract-langchain4j/src/main/java/org/acme/extraction/CustomPojoExtractionService.java @@ -0,0 +1,34 @@ +package org.acme.extraction; + +import java.time.LocalDate; + +import dev.langchain4j.service.UserMessage; +import dev.langchain4j.service.V; +import io.quarkiverse.langchain4j.RegisterAiService; +import io.quarkus.runtime.annotations.RegisterForReflection; +import jakarta.enterprise.context.ApplicationScoped; +import org.apache.camel.Handler; + +@RegisterAiService +@ApplicationScoped +public interface CustomPojoExtractionService { + + @RegisterForReflection + static class CustomPojo { + public boolean customerSatisfied; + public String customerName; + public LocalDate customerBirthday; + public String summary; + } + + static final String CUSTOM_POJO_EXTRACT_PROMPT = "Extract information about a customer from the text delimited by triple backticks: ```{text}```." + + "The customerBirthday field should be formatted as YYYY-MM-DD." + + "The summary field should concisely relate the customer main ask."; + + @UserMessage(CUSTOM_POJO_EXTRACT_PROMPT) + @Handler + // TODO: It should be possible to remove @V as this is working in data-experiments-camel-quarkus + // The issue is still there with q-platform 3.12.0, 3.12.1, 3.12.2, 3.12.3, 3.13.0.CR1 and maven.compiler.target/source = 21 + CustomPojo extractFromText(@V("text") String text); + //CustomPojo extractFromText(String text); +} diff --git a/data-extract-langchain4j/src/main/java/org/acme/extraction/Routes.java b/data-extract-langchain4j/src/main/java/org/acme/extraction/Routes.java new file mode 100644 index 0000000..03593e3 --- /dev/null +++ b/data-extract-langchain4j/src/main/java/org/acme/extraction/Routes.java @@ -0,0 +1,32 @@ +package org.acme.extraction; + +import jakarta.enterprise.context.ApplicationScoped; +import jakarta.inject.Inject; +import org.apache.camel.builder.RouteBuilder; + +@ApplicationScoped +public class Routes extends RouteBuilder { + + @Inject + CustomPojoExtractionService customPojoExtractionService; + + @Override + public void configure() { + from("platform-http:/custom-pojo-extraction-service?produces=application/json") + .log("Received ${body}") + .bean(customPojoExtractionService) + .bean(this, "toPrettyFormat"); + } + + private final static String FORMAT = "{" + + "\"customerSatisfied\": \"%s\"," + + "\"customerName\": \"%s\"," + + "\"customerBirthday\": \"%td %tB %tY\"," + + "\"summary\": \"%s\"" + + "}"; + + public static String toPrettyFormat(CustomPojoExtractionService.CustomPojo extract) { + return String.format(FORMAT, extract.customerSatisfied, extract.customerName, extract.customerBirthday, + extract.customerBirthday, extract.customerBirthday, extract.summary); + } +} diff --git a/data-extract-langchain4j/src/main/kubernetes/kubernetes.yml b/data-extract-langchain4j/src/main/kubernetes/kubernetes.yml new file mode 100644 index 0000000..3d42259 --- /dev/null +++ b/data-extract-langchain4j/src/main/kubernetes/kubernetes.yml @@ -0,0 +1,95 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You under the Apache License, Version 2.0 +# (the "License"); you may not use this file except in compliance with +# the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +apiVersion: apps/v1 +kind: Deployment +metadata: + name: camel-quarkus-examples-mariadb-database-deployment + labels: + app.kubernetes.io/name: camel-quarkus-examples-mariadb-database + app.kubernetes.io/version: 3.13.0-SNAPSHOT +spec: + replicas: 1 + selector: + matchLabels: + app.kubernetes.io/name: camel-quarkus-examples-mariadb-database + app.kubernetes.io/version: 3.13.0-SNAPSHOT + template: + metadata: + labels: + app.kubernetes.io/name: camel-quarkus-examples-mariadb-database + app.kubernetes.io/version: 3.13.0-SNAPSHOT + spec: + containers: + - name: mariadb-database + image: docker.io/mariadb:10.11 + ports: + - containerPort: 3306 + env: + - name: MARIADB_USER + valueFrom: + secretKeyRef: + name: mariadb-secret + key: db-user + - name: MARIADB_PASSWORD + valueFrom: + secretKeyRef: + name: mariadb-secret + key: db-password + - name: MARIADB_DATABASE + value: my-db + - name: MARIADB_RANDOM_ROOT_PASSWORD + value: generate + volumeMounts: + # The /var/lib/mysql folder is where the actual database content is stored + - name: mariadb-database-data-volume + mountPath: /var/lib/mysql + volumes: + # Explicitly create an empty dir volume in order to ensure read/write access needed to store database files + - name: mariadb-database-data-volume + emptyDir: {} +--- +apiVersion: v1 +kind: Service +metadata: + labels: + app.kubernetes.io/name: camel-quarkus-examples-mariadb-database + app.kubernetes.io/version: 3.13.0-SNAPSHOT + name: mariadb-database +spec: + ports: + - name: mariadb + port: 3306 + targetPort: 3306 + selector: + app.kubernetes.io/name: camel-quarkus-examples-mariadb-database + app.kubernetes.io/version: 3.13.0-SNAPSHOT + type: ClusterIP +--- +apiVersion: v1 +kind: Secret +metadata: + labels: + app.kubernetes.io/name: camel-quarkus-examples-mariadb-database + app.kubernetes.io/version: 3.13.0-SNAPSHOT + name: mariadb-secret +type: Opaque +data: + # mariadb + db-user: bWFyaWFkYg== + # s3cr3t + db-password: czNjcjN0 diff --git a/data-extract-langchain4j/src/main/kubernetes/openshift.yml b/data-extract-langchain4j/src/main/kubernetes/openshift.yml new file mode 100644 index 0000000..f35bd3d --- /dev/null +++ b/data-extract-langchain4j/src/main/kubernetes/openshift.yml @@ -0,0 +1,122 @@ +# +# Licensed to the Apache Software Foundation (ASF) under one or more +# contributor license agreements. See the NOTICE file distributed with +# this work for additional information regarding copyright ownership. +# The ASF licenses this file to You under the Apache License, Version 2.0 +# (the "License"); you may not use this file except in compliance with +# the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, software +# distributed under the License is distributed on an "AS IS" BASIS, +# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +# See the License for the specific language governing permissions and +# limitations under the License. +# + +apiVersion: apps/v1 +kind: Deployment +metadata: + name: camel-quarkus-examples-mariadb-database-deployment + labels: + app.kubernetes.io/name: camel-quarkus-examples-mariadb-database + app.kubernetes.io/version: 3.13.0-SNAPSHOT +spec: + replicas: 1 + selector: + matchLabels: + app.kubernetes.io/name: camel-quarkus-examples-mariadb-database + app.kubernetes.io/version: 3.13.0-SNAPSHOT + template: + metadata: + labels: + app.kubernetes.io/name: camel-quarkus-examples-mariadb-database + app.kubernetes.io/version: 3.13.0-SNAPSHOT + spec: + containers: + - name: mariadb-database + image: docker.io/mariadb:10.11 + ports: + - containerPort: 3306 + env: + - name: MARIADB_USER + valueFrom: + secretKeyRef: + name: mariadb-secret + key: db-user + - name: MARIADB_PASSWORD + valueFrom: + secretKeyRef: + name: mariadb-secret + key: db-password + - name: MARIADB_DATABASE + value: my-db + - name: MARIADB_RANDOM_ROOT_PASSWORD + value: generate + volumeMounts: + # The /var/lib/mysql folder is where the actual database content is stored + - name: mariadb-database-data-volume + mountPath: /var/lib/mysql + volumes: + # Explicitly create an empty dir volume in order to ensure read/write access needed to store database files + - name: mariadb-database-data-volume + emptyDir: {} +--- +apiVersion: v1 +kind: Service +metadata: + labels: + app.kubernetes.io/name: camel-quarkus-examples-mariadb-database + app.kubernetes.io/version: 3.13.0-SNAPSHOT + name: mariadb-database +spec: + ports: + - name: mariadb + port: 3306 + targetPort: 3306 + selector: + app.kubernetes.io/name: camel-quarkus-examples-mariadb-database + app.kubernetes.io/version: 3.13.0-SNAPSHOT + type: ClusterIP +--- +apiVersion: v1 +kind: Secret +metadata: + labels: + app.kubernetes.io/name: camel-quarkus-examples-mariadb-database + app.kubernetes.io/version: 3.13.0-SNAPSHOT + name: mariadb-secret +type: Opaque +data: + # mariadb + db-user: bWFyaWFkYg== + # s3cr3t + db-password: czNjcjN0 +--- +apiVersion: batch/v1 +kind: Job +metadata: + name: camel-quarkus-examples-jpa-idempotent-repository-flyway-init +spec: + completionMode: NonIndexed + template: + metadata: + labels: + app.kubernetes.io/name: camel-quarkus-examples-jpa-idempotent-repository-flyway-init + app.kubernetes.io/version: 3.13.0-SNAPSHOT + spec: + containers: + - env: + - name: DB_HOSTNAME + value: mariadb-database + - name: JAVA_APP_JAR + value: /deployments/quarkus-run.jar + - name: QUARKUS_INIT_AND_EXIT + value: "true" + - name: QUARKUS_FLYWAY_ENABLED + value: "true" + image: camel-quarkus-examples-jpa-idempotent-repository:3.9.0 + name: camel-quarkus-examples-jpa-idempotent-repository-flyway-init + restartPolicy: OnFailure + serviceAccountName: camel-quarkus-examples-jpa-idempotent-repository diff --git a/data-extract-langchain4j/src/main/resources/application.properties b/data-extract-langchain4j/src/main/resources/application.properties new file mode 100644 index 0000000..e0373ef --- /dev/null +++ b/data-extract-langchain4j/src/main/resources/application.properties @@ -0,0 +1,63 @@ +## --------------------------------------------------------------------------- +## Licensed to the Apache Software Foundation (ASF) under one or more +## contributor license agreements. See the NOTICE file distributed with +## this work for additional information regarding copyright ownership. +## The ASF licenses this file to You under the Apache License, Version 2.0 +## (the "License"); you may not use this file except in compliance with +## the License. You may obtain a copy of the License at +## +## http://www.apache.org/licenses/LICENSE-2.0 +## +## Unless required by applicable law or agreed to in writing, software +## distributed under the License is distributed on an "AS IS" BASIS, +## WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. +## See the License for the specific language governing permissions and +## limitations under the License. +## --------------------------------------------------------------------------- + +quarkus.banner.enabled = false + +# Configure Quarkus LangChain4j needed to interact with the Large Language Model +quarkus.langchain4j.ollama.timeout = 3m +quarkus.langchain4j.ollama.chat-model.model-id = codellama +quarkus.langchain4j.ollama.chat-model.format = json +quarkus.langchain4j.ollama.chat-model.temperature = 0 + +# Uncomment to log HTTP traffic between langchain4j & the LLM API +quarkus.rest-client.logging.scope=request-response +quarkus.rest-client.logging.body-limit=10000 +quarkus.log.category."org.jboss.resteasy.reactive.client.logging".level=DEBUG + +# Uncomment if your application image is to be pushed to an external registry +#quarkus.container-image.registry=my.docker-registry.net + +# Kubernetes + +# Uncomment to trust self signed certificates if they are presented by the Kubernetes API server +#quarkus.kubernetes-client.trust-certs=true + +quarkus.kubernetes.image-pull-policy=IfNotPresent +quarkus.kubernetes.env.vars.db-hostname=mariadb-database + +# Enable the application to resolve the MariaDB credentials via a secret +quarkus.kubernetes.env.secrets=mariadb-secret +quarkus.kubernetes.env.mapping.db-user.from-secret=mariadb-secret +quarkus.kubernetes.env.mapping.db-user.with-key=db-user +quarkus.kubernetes.env.mapping.db-password.from-secret=mariadb-secret +quarkus.kubernetes.env.mapping.db-password.with-key=db-password + +# Uncomment to set resource limits +#quarkus.kubernetes.resources.requests.memory=64Mi +#quarkus.kubernetes.resources.requests.cpu=250m +#quarkus.kubernetes.resources.limits.memory=512Mi +#quarkus.kubernetes.resources.limits.cpu=1000m + +# OpenShift +quarkus.openshift.image-pull-policy=IfNotPresent +quarkus.openshift.env.vars.db-hostname=mariadb-database + +# Uncomment to set resource limits +#quarkus.openshift.resources.requests.memory=64Mi +#quarkus.openshift.resources.requests.cpu=250m +#quarkus.openshift.resources.limits.memory=512Mi +#quarkus.openshift.resources.limits.cpu=1000m diff --git a/data-extract-langchain4j/src/test/java/org/acme/extraction/OllamaTestResource.java b/data-extract-langchain4j/src/test/java/org/acme/extraction/OllamaTestResource.java new file mode 100644 index 0000000..9604ff0 --- /dev/null +++ b/data-extract-langchain4j/src/test/java/org/acme/extraction/OllamaTestResource.java @@ -0,0 +1,51 @@ +package org.acme.extraction; + +import java.util.HashMap; +import java.util.Map; + +import io.quarkus.test.common.QuarkusTestResourceLifecycleManager; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; +import org.testcontainers.containers.GenericContainer; +import org.testcontainers.containers.output.Slf4jLogConsumer; +import org.testcontainers.containers.wait.strategy.Wait; + +public class OllamaTestResource implements QuarkusTestResourceLifecycleManager { + + private static final Logger LOG = LoggerFactory.getLogger(OllamaTestResource.class); + private static final String OLLAMA_IMAGE = "langchain4j/ollama-codellama:latest"; + private static final int OLLAMA_SERVER_PORT = 11434; + + private GenericContainer<?> ollamaContainer; + + @Override + public Map<String, String> start() { + Map<String, String> properties = new HashMap<>(); + + LOG.info("Starting Ollama container resource"); + ollamaContainer = new GenericContainer<>(OLLAMA_IMAGE) + .withExposedPorts(OLLAMA_SERVER_PORT) + .withLogConsumer(new Slf4jLogConsumer(LOG).withPrefix("basicAuthContainer")) + .waitingFor(Wait.forLogMessage(".* msg=\"inference compute\" .*", 1)); + + ollamaContainer.start(); + + String baseUrl = String.format("http://%s:%s", ollamaContainer.getHost(), + ollamaContainer.getMappedPort(OLLAMA_SERVER_PORT)); + properties.put("quarkus.langchain4j.ollama.base-url", baseUrl); + + return properties; + } + + @Override + public void stop() { + try { + if (ollamaContainer != null) { + ollamaContainer.stop(); + } + } catch (Exception ex) { + LOG.error("An issue occurred while stopping " + ollamaContainer.getNetworkAliases(), ex); + } + } + +} diff --git a/data-extract-langchain4j/src/test/java/org/acme/extraction/RouteIT.java b/data-extract-langchain4j/src/test/java/org/acme/extraction/RouteIT.java new file mode 100644 index 0000000..8a74314 --- /dev/null +++ b/data-extract-langchain4j/src/test/java/org/acme/extraction/RouteIT.java @@ -0,0 +1,8 @@ +package org.acme.extraction; + +import io.quarkus.test.junit.QuarkusIntegrationTest; + +@QuarkusIntegrationTest +public class RouteIT extends RouteTest { + +} diff --git a/data-extract-langchain4j/src/test/java/org/acme/extraction/RouteTest.java b/data-extract-langchain4j/src/test/java/org/acme/extraction/RouteTest.java new file mode 100644 index 0000000..6677026 --- /dev/null +++ b/data-extract-langchain4j/src/test/java/org/acme/extraction/RouteTest.java @@ -0,0 +1,46 @@ +package org.acme.extraction; + +import java.io.IOException; + +import com.github.dockerjava.zerodep.shaded.org.apache.commons.codec.Charsets; +import io.quarkus.test.common.QuarkusTestResource; +import io.quarkus.test.junit.QuarkusTest; +import io.restassured.RestAssured; +import io.restassured.config.HttpClientConfig; +import io.restassured.config.RestAssuredConfig; +import io.restassured.http.ContentType; +import org.junit.jupiter.api.Test; + +import static io.restassured.RestAssured.given; +import static org.apache.commons.io.IOUtils.resourceToString; +import static org.hamcrest.Matchers.empty; +import static org.hamcrest.Matchers.is; +import static org.hamcrest.Matchers.not; + +@QuarkusTestResource(OllamaTestResource.class) +@QuarkusTest +public class RouteTest { + + @Test + void customPojoExtractionServiceReturnPojo() throws IOException { + + RestAssuredConfig newConfig = RestAssured.config() + .httpClient(HttpClientConfig.httpClientConfig().setParam("http.connection.timeout", 180000)); + + String conversation = resourceToString("/texts/03_kate-boss-13-08-1999-satisfied.txt", Charsets.UTF_8); + + given() + .config(newConfig) + .contentType(ContentType.JSON) + .body(conversation) + .when() + .post("/custom-pojo-extraction-service") + .then() + .statusCode(200) + .body("customerSatisfied", is("true")) + .body("customerName", is("Kate Boss")) + .body("customerBirthday", is("13 August 1999")) + .body("summary", not(empty())); + } + +} diff --git a/data-extract-langchain4j/src/test/resources/application.properties b/data-extract-langchain4j/src/test/resources/application.properties new file mode 100644 index 0000000..8d298e8 --- /dev/null +++ b/data-extract-langchain4j/src/test/resources/application.properties @@ -0,0 +1,10 @@ +# TODO: should we remove part of this ? redundant with src/main/resources/application.properties + +quarkus.langchain4j.ollama.chat-model.model-id=codellama +quarkus.langchain4j.ollama.log-requests=false +quarkus.langchain4j.ollama.log-responses=false +quarkus.langchain4j.ollama.chat-model.temperature=0.0 +#quarkus.langchain4j.ollama.chat-model.top-p=0.0 +#quarkus.langchain4j.ollama.chat-model.top-k=0 +quarkus.langchain4j.ollama.chat-model.format=json +quarkus.langchain4j.ollama.timeout=3m diff --git a/data-extract-langchain4j/src/test/resources/texts/01_sarah-london-10-07-1986-satisfied.txt b/data-extract-langchain4j/src/test/resources/texts/01_sarah-london-10-07-1986-satisfied.txt new file mode 100644 index 0000000..ae6e5ff --- /dev/null +++ b/data-extract-langchain4j/src/test/resources/texts/01_sarah-london-10-07-1986-satisfied.txt @@ -0,0 +1,8 @@ +Operator: Hello, how may I help you ? +Customer: Hello, I'm calling because I need to declare an accident on my main vehicle. +Operator: Ok, can you please give me your name ? +Customer: My name is Sarah London. +Operator: Could you please give me your birth date ? +Customer: 1986, July the 10th. +Operator: Ok, I've got your contract and I'm happy to share with you that we'll be able to reimburse all expenses linked to this accident. +Customer: Oh great, many thanks. \ No newline at end of file diff --git a/data-extract-langchain4j/src/test/resources/texts/02_john-doe-01-11-2001-unsatisfied.txt b/data-extract-langchain4j/src/test/resources/texts/02_john-doe-01-11-2001-unsatisfied.txt new file mode 100644 index 0000000..8ee8cdd --- /dev/null +++ b/data-extract-langchain4j/src/test/resources/texts/02_john-doe-01-11-2001-unsatisfied.txt @@ -0,0 +1,13 @@ +Operator: Hello, how may I help you ? +Customer: Hello, I'm John. I need to share a problem with you. Actually, the insurance has reimbursed only half the money I have spent due to the accident. +Operator: Hello John, could you please give me your last name so that I can find your contract. +Customer: Sure, my surname is Doe. +Operator: And last thing, I need to know the date you were born. +Customer: Yes, so I was born in 2001, actually during the first day of November. +Operator: Great, I see your contract now. Actually, the full reimbursement option has been cancelled automatically by our system. This explain the half reimbursement. +Customer: Ah damn, this is not acceptable. I've not even been notified about this automatic change. +Operator: Oh, I'm sorry to hear that but the full reimbursement option was free for one year and at the time of subscription you were not interested in automatic renewal. +Customer: I don't discuss that. The important fact is that I should have been notified. +Operator: Sure, I understand your resentment. The best I can do is to inform my manager. +Customer: OK, let's do that. Good bye. +Operator: Good bye. And again let me apologize for the issue. \ No newline at end of file diff --git a/data-extract-langchain4j/src/test/resources/texts/03_kate-boss-13-08-1999-satisfied.txt b/data-extract-langchain4j/src/test/resources/texts/03_kate-boss-13-08-1999-satisfied.txt new file mode 100644 index 0000000..0ef1aa7 --- /dev/null +++ b/data-extract-langchain4j/src/test/resources/texts/03_kate-boss-13-08-1999-satisfied.txt @@ -0,0 +1,12 @@ +Operator: Hello, how may I help you? +Customer: Hello, I am currently at the police station because I've got an accident. The police would need a proof that I have an insurance. Could you please help me? +Operator: Sure, could you please remind me your name and birth date? +Customer: Of course, my name is Kate Hart and I was born on August the thirteen in the year nineteen ninety nine. +Operator: I'm sorry Kate, but we don't have any contract in our records. +Customer: Oh, I'm sorry that I've made a mistake. Actually, my last name is not Hart, but Boss. It changed since I'm married. +Operator: Indeed, I have now found your contract and everything looks good. Shall I send the proof of insurance to the police station? +Customer: Oh, if possible, my husband will go directly to your office in order to get it. +Operator: Yes, that's possible. I will let the paper at the entrance. Your beloved could just ask it to the front desk. +Customer: Many thanks. That's so helpful. I'm a bit more relieved now. +Operator: Sure, you're welcome Kate. Please come back to us any time in case more information is needed. Bye. +Customer: Bye. \ No newline at end of file