SPFX Bot Using Azure Bot Framework SDKV4 With Luis And QnA Maker

AThe zure Bot Framework SDKV4 can be used with LUIS models and QnA Maker knowledge bases. It helps to determine which LUIS model or QnA Maker knowledge base best matches the user input.
 
SPFX (SharePoint Framework) is the recommended and only option to deploy Azure bots into SharePoint Online Modern Sites.
 
In this article, I am going to extend my previous article with SPFX (SharePoint Framework).
SPFX Bot Using Azure BotFramework SDKV4 With Luis And QnA Maker
 
SPFX (SharePoint Framework) interacts with Azure Bot Services via directline.
 
Let's get started with implementation steps. 
 
Step 1
 
Navigate to Deployed Azure Bot and Add Direct Line as Channel & get Secret Key
  1. Select Channel and add a featured channel option; i.e. Direct Line, Ms Teams and Cortona. Select Direct Line to add.
  2. As you select direct line as channel, it will be added.
  3. Click edit to get the secret key. This key will be used in SPFX webpart to post requests to bot via direct line api & secret key. 
SPFX Bot Using Azure BotFramework SDKV4 With Luis And QnA Maker
 
Step 2 - Create SFPX Project
  1. Open Command Prompt or Visual Studio Code and Navigate or create a blank folder; i.e. ChatBot, and use CD command to navigate into folder.
  2. Type yo@Microsoft/SharePoint generator to create a framework.
  3. Type Solution Name: spfx-chat-bot
  4. Select SharePoint Online
  5. Select option to place a file as "Current Folder"
  6. Place the WebPart Name & Description as ChatBot
  7. Select framework as React to start.
SPFX Bot Using Azure BotFramework SDKV4 With Luis And QnA Maker
 
Step 2 - Install NPM Package
 
Install the below defined npm packages to SPFX solution. 
  1. npm install botframework-directlinejs  
  2. npm install botframework-webchat  
Step 3
 
Create State Class for Modal Dialog
 
State will hold variable to switch the modal dialog box.
  1. export interface IChatBotState {    
  2.     showModal: boolean;    
  3.     isDraggable: boolean;    
  4.     directline: any;    
  5.     styleSetOptions: any;    
  6. }     
Step 4 - Update Properties Interface
 
Properties have variables which help to set background color, font etc. 
  1. import { IWebPartContext } from '@microsoft/sp-webpart-base';  
  2. export interface IChatbotProps {  
  3.   description: string;  
  4.   directLineToken: string;  
  5.   bubbleBackground: string;  
  6.   bubbleTextColor: string;  
  7.   bubbleFromUserBackground: string;  
  8.   bubbleFromUserTextColor: string;  
  9.   backgroundColor: string;  
  10.   botAvatarImage: string;  
  11.   botAvatarInitials: string;  
  12.   userAvatarImage: string;  
  13.   userAvatarInitials: string;  
  14.   hideUploadButton: boolean;  
  15.   sendBoxBackground: string;  
  16.   sendBoxTextColor: string;  
  17.   context: IWebPartContext;  
  18. }  
Step 5 - React Component Implementation
 
Define construcutor, which will help to initilaize the defined properties and set the state variable.
  1. constructor(props) {  
  2.   super(props);  
  3.    
  4.   this.state = {  
  5.     showModal: false,  
  6.     isDraggable: true,  
  7.     directline: null,  
  8.     styleSetOptions: styleOptions  
  9.   };  
  10.   this._showModal = this._showModal.bind(this);  
  11.   this._closeModal = this._closeModal.bind(this);  
  12. }  
Show Modal and Close Modal used to set toggle variable.
  1. private _showModal = (): void => {  
  2.    this.setState({ showModal: true });  
  3.    this.fetchToken();  
  4.  };  
  5.   
  6.  private _closeModal = (): void => {  
  7.    this.setState({ showModal: false });  
  8.  };  
Initiate the post request to directline .
  1. async fetchToken() {  
  2.    var myToken ='<<--Secret Key-->>';  
  3.    const myHeaders = new Headers()  
  4.    myHeaders.append('Authorization''Bearer ' + myToken)  
  5.    const res = await fetch(  
  6.      'https://directline.botframework.com/v3/directline/tokens/generate',  
  7.      {  
  8.        method: 'POST',  
  9.        headers: myHeaders  
  10.      }  
  11.    )  
  12.    const { token } = await res.json();  
  13.    console.log(token);  
  14.    this.setState({  
  15.      directline: createDirectLine({ token })  
  16.    });  
  17.    this.state.directline.postActivity({  
  18.      from: { id: "serId", name: "USER_NAME" },  
  19.      name: "requestWelcomeDialog",  
  20.      type: "event",  
  21.      value: "token"  
  22.    }).subscribe(  
  23.      id => console.log(`Posted activity, assigned ID ${id}`),  
  24.      error => console.log(`Error posting activity ${error}`)  
  25.    );  
  26.   
  27.  }  
Use component did mount to call this method.
  1. async componentDidMount() {  
  2.     this.fetchToken();  
  3.   }  
Render Method
 
On Icon Click call Modal Dialog and which will invoke ReactWebChat Tag with direct line state variable,
  1. <div className={ styles.chatbot }>  
  2.         <DefaultButton style={{ border: 'none', textDecoration: 'none', background: 'none', outline: 'none' }} onClick={this._showModal}>  
  3.        <img src="https://data.blob.core.windows.net/boticon/ChatBotIcon.JPG" alt="Chatbot" height="100px" width="100px" />  
  4.      </DefaultButton>  
  5.      <Modal  
  6.        titleAriaId={this._titleId}  
  7.        subtitleAriaId={this._subtitleId}  
  8.        isOpen={this.state.showModal}  
  9.        onDismiss={this._closeModal}  
  10.        isBlocking={true}  
  11.        containerClassName={contentStyles.container}  
  12.        dragOptions={this.state.isDraggable ? this._dragOptions : undefined}  
  13.      >  
  14.        <div className={contentStyles.header}>  
  15.          <span id={this._titleId}>Virtual Assistant</span>  
  16.          <IconButton  
  17.            styles={iconButtonStyles}  
  18.            iconProps={{ iconName: 'Cancel' }}  
  19.            ariaLabel="Close popup modal"  
  20.            onClick={this._closeModal as any}  
  21.          />  
  22.        </div>  
  23.        <div id={this._subtitleId} className={contentStyles.body}>  
  24.          <ReactWebChat directLine={this.state.directline} styleOptions={this.state.styleSetOptions} />  
  25.        </div>  
  26.      </Modal>  
  27.      </div>  
Step 6 - Test locally
 
To run your solution type "Gulp Serve" in the terminal window. It will prompt the new window with local host workbench url " https://localhost:4321/temp/workbench.html"
 
SPFX Bot Using Azure BotFramework SDKV4 With Luis And QnA Maker
 
Click icon to get pop up. Start typing the question as defined into Luis and QnA Maker and results start appearing without any delay.
 
SPFX Bot Using Azure BotFramework SDKV4 With Luis And QnA Maker