Introduction
PowerApps is an enterprise service that lets you connect, create, and share business apps with your team in minutes and helps to build a highly tailored application with an optimized user experience. You can expedite the business solution with Power Apps as well as SharePoint Online.
PowerApps is known as a powerful platform that allows for less code and more power.
Let's get started and learn how to extend a SharePoint Framework SPFx solution with PowerApps. I am going to take a simple problem statement, i.e. The user needs to upload the reference document. There are multiple way to achieve this scenario, so let's see how easy it is using a low code solution.

Solution Overview
- Build an SPFx extension i.e. Application Command List View. It will appear as a button in the Library List view.
- On Library List view button click invoke Office UI Fabric, Modal Dialog window.
- Modal Dialog call designed Power Apps Canvas form in an iframe with document id as parameter.
- PowerApps Canvas form store reference document to different list as attachment with corresponding library document id as metadata.
Step 1. Create and Navigate to SPFx extension Folder
yo @microsoft/sharepoint

Create SPFx extension solution with below option

Set Command Name and Description
After a few minutes, the "Congratulations!" screen will appear to notify the successful generation of the package.
Step 2. Import and Add References
Browse the solution and navigate to filename ModalDialogReference.tsx.
Install "react-iframe" package using the following commands:
import { Modal } from 'office-ui-fabric-react/lib/Modal';
import { DefaultButton } from 'office-ui-fabric-react/lib/Button';
import { Icon } from 'office-ui-fabric-react/lib/Icon';
import { UrlQueryParameterCollection } from '@microsoft/sp-core-library';
import Iframe from 'react-iframe';
npm install --save react-iframe
Step 3. Set Extension to Specific Library
You can add extension to specific library as per below command and refer my previous article set extension to specific library here.
@override
public onListViewUpdated(event: IListViewCommandSetListViewUpdatedParameters): void {
const compareOneCommand: Command = this.tryGetCommand('COMMAND_1');
var Libraryurl = this.context.pageContext.list.title;
if (compareOneCommand) {
// This command should be hidden unless exactly one row is selected.
compareOneCommand.visible = (event.selectedRows.length === 1 && (Libraryurl == "AuditReport"));
}
}
@override
public onExecute(event: IListViewCommandSetExecuteEventParameters): void {
switch (event.itemId) {
case 'COMMAND_1':
if (event.selectedRows.length > 0) {
// Check the selected rows
event.selectedRows.forEach((row: RowAccessor, index: number) => {
const dialog = new Index({ id: row.getValueByName('ID'), showModal: true})
dialog.show().then(() => {
});
});
}
Add Row Accessor to LibraryExtensionCommandSet.ts file
import {
BaseListViewCommandSet,
Command,RowAccessor,
IListViewCommandSetListViewUpdatedParameters,
IListViewCommandSetExecuteEventParameters
} from '@microsoft/sp-listview-extensibility';
Step 4. Browse ModalDialogReference.tsx file and add modal dialog window
Add close button for pop up.
const CloseModal = () => (
<Icon iconName="ChromeClose" className="ms-IconExample" style={{fontWeight : "bold"}} />
);
Add State and Props for Modal Dialog and Item ID
export interface IModalWindowState {
showModal: boolean;
id: number;
}
export interface IModalWindowProps{
id:number;
close:any;
showModal: boolean;
}
Set State for Modal Show and Close
private _showModal = (): void => {
// renderOnDom()
this.setState({ showModal: true });
};
private _closeModal = (): void => {
this.props.close()
this.setState({ showModal: false });
};
Add Render method to class, which consists of a modal dialog window with IFrame
export default class ModalWindow extends React.Component<IModalWindowProps,IModalWindowState> {
constructor(props) {
super(props);
this.state = {
showModal: props.showModal,
id: props.id
};
}
componentWillReceiveProps(nextProps,prevState){
if(nextProps.id !== prevState.id){
this.setState({
id:nextProps.id,
showModal: nextProps.showModal
})
}
}
public render(): JSX.Element {
var libraryUrl = window.location.href;
libraryUrl= libraryUrl.toLowerCase()
let fields="";
let headertext =""
headertext ="Audit Report Relase Form"
fields = "https://web.powerapps.com/webplayer/iframeapp?source=iframe&screenColor=rgba(104,101,171,1)&appId=/providers/Microsoft.PowerApps/apps/8a7896aa-ff75-4bdf-b297-399d6785aec3&Input=" + this.state.id ;
return (
<div>
<Modal
isOpen={this.state.showModal}
onDismiss={this._closeModal}
isBlocking={true}
containerClassName="ms-modal-container">
<div className="ms-modal-head">
<span className="ms-modal-headerTitle">{headertext}</span>
<DefaultButton onClick={this._closeModal} className="CloseButton" ><CloseModal/></DefaultButton>
</div>
<div id="subtitleId" className="ms-modal-body">
<Iframe url={fields}
width="1024px" height="550px"
position="relative"
allowFullScreen>
</Iframe>
</div>
</Modal>
</div>
);
}
Note
To hide the Powerapps ribbon into modal dialog, we need to use below define format in the Iframe URL.
https://web.powerapps.com/webplayer/iframeapp?source=iframe&screenColor=rgba(104,101,171,1)&appId=/providers/Microsoft.PowerApps/apps/<PowerAppsFormID>
Step 5. Set reference for document library
Client Side Instance.XML for List to Library i.e. 101




















Siddharth VaghasiaPosted Dec 9, 2019, 11:32 PM
Interesting...how we can combine two concepts to build a solution which is cost-effective plus maintainable...thanks for sharing..!