IIS/ASP.NET访问共享文件夹的可用方式
【截止2014-10-14】
网上搜索了很多篇文章,所提及的总共有两种方式:
1.Asp.Net模拟登陆;
例如:
实战ASP.NET访问共享文件夹(含详细操作步骤)
实现一个2008serve的IIS的虚拟目录(通过网络路径(UNC)的形式,共享在另外一个2008服务器上
2.调用Windows API 的 WNetAddConnection2 、WNetCancelConnection2函数;
例如:
ASP.NET网络映射驱动器无权限访问的解决方案
ASP.NET访问网络驱动器(映射磁盘)
相对来说,第一种方式是最直接的,且改动较小的。但不足之处就是比较依赖共享所在服务器(如果切换共享服务器地址,那么本地的用户名和密码都要作调整。);
而第二种方式缺点(个人感觉),API函数的不稳定、链接数超出限制、内存泄露等不稳定的问题(如果有哪位朋友有解决方案,还请告知,谢谢)。
ps:折腾了两天,先用第一种方式吧。附上一个第二种方式的辅助类。
#define CheckReturn
using System;
using System.Collections.Generic;
using System.Text;
using System.Runtime.InteropServices; /// <summary>
/// 网络资源访问
/// </summary>
public class WNetConnectionHelper : IDisposable
{ /// <summary>
/// 添加远程网络连接。
/// </summary>
/// <param name="lpNetResource">是一个包含网络访问资源的结构,在这里作为参数用来指定详细的网络连接信息</param>
/// <param name="lpPassword">指出访问远程计算机的密码。在Windows 95/98/Me 系统中,该值必须设置为NULL或空字符串</param>
/// <param name="lpUsername">指出访问远程计算机的用户名。在Windows 95/98/Me 系统中,该值必须设置为NULL或空字符串</param>
/// <param name="dwFlags">指出连接选项,包含六种设置</param>
/// <returns>如果方法执行成功返回“NO_ERROR”即“0”。如果执行失败返回System Error Code。</returns>
[DllImport("Mpr.dll", EntryPoint = "WNetAddConnection2")]
/*
private static extern uint WNetAddConnection2(NetResource lpNetResource, [MarshalAs(UnmanagedType.LPStr)]string lpPassword, [MarshalAs(UnmanagedType.LPStr)]string lpUsername, uint dwFlags);
*/
private static extern uint WNetAddConnection2(IntPtr lpNetResource, string lpPassword, string lpUsername, uint dwFlags); /// <summary>
/// 释放存在的网络连接。
/// </summary>
/// <param name="lpName">指定本地驱动器或远程共享资源</param>
/// <param name="dwFlags">表示断开连接方式。设置 0 或CONNECT_UPDATE_PROFILE。</param>
/// <param name="fForce">如果当前正在使用远程资源,是否进行强制断开连接。如果设置FALSE,在有远程资源使用的情况下关闭连接操作将会失败。</param>
/// <returns>如果方法执行成功返回“NO_ERROR”即“0”。如果执行失败返回System Error Code。</returns>
[DllImport("Mpr.dll", EntryPoint = "WNetCancelConnection2")]
private static extern uint WNetCancelConnection2([MarshalAs(UnmanagedType.LPStr)]string lpName, uint dwFlags, int fForce); /// <summary>
/// 获取网络错误的扩展错误信息
/// </summary>
/// <param name="lpError">指定一个变量,用于装载网络错误代码。具体的代码由网络供应商决定</param>
/// <param name="lpErrorBuf">指定一个字串缓冲区,用于装载网络错误的说明</param>
/// <param name="nErrorBufSize">lpErrorBuf缓冲区包含的字符数量</param>
/// <param name="lpNameBuf">用于装载网络供应商名字的字串缓冲区</param>
/// <param name="nNameBufSize">lpNameBuf缓冲区的字符数量</param>
/// <returns></returns>
[DllImport("Mpr.dll", EntryPoint = "WNetGetLastError")]
private static extern uint WNetGetLastError(ref uint lpError, [MarshalAs(UnmanagedType.LPStr)]ref string lpErrorBuf, long nErrorBufSize, [MarshalAs(UnmanagedType.LPStr)]ref string lpNameBuf, uint nNameBufSize); [StructLayout(LayoutKind.Sequential, CharSet = CharSet.Ansi, Pack = )]
public struct NetResource
{
/// <summary>
/// 指定枚举范围。设置RESOURCE_CONNECTED,RESOURCE_GLOBALNET,RESOURCE_REMEMBERED三值之一。
/// </summary>
public int dwScope;
/// <summary>
/// 指定访问的资源类型。设置三个值之一。RESOURCETYPE_ANY表示所有资源;RESOURCETYPE_DISK表示磁盘资源;RESOURCETYPE_PRINT表示打印机。
/// </summary>
public int dwType;
/// <summary>
/// 指出资源显示类型。RESOURCEDISPLAYTYPE_DOMAIN;RESOURCEDISPLAYTYPE_SERVER;RESOURCEDISPLAYTYPE_SHARE;RESOURCEDISPLAYTYPE_GENERIC。
/// </summary>
public int dwDisplayType;
/// <summary>
/// 描述资源的使用方式。设置RESOURCEUSAGE_CONNECTABLE 或RESOURCEUSAGE_CONTAINER。
/// </summary>
public int dwUsage;
/// <summary>
/// 同dwScope关联,指定本地映射。
/// </summary>
//[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 256)]
public string lpLocalName;
/// <summary>
/// 远程访问文件夹路径。
/// </summary>
//[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 256)]
public string lpRemoteName;
/// <summary>
/// 描述。
/// </summary>
//[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 256)]
public string lpComment;
/// <summary>
/// 资源提供者,可以设置为NULL。
/// </summary>
//[MarshalAs(UnmanagedType.ByValTStr, SizeConst = 256)]
public string lpProvider;
} public enum RESOURCE_SCOPE
{
RESOURCE_CONNECTED = ,
RESOURCE_GLOBALNET = ,
RESOURCE_REMEMBERED = ,
RESOURCE_RECENT = ,
RESOURCE_CONTEXT =
} public enum RESOURCE_TYPE
{
RESOURCETYPE_ANY = ,
RESOURCETYPE_DISK = ,
RESOURCETYPE_PRINT = ,
RESOURCETYPE_RESERVED = ,
} public enum RESOURCE_USAGE
{
RESOURCEUSAGE_CONNECTABLE = ,
RESOURCEUSAGE_CONTAINER = ,
RESOURCEUSAGE_NOLOCALDEVICE = ,
RESOURCEUSAGE_SIBLING = ,
RESOURCEUSAGE_ATTACHED = ,
RESOURCEUSAGE_ALL = (RESOURCEUSAGE_CONNECTABLE | RESOURCEUSAGE_CONTAINER | RESOURCEUSAGE_ATTACHED),
} public enum RESOURCE_DISPLAYTYPE
{
RESOURCEDISPLAYTYPE_GENERIC = ,
RESOURCEDISPLAYTYPE_DOMAIN = ,
RESOURCEDISPLAYTYPE_SERVER = ,
RESOURCEDISPLAYTYPE_SHARE = ,
RESOURCEDISPLAYTYPE_FILE = ,
RESOURCEDISPLAYTYPE_GROUP = ,
RESOURCEDISPLAYTYPE_NETWORK = ,
RESOURCEDISPLAYTYPE_ROOT = ,
RESOURCEDISPLAYTYPE_SHAREADMIN = ,
RESOURCEDISPLAYTYPE_DIRECTORY = ,
RESOURCEDISPLAYTYPE_TREE = ,
RESOURCEDISPLAYTYPE_NDSCONTAINER =
} /// <summary>
/// 添加远程网络连接。
/// </summary>
/// <param name="netResource">是一个包含网络访问资源的结构,在这里作为参数用来指定详细的网络连接信息</param>
/// <param name="username">指出访问远程计算机的用户名。在Windows 95/98/Me 系统中,该值必须设置为NULL或空字符串</param>
/// <param name="password">指出访问远程计算机的密码。在Windows 95/98/Me 系统中,该值必须设置为NULL或空字符串</param>
/// <returns>如果方法执行成功返回“NO_ERROR”即“0”。如果执行失败返回System Error Code。</returns>
public static uint WNetAddConnection(NetResource netResource, string username, string password)
{
IntPtr ptr_netResource = IntPtr.Zero;
try
{
//分配内存
ptr_netResource = System.Runtime.InteropServices.Marshal.AllocHGlobal(System.Runtime.InteropServices.Marshal.SizeOf(netResource));
System.Runtime.InteropServices.Marshal.StructureToPtr(netResource, ptr_netResource, false); uint result = WNetAddConnection2(ptr_netResource, password, username, );
return result;
}
finally
{
if (ptr_netResource != IntPtr.Zero)
System.Runtime.InteropServices.Marshal.FreeCoTaskMem(ptr_netResource);
}
/*
uint result = WNetAddConnection2(netResource, password, username, 0);
return result;
*/
} /// <summary>
/// 添加远程网络连接。
/// </summary>
/// <param name="username">指出访问远程计算机的用户名。在Windows 95/98/Me 系统中,该值必须设置为NULL或空字符串</param>
/// <param name="password">指出访问远程计算机的密码。在Windows 95/98/Me 系统中,该值必须设置为NULL或空字符串</param>
/// <param name="remoteName">远程访问文件夹路径。</param>
/// <param name="localName">同dwScope关联,指定本地映射。</param>
/// <returns>如果方法执行成功返回“NO_ERROR”即“0”。如果执行失败返回System Error Code。</returns>
public static uint WNetAddConnection(string username, string password, string remoteName, string localName)
{
NetResource netResource = new NetResource();
netResource.dwScope = ; //RESOURCE_GLOBALNET
netResource.dwType = ; //RESOURCETYPE_DISK
netResource.dwDisplayType = ; //RESOURCEDISPLAYTYPE_SHARE
netResource.dwUsage = ; //RESOURCEUSAGE_CONNECTABLE
netResource.lpLocalName = localName;
netResource.lpRemoteName = remoteName.TrimEnd('/');
//netResource.lpRemoteName = lpComment;
//netResource.lpProvider = null;
uint result = WNetAddConnection(netResource, username, password);
return result;
} /// <summary>
/// 添加远程网络连接。
/// </summary>
/// <param name="name">指定本地驱动器或远程共享资源</param>
/// <param name="flags">表示断开连接方式。设置 0 或CONNECT_UPDATE_PROFILE。</param>
/// <param name="force">如果当前正在使用远程资源,是否进行强制断开连接。如果设置FALSE,在有远程资源使用的情况下关闭连接操作将会失败。</param>
/// <returns>如果方法执行成功返回“NO_ERROR”即“0”。如果执行失败返回System Error Code。</returns>
public static uint WNetCancelConnection(string name, uint flags, bool force)
{
uint nret = WNetCancelConnection2(name, flags, force ? : );
return nret;
} #region SelfUsing
bool connectSuccess = false;
string username, password, remoteName, localName;
private WNetConnectionHelper(string username, string password, string remoteName, string localName)
{
this.username = username;
this.password = password;
this.remoteName = remoteName;
this.localName = localName;
Close();
var code = WNetAddConnection(username, password, remoteName, localName);
connectSuccess = code == ;
#if CheckReturn if (code != )
{
GetLastError(); throw new InvalidOperationException("The method WNetAddConnection return " + code);
}
#endif
} private static void GetLastError()
{
uint lpError = ;
string lpErrorBuf = null;
uint nErrorBufSize = ;
string lpNameBuf = null;
uint nNameBufSize = ;
var errCode = WNetGetLastError(ref lpError, ref lpErrorBuf, nErrorBufSize, ref lpNameBuf, nNameBufSize);
} public static WNetConnectionHelper New(string username, string password, string remoteName, string localName)
{
if (string.IsNullOrEmpty(remoteName))
throw new ArgumentException("remoteName");
return new WNetConnectionHelper(username, password, remoteName.TrimEnd('/'), localName);
} #endregion #region IDisposable 成员 public void Dispose()
{
if (!connectSuccess) return;
if (string.IsNullOrEmpty(remoteName)) return;
var code = Close();
#if CheckReturn
if (code != )
{
GetLastError();
throw new InvalidOperationException("The method WNetCancelConnection return " + code); }
#endif
} private uint Close()
{ return WNetCancelConnection(remoteName, , true);
} #endregion
}
IIS/ASP.NET访问共享文件夹的可用方式的更多相关文章
- 实战ASP.NET访问共享文件夹(含详细操作步骤)
博客园找找看(http://zzk.cnblogs.com)的索引文件占用空间太大,需要移至另外一台服务器,所以要解决"在ASP.NET中通过共享文件夹访问索引文件"的问题. 假设 ...
- ASP.NET 访问共享文件夹
配置代码: var dataProtection = new Microsoft.AspNet.DataProtection.DataProtectionProvider(new DirectoryI ...
- (转)WIN7更改用户名访问共享文件夹
原文地址: http://ryy8013.blog.163.com/blog/static/71729589201210610533778/ 一直以来,windows7客户端访问windows ser ...
- PC问题-可以PING通IP,PING名字不通,可以远程,但不能访问共享文件夹?
问题现象:可以PING通IP,PING名字不通,可以远程,但不能访问共享文件夹? 问题原因:目标主机中NetLogon服务未启动. 问题处理:远程打开目标主机,“我的电脑-管理-服务-启动(改为自动) ...
- VirtualBox中的Ubuntu没有权限访问共享文件夹/media/sf_bak
之前已经搞定可以自动共享文件夹了,但是现在发现无法去访问,非root用户下,使用“ls /media/sf_bak”提示没有权限,当然如果切换到root,是可以的. [解决过程]1.把普通用户名加入到 ...
- 清除在Windows下访问共享文件夹时的登录信息
清除在Windows下访问共享文件夹时的登录信息 在实际工作中,经常需要访问局域网内其他机子上的共享文件夹,例如\\192.168.1.100\d$ , 首次访问时,需要输入用户名和密码才可以进入,即 ...
- IIS Asp.Net 访问 Com组件 报拒绝访问
IIS Asp.Net 访问 Com组件 报拒绝访问 解决方法: IIS 程序池->高级设置->进程模式->标识->内置帐户=LocalSystem
- [转]Win10企业版无法访问共享文件夹
Win10系统电脑在更新后,当我们访问共享文件夹时可能会出现如下图所示窗口,导致我们无法访问.那么这个问题如何解决呢?具体如下:1. 首先我们按“Windows+R键”打开运行窗口.2. 在该窗口文本 ...
- 第一篇-ubuntu18.04访问共享文件夹
1. 在访问Windows共享资料之前,请确保Windows共享是可用的.Linux访问Windows共享或者LInux共享资料给Windows时,都使用Samba软件 rpm -qa | grep ...
随机推荐
- U3D调用7z解压文件
using UnityEngine; using System; using System.IO; using System.Diagnostics; public class Test : Mono ...
- C++易混淆知识点整理
// 1 /////////////////////////////////////////////////////////////////////// // 常量指针:,指针可修改,变量不可修改(只 ...
- 《MySQL》一次MySQL慢查询导致的故障
本文转载自 http://www.jb51.net/article/70955.htm 我们知道分析MySQL语句查询性能的方法除了使用EXPLAIN 输出执行计划,还可以让MySQL记录下查询超过指 ...
- JSP中的动态包含和静态包含的区别
本文转载自http://blog.csdn.net/xuxu198899223/article/details/8501044 1. 语法格式 (1)静态包含:<%@ include file= ...
- EXCEL数据匹配:The 'Microsoft.Jet.Oledb.4.0' provider is not registered on the local machin
百度的处理结果: 作者:LisenYang http://blog.csdn.net/lisenyang/article/details/52106492 这篇博文里面说的,默认设置修改[启动32应用 ...
- C#后台传入数据JS接收
今天碰到个问题,就是后台传入的数据,在JS中for循环的时候,下面那个j根本就不会往上加.所以只能将后台传入的对象,转换为json格式,由js进行解析后生成js中的对象 @{j=0;} for (va ...
- 【面试题】100IT名企java面试必考面试题
一.Java 基础部分 1. JAVA 的基本数据类型有哪些 ? String 是不是基本数据类型 ? Java 有 8 种基本数据类型: byte int ...
- Delphi应用程序的调试(一)
集成式调试器是Delphi IDE的一个重要特性.该调试器使用户能方便地设置断点.监视变量.检查对象等等.在运行程序时,使用该调试器能快速查找出程序发生了什么(或未发生什么).一个号的调试器对程序开发 ...
- Kotlin 资料
https://kotlinlang.org/docs/reference/ 官方 https://github.com/JetBrains/kotlin/releases Kotlin SDK ...
- Elasticsearch学习之深入搜索二 --- 搜索底层原理剖析
1. 普通match如何转换为term+should { "match": { "title": "java elasticsearch"} ...