语音管理

This commit is contained in:
2026-02-02 16:06:11 +08:00
parent 6fd7f8ca94
commit 2e575f78b1
20 changed files with 775 additions and 6 deletions

View File

@ -47,5 +47,8 @@ public class AppBusinessFile extends TenantEntity {
*/
private String remark;
/**
* 文件时长
*/
private Integer duration;
}

View File

@ -38,7 +38,7 @@ public class AppBusinessFileBo extends BaseEntity {
private Long businessId;
/**
* 文件类型(1:操作说明2:产品参数)
* 文件类型(1:操作说明2:产品参数,3:语音管理)
*/
private Long fileType;
@ -49,4 +49,6 @@ public class AppBusinessFileBo extends BaseEntity {
private List<Long> ids;
private Integer duration;
}

View File

@ -27,4 +27,6 @@ public class AppFileVo {
* 文件url
*/
private String fileUrl;
private Integer duration;
}

View File

@ -78,4 +78,5 @@ public interface IAppBusinessFileService {
List<AppFileVo> queryAppFileList(AppBusinessFileBo bo);
}

View File

@ -5,7 +5,7 @@ PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN"
<mapper namespace="com.fuyuanshen.app.mapper.AppBusinessFileMapper">
<select id="queryAppFileList" resultType="com.fuyuanshen.app.domain.vo.AppFileVo">
select a.id,a.business_id,a.file_id,a.file_type,b.file_name,b.url fileUrl from app_business_file a left join sys_oss b on a.file_id = b.oss_id
select a.id,a.business_id,a.file_id,a.file_type,b.file_name,b.url fileUrl,a.duration from app_business_file a left join sys_oss b on a.file_id = b.oss_id
where 1=1
<if test="businessId != null">
and a.business_id = #{businessId}

View File

@ -16,10 +16,8 @@ import com.fuyuanshen.customer.domain.vo.ConsumerVo;
import com.fuyuanshen.customer.mapper.CustomerMapper;
import com.fuyuanshen.customer.service.CustomerService;
import com.fuyuanshen.system.domain.SysUserRole;
import com.fuyuanshen.system.domain.bo.SysUserBo;
import com.fuyuanshen.system.mapper.SysRoleMapper;
import com.fuyuanshen.system.mapper.SysUserRoleMapper;
import com.fuyuanshen.system.service.ISysUserService;
import com.fuyuanshen.system.service.impl.SysUserServiceImpl;
import io.undertow.util.BadRequestException;
import lombok.RequiredArgsConstructor;

View File

@ -113,6 +113,21 @@ public class AlibabaTTSUtil {
DEFAULT_VOLUME, DEFAULT_SPEECH_RATE, DEFAULT_PITCH_RATE);
}
public byte[] synthesizeTextToMp3(String text){
try {
// 获取访问令牌
String token = getValidAccessToken();
// 使用HTTP方式调用
HttpTtsClient httpClient = new HttpTtsClient(appkey,token);
return httpClient.synthesizeTextToMp3(text);
} catch (IOException e) {
e.printStackTrace();
}
return null;
}
/**
* 生成语音文件 - 完整版(支持所有参数调节)
*

View File

@ -0,0 +1,89 @@
package com.fuyuanshen.equipment.utils;
import com.alibaba.nls.client.AccessToken;
import java.io.*;
import java.net.HttpURLConnection;
import java.net.URL;
import static cn.dev33.satoken.SaManager.log;
public class HttpTtsClient {
private String appKey;
private String token;
/**
* 阿里云TTS服务基础URL
*/
private static final String BASE_URL = "https://nls-gateway-cn-shanghai.aliyuncs.com/stream/v1/tts";
public HttpTtsClient(String appKey, String token) {
this.appKey = appKey;
this.token = token;
}
/**
* 使用HTTP POST方式调用阿里云TTS服务生成MP3格式语音
*/
public byte[] synthesizeTextToMp3(String text) throws IOException {
String endpoint = "https://nls-gateway-cn-shanghai.aliyuncs.com/stream/v1/tts";
// 构建请求体
// String requestBody = String.format(
// "{\"appkey\":\"%s\",\"text\":\"%s\",\"voice\":\"zhifeng\",\"format\":\"MP3\",\"sample_rate\":24000,\"volume\":50,\"speech_rate\":0,\"pitch_rate\":0}",
// appKey,
// text.replace("\"", "\\\"")
// );
String requestBody = " {\n" +
" \"appkey\":\""+appKey+"\",\n" +
" \"text\":\""+text+"\",\n" +
" \"token\":\""+token+"\",\n" +
" \"format\":\"mp3\"\n" +
" }";
URL url = new URL(endpoint);
HttpURLConnection conn = (HttpURLConnection) url.openConnection();
// 设置请求方法和头部
conn.setRequestMethod("POST");
conn.setRequestProperty("Content-Type", "application/json");
// conn.setRequestProperty("Authorization", buildAuthorization());
conn.setRequestProperty("Content-Length", String.valueOf(requestBody.getBytes().length));
conn.setDoOutput(true);
// 发送请求体
try (OutputStream os = conn.getOutputStream()) {
os.write(requestBody.getBytes("UTF-8"));
}
// 读取响应
int responseCode = conn.getResponseCode();
if (responseCode == HttpURLConnection.HTTP_OK) {
// 读取音频数据
try (InputStream is = conn.getInputStream()) {
ByteArrayOutputStream buffer = new ByteArrayOutputStream();
int nRead;
byte[] data = new byte[1024];
while ((nRead = is.read(data, 0, data.length)) != -1) {
buffer.write(data, 0, nRead);
}
return buffer.toByteArray();
}
} else {
throw new IOException("HTTP请求失败状态码: " + responseCode);
}
}
/**
* 保存MP3到文件
*/
public String saveMp3ToFile(String text, String outputPath) throws IOException {
byte[] mp3Data = synthesizeTextToMp3(text);
try (FileOutputStream fos = new FileOutputStream(outputPath)) {
fos.write(mp3Data);
}
return outputPath;
}
}

View File

@ -0,0 +1,35 @@
package com.fuyuanshen.equipment.utils;
import org.jaudiotagger.audio.AudioFileIO;
import org.jaudiotagger.audio.mp3.MP3File;
import java.io.File;
public class Mp3Duration {
/**
* 获取MP3文件的播放时长
*
* @param filePath MP3文件路径
* @return 播放时长(秒)
*/
public static int getMp3Duration(String filePath) {
try {
File file = new File(filePath);
MP3File mp3File = (MP3File) AudioFileIO.read(file);
return mp3File.getMP3AudioHeader().getTrackLength();
} catch (Exception e) {
e.printStackTrace();
return -1; // 错误时返回-1
}
}
public static void main(String[] args) {
String filePath = "D:\\http_output.mp3"; // 替换为实际路径
int duration = getMp3Duration(filePath);
if (duration != -1) {
System.out.println("MP3时长: " + duration + "");
} else {
System.out.println("无法获取MP3时长");
}
}
}