Skip to content
Permalink
Browse files

Added the elevated privileges sample (#38)

  • Loading branch information...
waldekmastykarz authored and VesaJuvonen committed Oct 12, 2016
1 parent 749ea4a commit f3fcf61f843c8c46514a4cefddae6adc5cf0c794
Showing with 30,901 additions and 0 deletions.
  1. +96 −0 samples/react-sp-elevatedprivileges/README.md
  2. +22 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges.sln
  3. +9 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/App_Start/FilterConfig.cs
  4. +15 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/App_Start/WebApiConfig.cs
  5. +31 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/Controllers/ItemsController.cs
  6. +32 −0 ...-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/Filters/SharePointContextFilterAttribute.cs
  7. +1 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/Global.asax
  8. +12 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/Global.asax.cs
  9. +35 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/Properties/AssemblyInfo.cs
  10. +924 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/SharePointContext.cs
  11. +1,223 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/TokenHelper.cs
  12. +30 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/Web.Debug.config
  13. +31 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/Web.Release.config
  14. +71 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/Web.config
  15. BIN samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/favicon.ico
  16. +32 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/packages.config
  17. +295 −0 samples/react-sp-elevatedprivileges/api/pnp.api.elevatedprivileges/pnp.api.elevatedprivileges.csproj
  18. BIN samples/react-sp-elevatedprivileges/assets/preview.png
  19. +25 −0 samples/react-sp-elevatedprivileges/webpart/.editorconfig
  20. +1 −0 samples/react-sp-elevatedprivileges/webpart/.gitattributes
  21. +32 −0 samples/react-sp-elevatedprivileges/webpart/.gitignore
  22. +14 −0 samples/react-sp-elevatedprivileges/webpart/.npmignore
  23. +21 −0 samples/react-sp-elevatedprivileges/webpart/.vscode/settings.json
  24. +34 −0 samples/react-sp-elevatedprivileges/webpart/.vscode/tasks.json
  25. +7 −0 samples/react-sp-elevatedprivileges/webpart/.yo-rc.json
  26. +21 −0 samples/react-sp-elevatedprivileges/webpart/config/config.json
  27. +6 −0 samples/react-sp-elevatedprivileges/webpart/config/deploy-azure-storage.json
  28. +10 −0 samples/react-sp-elevatedprivileges/webpart/config/package-solution.json
  29. +3 −0 samples/react-sp-elevatedprivileges/webpart/config/prepare-deploy.json
  30. +9 −0 samples/react-sp-elevatedprivileges/webpart/config/serve.json
  31. +51 −0 samples/react-sp-elevatedprivileges/webpart/config/tslint.json
  32. +3 −0 samples/react-sp-elevatedprivileges/webpart/config/write-manifests.json
  33. +6 −0 samples/react-sp-elevatedprivileges/webpart/gulpfile.js
  34. +26 −0 samples/react-sp-elevatedprivileges/webpart/package.json
  35. +86 −0 samples/react-sp-elevatedprivileges/webpart/react-sp-elevatedprivileges.njsproj
  36. +5 −0 samples/react-sp-elevatedprivileges/webpart/src/tests.js
  37. +21 −0 samples/react-sp-elevatedprivileges/webpart/src/webparts/createTask/CreateTask.module.scss
  38. +18 −0 samples/react-sp-elevatedprivileges/webpart/src/webparts/createTask/CreateTaskWebPart.manifest.json
  39. +22 −0 samples/react-sp-elevatedprivileges/webpart/src/webparts/createTask/CreateTaskWebPart.ts
  40. +2 −0 samples/react-sp-elevatedprivileges/webpart/src/webparts/createTask/ICreateTaskWebPartProps.ts
  41. +136 −0 samples/react-sp-elevatedprivileges/webpart/src/webparts/createTask/components/CreateTask.tsx
  42. +7 −0 samples/react-sp-elevatedprivileges/webpart/src/webparts/createTask/loc/en-us.js
  43. +10 −0 samples/react-sp-elevatedprivileges/webpart/src/webparts/createTask/loc/mystrings.d.ts
  44. +7 −0 samples/react-sp-elevatedprivileges/webpart/src/webparts/createTask/tests/CreateTask.test.ts
  45. +9 −0 samples/react-sp-elevatedprivileges/webpart/tsconfig.json
  46. +13 −0 samples/react-sp-elevatedprivileges/webpart/typings/@ms/odsp-webpack.d.ts
  47. +10 −0 samples/react-sp-elevatedprivileges/webpart/typings/@ms/odsp.d.ts
  48. +15 −0 samples/react-sp-elevatedprivileges/webpart/typings/assertion-error/assertion-error.d.ts
  49. +388 −0 samples/react-sp-elevatedprivileges/webpart/typings/chai/chai.d.ts
  50. +107 −0 samples/react-sp-elevatedprivileges/webpart/typings/combokeys/combokeys.d.ts
  51. +113 −0 samples/react-sp-elevatedprivileges/webpart/typings/es6-collections/es6-collections.d.ts
  52. +74 −0 samples/react-sp-elevatedprivileges/webpart/typings/es6-promise/es6-promise.d.ts
  53. +631 −0 samples/react-sp-elevatedprivileges/webpart/typings/knockout/knockout.d.ts
  54. +20,808 −0 samples/react-sp-elevatedprivileges/webpart/typings/lodash/lodash.d.ts
  55. +214 −0 samples/react-sp-elevatedprivileges/webpart/typings/mocha/mocha.d.ts
  56. +2,392 −0 samples/react-sp-elevatedprivileges/webpart/typings/node/node.d.ts
  57. +19 −0 samples/react-sp-elevatedprivileges/webpart/typings/react/react-addons-shallow-compare.d.ts
  58. +155 −0 samples/react-sp-elevatedprivileges/webpart/typings/react/react-addons-test-utils.d.ts
  59. +35 −0 samples/react-sp-elevatedprivileges/webpart/typings/react/react-addons-update.d.ts
  60. +66 −0 samples/react-sp-elevatedprivileges/webpart/typings/react/react-dom.d.ts
  61. +2,284 −0 samples/react-sp-elevatedprivileges/webpart/typings/react/react.d.ts
  62. +21 −0 samples/react-sp-elevatedprivileges/webpart/typings/systemjs/systemjs.d.ts
  63. +18 −0 samples/react-sp-elevatedprivileges/webpart/typings/tsd.d.ts
  64. +87 −0 samples/react-sp-elevatedprivileges/webpart/typings/whatwg-fetch/whatwg-fetch.d.ts
@@ -0,0 +1,96 @@
# Communicate using elevated privileges with SharePoint

## Summary

Sample SharePoint Framework client-side web part illustrating communication with SharePoint using elevated privileges through a custom Web API.

![Sample web part showing orders retrieved from a custom Web API secured with Azure Active Directory](./assets/preview.png)

## Applies to

* [SharePoint Framework Developer Preview](http://dev.office.com/sharepoint/docs/spfx/sharepoint-framework-overview)
* [Office 365 developer tenant](http://dev.office.com/sharepoint/docs/spfx/set-up-your-developer-tenant)

## Solution

Solution|Author(s)
--------|---------
react-sp-elevatedprivileges|Waldek Mastykarz (MVP, Rencore, @waldekm)

## Version history

Version|Date|Comments
-------|----|--------
1.0|October 12, 2016|Initial release

## Disclaimer
**THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT.**

---

## Minimal Path to Awesome

- clone this repo

### Deploy custom Web API

- in the Azure Management Portal at https://portal.azure.com create a new API App
- in the settings enable CORS for all origins using an `*`
- copy the URL of the API App
- in your SharePoint site
- create a new list called **Tasks**
- navigate to https://yourtenant.sharepoint.com/_layouts/15/appregnew.aspx
- generate client ID and copy it
- generate client secret and copy it
- as the name use: **SPFx sample elevated privileges**
- as the URL use the URL of the Azure API App created previously
- as the domain use the host name of the Azure API App
- navigate to https://yourtenant.sharepoint.com/_layouts/15/appinv.aspx
- lookup the newly registered Add-in using the client ID you copied
- in the **Permissions** field past the following code:
```xml
<AppPermissionRequests AllowAppOnlyPolicy="true">
<AppPermissionRequest Scope="http://sharepoint/content/sitecollection/web/list" Right="Write" />
</AppPermissionRequests>
```
- after confirming the changes, when prompted, select the previously created **Tasks** list
- from the **api** folder, in Visual Studio open the **pnp.api.elevatedprivileges.sln** file
- in the web.config file
- update the value of the **clientId** setting with the previously copied client ID
- update the value of the **clientSecret** setting with the previously copied client secret
- update hte value of the **siteUrl** setting with the URL of your SharePoint site
- if you named your list other than **Tasks** update the value of the **listName** property with the name of your list
- build the solution
- deploy the **pnp.api.elevatedprivileges** project to the newly created API App
- verify that you can access the API by navigating in your web browser to **https://your-api-app.azurewebsites.net/api/items**
- you should get an error that GET is not a supported method
### Configure web part
- in the command line
- change the working directory to the **webpart** folder
- run `npm i`
- in your code editor open the **webpart** folder
- in the **./src/webparts/createTask/components/CreateTask.tsx** file
- in line 76 replace the URL with the URL of your API App
- in the command line execute `gulp serve`
- add the web part to SharePoint workbench
- enter the name of the new item and click the **Create** button
- verify that a new item with the name you specified has been created in the Tasks list
## Features
This project contains sample Web API using app-only permissions to create items in a specific SharePoint list, and a client-side web part connected to that API.
This project illustrates the following concepts:
- elevating user privileges for communicating with SharePoint through a custom Web API
- connecting SharePoint Framework client-side web part to a custom Web API hosted in Azure
- persisting state in React components
- communicating state updates in React components to users
- executing REST API web requests from React components
- using Office UI Fabric React components in SharePoint Framework client-side web parts
- using form controls in Rest components
<img src="https://telemetry.sharepointpnp.com/sp-dev-fx-webparts/samples/react-sp-elevatedprivileges" />
@@ -0,0 +1,22 @@

Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio 14
VisualStudioVersion = 14.0.25420.1
MinimumVisualStudioVersion = 10.0.40219.1
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "pnp.api.elevatedprivileges", "pnp.api.elevatedprivileges\pnp.api.elevatedprivileges.csproj", "{E9E8B537-849D-47B4-AA97-C3B7ED93227E}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Release|Any CPU = Release|Any CPU
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{E9E8B537-849D-47B4-AA97-C3B7ED93227E}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{E9E8B537-849D-47B4-AA97-C3B7ED93227E}.Debug|Any CPU.Build.0 = Debug|Any CPU
{E9E8B537-849D-47B4-AA97-C3B7ED93227E}.Release|Any CPU.ActiveCfg = Release|Any CPU
{E9E8B537-849D-47B4-AA97-C3B7ED93227E}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
EndGlobal
@@ -0,0 +1,9 @@
using System.Web.Mvc;

namespace pnp.api.elevatedprivileges {
public class FilterConfig {
public static void RegisterGlobalFilters(GlobalFilterCollection filters) {
filters.Add(new HandleErrorAttribute());
}
}
}
@@ -0,0 +1,15 @@
using System.Web.Http;

namespace pnp.api.elevatedprivileges {
public static class WebApiConfig {
public static void Register(HttpConfiguration config) {
config.MapHttpAttributeRoutes();

config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "api/{controller}/{id}",
defaults: new { id = RouteParameter.Optional }
);
}
}
}
@@ -0,0 +1,31 @@
using Microsoft.SharePoint.Client;
using OfficeDevPnP.Core;
using System;
using System.Configuration;
using System.Net.Http;
using System.Web.Http;

namespace pnp.api.elevatedprivileges.Controllers {
public class ItemsController : ApiController {
// POST api/values
public HttpResponseMessage Post([FromBody]dynamic data) {
try {
AuthenticationManager authMgr = new AuthenticationManager();
using (ClientContext ctx = authMgr.GetAppOnlyAuthenticatedContext(
ConfigurationManager.AppSettings["siteUrl"],
ConfigurationManager.AppSettings["clientId"],
ConfigurationManager.AppSettings["clientSecret"])) {
var list = ctx.Web.Lists.GetByTitle(ConfigurationManager.AppSettings["listName"]);
var item = list.AddItem(new ListItemCreationInformation());
item["Title"] = data.title.ToString();
item.Update();
ctx.ExecuteQuery();
return new HttpResponseMessage(System.Net.HttpStatusCode.Created);
}
}
catch {
return new HttpResponseMessage(System.Net.HttpStatusCode.InternalServerError);
}
}
}
}
@@ -0,0 +1,32 @@
using System;
using System.Web.Mvc;

namespace pnp.api.elevatedprivileges
{
/// <summary>
/// SharePoint action filter attribute.
/// </summary>
public class SharePointContextFilterAttribute : ActionFilterAttribute
{
public override void OnActionExecuting(ActionExecutingContext filterContext)
{
if (filterContext == null)
{
throw new ArgumentNullException("filterContext");
}

Uri redirectUrl;
switch (SharePointContextProvider.CheckRedirectionStatus(filterContext.HttpContext, out redirectUrl))
{
case RedirectionStatus.Ok:
return;
case RedirectionStatus.ShouldRedirect:
filterContext.Result = new RedirectResult(redirectUrl.AbsoluteUri);
break;
case RedirectionStatus.CanNotRedirect:
filterContext.Result = new ViewResult { ViewName = "Error" };
break;
}
}
}
}
@@ -0,0 +1 @@
<%@ Application Codebehind="Global.asax.cs" Inherits="pnp.api.elevatedprivileges.WebApiApplication" Language="C#" %>
@@ -0,0 +1,12 @@
using System.Web.Http;
using System.Web.Mvc;

namespace pnp.api.elevatedprivileges {
public class WebApiApplication : System.Web.HttpApplication {
protected void Application_Start() {
AreaRegistration.RegisterAllAreas();
GlobalConfiguration.Configure(WebApiConfig.Register);
FilterConfig.RegisterGlobalFilters(GlobalFilters.Filters);
}
}
}
@@ -0,0 +1,35 @@
using System.Reflection;
using System.Runtime.CompilerServices;
using System.Runtime.InteropServices;

// General Information about an assembly is controlled through the following
// set of attributes. Change these attribute values to modify the information
// associated with an assembly.
[assembly: AssemblyTitle("pnp.api.elevatedprivileges")]
[assembly: AssemblyDescription("")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyCompany("")]
[assembly: AssemblyProduct("pnp.api.elevatedprivileges")]
[assembly: AssemblyCopyright("Copyright © 2016")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]

// Setting ComVisible to false makes the types in this assembly not visible
// to COM components. If you need to access a type in this assembly from
// COM, set the ComVisible attribute to true on that type.
[assembly: ComVisible(false)]

// The following GUID is for the ID of the typelib if this project is exposed to COM
[assembly: Guid("eff521b1-a9db-4318-b4a8-800a497de4d2")]

// Version information for an assembly consists of the following four values:
//
// Major Version
// Minor Version
// Build Number
// Revision
//
// You can specify all the values or you can default the Revision and Build Numbers
// by using the '*' as shown below:
[assembly: AssemblyVersion("1.0.0.0")]
[assembly: AssemblyFileVersion("1.0.0.0")]

0 comments on commit f3fcf61

Please sign in to comment.
You can’t perform that action at this time.