1 package com.neuronrobotics.bowlerstudio;
3 import java.util.Arrays;
4 import java.util.HashMap;
6 import java.io.BufferedInputStream;
7 import java.io.IOException;
8 import java.io.InputStream;
9 import java.net.URISyntaxException;
10 import java.net.URLEncoder;
11 import java.nio.charset.StandardCharsets;
12 import java.time.Duration;
14 import javax.sound.sampled.AudioInputStream;
15 import javax.sound.sampled.AudioSystem;
17 import org.eclipse.jgit.api.errors.GitAPIException;
18 import org.eclipse.jgit.api.errors.InvalidRemoteException;
19 import org.eclipse.jgit.api.errors.TransportException;
20 import com.neuronrobotics.bowlerstudio.scripting.ScriptingEngine;
21 import com.squareup.okhttp.OkHttpClient;
22 import com.squareup.okhttp.Request;
23 import com.squareup.okhttp.Response;
24 import com.github.dockerjava.api.DockerClient;
25 import com.github.dockerjava.api.command.BuildImageResultCallback;
26 import com.github.dockerjava.api.command.CreateContainerResponse;
27 import com.github.dockerjava.api.model.BuildResponseItem;
28 import com.github.dockerjava.api.model.Container;
29 import com.github.dockerjava.api.model.ContainerPort;
30 import com.github.dockerjava.api.model.ExposedPort;
31 import com.github.dockerjava.api.model.Frame;
32 import com.github.dockerjava.api.model.HostConfig;
33 import com.github.dockerjava.api.model.Ports;
34 import com.github.dockerjava.api.model.WaitResponse;
35 import com.github.dockerjava.core.DefaultDockerClientConfig;
36 import com.github.dockerjava.core.DockerClientBuilder;
37 import com.github.dockerjava.core.command.LogContainerResultCallback;
38 import com.github.dockerjava.transport.DockerHttpClient;
39 import com.google.common.collect.Sets;
40 import com.github.dockerjava.api.command.WaitContainerResultCallback;
41 import com.github.dockerjava.httpclient5.ApacheDockerHttpClient;
47 private static HashMap<String, CoquiDockerManager>
managers =
new HashMap<>();
49 private static List<String>
voiceOptions = Arrays.asList(
"p225" ,
"p226" ,
"p227" ,
"p228" ,
"p229" ,
"p230" ,
"p231" ,
"p232" ,
"p233" ,
"p234" ,
"p236" ,
"p237" ,
50 "p238" ,
"p239" ,
"p240" ,
"p241" ,
"p243" ,
"p244" ,
"p245" ,
"p246" ,
"p247" ,
"p248" ,
"p249" ,
"p250" ,
"p251" ,
51 "p252" ,
"p253" ,
"p254" ,
"p255" ,
"p256" ,
"p257" ,
"p258" ,
"p259" ,
"p260" ,
"p261" ,
"p262" ,
"p263" ,
"p264" ,
"p265" ,
"p266" ,
"p267" ,
"p268" ,
"p269" ,
"p270" ,
52 "p271" ,
"p272" ,
"p273" ,
"p274" ,
"p275" ,
"p276" ,
"p277" ,
"p278" ,
"p279" ,
"p280" ,
"p281" ,
"p282" ,
"p283" ,
"p284" ,
"p285" ,
"p286" ,
"p287" ,
"p288" ,
"p292" ,
53 "p293" ,
"p294" ,
"p295" ,
"p297",
"p298" ,
"p299" ,
"p300" ,
"p301" ,
"p302" ,
"p303" ,
"p304" ,
"p305" ,
"p306" ,
"p307" ,
"p308" ,
"p310" ,
"p311" ,
"p312" ,
"p313" ,
54 "p314" ,
"p316" ,
"p317" ,
"p318" ,
"p323" ,
"p326" ,
"p329" ,
"p330" ,
"p333" ,
"p334" ,
"p335" ,
"p336" ,
"p339" ,
"p340" ,
"p341" ,
"p343" ,
"p345" ,
"p347" ,
"p351" ,
55 "p360" ,
"p361" ,
"p362" ,
"p363" ,
"p364" ,
"p374" ,
"p376"
57 private static List<String>
options = Arrays.asList(
"tts_models/en/vctk/vits",
"tts_models/en/jenny/jenny");
58 private static List<String>
speakerNeeded = Arrays.asList(
"tts_models/en/vctk/vits");
77 GitAPIException, IOException, URISyntaxException {
80 throw new RuntimeException(
"Only one manager allowed");
84 System.out.println(
"Coqui Voice " +
voice);
85 String[] parts =
voice.split(
"/");
86 String voiceSlug =
"-" + parts[parts.length - 1];
90 .
fileFromGit(
"https://github.com/Halloween2020TheChild/CoquiDocker.git",
"Dockerfile")
92 String imageName =
"coqui-java";
95 DefaultDockerClientConfig config = DefaultDockerClientConfig.createDefaultConfigBuilder().build();
96 client =
new ApacheDockerHttpClient.Builder().dockerHost(config.getDockerHost())
97 .sslConfig(config.getSSLConfig()).maxConnections(100).connectionTimeout(Duration.ofSeconds(30))
98 .responseTimeout(Duration.ofSeconds(45)).build();
99 dockerClient = DockerClientBuilder.getInstance(config).withDockerHttpClient(
client).build();
102 String command =
"python3 TTS/server/server.py --model_name " +
voice;
104 List<Container> allCOntainers =
dockerClient.listContainersCmd().withShowAll(
true).exec();
107 for (Container c : allCOntainers) {
110 System.out.println(
"Container: " + c);
111 String[] names = c.getNames();
112 for (String n : names) {
114 String cs =
"/" + imageName + voiceSlug;
116 System.out.println(
"Checking " + n +
" to " + cs);
117 boolean PortMatch=
false;
118 ContainerPort[] conPorts = c.getPorts();
119 for(ContainerPort cp:conPorts) {
123 if (n.contentEquals(cs) || PortMatch) {
124 if (!c.getStatus().contains(
"Exited")) {
127 }
catch(com.github.dockerjava.api.exception.ConflictException ex) {
128 ex.printStackTrace();
139 File dockerfile =
new File(dockerFilePath);
141 dockerClient.buildImageCmd(dockerfile).withTags(Sets.newHashSet(imageName))
142 .exec(
new BuildImageResultCallback() {
144 public void onNext(BuildResponseItem item) {
146 System.out.println(item.getStream());
150 System.out.println(
"Docker image built successfully.");
152 ExposedPort port = ExposedPort.tcp(
hostPort);
153 Ports portBindings =
new Ports();
154 portBindings.bind(port, Ports.Binding.bindPort(
containerPort));
155 CreateContainerResponse containerResponse =
dockerClient.createContainerCmd(imageName)
156 .withName(imageName + voiceSlug).withCmd(command.split(
" ")).withTty(
true)
157 .withExposedPorts(port).withHostConfig(
new HostConfig().withPortBindings(portBindings)).exec();
158 id = containerResponse.getId();
160 dockerClient.waitContainerCmd(
id).exec(
new WaitContainerResultCallback() {
162 public void onNext(WaitResponse item) {
164 System.out.println(item.toString());
167 }).awaitCompletion();
169 LogContainerResultCallback logCallback=
new LogContainerResultCallback() {
171 public void onNext(Frame item) {
172 String
string = item.toString();
173 System.out.println(
string);
174 if(
string.contains(
"Press CTRL+C to quit")) {
179 dockerClient.logContainerCmd(
id).withStdOut(
true).withStdErr(
true).withFollowStream(
true).exec(logCallback);
182 }
catch (com.github.dockerjava.api.exception.ConflictException ex) {
184 ex.printStackTrace();
190 System.out.println(
"Waiting for server to start");
201 public static CoquiDockerManager get(
double doubleValue)
throws InvalidRemoteException, TransportException,
202 InterruptedException, GitAPIException, IOException, URISyntaxException {
203 int value = (int) Math.round(doubleValue - 800);
212 String voiceval =
options.get(value);
217 return coquiDockerManager;
224 String content = URLEncoder.encode(text.trim(), StandardCharsets.UTF_8.toString()).replace(
"+",
"%20");
230 if(s.contains(
voice))
233 String url =
"http://[::1]:5002//api/tts?text=" + content
234 +
string +
"&style_wav=&language_id=HTTP/1.1\n";
235 Request request =
new Request.Builder().url(url).get().build();
237 Response response =
new OkHttpClient().newCall(request).execute();
239 InputStream is = response.body().byteStream();
241 AudioInputStream audio = AudioSystem.getAudioInputStream(
new BufferedInputStream(is));
244 tts.setDaemon(daemon);
245 if (progress !=
null)
250 }
catch (Exception e) {
void setAudio(AudioInputStream audio)
void setSpeakProgress(ISpeakingProgress speakProgress)
void setGain(float fGain)
static List< String > voiceOptions
DockerClient dockerClient
CoquiDockerManager(String voice)
static List< String > options
static HashMap< String, CoquiDockerManager > managers
static int getNummberOfOptions()
static List< String > speakerNeeded
int speak(String text, float gainValue, boolean daemon, boolean join, ISpeakingProgress progress)
static File cloneRepo(String remoteURI, String branch)
static File fileFromGit(String remoteURI, String fileInRepo)
static void pull(String remoteURI, String branch)