SharePoint Framework - Pillars of SPFx

When trying to grok a new technology, it’s sometimes useful to look behind the curtain and seperate out the moving pieces. Someimtes this lets you get a handle on scope and lets you focus on individual pieces of the whole stack.

With SharePoint Framework this is no exception. To my eye, it looks like this right now: screenshot

I’ve also shared a slide deck here: http://www.slideshare.net/SeanMcLellan2/sharepoint-framework-developer-preview

SharePoint Framework - Easter Egg

Yeah… so I was looking at @microsoft/sp-module-loader and came across this file: screenshot

Hm… Windows_95_Startup.mp3?

Wut?

So I start looking at this module and I find this… (@microsoft/sp-module-loader/dist/sp-module-loader.js line 2017) screenshot

LOL.

Have Fun!!

SharePoint Framework - Code Smells in Module Loading

The SharePoint guys recently sent out this video on developing jQuery based client side web parts with the SharePoint Framework.

http://dev.office.com/blogs/building-simple-sharepoint-framework-client-web-part

One thing that caught my eye when viewing the video was the module loading code in their render method: screenshot

Effectively this is saying “load jQuery… wait until it’s done… then load jQuery.simpleWeather… then call renderConents()”

It’s even worse since we know that within the webpart’s lifecycle, “render()” is called after the web part’s dependencies are loaded. So we’re actually waiting to pull down our bundle, then waiting for jquery then waiting for jquery.simpleWeather, then finally calling renderContents()

Further, this all is wrapped in a conditional on “this.renderedOnce()” to not load these libraries multiple times…

to sum it up…

ewwwww

What if we needed a few more libraries that depend on one another – we’d end up with a massive pyramid of doom.

Don’t do this. please.

We could simplify this code with Promise.all(...) however, it’s true that jQuery.simpleWeather depends on jQuery so we need to load them in order. Loading dependencies using UMD from a CDN makdes for a nice teaching example, but we’ve got all these advanced module loading and bundling capabilities right at our fingertips already included with SPFx, let’s use them!

I’m going to show one way of mitigating this code smell – there’s other ways, but this is pretty straightforward.

What we’re going to do is add jQuery and jQuery.simpleWeather to the project via NPM so that it will be part of the webparts bundled javascript.

As webpack is also included by default, we’ll use its “require” method to pull in jQuery and simpleWeather

Since the required files are contained in the existing bundle, there will be no additional external requests to fetch the additional libraries and we can use really simple module loading to boot.

  1. First, we’ll add the jquery and simpleweather from npm with the following command at the shell in your project’s directory. bash $ npm i jquery jquery.simpleweather --save

  2. Let’s add the references to jQuery and jQuery.simpleWeather at the top of our webpart’s configuration
    (lines 12 and 13 are new)
    screenshot This is using webpack’s require function to load jQuery and adding it to the global object and doing so in a TypeScript friendly manner.

    We then load simpleWeather.

  3. Let’s refactor the render method:
    screenshot

    Annnnd that’s it.

If we look at our timeline on the page, we see a single request to our simple-weather.bundle.js which now contains jQuery and jQuery.simpleWeather screenshot

So now the code performs better and is more maintainable. Fun!

Note: The jQuery.simpleweather library on the Github repo plays better with module loading, npm install the one from the github repo and you’ll be able to use jQuery in local scope rather than global.

SharePoint Framework - ClientSideWebPart vs AppPart

One of the interesting things about building a SharePoint Add-in model AppPart was the issue of where the client side script lived. App script parts surface their content within a containing IFrame on the page which points to the app part’s content (script files etc) on the app web. This means that the SP cross-domain library needed to be used any time the app part needed to access content on the host web through services, as that was a CORs call.

Back in 2014, Vesa (current MS PM leading SPFx) introduced us to the pattern of using the Add-in model to simply deploy a Script Editor web part that is configured to load the necessary JS associated with HTML+JS in a web part.

