diff --git a/java-ai/auth_and_run.sh b/java-ai/auth_and_run.sh new file mode 100644 index 0000000..f8cb18e --- /dev/null +++ b/java-ai/auth_and_run.sh @@ -0,0 +1,7 @@ +#!/bin/bash + +# token itself expires after 1 hour, but it is automatically refreshed as long as the stored credentials remain valid. +# provides long-lived authentication (~1 week) via Application Default Credentials (ADC). +gcloud auth application-default login +mvn clean package +java -jar .\target\oracleai-0.0.1-SNAPSHOT.jar diff --git a/java-ai/pom.xml b/java-ai/pom.xml index 56b6aa3..d63c0d7 100644 --- a/java-ai/pom.xml +++ b/java-ai/pom.xml @@ -16,8 +16,29 @@ 3.52.1 + 21.7.0.0 + + + + + com.google.cloud + libraries-bom + 26.32.0 + pom + import + + + + + + + + + + + org.springframework.boot @@ -40,7 +61,7 @@ com.oracle.cloud.spring spring-cloud-oci-starter - 1.3.0 + 1.4.0 com.oracle.oci.sdk @@ -99,6 +120,112 @@ service 0.12.0 + + + org.springframework.boot + spring-boot-starter-security + + + + + + + + com.oracle.database.jdbc + ojdbc8 + ${oracle.jdbc.version} + + + com.oracle.database.jdbc + ucp + ${oracle.jdbc.version} + + + com.oracle.database.security + oraclepki + ${oracle.jdbc.version} + + + com.oracle.database.security + osdt_core + ${oracle.jdbc.version} + + + com.oracle.database.security + osdt_cert + ${oracle.jdbc.version} + + + + com.google.cloud + google-cloud-texttospeech + + + com.google.cloud + google-cloud-speech + + + net.sourceforge.argparse4j + argparse4j + 0.9.0 + + + + + org.springframework.boot + spring-boot-starter-websocket + + + + + commons-cli + commons-cli + 1.6.0 + + + + com.google.auth + google-auth-library-oauth2-http + 1.18.0 + + + + jakarta.websocket + jakarta.websocket-api + 2.2.0 + + + + + org.apache.tomcat.embed + tomcat-embed-websocket + + + + + org.glassfish.tyrus + tyrus-server + 2.1.3 + + + + org.glassfish.tyrus + tyrus-container-servlet + 2.1.3 + + diff --git a/java-ai/src/main/java/oracleai/BinaryServerConfigurator.java b/java-ai/src/main/java/oracleai/BinaryServerConfigurator.java new file mode 100644 index 0000000..affa550 --- /dev/null +++ b/java-ai/src/main/java/oracleai/BinaryServerConfigurator.java @@ -0,0 +1,11 @@ +package oracleai; + +import jakarta.websocket.server.ServerEndpointConfig; + +public class BinaryServerConfigurator extends ServerEndpointConfig.Configurator { + @Override + public boolean checkOrigin(String originHeaderValue) { + System.out.println("✅ WebSocket checkOrigin originHeaderValue: " + originHeaderValue); + return true; // Allow all origins for WebSocket + } +} diff --git a/java-ai/src/main/java/oracleai/EchoController.java b/java-ai/src/main/java/oracleai/EchoController.java deleted file mode 100644 index 23b1d5a..0000000 --- a/java-ai/src/main/java/oracleai/EchoController.java +++ /dev/null @@ -1,22 +0,0 @@ -package oracleai; - -import org.springframework.web.bind.annotation.*; - -@RestController -@RequestMapping("/echo") -public class EchoController { - private String theValue = "init"; - - @GetMapping("/set") - public String setValue(@RequestParam("value") String value) { - theValue = value; - System.out.println("EchoController set: " + theValue); - return "set successfully: " + theValue; - } - - @GetMapping("/get") - public String getValue() { - System.out.println("EchoController get: " + theValue); - return theValue; - } -} diff --git a/java-ai/src/main/java/oracleai/SpeechWebSocketConfigurator.java b/java-ai/src/main/java/oracleai/SpeechWebSocketConfigurator.java new file mode 100644 index 0000000..47ced3b --- /dev/null +++ b/java-ai/src/main/java/oracleai/SpeechWebSocketConfigurator.java @@ -0,0 +1,12 @@ +package oracleai; + +import jakarta.websocket.server.HandshakeRequest; +import jakarta.websocket.HandshakeResponse; +import jakarta.websocket.server.ServerEndpointConfig; + +public class SpeechWebSocketConfigurator extends ServerEndpointConfig.Configurator { + @Override + public void modifyHandshake(ServerEndpointConfig sec, HandshakeRequest request, HandshakeResponse response) { + sec.getUserProperties().put("org.apache.tomcat.websocket.binaryBufferSize", 1024 * 1024); // Enable binary message support + } +} diff --git a/java-ai/src/main/java/oracleai/SpeechWebSocketServer.java b/java-ai/src/main/java/oracleai/SpeechWebSocketServer.java new file mode 100644 index 0000000..6769a33 --- /dev/null +++ b/java-ai/src/main/java/oracleai/SpeechWebSocketServer.java @@ -0,0 +1,160 @@ +package oracleai; + +import com.google.api.gax.rpc.BidiStreamingCallable; +import com.google.api.gax.rpc.ApiStreamObserver; +import com.google.cloud.speech.v1.*; +import com.google.protobuf.ByteString; + +import jakarta.websocket.*; +import jakarta.websocket.server.ServerEndpoint; +import java.io.*; +import java.nio.ByteBuffer; +import java.util.concurrent.Executors; +import java.util.concurrent.ScheduledExecutorService; +import javax.sound.sampled.*; + +import org.springframework.stereotype.Component; + +@ServerEndpoint(value = "/speech", configurator = SpeechWebSocketConfigurator.class) +@Component +public class SpeechWebSocketServer { + private static final ScheduledExecutorService executorService = Executors.newSingleThreadScheduledExecutor(); + private static SpeechClient speechClient; + private ApiStreamObserver requestObserver; + + static { + try { + speechClient = SpeechClient.create(); + } catch (IOException e) { + throw new RuntimeException("❌ Failed to initialize SpeechClient", e); + } + } + + @OnOpen + public void onOpen(Session session) { + System.out.println("✅ WebSocket Connected: " + session.getId()); + session.setMaxBinaryMessageBufferSize(1024 * 1024); // Allow large audio messages + + ApiStreamObserver responseObserver = new ApiStreamObserver<>() { + @Override + public void onNext(StreamingRecognizeResponse response) { + for (StreamingRecognitionResult result : response.getResultsList()) { + if (result.getAlternativesCount() > 0) { + String transcript = result.getAlternatives(0).getTranscript().trim(); + if (!transcript.isEmpty()) { + System.out.println("📝 Transcription: " + transcript); + try { + session.getBasicRemote().sendText(transcript); + } catch (IOException e) { + e.printStackTrace(); + } + } + } + } + } + + @Override + public void onError(Throwable t) { + System.err.println("❌ Google API Error: " + t.getMessage()); + } + + @Override + public void onCompleted() { + System.out.println("✅ Streaming completed."); + } + }; + + // Initialize Streaming to Google Speech API + BidiStreamingCallable callable = + speechClient.streamingRecognizeCallable(); + requestObserver = callable.bidiStreamingCall(responseObserver); + + requestObserver.onNext(StreamingRecognizeRequest.newBuilder() + .setStreamingConfig(StreamingRecognitionConfig.newBuilder() + .setConfig(RecognitionConfig.newBuilder() + .setEncoding(RecognitionConfig.AudioEncoding.LINEAR16) + .setSampleRateHertz(16000) + .setLanguageCode("en-US") + .setAudioChannelCount(1) + .setEnableAutomaticPunctuation(true) + .build()) + .setInterimResults(true) + .setSingleUtterance(false) + .build()) + .build()); + } + + /** + * 🔹 **Handles Incoming Binary Audio Data (From WebSocket)** + * This method now **reads a WAV file** instead of processing real-time audio streaming. + */ + @OnMessage + public void onMessage(Session session) { + String filePath = "C:/Users/opc/Downloads/audio_logs/sample.wav"; // Change to your WAV file path + byte[] audioBytes; + + try { + audioBytes = readWavFile(filePath); + if (audioBytes == null || audioBytes.length == 0) { + System.out.println("⚠️ WAV file is empty or could not be read."); + return; + } + } catch (IOException | UnsupportedAudioFileException e) { + System.err.println("❌ Error reading WAV file: " + e.getMessage()); + return; + } + + System.out.println("✅ Sending Audio Data from WAV file: " + audioBytes.length + " bytes"); + + if (requestObserver != null) { + requestObserver.onNext(StreamingRecognizeRequest.newBuilder() + .setAudioContent(ByteString.copyFrom(audioBytes)) + .build()); + } + } + + @OnClose + public void onClose(Session session) { + System.out.println("🔴 WebSocket Closed: " + session.getId()); + if (requestObserver != null) { + requestObserver.onCompleted(); + } + } + + @OnError + public void onError(Session session, Throwable throwable) { + System.err.println("⚠️ WebSocket error: " + throwable.getMessage()); + } + + /** + * **🔹 Reads WAV File and Extracts PCM Data** + * - Converts **WAV file** to **raw PCM data**. + * - Ensures it is in the **correct format** (16-bit mono PCM). + */ + private byte[] readWavFile(String filePath) throws IOException, UnsupportedAudioFileException { + File file = new File(filePath); + AudioInputStream audioInputStream = AudioSystem.getAudioInputStream(file); + AudioFormat format = audioInputStream.getFormat(); + + System.out.println("🎵 WAV File Format: " + format); + + // Convert to PCM Signed if necessary + if (format.getEncoding() != AudioFormat.Encoding.PCM_SIGNED) { + AudioFormat pcmFormat = new AudioFormat( + AudioFormat.Encoding.PCM_SIGNED, + format.getSampleRate(), + 16, // Force 16-bit audio + format.getChannels(), + format.getChannels() * 2, + format.getSampleRate(), + false // Little-endian + ); + audioInputStream = AudioSystem.getAudioInputStream(pcmFormat, audioInputStream); + } + + // Read raw audio data + byte[] audioBytes = audioInputStream.readAllBytes(); + audioInputStream.close(); + return audioBytes; + } +} diff --git a/java-ai/src/main/java/oracleai/WebConfig.java b/java-ai/src/main/java/oracleai/WebConfig.java index 755ea75..e9d1c5f 100644 --- a/java-ai/src/main/java/oracleai/WebConfig.java +++ b/java-ai/src/main/java/oracleai/WebConfig.java @@ -6,13 +6,18 @@ import org.springframework.web.servlet.config.annotation.WebMvcConfigurer; @Configuration -public class WebConfig implements WebMvcConfigurer { - @Override - public void addCorsMappings(CorsRegistry registry) { - registry.addMapping("/**") // This will apply to all routes - .allowedOrigins("https://130.61.51.75:4884") // Allow this origin - .allowedMethods("GET", "POST", "PUT", "DELETE") // Allowed methods - .allowedHeaders("*") // Allowed headers - .allowCredentials(true); // Allow credentials +public class WebConfig { + @Bean + public WebMvcConfigurer corsConfigurer() { + return new WebMvcConfigurer() { + @Override + public void addCorsMappings(CorsRegistry registry) { + registry.addMapping("/**") // Apply to all endpoints + .allowedOriginPatterns("*") // ✅ Use allowedOriginPatterns instead of "*" + .allowedMethods("GET", "POST", "PUT", "DELETE", "OPTIONS") + .allowedHeaders("*") + .allowCredentials(true); // ✅ Keep credentials enabled + } + }; } } diff --git a/java-ai/src/main/java/oracleai/aiholo/AIHoloController.java b/java-ai/src/main/java/oracleai/aiholo/AIHoloController.java new file mode 100644 index 0000000..59f5875 --- /dev/null +++ b/java-ai/src/main/java/oracleai/aiholo/AIHoloController.java @@ -0,0 +1,269 @@ +package oracleai.aiholo; + +import java.io.FileOutputStream; +import java.io.FileWriter; +import java.io.IOException; +import java.io.OutputStream; +import java.util.concurrent.Executors; +import java.util.concurrent.ScheduledExecutorService; +import java.util.concurrent.TimeUnit; + +import org.json.JSONObject; +import org.springframework.web.bind.annotation.*; +import org.springframework.web.client.RestTemplate; + +import com.google.cloud.texttospeech.v1.AudioEncoding; +import com.google.cloud.texttospeech.v1.SsmlVoiceGender; +import com.google.cloud.texttospeech.v1.SynthesisInput; +import com.google.cloud.texttospeech.v1.SynthesizeSpeechResponse; +import com.google.cloud.texttospeech.v1.TextToSpeechClient; +import com.google.cloud.texttospeech.v1.VoiceSelectionParams; +import com.google.protobuf.ByteString; +import com.google.cloud.texttospeech.v1.AudioConfig; + +import org.springframework.beans.factory.annotation.Autowired; + +import javax.sql.*; + +import java.sql.*; +import java.util.HashMap; +import java.util.Map; +import org.springframework.http.*; +import org.springframework.stereotype.Service; + +@RestController +@RequestMapping("/aiholo") +// @CrossOrigin(origins = "*") +public class AIHoloController { + private String theValue = "mirrorme"; + private static final ScheduledExecutorService scheduler = Executors.newScheduledThreadPool(1); + private static final String API_URL = "http://129.x.x.x/v1/chat/completions?client=server"; + private static final String AUTH_TOKEN = "Bearer asdf"; + private static final String DEFAULT_LANGUAGE_CODE = "pt-BR"; + private static final String DEFAULT_VOICE_NAME = "pt-BR-Wavenet-D"; + +// @Autowired + private DataSource dataSource; + + private static final Object metahumanLock = new Object(); + private static boolean isRecentQuestionProcessed; + + public AIHoloController() { + System.out.println("startInactivityMonitor..."); + startInactivityMonitor(); + } + + private void startInactivityMonitor() { + scheduler.scheduleAtFixedRate(() -> { + if (isRecentQuestionProcessed) { + System.out.println("isRecentQuestionProcessed true so skipping the timecheck/keepalive"); + isRecentQuestionProcessed = false; + } + String fileName = "currenttime.wav"; //testing123-brazil.wav + TTSAndAudio2Face.processMetahuman( + fileName, "a hora é agora " + TimeInWords.getTimeInWords(true), + DEFAULT_LANGUAGE_CODE, DEFAULT_VOICE_NAME); + }, 1, 15, TimeUnit.MINUTES); + } + + + static String sql = """ + SELECT DBMS_CLOUD_AI.GENERATE( + prompt => ?, + profile_name => 'VIDEOGAMES_PROFILE', + action => ? + ) FROM dual + """; + + @GetMapping("/play") + public String play(@RequestParam("question") String question, + @RequestParam("selectedMode") String selectedMode, + @RequestParam("languagecode") String languagecode, + @RequestParam("voicename") String voicename) throws Exception { + System.out.println( + "play question: " + question + " selectedMode: " + selectedMode + + " languagecode:"+ languagecode+ " voicename:"+ voicename); + question = "qual é o videogame mais popular"; + System.out.println( + "modified question: " + question ); + theValue = "question"; + String filePath = "C:/Users/opc/aiholo_output.txt"; + try (FileWriter writer = new FileWriter(filePath)) { + JSONObject json = new JSONObject(); + json.put("data", theValue); // Store the response inside JSON + writer.write(json.toString()); + writer.flush(); + } catch (IOException e) { + return "Error writing to file: " + e.getMessage(); + } + String answer = "I'm sorry. I couldn't find an answer", action = "chat"; //TODO, this should be in correct language + if (question.contains("use vectorrag")) { + action = "vectorrag"; + question = question.replace("use vectorrag", "").trim(); + answer = executeSandbox(question); + } else { + if (selectedMode.contains("use narrate")) { + action = "narrate"; +// question = question.replace("use narrate", "").trim(); + } else { + question = question.replace("use chat", "").trim(); + } + try (Connection connection = dataSource.getConnection(); + PreparedStatement preparedStatement = connection.prepareStatement(sql)) { + System.out.println("Database Connection : " + connection); + String response = null; + preparedStatement.setString(1, question); + preparedStatement.setString(2, action); + try (ResultSet resultSet = preparedStatement.executeQuery()) { + if (resultSet.next()) { + response = resultSet.getString(1); // Retrieve AI response from the first column + } + } + answer = response; + } catch (SQLException e) { + System.err.println("Failed to connect to the database: " + e.getMessage()); + return "Database Connection Failed!"; + } + } + String fileName = "output.wav"; + System.out.println("about to TTS and sendAudioToAudio2Face for answer: " + answer); + TTSAndAudio2Face.processMetahuman(fileName, answer, languagecode, voicename); + return answer; + } + + + + + + + + + + + + + public String executeSandbox(String cummulativeResult) { + System.out.println("isRag is true, using AI sandbox: " + cummulativeResult); + + // Remove "use RAG" references + // cummulativeResult = cummulativeResult.replace("use RAG", "").replace("use rag", "").trim(); + // cummulativeResult += " . Make answer one sentence that is shorter than 50 words"; + + // Prepare request body + Map payload = new HashMap<>(); + Map message = new HashMap<>(); + message.put("role", "user"); + message.put("content", cummulativeResult); + payload.put("messages", new Object[] { message }); + + // Convert payload to JSON + JSONObject jsonPayload = new JSONObject(payload); + + // Set headers + HttpHeaders headers = new HttpHeaders(); + headers.setContentType(MediaType.APPLICATION_JSON); + headers.set("Authorization", AUTH_TOKEN); + headers.set("Accept", "application/json"); + + HttpEntity request = new HttpEntity<>(jsonPayload.toString(), headers); + + RestTemplate restTemplate = new RestTemplate(); + ResponseEntity response = restTemplate.exchange(API_URL, HttpMethod.POST, request, String.class); + + String latestAnswer; + if (response.getStatusCode() == HttpStatus.OK) { + JSONObject responseData = new JSONObject(response.getBody()); + latestAnswer = responseData.getJSONArray("choices").getJSONObject(0).getJSONObject("message") + .getString("content"); + + System.out.println("RAG Full Response latest_answer: " + latestAnswer); + return latestAnswer; + } else { + System.out.println("Failed to fetch data: " + response.getStatusCode() + " " + response.getBody()); + return " I'm sorry, I couldn't find an answer"; + } + } + + // `https://host:port/aiholo/tts?textToConvert=${encodeURIComponent(textToConvert)}&languageCode=${encodeURIComponent(languageCode)}&ssmlGender=${encodeURIComponent(ssmlGender)}&voiceName=${encodeURIComponent(voiceName)}`; + @GetMapping("/tts") + public ResponseEntity tts(@RequestParam("textToConvert") String textToConvert, + @RequestParam("languageCode") String languageCode, + @RequestParam("ssmlGender") String ssmlGender, + @RequestParam("voiceName") String voiceName) throws Exception { + String info= "tts for textToConvert " + textToConvert; + System.out.println("in TTS GCP info:" + info); + try (TextToSpeechClient textToSpeechClient = TextToSpeechClient.create()) { + System.out.println("in TTS GCP textToSpeechClient:" + textToSpeechClient + " languagecode:" + languageCode); + SynthesisInput input = SynthesisInput.newBuilder().setText(textToConvert).build(); + VoiceSelectionParams voice = + VoiceSelectionParams.newBuilder() + .setLanguageCode(languageCode) + // .setSsmlGender(SsmlVoiceGender.NEUTRAL) + .setSsmlGender(SsmlVoiceGender.FEMALE) + .setName(voiceName) + // .setName("pt-BR-Wavenet-A") + .build(); + AudioConfig audioConfig = + AudioConfig.newBuilder() + .setAudioEncoding(AudioEncoding.LINEAR16) // wav + // .setAudioEncoding(AudioEncoding.MP3) + .build(); + SynthesizeSpeechResponse response = + textToSpeechClient.synthesizeSpeech(input, voice, audioConfig); + ByteString audioContents = response.getAudioContent(); + byte[] audioData = audioContents.toByteArray(); + + // Set response headers + HttpHeaders headers = new HttpHeaders(); + headers.set(HttpHeaders.CONTENT_TYPE, "audio/mpeg"); + headers.set(HttpHeaders.CONTENT_DISPOSITION, + "attachment; filename=\"tts-" + languageCode + "" + ssmlGender+ "" + voiceName + "_" + + getFirst10Chars(textToConvert) + ".mp3\""); + + return new ResponseEntity<>(audioData, headers, HttpStatus.OK); + + // try (OutputStream out = new FileOutputStream("output.wav")) { + // out.write(audioContents.toByteArray()); + // System.out.println("Audio content written to file \"output.wav\""); + // } + } + + // return "succesful " + info; + } + + public static String getFirst10Chars(String textToConvert) { + if (textToConvert == null || textToConvert.isEmpty()) { + return ""; + } + return textToConvert.length() > 10 ? textToConvert.substring(0, 10) : textToConvert; + } + + + @GetMapping("/set") + public String setValue(@RequestParam("value") String value) { + theValue = value; + System.out.println("EchoController set: " + theValue); + String filePath = "C:/Users/opc/aiholo_output.txt"; + try (FileWriter writer = new FileWriter(filePath)) { + JSONObject json = new JSONObject(); + json.put("data", value); // Store the response inside JSON + writer.write(json.toString()); + writer.flush(); + } catch (IOException e) { + return "Error writing to file: " + e.getMessage(); + } + + if (value.equals("mirrorme") || value.equals("question")) + return "「ミラーミー」モードが正常に有効化されました"; + else + return "set successfully: " + theValue; + + } + + @GetMapping("/get") + public String getValue() { + System.out.println("EchoController get: " + theValue); + return theValue; + } + +} diff --git a/java-ai/src/main/java/oracleai/aiholo/DataSourceConfiguration.java b/java-ai/src/main/java/oracleai/aiholo/DataSourceConfiguration.java new file mode 100644 index 0000000..bac1f77 --- /dev/null +++ b/java-ai/src/main/java/oracleai/aiholo/DataSourceConfiguration.java @@ -0,0 +1,25 @@ +package oracleai.aiholo; + +import oracle.jdbc.pool.OracleDataSource; +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; + +import javax.sql.DataSource; +import java.sql.Connection; +import java.sql.SQLException; + +//@Configuration +public class DataSourceConfiguration { + +// @Bean + public DataSource dataSource() throws SQLException { + OracleDataSource dataSource = new OracleDataSource(); + dataSource.setUser("moviestream"); + dataSource.setPassword("Welcome12345"); + dataSource.setURL("jdbc:oracle:thin:@selectaidb_high?TNS_ADMIN=C:/Users/opc/Downloads/Wallet_SelectAIDB"); + try (Connection connection = dataSource.getConnection()) { + System.out.println("✅ Successfully connected to Oracle DB: " + connection.getMetaData().getDatabaseProductVersion()); + } + return dataSource; + } +} diff --git a/java-ai/src/main/java/oracleai/aiholo/TTSAndAudio2Face.java b/java-ai/src/main/java/oracleai/aiholo/TTSAndAudio2Face.java new file mode 100644 index 0000000..0270a78 --- /dev/null +++ b/java-ai/src/main/java/oracleai/aiholo/TTSAndAudio2Face.java @@ -0,0 +1,108 @@ +package oracleai.aiholo; + +import com.google.cloud.texttospeech.v1.*; +import com.google.protobuf.ByteString; +import org.springframework.http.HttpEntity; +import org.springframework.http.HttpHeaders; +import org.springframework.http.MediaType; +import org.springframework.http.ResponseEntity; +import org.springframework.web.client.RestTemplate; + +import java.io.FileOutputStream; +import java.io.OutputStream; +import java.util.HashMap; +import java.util.Map; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; + +public class TTSAndAudio2Face { + private static final ExecutorService executor = Executors.newSingleThreadExecutor(); + + public static void processMetahuman(String fileName, String textToSay, String languageCode, String voiceName) { + executor.submit(() -> { + try { + TTS(fileName, textToSay, languageCode, voiceName); + sendToAudio2Face(fileName); + } catch (Exception e) { + System.out.println("processMetahuman exception during TTS:" + e); + //TODO might be funny and helpful to do this, ie have the system gives its status and ask for help ... + // sendToAudio2Face("uhoh-lookslikeIneedanewTTStoken.wav"); + sendToAudio2Face("hello-brazil.wav"); + } + + }); + } + + + public static void TTS(String fileName, String text, String languageCode, String voicename) throws Exception { + try (TextToSpeechClient textToSpeechClient = TextToSpeechClient.create()) { + System.out.println("in TTS languagecode:" + languageCode + " voicename:" + voicename + " text:" + text); + SynthesisInput input = SynthesisInput.newBuilder().setText(text).build(); + // "最受欢迎的游戏是Pods Of Kon。").build(); + // "最も人気のあるビデオゲームは「Pods Of Kon」です。").build(); + VoiceSelectionParams voice = + VoiceSelectionParams.newBuilder() + .setLanguageCode(languageCode) //ja-JP, en-US, ... + .setSsmlGender(SsmlVoiceGender.FEMALE) // NEUTRAL, MALE + .setName(voicename) // "Kore" pt-BR-Wavenet-D + .build(); + AudioConfig audioConfig = + AudioConfig.newBuilder() + .setAudioEncoding(AudioEncoding.LINEAR16) // wav AudioEncoding.MP3 + .build(); + SynthesizeSpeechResponse response = + textToSpeechClient.synthesizeSpeech(input, voice, audioConfig); + ByteString audioContents = response.getAudioContent(); + try (OutputStream out = new FileOutputStream(fileName)) { + out.write(audioContents.toByteArray()); + System.out.println("Audio content written to file:" + fileName); + } + } + } + + + + + + private static void sendToAudio2Face(String fileName) { + RestTemplate restTemplate = new RestTemplate(); + String baseUrl = "http://localhost:8011/A2F/Player/"; + + String setRootPathUrl = baseUrl + "SetRootPath"; + Map rootPathPayload = new HashMap<>(); + rootPathPayload.put("a2f_player", "/World/audio2face/Player"); + rootPathPayload.put("dir_path", "C:/Users/opc/src/github.com/paulparkinson/oracle-ai-for-sustainable-dev/java-ai"); + sendPostRequest(restTemplate, setRootPathUrl, rootPathPayload); + + String setTrackUrl = baseUrl + "SetTrack"; + Map trackPayload = new HashMap<>(); + trackPayload.put("a2f_player", "/World/audio2face/Player"); + trackPayload.put("file_name", fileName); + trackPayload.put("time_range", new int[] { 0, -1 }); + sendPostRequest(restTemplate, setTrackUrl, trackPayload); + + String playTrackUrl = baseUrl + "Play"; + Map playPayload = new HashMap<>(); + playPayload.put("a2f_player", "/World/audio2face/Player"); + sendPostRequest(restTemplate, playTrackUrl, playPayload); + } + + private static void sendPostRequest(RestTemplate restTemplate, String url, Map payload) { + HttpHeaders headers = new HttpHeaders(); + headers.setContentType(MediaType.APPLICATION_JSON); + HttpEntity> request = new HttpEntity<>(payload, headers); + + ResponseEntity response = restTemplate.postForEntity(url, request, String.class); + if (response.getStatusCode().is2xxSuccessful()) { + System.out.println("Successfully sent request to: " + url); + } else { + System.err.println("Failed to send request to " + url + ". Response: " + response.getBody()); + } + } + + + + + +} + diff --git a/java-ai/src/main/java/oracleai/aiholo/TimeInWords.java b/java-ai/src/main/java/oracleai/aiholo/TimeInWords.java new file mode 100644 index 0000000..9e5bac0 --- /dev/null +++ b/java-ai/src/main/java/oracleai/aiholo/TimeInWords.java @@ -0,0 +1,89 @@ +package oracleai.aiholo; + +import java.time.*; +import java.util.Map; +import java.time.*; +import java.util.Map; + +public class TimeInWords { + + private static final Map NUMBERS_EN = Map.ofEntries( + Map.entry(0, "Twelve"), Map.entry(1, "One"), Map.entry(2, "Two"), Map.entry(3, "Three"), + Map.entry(4, "Four"), Map.entry(5, "Five"), Map.entry(6, "Six"), Map.entry(7, "Seven"), + Map.entry(8, "Eight"), Map.entry(9, "Nine"), Map.entry(10, "Ten"), Map.entry(11, "Eleven"), + Map.entry(12, "Twelve"), Map.entry(13, "One"), Map.entry(14, "Two"), Map.entry(15, "Three"), + Map.entry(16, "Four"), Map.entry(17, "Five"), Map.entry(18, "Six"), Map.entry(19, "Seven"), + Map.entry(20, "Eight"), Map.entry(21, "Nine"), Map.entry(22, "Ten"), Map.entry(23, "Eleven") + ); + + private static final Map MINUTES_EN = Map.ofEntries( + Map.entry(0, "o'clock"), Map.entry(15, "fifteen"), Map.entry(30, "thirty"), Map.entry(45, "forty-five") + ); + + private static final Map AM_PM_EN = Map.of("AM", "AM", "PM", "PM"); + + // Brazilian Portuguese mappings + private static final Map NUMBERS_PT = Map.ofEntries( + Map.entry(0, "Doze"), Map.entry(1, "Uma"), Map.entry(2, "Duas"), Map.entry(3, "Três"), + Map.entry(4, "Quatro"), Map.entry(5, "Cinco"), Map.entry(6, "Seis"), Map.entry(7, "Sete"), + Map.entry(8, "Oito"), Map.entry(9, "Nove"), Map.entry(10, "Dez"), Map.entry(11, "Onze"), + Map.entry(12, "Doze"), Map.entry(13, "Uma"), Map.entry(14, "Duas"), Map.entry(15, "Três"), + Map.entry(16, "Quatro"), Map.entry(17, "Cinco"), Map.entry(18, "Seis"), Map.entry(19, "Sete"), + Map.entry(20, "Oito"), Map.entry(21, "Nove"), Map.entry(22, "Dez"), Map.entry(23, "Onze") + ); + + private static final Map MINUTES_PT = Map.ofEntries( + Map.entry(0, "em ponto"), Map.entry(15, "e quinze"), Map.entry(30, "e meia"), Map.entry(45, "para as"), + Map.entry(1, "e um"), Map.entry(2, "e dois"), Map.entry(3, "e três"), Map.entry(4, "e quatro"), + Map.entry(5, "e cinco"), Map.entry(6, "e seis"), Map.entry(7, "e sete"), Map.entry(8, "e oito"), + Map.entry(9, "e nove"), Map.entry(10, "e dez"), Map.entry(11, "e onze"), Map.entry(12, "e doze"), + Map.entry(13, "e treze"), Map.entry(14, "e quatorze"), Map.entry(16, "e dezesseis"), + Map.entry(17, "e dezessete"), Map.entry(18, "e dezoito"), Map.entry(19, "e dezenove"), + Map.entry(20, "e vinte"), Map.entry(21, "e vinte e um"), Map.entry(22, "e vinte e dois"), + Map.entry(23, "e vinte e três"), Map.entry(24, "e vinte e quatro"), Map.entry(25, "e vinte e cinco"), + Map.entry(26, "e vinte e seis"), Map.entry(27, "e vinte e sete"), Map.entry(28, "e vinte e oito"), + Map.entry(29, "e vinte e nove"), Map.entry(40, "e quarenta"), Map.entry(41, "e quarenta e um"), + Map.entry(42, "e quarenta e dois"), Map.entry(43, "e quarenta e três"), Map.entry(44, "e quarenta e quatro"), + Map.entry(46, "e quarenta e seis"), Map.entry(47, "e quarenta e sete"), Map.entry(48, "e quarenta e oito"), + Map.entry(49, "e quarenta e nove"), Map.entry(50, "e cinquenta"), Map.entry(51, "e cinquenta e um"), + Map.entry(52, "e cinquenta e dois"), Map.entry(53, "e cinquenta e três"), Map.entry(54, "e cinquenta e quatro"), + Map.entry(55, "e cinquenta e cinco"), Map.entry(56, "e cinquenta e seis"), Map.entry(57, "e cinquenta e sete"), + Map.entry(58, "e cinquenta e oito"), Map.entry(59, "e cinquenta e nove") + ); + + private static final Map AM_PM_PT = Map.of("AM", "da manhã", "PM", "da noite"); + + public static String getTimeInWords(boolean inPortuguese) { + ZoneId brazilZone = ZoneId.of("America/Sao_Paulo"); + LocalTime now = LocalTime.now(brazilZone); + + int hour = now.getHour() % 12; + int minute = now.getMinute(); + boolean isAM = now.getHour() < 12; + if (hour == 0) hour = 12; + + if (inPortuguese) { + return formatTime(NUMBERS_PT, MINUTES_PT, AM_PM_PT, hour, minute, isAM); + } else { + return formatTime(NUMBERS_EN, MINUTES_EN, AM_PM_EN, hour, minute, isAM); + } + } + + private static String formatTime(Map numbers, Map minutes, + Map amPm, int hour, int minute, boolean isAM) { + String hourWord = numbers.get(hour); + String minuteWord = minutes.getOrDefault(minute, "e " + minute); + String amPmWord = isAM ? amPm.get("AM") : amPm.get("PM"); + + if (minute == 0) { + return hourWord + " " + minuteWord + " " + amPmWord; + } else { + return hourWord + " " + minuteWord + " " + amPmWord; + } + } + + public static void main(String[] args) { + System.out.println("Current time in Brazil (English): " + getTimeInWords(false)); + System.out.println("Hora atual no Brasil (Português): " + getTimeInWords(true)); + } +} diff --git a/java-ai/src/main/java/oracleai/common/SecurityConfig.java b/java-ai/src/main/java/oracleai/common/SecurityConfig.java new file mode 100644 index 0000000..96fa5ba --- /dev/null +++ b/java-ai/src/main/java/oracleai/common/SecurityConfig.java @@ -0,0 +1,37 @@ +import org.springframework.context.annotation.Bean; +import org.springframework.context.annotation.Configuration; +import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity; +import org.springframework.security.core.userdetails.User; +import org.springframework.security.core.userdetails.UserDetails; +import org.springframework.security.core.userdetails.UserDetailsService; +import org.springframework.security.provisioning.InMemoryUserDetailsManager; +import org.springframework.security.config.annotation.web.builders.HttpSecurity; +import org.springframework.security.web.SecurityFilterChain; + +@Configuration +@EnableWebSecurity +public class SecurityConfig { + + @Bean + public SecurityFilterChain securityFilterChain(HttpSecurity http) throws Exception { + http + .authorizeHttpRequests(auth -> auth + .requestMatchers("/public").permitAll() // Allow public access + .anyRequest().authenticated() // Require authentication for all other endpoints + ) + .httpBasic(); // Enable Basic Authentication + + return http.build(); + } + + @Bean + public UserDetailsService userDetailsService() { + UserDetails user = User.withDefaultPasswordEncoder() + .username("oracleai") + .password("oracleai") + .roles("USER") + .build(); + + return new InMemoryUserDetailsManager(user); + } +} diff --git a/java-ai/src/main/resources/application.yaml b/java-ai/src/main/resources/application.yaml index a8659f5..1823cef 100644 --- a/java-ai/src/main/resources/application.yaml +++ b/java-ai/src/main/resources/application.yaml @@ -1,31 +1,66 @@ spring: + main: + allow-circular-references: true + security: + user: + name: oracleai + password: oracleai + + web: + resources: + static-locations: classpath:/static/ + + mvc: + cors: + allowed-origin-patterns: ["*"] # ✅ Allow all origins + allowed-methods: ["GET", "POST", "PUT", "DELETE", "OPTIONS"] + allowed-headers: ["*"] + servlet: + websocket: + buffer-size: 65536 # ✅ Increase WebSocket buffer size multipart: enabled: true max-file-size: 200MB max-request-size: 200MB + cloud: oci: config: type: INSTANCE_PRINCIPAL - datasource: - # Example where a wallet is used (TNS_ADMIN is the location of the wallet). - # Eg if using Oracle Cloud ADB (autonomous database) Always Free. - # url: "jdbc:oracle:thin:@xr_tp?TNS_ADMIN=/Users/me/Wallet_mydb" - # Example without wallet. Eg if using Oracle 23c Free. - # url: "jdbc:oracle:thin:@localhost:1521/freepdb1" - url: jdbc:oracle:thin:@mydb_tp?TNS_ADMIN=/Users/me/Wallet_mydb - # Use "admin" for username for setup with Oracle Cloud ADB - # and use "sys as sysdba" for username for setup with Oracle 23c Free - username: moviestream - password: Welcome12345 - driver-class-name: oracle.jdbc.OracleDriver - type: oracle.ucp.jdbc.PoolDataSource - oracleucp: - connection-factory-class-name: oracle.jdbc.pool.OracleDataSource -logging: - level: - org.springframework.web.cors: DEBUG + + # datasource: + # url: jdbc:oracle:thin:@selectaidb_high?TNS_ADMIN=C:/Users/opc/Downloads/Wallet_SelectAIDB/Wallet_SelectAIDB + + # username: moviestream + # password: Welcome12345 + # driver-class-name: oracle.jdbc.OracleDriver + # type: oracle.ucp.jdbc.PoolDataSource + # oracleucp: + # connection-factory-class-name: oracle.jdbc.pool.OracleDataSource + # connection-pool-name: AccountConnectionPool + # initial-pool-size: 15s + # min-pool-size: 10 + # max-pool-size: 30 + + +#logging: +# level: +# root: INFO +# org.springframework.web: DEBUG +# org.springframework.web.cors: DEBUG +# org.springframework.web.socket: DEBUG +# org.hibernate.SQL: DEBUG +# org.hibernate.type.descriptor.sql.BasicBinder: TRACE + server: + port: 8080 +# port: 8444 tomcat: max-swallow-size: 200MB +# ssl: +# enabled: true +# key-store-type: PKCS12 +# key-store: classpath:keystore.p12 +# key-store-password: Welcome1 +# key-alias: springboot diff --git a/java-ai/src/main/resources/static/AIHolo.html b/java-ai/src/main/resources/static/AIHolo.html new file mode 100644 index 0000000..41e6f73 --- /dev/null +++ b/java-ai/src/main/resources/static/AIHolo.html @@ -0,0 +1,55 @@ + + + + + + Flags and Images + + + + +
+ Flag 1 + Flag 4 + Flag 2 + Flag 3 + Flag 5 +
+ + + + + diff --git a/java-ai/src/main/resources/static/GCPVoices.html b/java-ai/src/main/resources/static/GCPVoices.html new file mode 100644 index 0000000..4d2b20b --- /dev/null +++ b/java-ai/src/main/resources/static/GCPVoices.html @@ -0,0 +1,106 @@ + + + + + + Text-to-Speech Form + + + +

