tiktokautouploader 2.7__py2.py3-none-any.whl → 2.9__py2.py3-none-any.whl

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.
@@ -1,18 +1,16 @@
1
1
  const { chromium } = require('playwright-extra')
2
2
 
3
- // Load the stealth plugin and use defaults (all tricks to hide playwright usage)
4
- // Note: playwright-extra is compatible with most puppeteer-extra plugins
3
+
5
4
  const stealth = require('puppeteer-extra-plugin-stealth')()
6
5
 
7
- // Add the plugin to playwright (any number of plugins can be added)
8
6
  chromium.use(stealth)
9
7
 
10
- // Define a delay function
11
- function delay(time) {
8
+
9
+ function sleep(time) {
12
10
  return new Promise(resolve => setTimeout(resolve, time));
13
11
  }
14
12
 
15
- // Define a function to check for redirects
13
+
16
14
  async function checkForRedirect(page) {
17
15
  const currentUrl = page.url();
18
16
  const pattern = /^https:\/\/www\.tiktok\.com\/foryou/;
@@ -25,19 +23,18 @@ async function checkForRedirect(page) {
25
23
  const page = await browser.newPage();
26
24
  await page.goto('https://www.tiktok.com/login');
27
25
 
28
- // Loop until redirect is detected
29
26
  while (!redirected) {
30
27
  redirected = await checkForRedirect(page);
31
28
  if (!redirected) {
32
- await delay(1000);
29
+ await sleep(1000);
33
30
  }
34
31
  }
35
32
 
36
- delay(2000)
33
+ sleep(2000)
37
34
  const cookies = await page.context().cookies();
38
35
  const fs = require('fs');
39
36
  fs.writeFileSync('TK_cookies.json', JSON.stringify(cookies, null, 2));
40
37
 
41
- // Close the browser
38
+
42
39
  await browser.close();
43
40
  })();
@@ -11,9 +11,6 @@ import os
11
11
  import warnings
12
12
  warnings.filterwarnings("ignore")
13
13
 
14
- def no_draft_warning():
15
- print("SAVE AS DRAFT BUTTON NOT FOUND; CODE WILL CONTINUE RUNNING BUT VIDEO IS UNLIKELY TO UPLOAD; BEING ABLE TO SAVE AS DRAFT IS ESSENTIAL TO BEING ABLE TO EDIT VIDEOS AND POST, PLEASE BUILD UP ENOUGH ACCOUNT HISTORY TO BE ABLE TO SAVE DRAFTS ")
16
-
17
14
  def login_warning():
18
15
  print("NO COOKIES FILE FOUND, PLEASE LOG-IN WHEN PROMPTED")
19
16
 
@@ -21,10 +18,26 @@ def save_cookies(cookies):
21
18
  with open('TK_cookies.json', 'w') as file:
22
19
  json.dump(cookies, file, indent=4)
23
20
 
21
+ def check_expiry():
22
+ with open('TK_cookies.json', 'r') as file:
23
+ cookies = json.load(file)
24
+
25
+ current_time = int(time.time())
26
+ cookies_expire = []
27
+ expired = False
28
+ for cookie in cookies:
29
+ if cookie['name'] in ['sessionid', 'sid_tt', 'sessionid_ss', 'passport_auth_status']:
30
+ expiry = cookie.get('expires')
31
+ cookies_expire.append(expiry < current_time)
32
+
33
+ if all(cookies_expire):
34
+ expired = True
35
+
36
+ return expired
37
+
24
38
  def run_javascript():
25
39
  js_file_path = pkg_resources.resource_filename(__name__, 'Js_assets/login.js')
26
40
  result = subprocess.run(['node', js_file_path], capture_output=True, text=True)
27
- return result.stdout, result.stderr
28
41
 
29
42
  def install_js_dependencies():
30
43
  js_dir = pkg_resources.resource_filename(__name__, 'Js_assets')
@@ -34,7 +47,6 @@ def install_js_dependencies():
34
47
  print("JavaScript dependencies not found. Installing...")
35
48
  subprocess.run(['npm', 'install', 'playwright', 'playwright-extra', 'puppeteer-extra-plugin-stealth', '--silent'], cwd=js_dir, check=True)
36
49
  else:
37
- print("found dependencies")
38
50
  time.sleep(0.1)
39
51
 
40
52
 
@@ -197,7 +209,6 @@ def upload_tiktok(video, description, hashtags=None, sound_name=None, sound_aud_
197
209
  video (str) -> path to video to upload
198
210
  description (str) -> description for video
199
211
  hashtags (str)(array) -> hashtags for video
200
- cookies_path (str) -> path to tik tok cookies .json file
201
212
  sound_name (str) -> name of tik tok sound to use for video
202
213
  sound_aud_vol (str) -> volume of tik tok sound, 'main', 'mix' or 'background', check documentation for more info -> https://github.com/haziq-exe/TikTokAutoUploader
203
214
  schedule (str) -> format HH:MM, your local time to upload video
@@ -209,12 +220,17 @@ def upload_tiktok(video, description, hashtags=None, sound_name=None, sound_aud_
209
220
 
210
221
  retries = 0
211
222
  cookie_read = False
223
+ install_js_dependencies()
212
224
 
213
225
  if os.path.exists('TK_cookies.json'):
214
226
  cookies, cookie_read = read_cookies(cookies_path='TK_cookies.json')
227
+ expired = check_expiry()
228
+ if expired == True:
229
+ os.remove('TK_cookies.json')
230
+ print("COOKIES EXPIRED, PLEASE LOG-IN AGAIN")
231
+ cookie_read = False
215
232
 
216
233
  if cookie_read == False:
217
- install_js_dependencies()
218
234
  login_warning()
219
235
  run_javascript()
220
236
 
@@ -224,11 +240,14 @@ def upload_tiktok(video, description, hashtags=None, sound_name=None, sound_aud_
224
240
 
225
241
 
226
242
  with sync_playwright() as p:
227
- browser = p.chromium.launch(headless=True)
243
+
244
+ browser = p.firefox.launch(headless=True)
245
+
228
246
  context = browser.new_context()
229
247
  context.add_cookies(cookies)
230
248
  page = context.new_page()
231
249
  url = 'https://www.tiktok.com/tiktokstudio/upload?from=upload&lang=en'
250
+ url2 = 'https://www.tiktok.com/tiktokstudio/content?tab=draft'
232
251
 
233
252
  while retries < 2:
234
253
  try:
@@ -254,7 +273,6 @@ def upload_tiktok(video, description, hashtags=None, sound_name=None, sound_aud_
254
273
  time.sleep(0.1)
255
274
 
256
275
  if captcha == True:
257
- print("CAPTCHA FOUND")
258
276
  image = get_image_src(page)
259
277
  if image:
260
278
  if suppressprint == False:
@@ -291,7 +309,7 @@ def upload_tiktok(video, description, hashtags=None, sound_name=None, sound_aud_
291
309
  if attempts > 5:
292
310
  sys.exit("FAILED TO SOLVE CAPTCHA")
293
311
  try:
294
- page.wait_for_selector('.upload-text-container', timeout=10000)
312
+ page.wait_for_selector('.upload-text-container', timeout=5000)
295
313
  os.remove('captcha_image.jpg')
296
314
  if suppressprint == False:
297
315
  print("Captcha Solved")
@@ -308,7 +326,6 @@ def upload_tiktok(video, description, hashtags=None, sound_name=None, sound_aud_
308
326
  while objectclick == 'N.A':
309
327
  page.click('span.secsdk_captcha_refresh--text')
310
328
  page.wait_for_selector('div.VerifyBar___StyledDiv-sc-12zaxoy-0.hRJhHT')
311
- time.sleep(2)
312
329
  question = page.locator('div.VerifyBar___StyledDiv-sc-12zaxoy-0.hRJhHT').text_content()
313
330
  objectclick = understood_Qs(question)
314
331
  image = get_image_src(page)
@@ -333,10 +350,10 @@ def upload_tiktok(video, description, hashtags=None, sound_name=None, sound_aud_
333
350
  click_on_objects(page, webpage_coords)
334
351
  time.sleep(0.5)
335
352
  page.click("div.verify-captcha-submit-button")
336
- if attempts > 5:
353
+ if attempts > 10:
337
354
  sys.exit("FAILED TO SOLVE CAPTCHA")
338
355
  try:
339
- page.wait_for_selector('.upload-text-container', timeout=10000)
356
+ page.wait_for_selector('.upload-text-container', timeout=5000)
340
357
  solved = True
341
358
  os.remove('captcha_image.jpg')
342
359
  if suppressprint == False:
@@ -344,13 +361,11 @@ def upload_tiktok(video, description, hashtags=None, sound_name=None, sound_aud_
344
361
  except:
345
362
  continue
346
363
 
347
-
348
364
 
349
365
  try:
350
366
  page.set_input_files('input[type="file"][accept="video/*"]', f'{video}')
351
367
  except:
352
368
  sys.exit("ERROR: FAILED TO INPUT FILE. Possible Issues: Wifi too slow, file directory wrong, or check documentation to see if captcha is solvable")
353
-
354
369
  page.wait_for_selector('div[data-contents="true"]')
355
370
  page.click('div[data-contents="true"]')
356
371
  if suppressprint == False:
@@ -400,75 +415,10 @@ def upload_tiktok(video, description, hashtags=None, sound_name=None, sound_aud_
400
415
  except:
401
416
  sys.exit("ERROR: TIK TOK TOOK TOO LONG TO UPLOAD YOUR FILE (>20min). Try again, if issue persists then try a lower file size or different wifi connection")
402
417
 
403
- time.sleep(0.5)
418
+ time.sleep(0.2)
404
419
  if suppressprint == False:
405
420
  print("Tik tok done loading file onto servers")
406
- try:
407
- page.click('button.TUXButton.TUXButton--default.TUXButton--large.TUXButton--secondary:has-text("Save draft")', timeout=10000)
408
- page.wait_for_selector("path[d='M37.37 4.85a4.01 4.01 0 0 0-.99-.79 3 3 0 0 0-2.72 0c-.45.23-.81.6-1 .79a9 9 0 0 1-.04.05l-19.3 19.3c-1.64 1.63-2.53 2.52-3.35 3.47a36 36 0 0 0-4.32 6.16c-.6 1.1-1.14 2.24-2.11 4.33l-.3.6c-.4.75-.84 1.61-.8 2.43a2.5 2.5 0 0 0 2.37 2.36c.82.05 1.68-.4 2.44-.79l.59-.3c2.09-.97 3.23-1.5 4.33-2.11a36 36 0 0 0 6.16-4.32c.95-.82 1.84-1.71 3.47-3.34l19.3-19.3.05-.06a3 3 0 0 0 .78-3.71c-.22-.45-.6-.81-.78-1l-.02-.02-.03-.03-3.67-3.67a8.7 8.7 0 0 1-.06-.05ZM16.2 26.97 35.02 8.15l2.83 2.83L19.03 29.8c-1.7 1.7-2.5 2.5-3.33 3.21a32 32 0 0 1-7.65 4.93 32 32 0 0 1 4.93-7.65c.73-.82 1.51-1.61 3.22-3.32Z']")
409
- page.click("path[d='M37.37 4.85a4.01 4.01 0 0 0-.99-.79 3 3 0 0 0-2.72 0c-.45.23-.81.6-1 .79a9 9 0 0 1-.04.05l-19.3 19.3c-1.64 1.63-2.53 2.52-3.35 3.47a36 36 0 0 0-4.32 6.16c-.6 1.1-1.14 2.24-2.11 4.33l-.3.6c-.4.75-.84 1.61-.8 2.43a2.5 2.5 0 0 0 2.37 2.36c.82.05 1.68-.4 2.44-.79l.59-.3c2.09-.97 3.23-1.5 4.33-2.11a36 36 0 0 0 6.16-4.32c.95-.82 1.84-1.71 3.47-3.34l19.3-19.3.05-.06a3 3 0 0 0 .78-3.71c-.22-.45-.6-.81-.78-1l-.02-.02-.03-.03-3.67-3.67a8.7 8.7 0 0 1-.06-.05ZM16.2 26.97 35.02 8.15l2.83 2.83L19.03 29.8c-1.7 1.7-2.5 2.5-3.33 3.21a32 32 0 0 1-7.65 4.93 32 32 0 0 1 4.93-7.65c.73-.82 1.51-1.61 3.22-3.32Z']")
410
- page.wait_for_selector('div[data-contents="true"]')
411
- page.wait_for_function("document.querySelector('.info-progress-num').textContent.trim() === '100%'", timeout=3000000)
412
- time.sleep(0.5)
413
- except:
414
- no_draft_warning()
415
-
416
- if sound_name != None:
417
- page.click("div.TUXButton-label:has-text('Edit video')")
418
- page.wait_for_selector("input.search-bar-input")
419
- page.fill(f"input.search-bar-input", f"{sound_name}")
420
- time.sleep(0.5)
421
- page.click("div.TUXButton-label:has-text('Search')")
422
- try:
423
- page.wait_for_selector('div.music-card-container')
424
- page.click("div.music-card-container")
425
- page.wait_for_selector("div.TUXButton-label:has-text('Use')")
426
- page.click("div.TUXButton-label:has-text('Use')")
427
- except:
428
- sys.exit("ERROR: SOUND NOT FOUND, VIDEO SAVED AS DRAFT")
429
- try:
430
- page.wait_for_selector('img[src="data:image/svg+xml;base64,PHN2ZyB3aWR0aD0iMjEiIGhlaWdodD0iMjAiIHZpZXdCb3g9IjAgMCAyMSAyMCIgZmlsbD0ibm9uZSIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj4KPHBhdGggZD0iTTAgNy41MDE2QzAgNi42NzMxNyAwLjY3MTU3MyA2LjAwMTYgMS41IDYuMDAxNkgzLjU3NzA5QzMuODY4MDUgNi4wMDE2IDQuMTQ0NTggNS44NzQ4OCA0LjMzNDU1IDUuNjU0NDlMOC43NDI1NSAwLjU0MDUyQzkuMzQ3OCAtMC4xNjE2NjggMTAuNSAwLjI2NjM3NCAxMC41IDEuMTkzNDFWMTguOTY3MkMxMC41IDE5Ljg3NDUgOS4zODg5NCAyMC4zMTI5IDguNzY5NDIgMTkuNjVMNC4zMzE3OSAxNC45MDIxQzQuMTQyNjkgMTQuNjk5OCAzLjg3ODE2IDE0LjU4NDkgMy42MDEyMiAxNC41ODQ5SDEuNUMwLjY3MTU3MyAxNC41ODQ5IDAgMTMuOTEzNCAwIDEzLjA4NDlWNy41MDE2Wk01Ljg0OTQ1IDYuOTYwMjdDNS4yNzk1NiA3LjYyMTQzIDQuNDQ5OTcgOC4wMDE2IDMuNTc3MDkgOC4wMDE2SDJWMTIuNTg0OUgzLjYwMTIyQzQuNDMyMDMgMTIuNTg0OSA1LjIyNTY0IDEyLjkyOTUgNS43OTI5NSAxMy41MzY0TDguNSAxNi40MzI4VjMuODg1MjJMNS44NDk0NSA2Ljk2MDI3WiIgZmlsbD0iIzE2MTgyMyIgZmlsbC1vcGFjaXR5PSIwLjYiLz4KPHBhdGggZD0iTTEzLjUxNSA3LjE5MTE5QzEzLjM0MjQgNi45NzU1OSAxMy4zMzk5IDYuNjYwNTYgMTMuNTM1MiA2LjQ2NTNMMTQuMjQyMyA1Ljc1ODE5QzE0LjQzNzYgNS41NjI5MyAxNC43NTU4IDUuNTYxNzUgMTQuOTM1NiA1Ljc3MTM2QzE2Ljk5NTkgOC4xNzM2MiAxNi45OTU5IDExLjgyOCAxNC45MzU2IDE0LjIzMDNDMTQuNzU1OCAxNC40Mzk5IDE0LjQzNzYgMTQuNDM4NyAxNC4yNDIzIDE0LjI0MzVMMTMuNTM1MiAxMy41MzY0QzEzLjMzOTkgMTMuMzQxMSAxMy4zNDI0IDEzLjAyNjEgMTMuNTE1IDEyLjgxMDVDMTQuODEzIDExLjE4ODUgMTQuODEzIDguODEzMTIgMTMuNTE1IDcuMTkxMTlaIiBmaWxsPSIjMTYxODIzIiBmaWxsLW9wYWNpdHk9IjAuNiIvPgo8cGF0aCBkPSJNMTYuNzE3MiAxNi43MTgzQzE2LjUyMTkgMTYuNTIzMSAxNi41MjMxIDE2LjIwNzQgMTYuNzA3MiAxNi4wMDE3QzE5LjcyNTcgMTIuNjMgMTkuNzI1NyA3LjM3MTY4IDE2LjcwNzIgNC4wMDAwMUMxNi41MjMxIDMuNzk0MjcgMTYuNTIxOSAzLjQ3ODU4IDE2LjcxNzIgMy4yODMzMkwxNy40MjQzIDIuNTc2MjFDMTcuNjE5NSAyLjM4MDk1IDE3LjkzNyAyLjM4MDIgMTguMTIzMyAyLjU4NDA4QzIxLjkwOTkgNi43MjkyNiAyMS45MDk5IDEzLjI3MjQgMTguMTIzMyAxNy40MTc2QzE3LjkzNyAxNy42MjE1IDE3LjYxOTUgMTcuNjIwNyAxNy40MjQzIDE3LjQyNTVMMTYuNzE3MiAxNi43MTgzWiIgZmlsbD0iIzE2MTgyMyIgZmlsbC1vcGFjaXR5PSIwLjYiLz4KPC9zdmc+Cg=="]')
431
- page.click('img[src="data:image/svg+xml;base64,PHN2ZyB3aWR0aD0iMjEiIGhlaWdodD0iMjAiIHZpZXdCb3g9IjAgMCAyMSAyMCIgZmlsbD0ibm9uZSIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj4KPHBhdGggZD0iTTAgNy41MDE2QzAgNi42NzMxNyAwLjY3MTU3MyA2LjAwMTYgMS41IDYuMDAxNkgzLjU3NzA5QzMuODY4MDUgNi4wMDE2IDQuMTQ0NTggNS44NzQ4OCA0LjMzNDU1IDUuNjU0NDlMOC43NDI1NSAwLjU0MDUyQzkuMzQ3OCAtMC4xNjE2NjggMTAuNSAwLjI2NjM3NCAxMC41IDEuMTkzNDFWMTguOTY3MkMxMC41IDE5Ljg3NDUgOS4zODg5NCAyMC4zMTI5IDguNzY5NDIgMTkuNjVMNC4zMzE3OSAxNC45MDIxQzQuMTQyNjkgMTQuNjk5OCAzLjg3ODE2IDE0LjU4NDkgMy42MDEyMiAxNC41ODQ5SDEuNUMwLjY3MTU3MyAxNC41ODQ5IDAgMTMuOTEzNCAwIDEzLjA4NDlWNy41MDE2Wk01Ljg0OTQ1IDYuOTYwMjdDNS4yNzk1NiA3LjYyMTQzIDQuNDQ5OTcgOC4wMDE2IDMuNTc3MDkgOC4wMDE2SDJWMTIuNTg0OUgzLjYwMTIyQzQuNDMyMDMgMTIuNTg0OSA1LjIyNTY0IDEyLjkyOTUgNS43OTI5NSAxMy41MzY0TDguNSAxNi40MzI4VjMuODg1MjJMNS44NDk0NSA2Ljk2MDI3WiIgZmlsbD0iIzE2MTgyMyIgZmlsbC1vcGFjaXR5PSIwLjYiLz4KPHBhdGggZD0iTTEzLjUxNSA3LjE5MTE5QzEzLjM0MjQgNi45NzU1OSAxMy4zMzk5IDYuNjYwNTYgMTMuNTM1MiA2LjQ2NTNMMTQuMjQyMyA1Ljc1ODE5QzE0LjQzNzYgNS41NjI5MyAxNC43NTU4IDUuNTYxNzUgMTQuOTM1NiA1Ljc3MTM2QzE2Ljk5NTkgOC4xNzM2MiAxNi45OTU5IDExLjgyOCAxNC45MzU2IDE0LjIzMDNDMTQuNzU1OCAxNC40Mzk5IDE0LjQzNzYgMTQuNDM4NyAxNC4yNDIzIDE0LjI0MzVMMTMuNTM1MiAxMy41MzY0QzEzLjMzOTkgMTMuMzQxMSAxMy4zNDI0IDEzLjAyNjEgMTMuNTE1IDEyLjgxMDVDMTQuODEzIDExLjE4ODUgMTQuODEzIDguODEzMTIgMTMuNTE1IDcuMTkxMTlaIiBmaWxsPSIjMTYxODIzIiBmaWxsLW9wYWNpdHk9IjAuNiIvPgo8cGF0aCBkPSJNMTYuNzE3MiAxNi43MTgzQzE2LjUyMTkgMTYuNTIzMSAxNi41MjMxIDE2LjIwNzQgMTYuNzA3MiAxNi4wMDE3QzE5LjcyNTcgMTIuNjMgMTkuNzI1NyA3LjM3MTY4IDE2LjcwNzIgNC4wMDAwMUMxNi41MjMxIDMuNzk0MjcgMTYuNTIxOSAzLjQ3ODU4IDE2LjcxNzIgMy4yODMzMkwxNy40MjQzIDIuNTc2MjFDMTcuNjE5NSAyLjM4MDk1IDE3LjkzNyAyLjM4MDIgMTguMTIzMyAyLjU4NDA4QzIxLjkwOTkgNi43MjkyNiAyMS45MDk5IDEzLjI3MjQgMTguMTIzMyAxNy40MTc2QzE3LjkzNyAxNy42MjE1IDE3LjYxOTUgMTcuNjIwNyAxNy40MjQzIDE3LjQyNTVMMTYuNzE3MiAxNi43MTgzWiIgZmlsbD0iIzE2MTgyMyIgZmlsbC1vcGFjaXR5PSIwLjYiLz4KPC9zdmc+Cg=="]')
432
- time.sleep(0.5)
433
- sliders = page.locator("input.scaleInput")
434
-
435
- if sound_aud_vol == 'background':
436
- slider1 = sliders.nth(0)
437
- bounding_box1 = slider1.bounding_box()
438
- if bounding_box1:
439
- x1 = bounding_box1["x"] + (bounding_box1["width"] * 0.95)
440
- y1 = bounding_box1["y"] + bounding_box1["height"] / 2
441
- page.mouse.click(x1, y1)
442
-
443
- slider2 = sliders.nth(1)
444
- bounding_box2 = slider2.bounding_box()
445
- if bounding_box2:
446
- x2 = bounding_box2["x"] + (bounding_box2["width"] * 0.097)
447
- y2 = bounding_box2["y"] + bounding_box2["height"] / 2
448
- page.mouse.click(x2, y2)
449
-
450
- if sound_aud_vol == 'main':
451
- slider1 = sliders.nth(0)
452
- bounding_box1 = slider1.bounding_box()
453
- if bounding_box1:
454
- x1 = bounding_box1["x"] + (bounding_box1["width"] * 0.097)
455
- y1 = bounding_box1["y"] + bounding_box1["height"] / 2
456
- page.mouse.click(x1, y1)
457
- slider2 = sliders.nth(1)
458
- bounding_box2 = slider2.bounding_box()
459
- if bounding_box2:
460
- x2 = bounding_box2["x"] + (bounding_box2["width"] * 0.95)
461
- y2 = bounding_box2["y"] + bounding_box2["height"] / 2
462
- page.mouse.click(x2, y2)
463
- except:
464
- sys.exit("ERROR ADJUSTING SOUND VOLUME, VIDEO SAVED AS DRAFT")
465
-
466
- page.wait_for_selector("div.TUXButton-label:has-text('Save edit')")
467
- page.click("div.TUXButton-label:has-text('Save edit')")
468
- if suppressprint == False:
469
- print("Added sound")
470
-
471
- page.wait_for_selector('div[data-contents="true"]')
421
+
472
422
  if schedule != None:
473
423
  try:
474
424
  hour = schedule[0:2]
@@ -480,25 +430,31 @@ def upload_tiktok(video, description, hashtags=None, sound_name=None, sound_aud_
480
430
  sys.exit("SCHEDULE TIME ERROR: PLEASE MAKE SURE YOUR SCHEDULE TIME IS A STRING THAT FOLLOWS THE 24H FORMAT 'HH:MM', VIDEO SAVED AS DRAFT")
481
431
 
482
432
  page.locator('div.TUXRadioStandalone.TUXRadioStandalone--medium').nth(1).click()
483
- time.sleep(0.5)
433
+ time.sleep(1)
434
+ if page.locator('button.TUXButton.TUXButton--default.TUXButton--medium.TUXButton--primary:has-text("Allow")').nth(0).is_visible():
435
+ page.locator('button.TUXButton.TUXButton--default.TUXButton--medium.TUXButton--primary:has-text("Allow")').nth(0).click()
436
+ time.sleep(0.2)
437
+ else:
438
+ if page.locator('div.TUXTextInputCore-trailingIconWrapper').nth(1).is_visible():
439
+ time.sleep(0.2)
484
440
  if day != None:
485
441
  page.locator('div.TUXTextInputCore-trailingIconWrapper').nth(1).click()
486
- time.sleep(0.5)
442
+ time.sleep(0.2)
487
443
  try:
488
444
  page.locator(f'span.day.valid:has-text("{day}")').click()
489
445
  except:
490
446
  sys.exit("SCHEDULE DAY ERROR: ERROR WITH SCHEDULED DAY, read documentation for more information on format of day")
491
447
  try:
448
+ time.sleep(1)
492
449
  page.locator('div.TUXTextInputCore-trailingIconWrapper').nth(0).click()
493
- time.sleep(0.5)
494
- page.locator(f'.tiktok-timepicker-option-text:has-text("{hour}")').nth(0).scroll_into_view_if_needed()
495
- page.locator(f'.tiktok-timepicker-option-text:has-text("{hour}")').nth(0).click()
496
- time.sleep(0.5)
497
- page.locator('div.TUXTextInputCore-trailingIconWrapper').nth(0).click()
498
- time.sleep(0.5)
450
+ time.sleep(0.2)
499
451
  page.locator(f'.tiktok-timepicker-option-text.tiktok-timepicker-right:has-text("{minute}")').nth(0).scroll_into_view_if_needed()
500
- time.sleep(0.5)
452
+ time.sleep(0.2)
501
453
  page.locator(f'.tiktok-timepicker-option-text.tiktok-timepicker-right:has-text("{minute}")').nth(0).click()
454
+ time.sleep(0.2)
455
+ page.locator(f'.tiktok-timepicker-option-text:has-text("{hour}")').nth(0).scroll_into_view_if_needed()
456
+ page.locator(f'.tiktok-timepicker-option-text:has-text("{hour}")').nth(0).click()
457
+ time.sleep(1)
502
458
 
503
459
  if suppressprint == False:
504
460
  print("Done scheduling video")
@@ -506,28 +462,29 @@ def upload_tiktok(video, description, hashtags=None, sound_name=None, sound_aud_
506
462
  except:
507
463
  sys.exit("SCHEDULING ERROR: VIDEO SAVED AS DRAFT")
508
464
 
465
+ if (schedule == None) and (day != None):
466
+ sys.exit("ERROR: CANT SCHEDULE FOR ANOTHER DAY USING 'day' WITHOUT ALSO INCLUDING TIME OF UPLOAD WITH 'schedule'; PLEASE ALSO INCLUDE TIME WITH 'schedule' PARAMETER")
509
467
 
510
- if copyrightcheck == True:
511
- page.locator(".TUXSwitch-input").nth(0).click()
512
- while copyrightcheck == True:
513
- time.sleep(0.5)
514
- if page.locator("span", has_text="No issues detected.").is_visible():
515
- if suppressprint == False:
516
- print("Copyright check complete")
517
- break
518
- if page.locator("span", has_text="Copyright issues detected.").is_visible():
519
- sys.exit("COPYRIGHT CHECK FAILED: VIDEO SAVED AS DRAFT, COPYRIGHT AUDIO DETECTED FROM TIKTOK")
520
-
521
468
 
522
- try:
469
+ if(sound_name == None):
470
+ if copyrightcheck == True:
471
+ page.locator(".TUXSwitch-input").nth(0).click()
472
+ while copyrightcheck == True:
473
+ time.sleep(0.2)
474
+ if page.locator("span", has_text="No issues detected.").is_visible():
475
+ if suppressprint == False:
476
+ print("Copyright check complete")
477
+ break
478
+ if page.locator("span", has_text="Copyright issues detected.").is_visible():
479
+ sys.exit("COPYRIGHT CHECK FAILED: COPYRIGHT AUDIO DETECTED FROM TIKTOK")
480
+
523
481
  if schedule == None:
524
482
  page.click('button.TUXButton.TUXButton--default.TUXButton--large.TUXButton--primary:has-text("Post")', timeout=10000)
525
483
  uploaded = False
526
484
  checks = 0
527
485
  while uploaded == False:
528
486
  if page.locator(':has-text("Leaving the page does not interrupt")').nth(0).is_visible():
529
- print("I see it")
530
- time.sleep(1)
487
+ time.sleep(0.2)
531
488
  break
532
489
  time.sleep(0.2)
533
490
  checks += 1
@@ -541,7 +498,7 @@ def upload_tiktok(video, description, hashtags=None, sound_name=None, sound_aud_
541
498
  checks = 0
542
499
  while uploaded == False:
543
500
  if page.locator(':has-text("Leaving the page does not interrupt")').nth(0).is_visible():
544
- time.sleep(1)
501
+ time.sleep(0.2)
545
502
  break
546
503
  time.sleep(0.2)
547
504
  checks += 1
@@ -551,9 +508,148 @@ def upload_tiktok(video, description, hashtags=None, sound_name=None, sound_aud_
551
508
  break
552
509
  if suppressprint == False:
553
510
  print("Done uploading video, NOTE: it may take a minute or two to show on TikTok")
554
- except:
555
- time.sleep(5)
556
- sys.exit("ERROR UPLOADING: VIDEO HAS SAVED AS DRAFT BUT CANT UPLOAD")
557
- time.sleep(1)
511
+
512
+ page.close()
513
+
514
+ else:
515
+ try:
516
+ page.click('button.TUXButton.TUXButton--default.TUXButton--large.TUXButton--secondary:has-text("Save draft")', timeout=10000)
517
+ except:
518
+ sys.exit("SAVE AS DRAFT BUTTON NOT FOUND; CANNOT ADD SOUND WITHOUT ABILITY TO SAVE DRAFTS")
519
+
520
+ time.sleep(0.5)
521
+ page.close()
522
+
523
+ browser = p.chromium.launch(headless=True)
524
+
525
+ context = browser.new_context()
526
+ context.add_cookies(cookies)
527
+ page = context.new_page()
528
+ url2 = 'https://www.tiktok.com/tiktokstudio/content?tab=draft'
529
+
530
+ while retries < 2:
531
+ try:
532
+ page.goto(url2, timeout=30000)
533
+ except:
534
+ retries +=1
535
+ time.sleep(5)
536
+ if retries == 2:
537
+ sys.exit("ERROR: TIK TOK PAGE FAILED TO LOAD, try again.")
538
+ else:
539
+ break
540
+
541
+ try:
542
+ page.wait_for_selector("path[d='M37.37 4.85a4.01 4.01 0 0 0-.99-.79 3 3 0 0 0-2.72 0c-.45.23-.81.6-1 .79a9 9 0 0 1-.04.05l-19.3 19.3c-1.64 1.63-2.53 2.52-3.35 3.47a36 36 0 0 0-4.32 6.16c-.6 1.1-1.14 2.24-2.11 4.33l-.3.6c-.4.75-.84 1.61-.8 2.43a2.5 2.5 0 0 0 2.37 2.36c.82.05 1.68-.4 2.44-.79l.59-.3c2.09-.97 3.23-1.5 4.33-2.11a36 36 0 0 0 6.16-4.32c.95-.82 1.84-1.71 3.47-3.34l19.3-19.3.05-.06a3 3 0 0 0 .78-3.71c-.22-.45-.6-.81-.78-1l-.02-.02-.03-.03-3.67-3.67a8.7 8.7 0 0 1-.06-.05ZM16.2 26.97 35.02 8.15l2.83 2.83L19.03 29.8c-1.7 1.7-2.5 2.5-3.33 3.21a32 32 0 0 1-7.65 4.93 32 32 0 0 1 4.93-7.65c.73-.82 1.51-1.61 3.22-3.32Z']")
543
+ page.click("path[d='M37.37 4.85a4.01 4.01 0 0 0-.99-.79 3 3 0 0 0-2.72 0c-.45.23-.81.6-1 .79a9 9 0 0 1-.04.05l-19.3 19.3c-1.64 1.63-2.53 2.52-3.35 3.47a36 36 0 0 0-4.32 6.16c-.6 1.1-1.14 2.24-2.11 4.33l-.3.6c-.4.75-.84 1.61-.8 2.43a2.5 2.5 0 0 0 2.37 2.36c.82.05 1.68-.4 2.44-.79l.59-.3c2.09-.97 3.23-1.5 4.33-2.11a36 36 0 0 0 6.16-4.32c.95-.82 1.84-1.71 3.47-3.34l19.3-19.3.05-.06a3 3 0 0 0 .78-3.71c-.22-.45-.6-.81-.78-1l-.02-.02-.03-.03-3.67-3.67a8.7 8.7 0 0 1-.06-.05ZM16.2 26.97 35.02 8.15l2.83 2.83L19.03 29.8c-1.7 1.7-2.5 2.5-3.33 3.21a32 32 0 0 1-7.65 4.93 32 32 0 0 1 4.93-7.65c.73-.82 1.51-1.61 3.22-3.32Z']")
544
+ page.wait_for_selector('div[data-contents="true"]')
545
+ page.wait_for_function("document.querySelector('.info-progress-num').textContent.trim() === '100%'", timeout=3000000)
546
+ time.sleep(0.2)
547
+ except:
548
+ sys.exit("ERROR ADDING SOUND: Video saved as draft")
549
+
550
+ if sound_name != None:
551
+ page.click("div.TUXButton-label:has-text('Edit video')")
552
+ page.wait_for_selector("input.search-bar-input")
553
+ page.fill(f"input.search-bar-input", f"{sound_name}")
554
+ time.sleep(0.2)
555
+ page.click("div.TUXButton-label:has-text('Search')")
556
+ try:
557
+ page.wait_for_selector('div.music-card-container')
558
+ page.click("div.music-card-container")
559
+ page.wait_for_selector("div.TUXButton-label:has-text('Use')")
560
+ page.click("div.TUXButton-label:has-text('Use')")
561
+ except:
562
+ sys.exit(f"ERROR: SOUND '{sound_name}' NOT FOUND")
563
+ try:
564
+ page.wait_for_selector('img[src="data:image/svg+xml;base64,PHN2ZyB3aWR0aD0iMjEiIGhlaWdodD0iMjAiIHZpZXdCb3g9IjAgMCAyMSAyMCIgZmlsbD0ibm9uZSIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj4KPHBhdGggZD0iTTAgNy41MDE2QzAgNi42NzMxNyAwLjY3MTU3MyA2LjAwMTYgMS41IDYuMDAxNkgzLjU3NzA5QzMuODY4MDUgNi4wMDE2IDQuMTQ0NTggNS44NzQ4OCA0LjMzNDU1IDUuNjU0NDlMOC43NDI1NSAwLjU0MDUyQzkuMzQ3OCAtMC4xNjE2NjggMTAuNSAwLjI2NjM3NCAxMC41IDEuMTkzNDFWMTguOTY3MkMxMC41IDE5Ljg3NDUgOS4zODg5NCAyMC4zMTI5IDguNzY5NDIgMTkuNjVMNC4zMzE3OSAxNC45MDIxQzQuMTQyNjkgMTQuNjk5OCAzLjg3ODE2IDE0LjU4NDkgMy42MDEyMiAxNC41ODQ5SDEuNUMwLjY3MTU3MyAxNC41ODQ5IDAgMTMuOTEzNCAwIDEzLjA4NDlWNy41MDE2Wk01Ljg0OTQ1IDYuOTYwMjdDNS4yNzk1NiA3LjYyMTQzIDQuNDQ5OTcgOC4wMDE2IDMuNTc3MDkgOC4wMDE2SDJWMTIuNTg0OUgzLjYwMTIyQzQuNDMyMDMgMTIuNTg0OSA1LjIyNTY0IDEyLjkyOTUgNS43OTI5NSAxMy41MzY0TDguNSAxNi40MzI4VjMuODg1MjJMNS44NDk0NSA2Ljk2MDI3WiIgZmlsbD0iIzE2MTgyMyIgZmlsbC1vcGFjaXR5PSIwLjYiLz4KPHBhdGggZD0iTTEzLjUxNSA3LjE5MTE5QzEzLjM0MjQgNi45NzU1OSAxMy4zMzk5IDYuNjYwNTYgMTMuNTM1MiA2LjQ2NTNMMTQuMjQyMyA1Ljc1ODE5QzE0LjQzNzYgNS41NjI5MyAxNC43NTU4IDUuNTYxNzUgMTQuOTM1NiA1Ljc3MTM2QzE2Ljk5NTkgOC4xNzM2MiAxNi45OTU5IDExLjgyOCAxNC45MzU2IDE0LjIzMDNDMTQuNzU1OCAxNC40Mzk5IDE0LjQzNzYgMTQuNDM4NyAxNC4yNDIzIDE0LjI0MzVMMTMuNTM1MiAxMy41MzY0QzEzLjMzOTkgMTMuMzQxMSAxMy4zNDI0IDEzLjAyNjEgMTMuNTE1IDEyLjgxMDVDMTQuODEzIDExLjE4ODUgMTQuODEzIDguODEzMTIgMTMuNTE1IDcuMTkxMTlaIiBmaWxsPSIjMTYxODIzIiBmaWxsLW9wYWNpdHk9IjAuNiIvPgo8cGF0aCBkPSJNMTYuNzE3MiAxNi43MTgzQzE2LjUyMTkgMTYuNTIzMSAxNi41MjMxIDE2LjIwNzQgMTYuNzA3MiAxNi4wMDE3QzE5LjcyNTcgMTIuNjMgMTkuNzI1NyA3LjM3MTY4IDE2LjcwNzIgNC4wMDAwMUMxNi41MjMxIDMuNzk0MjcgMTYuNTIxOSAzLjQ3ODU4IDE2LjcxNzIgMy4yODMzMkwxNy40MjQzIDIuNTc2MjFDMTcuNjE5NSAyLjM4MDk1IDE3LjkzNyAyLjM4MDIgMTguMTIzMyAyLjU4NDA4QzIxLjkwOTkgNi43MjkyNiAyMS45MDk5IDEzLjI3MjQgMTguMTIzMyAxNy40MTc2QzE3LjkzNyAxNy42MjE1IDE3LjYxOTUgMTcuNjIwNyAxNy40MjQzIDE3LjQyNTVMMTYuNzE3MiAxNi43MTgzWiIgZmlsbD0iIzE2MTgyMyIgZmlsbC1vcGFjaXR5PSIwLjYiLz4KPC9zdmc+Cg=="]')
565
+ page.click('img[src="data:image/svg+xml;base64,PHN2ZyB3aWR0aD0iMjEiIGhlaWdodD0iMjAiIHZpZXdCb3g9IjAgMCAyMSAyMCIgZmlsbD0ibm9uZSIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj4KPHBhdGggZD0iTTAgNy41MDE2QzAgNi42NzMxNyAwLjY3MTU3MyA2LjAwMTYgMS41IDYuMDAxNkgzLjU3NzA5QzMuODY4MDUgNi4wMDE2IDQuMTQ0NTggNS44NzQ4OCA0LjMzNDU1IDUuNjU0NDlMOC43NDI1NSAwLjU0MDUyQzkuMzQ3OCAtMC4xNjE2NjggMTAuNSAwLjI2NjM3NCAxMC41IDEuMTkzNDFWMTguOTY3MkMxMC41IDE5Ljg3NDUgOS4zODg5NCAyMC4zMTI5IDguNzY5NDIgMTkuNjVMNC4zMzE3OSAxNC45MDIxQzQuMTQyNjkgMTQuNjk5OCAzLjg3ODE2IDE0LjU4NDkgMy42MDEyMiAxNC41ODQ5SDEuNUMwLjY3MTU3MyAxNC41ODQ5IDAgMTMuOTEzNCAwIDEzLjA4NDlWNy41MDE2Wk01Ljg0OTQ1IDYuOTYwMjdDNS4yNzk1NiA3LjYyMTQzIDQuNDQ5OTcgOC4wMDE2IDMuNTc3MDkgOC4wMDE2SDJWMTIuNTg0OUgzLjYwMTIyQzQuNDMyMDMgMTIuNTg0OSA1LjIyNTY0IDEyLjkyOTUgNS43OTI5NSAxMy41MzY0TDguNSAxNi40MzI4VjMuODg1MjJMNS44NDk0NSA2Ljk2MDI3WiIgZmlsbD0iIzE2MTgyMyIgZmlsbC1vcGFjaXR5PSIwLjYiLz4KPHBhdGggZD0iTTEzLjUxNSA3LjE5MTE5QzEzLjM0MjQgNi45NzU1OSAxMy4zMzk5IDYuNjYwNTYgMTMuNTM1MiA2LjQ2NTNMMTQuMjQyMyA1Ljc1ODE5QzE0LjQzNzYgNS41NjI5MyAxNC43NTU4IDUuNTYxNzUgMTQuOTM1NiA1Ljc3MTM2QzE2Ljk5NTkgOC4xNzM2MiAxNi45OTU5IDExLjgyOCAxNC45MzU2IDE0LjIzMDNDMTQuNzU1OCAxNC40Mzk5IDE0LjQzNzYgMTQuNDM4NyAxNC4yNDIzIDE0LjI0MzVMMTMuNTM1MiAxMy41MzY0QzEzLjMzOTkgMTMuMzQxMSAxMy4zNDI0IDEzLjAyNjEgMTMuNTE1IDEyLjgxMDVDMTQuODEzIDExLjE4ODUgMTQuODEzIDguODEzMTIgMTMuNTE1IDcuMTkxMTlaIiBmaWxsPSIjMTYxODIzIiBmaWxsLW9wYWNpdHk9IjAuNiIvPgo8cGF0aCBkPSJNMTYuNzE3MiAxNi43MTgzQzE2LjUyMTkgMTYuNTIzMSAxNi41MjMxIDE2LjIwNzQgMTYuNzA3MiAxNi4wMDE3QzE5LjcyNTcgMTIuNjMgMTkuNzI1NyA3LjM3MTY4IDE2LjcwNzIgNC4wMDAwMUMxNi41MjMxIDMuNzk0MjcgMTYuNTIxOSAzLjQ3ODU4IDE2LjcxNzIgMy4yODMzMkwxNy40MjQzIDIuNTc2MjFDMTcuNjE5NSAyLjM4MDk1IDE3LjkzNyAyLjM4MDIgMTguMTIzMyAyLjU4NDA4QzIxLjkwOTkgNi43MjkyNiAyMS45MDk5IDEzLjI3MjQgMTguMTIzMyAxNy40MTc2QzE3LjkzNyAxNy42MjE1IDE3LjYxOTUgMTcuNjIwNyAxNy40MjQzIDE3LjQyNTVMMTYuNzE3MiAxNi43MTgzWiIgZmlsbD0iIzE2MTgyMyIgZmlsbC1vcGFjaXR5PSIwLjYiLz4KPC9zdmc+Cg=="]')
566
+ time.sleep(0.5)
567
+ sliders = page.locator("input.scaleInput")
568
+
569
+ if sound_aud_vol == 'background':
570
+ slider1 = sliders.nth(0)
571
+ bounding_box1 = slider1.bounding_box()
572
+ if bounding_box1:
573
+ x1 = bounding_box1["x"] + (bounding_box1["width"] * 0.92)
574
+ y1 = bounding_box1["y"] + bounding_box1["height"] / 2
575
+ page.mouse.click(x1, y1)
576
+
577
+ slider2 = sliders.nth(1)
578
+ bounding_box2 = slider2.bounding_box()
579
+ if bounding_box2:
580
+ x2 = bounding_box2["x"] + (bounding_box2["width"] * 0.097)
581
+ y2 = bounding_box2["y"] + bounding_box2["height"] / 2
582
+ page.mouse.click(x2, y2)
583
+
584
+ if sound_aud_vol == 'main':
585
+ slider1 = sliders.nth(0)
586
+ bounding_box1 = slider1.bounding_box()
587
+ if bounding_box1:
588
+ x1 = bounding_box1["x"] + (bounding_box1["width"] * 0.092)
589
+ y1 = bounding_box1["y"] + bounding_box1["height"] / 2
590
+ page.mouse.click(x1, y1)
591
+ slider2 = sliders.nth(1)
592
+ bounding_box2 = slider2.bounding_box()
593
+ if bounding_box2:
594
+ x2 = bounding_box2["x"] + (bounding_box2["width"] * 0.92)
595
+ y2 = bounding_box2["y"] + bounding_box2["height"] / 2
596
+ page.mouse.click(x2, y2)
597
+ except:
598
+ sys.exit("ERROR ADJUSTING SOUND VOLUME: please try again.")
599
+
600
+ page.wait_for_selector("div.TUXButton-label:has-text('Save edit')")
601
+ page.click("div.TUXButton-label:has-text('Save edit')")
602
+ if suppressprint == False:
603
+ print("Added sound")
604
+
605
+ page.wait_for_selector('div[data-contents="true"]')
606
+
607
+ if copyrightcheck == True:
608
+ page.locator(".TUXSwitch-input").nth(0).click()
609
+ while copyrightcheck == True:
610
+ time.sleep(0.2)
611
+ if page.locator("span", has_text="No issues detected.").is_visible():
612
+ if suppressprint == False:
613
+ print("Copyright check complete")
614
+ break
615
+ if page.locator("span", has_text="Copyright issues detected.").is_visible():
616
+ sys.exit("COPYRIGHT CHECK FAILED: VIDEO SAVED AS DRAFT, COPYRIGHT AUDIO DETECTED FROM TIKTOK")
617
+
618
+
619
+ try:
620
+ if schedule == None:
621
+ page.click('button.TUXButton.TUXButton--default.TUXButton--large.TUXButton--primary:has-text("Post")', timeout=10000)
622
+ uploaded = False
623
+ checks = 0
624
+ while uploaded == False:
625
+ if page.locator(':has-text("Leaving the page does not interrupt")').nth(0).is_visible():
626
+ time.sleep(0.2)
627
+ break
628
+ time.sleep(0.2)
629
+ checks += 1
630
+ if checks > 100:
631
+ time.sleep(10)
632
+ if checks == 150:
633
+ break
634
+ else:
635
+ page.click('button.TUXButton.TUXButton--default.TUXButton--large.TUXButton--primary:has-text("Schedule")', timeout=10000)
636
+ uploaded = False
637
+ checks = 0
638
+ while uploaded == False:
639
+ if page.locator(':has-text("Leaving the page does not interrupt")').nth(0).is_visible():
640
+ time.sleep(0.2)
641
+ break
642
+ time.sleep(0.2)
643
+ checks += 1
644
+ if checks > 100:
645
+ time.sleep(10)
646
+ if checks == 150:
647
+ break
648
+ if suppressprint == False:
649
+ print("Done uploading video, NOTE: it may take a minute or two to show on TikTok")
650
+ except:
651
+ time.sleep(5)
652
+ sys.exit("ERROR UPLOADING: VIDEO HAS SAVED AS DRAFT BUT CANT UPLOAD")
653
+ time.sleep(1)
558
654
 
559
- page.close()
655
+ page.close()
@@ -0,0 +1,138 @@
1
+ Metadata-Version: 2.3
2
+ Name: tiktokautouploader
3
+ Version: 2.9
4
+ Summary: Upload or schedule videos to TikTok with viral TikTok sounds and hashtags.
5
+ Project-URL: Homepage, https://github.com/haziq-exe/TikTokAutoUploader
6
+ Author-email: HAZIQ <haziqmk123@gmail.com>
7
+ License-File: LICENSE.md
8
+ Keywords: autoupload,tiktok,tiktokautoupload
9
+ Classifier: License :: OSI Approved :: MIT License
10
+ Classifier: Operating System :: OS Independent
11
+ Classifier: Programming Language :: Python :: 3
12
+ Classifier: Programming Language :: Python :: 3.8
13
+ Classifier: Programming Language :: Python :: 3.9
14
+ Classifier: Programming Language :: Python :: 3.10
15
+ Classifier: Programming Language :: Python :: 3.11
16
+ Requires-Dist: pillow>=8.0.0
17
+ Requires-Dist: playwright>=1.0.0
18
+ Requires-Dist: requests>=2.0.0
19
+ Requires-Dist: scikit-learn>=0.24.0
20
+ Description-Content-Type: text/markdown
21
+
22
+ <div align="center">
23
+ <h1>tiktokautouploader</h1>
24
+ </div>
25
+
26
+
27
+ ### AUTOMATE TIKTOK UPLOADS 🤖. USE TRENDING SOUNDS 🔊, ADD WORKING HASHTAGS 💯, SCHEDULE UPLOADS 🗓️, AUTOSOLVES CAPTCHAS 🧠, AND MORE 🎁
28
+
29
+ [![PyPI version](https://img.shields.io/pypi/v/tiktokautouploader.svg)](https://pypi.org/project/tiktokautouploader/) [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](https://opensource.org/licenses/MIT)
30
+
31
+
32
+ <p align="center">
33
+ <img src="READMEimage/Image.png" alt="" width="400"/>
34
+ </p>
35
+
36
+ ## 🚀 Features
37
+
38
+ - **🔐 Bypass/Auto Solve Captchas:** No more manual captcha solving; fully automated process!
39
+ - **🎵 Use TikTok Sounds:** Seamlessly add popular TikTok sounds to your videos.
40
+ - **🗓 Schedule Uploads:** Upload videos at specific times or upto 10 days in advance with our scheduling feature.
41
+ - **🔍 Copyright Check:** Ensure your video is safe from copyright claims before uploading.
42
+ - **🏷 Add Working Hashtags:** Increase your reach by adding effective hashtags that actually work.
43
+
44
+
45
+ ## 📦 Installation
46
+
47
+ 1. **Python Installation:** Install the package using `pip`:
48
+
49
+ ```bash
50
+ pip install tiktokautouploader
51
+ ```
52
+
53
+ ---
54
+
55
+ ## ⚙️ Pre-requisites
56
+
57
+ 1. **Node.js:** You must have Node.js installed on your system, as some parts of this package rely on JavaScript code. If you don't have Node.js installed, you can download it from [nodejs.org](https://nodejs.org/).
58
+
59
+ - **Note:** The necessary JavaScript dependencies (`playwright`,`playwright-extra`, `puppeteer-extra-plugin-stealth`) will be AUTOMATICALLY installed the first time you run the function, so you don't need to install them manually. Make sure that `npm` (Node.js package manager) is available in your system's PATH.
60
+
61
+
62
+ 2. **Browser Binaries:** If you don't have them already, you'll need to install the chromium browser binary for `playwright`.
63
+
64
+ To do so, just run the following command AFTER installing the package:
65
+
66
+ ```bash
67
+ python -m playwright install chromium
68
+ ```
69
+
70
+
71
+ ## 📝 Quick-Start
72
+
73
+ Here's how to upload a video to TikTok with hashtags using `tiktokautouploader`:
74
+
75
+ NOTE: It is highly recommended you read DOCUMENTATION.md before using the library.
76
+
77
+ The first time you run the code, you will be prompted to log-in, this will only occur the first time the function is used. Check documentation for more info.
78
+
79
+ ```python
80
+ from tiktokautouploader import upload_tiktok
81
+
82
+ video_path = 'path/to/your/video.mp4'
83
+ description = 'Check out my latest TikTok video!'
84
+ hashtags = ['#fun', '#viral']
85
+
86
+ upload_tiktok(video=video_path, description=description, hashtags=hashtags)
87
+
88
+ ```
89
+
90
+ ### Upload with TikTok Sound
91
+
92
+ ```python
93
+ upload_tiktok(video=video_path, description=description, sound_name='trending_sound', sound_aud_vol='main')
94
+ ```
95
+
96
+ PLEASE READ DOCUMENTATION FOR MORE INFO.
97
+
98
+ ### Schedule an Upload
99
+
100
+ ```python
101
+ upload_tiktok(video=video_path, description=description, schedule='03:10', day=11)
102
+ ```
103
+
104
+ PLEASE READ DOCUMENTATION FOR MORE INFO
105
+
106
+ ### Perform Copyright Check Before Uploading
107
+
108
+ ```python
109
+ upload_tiktok(video=video_path, description=description, hashtags=hashtags, copyrightcheck=True)
110
+ ```
111
+
112
+ ## 🎯 Why Choose `autotiktokuploader`?
113
+
114
+ - **No more captchas:** Fully automated uploads without interruptions, If captchas do show up, no worries, they will be solved. (read documentation for more info)
115
+ - **Maximize your reach:** Add popular sounds and effective hashtags that work to boost visibility.
116
+ - **Stay compliant:** Built-in copyright checks to avoid unforeseen takedowns.
117
+ - **Convenient scheduling:** Post at the right time, even when you're away.
118
+
119
+ ## 🛠 Dependencies
120
+
121
+ This library requires the following dependencies:
122
+
123
+ - `playwright`
124
+ - `requests`
125
+ - `Pillow`
126
+ - `scikit-learn`
127
+ - `inference`
128
+
129
+ These will be automatically installed when you install the package.
130
+
131
+ ## 👤 Author
132
+
133
+ Created by **Haziq Khalid**. Feel free to reach out at [haziqmk123@gmail.com](mailto:haziqmk123@gmail.com) or my LinkedIn.
134
+
135
+ ## 📄 License
136
+
137
+ This project is licensed under the MIT License. See the [LICENSE](LICENSE.md) file for details.
138
+ ```
@@ -0,0 +1,7 @@
1
+ tiktokautouploader/__init__.py,sha256=u7OWCK_u68ST8dfrkSF4Yw44CJOzV9NXI6ASRuoDfmE,64
2
+ tiktokautouploader/function.py,sha256=xH9h_yIxwuUo-CfvR1NpHDyGBhrS-6n-enNMx1l2Dqw,32635
3
+ tiktokautouploader/Js_assets/login.js,sha256=SLhtPYo8ZfTRUnbR7Xqp084lSuAOqIWUxi75FlFH3vs,966
4
+ tiktokautouploader-2.9.dist-info/METADATA,sha256=nIX_7UaWoh3EGi-RqElLzdZpT026RxvO0pABzqm7LZo,4878
5
+ tiktokautouploader-2.9.dist-info/WHEEL,sha256=fl6v0VwpzfGBVsGtkAkhILUlJxROXbA3HvRL6Fe3140,105
6
+ tiktokautouploader-2.9.dist-info/licenses/LICENSE.md,sha256=hYds_VJIpnS5gC73WhuWk2IY_e9BWjuEJthQCb9ThyU,1073
7
+ tiktokautouploader-2.9.dist-info/RECORD,,
@@ -1,19 +0,0 @@
1
- Metadata-Version: 2.3
2
- Name: tiktokautouploader
3
- Version: 2.7
4
- Summary: Upload or schedule videos to TikTok with TikTok sounds and hashtags that work.
5
- Project-URL: Homepage, https://github.com/haziq-exe/TikTokAutoUploader
6
- Author-email: HAZIQ KHALID <haziqmk123@gmail.com>
7
- License-File: LICENSE.md
8
- Keywords: autoupload,tiktok,tiktokautoupload
9
- Classifier: License :: OSI Approved :: MIT License
10
- Classifier: Operating System :: OS Independent
11
- Classifier: Programming Language :: Python :: 3
12
- Classifier: Programming Language :: Python :: 3.8
13
- Classifier: Programming Language :: Python :: 3.9
14
- Classifier: Programming Language :: Python :: 3.10
15
- Classifier: Programming Language :: Python :: 3.11
16
- Requires-Dist: pillow>=8.0.0
17
- Requires-Dist: playwright>=1.0.0
18
- Requires-Dist: requests>=2.0.0
19
- Requires-Dist: scikit-learn>=0.24.0
@@ -1,7 +0,0 @@
1
- tiktokautouploader/__init__.py,sha256=u7OWCK_u68ST8dfrkSF4Yw44CJOzV9NXI6ASRuoDfmE,64
2
- tiktokautouploader/function.py,sha256=3S18jcePZCEDSQ2RQNs27Z3Xbp3QW9vyu1aNtbSAHsE,28340
3
- tiktokautouploader/Js_assets/login.js,sha256=Qk_zUzRPeIN0ZnQVDtzahDNqIUJbIBbKoKw8GWW6et4,1318
4
- tiktokautouploader-2.7.dist-info/METADATA,sha256=dQtuZ0yRpDNo1X_X6tjm2iNyCPmF7pRNQXZH1YgS1gs,816
5
- tiktokautouploader-2.7.dist-info/WHEEL,sha256=fl6v0VwpzfGBVsGtkAkhILUlJxROXbA3HvRL6Fe3140,105
6
- tiktokautouploader-2.7.dist-info/licenses/LICENSE.md,sha256=hYds_VJIpnS5gC73WhuWk2IY_e9BWjuEJthQCb9ThyU,1073
7
- tiktokautouploader-2.7.dist-info/RECORD,,