https://blogs.msdn.microsoft.com/vesku/2014/07/08/introducing-app-script-part-pattern-for-office365-app-model/

By doing so we didn’t need to use the cross-domain library as the reference to our JS is just a script embed on the page. Cool.

Fast-forward to today and this pattern is now pretty much what the new SPFx ClientSideWebPart gives us, except that it fixes the two downsides that Vesa mentions in the above blog:

  1. With a script editor web part, Vesa mentions that an end-user could inadvertently change the embed script tag. The CSWP uses the manifest file to determine what JS references to load, so this potential is now gone.
  2. The current “mode” (view/edit) that the web part page is in is now passed to the CSWP code so a CSWP can easily determine what mode it is in and change the rendering accordingly.
  3. Module loading was a pain when you got into App Script development, the CSWP uses SystemJS to facilitate module loading and in doing so ensures that the required modules are loaded before your CSWP’s render method.

Unfortunately one big downside still remains in SPFx – since the packaged .spapp does reference a .webpart file, SPFx solutions are still not able to be hosted in the SharePoint app/addin store. Whether this changes by the time the SPFx RTMs or a new “SPFx Add-in” directory or a seperate permission level will spring up is yet to be seen.

So we’ve seen how the CSWP in SPFx could be seen as an evolution of Vesa’s app script part pattern, and some of the benefits that the CSWP gives you in developing HTML+JS based web parts over using app script parts.

Thanks,

SharePoint Framework - What It Is - Part 2

There were a few questions that came in, and I’ll do my best to answer:

What does SPFx provide to SPO that is currently not present in SP16? Is there a way I can use SPFx on-prem now?

At this point, the only thing that appears to be new on SPO is the new ClientSideWebPart, ClientSitePage, and a new xml element in elements.xml

This web part provides the following behavior: 1) Provides a client-side web-part property framework 2) Embeds SystemJS for module loading (the “System” object becomes available at the global scope when a CSWP is added)

They’ve mentioned some new things (new SharePoint pages experience, SharePoint specific web hooks) but those don’t appear to be available in the preview.

Really the approach should be to build your HTML/JS based native web app using any client-side technology you wish, possibly using the add-in web part (or not). When the CSWP becomes available in on-prem (via a future update) the effort to host your add-in in the webpart (if you so desire) will be minimal.

What is in the new Javascript libraries that SPFx provides and are there OSS versions of these?

The SPFx Yeoman template has your webpart requiring a base module named “@microsoft/sp-client-base”

MS doesn’t appear to have opened access to these components on Github yet, but they can be found on NPM here: https://www.npmjs.com/package/@microsoft/sp-client-base

Here’s some things that caught my eye – all of these are discoverable if you look at the node_modules/@microsoft folder after installing the SPFx yeoman template:

1) Fetch API polyfill used as the base HttpClient to making request to SP web services. See https://github.com/github/fetch 2) Digest caching (for X-RequestDigest). See https://github.com/beyond-sharepoint/spo-remote-auth 3) Class to generate GUIDs. See https://github.com/broofa/node-uuid 4) A custom bundle of lodash. Pull in full lodash (or specific components if needed), see the @microsoft/sp-lodash-subset package on NPM too. 5) New (but incomplete) JS-classes around SP-prefixed objects (SPUser, SPList, SPSite, etc). See https://github.com/Kaldeera/ng-SharePoint 6) A new SPModule loader which is a wrapper around SystemJS. Use SystemJS full yourself or your preferred module loader…

I’m sure this will expand over time.

You mentioned the new SharePoint pages experience, what will this bring?

Unfortunately I don’t know much more about SharePoint Pages – There’s a small stub in the sp-client-preview module, but it’s currently empty.

The workbench.aspx might be the start of the SharePoint Pages experience but it seems in it’s infancy (or I have high standards :))

