6 changed files with 112 additions and 301 deletions
-
6cmakepc.cmake
-
2dep/zlinuxcomponents
-
128src/service/voiceprocess/asr_service.cpp
-
90src/service/voiceprocess/asr_service.hpp
-
108src/test_aiui_service.cpp
-
79src/test_asr_main.cpp
@ -1 +1 @@ |
|||||
Subproject commit 2344b60385743afbe743660579ee72e8e9760552 |
|
||||
|
Subproject commit a72b77a07bfe7c79abaf603998d98c63a18a7328 |
@ -1,128 +0,0 @@ |
|||||
#include "asr_service.hpp"
|
|
||||
|
|
||||
#include "iflytopcpp/core/components/audio/wavheader.hpp"
|
|
||||
#include "zlinuxcomponents/aiui_ws/aiui.h"
|
|
||||
using namespace iflytop; |
|
||||
using namespace core; |
|
||||
using namespace std; |
|
||||
|
|
||||
static AiuiService *thisClass = nullptr; |
|
||||
static string getTTSFileName() { |
|
||||
static int i = 0; |
|
||||
i++; |
|
||||
if (i > 10) i = 0; |
|
||||
return fmt::format("/tmp/aiui_service_tts{}.wav", i); |
|
||||
} |
|
||||
|
|
||||
/**
|
|
||||
* aiui的识别结果返回大致如下,先返回一个nlp识别结果的包,然后再返回多个包含tts音频数据的json包 |
|
||||
* nlp->tts0->tts1->...->ttsn |
|
||||
* 1. 通过json["data"]["sub"]来判断是什么包,sub的值有:nlp,tts |
|
||||
* 2. 通过json["data"]["is_last"]判断是否是当前种类的最后一包. |
|
||||
* 3. 通过json["data"]["is_finish"]判断是否是本次传输的最后一包 |
|
||||
* |
|
||||
*/ |
|
||||
extern "C" { |
|
||||
extern size_t aiui_base64_decode(char *source, unsigned char *target, size_t targetlen); |
|
||||
} |
|
||||
void aiui_message_cb(const char *data, int len) { |
|
||||
if (thisClass) { |
|
||||
thisClass->call_aiui_message_cb(data, len); |
|
||||
} |
|
||||
} |
|
||||
void aiui_error_cb(int code, const char *str) { |
|
||||
if (thisClass) { |
|
||||
thisClass->call_aiui_error_cb(code, str); |
|
||||
} |
|
||||
} |
|
||||
AiuiService::AiuiService() { thisClass = this; } |
|
||||
int AiuiService::aiuiInit(const char *appid, const char *key, const char *param) { |
|
||||
thisClass = this; |
|
||||
return aiui_init(appid, key, param, aiui_message_cb, aiui_error_cb); |
|
||||
} |
|
||||
int AiuiService::aiuiWrite(const char *audio, int len) { return aiui_write(audio, len); } |
|
||||
int AiuiService::aiuiFinished() { return aiui_finished(); } |
|
||||
void AiuiService::aiuiDestroy() { |
|
||||
aiui_destroy(); |
|
||||
thisClass = nullptr; |
|
||||
} |
|
||||
void AiuiService::parseTTSContent(json &rxjson) { |
|
||||
if (!oneAsrResultTransmition) { |
|
||||
logger->error("oneAsrResultTransmition is null"); |
|
||||
return; |
|
||||
} |
|
||||
/**
|
|
||||
* @brief 解码base64数据,并保存起来 |
|
||||
*/ |
|
||||
string base64Data = rxjson["data"]["content"].get<string>(); |
|
||||
size_t size = base64Data.size() * 3 / 4 + 50; |
|
||||
shared_ptr<Binary> binary = make_shared<Binary>(size); |
|
||||
size_t realsize = aiui_base64_decode((char *)base64Data.c_str(), binary->data(), size); |
|
||||
binary->resize(realsize); |
|
||||
oneAsrResultTransmition->ttsRawData.push_back(binary); |
|
||||
} |
|
||||
|
|
||||
void AiuiService::endOneAsrResultTransmition() { |
|
||||
/**
|
|
||||
* @brief 如果是最后一包,则将接收到的tts保存成文件,然后同nlp结果打包在一起,然后上报。 |
|
||||
*/ |
|
||||
string ttsFileName = getTTSFileName(); |
|
||||
FILE *fp = fopen(ttsFileName.c_str(), "wb"); |
|
||||
size_t ttsframetotalsize = 0; |
|
||||
for (auto &binary : oneAsrResultTransmition->ttsRawData) { |
|
||||
ttsframetotalsize += binary->size(); |
|
||||
} |
|
||||
WAVHeader wavHeader(16000, 16, 1, ttsframetotalsize / 2); |
|
||||
if (fp) { |
|
||||
fwrite(wavHeader.data(), 1, wavHeader.size(), fp); |
|
||||
for (auto &binary : oneAsrResultTransmition->ttsRawData) { |
|
||||
fwrite(binary->data(), 1, binary->size(), fp); |
|
||||
ttsframetotalsize += binary->size(); |
|
||||
} |
|
||||
fclose(fp); |
|
||||
} |
|
||||
oneAsrResultTransmition->asrResult["data"]["intent"]["answer"]["ttsurl"] = ttsFileName; |
|
||||
/**
|
|
||||
* @brief 上报识别结果 |
|
||||
*/ |
|
||||
onAsrResult(oneAsrResultTransmition->asrResult); |
|
||||
oneAsrResultTransmition.reset(); |
|
||||
} |
|
||||
|
|
||||
void AiuiService::call_aiui_message_cb(const char *data, int len) { |
|
||||
try { |
|
||||
if (!oneAsrResultTransmition) { |
|
||||
oneAsrResultTransmition = make_unique<OneAsrResultTransmition>(); |
|
||||
logger->info("start rx aiui data"); |
|
||||
} |
|
||||
json rxjson = json::parse(data); |
|
||||
if (rxjson["action"].get<string>() != "result") { |
|
||||
return; |
|
||||
} |
|
||||
|
|
||||
/**
|
|
||||
* @brief 处理接收到的数据 |
|
||||
*/ |
|
||||
if (rxjson["data"]["sub"].get<string>() == "nlp") { |
|
||||
// 解析nlpcontent
|
|
||||
oneAsrResultTransmition->asrResult = rxjson; |
|
||||
} else if (rxjson["data"]["sub"].get<string>() == "tts") { |
|
||||
// 解析ttscontent
|
|
||||
parseTTSContent(rxjson); |
|
||||
} |
|
||||
/**
|
|
||||
* @brief 结束本次接收 |
|
||||
*/ |
|
||||
if (rxjson["data"]["is_finish"].get<bool>()) { |
|
||||
logger->info("end rx aiui data"); |
|
||||
// will call onAsrResult in this function
|
|
||||
endOneAsrResultTransmition(); |
|
||||
} |
|
||||
} catch (const std::exception &e) { |
|
||||
logger->error("AiuiService::call_aiui_message_cb error: {}", e.what()); |
|
||||
} |
|
||||
} |
|
||||
void AiuiService::call_aiui_error_cb(int code, const char *str) { |
|
||||
logger->error("AiuiService::call_aiui_error_cb error: {} => {}", code, str); |
|
||||
onError(code, str); |
|
||||
} |
|
@ -1,90 +0,0 @@ |
|||||
//
|
|
||||
// Created by zwsd
|
|
||||
//
|
|
||||
|
|
||||
#pragma once
|
|
||||
#include <fstream>
|
|
||||
#include <iostream>
|
|
||||
#include <list>
|
|
||||
#include <map>
|
|
||||
#include <memory>
|
|
||||
#include <set>
|
|
||||
#include <sstream>
|
|
||||
#include <string>
|
|
||||
#include <vector>
|
|
||||
|
|
||||
#include "iflytopcpp/core/basic/ds/binary.hpp"
|
|
||||
#include "iflytopcpp/core/basic/nlohmann/json.hpp"
|
|
||||
#include "iflytopcpp/core/basic/nod/nod.hpp"
|
|
||||
#include "iflytopcpp/core/spdlogfactory/logger.hpp"
|
|
||||
#include "iflytopcpp/core/thread/thread.hpp"
|
|
||||
|
|
||||
/**
|
|
||||
* @brief |
|
||||
* |
|
||||
* service: AsrService |
|
||||
* |
|
||||
* 监听事件: |
|
||||
* 依赖状态: |
|
||||
* 依赖服务: |
|
||||
* 作用: |
|
||||
* |
|
||||
*/ |
|
||||
|
|
||||
namespace iflytop { |
|
||||
using namespace std; |
|
||||
using namespace core; |
|
||||
using namespace nlohmann; |
|
||||
|
|
||||
class OneAsrResultTransmition { |
|
||||
public: |
|
||||
json asrResult; |
|
||||
list<json> ttsResult; |
|
||||
list<shared_ptr<Binary>> ttsRawData; |
|
||||
}; |
|
||||
|
|
||||
class AiuiService : public enable_shared_from_this<AiuiService> { |
|
||||
ENABLE_LOGGER(AiuiService); |
|
||||
|
|
||||
bool transFinished = false; |
|
||||
unique_ptr<OneAsrResultTransmition> oneAsrResultTransmition; |
|
||||
|
|
||||
public: |
|
||||
nod::signal<void(json &asrResult)> onAsrResult; |
|
||||
nod::signal<void(int code, const char *str)> onError; |
|
||||
|
|
||||
AiuiService(); |
|
||||
|
|
||||
int aiuiInit(const char *appid, const char *key, const char *param); |
|
||||
int aiuiWrite(const char *audio, int len); |
|
||||
int aiuiFinished(); |
|
||||
void aiuiDestroy(); |
|
||||
|
|
||||
void call_aiui_message_cb(const char *data, int len); |
|
||||
void call_aiui_error_cb(int code, const char *str); |
|
||||
|
|
||||
private: |
|
||||
void parseTTSContent(json &rxjson); |
|
||||
void endOneAsrResultTransmition(); |
|
||||
}; |
|
||||
|
|
||||
class AsrService : public enable_shared_from_this<AsrService> { |
|
||||
ENABLE_LOGGER(AsrService); |
|
||||
|
|
||||
public: |
|
||||
nod::signal<void(json &asrResult)> onAsrResult; |
|
||||
nod::signal<void()> onVoiceEnd; |
|
||||
|
|
||||
private: |
|
||||
//
|
|
||||
public: |
|
||||
AsrService(){}; |
|
||||
|
|
||||
void initialize(string appid, string key); |
|
||||
void startRequest(); |
|
||||
void endRequest(); |
|
||||
void writeVoice(uint16_t *voice, size_t voiceLen); |
|
||||
void writeVoice(string text); |
|
||||
void writeVoiceEnd(); |
|
||||
}; |
|
||||
} // namespace iflytop
|
|
@ -0,0 +1,108 @@ |
|||||
|
#include "zlinuxcomponents/zmainhelper.hpp"
|
||||
|
//
|
||||
|
#include "configs/config.hpp"
|
||||
|
#include "iflytopcpp/core/spdlogfactory/logger.hpp"
|
||||
|
#include "iflytopcpp/core/thread/thread.hpp"
|
||||
|
#include "spdlog/spdlog.h"
|
||||
|
#include "version.hpp"
|
||||
|
#include "zlinuxcomponents/rootfs_auto_update/rootfs_auto_update.hpp"
|
||||
|
#include "zservice_container/zservice_container.hpp"
|
||||
|
//
|
||||
|
#include "service/device_io_service.hpp"
|
||||
|
#include "service/device_io_service_mock.hpp"
|
||||
|
#include "service/light_control_service.hpp"
|
||||
|
#include "service/report_service.hpp"
|
||||
|
#include "zlinuxcomponents/aiui_ws/aiui_service.hpp"
|
||||
|
|
||||
|
//
|
||||
|
#include "zlinuxcomponents/alsaplayer/AudioPlayerAlsaImpl.hpp"
|
||||
|
// #include "zlinuxcomponents/audio/audio_recoder.hpp"
|
||||
|
#include <curl/curl.h>
|
||||
|
|
||||
|
#include <iostream>
|
||||
|
#include <string>
|
||||
|
|
||||
|
#include "zlinuxcomponents/aiui_ws/aiui.h"
|
||||
|
|
||||
|
//
|
||||
|
using namespace iflytop; |
||||
|
using namespace core; |
||||
|
using namespace std; |
||||
|
using namespace clipp; |
||||
|
|
||||
|
ZMAIN(); |
||||
|
void Main::onSIGINT() { exit(0); } |
||||
|
int Main::main(int argc, char *argv[]) { |
||||
|
string g_host_server_ip; |
||||
|
string g_device_id; |
||||
|
spdlog::flush_on(spdlog::level::debug); |
||||
|
|
||||
|
const char *appid = "5938b7c7"; // 应用ID,在AIUI开放平台创建并设置
|
||||
|
const char *key = "19c1f7becc78eedc7826b485aabe30de"; // 接口密钥,在AIUI开放平台查看
|
||||
|
const char *param = |
||||
|
"{\"result_level\":\"plain\",\"auth_id\":\"ac30105366ea460f9ff08ddac0c4f71e\",\"data_" |
||||
|
"type\":\"text\"," |
||||
|
"\"scene\":\"main_box\",\"sample_rate\":\"16000\", " |
||||
|
"\"context\":\"{\\\"sdk_support\\\":[\\\"nlp\\\",\\\"tts\\\"]}\"}"; |
||||
|
|
||||
|
json paramj; |
||||
|
paramj["result_level"] = "plain"; |
||||
|
paramj["auth_id"] = "ac30105366ea460f9ff08ddac0c4f71e"; |
||||
|
paramj["data_type"] = "text"; |
||||
|
paramj["scene"] = "main_box"; |
||||
|
paramj["sample_rate"] = "16000"; |
||||
|
paramj["context"] = R"({"sdk_support":["nlp","tts","vad","iat"]})"; |
||||
|
// logger->info("{}", paramj.dump());
|
||||
|
// logger->info("{}", param);
|
||||
|
|
||||
|
shared_ptr<AiuiService> aiuiService(new AiuiService()); |
||||
|
logger->info("test_asr_main.cpp"); |
||||
|
aiuiService->initialize(appid, key, paramj.dump()); |
||||
|
aiuiService->aiuiInit(); |
||||
|
aiuiService->onMessage.connect([&](json &rxjson) { |
||||
|
//
|
||||
|
string action = rxjson["action"]; |
||||
|
if (action == "started") { |
||||
|
logger->info("rx started:{}", rxjson.dump()); |
||||
|
} |
||||
|
//
|
||||
|
else if (action == "result") { |
||||
|
string sub = rxjson["data"]["sub"]; |
||||
|
if (sub == "nlp") { |
||||
|
logger->info("rx nlp:{}", rxjson.dump()); |
||||
|
} else if (sub == "tts") { |
||||
|
logger->info("rx tts:frame {}", rxjson["data"]["json_args"]["frame_id"].get<int>()); |
||||
|
bool isendFrame = false; |
||||
|
string ttsurl; |
||||
|
aiuiService->parseTTSContent(rxjson, isendFrame, ttsurl); |
||||
|
if (isendFrame) { |
||||
|
logger->info("rx tts end,url={}", ttsurl); |
||||
|
} |
||||
|
} else if (sub == "iat") { |
||||
|
logger->info("rx iat:{}", rxjson.dump()); |
||||
|
} else if (sub == "vad") { |
||||
|
logger->info("rx vad:{}", rxjson.dump()); |
||||
|
} else { |
||||
|
logger->info("rx {}:{}", sub, rxjson.dump()); |
||||
|
} |
||||
|
} |
||||
|
//
|
||||
|
else if (action == "error") { |
||||
|
logger->info("rx error:{}", rxjson.dump()); |
||||
|
} |
||||
|
//
|
||||
|
else if (action == "vad") { |
||||
|
} else { |
||||
|
logger->info("rx unkown:{}", rxjson.dump()); |
||||
|
} |
||||
|
|
||||
|
try { |
||||
|
if (rxjson["data"]["is_finish"].get<bool>()) { |
||||
|
logger->info("end tx"); |
||||
|
} |
||||
|
} catch (...) { |
||||
|
} |
||||
|
}); |
||||
|
aiuiService->aiuiWrite("今天天气怎么样", strlen("今天天气怎么样")); |
||||
|
while (true) sleep(1000); |
||||
|
} |
@ -1,79 +0,0 @@ |
|||||
#include "zlinuxcomponents/zmainhelper.hpp"
|
|
||||
//
|
|
||||
#include "configs/config.hpp"
|
|
||||
#include "iflytopcpp/core/spdlogfactory/logger.hpp"
|
|
||||
#include "iflytopcpp/core/thread/thread.hpp"
|
|
||||
#include "spdlog/spdlog.h"
|
|
||||
#include "version.hpp"
|
|
||||
#include "zlinuxcomponents/rootfs_auto_update/rootfs_auto_update.hpp"
|
|
||||
#include "zservice_container/zservice_container.hpp"
|
|
||||
#include "zwebservice/zwebservice.hpp"
|
|
||||
//
|
|
||||
#include "service/device_io_service.hpp"
|
|
||||
#include "service/device_io_service_mock.hpp"
|
|
||||
#include "service/light_control_service.hpp"
|
|
||||
#include "service/main_control_service.hpp"
|
|
||||
#include "service/report_service.hpp"
|
|
||||
#include "service/voiceprocess/asr_service.hpp"
|
|
||||
//
|
|
||||
#include "zlinuxcomponents/alsaplayer/AudioPlayerAlsaImpl.hpp"
|
|
||||
// #include "zlinuxcomponents/audio/audio_recoder.hpp"
|
|
||||
#include <curl/curl.h>
|
|
||||
|
|
||||
#include <iostream>
|
|
||||
#include <string>
|
|
||||
|
|
||||
#include "zlinuxcomponents/aiui_ws/aiui.h"
|
|
||||
|
|
||||
//
|
|
||||
using namespace iflytop; |
|
||||
using namespace core; |
|
||||
using namespace std; |
|
||||
using namespace clipp; |
|
||||
|
|
||||
ZMAIN(); |
|
||||
/***********************************************************************************************************************
|
|
||||
* =======================================================Main======================================================== * |
|
||||
***********************************************************************************************************************/ |
|
||||
static void onmessage(const char *data, int len) {} |
|
||||
static void onerror(int code, const char *str) { printf("aiui_init onerror %d => %s\n", code, str); } |
|
||||
|
|
||||
void Main::onSIGINT() { exit(0); } |
|
||||
|
|
||||
int Main::main(int argc, char *argv[]) { |
|
||||
string g_host_server_ip; |
|
||||
string g_device_id; |
|
||||
spdlog::flush_on(spdlog::level::debug); |
|
||||
|
|
||||
const char *appid = "5938b7c7"; // 应用ID,在AIUI开放平台创建并设置
|
|
||||
const char *key = "19c1f7becc78eedc7826b485aabe30de"; // 接口密钥,在AIUI开放平台查看
|
|
||||
const char *param = |
|
||||
"{\"result_level\":\"plain\",\"auth_id\":\"ac30105366ea460f9ff08ddac0c4f71e\",\"data_" |
|
||||
"type\":\"text\"," |
|
||||
"\"scene\":\"main_box\",\"sample_rate\":\"16000\", " |
|
||||
"\"context\":\"{\\\"sdk_support\\\":[\\\"nlp\\\",\\\"tts\\\"]}\"}"; |
|
||||
shared_ptr<AiuiService> aiuiService(new AiuiService()); |
|
||||
logger->info("test_asr_main.cpp"); |
|
||||
aiuiService->aiuiInit(appid, key, param); |
|
||||
aiuiService->onAsrResult.connect([this](json j) { |
|
||||
logger->info("onAsrResult: {}", j.dump(2)); |
|
||||
}); |
|
||||
aiuiService->aiuiWrite("今天天气怎么样", strlen("今天天气怎么样")); |
|
||||
// aiuiService->aiuiFinished();
|
|
||||
// aiuiService->aiuiDestroy();
|
|
||||
#if 0
|
|
||||
|
|
||||
|
|
||||
aiui_init(appid, key, param, onmessage, onerror); |
|
||||
|
|
||||
const char *text = "播放音乐"; |
|
||||
|
|
||||
aiui_write(text, strlen(text)); |
|
||||
|
|
||||
aiui_finished(); |
|
||||
|
|
||||
aiui_destroy(); |
|
||||
#endif
|
|
||||
|
|
||||
while (true) sleep(1000); |
|
||||
} |
|
Write
Preview
Loading…
Cancel
Save
Reference in new issue