buzzk 1.0.0 → 1.2.0
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 +24 -5
- package/lib/channel.js +52 -3
- package/lib/chat.js +69 -6
- package/lib/index.js +2 -0
- package/lib/live.js +43 -0
- package/lib/tool.js +16 -0
- package/lib/val.js +5 -0
- package/lib/vm.js +18 -0
- package/package.json +2 -1
package/README.md
CHANGED
|
@@ -15,15 +15,27 @@
|
|
|
15
15
|
|
|
16
16
|
---
|
|
17
17
|
|
|
18
|
+
## 업데이트 내역
|
|
19
|
+
|
|
20
|
+
- 자동완성 기능 지원
|
|
21
|
+
|
|
22
|
+
>
|
|
23
|
+
|
|
24
|
+
- 팔로우 / 언팔로우 기능 추가
|
|
25
|
+
- live.getLiveDetail의 Return 값에 chatLimit 추가 (팔로우 대상 채팅 등...)
|
|
26
|
+
- 폴링 함수 추가 (chatID 변경 감지)
|
|
27
|
+
- API 호출 실패 시 오류 핸들링 (Return true / null)
|
|
28
|
+
- chat.disconnect 함수 보완
|
|
29
|
+
- 버전 체크 함수 추가
|
|
30
|
+
|
|
18
31
|
## 설치
|
|
19
32
|
|
|
20
|
-
1.
|
|
21
|
-
2.
|
|
22
|
-
3. `const buzzk = require("./buzzk");`
|
|
33
|
+
1. `npm install buzzk`
|
|
34
|
+
2. `const buzzk = require("buzzk");`
|
|
23
35
|
|
|
24
36
|
## 빠른. 시작.
|
|
25
37
|
|
|
26
|
-
const buzzk = require("
|
|
38
|
+
const buzzk = require("buzzk");
|
|
27
39
|
buzzk.login("NID_AUT 쿠키 값", "NID_SES 쿠키 값");
|
|
28
40
|
|
|
29
41
|
const buzzkChat = buzzk.chat;
|
|
@@ -85,6 +97,12 @@ dotenv와 함께 사용하는 것을 매우 권장합니다.
|
|
|
85
97
|
|
|
86
98
|
</details>
|
|
87
99
|
|
|
100
|
+
await buzzk.channel.followChannel("channelID 값");
|
|
101
|
+
|
|
102
|
+
>
|
|
103
|
+
|
|
104
|
+
await buzzk.channel.unFollowChannel("channelID 값");
|
|
105
|
+
|
|
88
106
|
---
|
|
89
107
|
|
|
90
108
|
> live
|
|
@@ -99,6 +117,7 @@ dotenv와 함께 사용하는 것을 매우 권장합니다.
|
|
|
99
117
|
- channelID
|
|
100
118
|
- channel
|
|
101
119
|
- chatID
|
|
120
|
+
- chatLimit //팔로워 전용 채팅 등...
|
|
102
121
|
- userCount
|
|
103
122
|
- now
|
|
104
123
|
- total
|
|
@@ -189,4 +208,4 @@ dotenv와 함께 사용하는 것을 매우 권장합니다.
|
|
|
189
208
|
|
|
190
209
|
>
|
|
191
210
|
|
|
192
|
-
chat.disconnect(); //채팅창 연결 끊기
|
|
211
|
+
await chat.disconnect(); //채팅창 연결 끊기
|
package/lib/channel.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
const { reqChzzk } = require("./tool.js");
|
|
1
|
+
const { reqChzzk, exChzzk } = require("./tool.js");
|
|
2
2
|
|
|
3
3
|
class chzzkChannel {
|
|
4
4
|
constructor(channelID, name, description, follower, imageURL, isLive) {
|
|
@@ -11,13 +11,32 @@ class chzzkChannel {
|
|
|
11
11
|
}
|
|
12
12
|
}
|
|
13
13
|
|
|
14
|
+
/**
|
|
15
|
+
* @typedef {Object.<number, chzzkChannel>} chzzkChannels
|
|
16
|
+
*/
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* @typedef {Object} chzzkChannel
|
|
20
|
+
* @property {string} channelID
|
|
21
|
+
* @property {string} name
|
|
22
|
+
* @property {string} description
|
|
23
|
+
* @property {string} follower
|
|
24
|
+
* @property {string} imageURL
|
|
25
|
+
* @property {string} isLive
|
|
26
|
+
*/
|
|
27
|
+
|
|
28
|
+
/**
|
|
29
|
+
* @param {string} keyword
|
|
30
|
+
* @returns {Promise<chzzkChannels>}
|
|
31
|
+
*/
|
|
14
32
|
async function getChannel (keyword) {
|
|
15
33
|
return new Promise(async (resolve, reject) => {
|
|
16
34
|
|
|
17
35
|
let chSearch = await reqChzzk("service/v1/search/channels?keyword=" + keyword + "&offset=0&size=13&withFirstChannelContent=false");
|
|
36
|
+
if (chSearch.code != 200) return resolve(null);
|
|
18
37
|
chSearch = chSearch.content.data;
|
|
19
38
|
|
|
20
|
-
if (!chSearch) return resolve();
|
|
39
|
+
if (!chSearch) return resolve(null);
|
|
21
40
|
|
|
22
41
|
let chRes = new Map();
|
|
23
42
|
|
|
@@ -31,6 +50,36 @@ async function getChannel (keyword) {
|
|
|
31
50
|
});
|
|
32
51
|
}
|
|
33
52
|
|
|
53
|
+
/**
|
|
54
|
+
* @param {string} channelID
|
|
55
|
+
* @returns {Promise<boolean>}
|
|
56
|
+
*/
|
|
57
|
+
async function followChannel (channelID) {
|
|
58
|
+
return new Promise(async (resolve, reject) => {
|
|
59
|
+
|
|
60
|
+
let flRes = await exChzzk("POST", "service/v1/channels/" + channelID + "/follow");
|
|
61
|
+
if (flRes.code == 200) return resolve(true);
|
|
62
|
+
else return resolve(null);
|
|
63
|
+
|
|
64
|
+
});
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
/**
|
|
68
|
+
* @param {string} channelID
|
|
69
|
+
* @returns {Promise<boolean>}
|
|
70
|
+
*/
|
|
71
|
+
async function unFollowChannel (channelID) {
|
|
72
|
+
return new Promise(async (resolve, reject) => {
|
|
73
|
+
|
|
74
|
+
let flRes = await exChzzk("DELETE", "service/v1/channels/" + channelID + "/follow");
|
|
75
|
+
if (flRes.code == 200) return resolve(true);
|
|
76
|
+
else return resolve(null);
|
|
77
|
+
|
|
78
|
+
});
|
|
79
|
+
}
|
|
80
|
+
|
|
34
81
|
module.exports = {
|
|
35
|
-
getChannel: getChannel
|
|
82
|
+
getChannel: getChannel,
|
|
83
|
+
followChannel: followChannel,
|
|
84
|
+
unFollowChannel: unFollowChannel
|
|
36
85
|
}
|
package/lib/chat.js
CHANGED
|
@@ -15,19 +15,25 @@ class chzzkChat {
|
|
|
15
15
|
#svcid; //game
|
|
16
16
|
#sid;
|
|
17
17
|
#chatID;
|
|
18
|
+
|
|
19
|
+
#pollingStatus = false;
|
|
18
20
|
//Private
|
|
19
21
|
|
|
22
|
+
/**
|
|
23
|
+
* @returns {Promise<boolean>}
|
|
24
|
+
*/
|
|
20
25
|
connect() {
|
|
21
26
|
return new Promise(async (resolve, reject) => {
|
|
27
|
+
if (this.#ws) return resolve(null);
|
|
28
|
+
|
|
22
29
|
//Get ChatID
|
|
23
30
|
let cidRes = await getLiveStatus(this.channelID);
|
|
24
|
-
|
|
25
31
|
this.#chatID = cidRes.chatID;
|
|
26
32
|
//Get ChatID
|
|
27
33
|
|
|
28
34
|
//Get accTkn
|
|
29
35
|
let accRes = await reqGame("nng_main/v1/chats/access-token?channelId=" + this.#chatID + "&chatType=STREAMING");
|
|
30
|
-
|
|
36
|
+
if (accRes.code != 200) return resolve(null);
|
|
31
37
|
this.#accTkn = accRes.content.accessToken;
|
|
32
38
|
//Get accTkn
|
|
33
39
|
|
|
@@ -39,6 +45,10 @@ class chzzkChat {
|
|
|
39
45
|
this.#ws = new WebSocket("wss://kr-ss" + this.#ssID + ".chat.naver.com/chat");
|
|
40
46
|
//Connect Web Socket
|
|
41
47
|
|
|
48
|
+
//SetPolling
|
|
49
|
+
if (!this.#pollingStatus) this.polling();
|
|
50
|
+
//SetPolling
|
|
51
|
+
|
|
42
52
|
//WS Open
|
|
43
53
|
this.#ws.on("open", () => {
|
|
44
54
|
console.log("[WS] Connected!");
|
|
@@ -90,7 +100,7 @@ class chzzkChat {
|
|
|
90
100
|
//Ping Pong
|
|
91
101
|
|
|
92
102
|
//Connected
|
|
93
|
-
else if (data.cmd == 10100) resolve();
|
|
103
|
+
else if (data.cmd == 10100) resolve(true);
|
|
94
104
|
//Connected
|
|
95
105
|
});
|
|
96
106
|
//WS Message
|
|
@@ -98,8 +108,13 @@ class chzzkChat {
|
|
|
98
108
|
});
|
|
99
109
|
}
|
|
100
110
|
|
|
111
|
+
/**
|
|
112
|
+
* @param {string} message
|
|
113
|
+
* @returns {Promise<boolean>}
|
|
114
|
+
*/
|
|
101
115
|
send(message) {
|
|
102
116
|
return new Promise(async (resolve, reject) => {
|
|
117
|
+
if (!this.#ws) return resolve(null);
|
|
103
118
|
|
|
104
119
|
let extras = {
|
|
105
120
|
"chatType":"STREAMING",
|
|
@@ -129,12 +144,33 @@ class chzzkChat {
|
|
|
129
144
|
|
|
130
145
|
this.#ws.send(JSON.stringify(sendOpt));
|
|
131
146
|
|
|
132
|
-
return resolve();
|
|
147
|
+
return resolve(true);
|
|
133
148
|
//WS Send
|
|
134
149
|
|
|
135
150
|
});
|
|
136
151
|
}
|
|
137
152
|
|
|
153
|
+
/**
|
|
154
|
+
* @typedef {Object.<number, chzzkMessage>} chzzkMessages
|
|
155
|
+
*/
|
|
156
|
+
|
|
157
|
+
/**
|
|
158
|
+
* @typedef {Object} chzzkMessage
|
|
159
|
+
* @property {chzzkMessageAuthor} author
|
|
160
|
+
* @property {string} message
|
|
161
|
+
* @property {number} time
|
|
162
|
+
*/
|
|
163
|
+
|
|
164
|
+
/**
|
|
165
|
+
* @typedef {Object} chzzkMessageAuthor
|
|
166
|
+
* @property {string} id
|
|
167
|
+
* @property {string} name
|
|
168
|
+
* @property {string} imageURL
|
|
169
|
+
*/
|
|
170
|
+
|
|
171
|
+
/**
|
|
172
|
+
* @param {function(chzzkMessages)} callback
|
|
173
|
+
*/
|
|
138
174
|
onMessage(callback) {
|
|
139
175
|
if (!this.#ws) return callback(null);
|
|
140
176
|
|
|
@@ -166,6 +202,10 @@ class chzzkChat {
|
|
|
166
202
|
});
|
|
167
203
|
}
|
|
168
204
|
|
|
205
|
+
/**
|
|
206
|
+
* @param {?number} size
|
|
207
|
+
* @return {Promise<chzzkMessages>}
|
|
208
|
+
*/
|
|
169
209
|
getRecentChat(size) {
|
|
170
210
|
return new Promise(async (resolve, reject) => {
|
|
171
211
|
if (!this.#ws) return resolve(null);
|
|
@@ -213,8 +253,31 @@ class chzzkChat {
|
|
|
213
253
|
});
|
|
214
254
|
}
|
|
215
255
|
|
|
216
|
-
|
|
217
|
-
|
|
256
|
+
/**
|
|
257
|
+
* @returns {Promise<boolean>}
|
|
258
|
+
*/
|
|
259
|
+
async disconnect() {
|
|
260
|
+
return new Promise(async (resolve, reject) => {
|
|
261
|
+
if (!this.#ws) return resolve(null);
|
|
262
|
+
|
|
263
|
+
await this.#ws.close();
|
|
264
|
+
this.#ws = null;
|
|
265
|
+
return resolve(true);
|
|
266
|
+
});
|
|
267
|
+
}
|
|
268
|
+
|
|
269
|
+
async polling () {
|
|
270
|
+
if (!this.#ws) return this.#pollingStatus = false;
|
|
271
|
+
this.#pollingStatus = true;
|
|
272
|
+
|
|
273
|
+
//Get ChatID
|
|
274
|
+
let cidRes = await getLiveStatus(this.channelID);
|
|
275
|
+
this.#chatID = cidRes.chatID;
|
|
276
|
+
//Get ChatID
|
|
277
|
+
|
|
278
|
+
setTimeout(() => {
|
|
279
|
+
return this.polling();
|
|
280
|
+
}, cidRes.polling.callPeriodMilliSecond);
|
|
218
281
|
}
|
|
219
282
|
}
|
|
220
283
|
|
package/lib/index.js
CHANGED
package/lib/live.js
CHANGED
|
@@ -1,15 +1,42 @@
|
|
|
1
1
|
const { reqChzzk } = require("./tool.js");
|
|
2
2
|
|
|
3
|
+
/**
|
|
4
|
+
* @typedef {Object} chzzkLiveDetail
|
|
5
|
+
* @property {string} channelID
|
|
6
|
+
* @property {Object} channel
|
|
7
|
+
* @property {string} chatID
|
|
8
|
+
* @property {string} chatLimit
|
|
9
|
+
* @property {userCount} userCount
|
|
10
|
+
* @property {string} title
|
|
11
|
+
* @property {string} startOn
|
|
12
|
+
* @property {string} closeOn
|
|
13
|
+
* @property {string} status
|
|
14
|
+
* @property {Object} polling
|
|
15
|
+
*
|
|
16
|
+
*/
|
|
17
|
+
|
|
18
|
+
/**
|
|
19
|
+
* @typedef {Object} userCount
|
|
20
|
+
* @property {number} now
|
|
21
|
+
* @property {number} total
|
|
22
|
+
*/
|
|
23
|
+
|
|
24
|
+
/**
|
|
25
|
+
* @param {string} channelID
|
|
26
|
+
* @returns {Promise<chzzkLiveDetail>}
|
|
27
|
+
*/
|
|
3
28
|
async function getLiveDetail (channelID) {
|
|
4
29
|
return new Promise(async (resolve, reject) => {
|
|
5
30
|
|
|
6
31
|
let res = await reqChzzk("service/v2/channels/" + channelID + "/live-detail");
|
|
32
|
+
if (res.code != 200) return resolve(null);
|
|
7
33
|
res = res.content;
|
|
8
34
|
|
|
9
35
|
let lvDetail = {
|
|
10
36
|
channelID: res.channel.channelId,
|
|
11
37
|
channel: res.channel,
|
|
12
38
|
chatID: res.chatChannelId,
|
|
39
|
+
chatLimit: res.chatAvailableGroup,
|
|
13
40
|
userCount: { now: res.concurrentUserCount, total: res.accumulateCount },
|
|
14
41
|
title: res.liveTitle,
|
|
15
42
|
startOn: res.openDate,
|
|
@@ -23,10 +50,26 @@ async function getLiveDetail (channelID) {
|
|
|
23
50
|
});
|
|
24
51
|
}
|
|
25
52
|
|
|
53
|
+
/**
|
|
54
|
+
* @typedef {Object} chzzkLiveStatus
|
|
55
|
+
* @property {string} channelID
|
|
56
|
+
* @property {string} chatID
|
|
57
|
+
* @property {userCount} userCount
|
|
58
|
+
* @property {string} title
|
|
59
|
+
* @property {string} status
|
|
60
|
+
* @property {Object} polling
|
|
61
|
+
*
|
|
62
|
+
*/
|
|
63
|
+
|
|
64
|
+
/**
|
|
65
|
+
* @param {string} channelID
|
|
66
|
+
* @returns {Promise<chzzkLiveStatus>}
|
|
67
|
+
*/
|
|
26
68
|
async function getLiveStatus (channelID) {
|
|
27
69
|
return new Promise(async (resolve, reject) => {
|
|
28
70
|
|
|
29
71
|
let res = await reqChzzk("polling/v2/channels/" + channelID + "/live-status");
|
|
72
|
+
if (res.code != 200) return resolve(null);
|
|
30
73
|
res = res.content;
|
|
31
74
|
|
|
32
75
|
let lvStatus = {
|
package/lib/tool.js
CHANGED
|
@@ -15,6 +15,21 @@ function reqChzzk (path) {
|
|
|
15
15
|
});
|
|
16
16
|
}
|
|
17
17
|
|
|
18
|
+
function exChzzk (method, path) {
|
|
19
|
+
return new Promise(async (resolve, reject) => {
|
|
20
|
+
|
|
21
|
+
fetch(chzzkBaseURL + path, {
|
|
22
|
+
method: method,
|
|
23
|
+
headers: {
|
|
24
|
+
"Cookie": "NID_AUT=" + NID.AUT + ";NID_SES=" + NID.SES
|
|
25
|
+
}
|
|
26
|
+
})
|
|
27
|
+
|
|
28
|
+
.then((response) => resolve(response.json()));
|
|
29
|
+
|
|
30
|
+
});
|
|
31
|
+
}
|
|
32
|
+
|
|
18
33
|
function reqGame (path) {
|
|
19
34
|
return new Promise(async (resolve, reject) => {
|
|
20
35
|
|
|
@@ -32,5 +47,6 @@ function reqGame (path) {
|
|
|
32
47
|
|
|
33
48
|
module.exports = {
|
|
34
49
|
reqChzzk: reqChzzk,
|
|
50
|
+
exChzzk: exChzzk,
|
|
35
51
|
reqGame: reqGame
|
|
36
52
|
}
|
package/lib/val.js
CHANGED
package/lib/vm.js
ADDED
|
@@ -0,0 +1,18 @@
|
|
|
1
|
+
async function check () {
|
|
2
|
+
|
|
3
|
+
let localPkg = require("../package.json");
|
|
4
|
+
let remotePkg = await fetch("https://raw.githubusercontent.com/Emin-G/buzzk/master/package.json");
|
|
5
|
+
|
|
6
|
+
if (remotePkg.status != 200) return console.log("[BUZZK] 최신 버전에 대한 정보를 불러오지 못했습니다.");
|
|
7
|
+
|
|
8
|
+
remotePkg = await remotePkg.json();
|
|
9
|
+
|
|
10
|
+
localPkg = String(localPkg.version).split(".");
|
|
11
|
+
remotePkg = String(remotePkg.version).split(".");
|
|
12
|
+
|
|
13
|
+
for (let v in remotePkg) {
|
|
14
|
+
if (parseInt(remotePkg[v]) > parseInt(localPkg[v])) return console.log("[BUZZK] 새로운 버전을 찾았습니다! ( npm install buzzk@" + remotePkg.join(".") + " )");
|
|
15
|
+
}
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
check();
|
package/package.json
CHANGED