One could speculate that there could be a new type of webpart page that uses react components to handle the things that traditionally have been done via the (server-side) webpart manager, and facilitate inter-webpart messaging and so forth.

Speculating further, things like layout could be handled by client-side rendering through page configuration, rather than static layout .aspx pages.

ClientWebPart discovery will still need to be handled, however, whether this is done by a new system, or leverages the existing add-in catalog is TBD.

Any other info anyone has would be highly interesting.

What is the purpose of node? Can I use node in my SPFx solutions?

NodeJS is used just for the tooling. E.g. Yeoman, Webpack, Gulp, etc are all NodeJS based toolkits and the SPFx Yeoman template provides a standard configuration of these tools to build SPFx client web parts with.

Node is a server-side tech so it’s not something you can use directly for your client-side web parts. But, you can create services in node that your client side scripts call, if you want to, as well as import client-side JS files from node and require them in your SPFx web part.

What about .Net Core? Why doesn’t SPFx use MS’s own stuff?

Good question – I don’t have the precise answer to this but one can extrapolate:

  1. Timing; .Net Core is still very new as an RTM release, but .Net Core’s tooling is still in preview, and the ecosystem is still developing. It might have been pre-mature to build a solution based on yet-to-be-fully-proven .Net Core.

  2. Community; Modern Web Development is aggressively using NodeJS and the modules that SPFx uses. It makes sense that SPFx wanted to bring SharePoint development to be in-line with what the rest of the Web Development community is using.

  3. Expand audience; SPFx doesn’t replace existing ways to build SharePoint solutions. It provides another way - so by using this specific toolchain, and the client-side components in place, we might be able to see the types of developers that the SPFx is aiming to attract.

  4. Embrace OSS; The modules that SPFx uses are very clever tested components being maintained by large communities in themselves. Rather than re-create the wheel, it makes sense to embrace these open technologies and use them.

Will we see a reboot of SPFx to utilize .Net Core for the tooling? One can only surmise what goes on in terms of management and politics of blue-badge ‘softies…

SharePoint Framework - Tracking down the elephant in elements.xml

If we look at our webpart\sharepoint\solution\debug folder after we’ve packaged it at least once using the gulp task, we find the following: screenshot

As mentioned on Chris O’Brien’s Blog, the \sharepoint folder contains the .spapp file which is our add-in (just a zip file using the Open Packaging Conventions) that contains the files in the /debug folder.

If you’re a long time SharePont guy, you should recognize most of these files. The .webpart file contains the webpart definition (webpart type etc), and the WebPart_<guid>.xml is actually just our good old friend elements.xml: screenshot

yep, all looks familiar. down at the bottom is our <module> that deploys our .webpart into the web part catalog on the add-in host web. If we wanted to, we could throw additional modules entries to include additional files on the host web with our CSWP on add-in deployment.

However, the elephant in the room is this new “ClientSideComponent” element.

We haven’t seen this before in SharePoint on-prem, but we can easily figure out that this is pulling in the manifest.json file that describes the urls to our bundle files, some metadata and so forth.

We also have seen that this information provided here gets rendered by the CSWP to provide information to the SystemJS module loader of our web part. There’s the baseurl of our bundle which could be hosted in a file on SP, locally, on github or whereever.

Now, the $100,000 question is where this data gets stored in SPO to be retrieved by the CSWP. If we were able to modify this metadata we would be able to change the base location of our bundle files and the other metadata without needing to redeploy our addin.

This would be pretty handy in a dev/test scenario, or just upgrading an app hosted in a CSWP from one iteration to the next.

It’s not a property bag setting, nor is it a hidden list on the add-in host web. If the we had the bits to the CSWP we could use a .net reflection tool to get an inkling of where it’s being stored… but we don’t.

Anyone have any thoughts?

SharePoint Framework - Deciphering the ClientSideWebPart

