@@ -676,3 +676,238 @@ curl --request GET \
676
676
```
677
677
678
678
::: zone-end
679
+
680
+ ::: zone pivot="java"
681
+
682
+ ``` java
683
+ package com.example.agents ;
684
+
685
+ import com.azure.ai.agents.persistent.MessagesClient ;
686
+ import com.azure.ai.agents.persistent.PersistentAgentsAdministrationClient ;
687
+ import com.azure.ai.agents.persistent.PersistentAgentsClient ;
688
+ import com.azure.ai.agents.persistent.PersistentAgentsClientBuilder ;
689
+ import com.azure.ai.agents.persistent.RunsClient ;
690
+ import com.azure.ai.agents.persistent.ThreadsClient ;
691
+ import com.azure.ai.agents.persistent.models.CreateAgentOptions ;
692
+ import com.azure.ai.agents.persistent.models.CreateRunOptions ;
693
+ import com.azure.ai.agents.persistent.models.FunctionDefinition ;
694
+ import com.azure.ai.agents.persistent.models.FunctionToolDefinition ;
695
+ import com.azure.ai.agents.persistent.models.MessageImageFileContent ;
696
+ import com.azure.ai.agents.persistent.models.MessageRole ;
697
+ import com.azure.ai.agents.persistent.models.MessageTextContent ;
698
+ import com.azure.ai.agents.persistent.models.PersistentAgent ;
699
+ import com.azure.ai.agents.persistent.models.PersistentAgentThread ;
700
+ import com.azure.ai.agents.persistent.models.RequiredFunctionToolCall ;
701
+ import com.azure.ai.agents.persistent.models.RequiredToolCall ;
702
+ import com.azure.ai.agents.persistent.models.RunStatus ;
703
+ import com.azure.ai.agents.persistent.models.SubmitToolOutputsAction ;
704
+ import com.azure.ai.agents.persistent.models.ThreadMessage ;
705
+ import com.azure.ai.agents.persistent.models.ThreadRun ;
706
+ import com.azure.ai.agents.persistent.models.ToolOutput ;
707
+ import com.azure.ai.agents.persistent.models.MessageContent ;
708
+ import com.azure.core.http.rest.PagedIterable ;
709
+ import com.azure.core.util.BinaryData ;
710
+ import com.azure.identity.DefaultAzureCredentialBuilder ;
711
+ import com.fasterxml.jackson.core.JsonProcessingException ;
712
+ import com.fasterxml.jackson.databind.JsonNode ;
713
+ import com.fasterxml.jackson.databind.json.JsonMapper ;
714
+
715
+ import java.net.URL ;
716
+ import java.io.File ;
717
+ import java.io.FileNotFoundException ;
718
+ import java.net.URISyntaxException ;
719
+ import java.nio.file.Path ;
720
+ import java.util.ArrayList ;
721
+ import java.util.Arrays ;
722
+ import java.util.HashMap ;
723
+ import java.util.Map ;
724
+ import java.util.function.Function ;
725
+
726
+ public class AgentExample {
727
+
728
+ public static void main (String [] args ) throws FileNotFoundException , URISyntaxException {
729
+
730
+ // variables for authenticating requests to the agent service
731
+ String projectEndpoint = " https://aahi-may-resource.services.ai.azure.com/api/projects/aahi-may" ;// System.getenv("PROJECT_ENDPOINT");
732
+ String modelName = " gpt-4o" ;// System.getenv("MODEL_DEPLOYMENT_NAME");
733
+
734
+ PersistentAgentsClientBuilder clientBuilder = new PersistentAgentsClientBuilder (). endpoint(projectEndpoint)
735
+ .credential(new DefaultAzureCredentialBuilder (). build());
736
+ PersistentAgentsClient agentsClient = clientBuilder. buildClient();
737
+ PersistentAgentsAdministrationClient administrationClient = agentsClient. getPersistentAgentsAdministrationClient();
738
+ ThreadsClient threadsClient = agentsClient. getThreadsClient();
739
+ MessagesClient messagesClient = agentsClient. getMessagesClient();
740
+ RunsClient runsClient = agentsClient. getRunsClient();
741
+
742
+ Supplier<String > getUserFavoriteCity = () - > " Seattle, WA" ;
743
+ FunctionToolDefinition getUserFavoriteCityTool = new FunctionToolDefinition (
744
+ new FunctionDefinition (
745
+ " getUserFavoriteCity" ,
746
+ BinaryData . fromObject(
747
+ new Object ()
748
+ ))
749
+ );
750
+
751
+ Function<String , String > getCityNickname = location - > {
752
+ return " The Emerald City" ;
753
+ };
754
+
755
+ FunctionToolDefinition getCityNicknameTool = new FunctionToolDefinition (
756
+ new FunctionDefinition (
757
+ " getCityNickname" ,
758
+ BinaryData . fromObject(
759
+ mapOf(
760
+ " type" , " object" ,
761
+ " properties" , mapOf(
762
+ " location" ,
763
+ mapOf(
764
+ " type" , " string" ,
765
+ " description" , " The city and state, e.g. San Francisco, CA" )
766
+ ),
767
+ " required" , new String []{" location" }))
768
+ ). setDescription(" Get the nickname of a city" )
769
+ );
770
+
771
+ Function<RequiredToolCall , ToolOutput > getResolvedToolOutput = toolCall - > {
772
+ if (toolCall instanceof RequiredFunctionToolCall ) {
773
+ RequiredFunctionToolCall functionToolCall = (RequiredFunctionToolCall ) toolCall;
774
+ String functionName = functionToolCall. getFunction(). getName();
775
+ if (functionName. equals(" getUserFavoriteCity" )) {
776
+ return new ToolOutput (). setToolCallId(functionToolCall. getId())
777
+ .setOutput(getUserFavoriteCity. get());
778
+ } else if (functionName. equals(" getCityNickname" )) {
779
+ String arguments = functionToolCall. getFunction(). getArguments();
780
+ try {
781
+ JsonNode root = new JsonMapper (). readTree(arguments);
782
+ String location = String . valueOf(root. get(" location" ). asText());
783
+ return new ToolOutput (). setToolCallId(functionToolCall. getId())
784
+ .setOutput(getCityNickname. apply(location));
785
+ } catch (JsonProcessingException e) {
786
+ throw new RuntimeException (e);
787
+ }
788
+ }
789
+ }
790
+ return null ;
791
+ };
792
+
793
+ String agentName = " functions_example" ;
794
+ CreateAgentOptions createAgentOptions = new CreateAgentOptions (modelName)
795
+ .setName(agentName)
796
+ .setInstructions(" You are a weather bot. Use the provided functions to help answer questions. "
797
+ + " Customize your responses to the user's preferences as much as possible and use friendly "
798
+ + " nicknames for cities whenever possible." )
799
+ .setTools(Arrays . asList(getUserFavoriteCityTool, getCityNicknameTool));
800
+ PersistentAgent agent = administrationClient. createAgent(createAgentOptions);
801
+
802
+ PersistentAgentThread thread = threadsClient. createThread();
803
+ ThreadMessage createdMessage = messagesClient. createMessage(
804
+ thread. getId(),
805
+ MessageRole . USER ,
806
+ " What's the nickname of my favorite city?" );
807
+
808
+ try {
809
+ // run agent
810
+ CreateRunOptions createRunOptions = new CreateRunOptions (thread. getId(), agent. getId())
811
+ .setAdditionalInstructions(" " );
812
+ ThreadRun threadRun = runsClient. createRun(createRunOptions);
813
+
814
+ do {
815
+ Thread . sleep(500 );
816
+ threadRun = runsClient. getRun(thread. getId(), threadRun. getId());
817
+ if (threadRun. getStatus() == RunStatus . REQUIRES_ACTION
818
+ && threadRun. getRequiredAction() instanceof SubmitToolOutputsAction ) {
819
+ SubmitToolOutputsAction submitToolsOutputAction = (SubmitToolOutputsAction ) (threadRun. getRequiredAction());
820
+ ArrayList<ToolOutput > toolOutputs = new ArrayList<ToolOutput > ();
821
+ for (RequiredToolCall toolCall : submitToolsOutputAction. getSubmitToolOutputs(). getToolCalls()) {
822
+ toolOutputs. add(getResolvedToolOutput. apply(toolCall));
823
+ }
824
+ threadRun = runsClient. submitToolOutputsToRun(thread. getId(), threadRun. getId(), toolOutputs);
825
+ }
826
+ }
827
+ while (
828
+ threadRun. getStatus() == RunStatus . QUEUED
829
+ || threadRun. getStatus() == RunStatus . IN_PROGRESS
830
+ || threadRun. getStatus() == RunStatus . REQUIRES_ACTION );
831
+
832
+ if (threadRun. getStatus() == RunStatus . FAILED ) {
833
+ System . out. println(threadRun. getLastError(). getMessage());
834
+ }
835
+
836
+ printRunMessages(messagesClient, thread. getId());
837
+ } catch (InterruptedException e) {
838
+ throw new RuntimeException (e);
839
+ } finally {
840
+ // cleanup
841
+ threadsClient. deleteThread(thread. getId());
842
+ administrationClient. deleteAgent(agent. getId());
843
+ }
844
+ }
845
+
846
+ // Use "Map.of" if available
847
+ @SuppressWarnings (" unchecked" )
848
+ private static <T > Map<String , T > mapOf (Object ... inputs ) {
849
+ Map<String , T > map = new HashMap<> ();
850
+ for (int i = 0 ; i < inputs. length; i += 2 ) {
851
+ String key = (String ) inputs[i];
852
+ T value = (T ) inputs[i + 1 ];
853
+ map. put(key, value);
854
+ }
855
+ return map;
856
+ }
857
+ // A helper function to print messages from the agent
858
+ public static void printRunMessages (MessagesClient messagesClient , String threadId ) {
859
+
860
+ PagedIterable<ThreadMessage > runMessages = messagesClient. listMessages(threadId);
861
+ for (ThreadMessage message : runMessages) {
862
+ System . out. print(String . format(" %1$s - %2$s : " , message. getCreatedAt(), message. getRole()));
863
+ for (MessageContent contentItem : message. getContent()) {
864
+ if (contentItem instanceof MessageTextContent ) {
865
+ System . out. print((((MessageTextContent ) contentItem). getText(). getValue()));
866
+ } else if (contentItem instanceof MessageImageFileContent ) {
867
+ String imageFileId = (((MessageImageFileContent ) contentItem). getImageFile(). getFileId());
868
+ System . out. print(" Image from ID: " + imageFileId);
869
+ }
870
+ System . out. println();
871
+ }
872
+ }
873
+ }
874
+
875
+ // a helper function to wait until a run has completed running
876
+ public static void waitForRunCompletion (String threadId , ThreadRun threadRun , RunsClient runsClient )
877
+ throws InterruptedException {
878
+
879
+ do {
880
+ Thread . sleep(500 );
881
+ threadRun = runsClient. getRun(threadId, threadRun. getId());
882
+ }
883
+ while (
884
+ threadRun. getStatus() == RunStatus . QUEUED
885
+ || threadRun. getStatus() == RunStatus . IN_PROGRESS
886
+ || threadRun. getStatus() == RunStatus . REQUIRES_ACTION );
887
+
888
+ if (threadRun. getStatus() == RunStatus . FAILED ) {
889
+ System . out. println(threadRun. getLastError(). getMessage());
890
+ }
891
+ }
892
+ private static Path getFile (String fileName ) throws FileNotFoundException , URISyntaxException {
893
+ URL resource = AgentExample . class. getClassLoader(). getResource(fileName);
894
+ if (resource == null ) {
895
+ throw new FileNotFoundException (" File not found" );
896
+ }
897
+ File file = new File (resource. toURI());
898
+ return file. toPath();
899
+ }
900
+ @FunctionalInterface
901
+ public interface Supplier <T> extends java.util.function.Supplier<T > {
902
+ /**
903
+ * Retrieves an instance of the appropriate type. The returned object may or may not be a new
904
+ * instance, depending on the implementation.
905
+ *
906
+ * @return an instance of the appropriate type
907
+ */
908
+ @Override
909
+ T get ();
910
+ }
911
+ }
912
+ ```
913
+ ::: zone-end
0 commit comments