吾爱破解 - LCG - LSG |安卓破解|病毒分析|www.52pojie.cn

 找回密码
 注册[Register]

QQ登录

只需一步,快速开始

查看: 3036|回复: 48
收起左侧

[Python 原创] 通过右键生成链接在局域网内分享文件

  [复制链接]
xiaomingtt 发表于 2023-8-29 12:13
本帖最后由 xiaomingtt 于 2023-12-8 16:00 编辑

2023-08-29_121139.png
[Python] 纯文本查看 复制代码
# -*- coding: utf-8 -*-

from flask import Flask, send_from_directory 
import os
import sys
import netifaces 
import random
import pyperclip 
import winreg
import socket
import psutil
import time
import threading 
import tkinter as tk 
from tkinter import filedialog
from PIL import ImageTk, Image #
import qrcode
from colorama import init, Fore, Back, Style
from datetime import datetime
import shutil
import logging

def start_flask_server(p,fol,cip):
    app = Flask(__name__)
    logging.getLogger("werkzeug").disabled = True

    @app.route('/download/<filename>', methods=['GET'])
    def download_file(filename):
        file_path = os.path.join(fol, filename)
        if not os.path.exists(file_path):
            return "文件不存在", 404
        return send_from_directory(fol, filename, as_attachment=True, conditional=True)
         
    app.run(host=cip, port=p, debug=False, threaded=True)

def get_all_ips(): #获取并返回本机所有IP地址
    interfaces = netifaces.interfaces()
    ip_addresses = []
    for interface in interfaces:
        addresses = netifaces.ifaddresses(interface)
        if netifaces.AF_INET in addresses:
            for address in addresses[netifaces.AF_INET]:
                ip_address = address['addr']
                if ip_address != '127.0.0.1':
                    ip_addresses.append(ip_address)
    return ip_addresses

def choose_ip(): #选择要使用的IP 
    all_ips = get_all_ips()
    ip_count = len(all_ips)
    for i, ip in enumerate(all_ips):
        print(f"{i+1}、{ip}")
    while True:
        selected_index = input("选择要使用的IP,并输入编号,按回车确认:")
        try:
            selected_index = int(selected_index)  
            if selected_index >= 1 and selected_index <= ip_count:
                selected_ip = all_ips[selected_index - 1]
                print("已选择IP:" + selected_ip)
                return selected_ip
            else:
                print(Back.RED + Fore.WHITE + "无效的IP编号,请重新输入!" + Style.RESET_ALL)
        except ValueError:
            print(Back.RED + Fore.WHITE + "无效的IP编号,请重新输入!" + Style.RESET_ALL)
            
def write_registry_entry(epath, ico,cip): #写入注册表
    reg_path = r"*\shell\Share File"
    key = winreg.CreateKey(winreg.HKEY_CLASSES_ROOT, reg_path)
    winreg.SetValue(key, None, winreg.REG_SZ, "分享此文件")
    winreg.SetValueEx(key, 'ICON', 0, winreg.REG_SZ, ico)
    winreg.SetValueEx(key, 'ip', 0, winreg.REG_SZ, cip)
    winreg.SetValueEx(key, 'autoexit', 0, winreg.REG_SZ, "1")
    winreg.SetValueEx(key, 'showqr', 0, winreg.REG_SZ, "1")
    winreg.CloseKey(key)

    command_path = r"*\shell\Share File\command"
    command_key = winreg.CreateKey(winreg.HKEY_CLASSES_ROOT, command_path)
    winreg.SetValue(command_key, None, winreg.REG_SZ, epath + ' "%1"')
    winreg.CloseKey(command_key)

def read_registry_value(): #读取注册表
    try:
        key = winreg.OpenKey(winreg.HKEY_CLASSES_ROOT, r"Python.File\Shell\open\command")
        value, _ = winreg.QueryValueEx(key, "")
        winreg.CloseKey(key)
        value = value.split('"')
        return value[1]
    except OSError:
        print("注册表项不存在")
    except Exception as e:
        print(f"读取注册表值时出现错误: {e}")