Since we now understand that the new ClientSideWebPart (CSWP - not to be confused with the ClientWebPart, nor the ScriptEditorWebPart) forms the bulk of the current preview functionality in the SPFx, we can start to reverse engineer what the CSWP is doing exactly.

If we take a look at the DOM element of a CSWP that we drop on the page using the developer tools, we’ll find the following: screenshot

Ok, so that’s not so bad, a couple CSS references to Office UI Fabric, and a script reference to a file called “sp-module-loader…js” hosted on a SPO CDN, and a inline script element.

If we look at sp-module-loader.js real quick we’ll find that it’s the same as the module that is part of the SPFx yeoman template, @microsoft/sp-module-loader on NPM. We find that includes some ES6 polyfills: es6-collections, es6-promise and whatwgfetch. We also find a wrapper around SystemJS – this is what is used for the ‘System’ object at global scope.

So now we know where SystemJS is getting loaded and how module loading is performed by the CSWP.

If we expand the inline script element, we find a script that executes and adds a ‘preloadedData’ property to the global window object. screenshot

If we use the dev tools console, we can get a better view of what’s been set on window.preloadedData screenshot

Well that looks exactly like what’s within manifest.json that generated by the SPFx tooling, except that there are a few more manifests beyond my webpart, of a couple other componentTypes.

In my case, the manifests include:

  • classic-page-webpart-application
  • office-ui-fabric-react.bundle
  • sp-client-framework.bundle
  • react-flux.bundle
  • sp-client-preview
  • seans-dynamic-list-form.bundle

So this is where the other modules that makeup a SPFx webpart are getting loaded. React, Flux, Office UI Fabric, and some new SPFx client libraries that we covered previously.

Interestingly enough, if we look at the “componentType” properties of these objects, the first manifest has a “componentType” of “Application” and the others have a “componentType” of “Library”.

I’d wager that we’d be able to add additional components to our SPFx project that define these types of components – even though the current yeoman template and tutorial seems to indicate the current SPFx tooling does one thing, and one thing only: Generate a project that contains a single CSWP.

Finally, at the end of the script element, after the manifest definitions we see the following: screenshot

This is the actual code which is calling out to SystemJS to asynchronously load the module for my webpart (that’s my webpart guid as the first parameter) and then call a loadClientSideWebPart of @microsoft\sp-client-preview...classicpagebootstrapper.js. screenshot

If we follow this function down, we find it is responsible indirectly of calling the render method of my webpart through the ‘loadWebPart’ function of a ClientSideWebPartManager: screenshot

passing in the following context. This is important as these properties are being made available to us (if you recall the tutorial, we use the domElement.innerHTML to set the contents of our CSWP) screenshot

So there you have it. If you made it this far, we now have a bit of an understanding of what exactly the CSWP is doing, soup to nuts and somewhat of an understanding of what bits are responsible for calling our “render” method in our CSWP and what is being passed to the current context in our render method.

TLDR;

CSWP uses SystemJS to performing module loading, and loads office-ui-fabric, SPFx components and react-flux bundles as well as our webpart bundle. Once those are loaded it calls the “render” method of our CSWP which is the direct hook into our webpart code.

Hope this helps!

SharePoint Framework - What It Is

After diving in deep to SPFx I wanted to share some findings about some misconceptions about what SPFx is and isn’t that I had and couldn’t find elsewhere.

Feel free to correct where I’m wrong and supply any more info. This is all subject to change, but these are current findings with the current bits.

Chris O’Brien’s blog is a great help on this, and referenced throughout http://www.sharepointnutsandbolts.com/

Skipping the marketing for a second, what exactly is the SharePoint Framework (SPFx) from a technical standpoint?

TLDR; SPFx provides cross-platform tooling that generates a SharePoint add-in (.spapp) that defines a ClientSideWebPart (new to SP v16) and configures it with information about where the JS files that make up your client-side web part are located.

Long version: SPFx provides a yeoman template that contains a provides of things once initialized.

