connectbase-client 3.34.0 → 3.35.1

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/dist/index.mjs CHANGED
@@ -334,6 +334,15 @@ var HttpClient = class {
334
334
  getBaseUrl() {
335
335
  return this.config.baseUrl;
336
336
  }
337
+ /**
338
+ * 이 클라이언트에 설정된 앱 ID 반환 (미설정 시 undefined).
339
+ *
340
+ * 콘솔(앱 소유자 JWT) 경로를 호출하기 전에 appId 유무를 확인하기 위한 public 접근자.
341
+ * private `config` 필드를 access-modifier 관통 cast 없이 노출한다.
342
+ */
343
+ getAppId() {
344
+ return this.config.appId;
345
+ }
337
346
  async refreshAccessToken() {
338
347
  if (this.isRefreshing) {
339
348
  return this.refreshPromise;
@@ -666,12 +675,15 @@ var HttpClient = class {
666
675
  }
667
676
  async put(url, data, config) {
668
677
  const headers = await this.prepareHeaders(config);
678
+ if (data instanceof FormData) {
679
+ headers.delete("Content-Type");
680
+ }
669
681
  return this.doFetch(
670
682
  url,
671
683
  {
672
684
  method: "PUT",
673
685
  headers,
674
- body: JSON.stringify(data)
686
+ body: data instanceof FormData ? data : JSON.stringify(data)
675
687
  },
676
688
  config
677
689
  );
@@ -794,13 +806,14 @@ var AuthAPI = class {
794
806
  return;
795
807
  }
796
808
  if (typeof window === "undefined") return;
809
+ const bridge = window;
797
810
  if (memberId) {
798
- if (typeof window.__cbSetMember === "function") {
799
- window.__cbSetMember(memberId);
811
+ if (typeof bridge.__cbSetMember === "function") {
812
+ bridge.__cbSetMember(memberId);
800
813
  }
801
814
  } else {
802
- if (typeof window.__cbClearMember === "function") {
803
- window.__cbClearMember();
815
+ if (typeof bridge.__cbClearMember === "function") {
816
+ bridge.__cbClearMember();
804
817
  }
805
818
  }
806
819
  }
@@ -846,6 +859,15 @@ var AuthAPI = class {
846
859
  data,
847
860
  { skipAuth: true }
848
861
  );
862
+ assertShape(
863
+ response,
864
+ {
865
+ access_token: { type: "string" },
866
+ refresh_token: { type: "string" },
867
+ member_id: { type: "string-or-number" }
868
+ },
869
+ "auth.signUpMember"
870
+ );
849
871
  this.http.setTokens(response.access_token, response.refresh_token);
850
872
  this.notifyVisitorTracker(response.member_id);
851
873
  return response;
@@ -1076,6 +1098,14 @@ var AuthAPI = class {
1076
1098
  {},
1077
1099
  { headers: { "Authorization": `Bearer ${storedData.refreshToken}` }, skipAuth: true }
1078
1100
  );
1101
+ assertShape(
1102
+ refreshed,
1103
+ {
1104
+ access_token: { type: "string" },
1105
+ refresh_token: { type: "string" }
1106
+ },
1107
+ "auth.signInAsGuestMember.reissue"
1108
+ );
1079
1109
  this.http.setTokens(refreshed.access_token, refreshed.refresh_token);
1080
1110
  this.storeGuestMemberTokens(refreshed.access_token, refreshed.refresh_token, storedData.memberId);
1081
1111
  this.notifyVisitorTracker(storedData.memberId);
@@ -1096,6 +1126,15 @@ var AuthAPI = class {
1096
1126
  {},
1097
1127
  { skipAuth: true }
1098
1128
  );
1129
+ assertShape(
1130
+ response,
1131
+ {
1132
+ access_token: { type: "string" },
1133
+ refresh_token: { type: "string" },
1134
+ member_id: { type: "string-or-number" }
1135
+ },
1136
+ "auth.signInAsGuestMember.new"
1137
+ );
1099
1138
  this.http.setTokens(response.access_token, response.refresh_token);
1100
1139
  this.storeGuestMemberTokens(response.access_token, response.refresh_token, response.member_id);
1101
1140
  this.notifyVisitorTracker(response.member_id);
@@ -1282,7 +1321,7 @@ var DatabaseAPI = class {
1282
1321
  * appId 가 설정되어 있어야 콘솔 경로를 호출할 수 있습니다 (validation_schema set/delete).
1283
1322
  */
1284
1323
  requireAppId() {
1285
- const appId = this.http.config?.appId;
1324
+ const appId = this.http.getAppId();
1286
1325
  if (!appId) {
1287
1326
  throw new Error(
1288
1327
  "setValidationSchema/deleteValidationSchema \uB294 \uCF58\uC194 (JWT) \uC778\uC99D\uC774 \uD544\uC694\uD558\uBA70 ConnectBase config \uC5D0 appId \uAC00 \uC124\uC815\uB418\uC5B4\uC57C \uD569\uB2C8\uB2E4."
@@ -5809,9 +5848,13 @@ var SubscriptionAPI = class {
5809
5848
  * })
5810
5849
  * ```
5811
5850
  */
5812
- async cancel(subscriptionId, data) {
5851
+ async cancel(subscriptionId, data = {}) {
5813
5852
  const prefix = this.getPublicPrefix();
5814
- return this.http.post(`${prefix}/subscriptions/${subscriptionId}/cancel`, data);
5853
+ const body = {
5854
+ reason: data.reason,
5855
+ cancel_at_end: !data.immediate
5856
+ };
5857
+ return this.http.post(`${prefix}/subscriptions/${subscriptionId}/cancel`, body);
5815
5858
  }
5816
5859
  // =====================
5817
5860
  // Subscription Payment APIs
@@ -6211,12 +6254,8 @@ var VideoAPI = class {
6211
6254
  `/v1/public/storages/videos/${storageId}/uploads/init`,
6212
6255
  {
6213
6256
  filename: file.name,
6214
- size: file.size,
6215
- mime_type: file.type,
6216
- title: options.title,
6217
- description: options.description,
6218
- visibility: options.visibility || "private",
6219
- tags: options.tags
6257
+ file_size: file.size,
6258
+ mime_type: file.type
6220
6259
  }
6221
6260
  );
6222
6261
  const chunkSize = session.chunk_size || DEFAULT_CHUNK_SIZE;
@@ -6230,9 +6269,8 @@ var VideoAPI = class {
6230
6269
  const chunk = file.slice(start, end);
6231
6270
  const formData = new FormData();
6232
6271
  formData.append("chunk", chunk);
6233
- formData.append("chunk_index", String(i));
6234
- await this.http.post(
6235
- `/v1/public/storages/videos/${storageId}/uploads/${session.session_id}/chunk`,
6272
+ await this.http.put(
6273
+ `/v1/public/storages/videos/${storageId}/uploads/${session.upload_id}/chunk?chunk_index=${i}`,
6236
6274
  formData
6237
6275
  );
6238
6276
  uploadedChunks++;
@@ -6254,10 +6292,15 @@ var VideoAPI = class {
6254
6292
  }
6255
6293
  }
6256
6294
  const result = await this.http.post(
6257
- `/v1/public/storages/videos/${storageId}/uploads/${session.session_id}/complete`,
6258
- {}
6295
+ `/v1/public/storages/videos/${storageId}/uploads/${session.upload_id}/complete`,
6296
+ {
6297
+ title: options.title,
6298
+ description: options.description,
6299
+ visibility: options.visibility || "private",
6300
+ tags: options.tags
6301
+ }
6259
6302
  );
6260
- return result.video;
6303
+ return this.storage.getVideo(storageId, result.video_id);
6261
6304
  },
6262
6305
  /**
6263
6306
  * List videos in a specific storage
@@ -6374,15 +6417,10 @@ var VideoAPI = class {
6374
6417
  */
6375
6418
  async upload(file, options) {
6376
6419
  const prefix = this.getPublicPrefix();
6377
- const session = await this.videoFetch("POST", `${prefix}/uploads`, {
6420
+ const session = await this.videoFetch("POST", `${prefix}/uploads/init`, {
6378
6421
  filename: file.name,
6379
- size: file.size,
6380
- mime_type: file.type,
6381
- title: options.title,
6382
- description: options.description,
6383
- visibility: options.visibility || "private",
6384
- tags: options.tags,
6385
- channel_id: options.channel_id
6422
+ file_size: file.size,
6423
+ mime_type: file.type
6386
6424
  });
6387
6425
  const chunkSize = session.chunk_size || DEFAULT_CHUNK_SIZE;
6388
6426
  const totalChunks = Math.ceil(file.size / chunkSize);
@@ -6396,10 +6434,9 @@ var VideoAPI = class {
6396
6434
  const chunk = file.slice(start, end);
6397
6435
  const formData = new FormData();
6398
6436
  formData.append("chunk", chunk);
6399
- formData.append("chunk_index", String(i));
6400
6437
  await this.videoFetch(
6401
- "POST",
6402
- `${prefix}/uploads/${session.session_id}/chunks`,
6438
+ "PUT",
6439
+ `${prefix}/uploads/${session.upload_id}/chunk?chunk_index=${i}`,
6403
6440
  formData
6404
6441
  );
6405
6442
  uploadedChunks++;
@@ -6422,10 +6459,15 @@ var VideoAPI = class {
6422
6459
  }
6423
6460
  const result = await this.videoFetch(
6424
6461
  "POST",
6425
- `${prefix}/uploads/${session.session_id}/complete`,
6426
- {}
6462
+ `${prefix}/uploads/${session.upload_id}/complete`,
6463
+ {
6464
+ title: options.title,
6465
+ description: options.description,
6466
+ visibility: options.visibility || "private",
6467
+ tags: options.tags
6468
+ }
6427
6469
  );
6428
- return result.video;
6470
+ return this.get(result.video_id);
6429
6471
  }
6430
6472
  /**
6431
6473
  * Wait for video processing to complete
@@ -6537,15 +6579,23 @@ var VideoAPI = class {
6537
6579
  return this.videoFetch("GET", `${prefix}/videos/${videoId}/stream-url${params}`);
6538
6580
  }
6539
6581
  /**
6540
- * Get available thumbnails for a video
6582
+ * Get available thumbnails for a video.
6583
+ *
6584
+ * 서버는 대표 썸네일 1개(`thumbnail_url`) + 선택적 추가 썸네일 목록(`thumbnail_urls`)을
6585
+ * 반환한다. 둘을 합쳐 중복 없는 URL 배열로 정규화해 돌려준다.
6541
6586
  */
6542
6587
  async getThumbnails(videoId) {
6543
6588
  const prefix = this.getPublicPrefix();
6544
6589
  const response = await this.videoFetch(
6545
6590
  "GET",
6546
- `${prefix}/videos/${videoId}/thumbnails`
6591
+ `${prefix}/videos/${videoId}/thumbnail`
6547
6592
  );
6548
- return response.thumbnails;
6593
+ const urls = /* @__PURE__ */ new Set();
6594
+ if (response.thumbnail_url) urls.add(response.thumbnail_url);
6595
+ for (const u of response.thumbnail_urls ?? []) {
6596
+ if (u) urls.add(u);
6597
+ }
6598
+ return [...urls];
6549
6599
  }
6550
6600
  /**
6551
6601
  * Get transcode status
@@ -7545,7 +7595,8 @@ var GameAPI = class {
7545
7595
  "GAME_GET_ROOM_FAILED"
7546
7596
  );
7547
7597
  }
7548
- return response.json();
7598
+ const data = await response.json();
7599
+ return data.room;
7549
7600
  }
7550
7601
  /**
7551
7602
  * 룸 생성 (HTTP, gRPC 대안)
@@ -9597,13 +9648,14 @@ var AnalyticsAPI = class {
9597
9648
  setMemberId(memberId) {
9598
9649
  this.memberId = memberId || null;
9599
9650
  if (typeof window !== "undefined") {
9651
+ const bridge = window;
9600
9652
  if (memberId) {
9601
- if (typeof window.__cbSetMember === "function") {
9602
- window.__cbSetMember(memberId);
9653
+ if (typeof bridge.__cbSetMember === "function") {
9654
+ bridge.__cbSetMember(memberId);
9603
9655
  }
9604
9656
  } else {
9605
- if (typeof window.__cbClearMember === "function") {
9606
- window.__cbClearMember();
9657
+ if (typeof bridge.__cbClearMember === "function") {
9658
+ bridge.__cbClearMember();
9607
9659
  }
9608
9660
  }
9609
9661
  }
@@ -9727,7 +9779,7 @@ var AnalyticsAPI = class {
9727
9779
  * @example
9728
9780
  * ```ts
9729
9781
  * // 결제 완료 직후 이탈에 대비해 즉시 flush
9730
- * await cb.analytics.track('purchase_completed', { order_id: '123' })
9782
+ * await cb.analytics.trackEvent('purchase_completed', { order_id: '123' })
9731
9783
  * await cb.analytics.flush()
9732
9784
  * window.location.href = '/thank-you'
9733
9785
  * ```
@@ -9868,7 +9920,8 @@ var AnalyticsAPI = class {
9868
9920
  }
9869
9921
  isDNT() {
9870
9922
  if (typeof navigator === "undefined") return false;
9871
- return navigator.doNotTrack === "1" || navigator.globalPrivacyControl === true;
9923
+ const gpc = navigator.globalPrivacyControl;
9924
+ return navigator.doNotTrack === "1" || gpc === true;
9872
9925
  }
9873
9926
  createBaseEvent(type) {
9874
9927
  return {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "connectbase-client",
3
- "version": "3.34.0",
3
+ "version": "3.35.1",
4
4
  "description": "Connect Base JavaScript/TypeScript SDK for browser and Node.js",
5
5
  "repository": {
6
6
  "type": "git",