KekikStream 0.2.6__py3-none-any.whl → 0.2.8__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.
- KekikStream/Core/ExtractorLoader.py +30 -8
- KekikStream/Core/MediaHandler.py +15 -6
- KekikStream/Core/PluginBase.py +4 -0
- KekikStream/Extractors/Odnoklassniki.py +27 -12
- KekikStream/Managers/UIManager.py +1 -0
- KekikStream/Plugins/DiziBox.py +115 -0
- KekikStream/__init__.py +8 -1
- KekikStream/requirements.txt +1 -0
- {KekikStream-0.2.6.dist-info → KekikStream-0.2.8.dist-info}/METADATA +2 -1
- {KekikStream-0.2.6.dist-info → KekikStream-0.2.8.dist-info}/RECORD +14 -13
- {KekikStream-0.2.6.dist-info → KekikStream-0.2.8.dist-info}/LICENSE +0 -0
- {KekikStream-0.2.6.dist-info → KekikStream-0.2.8.dist-info}/WHEEL +0 -0
- {KekikStream-0.2.6.dist-info → KekikStream-0.2.8.dist-info}/entry_points.txt +0 -0
- {KekikStream-0.2.6.dist-info → KekikStream-0.2.8.dist-info}/top_level.txt +0 -0
@@ -11,33 +11,53 @@ class ExtractorLoader:
|
|
11
11
|
self.local_extractors_dir = Path(extractors_dir)
|
12
12
|
self.global_extractors_dir = Path(__file__).parent.parent / extractors_dir
|
13
13
|
if not self.local_extractors_dir.exists() and not self.global_extractors_dir.exists():
|
14
|
-
konsol.log(f"[red][!] Extractor dizini bulunamadı: {self.
|
14
|
+
konsol.log(f"[red][!] Extractor dizini bulunamadı: {self.global_extractors_dir}[/red]")
|
15
15
|
cikis_yap(False)
|
16
16
|
|
17
17
|
def load_all(self) -> list[ExtractorBase]:
|
18
18
|
extractors = []
|
19
19
|
|
20
|
+
# Global Extractor'ları yükle
|
20
21
|
if self.global_extractors_dir.exists():
|
21
22
|
konsol.log(f"[green][*] Global Extractor dizininden yükleniyor: {self.global_extractors_dir}[/green]")
|
22
|
-
|
23
|
+
global_extractors = self._load_from_directory(self.global_extractors_dir)
|
24
|
+
konsol.log(f"[green]Global Extractor'lar: {[e.__name__ for e in global_extractors]}[/green]")
|
25
|
+
extractors.extend(global_extractors)
|
23
26
|
|
27
|
+
# Yerel Extractor'ları yükle
|
24
28
|
if self.local_extractors_dir.exists():
|
25
29
|
konsol.log(f"[green][*] Yerel Extractor dizininden yükleniyor: {self.local_extractors_dir}[/green]")
|
26
|
-
|
30
|
+
local_extractors = self._load_from_directory(self.local_extractors_dir)
|
31
|
+
konsol.log(f"[green]Yerel Extractor'lar: {[e.__name__ for e in local_extractors]}[/green]")
|
32
|
+
extractors.extend(local_extractors)
|
27
33
|
|
28
|
-
|
29
|
-
|
34
|
+
# Benzersizliği sağlama (modül adı + sınıf adı bazında)
|
35
|
+
unique_extractors = []
|
36
|
+
seen = set()
|
37
|
+
for ext in extractors:
|
38
|
+
identifier = f"{ext.__module__}.{ext.__name__}"
|
39
|
+
if identifier not in seen:
|
40
|
+
unique_extractors.append(ext)
|
41
|
+
seen.add(identifier)
|
30
42
|
|
31
|
-
|
43
|
+
konsol.log(f"[blue]Sonuç Extractor'lar: {[e.__name__ for e in unique_extractors]}[/blue]")
|
44
|
+
|
45
|
+
if not unique_extractors:
|
46
|
+
konsol.log("[yellow][!] Yüklenecek bir Extractor bulunamadı![/yellow]")
|
47
|
+
|
48
|
+
return unique_extractors
|
32
49
|
|
33
50
|
def _load_from_directory(self, directory: Path) -> list[ExtractorBase]:
|
34
51
|
extractors = []
|
35
52
|
for file in os.listdir(directory):
|
36
53
|
if file.endswith(".py") and not file.startswith("__"):
|
37
54
|
module_name = file[:-3]
|
55
|
+
konsol.log(f"[cyan]Modül yükleniyor: {module_name}[/cyan]")
|
38
56
|
if extractor := self._load_extractor(directory, module_name):
|
57
|
+
konsol.log(f"[magenta]Extractor bulundu: {extractor.__name__}[/magenta]")
|
39
58
|
extractors.append(extractor)
|
40
59
|
|
60
|
+
konsol.log(f"[yellow]{directory} dizininden yüklenen Extractor'lar: {[e.__name__ for e in extractors]}[/yellow]")
|
41
61
|
return extractors
|
42
62
|
|
43
63
|
def _load_extractor(self, directory: Path, module_name: str):
|
@@ -50,12 +70,14 @@ class ExtractorLoader:
|
|
50
70
|
module = importlib.util.module_from_spec(spec)
|
51
71
|
spec.loader.exec_module(module)
|
52
72
|
|
73
|
+
# Yalnızca doğru modülden gelen ExtractorBase sınıflarını yükle
|
53
74
|
for attr in dir(module):
|
54
75
|
obj = getattr(module, attr)
|
55
|
-
if isinstance(obj, type) and issubclass(obj, ExtractorBase) and obj is not ExtractorBase:
|
76
|
+
if obj.__module__ == module_name and isinstance(obj, type) and issubclass(obj, ExtractorBase) and obj is not ExtractorBase:
|
77
|
+
konsol.log(f"[green]Yüklenen sınıf: {module_name}.{obj.__name__} ({obj.__module__}.{obj.__name__})[/green]")
|
56
78
|
return obj
|
57
79
|
|
58
80
|
except Exception as hata:
|
59
|
-
konsol.
|
81
|
+
konsol.log(f"[red][!] Extractor yüklenirken hata oluştu: {module_name}\nHata: {hata}")
|
60
82
|
|
61
83
|
return None
|
KekikStream/Core/MediaHandler.py
CHANGED
@@ -3,6 +3,7 @@
|
|
3
3
|
from ..CLI import konsol
|
4
4
|
from .ExtractorModels import ExtractResult
|
5
5
|
import subprocess
|
6
|
+
import os
|
6
7
|
|
7
8
|
class MediaHandler:
|
8
9
|
def __init__(self, title: str = "KekikStream", headers: dict = {"User-Agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_14_5)"}):
|
@@ -15,11 +16,13 @@ class MediaHandler:
|
|
15
16
|
self.play_with_mpv(extract_data)
|
16
17
|
return
|
17
18
|
|
18
|
-
vlc_command = ["vlc"]
|
19
|
+
vlc_command = ["vlc", "--quiet"]
|
19
20
|
|
20
21
|
if self.title:
|
21
|
-
vlc_command.
|
22
|
-
|
22
|
+
vlc_command.extend([
|
23
|
+
f"--meta-title={self.title}",
|
24
|
+
f"--input-title-format={self.title}"
|
25
|
+
])
|
23
26
|
|
24
27
|
if "User-Agent" in self.headers:
|
25
28
|
vlc_command.append(f"--http-user-agent={self.headers.get('User-Agent')}")
|
@@ -31,7 +34,10 @@ class MediaHandler:
|
|
31
34
|
vlc_command.append(f"--sub-file={subtitle.url}")
|
32
35
|
|
33
36
|
vlc_command.append(extract_data.url)
|
34
|
-
|
37
|
+
|
38
|
+
with open(os.devnull, "w") as devnull:
|
39
|
+
subprocess.run(vlc_command, stdout=devnull, stderr=devnull, check=True)
|
40
|
+
|
35
41
|
except subprocess.CalledProcessError as e:
|
36
42
|
konsol.print(f"[red]VLC oynatma hatası: {e}[/red]")
|
37
43
|
konsol.print({"title": self.title, "url": extract_data.url, "headers": self.headers})
|
@@ -41,7 +47,7 @@ class MediaHandler:
|
|
41
47
|
|
42
48
|
def play_with_mpv(self, extract_data: ExtractResult):
|
43
49
|
try:
|
44
|
-
mpv_command = ["mpv"]
|
50
|
+
mpv_command = ["mpv", "--really-quiet"]
|
45
51
|
|
46
52
|
if self.title:
|
47
53
|
mpv_command.append(f"--title={self.title}")
|
@@ -59,7 +65,10 @@ class MediaHandler:
|
|
59
65
|
mpv_command.append(f"--sub-file={subtitle.url}")
|
60
66
|
|
61
67
|
mpv_command.append(extract_data.url)
|
62
|
-
|
68
|
+
|
69
|
+
with open(os.devnull, "w") as devnull:
|
70
|
+
subprocess.run(mpv_command, stdout=devnull, stderr=devnull, check=True)
|
71
|
+
|
63
72
|
except subprocess.CalledProcessError as e:
|
64
73
|
konsol.print(f"[red]mpv oynatma hatası: {e}[/red]")
|
65
74
|
konsol.print({"title": self.title, "url": extract_data.url, "headers": self.headers})
|
KekikStream/Core/PluginBase.py
CHANGED
@@ -2,6 +2,7 @@
|
|
2
2
|
|
3
3
|
from abc import ABC, abstractmethod
|
4
4
|
from httpx import AsyncClient, Timeout
|
5
|
+
from cloudscraper import CloudScraper
|
5
6
|
from .PluginModels import SearchResult, MovieInfo
|
6
7
|
from .MediaHandler import MediaHandler
|
7
8
|
from urllib.parse import urljoin
|
@@ -21,6 +22,9 @@ class PluginBase(ABC):
|
|
21
22
|
timeout = Timeout(10.0),
|
22
23
|
)
|
23
24
|
self.media_handler = MediaHandler()
|
25
|
+
self.cloudscraper = CloudScraper()
|
26
|
+
self.oturum.headers.update(self.cloudscraper.headers)
|
27
|
+
self.oturum.cookies.update(self.cloudscraper.cookies)
|
24
28
|
|
25
29
|
@abstractmethod
|
26
30
|
async def search(self, query: str) -> list[SearchResult]:
|
@@ -1,5 +1,6 @@
|
|
1
1
|
# Bu araç @keyiflerolsun tarafından | @KekikAkademi için yazılmıştır.
|
2
2
|
|
3
|
+
from KekikStream.CLI import konsol
|
3
4
|
from KekikStream.Core import ExtractorBase, ExtractResult
|
4
5
|
import re
|
5
6
|
import json
|
@@ -16,18 +17,11 @@ class Odnoklassniki(ExtractorBase):
|
|
16
17
|
"User-Agent": "Mozilla/5.0 (Linux; Android 10; K) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/114.0.0.0 Mobile Safari/537.36"
|
17
18
|
})
|
18
19
|
|
19
|
-
|
20
|
-
|
21
|
-
istek = await self.oturum.get(url, follow_redirects=False)
|
22
|
-
if istek.status_code == 302: # Yönlendirme varsa
|
23
|
-
redirected_url = istek.headers.get("Location")
|
24
|
-
if not redirected_url:
|
25
|
-
raise ValueError("Redirect location not found.")
|
26
|
-
|
27
|
-
# Yönlendirilmiş URL'yi kullanarak isteği yeniden yap.
|
28
|
-
url = redirected_url if redirected_url.startswith("http") else f"https://{redirected_url}"
|
29
|
-
istek = await self.oturum.get(url)
|
20
|
+
if "/video/" in url:
|
21
|
+
url = url.replace("/video/", "/videoembed/")
|
30
22
|
|
23
|
+
try:
|
24
|
+
istek = await self.fetch_with_redirects(url)
|
31
25
|
istek.raise_for_status()
|
32
26
|
except Exception as e:
|
33
27
|
raise RuntimeError(f"Failed to fetch the URL: {url}, Error: {e}")
|
@@ -91,4 +85,25 @@ class Odnoklassniki(ExtractorBase):
|
|
91
85
|
url = best_video,
|
92
86
|
referer = self.main_url,
|
93
87
|
subtitles = []
|
94
|
-
)
|
88
|
+
)
|
89
|
+
|
90
|
+
async def fetch_with_redirects(self, url, max_redirects=5):
|
91
|
+
"""Yönlendirmeleri takip eden bir fonksiyon"""
|
92
|
+
redirects = 0
|
93
|
+
while redirects < max_redirects:
|
94
|
+
istek = await self.oturum.get(url, follow_redirects=False)
|
95
|
+
|
96
|
+
if istek.status_code in [301, 302]: # Yönlendirme varsa
|
97
|
+
redirected_url = istek.headers.get("Location")
|
98
|
+
print(redirected_url)
|
99
|
+
if not redirected_url:
|
100
|
+
raise ValueError("Redirect location not found.")
|
101
|
+
|
102
|
+
url = redirected_url if redirected_url.startswith("http") else f"https://{redirected_url}"
|
103
|
+
redirects += 1
|
104
|
+
else:
|
105
|
+
break # Yönlendirme yoksa çık
|
106
|
+
|
107
|
+
if redirects == max_redirects:
|
108
|
+
raise RuntimeError(f"Max redirects ({max_redirects}) reached.")
|
109
|
+
return istek
|
@@ -0,0 +1,115 @@
|
|
1
|
+
# Bu araç @keyiflerolsun tarafından | @KekikAkademi için yazılmıştır.
|
2
|
+
|
3
|
+
from KekikStream.Core import PluginBase, SearchResult, SeriesInfo, Episode
|
4
|
+
from Kekik.Sifreleme import CryptoJS
|
5
|
+
from parsel import Selector
|
6
|
+
import re, urllib.parse, base64
|
7
|
+
|
8
|
+
class DiziBox(PluginBase):
|
9
|
+
name = "DiziBox"
|
10
|
+
main_url = "https://www.dizibox.plus"
|
11
|
+
|
12
|
+
async def search(self, query: str) -> list[SearchResult]:
|
13
|
+
self.oturum.cookies.update({
|
14
|
+
"LockUser" : "true",
|
15
|
+
"isTrustedUser" : "true",
|
16
|
+
"dbxu" : "1722403730363"
|
17
|
+
})
|
18
|
+
istek = await self.oturum.get(f"{self.main_url}/?s={query}")
|
19
|
+
secici = Selector(istek.text)
|
20
|
+
|
21
|
+
return [
|
22
|
+
SearchResult(
|
23
|
+
title = item.css("h3 a::text").get(),
|
24
|
+
url = self.fix_url(item.css("h3 a::attr(href)").get()),
|
25
|
+
poster = self.fix_url(item.css("img::attr(src)").get()),
|
26
|
+
)
|
27
|
+
for item in secici.css("article.detailed-article")
|
28
|
+
]
|
29
|
+
|
30
|
+
async def load_item(self, url: str) -> SeriesInfo:
|
31
|
+
istek = await self.oturum.get(url)
|
32
|
+
secici = Selector(istek.text)
|
33
|
+
|
34
|
+
title = secici.css("div.tv-overview h1 a::text").get()
|
35
|
+
poster = self.fix_url(secici.css("div.tv-overview figure img::attr(src)").get())
|
36
|
+
description = secici.css("div.tv-story p::text").get()
|
37
|
+
year = secici.css("a[href*='/yil/']::text").re_first(r"(\d{4})")
|
38
|
+
tags = secici.css("a[href*='/tur/']::text").getall()
|
39
|
+
rating = secici.css("span.label-imdb b::text").re_first(r"[\d.,]+")
|
40
|
+
actors = [actor.css("::text").get() for actor in secici.css("a[href*='/oyuncu/']")]
|
41
|
+
|
42
|
+
episodes = []
|
43
|
+
for sezon_link in secici.css("div#seasons-list a::attr(href)").getall():
|
44
|
+
sezon_url = self.fix_url(sezon_link)
|
45
|
+
sezon_istek = await self.oturum.get(sezon_url)
|
46
|
+
sezon_secici = Selector(sezon_istek.text)
|
47
|
+
|
48
|
+
for bolum in sezon_secici.css("article.grid-box"):
|
49
|
+
ep_title = bolum.css("div.post-title a::text").get()
|
50
|
+
ep_href = self.fix_url(bolum.css("div.post-title a::attr(href)").get())
|
51
|
+
ep_season = bolum.css("div.post-title a::text").re_first(r"(\d+)\. ?Sezon")
|
52
|
+
ep_episode = bolum.css("div.post-title a::text").re_first(r"(\d+)\. ?Bölüm")
|
53
|
+
|
54
|
+
if ep_title and ep_href:
|
55
|
+
episodes.append(Episode(
|
56
|
+
season = ep_season,
|
57
|
+
episode = ep_episode,
|
58
|
+
title = ep_title.strip(),
|
59
|
+
url = ep_href,
|
60
|
+
))
|
61
|
+
|
62
|
+
return SeriesInfo(
|
63
|
+
url = url,
|
64
|
+
poster = poster,
|
65
|
+
title = title,
|
66
|
+
description = description,
|
67
|
+
tags = tags,
|
68
|
+
rating = rating,
|
69
|
+
year = year,
|
70
|
+
episodes = episodes,
|
71
|
+
actors = actors,
|
72
|
+
)
|
73
|
+
|
74
|
+
async def _iframe_decode(self, name:str, iframe_link:str, referer:str) -> list[str]:
|
75
|
+
results = []
|
76
|
+
|
77
|
+
if "/player/king/king.php" in iframe_link:
|
78
|
+
print(name, iframe_link)
|
79
|
+
elif "/player/moly/moly.php" in iframe_link:
|
80
|
+
print(name, iframe_link)
|
81
|
+
elif "/player/haydi.php" in iframe_link:
|
82
|
+
okru_url = base64.b64decode(iframe_link.split("?v=")[-1]).decode("utf-8")
|
83
|
+
results.append(okru_url)
|
84
|
+
|
85
|
+
return results
|
86
|
+
|
87
|
+
async def load_links(self, url: str) -> list[str]:
|
88
|
+
istek = await self.oturum.get(url)
|
89
|
+
secici = Selector(istek.text)
|
90
|
+
|
91
|
+
iframes = []
|
92
|
+
main_iframe = secici.css("div#video-area iframe::attr(src)").get()
|
93
|
+
if main_iframe:
|
94
|
+
if decoded := await self._iframe_decode(self.name, main_iframe, url):
|
95
|
+
iframes.extend(decoded)
|
96
|
+
|
97
|
+
for alternatif in secici.css("div.video-toolbar option[value]"):
|
98
|
+
alt_name = alternatif.css("::text").get()
|
99
|
+
alt_link = alternatif.css("::attr(value)").get()
|
100
|
+
|
101
|
+
if not alt_link:
|
102
|
+
continue
|
103
|
+
|
104
|
+
self.oturum.headers.update({"Referer": url})
|
105
|
+
alt_istek = await self.oturum.get(alt_link)
|
106
|
+
alt_istek.raise_for_status()
|
107
|
+
|
108
|
+
alt_secici = Selector(alt_istek.text)
|
109
|
+
alt_iframe = alt_secici.css("div#video-area iframe::attr(src)").get()
|
110
|
+
|
111
|
+
if alt_iframe:
|
112
|
+
if decoded := await self._iframe_decode(alt_name, alt_iframe, url):
|
113
|
+
iframes.extend(decoded)
|
114
|
+
|
115
|
+
return iframes
|
KekikStream/__init__.py
CHANGED
@@ -171,6 +171,7 @@ class KekikStream:
|
|
171
171
|
|
172
172
|
async def play_media(self, selected_link):
|
173
173
|
if hasattr(self.current_plugin, "play") and callable(self.current_plugin.play):
|
174
|
+
konsol.log(f"[yellow][»] Oynatılıyor : {selected_link}")
|
174
175
|
await self.current_plugin.play(
|
175
176
|
name = self.current_plugin._data[selected_link]["name"],
|
176
177
|
url = selected_link,
|
@@ -184,7 +185,12 @@ class KekikStream:
|
|
184
185
|
konsol.print("[bold red]Uygun Extractor bulunamadı.[/bold red]")
|
185
186
|
return
|
186
187
|
|
187
|
-
|
188
|
+
try:
|
189
|
+
extract_data = await extractor.extract(selected_link, referer=self.current_plugin.main_url)
|
190
|
+
except Exception as hata:
|
191
|
+
konsol.print(f"[bold red]{extractor.name} » hata oluştu: {hata}[/bold red]")
|
192
|
+
await self.handle_no_results()
|
193
|
+
return
|
188
194
|
|
189
195
|
if isinstance(extract_data, list):
|
190
196
|
selected_data = await self.ui_manager.select_from_list(
|
@@ -199,6 +205,7 @@ class KekikStream:
|
|
199
205
|
|
200
206
|
self.media_manager.set_title(f"{self.media_manager.get_title()} | {selected_data.name}")
|
201
207
|
self.media_manager.set_headers({"Referer": selected_data.referer})
|
208
|
+
konsol.log(f"[yellow][»] Oynatılıyor : {selected_data.url}")
|
202
209
|
self.media_manager.play_media(selected_data)
|
203
210
|
|
204
211
|
async def search_all_plugins(self, query: str):
|
KekikStream/requirements.txt
CHANGED
@@ -1,6 +1,6 @@
|
|
1
1
|
Metadata-Version: 2.1
|
2
2
|
Name: KekikStream
|
3
|
-
Version: 0.2.
|
3
|
+
Version: 0.2.8
|
4
4
|
Summary: terminal üzerinden medya içeriği aramanızı ve VLC/MPV gibi popüler medya oynatıcılar aracılığıyla doğrudan izlemenizi sağlayan modüler ve genişletilebilir bir bıdı bıdı
|
5
5
|
Home-page: https://github.com/keyiflerolsun/KekikStream
|
6
6
|
Author: keyiflerolsun
|
@@ -17,6 +17,7 @@ Requires-Dist: setuptools
|
|
17
17
|
Requires-Dist: wheel
|
18
18
|
Requires-Dist: Kekik
|
19
19
|
Requires-Dist: httpx
|
20
|
+
Requires-Dist: cloudscraper
|
20
21
|
Requires-Dist: parsel
|
21
22
|
Requires-Dist: pydantic
|
22
23
|
Requires-Dist: InquirerPy
|
@@ -1,13 +1,13 @@
|
|
1
|
-
KekikStream/__init__.py,sha256=
|
1
|
+
KekikStream/__init__.py,sha256=SZzntUwOYPjSWgtjGmoF2Iu77Y_7A4BtgwV_UX-abHk,10341
|
2
2
|
KekikStream/__main__.py,sha256=4U-NO1f0Mts5Mf_QnWhWqRbTsRBy2y2VPlpHyaqG9_I,137
|
3
|
-
KekikStream/requirements.txt,sha256=
|
3
|
+
KekikStream/requirements.txt,sha256=gS_TUUQx5A7FUmRGxj2dQedxheD7qA6AswdUb2y_Ub8,70
|
4
4
|
KekikStream/CLI/__init__.py,sha256=9YlF135BVff85y492hX4sq2WY2CNqa4BuVzF9hIIaKE,233
|
5
5
|
KekikStream/CLI/check_update.py,sha256=rOa16bO9sGN-p78yaTRaccFoNfhHWEfDgGZNavpcwNI,1642
|
6
6
|
KekikStream/Core/ExtractorBase.py,sha256=SPXKZPfpzvgkJeMds-USzgpm8-qb0vgZjjLDs58NfGU,1069
|
7
|
-
KekikStream/Core/ExtractorLoader.py,sha256=
|
7
|
+
KekikStream/Core/ExtractorLoader.py,sha256=1S0XaZDJnpFX9dUC4eoqRXx9la6Nlxk6EemJvvSknPA,3921
|
8
8
|
KekikStream/Core/ExtractorModels.py,sha256=vJeh4qd05K7nbqdCCGU29UkGQpce6jXfsCm7LuDL1G8,454
|
9
|
-
KekikStream/Core/MediaHandler.py,sha256=
|
10
|
-
KekikStream/Core/PluginBase.py,sha256=
|
9
|
+
KekikStream/Core/MediaHandler.py,sha256=TFFngsvWGV-zllYlrb2HTvFSluGYZ8t83vH_8AXAoO4,3247
|
10
|
+
KekikStream/Core/PluginBase.py,sha256=44sJRS8LqkOo0Ul7lE8R4A464wxyym4UplqkpMUJXqY,2511
|
11
11
|
KekikStream/Core/PluginLoader.py,sha256=og5EPfnVqrb2kUkeGU65AY0fU43IbiUo_h3ix6ZiINY,2596
|
12
12
|
KekikStream/Core/PluginModels.py,sha256=WWPEz8PpZZ4bLMDJzTE19BsQEJObkyhaYjDkyLaF2Ck,2365
|
13
13
|
KekikStream/Core/__init__.py,sha256=HZpXs3MKy4joO0sDpIGcZ2DrUKwK49IKG-GQgKbO2jk,416
|
@@ -20,7 +20,7 @@ KekikStream/Extractors/HDStreamAble.py,sha256=66n5EvIdX_or5cdnlJ_Uqmzi50n4rl9c5V
|
|
20
20
|
KekikStream/Extractors/Hotlinger.py,sha256=NFMRgUmb6BCrJfa7Hi0VarDNYvCeVknBWEk24FKBBa0,224
|
21
21
|
KekikStream/Extractors/MailRu.py,sha256=lB3Xy912EaSEUw7Im65L5TwtIeM7OLFV1_9lan39g40,1308
|
22
22
|
KekikStream/Extractors/MixPlayHD.py,sha256=4sSHingB3gquakFesnbC0LmkJZWW2Jvv5F4kOdo58tA,1528
|
23
|
-
KekikStream/Extractors/Odnoklassniki.py,sha256=
|
23
|
+
KekikStream/Extractors/Odnoklassniki.py,sha256=xt8gWi750ykkWVkFiP6o7HQc-0RwrSx1FxxuoNUU-Js,3765
|
24
24
|
KekikStream/Extractors/OkRuHTTP.py,sha256=L-B0i_i_Vnm61GvUfd6cGIW-o_H4M-C7DO_cdw2rQPU,228
|
25
25
|
KekikStream/Extractors/OkRuSSL.py,sha256=FHJ5XZ1dO5ED3mIku3e3vnq8K0slrcr0jqhaUnHmfVk,227
|
26
26
|
KekikStream/Extractors/PeaceMakerst.py,sha256=1l5Y5AQB_P53upVqgBuJTnjNV7nHVMr56tp673Q8omU,2123
|
@@ -39,17 +39,18 @@ KekikStream/Extractors/VideoSeyred.py,sha256=Sx1qHNBMboGgU_bXHVgx3MlxtyKpR_LBJIQ
|
|
39
39
|
KekikStream/Managers/ExtractorManager.py,sha256=9rGlUsnedJ7fwIeObN5Vsm8H5VLal0ODO7F93dDRx8w,976
|
40
40
|
KekikStream/Managers/MediaManager.py,sha256=F7mkSvAttAaMHRvnDcxnV2K1D_sK644BCSrEaAmMl_U,522
|
41
41
|
KekikStream/Managers/PluginManager.py,sha256=YDBLHB_Fh79A3Pei0ny2KLVY4VSihdNiKBh_w5tBl-0,637
|
42
|
-
KekikStream/Managers/UIManager.py,sha256=
|
42
|
+
KekikStream/Managers/UIManager.py,sha256=OrGxzbhRPTCqiLEXjipLb8ChF7saV3fvFIUXLKT9w6Q,1612
|
43
43
|
KekikStream/Managers/__init__.py,sha256=3085I_9Sa2L_Vq6Z-QvYUYn1BapkN4sQqBo8ITZoD_4,251
|
44
|
+
KekikStream/Plugins/DiziBox.py,sha256=zh8qbmI1RDwqBQAo32Okd9uuLFbnEIGgbnaytb6zYqU,4624
|
44
45
|
KekikStream/Plugins/FilmMakinesi.py,sha256=g4LRDP5Atn97PqbgnEdm0-wjVdXaJIVk1Ru0F8B66Ws,2902
|
45
46
|
KekikStream/Plugins/FullHDFilmizlesene.py,sha256=HJzHDXHhhMpvXxiD2SjpoZEYs7dmnPymE8EXCSvLKVo,3106
|
46
47
|
KekikStream/Plugins/JetFilmizle.py,sha256=DPdvTEns8r2MI9pHY8d9EEsUZmlQU7N2C9yr8ox80qU,4016
|
47
48
|
KekikStream/Plugins/SezonlukDizi.py,sha256=5BZVzQ2eQtymHxO0bzjA2ho4FFNahPFQly4hoHuH8lo,4441
|
48
49
|
KekikStream/Plugins/SineWix.py,sha256=ZtcIwPW0ONGkSjT7Ye8b71RWdHZMUZefX-JTWu6uGSs,4854
|
49
50
|
KekikStream/Plugins/UgurFilm.py,sha256=U7ryNWpjSZJWuYlMGX1Be9uuyiM3SfuI9VJcEiXedNs,2960
|
50
|
-
KekikStream-0.2.
|
51
|
-
KekikStream-0.2.
|
52
|
-
KekikStream-0.2.
|
53
|
-
KekikStream-0.2.
|
54
|
-
KekikStream-0.2.
|
55
|
-
KekikStream-0.2.
|
51
|
+
KekikStream-0.2.8.dist-info/LICENSE,sha256=OXLcl0T2SZ8Pmy2_dmlvKuetivmyPd5m1q-Gyd-zaYY,35149
|
52
|
+
KekikStream-0.2.8.dist-info/METADATA,sha256=pnnKXvIpKVjAl1v5qymb8jYVRyVnYjFT7BqJcWWyxAM,3987
|
53
|
+
KekikStream-0.2.8.dist-info/WHEEL,sha256=PZUExdf71Ui_so67QXpySuHtCi3-J3wvF4ORK6k_S8U,91
|
54
|
+
KekikStream-0.2.8.dist-info/entry_points.txt,sha256=dFwdiTx8djyehI0Gsz-rZwjAfZzUzoBSrmzRu9ubjJc,50
|
55
|
+
KekikStream-0.2.8.dist-info/top_level.txt,sha256=DNmGJDXl27Drdfobrak8KYLmocW_uznVYFJOzcjUgmY,12
|
56
|
+
KekikStream-0.2.8.dist-info/RECORD,,
|
File without changes
|
File without changes
|
File without changes
|
File without changes
|