.Net下载共享文件夹中的文件

由于IIS站点权限等问题,总是没找到处理办法,所以改用外挂的winform的方式来下载共享文件(也可以改为使用windows服务的方式)。
前提需要先在资源管理器中登录到共享文件夹,确保系统能访问。

  1. 服务端代码 (.NET后端)
using System;
using System.IO;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Web;public class FileDownloadService
{private const int WinFormPort = 11000;public void DownloadFile(string filePath){try{// 1. 连接到WinForm客户端using (TcpClient client = new TcpClient("127.0.0.1", WinFormPort))using (NetworkStream netStream = client.GetStream()){// 2. 发送文件路径byte[] pathData = Encoding.UTF8.GetBytes(filePath);netStream.Write(pathData, 0, pathData.Length);// 3. 设置响应头Response.Clear();Response.ContentType = "application/octet-stream";Response.AddHeader("Content-Disposition", $"attachment; filename={HttpUtility.UrlEncode(Path.GetFileName(filePath))}");// 4. 流式传输到客户端浏览器byte[] buffer = new byte[1024 * 1024]; // 1MB缓冲区int bytesRead;while ((bytesRead = netStream.Read(buffer, 0, buffer.Length)) > 0){Response.OutputStream.Write(buffer, 0, bytesRead);Response.Flush();}}}catch (Exception ex){Response.Write($"下载错误: {ex.Message}");}finally{Response.End();}}
}
  1. WinForm客户端代码
using System;
using System.IO;
using System.Net;
using System.Net.Sockets;
using System.Text;
using System.Threading;
using System.Windows.Forms;public class FileTransferService : IDisposable
{private TcpListener _listener;private const int Port = 11000;private bool _isRunning;public void Start(){_isRunning = true;_listener = new TcpListener(IPAddress.Loopback, Port);_listener.Start(10); // 允许10个等待连接BeginAcceptClient();}private void BeginAcceptClient(){if (_isRunning){_listener.BeginAcceptTcpClient(ClientHandler, null);}}private void ClientHandler(IAsyncResult ar){TcpClient client = null;try{client = _listener.EndAcceptTcpClient(ar);ThreadPool.QueueUserWorkItem(ProcessClient, client);}catch (Exception ex){client?.Dispose();MessageBox.Show($"接受连接错误: {ex.Message}");}finally{BeginAcceptClient(); // 继续监听新连接}}private void ProcessClient(object state){using (TcpClient client = (TcpClient)state){try{client.SendTimeout = 30000; // 30秒发送超时client.ReceiveTimeout = 30000; // 30秒接收超时using (NetworkStream netStream = client.GetStream()){// 1. 接收文件路径byte[] buffer = new byte[1024];int received = netStream.Read(buffer, 0, buffer.Length);string filePath = Encoding.UTF8.GetString(buffer, 0, received);// 2. 检查文件是否存在if (!File.Exists(filePath)){byte[] error = Encoding.UTF8.GetBytes("FILE_NOT_FOUND");netStream.Write(error, 0, error.Length);return;}// 3. 分块读取文件并传输using (FileStream fs = File.OpenRead(filePath)){byte[] fileBuffer = new byte[1024 * 1024]; // 1MB缓冲区int bytesRead;while ((bytesRead = fs.Read(fileBuffer, 0, fileBuffer.Length)) > 0){netStream.Write(fileBuffer, 0, bytesRead);}}}}catch (Exception ex){try{byte[] error = Encoding.UTF8.GetBytes($"ERROR:{ex.Message}");client.GetStream().Write(error, 0, error.Length);}catch { /* 忽略二次错误 */ }}}}public void Stop(){_isRunning = false;_listener?.Stop();}public void Dispose(){Stop();_listener?.Dispose();}
}
  1. WinForm界面
public partial class MainForm : Form
{private FileTransferService _fileService;public MainForm(){InitializeComponent();_fileService = new FileTransferService();_fileService.Start();}protected override void OnFormClosing(FormClosingEventArgs e){_fileService.Dispose();base.OnFormClosing(e);}private void btnStart_Click(object sender, EventArgs e){_fileService.Start();lblStatus.Text = "服务已启动 (端口:11000)";}private void btnStop_Click(object sender, EventArgs e){_fileService.Stop();lblStatus.Text = "服务已停止";}
}

Windows查看端口是否被占用

netstat -ano | findstr "端口号"

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。
如若转载,请注明出处:http://www.pswp.cn/news/917961.shtml
繁体地址,请注明出处:http://hk.pswp.cn/news/917961.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

目标检测数据集 - 眼睛瞳孔检测数据集下载「包含COCO、YOLO两种格式」

数据集介绍:眼睛瞳孔检测数据集,真实采集高质量人脸眼部图片数据,适用于人脸定位、人脸疾病如白内障等疾病的视觉检测。数据标注标签包括 eyepupil 瞳孔一 个缺陷类别;适用实际项目应用:眼睛瞳孔检测项目,以…

Keil MDK-ARM V5.42a 完整安装教程

文章目录一、安装前期准备二、Keil MDK-ARM 主程序安装三、器件支持包(Pack)安装四、许可证激活五、安装验证Keil MDK(Microcontroller Development Kit)是针对 Arm Cortex-M 系列微控制器的专业开发环境,集成了 μVis…

WPF中引用其他元素各种方法

在WPF中,引用其他元素的方式有多种,每种方式适用于不同场景,各有优缺点。除了x:Reference,常用的还有以下几种: 一、ElementName 绑定(最常用的XAML绑定方式) 通过元素的x:Name属性引用同一作用…

Python生成统计学公式

一元线性回归模型 2.1回归分析概述/25 一、回归分析基本概念/25 二、总体回归函数/27 三、随机误差项/29 四、样本回归函数/30 2.2 一元线性回归模型的参数估计/32 一、参数估计的普通最小二乘法/32 二、拟合优度/35 2.3基本假设与普通最小二乘估计量的统计性质/36 一、一元线性…

网络工程师--华为命令专题

一、交换机 交换机分类:1.根据交换方式划分:(1)存储转发式交换(Store and Forward)(2)直通式交换(Cut-through)(3)碎片过滤式交换&…

判断可编辑div的光标是否在最前面

要判断一个可编辑div(contenteditable)中的光标是否位于最前面,可以使用以下几种方法: 方法一:使用Selection和Range API function isCaretAtStart(div) {const selection window.getSelection();if (selection.rangeCount 0) return false…

【unity实战】使用Unity程序化生成3D随机地牢(附项目源码)

最终效果 文章目录最终效果前言1、理解程序生成的核心概念2、种子值的核心作用3、程序生成的实际应用4、主流程序生成技术概览5、选择合适的技术实战1、素材2、生成一面墙变换矩阵数据3、渲染墙壁4、加点随机不同的墙壁效果5、绘制四面墙壁4、在四个角落生成支柱5、生成地板6、…

多账号管理方案:解析一款免Root的App分身工具

之前有小伙伴问阿灿有没有可以软件分身的免费软件,后来阿灿找到了一款可以无限分身的app感觉很实用,只有10M大小 02软件介绍说白了它能给各种app和游戏做分身,包括V信、qQ、某音、某付宝这些,而且支持最新的安卓15系统。每个分身…

(附源码)基于PHP和Vue的网上购物平台

内容摘要 内容摘要: 随着互联网技术的迅猛发展,网上购物已成为人们日常生活的重要组成部分。本文围绕PHPVue技术栈构建的网上购物平台展开研究,深入探讨了该平台的架构设计与实现细节。平台前端采用Vue框架,利用其组件化开发和数据驱动的特性…

51单片机

中断系统1.什么是中断当CPU正在处理某件事的时候外界发生了紧急事件请求,要求CPU暂停当前的工作,转而去处理这个紧急事件,处理完以后,再回到原来被中断的地方,继续原来的工作,这样的过程称为中断2.为什么要…

前端开发:HTML(5)—— 表单

下面我们来学习表单。 目录 什么是Web表单? 表单标签 1.form标签 2.输入框 文本框和密码框 单选框和复选框 1.单选框 2.复选框 3.按钮 (1)普通按钮 (2)提交按钮 (3)重置按钮 &#…

【YOLOv8改进 - C2f融合】C2f融合SFS-Conv(空间 - 频率选择卷积)提升特征多样性,同时减少参数和计算量

YOLOv8目标检测创新改进与实战案例专栏 专栏目录: YOLOv8有效改进系列及项目实战目录 包含卷积,主干 注意力,检测头等创新机制 以及 各种目标检测分割项目实战案例 专栏链接: YOLOv8基础解析+创新改进+实战案例 文章目录 YOLOv8目标检测创新改进与实战案例专栏 介绍 摘要 文…

如何将照片从POCO手机传输到Mac电脑

将照片从POCO手机传输到Mac电脑可能会有些困难,因为与iPhone不同,POCO设备没有原生的macOS支持。这常常让用户寻找简单、有效的方法来移动图片,同时避免丢失质量,节省时间,并避免复杂的软件设置。如果你想知道如何将照…

最新教程 | CentOS 7 内网环境 Nginx + ECharts 页面离线部署手册(RPM 安装方式)

📁 一、准备阶段(在联网电脑上完成) 1.1 下载 Nginx 官方 RPM 安装包 在联网电脑浏览器中访问 Nginx 官方稳定版本仓库: 🔗 地址:http://nginx.org/packages/centos/7/x86_64/ ☁️云盘:htt…

Redis 常用数据类型 (下)

文章目录前言一 Hash 哈希1. Hash 相关命令hset 和 hgethexistshdelhkeyshvalshgetallhmgethlenhsetnxhincrbyincrbyfloat2. Hash 命令小结3. Hash 内部编码Hash 在缓存中的应用场景介绍缓存方式对比二、List 列表1. LIST总体介绍2. List 普通命令lpushlpushxrpushrpushxlrange…

Java Lambda表达式:简洁高效的函数式编程

1 lambda表达式Lambda 表达式本质是一个匿名函数,用于把函数作为参数,传入方法中,实现函数式编程风格。使用Lambda 表达式可以使代码变的更加简洁紧凑。语法格式:(parameters)-> expression 或 (parameters)->{ statements…

python中的集合

目录 初识集合 集合的含义 集合的作用 集合的使用场景 集合的定义 集合的常用操作 元素的增加 函数add() 元素的删除 函数remove() 函数clear() 函数pop() 集合的遍历 for循环 while循环 初识集合 集合的含义 在pyrhon中,集合是一种内置的数据结构…

如何将普通HTTP API接口改造为MCP服务器

在现代微服务架构中,MCP(Mesh Configuration Protocol) 作为高效配置分发协议,正逐渐替代传统HTTP API。本文将手把手教你如何将普通HTTP API升级为高性能MCP服务器。 为什么需要MCP? 传统HTTP API在配置分发场景存在…

数据结构第8问:什么是树?

树 【本节仅描述树的定义、术语以及相关性质】 定义 树是由若干个结点组成的有限集合。具有如下特征: 有且仅有一个根结点;除根结点外,每个其它结点有且仅有一个直接的父结点;除根结点外,每个结点可以有零个或者多个子…

PyTorch RNN 名字分类器

PyTorch RNN 名字分类器详解 使用PyTorch实现的字符级RNN(循环神经网络)项目,用于根据人名预测其所属的语言/国家。该模型通过学习不同语言名字的字符模式,够识别名字的语言起源。 环境设置 import torch import string import un…