Text-to-Speech Configuration

+
+ + +

+
+
+ +
+ + diff --git a/java-ai/src/main/resources/static/aiholo/AIHolo-Brazil.html b/java-ai/src/main/resources/static/aiholo/AIHolo-Brazil.html new file mode 100644 index 0000000..e8ff867 --- /dev/null +++ b/java-ai/src/main/resources/static/aiholo/AIHolo-Brazil.html @@ -0,0 +1,180 @@ + + + + + + Interactive AI Hologram With Oracle Database + + + + + +
+ Flag 1 + Flag 2 + Flag 3 + Flag 4 + Flag 5 +
+ +

Oracle Database hologramas de IA interativos

+

Click "Start" and speak in Portuguese.
Click "Stop & Send" to finish and send your question.
Por exemplo "qual é o videogame mais vendido"

+ +
+ + +
+ + + + + + +
+

+ + + + + + + diff --git a/java-ai/src/main/resources/static/aiholo/AIHolo-Italy.html b/java-ai/src/main/resources/static/aiholo/AIHolo-Italy.html new file mode 100644 index 0000000..e3fabb9 --- /dev/null +++ b/java-ai/src/main/resources/static/aiholo/AIHolo-Italy.html @@ -0,0 +1,185 @@ + + + + + + Interactive AI Hologram With Oracle Database + + + + + +
+ Flag 1 + Flag 2 + Flag 3 + Flag 4 + Flag 5 +
+ +

Oracle Database hologramas de IA interativos

+

Click "Start" and speak in Portuguese.
Click "Stop & Send" to finish and send your question.
Por exemplo "qual é o videogame mais vendido"

+ +
+ + +
+ + + + + + +
+

+ + + + + + + diff --git a/java-ai/src/main/resources/static/aiholo/AIHolo-Mandarin.html b/java-ai/src/main/resources/static/aiholo/AIHolo-Mandarin.html new file mode 100644 index 0000000..e3fabb9 --- /dev/null +++ b/java-ai/src/main/resources/static/aiholo/AIHolo-Mandarin.html @@ -0,0 +1,185 @@ + + + + + + Interactive AI Hologram With Oracle Database + + + + + +
+ Flag 1 + Flag 2 + Flag 3 + Flag 4 + Flag 5 +
+ +

Oracle Database hologramas de IA interativos

+

Click "Start" and speak in Portuguese.
Click "Stop & Send" to finish and send your question.
Por exemplo "qual é o videogame mais vendido"

+ +
+ + +
+ + + + + + +
+

+ + + + + + + diff --git a/java-ai/src/main/resources/static/aiholo/AIHolo-OCWTokyo.html b/java-ai/src/main/resources/static/aiholo/AIHolo-OCWTokyo.html new file mode 100644 index 0000000..d12d505 --- /dev/null +++ b/java-ai/src/main/resources/static/aiholo/AIHolo-OCWTokyo.html @@ -0,0 +1,191 @@ + + + + + + Interactive AI Hologram With Oracle Database + + + + + +

Oracle Databaseを使用したインタラクティブAIホログラム

+

「スタート」をクリックし、日本語で話してください。終了して質問を送信するには「ストップ & 送信」をクリックしてください。

+ +
+ + + +
+ + + + + +
たとえば、「最も売れているビデオゲームは何ですか?」 +
+

+ + +
+ + AI Holo Architecture + + + Oracle 23 AI + +
+ + + diff --git a/java-ai/src/main/resources/static/aiholo/AIHolo-Spain.html b/java-ai/src/main/resources/static/aiholo/AIHolo-Spain.html new file mode 100644 index 0000000..e3fabb9 --- /dev/null +++ b/java-ai/src/main/resources/static/aiholo/AIHolo-Spain.html @@ -0,0 +1,185 @@ + + + + + + Interactive AI Hologram With Oracle Database + + + + + +
+ Flag 1 + Flag 2 + Flag 3 + Flag 4 + Flag 5 +
+ +

Oracle Database hologramas de IA interativos

+

Click "Start" and speak in Portuguese.
Click "Stop & Send" to finish and send your question.
Por exemplo "qual é o videogame mais vendido"

+ +
+ + +
+ + + + + + +
+

+ + + + + + + diff --git a/java-ai/src/main/resources/static/aiholo/AIHolo-United-Kingdom.html b/java-ai/src/main/resources/static/aiholo/AIHolo-United-Kingdom.html new file mode 100644 index 0000000..e3fabb9 --- /dev/null +++ b/java-ai/src/main/resources/static/aiholo/AIHolo-United-Kingdom.html @@ -0,0 +1,185 @@ + + + + + + Interactive AI Hologram With Oracle Database + + + + + +
+ Flag 1 + Flag 2 + Flag 3 + Flag 4 + Flag 5 +
+ +

Oracle Database hologramas de IA interativos

+

Click "Start" and speak in Portuguese.
Click "Stop & Send" to finish and send your question.
Por exemplo "qual é o videogame mais vendido"

+ +
+ + +
+ + + + + + +
+

+ + + + + + + diff --git a/java-ai/src/main/resources/static/aiholo/AIHolo-languageselectable.html b/java-ai/src/main/resources/static/aiholo/AIHolo-languageselectable.html new file mode 100644 index 0000000..c91f13f --- /dev/null +++ b/java-ai/src/main/resources/static/aiholo/AIHolo-languageselectable.html @@ -0,0 +1,181 @@ + + + + + + Interactive AI Hologram With Oracle Database + + + + + +

Oracle Database hologramas de IA interativos

+

Click "Start" and speak in Portuguese. +
Click "Stop & Send" to finish and send your question. +
Por exemplo "qual é o videogame mais vendido" +

+ +
+ + +
+ +
+ + +
+ +
+ + +
+ + + + + + +
+