def check_reg_key(keyname): #读取注册表指定项
    key_path = r'*\shell\Share File'
    try:
        key = winreg.OpenKey(winreg.HKEY_CLASSES_ROOT, key_path)
        value, reg_type = winreg.QueryValueEx(key, keyname)
        return value
    except FileNotFoundError:
        return None

def CheckPortUse(port): #检测端口是否被占用
    sock = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
    result = sock.connect_ex(('127.0.0.1', port))
    if result == 0:
        sock.close()
        return False
    else:
        connections = psutil.net_connections()
        for conn in connections:
            if conn.laddr.port == port:
                return False
        return True

def get_port_connections(port): #获取本机端口的连接状态
    global sflj
    global clients
    current_time = datetime.now()
    formatted_time = current_time.strftime("%Y-%m-%d %H:%M:%S")
    connections = psutil.net_connections()
    stat= ""
    ips = []
    for conn in connections:
        if conn.laddr.port == port:
            stat= conn.status
            if conn.status == 'ESTABLISHED':
                ips.append(conn.raddr.ip)
                
    diff1 = set(ips) - set(clients)
    if diff1:
        print(Back.WHITE + Fore.GREEN + "有新用户接入:{}".format(list(diff1)) + Style.RESET_ALL, formatted_time)
    diff2= set(clients) - set(ips)
    if diff2:
        print(Back.RED + Fore.WHITE + "用户:{}已断开连接。".format(list(diff2)) + Style.RESET_ALL, formatted_time)
    clients = ips
    
    ipnum = len(list(set(ips)))
    if ipnum > 0:
        if sflj == 0:
            sflj += 1
        print(Fore.GREEN + "当前所有在线用户:{}".format(list(set(ips))) + Style.RESET_ALL, formatted_time)
        return False
    else:
        if sflj == 0:
            #print("暂无用户连接")
            return False
        else:
            #print("所有用户都断开连接")
            return True
            
def save_qr_code(img):
    filename = filedialog.asksaveasfilename(defaultextension=".png",
                                            filetypes=[("PNG Image", "*.png")],
                                            initialfile="文件分享二维码.png")
    if filename:
        img.save(filename)


def show_qr_code(data):
    window = tk.Tk()
    window.title("二维码分享")
    window.resizable(False, False) 
    window.attributes('-toolwindow', True)
    qr = qrcode.QRCode(
        version=1,
        error_correction=qrcode.constants.ERROR_CORRECT_H,
        box_size=10,
        border=4,
    )
    qr.add_data(data)
    qr.make(fit=True)
    img = qr.make_image(fill_color="black", back_color="white")
    width, height = img.size
    max_width = 200
    max_height = 200
    if width > max_width or height > max_height:
        scale = min(max_width/width, max_height/height)
        new_width = int(width * scale)
        new_height = int(height * scale)
        img = img.resize((new_width, new_height), Image.Resampling.LANCZOS)

    photo = ImageTk.PhotoImage(img)
    label = tk.Label(window, image=photo)
    label.pack()
    
    save_button = tk.Button(window, text="  保 存  ", command=lambda: save_qr_code(img))
    save_button.pack()
    
    window.update_idletasks()
    screen_width = window.winfo_screenwidth()
    screen_height = window.winfo_screenheight()
    window_width = window.winfo_width()
    window_height = window.winfo_height()
    x = int((screen_width - window_width) / 2)
    y = int((screen_height - window_height) / 2)
    window.geometry(f"{window_width}x{window_height}+{x}+{y}")
    window.mainloop()

def sys_init(arg):
    ip = cip = choose_ip()
    executable_path = os.path.abspath(sys.executable)
    if getattr(sys, 'frozen', False):
        exe = icon = '"' + executable_path + '"'
        #print("脚本已编译成exe文件")
    else:
        pypath = read_registry_value()
        exe = '"' + pypath + '" "' + arg[0] + '"'
        icon = '"' + pypath + '"'
        #print("脚本未被编译成exe文件")
    write_registry_entry(exe,icon,cip)
    return ip

def qr_code_thread(url):
    show_qr_code(url)

