
You can implement SharePoint documents in your AngularJS applications much easier when you create your code in a Visual Studio LightSwitch Cloud Business app. Essentially we will make a SharePoint CSOM call to create a Word Document in an associated SharePoint list when we create a new task in our SharePoint Provider Hosted application.
The Application

We start with the application created in AngularJS Posting To SharePoint Newsfeed Using Visual Studio LightSwitch.
We add tasks using the add new button and then click Save.

After the task is saved, we can click on the task in the list to edit it.

We will see that a Microsoft Word Document has been created and attached to the task.
We can click on either the Direct Link or the Inline Edit link to open the document.

If we click on the Inline Edit link, the document will open in Word Online in Office 365.
Creating The Application

We start with the application created in AngularJS Posting To SharePoint Newsfeed Using Visual Studio LightSwitch.

This project is based on the application created in the article An End-to-End AngularJS SharePoint Module using LightSwitch OData as a Back-End.
Add References

First, to provide the functionality to programmatically create Word documents, install the Open XML SDK for Microsoft Office (OpenXMLSDKV25.msi) from this link.

Add a reference to DocumentFormat.OpenXml…

…and WindowsBase.

In the Properties for DocumentFormat.OpenXml, ensure you set Copy Local to True so that it will be deployed when you deploy the application to production.
Update the ToDo Table

Open the ToDo table and create a field called TaskID.
We will use this field later to connect this table to the SharePoint Document Library.
Connect LightSwitch To SharePoint Document Library

We will now follow the instructions in the article: Implementing Documents in a SharePoint 2013 Cloud Business App (LightSwitch) to connect the project to the SharePoint Document Library.

First, we need to create a SharePoint Document Library List.
Log into your SharePoint Development site, and click add an app under Site Contents.

Add a Document Library.

Call it TaskDocuments.

After the list is added to the list of apps in Site Contents, select the SETTINGS.
We now need to add a column (TaskID) to allow us to associate a Document to a Task.

In the Settings, select Create column.

Call the column TaskID and set its type to Single line of text.
This is so that each document can be associated with a Task in the application.
Click OK.
Connect To The Document Library

In Visual Studio, right-click on Data Sources and select Add Data Source.

Select SharePoint.

Enter the address of your Development SharePoint server.

You may have to log in.

Select the TaskDocuments from Document Libraries, and UserInformationList from Lists.

The lists will show in the project.

- Open the TaskDocument table and click the Relationship button.
- Select ToDo as the To table and set the Multiplicity to Many to One.
- Set TaskID as the Primary and Foreign keys.
- Click OK.

The relationship will show.
Creating The Word Document

Next, we open the ToDo table and select the _Inserting method.
We add the following code to the end of the method:
entity.TaskID = System.Guid.NewGuid().ToString();
var clientContext =
this.Application.SharePoint.GetHostWebClientContext();
Microsoft.SharePoint.Client.Web web = clientContext.Web;
clientContext.Load(web);
clientContext.ExecuteQuery();
Microsoft.SharePoint.Client.WebCollection webs = web.Webs;
clientContext.Load<Microsoft.SharePoint.Client.WebCollection>(webs);
clientContext.ExecuteQuery();
Microsoft.SharePoint.Client.ListCollection Lists = web.Lists;
clientContext.Load<Microsoft.SharePoint.Client.ListCollection>(Lists);
clientContext.ExecuteQuery();
Microsoft.SharePoint.Client.List TaskDocumentsLibrary =
Lists.GetByTitle("TaskDocuments");
Microsoft.SharePoint.Client.Folder destintationFolder =
TaskDocumentsLibrary.RootFolder;
clientContext.Load(destintationFolder);
clientContext.ExecuteQuery();
using (WordprocessingDocument wordDocument =
WordprocessingDocument.Create(
HttpContext.Current.Server.MapPath("~/LocalOOXMLDocument.docx"),
WordprocessingDocumentType.Document))
{
MainDocumentPart mainPart = wordDocument.AddMainDocumentPart();
mainPart.Document = new Document();
Body body = mainPart.Document.AppendChild(new Body());
Paragraph para = body.AppendChild(new Paragraph());
Run run = para.AppendChild(new Run());
run.AppendChild(
new Text(
String.Format("Here's some text for {0}",entity.TaskName)
));
}
FileStream fs = null;
byte[] documentBytes;
fs = System.IO.File.OpenRead(
HttpContext.Current.Server.MapPath("~/LocalOOXMLDocument.docx"));
documentBytes = new byte[fs.Length];
fs.Read(documentBytes, 0, Convert.ToInt32(fs.Length));
Microsoft.SharePoint.Client.FileCreationInformation ooxmlFile
= new Microsoft.SharePoint.Client.FileCreationInformation();
ooxmlFile.Overwrite = true;
ooxmlFile.Url = clientContext.Url
+ destintationFolder.Name
+ "/" + entity.TaskName + ".docx";
ooxmlFile.Content = documentBytes;
Microsoft.SharePoint.Client.File newFile = TaskDocumentsLibrary.RootFolder.Files.Add(ooxmlFile);
clientContext.Load(newFile);
clientContext.ExecuteQuery();
Microsoft.SharePoint.Client.ListItem listItem = newFile.ListItemAllFields;
listItem["TaskID"] = entity.TaskID;
listItem.Update();
clientContext.ExecuteQuery();
You will need to add the following Using statements to the top of the class:
using System.IO;
using Microsoft.SharePoint.Client;
using System.Web;
using DocumentFormat.OpenXml;
using DocumentFormat.OpenXml.Packaging;
using DocumentFormat.OpenXml.Wordprocessing;
Update the AngularJS Application