+ + + + + diff --git a/java-ai/src/main/resources/static/aiholo/index.html b/java-ai/src/main/resources/static/aiholo/index.html new file mode 100644 index 0000000..141a17f --- /dev/null +++ b/java-ai/src/main/resources/static/aiholo/index.html @@ -0,0 +1,55 @@ + + + + + + Flags and Images + + + + +
+ Flag 1 + Flag 4 + Flag 2 + Flag 3 + Flag 5 +
+ + + + + diff --git a/java-ai/src/main/resources/static/favicon.ico b/java-ai/src/main/resources/static/favicon.ico new file mode 100644 index 0000000..8f9edc2 Binary files /dev/null and b/java-ai/src/main/resources/static/favicon.ico differ diff --git a/java-ai/src/main/resources/static/faviconold.ico b/java-ai/src/main/resources/static/faviconold.ico new file mode 100644 index 0000000..2459107 Binary files /dev/null and b/java-ai/src/main/resources/static/faviconold.ico differ diff --git a/java-ai/src/main/resources/static/gcp-voices.json b/java-ai/src/main/resources/static/gcp-voices.json new file mode 100644 index 0000000..5a20940 --- /dev/null +++ b/java-ai/src/main/resources/static/gcp-voices.json @@ -0,0 +1,4645 @@ +{ + "voices": [ + { + "languageCodes": [ + "en-US" + ], + "name": "Aoede", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "Charon", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "Fenrir", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "Kore", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "Leda", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "Orus", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "Puck", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "Zephyr", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "af-ZA" + ], + "name": "af-ZA-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "am-ET" + ], + "name": "am-ET-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "am-ET" + ], + "name": "am-ET-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "am-ET" + ], + "name": "am-ET-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "am-ET" + ], + "name": "am-ET-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ar-XA" + ], + "name": "ar-XA-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ar-XA" + ], + "name": "ar-XA-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ar-XA" + ], + "name": "ar-XA-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ar-XA" + ], + "name": "ar-XA-Standard-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ar-XA" + ], + "name": "ar-XA-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ar-XA" + ], + "name": "ar-XA-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ar-XA" + ], + "name": "ar-XA-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ar-XA" + ], + "name": "ar-XA-Wavenet-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "bg-BG" + ], + "name": "bg-BG-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "bg-BG" + ], + "name": "bg-BG-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "bn-IN" + ], + "name": "bn-IN-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "bn-IN" + ], + "name": "bn-IN-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "bn-IN" + ], + "name": "bn-IN-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "bn-IN" + ], + "name": "bn-IN-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "bn-IN" + ], + "name": "bn-IN-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "bn-IN" + ], + "name": "bn-IN-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "bn-IN" + ], + "name": "bn-IN-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "bn-IN" + ], + "name": "bn-IN-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ca-ES" + ], + "name": "ca-ES-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ca-ES" + ], + "name": "ca-ES-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-CN" + ], + "name": "cmn-CN-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-CN" + ], + "name": "cmn-CN-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-CN" + ], + "name": "cmn-CN-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-CN" + ], + "name": "cmn-CN-Standard-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-CN" + ], + "name": "cmn-CN-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-CN" + ], + "name": "cmn-CN-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-CN" + ], + "name": "cmn-CN-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-CN" + ], + "name": "cmn-CN-Wavenet-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-TW" + ], + "name": "cmn-TW-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-TW" + ], + "name": "cmn-TW-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-TW" + ], + "name": "cmn-TW-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-TW" + ], + "name": "cmn-TW-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-TW" + ], + "name": "cmn-TW-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cmn-TW" + ], + "name": "cmn-TW-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cs-CZ" + ], + "name": "cs-CZ-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cs-CZ" + ], + "name": "cs-CZ-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cs-CZ" + ], + "name": "cs-CZ-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "cs-CZ" + ], + "name": "cs-CZ-Wavenet-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "da-DK" + ], + "name": "da-DK-Neural2-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "da-DK" + ], + "name": "da-DK-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "da-DK" + ], + "name": "da-DK-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "da-DK" + ], + "name": "da-DK-Standard-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "da-DK" + ], + "name": "da-DK-Standard-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "da-DK" + ], + "name": "da-DK-Standard-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "da-DK" + ], + "name": "da-DK-Standard-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "da-DK" + ], + "name": "da-DK-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "da-DK" + ], + "name": "da-DK-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "da-DK" + ], + "name": "da-DK-Wavenet-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "da-DK" + ], + "name": "da-DK-Wavenet-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "da-DK" + ], + "name": "da-DK-Wavenet-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "da-DK" + ], + "name": "da-DK-Wavenet-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Chirp-HD-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Chirp-HD-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Chirp-HD-O", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Neural2-G", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Neural2-H", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Polyglot-1", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Standard-E", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Standard-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Standard-G", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Standard-H", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Studio-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Studio-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Wavenet-E", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Wavenet-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Wavenet-G", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "de-DE" + ], + "name": "de-DE-Wavenet-H", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "el-GR" + ], + "name": "el-GR-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "el-GR" + ], + "name": "el-GR-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "el-GR" + ], + "name": "el-GR-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "el-GR" + ], + "name": "el-GR-Wavenet-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Chirp-HD-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Chirp-HD-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Chirp-HD-O", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Neural2-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Neural2-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Neural2-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Neural2-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-News-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-News-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-News-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Polyglot-1", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-AU" + ], + "name": "en-AU-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Chirp-HD-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Chirp-HD-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Chirp-HD-O", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Neural2-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Neural2-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Neural2-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Neural2-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Neural2-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Neural2-N", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Neural2-O", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-News-G", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-News-H", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-News-I", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-News-J", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-News-K", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-News-L", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-News-M", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Standard-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Standard-N", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Standard-O", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Studio-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Studio-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Wavenet-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Wavenet-N", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-GB" + ], + "name": "en-GB-Wavenet-O", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Chirp-HD-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Chirp-HD-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Chirp-HD-O", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Neural2-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Neural2-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Neural2-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Neural2-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Standard-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Standard-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Standard-F", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Wavenet-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Wavenet-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-IN" + ], + "name": "en-IN-Wavenet-F", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Casual-K", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Chirp-HD-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Chirp-HD-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Chirp-HD-O", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Neural2-A", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Neural2-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Neural2-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Neural2-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Neural2-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Neural2-G", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Neural2-H", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Neural2-I", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Neural2-J", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-News-K", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-News-L", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-News-N", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Polyglot-1", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Standard-A", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Standard-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Standard-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Standard-G", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Standard-H", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Standard-I", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Standard-J", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Studio-O", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Studio-Q", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Wavenet-A", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Wavenet-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Wavenet-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Wavenet-G", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Wavenet-H", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Wavenet-I", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "en-US" + ], + "name": "en-US-Wavenet-J", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Chirp-HD-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Chirp-HD-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Chirp-HD-O", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Neural2-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Neural2-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Neural2-F", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Neural2-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Neural2-H", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Polyglot-1", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Standard-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Standard-E", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Standard-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Standard-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Standard-H", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Studio-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Studio-F", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Wavenet-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Wavenet-E", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Wavenet-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Wavenet-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-ES" + ], + "name": "es-ES-Wavenet-H", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Chirp-HD-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Chirp-HD-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Chirp-HD-O", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Neural2-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Neural2-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Neural2-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-News-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-News-E", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-News-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-News-G", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Polyglot-1", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Studio-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "es-US" + ], + "name": "es-US-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "et-EE" + ], + "name": "et-EE-Standard-A", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "eu-ES" + ], + "name": "eu-ES-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "eu-ES" + ], + "name": "eu-ES-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fi-FI" + ], + "name": "fi-FI-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fi-FI" + ], + "name": "fi-FI-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fi-FI" + ], + "name": "fi-FI-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fi-FI" + ], + "name": "fi-FI-Wavenet-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fil-PH" + ], + "name": "fil-PH-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fil-PH" + ], + "name": "fil-PH-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fil-PH" + ], + "name": "fil-PH-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fil-PH" + ], + "name": "fil-PH-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fil-PH" + ], + "name": "fil-PH-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fil-PH" + ], + "name": "fil-PH-Wavenet-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fil-PH" + ], + "name": "fil-PH-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fil-PH" + ], + "name": "fil-PH-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fil-PH" + ], + "name": "fil-ph-Neural2-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fil-PH" + ], + "name": "fil-ph-Neural2-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Chirp-HD-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Chirp-HD-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Chirp-HD-O", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Neural2-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Neural2-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Neural2-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Neural2-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-CA" + ], + "name": "fr-CA-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Chirp-HD-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Chirp-HD-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Chirp-HD-O", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Neural2-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Neural2-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Polyglot-1", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Standard-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Standard-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Standard-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Studio-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Studio-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Wavenet-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Wavenet-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "fr-FR" + ], + "name": "fr-FR-Wavenet-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "gl-ES" + ], + "name": "gl-ES-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "gl-ES" + ], + "name": "gl-ES-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "gu-IN" + ], + "name": "gu-IN-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "gu-IN" + ], + "name": "gu-IN-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "gu-IN" + ], + "name": "gu-IN-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "gu-IN" + ], + "name": "gu-IN-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "gu-IN" + ], + "name": "gu-IN-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "gu-IN" + ], + "name": "gu-IN-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "gu-IN" + ], + "name": "gu-IN-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "gu-IN" + ], + "name": "gu-IN-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "he-IL" + ], + "name": "he-IL-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "he-IL" + ], + "name": "he-IL-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "he-IL" + ], + "name": "he-IL-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "he-IL" + ], + "name": "he-IL-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "he-IL" + ], + "name": "he-IL-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "he-IL" + ], + "name": "he-IL-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "he-IL" + ], + "name": "he-IL-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "he-IL" + ], + "name": "he-IL-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Neural2-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Neural2-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Neural2-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Neural2-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Standard-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Standard-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Standard-F", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Wavenet-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Wavenet-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hi-IN" + ], + "name": "hi-IN-Wavenet-F", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hu-HU" + ], + "name": "hu-HU-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hu-HU" + ], + "name": "hu-HU-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "hu-HU" + ], + "name": "hu-HU-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "id-ID" + ], + "name": "id-ID-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "id-ID" + ], + "name": "id-ID-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "id-ID" + ], + "name": "id-ID-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "id-ID" + ], + "name": "id-ID-Standard-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "id-ID" + ], + "name": "id-ID-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "id-ID" + ], + "name": "id-ID-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "id-ID" + ], + "name": "id-ID-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "id-ID" + ], + "name": "id-ID-Wavenet-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "is-IS" + ], + "name": "is-IS-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "is-IS" + ], + "name": "is-IS-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Chirp-HD-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Chirp-HD-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Chirp-HD-O", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Neural2-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Neural2-F", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Standard-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Standard-F", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Wavenet-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Wavenet-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "it-IT" + ], + "name": "it-IT-Wavenet-F", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ja-JP" + ], + "name": "ja-JP-Neural2-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ja-JP" + ], + "name": "ja-JP-Neural2-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ja-JP" + ], + "name": "ja-JP-Neural2-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ja-JP" + ], + "name": "ja-JP-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ja-JP" + ], + "name": "ja-JP-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ja-JP" + ], + "name": "ja-JP-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ja-JP" + ], + "name": "ja-JP-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ja-JP" + ], + "name": "ja-JP-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ja-JP" + ], + "name": "ja-JP-Wavenet-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ja-JP" + ], + "name": "ja-JP-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ja-JP" + ], + "name": "ja-JP-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "kn-IN" + ], + "name": "kn-IN-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "kn-IN" + ], + "name": "kn-IN-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "kn-IN" + ], + "name": "kn-IN-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "kn-IN" + ], + "name": "kn-IN-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "kn-IN" + ], + "name": "kn-IN-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "kn-IN" + ], + "name": "kn-IN-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "kn-IN" + ], + "name": "kn-IN-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "kn-IN" + ], + "name": "kn-IN-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ko-KR" + ], + "name": "ko-KR-Neural2-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ko-KR" + ], + "name": "ko-KR-Neural2-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ko-KR" + ], + "name": "ko-KR-Neural2-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ko-KR" + ], + "name": "ko-KR-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ko-KR" + ], + "name": "ko-KR-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ko-KR" + ], + "name": "ko-KR-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ko-KR" + ], + "name": "ko-KR-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ko-KR" + ], + "name": "ko-KR-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ko-KR" + ], + "name": "ko-KR-Wavenet-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ko-KR" + ], + "name": "ko-KR-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ko-KR" + ], + "name": "ko-KR-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "lt-LT" + ], + "name": "lt-LT-Standard-A", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "lt-LT" + ], + "name": "lt-LT-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "lv-LV" + ], + "name": "lv-LV-Standard-A", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "lv-LV" + ], + "name": "lv-LV-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ml-IN" + ], + "name": "ml-IN-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ml-IN" + ], + "name": "ml-IN-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ml-IN" + ], + "name": "ml-IN-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ml-IN" + ], + "name": "ml-IN-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ml-IN" + ], + "name": "ml-IN-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ml-IN" + ], + "name": "ml-IN-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ml-IN" + ], + "name": "ml-IN-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ml-IN" + ], + "name": "ml-IN-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "mr-IN" + ], + "name": "mr-IN-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "mr-IN" + ], + "name": "mr-IN-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "mr-IN" + ], + "name": "mr-IN-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "mr-IN" + ], + "name": "mr-IN-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "mr-IN" + ], + "name": "mr-IN-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "mr-IN" + ], + "name": "mr-IN-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ms-MY" + ], + "name": "ms-MY-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ms-MY" + ], + "name": "ms-MY-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ms-MY" + ], + "name": "ms-MY-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ms-MY" + ], + "name": "ms-MY-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ms-MY" + ], + "name": "ms-MY-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ms-MY" + ], + "name": "ms-MY-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ms-MY" + ], + "name": "ms-MY-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ms-MY" + ], + "name": "ms-MY-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Standard-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Standard-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Standard-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Wavenet-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Wavenet-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nb-NO" + ], + "name": "nb-NO-Wavenet-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-BE" + ], + "name": "nl-BE-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-BE" + ], + "name": "nl-BE-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-BE" + ], + "name": "nl-BE-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-BE" + ], + "name": "nl-BE-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-BE" + ], + "name": "nl-BE-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-BE" + ], + "name": "nl-BE-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-BE" + ], + "name": "nl-BE-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-BE" + ], + "name": "nl-BE-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Standard-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Standard-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Standard-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Standard-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Wavenet-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Wavenet-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Wavenet-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "nl-NL" + ], + "name": "nl-NL-Wavenet-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pa-IN" + ], + "name": "pa-IN-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pa-IN" + ], + "name": "pa-IN-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pa-IN" + ], + "name": "pa-IN-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pa-IN" + ], + "name": "pa-IN-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pa-IN" + ], + "name": "pa-IN-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pa-IN" + ], + "name": "pa-IN-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pa-IN" + ], + "name": "pa-IN-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pa-IN" + ], + "name": "pa-IN-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Standard-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Standard-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Standard-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Standard-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Wavenet-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Wavenet-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Wavenet-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pl-PL" + ], + "name": "pl-PL-Wavenet-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-BR" + ], + "name": "pt-BR-Neural2-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-BR" + ], + "name": "pt-BR-Neural2-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-BR" + ], + "name": "pt-BR-Neural2-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-BR" + ], + "name": "pt-BR-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-BR" + ], + "name": "pt-BR-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-BR" + ], + "name": "pt-BR-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-BR" + ], + "name": "pt-BR-Standard-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-BR" + ], + "name": "pt-BR-Standard-E", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-BR" + ], + "name": "pt-BR-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-BR" + ], + "name": "pt-BR-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-BR" + ], + "name": "pt-BR-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-BR" + ], + "name": "pt-BR-Wavenet-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-BR" + ], + "name": "pt-BR-Wavenet-E", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-PT" + ], + "name": "pt-PT-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-PT" + ], + "name": "pt-PT-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-PT" + ], + "name": "pt-PT-Standard-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-PT" + ], + "name": "pt-PT-Standard-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-PT" + ], + "name": "pt-PT-Standard-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-PT" + ], + "name": "pt-PT-Standard-F", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-PT" + ], + "name": "pt-PT-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-PT" + ], + "name": "pt-PT-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-PT" + ], + "name": "pt-PT-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-PT" + ], + "name": "pt-PT-Wavenet-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-PT" + ], + "name": "pt-PT-Wavenet-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "pt-PT" + ], + "name": "pt-PT-Wavenet-F", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ro-RO" + ], + "name": "ro-RO-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ro-RO" + ], + "name": "ro-RO-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ro-RO" + ], + "name": "ro-RO-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ro-RO" + ], + "name": "ro-RO-Wavenet-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ru-RU" + ], + "name": "ru-RU-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ru-RU" + ], + "name": "ru-RU-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ru-RU" + ], + "name": "ru-RU-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ru-RU" + ], + "name": "ru-RU-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ru-RU" + ], + "name": "ru-RU-Standard-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ru-RU" + ], + "name": "ru-RU-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ru-RU" + ], + "name": "ru-RU-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ru-RU" + ], + "name": "ru-RU-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ru-RU" + ], + "name": "ru-RU-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ru-RU" + ], + "name": "ru-RU-Wavenet-E", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sk-SK" + ], + "name": "sk-SK-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sk-SK" + ], + "name": "sk-SK-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sk-SK" + ], + "name": "sk-SK-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sk-SK" + ], + "name": "sk-SK-Wavenet-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sr-RS" + ], + "name": "sr-RS-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Standard-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Standard-E", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Standard-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Standard-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Wavenet-B", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Wavenet-C", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Wavenet-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Wavenet-E", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Wavenet-F", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "sv-SE" + ], + "name": "sv-SE-Wavenet-G", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ta-IN" + ], + "name": "ta-IN-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ta-IN" + ], + "name": "ta-IN-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ta-IN" + ], + "name": "ta-IN-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ta-IN" + ], + "name": "ta-IN-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ta-IN" + ], + "name": "ta-IN-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ta-IN" + ], + "name": "ta-IN-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ta-IN" + ], + "name": "ta-IN-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ta-IN" + ], + "name": "ta-IN-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "te-IN" + ], + "name": "te-IN-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "te-IN" + ], + "name": "te-IN-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "te-IN" + ], + "name": "te-IN-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "te-IN" + ], + "name": "te-IN-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "th-TH" + ], + "name": "th-TH-Neural2-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "th-TH" + ], + "name": "th-TH-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "tr-TR" + ], + "name": "tr-TR-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "tr-TR" + ], + "name": "tr-TR-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "tr-TR" + ], + "name": "tr-TR-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "tr-TR" + ], + "name": "tr-TR-Standard-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "tr-TR" + ], + "name": "tr-TR-Standard-E", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "tr-TR" + ], + "name": "tr-TR-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "tr-TR" + ], + "name": "tr-TR-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "tr-TR" + ], + "name": "tr-TR-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "tr-TR" + ], + "name": "tr-TR-Wavenet-D", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "tr-TR" + ], + "name": "tr-TR-Wavenet-E", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "uk-UA" + ], + "name": "uk-UA-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "uk-UA" + ], + "name": "uk-UA-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ur-IN" + ], + "name": "ur-IN-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ur-IN" + ], + "name": "ur-IN-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ur-IN" + ], + "name": "ur-IN-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "ur-IN" + ], + "name": "ur-IN-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "vi-VN" + ], + "name": "vi-VN-Neural2-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "vi-VN" + ], + "name": "vi-VN-Neural2-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "vi-VN" + ], + "name": "vi-VN-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "vi-VN" + ], + "name": "vi-VN-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "vi-VN" + ], + "name": "vi-VN-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "vi-VN" + ], + "name": "vi-VN-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "vi-VN" + ], + "name": "vi-VN-Wavenet-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "vi-VN" + ], + "name": "vi-VN-Wavenet-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "vi-VN" + ], + "name": "vi-VN-Wavenet-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "vi-VN" + ], + "name": "vi-VN-Wavenet-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "yue-HK" + ], + "name": "yue-HK-Standard-A", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "yue-HK" + ], + "name": "yue-HK-Standard-B", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "yue-HK" + ], + "name": "yue-HK-Standard-C", + "ssmlGender": "FEMALE", + "naturalSampleRateHertz": 24000 + }, + { + "languageCodes": [ + "yue-HK" + ], + "name": "yue-HK-Standard-D", + "ssmlGender": "MALE", + "naturalSampleRateHertz": 24000 + } + ] + } + \ No newline at end of file diff --git a/java-ai/src/main/resources/static/images/aiholoarch.png b/java-ai/src/main/resources/static/images/aiholoarch.png new file mode 100644 index 0000000..fe761cc Binary files /dev/null and b/java-ai/src/main/resources/static/images/aiholoarch.png differ diff --git a/java-ai/src/main/resources/static/digitaldouble_QRCode.png b/java-ai/src/main/resources/static/images/digitaldouble_QRCode.png similarity index 100% rename from java-ai/src/main/resources/static/digitaldouble_QRCode.png rename to java-ai/src/main/resources/static/images/digitaldouble_QRCode.png diff --git a/java-ai/src/main/resources/static/images/flags/Brazil-Flag.png b/java-ai/src/main/resources/static/images/flags/Brazil-Flag.png new file mode 100755 index 0000000..b3e8fb0 Binary files /dev/null and b/java-ai/src/main/resources/static/images/flags/Brazil-Flag.png differ diff --git a/java-ai/src/main/resources/static/images/flags/China-Flag.png b/java-ai/src/main/resources/static/images/flags/China-Flag.png new file mode 100755 index 0000000..01d8ec0 Binary files /dev/null and b/java-ai/src/main/resources/static/images/flags/China-Flag.png differ diff --git a/java-ai/src/main/resources/static/images/flags/Germany-Flag.png b/java-ai/src/main/resources/static/images/flags/Germany-Flag.png new file mode 100755 index 0000000..89dc2b2 Binary files /dev/null and b/java-ai/src/main/resources/static/images/flags/Germany-Flag.png differ diff --git a/java-ai/src/main/resources/static/images/flags/India-Flag.png b/java-ai/src/main/resources/static/images/flags/India-Flag.png new file mode 100755 index 0000000..9365ae5 Binary files /dev/null and b/java-ai/src/main/resources/static/images/flags/India-Flag.png differ diff --git a/java-ai/src/main/resources/static/images/flags/Israel-Flag.png b/java-ai/src/main/resources/static/images/flags/Israel-Flag.png new file mode 100755 index 0000000..44e0ce5 Binary files /dev/null and b/java-ai/src/main/resources/static/images/flags/Israel-Flag.png differ diff --git a/java-ai/src/main/resources/static/images/flags/Italy-Flag.png b/java-ai/src/main/resources/static/images/flags/Italy-Flag.png new file mode 100755 index 0000000..1660abb Binary files /dev/null and b/java-ai/src/main/resources/static/images/flags/Italy-Flag.png differ diff --git a/java-ai/src/main/resources/static/images/flags/Japan-Flag.png b/java-ai/src/main/resources/static/images/flags/Japan-Flag.png new file mode 100755 index 0000000..070a662 Binary files /dev/null and b/java-ai/src/main/resources/static/images/flags/Japan-Flag.png differ diff --git a/java-ai/src/main/resources/static/images/flags/Spain-Flag.png b/java-ai/src/main/resources/static/images/flags/Spain-Flag.png new file mode 100755 index 0000000..bbf6686 Binary files /dev/null and b/java-ai/src/main/resources/static/images/flags/Spain-Flag.png differ diff --git a/java-ai/src/main/resources/static/images/flags/United-Arab-Emirates-Flag.png b/java-ai/src/main/resources/static/images/flags/United-Arab-Emirates-Flag.png new file mode 100755 index 0000000..b0ef650 Binary files /dev/null and b/java-ai/src/main/resources/static/images/flags/United-Arab-Emirates-Flag.png differ diff --git a/java-ai/src/main/resources/static/images/flags/United-Kingdom-Flag.png b/java-ai/src/main/resources/static/images/flags/United-Kingdom-Flag.png new file mode 100755 index 0000000..1f9d88c Binary files /dev/null and b/java-ai/src/main/resources/static/images/flags/United-Kingdom-Flag.png differ diff --git a/java-ai/src/main/resources/static/images/flags/United-States-Flag.png b/java-ai/src/main/resources/static/images/flags/United-States-Flag.png new file mode 100755 index 0000000..7ca4218 Binary files /dev/null and b/java-ai/src/main/resources/static/images/flags/United-States-Flag.png differ diff --git a/java-ai/src/main/resources/static/images/oracle23ai.png b/java-ai/src/main/resources/static/images/oracle23ai.png new file mode 100644 index 0000000..788b182 Binary files /dev/null and b/java-ai/src/main/resources/static/images/oracle23ai.png differ diff --git a/java-ai/src/main/resources/static/images/oracle23aiblock.webp b/java-ai/src/main/resources/static/images/oracle23aiblock.webp new file mode 100644 index 0000000..de96fc9 Binary files /dev/null and b/java-ai/src/main/resources/static/images/oracle23aiblock.webp differ diff --git a/java-ai/src/main/resources/static/images/oracleconverged23ai.webp b/java-ai/src/main/resources/static/images/oracleconverged23ai.webp new file mode 100644 index 0000000..cd982bb Binary files /dev/null and b/java-ai/src/main/resources/static/images/oracleconverged23ai.webp differ diff --git a/java-gcpspeechai/pom.xml b/java-gcpspeechai/pom.xml deleted file mode 100644 index b591b42..0000000 --- a/java-gcpspeechai/pom.xml +++ /dev/null @@ -1,134 +0,0 @@ - - - 4.0.0 - - org.springframework.boot - spring-boot-starter-parent - 3.3.1 - - - oracleai - oracleai-gcpspeechai - 0.0.1-SNAPSHOT - oracleai - Oracle AI Demos - - - 3.52.1 - - - - - com.google.cloud - libraries-bom - 26.51.0 - pom - import - - - - - - - com.google.cloud - google-cloud-speech - - - - org.springframework.boot - spring-boot-starter-web - - - org.springframework.boot - spring-boot-starter-thymeleaf - - - org.json - json - 20231013 - - - commons-io - commons-io - 2.8.0 - - - com.oracle.cloud.spring - spring-cloud-oci-starter - 1.3.0 - - - com.oracle.oci.sdk - oci-java-sdk-common-httpclient-jersey - ${oci.sdk.version} - - - com.oracle.oci.sdk - oci-java-sdk-generativeaiinference - ${oci.sdk.version} - - - com.oracle.oci.sdk - oci-java-sdk-aivision - ${oci.sdk.version} - - - com.oracle.oci.sdk - oci-java-sdk-aispeech - ${oci.sdk.version} - - - com.oracle.oci.sdk - oci-java-sdk-ailanguage - ${oci.sdk.version} - - - com.oracle.oci.sdk - oci-java-sdk-objectstorage - ${oci.sdk.version} - - - - org.slf4j - slf4j-simple - 2.0.6 - - - javax.xml.bind - jaxb-api - 2.4.0-b180830.0359 - - - com.fasterxml.jackson.core - jackson-databind - - - - - org.projectlombok - lombok - - - - com.theokanning.openai-gpt3-java - service - 0.12.0 - - - - - - org.springframework.boot - spring-boot-maven-plugin - - - org.apache.maven.plugins - maven-compiler-plugin - 1111 - - - - - - diff --git a/java-gcpspeechai/src/main/java/oracleai/AIApplication.java b/java-gcpspeechai/src/main/java/oracleai/AIApplication.java deleted file mode 100644 index 96ce305..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/AIApplication.java +++ /dev/null @@ -1,37 +0,0 @@ -package oracleai; - -import com.oracle.bmc.retrier.RetryConfiguration; -import org.springframework.boot.SpringApplication; -import org.springframework.boot.autoconfigure.SpringBootApplication; - - -@SpringBootApplication -public class AIApplication { - - public static final String COMPARTMENT_ID = System.getenv("COMPARTMENT_ID"); - public static final String OBJECTSTORAGE_NAMESPACE = System.getenv("OBJECTSTORAGE_NAMESPACE"); - public static final String OBJECTSTORAGE_BUCKETNAME = System.getenv("OBJECTSTORAGE_BUCKETNAME"); - public static final String ORDS_ENDPOINT_URL = System.getenv("ORDS_ENDPOINT_URL"); - public static final String ORDS_OMLOPSENDPOINT_URL= System.getenv("ORDS_ENDPOINT_URL") + "/omlopsuser/"; - public static final String OCI_VISION_SERVICE_ENDPOINT = System.getenv("OCI_VISION_SERVICE_ENDPOINT"); - public static final String OCICONFIG_FILE = System.getenv("OCICONFIG_FILE"); - public static final String OCICONFIG_PROFILE = System.getenv("OCICONFIG_PROFILE"); - public static final String DIGITAL_DOUBLES_IMAGES_ENDPOINT = System.getenv("DIGITAL_DOUBLES_IMAGES_ENDPOINT"); - public static final String THREEDEY = "msy_mykey"; - - static { - System.out.println("AIApplication.static initializer COMPARTMENT_ID:" + COMPARTMENT_ID); - System.out.println("AIApplication.static initializer OBJECTSTORAGE_NAMESPACE:" + OBJECTSTORAGE_NAMESPACE); - System.out.println("AIApplication.static initializer OBJECTSTORAGE_BUCKETNAME:" + OBJECTSTORAGE_BUCKETNAME); - System.out.println("AIApplication.static initializer ORDS_ENDPOINT_URL:" + ORDS_ENDPOINT_URL); - System.out.println("AIApplication.static initializer OCI_VISION_SERVICE_ENDPOINT:" + OCI_VISION_SERVICE_ENDPOINT); - } - - public static void main(String[] args) { -// RetryConfiguration retryConfiguration = RetryConfiguration.builder() -// .terminationStrategy(RetryUtils.createExponentialBackoffStrategy(500, 5)) // Configure limits -// .build(); - SpringApplication.run(AIApplication.class, args); - } - -} diff --git a/java-gcpspeechai/src/main/java/oracleai/ExplainAndAdviseOnHealthTestResults.java b/java-gcpspeechai/src/main/java/oracleai/ExplainAndAdviseOnHealthTestResults.java deleted file mode 100644 index f07506f..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/ExplainAndAdviseOnHealthTestResults.java +++ /dev/null @@ -1,69 +0,0 @@ -package oracleai; - -import com.fasterxml.jackson.databind.ObjectMapper; -import com.oracle.bmc.aivision.model.ImageTextDetectionFeature; -import com.oracle.bmc.generativeaiinference.model.OnDemandServingMode; -import oracleai.services.ORDSCalls; -import oracleai.services.OracleGenAI; -import oracleai.services.OracleObjectStore; -import oracleai.services.OracleVisionAI; -import org.springframework.stereotype.Controller; -import org.springframework.web.bind.annotation.*; -import org.springframework.web.multipart.MultipartFile; - -import org.springframework.ui.Model; - -@Controller -@RequestMapping("/health") -public class ExplainAndAdviseOnHealthTestResults { - - - @PostMapping("/analyzedoc") - public String analyzedoc(@RequestParam("file") MultipartFile multipartFile, - @RequestParam("opts") String opts, Model model) - throws Exception { - System.out.println("analyzedocmultipartFile = " + multipartFile + ", opts = " + opts); - String concatenatedText; - if (opts.equals("inline")) { - String objectDetectionResults = OracleVisionAI.processImage( - multipartFile.getBytes(), ImageTextDetectionFeature.builder().build()); - OracleVisionAI.ImageData imageData = - new ObjectMapper().readValue(objectDetectionResults, OracleVisionAI.ImageData.class); - concatenatedText = concatenateText(imageData); - } else { - OracleObjectStore.sendToObjectStorage(multipartFile.getOriginalFilename(), multipartFile.getInputStream()); - concatenatedText = ORDSCalls.analyzeImageInObjectStore( - AIApplication.ORDS_ENDPOINT_URL + "VISIONAI_TEXTDETECTION/", - AIApplication.OCI_VISION_SERVICE_ENDPOINT, - AIApplication.COMPARTMENT_ID, - AIApplication.OBJECTSTORAGE_BUCKETNAME, - AIApplication.OBJECTSTORAGE_NAMESPACE, - multipartFile.getOriginalFilename(), //"objectdetectiontestimage.jpg" - "TEXT_DETECTION", - "MedicalReportSummary"); - } - System.out.println(concatenatedText); - System.out.println("analyzedoc fullText = " + concatenatedText); - OnDemandServingMode chatServingMode = OnDemandServingMode.builder() - .modelId("cohere.command-r-16k") - .build(); - String explanationOfResults = - OracleGenAI.builder().compartment(AIApplication.COMPARTMENT_ID) - .servingMode(chatServingMode) - .build().chat("explain these test results in simple terms, in less than 100 words, " + - "and tell me what should I do to get better results: \"" + concatenatedText + "\""); - System.out.println("ExplainAndAdviseOnHealthTestResults.analyzedoc explanationOfResults:" + explanationOfResults); - model.addAttribute("results", "SUMMARY WITH ADVICE: " + explanationOfResults + - " ...This is of course not a substitute for actual medical advice from a professional."); - return "resultspage"; - } - - private static String concatenateText(OracleVisionAI.ImageData imageData) { - if (imageData.getImageText() == null || imageData.getImageText().getWords() == null) return ""; - StringBuilder sb = new StringBuilder(); - for (OracleVisionAI.Word word : imageData.getImageText().getWords()) { - sb.append(word.getText()).append(" "); - } - return sb.toString().trim(); - } -} diff --git a/java-gcpspeechai/src/main/java/oracleai/FaceRecognition.java b/java-gcpspeechai/src/main/java/oracleai/FaceRecognition.java deleted file mode 100644 index 3bc61f0..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/FaceRecognition.java +++ /dev/null @@ -1,87 +0,0 @@ -package oracleai; - -import com.oracle.bmc.aivision.model.FaceDetectionFeature; -import oracleai.services.OracleVisionAI; -import org.springframework.stereotype.Controller; -import org.springframework.ui.Model; -import org.springframework.web.bind.annotation.PostMapping; -import org.springframework.web.bind.annotation.RequestMapping; -import org.springframework.web.bind.annotation.RequestParam; -import org.springframework.web.multipart.MultipartFile; - - -@Controller -@RequestMapping("/facerecognition") -public class FaceRecognition { - - - @PostMapping("/facerecognition") - public String facerecognition(@RequestParam("file") MultipartFile multipartFile, Model model) - throws Exception { - model.addAttribute("results", - OracleVisionAI.processImage(multipartFile.getBytes(), FaceDetectionFeature.builder().shouldReturnLandmarks(true).build())); - return "resultspage"; - } - } - -/** - * { - * "ontologyClasses": [], - * "detectedFaces": [ - * { - * "confidence": 0.9453162, - * "boundingPolygon": { - * "normalizedVertices": [ - * { - * "x": 0.43885306576845223, - * "y": 0.33600531005859374 - * }, - * { - * "x": 0.5433995575670001, - * "y": 0.33600531005859374 - * }, - * { - * "x": 0.5433995575670001, - * "y": 0.404624267578125 - * }, - * { - * "x": 0.43885306576845223, - * "y": 0.404624267578125 - * } - * ] - * }, - * "qualityScore": 0.887661, - * "landmarks": [ - * { - * "type": "LEFT_EYE", - * "x": 0.46573874, - * "y": 0.36125 - * }, - * { - * "type": "RIGHT_EYE", - * "x": 0.5149893, - * "y": 0.36175 - * }, - * { - * "type": "NOSE_TIP", - * "x": 0.4898287, - * "y": 0.37575 - * }, - * { - * "type": "LEFT_EDGE_OF_MOUTH", - * "x": 0.46734476, - * "y": 0.3845 - * }, - * { - * "type": "RIGHT_EDGE_OF_MOUTH", - * "x": 0.51338327, - * "y": 0.38475 - * } - * ] - * } - * ], - * "faceDetectionModelVersion": "1.0.29", - * "errors": [] - * } - */ - diff --git a/java-gcpspeechai/src/main/java/oracleai/GenerateAPictureStoryUsingOnlySpeech.java b/java-gcpspeechai/src/main/java/oracleai/GenerateAPictureStoryUsingOnlySpeech.java deleted file mode 100644 index 47f2fdd..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/GenerateAPictureStoryUsingOnlySpeech.java +++ /dev/null @@ -1,189 +0,0 @@ -package oracleai; - -import com.fasterxml.jackson.core.JsonProcessingException; -import com.fasterxml.jackson.databind.ObjectMapper; -import oracleai.services.ImageGeneration; -import oracleai.services.OracleObjectStore; -import oracleai.services.OracleSpeechAI; -import org.jetbrains.annotations.NotNull; -import org.springframework.stereotype.Controller; -import org.springframework.ui.Model; -import org.springframework.web.bind.annotation.*; -import org.springframework.web.multipart.MultipartFile; - -import javax.sound.sampled.*; -import java.io.*; -import java.util.*; -import java.util.stream.Collectors; - -@Controller -@RequestMapping("/picturestory") -public class GenerateAPictureStoryUsingOnlySpeech { - - static List imageLocations = new ArrayList(); - - @GetMapping("/reset") - public String reset(Model model) { - imageLocations = new ArrayList(); - model.addAttribute("results", "story board cleared successfully"); - return "resultspage"; - } - - @PostMapping("/picturestory") - public String picturestory(@RequestParam("opts") String opts, - @RequestParam("genopts") String genopts, - @RequestParam("file") MultipartFile multipartFile, - Model model) throws Exception { - if (opts.equals("fileaudio") ) return fileaudio(genopts, multipartFile, model); - else return liveaudio(genopts, model); - } - - @NotNull - private String fileaudio(String genopts, MultipartFile multipartFile, Model model) throws Exception { - OracleObjectStore.sendToObjectStorage(multipartFile.getOriginalFilename(), multipartFile.getInputStream()); - String transcriptionJobId = OracleSpeechAI.getTranscriptFromOCISpeech(multipartFile.getOriginalFilename()); - System.out.println("transcriptionJobId: " + transcriptionJobId); - String jsonTranscriptFromObjectStorage = - OracleObjectStore.getFromObjectStorage(transcriptionJobId, - AIApplication.OBJECTSTORAGE_NAMESPACE + "_" + - AIApplication.OBJECTSTORAGE_BUCKETNAME + "_" + - multipartFile.getOriginalFilename() + ".json"); - System.out.println("jsonTranscriptFromObjectStorage: " + jsonTranscriptFromObjectStorage); - String pictureDescription = getConcatenatedTokens(jsonTranscriptFromObjectStorage); - imageLocations.add(ImageGeneration.imagegeneration(pictureDescription + " " + genopts)); - model.addAttribute("imageLocations", imageLocations.toArray(new String[0])); - return "resultswithimages"; - } - - public String liveaudio(String genopts, Model model) throws Exception { - AudioFormat format = - new AudioFormat(AudioFormat.Encoding.PCM_SIGNED, 44100.0f, 16, 1, - (16 / 8) * 1, 44100.0f, true); - SoundRecorder soundRecorder = new SoundRecorder(); - soundRecorder.build(format); - System.out.println("Start recording ...."); - soundRecorder.start(); - Thread.sleep(8000); - soundRecorder.stop(); - System.out.println("Stopped recording ...."); - Thread.sleep(5000); //give the process time - String name = "AISoundClip"; - AudioFileFormat.Type fileType = AudioFileFormat.Type.WAVE; - AudioInputStream audioInputStream = soundRecorder.audioInputStream; - System.out.println("Saving..."); - File file = new File(name + "." + fileType.getExtension()); - audioInputStream.reset(); - AudioSystem.write(audioInputStream, fileType, file); - System.out.println("Saved " + file.getAbsolutePath()); - OracleObjectStore.sendToObjectStorage(file.getName(), new FileInputStream(file)); - String transcriptionJobId = OracleSpeechAI.getTranscriptFromOCISpeech(file.getName()); - System.out.println("transcriptionJobId: " + transcriptionJobId); - String jsonTranscriptFromObjectStorage = - OracleObjectStore.getFromObjectStorage(transcriptionJobId, - AIApplication.OBJECTSTORAGE_NAMESPACE + "_" + - AIApplication.OBJECTSTORAGE_BUCKETNAME + "_" + file.getName() + ".json"); - System.out.println("jsonTranscriptFromObjectStorage: " + jsonTranscriptFromObjectStorage); - String pictureDescription = getConcatenatedTokens(jsonTranscriptFromObjectStorage); - imageLocations.add(ImageGeneration.imagegeneration(pictureDescription + " " + genopts)); - model.addAttribute("imageLocations", imageLocations.toArray(new String[0])); - return "resultswithimages"; - } - - public String getConcatenatedTokens(String json) { - ObjectMapper objectMapper = new ObjectMapper(); - try { - OracleSpeechAI.TranscriptionResponse response = - objectMapper.readValue(json, OracleSpeechAI.TranscriptionResponse.class); - return response.getTranscriptions().stream() - .flatMap(transcription -> transcription.getTokens().stream()) - .map(OracleSpeechAI.TranscriptionResponse.Transcription.Token::getToken) - .collect(Collectors.joining(" ")); - } catch (JsonProcessingException e) { - e.printStackTrace(); - return null; - } - } - - public class SoundRecorder implements Runnable { - AudioInputStream audioInputStream; - private AudioFormat format; - public Thread thread; - - - public SoundRecorder build(AudioFormat format) { - this.format = format; - return this; - } - - public void start() { - thread = new Thread(this); - thread.start(); - } - - public void stop() { - thread = null; - } - - @Override - public void run() { - try (final ByteArrayOutputStream out = new ByteArrayOutputStream(); - final TargetDataLine line = getTargetDataLineForRecord();) { - int frameSizeInBytes = format.getFrameSize(); - int bufferLengthInFrames = line.getBufferSize() / 8; - final int bufferLengthInBytes = bufferLengthInFrames * frameSizeInBytes; - buildByteOutputStream(out, line, frameSizeInBytes, bufferLengthInBytes); - this.audioInputStream = new AudioInputStream(line); - setAudioInputStream(convertToAudioIStream(out, frameSizeInBytes)); - audioInputStream.reset(); - } catch (IOException ex) { - ex.printStackTrace(); - } catch (Exception ex) { - ex.printStackTrace(); - } - } - - public void buildByteOutputStream(final ByteArrayOutputStream out, - final TargetDataLine line, int frameSizeInBytes, - final int bufferLengthInBytes) throws IOException { - final byte[] data = new byte[bufferLengthInBytes]; - int numBytesRead; - - line.start(); - while (thread != null) { - if ((numBytesRead = line.read(data, 0, bufferLengthInBytes)) == -1) { - break; - } - out.write(data, 0, numBytesRead); - } - } - - private void setAudioInputStream(AudioInputStream aStream) { - this.audioInputStream = aStream; - } - - public AudioInputStream convertToAudioIStream(final ByteArrayOutputStream out, int frameSizeInBytes) { - byte[] audioBytes = out.toByteArray(); - AudioInputStream audioStream = - new AudioInputStream(new ByteArrayInputStream(audioBytes), format, - audioBytes.length / frameSizeInBytes); - System.out.println("Recording finished"); - return audioStream; - } - - public TargetDataLine getTargetDataLineForRecord() { - TargetDataLine line; - DataLine.Info info = new DataLine.Info(TargetDataLine.class, format); - if (!AudioSystem.isLineSupported(info)) { - throw new UnsupportedOperationException("Line not supported"); - } - try { - line = (TargetDataLine) AudioSystem.getLine(info); - line.open(format, line.getBufferSize()); - } catch (final Exception ex) { - return null; - } - return line; - } - } - -} diff --git a/java-gcpspeechai/src/main/java/oracleai/InfiniteStreamRecognize.java b/java-gcpspeechai/src/main/java/oracleai/InfiniteStreamRecognize.java deleted file mode 100644 index 506582c..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/InfiniteStreamRecognize.java +++ /dev/null @@ -1,284 +0,0 @@ -package oracleai; - - -import com.google.api.gax.rpc.ClientStream; -import com.google.api.gax.rpc.ResponseObserver; -import com.google.api.gax.rpc.StreamController; -import com.google.cloud.speech.v1p1beta1.RecognitionConfig; -import com.google.cloud.speech.v1p1beta1.SpeechClient; -import com.google.cloud.speech.v1p1beta1.SpeechRecognitionAlternative; -import com.google.cloud.speech.v1p1beta1.StreamingRecognitionConfig; -import com.google.cloud.speech.v1p1beta1.StreamingRecognitionResult; -import com.google.cloud.speech.v1p1beta1.StreamingRecognizeRequest; -import com.google.cloud.speech.v1p1beta1.StreamingRecognizeResponse; -import com.google.protobuf.ByteString; -import com.google.protobuf.Duration; -import java.text.DecimalFormat; -import java.util.ArrayList; -import java.util.concurrent.BlockingQueue; -import java.util.concurrent.LinkedBlockingQueue; -import java.util.concurrent.TimeUnit; -import javax.sound.sampled.AudioFormat; -import javax.sound.sampled.AudioSystem; -import javax.sound.sampled.DataLine; -import javax.sound.sampled.DataLine.Info; -import javax.sound.sampled.TargetDataLine; - -public class InfiniteStreamRecognize { - - private static final int STREAMING_LIMIT = 290000; // ~5 minutes - - public static final String RED = "\033[0;31m"; - public static final String GREEN = "\033[0;32m"; - public static final String YELLOW = "\033[0;33m"; - - // Creating shared object - private static volatile BlockingQueue sharedQueue = new LinkedBlockingQueue(); - private static TargetDataLine targetDataLine; - private static int BYTES_PER_BUFFER = 6400; // buffer size in bytes - - private static int restartCounter = 0; - private static ArrayList audioInput = new ArrayList(); - private static ArrayList lastAudioInput = new ArrayList(); - private static int resultEndTimeInMS = 0; - private static int isFinalEndTime = 0; - private static int finalRequestEndTime = 0; - private static boolean newStream = true; - private static double bridgingOffset = 0; - private static boolean lastTranscriptWasFinal = false; - private static StreamController referenceToStreamController; - private static ByteString tempByteString; - - public static void main(String... args) { - InfiniteStreamRecognizeOptions options = InfiniteStreamRecognizeOptions.fromFlags(args); - if (options == null) { - // Could not parse. - System.out.println("Failed to parse options."); - System.exit(1); - } - - try { - infiniteStreamingRecognize(options.langCode); - } catch (Exception e) { - System.out.println("Exception caught: " + e); - } - } - - public static String convertMillisToDate(double milliSeconds) { - long millis = (long) milliSeconds; - DecimalFormat format = new DecimalFormat(); - format.setMinimumIntegerDigits(2); - return String.format( - "%s:%s /", - format.format(TimeUnit.MILLISECONDS.toMinutes(millis)), - format.format( - TimeUnit.MILLISECONDS.toSeconds(millis) - - TimeUnit.MINUTES.toSeconds(TimeUnit.MILLISECONDS.toMinutes(millis)))); - } - - /** Performs infinite streaming speech recognition */ - public static void infiniteStreamingRecognize(String languageCode) throws Exception { - - // Microphone Input buffering - class MicBuffer implements Runnable { - - @Override - public void run() { - System.out.println(YELLOW); - System.out.println("Start speaking...Press Ctrl-C to stop"); - targetDataLine.start(); - byte[] data = new byte[BYTES_PER_BUFFER]; - while (targetDataLine.isOpen()) { - try { - int numBytesRead = targetDataLine.read(data, 0, data.length); - if ((numBytesRead <= 0) && (targetDataLine.isOpen())) { - continue; - } - sharedQueue.put(data.clone()); - } catch (InterruptedException e) { - System.out.println("Microphone input buffering interrupted : " + e.getMessage()); - } - } - } - } - - // Creating microphone input buffer thread - MicBuffer micrunnable = new MicBuffer(); - Thread micThread = new Thread(micrunnable); - ResponseObserver responseObserver = null; - try (SpeechClient client = SpeechClient.create()) { - ClientStream clientStream; - responseObserver = - new ResponseObserver() { - - ArrayList responses = new ArrayList<>(); - - public void onStart(StreamController controller) { - referenceToStreamController = controller; - } - - public void onResponse(StreamingRecognizeResponse response) { - responses.add(response); - StreamingRecognitionResult result = response.getResultsList().get(0); - Duration resultEndTime = result.getResultEndTime(); - resultEndTimeInMS = - (int) - ((resultEndTime.getSeconds() * 1000) + (resultEndTime.getNanos() / 1000000)); - double correctedTime = - resultEndTimeInMS - bridgingOffset + (STREAMING_LIMIT * restartCounter); - - SpeechRecognitionAlternative alternative = result.getAlternativesList().get(0); - if (result.getIsFinal()) { - System.out.print(GREEN); - System.out.print("\033[2K\r"); - System.out.printf( - "%s: %s [confidence: %.2f]\n", - convertMillisToDate(correctedTime), - alternative.getTranscript(), - alternative.getConfidence()); - isFinalEndTime = resultEndTimeInMS; - lastTranscriptWasFinal = true; - } else { - System.out.print(RED); - System.out.print("\033[2K\r"); - System.out.printf( - "%s: %s", convertMillisToDate(correctedTime), alternative.getTranscript()); - lastTranscriptWasFinal = false; - } - } - - public void onComplete() {} - - public void onError(Throwable t) {} - }; - clientStream = client.streamingRecognizeCallable().splitCall(responseObserver); - - RecognitionConfig recognitionConfig = - RecognitionConfig.newBuilder() - .setEncoding(RecognitionConfig.AudioEncoding.LINEAR16) - .setLanguageCode(languageCode) - .setSampleRateHertz(16000) - .build(); - - StreamingRecognitionConfig streamingRecognitionConfig = - StreamingRecognitionConfig.newBuilder() - .setConfig(recognitionConfig) - .setInterimResults(true) - .build(); - - StreamingRecognizeRequest request = - StreamingRecognizeRequest.newBuilder() - .setStreamingConfig(streamingRecognitionConfig) - .build(); // The first request in a streaming call has to be a config - - clientStream.send(request); - - try { - // SampleRate:16000Hz, SampleSizeInBits: 16, Number of channels: 1, Signed: true, - // bigEndian: false - AudioFormat audioFormat = new AudioFormat(16000, 16, 1, true, false); - DataLine.Info targetInfo = - new Info( - TargetDataLine.class, - audioFormat); // Set the system information to read from the microphone audio - // stream - - if (!AudioSystem.isLineSupported(targetInfo)) { - System.out.println("Microphone not supported"); - System.exit(0); - } - // Target data line captures the audio stream the microphone produces. - targetDataLine = (TargetDataLine) AudioSystem.getLine(targetInfo); - targetDataLine.open(audioFormat); - micThread.start(); - - long startTime = System.currentTimeMillis(); - - while (true) { - - long estimatedTime = System.currentTimeMillis() - startTime; - - if (estimatedTime >= STREAMING_LIMIT) { - - clientStream.closeSend(); - referenceToStreamController.cancel(); // remove Observer - - if (resultEndTimeInMS > 0) { - finalRequestEndTime = isFinalEndTime; - } - resultEndTimeInMS = 0; - - lastAudioInput = null; - lastAudioInput = audioInput; - audioInput = new ArrayList(); - - restartCounter++; - - if (!lastTranscriptWasFinal) { - System.out.print('\n'); - } - - newStream = true; - - clientStream = client.streamingRecognizeCallable().splitCall(responseObserver); - - request = - StreamingRecognizeRequest.newBuilder() - .setStreamingConfig(streamingRecognitionConfig) - .build(); - - System.out.println(YELLOW); - System.out.printf("%d: RESTARTING REQUEST\n", restartCounter * STREAMING_LIMIT); - - startTime = System.currentTimeMillis(); - - } else { - - if ((newStream) && (lastAudioInput.size() > 0)) { - // if this is the first audio from a new request - // calculate amount of unfinalized audio from last request - // resend the audio to the speech client before incoming audio - double chunkTime = STREAMING_LIMIT / lastAudioInput.size(); - // ms length of each chunk in previous request audio arrayList - if (chunkTime != 0) { - if (bridgingOffset < 0) { - // bridging Offset accounts for time of resent audio - // calculated from last request - bridgingOffset = 0; - } - if (bridgingOffset > finalRequestEndTime) { - bridgingOffset = finalRequestEndTime; - } - int chunksFromMs = - (int) Math.floor((finalRequestEndTime - bridgingOffset) / chunkTime); - // chunks from MS is number of chunks to resend - bridgingOffset = - (int) Math.floor((lastAudioInput.size() - chunksFromMs) * chunkTime); - // set bridging offset for next request - for (int i = chunksFromMs; i < lastAudioInput.size(); i++) { - request = - StreamingRecognizeRequest.newBuilder() - .setAudioContent(lastAudioInput.get(i)) - .build(); - clientStream.send(request); - } - } - newStream = false; - } - - tempByteString = ByteString.copyFrom(sharedQueue.take()); - - request = - StreamingRecognizeRequest.newBuilder().setAudioContent(tempByteString).build(); - - audioInput.add(tempByteString); - } - - clientStream.send(request); - } - } catch (Exception e) { - System.out.println(e); - } - } - } -} diff --git a/java-gcpspeechai/src/main/java/oracleai/TextSearch.java b/java-gcpspeechai/src/main/java/oracleai/TextSearch.java deleted file mode 100644 index 1b64898..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/TextSearch.java +++ /dev/null @@ -1,24 +0,0 @@ -package oracleai; - - -import oracleai.services.ORDSCalls; -import org.springframework.stereotype.Controller; -import org.springframework.ui.Model; -import org.springframework.web.bind.annotation.PostMapping; -import org.springframework.web.bind.annotation.RequestMapping; -import org.springframework.web.bind.annotation.RequestParam; - - -@Controller -@RequestMapping("/textsearch") -public class TextSearch { - - @PostMapping("/textsearch") - public String textsearch(@RequestParam("sql") String sql, Model model) { - String explanationOfResults = ORDSCalls.executeTextSearchContains( - AIApplication.ORDS_ENDPOINT_URL + "VISIONAI_RESULTS_TEXT_SEARCH/", sql); - model.addAttribute("results", explanationOfResults); - return "resultspage"; - } - -} diff --git a/java-gcpspeechai/src/main/java/oracleai/UploadDownloadImage.java b/java-gcpspeechai/src/main/java/oracleai/UploadDownloadImage.java deleted file mode 100644 index fd566a8..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/UploadDownloadImage.java +++ /dev/null @@ -1,30 +0,0 @@ -package oracleai; - -import oracleai.digitaldouble.ImageStore; -import oracleai.services.ORDSCalls; -import org.springframework.stereotype.Controller; -import org.springframework.ui.Model; -import org.springframework.web.bind.annotation.*; -import org.springframework.web.multipart.MultipartFile; - - -@Controller -@RequestMapping("/transferimage") -public class UploadDownloadImage { - - @PostMapping("/uploadimage") - public String uploadImage(@RequestParam("image") MultipartFile image, Model model) { - ORDSCalls.uploadImage(image); - System.out.println("Image upload complete for: " + image.getOriginalFilename()); - ImageStore[] imageStores = ORDSCalls.getImageStoreData(); - model.addAttribute("images", imageStores); - return "images"; - } - - @GetMapping("/downloadimages") - public String getImageStoreData(Model model) { - ImageStore[] imageStores = ORDSCalls.getImageStoreData(); - model.addAttribute("images", imageStores); - return "images"; - } -} diff --git a/java-gcpspeechai/src/main/java/oracleai/WriteAStoryAboutAPictureAndGiveItsSentiments.java b/java-gcpspeechai/src/main/java/oracleai/WriteAStoryAboutAPictureAndGiveItsSentiments.java deleted file mode 100644 index 7e15d6c..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/WriteAStoryAboutAPictureAndGiveItsSentiments.java +++ /dev/null @@ -1,53 +0,0 @@ -package oracleai; - -import com.fasterxml.jackson.databind.ObjectMapper; -import com.oracle.bmc.aivision.model.*; -import oracleai.services.*; -import org.springframework.stereotype.Controller; -import org.springframework.web.bind.annotation.*; -import org.springframework.web.multipart.MultipartFile; -import org.springframework.ui.Model; - -@Controller -@RequestMapping("/tellastory") -public class WriteAStoryAboutAPictureAndGiveItsSentiments { - - @PostMapping("/tellastory") - public String tellastory(@RequestParam("file") MultipartFile multipartFile, @RequestParam("opts") String opts, - @RequestParam("genopts") String genopts, Model model) - throws Exception { - System.out.println("WriteAStoryAboutAPictureAndGiveItsSentiments.tellastory file = " + - multipartFile.getOriginalFilename()); - String fullText = ""; - if(opts.equals("inline")) { - String objectDetectionResults = - OracleVisionAI.processImage(multipartFile.getBytes(), - ImageObjectDetectionFeature.builder().maxResults(10).build()); - OracleVisionAI.ImageAnalysisResult imageAnalysis = - new ObjectMapper().readValue(objectDetectionResults, OracleVisionAI.ImageAnalysisResult.class); - for (OracleVisionAI.ImageObject image : imageAnalysis.getImageObjects()) fullText += image.getName() + ", "; - System.out.println("WriteAStoryAboutAPictureAndGiveItsSentiments.tellastory images = " + fullText); - } - else { - OracleObjectStore.sendToObjectStorage(multipartFile.getOriginalFilename(), multipartFile.getInputStream()); - fullText = ORDSCalls.analyzeImageInObjectStore( - AIApplication.ORDS_ENDPOINT_URL + "VISIONAI_OBJECTDETECTION/", - AIApplication.OCI_VISION_SERVICE_ENDPOINT, - AIApplication.COMPARTMENT_ID, - AIApplication.OBJECTSTORAGE_BUCKETNAME, - AIApplication.OBJECTSTORAGE_NAMESPACE, - multipartFile.getOriginalFilename(), //"objectdetectiontestimage.jpg" - "OBJECT_DETECTION", - "TellAStory"); - } - String generatedstory = OracleGenAI.builder().build().chat("using strong negative and positive sentiments, " + - "write a story that is " + genopts + " and includes " + fullText ); - model.addAttribute("results", "STORY: " + generatedstory + - " --->SENTIMENT ANALYSIS: " + OracleLanguageAI.sentimentAnalysis(generatedstory) ); - return "resultspage"; - } - -} - - - diff --git a/java-gcpspeechai/src/main/java/oracleai/common/FileUploadExceptionAdvice.java b/java-gcpspeechai/src/main/java/oracleai/common/FileUploadExceptionAdvice.java deleted file mode 100644 index f164b7d..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/common/FileUploadExceptionAdvice.java +++ /dev/null @@ -1,16 +0,0 @@ -package oracleai.common; - -import org.springframework.http.HttpStatus; -import org.springframework.http.ResponseEntity; -import org.springframework.web.bind.annotation.ControllerAdvice; -import org.springframework.web.bind.annotation.ExceptionHandler; -import org.springframework.web.multipart.MaxUploadSizeExceededException; - -@ControllerAdvice -public class FileUploadExceptionAdvice { - - @ExceptionHandler(MaxUploadSizeExceededException.class) - public ResponseEntity handleMaxSizeException(MaxUploadSizeExceededException exc) { - return ResponseEntity.status(HttpStatus.EXPECTATION_FAILED).body("File too large!"); - } -} \ No newline at end of file diff --git a/java-gcpspeechai/src/main/java/oracleai/digitaldouble/DigitalDoubleDownloadInfo.java b/java-gcpspeechai/src/main/java/oracleai/digitaldouble/DigitalDoubleDownloadInfo.java deleted file mode 100644 index 1b90219..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/digitaldouble/DigitalDoubleDownloadInfo.java +++ /dev/null @@ -1,103 +0,0 @@ -package oracleai.digitaldouble; - -public class DigitalDoubleDownloadInfo { - - String email; - String modelUrl; - String modelGlbUrl; - String modelFbxUrl ; - String modelUsdzUrl ; - String thumbnailUrl; - String animatedVideoLocation; - String similarImageUrl; - - - - public DigitalDoubleDownloadInfo() { - - } - public DigitalDoubleDownloadInfo(String modelUrl, String modelGlbUrl, String modelFbxUrl, - String modelUsdzUrl, String thumbnailUrl) { - this.modelUrl = modelUrl; - this.modelGlbUrl = modelGlbUrl; - this.modelFbxUrl = modelFbxUrl; - this.modelUsdzUrl = modelUsdzUrl; - this.thumbnailUrl = thumbnailUrl; - } - - public DigitalDoubleDownloadInfo(String modelGlbUrl, String modelFbxUrl, String modelUsdzUrl, - String thumbnailUrl, String animatedVideoLocation, - String email, String similarImageUrl) { - this.modelGlbUrl = modelGlbUrl; - this.modelFbxUrl = modelFbxUrl; - this.modelUsdzUrl = modelUsdzUrl; - this.thumbnailUrl = thumbnailUrl; - this.animatedVideoLocation = animatedVideoLocation; - this.email = email; - this.similarImageUrl = similarImageUrl; - } - - public void setEmail(String email) { - this.email = email; - } - - public void setModelUrl(String modelUrl) { - this.modelUrl = modelUrl; - } - - public void setModelGlbUrl(String modelGlbUrl) { - this.modelGlbUrl = modelGlbUrl; - } - - public void setModelFbxUrl(String modelFbxUrl) { - this.modelFbxUrl = modelFbxUrl; - } - - public void setModelUsdzUrl(String modelUsdzUrl) { - this.modelUsdzUrl = modelUsdzUrl; - } - - public void setThumbnailUrl(String thumbnailUrl) { - this.thumbnailUrl = thumbnailUrl; - } - - public void setAnimatedVideoLocation(String animatedVideoLocation) { - this.animatedVideoLocation = animatedVideoLocation; - } - - public void setSimilarImageUrl(String similarImageUrl) { - this.similarImageUrl = similarImageUrl; - } - - public String getEmail() { - return email; - } - - public String getModelUrl() { - return modelUrl; - } - - public String getModelGlbUrl() { - return modelGlbUrl; - } - - public String getModelFbxUrl() { - return modelFbxUrl; - } - - public String getModelUsdzUrl() { - return modelUsdzUrl; - } - - public String getThumbnailUrl() { - return thumbnailUrl; - } - - public String getAnimatedVideoLocation() { - return animatedVideoLocation; - } - - public String getSimilarImageUrl() { - return similarImageUrl; - } -} diff --git a/java-gcpspeechai/src/main/java/oracleai/digitaldouble/DigitalDoubleService.java b/java-gcpspeechai/src/main/java/oracleai/digitaldouble/DigitalDoubleService.java deleted file mode 100644 index f660a46..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/digitaldouble/DigitalDoubleService.java +++ /dev/null @@ -1,39 +0,0 @@ -package oracleai.digitaldouble; - -import oracleai.AIApplication; -import org.springframework.http.*; -import org.springframework.stereotype.Service; -import org.springframework.web.client.RestTemplate; - -import java.util.HashMap; -import java.util.Map; - -@Service -public class DigitalDoubleService { - - public void updateDigitalDoubleData(DigitalDoubleDownloadInfo info) { - String url = AIApplication.ORDS_OMLOPSENDPOINT_URL + "update_digital_double_data/"; - - HttpHeaders headers = new HttpHeaders(); - headers.setContentType(MediaType.APPLICATION_JSON); - - Map requestBody = new HashMap<>(); - requestBody.put("p_participant_email", info.getEmail()); - requestBody.put("p_modelglburl_out", info.getModelGlbUrl()); - requestBody.put("p_modelfbxurl_out", info.modelFbxUrl); - requestBody.put("p_modelusdzurl_out", info.modelUsdzUrl); - requestBody.put("p_thumbnailurl_out", info.thumbnailUrl); - - HttpEntity> entity = new HttpEntity<>(requestBody, headers); - - ResponseEntity response = - new RestTemplate().exchange(url, HttpMethod.POST, entity, String.class); - - if (response.getStatusCode().is2xxSuccessful()) { - System.out.println("Request successful: " + response.getBody()); - } else { - System.err.println("Request failed with status code: " + response.getStatusCode()); - } - - } -} \ No newline at end of file diff --git a/java-gcpspeechai/src/main/java/oracleai/digitaldouble/DigitalDoublesController.java b/java-gcpspeechai/src/main/java/oracleai/digitaldouble/DigitalDoublesController.java deleted file mode 100644 index 2276965..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/digitaldouble/DigitalDoublesController.java +++ /dev/null @@ -1,94 +0,0 @@ -package oracleai.digitaldouble; - - -import oracleai.services.ORDSCalls; -import oracleai.services.OracleObjectStore; -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.http.ResponseEntity; -import org.springframework.stereotype.Controller; -import org.springframework.ui.Model; -import org.springframework.web.bind.annotation.*; -import org.springframework.web.multipart.MultipartFile; - -import java.io.File; -import java.io.IOException; - -import org.springframework.http.MediaType; - -@Controller -@RequestMapping("/digitaldoubles") -public class DigitalDoublesController { - - private final ImageProcessor imageProcessor; - - @Autowired - public DigitalDoublesController(ImageProcessor imageProcessor) { - this.imageProcessor = imageProcessor; - } - private static final String DIRECTORY = "/tmp/images/"; - - @GetMapping("/uploadordownload") - public String digitaldouble(@RequestParam("action") String action, Model model) { - return action.equals("uploading") ? "digitaldoubleupload" : "digitaldoubledownload"; - } - - - @PostMapping("/uploadimageandvideo") - public String uploadimageandvideo( - @RequestParam("image") MultipartFile image, - @RequestParam("video") MultipartFile video, - @RequestParam("animstyle") String animstyle, - @RequestParam("animprompt") String animprompt, - @RequestParam("firstName") String firstName, - @RequestParam("lastName") String lastName, - @RequestParam("email") String email, - @RequestParam("company") String company, - @RequestParam("jobrole") String jobRole, - @RequestParam("tshirtsize") String tshirtSize, - @RequestParam("comments") String comments, - Model model) throws IOException { - - String commentsWithAnimStyleAndPrompt = animstyle + " " + animprompt + " " + comments; - System.out.println("image = " + image + ", video = " + video + ", animstyle = " + animstyle + - ", firstName = " + firstName + ", lastName = " + lastName + - ", email = " + email + ", company = " + company + - ", jobRole = " + jobRole + ", tshirtSize = " + tshirtSize + - ", comments = " + comments + ", model = " + model + - "\ncomments with animstyle and prompt = " + commentsWithAnimStyleAndPrompt); - ORDSCalls.insertDigitalDoubleData( - image, null, firstName, lastName, email, company, jobRole, tshirtSize, commentsWithAnimStyleAndPrompt); - - String fullVideoName =""; - if (!video.isEmpty()) { - fullVideoName = email + "_" + animstyle + "_" + video.getOriginalFilename(); - OracleObjectStore.sendToObjectStorage(fullVideoName, video.getInputStream()); - } - imageProcessor.handleImageUpload(email, image, fullVideoName); - - return "digitaldoubledownload"; - - } - - @GetMapping("/images/{filename:.+}") - public ResponseEntity getImage(@PathVariable String filename) throws IOException { - try { - File file = new File(DIRECTORY, filename); - byte[] fileContent = org.apache.commons.io.FileUtils.readFileToByteArray(file); - return ResponseEntity.ok().contentType(MediaType.IMAGE_JPEG).body(fileContent); - } catch (IOException e) { - return ResponseEntity.notFound().build(); - } - } - - - @PostMapping("/downloaddigitaldouble") - public String downloaddigitaldouble(@RequestParam("email") String email, Model model) throws Exception { - model.addAttribute("fbxlink", ORDSCalls.getDigitalDoubleData(email)); - model.addAttribute("fbxtext", "FBX 3D Model"); - model.addAttribute("mp4link", ImageProcessor.objectStoreLocation + email + ".mp4"); - model.addAttribute("mp4text", "MP4 Animation"); - return "digitaldoubleresults"; - } - - -} diff --git a/java-gcpspeechai/src/main/java/oracleai/digitaldouble/ImageProcessor.java b/java-gcpspeechai/src/main/java/oracleai/digitaldouble/ImageProcessor.java deleted file mode 100644 index 2592dbb..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/digitaldouble/ImageProcessor.java +++ /dev/null @@ -1,108 +0,0 @@ -package oracleai.digitaldouble; - -import oracleai.AIApplication; -import oracleai.services.ORDSCalls; -import org.apache.commons.io.FileUtils; -import org.springframework.beans.factory.annotation.Autowired; -import org.springframework.stereotype.Service; -import org.springframework.web.multipart.MultipartFile; - -import java.io.File; -import java.io.IOException; -import java.nio.file.Path; -import java.nio.file.Paths; -import java.util.concurrent.BlockingQueue; -import java.util.concurrent.LinkedBlockingQueue; - -@Service -public class ImageProcessor { - - private static final String DIRECTORY = "/tmp/images/"; - private static final BlockingQueue queue = new LinkedBlockingQueue<>(); - - // Inject DigitalDoubleService to make REST call - private final DigitalDoubleService digitalDoubleService; - - @Autowired - public ImageProcessor(DigitalDoubleService digitalDoubleService) { - this.digitalDoubleService = digitalDoubleService; - new Thread(this::processQueue).start(); - } - - public String handleImageUpload(String email, MultipartFile image, String fullVideoName) throws IOException { - String imageFileNameWithEmailPrefix = ""; - if (image != null && !image.isEmpty()) { - FileUtils.forceMkdir(new File(DIRECTORY)); - imageFileNameWithEmailPrefix = email + "_" + image.getOriginalFilename(); - Path path = Paths.get(DIRECTORY + imageFileNameWithEmailPrefix); - image.transferTo(path); - } - queue.offer(new ImageTask(email, imageFileNameWithEmailPrefix, fullVideoName)); - return "Image is being processed"; - } - - public static String objectStoreLocation = - "https://" + AIApplication.OBJECTSTORAGE_NAMESPACE + ".compat.objectstorage.us-ashburn-1.oraclecloud.com/" + - AIApplication.OBJECTSTORAGE_BUCKETNAME + "/anim/"; - - private void processQueue() { - while (true) { - try { - ImageTask task = queue.take(); - DigitalDoubleDownloadInfo digitalDoubleDownloadInfo; - if (!task.getImageFileNameWithEmailPrefix().equals("")) { - digitalDoubleDownloadInfo = ORDSCalls.convertImageAndQueueResults( - AIApplication.DIGITAL_DOUBLES_IMAGES_ENDPOINT, - task.getImageFileNameWithEmailPrefix()); - } else { - digitalDoubleDownloadInfo = new DigitalDoubleDownloadInfo(); - } - - digitalDoubleDownloadInfo.animatedVideoLocation = objectStoreLocation + task.getFullVideoName(); - - // Call the method to update Digital Double data - digitalDoubleService.updateDigitalDoubleData( - new DigitalDoubleDownloadInfo( - digitalDoubleDownloadInfo.modelGlbUrl, - digitalDoubleDownloadInfo.modelFbxUrl, - digitalDoubleDownloadInfo.modelUsdzUrl, - digitalDoubleDownloadInfo.thumbnailUrl, - digitalDoubleDownloadInfo.animatedVideoLocation, - task.getEmail(), - "" // Similar image can be passed here if available - ) - ); - - } catch (InterruptedException e) { - Thread.currentThread().interrupt(); - break; - } catch (Exception e) { - System.err.println("Failed to process image for: " + e.getMessage()); - } - } - } - - private static class ImageTask { - private final String email; - private final String imageFileNameWithEmailPrefix; - private final String fullVideoName; - - public ImageTask(String email, String imageFileNameWithEmailPrefix, String fullVideoName) { - this.email = email; - this.imageFileNameWithEmailPrefix = imageFileNameWithEmailPrefix; - this.fullVideoName = fullVideoName; - } - - public String getEmail() { - return email; - } - - public String getImageFileNameWithEmailPrefix() { - return imageFileNameWithEmailPrefix; - } - - public String getFullVideoName() { - return fullVideoName; - } - } -} \ No newline at end of file diff --git a/java-gcpspeechai/src/main/java/oracleai/digitaldouble/ImageStore.java b/java-gcpspeechai/src/main/java/oracleai/digitaldouble/ImageStore.java deleted file mode 100644 index e4fd2d2..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/digitaldouble/ImageStore.java +++ /dev/null @@ -1,38 +0,0 @@ -package oracleai.digitaldouble; -import com.fasterxml.jackson.annotation.JsonIgnoreProperties; -import com.fasterxml.jackson.annotation.JsonProperty; - -@JsonIgnoreProperties(ignoreUnknown = true) -public class ImageStore { - private Long id; - - @JsonProperty("image_name") - private String imageName; - - @JsonProperty("image") // Assuming the BLOB is mapped to this field - private String imageBase64; - - public Long getId() { - return id; - } - - public void setId(Long id) { - this.id = id; - } - - public String getImageName() { - return imageName; - } - - public void setImageName(String imageName) { - this.imageName = imageName; - } - - public String getImageBase64() { - return imageBase64; - } - - public void setImageBase64(String imageBase64) { - this.imageBase64 = imageBase64; - } -} \ No newline at end of file diff --git a/java-gcpspeechai/src/main/java/oracleai/digitaldouble/ImageStoreWrapper.java b/java-gcpspeechai/src/main/java/oracleai/digitaldouble/ImageStoreWrapper.java deleted file mode 100644 index 29f230d..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/digitaldouble/ImageStoreWrapper.java +++ /dev/null @@ -1,17 +0,0 @@ -package oracleai.digitaldouble; - -import com.fasterxml.jackson.annotation.JsonIgnoreProperties; -import java.util.List; - -@JsonIgnoreProperties(ignoreUnknown = true) -public class ImageStoreWrapper { - private List items; - - public List getItems() { - return items; - } - - public void setItems(List items) { - this.items = items; - } -} \ No newline at end of file diff --git a/java-gcpspeechai/src/main/java/oracleai/services/AuthProvider.java b/java-gcpspeechai/src/main/java/oracleai/services/AuthProvider.java deleted file mode 100644 index 995727d..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/services/AuthProvider.java +++ /dev/null @@ -1,23 +0,0 @@ -package oracleai.services; - -import com.oracle.bmc.auth.ConfigFileAuthenticationDetailsProvider; -import com.oracle.bmc.auth.BasicAuthenticationDetailsProvider; -import com.oracle.bmc.auth.InstancePrincipalsAuthenticationDetailsProvider; -import oracleai.AIApplication; - -import java.io.IOException; - -public class AuthProvider { - - public static BasicAuthenticationDetailsProvider getAuthenticationDetailsProvider() throws IOException { - if (isRunningInOKE()) return InstancePrincipalsAuthenticationDetailsProvider.builder().build(); - else return new ConfigFileAuthenticationDetailsProvider( -// "~/.oci/config", "DEFAULT"); - AIApplication.OCICONFIG_FILE, AIApplication.OCICONFIG_PROFILE); - } - - private static boolean isRunningInOKE() { - return false; //System.getenv("OCI_RESOURCE_PRINCIPAL_VERSION") != null; - } - -} diff --git a/java-gcpspeechai/src/main/java/oracleai/services/DigitalDoubleDataRequest.java b/java-gcpspeechai/src/main/java/oracleai/services/DigitalDoubleDataRequest.java deleted file mode 100644 index 779c885..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/services/DigitalDoubleDataRequest.java +++ /dev/null @@ -1,15 +0,0 @@ -package oracleai.services; - -public class DigitalDoubleDataRequest { - public String p_participant_firstname; - public String p_participant_lastname; - public String p_participant_email; - public String p_participant_company; - public String p_participant_role; - public String p_participant_tshirt; - public String p_participant_comments; - public String p_id_image_in; // You can change this to byte[] for BLOB - public String p_image_in; // You can change this to byte[] for BLOB - public String p_video_in; // You can change this to byte[] for BLOB - -} \ No newline at end of file diff --git a/java-gcpspeechai/src/main/java/oracleai/services/DigitalDoubleORDS.java b/java-gcpspeechai/src/main/java/oracleai/services/DigitalDoubleORDS.java deleted file mode 100644 index 7910cb3..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/services/DigitalDoubleORDS.java +++ /dev/null @@ -1,32 +0,0 @@ -package oracleai.services; - -import oracleai.AIApplication; -import org.springframework.http.HttpEntity; -import org.springframework.http.HttpHeaders; -import org.springframework.http.HttpMethod; -import org.springframework.http.MediaType; -import org.springframework.http.ResponseEntity; -import org.springframework.web.client.RestTemplate; - -public class DigitalDoubleORDS { - - public void insertDigitalDoubleData(DigitalDoubleDataRequest request) { - String url = AIApplication.ORDS_OMLOPSENDPOINT_URL + "insert_digital_double_data/"; - - RestTemplate restTemplate = new RestTemplate(); - - HttpHeaders headers = new HttpHeaders(); - headers.setContentType(MediaType.APPLICATION_JSON); - - HttpEntity entity = new HttpEntity<>(request, headers); - - ResponseEntity response = restTemplate.exchange( - url, - HttpMethod.POST, - entity, - String.class - ); - - System.out.println(response.getBody()); - } -} \ No newline at end of file diff --git a/java-gcpspeechai/src/main/java/oracleai/services/ImageGeneration.java b/java-gcpspeechai/src/main/java/oracleai/services/ImageGeneration.java deleted file mode 100644 index 7ee33d8..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/services/ImageGeneration.java +++ /dev/null @@ -1,22 +0,0 @@ -package oracleai.services; - -import com.theokanning.openai.image.CreateImageRequest; -import com.theokanning.openai.service.OpenAiService; - -import java.time.Duration; - -public class ImageGeneration { - - static public String imagegeneration(String imagedescription) throws Exception { - OpenAiService service = - new OpenAiService(System.getenv("OPENAI_KEY"), Duration.ofSeconds(60)); - CreateImageRequest openairequest = CreateImageRequest.builder() - .prompt(imagedescription) - .build(); - String imageLocation = service.createImage(openairequest).getData().get(0).getUrl(); - System.out.println("Image is located at:" + imageLocation); - service.shutdownExecutor(); - return imageLocation; - } - -} diff --git a/java-gcpspeechai/src/main/java/oracleai/services/ORDSCalls.java b/java-gcpspeechai/src/main/java/oracleai/services/ORDSCalls.java deleted file mode 100644 index f09ee99..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/services/ORDSCalls.java +++ /dev/null @@ -1,233 +0,0 @@ -package oracleai.services; - -import com.fasterxml.jackson.databind.JsonNode; -import com.fasterxml.jackson.databind.ObjectMapper; -import oracleai.*; -import oracleai.digitaldouble.DigitalDoubleDownloadInfo; -import oracleai.digitaldouble.ImageStore; -import oracleai.digitaldouble.ImageStoreWrapper; -import org.springframework.http.*; -import org.springframework.stereotype.Service; -import org.springframework.web.client.RestTemplate; -import org.springframework.web.multipart.MultipartFile; -import org.springframework.web.util.UriComponentsBuilder; - - -import java.io.IOException; -import java.net.URI; -import java.net.URLEncoder; -import java.util.Base64; -import java.util.Collections; -import java.util.HashMap; -import java.util.Map; - -@Service -public class ORDSCalls { - - public static String callAnalyzeImageInline(String ordsEndpoint, String visionServiceIndpoint, - String compartmentOcid, MultipartFile imageFile) - throws Exception { - RestTemplate restTemplate = new RestTemplate(); - String base64ImageData = Base64.getEncoder().encodeToString(imageFile.getBytes()); - String jsonBody = String.format("{\"p_compartment_ocid\": \"%s\", \"p_endpoint\": \"%s\", \"p_image_data\": \"%s\"}", - compartmentOcid, visionServiceIndpoint, base64ImageData); - HttpHeaders headers = new HttpHeaders(); - headers.setContentType(MediaType.APPLICATION_JSON); - HttpEntity requestEntity = new HttpEntity<>(jsonBody, headers); - ResponseEntity response = restTemplate.exchange(ordsEndpoint, HttpMethod.POST, requestEntity, String.class); - return response.getBody(); - } - - - //As written only supports one feature type per call - public static String analyzeImageInObjectStore( - String ordsEndpoint, String visionServiceEndpoint, String compartmentOcid, - String bucketName, String namespaceName, String objectName, String featureType, String label) { - System.out.println("ORDSCalls.analyzeImageInObjectStore"); - System.out.println("ordsEndpoint = " + ordsEndpoint + ", visionServiceEndpoint = " + visionServiceEndpoint + ", compartmentOcid = " + compartmentOcid + ", bucketName = " + bucketName + ", namespaceName = " + namespaceName + ", objectName = " + objectName + ", featureType = " + featureType + ", label = " + label); - RestTemplate restTemplate = new RestTemplate(); - String jsonPayload = String.format( - "{\"p_bucketname\": \"%s\", \"p_compartment_ocid\": \"%s\", \"p_endpoint\": \"%s\", " + - "\"p_namespacename\": \"%s\", \"p_objectname\": \"%s\", \"p_featuretype\": \"%s\", \"p_label\": \"%s\"}", - bucketName, compartmentOcid, visionServiceEndpoint, namespaceName, objectName, featureType, label); - System.out.println("ORDSCalls.analyzeImageInObjectStore jsonPayload:" + jsonPayload); - HttpHeaders headers = new HttpHeaders(); - headers.setAccept(Collections.singletonList(MediaType.APPLICATION_JSON)); - headers.setContentType(MediaType.APPLICATION_JSON); - HttpEntity entity = new HttpEntity<>(jsonPayload, headers); - ResponseEntity response = restTemplate.exchange(ordsEndpoint, HttpMethod.POST, entity, String.class); - System.out.println("ORDSCalls.analyzeImageInObjectStore response.getBody():" + response.getBody()); - return response.getBody(); - } - - public static String executeTextSearchContains(String ordsEndpoint, String sql) { - String jsonPayload = String.format("{\"p_sql\": \"%s\"}", sql); - return callTextSearch(ordsEndpoint, jsonPayload); - } - - public static String executeTextSearchOR(String ordsEndpoint, String sql, String sql2) { - String jsonPayload = String.format("{\"p_sql\": \"%s\", \"p_sql\": \"%s\"}", sql, sql2); - return callTextSearch(ordsEndpoint, jsonPayload); - } - - private static String callTextSearch(String ordsEndpoint, String jsonPayload) { - HttpHeaders headers = new HttpHeaders(); - headers.setContentType(MediaType.APPLICATION_JSON); - HttpEntity entity = new HttpEntity<>(jsonPayload, headers); - ResponseEntity response = new RestTemplate().exchange(ordsEndpoint, HttpMethod.POST, entity, String.class); - System.out.println("ORDSCalls.analyzeImageInObjectStore response.getBody():" + response.getBody()); - return response.getBody(); - } - - public static ResponseEntity uploadImage(MultipartFile image) { - try { - String base64Image = Base64.getEncoder().encodeToString(image.getBytes()); - Map payload = new HashMap<>(); - payload.put("p_image_name", image.getOriginalFilename()); - payload.put("p_image", base64Image); - HttpHeaders headers = new HttpHeaders(); - headers.setContentType(MediaType.APPLICATION_JSON); - HttpEntity> requestEntity = new HttpEntity<>(payload, headers); - RestTemplate restTemplate = new RestTemplate(); - String uploadUrl = AIApplication.ORDS_ENDPOINT_URL + "insert_image/"; - return restTemplate.exchange(uploadUrl, HttpMethod.POST, requestEntity, String.class); - } catch (Exception e) { - throw new RuntimeException("Failed to upload image", e); - } - } - - - public static ImageStore[] getImageStoreData() { - String url = AIApplication.ORDS_ENDPOINT_URL + "image_store/"; - RestTemplate restTemplate = new RestTemplate(); - ResponseEntity response = restTemplate.getForEntity(url, ImageStoreWrapper.class); - ImageStoreWrapper wrapper = response.getBody(); - if (wrapper != null) { - for (ImageStore imageStore : wrapper.getItems()) { - System.out.println("Image Name: " + imageStore.getImageName()); - } - return wrapper.getItems().toArray(new ImageStore[0]); - } else { - return new ImageStore[0]; - } - } - - public static ImageStore[] make3Drequest() { - String url = AIApplication.ORDS_ENDPOINT_URL + "image_store/"; - RestTemplate restTemplate = new RestTemplate(); - ResponseEntity response = restTemplate.getForEntity(url, ImageStoreWrapper.class); - ImageStoreWrapper wrapper = response.getBody(); - if (wrapper != null) { - for (ImageStore imageStore : wrapper.getItems()) { - System.out.println("Image Name: " + imageStore.getImageName()); - } - return wrapper.getItems().toArray(new ImageStore[0]); - } else { - return new ImageStore[0]; - } - } - - - public static DigitalDoubleDownloadInfo convertImageAndQueueResults( - String imageLocation, String fileName) { - String apiUrl = "https://api.meshy.ai/v1/image-to-3d"; - RestTemplate restTemplate = new RestTemplate(); - HttpHeaders headers = new HttpHeaders(); - headers.setContentType(MediaType.APPLICATION_JSON); - headers.set("Authorization", "Bearer " + AIApplication.THREEDEY); - String requestJson = - "{\"image_url\": \"" + imageLocation + fileName + "\", " + - "\"enable_pbr\": true, \"surface_mode\": \"hard\"}"; - HttpEntity entity = new HttpEntity<>(requestJson, headers); - ResponseEntity response = restTemplate.postForEntity(apiUrl, entity, String.class); - ObjectMapper mapper = new ObjectMapper(); - try { - JsonNode root = mapper.readTree(response.getBody()); - String theResultString = root.path("result").asText(); - return pollApiUntilSuccess(fileName, theResultString); - } catch (IOException e) { - e.printStackTrace(); - return new DigitalDoubleDownloadInfo(); - } - } - - public static DigitalDoubleDownloadInfo pollApiUntilSuccess( - String fileName, String theResultString) { - RestTemplate restTemplate = new RestTemplate(); - HttpHeaders headers = new HttpHeaders(); - headers.set("Authorization", "Bearer " + AIApplication.THREEDEY); - headers.setContentType(MediaType.APPLICATION_JSON); - HttpEntity entity = new HttpEntity<>(headers); - - ObjectMapper mapper = new ObjectMapper(); - while (true) { - try { - ResponseEntity response = - restTemplate.exchange( - "https://api.meshy.ai/v1/image-to-3d/" + theResultString, - HttpMethod.GET, entity, String.class); - JsonNode rootNode = mapper.readTree(response.getBody()); - String status = rootNode.path("status").asText(); - System.out.println(fileName + " status:" + status); - if ("SUCCEEDED".equals(status)) { - String modelUrl = rootNode.path("model_url").asText(); - String modelGlbUrl = rootNode.path("model_urls").path("glb").asText(); - String modelFbxUrl = rootNode.path("model_urls").path("fbx").asText(); - String modelUsdzUrl = rootNode.path("model_urls").path("usdz").asText(); - String thumbnailUrl = rootNode.path("thumbnail_url").asText(); - System.out.println("ORDSCalls.pollApiUntilSuccess modelFbxUrl:" + modelFbxUrl); - return new DigitalDoubleDownloadInfo( - modelUrl, modelGlbUrl, modelFbxUrl, modelUsdzUrl, thumbnailUrl); - } - Thread.sleep(5000); - } catch (Exception e) { - e.printStackTrace(); - } - } - } - - public static void insertDigitalDoubleData(MultipartFile image, MultipartFile video, - String firstName, String lastName, String email, - String company, String jobRole, String tshirtSize, - String comments) throws IOException { - DigitalDoubleORDS client = new DigitalDoubleORDS(); - DigitalDoubleDataRequest request = new DigitalDoubleDataRequest(); - request.p_participant_firstname = firstName; - request.p_participant_lastname = lastName; - request.p_participant_email = email; - request.p_participant_company = company; - request.p_participant_role = jobRole; - request.p_participant_tshirt = tshirtSize; - request.p_participant_comments = comments; -// request.p_id_image_in = idimage; - if (image != null) request.p_image_in = Base64.getEncoder().encodeToString(image.getBytes()); - if (video != null) request.p_video_in = Base64.getEncoder().encodeToString(video.getBytes()); - client.insertDigitalDoubleData(request); - System.out.println("ORDSCalls.insertDigitalDoubleData insert complete"); - } - - - public static String getDigitalDoubleData(String email) throws Exception { - System.out.println("DigitalDoubles.downloaddigitaldouble lookup email:" + email); -// String url = AIApplication.ORDS_OMLOPSENDPOINT_URL + "modelurls/geturls/" + email; - String baseUrl = AIApplication.ORDS_OMLOPSENDPOINT_URL + "/digitaldouble/fbxurl/" ; - URI uri = UriComponentsBuilder.fromHttpUrl(baseUrl) - .pathSegment(URLEncoder.encode(email, "UTF-8")) - .build(true).toUri(); - System.out.println("ORDSCalls.getDigitalDoubleData uri=" + uri); - HttpHeaders headers = new HttpHeaders(); - headers.setContentType(MediaType.APPLICATION_JSON); - HttpEntity entity = new HttpEntity<>(headers); - ResponseEntity response = new RestTemplate().exchange(uri, HttpMethod.GET, entity, String.class); - if (response.getStatusCode().is2xxSuccessful()) { - String modelFbxUrl = response.getBody(); - System.out.println("MODELFBXURL_OUT: " + modelFbxUrl); - return modelFbxUrl; - } else { - System.err.println("Failed to retrieve FBX URL. Status code: " + response.getStatusCode()); - return null; - } - - } -} - diff --git a/java-gcpspeechai/src/main/java/oracleai/services/OracleGenAI.java b/java-gcpspeechai/src/main/java/oracleai/services/OracleGenAI.java deleted file mode 100644 index d7a9cad..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/services/OracleGenAI.java +++ /dev/null @@ -1,214 +0,0 @@ -package oracleai.services; - -import java.util.ArrayList; -import java.util.List; -import java.util.Objects; -import java.util.stream.Collectors; - -import com.oracle.bmc.auth.BasicAuthenticationDetailsProvider; -import com.oracle.bmc.generativeaiinference.GenerativeAiInference; -import com.oracle.bmc.generativeaiinference.GenerativeAiInferenceClient; -import com.oracle.bmc.generativeaiinference.model.*; -import com.oracle.bmc.generativeaiinference.requests.ChatRequest; -import com.oracle.bmc.generativeaiinference.responses.ChatResponse; -import lombok.Builder; -import lombok.Getter; -import oracleai.AIApplication; - -/** - * OCI GenAI Chat - */ -public class OracleGenAI { - private final GenerativeAiInference client; - private final ServingMode servingMode; - private final String compartment; - private final String preambleOverride; - private final Double temperature; - private final Double frequencyPenalty; - private final Integer maxTokens; - private final Double presencePenalty; - private final Double topP; - private final Integer topK; - private final InferenceRequestType inferenceRequestType; - private List cohereChatMessages; - private List genericChatMessages; - - @Builder - public OracleGenAI(BasicAuthenticationDetailsProvider authProvider, - ServingMode servingMode, - String compartment, - String preambleOverride, - Double temperature, - Double frequencyPenalty, - Integer maxTokens, - Double presencePenalty, - Double topP, - Integer topK, - InferenceRequestType inferenceRequestType) throws Exception { - - - - this.client = GenerativeAiInferenceClient.builder() - .build(AuthProvider.getAuthenticationDetailsProvider()); - this.servingMode = servingMode; - this.compartment = compartment; - this.preambleOverride = preambleOverride; - - this.temperature = Objects.requireNonNullElse(temperature, 1.0); - this.frequencyPenalty = Objects.requireNonNullElse( - frequencyPenalty, - 0.0 - ); - this.maxTokens = Objects.requireNonNullElse(maxTokens, 600); - this.presencePenalty = Objects.requireNonNullElse( - presencePenalty, - 0.0 - ); - this.topP = Objects.requireNonNullElse(topP, 0.75); - this.inferenceRequestType = Objects.requireNonNullElse( - inferenceRequestType, - InferenceRequestType.COHERE - ); - this.topK = Objects.requireNonNullElseGet(topK, () -> { - if (this.inferenceRequestType == InferenceRequestType.COHERE) { - return 0; - } - return -1; - }); - } - - @Getter - public enum InferenceRequestType { - COHERE("COHERE"), - LLAMA("LLAMA"); - - private final String type; - - InferenceRequestType(String type) { - this.type = type; - } - } - - /** - * Chat using OCI GenAI. - * @param prompt Prompt text sent to OCI GenAI chat model. - * @return OCI GenAI ChatResponse - */ - public String chat1(String prompt) { - return "whateve"; - } - - public String chat(String prompt) { - ChatDetails chatDetails = ChatDetails.builder() -// .compartmentId(AIApplication.COMPARTMENT_ID) - .compartmentId(compartment) -// .servingMode(OnDemandServingMode.builder().build()) - .servingMode(servingMode) - .chatRequest(createChatRequest(prompt)) - .build(); - ChatRequest chatRequest = ChatRequest.builder() - .body$(chatDetails) - .build(); - ChatResponse response = client.chat(chatRequest); - saveChatHistory(response); - return extractText(response); - } - - /** - * Create a ChatRequest from a text prompt. Supports COHERE or LLAMA inference. - * @param prompt To create a ChatRequest from. - * @return A COHERE or LLAMA ChatRequest. - */ - private BaseChatRequest createChatRequest(String prompt) { - switch (inferenceRequestType) { - case COHERE: - return CohereChatRequest.builder() - .frequencyPenalty(frequencyPenalty) - .maxTokens(maxTokens) - .presencePenalty(presencePenalty) - .message(prompt) - .temperature(temperature) - .topP(topP) - .topK(topK) - .chatHistory(cohereChatMessages) - .preambleOverride(preambleOverride) - .build(); - case LLAMA: - List messages = genericChatMessages == null ? - new ArrayList<>() : - genericChatMessages.stream() - .map(ChatChoice::getMessage) - .collect(Collectors.toList()); - ChatContent content = TextContent.builder() - .text(prompt) - .build(); - List contents = new ArrayList<>(); - contents.add(content); - UserMessage message = UserMessage.builder() - .name("USER") - .content(contents) - .build(); - messages.add(message); - return GenericChatRequest.builder() - .messages(messages) - .frequencyPenalty(frequencyPenalty) - .temperature(temperature) - .maxTokens(maxTokens) - .presencePenalty(presencePenalty) - .topP(topP) - .topK(topK) - .build(); - } - - throw new IllegalArgumentException(String.format( - "Unknown request type %s", - inferenceRequestType - )); - } - - /** - * Save the current chat history to memory. - * @param chatResponse The latest chat response. - */ - private void saveChatHistory(ChatResponse chatResponse) { - BaseChatResponse bcr = chatResponse.getChatResult() - .getChatResponse(); - if (bcr instanceof CohereChatResponse resp) { - cohereChatMessages = resp.getChatHistory(); - } else if (bcr instanceof GenericChatResponse resp) { - genericChatMessages = resp.getChoices(); - } else { - throw new IllegalStateException(String.format( - "Unexpected chat response type: %s", - bcr.getClass().getName() - )); - } - } - - /** - * Extract text from an OCI GenAI ChatResponse. - * @param chatResponse The response to extract text from. - * @return The chat response text. - */ - private String extractText(ChatResponse chatResponse) { - BaseChatResponse bcr = chatResponse - .getChatResult() - .getChatResponse(); - if (bcr instanceof CohereChatResponse resp) { - return resp.getText(); - } else if (bcr instanceof GenericChatResponse resp) { - List choices = resp.getChoices(); - List contents = choices.get(choices.size() - 1) - .getMessage() - .getContent(); - ChatContent content = contents.get(contents.size() - 1); - if (content instanceof TextContent) { - return ((TextContent) content).getText(); - } - } - throw new IllegalStateException(String.format( - "Unexpected chat response type: %s", - bcr.getClass().getName() - )); - } -} \ No newline at end of file diff --git a/java-gcpspeechai/src/main/java/oracleai/services/OracleLanguageAI.java b/java-gcpspeechai/src/main/java/oracleai/services/OracleLanguageAI.java deleted file mode 100644 index f56d0e2..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/services/OracleLanguageAI.java +++ /dev/null @@ -1,43 +0,0 @@ -package oracleai.services; - -import com.oracle.bmc.ailanguage.AIServiceLanguageClient; -import com.oracle.bmc.ailanguage.model.DetectLanguageSentimentsDetails; -import com.oracle.bmc.ailanguage.model.DetectLanguageSentimentsResult; -import com.oracle.bmc.ailanguage.model.SentimentAspect; -import com.oracle.bmc.ailanguage.requests.DetectLanguageSentimentsRequest; -import com.oracle.bmc.ailanguage.responses.DetectLanguageSentimentsResponse; -import com.oracle.bmc.model.BmcException; - -import java.io.IOException; - -public class OracleLanguageAI { - - - public static String sentimentAnalysis(String textcontent) throws IOException { - System.out.println("OracleLanguageAI.sentiments analyze text for sentiment:" + textcontent); - AIServiceLanguageClient languageClient = - AIServiceLanguageClient.builder().build(AuthProvider.getAuthenticationDetailsProvider()); - DetectLanguageSentimentsDetails details = - DetectLanguageSentimentsDetails.builder() - .text(textcontent) - .build(); - DetectLanguageSentimentsRequest detectLanguageSentimentsRequest = - DetectLanguageSentimentsRequest.builder() - .detectLanguageSentimentsDetails(details) - .build(); - DetectLanguageSentimentsResponse response = null; - try { - response = languageClient.detectLanguageSentiments(detectLanguageSentimentsRequest); - } catch (BmcException e) { - System.err.println("Failed to detect language and sentiments: " + e.getMessage()); - } - DetectLanguageSentimentsResult detectLanguageSentimentsResult = response.getDetectLanguageSentimentsResult(); - String sentimentReturn = ""; - for (SentimentAspect aspect : detectLanguageSentimentsResult.getAspects()) { - sentimentReturn += " sentiment:" + aspect.getSentiment(); - sentimentReturn += " text:" + aspect.getText(); - sentimentReturn += ", "; - } - return sentimentReturn; - } -} diff --git a/java-gcpspeechai/src/main/java/oracleai/services/OracleObjectStore.java b/java-gcpspeechai/src/main/java/oracleai/services/OracleObjectStore.java deleted file mode 100644 index 56049e7..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/services/OracleObjectStore.java +++ /dev/null @@ -1,54 +0,0 @@ -package oracleai.services; - -import com.oracle.bmc.auth.BasicAuthenticationDetailsProvider; -import com.oracle.bmc.objectstorage.ObjectStorageClient; -import com.oracle.bmc.objectstorage.requests.GetObjectRequest; -import com.oracle.bmc.objectstorage.requests.PutObjectRequest; -import com.oracle.bmc.objectstorage.responses.GetObjectResponse; -import com.oracle.bmc.objectstorage.responses.PutObjectResponse; -import oracleai.AIApplication; - -import java.io.BufferedReader; -import java.io.IOException; -import java.io.InputStream; -import java.io.InputStreamReader; -import java.nio.charset.StandardCharsets; - -public class OracleObjectStore { - - - public static void sendToObjectStorage(String fileName, InputStream inputStreamForFile) throws IOException { - System.out.println("sendToObjectStorage fileToUpload:" + fileName); - BasicAuthenticationDetailsProvider provider = AuthProvider.getAuthenticationDetailsProvider(); - ObjectStorageClient client = ObjectStorageClient.builder().build(provider); - PutObjectRequest putObjectRequest = PutObjectRequest.builder() - .namespaceName(AIApplication.OBJECTSTORAGE_NAMESPACE) - .bucketName(AIApplication.OBJECTSTORAGE_BUCKETNAME) - .objectName(fileName) - .putObjectBody(inputStreamForFile) //InputStream - .build(); - PutObjectResponse response = client.putObject(putObjectRequest); - System.out.println("File uploaded successfully. Object Storage Location: " + fileName); - } - - public static String getFromObjectStorage(String transcriptionJobId, String objectName) throws Exception { - System.out.println("GenerateAPictureStoryUsingOnlySpeech.getFromObjectStorage objectName:" + objectName); - BasicAuthenticationDetailsProvider provider = AuthProvider.getAuthenticationDetailsProvider(); - ObjectStorageClient client = ObjectStorageClient.builder().build(provider); - GetObjectRequest putObjectRequest = GetObjectRequest.builder() - .namespaceName(AIApplication.OBJECTSTORAGE_NAMESPACE) - .bucketName(AIApplication.OBJECTSTORAGE_BUCKETNAME) - .objectName(transcriptionJobId + "/" + objectName) - .build(); - GetObjectResponse response = client.getObject(putObjectRequest); - String responseString = ""; - try (InputStream inputStream = response.getInputStream(); - BufferedReader reader = new BufferedReader(new InputStreamReader(inputStream, StandardCharsets.UTF_8))) { - String line; - while ((line = reader.readLine()) != null) { - responseString += line; - } - } - return responseString; - } -} diff --git a/java-gcpspeechai/src/main/java/oracleai/services/OracleSpeechAI.java b/java-gcpspeechai/src/main/java/oracleai/services/OracleSpeechAI.java deleted file mode 100644 index 0243b68..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/services/OracleSpeechAI.java +++ /dev/null @@ -1,125 +0,0 @@ -package oracleai.services; - -import com.fasterxml.jackson.annotation.JsonIgnoreProperties; -import com.oracle.bmc.aispeech.AIServiceSpeechClient; -import com.oracle.bmc.aispeech.model.*; -import com.oracle.bmc.aispeech.requests.CreateTranscriptionJobRequest; -import com.oracle.bmc.aispeech.requests.GetTranscriptionJobRequest; -import com.oracle.bmc.aispeech.responses.CreateTranscriptionJobResponse; -import com.oracle.bmc.aispeech.responses.GetTranscriptionJobResponse; -import com.oracle.bmc.auth.BasicAuthenticationDetailsProvider; -import lombok.Getter; -import lombok.Setter; -import oracleai.AIApplication; - -import java.io.IOException; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; - -public class OracleSpeechAI { - - public static String getTranscriptFromOCISpeech(String fileName) throws IOException, InterruptedException { - BasicAuthenticationDetailsProvider provider = AuthProvider.getAuthenticationDetailsProvider(); - AIServiceSpeechClient client = - AIServiceSpeechClient.builder().build(provider); - CreateTranscriptionJobDetails createTranscriptionJobDetails = CreateTranscriptionJobDetails.builder() - // .displayName("EXAMPLE-displayName-Value") - .compartmentId(AIApplication.COMPARTMENT_ID) - // .description("EXAMPLE-description-Value") - .additionalTranscriptionFormats(new ArrayList<>(Arrays.asList(CreateTranscriptionJobDetails.AdditionalTranscriptionFormats.Srt))) - .modelDetails(TranscriptionModelDetails.builder() - .domain(TranscriptionModelDetails.Domain.Generic) - .languageCode(TranscriptionModelDetails.LanguageCode.EnUs) - .transcriptionSettings(TranscriptionSettings.builder() - .diarization(Diarization.builder() - .isDiarizationEnabled(false) - .numberOfSpeakers(7).build()).build()).build()) - .normalization(TranscriptionNormalization.builder() - .isPunctuationEnabled(true) - .filters(new ArrayList<>(Arrays.asList(ProfanityTranscriptionFilter.builder() - .mode(ProfanityTranscriptionFilter.Mode.Mask).build()))).build()) - .inputLocation(ObjectListInlineInputLocation.builder() - .objectLocations(new ArrayList<>(Arrays.asList(ObjectLocation.builder() - .namespaceName(AIApplication.OBJECTSTORAGE_NAMESPACE) - .bucketName(AIApplication.OBJECTSTORAGE_BUCKETNAME) - .objectNames(new ArrayList<>(Arrays.asList(fileName))).build()))).build()) - .outputLocation(OutputLocation.builder() - .namespaceName(AIApplication.OBJECTSTORAGE_NAMESPACE) - .bucketName(AIApplication.OBJECTSTORAGE_BUCKETNAME) -// .prefix("EXAMPLE-prefix-Value1") - .build()) -// .freeformTags(new HashMap() { -// { -// put("EXAMPLE_KEY_yRf3m","EXAMPLE_VALUE_8Huo8VgOyTwUIGjFP4Xr"); -// } -// }) -// .definedTags(new HashMap>() { -// { -// put("EXAMPLE_KEY_9ftH6",new HashMap() { -// { -// put("EXAMPLE_KEY_TYlyl","EXAMPLE--Value"); -// } -// }); -// } -// }) - .build(); - - CreateTranscriptionJobRequest createTranscriptionJobRequest = CreateTranscriptionJobRequest.builder() - .createTranscriptionJobDetails(createTranscriptionJobDetails) - .build(); - CreateTranscriptionJobResponse response = client.createTranscriptionJob(createTranscriptionJobRequest); - GetTranscriptionJobRequest getTranscriptionJobRequest = GetTranscriptionJobRequest.builder() - .transcriptionJobId(response.getTranscriptionJob().getId()) - .build(); - GetTranscriptionJobResponse getTranscriptionJobResponseresponse = null; - TranscriptionJob.LifecycleState transcriptJobState = null; - TranscriptionJob.LifecycleState lastState; - while ( - transcriptJobState == null || - ( - !transcriptJobState.equals(TranscriptionJob.LifecycleState.Succeeded) && - !transcriptJobState.equals(TranscriptionJob.LifecycleState.Canceling) && - !transcriptJobState.equals(TranscriptionJob.LifecycleState.Canceled) && - !transcriptJobState.equals(TranscriptionJob.LifecycleState.Failed)) - ) { - Thread.currentThread().sleep(1000); - lastState = transcriptJobState; - getTranscriptionJobResponseresponse = - client.getTranscriptionJob(getTranscriptionJobRequest); - transcriptJobState = getTranscriptionJobResponseresponse.getTranscriptionJob().getLifecycleState(); - if (lastState != null && lastState.equals(transcriptJobState)) System.out.print("."); - else System.out.println("transcriptJobState:" + transcriptJobState); - } - System.out.println("getInputLocation:" + - getTranscriptionJobResponseresponse.getTranscriptionJob().getInputLocation()); - String fullString = getTranscriptionJobResponseresponse.getTranscriptionJob().getId(); - int lastIndex = fullString.lastIndexOf("."); - String extractedString = ""; - if (lastIndex != -1) extractedString = fullString.substring(lastIndex + 1); - return "job-" + extractedString; - } - - @JsonIgnoreProperties(ignoreUnknown = true) - @Getter - @Setter - public static class TranscriptionResponse { - private List transcriptions; - - @JsonIgnoreProperties(ignoreUnknown = true) - @Getter - @Setter - public static class Transcription { - private List tokens; - - @JsonIgnoreProperties(ignoreUnknown = true) - @Getter - @Setter - public static class Token { - private String token; - } - } - } - - -} diff --git a/java-gcpspeechai/src/main/java/oracleai/services/OracleVisionAI.java b/java-gcpspeechai/src/main/java/oracleai/services/OracleVisionAI.java deleted file mode 100644 index 3146b6d..0000000 --- a/java-gcpspeechai/src/main/java/oracleai/services/OracleVisionAI.java +++ /dev/null @@ -1,121 +0,0 @@ -package oracleai.services; - -import com.fasterxml.jackson.annotation.JsonIgnoreProperties; -import com.fasterxml.jackson.databind.ObjectMapper; -import com.fasterxml.jackson.databind.ser.impl.SimpleFilterProvider; -import com.oracle.bmc.aivision.AIServiceVisionClient; -import com.oracle.bmc.aivision.model.*; -import com.oracle.bmc.aivision.requests.AnalyzeImageRequest; -import com.oracle.bmc.aivision.responses.AnalyzeImageResponse; -import com.oracle.bmc.auth.BasicAuthenticationDetailsProvider; -import lombok.Getter; -import lombok.Setter; - -import java.util.ArrayList; -import java.util.List; - -public class OracleVisionAI { - - /** - * As written only supports on feature type per call. Examples include... - ImageFeature faceDetectionFeature = FaceDetectionFeature.builder() - .maxResults(10) - .build(); - ImageFeature classifyFeature = ImageClassificationFeature.builder() - .maxResults(10) - .build(); - ImageFeature detectImageFeature = ImageObjectDetectionFeature.builder() - .maxResults(10) - .build(); - * - */ - public static String processImage(byte[] bytes, ImageFeature feature) throws Exception { - BasicAuthenticationDetailsProvider provider = AuthProvider.getAuthenticationDetailsProvider(); - AIServiceVisionClient aiServiceVisionClient = AIServiceVisionClient.builder().build(provider); - List features = new ArrayList<>(); - features.add(feature); - InlineImageDetails inlineImageDetails = InlineImageDetails.builder() - .data(bytes) - .build(); - AnalyzeImageDetails analyzeImageDetails = AnalyzeImageDetails.builder() - .image(inlineImageDetails) - .features(features) - .build(); - AnalyzeImageRequest request = AnalyzeImageRequest.builder() - .analyzeImageDetails(analyzeImageDetails) - .build(); - AnalyzeImageResponse response = aiServiceVisionClient.analyzeImage(request); - ObjectMapper mapper = new ObjectMapper(); - mapper.setFilterProvider(new SimpleFilterProvider().setFailOnUnknownId(false)); - String json = mapper.writeValueAsString(response.getAnalyzeImageResult()); - return json; - } - - - //For Text Detection.... - @JsonIgnoreProperties(ignoreUnknown = true) - @Getter - @Setter - public static class ImageData { - private ImageText imageText; - } - - @JsonIgnoreProperties(ignoreUnknown = true) - @Getter - @Setter - public static class ImageText { - private List words; - } - - @JsonIgnoreProperties(ignoreUnknown = true) - @Getter - @Setter - public static class Word { - private String text; - } - - - //For Image Detection... - - @JsonIgnoreProperties(ignoreUnknown = true) - @Getter - @Setter - public static class ImageAnalysisResult { - private List imageObjects; - private List ontologyClasses; - } - - @JsonIgnoreProperties(ignoreUnknown = true) - @Getter - @Setter - public static class ImageObject { - private String name; - private Double confidence; - private BoundingPolygon boundingPolygon; - } - - @JsonIgnoreProperties(ignoreUnknown = true) - @Getter - @Setter - public static class BoundingPolygon { - private List normalizedVertices; - } - - @JsonIgnoreProperties(ignoreUnknown = true) - @Getter - @Setter - public static class Vertex { - private Double x; - private Double y; - } - - @JsonIgnoreProperties(ignoreUnknown = true) - @Getter - @Setter - public static class OntologyClass { - private String name; - private List parentNames; - private List synonymNames; - } - -} diff --git a/java-gcpspeechai/src/main/resources/application.yaml b/java-gcpspeechai/src/main/resources/application.yaml deleted file mode 100644 index f0e4baf..0000000 --- a/java-gcpspeechai/src/main/resources/application.yaml +++ /dev/null @@ -1,31 +0,0 @@ -spring: - servlet: - multipart: - enabled: true - max-file-size: 200MB - max-request-size: 200MB - cloud: - oci: - config: - type: INSTANCE_PRINCIPAL - datasource: - # Example where a wallet is used (TNS_ADMIN is the location of the wallet). - # Eg if using Oracle Cloud ADB (autonomous database) Always Free. - # url: "jdbc:oracle:thin:@xr_tp?TNS_ADMIN=/Users/me/Wallet_mydb" - # Example without wallet. Eg if using Oracle 23c Free. - # url: "jdbc:oracle:thin:@localhost:1521/freepdb1" - url: jdbc:oracle:thin:@mydb_tp?TNS_ADMIN=/Users/me/Wallet_mydb - # Use "admin" for username for setup with Oracle Cloud ADB - # and use "sys as sysdba" for username for setup with Oracle 23c Free - username: testuser - password: testpassword - driver-class-name: oracle.jdbc.OracleDriver - type: oracle.ucp.jdbc.PoolDataSource - oracleucp: - connection-factory-class-name: oracle.jdbc.pool.OracleDataSource -logging: - level: - org.springframework.web.cors: DEBUG -server: - tomcat: - max-swallow-size: 200MB \ No newline at end of file diff --git a/java-gcpspeechai/src/main/resources/static/DDAdminUpload.html b/java-gcpspeechai/src/main/resources/static/DDAdminUpload.html deleted file mode 100644 index ebd636d..0000000 --- a/java-gcpspeechai/src/main/resources/static/DDAdminUpload.html +++ /dev/null @@ -1,169 +0,0 @@ - - - - - - Player Form - - - -
-

Please provide image and/or video and some basic info...

-
- - - - - - - - -
-
- - -
-
- - -
-
- -
- - -
-
- - -
-
- - -
-
- - -
-
- - -
-
- - -
-
- - -
-
- -
-
-
- - \ No newline at end of file diff --git a/java-gcpspeechai/src/main/resources/static/DownloadImages.html b/java-gcpspeechai/src/main/resources/static/DownloadImages.html deleted file mode 100644 index b9c5a58..0000000 --- a/java-gcpspeechai/src/main/resources/static/DownloadImages.html +++ /dev/null @@ -1,13 +0,0 @@ - - - - - Upload Image - - -

Download Images

-
- -
- - \ No newline at end of file diff --git a/java-gcpspeechai/src/main/resources/static/FaceRecognition.html b/java-gcpspeechai/src/main/resources/static/FaceRecognition.html deleted file mode 100644 index 11bc5fd..0000000 --- a/java-gcpspeechai/src/main/resources/static/FaceRecognition.html +++ /dev/null @@ -1,46 +0,0 @@ - - -Oracle AI - - - - - - -
-

Menu

-
-
-
- -
-

Develop with Oracle AI Services and Oracle Database

-
- -
- -

Obtain facial recognition information

-
-
Provide a picture containing faces and receive a return of the faces recognized and location of various facial features.
-
Uses Oracle Vision AI
-
-
- Select an image file to conduct face recognition upon...
- -
You can use the sample image found here -
-
-

-
-
- -
- - - diff --git a/java-gcpspeechai/src/main/resources/static/ObjectDetectionGenAIAndSentimentAnalysis.html b/java-gcpspeechai/src/main/resources/static/ObjectDetectionGenAIAndSentimentAnalysis.html deleted file mode 100644 index 54a7a9c..0000000 --- a/java-gcpspeechai/src/main/resources/static/ObjectDetectionGenAIAndSentimentAnalysis.html +++ /dev/null @@ -1,59 +0,0 @@ - - -Oracle AI - - - - - - -
-

Menu

-
-
-
- -
-

Develop with Oracle AI Services and Oracle Database

-
- -
- -

Generate a story with sentiment analysis from a picture

-
-
Provide a picture and receive a generated story with sentiment analysis based on the picture<.
-
Uses Oracle Vision AI, Oracle Gen AI, and Oracle Language AI
-
- -
- Select an image file to create story from... - -
You can download and use the sample image found here -
-
Options for story generation... -
an adventure -
romantic -
a dystopia -
a documentary -
an anime -

Options... -
Process image inline (do not store image or results) -
(makes calls to Vision AI and Gen AI directly from this application) -
-
Store image in objectstore and summary text results in database -
(makes calls to Vision AI and Gen AI from the Oracle Database using DBMS_CLOUD) -

-
-
-
- -
- - - diff --git a/java-gcpspeechai/src/main/resources/static/SpeechTranscriptionAndImageGeneration.html b/java-gcpspeechai/src/main/resources/static/SpeechTranscriptionAndImageGeneration.html deleted file mode 100644 index f00ada8..0000000 --- a/java-gcpspeechai/src/main/resources/static/SpeechTranscriptionAndImageGeneration.html +++ /dev/null @@ -1,62 +0,0 @@ - - -Oracle AI - - - - - - -
- Home
-
-
-
- -
-

Develop with Oracle AI Services and Oracle Database

-
- -
- -

Generate a picture story board from voice recordings

-
-
Provide the audio file of a verbal description of a scene.
-
Uses Oracle Speech AI and Image Generation AI (eg DALL-E, Stable Diffusion, DeepFloyd IF, ...)
-
- -
- Audio Recording Options... -
Audio from file (select this to use audio file) -
-
You can download and use the sample audio here: -
shipwrecked -
paradise -
invaded -
-
Audio from live recording (select this to record 8 seconds of audio from mic - process must be running on local machine) -

Image Options... -
photo taken on a Pentax k1000 -
pixel art -
digital art -
3d render -

- - -
-

-
- -
-
- -
- - - diff --git a/java-gcpspeechai/src/main/resources/static/TextDetectionAndSummarization.html b/java-gcpspeechai/src/main/resources/static/TextDetectionAndSummarization.html deleted file mode 100644 index 355ed8f..0000000 --- a/java-gcpspeechai/src/main/resources/static/TextDetectionAndSummarization.html +++ /dev/null @@ -1,52 +0,0 @@ - - -Oracle AI - - - - - - -
- Home
-
-
-
- -
-

Develop with Oracle AI Services and Oracle Database

-
- -
-

Text Detection And Summarization Generation

-
-
Provide an image of a health report and receive an explanation in simplified terms along with advice.
-
Uses Oracle Vision AI Document/Text Detection and Oracle Gen AI Services
-
-
- Select an image file...
- -
You can download and use the sample audio found here -
-
-
Options... -
Process image inline (do not store image or results) -
(makes calls to Vision AI and Gen AI directly from this application) -
-
Store image in objectstore and summary text results in database -
(makes calls to Vision AI and Gen AI from the Oracle Database using DBMS_CLOUD) -
-

-
-
- -
- - - diff --git a/java-gcpspeechai/src/main/resources/static/TextSearch.html b/java-gcpspeechai/src/main/resources/static/TextSearch.html deleted file mode 100644 index 9076faa..0000000 --- a/java-gcpspeechai/src/main/resources/static/TextSearch.html +++ /dev/null @@ -1,48 +0,0 @@ - - -Oracle AI - - - - - - -
- Home
-
-
-
- -
-

Develop with Oracle AI Services and Oracle Database

-
- -
-

Oracle Database Text Search

-
-
Search Tables Storing Results of AI Operations.
-
Uses Oracle Text Indexing Searches (and in 23c DBMS_SEARCH multi-table search)
-
-
- Enter SQL for text search... -
    select textfromai from aivision_results where CONTAINS ( textfromai, '' ) > 0 -

-
Example values... -
AND/phrase search: 'Wine Glass' -
OR search: 'Wine' OR 'Fork' -
Wildcards: 'Win%' -
Fuzzy: fuzzy('Winz') - -
-
- -
- - - diff --git a/java-gcpspeechai/src/main/resources/static/UploadForDigitalDoubles.html b/java-gcpspeechai/src/main/resources/static/UploadForDigitalDoubles.html deleted file mode 100644 index 843ff17..0000000 --- a/java-gcpspeechai/src/main/resources/static/UploadForDigitalDoubles.html +++ /dev/null @@ -1,61 +0,0 @@ - - - - - - Player Selection - - - -
-

Which are you doing?...

-
-
- - -
-
-
- - - diff --git a/java-gcpspeechai/src/main/resources/static/UploadImage.html b/java-gcpspeechai/src/main/resources/static/UploadImage.html deleted file mode 100644 index f031f1c..0000000 --- a/java-gcpspeechai/src/main/resources/static/UploadImage.html +++ /dev/null @@ -1,15 +0,0 @@ - - - - - Upload Image - - -

Upload Image

-
- - - -
- - \ No newline at end of file diff --git a/java-gcpspeechai/src/main/resources/static/VideoAnalysis.html b/java-gcpspeechai/src/main/resources/static/VideoAnalysis.html deleted file mode 100644 index 91ca109..0000000 --- a/java-gcpspeechai/src/main/resources/static/VideoAnalysis.html +++ /dev/null @@ -1,53 +0,0 @@ - - -Oracle AI - - - - - - -
- Home
-
-
-
- -
-

Develop with Oracle AI Services and Oracle Database

-
- -
- -

Obtain information from video

-
-
Provide a video and receive information about it.
-
Uses Oracle Vision AI
-
-
- Select an image file...
- -
You can download and use the sample audio found here -
-
-
Options... -
Process video inline (do not store video or results) -
(makes calls to Vision AI directly from this application) -
-
Store video in objectstore and text results in database -
(makes calls to Vision AI from the Oracle Database using DBMS_CLOUD) -
-

-
-
- -
- - - diff --git a/java-gcpspeechai/src/main/resources/static/audio/invaded.m4a b/java-gcpspeechai/src/main/resources/static/audio/invaded.m4a deleted file mode 100644 index 3fcc58a..0000000 Binary files a/java-gcpspeechai/src/main/resources/static/audio/invaded.m4a and /dev/null differ diff --git a/java-gcpspeechai/src/main/resources/static/audio/paradise.m4a b/java-gcpspeechai/src/main/resources/static/audio/paradise.m4a deleted file mode 100644 index b6247ba..0000000 Binary files a/java-gcpspeechai/src/main/resources/static/audio/paradise.m4a and /dev/null differ diff --git a/java-gcpspeechai/src/main/resources/static/audio/shipwrecked.m4a b/java-gcpspeechai/src/main/resources/static/audio/shipwrecked.m4a deleted file mode 100644 index 995e1ea..0000000 Binary files a/java-gcpspeechai/src/main/resources/static/audio/shipwrecked.m4a and /dev/null differ diff --git a/java-gcpspeechai/src/main/resources/static/digitaldouble_QRCode.png b/java-gcpspeechai/src/main/resources/static/digitaldouble_QRCode.png deleted file mode 100644 index bd2e8eb..0000000 Binary files a/java-gcpspeechai/src/main/resources/static/digitaldouble_QRCode.png and /dev/null differ diff --git a/java-gcpspeechai/src/main/resources/static/images/bloodsugarreport.jpeg b/java-gcpspeechai/src/main/resources/static/images/bloodsugarreport.jpeg deleted file mode 100644 index e9ef26b..0000000 Binary files a/java-gcpspeechai/src/main/resources/static/images/bloodsugarreport.jpeg and /dev/null differ diff --git a/java-gcpspeechai/src/main/resources/static/images/faces.png b/java-gcpspeechai/src/main/resources/static/images/faces.png deleted file mode 100644 index 229d441..0000000 Binary files a/java-gcpspeechai/src/main/resources/static/images/faces.png and /dev/null differ diff --git a/java-gcpspeechai/src/main/resources/static/images/objectdetectiontestimage.jpg b/java-gcpspeechai/src/main/resources/static/images/objectdetectiontestimage.jpg deleted file mode 100644 index 225cbfc..0000000 Binary files a/java-gcpspeechai/src/main/resources/static/images/objectdetectiontestimage.jpg and /dev/null differ diff --git a/java-gcpspeechai/src/main/resources/static/index.html b/java-gcpspeechai/src/main/resources/static/index.html deleted file mode 100644 index 5b2049a..0000000 --- a/java-gcpspeechai/src/main/resources/static/index.html +++ /dev/null @@ -1,39 +0,0 @@ - - - -Oracle AI - - - - - - -
-

Labs

-
-
-
- -
-

Develop with Oracle AI Services and Oracle Database

-
- -
-
-
- -
- - - diff --git a/java-gcpspeechai/src/main/resources/static/sidebar.html b/java-gcpspeechai/src/main/resources/static/sidebar.html deleted file mode 100644 index 5383890..0000000 --- a/java-gcpspeechai/src/main/resources/static/sidebar.html +++ /dev/null @@ -1,11 +0,0 @@ -Text Detection And Summarization Generation
-Speech Transcription And Image Generation
-Object Detection, Text Generation, and Sentiment Analysis
-Face Recognition
-Database Text Search and DBMS_SEARCH
-Upload Image
-Download Images
-Video Analysis (coming soon)
-Speech Transcription And Translation (coming soon)
-Realtime Speech Transcription (coming soon)
-Speech To Text (coming soon)
\ No newline at end of file diff --git a/java-gcpspeechai/src/main/resources/templates/digitaldoubledownload.html b/java-gcpspeechai/src/main/resources/templates/digitaldoubledownload.html deleted file mode 100644 index fd45d2f..0000000 --- a/java-gcpspeechai/src/main/resources/templates/digitaldoubledownload.html +++ /dev/null @@ -1,82 +0,0 @@ - - - - - - Player Form - - - -
-

Please enter your email to retrieve links to your digital doubles

-
- -
- - -
-
- -
-
-
- - \ No newline at end of file diff --git a/java-gcpspeechai/src/main/resources/templates/digitaldoubleresults.html b/java-gcpspeechai/src/main/resources/templates/digitaldoubleresults.html deleted file mode 100644 index 48c50ba..0000000 --- a/java-gcpspeechai/src/main/resources/templates/digitaldoubleresults.html +++ /dev/null @@ -1,90 +0,0 @@ - - - - - - Player Form - - - -
-

Your Digital Doubles For Download......

-

*Note that links will not be active until assets are ready for download.

-

*Updates on status will be emailed nightly.

-

*Animations are MP4 format and 3D models are FBX format which can be opened in some browsers, free online sites, and 3d software.

- - - -
- - \ No newline at end of file diff --git a/java-gcpspeechai/src/main/resources/templates/digitaldoubleupload.html b/java-gcpspeechai/src/main/resources/templates/digitaldoubleupload.html deleted file mode 100644 index 3f8e588..0000000 --- a/java-gcpspeechai/src/main/resources/templates/digitaldoubleupload.html +++ /dev/null @@ -1,150 +0,0 @@ - - - - - - Player Form - - - -
-

Please provide image and/or video and some basic info...

-
- - - - - - - - -
-
- - -
-
- - -
-
- -
- - -
-
- - -
-
- - -
-
- - -
-
- - -
-
- - -
-
- - -
-
- - -
-
-
- - \ No newline at end of file diff --git a/java-gcpspeechai/src/main/resources/templates/images.html b/java-gcpspeechai/src/main/resources/templates/images.html deleted file mode 100644 index 6f3f33a..0000000 --- a/java-gcpspeechai/src/main/resources/templates/images.html +++ /dev/null @@ -1,43 +0,0 @@ - - - - - Oracle AI - - - - - - -
-

Labs

-
-
-
- -
-

Develop with Oracle AI Services and Oracle Database

-
- -
-
    -
  • -

    Image Name

    - Image -
  • -
-
-
- - - - - - - diff --git a/java-gcpspeechai/src/main/resources/templates/resultspage.html b/java-gcpspeechai/src/main/resources/templates/resultspage.html deleted file mode 100644 index 02e1826..0000000 --- a/java-gcpspeechai/src/main/resources/templates/resultspage.html +++ /dev/null @@ -1,35 +0,0 @@ - - - - - Oracle AI - - - - - - -
-

Labs

-
-
-
- -
-

Develop with Oracle AI Services and Oracle Database

-
- -
- -
- -
- - - diff --git a/java-gcpspeechai/src/main/resources/templates/resultswithimages.html b/java-gcpspeechai/src/main/resources/templates/resultswithimages.html deleted file mode 100644 index af580d1..0000000 --- a/java-gcpspeechai/src/main/resources/templates/resultswithimages.html +++ /dev/null @@ -1,38 +0,0 @@ - - - - - Oracle AI - - - - - - -
-

Labs

-
-
-
- -
-

Develop with Oracle AI Services and Oracle Database

-
-
Click here to add more pictures. -
-
- - image generated from audio transcript and Gen AI - -
- -
- - - diff --git a/java-gcpspeechai/src/main/resources/templates/resultswithlinkpage.html b/java-gcpspeechai/src/main/resources/templates/resultswithlinkpage.html deleted file mode 100644 index c2d5b69..0000000 --- a/java-gcpspeechai/src/main/resources/templates/resultswithlinkpage.html +++ /dev/null @@ -1,35 +0,0 @@ - - - - - Oracle AI - - - - - - -
-

Labs

-
-
-
- -
-

Develop with Oracle AI Services and Oracle Database

-
- - - -
- - - diff --git a/java-gcpspeechai/src/main/resources/templates/successful.html b/java-gcpspeechai/src/main/resources/templates/successful.html deleted file mode 100644 index beb4273..0000000 --- a/java-gcpspeechai/src/main/resources/templates/successful.html +++ /dev/null @@ -1,80 +0,0 @@ - - - - - - Player Form - - - -
- -

Thank You!

- -
- - \ No newline at end of file diff --git a/python-realtimeSTT-NL2SQL-TTS/src/RealtimeSTT_NL2SQL_TTS_AudioPlayback.py b/python-realtimeSTT-NL2SQL-TTS/src/RealtimeSTT_NL2SQL_TTS_AudioPlayback.py index 74d34c7..03ecc35 100644 --- a/python-realtimeSTT-NL2SQL-TTS/src/RealtimeSTT_NL2SQL_TTS_AudioPlayback.py +++ b/python-realtimeSTT-NL2SQL-TTS/src/RealtimeSTT_NL2SQL_TTS_AudioPlayback.py @@ -12,8 +12,8 @@ from oci.config import from_file from oci.auth.signers.security_token_signer import SecurityTokenSigner from oci.ai_speech_realtime import ( - RealtimeClient, - RealtimeClientListener, + RealtimeSpeechClient, + RealtimeSpeechClientListener, RealtimeParameters, ) from aiohttp import web @@ -27,6 +27,9 @@ compartment_id = os.getenv('COMPARTMENT_ID') print(f"compartment_id: {compartment_id}") +# If using thick mode/driver, do the following to load needed libraries... +# (client can be downloaded from https://www.oracle.com/database/technologies/instant-client/winx64-64-downloads.html) +# oracledb.init_oracle_client(lib_dir=r"C:\[path_to_instant_client]\instantclient_23_7") connection = oracledb.connect( user="moviestream", password="Welcome12345", @@ -105,7 +108,7 @@ def play_audio(file_path): print(f"Error playing audio: {e}") -class SpeechListener(RealtimeClientListener): +class SpeechListener(RealtimeSpeechClientListener): def on_result(self, result): global cummulativeResult, isSelect, isNarrate, isShowSQL, isRunSQL, isExplainSQL, last_result_time if result["transcriptions"][0]["isFinal"]: @@ -174,7 +177,7 @@ async def check_idle(): def authenticator(): - config = from_file("~/.oci/config", "MYSPEECHAIPROFILE") + config = from_file("~/.oci/config", "DEFAULT") with open(config["security_token_file"], "r") as f: token = f.readline() private_key = oci.signer.load_private_key_from_file(config["key_file"]) @@ -199,7 +202,7 @@ def executeSelectAI(): query = """SELECT DBMS_CLOUD_AI.GENERATE( prompt => :prompt, - profile_name => 'AIHOLO', + profile_name => 'GENAI', action => :action) FROM dual""" @@ -219,32 +222,33 @@ def executeSelectAI(): if selectai_action in ("showsql", "runsql", "explainsql"): return - # API key-based authentication... + # API key-based authentication, using phoenix OCI Region - https://docs.oracle.com/en-us/iaas/Content/speech/using/speech.htm#ser-limits config = oci.config.from_file("~/.oci/config", "DEFAULT") - speech_client = AIServiceSpeechClient(config) - - text_to_speech = SynthesizeSpeechDetails( - text=f" {latest_answer}", - is_stream_enabled=False, - configuration=oci.ai_speech.models.TtsOracleConfiguration( - model_family="ORACLE", - # Brian Annabelle Bob Stacy Phil Cindy Brad - model_details=oci.ai_speech.models.TtsOracleTts2NaturalModelDetails(voice_id="Brian"), - speech_settings=oci.ai_speech.models.TtsOracleSpeechSettings( - speech_mark_types=["WORD"] - ), - ) - ) - - response = speech_client.synthesize_speech(synthesize_speech_details=text_to_speech) - - with open("TTSoutput.wav", "wb") as audio_file: - audio_file.write(response.data.content) - - print("Speech synthesis completed and saved as TTSoutput.wav") + ai_speech_client = oci.ai_speech.AIServiceSpeechClient(config) + synthesize_speech_response = ai_speech_client.synthesize_speech( + synthesize_speech_details=oci.ai_speech.models.SynthesizeSpeechDetails( + text=f" {latest_answer}", + is_stream_enabled=True, + compartment_id=compartment_id, + configuration=oci.ai_speech.models.TtsOracleConfiguration( + model_family="ORACLE", + model_details=oci.ai_speech.models.TtsOracleTts1StandardModelDetails( + model_name="TTS_1_STANDARD", + voice_id="Bob"), + speech_settings=oci.ai_speech.models.TtsOracleSpeechSettings( + text_type="SSML", + sample_rate_in_hz=28000, + output_format="PCM", + speech_mark_types=["WORD"])), + audio_config=oci.ai_speech.models.TtsBaseAudioConfig( + config_type="BASE_AUDIO_CONFIG") + ) ) + with open("TTSoutput.pcm", "wb") as audio_file: + audio_file.write(synthesize_speech_response.data.content) + print("Speech synthesis completed and saved as TTSoutput.pcm") # Play the generated speech - play_audio("TTSoutput.wav") + play_audio("TTSoutput.pcm") except Exception as e: print(f"An error occurred: {e}") @@ -272,7 +276,7 @@ async def handle_request(request): realtime_speech_parameters.final_silence_threshold_in_ms = 2000 realtime_speech_url = "wss://realtime.aiservice.us-phoenix-1.oci.oraclecloud.com" - client = RealtimeClient( + client = RealtimeSpeechClient( config=config, realtime_speech_parameters=realtime_speech_parameters, listener=SpeechListener(), @@ -282,7 +286,7 @@ async def handle_request(request): ) # Instance, resource principal, or session token-based authentication (as shown below) can also be used - # client = RealtimeClient( + # client = RealtimeSpeechClient( # config=config, # realtime_speech_parameters=realtime_speech_parameters, # listener=SpeechListener(),