if __name__ == '__main__':
    init(autoreset=True)
    #下面两行为了清除打包时启用“输出引导进度信息”而在启动时打印的日志信息
    os.system("cls" if os.name in ("nt", "dos") else "clear")
    #print("\033c", end="")
    args = sys.argv
    ip = check_reg_key("ip")
    if ip == None:
        ip = sys_init(args)

    if len(args) - 1 == 0:
        print(Back.RED + Fore.WHITE + "\n**请通过右键菜单运行此程序**\n" + Style.RESET_ALL)
        print(Back.BLUE + Fore.WHITE + "Tips:如不需自动退出和二维码功能,请在注册表HKEY_CLASSES_ROOT\\*\\shell\\Share File中自行修改" + Style.RESET_ALL)
        hc = input("\n直接按回车键退出程序,输入其他任意内容后回车重新设置IP:")
        if hc != "":
            sys_init(args)
        sys.exit(0)
    file = args[1]
    path = os.path.dirname(file)
    filename = os.path.basename(file)
    while True:
        port = random.randint(10000, 65500)
        if CheckPortUse(port):
            break
    url = "http://" + ip + ":" + str(port) + "/download/" + filename
    pyperclip.copy(url)
    print(Back.BLUE + Fore.WHITE + "\n↓↓文件下载地址已复制到剪贴板↓↓\n" + Style.RESET_ALL)
    print(Back.GREEN + Fore.WHITE + url + Style.RESET_ALL)
    print(Back.BLUE + Fore.WHITE + "\n↑↑文件下载地址已复制到剪贴板↑↑\n" + Style.RESET_ALL)
    print("Tips:如无法重新复制上方链接,可在此窗口标题栏点击右键选择属性,勾选“快速编辑模式”,点击确定保存。")
    print(Fore.GREEN + "\n52PoJie\n" + Style.RESET_ALL)
    
    qr = check_reg_key("showqr")
    if str(qr) == "1":
        print(Back.CYAN + Fore.WHITE + "显示二维码:" + Style.RESET_ALL, Back.GREEN + Fore.WHITE + " 开 " + Style.RESET_ALL)
        print(Fore.YELLOW + "如不需二维码功能请在注册表HKEY_CLASSES_ROOT\\*\\shell\\Share File\\showqr中自行修改值为0"+ Style.RESET_ALL)
        qr_thread = threading.Thread(target=qr_code_thread, args=(url,))
        qr_thread.start()
    else:
        print(Back.CYAN + Fore.WHITE + "显示二维码:" + Style.RESET_ALL, Back.RED + Fore.WHITE + " 关 " + Style.RESET_ALL)
        print(Fore.YELLOW + "如需开启二维码功能请在注册表HKEY_CLASSES_ROOT\\*\\shell\\Share File\\showqr中自行修改值为1"+ Style.RESET_ALL)

    autoexit = check_reg_key("autoexit")
    if str(autoexit) == "1":
        print(Back.CYAN + Fore.WHITE + "所有连接关闭将自动退出功能:" + Style.RESET_ALL,  Back.GREEN + Fore.WHITE + " 开 " + Style.RESET_ALL)
        print(Fore.YELLOW + "如不需自动退出功能请在注册表HKEY_CLASSES_ROOT\\*\\shell\\Share File\\autoexit中自行修改值为0"+ Style.RESET_ALL)
    else:
        print(Back.CYAN + Fore.WHITE + "所有连接关闭将自动退出功能:" + Style.RESET_ALL,  Back.RED + Fore.WHITE + " 关 " + Style.RESET_ALL)
        print(Fore.YELLOW + "如需开启自动退出功能请在注册表HKEY_CLASSES_ROOT\\*\\shell\\Share File\\autoexit中自行修改值为1"+ Style.RESET_ALL)

    columns = shutil.get_terminal_size().columns
    print('~' * columns)
    
    server_thread = threading.Thread(target=start_flask_server, args=(port, path, ip))
    server_thread.start()
    
    sflj = 0
    clients = []
    while True:
        zt = get_port_connections(port)
        if zt and str(autoexit) == "1":
            print("结束了,可以退出了")
            time.sleep(3)
            os._exit(0)
        time.sleep(3)

