mirror of
https://github.com/zhw2590582/ArtPlayer.git
synced 2026-10-11 13:56:15 -08:00
refactor(asr): [PKG-ASR-04] preserve old declarations and add precise runtime types
This commit is contained in:
1 parent
0cf2af4840
commit
93208e59e1
24 files changed
+1224
-19
No files matched your search
+2
-1
@@ -94,7 +94,8 @@
|
||||
"check:ci": "node refactor/scripts/ci-workflow.mjs",
|
||||
"test:ci": "node --test test/ci-summary.test.js refactor/scripts/ci-workflow.test.mjs refactor/scripts/impact.test.mjs test/package-runtime.test.js",
|
||||
"test:package:runtime": "node scripts/package-runtime.mjs --canonical",
|
||||
"test:asr": "node --test test/asr.test.js test/asr-audio.test.js test/asr-encoding.test.js test/asr-lifecycle.test.js test/asr-distribution.test.js"
|
||||
"test:asr": "node --test test/asr.test.js test/asr-audio.test.js test/asr-encoding.test.js test/asr-lifecycle.test.js test/asr-distribution.test.js",
|
||||
"test:asr-types-package": "node refactor/scripts/asr-package-types.mjs"
|
||||
},
|
||||
"browserslist": "last 1 Chrome version",
|
||||
"devDependencies": {
|
||||
|
||||
@@ -2,4 +2,5 @@ node_modules
|
||||
.DS_Store
|
||||
yarn.lock
|
||||
package-lock.json
|
||||
src
|
||||
src
|
||||
tsconfig.json
|
||||
@@ -63,10 +63,20 @@ HTML, punctuation splitting, replacement, ignored non-string values and the
|
||||
historical `length=0` behavior. The CJS function has a non-enumerable self `default`
|
||||
alias for consumers of the 2.0 namespace, while preserving the callable 2.1 form.
|
||||
|
||||
Root public declarations have not yet migrated: they describe stop as void and
|
||||
the callback as void/Promise<void>. PKG-ASR-04 owns exact asynchronous public types,
|
||||
old assignment consumers, module forms and installed tarball acceptance. Internal
|
||||
strict TypeScript does not prove that public type migration complete.
|
||||
Root and `/legacy` declarations intentionally retain the historical factory,
|
||||
void stop and void/Promise<void> callback. Their NodeNext ESM default import remains
|
||||
the old namespace type: changing it into a callable default would break legal
|
||||
namespace substitution. Historical direct-call errors are frozen separately from
|
||||
legal namespace consumers. Do not silently rewrite these declarations to match
|
||||
runtime behavior or require a self-default property on old replacement factories.
|
||||
|
||||
The additive `/runtime` entry references the same main/ESM implementation, with
|
||||
`RuntimeOption`, `RuntimeResult` and `RuntimeFactory`: callback text/null/no result
|
||||
and asynchronous stop are accurate. Its `.d.mts` default export and `.d.cts`/
|
||||
`.d.ts` export assignment support ESM, raw CommonJS and old Node10 resolution.
|
||||
Pure type namespaces make all four named runtime types available in every mode.
|
||||
The root also exports those types for convenient annotations. No runtime code or
|
||||
version changes are needed for this entry.
|
||||
|
||||
From the repository root:
|
||||
|
||||
@@ -76,6 +86,11 @@ From the repository root:
|
||||
published/current core, pause/resume, source switch, stop/restart and destroy.
|
||||
Set `ARTPLAYER_ASR_ARTIFACT` to an actual main/legacy file to test that artifact.
|
||||
- `yarn typecheck`: includes the package strict/noUncheckedIndexedAccess project.
|
||||
- `yarn test:asr-types-package`: packs and installs core/ASR outside the workspace,
|
||||
checks frozen 2.0/2.1 consumers and candidate declarations in strict compiler
|
||||
modes, verifies offline frozen reinstall and file hashes, exercises actual
|
||||
import/require exports, and rejects invalid uses. Historical declaration errors
|
||||
are explicit expectations and never counted as candidate success.
|
||||
- `yarn dev artplayer-plugin-asr` and `yarn build artplayer-plugin-asr`: normal
|
||||
repository development and three-format production builds.
|
||||
|
||||
|
||||
@@ -8,6 +8,35 @@ restart capture; the player's direct Web Audio connection remains alive until
|
||||
the player is destroyed so that stopping recognition does not silence playback.
|
||||
Call `art.destroy()` when disposing the player.
|
||||
|
||||
## TypeScript
|
||||
|
||||
Existing imports keep their historical types, including `stop(): void` and a
|
||||
`void | Promise<void>` recognition callback. For accurate asynchronous types, use
|
||||
the additive `/runtime` entry. It loads the same implementation as the root entry:
|
||||
|
||||
```ts
|
||||
import Artplayer from 'artplayer'
|
||||
import asr from 'artplayer-plugin-asr/runtime'
|
||||
import type { RuntimeOption } from 'artplayer-plugin-asr/runtime'
|
||||
|
||||
const option: RuntimeOption = {
|
||||
onAudioChunk: async ({ pcm, wav }) => {
|
||||
// Send one of these buffers to your own recognition service.
|
||||
void [pcm, wav]
|
||||
return 'Recognized text.'
|
||||
},
|
||||
}
|
||||
const art = new Artplayer({ container: '#player', url: '/video.mp4' })
|
||||
const recognition = asr(option)(art)
|
||||
await recognition.stop()
|
||||
```
|
||||
|
||||
The callback may return text, `null`, or no value, synchronously or asynchronously.
|
||||
CommonJS TypeScript can use `import asr = require('artplayer-plugin-asr/runtime')`.
|
||||
The root declaration retains its historical NodeNext ESM namespace shape; use
|
||||
`/runtime` for a directly callable default import in that mode. This is an opt-in
|
||||
type entry, and does not require changes to existing JavaScript consumers.
|
||||
|
||||
## Maintenance
|
||||
|
||||
See [ARCHITECTURE.md](ARCHITECTURE.md) for the current audio flow, public behavior,
|
||||
|
||||
@@ -27,11 +27,31 @@
|
||||
"types": "./types/artplayer-plugin-asr.d.ts",
|
||||
"import": "./dist/artplayer-plugin-asr.legacy.js",
|
||||
"require": "./dist/artplayer-plugin-asr.legacy.js"
|
||||
},
|
||||
"./runtime": {
|
||||
"import": {
|
||||
"types": "./types/runtime.d.mts",
|
||||
"default": "./dist/artplayer-plugin-asr.mjs"
|
||||
},
|
||||
"require": {
|
||||
"types": "./types/runtime.d.cts",
|
||||
"default": "./dist/artplayer-plugin-asr.js"
|
||||
}
|
||||
}
|
||||
},
|
||||
"main": "./dist/artplayer-plugin-asr.js",
|
||||
"module": "./dist/artplayer-plugin-asr.mjs",
|
||||
"types": "./types/artplayer-plugin-asr.d.ts",
|
||||
"legacy": "./dist/artplayer-plugin-asr.legacy.js",
|
||||
"browserslist": "last 1 Chrome version"
|
||||
"browserslist": "last 1 Chrome version",
|
||||
"typesVersions": {
|
||||
"*": {
|
||||
"legacy": [
|
||||
"types/artplayer-plugin-asr.d.ts"
|
||||
],
|
||||
"runtime": [
|
||||
"types/runtime.d.ts"
|
||||
]
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,5 +1,5 @@
|
||||
{
|
||||
"extends": "../../tsconfig.base.json",
|
||||
"compilerOptions": { "allowJs": false },
|
||||
"include": ["src/**/*.ts", "types/**/*.d.ts", "../../types/assets.d.ts"]
|
||||
"include": ["src/**/*.ts", "types/**/*.d.ts", "types/**/*.d.mts", "types/**/*.d.cts", "../../types/assets.d.ts"]
|
||||
}
|
||||
@@ -1,11 +1,11 @@
|
||||
import type Artplayer from 'artplayer'
|
||||
|
||||
interface AudioChunk {
|
||||
export interface AudioChunk {
|
||||
pcm: ArrayBuffer
|
||||
wav: ArrayBuffer
|
||||
}
|
||||
|
||||
interface AsrPluginOption {
|
||||
export interface AsrPluginOption {
|
||||
length?: number
|
||||
interval?: number
|
||||
sampleRate?: number
|
||||
@@ -13,13 +13,30 @@ interface AsrPluginOption {
|
||||
onAudioChunk?: (chunk: AudioChunk) => void | Promise<void>
|
||||
}
|
||||
|
||||
interface AsrPluginInstance {
|
||||
export interface AsrPluginInstance {
|
||||
name: 'artplayerPluginAsr'
|
||||
stop: () => void
|
||||
hide: () => void
|
||||
append: (subtitle: string) => void
|
||||
}
|
||||
|
||||
/** Historical factory shape, including void stop and callback results. */
|
||||
export type Factory = (option?: AsrPluginOption) => (art: Artplayer) => AsrPluginInstance
|
||||
|
||||
/** Accurate asynchronous view available through the /runtime entry. */
|
||||
export interface RuntimeOption extends Omit<AsrPluginOption, 'onAudioChunk'> {
|
||||
onAudioChunk?: (chunk: AudioChunk) => string | void | null | Promise<string | void | null>
|
||||
}
|
||||
|
||||
export interface RuntimeResult extends Omit<AsrPluginInstance, 'stop'> {
|
||||
stop: () => Promise<void>
|
||||
}
|
||||
|
||||
export interface RuntimeFactory {
|
||||
(option?: RuntimeOption): (art: Artplayer) => RuntimeResult
|
||||
readonly default: RuntimeFactory
|
||||
}
|
||||
|
||||
declare function artplayerPluginAsr(option?: AsrPluginOption): (art: Artplayer) => AsrPluginInstance
|
||||
|
||||
export default artplayerPluginAsr
|
||||
@@ -0,0 +1,11 @@
|
||||
import type { RuntimeFactory } from './artplayer-plugin-asr.js'
|
||||
|
||||
declare const artplayerPluginAsr: RuntimeFactory
|
||||
// eslint-disable-next-line ts/no-redeclare -- Ambient merge exposes types on the CommonJS factory.
|
||||
declare namespace artplayerPluginAsr {
|
||||
type AudioChunk = import('./artplayer-plugin-asr.js').AudioChunk
|
||||
type RuntimeFactory = import('./artplayer-plugin-asr.js').RuntimeFactory
|
||||
type RuntimeOption = import('./artplayer-plugin-asr.js').RuntimeOption
|
||||
type RuntimeResult = import('./artplayer-plugin-asr.js').RuntimeResult
|
||||
}
|
||||
export = artplayerPluginAsr
|
||||
@@ -0,0 +1,5 @@
|
||||
import type { RuntimeFactory } from './artplayer-plugin-asr.js'
|
||||
|
||||
declare const artplayerPluginAsr: RuntimeFactory
|
||||
export default artplayerPluginAsr
|
||||
export type { AudioChunk, RuntimeFactory, RuntimeOption, RuntimeResult } from './artplayer-plugin-asr.js'
|
||||
@@ -0,0 +1,11 @@
|
||||
import type { RuntimeFactory } from './artplayer-plugin-asr.js'
|
||||
|
||||
declare const artplayerPluginAsr: RuntimeFactory
|
||||
// eslint-disable-next-line ts/no-redeclare -- Ambient merge exposes types on the CommonJS factory.
|
||||
declare namespace artplayerPluginAsr {
|
||||
type AudioChunk = import('./artplayer-plugin-asr.js').AudioChunk
|
||||
type RuntimeFactory = import('./artplayer-plugin-asr.js').RuntimeFactory
|
||||
type RuntimeOption = import('./artplayer-plugin-asr.js').RuntimeOption
|
||||
type RuntimeResult = import('./artplayer-plugin-asr.js').RuntimeResult
|
||||
}
|
||||
export = artplayerPluginAsr
|
||||
@@ -0,0 +1,254 @@
|
||||
{
|
||||
"schemaVersion": 1,
|
||||
"task": "PKG-ASR-04",
|
||||
"sourceReport": "refactor/.cache/asr-package-types-3KzGBO/report.json",
|
||||
"scope": "Observed strict installed consumers from frozen 2.0.0 and 2.1.0 archives with packed candidate core. Both old NodeNext ESM default imports are namespaces; direct-call diagnostics are retained, not counted as passing compatibility. Legal namespace consumers are verified separately.",
|
||||
"cases": [
|
||||
{
|
||||
"plugin": "published-2.0.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "node10-commonjs",
|
||||
"diagnostics": []
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.0.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "nodenext-cjs",
|
||||
"diagnostics": []
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.0.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "nodenext-esm",
|
||||
"diagnostics": [
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 26,
|
||||
"code": 2322,
|
||||
"message": "Type '{ length: number; interval: number; sampleRate: number; autoHideTimeout: number; onAudioChunk(chunk: any): void; }' is not assignable to type 'never'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 26,
|
||||
"code": 2344,
|
||||
"message": "Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' does not satisfy the constraint '(...args: any) => any'.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' provides no match for the signature '(...args: any): any'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 31,
|
||||
"code": 7006,
|
||||
"message": "Parameter 'chunk' implicitly has an 'any' type."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 37,
|
||||
"code": 2322,
|
||||
"message": "Type 'undefined' is not assignable to type 'never'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 37,
|
||||
"code": 2344,
|
||||
"message": "Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' does not satisfy the constraint '(...args: any) => any'.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' provides no match for the signature '(...args: any): any'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 39,
|
||||
"code": 2344,
|
||||
"message": "Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' does not satisfy the constraint '(...args: any) => any'.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' provides no match for the signature '(...args: any): any'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 46,
|
||||
"code": 2322,
|
||||
"message": "Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' is not assignable to type 'PublishedFactory'.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' provides no match for the signature '(option?: PublishedOption | undefined): (art: Artplayer) => PublishedResult'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 47,
|
||||
"code": 2322,
|
||||
"message": "Type 'PublishedFactory' is not assignable to type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 48,
|
||||
"code": 2322,
|
||||
"message": "Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' is not assignable to type 'PublishedFactory'.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' provides no match for the signature '(option?: PublishedOption | undefined): (art: Artplayer) => PublishedResult'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 49,
|
||||
"code": 2349,
|
||||
"message": "This expression is not callable.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' has no call signatures."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 49,
|
||||
"code": 2349,
|
||||
"message": "This expression is not callable.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' has no call signatures."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 49,
|
||||
"code": 2349,
|
||||
"message": "This expression is not callable.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' has no call signatures."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 49,
|
||||
"code": 2349,
|
||||
"message": "This expression is not callable.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' has no call signatures."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 50,
|
||||
"code": 2349,
|
||||
"message": "This expression is not callable.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' has no call signatures."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 54,
|
||||
"code": 2339,
|
||||
"message": "Property 'onAudioChunk' does not exist on type 'never'."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.0.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "bundler-esm",
|
||||
"diagnostics": []
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.0.0",
|
||||
"compiler": "4.3.5",
|
||||
"mode": "node10-commonjs",
|
||||
"diagnostics": []
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.1.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "node10-commonjs",
|
||||
"diagnostics": []
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.1.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "nodenext-cjs",
|
||||
"diagnostics": []
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.1.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "nodenext-esm",
|
||||
"diagnostics": [
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 26,
|
||||
"code": 2322,
|
||||
"message": "Type '{ length: number; interval: number; sampleRate: number; autoHideTimeout: number; onAudioChunk(chunk: any): void; }' is not assignable to type 'never'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 26,
|
||||
"code": 2344,
|
||||
"message": "Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' does not satisfy the constraint '(...args: any) => any'.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' provides no match for the signature '(...args: any): any'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 31,
|
||||
"code": 7006,
|
||||
"message": "Parameter 'chunk' implicitly has an 'any' type."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 37,
|
||||
"code": 2322,
|
||||
"message": "Type 'undefined' is not assignable to type 'never'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 37,
|
||||
"code": 2344,
|
||||
"message": "Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' does not satisfy the constraint '(...args: any) => any'.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' provides no match for the signature '(...args: any): any'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 39,
|
||||
"code": 2344,
|
||||
"message": "Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' does not satisfy the constraint '(...args: any) => any'.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' provides no match for the signature '(...args: any): any'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 46,
|
||||
"code": 2322,
|
||||
"message": "Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' is not assignable to type 'PublishedFactory'.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' provides no match for the signature '(option?: PublishedOption | undefined): (art: Artplayer) => PublishedResult'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 47,
|
||||
"code": 2322,
|
||||
"message": "Type 'PublishedFactory' is not assignable to type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 48,
|
||||
"code": 2322,
|
||||
"message": "Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' is not assignable to type 'PublishedFactory'.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' provides no match for the signature '(option?: PublishedOption | undefined): (art: Artplayer) => PublishedResult'."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 49,
|
||||
"code": 2349,
|
||||
"message": "This expression is not callable.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' has no call signatures."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 49,
|
||||
"code": 2349,
|
||||
"message": "This expression is not callable.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' has no call signatures."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 49,
|
||||
"code": 2349,
|
||||
"message": "This expression is not callable.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' has no call signatures."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 49,
|
||||
"code": 2349,
|
||||
"message": "This expression is not callable.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' has no call signatures."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 50,
|
||||
"code": 2349,
|
||||
"message": "This expression is not callable.\n Type 'typeof import(\"<consumer>/node_modules/artplayer-plugin-asr/types/artplayer-plugin-asr\")' has no call signatures."
|
||||
},
|
||||
{
|
||||
"file": "consumer.mts",
|
||||
"line": 54,
|
||||
"code": 2339,
|
||||
"message": "Property 'onAudioChunk' does not exist on type 'never'."
|
||||
}
|
||||
]
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.1.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "bundler-esm",
|
||||
"diagnostics": []
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.1.0",
|
||||
"compiler": "4.3.5",
|
||||
"mode": "node10-commonjs",
|
||||
"diagnostics": []
|
||||
}
|
||||
],
|
||||
"fixtures": {
|
||||
"refactor/fixtures/consumers/asr-published.ts": "7611ab9ef9765fe6a6ca5112589228d49012400bf0b9d9cede96ead8e63cffc2",
|
||||
"refactor/fixtures/consumers/asr-esm-namespace.ts": "1e3b7475452f43f71e4e038c17368860fe2bc00a61451397fe609e9a3e078d98"
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,363 @@
|
||||
{
|
||||
"schemaVersion": 1,
|
||||
"task": "PKG-ASR-04",
|
||||
"capturedAt": "2026-09-13T07:06:14.836Z",
|
||||
"baseCommit": "0cf2af48400908fbe4217259e7d9fd37c1e15d1f",
|
||||
"runtimeChanged": false,
|
||||
"dependenciesAdded": [],
|
||||
"versionChanged": false,
|
||||
"installation": {
|
||||
"node": "v24.21.0",
|
||||
"yarn": "1.22.22",
|
||||
"outsideWorkspace": true,
|
||||
"offline": true,
|
||||
"frozenReinstall": true,
|
||||
"installedHashesVerified": true,
|
||||
"workspaceLinks": false,
|
||||
"runtimeExportsExecuted": true,
|
||||
"packages": [
|
||||
{
|
||||
"name": "artplayer",
|
||||
"archive": "D:\\github\\ArtPlayer\\refactor\\.cache\\asr-package-types-nlZPaL\\artplayer.tgz",
|
||||
"sha256": "0c0ea52d41575261b836aefac68280733b119c75834ecad6d4bc78edb073f4c1",
|
||||
"files": {
|
||||
"package/ARCHITECTURE.md": "bee98fc9d93a3911d58e98ef15f2dbe07e12f2274c444d989094248a22079e46",
|
||||
"package/README.md": "1e185e65f67fc2081b4182bbc6c4558ea05b6e3fa3acc5dd0c3ac7df1d542b09",
|
||||
"package/THIRD_PARTY_NOTICES": "b77b5b46b79fa0cda850b0781f78c3b1112c4ed9672fa291956fe8eff53098e7",
|
||||
"package/dist/artplayer.js": "6dc8ca6d6eb34aa8a056cbc31328efd634530b3c5c60f0014cb7ce719fabc335",
|
||||
"package/dist/artplayer.legacy.js": "80f74a8a39df4baf64cc00c65d21cd57c011bfcdead0da38eea077fbc67c5c04",
|
||||
"package/dist/artplayer.mjs": "432e2b0ad92009a09743e020bf7c928c8b8f18a52496622b16259ec9ab20059f",
|
||||
"package/dist/i18n/ar.js": "bd0bef65f4f7dc3f8ed562904cc6fa9071ff4537fb64c1e0fc3d554141bcd3cb",
|
||||
"package/dist/i18n/ar.mjs": "59310b7bbeea83bbb7d73aadc5ca82a6ec269c3530d19aa741c94d5c64fc5da8",
|
||||
"package/dist/i18n/cs.js": "6e2c93daba24c2e48dfa206bcf4f2f2a8a02713b856e404d2e4e4ecd8309ca2f",
|
||||
"package/dist/i18n/cs.mjs": "c73fba18797d62d7b2581e67fe7340c35fe84510b2250ff1ecaad253d9cabbac",
|
||||
"package/dist/i18n/es.js": "f4133ac6ea06b69a474b33c4a1809a4066e2376bb9464a3f3aa8330f01f1944a",
|
||||
"package/dist/i18n/es.mjs": "1390bca3def2be115e811de337df0a0c3f63998e51359f283023246245c552a7",
|
||||
"package/dist/i18n/fa.js": "8d3ef2e0f0cc0ea480c2167b6fcb87cdf444e90759c3519e8daa139fec576da4",
|
||||
"package/dist/i18n/fa.mjs": "ab441e8a2d79043b29ceca87c783bf06874bb9d3a149c1604bc167eb481be2a9",
|
||||
"package/dist/i18n/fr.js": "89dc4194a6c0a962b9ce756b52c90401c1acf3b159f265f3bc0d7d6d7d987f03",
|
||||
"package/dist/i18n/fr.mjs": "99491878430fb7b6f2b7bf93da0588a831704b412e01116f23ba1d9d45863816",
|
||||
"package/dist/i18n/id.js": "4c6dc86db741bcc2857df55a9d037e82e91d375fa6fd22e0562809ff621b92db",
|
||||
"package/dist/i18n/id.mjs": "383e5803a6b6686c6de4e867770241de75b6f517dcca2bdedc6f2004bf6e1fb3",
|
||||
"package/dist/i18n/pl.js": "3a38828b1c3d719c0aca9906cf6a46c23555a8411f8d57645f0e0ce8147dc664",
|
||||
"package/dist/i18n/pl.mjs": "079ed96732979035297af387c64a7b99519b5a43107fb86735a654ea4fe8e9b5",
|
||||
"package/dist/i18n/ru.js": "62fac9dddb302eb16382e6e9301fc4b2c66f5f69d4a358a26b67026a5fa4e787",
|
||||
"package/dist/i18n/ru.mjs": "a893aeaee1d79409db72e324fbff200e3864f33ed168f04d91d25f7cf2efa765",
|
||||
"package/dist/i18n/tr.js": "1492c36b069a7d73db4f3913bd18085faff7afd8b3c158138fe264e31600e38c",
|
||||
"package/dist/i18n/tr.mjs": "a90478cac078836b76c2a98261907610fee07f3e4b28671b8e7dbf533778f918",
|
||||
"package/dist/i18n/vi.js": "c7216ef7e608a79b7e2c479a07bf310d4ab79577947ac4a62d676faaced0e9cf",
|
||||
"package/dist/i18n/vi.mjs": "66270fdfa0b5da396322d1769169b7df37a030ba15ac18eb30bd87b3af8074ec",
|
||||
"package/dist/i18n/zh-tw.js": "11c49857d6d40a5ffd224ffa59c9026e71621b345f63c5a086326db80a22371a",
|
||||
"package/dist/i18n/zh-tw.mjs": "a38e630cb96de96c15d824686aec750e25cf6c8ada01285a292442a81566314f",
|
||||
"package/package.json": "82e92699e7c29847f32ac6767ece0401290e7d7a12854722bdbcfd09b90b7954",
|
||||
"package/types/COMPATIBILITY.md": "a7da9e102a116104b513df4f7451247b7759bc502d3375f30bd5b14a541826e0",
|
||||
"package/types/README.md": "1bd9868e773610e6312fd48a1c5aa20772d29df0af40c3db66e75b7ab4a1aee0",
|
||||
"package/types/artplayer.d.cts": "3685065e4263abcfd9d953176e461d5b3eb990b0363b54689a7f55deba770fef",
|
||||
"package/types/artplayer.d.mts": "b664fec51ee5c5381f2ceab25d99d52aee56feab04a2ee7b4ea5b2145ea5fa0e",
|
||||
"package/types/artplayer.d.ts": "5d0162adf7ac6d0f2bb9b5cfe361f28657c4d9c540cadbf36eba3cc954ce50f8",
|
||||
"package/types/component.d.ts": "ae5bc1ddeaa1ee1ebbc62573e32423993727079205c64751a5a314170e588a32",
|
||||
"package/types/config.d.ts": "36f9a84cd436f17701a0d11d3417fc1fe0414e0c52c80083b94a85dfc329e37e",
|
||||
"package/types/cssVar.d.ts": "93217860fff2ebf750f606d95ddd22220a58837119e63bdf2f5f78fd7488458b",
|
||||
"package/types/emitter.d.ts": "7e1f9a2a8ce65feb95734f1ed52d1334e57aa388bbef2a43d8bc53a9b6f6623c",
|
||||
"package/types/events.d.ts": "f83624c9268a284477e8bd793fe3562a2363b72f2a44d5c64fe8c6a6cede8830",
|
||||
"package/types/i18n.d.ts": "f4f2f05bdfda73c74fef34767cb18ee8e11b743120b1c4598e9714d7846018e5",
|
||||
"package/types/icons.d.ts": "326a67ba7bdcf52862c5b2a269e540140aff98d05c7b96196485a77f84fe5960",
|
||||
"package/types/language.d.cts": "f7928e108cf7b7814c2d75cb0a525333e95873fca6cd6d89a740450656b9c1cd",
|
||||
"package/types/language.d.mts": "6619a26d604b7cccbe2f596243d87ae37cfaae33b8b52874ec071d9787446f9e",
|
||||
"package/types/legacy/language.d.ts": "c7abda4d506fd933c350e9030290bf9e64347a921d683a66115da1995ebe0a81",
|
||||
"package/types/option.d.ts": "ccf2c8ddc537dc65c9682d39f044726e23bff18f476b622512d7e6a4b949b5f6",
|
||||
"package/types/playback.d.ts": "58705c273df6e76a77a6575e769a9ec6c013785c25080f2551aa22415788d870",
|
||||
"package/types/player.d.ts": "92b00211b70ac71336e495899df972a0519dd138111846044fe4e0f967966177",
|
||||
"package/types/plugin.d.ts": "fc3594a41c51d8248713e33c486fb1f6a518ac5c7ce31be6988a6cd8d052c5f3",
|
||||
"package/types/quality.d.ts": "1ac1a48b4f74ff9ba1ce60443e1463d50d1c6a2e5d87d63dc7d2a8eb7f4c2c34",
|
||||
"package/types/runtime.d.cts": "7ee988dfea9a0ac71a34a656f96f7b74e78aa92547cfdfab7ff7e1139a77d4a3",
|
||||
"package/types/runtime.d.mts": "dcb85f59a8b7714918ced0c1d18c2bb24e8b80b56d8c594e019dcbdb5ad88b08",
|
||||
"package/types/runtime.d.ts": "9c6ccd39a1be293f17ae46dae8ea077053e12635ee79d73a5e3b3a559230fcff",
|
||||
"package/types/runtime/component.d.ts": "1b4c0cee44568649e80140fe778febfcae88af0ac85515f1cbeff78ab0c6d14f",
|
||||
"package/types/runtime/construction.d.ts": "7a87bedf6f7ffff0c46078aa5f1551e0077d35574e286516121f5f935e2d9ce4",
|
||||
"package/types/runtime/events.d.ts": "a1e2f9d387475453eaf95c2a5ee79e228636c0bb859bda3fcc46da46574a0c31",
|
||||
"package/types/runtime/media.d.ts": "8fc89401be7fe25542c169d07dd5675f10916ed20be8493e19695966cf3864a8",
|
||||
"package/types/runtime/option.d.ts": "6e334e1a76fdcc40b4665c02523bd31c3994d96078fadeb40e23422aa54c1a1d",
|
||||
"package/types/runtime/player.d.ts": "8ac6383502e4872e83659838844856903031a81a0adc8e8535feb78453aa042c",
|
||||
"package/types/runtime/plugin.d.ts": "8528f2b17843149f42f9cc16d6fd70baa238c9dc2c329b67d2c38096799c69bd",
|
||||
"package/types/runtime/services.d.ts": "604c9f8e4b6c0da818f96576bf9f4b0e96085a9003927b2f7ba30027b1ba237e",
|
||||
"package/types/runtime/setting.d.ts": "349c1fcb205ad312916bd3ee55e6bf241ea8a569fb2ab6c80822e69fc518f7d7",
|
||||
"package/types/runtime/subtitle.d.ts": "269ff84678d327b3a9dc2f5bc6cc0d731d1e081b85422e474621d5d792efb153",
|
||||
"package/types/runtime/template.d.ts": "7a62f968a38b4bf9109a4439557c02074eb1d62ba1f6e21a8eb194e91f0badfe",
|
||||
"package/types/runtime/utils.d.ts": "6bf731705d86853e066dbaf3b8d4003b6548423fe615b7412b722bd0d3a6e48b",
|
||||
"package/types/setting.d.ts": "08305a75dff96f06490430e099338b463df471b550c1d0dac3abc8995b39eb09",
|
||||
"package/types/subtitle.d.ts": "b18314e2d64efdb6045830b6e12f615ae2ed585416130e562329ad3ea337f6ce",
|
||||
"package/types/template.d.ts": "4792bc0c2cbcb7966e4375118bd34b326166e0831862e94ace4cf6b1bbe6a8c8",
|
||||
"package/types/utils.d.ts": "fca0d3d814df94a25f9eb067c86fa0cf272e2791bac793b91229d57680797712"
|
||||
}
|
||||
},
|
||||
{
|
||||
"name": "artplayer-plugin-asr",
|
||||
"archive": "D:\\github\\ArtPlayer\\refactor\\.cache\\asr-package-types-nlZPaL\\artplayer-plugin-asr.tgz",
|
||||
"sha256": "d784829c8fbc06f78d8a7647ef3530cec1cf3f5157a053bfbc58111d772eb543",
|
||||
"files": {
|
||||
"package/ARCHITECTURE.md": "a46a1abf28a4c783a4cec2983c4ba276b7e9e33e8446d811cc9c49c1f5231ef8",
|
||||
"package/README.md": "d8eec6fafd308a3f52c16548a27ea07c2cb247d950b3e155d94f98e010e6b994",
|
||||
"package/dist/artplayer-plugin-asr.js": "533b60d6348764fa460c2436cc1197b95544051fb4d1ec4d950fec9f88e1c5cb",
|
||||
"package/dist/artplayer-plugin-asr.legacy.js": "c36ebbea3a4e5f30b2736ffb6a964d45e330b0911f51e32d9cab44397ec16912",
|
||||
"package/dist/artplayer-plugin-asr.mjs": "751201241a848cdc26235334ce7603b174a90bf4ac793ff3f85182b1783f6996",
|
||||
"package/package.json": "781b1eebefdff5fdc234b793ff9d6d8263275115ccff4c4d90c55eca942f2444",
|
||||
"package/types/artplayer-plugin-asr.d.ts": "8fce55a45c368dc95fc6169750d2157ad57f683f62b586b8162ac720e1efdf42",
|
||||
"package/types/runtime.d.cts": "2965dccc49a3a75c3b16c0c13501077b8ac199e78bac2d19d57be3d811583606",
|
||||
"package/types/runtime.d.mts": "ff0769d3e408d66c7d38574171ff2621456afccc50ee8191ca4ee394dc57666e",
|
||||
"package/types/runtime.d.ts": "2965dccc49a3a75c3b16c0c13501077b8ac199e78bac2d19d57be3d811583606"
|
||||
}
|
||||
}
|
||||
],
|
||||
"published": [
|
||||
{
|
||||
"label": "published-2.0.0",
|
||||
"archive": "D:\\github\\ArtPlayer\\refactor\\.cache\\releases\\artplayer-plugin-asr-2.0.0.tgz",
|
||||
"sha256": "faa726b9536306664d935c95367230e0c622bd046faf636fc2dcef4bbce4cd47"
|
||||
},
|
||||
{
|
||||
"label": "published-2.1.0",
|
||||
"archive": "D:\\github\\ArtPlayer\\refactor\\.cache\\releases\\artplayer-plugin-asr-2.1.0.tgz",
|
||||
"sha256": "8bc3cd93f78ce99e5c09cc546c770a63e8aea5729d3d584134ce04d826b7708b"
|
||||
}
|
||||
]
|
||||
},
|
||||
"strict": {
|
||||
"skipLibCheck": false,
|
||||
"ambientTypes": [],
|
||||
"sourceProjects": [
|
||||
"tsconfig.json",
|
||||
"packages/artplayer-plugin-asr/tsconfig.json"
|
||||
],
|
||||
"installedResolution": "Only isolated consumer and executing compiler standard libraries",
|
||||
"compilerVersions": [
|
||||
"5.9.3",
|
||||
"4.3.5"
|
||||
]
|
||||
},
|
||||
"matrix": [
|
||||
{
|
||||
"plugin": "published-2.0.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "node10-commonjs",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 0,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.0.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "nodenext-cjs",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 0,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.0.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "nodenext-esm",
|
||||
"validConsumerDiagnostics": 15,
|
||||
"invalidStatementsRejected": 0,
|
||||
"originalDirectDiagnostics": 15,
|
||||
"namespaceChecked": true,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.0.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "bundler-esm",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 0,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.0.0",
|
||||
"compiler": "4.3.5",
|
||||
"mode": "node10-commonjs",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 0,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.1.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "node10-commonjs",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 0,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.1.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "nodenext-cjs",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 0,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.1.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "nodenext-esm",
|
||||
"validConsumerDiagnostics": 15,
|
||||
"invalidStatementsRejected": 0,
|
||||
"originalDirectDiagnostics": 15,
|
||||
"namespaceChecked": true,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.1.0",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "bundler-esm",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 0,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "published-2.1.0",
|
||||
"compiler": "4.3.5",
|
||||
"mode": "node10-commonjs",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 0,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "candidate",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "node10-commonjs",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 12,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "candidate",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "nodenext-cjs",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 12,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "candidate",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "nodenext-esm",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 12,
|
||||
"originalDirectDiagnostics": 15,
|
||||
"namespaceChecked": true,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "candidate",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "bundler-esm",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 12,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "candidate",
|
||||
"compiler": "4.3.5",
|
||||
"mode": "node10-commonjs",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 12,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "candidate",
|
||||
"compiler": "5.9.3",
|
||||
"mode": "node10-commonjs-no-interop",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 12,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
},
|
||||
{
|
||||
"plugin": "candidate",
|
||||
"compiler": "4.3.5",
|
||||
"mode": "node10-commonjs-no-interop",
|
||||
"validConsumerDiagnostics": 0,
|
||||
"invalidStatementsRejected": 12,
|
||||
"originalDirectDiagnostics": 0,
|
||||
"namespaceChecked": false,
|
||||
"namespaceDiagnostics": 0
|
||||
}
|
||||
],
|
||||
"historicalLimits": "Both old releases have 15 NodeNext ESM direct-call diagnostics. These are frozen in asr-type-diagnostics.json and remain on candidate root; legal namespace consumers pass all three packages. Runtime ESM default import is accurate through the additive /runtime entry.",
|
||||
"correctedDuringReview": [
|
||||
"Added missing runtime named type exports to CommonJS/Node10 declarations",
|
||||
"Retained original root namespace declarations after detecting replacement-object incompatibility",
|
||||
"Excluded implementation tsconfig from actual package",
|
||||
"Used a compiler-portable invalid buffer example; old TS typed-array structural acceptance is not claimed as rejection"
|
||||
],
|
||||
"inputs": {
|
||||
"packages/artplayer-plugin-asr/.npmignore": "145c5fa0341195e21cf13df3423a057282f8ea374e9a1b3065e2280e1ce1c5c1",
|
||||
"packages/artplayer-plugin-asr/package.json": "781b1eebefdff5fdc234b793ff9d6d8263275115ccff4c4d90c55eca942f2444",
|
||||
"packages/artplayer-plugin-asr/tsconfig.json": "583e4ac1afa99e3a29c7f899df9fdeefcbd14d3847d69143e3fa6a8facac6d99",
|
||||
"packages/artplayer-plugin-asr/types/artplayer-plugin-asr.d.ts": "dca6dfb5a6b6d58a891412c29d857214c95834e60bdabf0aa9d2fec48f31ec12",
|
||||
"packages/artplayer-plugin-asr/types/runtime.d.ts": "2965dccc49a3a75c3b16c0c13501077b8ac199e78bac2d19d57be3d811583606",
|
||||
"packages/artplayer-plugin-asr/types/runtime.d.cts": "2965dccc49a3a75c3b16c0c13501077b8ac199e78bac2d19d57be3d811583606",
|
||||
"packages/artplayer-plugin-asr/types/runtime.d.mts": "ff0769d3e408d66c7d38574171ff2621456afccc50ee8191ca4ee394dc57666e",
|
||||
"refactor/scripts/asr-package-types.mjs": "00de7c03cba39bed912933d58d686fb0b4aea374944c460ee70a7e404119d259",
|
||||
"refactor/fixtures/consumers/asr-published.ts": "7611ab9ef9765fe6a6ca5112589228d49012400bf0b9d9cede96ead8e63cffc2",
|
||||
"refactor/fixtures/consumers/asr-esm-namespace.ts": "1e3b7475452f43f71e4e038c17368860fe2bc00a61451397fe609e9a3e078d98",
|
||||
"test/types/asr-public.ts": "19eac65cf88ccf908f175dc03243f6933b62dfa3d254525501c2396a571c8843",
|
||||
"test/types/asr-source.ts": "f2541df4f4e7976a97fa9f31c730298e98fea4749eef2a2e098da539fbc240ca",
|
||||
"scripts/typecheck.mjs": "96b166178bada2ab2130af1ea422e01965cc6467746ecf605e87ec3b29068309",
|
||||
"package.json": "a95566e7e6825cda949428a71d11cbcc39c1ba3651fc631ed8511ca5e078d340"
|
||||
},
|
||||
"evidence": [
|
||||
{
|
||||
"file": "refactor/.cache/asr-package-types-nlZPaL/report.json",
|
||||
"sha256": "5b32bda6481f74a9db7fe68f54f36a9752deb2cbb8e56b2a42cdc061297b8df7"
|
||||
},
|
||||
{
|
||||
"file": "refactor/.cache/asr04-installed-final.log",
|
||||
"sha256": "cebbdebc4b5419f16e419a33e0ba5ae33102091c3dcfd2fb95d541f0e2640634"
|
||||
},
|
||||
{
|
||||
"file": "refactor/.cache/asr04-strict-final.log",
|
||||
"sha256": "0d6e90ea1b4dadf17e3dd5dee44c3894e17455e124d2a7ab31d5850249ec72b7"
|
||||
},
|
||||
{
|
||||
"file": "refactor/.cache/asr04-lint-final.log",
|
||||
"sha256": "e3b0c44298fc1c149afbf4c8996fb92427ae41e4649b934ca495991b7852b855"
|
||||
},
|
||||
{
|
||||
"file": "refactor/.cache/asr04-artifact-identity.log",
|
||||
"sha256": "0ad9dc4536c26e81edf671c68cc218aef044e3655bc1ba91afbcf42187783215"
|
||||
}
|
||||
],
|
||||
"unchangedRuntimeEvidence": "refactor/baselines/asr-ownership-validation.json",
|
||||
"limitation": [
|
||||
"No full CI or browser rerun for unchanged JS",
|
||||
"Node 24 actual installs only; full Node/OS distribution matrix remains later acceptance",
|
||||
"ASR-05 native fallback/volume/CORS/device evidence remains incomplete",
|
||||
"ASR-06 release documentation and distribution remains incomplete"
|
||||
],
|
||||
"releaseReady": false
|
||||
}
|
||||
@@ -0,0 +1,53 @@
|
||||
# PKG-ASR-04:ASR 公共类型与隔离安装
|
||||
|
||||
本任务延续 ASR-03 的 8 个严格 TS 模块,处理公共类型与安装边界。保留根入口及
|
||||
`/legacy` 的历史工厂形状,新增 `/runtime` 精确描述回调返回字幕、异步 stop。
|
||||
不改运行时 JS、不新增依赖、不修改版本;大版本与发布仍按后续任务统一执行。
|
||||
|
||||
## 兼容决策
|
||||
|
||||
- 根入口仍是原来的可选参数、同步注册、void stop、void/Promise<void> callback;
|
||||
旧工厂和插件结果可双向赋值,Parameters/ReturnType 提取也保留。
|
||||
- `/runtime` 加载同一 main/ESM 产物,只提供准确的类型入口:回调可同步或异步返回
|
||||
string/null/void,stop 返回 Promise<void>,工厂具有只读 self.default。
|
||||
不将 self.default 加到旧工厂类型,避免要求用户的替换函数提供额外属性。
|
||||
- root 与 runtime 都导出 AudioChunk/RuntimeOption/RuntimeResult/RuntimeFactory。
|
||||
runtime 的 ESM 使用 `.d.mts`,CommonJS/Node10 使用 export assignment。
|
||||
子代理发现后者漏了命名类型,已补纯类型 namespace 并加入四类型等价回归。
|
||||
- 旧根声明在 NodeNext ESM 下把 default import 描述成命名空间,合法的
|
||||
`asr.default()`、`namespace.default.default()` 和 `{default: factory}` 替换必须保留。
|
||||
原拟直接工厂 `.d.mts` 会破坏这些旧类型用法,已撤回;准确 ESM 默认导入用 `/runtime`。
|
||||
这是声明兼容测试,不能推断旧 JS 支持所有双层 default 调用。
|
||||
|
||||
包内 README 给出新入口用法,ARCHITECTURE 记录维护限制。实际打包发现 tsconfig
|
||||
泄漏,已补 `.npmignore`,保留所有历史 dist/types 文件。源码 TS 与测试不进入包。
|
||||
|
||||
## 验证与证据
|
||||
|
||||
`yarn test:asr-types-package` 实际打包核心与 ASR,在工作区外逐个安装 frozen
|
||||
2.0.0、2.1.0 及候选包。离线安装后用 frozen lockfile 再安装;检查锁文件不变、
|
||||
无工作区符号链接、全部包文件与 archive 哈希相符。类型程序只能读取该临时消费者
|
||||
及当前编译器标准库;strict、skipLibCheck:false、types:[],不靠 ambient 类型兜底。
|
||||
|
||||
- 2 个旧发布包各 5 种配置;每包 4 种直接用法通过,NodeNext ESM 原有 15 条诊断
|
||||
按完整消息冻结。合法 ESM 命名空间 fixture 在两个旧包及候选包均通过。
|
||||
- 候选 7 种配置:TS 5.9.3 Node10/NodeNext CJS/NodeNext ESM/Bundler,TS 4.3.5
|
||||
Node10,以及两编译器 Node10 关闭 interop。每种公共用法零诊断,12 项负例在
|
||||
各自语句行被拒绝;原 direct fixture 的 NodeNext ESM 诊断也与旧包一致。
|
||||
- 实际 Node 24.21.0 import/require 验证三候选入口、root/runtime 实现身份、
|
||||
self.default 不可枚举、legacy 默认导入身份;旧包验证各自 CJS 和 ESM 导出。
|
||||
- 根项目及 ASR 分包严格检查通过,source/public 类型边界加入持续检查。
|
||||
定向 ESLint 和台账测试通过,ASR 构建 JS 与 ASR-03 HEAD 逐字节相同。
|
||||
|
||||
类型反例中的 typed-array 与 ArrayBuffer 在旧 TS 标准库下结构可赋值,不能声称
|
||||
TS 4.3.5 会拒绝。负例使用所有目标编译器都应拒绝的字符串 buffer,保持公开
|
||||
ArrayBuffer 字段不变;没有通过缩窄字段或升级最低编译器绕过兼容性。
|
||||
|
||||
具体 archive、输入、日志哈希及矩阵摘要见
|
||||
[验证记录](../baselines/asr-types-validation.json),旧 direct 诊断见
|
||||
[冻结声明诊断](../baselines/asr-type-diagnostics.json)。此前 ASR-03 的音频/浏览器
|
||||
证据继续对应未变的 JS;本任务没有重复整仓 CI 或浏览器回归,也不声称完成真实
|
||||
fallback、音量/静音、CORS、物理设备或全 Node 版本验收。这些仍归 ASR-05/06。
|
||||
|
||||
子代理独立提供公共/历史消费者与声明审查,主代理修复声明、运行实际隔离安装、
|
||||
整合证据和提交。回退本任务移除新增类型入口与测试,不改变 ASR-03 运行时修复。
|
||||
@@ -0,0 +1,46 @@
|
||||
import type Artplayer from 'artplayer'
|
||||
import asr from 'artplayer-plugin-asr'
|
||||
import * as namespace from 'artplayer-plugin-asr'
|
||||
|
||||
// Compile this fixture as .mts with NodeNext: published declarations expose
|
||||
// a CommonJS declaration namespace even though the runtime import is ESM.
|
||||
interface HistoricalOption {
|
||||
length?: number
|
||||
interval?: number
|
||||
sampleRate?: number
|
||||
autoHideTimeout?: number
|
||||
onAudioChunk?: (chunk: { pcm: ArrayBuffer, wav: ArrayBuffer }) => void | Promise<void>
|
||||
}
|
||||
|
||||
interface HistoricalResult {
|
||||
name: 'artplayerPluginAsr'
|
||||
stop: () => void
|
||||
hide: () => void
|
||||
append: (subtitle: string) => void
|
||||
}
|
||||
|
||||
type HistoricalFactory = (option?: HistoricalOption) => (art: Artplayer) => HistoricalResult
|
||||
interface HistoricalModule { default: HistoricalFactory }
|
||||
const result: ReturnType<ReturnType<typeof asr.default>> = {
|
||||
name: 'artplayerPluginAsr',
|
||||
stop() {},
|
||||
hide() {},
|
||||
append(_subtitle: string) {},
|
||||
}
|
||||
const replacementFactory: HistoricalFactory = (_option?: HistoricalOption) => (_art: Artplayer) => result
|
||||
const replacementModule: typeof asr = { default: replacementFactory }
|
||||
const assignToOld: HistoricalModule = asr
|
||||
const assignFromOld: typeof asr = assignToOld
|
||||
const namespaceModule: typeof namespace.default = replacementModule
|
||||
const factoryToOld: HistoricalFactory = asr.default
|
||||
const factoryFromOld: typeof asr.default = replacementFactory
|
||||
const option: Parameters<typeof asr.default>[0] = {
|
||||
onAudioChunk: async (_chunk): Promise<void> => {},
|
||||
}
|
||||
const absent: Parameters<typeof namespace.default.default>[0] = undefined
|
||||
declare const art: Artplayer
|
||||
const installed: HistoricalResult = asr.default(option)(art)
|
||||
const namespaceResult: HistoricalResult = namespace.default.default(absent)(art)
|
||||
const stop: void = installed.stop()
|
||||
const append: void = namespaceResult.append('Old namespace import.')
|
||||
void [assignFromOld, namespaceModule, factoryToOld, factoryFromOld, stop, append]
|
||||
@@ -0,0 +1,55 @@
|
||||
import Artplayer from 'artplayer'
|
||||
import asr from 'artplayer-plugin-asr'
|
||||
import * as namespace from 'artplayer-plugin-asr'
|
||||
|
||||
interface PublishedChunk {
|
||||
pcm: ArrayBuffer
|
||||
wav: ArrayBuffer
|
||||
}
|
||||
|
||||
interface PublishedOption {
|
||||
length?: number
|
||||
interval?: number
|
||||
sampleRate?: number
|
||||
autoHideTimeout?: number
|
||||
onAudioChunk?: (chunk: PublishedChunk) => void | Promise<void>
|
||||
}
|
||||
|
||||
interface PublishedResult {
|
||||
name: 'artplayerPluginAsr'
|
||||
stop: () => void
|
||||
hide: () => void
|
||||
append: (subtitle: string) => void
|
||||
}
|
||||
|
||||
type PublishedFactory = (option?: PublishedOption) => (art: Artplayer) => PublishedResult
|
||||
const option: Parameters<typeof asr>[0] = {
|
||||
length: 3,
|
||||
interval: 100,
|
||||
sampleRate: 16000,
|
||||
autoHideTimeout: 10000,
|
||||
onAudioChunk(chunk) {
|
||||
const pcm: ArrayBuffer = chunk.pcm
|
||||
const wav: ArrayBuffer = chunk.wav
|
||||
void [pcm, wav]
|
||||
},
|
||||
}
|
||||
const empty: Parameters<typeof asr>[0] = undefined
|
||||
const asyncOption: PublishedOption = { onAudioChunk: async (_chunk: PublishedChunk): Promise<void> => {} }
|
||||
const result: ReturnType<ReturnType<typeof asr>> = {
|
||||
name: 'artplayerPluginAsr',
|
||||
stop() {},
|
||||
hide() {},
|
||||
append(_subtitle: string) {},
|
||||
}
|
||||
const replacement: PublishedFactory = (_option?: PublishedOption) => (_art: Artplayer) => result
|
||||
const assignToOld: PublishedFactory = asr
|
||||
const assignFromOld: typeof asr = replacement
|
||||
const namespaceFactory: PublishedFactory = namespace.default
|
||||
const art = new Artplayer({ container: '#player', url: '/video.mp4', plugins: [asr(option), asr(asyncOption), asr(), namespace.default(empty)] })
|
||||
const installed: PublishedResult = asr(option)(art)
|
||||
const stop: void = installed.stop()
|
||||
const hide: void = installed.hide()
|
||||
const append: void = installed.append('Historical subtitle.')
|
||||
const callback: ((chunk: PublishedChunk) => void | Promise<void>) | undefined = option.onAudioChunk
|
||||
void [assignToOld, assignFromOld, namespaceFactory, stop, hide, append, callback]
|
||||
+3
-2
@@ -4,7 +4,7 @@
|
||||
|
||||
基线:`40fcda6a37d0049d42e49c1e64e70d4fd9ba5f7f`。总任务 225 项,范围 22 个包及工作区/示例。
|
||||
|
||||
状态:todo 83 / doing 16 / blocked 0 / done 126 / deferred 0。风险 L/M/H 表示兼容风险,不表示工期。
|
||||
状态:todo 82 / doing 16 / blocked 0 / done 127 / deferred 0。风险 L/M/H 表示兼容风险,不表示工期。
|
||||
|
||||
前置依赖是启动条件;验收是完成条件。任务可以继续拆分,但不能复用或悄悄删除旧 ID。
|
||||
|
||||
@@ -254,7 +254,7 @@
|
||||
| PKG-ASR-01 | artplayer-plugin-asr<br>核对包契约与历史用法 | BASE-05 | length/interval/sampleRate/onAudioChunk、append/hide/stop 的真实能力 | 源码/声明/README/demo/发布包差异已登记;公开形状和版本范围冻结 | H | done |
|
||||
| PKG-ASR-02 | artplayer-plugin-asr<br>建立特有行为与错误测试 | PKG-ASR-01, ENG-03, ENG-05 | PCM/WAV、chunk 时序、回调慢/拒绝、重复初始化与停止 | 旧版本行为可重跑,成功/失败/切源/销毁有必要断言 | H | done |
|
||||
| PKG-ASR-03 | artplayer-plugin-asr<br>整理内部职责与资源 | PKG-ASR-02, CORE-10, CORE-18 | AudioContext/Worklet/Stream 生命周期和背压分离 | 结构变化和缺陷修复分开记录;原 API/事件/资源生命周期通过 | H | done |
|
||||
| PKG-ASR-04 | artplayer-plugin-asr<br>迁移自有源码和公开类型 | PKG-ASR-03, ENG-04, ENG-06, CORE-07 | 主线程/Worklet/音频 buffer 与异步回调类型 | 严格类型检查、旧消费样例通过;声明路径/导出和同步异步兼容 | H | todo |
|
||||
| PKG-ASR-04 | artplayer-plugin-asr<br>迁移自有源码和公开类型 | PKG-ASR-03, ENG-04, ENG-06, CORE-07 | 主线程/Worklet/音频 buffer 与异步回调类型 | 严格类型检查、旧消费样例通过;声明路径/导出和同步异步兼容 | H | done |
|
||||
| PKG-ASR-05 | artplayer-plugin-asr<br>验证新旧核心和组合 | PKG-ASR-04, CORE-22 | 真实 WebAudio 分块、播放暂停/切源/销毁,不引入网络 ASR | 最终核心与原支持范围核心分别通过;设备/SDK 缺证据不能标完成 | H | todo |
|
||||
| PKG-ASR-06 | artplayer-plugin-asr<br>验证分发并同步文档 | PKG-ASR-05, ENG-07 | asr.js、Worklet 资源、输出格式与声明证据 | tarball 入口/资源、类型、8082 demo 和 README 一致,有回退记录 | H | todo |
|
||||
|
||||
@@ -529,6 +529,7 @@
|
||||
- PKG-ASR-01: [记录](changes/2026-09-13-PKG-ASR-01-contracts.md) [记录](baselines/asr-contract.md) [记录](baselines/asr-release.json)
|
||||
- PKG-ASR-02: [记录](changes/2026-09-13-PKG-ASR-02-audio-baseline.md) [记录](baselines/asr-audio-validation.json)
|
||||
- PKG-ASR-03: [记录](changes/2026-09-13-PKG-ASR-03-audio-ownership.md) [记录](baselines/asr-ownership-validation.json)
|
||||
- PKG-ASR-04: [记录](changes/2026-09-13-PKG-ASR-04-public-types.md) [记录](baselines/asr-types-validation.json) [记录](baselines/asr-type-diagnostics.json)
|
||||
- PKG-ADS-01: [记录](baselines/ads-release.json) [记录](baselines/ads-contract.md) [记录](baselines/ads-contract-validation.json) [记录](changes/2026-09-12-PKG-ADS-01-contract.md) [记录](scripts/ads-contract.test.mjs)
|
||||
- PKG-ADS-02: [记录](changes/2026-09-12-PKG-ADS-02-tests.md) [记录](ads-validation.md) [记录](baselines/ads-validation.json)
|
||||
- PKG-ADS-03: [记录](changes/2026-09-12-PKG-ADS-03-lifecycle.md) [记录](ads-validation.md) [记录](baselines/ads-lifecycle-validation.json)
|
||||
|
||||
@@ -1,5 +1,19 @@
|
||||
# 进度与证据
|
||||
|
||||
## PKG-ASR-04 公共类型与安装兼容完成
|
||||
|
||||
保留根入口及 legacy 的旧工厂、void stop 和 NodeNext ESM 命名空间形状;新增
|
||||
runtime 精确类型入口,描述字幕回调与 Promise stop。子代理补消费者并发现
|
||||
CommonJS 命名类型遗漏、旧 ESM 替换对象兼容风险,均修复后由主代理隔离安装验收。
|
||||
实际 2.0/2.1/候选共 17 配置:候选 7 配置通过,每种 12 负例按语句拒绝;两旧包
|
||||
各有 1 组原生 NodeNext direct 声明错误单独冻结,三个包的合法 namespace 用法通过。
|
||||
根/分包 strict、定向 lint、包字节与 frozen reinstall 检查通过,修复 tsconfig 打包泄漏。
|
||||
见[变更](changes/2026-09-13-PKG-ASR-04-public-types.md)与[证据](baselines/asr-types-validation.json)。
|
||||
225 项:127 done、16 doing、82 todo;205 风险,ASR-TYPE-01 闭环。
|
||||
下一步 ASR-05 原生 fallback/音量/跨源/设备组合与 ASR-06 发行;运行时 JS 未改,
|
||||
沿用 ASR-03 浏览器证据,本项不等于 ASR 整包发布验收,没有推送或发布。
|
||||
|
||||
|
||||
## PKG-ASR-03 TS 拆分与音频生命周期完成
|
||||
|
||||
生产源码拆为 8 个严格 TS 模块;队列保留半块/尾部,识别回调背压、拒绝恢复、
|
||||
|
||||
@@ -206,6 +206,6 @@
|
||||
| JASSUB-EXPORT-01 | open / 已复现 | JASSUB historical CommonJS object.default changes to a direct factory in 1.1.0 | PKG-JASSUB-04, PKG-JASSUB-06 |
|
||||
| CORE-DEFAULTS-SSR-01 | resolved / 已复现 | Reading static defaults throws when navigator is absent | CORE-25 |
|
||||
| ENG-DIST-PUBLIC-01 | resolved / 已复现 | Vite copied authored declarations into library distribution | ENG-12 |
|
||||
| ASR-TYPE-01 | open / 源码/产物事实 | ASR declarations omit asynchronous stop and callback text results | PKG-ASR-04 |
|
||||
| ASR-TYPE-01 | resolved / 已复现 | ASR declarations omit asynchronous stop and callback text results | PKG-ASR-04 |
|
||||
| ASR-CHUNK-01 | resolved / 已复现 | ASR tick discards underfilled chunks and overrun samples in source | PKG-ASR-02, PKG-ASR-03 |
|
||||
| ASR-LIFE-01 | resolved / 已复现 | ASR partial initialization, pause resume and stale callback cleanup need controlled evidence | PKG-ASR-02, PKG-ASR-03, PKG-ASR-05 |
|
||||
+11
-3
@@ -4545,8 +4545,8 @@
|
||||
{
|
||||
"id": "ASR-TYPE-01",
|
||||
"title": "ASR declarations omit asynchronous stop and callback text results",
|
||||
"confirmation": "source-observed",
|
||||
"status": "open",
|
||||
"confirmation": "reproduced",
|
||||
"status": "resolved",
|
||||
"owners": [
|
||||
"PKG-ASR-04"
|
||||
],
|
||||
@@ -4555,7 +4555,15 @@
|
||||
"refactor/baselines/asr-release.json"
|
||||
],
|
||||
"compatibleResolution": "Keep historical assignment compatibility while supplying accurate asynchronous consumption.",
|
||||
"closureCriteria": "Actual old/new installed TS consumers cover void callback, Promise<void>, returned text and factory substitution."
|
||||
"closureCriteria": "Actual old/new installed TS consumers cover void callback, Promise<void>, returned text and factory substitution.",
|
||||
"resolutionEvidence": [
|
||||
"refactor/changes/2026-09-13-PKG-ASR-04-public-types.md",
|
||||
"refactor/baselines/asr-types-validation.json",
|
||||
"refactor/scripts/asr-package-types.mjs",
|
||||
"test/types/asr-public.ts",
|
||||
"refactor/fixtures/consumers/asr-esm-namespace.ts"
|
||||
],
|
||||
"resolutionRationale": "Root/legacy preserve historical void callback and stop, factory substitution and legal NodeNext namespace shape. Additive runtime supplies text/null/void callbacks and Promise stop with consistent named types. Actual isolated 2.0/2.1/candidate installs, seven candidate compiler configurations and 12 per-mode invalid statements verify declarations. Existing old NodeNext direct-call diagnostics remain explicit, not candidate success."
|
||||
},
|
||||
{
|
||||
"id": "ASR-CHUNK-01",
|
||||
|
||||
@@ -0,0 +1,166 @@
|
||||
import assert from 'node:assert/strict'
|
||||
import fs from 'node:fs'
|
||||
import path from 'node:path'
|
||||
import process from 'node:process'
|
||||
import ts from 'typescript'
|
||||
import compat from 'typescript-compat'
|
||||
import { checkFiles, packedFiles } from '../../scripts/package-check.mjs'
|
||||
import { consumerDirectory, removeConsumer, run, workspace, writeJson } from '../../scripts/package-consumer.mjs'
|
||||
import { verifyAsrContract } from './asr-contract.mjs'
|
||||
import { hash, readMember } from './releases.mjs'
|
||||
|
||||
const publicFixture = fs.readFileSync(path.join(workspace, 'test/types/asr-public.ts'), 'utf8')
|
||||
const publishedFixture = fs.readFileSync(path.join(workspace, 'refactor/fixtures/consumers/asr-published.ts'), 'utf8')
|
||||
const standardModes = [[ts, 'node10-commonjs'], [ts, 'nodenext-cjs'], [ts, 'nodenext-esm'], [ts, 'bundler-esm'], [compat, 'node10-commonjs']]
|
||||
|
||||
function typecheck(consumer, compiler, mode, candidate) {
|
||||
const next = mode.startsWith('nodenext')
|
||||
const extension = next ? mode.endsWith('-cjs') ? 'cts' : 'mts' : 'ts'
|
||||
const filename = path.join(consumer, `consumer.${extension}`)
|
||||
const files = [filename]
|
||||
if (candidate && mode !== 'bundler-esm' && mode !== 'nodenext-esm') {
|
||||
const commonjs = path.join(consumer, `commonjs.${extension}`)
|
||||
fs.writeFileSync(commonjs, `import asr = require('artplayer-plugin-asr');
|
||||
import legacy = require('artplayer-plugin-asr/legacy');
|
||||
import runtime = require('artplayer-plugin-asr/runtime');
|
||||
import type Artplayer from 'artplayer';
|
||||
const replacement: typeof asr.default = () => (_art: Artplayer) => ({name: 'artplayerPluginAsr', stop() {}, hide() {}, append(_text: string) {}});
|
||||
const legacyReplacement: typeof legacy.default = replacement;
|
||||
asr.default(); legacy.default(); runtime({onAudioChunk: async () => 'Text.'}); runtime.default();
|
||||
declare const art: Artplayer;
|
||||
const stopped: Promise<void> = runtime()(art).stop();
|
||||
void [legacyReplacement, stopped];`)
|
||||
files.push(commonjs)
|
||||
}
|
||||
const options = {
|
||||
strict: true,
|
||||
noEmit: true,
|
||||
skipLibCheck: false,
|
||||
types: [],
|
||||
esModuleInterop: !mode.endsWith('-no-interop'),
|
||||
target: compiler.ScriptTarget.ES2020,
|
||||
lib: ['lib.es2020.d.ts', 'lib.dom.d.ts'],
|
||||
module: next ? compiler.ModuleKind.NodeNext : mode === 'bundler-esm' ? compiler.ModuleKind.ESNext : compiler.ModuleKind.CommonJS,
|
||||
moduleResolution: next ? compiler.ModuleResolutionKind.NodeNext : mode === 'bundler-esm' ? compiler.ModuleResolutionKind.Bundler : compiler.ModuleResolutionKind.NodeJs,
|
||||
}
|
||||
function compile(code) {
|
||||
fs.writeFileSync(filename, code)
|
||||
const program = compiler.createProgram(files, options)
|
||||
for (const file of program.getSourceFiles()) {
|
||||
const actual = fs.realpathSync(file.fileName)
|
||||
assert(actual.startsWith(fs.realpathSync(consumer) + path.sep)
|
||||
|| (program.isSourceFileDefaultLibrary(file) && path.dirname(actual) === fs.realpathSync(path.dirname(compiler.sys.getExecutingFilePath()))), `Types escaped installed consumer: ${actual}`)
|
||||
}
|
||||
return compiler.getPreEmitDiagnostics(program).map(item => ({
|
||||
file: item.file ? path.relative(consumer, item.file.fileName).replaceAll('\\', '/') : null,
|
||||
line: item.file && item.start !== undefined ? item.file.getLineAndCharacterOfPosition(item.start).line + 1 : null,
|
||||
code: item.code,
|
||||
message: compiler.flattenDiagnosticMessageText(item.messageText, '\n').replaceAll(consumer.replaceAll('\\', '/'), '<consumer>'),
|
||||
}))
|
||||
}
|
||||
let source = candidate
|
||||
? mode.endsWith('-no-interop') ? publicFixture.replace('import runtime from \'artplayer-plugin-asr/runtime\'', 'import runtime = require(\'artplayer-plugin-asr/runtime\')') : publicFixture
|
||||
: publishedFixture
|
||||
if (candidate && mode === 'nodenext-esm') {
|
||||
source = source
|
||||
.replace('import legacy from \'artplayer-plugin-asr\'', 'import legacyModule from \'artplayer-plugin-asr\'\nconst legacy = legacyModule.default')
|
||||
.replace('import legacyEntry from \'artplayer-plugin-asr/legacy\'', 'import legacyEntryModule from \'artplayer-plugin-asr/legacy\'\nconst legacyEntry = legacyEntryModule.default')
|
||||
.replace('namespace.default', 'namespace.default.default')
|
||||
}
|
||||
const diagnostics = compile(source)
|
||||
const invalid = candidate ? compile(source.replaceAll(/\/\/ @ts-expect-error[^\n]*\n/g, '')) : []
|
||||
if (candidate) {
|
||||
const expectedLines = []
|
||||
let line = 1
|
||||
for (const text of source.split('\n')) {
|
||||
if (text.startsWith('// @ts-expect-error'))
|
||||
expectedLines.push(line)
|
||||
else line++
|
||||
}
|
||||
assert.deepEqual(invalid.map(item => item.line).sort((a, b) => a - b), expectedLines, 'Each invalid statement must fail at its own line')
|
||||
}
|
||||
const published = candidate ? compile(publishedFixture) : diagnostics
|
||||
const namespace = mode === 'nodenext-esm' ? compile(fs.readFileSync(path.join(workspace, 'refactor/fixtures/consumers/asr-esm-namespace.ts'), 'utf8')) : []
|
||||
return { compiler: compiler.version, mode, diagnostics, invalid, published, namespace }
|
||||
}
|
||||
|
||||
async function main() {
|
||||
assert.equal(process.env.npm_config_user_agent?.split(' ')[0], 'yarn/1.22.22', 'Use yarn test:asr-types-package')
|
||||
const yarn = process.env.npm_execpath
|
||||
assert(yarn && fs.existsSync(yarn))
|
||||
const output = fs.mkdtempSync(path.join(workspace, 'refactor/.cache/asr-package-types-'))
|
||||
console.log(`ASR isolated package evidence: ${output}`)
|
||||
const contract = await verifyAsrContract()
|
||||
const expected = JSON.parse(fs.readFileSync(path.join(workspace, 'refactor/baselines/asr-type-diagnostics.json'), 'utf8'))
|
||||
for (const [file, digest] of Object.entries(expected.fixtures))
|
||||
assert.equal(hash(fs.readFileSync(path.join(workspace, file), 'utf8').replaceAll('\r\n', '\n')), digest, `Frozen ASR fixture changed: ${file}`)
|
||||
const packages = []
|
||||
for (const name of ['artplayer', 'artplayer-plugin-asr']) {
|
||||
const archive = path.join(output, `${name}.tgz`)
|
||||
fs.writeFileSync(path.join(output, `${name}-pack.log`), run([yarn, 'pack', '--filename', archive], path.join(workspace, 'packages', name)))
|
||||
const manifest = JSON.parse(readMember(archive, 'package/package.json'))
|
||||
const files = packedFiles(archive)
|
||||
checkFiles(manifest, files, name === contract.baseline.release.name ? Object.keys(contract.baseline.release.files) : [])
|
||||
packages.push({ name, archive, sha256: hash(fs.readFileSync(archive)), files: Object.fromEntries(files.map(member => [member, hash(readMember(archive, member))])) })
|
||||
}
|
||||
const matrix = []
|
||||
const core = packages[0]
|
||||
const candidates = [
|
||||
...[...contract.baseline.previous].reverse().concat(contract.baseline.release).map(release => ({ ...release, archive: contract.archives.get(release.version), label: `published-${release.version}` })),
|
||||
{ ...packages[1], label: 'candidate' },
|
||||
]
|
||||
for (const plugin of candidates) {
|
||||
const candidate = plugin.label === 'candidate'
|
||||
const consumer = consumerDirectory()
|
||||
try {
|
||||
writeJson(path.join(consumer, 'package.json'), { name: 'asr-isolated-consumer', private: true, dependencies: Object.fromEntries([core, plugin].map(pkg => [pkg.name, `file:${pkg.archive.replaceAll('\\', '/')}`])) })
|
||||
fs.copyFileSync(path.join(workspace, 'yarn.lock'), path.join(consumer, 'yarn.lock'))
|
||||
fs.writeFileSync(path.join(output, `${plugin.label}-install.log`), run([yarn, 'install', '--offline', '--ignore-scripts', '--non-interactive'], consumer))
|
||||
const lock = fs.readFileSync(path.join(consumer, 'yarn.lock'))
|
||||
fs.writeFileSync(path.join(output, `${plugin.label}-frozen-install.log`), run([yarn, 'install', '--offline', '--frozen-lockfile', '--ignore-scripts', '--non-interactive'], consumer))
|
||||
assert.deepEqual(fs.readFileSync(path.join(consumer, 'yarn.lock')), lock)
|
||||
fs.writeFileSync(path.join(output, `${plugin.label}-yarn.lock`), lock)
|
||||
for (const pkg of [core, plugin]) {
|
||||
const root = path.join(consumer, 'node_modules', pkg.name)
|
||||
assert.equal(fs.realpathSync(root), root, 'Installed package must not be a workspace link')
|
||||
for (const [member, expected] of Object.entries(pkg.files))
|
||||
assert.equal(hash(fs.readFileSync(path.join(root, member.slice(8)))), expected, `Installed bytes differ: ${member}`)
|
||||
}
|
||||
const runtimeFile = path.join(consumer, 'exports.cjs')
|
||||
fs.writeFileSync(runtimeFile, candidate
|
||||
? `const assert = require('node:assert/strict');
|
||||
for (const name of ['artplayer-plugin-asr', 'artplayer-plugin-asr/legacy', 'artplayer-plugin-asr/runtime']) { const factory = require(name); assert.equal(typeof factory, 'function'); assert.equal(factory.default, factory); assert.equal(Object.getOwnPropertyDescriptor(factory, 'default').enumerable, false); assert.equal(typeof factory({}), 'function'); }
|
||||
assert.equal(require('artplayer-plugin-asr/runtime'), require('artplayer-plugin-asr'));
|
||||
Promise.all(['artplayer-plugin-asr', 'artplayer-plugin-asr/runtime', 'artplayer-plugin-asr/legacy'].map(name => import(name))).then(([root, runtime, legacy]) => { assert.deepEqual(Object.keys(root), ['default']); assert.deepEqual(Object.keys(runtime), ['default']); assert.equal(runtime.default, root.default); assert.equal(root.default.default, root.default); assert.equal(legacy.default, require('artplayer-plugin-asr/legacy')); }).catch(error => { console.error(error); process.exitCode = 1; });`
|
||||
: `const assert = require('node:assert/strict'); const value = require('artplayer-plugin-asr'); assert.equal(typeof value, '${plugin.version === '2.1.0' ? 'function' : 'object'}'); assert.equal(typeof (value.default || value)({}), 'function'); assert.equal(typeof value.default, '${plugin.version === '2.1.0' ? 'undefined' : 'function'}'); import('artplayer-plugin-asr').then(module => { assert.equal(typeof module.default, 'function'); assert.equal(typeof module.default({}), 'function'); }).catch(error => { console.error(error); process.exitCode = 1; });`)
|
||||
fs.writeFileSync(path.join(output, `${plugin.label}-runtime.log`), run([runtimeFile], consumer))
|
||||
const modes = candidate ? [...standardModes, [ts, 'node10-commonjs-no-interop'], [compat, 'node10-commonjs-no-interop']] : standardModes
|
||||
for (const [compiler, mode] of modes) {
|
||||
const result = { plugin: plugin.label, ...typecheck(consumer, compiler, mode, candidate) }
|
||||
matrix.push(result)
|
||||
writeJson(path.join(output, `${plugin.label}-${compiler.version}-${mode}.json`), result)
|
||||
console.log(`${plugin.label} TS ${compiler.version} ${mode}: ${result.diagnostics.length} diagnostics; ${result.invalid.length} negative diagnostics`)
|
||||
}
|
||||
}
|
||||
finally {
|
||||
removeConsumer(consumer)
|
||||
}
|
||||
}
|
||||
writeJson(path.join(output, 'report.json'), { suite: 'asr-isolated-package-types', introducedBy: 'PKG-ASR-04', packages, published: candidates.slice(0, -1).map(pkg => ({ label: pkg.label, archive: pkg.archive, sha256: hash(fs.readFileSync(pkg.archive)) })), matrix })
|
||||
for (const result of matrix) {
|
||||
const baseline = result.plugin === 'candidate' ? [] : expected.cases.find(item => item.plugin === result.plugin && item.compiler === result.compiler && item.mode === result.mode)?.diagnostics
|
||||
assert.deepEqual(result.diagnostics, baseline, `${result.plugin} TS ${result.compiler} ${result.mode}`)
|
||||
assert.deepEqual(result.namespace, [], `Historical ESM namespace: ${result.plugin}`)
|
||||
if (result.plugin === 'candidate') {
|
||||
const publishedBaseline = result.mode === 'nodenext-esm' ? expected.cases.find(item => item.plugin === 'published-2.1.0' && item.compiler === result.compiler && item.mode === result.mode).diagnostics : []
|
||||
assert.deepEqual(result.published, publishedBaseline, `Historical direct consumer: ${result.compiler} ${result.mode}`)
|
||||
assert.equal(result.invalid.length, 12, 'Installed declarations must reject all 12 invalid uses')
|
||||
}
|
||||
}
|
||||
console.log(`ASR installed matrix verified: ${matrix.length} cases; ${output}`)
|
||||
}
|
||||
|
||||
main().catch((error) => {
|
||||
console.error(error)
|
||||
process.exitCode = 1
|
||||
})
|
||||
+6
-2
@@ -2682,11 +2682,15 @@
|
||||
"ENG-06",
|
||||
"CORE-07"
|
||||
],
|
||||
"status": "todo",
|
||||
"status": "done",
|
||||
"risk": "H",
|
||||
"deliverable": "主线程/Worklet/音频 buffer 与异步回调类型",
|
||||
"acceptance": "严格类型检查、旧消费样例通过;声明路径/导出和同步异步兼容",
|
||||
"evidence": []
|
||||
"evidence": [
|
||||
"changes/2026-09-13-PKG-ASR-04-public-types.md",
|
||||
"baselines/asr-types-validation.json",
|
||||
"baselines/asr-type-diagnostics.json"
|
||||
]
|
||||
},
|
||||
{
|
||||
"id": "PKG-ASR-05",
|
||||
|
||||
@@ -73,6 +73,15 @@ export function runTypechecks() {
|
||||
console.log(`Strict project passed: ${relative(config)} (${result.files.length} root files)`)
|
||||
}
|
||||
for (const [compiler, mode] of [[ts, 'node10-commonjs'], [ts, 'nodenext-cjs'], [ts, 'bundler-esm'], [ts, 'nodenext-esm'], [compat, 'node10-commonjs']]) {
|
||||
for (const fixture of ['test/types/asr-public.ts', mode === 'nodenext-esm' ? 'refactor/fixtures/consumers/asr-esm-namespace.ts' : 'refactor/fixtures/consumers/asr-published.ts']) {
|
||||
let source = fs.readFileSync(path.join(root, fixture), 'utf8')
|
||||
if (fixture === 'test/types/asr-public.ts' && mode === 'nodenext-esm') {
|
||||
source = source.replace('import legacy from \'artplayer-plugin-asr\'', 'import legacyModule from \'artplayer-plugin-asr\'\nconst legacy = legacyModule.default')
|
||||
.replace('import legacyEntry from \'artplayer-plugin-asr/legacy\'', 'import legacyEntryModule from \'artplayer-plugin-asr/legacy\'\nconst legacyEntry = legacyEntryModule.default')
|
||||
.replace('namespace.default', 'namespace.default.default')
|
||||
}
|
||||
assert.deepEqual(checkConsumer(compiler, mode, source), [], `ASR consumer failed: TS ${compiler.version} ${mode}`)
|
||||
}
|
||||
for (const fixture of ['test/types/public.ts', 'test/types/declaration-inputs.ts', 'test/types/declaration-legacy.ts', 'test/types/plugins-public.ts', 'test/types/playback-public.ts', 'test/types/chapter-options.ts', 'test/types/chapter-exports.ts', 'test/types/hls-control.ts', 'test/types/dash-control.ts', 'test/types/ads.ts', 'refactor/fixtures/consumers/ads-published.ts', 'refactor/fixtures/consumers/ads-workspace.ts', 'refactor/fixtures/consumers/dash-control-legacy.ts', 'test/types/audio-track.ts', 'test/types/language-value.ts', 'refactor/fixtures/consumers/language.ts', 'refactor/fixtures/consumers/legacy-plugin.ts']) {
|
||||
assert.deepEqual(checkConsumer(compiler, mode, fs.readFileSync(path.join(root, fixture), 'utf8')), [], `Consumer failed: TS ${compiler.version} ${mode} ${fixture}`)
|
||||
}
|
||||
|
||||
@@ -0,0 +1,101 @@
|
||||
import type { AsrPluginInstance, AsrPluginOption, AudioChunk, RuntimeFactory, RuntimeOption, RuntimeResult } from 'artplayer-plugin-asr'
|
||||
import type { AudioChunk as EntryChunk, RuntimeFactory as EntryFactory, RuntimeOption as EntryOption, RuntimeResult as EntryResult } from 'artplayer-plugin-asr/runtime'
|
||||
import Artplayer from 'artplayer'
|
||||
import legacy from 'artplayer-plugin-asr'
|
||||
import * as namespace from 'artplayer-plugin-asr'
|
||||
import legacyEntry from 'artplayer-plugin-asr/legacy'
|
||||
import runtime from 'artplayer-plugin-asr/runtime'
|
||||
|
||||
type Equal<A, B> = (<T>() => T extends A ? 1 : 2) extends (<T>() => T extends B ? 1 : 2) ? true : false
|
||||
type Assert<T extends true> = T
|
||||
type RuntimeEntryTypes = Assert<Equal<[EntryChunk, EntryFactory, EntryOption, EntryResult], [AudioChunk, RuntimeFactory, RuntimeOption, RuntimeResult]>>
|
||||
|
||||
interface HistoricalOption {
|
||||
length?: number
|
||||
interval?: number
|
||||
sampleRate?: number
|
||||
autoHideTimeout?: number
|
||||
onAudioChunk?: (chunk: { pcm: ArrayBuffer, wav: ArrayBuffer }) => void | Promise<void>
|
||||
}
|
||||
|
||||
interface HistoricalResult {
|
||||
name: 'artplayerPluginAsr'
|
||||
stop: () => void
|
||||
hide: () => void
|
||||
append: (subtitle: string) => void
|
||||
}
|
||||
|
||||
type HistoricalFactory = (option?: HistoricalOption) => (art: Artplayer) => HistoricalResult
|
||||
type RootArguments = Assert<Equal<Parameters<typeof legacy>, [option?: AsrPluginOption]>>
|
||||
type RootOption = Assert<Equal<AsrPluginOption, HistoricalOption>>
|
||||
type RootResult = Assert<Equal<ReturnType<ReturnType<typeof legacy>>, AsrPluginInstance>>
|
||||
type RootShape = Assert<Equal<AsrPluginInstance, HistoricalResult>>
|
||||
type RootFactory = Assert<Equal<typeof legacy, HistoricalFactory>>
|
||||
type RootStop = Assert<Equal<ReturnType<AsrPluginInstance['stop']>, void>>
|
||||
type ChunkShape = Assert<Equal<AudioChunk, { pcm: ArrayBuffer, wav: ArrayBuffer }>>
|
||||
type PreciseArguments = Assert<Equal<Parameters<typeof runtime>, [option?: RuntimeOption]>>
|
||||
type PreciseResult = Assert<Equal<ReturnType<ReturnType<typeof runtime>>, RuntimeResult>>
|
||||
type PreciseStop = Assert<Equal<ReturnType<RuntimeResult['stop']>, Promise<void>>>
|
||||
type PreciseFactory = Assert<Equal<typeof runtime, RuntimeFactory>>
|
||||
type PreciseCallback = Assert<Equal<NonNullable<RuntimeOption['onAudioChunk']>, (chunk: AudioChunk) => string | void | null | Promise<string | void | null>>>
|
||||
|
||||
const replacement: HistoricalFactory = (_option?: HistoricalOption) => (_art: Artplayer) => ({
|
||||
name: 'artplayerPluginAsr',
|
||||
stop() {},
|
||||
hide() {},
|
||||
append(_subtitle: string) {},
|
||||
})
|
||||
const assignToOld: HistoricalFactory = legacy
|
||||
const assignFromOld: typeof legacy = replacement
|
||||
const namespaceFactory: HistoricalFactory = namespace.default
|
||||
const explicitLegacy: HistoricalFactory = legacyEntry
|
||||
const option: AsrPluginOption = { onAudioChunk: async (_chunk: AudioChunk): Promise<void> => {} }
|
||||
const absent: Parameters<typeof legacy>[0] = undefined
|
||||
const art = new Artplayer({ container: '#player', url: '/video.mp4', plugins: [legacy(option), runtime(), legacyEntry(absent)] })
|
||||
const old = legacy(option)(art)
|
||||
const oldReturns: void[] = [old.stop(), old.hide(), old.append('Subtitle.')]
|
||||
const bareRoot: typeof legacy = replacement
|
||||
|
||||
const runtimeOption: RuntimeOption = { length: 2, interval: 250, sampleRate: 48000, autoHideTimeout: 3000, onAudioChunk: async (chunk) => {
|
||||
const pcm: ArrayBuffer = chunk.pcm
|
||||
const wav: ArrayBuffer = chunk.wav
|
||||
void [pcm, wav]
|
||||
return 'Recognized subtitle.'
|
||||
} }
|
||||
const correct: RuntimeResult = runtime(runtimeOption)(art)
|
||||
const stopped: Promise<void> = correct.stop()
|
||||
const alias: RuntimeFactory = runtime.default.default
|
||||
const aliasResult: RuntimeResult = alias(undefined)(art)
|
||||
runtime({ onAudioChunk: () => 'Synchronous subtitle.' })
|
||||
runtime({ onAudioChunk: () => null })
|
||||
runtime({ onAudioChunk: () => undefined })
|
||||
runtime({ onAudioChunk: async () => {} })
|
||||
runtime({ onAudioChunk: async () => null })
|
||||
runtime(option)
|
||||
|
||||
// @ts-expect-error Root options preserve the historical void/Promise<void> callback shape.
|
||||
legacy({ onAudioChunk: () => 'Only the precise entry describes returned subtitles.' })
|
||||
// @ts-expect-error Root stop extraction remains void for historical replacement factories.
|
||||
const rootPromise: Promise<void> = old.stop()
|
||||
// @ts-expect-error The legacy factory type must not demand or expose a self default alias.
|
||||
bareRoot.default()
|
||||
// @ts-expect-error Accurate stop is asynchronous.
|
||||
const synchronous: void = correct.stop()
|
||||
// @ts-expect-error Accurate result replacements cannot return void from stop.
|
||||
const wrongStop: RuntimeResult = { name: 'artplayerPluginAsr', stop() {}, hide() {}, append(_text: string) {} }
|
||||
// @ts-expect-error Callback results do not include booleans.
|
||||
runtime({ onAudioChunk: () => true })
|
||||
// @ts-expect-error Async callback results do not include booleans.
|
||||
runtime({ onAudioChunk: async () => true })
|
||||
// @ts-expect-error Options use numeric sample rates.
|
||||
runtime({ sampleRate: '16000' })
|
||||
// @ts-expect-error Unknown options remain rejected.
|
||||
runtime({ unknown: true })
|
||||
// @ts-expect-error Registration requires an Artplayer instance.
|
||||
runtime()()
|
||||
// @ts-expect-error Append accepts a string.
|
||||
correct.append(123)
|
||||
// @ts-expect-error PCM is an ArrayBuffer rather than encoded text.
|
||||
const invalidChunk: AudioChunk = { pcm: 'raw audio', wav: new ArrayBuffer(4) }
|
||||
void [assignToOld, assignFromOld, namespaceFactory, explicitLegacy, oldReturns, stopped, aliasResult, rootPromise, synchronous, wrongStop, invalidChunk]
|
||||
export type { ChunkShape, PreciseArguments, PreciseCallback, PreciseFactory, PreciseResult, PreciseStop, RootArguments, RootFactory, RootOption, RootResult, RootShape, RootStop, RuntimeEntryTypes }
|
||||
@@ -0,0 +1,21 @@
|
||||
import type { AudioChunk, Factory, RuntimeFactory, RuntimeOption, RuntimeResult } from 'artplayer-plugin-asr'
|
||||
import type source from '../../packages/artplayer-plugin-asr/src/index'
|
||||
import type { AsrOptions, AsrResult, AudioChunk as SourceChunk } from '../../packages/artplayer-plugin-asr/src/types'
|
||||
|
||||
declare const implementation: typeof source
|
||||
declare const runtimeFactory: RuntimeFactory
|
||||
declare const runtimeOption: RuntimeOption
|
||||
declare const sourceResult: AsrResult
|
||||
declare const publicResult: RuntimeResult
|
||||
declare const sourceChunk: SourceChunk
|
||||
declare const publicChunk: AudioChunk
|
||||
|
||||
const historical: Factory = implementation
|
||||
const accurate: Factory = runtimeFactory
|
||||
const runtimeCall: (option?: RuntimeOption) => ReturnType<RuntimeFactory> = implementation
|
||||
const sourceOption: AsrOptions = runtimeOption
|
||||
const resultToPublic: RuntimeResult = sourceResult
|
||||
const resultToSource: AsrResult = publicResult
|
||||
const chunkToPublic: AudioChunk = sourceChunk
|
||||
const chunkToSource: SourceChunk = publicChunk
|
||||
void [historical, accurate, runtimeCall, sourceOption, resultToPublic, resultToSource, chunkToPublic, chunkToSource]
|
||||
Reference in new issue
Block a user