File size: 3,384 Bytes
0a512d5
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
import instaloader
import os
import requests
from urllib.parse import urlparse
from dotenv import load_dotenv
import time

# Load environment variables from .env file
load_dotenv()

def extract_shortcode(reel_url: str) -> str:
    """Extract shortcode from Instagram URL"""
    path = urlparse(reel_url).path.strip("/")
    parts = [p for p in path.split("/") if p]
    if len(parts) >= 2 and parts[0] in {"reel", "p"}:
        return parts[1]
    return parts[-1] if parts else ""

def download_reel_with_audio(reel_url: str, output_folder: str, sessionid: str) -> str:
    """

    Download Instagram reel with audio

    Returns the full path to the downloaded video file

    """
    try:
        L = instaloader.Instaloader()

        # πŸ”‘ Use sessionid from environment
        L.context._session.cookies.set("sessionid", sessionid, domain=".instagram.com")

        shortcode = extract_shortcode(reel_url)
        post = instaloader.Post.from_shortcode(L.context, shortcode)

        video_url = post.video_url
        if not video_url and post.typename == "GraphSidecar":
            for node in post.get_sidecar_nodes():
                if node.is_video:
                    video_url = node.video_url
                    break

        if not video_url:
            raise Exception("No video URL found for this post")

        # Ensure the filename is valid and doesn't have special characters
        video_filename = f"reel_{int(time.time())}_{shortcode}.mp4"
        video_path = os.path.join(output_folder, video_filename)

        print("⬇️ Downloading video with audio...")
        r = requests.get(video_url, stream=True)
        with open(video_path, "wb") as f:
            for chunk in r.iter_content(chunk_size=8192):
                if chunk:
                    f.write(chunk)

        # Verify file was written correctly
        if not os.path.exists(video_path):
            raise Exception(f"Failed to save video to {video_path}")

        file_size = os.path.getsize(video_path)
        if file_size == 0:
            raise Exception("Downloaded file is empty")

        print(f"βœ… Video saved successfully: {video_path} ({file_size} bytes)")
        return video_path

    except Exception as e:
        raise Exception(f"Download failed: {str(e)}")

def main():
    print("Instagram Reel Downloader with Audio")
    print("="*40)

    try:
        reel_url = input("Enter Instagram reel URL: ").strip()
        if not reel_url:
            print("No URL provided")
            return

        # Get sessionid from environment variable (now loaded from .env)
        sessionid = os.getenv("IG_SESSIONID")
        if not sessionid:
            raise Exception("No IG_SESSIONID found! Please set in .env file.")

        video_path = download_reel_with_audio(reel_url, "downloads", sessionid)

        print(f"\nβœ… Successfully downloaded with audio!")
        print(f"πŸ“ File location: {video_path}")
        print(f"πŸ“Š File size: {os.path.getsize(video_path) / 1024 / 1024:.2f} MB")

    except Exception as e:
        print(f"\n❌ Error: {str(e)}")
        print("\nTips:")
        print("- Make sure IG_SESSIONID is set in the .env file")
        print("- If expired, grab a new sessionid from Chrome cookies")

if __name__ == "__main__":
    main()