@dan-uni/dan-any 0.9.2 → 0.9.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +1 -1
- package/dist/index.js +225 -352
- package/dist/index.min.js +225 -352
- package/dist/index.umd.min.js +228 -354
- package/dist/src/index.d.ts +15 -41
- package/package.json +5 -5
- package/src/ass-gen/ass/create.ts +2 -2
- package/src/ass-gen/ass/raw.ts +19 -19
- package/src/index.test.ts +19 -12
- package/src/index.ts +100 -130
- package/src/proto/gen/bili/dm_pb.ts +1 -1
- package/src/proto/gen/danuni_pb.ts +1 -1
- package/src/utils/dm-gen.test.ts +3 -3
- package/src/utils/dm-gen.ts +30 -31
package/dist/src/index.d.ts
CHANGED
|
@@ -52,6 +52,11 @@ export interface DM_JSON_DDPlay {
|
|
|
52
52
|
}
|
|
53
53
|
export type DM_format = 'danuni.json' | 'danuni.pb.bin' | 'bili.xml' | 'bili.pb.bin' | 'bili.cmd.pb.bin' | 'dplayer.json' | 'artplayer.json' | 'ddplay.json' | 'common.ass';
|
|
54
54
|
type shareItems = Partial<Pick<UniDMTools.UniDMObj, 'SOID' | 'senderID' | 'platform' | 'SOID' | 'pool' | 'mode' | 'color'>>;
|
|
55
|
+
type statItems = Partial<Pick<UniDMTools.UniDMObj, 'SOID' | 'mode' | 'fontsize' | 'color' | 'senderID' | 'content' | 'weight' | 'pool' | 'platform'>>;
|
|
56
|
+
interface Stat {
|
|
57
|
+
val: statItems[keyof statItems];
|
|
58
|
+
count: number;
|
|
59
|
+
}
|
|
55
60
|
type UniPoolPipe = (that: UniPool) => Promise<UniPool>;
|
|
56
61
|
type UniPoolPipeSync = (that: UniPool) => UniPool;
|
|
57
62
|
export interface Options {
|
|
@@ -76,44 +81,9 @@ export declare class UniPool {
|
|
|
76
81
|
pipe(fn: UniPoolPipe): Promise<UniPool>;
|
|
77
82
|
pipeSync(fn: UniPoolPipeSync): UniPool;
|
|
78
83
|
get shared(): shareItems;
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
count: number;
|
|
83
|
-
}[];
|
|
84
|
-
mode: {
|
|
85
|
-
val: UniDMTools.Modes;
|
|
86
|
-
count: number;
|
|
87
|
-
}[];
|
|
88
|
-
fontsize: {
|
|
89
|
-
val: number;
|
|
90
|
-
count: number;
|
|
91
|
-
}[];
|
|
92
|
-
color: {
|
|
93
|
-
val: number;
|
|
94
|
-
count: number;
|
|
95
|
-
}[];
|
|
96
|
-
senderID: {
|
|
97
|
-
val: string;
|
|
98
|
-
count: number;
|
|
99
|
-
}[];
|
|
100
|
-
content: {
|
|
101
|
-
val: string;
|
|
102
|
-
count: number;
|
|
103
|
-
}[];
|
|
104
|
-
weight: {
|
|
105
|
-
val: number;
|
|
106
|
-
count: number;
|
|
107
|
-
}[];
|
|
108
|
-
pool: {
|
|
109
|
-
val: UniDMTools.Pools;
|
|
110
|
-
count: number;
|
|
111
|
-
}[];
|
|
112
|
-
platform: {
|
|
113
|
-
val?: string;
|
|
114
|
-
count: number;
|
|
115
|
-
}[];
|
|
116
|
-
};
|
|
84
|
+
getShared(key: keyof shareItems): shareItems[keyof shareItems];
|
|
85
|
+
getStat(key: keyof statItems): Stat[];
|
|
86
|
+
getMost(key: keyof statItems): Stat;
|
|
117
87
|
get most(): {
|
|
118
88
|
mode: UniDMTools.Modes;
|
|
119
89
|
fontsize: number;
|
|
@@ -143,11 +113,15 @@ export declare class UniPool {
|
|
|
143
113
|
*/
|
|
144
114
|
merge(lifetime?: number): UniPool;
|
|
145
115
|
minify(): (Partial<UniDMTools.UniDMObj> & Pick<UniDMTools.UniDMObj, "SOID">)[];
|
|
146
|
-
static import(file: unknown, options?: Options
|
|
116
|
+
static import(file: unknown, options?: Options,
|
|
117
|
+
/**
|
|
118
|
+
* 加载指定解析模块,为空则全选
|
|
119
|
+
*/
|
|
120
|
+
mod?: ('json' | 'str' | 'bin')[]): {
|
|
147
121
|
pool: UniPool;
|
|
148
122
|
fmt: DM_format;
|
|
149
123
|
};
|
|
150
|
-
convert2(format: DM_format, continue_on_error?: boolean): string | Uint8Array<
|
|
124
|
+
convert2(format: DM_format, continue_on_error?: boolean): string | Uint8Array<ArrayBuffer> | UniDM[] | (DM_JSON_Dplayer & {
|
|
151
125
|
danuni?: DanUniConvertTip;
|
|
152
126
|
}) | (DM_JSON_Artplayer & {
|
|
153
127
|
danuni?: DanUniConvertTip;
|
|
@@ -158,7 +132,7 @@ export declare class UniPool {
|
|
|
158
132
|
/**
|
|
159
133
|
* 转为 protobuf 二进制
|
|
160
134
|
*/
|
|
161
|
-
toPb(): Uint8Array<
|
|
135
|
+
toPb(): Uint8Array<ArrayBuffer>;
|
|
162
136
|
static fromBiliXML(xml: string, options?: Options): UniPool;
|
|
163
137
|
toBiliXML(options?: {
|
|
164
138
|
/**
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@dan-uni/dan-any",
|
|
3
|
-
"version": "0.9.
|
|
3
|
+
"version": "0.9.4",
|
|
4
4
|
"description": "A danmaku transformer lib, supporting danmaku from different platforms.",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"keywords": [
|
|
@@ -32,7 +32,7 @@
|
|
|
32
32
|
"buf": "buf generate"
|
|
33
33
|
},
|
|
34
34
|
"dependencies": {
|
|
35
|
-
"@bufbuild/protobuf": "^2.
|
|
35
|
+
"@bufbuild/protobuf": "^2.7.0",
|
|
36
36
|
"base16384": "^1.0.0",
|
|
37
37
|
"class-transformer": "^0.5.1",
|
|
38
38
|
"class-validator": "^0.14.2",
|
|
@@ -45,11 +45,11 @@
|
|
|
45
45
|
},
|
|
46
46
|
"devDependencies": {
|
|
47
47
|
"@bufbuild/buf": "^1.56.0",
|
|
48
|
-
"@bufbuild/protoc-gen-es": "^2.
|
|
48
|
+
"@bufbuild/protoc-gen-es": "^2.7.0",
|
|
49
49
|
"@types/fs-extra": "^11.0.4",
|
|
50
50
|
"@types/hh-mm-ss": "^1.2.3",
|
|
51
51
|
"@types/json-bigint": "^1.0.4",
|
|
52
|
-
"canvas": "^3.
|
|
53
|
-
"protobufjs": "^7.5.
|
|
52
|
+
"canvas": "^3.2.0",
|
|
53
|
+
"protobufjs": "^7.5.4"
|
|
54
54
|
}
|
|
55
55
|
}
|
|
@@ -16,8 +16,8 @@ export default (
|
|
|
16
16
|
context: Context = { filename: 'unknown', title: 'unknown' },
|
|
17
17
|
rawConfig?: RawConfig,
|
|
18
18
|
) => {
|
|
19
|
-
const Elist = UniPool2DanmakuLists(list)
|
|
20
|
-
|
|
19
|
+
const Elist = UniPool2DanmakuLists(list)
|
|
20
|
+
const ErawList = UniPool2DanmakuLists(rawList)
|
|
21
21
|
const content = [info(config, context), style(config), event(Elist, config)]
|
|
22
22
|
|
|
23
23
|
if (config.includeRaw) {
|
package/src/ass-gen/ass/raw.ts
CHANGED
|
@@ -9,8 +9,8 @@ import type { Context, Danmaku, SubtitleStyle } from '../types'
|
|
|
9
9
|
|
|
10
10
|
type compressType = 'brotli' | 'gzip'
|
|
11
11
|
type baseType = 'base64' | 'base18384'
|
|
12
|
-
const compressTypes = ['brotli', 'gzip']
|
|
13
|
-
|
|
12
|
+
const compressTypes = ['brotli', 'gzip']
|
|
13
|
+
const baseTypes = ['base64', 'base18384']
|
|
14
14
|
|
|
15
15
|
export interface RawConfig {
|
|
16
16
|
compressType: compressType
|
|
@@ -32,8 +32,8 @@ export function raw(
|
|
|
32
32
|
compressType: compressType = 'brotli',
|
|
33
33
|
baseType: baseType = 'base18384',
|
|
34
34
|
) {
|
|
35
|
-
const raw = { list, config, context }
|
|
36
|
-
|
|
35
|
+
const raw = { list, config, context }
|
|
36
|
+
const rawText = JSON.stringify(raw)
|
|
37
37
|
let compress: Buffer
|
|
38
38
|
if (compressType === 'brotli') compress = brotliCompressSync(rawText)
|
|
39
39
|
else compress = gzipSync(rawText)
|
|
@@ -47,25 +47,25 @@ export function deRaw(ass: string):
|
|
|
47
47
|
context: Context
|
|
48
48
|
}
|
|
49
49
|
| undefined {
|
|
50
|
-
const arr = ass.split('\n')
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
50
|
+
const arr = ass.split('\n')
|
|
51
|
+
const lineCompressType = arr.find((line) =>
|
|
52
|
+
line.startsWith(';RawCompressType:'),
|
|
53
|
+
)
|
|
54
|
+
const lineBaseType = arr.find((line) => line.startsWith(';RawBaseType:'))
|
|
55
|
+
const lineRaw = arr.find((line) => line.startsWith(';Raw:'))
|
|
54
56
|
if (!lineCompressType || !lineBaseType || !lineRaw) return undefined
|
|
55
57
|
else {
|
|
56
|
-
let compressType = lineCompressType
|
|
57
|
-
|
|
58
|
-
.trim(),
|
|
59
|
-
baseType = lineBaseType.replace(';RawBaseType: ', '').trim()
|
|
58
|
+
let compressType = lineCompressType.replace(';RawCompressType: ', '').trim()
|
|
59
|
+
let baseType = lineBaseType.replace(';RawBaseType: ', '').trim()
|
|
60
60
|
if (!compressTypes.includes(compressType)) compressType = 'gzip'
|
|
61
61
|
if (!baseTypes.includes(baseType)) baseType = 'base64'
|
|
62
|
-
const text = lineRaw.replace(';Raw: ', '').trim()
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
62
|
+
const text = lineRaw.replace(';Raw: ', '').trim()
|
|
63
|
+
const buffer =
|
|
64
|
+
baseType === 'base64'
|
|
65
|
+
? Buffer.from(text, 'base64')
|
|
66
|
+
: Buffer.from(
|
|
67
|
+
base16384.decode(Buffer.from(text, 'utf-8').toString('utf-8')),
|
|
68
|
+
)
|
|
69
69
|
let decompress: Buffer
|
|
70
70
|
if (compressType === 'brotli') decompress = brotliDecompressSync(buffer)
|
|
71
71
|
else decompress = gunzipSync(buffer)
|
package/src/index.test.ts
CHANGED
|
@@ -41,18 +41,18 @@ describe('转化自', () => {
|
|
|
41
41
|
})
|
|
42
42
|
it('artplayer(json)', () => {
|
|
43
43
|
const json = {
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
55
|
-
|
|
44
|
+
danmuku: [
|
|
45
|
+
{
|
|
46
|
+
text: 'artplayer测试弹幕', // 弹幕文本
|
|
47
|
+
time: 10, // 弹幕时间, 默认为当前播放器时间
|
|
48
|
+
mode: 0, // 弹幕模式: 0: 滚动(默认),1: 顶部,2: 底部
|
|
49
|
+
color: '#FFFFFF', // 弹幕颜色,默认为白色
|
|
50
|
+
border: false, // 弹幕是否有描边, 默认为 false
|
|
51
|
+
style: { border: '10rem' }, // 弹幕自定义样式, 默认为空对象
|
|
52
|
+
},
|
|
53
|
+
],
|
|
54
|
+
}
|
|
55
|
+
const pool = UniPool.fromArtplayer(json, 'playerid-test', 'acfun')
|
|
56
56
|
console.info(json)
|
|
57
57
|
console.info(pool)
|
|
58
58
|
const imp = UniPool.import(json)
|
|
@@ -90,7 +90,14 @@ describe('转化自', () => {
|
|
|
90
90
|
describe('共通值', () => {
|
|
91
91
|
const pool = UniPool.fromBiliXML(xml)
|
|
92
92
|
it('获取shared', () => {
|
|
93
|
+
console.info(pool.getMost('SOID'))
|
|
93
94
|
console.info(pool.shared)
|
|
95
|
+
expect(pool.getShared('SOID')).toBe(pool.shared.SOID)
|
|
96
|
+
})
|
|
97
|
+
it('获取most', () => {
|
|
98
|
+
console.info(pool.getMost('senderID'))
|
|
99
|
+
console.info(pool.most)
|
|
100
|
+
expect(pool.getMost('senderID').val).toBe(pool.most.senderID)
|
|
94
101
|
})
|
|
95
102
|
it('按pool分组', () => {
|
|
96
103
|
console.info(pool.split('pool'))
|
package/src/index.ts
CHANGED
|
@@ -102,6 +102,24 @@ type shareItems = Partial<
|
|
|
102
102
|
'SOID' | 'senderID' | 'platform' | 'SOID' | 'pool' | 'mode' | 'color'
|
|
103
103
|
>
|
|
104
104
|
>
|
|
105
|
+
type statItems = Partial<
|
|
106
|
+
Pick<
|
|
107
|
+
UniDMTools.UniDMObj,
|
|
108
|
+
| 'SOID'
|
|
109
|
+
| 'mode'
|
|
110
|
+
| 'fontsize'
|
|
111
|
+
| 'color'
|
|
112
|
+
| 'senderID'
|
|
113
|
+
| 'content'
|
|
114
|
+
| 'weight'
|
|
115
|
+
| 'pool'
|
|
116
|
+
| 'platform'
|
|
117
|
+
>
|
|
118
|
+
>
|
|
119
|
+
interface Stat {
|
|
120
|
+
val: statItems[keyof statItems]
|
|
121
|
+
count: number
|
|
122
|
+
}
|
|
105
123
|
|
|
106
124
|
type UniPoolPipe = (that: UniPool) => Promise<UniPool>
|
|
107
125
|
type UniPoolPipeSync = (that: UniPool) => UniPool
|
|
@@ -144,104 +162,38 @@ export class UniPool {
|
|
|
144
162
|
color: isShared('color') ? this.dans[0].color : undefined,
|
|
145
163
|
}
|
|
146
164
|
}
|
|
147
|
-
|
|
148
|
-
const
|
|
149
|
-
|
|
150
|
-
mode: [
|
|
151
|
-
{ val: UniDMTools.Modes.Normal, count: 0 },
|
|
152
|
-
{ val: UniDMTools.Modes.Bottom, count: 0 },
|
|
153
|
-
{ val: UniDMTools.Modes.Top, count: 0 },
|
|
154
|
-
{ val: UniDMTools.Modes.Reverse, count: 0 },
|
|
155
|
-
{ val: UniDMTools.Modes.Ext, count: 0 },
|
|
156
|
-
],
|
|
157
|
-
fontsize: [
|
|
158
|
-
// { val: 18, count: 0 },
|
|
159
|
-
// { val: 25, count: 0 },
|
|
160
|
-
// { val: 36, count: 0 },
|
|
161
|
-
] as { val: number; count: number }[],
|
|
162
|
-
color: [] as { val: number; count: number }[],
|
|
163
|
-
senderID: [] as { val: string; count: number }[],
|
|
164
|
-
content: [] as { val: string; count: number }[],
|
|
165
|
-
weight: [] as { val: number; count: number }[],
|
|
166
|
-
pool: [
|
|
167
|
-
{ val: UniDMTools.Pools.Def, count: 0 },
|
|
168
|
-
{ val: UniDMTools.Pools.Sub, count: 0 },
|
|
169
|
-
{ val: UniDMTools.Pools.Adv, count: 0 },
|
|
170
|
-
{ val: UniDMTools.Pools.Ix, count: 0 },
|
|
171
|
-
],
|
|
172
|
-
platform: [] as { val?: string; count: number }[],
|
|
165
|
+
getShared(key: keyof shareItems): shareItems[keyof shareItems] {
|
|
166
|
+
const isShared = (key: keyof UniDMTools.UniDMObj) => {
|
|
167
|
+
return this.dans.every((d) => d[key])
|
|
173
168
|
}
|
|
174
|
-
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
180
|
-
|
|
181
|
-
|
|
182
|
-
const mode = s.mode.find((i) => i.val === d.mode)
|
|
183
|
-
if (!mode) {
|
|
184
|
-
s.mode.push({ val: d.mode, count: 1 })
|
|
185
|
-
} else {
|
|
186
|
-
mode.count++
|
|
187
|
-
}
|
|
188
|
-
const fontsize = s.fontsize.find((i) => i.val === d.fontsize)
|
|
189
|
-
if (!fontsize) {
|
|
190
|
-
s.fontsize.push({ val: d.fontsize, count: 1 })
|
|
191
|
-
} else {
|
|
192
|
-
fontsize.count++
|
|
193
|
-
}
|
|
194
|
-
const color = s.color.find((i) => i.val === d.color)
|
|
195
|
-
if (!color) {
|
|
196
|
-
s.color.push({ val: d.color, count: 1 })
|
|
197
|
-
} else {
|
|
198
|
-
color.count++
|
|
199
|
-
}
|
|
200
|
-
const senderID = s.senderID.find((i) => i.val === d.senderID)
|
|
201
|
-
if (!senderID) {
|
|
202
|
-
s.senderID.push({ val: d.senderID, count: 1 })
|
|
203
|
-
} else {
|
|
204
|
-
senderID.count++
|
|
205
|
-
}
|
|
206
|
-
const content = s.content.find((i) => i.val === d.content)
|
|
207
|
-
if (!content) {
|
|
208
|
-
s.content.push({ val: d.content, count: 1 })
|
|
209
|
-
} else {
|
|
210
|
-
content.count++
|
|
211
|
-
}
|
|
212
|
-
const weight = s.weight.find((i) => i.val === d.weight)
|
|
213
|
-
if (!weight) {
|
|
214
|
-
s.weight.push({ val: d.weight, count: 1 })
|
|
215
|
-
} else {
|
|
216
|
-
weight.count++
|
|
217
|
-
}
|
|
218
|
-
const pool = s.pool.find((i) => i.val === d.pool)
|
|
219
|
-
if (!pool) {
|
|
220
|
-
s.pool.push({ val: d.pool, count: 1 })
|
|
221
|
-
} else {
|
|
222
|
-
pool.count++
|
|
223
|
-
}
|
|
224
|
-
const platform = s.platform.find((i) => i.val === d.platform)
|
|
225
|
-
if (!platform) {
|
|
226
|
-
s.platform.push({ val: d.platform, count: 1 })
|
|
169
|
+
return isShared(key) ? this.dans[0][key] : undefined
|
|
170
|
+
}
|
|
171
|
+
getStat(key: keyof statItems): Stat[] {
|
|
172
|
+
const default_stat: Stat[] = []
|
|
173
|
+
const stats = this.dans.reduce((stat, dan) => {
|
|
174
|
+
const valWithCount = stat.find((i) => i.val === dan[key])
|
|
175
|
+
if (!valWithCount) {
|
|
176
|
+
stat.push({ val: dan[key], count: 1 })
|
|
227
177
|
} else {
|
|
228
|
-
|
|
178
|
+
valWithCount.count++
|
|
229
179
|
}
|
|
230
|
-
return
|
|
180
|
+
return stat
|
|
231
181
|
}, default_stat)
|
|
232
|
-
return
|
|
182
|
+
return stats
|
|
183
|
+
}
|
|
184
|
+
getMost(key: keyof statItems) {
|
|
185
|
+
return this.getStat(key).sort((a, b) => b.count - a.count)[0]
|
|
233
186
|
}
|
|
234
187
|
get most() {
|
|
235
|
-
const s = this.stat
|
|
236
188
|
return {
|
|
237
|
-
mode:
|
|
238
|
-
fontsize:
|
|
239
|
-
color:
|
|
240
|
-
senderID:
|
|
241
|
-
content:
|
|
242
|
-
weight:
|
|
243
|
-
pool:
|
|
244
|
-
platform:
|
|
189
|
+
mode: this.getMost('mode').val as UniDMTools.Modes,
|
|
190
|
+
fontsize: this.getMost('fontsize').val as number,
|
|
191
|
+
color: this.getMost('color').val as number,
|
|
192
|
+
senderID: this.getMost('senderID').val as string,
|
|
193
|
+
content: this.getMost('content').val as string,
|
|
194
|
+
weight: this.getMost('weight').val as number,
|
|
195
|
+
pool: this.getMost('pool').val as UniDMTools.Pools,
|
|
196
|
+
platform: this.getMost('platform').val as string | undefined,
|
|
245
197
|
}
|
|
246
198
|
}
|
|
247
199
|
static create(options?: Options) {
|
|
@@ -361,8 +313,8 @@ export class UniPool {
|
|
|
361
313
|
const key = ['content', 'mode', 'platform', 'pool']
|
|
362
314
|
.map((k) => danmaku[k as keyof UniDM])
|
|
363
315
|
.join('|')
|
|
364
|
-
const extra = result[i].extra
|
|
365
|
-
|
|
316
|
+
const extra = result[i].extra
|
|
317
|
+
const mergeData = mergeObj[key]
|
|
366
318
|
result[i].extraStr = JSON.stringify({
|
|
367
319
|
...extra,
|
|
368
320
|
danuni: {
|
|
@@ -399,7 +351,12 @@ export class UniPool {
|
|
|
399
351
|
static import(
|
|
400
352
|
file: unknown,
|
|
401
353
|
options?: Options,
|
|
354
|
+
/**
|
|
355
|
+
* 加载指定解析模块,为空则全选
|
|
356
|
+
*/
|
|
357
|
+
mod?: ('json' | 'str' | 'bin')[],
|
|
402
358
|
): { pool: UniPool; fmt: DM_format } {
|
|
359
|
+
if (!mod) mod = ['json', 'str', 'bin']
|
|
403
360
|
const err = '无法识别该文件,请手动指定格式!'
|
|
404
361
|
const parseJSON = (
|
|
405
362
|
json: DM_JSON_Artplayer &
|
|
@@ -448,49 +405,61 @@ export class UniPool {
|
|
|
448
405
|
const parseStr = (
|
|
449
406
|
file: string,
|
|
450
407
|
): { pool: UniPool; fmt: DM_format } | undefined => {
|
|
451
|
-
|
|
452
|
-
|
|
453
|
-
const json = JSON.parse(file)
|
|
454
|
-
return parseJSON(json)
|
|
455
|
-
}
|
|
456
|
-
} catch {}
|
|
457
|
-
try {
|
|
458
|
-
const xmlParser = new XMLParser({ ignoreAttributes: false })
|
|
459
|
-
const xml = xmlParser.parse(file)
|
|
460
|
-
if (xml?.i?.d)
|
|
461
|
-
return { pool: this.fromBiliXML(file, options), fmt: 'bili.xml' }
|
|
462
|
-
} catch {}
|
|
463
|
-
try {
|
|
464
|
-
return { pool: this.fromASS(file, options), fmt: 'common.ass' }
|
|
465
|
-
} catch {}
|
|
466
|
-
}
|
|
467
|
-
let errmesg
|
|
468
|
-
if (isObject(file)) {
|
|
469
|
-
if (file instanceof ArrayBuffer || file instanceof Uint8Array) {
|
|
408
|
+
// json-str
|
|
409
|
+
if (mod.includes('json'))
|
|
470
410
|
try {
|
|
471
|
-
|
|
411
|
+
if (isJSON(file)) {
|
|
412
|
+
const json = JSON.parse(file)
|
|
413
|
+
return parseJSON(json)
|
|
414
|
+
}
|
|
472
415
|
} catch {}
|
|
416
|
+
// pure-str (xml/ass)
|
|
417
|
+
if (mod.includes('str')) {
|
|
473
418
|
try {
|
|
474
|
-
|
|
419
|
+
const xmlParser = new XMLParser({ ignoreAttributes: false })
|
|
420
|
+
const xml = xmlParser.parse(file)
|
|
421
|
+
if (xml?.i?.d)
|
|
422
|
+
return { pool: this.fromBiliXML(file, options), fmt: 'bili.xml' }
|
|
475
423
|
} catch {}
|
|
476
424
|
try {
|
|
477
|
-
return {
|
|
478
|
-
pool: this.fromBiliCommandGrpc(file),
|
|
479
|
-
fmt: 'bili.cmd.pb.bin',
|
|
480
|
-
}
|
|
425
|
+
return { pool: this.fromASS(file, options), fmt: 'common.ass' }
|
|
481
426
|
} catch {}
|
|
427
|
+
}
|
|
428
|
+
}
|
|
429
|
+
let errmesg
|
|
430
|
+
if (isObject(file)) {
|
|
431
|
+
if (file instanceof ArrayBuffer || file instanceof Uint8Array) {
|
|
432
|
+
// pure-bin (pb)
|
|
433
|
+
if (mod.includes('bin')) {
|
|
434
|
+
try {
|
|
435
|
+
return { pool: this.fromPb(file), fmt: 'danuni.pb.bin' }
|
|
436
|
+
} catch {}
|
|
437
|
+
try {
|
|
438
|
+
return { pool: this.fromBiliGrpc(file), fmt: 'bili.pb.bin' }
|
|
439
|
+
} catch {}
|
|
440
|
+
try {
|
|
441
|
+
return {
|
|
442
|
+
pool: this.fromBiliCommandGrpc(file),
|
|
443
|
+
fmt: 'bili.cmd.pb.bin',
|
|
444
|
+
}
|
|
445
|
+
} catch {}
|
|
446
|
+
}
|
|
447
|
+
// str-bin (pure-str + json-str)
|
|
448
|
+
|
|
482
449
|
try {
|
|
483
450
|
const fileStr = new TextDecoder().decode(file)
|
|
484
451
|
const prStr = parseStr(fileStr)
|
|
485
452
|
if (!prStr) errmesg = `${err}(定位: bin->string)`
|
|
486
453
|
else return prStr
|
|
487
454
|
} catch {}
|
|
488
|
-
} else {
|
|
455
|
+
} else if (mod.includes('json')) {
|
|
456
|
+
// pure-json
|
|
489
457
|
const prJSON = parseJSON(file as any)
|
|
490
458
|
if (!prJSON) throw new Error(`${err}(定位: json)`)
|
|
491
459
|
return prJSON
|
|
492
460
|
}
|
|
493
461
|
} else if (isString(file)) {
|
|
462
|
+
// pure-str + json-str
|
|
494
463
|
const prStr = parseStr(file)
|
|
495
464
|
if (!prStr) throw new Error(`${err}(定位: string)`)
|
|
496
465
|
return prStr
|
|
@@ -574,16 +543,17 @@ export class UniPool {
|
|
|
574
543
|
)
|
|
575
544
|
}
|
|
576
545
|
static fromBiliXML(xml: string, options?: Options) {
|
|
577
|
-
const parser = new XMLParser({ ignoreAttributes: false })
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
581
|
-
|
|
546
|
+
const parser = new XMLParser({ ignoreAttributes: false })
|
|
547
|
+
const oriData: DM_XML_Bili & { danuni?: DanUniConvertTip } =
|
|
548
|
+
parser.parse(xml)
|
|
549
|
+
const dans = oriData.i.d
|
|
550
|
+
const fromConverted = !!oriData.danuni
|
|
551
|
+
const cid = BigInt(oriData.i.chatid)
|
|
582
552
|
return new UniPool(
|
|
583
553
|
dans
|
|
584
554
|
.map((d) => {
|
|
585
|
-
const p_str = d['@_p']
|
|
586
|
-
|
|
555
|
+
const p_str = d['@_p']
|
|
556
|
+
const p_arr = p_str.split(',')
|
|
587
557
|
return UniDM.fromBili(
|
|
588
558
|
{
|
|
589
559
|
content: d['#text'],
|
|
@@ -657,8 +627,8 @@ export class UniPool {
|
|
|
657
627
|
})
|
|
658
628
|
}
|
|
659
629
|
static fromBiliGrpc(bin: Uint8Array | ArrayBuffer, options?: Options) {
|
|
660
|
-
const data = fromBinary(DmSegMobileReplySchema, new Uint8Array(bin))
|
|
661
|
-
|
|
630
|
+
const data = fromBinary(DmSegMobileReplySchema, new Uint8Array(bin))
|
|
631
|
+
const json = data.elems
|
|
662
632
|
return new UniPool(
|
|
663
633
|
json.map((d) => {
|
|
664
634
|
return UniDM.fromBili(
|
|
@@ -674,8 +644,8 @@ export class UniPool {
|
|
|
674
644
|
* @param bin 符合`DmWebViewReplySchema`(bili视频meta)的protobuf二进制
|
|
675
645
|
*/
|
|
676
646
|
static fromBiliCommandGrpc(bin: Uint8Array | ArrayBuffer, options?: Options) {
|
|
677
|
-
const data = fromBinary(DmWebViewReplySchema, new Uint8Array(bin))
|
|
678
|
-
|
|
647
|
+
const data = fromBinary(DmWebViewReplySchema, new Uint8Array(bin))
|
|
648
|
+
const json = data.commandDms
|
|
679
649
|
return new UniPool(
|
|
680
650
|
json.map((d) => {
|
|
681
651
|
return UniDM.fromBiliCommand(d, d.oid, options)
|
package/src/utils/dm-gen.test.ts
CHANGED
|
@@ -83,9 +83,9 @@ describe('其它', () => {
|
|
|
83
83
|
expect(pool.dans[0].content).toBe('喜欢')
|
|
84
84
|
expect(pool.dans[1].content).toBe('不喜欢')
|
|
85
85
|
// 正式测试
|
|
86
|
-
const a = pool.dans[0].isSameAs(pool.dans[1])
|
|
87
|
-
|
|
88
|
-
|
|
86
|
+
const a = pool.dans[0].isSameAs(pool.dans[1])
|
|
87
|
+
const b = pool.dans[1].isSameAs(pool.dans[2])
|
|
88
|
+
const c = pool.dans[1].isSameAs(pool.dans[3])
|
|
89
89
|
console.info(a, b, c)
|
|
90
90
|
expect(a).toBe(false)
|
|
91
91
|
expect(b).toBe(true)
|