免费评分

参与人数 15吾爱币 +20 热心值 +14 收起 理由
alentonly + 1 + 1 谢谢@Thanks!
苏紫方璇 + 5 + 1 欢迎分析讨论交流,吾爱破解论坛有你更精彩!
54amm + 1 + 1 谢谢@Thanks!
吾恋兮不知 + 1 + 1 谢谢@Thanks!
AkerIII + 1 + 1 用心讨论,共获提升!
hwh425 + 1 谢谢@Thanks!
jinzi2736 + 1 + 1 谢谢@Thanks!
winbbsl + 1 + 1 热心回复!
ase1993 + 1 + 1 鼓励转贴优秀软件安全工具和文档!
songbing490 + 2 + 1 文件夹不可以分享,建议加上
daoye9988 + 1 + 1 热心回复!
blindcat + 1 + 1 谢谢@Thanks!
guyang9264 + 1 + 1 我很赞同!
hrh123 + 1 + 1 欢迎分析讨论交流,吾爱破解论坛有你更精彩!
fxwl + 1 + 1 谢谢@Thanks!

查看全部评分

本帖被以下淘专辑推荐:

发帖前要善用论坛搜索功能,那里可能会有你要找的答案或者已经有人发布过相同内容了,请勿重复发帖。

 楼主| xiaomingtt 发表于 2023-8-29 13:39
本帖最后由 xiaomingtt 于 2023-9-1 08:51 编辑

https://mmn.lanzoue.com/i8rlc172jxjc
 楼主| xiaomingtt 发表于 2023-8-30 10:50
AkerIII 发表于 2023-8-30 09:15
get_wired_ip好像无法获取我机器正确的局域网IP,可能是我本机装了VMWare给机器添加了很多虚拟网卡

代码修改了,可以选择要使用的IP。
 楼主| xiaomingtt 发表于 2023-8-29 15:48
drw 发表于 2023-8-29 15:40
就是说可以直接在本机共享一个文件供同一个局域网内的其他人下载?

对,主要适用于禁止系统默认共享的电脑,通过HTTP一键共享文件。
 楼主| xiaomingtt 发表于 2023-8-29 15:45
a397555462 发表于 2023-8-29 14:32
访问失败,网页走丢了

看看是不是防火墙拦截了
 楼主| xiaomingtt 发表于 2023-8-29 13:36
上面的代码编译或不编译都行,运行后在所有文件的右键菜单都会多出一条“分享此文件”,点击后会形成一个链接并自动复制到剪贴板。分享此链接,在局域网内其他电脑访问此链接就可以下载文件。
 楼主| xiaomingtt 发表于 2023-8-29 16:17
panda7355608 发表于 2023-8-29 15:50
哥,不用麻烦了,有个现成工具,HFS,很实用。

HFS也用过,现在主要用dufs。但我这个工具不是给自己用的。单位几百号人,很多年龄非常大了,你让他们用HFS不现实,他们的需求就是点几下鼠标就能实现功能。
a2523188267 发表于 2023-8-29 13:03
谢谢楼主分享。好方法
lingwushexi 发表于 2023-8-29 13:19
感谢分享
yuxiaojiesheng 发表于 2023-8-29 13:33
这个怎么用啊?能说的详细一些吗?
梦中之梦 发表于 2023-8-29 13:34
打包成exe文件呗
751811164 发表于 2023-8-29 14:17
感谢感谢
guyang9264 发表于 2023-8-29 14:17
工具很不对,加油。
dsyxa 发表于 2023-8-29 14:32
谢谢楼主分享,实用。。。
您需要登录后才可以回帖 登录 | 注册[Register]

本版积分规则 警告:本版块禁止灌水或回复与主题无关内容,违者重罚!

快速回复 收藏帖子 返回列表 搜索

RSS订阅|小黑屋|处罚记录|联系我们|吾爱破解 - LCG - LSG ( 京ICP备16042023号 | 京公网安备 11010502030087号 )

GMT+8, 2024-5-21 17:55

Powered by Discuz!

Copyright © 2001-2020, Tencent Cloud.

快速回复 返回顶部 返回列表