1) Pulls in a number of npm packages that contain the ‘framework’ and provides ts->js transpilation and webpack packaging

2) Defines a number of gulp tasks that generates the files that go into a .spapp (AppManifest.xml, etc) and zips them up. Other tasks provide local serving of a client-side webpart.

3) Basic project structure based on inputs. See http://www.sharepointnutsandbolts.com/2016/07/web-part-manifest-bundle-json-framework.html for a rundown of the structure.

Webpack is utilized for module loading and bundling.

The entry point to a client web part is provided by a render() method.

In idiomatic javascript terms, how does the content of my web part get surfaced?

When a SPFx ClientSideWebPart is rendered, it loads the files provided in the web part json configuration and calls the “render()” function that is exported on the ‘entry’ class. This serves as the entry point to providing JS-based behavior.

The value of ‘this’ in the scope of the ‘render’ method contains a number of properties that can be used.

One of these properties is ‘domElement’ which is exactly as it sounds – the dom element that represents the body of the web part. Setting this.domElement.innerHTML property provides the html contents of the web part.

But what about frameworks like angular that ‘render’ the html for me?’

Remember that everything is running in JS. So, to get angular to work with the SPFx, after including the angular javascript files, one would initialize the angular app within the render method (or in any loaded JS) and provide this.domElement.innerHTML property with the desired html with Angular markup.

For instance: screenshot

Can I use the ClientSideWebPart outside of the tooling that MS provides, for instance, can I create an old-school web part definition that I upload to the web part catalog without using the add-in model?

There might be benefits to using the add-in model (reuse, discovery) but, yeah, absolutely, in fact the tooling does this for you, but then bundles it up in the .spapp screenshot

The namespace to include in your .webpart file is:

Microsoft.SharePoint.WebPartPages.ClientSideWebPart, Microsoft.SharePoint, Version=16.0.0.0, Culture=neutral, PublicKeyToken=71e9bce111e9429c

The ClientSideWebPartId must be specified, and it’s currently unclear to me if it’s possible to set those values outside an add-in.

Can I use the webpart generated by the SPFx on an existing Web Part Page?

Yes. Currently generated by SPFx is just a plain ‘ol web part in the add-in model, just pre-loaded with JS goodness.

Should I place an emphasis on learning SPFx or client-side frameworks?

SPFx is a shim to any client side framework, so beyond the initial set up of a project, and defining/obtaining web part properties, the real emphasis is in building your add-in with whatever client-side framework you choose.

Which client-side frameworks should I learn with SPFx?

While the SPFx does utilize react, redux and flux, any client-side framework can be utilized with SPFx.

This includes “naked javascript” to jQuery to bigger stacks like Angular and React.

The SPFx does emphasize using TypeScript.

Does SPFx invalidate any current approaches with the add-in model, webparts or .aspx files?

No. As seen above, actually SPFx utilizes the add-in model to define the webparts you create and leverages the existing webpart framework in .aspx pages that’s been around since SP2010.

The official line from Bill Baer is that “The SharePoint Framework does not make obsolete nor deprecate the existing Add-In Model for SharePoint.”

I’m more of a idiomatic javascript guy, can I use the SPFx without Typescript? What about coffeescript, flowtype?

Sure, there may or may not be advantages to strong typing, but if you’re more comfortable using pure javascript or prefer another language that transpiles to JS you can – but keep in mind you’re going off the SPFx reservation.

Look at the js that SPFx generates for more info, but the key points are to extend the BaseClientSideWebPart prototype, providing a render() function and a propertyPaneSettings property.

It’s possible to release your own Yeoman template that simply uses ES6 or any transpiled language.

What benefits does the SPFx have over add-in parts, creating custom .aspx pages and other approaches that utilize client side techniques that we’ve utilized with SPO.

Good question… as you can see by now, SPFx actually leverages the existing add-in model and web parts. It does provide cross-platform tooling that gives you a standard project structure and abstracts away the configuration of a number of toolsets that are becoming standard when developing HTML/JS code (Webpack, Typescript/typings, etc…)

