2013-02-07 238 views
1

時需要模擬當我試圖從本地訪問網絡驅動器文件的工作正常,但是當我部署的代碼,我在System.IO .__ Error.WinIOError越來越波紋錯誤訪問共享網絡驅動器

(的Int32的errorCode,字符串maybeFullPath)

在System.IO.FileStream.Init(字符串路徑,模式的FileMode,FileAccess的訪問,的Int32權利,布爾useRights,文件共享份額,緩衝區大小的Int32,FileOptions選項,SECURITY_ATTRIBUTES secAttrs,字符串MSGPATH,布爾bFromProxy )

at System.IO.File Stream..ctor(字符串路徑,的FileMode模式,FileAccess的訪問,文件共享份額)

在System.Web.HttpResponse.WriteFile(字符串文件名,布爾readIntoMemory)

在System.Web.HttpResponse.WriteFile(字符串文件名)

在Configs.gvConfigs_RowCommand(對象發件人,GridViewCommandEventArgs e)如C:\用戶\ bpucha1103c \桌面\ CellBackHaul_Publish \ Configs.aspx.cs:線59 2013年2月5日13:31:21412 [19 ]警告System.Web.UI.Page [(null)] - 日誌記錄:System.IO.IOException:使用的帳戶是計算機帳戶。使用您的全局用戶帳戶或本地用戶帳戶來訪問此服務器。

如何在訪問網絡共享文件夾中的文件時進行模擬操作?下面是我的代碼

GridViewRow rw = (GridViewRow)(((LinkButton)e.CommandSource).NamingContainer); 
LinkButton lnkTxtFile = (LinkButton)rw.FindControl("lnkTxtFile"); 
string strFilename = lnkTxtFile.Text.Replace("/","\\"); 
System.IO.FileInfo targetFile = new System.IO.FileInfo(strFilename); 
Response.Clear(); 
Response.AddHeader("Content-Disposition", "attachment; filename=" + targetFile.Name); 
Response.ContentType = "application/octet-stream"; 
Response.WriteFile(targetFile.FullName); 
//HttpContext.Current.ApplicationInstance.CompleteRequest(); 
Response.End(); 

這裏是我修改後的代碼

GridViewRow rw = (GridViewRow)(((LinkButton)e.CommandSource).NamingContainer); 
LinkButton lnkTxtFile = (LinkButton)rw.FindControl("lnkTxtFile"); 
string strFilename = lnkTxtFile.Text.Replace("/", "\\"); 
System.IO.FileInfo targetFile = new System.IO.FileInfo(strFilename); 
RunOperationAsUser(() => 
{ 
    //GridViewRow rw = (GridViewRow)(((LinkButton)e.CommandSource).NamingContainer); 
    //LinkButton lnkTxtFile = (LinkButton)rw.FindControl("lnkTxtFile"); 
    //string strFilename = lnkTxtFile.Text.Replace("/", "\\"); 
    //System.IO.FileInfo targetFile = new System.IO.FileInfo(strFilename); 
    Response.Clear(); 
    Response.AddHeader("Content-Disposition", "attachment; filename=" + targetFile.Name); 
    Response.ContentType = "application/octet-stream"; 
    Response.WriteFile(targetFile.FullName); 
    //HttpContext.Current.ApplicationInstance.CompleteRequest(); 
    Response.End(); 
}, "bpucha1103c", targetFile.DirectoryName , "White1234"); 
+0

可能的重複e [從C#訪問遠程目錄](http://stackoverflow.com/questions/5433570/access-a-remote-directory-from-c-sharp) –

+0

@DanielHilgarth - 我可以下載該文件的第一次..當我第二次嘗試時,出現錯誤,例如「不允許同一用戶使用多個用戶名連接到服務器或共享資源。斷開以前連接到服務器或共享資源的所有連接,然後再次嘗試「....即使我在處理連接後下載其不工作.. – Srav

+0

您使用的是哪一個代碼?來自其他問題的鏈接? –

回答

6

您可以嘗試使用下面的代碼來冒充其他用戶身份和執行的操作:

[DllImport("advapi32.dll", SetLastError = true)] 
private static extern bool LogonUser(string lpszUsername, string lpszDomain, string lpszPassword, int dwLogonType, int dwLogonProvider, ref IntPtr phToken); 
[DllImport("advapi32.dll", CharSet = CharSet.Auto, SetLastError = true)] 
public extern static bool DuplicateToken(IntPtr existingTokenHandle, int impersonationLevel, ref IntPtr duplicateTokenHandle); 
[DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)] 
private static extern bool CloseHandle(IntPtr handle); 
[DllImport("advapi32.dll", CharSet = CharSet.Auto, SetLastError = true)] 
public static extern bool RevertToSelf(); 
[DllImport("userenv.dll", SetLastError = true, CharSet = CharSet.Auto)] 
public static extern bool LoadUserProfile(IntPtr hToken, ref ProfileInfo lpProfileInfo); 

[DllImport("Userenv.dll", CallingConvention = 
    CallingConvention.Winapi, SetLastError = true, CharSet = CharSet.Auto)] 
public static extern bool UnloadUserProfile 
    (IntPtr hToken, IntPtr lpProfileInfo); 

[DllImport("ole32.dll")] 
public static extern int CoInitializeSecurity(IntPtr pVoid, int 
    cAuthSvc, IntPtr asAuthSvc, IntPtr pReserved1, RpcAuthnLevel level, 
    RpcImpLevel impers, IntPtr pAuthList, EoAuthnCap dwCapabilities, IntPtr 
    pReserved3); 

