Building Proxy Provider for SharePoint Framework and Microsoft Graph Toolkit

The Microsoft Graph Toolkit (MGT) is a collection of reusable, framework-agnostic components and authentication providers for accessing and working with Microsoft Graph. The components are fully functional right out of the box, with built in providers that authenticate with and fetch data from Microsoft Graph.

MGT has a nice and simple integration with SharePoint Framework with just one line of code:

Providers.globalProvider = new SharePointProvider(this.context);

However, MGT supports other provider types as well. Like Proxy provider. In some cases, it makes sense to use the Proxy provider inside your SharePoint Framework solution instead of the SharePointProvider. Here is why:

  • you have a backend API that talks to MS Graph with on-behalf-of (OBO) flow. You don't use JS code to talk to MS Graph and rely solely on the backend
  • you don't want to maintain many "webApiPermissionRequests" entries inside package-solution.json, because every new permission requires re-deployment

If the above is true for you, then you can implement the Proxy provider for MGT instead of SharePointProvider.

The source code for this sample is available at GitHub here.

More...

spfx-fast-serve 3.0: it's all about simplicity

- What?? Two major releases in just two weeks? Should I again migrate?

- Unfortunately, yes, you should migrate again. Fortunately, it's not that difficult. Additionally, 3.0 is a lot more flexible and simple.

Technically, it's the same codebase and functionality as 2.0, however recent findings made me available to drastically change the way of handling the "serve" command. Also, I removed some cli options (pnpm now is supported out-of-the-box, sp-rest-proxy is supported as an extension using webpack.extend.js). Since cli options were changed and the "serve" handling, I had to introduce a new major version. 

The new version gives the below benefits:

  • A lot easier configuration - you don't need a lot of webpack dependencies in your package.json, you don't even need webpack.js in your project tree. As a result, spfx-fast-serve adds only a small footprint to your SPFx project
  • A lot easier migration between SPFx versions - now you don't need to run spfx-fast-serve each time you migrate your project to the next SPFx version, instead, you just need to update a dependency in package.json
  • A lot easier bug fixing - now all fixes are delivered automatically as a regular npm module dependency, no need to update spfx-fast-serve and run it again

Check out what code is added to your gulpfile.js:

const { addFastServe } = require("spfx-fast-serve-helpers");
addFastServe(build);

Check out which additional dependencies you need in your pacakge.json:

"spfx-fast-serve-helpers": "~1.12.0"

1.12 - reflects SPFx version. If you need to migrate to a new SPFx version - you change the minor version for spfx-fast-serve-helpers and that's it.

And finally serve command:

"serve": "gulp bundle --custom-serve --max_old_space_size=4096 && fast-serve"

You can also browse the code of the basic sample here. It contains the bare minimum needed to run 3.x with SPFx 1.12.1.

Check out this doc to learn how to upgrade to the latest 3.x version. If you use spfx-fast-serve, I recommend you migrate to the 3.x version today, because all future updates will be based on the 3.x version only. This version is considered stable and no more major releases planned in the nearest future. 

Title image credits - Business vector created by freepik - www.freepik.com

spfx-fast-serve 2.0: new architecture, better extensibility, support of the latest SPFx

In the last few weeks, I was working on spfx-fast-serve v2.0 release. What is spfx-fast-serve?

A command line utility, which modifies your SharePoint Framework solution, so that it runs continuous serve command as fast as possible.

New architecture

At the very beginning, this tool was more like an experiment to see what is possible and also to see the potential limitations. During last year I fixed a bunch of bugs, added support for library components. However, the code was not as good as it should be. It was just a javascript file with all the logic. I see that the usage of spfx-fast-serve is growing, thus decided that it's a good chance to make it better. 

In a new version, everything is done using TypeScript with a lot better architecture. Different commands are responsible for different solution modifications - package.json update, gulpfile update, write webpack.js to disk, etc.  It will be a lot easier to maintain and to upgrade between different SPFx versions. It also easier for potential contributors to make changes. More...

SPFx Check Locale - a nice option to check your localization consistency across SharePoint Framework solution

If you develop multi-lingual SharePoint Framework solutions, you know that you should keep your localization files in sync. You have a "master" file, which defines your localization resources structure, by default it's called "mystrings.d.ts" where you define all different keys. In the corresponding {locale}.js file you implement actual translations. In some cases, when you have a lot of labels after the refactoring you might lose the synchronization between your "mystrings.d.ts" and JS resource files. That leads to empty labels and UI problems in your web parts. SPFx doesn't provide a mechanism to check it. 

