mirror of
https://github.com/neodyland/sbv2-api.git
synced 2025-12-25 00:29:57 +00:00
Compare commits
32 Commits
v0.2.0-alp
...
mecab
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
4744f02792 | ||
|
|
5de9514546 | ||
|
|
dc88251d41 | ||
|
|
1550ce6ee4 | ||
|
|
c1bebea69b | ||
|
|
af5a550b8f | ||
|
|
febfd0d84f | ||
|
|
55698f4a61 | ||
|
|
b0155f5ffa | ||
|
|
0e9c7b6522 | ||
|
|
b0d8be32b6 | ||
|
|
f76f5e6d1c | ||
|
|
e8cc450693 | ||
|
|
6f0fcd491c | ||
|
|
5cf4149024 | ||
|
|
65303173a8 | ||
|
|
30e4cde3ed | ||
|
|
596eec654d | ||
|
|
ee292315e1 | ||
|
|
731c751455 | ||
|
|
497bdd79ea | ||
|
|
b887fae47b | ||
|
|
ca0b8553e4 | ||
|
|
29b14895bb | ||
|
|
c2910ad9e8 | ||
|
|
5c092e8cbb | ||
|
|
d380e549c4 | ||
|
|
395f5b0004 | ||
|
|
f5609035b7 | ||
|
|
1e9f25dcb1 | ||
|
|
321ca4e749 | ||
|
|
bb23bd145b |
9
.github/pull_request_template.md
vendored
9
.github/pull_request_template.md
vendored
@@ -1,8 +1,13 @@
|
||||
## 概要
|
||||
(ここに本PRの説明をしてください。)
|
||||
<!--
|
||||
ここに本PRの説明をしてください。
|
||||
-->
|
||||
|
||||
## 関連issue
|
||||
(ここに該当するissueの番号を書いてください。)
|
||||
<!--
|
||||
ここに該当するissueの番号を書いてください。
|
||||
#nの前にfixesを置くとプルリクが閉じた時に自動的に該当issueもクローズします、
|
||||
-->
|
||||
|
||||
## 確認
|
||||
- [ ] 動作確認しましたか?
|
||||
|
||||
34
.github/workflows/CI.yml
vendored
34
.github/workflows/CI.yml
vendored
@@ -130,3 +130,37 @@ jobs:
|
||||
with:
|
||||
command: upload
|
||||
args: --non-interactive --skip-existing wheels-*/*
|
||||
|
||||
push-docker:
|
||||
runs-on: ubuntu-latest
|
||||
if: "startsWith(github.ref, 'refs/tags/')"
|
||||
permissions:
|
||||
contents: read
|
||||
packages: write
|
||||
strategy:
|
||||
matrix:
|
||||
tag: [cpu, cuda]
|
||||
platform:
|
||||
- linux/amd64
|
||||
- linux/arm64
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
- name: Set up QEMU
|
||||
uses: docker/setup-qemu-action@v3
|
||||
- name: Set up Docker Buildx
|
||||
uses: docker/setup-buildx-action@v3
|
||||
- name: Login to GitHub Container Registry
|
||||
uses: docker/login-action@v3
|
||||
with:
|
||||
registry: ghcr.io
|
||||
username: ${{ github.actor }}
|
||||
password: ${{ secrets.GITHUB_TOKEN }}
|
||||
- name: Build and push image
|
||||
uses: docker/build-push-action@v6
|
||||
with:
|
||||
context: .
|
||||
push: true
|
||||
tags: |
|
||||
ghcr.io/${{ github.repository }}:${{ matrix.tag }}
|
||||
file: docker/${{ matrix.tag }}.Dockerfile
|
||||
platforms: ${{ matrix.platform }}
|
||||
|
||||
40
.github/workflows/build.yml
vendored
40
.github/workflows/build.yml
vendored
@@ -1,40 +0,0 @@
|
||||
name: Push to github container register
|
||||
|
||||
on:
|
||||
release:
|
||||
types: [created]
|
||||
workflow_dispatch:
|
||||
|
||||
jobs:
|
||||
push-docker:
|
||||
runs-on: ubuntu-latest
|
||||
permissions:
|
||||
contents: read
|
||||
packages: write
|
||||
strategy:
|
||||
matrix:
|
||||
tag: [cpu, cuda]
|
||||
platform:
|
||||
- linux/amd64
|
||||
- linux/arm64
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
- name: Set up QEMU
|
||||
uses: docker/setup-qemu-action@v3
|
||||
- name: Set up Docker Buildx
|
||||
uses: docker/setup-buildx-action@v3
|
||||
- name: Login to GitHub Container Registry
|
||||
uses: docker/login-action@v3
|
||||
with:
|
||||
registry: ghcr.io
|
||||
username: ${{ github.actor }}
|
||||
password: ${{ secrets.GITHUB_TOKEN }}
|
||||
- name: Build and push image
|
||||
uses: docker/build-push-action@v6
|
||||
with:
|
||||
context: .
|
||||
push: true
|
||||
tags: |
|
||||
ghcr.io/${{ github.repository }}:${{ matrix.tag }}
|
||||
file: docker/${{ matrix.tag }}.Dockerfile
|
||||
platforms: ${{ matrix.platform }}
|
||||
3
.gitignore
vendored
3
.gitignore
vendored
@@ -4,4 +4,5 @@ models/
|
||||
venv/
|
||||
.env
|
||||
output.wav
|
||||
node_modules
|
||||
node_modules
|
||||
dist/
|
||||
612
Cargo.lock
generated
612
Cargo.lock
generated
@@ -17,6 +17,17 @@ version = "2.0.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "512761e0bb2578dd7380c6baaa0f4ce03e84f95e960231d1dec8bf4d7d6e2627"
|
||||
|
||||
[[package]]
|
||||
name = "ahash"
|
||||
version = "0.7.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "891477e0c6a8957309ee5c45a6368af3ae14bb510732d2684ffa19af310920f9"
|
||||
dependencies = [
|
||||
"getrandom",
|
||||
"once_cell",
|
||||
"version_check",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "aho-corasick"
|
||||
version = "1.1.3"
|
||||
@@ -81,6 +92,44 @@ version = "1.0.89"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "86fdf8605db99b54d3cd748a44c6d04df638eb5dafb219b135d0149bd0db01f6"
|
||||
|
||||
[[package]]
|
||||
name = "argmin"
|
||||
version = "0.7.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5698c8cd3510117a4e6b96749a8061ba7dce1a19578ce4ecdb12dd36d94a7f8d"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"argmin-math",
|
||||
"bincode 1.3.3",
|
||||
"instant",
|
||||
"num-traits",
|
||||
"paste",
|
||||
"rand",
|
||||
"rand_xoshiro",
|
||||
"serde",
|
||||
"serde_json",
|
||||
"slog",
|
||||
"slog-async",
|
||||
"slog-json",
|
||||
"slog-term",
|
||||
"thiserror",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "argmin-math"
|
||||
version = "0.2.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "75f2b0dada81340718682df780c9a696b090b6ef7e83c3dcc770af6de9302995"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"cfg-if",
|
||||
"num-complex",
|
||||
"num-integer",
|
||||
"num-traits",
|
||||
"rand",
|
||||
"thiserror",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "async-trait"
|
||||
version = "0.1.82"
|
||||
@@ -89,7 +138,7 @@ checksum = "a27b8a3a6e1a44fa4c8baf1f653e4172e81486d4941f2237e20dc2d0cf4ddff1"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -100,9 +149,9 @@ checksum = "0c4b4d0bd25bd0b74681c0ad21497610ce1b7c91b1022cd21c80c6fbdd9476b0"
|
||||
|
||||
[[package]]
|
||||
name = "axum"
|
||||
version = "0.7.6"
|
||||
version = "0.7.7"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8f43644eed690f5374f1af436ecd6aea01cd201f6fbdf0178adaf6907afb2cec"
|
||||
checksum = "504e3947307ac8326a5437504c517c4b56716c9d98fac0028c2acc7ca47d70ae"
|
||||
dependencies = [
|
||||
"async-trait",
|
||||
"axum-core",
|
||||
@@ -134,9 +183,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "axum-core"
|
||||
version = "0.4.4"
|
||||
version = "0.4.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5e6b8ba012a258d63c9adfa28b9ddcf66149da6f986c5b5452e629d5ee64bf00"
|
||||
checksum = "09f2bd6146b97ae3359fa0cc6d6b376d9539582c7b4220f041a33ec24c226199"
|
||||
dependencies = [
|
||||
"async-trait",
|
||||
"bytes",
|
||||
@@ -189,6 +238,40 @@ dependencies = [
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "bincode"
|
||||
version = "2.0.0-rc.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f11ea1a0346b94ef188834a65c068a03aec181c94896d481d7a0a40d85b0ce95"
|
||||
dependencies = [
|
||||
"bincode_derive",
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "bincode_derive"
|
||||
version = "2.0.0-rc.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7e30759b3b99a1b802a7a3aa21c85c3ded5c28e1c83170d82d70f08bbf7f3e4c"
|
||||
dependencies = [
|
||||
"virtue",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "bit-set"
|
||||
version = "0.5.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0700ddab506f33b20a03b13996eccd309a48e5ff77d0d95926aa0210fb4e95f1"
|
||||
dependencies = [
|
||||
"bit-vec",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "bit-vec"
|
||||
version = "0.6.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "349f9b6a179ed607305526ca489b34ad0a41aed5f7980fa90eb03160b69598fb"
|
||||
|
||||
[[package]]
|
||||
name = "bitflags"
|
||||
version = "1.3.2"
|
||||
@@ -210,6 +293,12 @@ dependencies = [
|
||||
"generic-array",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "bumpalo"
|
||||
version = "3.16.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "79296716171880943b8470b5f8d03aa55eb2e645a4874bdbb28adb49162e012c"
|
||||
|
||||
[[package]]
|
||||
name = "byteorder"
|
||||
version = "1.5.0"
|
||||
@@ -267,6 +356,12 @@ dependencies = [
|
||||
"libc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "crawdad"
|
||||
version = "0.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "87fbd1ecd2ed790e11c8fbe034f9b3e7687404818d1bdfd8218d26ec645ec7c5"
|
||||
|
||||
[[package]]
|
||||
name = "crc32fast"
|
||||
version = "1.4.2"
|
||||
@@ -276,6 +371,15 @@ dependencies = [
|
||||
"cfg-if",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "crossbeam-channel"
|
||||
version = "0.5.13"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "33480d6946193aa8033910124896ca395333cae7e2d1113d1fef6c3272217df2"
|
||||
dependencies = [
|
||||
"crossbeam-utils",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "crossbeam-deque"
|
||||
version = "0.8.5"
|
||||
@@ -359,7 +463,7 @@ dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"strsim",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -370,7 +474,16 @@ checksum = "d336a2a514f6ccccaa3e09b02d41d35330c07ddf03a62165fcec10bb561c7806"
|
||||
dependencies = [
|
||||
"darling_core",
|
||||
"quote",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "deranged"
|
||||
version = "0.3.11"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b42b6fa04a440b495c8b04d0e71b707c585f83cb9cb28cf8cd0d976c315e31b4"
|
||||
dependencies = [
|
||||
"powerfmt",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -391,7 +504,7 @@ dependencies = [
|
||||
"darling",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -401,7 +514,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4abae7035bf79b9877b779505d8cf3749285b80c43941eda66604841889451dc"
|
||||
dependencies = [
|
||||
"derive_builder_core",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -414,6 +527,27 @@ dependencies = [
|
||||
"crypto-common",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "dirs-next"
|
||||
version = "2.0.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b98cf8ebf19c3d1b223e151f99a4f9f0690dca41414773390fc824184ac833e1"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"dirs-sys-next",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "dirs-sys-next"
|
||||
version = "0.1.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4ebda144c4fe02d1f7ea1a7d9641b6fc6b580adcfa024ae48797ecdeb6825b4d"
|
||||
dependencies = [
|
||||
"libc",
|
||||
"redox_users",
|
||||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "dotenvy"
|
||||
version = "0.15.7"
|
||||
@@ -537,6 +671,12 @@ dependencies = [
|
||||
"log",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "equivalent"
|
||||
version = "1.0.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5443807d6dff69373d433ab9ef5378ad8df50ca6298caf15de6e52e24aaf54d5"
|
||||
|
||||
[[package]]
|
||||
name = "errno"
|
||||
version = "0.3.9"
|
||||
@@ -556,6 +696,17 @@ dependencies = [
|
||||
"cc",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "fancy-regex"
|
||||
version = "0.13.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "531e46835a22af56d1e3b66f04844bed63158bc094a628bec1d321d9b4c44bf2"
|
||||
dependencies = [
|
||||
"bit-set",
|
||||
"regex-automata",
|
||||
"regex-syntax",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "filetime"
|
||||
version = "0.2.25"
|
||||
@@ -643,8 +794,10 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c4567c8db10ae91089c99af84c68c38da3ec2f087c3f82960bcdbf3656b6f4d7"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"js-sys",
|
||||
"libc",
|
||||
"wasi",
|
||||
"wasm-bindgen",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -669,6 +822,21 @@ dependencies = [
|
||||
"crunchy",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "hashbrown"
|
||||
version = "0.12.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8a9ee70c43aaf417c914396645a0fa852624801b24ebb7ae78fe8272889ac888"
|
||||
dependencies = [
|
||||
"ahash",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "hashbrown"
|
||||
version = "0.14.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e5274423e17b7c9fc20b6e7e208532f9b19825d82dfd615708b70edd83df41f1"
|
||||
|
||||
[[package]]
|
||||
name = "heck"
|
||||
version = "0.5.0"
|
||||
@@ -681,6 +849,12 @@ version = "0.3.9"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "d231dfb89cfffdbc30e7fc41579ed6066ad03abda9e567ccafae602b97ec5024"
|
||||
|
||||
[[package]]
|
||||
name = "hermit-abi"
|
||||
version = "0.4.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "fbf6a919d6cf397374f7dfeeea91d974c7c0a7221d0d0f4f20d859d329e53fcc"
|
||||
|
||||
[[package]]
|
||||
name = "hound"
|
||||
version = "3.5.1"
|
||||
@@ -791,6 +965,17 @@ dependencies = [
|
||||
"unicode-normalization",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "indexmap"
|
||||
version = "2.5.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "68b900aa2f7301e21c36462b170ee99994de34dff39a4a6a528e80e7376d07e5"
|
||||
dependencies = [
|
||||
"equivalent",
|
||||
"hashbrown 0.14.5",
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "indicatif"
|
||||
version = "0.17.8"
|
||||
@@ -819,6 +1004,17 @@ dependencies = [
|
||||
"cfg-if",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "is-terminal"
|
||||
version = "0.4.13"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "261f68e344040fbd0edea105bef17c66edf46f984ddb1115b775ce31be948f4b"
|
||||
dependencies = [
|
||||
"hermit-abi 0.4.0",
|
||||
"libc",
|
||||
"windows-sys 0.52.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "is_terminal_polyfill"
|
||||
version = "1.70.1"
|
||||
@@ -893,7 +1089,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "fe30c65ff4c092320f1bba3418ac111443a4827a9155442f6a7d8d0e3707cb51"
|
||||
dependencies = [
|
||||
"aho-corasick",
|
||||
"bincode",
|
||||
"bincode 1.3.3",
|
||||
"lindera-core",
|
||||
"lindera-tokenizer",
|
||||
"once_cell",
|
||||
@@ -909,7 +1105,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c156a875d35ef6fedf31cb9d6bb3c562d16faad4506a5be27e2ed44357d755d4"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"bincode",
|
||||
"bincode 1.3.3",
|
||||
"byteorder",
|
||||
"jpreprocess-core",
|
||||
"lindera-core",
|
||||
@@ -926,7 +1122,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0cd89b119949a5071e6f49d805829f3dc17169eb7c6aab809e4f373c70098709"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"bincode",
|
||||
"bincode 1.3.3",
|
||||
"byteorder",
|
||||
"csv",
|
||||
"glob",
|
||||
@@ -985,6 +1181,15 @@ version = "0.10.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9c06d7aceb8ce626a3318183096aa6dad82f046b3cec5d43e90066d1b07445a2"
|
||||
|
||||
[[package]]
|
||||
name = "js-sys"
|
||||
version = "0.3.70"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "1868808506b929d7b0cfa8f75951347aa71bb21144b7791bae35d9bccfcfe37a"
|
||||
dependencies = [
|
||||
"wasm-bindgen",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "lazy_static"
|
||||
version = "1.5.0"
|
||||
@@ -1037,7 +1242,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0c28191456debc98af6aa5f7db77872471983e9fa2a737b1c232b6ef543aed62"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"bincode",
|
||||
"bincode 1.3.3",
|
||||
"byteorder",
|
||||
"encoding_rs",
|
||||
"log",
|
||||
@@ -1065,7 +1270,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "bdf5f91725e32b9a21b1656baa7030766c9bafc4de4b4ddeb8ffdde7224dd2f6"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"bincode",
|
||||
"bincode 1.3.3",
|
||||
"byteorder",
|
||||
"lindera-cc-cedict-builder",
|
||||
"lindera-core",
|
||||
@@ -1085,7 +1290,7 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "e41f00ba7ac541b0ffd8c30e7a73f2dd197546cc5780462ec4f2e4782945a780"
|
||||
dependencies = [
|
||||
"anyhow",
|
||||
"bincode",
|
||||
"bincode 1.3.3",
|
||||
"byteorder",
|
||||
"csv",
|
||||
"derive_builder",
|
||||
@@ -1141,7 +1346,7 @@ version = "0.32.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "903e558981bcb6f59870aa7d6b4bcb09e8f7db778886a6a70f67fd74c9fa2ca3"
|
||||
dependencies = [
|
||||
"bincode",
|
||||
"bincode 1.3.3",
|
||||
"lindera-core",
|
||||
"lindera-dictionary",
|
||||
"once_cell",
|
||||
@@ -1257,7 +1462,7 @@ version = "1.0.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "80e04d1dcff3aae0704555fe5fee3bcfaf3d1fdf8a7e521d5b9d2b42acb52cec"
|
||||
dependencies = [
|
||||
"hermit-abi",
|
||||
"hermit-abi 0.3.9",
|
||||
"libc",
|
||||
"wasi",
|
||||
"windows-sys 0.52.0",
|
||||
@@ -1281,7 +1486,7 @@ checksum = "a7ce64b975ed4f123575d11afd9491f2e37bbd5813fbfbc0f09ae1fbddea74e0"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -1318,6 +1523,12 @@ dependencies = [
|
||||
"num-traits",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "num-conv"
|
||||
version = "0.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "51d515d32fb182ee37cda2ccdcb92950d6a3c2893aa280e540671c2cd0f3b1d9"
|
||||
|
||||
[[package]]
|
||||
name = "num-integer"
|
||||
version = "0.1.46"
|
||||
@@ -1342,7 +1553,7 @@ version = "1.16.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4161fcb6d602d4d2081af7c3a45852d875a03dd337a6bfdd6e06407b61342a43"
|
||||
dependencies = [
|
||||
"hermit-abi",
|
||||
"hermit-abi 0.3.9",
|
||||
"libc",
|
||||
]
|
||||
|
||||
@@ -1363,9 +1574,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "once_cell"
|
||||
version = "1.20.0"
|
||||
version = "1.20.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "33ea5043e58958ee56f3e15a90aee535795cd7dfd319846288d93c5b57d85cbe"
|
||||
checksum = "1261fe7e33c73b354eab43b1273a57c8f967d0391e80353e51f764ac02cf6775"
|
||||
|
||||
[[package]]
|
||||
name = "onig"
|
||||
@@ -1478,7 +1689,7 @@ dependencies = [
|
||||
"phf_shared",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -1507,7 +1718,7 @@ checksum = "2f38a4412a78282e09a2cf38d195ea5420d15ba0602cb375210efbc877243965"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -1543,6 +1754,12 @@ dependencies = [
|
||||
"portable-atomic",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "powerfmt"
|
||||
version = "0.2.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "439ee305def115ba05938db6eb1644ff94165c5ab5e9420d1c1bcedbba909391"
|
||||
|
||||
[[package]]
|
||||
name = "ppv-lite86"
|
||||
version = "0.2.20"
|
||||
@@ -1552,6 +1769,30 @@ dependencies = [
|
||||
"zerocopy",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro-error"
|
||||
version = "1.0.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "da25490ff9892aab3fcf7c36f08cfb902dd3e71ca0f9f9517bea02a73a5ce38c"
|
||||
dependencies = [
|
||||
"proc-macro-error-attr",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 1.0.109",
|
||||
"version_check",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro-error-attr"
|
||||
version = "1.0.4"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a1be40180e52ecc98ad80b184934baf3d0d29f979574e439af5a55274b35f869"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"version_check",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "proc-macro2"
|
||||
version = "1.0.86"
|
||||
@@ -1609,7 +1850,7 @@ dependencies = [
|
||||
"proc-macro2",
|
||||
"pyo3-macros-backend",
|
||||
"quote",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -1622,7 +1863,7 @@ dependencies = [
|
||||
"proc-macro2",
|
||||
"pyo3-build-config",
|
||||
"quote",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -1643,6 +1884,7 @@ dependencies = [
|
||||
"libc",
|
||||
"rand_chacha",
|
||||
"rand_core",
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -1662,6 +1904,17 @@ source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ec0be4795e2f6a28069bec0b5ff3e2ac9bafc99e6a9a7dc3547996c5c816922c"
|
||||
dependencies = [
|
||||
"getrandom",
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rand_xoshiro"
|
||||
version = "0.6.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "6f97cdb2a36ed4183de61b2f824cc45c9f1037f28afe0a322e9fff4c108b5aaa"
|
||||
dependencies = [
|
||||
"rand_core",
|
||||
"serde",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -1711,10 +1964,21 @@ dependencies = [
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "regex"
|
||||
version = "1.10.6"
|
||||
name = "redox_users"
|
||||
version = "0.4.6"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "4219d74c6b67a3654a9fbebc4b419e22126d13d2f3c4a07ee0cb61ff79a79619"
|
||||
checksum = "ba009ff324d1fc1b900bd1fdb31564febe58a8ccc8a6fdbb93b543d33b13ca43"
|
||||
dependencies = [
|
||||
"getrandom",
|
||||
"libredox",
|
||||
"thiserror",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "regex"
|
||||
version = "1.11.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "38200e5ee88914975b69f657f0801b6f6dccafd44fd9326302a4aaeecfacb1d8"
|
||||
dependencies = [
|
||||
"aho-corasick",
|
||||
"memchr",
|
||||
@@ -1724,9 +1988,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "regex-automata"
|
||||
version = "0.4.7"
|
||||
version = "0.4.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "38caf58cc5ef2fed281f89292ef23f6365465ed9a41b7a7754eb4e26496c92df"
|
||||
checksum = "368758f23274712b504848e9d5a6f010445cc8b87a7cdb4d7cbee666c1288da3"
|
||||
dependencies = [
|
||||
"aho-corasick",
|
||||
"memchr",
|
||||
@@ -1735,9 +1999,9 @@ dependencies = [
|
||||
|
||||
[[package]]
|
||||
name = "regex-syntax"
|
||||
version = "0.8.4"
|
||||
version = "0.8.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7a66a03ae7c801facd77a29370b4faec201768915ac14a721ba36f20bc9c209b"
|
||||
checksum = "2b15c43186be67a4fd63bee50d0303afffcef381492ebe2c5d87f324e1b8815c"
|
||||
|
||||
[[package]]
|
||||
name = "ring"
|
||||
@@ -1754,6 +2018,19 @@ dependencies = [
|
||||
"windows-sys 0.52.0",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rucrf"
|
||||
version = "0.3.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "640271497e95c3a3a9502740187b5fc3a19485cad172e7be9a2fd8d86ffc1c28"
|
||||
dependencies = [
|
||||
"argmin",
|
||||
"argmin-math",
|
||||
"bincode 2.0.0-rc.3",
|
||||
"crossbeam-channel",
|
||||
"hashbrown 0.12.3",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "rustc-demangle"
|
||||
version = "0.1.24"
|
||||
@@ -1829,6 +2106,8 @@ dependencies = [
|
||||
"sbv2_core",
|
||||
"serde",
|
||||
"tokio",
|
||||
"utoipa",
|
||||
"utoipa-scalar",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -1860,9 +2139,22 @@ dependencies = [
|
||||
"tar",
|
||||
"thiserror",
|
||||
"tokenizers",
|
||||
"vibrato",
|
||||
"zstd",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "sbv2_wasm"
|
||||
version = "0.1.0"
|
||||
dependencies = [
|
||||
"js-sys",
|
||||
"ndarray",
|
||||
"once_cell",
|
||||
"sbv2_core",
|
||||
"wasm-bindgen",
|
||||
"wasm-bindgen-futures",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "scopeguard"
|
||||
version = "1.2.0"
|
||||
@@ -1886,7 +2178,7 @@ checksum = "243902eda00fad750862fc144cea25caca5e20d615af0a81bee94ca738f1df1f"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -1955,6 +2247,49 @@ version = "0.3.11"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "38b58827f4464d87d377d175e90bf58eb00fd8716ff0a62f80356b5e61555d0d"
|
||||
|
||||
[[package]]
|
||||
name = "slog"
|
||||
version = "2.7.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8347046d4ebd943127157b94d63abb990fcf729dc4e9978927fdf4ac3c998d06"
|
||||
|
||||
[[package]]
|
||||
name = "slog-async"
|
||||
version = "2.8.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "72c8038f898a2c79507940990f05386455b3a317d8f18d4caea7cbc3d5096b84"
|
||||
dependencies = [
|
||||
"crossbeam-channel",
|
||||
"slog",
|
||||
"take_mut",
|
||||
"thread_local",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "slog-json"
|
||||
version = "2.6.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3e1e53f61af1e3c8b852eef0a9dee29008f55d6dd63794f3f12cef786cf0f219"
|
||||
dependencies = [
|
||||
"serde",
|
||||
"serde_json",
|
||||
"slog",
|
||||
"time",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "slog-term"
|
||||
version = "2.9.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b6e022d0b998abfe5c3782c1f03551a596269450ccd677ea51c56f8b214610e8"
|
||||
dependencies = [
|
||||
"is-terminal",
|
||||
"slog",
|
||||
"term",
|
||||
"thread_local",
|
||||
"time",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "smallvec"
|
||||
version = "1.13.2"
|
||||
@@ -2025,7 +2360,7 @@ dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"rustversion",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -2034,6 +2369,16 @@ version = "2.6.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "13c2bddecc57b384dee18652358fb23172facb8a2c51ccc10d74c157bdea3292"
|
||||
|
||||
[[package]]
|
||||
name = "syn"
|
||||
version = "1.0.109"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "72b64191b275b66ffe2469e8af2c1cfe3bafa67b529ead792a6d0160888b4237"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"unicode-ident",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "syn"
|
||||
version = "2.0.77"
|
||||
@@ -2057,6 +2402,12 @@ version = "1.0.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a7065abeca94b6a8a577f9bd45aa0867a2238b74e8eb67cf10d492bc39351394"
|
||||
|
||||
[[package]]
|
||||
name = "take_mut"
|
||||
version = "0.2.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "f764005d11ee5f36500a149ace24e00e3da98b0158b3e2d53a7495660d3f4d60"
|
||||
|
||||
[[package]]
|
||||
name = "tar"
|
||||
version = "0.4.42"
|
||||
@@ -2074,6 +2425,17 @@ version = "0.12.16"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "61c41af27dd6d1e27b1b16b489db798443478cef1f06a660c96db617ba5de3b1"
|
||||
|
||||
[[package]]
|
||||
name = "term"
|
||||
version = "0.7.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c59df8ac95d96ff9bede18eb7300b0fda5e5d8d90960e76f8e14ae765eedbf1f"
|
||||
dependencies = [
|
||||
"dirs-next",
|
||||
"rustversion",
|
||||
"winapi",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "thiserror"
|
||||
version = "1.0.64"
|
||||
@@ -2091,7 +2453,48 @@ checksum = "08904e7672f5eb876eaaf87e0ce17857500934f4981c4a0ab2b4aa98baac7fc3"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "thread_local"
|
||||
version = "1.1.8"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "8b9ef9bad013ada3808854ceac7b46812a6465ba368859a37e2100283d2d719c"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"once_cell",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "time"
|
||||
version = "0.3.36"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "5dfd88e563464686c916c7e46e623e520ddc6d79fa6641390f2e3fa86e83e885"
|
||||
dependencies = [
|
||||
"deranged",
|
||||
"itoa",
|
||||
"num-conv",
|
||||
"powerfmt",
|
||||
"serde",
|
||||
"time-core",
|
||||
"time-macros",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "time-core"
|
||||
version = "0.1.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "ef927ca75afb808a4d64dd374f00a2adf8d0fcff8e7b184af886c3c87ec4a3f3"
|
||||
|
||||
[[package]]
|
||||
name = "time-macros"
|
||||
version = "0.2.18"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "3f252a68540fde3a3877aeea552b832b40ab9a69e318efd078774a01ddee1ccf"
|
||||
dependencies = [
|
||||
"num-conv",
|
||||
"time-core",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -2118,6 +2521,7 @@ dependencies = [
|
||||
"aho-corasick",
|
||||
"derive_builder",
|
||||
"esaxx-rs",
|
||||
"fancy-regex",
|
||||
"getrandom",
|
||||
"indicatif",
|
||||
"itertools 0.12.1",
|
||||
@@ -2167,7 +2571,7 @@ checksum = "693d596312e88961bc67d7f1f97af8a70227d9f90c31bba5806eec004978d752"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
@@ -2332,18 +2736,152 @@ version = "0.2.2"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "06abde3611657adf66d383f00b093d7faecc7fa57071cce2578660c9f1010821"
|
||||
|
||||
[[package]]
|
||||
name = "utoipa"
|
||||
version = "4.2.3"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c5afb1a60e207dca502682537fefcfd9921e71d0b83e9576060f09abc6efab23"
|
||||
dependencies = [
|
||||
"indexmap",
|
||||
"serde",
|
||||
"serde_json",
|
||||
"utoipa-gen",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "utoipa-gen"
|
||||
version = "4.3.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "7bf0e16c02bc4bf5322ab65f10ab1149bdbcaa782cba66dc7057370a3f8190be"
|
||||
dependencies = [
|
||||
"proc-macro-error",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"regex",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "utoipa-scalar"
|
||||
version = "0.1.0"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "b3ab4b7269d14d93626b0bfedf212f1b0995cb7d13d35daba21d579511e7fae8"
|
||||
dependencies = [
|
||||
"axum",
|
||||
"serde",
|
||||
"serde_json",
|
||||
"utoipa",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "version_check"
|
||||
version = "0.9.5"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "0b928f33d975fc6ad9f86c8f283853ad26bdd5b10b7f1542aa2fa15e2289105a"
|
||||
|
||||
[[package]]
|
||||
name = "vibrato"
|
||||
version = "0.5.1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "df95d99b268877738d8f644c38604c4c9c09950219b1d1a725ada94d62e98722"
|
||||
dependencies = [
|
||||
"bincode 2.0.0-rc.3",
|
||||
"crawdad",
|
||||
"csv-core",
|
||||
"hashbrown 0.12.3",
|
||||
"regex",
|
||||
"rucrf",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "virtue"
|
||||
version = "0.0.13"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9dcc60c0624df774c82a0ef104151231d37da4962957d691c011c852b2473314"
|
||||
|
||||
[[package]]
|
||||
name = "wasi"
|
||||
version = "0.11.0+wasi-snapshot-preview1"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9c8d87e72b64a3b4db28d11ce29237c246188f4f51057d65a7eab63b7987e423"
|
||||
|
||||
[[package]]
|
||||
name = "wasm-bindgen"
|
||||
version = "0.2.93"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "a82edfc16a6c469f5f44dc7b571814045d60404b55a0ee849f9bcfa2e63dd9b5"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"once_cell",
|
||||
"wasm-bindgen-macro",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "wasm-bindgen-backend"
|
||||
version = "0.2.93"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "9de396da306523044d3302746f1208fa71d7532227f15e347e2d93e4145dd77b"
|
||||
dependencies = [
|
||||
"bumpalo",
|
||||
"log",
|
||||
"once_cell",
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 2.0.77",
|
||||
"wasm-bindgen-shared",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "wasm-bindgen-futures"
|
||||
version = "0.4.43"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "61e9300f63a621e96ed275155c108eb6f843b6a26d053f122ab69724559dc8ed"
|
||||
dependencies = [
|
||||
"cfg-if",
|
||||
"js-sys",
|
||||
"wasm-bindgen",
|
||||
"web-sys",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "wasm-bindgen-macro"
|
||||
version = "0.2.93"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "585c4c91a46b072c92e908d99cb1dcdf95c5218eeb6f3bf1efa991ee7a68cccf"
|
||||
dependencies = [
|
||||
"quote",
|
||||
"wasm-bindgen-macro-support",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "wasm-bindgen-macro-support"
|
||||
version = "0.2.93"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "afc340c74d9005395cf9dd098506f7f44e38f2b4a21c6aaacf9a105ea5e1e836"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn 2.0.77",
|
||||
"wasm-bindgen-backend",
|
||||
"wasm-bindgen-shared",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "wasm-bindgen-shared"
|
||||
version = "0.2.93"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "c62a0a307cb4a311d3a07867860911ca130c3494e8c2719593806c08bc5d0484"
|
||||
|
||||
[[package]]
|
||||
name = "web-sys"
|
||||
version = "0.3.70"
|
||||
source = "registry+https://github.com/rust-lang/crates.io-index"
|
||||
checksum = "26fdeaafd9bd129f65e7c031593c24d62186301e0c72c8978fa1678be7d532c0"
|
||||
dependencies = [
|
||||
"js-sys",
|
||||
"wasm-bindgen",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
name = "webpki-roots"
|
||||
version = "0.26.5"
|
||||
@@ -2492,7 +3030,7 @@ checksum = "fa4f8080344d4671fb4e831a13ad1e68092748387dfc4f55e356242fae12ce3e"
|
||||
dependencies = [
|
||||
"proc-macro2",
|
||||
"quote",
|
||||
"syn",
|
||||
"syn 2.0.77",
|
||||
]
|
||||
|
||||
[[package]]
|
||||
|
||||
@@ -1,14 +1,15 @@
|
||||
[workspace]
|
||||
resolver = "2"
|
||||
members = ["sbv2_api", "sbv2_core", "sbv2_bindings"]
|
||||
members = ["sbv2_api", "sbv2_core", "sbv2_bindings", "sbv2_wasm"]
|
||||
|
||||
[workspace.dependencies]
|
||||
anyhow = "1.0.86"
|
||||
dotenvy = "0.15.7"
|
||||
env_logger = "0.11.5"
|
||||
ndarray = "0.16.1"
|
||||
once_cell = "1.19.0"
|
||||
|
||||
[profile.release]
|
||||
lto = true
|
||||
debug = false
|
||||
strip = true
|
||||
strip = true
|
||||
|
||||
@@ -31,6 +31,7 @@ JP-Extra しか対応していません。(基本的に対応する予定もあ
|
||||
- [x] GPU 対応(CoreML)
|
||||
- [ ] WASM 変換(依存ライブラリの関係により現在は不可)
|
||||
- [x] arm64のdockerサポート
|
||||
- [ ] MeCabを利用する
|
||||
|
||||
## 構造説明
|
||||
|
||||
|
||||
@@ -12,6 +12,8 @@ log = "0.4.22"
|
||||
sbv2_core = { version = "0.2.0-alpha", path = "../sbv2_core" }
|
||||
serde = { version = "1.0.210", features = ["derive"] }
|
||||
tokio = { version = "1.40.0", features = ["full"] }
|
||||
utoipa = { version = "4.2.3", features = ["axum_extras"] }
|
||||
utoipa-scalar = { version = "0.1.0", features = ["axum"] }
|
||||
|
||||
[features]
|
||||
coreml = ["sbv2_core/coreml"]
|
||||
@@ -19,4 +21,4 @@ cuda = ["sbv2_core/cuda"]
|
||||
cuda_tf32 = ["sbv2_core/cuda_tf32"]
|
||||
dynamic = ["sbv2_core/dynamic"]
|
||||
directml = ["sbv2_core/directml"]
|
||||
tensorrt = ["sbv2_core/tensorrt"]
|
||||
tensorrt = ["sbv2_core/tensorrt"]
|
||||
|
||||
@@ -11,10 +11,23 @@ use std::env;
|
||||
use std::sync::Arc;
|
||||
use tokio::fs;
|
||||
use tokio::sync::Mutex;
|
||||
use utoipa::{OpenApi, ToSchema};
|
||||
use utoipa_scalar::{Scalar, Servable};
|
||||
|
||||
mod error;
|
||||
use crate::error::AppResult;
|
||||
|
||||
#[derive(OpenApi)]
|
||||
#[openapi(paths(models, synthesize), components(schemas(SynthesizeRequest)))]
|
||||
struct ApiDoc;
|
||||
|
||||
#[utoipa::path(
|
||||
get,
|
||||
path = "/models",
|
||||
responses(
|
||||
(status = 200, description = "Return model list", body = Vec<String>),
|
||||
)
|
||||
)]
|
||||
async fn models(State(state): State<AppState>) -> AppResult<impl IntoResponse> {
|
||||
Ok(Json(state.tts_model.lock().await.models()))
|
||||
}
|
||||
@@ -27,7 +40,7 @@ fn length_default() -> f32 {
|
||||
1.0
|
||||
}
|
||||
|
||||
#[derive(Deserialize)]
|
||||
#[derive(Deserialize, ToSchema)]
|
||||
struct SynthesizeRequest {
|
||||
text: String,
|
||||
ident: String,
|
||||
@@ -37,6 +50,14 @@ struct SynthesizeRequest {
|
||||
length_scale: f32,
|
||||
}
|
||||
|
||||
#[utoipa::path(
|
||||
post,
|
||||
path = "/synthesize",
|
||||
request_body = SynthesizeRequest,
|
||||
responses(
|
||||
(status = 200, description = "Return audio/wav", body = Vec<u8>, content_type = "audio/wav")
|
||||
)
|
||||
)]
|
||||
async fn synthesize(
|
||||
State(state): State<AppState>,
|
||||
Json(SynthesizeRequest {
|
||||
@@ -139,7 +160,8 @@ async fn main() -> anyhow::Result<()> {
|
||||
.route("/", get(|| async { "Hello, World!" }))
|
||||
.route("/synthesize", post(synthesize))
|
||||
.route("/models", get(models))
|
||||
.with_state(AppState::new().await?);
|
||||
.with_state(AppState::new().await?)
|
||||
.merge(Scalar::with_url("/docs", ApiDoc::openapi()));
|
||||
let addr = env::var("ADDR").unwrap_or("0.0.0.0:3000".to_string());
|
||||
let listener = tokio::net::TcpListener::bind(&addr).await?;
|
||||
log::info!("Listening on {addr}");
|
||||
|
||||
@@ -16,20 +16,25 @@ hound = "3.5.1"
|
||||
jpreprocess = { version = "0.10.0", features = ["naist-jdic"] }
|
||||
ndarray.workspace = true
|
||||
num_cpus = "1.16.0"
|
||||
once_cell = "1.19.0"
|
||||
ort = { git = "https://github.com/pykeio/ort.git", version = "2.0.0-rc.6" }
|
||||
once_cell.workspace = true
|
||||
ort = { git = "https://github.com/pykeio/ort.git", version = "2.0.0-rc.6", optional = true }
|
||||
regex = "1.10.6"
|
||||
serde = { version = "1.0.210", features = ["derive"] }
|
||||
serde_json = "1.0.128"
|
||||
tar = "0.4.41"
|
||||
thiserror = "1.0.63"
|
||||
tokenizers = "0.20.0"
|
||||
tokenizers = { version = "0.20.0", default-features = false }
|
||||
vibrato = { version = "0.5.1", optional = true }
|
||||
zstd = "0.13.2"
|
||||
|
||||
[features]
|
||||
cuda = ["ort/cuda"]
|
||||
cuda_tf32 = []
|
||||
dynamic = ["ort/load-dynamic"]
|
||||
directml = ["ort/directml"]
|
||||
tensorrt = ["ort/tensorrt"]
|
||||
coreml = ["ort/coreml"]
|
||||
cuda = ["ort/cuda", "std"]
|
||||
cuda_tf32 = ["std", "cuda"]
|
||||
std = ["dep:ort", "tokenizers/progressbar", "tokenizers/onig", "tokenizers/esaxx_fast"]
|
||||
dynamic = ["ort/load-dynamic", "std"]
|
||||
directml = ["ort/directml", "std"]
|
||||
tensorrt = ["ort/tensorrt", "std"]
|
||||
coreml = ["ort/coreml", "std"]
|
||||
default = ["std"]
|
||||
no_std = ["tokenizers/unstable_wasm"]
|
||||
mecab = ["vibrato"]
|
||||
|
||||
@@ -6,6 +6,7 @@ pub enum Error {
|
||||
TokenizerError(#[from] tokenizers::Error),
|
||||
#[error("JPreprocess error: {0}")]
|
||||
JPreprocessError(#[from] jpreprocess::error::JPreprocessError),
|
||||
#[cfg(feature = "std")]
|
||||
#[error("ONNX error: {0}")]
|
||||
OrtError(#[from] ort::Error),
|
||||
#[error("NDArray error: {0}")]
|
||||
@@ -20,6 +21,8 @@ pub enum Error {
|
||||
HoundError(#[from] hound::Error),
|
||||
#[error("model not found error")]
|
||||
ModelNotFoundError(String),
|
||||
#[error("other")]
|
||||
OtherError(String),
|
||||
}
|
||||
|
||||
pub type Result<T> = std::result::Result<T, Error>;
|
||||
|
||||
@@ -1,11 +1,19 @@
|
||||
#[cfg(feature = "std")]
|
||||
pub mod bert;
|
||||
pub mod error;
|
||||
pub mod jtalk;
|
||||
#[cfg(feature = "std")]
|
||||
pub mod model;
|
||||
pub mod mora;
|
||||
pub mod nlp;
|
||||
pub mod norm;
|
||||
pub mod sbv2file;
|
||||
pub mod style;
|
||||
pub mod tokenizer;
|
||||
#[cfg(feature = "std")]
|
||||
pub mod tts;
|
||||
pub mod tts_util;
|
||||
pub mod utils;
|
||||
|
||||
#[cfg(feature = "mecab")]
|
||||
pub mod mecab;
|
||||
@@ -1,9 +1,9 @@
|
||||
use std::env;
|
||||
use std::fs;
|
||||
|
||||
use sbv2_core::tts;
|
||||
use std::env;
|
||||
|
||||
fn main() -> anyhow::Result<()> {
|
||||
#[cfg(feature = "std")]
|
||||
fn main_inner() -> anyhow::Result<()> {
|
||||
use sbv2_core::tts;
|
||||
dotenvy::dotenv_override().ok();
|
||||
env_logger::init();
|
||||
let text = fs::read_to_string("content.txt")?;
|
||||
@@ -19,3 +19,13 @@ fn main() -> anyhow::Result<()> {
|
||||
|
||||
Ok(())
|
||||
}
|
||||
#[cfg(not(feature = "std"))]
|
||||
fn main_inner() -> anyhow::Result<()> {
|
||||
Ok(())
|
||||
}
|
||||
|
||||
fn main() {
|
||||
if let Err(e) = main_inner() {
|
||||
println!("Error: {e}");
|
||||
}
|
||||
}
|
||||
|
||||
0
sbv2_core/src/mecab.rs
Normal file
0
sbv2_core/src/mecab.rs
Normal file
37
sbv2_core/src/sbv2file.rs
Normal file
37
sbv2_core/src/sbv2file.rs
Normal file
@@ -0,0 +1,37 @@
|
||||
use std::io::{Cursor, Read};
|
||||
|
||||
use tar::Archive;
|
||||
use zstd::decode_all;
|
||||
|
||||
use crate::error::{Error, Result};
|
||||
|
||||
/// Parse a .sbv2 file binary
|
||||
///
|
||||
/// # Examples
|
||||
///
|
||||
/// ```rs
|
||||
/// parse_sbv2file("tsukuyomi", std::fs::read("tsukuyomi.sbv2")?)?;
|
||||
/// ```
|
||||
pub fn parse_sbv2file<P: AsRef<[u8]>>(sbv2_bytes: P) -> Result<(Vec<u8>, Vec<u8>)> {
|
||||
let mut arc = Archive::new(Cursor::new(decode_all(Cursor::new(sbv2_bytes.as_ref()))?));
|
||||
let mut vits2 = None;
|
||||
let mut style_vectors = None;
|
||||
let mut et = arc.entries()?;
|
||||
while let Some(Ok(mut e)) = et.next() {
|
||||
let pth = String::from_utf8_lossy(&e.path_bytes()).to_string();
|
||||
let mut b = Vec::with_capacity(e.size() as usize);
|
||||
e.read_to_end(&mut b)?;
|
||||
match pth.as_str() {
|
||||
"model.onnx" => vits2 = Some(b),
|
||||
"style_vectors.json" => style_vectors = Some(b),
|
||||
_ => continue,
|
||||
}
|
||||
}
|
||||
if style_vectors.is_none() {
|
||||
return Err(Error::ModelNotFoundError("style_vectors".to_string()));
|
||||
}
|
||||
if vits2.is_none() {
|
||||
return Err(Error::ModelNotFoundError("vits2".to_string()));
|
||||
}
|
||||
Ok((style_vectors.unwrap(), vits2.unwrap()))
|
||||
}
|
||||
@@ -1,5 +1,5 @@
|
||||
use crate::error::Result;
|
||||
use tokenizers::Tokenizer;
|
||||
pub use tokenizers::Tokenizer;
|
||||
|
||||
pub fn get_tokenizer<P: AsRef<[u8]>>(p: P) -> Result<Tokenizer> {
|
||||
let tokenizer = Tokenizer::from_bytes(p)?;
|
||||
|
||||
@@ -1,12 +1,8 @@
|
||||
use crate::error::{Error, Result};
|
||||
use crate::{bert, jtalk, model, nlp, norm, style, tokenizer, utils};
|
||||
use hound::{SampleFormat, WavSpec, WavWriter};
|
||||
use ndarray::{concatenate, s, Array, Array1, Array2, Array3, Axis};
|
||||
use crate::{jtalk, model, style, tokenizer, tts_util};
|
||||
use ndarray::{concatenate, Array1, Array2, Array3, Axis};
|
||||
use ort::Session;
|
||||
use std::io::{Cursor, Read};
|
||||
use tar::Archive;
|
||||
use tokenizers::Tokenizer;
|
||||
use zstd::decode_all;
|
||||
|
||||
#[derive(PartialEq, Eq, Clone)]
|
||||
pub struct TTSIdent(String);
|
||||
@@ -78,27 +74,8 @@ impl TTSModelHolder {
|
||||
ident: I,
|
||||
sbv2_bytes: P,
|
||||
) -> Result<()> {
|
||||
let mut arc = Archive::new(Cursor::new(decode_all(Cursor::new(sbv2_bytes.as_ref()))?));
|
||||
let mut vits2 = None;
|
||||
let mut style_vectors = None;
|
||||
let mut et = arc.entries()?;
|
||||
while let Some(Ok(mut e)) = et.next() {
|
||||
let pth = String::from_utf8_lossy(&e.path_bytes()).to_string();
|
||||
let mut b = Vec::with_capacity(e.size() as usize);
|
||||
e.read_to_end(&mut b)?;
|
||||
match pth.as_str() {
|
||||
"model.onnx" => vits2 = Some(b),
|
||||
"style_vectors.json" => style_vectors = Some(b),
|
||||
_ => continue,
|
||||
}
|
||||
}
|
||||
if style_vectors.is_none() {
|
||||
return Err(Error::ModelNotFoundError("style_vectors".to_string()));
|
||||
}
|
||||
if vits2.is_none() {
|
||||
return Err(Error::ModelNotFoundError("vits2".to_string()));
|
||||
}
|
||||
self.load(ident, style_vectors.unwrap(), vits2.unwrap())?;
|
||||
let (style_vectors, vits2) = crate::sbv2file::parse_sbv2file(sbv2_bytes)?;
|
||||
self.load(ident, style_vectors, vits2)?;
|
||||
Ok(())
|
||||
}
|
||||
|
||||
@@ -151,69 +128,14 @@ impl TTSModelHolder {
|
||||
&self,
|
||||
text: &str,
|
||||
) -> Result<(Array2<f32>, Array1<i64>, Array1<i64>, Array1<i64>)> {
|
||||
let text = self.jtalk.num2word(text)?;
|
||||
let normalized_text = norm::normalize_text(&text);
|
||||
|
||||
let process = self.jtalk.process_text(&normalized_text)?;
|
||||
let (phones, tones, mut word2ph) = process.g2p()?;
|
||||
let (phones, tones, lang_ids) = nlp::cleaned_text_to_sequence(phones, tones);
|
||||
|
||||
let phones = utils::intersperse(&phones, 0);
|
||||
let tones = utils::intersperse(&tones, 0);
|
||||
let lang_ids = utils::intersperse(&lang_ids, 0);
|
||||
for item in &mut word2ph {
|
||||
*item *= 2;
|
||||
}
|
||||
word2ph[0] += 1;
|
||||
|
||||
let text = {
|
||||
let (seq_text, _) = process.text_to_seq_kata()?;
|
||||
seq_text.join("")
|
||||
};
|
||||
let (token_ids, attention_masks) = tokenizer::tokenize(&text, &self.tokenizer)?;
|
||||
|
||||
let bert_content = bert::predict(&self.bert, token_ids, attention_masks)?;
|
||||
|
||||
assert!(
|
||||
word2ph.len() == text.chars().count() + 2,
|
||||
"{} {}",
|
||||
word2ph.len(),
|
||||
normalized_text.chars().count()
|
||||
);
|
||||
|
||||
let mut phone_level_feature = vec![];
|
||||
for (i, reps) in word2ph.iter().enumerate() {
|
||||
let repeat_feature = {
|
||||
let (reps_rows, reps_cols) = (*reps, 1);
|
||||
let arr_len = bert_content.slice(s![i, ..]).len();
|
||||
|
||||
let mut results: Array2<f32> =
|
||||
Array::zeros((reps_rows as usize, arr_len * reps_cols));
|
||||
|
||||
for j in 0..reps_rows {
|
||||
for k in 0..reps_cols {
|
||||
let mut view = results.slice_mut(s![j, k * arr_len..(k + 1) * arr_len]);
|
||||
view.assign(&bert_content.slice(s![i, ..]));
|
||||
}
|
||||
}
|
||||
results
|
||||
};
|
||||
phone_level_feature.push(repeat_feature);
|
||||
}
|
||||
let phone_level_feature = concatenate(
|
||||
Axis(0),
|
||||
&phone_level_feature
|
||||
.iter()
|
||||
.map(|x| x.view())
|
||||
.collect::<Vec<_>>(),
|
||||
)?;
|
||||
let bert_ori = phone_level_feature.t();
|
||||
Ok((
|
||||
bert_ori.to_owned(),
|
||||
phones.into(),
|
||||
tones.into(),
|
||||
lang_ids.into(),
|
||||
))
|
||||
crate::tts_util::parse_text_blocking(
|
||||
text,
|
||||
&self.jtalk,
|
||||
&self.tokenizer,
|
||||
|token_ids, attention_masks| {
|
||||
crate::bert::predict(&self.bert, token_ids, attention_masks)
|
||||
},
|
||||
)
|
||||
}
|
||||
|
||||
fn find_model<I: Into<TTSIdent>>(&self, ident: I) -> Result<&TTSModel> {
|
||||
@@ -292,26 +214,7 @@ impl TTSModelHolder {
|
||||
options.length_scale,
|
||||
)?
|
||||
};
|
||||
Self::array_to_vec(audio_array)
|
||||
}
|
||||
|
||||
fn array_to_vec(audio_array: Array3<f32>) -> Result<Vec<u8>> {
|
||||
let spec = WavSpec {
|
||||
channels: 1,
|
||||
sample_rate: 44100,
|
||||
bits_per_sample: 32,
|
||||
sample_format: SampleFormat::Float,
|
||||
};
|
||||
let mut cursor = Cursor::new(Vec::new());
|
||||
let mut writer = WavWriter::new(&mut cursor, spec)?;
|
||||
for i in 0..audio_array.shape()[0] {
|
||||
let output = audio_array.slice(s![i, 0, ..]).to_vec();
|
||||
for sample in output {
|
||||
writer.write_sample(sample)?;
|
||||
}
|
||||
}
|
||||
writer.finalize()?;
|
||||
Ok(cursor.into_inner())
|
||||
tts_util::array_to_vec(audio_array)
|
||||
}
|
||||
|
||||
/// Synthesize text to audio
|
||||
@@ -340,7 +243,7 @@ impl TTSModelHolder {
|
||||
sdp_ratio,
|
||||
length_scale,
|
||||
)?;
|
||||
Self::array_to_vec(audio_array)
|
||||
tts_util::array_to_vec(audio_array)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
180
sbv2_core/src/tts_util.rs
Normal file
180
sbv2_core/src/tts_util.rs
Normal file
@@ -0,0 +1,180 @@
|
||||
use std::io::Cursor;
|
||||
|
||||
use crate::error::Result;
|
||||
use crate::{jtalk, nlp, norm, tokenizer, utils};
|
||||
use hound::{SampleFormat, WavSpec, WavWriter};
|
||||
use ndarray::{concatenate, s, Array, Array1, Array2, Array3, Axis};
|
||||
use tokenizers::Tokenizer;
|
||||
/// Parse text and return the input for synthesize
|
||||
///
|
||||
/// # Note
|
||||
/// This function is for low-level usage, use `easy_synthesize` for high-level usage.
|
||||
#[allow(clippy::type_complexity)]
|
||||
pub async fn parse_text(
|
||||
text: &str,
|
||||
jtalk: &jtalk::JTalk,
|
||||
tokenizer: &Tokenizer,
|
||||
bert_predict: impl FnOnce(
|
||||
Vec<i64>,
|
||||
Vec<i64>,
|
||||
) -> std::pin::Pin<
|
||||
Box<dyn std::future::Future<Output = Result<ndarray::Array2<f32>>>>,
|
||||
>,
|
||||
) -> Result<(Array2<f32>, Array1<i64>, Array1<i64>, Array1<i64>)> {
|
||||
let text = jtalk.num2word(text)?;
|
||||
let normalized_text = norm::normalize_text(&text);
|
||||
|
||||
let process = jtalk.process_text(&normalized_text)?;
|
||||
let (phones, tones, mut word2ph) = process.g2p()?;
|
||||
let (phones, tones, lang_ids) = nlp::cleaned_text_to_sequence(phones, tones);
|
||||
|
||||
let phones = utils::intersperse(&phones, 0);
|
||||
let tones = utils::intersperse(&tones, 0);
|
||||
let lang_ids = utils::intersperse(&lang_ids, 0);
|
||||
for item in &mut word2ph {
|
||||
*item *= 2;
|
||||
}
|
||||
word2ph[0] += 1;
|
||||
|
||||
let text = {
|
||||
let (seq_text, _) = process.text_to_seq_kata()?;
|
||||
seq_text.join("")
|
||||
};
|
||||
let (token_ids, attention_masks) = tokenizer::tokenize(&text, tokenizer)?;
|
||||
|
||||
let bert_content = bert_predict(token_ids, attention_masks).await?;
|
||||
|
||||
assert!(
|
||||
word2ph.len() == text.chars().count() + 2,
|
||||
"{} {}",
|
||||
word2ph.len(),
|
||||
normalized_text.chars().count()
|
||||
);
|
||||
|
||||
let mut phone_level_feature = vec![];
|
||||
for (i, reps) in word2ph.iter().enumerate() {
|
||||
let repeat_feature = {
|
||||
let (reps_rows, reps_cols) = (*reps, 1);
|
||||
let arr_len = bert_content.slice(s![i, ..]).len();
|
||||
|
||||
let mut results: Array2<f32> = Array::zeros((reps_rows as usize, arr_len * reps_cols));
|
||||
|
||||
for j in 0..reps_rows {
|
||||
for k in 0..reps_cols {
|
||||
let mut view = results.slice_mut(s![j, k * arr_len..(k + 1) * arr_len]);
|
||||
view.assign(&bert_content.slice(s![i, ..]));
|
||||
}
|
||||
}
|
||||
results
|
||||
};
|
||||
phone_level_feature.push(repeat_feature);
|
||||
}
|
||||
let phone_level_feature = concatenate(
|
||||
Axis(0),
|
||||
&phone_level_feature
|
||||
.iter()
|
||||
.map(|x| x.view())
|
||||
.collect::<Vec<_>>(),
|
||||
)?;
|
||||
let bert_ori = phone_level_feature.t();
|
||||
Ok((
|
||||
bert_ori.to_owned(),
|
||||
phones.into(),
|
||||
tones.into(),
|
||||
lang_ids.into(),
|
||||
))
|
||||
}
|
||||
|
||||
/// Parse text and return the input for synthesize
|
||||
///
|
||||
/// # Note
|
||||
/// This function is for low-level usage, use `easy_synthesize` for high-level usage.
|
||||
#[allow(clippy::type_complexity)]
|
||||
pub fn parse_text_blocking(
|
||||
text: &str,
|
||||
jtalk: &jtalk::JTalk,
|
||||
tokenizer: &Tokenizer,
|
||||
bert_predict: impl FnOnce(Vec<i64>, Vec<i64>) -> Result<ndarray::Array2<f32>>,
|
||||
) -> Result<(Array2<f32>, Array1<i64>, Array1<i64>, Array1<i64>)> {
|
||||
let text = jtalk.num2word(text)?;
|
||||
let normalized_text = norm::normalize_text(&text);
|
||||
|
||||
let process = jtalk.process_text(&normalized_text)?;
|
||||
let (phones, tones, mut word2ph) = process.g2p()?;
|
||||
let (phones, tones, lang_ids) = nlp::cleaned_text_to_sequence(phones, tones);
|
||||
|
||||
let phones = utils::intersperse(&phones, 0);
|
||||
let tones = utils::intersperse(&tones, 0);
|
||||
let lang_ids = utils::intersperse(&lang_ids, 0);
|
||||
for item in &mut word2ph {
|
||||
*item *= 2;
|
||||
}
|
||||
word2ph[0] += 1;
|
||||
|
||||
let text = {
|
||||
let (seq_text, _) = process.text_to_seq_kata()?;
|
||||
seq_text.join("")
|
||||
};
|
||||
let (token_ids, attention_masks) = tokenizer::tokenize(&text, tokenizer)?;
|
||||
|
||||
let bert_content = bert_predict(token_ids, attention_masks)?;
|
||||
|
||||
assert!(
|
||||
word2ph.len() == text.chars().count() + 2,
|
||||
"{} {}",
|
||||
word2ph.len(),
|
||||
normalized_text.chars().count()
|
||||
);
|
||||
|
||||
let mut phone_level_feature = vec![];
|
||||
for (i, reps) in word2ph.iter().enumerate() {
|
||||
let repeat_feature = {
|
||||
let (reps_rows, reps_cols) = (*reps, 1);
|
||||
let arr_len = bert_content.slice(s![i, ..]).len();
|
||||
|
||||
let mut results: Array2<f32> = Array::zeros((reps_rows as usize, arr_len * reps_cols));
|
||||
|
||||
for j in 0..reps_rows {
|
||||
for k in 0..reps_cols {
|
||||
let mut view = results.slice_mut(s![j, k * arr_len..(k + 1) * arr_len]);
|
||||
view.assign(&bert_content.slice(s![i, ..]));
|
||||
}
|
||||
}
|
||||
results
|
||||
};
|
||||
phone_level_feature.push(repeat_feature);
|
||||
}
|
||||
let phone_level_feature = concatenate(
|
||||
Axis(0),
|
||||
&phone_level_feature
|
||||
.iter()
|
||||
.map(|x| x.view())
|
||||
.collect::<Vec<_>>(),
|
||||
)?;
|
||||
let bert_ori = phone_level_feature.t();
|
||||
Ok((
|
||||
bert_ori.to_owned(),
|
||||
phones.into(),
|
||||
tones.into(),
|
||||
lang_ids.into(),
|
||||
))
|
||||
}
|
||||
|
||||
pub fn array_to_vec(audio_array: Array3<f32>) -> Result<Vec<u8>> {
|
||||
let spec = WavSpec {
|
||||
channels: 1,
|
||||
sample_rate: 44100,
|
||||
bits_per_sample: 32,
|
||||
sample_format: SampleFormat::Float,
|
||||
};
|
||||
let mut cursor = Cursor::new(Vec::new());
|
||||
let mut writer = WavWriter::new(&mut cursor, spec)?;
|
||||
for i in 0..audio_array.shape()[0] {
|
||||
let output = audio_array.slice(s![i, 0, ..]).to_vec();
|
||||
for sample in output {
|
||||
writer.write_sample(sample)?;
|
||||
}
|
||||
}
|
||||
writer.finalize()?;
|
||||
Ok(cursor.into_inner())
|
||||
}
|
||||
19
sbv2_wasm/Cargo.toml
Normal file
19
sbv2_wasm/Cargo.toml
Normal file
@@ -0,0 +1,19 @@
|
||||
[package]
|
||||
name = "sbv2_wasm"
|
||||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
|
||||
[lib]
|
||||
crate-type = ["cdylib", "rlib"]
|
||||
|
||||
[dependencies]
|
||||
wasm-bindgen = "0.2.93"
|
||||
sbv2_core = { path = "../sbv2_core", default-features = false, features = ["no_std"] }
|
||||
once_cell.workspace = true
|
||||
js-sys = "0.3.70"
|
||||
ndarray.workspace = true
|
||||
wasm-bindgen-futures = "0.4.43"
|
||||
|
||||
[profile.release]
|
||||
lto = true
|
||||
opt-level = "s"
|
||||
2
sbv2_wasm/README.md
Normal file
2
sbv2_wasm/README.md
Normal file
@@ -0,0 +1,2 @@
|
||||
# StyleBertVITS2 wasm
|
||||
refer to https://github.com/tuna2134/sbv2-api
|
||||
31
sbv2_wasm/biome.json
Normal file
31
sbv2_wasm/biome.json
Normal file
@@ -0,0 +1,31 @@
|
||||
{
|
||||
"$schema": "https://biomejs.dev/schemas/1.9.2/schema.json",
|
||||
"vcs": {
|
||||
"enabled": false,
|
||||
"clientKind": "git",
|
||||
"useIgnoreFile": false
|
||||
},
|
||||
"files": {
|
||||
"ignoreUnknown": false,
|
||||
"ignore": []
|
||||
},
|
||||
"formatter": {
|
||||
"enabled": true,
|
||||
"indentStyle": "tab",
|
||||
"ignore": ["dist/", "pkg/"]
|
||||
},
|
||||
"organizeImports": {
|
||||
"enabled": true
|
||||
},
|
||||
"linter": {
|
||||
"enabled": true,
|
||||
"rules": {
|
||||
"recommended": true
|
||||
}
|
||||
},
|
||||
"javascript": {
|
||||
"formatter": {
|
||||
"quoteStyle": "double"
|
||||
}
|
||||
}
|
||||
}
|
||||
4
sbv2_wasm/build.sh
Executable file
4
sbv2_wasm/build.sh
Executable file
@@ -0,0 +1,4 @@
|
||||
wasm-pack build --target web sbv2_wasm
|
||||
wasm-opt -O3 -o sbv2_wasm/pkg/sbv2_wasm_bg.wasm sbv2_wasm/pkg/sbv2_wasm_bg.wasm
|
||||
mkdir -p sbv2_wasm/dist
|
||||
cp sbv2_wasm/sbv2_wasm/pkg/sbv2_wasm_bg.wasm sbv2_wasm/dist/sbv2_wasm_bg.wasm
|
||||
51
sbv2_wasm/example.html
Normal file
51
sbv2_wasm/example.html
Normal file
@@ -0,0 +1,51 @@
|
||||
<!doctype html>
|
||||
<html lang="en">
|
||||
|
||||
<head>
|
||||
<meta charset="UTF-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>Style Bert VITS2 Web</title>
|
||||
<script type="importmap">
|
||||
{
|
||||
"imports": {
|
||||
"onnxruntime-web": "https://cdn.jsdelivr.net/npm/onnxruntime-web@1.19.2/dist/ort.all.min.mjs",
|
||||
"sbv2": "https://cdn.jsdelivr.net/npm/sbv2@0.1.1+esm"
|
||||
}
|
||||
}
|
||||
</script>
|
||||
<script type="module" async defer>
|
||||
import { ModelHolder } from "sbv2";
|
||||
await ModelHolder.globalInit(
|
||||
await (
|
||||
await fetch("https://esm.sh/sbv2@0.1.1/dist/sbv2_wasm_bg.wasm", { cache: "force-cache" })
|
||||
).arrayBuffer(),
|
||||
);
|
||||
const holder = await ModelHolder.create(
|
||||
await (
|
||||
await fetch("/models/tokenizer.json", { cache: "force-cache" })
|
||||
).text(),
|
||||
await (
|
||||
await fetch("/models/deberta.onnx", { cache: "force-cache" })
|
||||
).arrayBuffer(),
|
||||
);
|
||||
if (typeof window.onready == "function") {
|
||||
window.onready(holder);
|
||||
}
|
||||
</script>
|
||||
<script type="module" async defer>
|
||||
window.onready = async function (holder) {
|
||||
await holder.load(
|
||||
"amitaro",
|
||||
await (await fetch("/models/amitaro.sbv2")).arrayBuffer(),
|
||||
);
|
||||
const wave = await holder.synthesize("amitaro", "おはよう");
|
||||
console.log(wave);
|
||||
};
|
||||
</script>
|
||||
</head>
|
||||
|
||||
<body>
|
||||
<div id="root"></div>
|
||||
</body>
|
||||
|
||||
</html>
|
||||
11
sbv2_wasm/example.js
Normal file
11
sbv2_wasm/example.js
Normal file
@@ -0,0 +1,11 @@
|
||||
import { ModelHolder } from "./dist/index.js";
|
||||
import fs from "node:fs/promises";
|
||||
|
||||
ModelHolder.globalInit(await fs.readFile("./dist/sbv2_wasm_bg.wasm"));
|
||||
const holder = await ModelHolder.create(
|
||||
(await fs.readFile("../models/tokenizer.json")).toString("utf-8"),
|
||||
await fs.readFile("../models/deberta.onnx"),
|
||||
);
|
||||
await holder.load("tsukuyomi", await fs.readFile("../models/iroha2.sbv2"));
|
||||
await fs.writeFile("out.wav", await holder.synthesize("tsukuyomi", "おはよう"));
|
||||
holder.unload("tsukuyomi");
|
||||
25
sbv2_wasm/package.json
Normal file
25
sbv2_wasm/package.json
Normal file
@@ -0,0 +1,25 @@
|
||||
{
|
||||
"name": "sbv2",
|
||||
"version": "0.1.1",
|
||||
"description": "Style Bert VITS2 wasm",
|
||||
"main": "dist/index.js",
|
||||
"types": "dist/index.d.ts",
|
||||
"type": "module",
|
||||
"scripts": {
|
||||
"build": "tsc && esbuild src-js/index.ts --outfile=dist/index.js --minify --format=esm --bundle --external:onnxruntime-web",
|
||||
"format": "biome format --write ."
|
||||
},
|
||||
"keywords": [],
|
||||
"author": "tuna2134",
|
||||
"license": "MIT",
|
||||
"devDependencies": {
|
||||
"@biomejs/biome": "^1.9.2",
|
||||
"@types/node": "^22.7.4",
|
||||
"esbuild": "^0.24.0",
|
||||
"typescript": "^5.6.2"
|
||||
},
|
||||
"dependencies": {
|
||||
"onnxruntime-web": "^1.19.2"
|
||||
},
|
||||
"files": ["dist/*", "package.json", "README.md"]
|
||||
}
|
||||
494
sbv2_wasm/pnpm-lock.yaml
generated
Normal file
494
sbv2_wasm/pnpm-lock.yaml
generated
Normal file
@@ -0,0 +1,494 @@
|
||||
lockfileVersion: '9.0'
|
||||
|
||||
settings:
|
||||
autoInstallPeers: true
|
||||
excludeLinksFromLockfile: false
|
||||
|
||||
importers:
|
||||
|
||||
.:
|
||||
dependencies:
|
||||
onnxruntime-web:
|
||||
specifier: ^1.19.2
|
||||
version: 1.19.2
|
||||
devDependencies:
|
||||
'@biomejs/biome':
|
||||
specifier: ^1.9.2
|
||||
version: 1.9.3
|
||||
'@types/node':
|
||||
specifier: ^22.7.4
|
||||
version: 22.7.4
|
||||
esbuild:
|
||||
specifier: ^0.24.0
|
||||
version: 0.24.0
|
||||
typescript:
|
||||
specifier: ^5.6.2
|
||||
version: 5.6.2
|
||||
|
||||
packages:
|
||||
|
||||
'@biomejs/biome@1.9.3':
|
||||
resolution: {integrity: sha512-POjAPz0APAmX33WOQFGQrwLvlu7WLV4CFJMlB12b6ZSg+2q6fYu9kZwLCOA+x83zXfcPd1RpuWOKJW0GbBwLIQ==}
|
||||
engines: {node: '>=14.21.3'}
|
||||
hasBin: true
|
||||
|
||||
'@biomejs/cli-darwin-arm64@1.9.3':
|
||||
resolution: {integrity: sha512-QZzD2XrjJDUyIZK+aR2i5DDxCJfdwiYbUKu9GzkCUJpL78uSelAHAPy7m0GuPMVtF/Uo+OKv97W3P9nuWZangQ==}
|
||||
engines: {node: '>=14.21.3'}
|
||||
cpu: [arm64]
|
||||
os: [darwin]
|
||||
|
||||
'@biomejs/cli-darwin-x64@1.9.3':
|
||||
resolution: {integrity: sha512-vSCoIBJE0BN3SWDFuAY/tRavpUtNoqiceJ5PrU3xDfsLcm/U6N93JSM0M9OAiC/X7mPPfejtr6Yc9vSgWlEgVw==}
|
||||
engines: {node: '>=14.21.3'}
|
||||
cpu: [x64]
|
||||
os: [darwin]
|
||||
|
||||
'@biomejs/cli-linux-arm64-musl@1.9.3':
|
||||
resolution: {integrity: sha512-VBzyhaqqqwP3bAkkBrhVq50i3Uj9+RWuj+pYmXrMDgjS5+SKYGE56BwNw4l8hR3SmYbLSbEo15GcV043CDSk+Q==}
|
||||
engines: {node: '>=14.21.3'}
|
||||
cpu: [arm64]
|
||||
os: [linux]
|
||||
|
||||
'@biomejs/cli-linux-arm64@1.9.3':
|
||||
resolution: {integrity: sha512-vJkAimD2+sVviNTbaWOGqEBy31cW0ZB52KtpVIbkuma7PlfII3tsLhFa+cwbRAcRBkobBBhqZ06hXoZAN8NODQ==}
|
||||
engines: {node: '>=14.21.3'}
|
||||
cpu: [arm64]
|
||||
os: [linux]
|
||||
|
||||
'@biomejs/cli-linux-x64-musl@1.9.3':
|
||||
resolution: {integrity: sha512-TJmnOG2+NOGM72mlczEsNki9UT+XAsMFAOo8J0me/N47EJ/vkLXxf481evfHLlxMejTY6IN8SdRSiPVLv6AHlA==}
|
||||
engines: {node: '>=14.21.3'}
|
||||
cpu: [x64]
|
||||
os: [linux]
|
||||
|
||||
'@biomejs/cli-linux-x64@1.9.3':
|
||||
resolution: {integrity: sha512-x220V4c+romd26Mu1ptU+EudMXVS4xmzKxPVb9mgnfYlN4Yx9vD5NZraSx/onJnd3Gh/y8iPUdU5CDZJKg9COA==}
|
||||
engines: {node: '>=14.21.3'}
|
||||
cpu: [x64]
|
||||
os: [linux]
|
||||
|
||||
'@biomejs/cli-win32-arm64@1.9.3':
|
||||
resolution: {integrity: sha512-lg/yZis2HdQGsycUvHWSzo9kOvnGgvtrYRgoCEwPBwwAL8/6crOp3+f47tPwI/LI1dZrhSji7PNsGKGHbwyAhw==}
|
||||
engines: {node: '>=14.21.3'}
|
||||
cpu: [arm64]
|
||||
os: [win32]
|
||||
|
||||
'@biomejs/cli-win32-x64@1.9.3':
|
||||
resolution: {integrity: sha512-cQMy2zanBkVLpmmxXdK6YePzmZx0s5Z7KEnwmrW54rcXK3myCNbQa09SwGZ8i/8sLw0H9F3X7K4rxVNGU8/D4Q==}
|
||||
engines: {node: '>=14.21.3'}
|
||||
cpu: [x64]
|
||||
os: [win32]
|
||||
|
||||
'@esbuild/aix-ppc64@0.24.0':
|
||||
resolution: {integrity: sha512-WtKdFM7ls47zkKHFVzMz8opM7LkcsIp9amDUBIAWirg70RM71WRSjdILPsY5Uv1D42ZpUfaPILDlfactHgsRkw==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [ppc64]
|
||||
os: [aix]
|
||||
|
||||
'@esbuild/android-arm64@0.24.0':
|
||||
resolution: {integrity: sha512-Vsm497xFM7tTIPYK9bNTYJyF/lsP590Qc1WxJdlB6ljCbdZKU9SY8i7+Iin4kyhV/KV5J2rOKsBQbB77Ab7L/w==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [arm64]
|
||||
os: [android]
|
||||
|
||||
'@esbuild/android-arm@0.24.0':
|
||||
resolution: {integrity: sha512-arAtTPo76fJ/ICkXWetLCc9EwEHKaeya4vMrReVlEIUCAUncH7M4bhMQ+M9Vf+FFOZJdTNMXNBrWwW+OXWpSew==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [arm]
|
||||
os: [android]
|
||||
|
||||
'@esbuild/android-x64@0.24.0':
|
||||
resolution: {integrity: sha512-t8GrvnFkiIY7pa7mMgJd7p8p8qqYIz1NYiAoKc75Zyv73L3DZW++oYMSHPRarcotTKuSs6m3hTOa5CKHaS02TQ==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [x64]
|
||||
os: [android]
|
||||
|
||||
'@esbuild/darwin-arm64@0.24.0':
|
||||
resolution: {integrity: sha512-CKyDpRbK1hXwv79soeTJNHb5EiG6ct3efd/FTPdzOWdbZZfGhpbcqIpiD0+vwmpu0wTIL97ZRPZu8vUt46nBSw==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [arm64]
|
||||
os: [darwin]
|
||||
|
||||
'@esbuild/darwin-x64@0.24.0':
|
||||
resolution: {integrity: sha512-rgtz6flkVkh58od4PwTRqxbKH9cOjaXCMZgWD905JOzjFKW+7EiUObfd/Kav+A6Gyud6WZk9w+xu6QLytdi2OA==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [x64]
|
||||
os: [darwin]
|
||||
|
||||
'@esbuild/freebsd-arm64@0.24.0':
|
||||
resolution: {integrity: sha512-6Mtdq5nHggwfDNLAHkPlyLBpE5L6hwsuXZX8XNmHno9JuL2+bg2BX5tRkwjyfn6sKbxZTq68suOjgWqCicvPXA==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [arm64]
|
||||
os: [freebsd]
|
||||
|
||||
'@esbuild/freebsd-x64@0.24.0':
|
||||
resolution: {integrity: sha512-D3H+xh3/zphoX8ck4S2RxKR6gHlHDXXzOf6f/9dbFt/NRBDIE33+cVa49Kil4WUjxMGW0ZIYBYtaGCa2+OsQwQ==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [x64]
|
||||
os: [freebsd]
|
||||
|
||||
'@esbuild/linux-arm64@0.24.0':
|
||||
resolution: {integrity: sha512-TDijPXTOeE3eaMkRYpcy3LarIg13dS9wWHRdwYRnzlwlA370rNdZqbcp0WTyyV/k2zSxfko52+C7jU5F9Tfj1g==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [arm64]
|
||||
os: [linux]
|
||||
|
||||
'@esbuild/linux-arm@0.24.0':
|
||||
resolution: {integrity: sha512-gJKIi2IjRo5G6Glxb8d3DzYXlxdEj2NlkixPsqePSZMhLudqPhtZ4BUrpIuTjJYXxvF9njql+vRjB2oaC9XpBw==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [arm]
|
||||
os: [linux]
|
||||
|
||||
'@esbuild/linux-ia32@0.24.0':
|
||||
resolution: {integrity: sha512-K40ip1LAcA0byL05TbCQ4yJ4swvnbzHscRmUilrmP9Am7//0UjPreh4lpYzvThT2Quw66MhjG//20mrufm40mA==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [ia32]
|
||||
os: [linux]
|
||||
|
||||
'@esbuild/linux-loong64@0.24.0':
|
||||
resolution: {integrity: sha512-0mswrYP/9ai+CU0BzBfPMZ8RVm3RGAN/lmOMgW4aFUSOQBjA31UP8Mr6DDhWSuMwj7jaWOT0p0WoZ6jeHhrD7g==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [loong64]
|
||||
os: [linux]
|
||||
|
||||
'@esbuild/linux-mips64el@0.24.0':
|
||||
resolution: {integrity: sha512-hIKvXm0/3w/5+RDtCJeXqMZGkI2s4oMUGj3/jM0QzhgIASWrGO5/RlzAzm5nNh/awHE0A19h/CvHQe6FaBNrRA==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [mips64el]
|
||||
os: [linux]
|
||||
|
||||
'@esbuild/linux-ppc64@0.24.0':
|
||||
resolution: {integrity: sha512-HcZh5BNq0aC52UoocJxaKORfFODWXZxtBaaZNuN3PUX3MoDsChsZqopzi5UupRhPHSEHotoiptqikjN/B77mYQ==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [ppc64]
|
||||
os: [linux]
|
||||
|
||||
'@esbuild/linux-riscv64@0.24.0':
|
||||
resolution: {integrity: sha512-bEh7dMn/h3QxeR2KTy1DUszQjUrIHPZKyO6aN1X4BCnhfYhuQqedHaa5MxSQA/06j3GpiIlFGSsy1c7Gf9padw==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [riscv64]
|
||||
os: [linux]
|
||||
|
||||
'@esbuild/linux-s390x@0.24.0':
|
||||
resolution: {integrity: sha512-ZcQ6+qRkw1UcZGPyrCiHHkmBaj9SiCD8Oqd556HldP+QlpUIe2Wgn3ehQGVoPOvZvtHm8HPx+bH20c9pvbkX3g==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [s390x]
|
||||
os: [linux]
|
||||
|
||||
'@esbuild/linux-x64@0.24.0':
|
||||
resolution: {integrity: sha512-vbutsFqQ+foy3wSSbmjBXXIJ6PL3scghJoM8zCL142cGaZKAdCZHyf+Bpu/MmX9zT9Q0zFBVKb36Ma5Fzfa8xA==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [x64]
|
||||
os: [linux]
|
||||
|
||||
'@esbuild/netbsd-x64@0.24.0':
|
||||
resolution: {integrity: sha512-hjQ0R/ulkO8fCYFsG0FZoH+pWgTTDreqpqY7UnQntnaKv95uP5iW3+dChxnx7C3trQQU40S+OgWhUVwCjVFLvg==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [x64]
|
||||
os: [netbsd]
|
||||
|
||||
'@esbuild/openbsd-arm64@0.24.0':
|
||||
resolution: {integrity: sha512-MD9uzzkPQbYehwcN583yx3Tu5M8EIoTD+tUgKF982WYL9Pf5rKy9ltgD0eUgs8pvKnmizxjXZyLt0z6DC3rRXg==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [arm64]
|
||||
os: [openbsd]
|
||||
|
||||
'@esbuild/openbsd-x64@0.24.0':
|
||||
resolution: {integrity: sha512-4ir0aY1NGUhIC1hdoCzr1+5b43mw99uNwVzhIq1OY3QcEwPDO3B7WNXBzaKY5Nsf1+N11i1eOfFcq+D/gOS15Q==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [x64]
|
||||
os: [openbsd]
|
||||
|
||||
'@esbuild/sunos-x64@0.24.0':
|
||||
resolution: {integrity: sha512-jVzdzsbM5xrotH+W5f1s+JtUy1UWgjU0Cf4wMvffTB8m6wP5/kx0KiaLHlbJO+dMgtxKV8RQ/JvtlFcdZ1zCPA==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [x64]
|
||||
os: [sunos]
|
||||
|
||||
'@esbuild/win32-arm64@0.24.0':
|
||||
resolution: {integrity: sha512-iKc8GAslzRpBytO2/aN3d2yb2z8XTVfNV0PjGlCxKo5SgWmNXx82I/Q3aG1tFfS+A2igVCY97TJ8tnYwpUWLCA==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [arm64]
|
||||
os: [win32]
|
||||
|
||||
'@esbuild/win32-ia32@0.24.0':
|
||||
resolution: {integrity: sha512-vQW36KZolfIudCcTnaTpmLQ24Ha1RjygBo39/aLkM2kmjkWmZGEJ5Gn9l5/7tzXA42QGIoWbICfg6KLLkIw6yw==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [ia32]
|
||||
os: [win32]
|
||||
|
||||
'@esbuild/win32-x64@0.24.0':
|
||||
resolution: {integrity: sha512-7IAFPrjSQIJrGsK6flwg7NFmwBoSTyF3rl7If0hNUFQU4ilTsEPL6GuMuU9BfIWVVGuRnuIidkSMC+c0Otu8IA==}
|
||||
engines: {node: '>=18'}
|
||||
cpu: [x64]
|
||||
os: [win32]
|
||||
|
||||
'@protobufjs/aspromise@1.1.2':
|
||||
resolution: {integrity: sha512-j+gKExEuLmKwvz3OgROXtrJ2UG2x8Ch2YZUxahh+s1F2HZ+wAceUNLkvy6zKCPVRkU++ZWQrdxsUeQXmcg4uoQ==}
|
||||
|
||||
'@protobufjs/base64@1.1.2':
|
||||
resolution: {integrity: sha512-AZkcAA5vnN/v4PDqKyMR5lx7hZttPDgClv83E//FMNhR2TMcLUhfRUBHCmSl0oi9zMgDDqRUJkSxO3wm85+XLg==}
|
||||
|
||||
'@protobufjs/codegen@2.0.4':
|
||||
resolution: {integrity: sha512-YyFaikqM5sH0ziFZCN3xDC7zeGaB/d0IUb9CATugHWbd1FRFwWwt4ld4OYMPWu5a3Xe01mGAULCdqhMlPl29Jg==}
|
||||
|
||||
'@protobufjs/eventemitter@1.1.0':
|
||||
resolution: {integrity: sha512-j9ednRT81vYJ9OfVuXG6ERSTdEL1xVsNgqpkxMsbIabzSo3goCjDIveeGv5d03om39ML71RdmrGNjG5SReBP/Q==}
|
||||
|
||||
'@protobufjs/fetch@1.1.0':
|
||||
resolution: {integrity: sha512-lljVXpqXebpsijW71PZaCYeIcE5on1w5DlQy5WH6GLbFryLUrBD4932W/E2BSpfRJWseIL4v/KPgBFxDOIdKpQ==}
|
||||
|
||||
'@protobufjs/float@1.0.2':
|
||||
resolution: {integrity: sha512-Ddb+kVXlXst9d+R9PfTIxh1EdNkgoRe5tOX6t01f1lYWOvJnSPDBlG241QLzcyPdoNTsblLUdujGSE4RzrTZGQ==}
|
||||
|
||||
'@protobufjs/inquire@1.1.0':
|
||||
resolution: {integrity: sha512-kdSefcPdruJiFMVSbn801t4vFK7KB/5gd2fYvrxhuJYg8ILrmn9SKSX2tZdV6V+ksulWqS7aXjBcRXl3wHoD9Q==}
|
||||
|
||||
'@protobufjs/path@1.1.2':
|
||||
resolution: {integrity: sha512-6JOcJ5Tm08dOHAbdR3GrvP+yUUfkjG5ePsHYczMFLq3ZmMkAD98cDgcT2iA1lJ9NVwFd4tH/iSSoe44YWkltEA==}
|
||||
|
||||
'@protobufjs/pool@1.1.0':
|
||||
resolution: {integrity: sha512-0kELaGSIDBKvcgS4zkjz1PeddatrjYcmMWOlAuAPwAeccUrPHdUqo/J6LiymHHEiJT5NrF1UVwxY14f+fy4WQw==}
|
||||
|
||||
'@protobufjs/utf8@1.1.0':
|
||||
resolution: {integrity: sha512-Vvn3zZrhQZkkBE8LSuW3em98c0FwgO4nxzv6OdSxPKJIEKY2bGbHn+mhGIPerzI4twdxaP8/0+06HBpwf345Lw==}
|
||||
|
||||
'@types/node@22.7.4':
|
||||
resolution: {integrity: sha512-y+NPi1rFzDs1NdQHHToqeiX2TIS79SWEAw9GYhkkx8bD0ChpfqC+n2j5OXOCpzfojBEBt6DnEnnG9MY0zk1XLg==}
|
||||
|
||||
esbuild@0.24.0:
|
||||
resolution: {integrity: sha512-FuLPevChGDshgSicjisSooU0cemp/sGXR841D5LHMB7mTVOmsEHcAxaH3irL53+8YDIeVNQEySh4DaYU/iuPqQ==}
|
||||
engines: {node: '>=18'}
|
||||
hasBin: true
|
||||
|
||||
flatbuffers@1.12.0:
|
||||
resolution: {integrity: sha512-c7CZADjRcl6j0PlvFy0ZqXQ67qSEZfrVPynmnL+2zPc+NtMvrF8Y0QceMo7QqnSPc7+uWjUIAbvCQ5WIKlMVdQ==}
|
||||
|
||||
guid-typescript@1.0.9:
|
||||
resolution: {integrity: sha512-Y8T4vYhEfwJOTbouREvG+3XDsjr8E3kIr7uf+JZ0BYloFsttiHU0WfvANVsR7TxNUJa/WpCnw/Ino/p+DeBhBQ==}
|
||||
|
||||
long@5.2.3:
|
||||
resolution: {integrity: sha512-lcHwpNoggQTObv5apGNCTdJrO69eHOZMi4BNC+rTLER8iHAqGrUVeLh/irVIM7zTw2bOXA8T6uNPeujwOLg/2Q==}
|
||||
|
||||
onnxruntime-common@1.19.2:
|
||||
resolution: {integrity: sha512-a4R7wYEVFbZBlp0BfhpbFWqe4opCor3KM+5Wm22Az3NGDcQMiU2hfG/0MfnBs+1ZrlSGmlgWeMcXQkDk1UFb8Q==}
|
||||
|
||||
onnxruntime-web@1.19.2:
|
||||
resolution: {integrity: sha512-r0ok6KpTUXR4WA+rHvUiZn7JoH02e8iS7XE1p5bXk7q3E0UaRFfYvpMNUHqEPiTBMuIssfBxDCQjUihV8dDFPg==}
|
||||
|
||||
platform@1.3.6:
|
||||
resolution: {integrity: sha512-fnWVljUchTro6RiCFvCXBbNhJc2NijN7oIQxbwsyL0buWJPG85v81ehlHI9fXrJsMNgTofEoWIQeClKpgxFLrg==}
|
||||
|
||||
protobufjs@7.4.0:
|
||||
resolution: {integrity: sha512-mRUWCc3KUU4w1jU8sGxICXH/gNS94DvI1gxqDvBzhj1JpcsimQkYiOJfwsPUykUI5ZaspFbSgmBLER8IrQ3tqw==}
|
||||
engines: {node: '>=12.0.0'}
|
||||
|
||||
typescript@5.6.2:
|
||||
resolution: {integrity: sha512-NW8ByodCSNCwZeghjN3o+JX5OFH0Ojg6sadjEKY4huZ52TqbJTJnDo5+Tw98lSy63NZvi4n+ez5m2u5d4PkZyw==}
|
||||
engines: {node: '>=14.17'}
|
||||
hasBin: true
|
||||
|
||||
undici-types@6.19.8:
|
||||
resolution: {integrity: sha512-ve2KP6f/JnbPBFyobGHuerC9g1FYGn/F8n1LWTwNxCEzd6IfqTwUQcNXgEtmmQ6DlRrC1hrSrBnCZPokRrDHjw==}
|
||||
|
||||
snapshots:
|
||||
|
||||
'@biomejs/biome@1.9.3':
|
||||
optionalDependencies:
|
||||
'@biomejs/cli-darwin-arm64': 1.9.3
|
||||
'@biomejs/cli-darwin-x64': 1.9.3
|
||||
'@biomejs/cli-linux-arm64': 1.9.3
|
||||
'@biomejs/cli-linux-arm64-musl': 1.9.3
|
||||
'@biomejs/cli-linux-x64': 1.9.3
|
||||
'@biomejs/cli-linux-x64-musl': 1.9.3
|
||||
'@biomejs/cli-win32-arm64': 1.9.3
|
||||
'@biomejs/cli-win32-x64': 1.9.3
|
||||
|
||||
'@biomejs/cli-darwin-arm64@1.9.3':
|
||||
optional: true
|
||||
|
||||
'@biomejs/cli-darwin-x64@1.9.3':
|
||||
optional: true
|
||||
|
||||
'@biomejs/cli-linux-arm64-musl@1.9.3':
|
||||
optional: true
|
||||
|
||||
'@biomejs/cli-linux-arm64@1.9.3':
|
||||
optional: true
|
||||
|
||||
'@biomejs/cli-linux-x64-musl@1.9.3':
|
||||
optional: true
|
||||
|
||||
'@biomejs/cli-linux-x64@1.9.3':
|
||||
optional: true
|
||||
|
||||
'@biomejs/cli-win32-arm64@1.9.3':
|
||||
optional: true
|
||||
|
||||
'@biomejs/cli-win32-x64@1.9.3':
|
||||
optional: true
|
||||
|
||||
'@esbuild/aix-ppc64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/android-arm64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/android-arm@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/android-x64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/darwin-arm64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/darwin-x64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/freebsd-arm64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/freebsd-x64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/linux-arm64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/linux-arm@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/linux-ia32@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/linux-loong64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/linux-mips64el@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/linux-ppc64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/linux-riscv64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/linux-s390x@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/linux-x64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/netbsd-x64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/openbsd-arm64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/openbsd-x64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/sunos-x64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/win32-arm64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/win32-ia32@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@esbuild/win32-x64@0.24.0':
|
||||
optional: true
|
||||
|
||||
'@protobufjs/aspromise@1.1.2': {}
|
||||
|
||||
'@protobufjs/base64@1.1.2': {}
|
||||
|
||||
'@protobufjs/codegen@2.0.4': {}
|
||||
|
||||
'@protobufjs/eventemitter@1.1.0': {}
|
||||
|
||||
'@protobufjs/fetch@1.1.0':
|
||||
dependencies:
|
||||
'@protobufjs/aspromise': 1.1.2
|
||||
'@protobufjs/inquire': 1.1.0
|
||||
|
||||
'@protobufjs/float@1.0.2': {}
|
||||
|
||||
'@protobufjs/inquire@1.1.0': {}
|
||||
|
||||
'@protobufjs/path@1.1.2': {}
|
||||
|
||||
'@protobufjs/pool@1.1.0': {}
|
||||
|
||||
'@protobufjs/utf8@1.1.0': {}
|
||||
|
||||
'@types/node@22.7.4':
|
||||
dependencies:
|
||||
undici-types: 6.19.8
|
||||
|
||||
esbuild@0.24.0:
|
||||
optionalDependencies:
|
||||
'@esbuild/aix-ppc64': 0.24.0
|
||||
'@esbuild/android-arm': 0.24.0
|
||||
'@esbuild/android-arm64': 0.24.0
|
||||
'@esbuild/android-x64': 0.24.0
|
||||
'@esbuild/darwin-arm64': 0.24.0
|
||||
'@esbuild/darwin-x64': 0.24.0
|
||||
'@esbuild/freebsd-arm64': 0.24.0
|
||||
'@esbuild/freebsd-x64': 0.24.0
|
||||
'@esbuild/linux-arm': 0.24.0
|
||||
'@esbuild/linux-arm64': 0.24.0
|
||||
'@esbuild/linux-ia32': 0.24.0
|
||||
'@esbuild/linux-loong64': 0.24.0
|
||||
'@esbuild/linux-mips64el': 0.24.0
|
||||
'@esbuild/linux-ppc64': 0.24.0
|
||||
'@esbuild/linux-riscv64': 0.24.0
|
||||
'@esbuild/linux-s390x': 0.24.0
|
||||
'@esbuild/linux-x64': 0.24.0
|
||||
'@esbuild/netbsd-x64': 0.24.0
|
||||
'@esbuild/openbsd-arm64': 0.24.0
|
||||
'@esbuild/openbsd-x64': 0.24.0
|
||||
'@esbuild/sunos-x64': 0.24.0
|
||||
'@esbuild/win32-arm64': 0.24.0
|
||||
'@esbuild/win32-ia32': 0.24.0
|
||||
'@esbuild/win32-x64': 0.24.0
|
||||
|
||||
flatbuffers@1.12.0: {}
|
||||
|
||||
guid-typescript@1.0.9: {}
|
||||
|
||||
long@5.2.3: {}
|
||||
|
||||
onnxruntime-common@1.19.2: {}
|
||||
|
||||
onnxruntime-web@1.19.2:
|
||||
dependencies:
|
||||
flatbuffers: 1.12.0
|
||||
guid-typescript: 1.0.9
|
||||
long: 5.2.3
|
||||
onnxruntime-common: 1.19.2
|
||||
platform: 1.3.6
|
||||
protobufjs: 7.4.0
|
||||
|
||||
platform@1.3.6: {}
|
||||
|
||||
protobufjs@7.4.0:
|
||||
dependencies:
|
||||
'@protobufjs/aspromise': 1.1.2
|
||||
'@protobufjs/base64': 1.1.2
|
||||
'@protobufjs/codegen': 2.0.4
|
||||
'@protobufjs/eventemitter': 1.1.0
|
||||
'@protobufjs/fetch': 1.1.0
|
||||
'@protobufjs/float': 1.0.2
|
||||
'@protobufjs/inquire': 1.1.0
|
||||
'@protobufjs/path': 1.1.2
|
||||
'@protobufjs/pool': 1.1.0
|
||||
'@protobufjs/utf8': 1.1.0
|
||||
'@types/node': 22.7.4
|
||||
long: 5.2.3
|
||||
|
||||
typescript@5.6.2: {}
|
||||
|
||||
undici-types@6.19.8: {}
|
||||
106
sbv2_wasm/src-js/index.ts
Normal file
106
sbv2_wasm/src-js/index.ts
Normal file
@@ -0,0 +1,106 @@
|
||||
import * as wasm from "../pkg/sbv2_wasm.js";
|
||||
import { InferenceSession, Tensor } from "onnxruntime-web";
|
||||
|
||||
export class ModelHolder {
|
||||
private models: Map<string, [InferenceSession, wasm.StyleVectorWrap]> =
|
||||
new Map();
|
||||
constructor(
|
||||
private tok: wasm.TokenizerWrap,
|
||||
private deberta: InferenceSession,
|
||||
) {}
|
||||
public static async globalInit(buf: ArrayBufferLike) {
|
||||
await wasm.default(buf);
|
||||
}
|
||||
public static async create(tok: string, deberta: ArrayBufferLike) {
|
||||
return new ModelHolder(
|
||||
wasm.load_tokenizer(tok),
|
||||
await InferenceSession.create(deberta, {
|
||||
executionProviders: ["webnn", "webgpu", "wasm", "cpu"],
|
||||
graphOptimizationLevel: "all",
|
||||
}),
|
||||
);
|
||||
}
|
||||
public async synthesize(
|
||||
name: string,
|
||||
text: string,
|
||||
style_id: number = 0,
|
||||
style_weight: number = 1.0,
|
||||
sdp_ratio: number = 0.4,
|
||||
speed: number = 1.0,
|
||||
) {
|
||||
const mod = this.models.get(name);
|
||||
if (!mod) throw new Error(`No model named ${name}`);
|
||||
const [vits2, style] = mod;
|
||||
return wasm.synthesize(
|
||||
text,
|
||||
this.tok,
|
||||
async (a: BigInt64Array, b: BigInt64Array) => {
|
||||
try {
|
||||
const res = (
|
||||
await this.deberta.run({
|
||||
input_ids: new Tensor("int64", a, [1, a.length]),
|
||||
attention_mask: new Tensor("int64", b, [1, b.length]),
|
||||
})
|
||||
)["output"];
|
||||
return [new Uint32Array(res.dims), await res.getData(true)];
|
||||
} catch (e) {
|
||||
console.warn(e);
|
||||
throw e;
|
||||
}
|
||||
},
|
||||
async (
|
||||
[a_shape, a_array]: any,
|
||||
b_d: any,
|
||||
c_d: any,
|
||||
d_d: any,
|
||||
e_d: any,
|
||||
f: number,
|
||||
g: number,
|
||||
) => {
|
||||
try {
|
||||
const a = new Tensor("float32", a_array, [1, ...a_shape]);
|
||||
const b = new Tensor("int64", b_d, [1, b_d.length]);
|
||||
const c = new Tensor("int64", c_d, [1, c_d.length]);
|
||||
const d = new Tensor("int64", d_d, [1, d_d.length]);
|
||||
const e = new Tensor("float32", e_d, [1, e_d.length]);
|
||||
const res = (
|
||||
await vits2.run({
|
||||
x_tst: b,
|
||||
x_tst_lengths: new Tensor("int64", [b_d.length]),
|
||||
sid: new Tensor("int64", [0]),
|
||||
tones: c,
|
||||
language: d,
|
||||
bert: a,
|
||||
style_vec: e,
|
||||
sdp_ratio: new Tensor("float32", [f]),
|
||||
length_scale: new Tensor("float32", [g]),
|
||||
})
|
||||
).output;
|
||||
return [new Uint32Array(res.dims), await res.getData(true)];
|
||||
} catch (e) {
|
||||
console.warn(e);
|
||||
throw e;
|
||||
}
|
||||
},
|
||||
sdp_ratio,
|
||||
1.0 / speed,
|
||||
style_id,
|
||||
style_weight,
|
||||
style,
|
||||
);
|
||||
}
|
||||
public async load(name: string, b: Uint8Array) {
|
||||
const [style, vits2_b] = wasm.load_sbv2file(b);
|
||||
const vits2 = await InferenceSession.create(vits2_b as Uint8Array, {
|
||||
executionProviders: ["webnn", "webgpu", "wasm", "cpu"],
|
||||
graphOptimizationLevel: "all",
|
||||
});
|
||||
this.models.set(name, [vits2, style]);
|
||||
}
|
||||
public async unload(name: string) {
|
||||
return this.models.delete(name);
|
||||
}
|
||||
public modelList() {
|
||||
return this.models.keys();
|
||||
}
|
||||
}
|
||||
102
sbv2_wasm/src/array_helper.rs
Normal file
102
sbv2_wasm/src/array_helper.rs
Normal file
@@ -0,0 +1,102 @@
|
||||
pub fn vec8_to_array8(v: Vec<u8>) -> js_sys::Uint8Array {
|
||||
let arr = js_sys::Uint8Array::new_with_length(v.len() as u32);
|
||||
arr.copy_from(&v);
|
||||
arr
|
||||
}
|
||||
|
||||
pub fn vec_f32_to_array_f32(v: Vec<f32>) -> js_sys::Float32Array {
|
||||
let arr = js_sys::Float32Array::new_with_length(v.len() as u32);
|
||||
arr.copy_from(&v);
|
||||
arr
|
||||
}
|
||||
|
||||
pub fn array8_to_vec8(buf: js_sys::Uint8Array) -> Vec<u8> {
|
||||
let mut body = vec![0; buf.length() as usize];
|
||||
buf.copy_to(&mut body[..]);
|
||||
body
|
||||
}
|
||||
|
||||
pub fn vec64_to_array64(v: Vec<i64>) -> js_sys::BigInt64Array {
|
||||
let arr = js_sys::BigInt64Array::new_with_length(v.len() as u32);
|
||||
arr.copy_from(&v);
|
||||
arr
|
||||
}
|
||||
|
||||
pub fn vec_to_array(v: Vec<wasm_bindgen::JsValue>) -> js_sys::Array {
|
||||
let arr = js_sys::Array::new_with_length(v.len() as u32);
|
||||
for (i, v) in v.into_iter().enumerate() {
|
||||
arr.set(i as u32, v);
|
||||
}
|
||||
arr
|
||||
}
|
||||
|
||||
struct A {
|
||||
shape: Vec<u32>,
|
||||
data: Vec<f32>,
|
||||
}
|
||||
|
||||
impl TryFrom<wasm_bindgen::JsValue> for A {
|
||||
type Error = sbv2_core::error::Error;
|
||||
|
||||
fn try_from(value: wasm_bindgen::JsValue) -> Result<Self, Self::Error> {
|
||||
let value: js_sys::Array = value.into();
|
||||
let mut shape = vec![];
|
||||
let mut data = vec![];
|
||||
for (i, v) in value.iter().enumerate() {
|
||||
match i {
|
||||
0 => {
|
||||
let v: js_sys::Uint32Array = v.into();
|
||||
shape = vec![0; v.length() as usize];
|
||||
v.copy_to(&mut shape);
|
||||
}
|
||||
1 => {
|
||||
let v: js_sys::Float32Array = v.into();
|
||||
data = vec![0.0; v.length() as usize];
|
||||
v.copy_to(&mut data);
|
||||
}
|
||||
_ => {}
|
||||
};
|
||||
}
|
||||
Ok(A { shape, data })
|
||||
}
|
||||
}
|
||||
|
||||
pub fn array_to_array2_f32(
|
||||
a: wasm_bindgen::JsValue,
|
||||
) -> sbv2_core::error::Result<ndarray::Array2<f32>> {
|
||||
let a = A::try_from(a)?;
|
||||
if a.shape.len() != 2 {
|
||||
return Err(sbv2_core::error::Error::OtherError(
|
||||
"Length mismatch".to_string(),
|
||||
));
|
||||
}
|
||||
let shape = [a.shape[0] as usize, a.shape[1] as usize];
|
||||
let arr = ndarray::Array2::from_shape_vec(shape, a.data.to_vec())
|
||||
.map_err(|e| sbv2_core::error::Error::OtherError(e.to_string()))?;
|
||||
Ok(arr)
|
||||
}
|
||||
pub fn array_to_array3_f32(
|
||||
a: wasm_bindgen::JsValue,
|
||||
) -> sbv2_core::error::Result<ndarray::Array3<f32>> {
|
||||
let a = A::try_from(a)?;
|
||||
if a.shape.len() != 3 {
|
||||
return Err(sbv2_core::error::Error::OtherError(
|
||||
"Length mismatch".to_string(),
|
||||
));
|
||||
}
|
||||
let shape = [
|
||||
a.shape[0] as usize,
|
||||
a.shape[1] as usize,
|
||||
a.shape[2] as usize,
|
||||
];
|
||||
let arr = ndarray::Array3::from_shape_vec(shape, a.data.to_vec())
|
||||
.map_err(|e| sbv2_core::error::Error::OtherError(e.to_string()))?;
|
||||
Ok(arr)
|
||||
}
|
||||
|
||||
pub fn array2_f32_to_array(a: ndarray::Array2<f32>) -> js_sys::Array {
|
||||
let shape: Vec<wasm_bindgen::JsValue> = a.shape().iter().map(|f| (*f as u32).into()).collect();
|
||||
let typed_array = js_sys::Float32Array::new_with_length(a.len() as u32);
|
||||
typed_array.copy_from(&a.into_flat().to_vec());
|
||||
vec_to_array(vec![vec_to_array(shape).into(), typed_array.into()])
|
||||
}
|
||||
123
sbv2_wasm/src/lib.rs
Normal file
123
sbv2_wasm/src/lib.rs
Normal file
@@ -0,0 +1,123 @@
|
||||
use once_cell::sync::Lazy;
|
||||
use sbv2_core::*;
|
||||
use wasm_bindgen::prelude::*;
|
||||
use wasm_bindgen_futures::JsFuture;
|
||||
mod array_helper;
|
||||
|
||||
static JTALK: Lazy<jtalk::JTalk> = Lazy::new(|| jtalk::JTalk::new().unwrap());
|
||||
|
||||
#[wasm_bindgen]
|
||||
pub struct TokenizerWrap {
|
||||
tokenizer: tokenizer::Tokenizer,
|
||||
}
|
||||
|
||||
#[wasm_bindgen]
|
||||
pub fn load_tokenizer(s: js_sys::JsString) -> Result<TokenizerWrap, JsError> {
|
||||
if let Some(s) = s.as_string() {
|
||||
Ok(TokenizerWrap {
|
||||
tokenizer: tokenizer::Tokenizer::from_bytes(s.as_bytes())
|
||||
.map_err(|e| JsError::new(&e.to_string()))?,
|
||||
})
|
||||
} else {
|
||||
Err(JsError::new("invalid utf8"))
|
||||
}
|
||||
}
|
||||
|
||||
#[wasm_bindgen]
|
||||
pub struct StyleVectorWrap {
|
||||
style_vector: ndarray::Array2<f32>,
|
||||
}
|
||||
|
||||
#[wasm_bindgen]
|
||||
pub fn load_sbv2file(buf: js_sys::Uint8Array) -> Result<js_sys::Array, JsError> {
|
||||
let (style_vectors, vits2) = sbv2file::parse_sbv2file(array_helper::array8_to_vec8(buf))?;
|
||||
let buf = array_helper::vec8_to_array8(vits2);
|
||||
Ok(array_helper::vec_to_array(vec![
|
||||
StyleVectorWrap {
|
||||
style_vector: style::load_style(style_vectors)?,
|
||||
}
|
||||
.into(),
|
||||
buf.into(),
|
||||
]))
|
||||
}
|
||||
|
||||
#[allow(clippy::too_many_arguments)]
|
||||
#[wasm_bindgen]
|
||||
pub async fn synthesize(
|
||||
text: &str,
|
||||
tokenizer: &TokenizerWrap,
|
||||
bert_predict_fn: js_sys::Function,
|
||||
synthesize_fn: js_sys::Function,
|
||||
sdp_ratio: f32,
|
||||
length_scale: f32,
|
||||
style_id: i32,
|
||||
style_weight: f32,
|
||||
style_vectors: &StyleVectorWrap,
|
||||
) -> Result<js_sys::Uint8Array, JsError> {
|
||||
let synthesize_wrap = |bert_ori: ndarray::Array2<f32>,
|
||||
x_tst: ndarray::Array1<i64>,
|
||||
tones: ndarray::Array1<i64>,
|
||||
lang_ids: ndarray::Array1<i64>,
|
||||
style_vector: ndarray::Array1<f32>,
|
||||
sdp_ratio: f32,
|
||||
length_scale: f32| async move {
|
||||
let arr = array_helper::vec_to_array(vec![
|
||||
array_helper::array2_f32_to_array(bert_ori).into(),
|
||||
array_helper::vec64_to_array64(x_tst.to_vec()).into(),
|
||||
array_helper::vec64_to_array64(tones.to_vec()).into(),
|
||||
array_helper::vec64_to_array64(lang_ids.to_vec()).into(),
|
||||
array_helper::vec_f32_to_array_f32(style_vector.to_vec()).into(),
|
||||
sdp_ratio.into(),
|
||||
length_scale.into(),
|
||||
]);
|
||||
let res = synthesize_fn
|
||||
.apply(&js_sys::Object::new().into(), &arr)
|
||||
.map_err(|e| {
|
||||
error::Error::OtherError(e.as_string().unwrap_or("unknown".to_string()))
|
||||
})?;
|
||||
let res = JsFuture::from(Into::<js_sys::Promise>::into(res))
|
||||
.await
|
||||
.map_err(|e| {
|
||||
sbv2_core::error::Error::OtherError(e.as_string().unwrap_or("unknown".to_string()))
|
||||
})?;
|
||||
array_helper::array_to_array3_f32(res)
|
||||
};
|
||||
let (bert_ori, phones, tones, lang_ids) = tts_util::parse_text(
|
||||
text,
|
||||
&JTALK,
|
||||
&tokenizer.tokenizer,
|
||||
|token_ids: Vec<i64>, attention_masks: Vec<i64>| {
|
||||
Box::pin(async move {
|
||||
let arr = array_helper::vec_to_array(vec![
|
||||
array_helper::vec64_to_array64(token_ids).into(),
|
||||
array_helper::vec64_to_array64(attention_masks).into(),
|
||||
]);
|
||||
let res = bert_predict_fn
|
||||
.apply(&js_sys::Object::new().into(), &arr)
|
||||
.map_err(|e| {
|
||||
error::Error::OtherError(e.as_string().unwrap_or("unknown".to_string()))
|
||||
})?;
|
||||
let res = JsFuture::from(Into::<js_sys::Promise>::into(res))
|
||||
.await
|
||||
.map_err(|e| {
|
||||
sbv2_core::error::Error::OtherError(
|
||||
e.as_string().unwrap_or("unknown".to_string()),
|
||||
)
|
||||
})?;
|
||||
array_helper::array_to_array2_f32(res)
|
||||
})
|
||||
},
|
||||
)
|
||||
.await?;
|
||||
let audio = synthesize_wrap(
|
||||
bert_ori.to_owned(),
|
||||
phones,
|
||||
tones,
|
||||
lang_ids,
|
||||
style::get_style_vector(&style_vectors.style_vector, style_id, style_weight)?,
|
||||
sdp_ratio,
|
||||
length_scale,
|
||||
)
|
||||
.await?;
|
||||
Ok(array_helper::vec8_to_array8(tts_util::array_to_vec(audio)?))
|
||||
}
|
||||
15
sbv2_wasm/tsconfig.json
Normal file
15
sbv2_wasm/tsconfig.json
Normal file
@@ -0,0 +1,15 @@
|
||||
{
|
||||
"compilerOptions": {
|
||||
"target": "ESNext",
|
||||
"module": "ESNext",
|
||||
"rootDir": "./src-js",
|
||||
"outDir": "./dist",
|
||||
"moduleResolution": "node",
|
||||
"esModuleInterop": true,
|
||||
"forceConsistentCasingInFileNames": true,
|
||||
"strict": true,
|
||||
"skipLibCheck": true,
|
||||
"declaration": true,
|
||||
"emitDeclarationOnly": true
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user