It would benefit oneself to learning these underlying technologies because at some point, one is probably going to need to touch them. (Or at least move code from SPFx Preview to RTM whenever that happens)

If this is MS’s way of forcing SP devs to get off the laurels and learn HTML+JS technologies then great.

What about the new “SharePoint Pages” experience?

Not sure – the current preview bits don’t indicate how the “New SharePoint Page Experience” fits in, nor what the migration path.

Looking at the @sharepoint\sp-client-preview module, it does make reference to a ClientSideWebPartManager, and a differentiation between “Classic” and “Client” pages.

There’s also workbench.aspx which imports a ASP.Net class called “ClientSidePage” – perhaps this represents the current state-in-time of the new pages experience being developed.

What about sharePoint WebHooks?

Doesn’t look like SharePoint specific webhooks have been made available yet, WebHooks as part of the MicroSoft graph are available (Outlook and OneDrive)

Wrap-up:

One shouldn’t feel ashamed for not looking at SPFx especially if one is currently is or has utilized any client-side frameworks. The bulk of the needed knowledge lies in actually building your app, so it’s probably a pragmatic approach to let the dust settle on the SPFx before making too much of a time investment.

Also keep in mind that the above will probably change, as the Github docs repo states:

“Note: SharePoint Framework web parts during preview are not supported for production use. The SharePoint Framework is currently available for use in Classic Pages within Office 365 Developer Tenancies. We’ll be expanding coverage to more Office 365 Tenancies over the coming months.”

Creating an email enabled list in Office 365 and Microsoft Flow

Had some extra time this morning to play around with O365 and Microsoft Flow.

So in this walkthrough, the desired functionality is to have a replacement for an e-mail enabled document library. Since this functionality isn’t available directly in O365, we’ll use Shared Mailboxes with Microsoft Flow to achieve similar functionality.

This process could also be done with Site Mailboxes, however, for whatever reason after waiting 2 hours after I created a site mailbox I still wasn’t able to access the mailbox in Outlook Online to set up a forwarding rule and kept getting a “ConnectionFailedTransientException” … so I went the shared mailbox route. Fun.

To get started, I’ll create a Shared Mailbox in Office 365 by going to the Admin Center Home -> Shared Mailboxes.

I created a shared mailbox creatively called “emailenabledlist” screenshot

Next, I granted permissions to myself on this mailbox. Now, since the Shared Mailbox is just a mailbox that’s not associated with a user account, I’ll need to set up a forwarding rule to forward emails to my mailbox in order to have it work with Microsoft Flow. screenshot

I’ll also create a folder in my personal account that will house the emails, and create a rule to move emails received from emailenabledlist to the folder. Note that there are many ways to skin a cat and this is just one method – you’ll probably want to create and document a more maintainable one. screenshot

Next, I went over to https://flow.microsoft.com/en-us/

and used the “Save my email attachments to a SharePoint document library” template: screenshot

When setting up the template, I went ahead set the incoming folder to be folder we set up in the rule, in my case “Site Mailbox Temp Drop Folder” screenshot

I then set the create file action to the following settings. screenshot

Saved and clicked done. At this point I should be able start testing to see if this is all actually works. I’ll send an e-mail to emailenabledlist with attachments see if the attachments get to where they need to be.

And here it is! screenshot

So there’s one way to do it without writing a line of code. As I mentioned, this should work with Site Mailboxes too, but O365 was hiccuping on me.

Now if you customize the template and add conditionals you’ll be able to do some advanced functionality. One might be to place attachments in separate folders or document libraries based on the email subject line.

As mentioned, this should be able to be done with code-based solutions (through Azure Web Jobs or an API via a WebHook by monitoring the shared mailbox directly and creating the file in O365. This could give additional customization options not found in the MS Flow based solution.

Thanks,