Now you can use SPFx Check Locale VSCode add-in and a Nodejs module to perform such checks. 

VSCode

You can install the addin from here or just search in VScode for "SPFx Check Locale".

The below video describes the core features of the addin: 

If you have and differences between your maser "mystrings.d.ts" and {locale}.js resource, the error will be immediately reported (including line and message). Using the addin you now have a clear visual indication that something is wrong with your localization files. 

Nodejs

You can also integrate SPFx check-locale as an additional quality check into your build pipeline since it's also available as a nodejs module

Install "spfx-check-locale" module and just add the below code to your gulpfile.js:

const checkLocales = require('spfx-check-locale').checkForErrors;

const argv = build.rig.getYargs().argv;
if (argv.production) {
  const check = build.subTask('check-locales', function (gulp, buildOptions, done) {
    checkLocales({
      projectPath: __dirname,
      printErrors: true
    })
      .then(result => {
        if (result.diagnosticData.length === 0) {
          done();
        } else {
          done('Found errors in localization files');
        }
      }).catch(done);
  });

  build.rig.addPostBuildTask(build.task('check-locales', check));
}

That way before publishing to production you always sure that your resources are good, otherwise your build will fail. The above code performs locale checks only on production builds (argv.production, which is true for gulp bundle --ship). You can also do it on a normal gulp serve, however, it will slow down your build for additional 2-4 seconds. With VSCode add-in it doesn't make a lot of sense to have it in serve command. 

"spfx-check-locale" integrates smoothly with your CI\CD process as well.

How it works

Every SharePoint Framework project contains a config.json file, which lists localizedResources - a collection of project resources. spfx-check-locale module opens every folder with resources and extracts interface name from "mystrings.d.ts" (using TypeScript AST). Then it creates a virtual TypeScript project in memory adding all files inside the resources folder. {locale}.js are renamed to {locale}.ts. For every {locale}.ts it also adds a return value for a function to be equal to the interface name from "mystrings.d.ts". 

For example, a en-us.ts will look like below:

define([], function(): IHelloWorldWebPartStrings {
  return {
    "PropertyPaneDescription": "Description",
    "BasicGroupName": "Group Name",
    "DescriptionFieldLabel": "Description Field"
  }
});

Next, the module runs TS compilation in memory and VSCode add-in simply maps TS errors to the corresponding lines inside IDE. That way we can see all problems in a real time. 

Title image credits - People vector created by pch.vector - www.freepik.com

Building Outlook addin with SPFx - save mail to OneDrive with Azure Function, MSAL.NET and MS Graph .NET

In this post, we're going to build a prototype of an outlook add-in, which saves the current email to your OneDrive. The interesting part is, that our add-in will be SPFx based, and our code, which saves emails, is hosted on Azure Functions and uses MSAL.NET for authentication and MS Graph .NET library to interact with MS Graph API.

Important! On the moment of writing (March 2021), SPFx Office add-ins support is still in preview. You can only build an add-in for outlook web. Thus I don't provide any production deployment instruction, because there is a chance, that it will change in the future.

The source code for this post is available on GitHub here. More...

Different ways of consuming organizational data (i.e. SharePoint or MS Graph API or other) from SPFx web parts

In this post, I'm going to cover different options when it comes to accessing organizational data from SPFx web parts. By organizational data I mean the most common APIs like SharePoint or MS Graph. However, it's valid for all other APIs as well. 

I'm going to cover two primary options here. The first one doesn't include any custom services or custom APIs and relies solely on SPFx OOB functionality. In the second option, we use Azure Function as a custom Web API component to access organizational data. As a bonus, we also have the third one which is a combination of the first two. More...

SharePoint Framework with ESLint

If you're still using tslint, I have bad news for you - it has been deprecated a long time ago. If tslint works for your old projects, then it's ok. However, for new projects use eslint. ESLint nowadays supports TypeScript with help of a plugin and parser. 

SharePoint Framework build pipeline is not as fast as the JavaScript tooling world and still uses tslint as a default linter. The good news is that we can fix it!

The source code for this post you can find on GitHub here.

More...