Scripting way to upload videos to peertube and youtube
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

240 lines
7.4 KiB

  1. #!/usr/bin/python
  2. # coding: utf-8
  3. from configparser import RawConfigParser, NoOptionError, NoSectionError
  4. from os.path import dirname, splitext, basename, isfile, getmtime
  5. import re
  6. import unidecode
  7. import logging
  8. import datetime
  9. logger = logging.getLogger('Prismedia')
  10. ### CATEGORIES ###
  11. YOUTUBE_CATEGORY = {
  12. "music": 10,
  13. "films": 1,
  14. "vehicles": 2,
  15. "sport": 17,
  16. "travels": 19,
  17. "gaming": 20,
  18. "people": 22,
  19. "comedy": 23,
  20. "entertainment": 24,
  21. "news": 25,
  22. "how to": 26,
  23. "education": 27,
  24. "activism": 29,
  25. "science & technology": 28,
  26. "science": 28,
  27. "technology": 28,
  28. "animals": 15
  29. }
  30. PEERTUBE_CATEGORY = {
  31. "music": 1,
  32. "films": 2,
  33. "vehicles": 3,
  34. "sport": 5,
  35. "travels": 6,
  36. "gaming": 7,
  37. "people": 8,
  38. "comedy": 9,
  39. "entertainment": 10,
  40. "news": 11,
  41. "how to": 12,
  42. "education": 13,
  43. "activism": 14,
  44. "science & technology": 15,
  45. "science": 15,
  46. "technology": 15,
  47. "animals": 16
  48. }
  49. ### LANGUAGES ###
  50. YOUTUBE_LANGUAGE = {
  51. "arabic": 'ar',
  52. "english": 'en',
  53. "french": 'fr',
  54. "german": 'de',
  55. "hindi": 'hi',
  56. "italian": 'it',
  57. "japanese": 'ja',
  58. "korean": 'ko',
  59. "mandarin": 'zh-CN',
  60. "portuguese": 'pt-PT',
  61. "punjabi": 'pa',
  62. "russian": 'ru',
  63. "spanish": 'es'
  64. }
  65. PEERTUBE_LANGUAGE = {
  66. "arabic": "ar",
  67. "english": "en",
  68. "french": "fr",
  69. "german": "de",
  70. "hindi": "hi",
  71. "italian": "it",
  72. "japanese": "ja",
  73. "korean": "ko",
  74. "mandarin": "zh",
  75. "portuguese": "pt",
  76. "punjabi": "pa",
  77. "russian": "ru",
  78. "spanish": "es"
  79. }
  80. ######################
  81. def getCategory(category, platform):
  82. if platform == "youtube":
  83. return YOUTUBE_CATEGORY[category.lower()]
  84. else:
  85. return PEERTUBE_CATEGORY[category.lower()]
  86. def getLanguage(language, platform):
  87. if platform == "youtube":
  88. return YOUTUBE_LANGUAGE[language.lower()]
  89. else:
  90. return PEERTUBE_LANGUAGE[language.lower()]
  91. def ask_overwrite(question):
  92. while True:
  93. reply = str(input(question + ' (Yes/[No]): ') or "No").lower().strip()
  94. if reply[:1] == 'y':
  95. return True
  96. if reply[:1] == 'n':
  97. return False
  98. def remove_empty_kwargs(**kwargs):
  99. good_kwargs = {}
  100. if kwargs is not None:
  101. for key, value in kwargs.items():
  102. if value:
  103. good_kwargs[key] = value
  104. return good_kwargs
  105. def searchThumbnail(options):
  106. video_directory = dirname(options.get('--file')) + "/"
  107. # First, check for thumbnail based on videoname
  108. if options.get('--name'):
  109. if isfile(video_directory + options.get('--name') + ".jpg"):
  110. options['--thumbnail'] = video_directory + options.get('--name') + ".jpg"
  111. elif isfile(video_directory + options.get('--name') + ".jpeg"):
  112. options['--thumbnail'] = video_directory + options.get('--name') + ".jpeg"
  113. elif isfile(video_directory + options.get('--name') + ".png"):
  114. options['--thumbnail'] = video_directory + options.get('--name') + ".png"
  115. # Then, if we still not have thumbnail, check for thumbnail based on videofile name
  116. if not options.get('--thumbnail'):
  117. video_file = splitext(basename(options.get('--file')))[0]
  118. if isfile(video_directory + video_file + ".jpg"):
  119. options['--thumbnail'] = video_directory + video_file + ".jpg"
  120. elif isfile(video_directory + video_file + ".jpeg"):
  121. options['--thumbnail'] = video_directory + video_file + ".jpeg"
  122. elif isfile(video_directory + video_file + ".png"):
  123. options['--thumbnail'] = video_directory + video_file + ".png"
  124. # Display some info after research
  125. if not options.get('--thumbnail'):
  126. logger.debug("No thumbnail has been found, continuing")
  127. else:
  128. logger.info("Using " + options.get('--thumbnail') + " as thumbnail")
  129. return options
  130. def searchOriginalDate(options):
  131. fileModificationDate = str(getmtime(options.get('--file'))).split('.')
  132. return datetime.datetime.fromtimestamp(int(fileModificationDate[0])).isoformat()
  133. # return the nfo as a RawConfigParser object
  134. def loadNFO(filename):
  135. try:
  136. logger.info("Loading " + filename + " as NFO")
  137. nfo = RawConfigParser()
  138. nfo.read(filename, encoding='utf-8')
  139. return nfo
  140. except Exception as e:
  141. logger.critical("Problem loading NFO file " + filename + ": " + str(e))
  142. exit(1)
  143. return False
  144. def parseNFO(options):
  145. video_directory = dirname(options.get('--file'))
  146. directory_name = basename(video_directory)
  147. nfo_txt = False
  148. nfo_directory = False
  149. nfo_videoname = False
  150. nfo_file = False
  151. nfo_cli = False
  152. if isfile(video_directory + "/" + "nfo.txt"):
  153. nfo_txt = loadNFO(video_directory + "/" + "nfo.txt")
  154. elif isfile(video_directory + "/" + "NFO.txt"):
  155. nfo_txt = loadNFO(video_directory + "/" + "NFO.txt")
  156. if isfile(video_directory + "/" + directory_name + ".txt"):
  157. nfo_directory = loadNFO(video_directory + "/" + directory_name + ".txt")
  158. if options.get('--name'):
  159. if isfile(video_directory + "/" + options.get('--name')):
  160. nfo_videoname = loadNFO(video_directory + "/" + options.get('--name') + ".txt")
  161. video_file = splitext(basename(options.get('--file')))[0]
  162. if isfile(video_directory + "/" + video_file + ".txt"):
  163. nfo_file = loadNFO(video_directory + "/" + video_file + ".txt")
  164. if options.get('--nfo'):
  165. if isfile(options.get('--nfo')):
  166. nfo_cli = loadNFO(options.get('--nfo'))
  167. else:
  168. logger.critical("Given NFO file does not exist, please check your path.")
  169. exit(1)
  170. # If there is no NFO and strict option is enabled, then stop there
  171. if options.get('--withNFO'):
  172. if not isinstance(nfo_cli, RawConfigParser) and \
  173. not isinstance(nfo_file, RawConfigParser) and \
  174. not isinstance(nfo_videoname, RawConfigParser) and \
  175. not isinstance(nfo_directory, RawConfigParser) and \
  176. not isinstance(nfo_txt, RawConfigParser):
  177. logger.critical("You have required the strict presence of NFO but none is found, please use a NFO.")
  178. exit(1)
  179. # We need to load NFO in this exact order to keep the priorities
  180. # options in cli > nfo_cli > nfo_file > nfo_videoname > nfo_directory > nfo_txt
  181. for nfo in [nfo_cli, nfo_file, nfo_videoname, nfo_directory, nfo_txt]:
  182. if nfo:
  183. # We need to check all options and replace it with the nfo value if not defined (None or False)
  184. for key, value in options.items():
  185. key = key.replace("--", "")
  186. try:
  187. # get string options
  188. if value is None and nfo.get('video', key):
  189. options['--' + key] = nfo.get('video', key)
  190. # get boolean options
  191. elif value is False and nfo.getboolean('video', key):
  192. options['--' + key] = nfo.getboolean('video', key)
  193. except NoOptionError:
  194. continue
  195. except NoSectionError:
  196. logger.critical(nfo + " misses section [video], please check syntax of your NFO.")
  197. exit(1)
  198. return options
  199. def upcaseFirstLetter(s):
  200. return s[0].upper() + s[1:]
  201. def cleanString(toclean):
  202. toclean = unidecode.unidecode(toclean)
  203. cleaned = re.sub('[^A-Za-z0-9]+', '', toclean)
  204. return cleaned