2017-08-16 2 views
0

Je dois déplacer beaucoup de pièces jointes de plusieurs listes dans SharePoint vers une table BLOB dans SQL. J'ai trouvé du code qui me permet de télécharger les pièces jointes sur mon disque local, mais je n'ai pas été capable de le modifier pour le charger en tant que données binaires directement dans SharePoint.Migration des pièces jointes de SP vers SQL BLOB

using Microsoft.SharePoint.Client; 
using System; 
using System.IO; 
using System.Net; 
using System.Windows.Forms; 
using System.Data; 
using Microsoft.SqlServer.Dts.Pipeline.Wrapper; 
using Microsoft.SqlServer.Dts.Runtime.Wrapper; 
[Microsoft.SqlServer.Dts.Pipeline.SSISScriptComponentEntryPointAttribute] 
public class ScriptMain : UserComponent 
{ 
    public override void CreateNewOutputRows() 
    { 
    try 
    { 
     int startListID = 1; 

     String siteUrl = "https://mysharepointsite.com/sites/mysite"; 
     String listName = "AttachmentTesting"; 
     NetworkCredential credentials = 
        new NetworkCredential("username", "password", "domain"); 

     using (ClientContext clientContext = new ClientContext(siteUrl)) 
     { 
      clientContext.Credentials = credentials; 

      //Get the Site Collection 
      Site oSite = clientContext.Site; 
      clientContext.Load(oSite); 
      clientContext.ExecuteQuery(); 

      // Get the Web 
      Web oWeb = clientContext.Web; 
      clientContext.Load(oWeb); 
      clientContext.ExecuteQuery(); 

      CamlQuery query = new CamlQuery(); 
      query.ViewXml = @""; 

      List oList = clientContext.Web.Lists.GetByTitle(listName); 
      clientContext.Load(oList); 
      clientContext.ExecuteQuery(); 

      ListItemCollection items = oList.GetItems(query); 
      clientContext.Load(items); 
      clientContext.ExecuteQuery(); 

      foreach (ListItem listItem in items) 
      { 
       if (Int32.Parse(listItem["ID"].ToString()) >= startListID) 
       { 

        Folder folder = 
          oWeb.GetFolderByServerRelativeUrl(oSite.Url + 
          "/Lists/" + listName + "/Attachments/" + 

          listItem["ID"]); 

        clientContext.Load(folder); 

        try 
        { 
         clientContext.ExecuteQuery(); 
        } 
        catch (ServerException ex) 
        { 
        } 

        FileCollection attachments = folder.Files; 
        clientContext.Load(attachments); 
        clientContext.ExecuteQuery(); 

        foreach (Microsoft.SharePoint.Client.File oFile in folder.Files) 
        { 
         FileInfo myFileinfo = new FileInfo(oFile.Name); 
         WebClient client1 = new WebClient(); 
         client1.Credentials = credentials; 

         byte[] fileContents = 
           client1.DownloadData("https://mysharepointsite.com" + 
           oFile.ServerRelativeUrl); 

        } 
       } 
      } 

     } 
    } 
    catch (Exception e) 
    { 
    } 
} 
} 

Le flux de fichiers à la fin sert uniquement à tester l'ancien code, et il récupère les pièces jointes avec succès. Maintenant, je dois passer à l'étape suivante et la charger dans une sorte de tampon pour pousser dans SQL. Je l'ai essayé d'utiliser:

Output0Buffer.AddRow(); 
Output0Buffer.fileName = oFile.Name; 

intérieur de la boucle et Output0Buffer.SetEndOfRowset(); à la fin, mais cela donne une erreur:

[Import Column [2]] Error: SSIS Error Code DTS_E_INDUCEDTRANSFORMFAILUREONERROR. The "Import Column" failed because error code 0xC02090BB occurred, and the error row disposition on "Import Column.Inputs[Import Column Input].Columns[fileName]" specifies failure on error. An error occurred on the specified object of the specified component. There may be error messages posted before this with more information about the failure. 

Comment dois-je faire la dernière étape de pousser mon tableau d'octets fileContents dans ma table SQL colonne blob? Merci beaucoup.

EDIT: J'aurais dû omettre le fstream. C'était juste à des fins de test. Ce que j'essaye de faire est de pousser la pièce jointe directement de SharePoint à SQL sans l'étape intermédiaire de le stocker sur mon local.

Répondre

0

Résolu!

Merci à tinamou pour leur réponse, mais j'aurais dû mentionner que j'essayais d'éviter l'étape intermédiaire de placer les fichiers sur un disque local. Je l'ai résolu en ajoutant une autre sortie au composant de script, nommé "fileBinary", et en utilisant la méthode AddBlobData pour le remplir avec mon tableau d'octets.

byte[] fileContents = client1.DownloadData("https://mysharepointsite.com/sites/mysite" + 
           oFile.ServerRelativeUrl); 

Output0Buffer.AddRow(); 
Output0Buffer.fileName = oFile.Name; 
Output0Buffer.fileBinary.AddBlobData(fileContents); 

puis en dehors de ma boucles FOR (également suggérée par tinamou):

Output0Buffer.SetEndOfRowset(); 
0

Vous devez utiliser votre chemin depuis le lecteur local.

string path = "C:\\Temp\\" + oFile.Name; 
FileStream fStream = new FileStream(path, FileMode.Create); 

fStream.Write(fileContents, 0, fileContents.Length); 
fStream.Close(); 

Output0Buffer.AddRow(); 
Output0Buffer.fileName = path; 

// ... after foreach loop 
Output0Buffer.SetEndOfRowset();