[StructLayout(LayoutKind.Sequential)] 
public struct ProfileInfo 
{ 
    /// 
    /// Specifies the size of the structure, in bytes. 
    /// 
    public int dwSize; 

    /// 
    /// This member can be one of the following flags: 
    /// PI_NOUI or PI_APPLYPOLICY 
    /// 
    public int dwFlags; 

    /// 
    /// Pointer to the name of the user. 
    /// This member is used as the base name of the directory 
    /// in which to store a new profile. 
    /// 
    public string lpUserName; 

    /// 
    /// Pointer to the roaming user profile path. 
    /// If the user does not have a roaming profile, this member can be NULL. 
    /// 
    public string lpProfilePath; 

    /// 
    /// Pointer to the default user profile path. This member can be NULL. 
    /// 
    public string lpDefaultPath; 

    /// 
    /// Pointer to the name of the validating domain controller, in NetBIOS format. 
    /// If this member is NULL, the Windows NT 4.0-style policy will not be applied. 
    /// 
    public string lpServerName; 

    /// 
    /// Pointer to the path of the Windows NT 4.0-style policy file. 
    /// This member can be NULL. 
    /// 
    public string lpPolicyPath; 

    /// 
    /// Handle to the HKEY_CURRENT_USER registry key. 
    /// 
    public IntPtr hProfile; 
} 

public enum RpcAuthnLevel 
{ 
    Default = 0, 
    None = 1, 
    Connect = 2, 
    Call = 3, 
    Pkt = 4, 
    PktIntegrity = 5, 
    PktPrivacy = 6 
} 

public enum RpcImpLevel 
{ 
    Default = 0, 
    Anonymous = 1, 
    Identify = 2, 
    Impersonate = 3, 
    Delegate = 4 
} 

public enum EoAuthnCap 
{ 
    None = 0x00, 
    MutualAuth = 0x01, 
    StaticCloaking = 0x20, 
    DynamicCloaking = 0x40, 
    AnyAuthority = 0x80, 
    MakeFullSIC = 0x100, 
    Default = 0x800, 
    SecureRefs = 0x02, 
    AccessControl = 0x04, 
    AppID = 0x08, 
    Dynamic = 0x10, 
    RequireFullSIC = 0x200, 
    AutoImpersonate = 0x400, 
    NoCustomMarshal = 0x2000, 
    DisableAAA = 0x1000 
} 

const int LOGON32_PROVIDER_DEFAULT = 0; 
const int LOGON32_LOGON_NEW_CREDENTIALS = 9; 
const int SECURITY_IMPERSONATION_LEVEL = 2; 

public void RunOperationAsUser(Action operation, string userName, string domain, string password) 
{ 
    IntPtr token = IntPtr.Zero; 
    IntPtr dupToken = IntPtr.Zero; 

    //Impersonate the user 
    if (LogonUser(userName, domain, password, LOGON32_LOGON_NEW_CREDENTIALS, LOGON32_PROVIDER_DEFAULT, ref token)) 
    { 
     if (DuplicateToken(token, SECURITY_IMPERSONATION_LEVEL, ref dupToken)) 
     { 

      WindowsIdentity newIdentity = new WindowsIdentity(dupToken); 
      WindowsImpersonationContext impersonatedUser = newIdentity.Impersonate(); 

      int retCode = CoInitializeSecurity(IntPtr.Zero, -1, IntPtr.Zero, IntPtr.Zero, 
       RpcAuthnLevel.PktPrivacy, RpcImpLevel.Impersonate, IntPtr.Zero, EoAuthnCap.DynamicCloaking, IntPtr.Zero); 

      if (impersonatedUser != null) 
      { 
       var username = WindowsIdentity.GetCurrent(TokenAccessLevels.MaximumAllowed).Name; 
       var sid = WindowsIdentity.GetCurrent(TokenAccessLevels.MaximumAllowed).User.Value; 

       ProfileInfo profileInfo = new ProfileInfo(); 
       profileInfo.dwSize = Marshal.SizeOf(profileInfo); 
       profileInfo.lpUserName = userName; 
       profileInfo.dwFlags = 1; 

       Boolean loadSuccess = LoadUserProfile(dupToken, ref profileInfo); 
      } 

      operation(); 

      impersonatedUser.Undo(); 
     } 
    } 
    if (token != IntPtr.Zero) 
    { 
     CloseHandle(token); 
    } 
    if (dupToken != IntPtr.Zero) 
    { 
     try 
     { 
      CloseHandle(token); 
     } 
     catch 
     { } 
    } 
} 

現在你可以做

RunOperationAsUser(() => { 
    GridViewRow rw = (GridViewRow)(((LinkButton)e.CommandSource).NamingContainer); 
    LinkButton lnkTxtFile = (LinkButton)rw.FindControl("lnkTxtFile"); 
    string strFilename = lnkTxtFile.Text.Replace("/","\\"); 
    System.IO.FileInfo targetFile = new System.IO.FileInfo(strFilename); 
    Response.Clear(); 
    Response.AddHeader("Content-Disposition", "attachment; filename=" + targetFile.Name); 
    Response.ContentType = "application/octet-stream"; 
    Response.WriteFile(targetFile.FullName); 
    //HttpContext.Current.ApplicationInstance.CompleteRequest(); 
    Response.End(); 
}, userName, domain, password) 
+0

像LogonUser,DuplicateToken的方法怎麼樣?我需要指定什麼? – Srav

+0

Ups,對不起,這些是一些DllImport你需要引用 –

+0

你可以哪些DLL我需要像LogonUser,DuplicateToken等方法的參考 – Srav