Open the JayDataCRUD.js file and update the Angular controller with the following code:
$scope.TaskDocuments = [];
$data.initService('/SharePointDocuments.svc').then(function (SharePointDocuments) {
$scope.SharePointDocuments = SharePointDocuments;
$scope.TaskDocuments = SharePointDocuments.TaskDocuments.toLiveArray();
});
Object.defineProperty($scope, "colTaskDocument", {
get: function () {
if ($scope.selectedToDo)
return $scope.SharePointDocuments
.TaskDocuments
.filter('TaskID',
'==',
$scope.selectedToDo.TaskID)
.toLiveArray();
}
});

Open the JayDataCRUD.aspx file and update the markup with the following code:
<table>
<tr data-ng-repeat="TaskDocument in colTaskDocument">
<td>
{{TaskDocument.Name}}
</td>
</tr>
</table>

We can now run the application…

We can create a new task and then click on it to edit it.
We see that an associated Word document has been created and its name will display.

When we go directly to the SharePoint TaskDocument list, we see the Word document can be viewed.
Link To The SharePoint Document From AngularJS

If we navigate directly to the LightSwitch OData feed that it automatically creates for the SharePoint TaskDocuments list (when we connect to it in LightSwitch), we see that it exposes a direct link to the Word document (don’t worry a user still has to be authenticated to get to it).
We can use this property to provide a link to the document in our AngularJS application.
First we add the following filter to the JayDataCRUD.js file (place under var app = angular.module('app', ['jaydata']):
app.filter('WordViewer', function () {
return function (DocumentURL, DocumentName) {
var a = document.createElement('a');
a.href = DocumentURL;
return 'https://'
+ a.hostname
+ '/_layouts/15/WopiFrame.aspx?sourcedoc='
+ DocumentURL
+ '&file='
+ DocumentName
+ '&action=default';
};
});
Next, we update the markup in the JayDataCRUD.aspx file to consume the filter:
<table>
<tr data-ng-repeat="TaskDocument in colTaskDocument">
<td>
{{TaskDocument.Name}}
<a href="{{TaskDocument.Microsoft_LightSwitch_ReadLink}}">[Direct Link]</a>
<a href="{{ TaskDocument.Microsoft_LightSwitch_ReadLink | WordViewer : TaskDocument.Name }}">
[Inline Edit]</a>
</td>
</tr>
</table>

When we run the application, we now have a direct link and a inline edit link to the associated Word document.
Links
SharePoint 2013: Create Word documents using OOXML in apps for SharePoint
Link to open in browser with Office Web Apps
Welcome to the Open XML SDK 2.5 for Office
Links – LightSwitch Help Website
AngularJS Posting To SharePoint Newsfeed Using Visual Studio LightSwitch
An End-to-End AngularJS SharePoint Module using LightSwitch OData as a Back-End
Deploy A LightSwitch Application To Office 365 / SharePoint Online
Exploring SharePoint 2013 Visual Studio Cloud Business Apps (LightSwitch)
Implementing Documents in a SharePoint 2013 Cloud Business App (LightSwitch)
Creating A SharePoint Online Testing Site
Creating A LightSwitch SharePoint 2013 Multi-Tenant Provider-Hosted Application