├── CSharp ├── .gitignore ├── AzureSql-CreateTable.sql ├── Library │ ├── Microsoft.Bot.Builder.Azure.Logging │ │ ├── AzureQueueActivityLogger.cs │ │ ├── AzureQueueReader.cs │ │ ├── IQueueReader.cs │ │ ├── LargeMessageMode.cs │ │ ├── Microsoft.Bot.Builder.Azure.Logging.csproj │ │ ├── Properties │ │ │ └── AssemblyInfo.cs │ │ ├── QueueActivityModule.cs │ │ ├── QueueLoggerSettings.cs │ │ ├── ServiceBusActivityLogger.cs │ │ ├── ServiceBusQueueReader.cs │ │ ├── app.config │ │ └── packages.config │ └── Microsoft.Bot.Builder.Azure │ │ ├── AzureBot.cs │ │ ├── AzureModule.cs │ │ ├── BotDataStoreBridge.cs │ │ ├── BotService.cs │ │ ├── DocumentDbBotDataStore.cs │ │ ├── Extensions.cs │ │ ├── Microsoft.Bot.Builder.Azure.csproj │ │ ├── Microsoft.Bot.Builder.Azure.nuspec │ │ ├── Properties │ │ └── AssemblyInfo.cs │ │ ├── SqlBotDataStore.cs │ │ ├── TableBotDataStore.cs │ │ ├── TableBotDataStore2.cs │ │ ├── TableLogger.cs │ │ ├── Utils.cs │ │ ├── app.config │ │ ├── createpackage.cmd │ │ └── packages.config ├── Microsoft.Bot.Builder.Azure.sln ├── Samples │ ├── AzureSql │ │ ├── Controllers │ │ │ └── MessagesController.cs │ │ ├── Dialogs │ │ │ └── EchoDialog.cs │ │ ├── Global.asax │ │ ├── Global.asax.cs │ │ ├── Microsoft.Bot.Sample.AzureSql.csproj │ │ ├── Properties │ │ │ └── AssemblyInfo.cs │ │ ├── README.md │ │ ├── Web.Debug.config │ │ ├── Web.Release.config │ │ ├── Web.config │ │ ├── default.htm │ │ └── packages.config │ ├── AzureTable │ │ ├── Controllers │ │ │ └── MessagesController.cs │ │ ├── Dialogs │ │ │ └── EchoDialog.cs │ │ ├── Global.asax │ │ ├── Global.asax.cs │ │ ├── Microsoft.Bot.Sample.AzureTable.csproj │ │ ├── Microsoft.Bot.Sample.AzureTable.csproj.user │ │ ├── Properties │ │ │ └── AssemblyInfo.cs │ │ ├── README.md │ │ ├── Web.Debug.config │ │ ├── Web.Release.config │ │ ├── Web.config │ │ └── packages.config │ └── DocumentDb │ │ ├── Controllers │ │ └── MessagesController.cs │ │ ├── Dialogs │ │ └── EchoDialog.cs │ │ ├── Global.asax │ │ ├── Global.asax.cs │ │ ├── Microsoft.Bot.Sample.DocumentDb.csproj │ │ ├── Microsoft.Bot.Sample.DocumentDb.csproj.user │ │ ├── Properties │ │ └── AssemblyInfo.cs │ │ ├── README.md │ │ ├── Web.Debug.config │ │ ├── Web.Release.config │ │ ├── Web.config │ │ └── packages.config ├── SimpleEchoBot │ ├── .gitignore │ ├── EchoBot.cs │ ├── EchoDialog.cs │ ├── SimpleEchoBot.csproj │ └── host.json ├── Tests │ └── Microsoft.Bot.Builder.Azure.Tests │ │ ├── BotDataStoreBridgeTests.cs │ │ ├── BotServiceTests.cs │ │ ├── DataStoreTests.cs │ │ ├── DialogTestBase.cs │ │ ├── DocumentDbDataStoreTests.cs │ │ ├── DocumentDbDeleter.cs │ │ ├── LoggerTestBase.cs │ │ ├── LoggerTests.cs │ │ ├── Microsoft.Bot.Builder.Azure.Tests.csproj │ │ ├── MockConnectorFactory.cs │ │ ├── Properties │ │ └── AssemblyInfo.cs │ │ ├── QueueLoggerTest.cs │ │ ├── StorageEmulatorRunner.cs │ │ ├── TableDataStore2Tests.cs │ │ ├── TableDataStoreTests.cs │ │ ├── app.config │ │ └── packages.config ├── buildtools │ ├── 35MSSharedLib1024.snk │ ├── SetVersionInAssemblyInfoCsFiles.ps1 │ └── updateAssemblyInfo.ps1 └── readme.md ├── Contributing.md ├── LICENSE ├── Node ├── .gitignore ├── .npmignore ├── docs │ ├── botframework │ │ ├── assets │ │ │ ├── css │ │ │ │ ├── main.css │ │ │ │ └── main.css.map │ │ │ ├── images │ │ │ │ ├── icons.png │ │ │ │ ├── icons@2x.png │ │ │ │ ├── widgets.png │ │ │ │ └── widgets@2x.png │ │ │ └── js │ │ │ │ ├── main.js │ │ │ │ └── modernizr.js │ │ ├── layouts │ │ │ └── default.hbs │ │ ├── partials │ │ │ ├── analytics.hbs │ │ │ ├── breadcrumb.hbs │ │ │ ├── comment.hbs │ │ │ ├── docs-header.hbs │ │ │ ├── footer.hbs │ │ │ ├── header.hbs │ │ │ ├── hierarchy.hbs │ │ │ ├── index.hbs │ │ │ ├── member.declaration.hbs │ │ │ ├── member.getterSetter.hbs │ │ │ ├── member.hbs │ │ │ ├── member.signature.body.hbs │ │ │ ├── member.signature.title.hbs │ │ │ ├── member.signatures.hbs │ │ │ ├── member.sources.hbs │ │ │ ├── members.group.hbs │ │ │ ├── members.hbs │ │ │ ├── ms-footer.hbs │ │ │ ├── navigation.hbs │ │ │ ├── parameter.hbs │ │ │ ├── toc.hbs │ │ │ ├── toc.root.hbs │ │ │ ├── type.hbs │ │ │ ├── typeAndParent.hbs │ │ │ └── typeParameters.hbs │ │ └── templates │ │ │ ├── index.hbs │ │ │ └── reflection.hbs │ └── build-docs.cmd ├── examples │ ├── feature-azureSql │ │ └── app.js │ ├── feature-azureTable │ │ └── app.js │ └── feature-documentDb │ │ └── app.js ├── lib │ ├── AzureBotStorage.js │ ├── AzureSqlClient.js │ ├── AzureTableClient.js │ ├── BotServiceConnector.js │ ├── Consts.js │ ├── DocumentDbClient.js │ ├── IStorageClient.js │ ├── botbuilder-azure.d.ts │ └── botbuilder-azure.js ├── npm-debug.log ├── package-lock.json ├── package.json ├── readme.md ├── src │ ├── AzureBotStorage.ts │ ├── AzureSqlClient.ts │ ├── AzureTableClient.ts │ ├── BotServiceConnector.ts │ ├── Consts.ts │ ├── DocumentDbClient.ts │ ├── IStorageClient.ts │ ├── botbuilder-azure.d.ts │ ├── botbuilder-azure.ts │ └── tsconfig.json └── test │ ├── .vscode │ ├── launch.json │ └── tasks.json │ ├── AzureTableClientTest.js │ ├── DocumentDbClientTest.js │ ├── Readme.md │ ├── TableBotStorageFaultTest.js │ ├── TableBotStorageTest.js │ ├── lib │ └── FaultyAzureTableClient.js │ └── src │ ├── FaultyAzureTableClient.ts │ └── tsconfig.json └── README.md /CSharp/.gitignore: -------------------------------------------------------------------------------- 1 | ## Ignore Visual Studio temporary files, build results, and 2 | ## files generated by popular Visual Studio add-ons. 3 | 4 | # User-specific files 5 | *.suo 6 | *.user 7 | *.userosscache 8 | *.sln.docstates 9 | 10 | # User-specific files (MonoDevelop/Xamarin Studio) 11 | *.userprefs 12 | 13 | # Build results 14 | [Dd]ebug/ 15 | [Dd]ebugPublic/ 16 | [Rr]elease/ 17 | [Rr]eleases/ 18 | x64/ 19 | x86/ 20 | build/ 21 | bld/ 22 | [Bb]in/ 23 | [Oo]bj/ 24 | ecf/ 25 | rcf/ 26 | 27 | # Visual Studio 2015 cache/options directory 28 | .vs/ 29 | 30 | # MSTest test Results 31 | [Tt]est[Rr]esult*/ 32 | [Bb]uild[Ll]og.* 33 | 34 | # NUNIT 35 | *.VisualState.xml 36 | TestResult.xml 37 | 38 | # Build Results of an ATL Project 39 | [Dd]ebugPS/ 40 | [Rr]eleasePS/ 41 | dlldata.c 42 | 43 | # DNX 44 | *.lock.json 45 | artifacts/ 46 | 47 | *_i.c 48 | *_p.c 49 | *_i.h 50 | *.ilk 51 | *.meta 52 | *.obj 53 | *.pch 54 | *.pdb 55 | *.pgc 56 | *.pgd 57 | *.rsp 58 | *.sbr 59 | *.tlb 60 | *.tli 61 | *.tlh 62 | *.tmp 63 | *.tmp_proj 64 | *.log 65 | *.vspscc 66 | *.vssscc 67 | .builds 68 | *.pidb 69 | *.svclog 70 | *.scc 71 | 72 | # Chutzpah Test files 73 | _Chutzpah* 74 | 75 | # Visual C++ cache files 76 | ipch/ 77 | *.aps 78 | *.ncb 79 | *.opensdf 80 | *.sdf 81 | *.cachefile 82 | 83 | # Visual Studio profiler 84 | *.psess 85 | *.vsp 86 | *.vspx 87 | 88 | # TFS 2012 Local Workspace 89 | $tf/ 90 | 91 | # Guidance Automation Toolkit 92 | *.gpState 93 | 94 | # ReSharper is a .NET coding add-in 95 | _ReSharper*/ 96 | *.[Rr]e[Ss]harper 97 | *.DotSettings.user 98 | 99 | # JustCode is a .NET coding add-in 100 | .JustCode 101 | 102 | # TeamCity is a build add-in 103 | _TeamCity* 104 | 105 | # DotCover is a Code Coverage Tool 106 | *.dotCover 107 | 108 | # NCrunch 109 | _NCrunch_* 110 | .*crunch*.local.xml 111 | 112 | # MightyMoose 113 | *.mm.* 114 | AutoTest.Net/ 115 | 116 | # Web workbench (sass) 117 | .sass-cache/ 118 | 119 | # Installshield output folder 120 | [Ee]xpress/ 121 | 122 | # DocProject is a documentation generator add-in 123 | DocProject/buildhelp/ 124 | DocProject/Help/*.HxT 125 | DocProject/Help/*.HxC 126 | DocProject/Help/*.hhc 127 | DocProject/Help/*.hhk 128 | DocProject/Help/*.hhp 129 | DocProject/Help/Html2 130 | DocProject/Help/html 131 | 132 | # Click-Once directory 133 | publish/ 134 | 135 | # Publish Web Output 136 | *.[Pp]ublish.xml 137 | ## TODO: Comment the next line if you want to checkin your 138 | ## web deploy settings but do note that will include unencrypted 139 | ## passwords 140 | #*.pubxml 141 | 142 | ## ignore imporeted publish xml files 143 | *intercom-botdirectory-scratch\ -\ FTP.pubxml 144 | *intercom-botdirectory-scratch\ -\ Web\ Deploy.pubxml 145 | 146 | *.publishproj 147 | 148 | # NuGet Packages 149 | *.nupkg 150 | # The packages folder can be ignored because of Package Restore 151 | **/packages/* 152 | # except build/, which is used as an MSBuild target. 153 | !**/packages/build/ 154 | # Uncomment if necessary however generally it will be regenerated when needed 155 | #!**/packages/repositories.config 156 | 157 | # Windows Azure Build Output 158 | csx/ 159 | *.build.csdef 160 | 161 | # Windows Store app package directory 162 | AppPackages/ 163 | 164 | # Visual Studio cache files 165 | # files ending in .cache can be ignored 166 | *.[Cc]ache 167 | # but keep track of directories ending in .cache 168 | !*.[Cc]ache/ 169 | 170 | # Others 171 | ClientBin/ 172 | [Ss]tyle[Cc]op.* 173 | ~$* 174 | *~ 175 | *.dbmdl 176 | *.dbproj.schemaview 177 | *.pfx 178 | *.publishsettings 179 | node_modules/ 180 | orleans.codegen.cs 181 | 182 | # RIA/Silverlight projects 183 | Generated_Code/ 184 | 185 | # Backup & report files from converting an old project file 186 | # to a newer Visual Studio version. Backup files are not needed, 187 | # because we have git ;-) 188 | _UpgradeReport_Files/ 189 | Backup*/ 190 | UpgradeLog*.XML 191 | UpgradeLog*.htm 192 | 193 | # SQL Server files 194 | *.mdf 195 | *.ldf 196 | 197 | # Business Intelligence projects 198 | *.rdl.data 199 | *.bim.layout 200 | *.bim_*.settings 201 | 202 | # Microsoft Fakes 203 | FakesAssemblies/ 204 | 205 | # Node.js Tools for Visual Studio 206 | .ntvs_analysis.dat 207 | 208 | # Visual Studio 6 build log 209 | *.plg 210 | 211 | # Visual Studio 6 workspace options file 212 | *.opt 213 | 214 | # LightSwitch generated files 215 | GeneratedArtifacts/ 216 | _Pvt_Extensions/ 217 | ModelManifest.xml 218 | /Microsoft.CodeDom.Providers.DotNetCompilerPlatform.dll 219 | /Microsoft.CodeDom.Providers.DotNetCompilerPlatform.xml 220 | /PublishScripts/Scripts/Deploy-AzureResourceGroup-5.ps1 221 | /PublishScripts 222 | 223 | 224 | 225 | 226 | 227 | 228 | 229 | 230 | 231 | # User-specific files 232 | Documentation/Doxygen_warnings.txt 233 | 234 | # Build results 235 | Documentation/docs/ 236 | 237 | # Azure publish profiles 238 | *.pubxml 239 | PublishProfiles/ 240 | -------------------------------------------------------------------------------- /CSharp/AzureSql-CreateTable.sql: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/microsoft/BotBuilder-Azure/51fa832dc243ffbfb34f741fb929f349e903ec06/CSharp/AzureSql-CreateTable.sql -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure.Logging/AzureQueueActivityLogger.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Text; 3 | using System.Threading.Tasks; 4 | using Microsoft.Bot.Builder.History; 5 | using Microsoft.Bot.Builder.Internals.Fibers; 6 | using Microsoft.Bot.Connector; 7 | using Microsoft.WindowsAzure.Storage.Queue; 8 | using Newtonsoft.Json; 9 | 10 | namespace Microsoft.Bot.Builder.Azure 11 | { 12 | /// 13 | /// Log activities to Azure Storage Queue. 14 | /// 15 | /// 16 | /// Activities are limited to size of Azure Storage queue payload. Disposition of larger messages is controlled by QueueLoggerSettings. 17 | /// for more information on limits see https://docs.microsoft.com/en-us/azure/service-bus-messaging/service-bus-azure-and-service-bus-queues-compared-contrasted 18 | /// 19 | public class AzureQueueActivityLogger : IActivityLogger 20 | { 21 | private readonly JsonSerializerSettings _jsonSerializerSettings; 22 | private readonly CloudQueue _cloudQueue; 23 | private readonly QueueLoggerSettings _queueLoggerSettings; 24 | 25 | private readonly float _cutCoefficient; 26 | 27 | /// 28 | /// Constructs an instance of AzureQueueActivityLogger 29 | /// 30 | /// Reference to a CloudQueue instance 31 | /// Settings informing the logger how to handle large messages and whether compression is required 32 | /// JSON serialziation settings used to write the formatted JSON message before adding to the queue 33 | public AzureQueueActivityLogger(CloudQueue cloudQueue, QueueLoggerSettings queueSettings = null, JsonSerializerSettings settings = null) 34 | { 35 | SetField.NotNull(out _cloudQueue, nameof(cloudQueue), cloudQueue); 36 | 37 | //set the defaults 38 | _queueLoggerSettings = queueSettings ?? new QueueLoggerSettings(); 39 | _jsonSerializerSettings = settings; 40 | _cutCoefficient = 1 - _queueLoggerSettings.MessageTrimRate; 41 | } 42 | 43 | /// 44 | /// Logs a single Activity message 45 | /// 46 | /// An activity to be logged 47 | /// 48 | /// thrown when message exceeds length limit 49 | public async Task LogAsync(IActivity activity) 50 | { 51 | var message = activity.AsMessageActivity(); 52 | 53 | var jsonMsg = JsonConvert.SerializeObject(message, _jsonSerializerSettings); 54 | var bytes = GetBytes(jsonMsg); 55 | 56 | if (_queueLoggerSettings.OverflowHanding == LargeMessageMode.Discard) 57 | { 58 | //if fails, do not do anything.... 59 | try 60 | { 61 | await _cloudQueue.AddMessageAsync(new CloudQueueMessage(bytes)); 62 | } 63 | catch 64 | { 65 | // ignored 66 | } 67 | } 68 | else if (_queueLoggerSettings.OverflowHanding == LargeMessageMode.Error) 69 | { 70 | //let it fail 71 | await _cloudQueue.AddMessageAsync(new CloudQueueMessage(bytes)); 72 | } 73 | else if (_queueLoggerSettings.OverflowHanding == LargeMessageMode.Trim) 74 | { 75 | do 76 | { 77 | try 78 | { 79 | await _cloudQueue.AddMessageAsync(new CloudQueueMessage(bytes)); 80 | return; 81 | } 82 | catch (Exception) 83 | { 84 | //cut off some of the text to fit 85 | message.Text = message.Text.Substring(0, (int)(message.Text.Length * _cutCoefficient)); 86 | jsonMsg = JsonConvert.SerializeObject(message, _jsonSerializerSettings); 87 | bytes = GetBytes(jsonMsg); 88 | } 89 | } while (true); 90 | } 91 | } 92 | 93 | byte[] GetBytes(string message) 94 | { 95 | return _queueLoggerSettings.CompressMessage ? message.Compress() : Encoding.UTF8.GetBytes(message); 96 | } 97 | } 98 | } -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure.Logging/AzureQueueReader.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Threading.Tasks; 4 | using Microsoft.Bot.Builder.Internals.Fibers; 5 | using Microsoft.Bot.Connector; 6 | using Microsoft.WindowsAzure.Storage.Queue; 7 | using Newtonsoft.Json; 8 | 9 | namespace Microsoft.Bot.Builder.Azure 10 | { 11 | /// 12 | /// Reads messages from an Azure Storage Queue 13 | /// 14 | public class AzureQueueReader : IQueueReader 15 | { 16 | private readonly CloudQueue _cloudQueue; 17 | private readonly QueueLoggerSettings _queueLoggerSettings; 18 | 19 | /// 20 | /// 21 | /// 22 | /// Reference to a CloudQueue instance 23 | /// Settings informing the logger how to handle large messages and whether compression is required 24 | public AzureQueueReader(CloudQueue cloudQueue, QueueLoggerSettings queueSettings = null) 25 | { 26 | SetField.NotNull(out _cloudQueue, nameof(cloudQueue), cloudQueue); 27 | 28 | //set the defaults 29 | _queueLoggerSettings = queueSettings ?? new QueueLoggerSettings(); 30 | } 31 | private Activity DeserializeItem(CloudQueueMessage msg) 32 | { 33 | string jsonActivity; 34 | 35 | //message is compressed 36 | if (_queueLoggerSettings.CompressMessage) 37 | jsonActivity = msg.AsBytes.Decompress(); 38 | else 39 | jsonActivity = msg.AsString; 40 | 41 | var data = JsonConvert.DeserializeObject(jsonActivity); 42 | 43 | return data; 44 | } 45 | /// 46 | /// Read a single activity message from the queue 47 | /// 48 | /// 49 | public IActivity Read() 50 | { 51 | return ReadAsync().GetAwaiter().GetResult(); 52 | } 53 | 54 | /// 55 | /// Read a single activity message from the queue, asynchronously 56 | /// 57 | /// 58 | public async Task ReadAsync() 59 | { 60 | var msg = await _cloudQueue.GetMessageAsync(); 61 | 62 | if (msg == null) 63 | return null; 64 | 65 | var data = DeserializeItem(msg); 66 | 67 | return data; 68 | } 69 | 70 | /// 71 | /// Queue may contain more than one message, read the {messageCount} of messages from the queue 72 | /// 73 | /// Maximum number of messages to return 74 | /// 75 | public List ReadBatch(int messageCount) 76 | { 77 | return ReadBatchAsync(messageCount).GetAwaiter().GetResult(); 78 | } 79 | 80 | /// 81 | /// Reads a batch of messages from the queue not to exceed the message count. 82 | /// 83 | /// Maximum number of messages to return 84 | /// This parameter is ignored 85 | /// 86 | public List ReadBatch(int messageCount, TimeSpan serviceWaitTime) 87 | { 88 | return ReadBatch(messageCount); 89 | } 90 | 91 | /// 92 | /// Reads a batch of messages from the queue not to exceed the message count. 93 | /// 94 | /// Maximum number of messages to return 95 | /// 96 | public async Task> ReadBatchAsync(int messageCount) 97 | { 98 | List batch = new List(); 99 | var messageBatch = await _cloudQueue.GetMessagesAsync(messageCount); 100 | 101 | foreach (var msg in messageBatch) 102 | { 103 | batch.Add(DeserializeItem(msg)); 104 | } 105 | 106 | return batch; 107 | } 108 | /// 109 | /// Reads a batch of messages from the queue not to exceed the message count. 110 | /// 111 | /// Maximum number of messages to return 112 | /// This parameter is ignored 113 | /// 114 | public Task> ReadBatchAsync(int messageCount, TimeSpan serviceWaitTime) 115 | { 116 | return ReadBatchAsync(messageCount); 117 | } 118 | } 119 | } 120 | -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure.Logging/IQueueReader.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Threading.Tasks; 4 | using Microsoft.Bot.Connector; 5 | 6 | namespace Microsoft.Bot.Builder.Azure 7 | { 8 | /// 9 | /// Interface for queue reader 10 | /// 11 | public interface IQueueReader 12 | { 13 | /// 14 | /// Read a single activity message from the queue 15 | /// 16 | IActivity Read(); 17 | /// 18 | /// Read a single activity message from the queue, asynchronously 19 | /// 20 | Task ReadAsync(); 21 | /// 22 | /// Reads a batch of messages from the queue not to exceed the message count. 23 | /// 24 | /// Maximum number of messages to return 25 | List ReadBatch(int messageCount); 26 | /// 27 | /// Reads a batch of messages from the queue not to exceed the message count. 28 | /// 29 | /// Maximum number of messages to return 30 | Task> ReadBatchAsync(int messageCount, TimeSpan serviceWaitTime); 31 | /// 32 | /// Reads a batch of messages from the queue not to exceed the message count, asynchronously 33 | /// 34 | /// Maximum number of messages to return 35 | Task> ReadBatchAsync(int messageCount); 36 | } 37 | } -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure.Logging/LargeMessageMode.cs: -------------------------------------------------------------------------------- 1 | namespace Microsoft.Bot.Builder.Azure 2 | { 3 | /// 4 | /// Enumeration for handling of large messages 5 | /// 6 | public enum LargeMessageMode 7 | { 8 | /// 9 | /// Drop the message if exceeds the length limit 10 | /// 11 | Discard, 12 | /// 13 | /// Limit the text to be within the allowed limits 14 | /// 15 | Trim, 16 | /// 17 | /// Throw an exception if message exceeds allowed limit 18 | /// 19 | Error 20 | } 21 | } -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure.Logging/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Runtime.CompilerServices; 3 | using System.Runtime.InteropServices; 4 | 5 | // General Information about an assembly is controlled through the following 6 | // set of attributes. Change these attribute values to modify the information 7 | // associated with an assembly. 8 | [assembly: AssemblyTitle("Microsoft.Bot.Builder.Azure.Logging")] 9 | [assembly: AssemblyDescription("")] 10 | [assembly: AssemblyConfiguration("")] 11 | [assembly: AssemblyCompany("")] 12 | [assembly: AssemblyProduct("Microsoft.Bot.Builder.Azure.Logging")] 13 | [assembly: AssemblyCopyright("Copyright © 2017")] 14 | [assembly: AssemblyTrademark("")] 15 | [assembly: AssemblyCulture("")] 16 | 17 | // Setting ComVisible to false makes the types in this assembly not visible 18 | // to COM components. If you need to access a type in this assembly from 19 | // COM, set the ComVisible attribute to true on that type. 20 | [assembly: ComVisible(false)] 21 | 22 | // The following GUID is for the ID of the typelib if this project is exposed to COM 23 | [assembly: Guid("f8fdcbfb-3a5d-41e4-8c3d-a158d8783b3e")] 24 | 25 | // Version information for an assembly consists of the following four values: 26 | // 27 | // Major Version 28 | // Minor Version 29 | // Build Number 30 | // Revision 31 | // 32 | // You can specify all the values or you can default the Build and Revision Numbers 33 | // by using the '*' as shown below: 34 | // [assembly: AssemblyVersion("1.0.*")] 35 | [assembly: AssemblyVersion("1.0.1.0")] 36 | [assembly: AssemblyFileVersion("1.0.1.0")] 37 | -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure.Logging/QueueLoggerSettings.cs: -------------------------------------------------------------------------------- 1 | namespace Microsoft.Bot.Builder.Azure 2 | { 3 | /// 4 | /// Logger setting to control compression and how to handle large messages 5 | /// 6 | public class QueueLoggerSettings 7 | { 8 | /// 9 | /// Creates an instance of QueueLoggerSettings with default settings 10 | /// 11 | public QueueLoggerSettings() 12 | { 13 | CompressMessage = false; 14 | OverflowHanding = LargeMessageMode.Discard; 15 | MessageTrimRate = 0.10f; 16 | } 17 | /// 18 | /// Informs logger to compress messages, default is false 19 | /// 20 | public bool CompressMessage { get; set; } 21 | /// 22 | /// Informs logger what to do with messages that exceed length limit, default is Discard 23 | /// 24 | public LargeMessageMode OverflowHanding { get; set; } 25 | 26 | //if Overflow is set to trim, MessageTrimRate controls how much string to trim at one time, default is 0.10 27 | public float MessageTrimRate; 28 | } 29 | } -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure.Logging/ServiceBusActivityLogger.cs: -------------------------------------------------------------------------------- 1 | using System.Text; 2 | using System.Threading.Tasks; 3 | using Microsoft.Bot.Builder.History; 4 | using Microsoft.Bot.Builder.Internals.Fibers; 5 | using Microsoft.Bot.Connector; 6 | using Microsoft.ServiceBus.Messaging; 7 | using Newtonsoft.Json; 8 | 9 | namespace Microsoft.Bot.Builder.Azure 10 | { 11 | /// 12 | /// Log activities to Service Bus Queue. 13 | /// 14 | /// 15 | /// Activities are limited to size of Service Bus queue payload. Disposition of larger messages is controlled by QueueLoggerSettings. 16 | /// for more information on limits see https://docs.microsoft.com/en-us/azure/service-bus-messaging/service-bus-azure-and-service-bus-queues-compared-contrasted 17 | /// 18 | public class ServiceBusActivityLogger : IActivityLogger 19 | { 20 | private readonly QueueClient _client; 21 | private readonly JsonSerializerSettings _jsonSerializerSettings; 22 | private readonly QueueLoggerSettings _queueLoggerSettings; 23 | 24 | //controls how much message we will keep after the cut 25 | private readonly float _cutCoefficient; 26 | 27 | /// 28 | /// Constructs an instance of ServiceBusActivityLogger 29 | /// 30 | /// Reference to a QueueClient instance 31 | /// Settings informing the logger how to handle large messages and whether compression is required 32 | /// JSON serialziation settings used to write the formatted JSON message before adding to the queue 33 | public ServiceBusActivityLogger(QueueClient client, QueueLoggerSettings queueSettings = null, 34 | JsonSerializerSettings settings = null) 35 | { 36 | 37 | SetField.NotNull(out _client, nameof(client), client); 38 | 39 | //set the defaults 40 | _queueLoggerSettings = queueSettings ?? new QueueLoggerSettings(); 41 | 42 | _jsonSerializerSettings = settings; 43 | _cutCoefficient = 1 - _queueLoggerSettings.MessageTrimRate; 44 | } 45 | 46 | byte[] GetBytes(string message) 47 | { 48 | return _queueLoggerSettings.CompressMessage ? message.Compress() : Encoding.UTF8.GetBytes(message); 49 | } 50 | 51 | /// 52 | /// Logs a single Activity message 53 | /// 54 | /// An activity to be logged 55 | /// 56 | /// thrown when message exceeds length limit 57 | public async Task LogAsync(IActivity activity) 58 | { 59 | var message = activity.AsMessageActivity(); 60 | 61 | string jsonMsg = JsonConvert.SerializeObject(message, _jsonSerializerSettings); 62 | var bytes = GetBytes(jsonMsg); 63 | 64 | if (_queueLoggerSettings.OverflowHanding == LargeMessageMode.Discard) 65 | { 66 | //if fails do not do anything.... 67 | try 68 | { 69 | await _client.SendAsync(new BrokeredMessage(bytes)); 70 | } 71 | catch 72 | { 73 | // ignored 74 | } 75 | } 76 | else if (_queueLoggerSettings.OverflowHanding == LargeMessageMode.Error) 77 | { 78 | //let it fail 79 | await _client.SendAsync(new BrokeredMessage(bytes)); 80 | } 81 | else if (_queueLoggerSettings.OverflowHanding == LargeMessageMode.Trim) 82 | { 83 | do 84 | { 85 | try 86 | { 87 | await _client.SendAsync(new BrokeredMessage(bytes)); 88 | return; 89 | } 90 | catch 91 | { 92 | //cut off some of the text to fit 93 | message.Text = message.Text.Substring(0, (int)(message.Text.Length * _cutCoefficient)); 94 | jsonMsg = JsonConvert.SerializeObject(message, _jsonSerializerSettings); 95 | bytes = GetBytes(jsonMsg); 96 | } 97 | 98 | } while (true); 99 | } 100 | } 101 | } 102 | } -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure.Logging/packages.config: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure/AzureBot.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Linq; 4 | using System.Reflection; 5 | using System.Text; 6 | using System.Threading.Tasks; 7 | using Microsoft.Bot.Builder.Dialogs; 8 | using Microsoft.Bot.Connector; 9 | 10 | namespace Microsoft.Bot.Builder.Azure 11 | { 12 | /// 13 | /// The azure bot utilities and helpers. 14 | /// 15 | /// 16 | /// This class is obsolete now. Use instead. 17 | /// 18 | [Obsolete("This class is obsolete. Use BotService instead.", false)] 19 | public static class AzureBot 20 | { 21 | /// 22 | /// The bot authenticator. 23 | /// 24 | public static BotAuthenticator Authenticator => BotService.Authenticator; 25 | 26 | /// 27 | /// Update the for azure bots. 28 | /// 29 | public static void Initialize() 30 | { 31 | BotService.Initialize(Assembly.GetCallingAssembly()); 32 | } 33 | } 34 | } 35 | -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure/BotDataStoreBridge.cs: -------------------------------------------------------------------------------- 1 | using Microsoft.Bot.Builder.Dialogs; 2 | using Microsoft.Bot.Builder.Dialogs.Internals; 3 | using Microsoft.Bot.Connector; 4 | using System; 5 | using System.Threading; 6 | using System.Threading.Tasks; 7 | using System.Web; 8 | 9 | namespace Microsoft.Bot.Builder.Azure 10 | { 11 | /// 12 | /// This bridge class should be used during a migration of data from one BotDataStore to another 13 | /// 14 | /// 15 | /// It works by reading from both source and target stores and only writing data to the new store. 16 | /// This allows live code to continue to work while a background job is migrating data from the source store to the target store. 17 | /// To use: deploy your bot using this dual data store while a background job is migrating the data from the 18 | /// source store to the target store. When the background migration job is done you can deploy your bot using the target store 19 | /// 20 | /// NOTE: migration job should ignore precondition failures on write, because if the record already exists in the new store it was migrated 21 | /// dynamically by the use of this class 22 | /// 23 | public class BotDataStoreBridge : IBotDataStore 24 | { 25 | private IBotDataStore sourceStore; 26 | private IBotDataStore targetStore; 27 | 28 | /// 29 | /// 30 | /// 31 | /// 32 | /// 33 | /// if true, a successful write to the target store will remove from the source 34 | public BotDataStoreBridge(IBotDataStore sourceStore, IBotDataStore targetStore) 35 | { 36 | this.sourceStore = sourceStore ?? throw new ArgumentNullException("sourceStore"); 37 | this.targetStore = targetStore ?? throw new ArgumentNullException("targetStore"); 38 | } 39 | 40 | public async Task LoadAsync(IAddress key, BotStoreType botStoreType, CancellationToken cancellationToken) 41 | { 42 | // read from both in parallel 43 | var sourceStoreReadTask = this.sourceStore.LoadAsync(key, botStoreType, cancellationToken); 44 | var targetStoreReadTask = this.targetStore.LoadAsync(key, botStoreType, cancellationToken); 45 | await Task.WhenAll(sourceStoreReadTask, targetStoreReadTask).ConfigureAwait(false); 46 | 47 | // if record isn't in targetStore yet, return sourceStore record 48 | if (String.IsNullOrEmpty(targetStoreReadTask.Result.ETag) || targetStoreReadTask.Result.ETag == "*") 49 | { 50 | // but with wildcard etag so save will create new record in target store 51 | sourceStoreReadTask.Result.ETag = "*"; 52 | return sourceStoreReadTask.Result; 53 | } 54 | return targetStoreReadTask.Result; 55 | } 56 | 57 | public async Task SaveAsync(IAddress key, BotStoreType botStoreType, BotData data, CancellationToken cancellationToken) 58 | { 59 | // Always save to target store 60 | await this.targetStore.SaveAsync(key, botStoreType, data, cancellationToken); 61 | } 62 | 63 | public Task FlushAsync(IAddress key, CancellationToken cancellationToken) 64 | { 65 | // always flush to target store (since we are only writing to target store) 66 | return this.targetStore.FlushAsync(key, cancellationToken); 67 | } 68 | } 69 | } 70 | -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure/Extensions.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Text.RegularExpressions; 4 | 5 | namespace Microsoft.Bot.Builder.Azure 6 | { 7 | internal static class StringExtensions 8 | { 9 | private static readonly Dictionary _DefaultReplacementsForCharactersDisallowedByAzure = new Dictionary() { { "/", "|s|" }, { @"\", "|b|" }, { "#", "|h|" }, { "?", "|q|" } }; 10 | 11 | /// 12 | /// Replaces the four characters disallowed in Azure keys with something more palatable. You can provide your own mapping if you don't like the defaults. 13 | /// 14 | internal static string SanitizeForAzureKeys(this string input, Dictionary replacements = null) 15 | { 16 | var repmap = replacements ?? _DefaultReplacementsForCharactersDisallowedByAzure; 17 | return input.Trim().Replace("/", repmap["/"]).Replace(@"\", repmap[@"\"]).Replace("#", repmap["#"]).Replace("?", repmap["?"]); 18 | } 19 | 20 | internal static string SanitizeTableName(this string input) 21 | { 22 | if (input.Length > 63) 23 | { 24 | input = input.Substring(0, 63); 25 | } 26 | input = Regex.Replace(input, @"[^a-zA-Z0-9]+", ""); 27 | return input; 28 | } 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure/Microsoft.Bot.Builder.Azure.nuspec: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | Microsoft.Bot.Builder.Azure 5 | $version$ 6 | Microsoft 7 | microsoft, BotFramework, nugetbotbuilder 8 | © Microsoft Corporation. All rights reserved. 9 | true 10 | https://github.com/Microsoft/BotBuilder-Azure/blob/master/LICENSE 11 | 12 | Provide Microsoft Azure extensions to the Microsoft Bot Builder. In particular this includes: 13 | * TableLogger -- Activity logger for table storage which allows recording and retrieving conversation activities. 14 | * ReplayTranscript -- Replay activity history on any channel. 15 | * AzureModule -- Module for setting up components for bot builder based on Azure dependencies 16 | * TableBotDataStore2 -- IBotDataStore implementation based on Azure table storage. 17 | * DocumentDbBotDataStore -- IBotDataStore implementation based on Azure table storage. 18 | * SqlBotDataStore -- IBotDataStore implementation based on Azure Sql Server. 19 | 20 | https://github.com/Microsoft/BotBuilder-Azure 21 | http://docs.botframework.com/images/bot_icon.png 22 | Microsoft Azure extensions for Microsoft Bot Builder. 23 | en-US 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Runtime.InteropServices; 3 | 4 | // General Information about an assembly is controlled through the following 5 | // set of attributes. Change these attribute values to modify the information 6 | // associated with an assembly. 7 | [assembly: AssemblyTitle("Microsoft.Bot.Builder.Azure")] 8 | [assembly: AssemblyDescription("")] 9 | [assembly: AssemblyConfiguration("")] 10 | [assembly: AssemblyCompany("")] 11 | [assembly: AssemblyProduct("Microsoft.Bot.Builder.Azure")] 12 | [assembly: AssemblyCopyright("Copyright © 2017")] 13 | [assembly: AssemblyTrademark("")] 14 | [assembly: AssemblyCulture("")] 15 | 16 | // Setting ComVisible to false makes the types in this assembly not visible 17 | // to COM components. If you need to access a type in this assembly from 18 | // COM, set the ComVisible attribute to true on that type. 19 | [assembly: ComVisible(false)] 20 | 21 | // The following GUID is for the ID of the typelib if this project is exposed to COM 22 | [assembly: Guid("77299f9c-8f49-4839-b7ea-55ba726321d5")] 23 | 24 | // Version information for an assembly consists of the following four values: 25 | // 26 | // Major Version 27 | // Minor Version 28 | // Build Number 29 | // Revision 30 | // 31 | // You can specify all the values or you can default the Build and Revision Numbers 32 | // by using the '*' as shown below: 33 | // [assembly: AssemblyVersion("1.0.*")] 34 | [assembly: AssemblyVersion("3.16.3.0")] 35 | [assembly: AssemblyFileVersion("3.16.3.0")] 36 | 37 | //[assembly: AssemblyKeyFileAttribute(@"..\\..\\buildtools\\35MSSharedLib1024.snk")] 38 | //[assembly: AssemblyDelaySignAttribute(true)] 39 | -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure/createpackage.cmd: -------------------------------------------------------------------------------- 1 | @echo off 2 | echo *** Building Microsoft.Bot.Builder.Azure 3 | setlocal 4 | setlocal enabledelayedexpansion 5 | setlocal enableextensions 6 | set errorlevel=0 7 | mkdir ..\nuget 8 | erase /s ..\nuget\Microsoft.Bot.Builder.Azure*nupkg 9 | msbuild /property:Configuration=release Microsoft.Bot.Builder.Azure.csproj 10 | for /f %%v in ('powershell -noprofile "(Get-Command .\bin\release\Microsoft.Bot.Builder.dll).FileVersionInfo.FileVersion"') do set builder=%%v 11 | for /f %%v in ('powershell -noprofile "(Get-Command .\bin\release\Microsoft.Bot.Builder.History.dll).FileVersionInfo.FileVersion"') do set history=%%v 12 | for /f %%v in ('powershell -noprofile "(Get-Command .\bin\release\Microsoft.Bot.Builder.Azure.dll).FileVersionInfo.FileVersion"') do set version=%%v 13 | ..\..\packages\NuGet.CommandLine.3.4.3\tools\NuGet.exe pack Microsoft.Bot.Builder.Azure.nuspec -symbols -properties version=%version%;history=%history%;builder=%builder% -OutputDirectory ..\nuget 14 | echo *** Finished building Microsoft.Bot.Builder.Azure 15 | 16 | -------------------------------------------------------------------------------- /CSharp/Library/Microsoft.Bot.Builder.Azure/packages.config: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureSql/Controllers/MessagesController.cs: -------------------------------------------------------------------------------- 1 | using System.Net; 2 | using System.Net.Http; 3 | using System.Threading.Tasks; 4 | using System.Web.Http; 5 | using Microsoft.Bot.Builder.Dialogs; 6 | using Microsoft.Bot.Connector; 7 | 8 | namespace Microsoft.Bot.Sample.AzureSql 9 | { 10 | [BotAuthentication] 11 | public class MessagesController : ApiController 12 | { 13 | /// 14 | /// POST: api/Messages 15 | /// Receive a message from a user and reply to it 16 | /// 17 | public async Task Post([FromBody]Activity activity) 18 | { 19 | if (activity.Type == ActivityTypes.Message) 20 | { 21 | await Conversation.SendAsync(activity, () => new Dialogs.EchoDialog()); 22 | } 23 | else 24 | { 25 | HandleSystemMessage(activity); 26 | } 27 | var response = Request.CreateResponse(HttpStatusCode.OK); 28 | return response; 29 | } 30 | 31 | private Activity HandleSystemMessage(Activity message) 32 | { 33 | if (message.Type == ActivityTypes.DeleteUserData) 34 | { 35 | // Implement user deletion here 36 | // If we handle user deletion, return a real message 37 | } 38 | else if (message.Type == ActivityTypes.ConversationUpdate) 39 | { 40 | // Handle conversation state changes, like members being added and removed 41 | // Use Activity.MembersAdded and Activity.MembersRemoved and Activity.Action for info 42 | // Not available in all channels 43 | } 44 | else if (message.Type == ActivityTypes.ContactRelationUpdate) 45 | { 46 | // Handle add/remove from contact lists 47 | // Activity.From + Activity.Action represent what happened 48 | } 49 | else if (message.Type == ActivityTypes.Typing) 50 | { 51 | // Handle knowing tha the user is typing 52 | } 53 | else if (message.Type == ActivityTypes.Ping) 54 | { 55 | } 56 | 57 | return null; 58 | } 59 | } 60 | } -------------------------------------------------------------------------------- /CSharp/Samples/AzureSql/Dialogs/EchoDialog.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Threading.Tasks; 3 | using Microsoft.Bot.Builder.Dialogs; 4 | using Microsoft.Bot.Connector; 5 | using Microsoft.Bot.Builder.Dialogs.Internals; 6 | 7 | namespace Microsoft.Bot.Sample.AzureSql.Dialogs 8 | { 9 | [Serializable] 10 | public class EchoDialog : IDialog 11 | { 12 | public async Task StartAsync(IDialogContext context) 13 | { 14 | context.Wait(MessageReceivedAsync); 15 | } 16 | 17 | public async Task MessageReceivedAsync(IDialogContext context, IAwaitable argument) 18 | { 19 | var message = await argument; 20 | await context.PostAsync("You said: " + message.Text); 21 | context.Wait(MessageReceivedAsync); 22 | } 23 | } 24 | } -------------------------------------------------------------------------------- /CSharp/Samples/AzureSql/Global.asax: -------------------------------------------------------------------------------- 1 | <%@ Application CodeBehind="Global.asax.cs" Inherits="Microsoft.Bot.Sample.AzureSql.Global" Language="C#" %> 2 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureSql/Global.asax.cs: -------------------------------------------------------------------------------- 1 | using Autofac; 2 | using Autofac.Integration.WebApi; 3 | using Microsoft.Bot.Builder.Azure; 4 | using Microsoft.Bot.Builder.Dialogs; 5 | using Microsoft.Bot.Builder.Dialogs.Internals; 6 | using Microsoft.Bot.Connector; 7 | using Microsoft.Bot.Sample.AzureSql.Dialogs; 8 | using System; 9 | using System.Configuration; 10 | using System.Reflection; 11 | using System.Web.Http; 12 | 13 | namespace Microsoft.Bot.Sample.AzureSql 14 | { 15 | public class Global : System.Web.HttpApplication 16 | { 17 | protected void Application_Start(object sender, EventArgs e) 18 | { 19 | { 20 | var config = GlobalConfiguration.Configuration; 21 | 22 | Conversation.UpdateContainer( 23 | builder => 24 | { 25 | builder.RegisterModule(new AzureModule(Assembly.GetExecutingAssembly())); 26 | 27 | var store = new SqlBotDataStore(ConfigurationManager.ConnectionStrings["BotDataContextConnectionString"].ConnectionString); 28 | 29 | builder.Register(c => store) 30 | .Keyed>(AzureModule.Key_DataStore) 31 | .AsSelf() 32 | .SingleInstance(); 33 | 34 | 35 | // Register your Web API controllers. 36 | builder.RegisterApiControllers(Assembly.GetExecutingAssembly()); 37 | builder.RegisterWebApiFilterProvider(config); 38 | 39 | }); 40 | 41 | config.DependencyResolver = new AutofacWebApiDependencyResolver(Conversation.Container); 42 | } 43 | 44 | // WebApiConfig stuff 45 | GlobalConfiguration.Configure(config => 46 | { 47 | config.MapHttpAttributeRoutes(); 48 | 49 | config.Routes.MapHttpRoute( 50 | name: "DefaultApi", 51 | routeTemplate: "api/{controller}/{id}", 52 | defaults: new { id = RouteParameter.Optional } 53 | ); 54 | }); 55 | } 56 | 57 | public static ILifetimeScope FindContainer() 58 | { 59 | var config = GlobalConfiguration.Configuration; 60 | var resolver = (AutofacWebApiDependencyResolver)config.DependencyResolver; 61 | return resolver.Container; 62 | } 63 | } 64 | } 65 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureSql/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Runtime.CompilerServices; 3 | using System.Runtime.InteropServices; 4 | 5 | // General Information about an assembly is controlled through the following 6 | // set of attributes. Change these attribute values to modify the information 7 | // associated with an assembly. 8 | [assembly: AssemblyTitle("Microsoft.Bot.Sample.AzureSql")] 9 | [assembly: AssemblyDescription("")] 10 | [assembly: AssemblyConfiguration("")] 11 | [assembly: AssemblyCompany("")] 12 | [assembly: AssemblyProduct("Microsoft.Bot.Sample.AzureSql")] 13 | [assembly: AssemblyCopyright("Copyright © 2017")] 14 | [assembly: AssemblyTrademark("")] 15 | [assembly: AssemblyCulture("")] 16 | 17 | // Setting ComVisible to false makes the types in this assembly not visible 18 | // to COM components. If you need to access a type in this assembly from 19 | // COM, set the ComVisible attribute to true on that type. 20 | [assembly: ComVisible(false)] 21 | 22 | // The following GUID is for the ID of the typelib if this project is exposed to COM 23 | [assembly: Guid("18c42588-d8f0-48a9-a7af-02a5bf8252a9")] 24 | 25 | // Version information for an assembly consists of the following four values: 26 | // 27 | // Major Version 28 | // Minor Version 29 | // Build Number 30 | // Revision 31 | // 32 | // You can specify all the values or you can default the Revision and Build Numbers 33 | // by using the '*' as shown below: 34 | [assembly: AssemblyVersion("1.0.0.0")] 35 | [assembly: AssemblyFileVersion("1.0.0.0")] 36 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureSql/README.md: -------------------------------------------------------------------------------- 1 | # Azure Sql Sample 2 | 3 | This simple echo bots illustrates how to use your own Azure Sql Storage to store the bot state. 4 | 5 | To use Azure Sql, we configure the Autofac Dependency Injection in [Global.asax](Global.asax.cs). Particularly the following is the piece of code that configures injection of Azure Sql Storage: 6 | 7 | ```csharp 8 | var store = new SqlBotDataStore(ConfigurationManager.ConnectionStrings["BotDataContextConnectionString"].ConnectionString); 9 | builder.Register(c => store) 10 | .Keyed>(AzureModule.Key_DataStore) 11 | .AsSelf() 12 | .SingleInstance(); 13 | ``` 14 | 15 | Note that the connection string should be in the web.config: 16 | 17 | ```xml 18 | 19 | 22 | 23 | ``` -------------------------------------------------------------------------------- /CSharp/Samples/AzureSql/Web.Debug.config: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 17 | 18 | 29 | 30 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureSql/Web.Release.config: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 17 | 18 | 19 | 30 | 31 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureSql/default.htm: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 |

Microsoft.Bot.Sample.AzureSql

9 |

Describe your bot here and your terms of use etc.

10 |

Visit Bot Framework to register your bot. When you register it, remember to set your bot's endpoint to

https://your_bots_hostname/api/messages

11 | 12 | 13 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureSql/packages.config: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureTable/Controllers/MessagesController.cs: -------------------------------------------------------------------------------- 1 | using Autofac; 2 | using Microsoft.Bot.Builder.Dialogs.Internals; 3 | using Microsoft.Bot.Builder.Internals.Fibers; 4 | using Microsoft.Bot.Connector; 5 | using System; 6 | using System.Collections.Generic; 7 | using System.Linq; 8 | using System.Net; 9 | using System.Net.Http; 10 | using System.Threading; 11 | using System.Threading.Tasks; 12 | using System.Web.Http; 13 | using System.Web.Http.Description; 14 | using Microsoft.Bot.Builder.Dialogs; 15 | using Microsoft.Bot.Sample.AzureTable.Dialogs; 16 | 17 | namespace Microsoft.Bot.Sample.AzureTable.Controllers 18 | { 19 | // Autofac provides a mechanism to inject ActionFilterAttributes from the container 20 | // but seems to require the implementation of special interfaces 21 | // https://github.com/autofac/Autofac.WebApi/issues/6 22 | [BotAuthentication] 23 | public class MessagesController : ApiController 24 | { 25 | // TODO: "service locator" 26 | private readonly ILifetimeScope scope; 27 | public MessagesController(ILifetimeScope scope) 28 | { 29 | SetField.NotNull(out this.scope, nameof(scope), scope); 30 | } 31 | 32 | /// 33 | /// POST: api/Messages 34 | /// receive a message from a user and send replies 35 | /// 36 | /// 37 | [ResponseType(typeof(void))] 38 | public virtual async Task Post([FromBody] Activity activity) 39 | { 40 | // check if activity is of type message 41 | if (activity != null && activity.GetActivityType() == ActivityTypes.Message) 42 | { 43 | await Conversation.SendAsync(activity, () => new EchoDialog()); 44 | } 45 | else 46 | { 47 | HandleSystemMessage(activity); 48 | } 49 | return new HttpResponseMessage(System.Net.HttpStatusCode.Accepted); 50 | } 51 | 52 | private Activity HandleSystemMessage(Activity message) 53 | { 54 | if (message.Type == ActivityTypes.DeleteUserData) 55 | { 56 | // Implement user deletion here 57 | // If we handle user deletion, return a real message 58 | } 59 | else if (message.Type == ActivityTypes.ConversationUpdate) 60 | { 61 | // Handle conversation state changes, like members being added and removed 62 | // Use Activity.MembersAdded and Activity.MembersRemoved and Activity.Action for info 63 | // Not available in all channels 64 | } 65 | else if (message.Type == ActivityTypes.ContactRelationUpdate) 66 | { 67 | // Handle add/remove from contact lists 68 | // Activity.From + Activity.Action represent what happened 69 | } 70 | else if (message.Type == ActivityTypes.Typing) 71 | { 72 | // Handle knowing tha the user is typing 73 | } 74 | else if (message.Type == ActivityTypes.Ping) 75 | { 76 | } 77 | 78 | return null; 79 | } 80 | } 81 | } -------------------------------------------------------------------------------- /CSharp/Samples/AzureTable/Dialogs/EchoDialog.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Linq; 4 | using System.Threading.Tasks; 5 | using System.Web; 6 | using Microsoft.Bot.Builder.Dialogs; 7 | using Microsoft.Bot.Connector; 8 | 9 | namespace Microsoft.Bot.Sample.AzureTable.Dialogs 10 | { 11 | [Serializable] 12 | public class EchoDialog : IDialog 13 | { 14 | public async Task StartAsync(IDialogContext context) 15 | { 16 | context.Wait(MessageReceivedAsync); 17 | } 18 | 19 | public async Task MessageReceivedAsync(IDialogContext context, IAwaitable argument) 20 | { 21 | var message = await argument; 22 | await context.PostAsync("You said: " + message.Text); 23 | context.Wait(MessageReceivedAsync); 24 | } 25 | } 26 | } -------------------------------------------------------------------------------- /CSharp/Samples/AzureTable/Global.asax: -------------------------------------------------------------------------------- 1 | <%@ Application CodeBehind="Global.asax.cs" Inherits="Microsoft.Bot.Sample.AzureTable.Global" Language="C#" %> 2 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureTable/Global.asax.cs: -------------------------------------------------------------------------------- 1 | using Autofac; 2 | using Autofac.Integration.WebApi; 3 | using Microsoft.Bot.Builder.Azure; 4 | using Microsoft.Bot.Builder.Dialogs.Internals; 5 | using System; 6 | using System.Collections.Generic; 7 | using System.Globalization; 8 | using System.Linq; 9 | using System.Reflection; 10 | using System.Web.Http; 11 | using Microsoft.Bot.Builder.Dialogs; 12 | using Microsoft.Bot.Connector; 13 | using Microsoft.Bot.Sample.AzureTable.Controllers; 14 | using Microsoft.Bot.Sample.AzureTable.Dialogs; 15 | using Microsoft.WindowsAzure.Storage; 16 | 17 | 18 | namespace Microsoft.Bot.Sample.AzureTable 19 | { 20 | public class Global : System.Web.HttpApplication 21 | { 22 | protected void Application_Start(object sender, EventArgs e) 23 | { 24 | { 25 | var config = GlobalConfiguration.Configuration; 26 | Conversation.UpdateContainer( 27 | builder => 28 | { 29 | builder.RegisterModule(new AzureModule(Assembly.GetExecutingAssembly())); 30 | 31 | var store = new TableBotDataStore(CloudStorageAccount.DevelopmentStorageAccount); 32 | builder.Register(c => store) 33 | .Keyed>(AzureModule.Key_DataStore) 34 | .AsSelf() 35 | .SingleInstance(); 36 | 37 | // Register your Web API controllers. 38 | builder.RegisterApiControllers(Assembly.GetExecutingAssembly()); 39 | builder.RegisterWebApiFilterProvider(config); 40 | 41 | }); 42 | 43 | config.DependencyResolver = new AutofacWebApiDependencyResolver(Conversation.Container); 44 | } 45 | 46 | // WebApiConfig stuff 47 | GlobalConfiguration.Configure(config => 48 | { 49 | config.MapHttpAttributeRoutes(); 50 | 51 | config.Routes.MapHttpRoute( 52 | name: "DefaultApi", 53 | routeTemplate: "api/{controller}/{id}", 54 | defaults: new { id = RouteParameter.Optional } 55 | ); 56 | }); 57 | } 58 | 59 | public static ILifetimeScope FindContainer() 60 | { 61 | var config = GlobalConfiguration.Configuration; 62 | var resolver = (AutofacWebApiDependencyResolver)config.DependencyResolver; 63 | return resolver.Container; 64 | } 65 | } 66 | } -------------------------------------------------------------------------------- /CSharp/Samples/AzureTable/Microsoft.Bot.Sample.AzureTable.csproj.user: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | true 5 | ShowAllFiles 6 | 7 | 8 | 9 | 10 | 11 | 12 | Debug|Any CPU 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | CurrentPage 21 | True 22 | False 23 | False 24 | False 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | True 34 | True 35 | 36 | 37 | 38 | 39 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureTable/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Runtime.CompilerServices; 3 | using System.Runtime.InteropServices; 4 | 5 | // General Information about an assembly is controlled through the following 6 | // set of attributes. Change these attribute values to modify the information 7 | // associated with an assembly. 8 | [assembly: AssemblyTitle("Microsoft.Bot.Sample.AzureTable")] 9 | [assembly: AssemblyDescription("")] 10 | [assembly: AssemblyConfiguration("")] 11 | [assembly: AssemblyCompany("")] 12 | [assembly: AssemblyProduct("Microsoft.Bot.Sample.AzureTable")] 13 | [assembly: AssemblyCopyright("Copyright © 2017")] 14 | [assembly: AssemblyTrademark("")] 15 | [assembly: AssemblyCulture("")] 16 | 17 | // Setting ComVisible to false makes the types in this assembly not visible 18 | // to COM components. If you need to access a type in this assembly from 19 | // COM, set the ComVisible attribute to true on that type. 20 | [assembly: ComVisible(false)] 21 | 22 | // The following GUID is for the ID of the typelib if this project is exposed to COM 23 | [assembly: Guid("d414f82f-c102-45b1-979c-d905d278c34a")] 24 | 25 | // Version information for an assembly consists of the following four values: 26 | // 27 | // Major Version 28 | // Minor Version 29 | // Build Number 30 | // Revision 31 | // 32 | // You can specify all the values or you can default the Revision and Build Numbers 33 | // by using the '*' as shown below: 34 | [assembly: AssemblyVersion("1.0.0.0")] 35 | [assembly: AssemblyFileVersion("1.0.0.0")] 36 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureTable/README.md: -------------------------------------------------------------------------------- 1 | # Azure Table Sample 2 | 3 | This simple echo bots illustrates how to use your own Azure Table Storage to store the bot state. 4 | 5 | To use Azure Table Store, we configure the Autofac Dependency Injection in [Global.asax](Global.asax.cs). Particularly the following is the piece of code that configures injection of Azure Table Storage: 6 | 7 | ```csharp 8 | var store = new TableBotDataStore(CloudStorageAccount.DevelopmentStorageAccount); 9 | builder.Register(c => store) 10 | .Keyed>(AzureModule.Key_DataStore) 11 | .AsSelf() 12 | .SingleInstance(); 13 | ``` 14 | 15 | Note that instead of passing ```csharp CloudStorageAccount.DevelopmentStorageAccount```, real Azure Storage Table credentials can be passed to configure an Azure storage account. 16 | 17 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureTable/Web.Debug.config: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 17 | 18 | 29 | 30 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureTable/Web.Release.config: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 17 | 18 | 19 | 30 | 31 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureTable/Web.config: -------------------------------------------------------------------------------- 1 |  2 | 6 | 7 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | -------------------------------------------------------------------------------- /CSharp/Samples/AzureTable/packages.config: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | -------------------------------------------------------------------------------- /CSharp/Samples/DocumentDb/Controllers/MessagesController.cs: -------------------------------------------------------------------------------- 1 | using Autofac; 2 | using Microsoft.Bot.Builder.Dialogs.Internals; 3 | using Microsoft.Bot.Builder.Internals.Fibers; 4 | using Microsoft.Bot.Connector; 5 | using System; 6 | using System.Collections.Generic; 7 | using System.Linq; 8 | using System.Net; 9 | using System.Net.Http; 10 | using System.Threading; 11 | using System.Threading.Tasks; 12 | using System.Web.Http; 13 | using System.Web.Http.Description; 14 | using Microsoft.Bot.Builder.Dialogs; 15 | using Microsoft.Bot.Sample.DocumentDb.Dialogs; 16 | 17 | namespace Microsoft.Bot.Sample.DocumentDb.Controllers 18 | { 19 | // Autofac provides a mechanism to inject ActionFilterAttributes from the container 20 | // but seems to require the implementation of special interfaces 21 | // https://github.com/autofac/Autofac.WebApi/issues/6 22 | [BotAuthentication] 23 | public class MessagesController : ApiController 24 | { 25 | // TODO: "service locator" 26 | private readonly ILifetimeScope scope; 27 | public MessagesController(ILifetimeScope scope) 28 | { 29 | SetField.NotNull(out this.scope, nameof(scope), scope); 30 | } 31 | /// 32 | /// POST: api/Messages 33 | /// receive a message from a user and send replies 34 | /// 35 | /// 36 | [ResponseType(typeof(void))] 37 | public virtual async Task Post([FromBody] Activity activity) 38 | { 39 | // check if activity is of type message 40 | if (activity != null && activity.GetActivityType() == ActivityTypes.Message) 41 | { 42 | await Conversation.SendAsync(activity, () => new EchoDialog()); 43 | } 44 | else 45 | { 46 | HandleSystemMessage(activity); 47 | } 48 | return new HttpResponseMessage(System.Net.HttpStatusCode.Accepted); 49 | } 50 | 51 | private Activity HandleSystemMessage(Activity message) 52 | { 53 | if (message.Type == ActivityTypes.DeleteUserData) 54 | { 55 | // Implement user deletion here 56 | // If we handle user deletion, return a real message 57 | } 58 | else if (message.Type == ActivityTypes.ConversationUpdate) 59 | { 60 | // Handle conversation state changes, like members being added and removed 61 | // Use Activity.MembersAdded and Activity.MembersRemoved and Activity.Action for info 62 | // Not available in all channels 63 | } 64 | else if (message.Type == ActivityTypes.ContactRelationUpdate) 65 | { 66 | // Handle add/remove from contact lists 67 | // Activity.From + Activity.Action represent what happened 68 | } 69 | else if (message.Type == ActivityTypes.Typing) 70 | { 71 | // Handle knowing tha the user is typing 72 | } 73 | else if (message.Type == ActivityTypes.Ping) 74 | { 75 | } 76 | 77 | return null; 78 | } 79 | } 80 | } -------------------------------------------------------------------------------- /CSharp/Samples/DocumentDb/Dialogs/EchoDialog.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Linq; 4 | using System.Threading.Tasks; 5 | using System.Web; 6 | using Microsoft.Bot.Builder.Dialogs; 7 | using Microsoft.Bot.Connector; 8 | 9 | namespace Microsoft.Bot.Sample.DocumentDb.Dialogs 10 | { 11 | [Serializable] 12 | public class EchoDialog : IDialog 13 | { 14 | public async Task StartAsync(IDialogContext context) 15 | { 16 | context.Wait(MessageReceivedAsync); 17 | } 18 | 19 | public async Task MessageReceivedAsync(IDialogContext context, IAwaitable argument) 20 | { 21 | var message = await argument; 22 | await context.PostAsync("You said: " + message.Text); 23 | context.Wait(MessageReceivedAsync); 24 | } 25 | } 26 | 27 | } -------------------------------------------------------------------------------- /CSharp/Samples/DocumentDb/Global.asax: -------------------------------------------------------------------------------- 1 | <%@ Application CodeBehind="Global.asax.cs" Inherits="Microsoft.Bot.Sample.DocumentDb.Global" Language="C#" %> 2 | -------------------------------------------------------------------------------- /CSharp/Samples/DocumentDb/Global.asax.cs: -------------------------------------------------------------------------------- 1 | using Autofac; 2 | using Autofac.Integration.WebApi; 3 | using Microsoft.Bot.Builder.Azure; 4 | using Microsoft.Bot.Builder.Dialogs.Internals; 5 | using System; 6 | using System.Collections.Generic; 7 | using System.Globalization; 8 | using System.Linq; 9 | using System.Reflection; 10 | using System.Web.Http; 11 | using Microsoft.Bot.Builder.Dialogs; 12 | using Microsoft.Bot.Connector; 13 | using Microsoft.Bot.Sample.DocumentDb.Controllers; 14 | using Microsoft.Bot.Sample.DocumentDb.Dialogs; 15 | using Microsoft.WindowsAzure.Storage; 16 | 17 | 18 | namespace Microsoft.Bot.Sample.DocumentDb 19 | { 20 | public class Global : System.Web.HttpApplication 21 | { 22 | protected void Application_Start(object sender, EventArgs e) 23 | { 24 | { 25 | //Using the local DocDbEmulator, which should be installed and started. Otherwise, edit the docDbEmulatorUri and docDbEmulatorKey variables to your DocDb database 26 | //Reference: https://docs.microsoft.com/en-us/azure/documentdb/documentdb-nosql-local-emulator 27 | 28 | //Fixed docDb emulator local Uri. 29 | Uri docDbEmulatorUri = new Uri("https://localhost:8081"); 30 | 31 | //Fixed docDb emulator key 32 | const string docDbEmulatorKey = "C2y6yDjf5/R+ob0N8A7Cgv30VRDJIWEHLM+4QDU5DE2nQ9nDuVTqobD4b8mGGyPMbIZnqyMsEcaGQy67XIw/Jw=="; 33 | 34 | var config = GlobalConfiguration.Configuration; 35 | 36 | Conversation.UpdateContainer( 37 | builder => 38 | { 39 | builder.RegisterModule(new AzureModule(Assembly.GetExecutingAssembly())); 40 | 41 | var store = new DocumentDbBotDataStore(docDbEmulatorUri, docDbEmulatorKey); 42 | 43 | builder.Register(c => store) 44 | .Keyed>(AzureModule.Key_DataStore) 45 | .AsSelf() 46 | .SingleInstance(); 47 | 48 | // Register your Web API controllers. 49 | builder.RegisterApiControllers(Assembly.GetExecutingAssembly()); 50 | builder.RegisterWebApiFilterProvider(config); 51 | 52 | }); 53 | 54 | config.DependencyResolver = new AutofacWebApiDependencyResolver(Conversation.Container); 55 | } 56 | 57 | // WebApiConfig stuff 58 | GlobalConfiguration.Configure(config => 59 | { 60 | config.MapHttpAttributeRoutes(); 61 | 62 | config.Routes.MapHttpRoute( 63 | name: "DefaultApi", 64 | routeTemplate: "api/{controller}/{id}", 65 | defaults: new { id = RouteParameter.Optional } 66 | ); 67 | }); 68 | } 69 | 70 | public static ILifetimeScope FindContainer() 71 | { 72 | var config = GlobalConfiguration.Configuration; 73 | var resolver = (AutofacWebApiDependencyResolver)config.DependencyResolver; 74 | return resolver.Container; 75 | } 76 | } 77 | } -------------------------------------------------------------------------------- /CSharp/Samples/DocumentDb/Microsoft.Bot.Sample.DocumentDb.csproj.user: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | true 5 | ShowAllFiles 6 | 7 | 8 | 9 | 10 | 11 | 12 | Debug|Any CPU 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | CurrentPage 21 | True 22 | False 23 | False 24 | False 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | True 34 | True 35 | 36 | 37 | 38 | 39 | -------------------------------------------------------------------------------- /CSharp/Samples/DocumentDb/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Runtime.CompilerServices; 3 | using System.Runtime.InteropServices; 4 | 5 | // General Information about an assembly is controlled through the following 6 | // set of attributes. Change these attribute values to modify the information 7 | // associated with an assembly. 8 | [assembly: AssemblyTitle("Microsoft.Bot.Sample.DocumentDb")] 9 | [assembly: AssemblyDescription("")] 10 | [assembly: AssemblyConfiguration("")] 11 | [assembly: AssemblyCompany("")] 12 | [assembly: AssemblyProduct("Microsoft.Bot.Sample.DocumentDb")] 13 | [assembly: AssemblyCopyright("Copyright © 2017")] 14 | [assembly: AssemblyTrademark("")] 15 | [assembly: AssemblyCulture("")] 16 | 17 | // Setting ComVisible to false makes the types in this assembly not visible 18 | // to COM components. If you need to access a type in this assembly from 19 | // COM, set the ComVisible attribute to true on that type. 20 | [assembly: ComVisible(false)] 21 | 22 | // The following GUID is for the ID of the typelib if this project is exposed to COM 23 | [assembly: Guid("d414f82f-c102-45b1-979c-d905d278c34a")] 24 | 25 | // Version information for an assembly consists of the following four values: 26 | // 27 | // Major Version 28 | // Minor Version 29 | // Build Number 30 | // Revision 31 | // 32 | // You can specify all the values or you can default the Revision and Build Numbers 33 | // by using the '*' as shown below: 34 | [assembly: AssemblyVersion("1.0.0.0")] 35 | [assembly: AssemblyFileVersion("1.0.0.0")] 36 | -------------------------------------------------------------------------------- /CSharp/Samples/DocumentDb/README.md: -------------------------------------------------------------------------------- 1 | # Azure DocumentDB Sample 2 | 3 | This simple echo bots illustrates how to use your own Azure DocumentDB to store the bot state. 4 | 5 | To use DocumentDB Store, we configure the Autofac Dependency Injection in [Global.asax](Global.asax.cs). Particularly the following is the piece of code that configures injection of DocumentDB: 6 | 7 | ```csharp 8 | var store = new DocumentDbBotDataStore(docDbEmulatorUri, docDbEmulatorKey); 9 | builder.Register(c => store) 10 | .Keyed>(AzureModule.Key_DataStore) 11 | .AsSelf() 12 | .SingleInstance(); 13 | ``` 14 | 15 | Note that instead of passing ```docDbEmulatorUri, docDbEmulatorKey```, real Azure DocumentDB credentials can be passed to configure an Azure DocumentDB account. 16 | 17 | -------------------------------------------------------------------------------- /CSharp/Samples/DocumentDb/Web.Debug.config: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 17 | 18 | 29 | 30 | -------------------------------------------------------------------------------- /CSharp/Samples/DocumentDb/Web.Release.config: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | 17 | 18 | 19 | 30 | 31 | -------------------------------------------------------------------------------- /CSharp/Samples/DocumentDb/Web.config: -------------------------------------------------------------------------------- 1 |  2 | 6 | 7 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | 44 | 45 | 46 | 47 | 48 | 49 | 50 | 51 | 52 | 53 | 54 | 55 | 56 | 57 | 58 | 59 | 60 | 61 | 62 | 63 | 64 | 65 | 66 | 67 | 68 | 69 | 70 | 71 | 72 | 73 | 74 | -------------------------------------------------------------------------------- /CSharp/Samples/DocumentDb/packages.config: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | -------------------------------------------------------------------------------- /CSharp/SimpleEchoBot/EchoBot.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Linq; 3 | using System.Net; 4 | using System.Net.Http; 5 | using System.Threading; 6 | using System.Threading.Tasks; 7 | using Microsoft.Azure.WebJobs; 8 | using Microsoft.Azure.WebJobs.Extensions.Http; 9 | using Microsoft.Azure.WebJobs.Host; 10 | using Microsoft.Bot.Builder.Azure; 11 | using Microsoft.Bot.Builder.Dialogs; 12 | using Microsoft.Bot.Connector; 13 | using Newtonsoft.Json; 14 | 15 | namespace SimpleEchoBot 16 | { 17 | public static class EchoBot 18 | { 19 | [FunctionName("EchoBot")] 20 | public static async Task Run([HttpTrigger(AuthorizationLevel.Function, "get", "post", Route = "HttpTriggerCSharp/name/{name}")]HttpRequestMessage req, string name, TraceWriter log) 21 | { 22 | log.Info("C# HTTP trigger function processed a request."); 23 | log.Info($"Web hook was triggered!"); 24 | 25 | // Initialize the azure bot 26 | using (BotService.Initialize()) 27 | { 28 | // De-serialize the incoming activity 29 | string jsonContent = await req.Content.ReadAsStringAsync(); 30 | var activity = JsonConvert.DeserializeObject(jsonContent); 31 | 32 | // authenticate incoming request and add activity.ServiceUrl to MicrosoftAppCredentials.TrustedHostNames 33 | // if request is authenticated 34 | if (!await BotService.Authenticator.TryAuthenticateAsync(req, new[] { activity }, CancellationToken.None)) 35 | { 36 | return BotAuthenticator.GenerateUnauthorizedResponse(req); 37 | } 38 | 39 | if (activity != null) 40 | { 41 | // one of these will have an interface and process it 42 | switch (activity.GetActivityType()) 43 | { 44 | case ActivityTypes.Message: 45 | await Conversation.SendAsync(activity, () => new EchoDialog()); 46 | break; 47 | case ActivityTypes.ConversationUpdate: 48 | var client = new ConnectorClient(new Uri(activity.ServiceUrl)); 49 | IConversationUpdateActivity update = activity; 50 | if (update.MembersAdded.Any()) 51 | { 52 | var reply = activity.CreateReply(); 53 | var newMembers = update.MembersAdded?.Where(t => t.Id != activity.Recipient.Id); 54 | foreach (var newMember in newMembers) 55 | { 56 | reply.Text = "Welcome"; 57 | if (!string.IsNullOrEmpty(newMember.Name)) 58 | { 59 | reply.Text += $" {newMember.Name}"; 60 | } 61 | reply.Text += "!"; 62 | await client.Conversations.ReplyToActivityAsync(reply); 63 | } 64 | } 65 | break; 66 | case ActivityTypes.ContactRelationUpdate: 67 | case ActivityTypes.Typing: 68 | case ActivityTypes.DeleteUserData: 69 | case ActivityTypes.Ping: 70 | default: 71 | log.Error($"Unknown activity type ignored: {activity.GetActivityType()}"); 72 | break; 73 | } 74 | } 75 | return req.CreateResponse(HttpStatusCode.Accepted); 76 | } 77 | } 78 | } 79 | } 80 | -------------------------------------------------------------------------------- /CSharp/SimpleEchoBot/EchoDialog.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Threading.Tasks; 3 | using Microsoft.Bot.Builder.Dialogs; 4 | using Microsoft.Bot.Connector; 5 | 6 | namespace SimpleEchoBot 7 | { 8 | [Serializable] 9 | public class EchoDialog : IDialog 10 | { 11 | protected int count = 1; 12 | 13 | public Task StartAsync(IDialogContext context) 14 | { 15 | try 16 | { 17 | context.Wait(MessageReceivedAsync); 18 | } 19 | catch (OperationCanceledException error) 20 | { 21 | return Task.FromCanceled(error.CancellationToken); 22 | } 23 | catch (Exception error) 24 | { 25 | return Task.FromException(error); 26 | } 27 | 28 | return Task.CompletedTask; 29 | } 30 | 31 | public virtual async Task MessageReceivedAsync(IDialogContext context, IAwaitable argument) 32 | { 33 | var message = await argument; 34 | if (message.Text == "reset") 35 | { 36 | PromptDialog.Confirm( 37 | context, 38 | AfterResetAsync, 39 | "Are you sure you want to reset the count?", 40 | "Didn't get that!", 41 | promptStyle: PromptStyle.Auto); 42 | } 43 | else 44 | { 45 | await context.PostAsync($"{this.count++}: You said {message.Text}"); 46 | context.Wait(MessageReceivedAsync); 47 | } 48 | } 49 | 50 | public async Task AfterResetAsync(IDialogContext context, IAwaitable argument) 51 | { 52 | var confirm = await argument; 53 | if (confirm) 54 | { 55 | this.count = 1; 56 | await context.PostAsync("Reset count."); 57 | } 58 | else 59 | { 60 | await context.PostAsync("Did not reset count."); 61 | } 62 | context.Wait(MessageReceivedAsync); 63 | } 64 | } 65 | } 66 | -------------------------------------------------------------------------------- /CSharp/SimpleEchoBot/SimpleEchoBot.csproj: -------------------------------------------------------------------------------- 1 |  2 | 3 | net461 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | PreserveNewest 21 | 22 | 23 | PreserveNewest 24 | 25 | 26 | 27 | -------------------------------------------------------------------------------- /CSharp/SimpleEchoBot/host.json: -------------------------------------------------------------------------------- 1 | { 2 | } -------------------------------------------------------------------------------- /CSharp/Tests/Microsoft.Bot.Builder.Azure.Tests/BotServiceTests.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Collections.Generic; 3 | using System.Linq; 4 | using System.Reflection; 5 | using System.Text; 6 | using System.Threading; 7 | using System.Threading.Tasks; 8 | using Autofac; 9 | using Microsoft.Bot.Builder.Dialogs; 10 | using Microsoft.Bot.Builder.Dialogs.Internals; 11 | using Microsoft.Bot.Builder.Tests; 12 | using Microsoft.Bot.Connector; 13 | using Microsoft.VisualStudio.TestTools.UnitTesting; 14 | using Microsoft.WindowsAzure.Storage; 15 | 16 | namespace Microsoft.Bot.Builder.Azure.Tests 17 | { 18 | [TestClass] 19 | public class BotServiceTests : DialogTestBase 20 | { 21 | [TestMethod] 22 | public async Task UseTableStorage_Test() 23 | { 24 | var oldValue = Environment.GetEnvironmentVariable(AppSettingKeys.UseTableStorageForConversationState); 25 | // set the environment variable so bot uses table storage as state store 26 | System.Environment.SetEnvironmentVariable(AppSettingKeys.UseTableStorageForConversationState, true.ToString()); 27 | bool shouldUse = false; 28 | // assert that UseTableStorage is set to true 29 | Assert.IsTrue(bool.TryParse(Utils.GetAppSetting(AppSettingKeys.UseTableStorageForConversationState), out shouldUse) && shouldUse); 30 | 31 | var echo = Chain.PostToChain().Select(msg => $"echo: {msg.Text}").PostToUser().Loop(); 32 | 33 | using (var container = Build(Options.ResolveDialogFromContainer)) 34 | { 35 | var builder = new ContainerBuilder(); 36 | builder.RegisterModule(new AzureModule(Assembly.GetExecutingAssembly())); 37 | builder 38 | .RegisterInstance(echo) 39 | .As>(); 40 | 41 | // register the development storage as the storage for TableBotDataStore 42 | builder.Register(c => new TableBotDataStore(CloudStorageAccount.DevelopmentStorageAccount)) 43 | .Keyed>(AzureModule.Key_DataStore) 44 | .AsSelf() 45 | .SingleInstance(); 46 | 47 | builder.Update(container); 48 | 49 | 50 | var toBot = MakeTestMessage(); 51 | 52 | toBot.Text = "hello"; 53 | 54 | using (var scope = DialogModule.BeginLifetimeScope(container, toBot)) 55 | { 56 | var task = scope.Resolve(); 57 | await task.PostAsync(toBot, CancellationToken.None); 58 | } 59 | 60 | 61 | var queue = container.Resolve>(); 62 | Assert.AreEqual("echo: hello", queue.Dequeue().Text); 63 | 64 | IBotDataStore tableStore = container.Resolve(); 65 | var privateConversationData = await tableStore.LoadAsync(Address.FromActivity(toBot), 66 | BotStoreType.BotPrivateConversationData, CancellationToken.None); 67 | Assert.IsNotNull(privateConversationData.Data); 68 | } 69 | 70 | Environment.SetEnvironmentVariable(AppSettingKeys.UseTableStorageForConversationState, oldValue); 71 | } 72 | } 73 | } 74 | -------------------------------------------------------------------------------- /CSharp/Tests/Microsoft.Bot.Builder.Azure.Tests/DocumentDbDataStoreTests.cs: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) Microsoft. All rights reserved. 3 | // Licensed under the MIT license. 4 | // 5 | // Microsoft Bot Framework: http://botframework.com 6 | // 7 | // Bot Builder SDK Github: 8 | // https://github.com/Microsoft/BotBuilder 9 | // 10 | // Copyright (c) Microsoft Corporation 11 | // All rights reserved. 12 | // 13 | // MIT License: 14 | // Permission is hereby granted, free of charge, to any person obtaining 15 | // a copy of this software and associated documentation files (the 16 | // "Software"), to deal in the Software without restriction, including 17 | // without limitation the rights to use, copy, modify, merge, publish, 18 | // distribute, sublicense, and/or sell copies of the Software, and to 19 | // permit persons to whom the Software is furnished to do so, subject to 20 | // the following conditions: 21 | // 22 | // The above copyright notice and this permission notice shall be 23 | // included in all copies or substantial portions of the Software. 24 | // 25 | // THE SOFTWARE IS PROVIDED ""AS IS"", WITHOUT WARRANTY OF ANY KIND, 26 | // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 27 | // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 28 | // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 29 | // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 30 | // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 31 | // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 32 | // 33 | 34 | using System; 35 | using Microsoft.VisualStudio.TestTools.UnitTesting; 36 | using System.Threading.Tasks; 37 | using Microsoft.WindowsAzure.Storage; 38 | using Microsoft.Bot.Builder.Tests; 39 | using Microsoft.Bot.Builder.Dialogs.Internals; 40 | using Microsoft.Bot.Builder.Dialogs; 41 | using Microsoft.Bot.Connector; 42 | 43 | namespace Microsoft.Bot.Builder.Azure.Tests 44 | { 45 | [TestClass] 46 | public class DocumentDbDataStoreTests : BaseDataStoreTests 47 | { 48 | //This test requires the DocDbEmulator to be installed and started. 49 | //Reference: https://docs.microsoft.com/en-us/azure/documentdb/documentdb-nosql-local-emulator 50 | 51 | //Fixed docDb emulator local Uri. 52 | private static readonly Uri docDbEmulatorUri = new Uri("https://localhost:8081"); 53 | 54 | //Fixed docDb emulator key 55 | private static readonly string docDbEmulatorKey = "C2y6yDjf5/R+ob0N8A7Cgv30VRDJIWEHLM+4QDU5DE2nQ9nDuVTqobD4b8mGGyPMbIZnqyMsEcaGQy67XIw/Jw=="; 56 | 57 | private DocumentDbDeleter docDbDeleter; 58 | 59 | public override IBotDataStore GetTestCaseDataStore() 60 | { 61 | return new DocumentDbBotDataStore(docDbEmulatorUri, docDbEmulatorKey); 62 | } 63 | 64 | [TestInitialize] 65 | public void TestInitialize() 66 | { 67 | if (docDbDeleter == null) 68 | { 69 | docDbDeleter = new DocumentDbDeleter(docDbEmulatorUri, docDbEmulatorKey); 70 | } 71 | 72 | docDbDeleter.DeleteDatabaseIfExists().Wait(); 73 | } 74 | 75 | [TestCleanup] 76 | public void TestCleanup() 77 | { 78 | docDbDeleter.DeleteDatabaseIfExists().Wait(); 79 | } 80 | 81 | [TestMethod] 82 | public new async Task SetGet() 83 | { 84 | await base.SetGet(); 85 | } 86 | 87 | [TestMethod] 88 | public new async Task SaveSemantics() 89 | { 90 | await base.SaveSemantics(); 91 | } 92 | 93 | [TestMethod] 94 | public new async Task GetUnknownAddress() 95 | { 96 | await base.GetUnknownAddress(); 97 | } 98 | } 99 | } 100 | 101 | -------------------------------------------------------------------------------- /CSharp/Tests/Microsoft.Bot.Builder.Azure.Tests/DocumentDbDeleter.cs: -------------------------------------------------------------------------------- 1 | using System; 2 | using System.Net; 3 | using System.Threading.Tasks; 4 | using Microsoft.Azure.Documents; 5 | using Microsoft.Azure.Documents.Client; 6 | using Microsoft.Bot.Builder.Internals.Fibers; 7 | 8 | namespace Microsoft.Bot.Builder.Azure.Tests 9 | { 10 | public class DocumentDbDeleter 11 | { 12 | private readonly DocumentClient documentClient; 13 | private readonly string databaseId; 14 | 15 | public DocumentDbDeleter(Uri serviceEndpoint, string authKey, string databaseId = "botdb") 16 | { 17 | documentClient = new DocumentClient(serviceEndpoint, authKey); 18 | SetField.NotNull(out this.databaseId, nameof(databaseId), databaseId); 19 | } 20 | 21 | public async Task DeleteDatabaseIfExists() 22 | { 23 | try 24 | { 25 | await documentClient.ReadDatabaseAsync(UriFactory.CreateDatabaseUri(databaseId)); 26 | await documentClient.DeleteDatabaseAsync(UriFactory.CreateDatabaseUri(databaseId)); 27 | } 28 | catch (DocumentClientException e) 29 | { 30 | if (e.StatusCode == HttpStatusCode.NotFound) 31 | { 32 | //Database already non existent, nothing to do here. 33 | } 34 | else 35 | { 36 | throw; 37 | } 38 | } 39 | } 40 | } 41 | } -------------------------------------------------------------------------------- /CSharp/Tests/Microsoft.Bot.Builder.Azure.Tests/Properties/AssemblyInfo.cs: -------------------------------------------------------------------------------- 1 | using System.Reflection; 2 | using System.Runtime.CompilerServices; 3 | using System.Runtime.InteropServices; 4 | 5 | // General Information about an assembly is controlled through the following 6 | // set of attributes. Change these attribute values to modify the information 7 | // associated with an assembly. 8 | [assembly: AssemblyTitle("Microsoft.Bot.Builder.Azure.Tests")] 9 | [assembly: AssemblyDescription("")] 10 | [assembly: AssemblyConfiguration("")] 11 | [assembly: AssemblyCompany("")] 12 | [assembly: AssemblyProduct("Microsoft.Bot.Builder.Azure.Tests")] 13 | [assembly: AssemblyCopyright("Copyright © 2016")] 14 | [assembly: AssemblyTrademark("")] 15 | [assembly: AssemblyCulture("")] 16 | 17 | // Setting ComVisible to false makes the types in this assembly not visible 18 | // to COM components. If you need to access a type in this assembly from 19 | // COM, set the ComVisible attribute to true on that type. 20 | [assembly: ComVisible(false)] 21 | 22 | // The following GUID is for the ID of the typelib if this project is exposed to COM 23 | [assembly: Guid("c0fc2275-93a1-462c-acc6-7329aafddab4")] 24 | 25 | // Version information for an assembly consists of the following four values: 26 | // 27 | // Major Version 28 | // Minor Version 29 | // Build Number 30 | // Revision 31 | // 32 | // You can specify all the values or you can default the Build and Revision Numbers 33 | // by using the '*' as shown below: 34 | // [assembly: AssemblyVersion("1.0.*")] 35 | [assembly: AssemblyVersion("1.0.0.0")] 36 | [assembly: AssemblyFileVersion("1.0.0.0")] 37 | -------------------------------------------------------------------------------- /CSharp/Tests/Microsoft.Bot.Builder.Azure.Tests/StorageEmulatorRunner.cs: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) Microsoft. All rights reserved. 3 | // Licensed under the MIT license. 4 | // 5 | // Microsoft Bot Framework: http://botframework.com 6 | // 7 | // Bot Builder SDK Github: 8 | // https://github.com/Microsoft/BotBuilder 9 | // 10 | // Copyright (c) Microsoft Corporation 11 | // All rights reserved. 12 | // 13 | // MIT License: 14 | // Permission is hereby granted, free of charge, to any person obtaining 15 | // a copy of this software and associated documentation files (the 16 | // "Software"), to deal in the Software without restriction, including 17 | // without limitation the rights to use, copy, modify, merge, publish, 18 | // distribute, sublicense, and/or sell copies of the Software, and to 19 | // permit persons to whom the Software is furnished to do so, subject to 20 | // the following conditions: 21 | // 22 | // The above copyright notice and this permission notice shall be 23 | // included in all copies or substantial portions of the Software. 24 | // 25 | // THE SOFTWARE IS PROVIDED ""AS IS"", WITHOUT WARRANTY OF ANY KIND, 26 | // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 27 | // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 28 | // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 29 | // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 30 | // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 31 | // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 32 | // 33 | 34 | using System; 35 | using System.Collections.Generic; 36 | using System.Diagnostics; 37 | using System.IO; 38 | using System.Linq; 39 | using System.Text; 40 | using System.Threading.Tasks; 41 | 42 | namespace Microsoft.Bot.Builder.Azure.Tests 43 | { 44 | /// 45 | /// Starts and stops Azure Storage Emulator for use in unit or integration tests 46 | /// 47 | internal static class StorageEmulatorRunner 48 | { 49 | //Azure storage emulator process name varies by version and architecture, taking one of the names below 50 | private const string EmulatorProcessNameV1 = "AZURES~1"; 51 | private const string EmulatorProcessNameV2 = "AzureStorageEmulator"; 52 | 53 | private const string EmulatorExecutableFileName = "AzureStorageEmulator.exe"; 54 | private const string AzureSdkSubDirectory = @"{0}\Microsoft SDKs\Azure\Storage Emulator"; 55 | 56 | private static bool isRunning = false; 57 | private static bool emulatorWasPreviouslyRunning = false; 58 | 59 | /// 60 | /// Starts Azure Storage Emulator if it has not been started already 61 | /// 62 | public static void Start() 63 | { 64 | if (isRunning) 65 | { 66 | return; 67 | } 68 | 69 | Process[] processes = Process.GetProcesses(); 70 | if(processes.Any(p => IsStorageEmulator(p))) 71 | { 72 | isRunning = true; 73 | return; 74 | } 75 | 76 | var azureSdkDirectory = string.Format(AzureSdkSubDirectory, Environment.GetFolderPath(Environment.SpecialFolder.ProgramFilesX86)); 77 | var executableFullFilePath = Path.Combine(azureSdkDirectory, EmulatorExecutableFileName); 78 | 79 | if (!File.Exists(executableFullFilePath)) 80 | { 81 | throw new FileNotFoundException($"Failed to find Azure Storage Emulator at {executableFullFilePath}. Make sure Azure Storage Emulator is installed"); 82 | } 83 | 84 | var processStartInfo = new ProcessStartInfo 85 | { 86 | FileName = executableFullFilePath, 87 | Arguments = "start" 88 | }; 89 | 90 | using (Process emulatorProcess = Process.Start(processStartInfo)) 91 | { 92 | emulatorProcess.WaitForExit(); 93 | emulatorWasPreviouslyRunning = false; 94 | isRunning = true; 95 | } 96 | } 97 | 98 | /// 99 | /// Stops Azure Storage Emulator 100 | /// 101 | public static void Stop() 102 | { 103 | Process[] azureStorageProcesses = Process.GetProcesses(); 104 | var emulatorProcess = azureStorageProcesses.SingleOrDefault(p => IsStorageEmulator(p)); 105 | 106 | // If the emulator is running and we were the ones that started it, we stop the process 107 | if (emulatorProcess != null && !emulatorWasPreviouslyRunning) 108 | { 109 | emulatorProcess.Kill(); 110 | isRunning = false; 111 | } 112 | } 113 | 114 | private static bool IsStorageEmulator(Process p) 115 | { 116 | return p.ProcessName.StartsWith(EmulatorProcessNameV1, StringComparison.InvariantCultureIgnoreCase) 117 | || p.ProcessName.StartsWith(EmulatorProcessNameV2, StringComparison.InvariantCultureIgnoreCase); 118 | } 119 | } 120 | } 121 | -------------------------------------------------------------------------------- /CSharp/Tests/Microsoft.Bot.Builder.Azure.Tests/TableDataStore2Tests.cs: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) Microsoft. All rights reserved. 3 | // Licensed under the MIT license. 4 | // 5 | // Microsoft Bot Framework: http://botframework.com 6 | // 7 | // Bot Builder SDK Github: 8 | // https://github.com/Microsoft/BotBuilder 9 | // 10 | // Copyright (c) Microsoft Corporation 11 | // All rights reserved. 12 | // 13 | // MIT License: 14 | // Permission is hereby granted, free of charge, to any person obtaining 15 | // a copy of this software and associated documentation files (the 16 | // "Software"), to deal in the Software without restriction, including 17 | // without limitation the rights to use, copy, modify, merge, publish, 18 | // distribute, sublicense, and/or sell copies of the Software, and to 19 | // permit persons to whom the Software is furnished to do so, subject to 20 | // the following conditions: 21 | // 22 | // The above copyright notice and this permission notice shall be 23 | // included in all copies or substantial portions of the Software. 24 | // 25 | // THE SOFTWARE IS PROVIDED ""AS IS"", WITHOUT WARRANTY OF ANY KIND, 26 | // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 27 | // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 28 | // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 29 | // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 30 | // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 31 | // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 32 | // 33 | 34 | using Microsoft.VisualStudio.TestTools.UnitTesting; 35 | using System.Threading.Tasks; 36 | using Microsoft.WindowsAzure.Storage; 37 | using Microsoft.Bot.Builder.Tests; 38 | using Microsoft.Bot.Builder.Dialogs.Internals; 39 | using Microsoft.Bot.Builder.Dialogs; 40 | using Microsoft.Bot.Connector; 41 | 42 | namespace Microsoft.Bot.Builder.Azure.Tests 43 | { 44 | 45 | [TestClass] 46 | public class TableDataStore2Tests : BaseDataStoreTests 47 | { 48 | TableBotDataStore2 store; 49 | [TestInitialize] 50 | public void Initialize() 51 | { 52 | store = new TableBotDataStore2(CloudStorageAccount.DevelopmentStorageAccount); 53 | } 54 | 55 | [TestCleanup] 56 | public void Cleanup() 57 | { 58 | foreach(var table in store.Tables) 59 | { 60 | table.DeleteIfExists(); 61 | } 62 | } 63 | 64 | 65 | public override IBotDataStore GetTestCaseDataStore() 66 | { 67 | return store; 68 | } 69 | 70 | 71 | [TestMethod] 72 | public new async Task SetGet() 73 | { 74 | await base.SetGet(); 75 | } 76 | 77 | [TestMethod] 78 | public new async Task SaveSemantics() 79 | { 80 | await base.SaveSemantics(); 81 | } 82 | 83 | [TestMethod] 84 | public new async Task GetUnknownAddress() 85 | { 86 | await base.GetUnknownAddress(); 87 | } 88 | } 89 | } 90 | -------------------------------------------------------------------------------- /CSharp/Tests/Microsoft.Bot.Builder.Azure.Tests/TableDataStoreTests.cs: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) Microsoft. All rights reserved. 3 | // Licensed under the MIT license. 4 | // 5 | // Microsoft Bot Framework: http://botframework.com 6 | // 7 | // Bot Builder SDK Github: 8 | // https://github.com/Microsoft/BotBuilder 9 | // 10 | // Copyright (c) Microsoft Corporation 11 | // All rights reserved. 12 | // 13 | // MIT License: 14 | // Permission is hereby granted, free of charge, to any person obtaining 15 | // a copy of this software and associated documentation files (the 16 | // "Software"), to deal in the Software without restriction, including 17 | // without limitation the rights to use, copy, modify, merge, publish, 18 | // distribute, sublicense, and/or sell copies of the Software, and to 19 | // permit persons to whom the Software is furnished to do so, subject to 20 | // the following conditions: 21 | // 22 | // The above copyright notice and this permission notice shall be 23 | // included in all copies or substantial portions of the Software. 24 | // 25 | // THE SOFTWARE IS PROVIDED ""AS IS"", WITHOUT WARRANTY OF ANY KIND, 26 | // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 27 | // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 28 | // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 29 | // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 30 | // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 31 | // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 32 | // 33 | 34 | using Microsoft.VisualStudio.TestTools.UnitTesting; 35 | using System.Threading.Tasks; 36 | using Microsoft.WindowsAzure.Storage; 37 | using Microsoft.Bot.Builder.Tests; 38 | using Microsoft.Bot.Builder.Dialogs.Internals; 39 | using Microsoft.Bot.Builder.Dialogs; 40 | using Microsoft.Bot.Connector; 41 | 42 | namespace Microsoft.Bot.Builder.Azure.Tests 43 | { 44 | 45 | [TestClass] 46 | public class TableDataStoreTests : BaseDataStoreTests 47 | { 48 | public override IBotDataStore GetTestCaseDataStore() 49 | { 50 | var tableName = "TableBotDataTest"; 51 | var account = CloudStorageAccount.DevelopmentStorageAccount; 52 | var table = account.CreateCloudTableClient().GetTableReference(tableName); 53 | table.DeleteIfExists(); 54 | table.CreateIfNotExists(); 55 | return new TableBotDataStore(table); 56 | } 57 | 58 | [TestMethod] 59 | public new async Task SetGet() 60 | { 61 | await base.SetGet(); 62 | } 63 | 64 | [TestMethod] 65 | public new async Task SaveSemantics() 66 | { 67 | await base.SaveSemantics(); 68 | } 69 | 70 | [TestMethod] 71 | public new async Task GetUnknownAddress() 72 | { 73 | await base.GetUnknownAddress(); 74 | } 75 | } 76 | } 77 | -------------------------------------------------------------------------------- /CSharp/Tests/Microsoft.Bot.Builder.Azure.Tests/app.config: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | 27 | 28 | 29 | 30 | 31 | 32 | 33 | 34 | 35 | 36 | 37 | 38 | 39 | 40 | 41 | 42 | 43 | -------------------------------------------------------------------------------- /CSharp/Tests/Microsoft.Bot.Builder.Azure.Tests/packages.config: -------------------------------------------------------------------------------- 1 |  2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 20 | 21 | 22 | 23 | 24 | 25 | 26 | -------------------------------------------------------------------------------- /CSharp/buildtools/35MSSharedLib1024.snk: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/microsoft/BotBuilder-Azure/51fa832dc243ffbfb34f741fb929f349e903ec06/CSharp/buildtools/35MSSharedLib1024.snk -------------------------------------------------------------------------------- /CSharp/buildtools/SetVersionInAssemblyInfoCsFiles.ps1: -------------------------------------------------------------------------------- 1 | # Set version in AssemblyInfo.cs files. 2 | Param ( 3 | [string]$rootFolder, 4 | [string]$version, 5 | [string]$filePattern = "AssemblyInfo.cs" 6 | ) 7 | 8 | function UpdateAssemblyInfo() 9 | { 10 | foreach ($file in $input) 11 | { 12 | $path = $file.FullName 13 | Write-Host ($path) 14 | $isUpdated = $false 15 | 16 | $patternAV = '^((?!\/\/).)*\[assembly: AssemblyVersion\("(.*)"\)\]' 17 | $patternAFV = '^((?!\/\/).)*\[assembly: AssemblyFileVersion\("(.*)"\)\]' 18 | (Get-Content $path) | ForEach-Object{ 19 | if($_ -match $patternAV){ 20 | # We have found the matching line 21 | $isUpdated = $true 22 | '[assembly: AssemblyVersion("{0}")]' -f $version 23 | } elseif($_ -match $patternAFV){ 24 | $isUpdated = $true 25 | # We have found the matching line 26 | '[assembly: AssemblyFileVersion("{0}")]' -f $version 27 | } else { 28 | # Output line as is 29 | $_ 30 | } 31 | } | Set-Content $path 32 | if (!$isUpdated) { 33 | Write-Host ' Nothing found to update.' 34 | } 35 | } 36 | } 37 | 38 | Write-Host ("Root folder: " + $rootFolder) 39 | Write-Host ("File pattern: " + $filePattern) 40 | Write-Host ("Version: " + $version) 41 | 42 | Write-Host ("Updating files...") 43 | Get-Childitem -Path $rootFolder -recurse |? {$_.Name -like $filePattern} | UpdateAssemblyInfo; 44 | -------------------------------------------------------------------------------- /CSharp/buildtools/updateAssemblyInfo.ps1: -------------------------------------------------------------------------------- 1 | # 2 | # Update AssemblyInfo.cs files to support delay signing. 3 | # 4 | Param ([string]$rootFolder = $(get-location).Path, 5 | [string]$filePattern 6 | ) 7 | 8 | Write-Host ("Root folder: " + $rootFolder) 9 | Write-Host ("File pattern: " + $filePattern) 10 | 11 | $replace = $true; 12 | 13 | function UpdateAssemblyInfo() 14 | { 15 | foreach ($file in $input) 16 | { 17 | Write-Host ($file.FullName) 18 | 19 | if($replace) 20 | { 21 | $tmpFile = $file.FullName + ".tmp" 22 | $fileContent = Get-Content $file.FullName -encoding utf8 23 | 24 | $fileContent = TryRemove InternalsVisibleTo; 25 | $fileContent = AddCodeSign ; 26 | 27 | Set-Content $tmpFile -value $fileContent -encoding utf8 28 | 29 | Move-Item $tmpFile $file.FullName -force 30 | } 31 | 32 | } 33 | } 34 | 35 | function AddCodeSign() 36 | { 37 | $fileContent = $fileContent + "`r`n[assembly: AssemblyKeyFileAttribute(@`"..\\..\\buildtools\\35MSSharedLib1024.snk`")] `r`n [assembly: AssemblyDelaySignAttribute(true)]" 38 | return $fileContent 39 | } 40 | 41 | function TryRemove($attributeName) 42 | { 43 | $fileContent = $fileContent -replace ('\[assembly:\s*'+$attributeName +'\(".*"\)\s*\]'), "" 44 | return $fileContent 45 | } 46 | 47 | Write-Host ("Updating files...") 48 | Get-Childitem -Path $rootFolder -recurse |? {$_.Name -like $filePattern} | UpdateAssemblyInfo; 49 | -------------------------------------------------------------------------------- /CSharp/readme.md: -------------------------------------------------------------------------------- 1 | # Bot Builder Azure Extensions for .NET 2 | Bot Builder Azure Extensions for .NET enable bot developers to integrate bots with specific Azure components. 3 | 4 | 5 | 6 | ## High level features: 7 | 8 | * Azure Table Storage: Allows bot developers to store bot state in their own Azure Storage accounts. For more information on Azure Table Storage, visit the **[Azure Table Storage Documentation](https://azure.microsoft.com/en-us/services/storage/tables/)** 9 | * Azure CosmosDb: Allows bot developers to store bot state in CosmosDb. For more information on Azure CosmosDb, visit the **[Azure CosmosDB Documentation](https://docs.microsoft.com/en-us/azure/cosmos-db/introduction)** 10 | * Azure SQL Database: Allows bot developers to store bot state using Azure SQL. For more information on Azure SQL, visit the **[Azure SQL Database Documentation](https://docs.microsoft.com/en-us/azure/sql-database/)** Note: A script for creating the SqlBotDataEntities table can be found [here](AzureSql-CreateTable.sql) 11 | 12 | ## Creating a Bot Project 13 | 14 | Bot project templates for Visual Studio can be downloaded from [here](https://docs.microsoft.com/en-us/bot-framework/dotnet/bot-builder-dotnet-quickstart) 15 | 16 | ## Sample 17 | 18 | You can also base your bot on one of our samples, which showcase using [Azure Table Storage](samples/AzureTable/), [CosmosDb](samples/DocumentDb/) and [Azure SQL](samples/AzureSql/). Read the detailed steps in the sample to set up storage emulators or connect to Azure. 19 | 20 | ## Test your bot 21 | Use the [Bot Framework Emulator](http://docs.botframework.com/connector/tools/bot-framework-emulator/) to test your bot on localhost. The emulator can be downloaded from [here](http://aka.ms/bf-bc-emulator) 22 | 23 | ## Publish your bot 24 | Register your bot with the [Bot Framework](http://docs.botframework.com/connector/getstarted/#registering-your-bot-with-the-microsoft-bot-framework) then deploy. If you're deploying your bot to Microsoft Azure you can use this great guide: [Deploy a .NET bot to Azure from Visual Studio](https://docs.microsoft.com/en-us/bot-framework/deploy-dotnet-bot-visual-studio). 25 | 26 | NOTE: Once you register your bot with the Bot Framework you'll want to update the MicrosoftAppId & MicrosoftAppPassword in the Web.config with the values assigned to you by the portal. 27 | 28 | ## Bot Framework 29 | 30 | The Microsoft Bot Framework provides just what you need to build and connect intelligent bots that interact naturally wherever your users are talking, from text/sms to Skype, Slack, Office 365 mail and other popular services. 31 | 32 | Bots (or conversation agents) are rapidly becoming an integral part of one’s digital experience – they are as vital a way for users to interact with a service or application as is a web site or a mobile experience. Developers writing bots all face the same problems: bots require basic I/O; they must have language and dialog skills; and they must connect to users – preferably in any conversation experience and language the user chooses. The Bot Framework provides tools to easily solve these problems and more for developers e.g., automatic translation to more than 30 languages, user and conversation state management, debugging tools, an embeddable web chat control and a way for users to discover, try, and add bots to the conversation experiences they love. 33 | 34 | 35 | ## Dive deeper 36 | Learn how to build great bots. 37 | 38 | * [Core Concepts Guide](https://docs.microsoft.com/en-us/bot-framework/dotnet/bot-builder-dotnet-concepts) 39 | * [Bot Builder for .NET Reference](https://docs.microsoft.com/en-us/bot-framework/dotnet/bot-builder-dotnet-overview) 40 | -------------------------------------------------------------------------------- /Contributing.md: -------------------------------------------------------------------------------- 1 | # Instructions for Logging Issues 2 | 3 | ## 1. Search for Duplicates 4 | 5 | [Search the existing issues](https://github.com/Microsoft/BotBuilder/issues?utf8=%E2%9C%93&q=is%3Aissue) before logging a new one. 6 | 7 | ## 2. Do you have a question? 8 | 9 | The issue tracker is for **issues**, in other words, bugs and suggestions. 10 | If you have a *question*, *feedback* or *suggestions*, please check our [support page](http://docs.botframework.com/support/). 11 | 12 | In general, things we find useful when reviewing suggestions are: 13 | * A description of the problem you're trying to solve 14 | * An overview of the suggested solution 15 | * Examples of how the suggestion would work in various places 16 | * Code examples showing e.g. "this would be an error, this wouldn't" 17 | * Code examples showing the generated JavaScript (if applicable) 18 | * If relevant, precedent in other languages can be useful for establishing context and expected behavior 19 | 20 | ## 3. Did you find a bug? 21 | 22 | When logging a bug, please be sure to include the following: 23 | * What version of BotBuilder you're using 24 | * If at all possible, an *isolated* way to reproduce the behavior 25 | * The behavior you expect to see, and the actual behavior 26 | 27 | # Instructions for Contributing Code 28 | 29 | ## Code of Conduct 30 | 31 | This project has adopted the [Microsoft Open Source Code of Conduct](https://opensource.microsoft.com/codeofconduct/). For more information see the [Code of Conduct FAQ](https://opensource.microsoft.com/codeofconduct/faq/) or contact [opencode@microsoft.com](mailto:opencode@microsoft.com) with any additional questions or comments. 32 | 33 | ## Contributing bug fixes and features 34 | 35 | BotBuilder is currently accepting contributions in the form of bug fixes and new features. Any submission must have an issue tracking it in the issue tracker that has been approved by the BotBuilder team. Your pull request should include a link to the bug that you are fixing. If you've submitted a PR for a bug, please post a comment in the bug to avoid duplication of effort. 36 | 37 | ## Legal 38 | 39 | If your contribution is more than 15 lines of code, you will need to complete a Contributor License Agreement (CLA). Briefly, this agreement testifies that you are granting us permission to use the submitted change according to the terms of the project's license, and that the work being submitted is under appropriate copyright. 40 | 41 | Please submit a Contributor License Agreement (CLA) before submitting a pull request. You may visit https://cla.azure.com to sign digitally. Alternatively, download the agreement ([Microsoft Contribution License Agreement.docx](https://www.codeplex.com/Download?ProjectName=typescript&DownloadId=822190) or [Microsoft Contribution License Agreement.pdf](https://www.codeplex.com/Download?ProjectName=typescript&DownloadId=921298)), sign, scan, and email it back to . Be sure to include your github user name along with the agreement. Once we have received the signed CLA, we'll review the request. 42 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | The MIT License (MIT) 2 | 3 | Copyright (c) 2016 Microsoft 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /Node/.gitignore: -------------------------------------------------------------------------------- 1 | /**/node_modules 2 | /**/.vscode 3 | /**/*.VC.db 4 | /built 5 | /docs/doc 6 | -------------------------------------------------------------------------------- /Node/.npmignore: -------------------------------------------------------------------------------- 1 | /built 2 | /docs 3 | /**/node_modules 4 | /src 5 | /**/.vscode -------------------------------------------------------------------------------- /Node/docs/botframework/assets/images/icons.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/microsoft/BotBuilder-Azure/51fa832dc243ffbfb34f741fb929f349e903ec06/Node/docs/botframework/assets/images/icons.png -------------------------------------------------------------------------------- /Node/docs/botframework/assets/images/icons@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/microsoft/BotBuilder-Azure/51fa832dc243ffbfb34f741fb929f349e903ec06/Node/docs/botframework/assets/images/icons@2x.png -------------------------------------------------------------------------------- /Node/docs/botframework/assets/images/widgets.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/microsoft/BotBuilder-Azure/51fa832dc243ffbfb34f741fb929f349e903ec06/Node/docs/botframework/assets/images/widgets.png -------------------------------------------------------------------------------- /Node/docs/botframework/assets/images/widgets@2x.png: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/microsoft/BotBuilder-Azure/51fa832dc243ffbfb34f741fb929f349e903ec06/Node/docs/botframework/assets/images/widgets@2x.png -------------------------------------------------------------------------------- /Node/docs/botframework/layouts/default.hbs: -------------------------------------------------------------------------------- 1 | --- 2 | --- 3 | 4 | 5 | 6 | 7 | 8 | {{#ifCond model.name '==' project.name}}{{project.name}}{{else}}{{model.name}} | {{project.name}}{{/ifCond}} | Bot Framework 9 | 10 | 11 | 12 | 13 | 14 | 15 | 16 | 17 | 18 | 19 | 22 | 32 | 33 | 34 |
35 |
36 | 37 | {{> header}} 38 |
39 |
40 |
41 | {% include leftnav.html %} 42 |
43 |
44 | 45 | {{> docs-header}} 46 |
47 |
48 |
49 | {{{contents}}} 50 |
51 | 68 |
69 |
70 | {{> footer}} 71 |
72 |
73 |
74 | {{> ms-footer}} 75 | 76 |
77 | 78 | 79 | 80 | {{> analytics}} 81 |
82 |
83 | 84 | 85 | 86 | 87 | 88 | 89 | 90 | 91 | -------------------------------------------------------------------------------- /Node/docs/botframework/partials/analytics.hbs: -------------------------------------------------------------------------------- 1 | {{#if settings.gaID}} 2 | 11 | {{/if}} -------------------------------------------------------------------------------- /Node/docs/botframework/partials/breadcrumb.hbs: -------------------------------------------------------------------------------- 1 | {{#if parent}} 2 | {{#with parent}}{{> breadcrumb}}{{/with}} 3 |
  • 4 | {{#if url}} 5 | {{name}} 6 | {{else}} 7 | {{name}} 8 | {{/if}} 9 |
  • 10 | {{else}} 11 | {{#if url}} 12 |
  • 13 | Globals 14 |
  • 15 | {{/if}} 16 | {{/if}} -------------------------------------------------------------------------------- /Node/docs/botframework/partials/comment.hbs: -------------------------------------------------------------------------------- 1 | {{#with comment}} 2 | {{#if hasVisibleComponent}} 3 |
    4 | {{#if shortText}} 5 |
    6 | {{#markdown}}{{{shortText}}}{{/markdown}} 7 |
    8 | {{/if}} 9 | {{#if text}} 10 | {{#markdown}}{{{text}}}{{/markdown}} 11 | {{/if}} 12 | {{#if tags}} 13 |
    14 | {{#each tags}} 15 |
    {{tagName}}
    16 |
    {{#markdown}}{{{text}}}{{/markdown}}
    17 | {{/each}} 18 |
    19 | {{/if}} 20 |
    21 | {{/if}} 22 | {{/with}} -------------------------------------------------------------------------------- /Node/docs/botframework/partials/docs-header.hbs: -------------------------------------------------------------------------------- 1 | 2 |
    3 |
    4 |
    5 |
    6 | 19 | 20 |
    21 |
    22 | Options 23 |
    24 |
    25 | All 26 |
      27 |
    • Public
    • 28 |
    • Public/Protected
    • 29 |
    • All
    • 30 |
    31 |
    32 | 33 | 34 | 35 | 36 | {{#unless settings.excludeExternals}} 37 | 38 | 39 | {{/unless}} 40 | 41 | 42 | 43 |
    44 |
    45 | 46 | Menu 47 |
    48 |
    49 |
    50 |
    51 |
    52 |
    53 |
      54 | {{#with model}}{{> breadcrumb}}{{/with}} 55 |
    56 |

    {{#compact}} 57 | {{model.kindString}}  58 | {{model.name}} 59 | {{#if model.typeParameters}} 60 | < 61 | {{#each model.typeParameters}} 62 | {{#if @index}}, {{/if}} 63 | {{name}} 64 | {{/each}} 65 | > 66 | {{/if}} 67 | {{/compact}}

    68 |
    69 |
    70 |
    -------------------------------------------------------------------------------- /Node/docs/botframework/partials/header.hbs: -------------------------------------------------------------------------------- 1 |
    2 |
    3 |
    4 | 9 |
    10 | 11 |
    12 |
    13 |
    14 |
    15 |
    16 |
    17 |
    18 |
    19 | Bot Framework 20 |
    21 | 32 | 45 |
    46 |
    47 | 48 | 49 | -------------------------------------------------------------------------------- /Node/docs/botframework/partials/hierarchy.hbs: -------------------------------------------------------------------------------- 1 |
      2 | {{#each types}} 3 |
    • 4 | {{#if ../isTarget}} 5 | {{this}} 6 | {{else}} 7 | {{> type}} 8 | {{/if}} 9 | 10 | {{#if @last}} 11 | {{#with ../../next}} 12 | {{> hierarchy}} 13 | {{/with}} 14 | {{/if}} 15 |
    • 16 | {{/each}} 17 |
    18 | -------------------------------------------------------------------------------- /Node/docs/botframework/partials/index.hbs: -------------------------------------------------------------------------------- 1 | {{#if groups}} 2 |
    3 |

    Index

    4 |
    5 |
    6 | {{#each groups}} 7 |
    8 |

    {{title}}

    9 | 14 |
    15 | {{/each}} 16 |
    17 |
    18 |
    19 | {{/if}} -------------------------------------------------------------------------------- /Node/docs/botframework/partials/member.declaration.hbs: -------------------------------------------------------------------------------- 1 |
    {{#compact}} 2 | {{{wbr name}}}{{#if isOptional}}?{{/if}}: {{#with type}}{{>type}}{{/with}} 3 | {{/compact}}
    4 | 5 | {{> member.sources}} 6 | 7 | {{> comment}} 8 | 9 | {{#if type.declaration}} 10 |
    11 |

    Type declaration

    12 | {{#with type.declaration}} 13 | {{> parameter}} 14 | {{/with}} 15 |
    16 | {{/if}} -------------------------------------------------------------------------------- /Node/docs/botframework/partials/member.getterSetter.hbs: -------------------------------------------------------------------------------- 1 |
      2 | {{#if getSignature}} 3 | {{#with getSignature}} 4 |
    • {{#compact}} 5 | get  6 | {{../../name}} 7 | {{> member.signature.title hideName=true }} 8 | {{/compact}}
    • 9 | {{/with}} 10 | {{/if}} 11 | {{#if setSignature}} 12 | {{#with setSignature}} 13 |
    • {{#compact}} 14 | set  15 | {{../../name}} 16 | {{> member.signature.title hideName=true }} 17 | {{/compact}}
    • 18 | {{/with}} 19 | {{/if}} 20 |
    21 | 22 |
      23 | {{#if getSignature}} 24 | {{#with getSignature}} 25 |
    • 26 | {{> member.signature.body }} 27 |
    • 28 | {{/with}} 29 | {{/if}} 30 | {{#if setSignature}} 31 | {{#with setSignature}} 32 |
    • 33 | {{> member.signature.body }} 34 |
    • 35 | {{/with}} 36 | {{/if}} 37 |
    -------------------------------------------------------------------------------- /Node/docs/botframework/partials/member.hbs: -------------------------------------------------------------------------------- 1 |
    2 | 3 | {{#if name}} 4 |

    {{#each flags}}{{this}} {{/each}}{{{wbr name}}}

    5 | {{/if}} 6 | 7 | {{#if signatures}} 8 | {{> member.signatures}} 9 | {{else}}{{#if hasGetterOrSetter}} 10 | {{> member.getterSetter}} 11 | {{else}} 12 | {{> member.declaration}} 13 | {{/if}}{{/if}} 14 | 15 | {{#each groups}} 16 | {{#each children}} 17 | {{#unless hasOwnDocument}} 18 | {{> member}} 19 | {{/unless}} 20 | {{/each}} 21 | {{/each}} 22 |
    23 | -------------------------------------------------------------------------------- /Node/docs/botframework/partials/member.signature.body.hbs: -------------------------------------------------------------------------------- 1 | {{#unless hideSources}} 2 | {{> member.sources}} 3 | {{/unless}} 4 | 5 | {{> comment}} 6 | 7 | {{#if typeParameters}} 8 |

    Type parameters

    9 | {{> typeParameters}} 10 | {{/if}} 11 | 12 | {{#if parameters}} 13 |

    Parameters

    14 |
      15 | {{#each parameters}} 16 |
    • 17 |
      {{#compact}} 18 | {{#each flags}} 19 | {{this}}  20 | {{/each}} 21 | {{#if flags.isRest}}...{{/if}} 22 | {{name}}:  23 | {{#with type}}{{>type}}{{/with}} 24 | {{#if defaultValue}} 25 | 26 |  =  27 | {{defaultValue}} 28 | 29 | {{/if}} 30 | {{/compact}}
      31 | 32 | {{> comment}} 33 | 34 | {{#if type.declaration}} 35 | {{#with type.declaration}} 36 | {{> parameter}} 37 | {{/with}} 38 | {{/if}} 39 |
    • 40 | {{/each}} 41 |
    42 | {{/if}} 43 | 44 | {{#if type}} 45 |

    Returns {{#with type}}{{>type}}{{/with}}

    46 | 47 | {{#if comment.returns}} 48 | {{#markdown}}{{{comment.returns}}}{{/markdown}} 49 | {{/if}} 50 | 51 | {{#if type.declaration}} 52 | {{#with type.declaration}} 53 | {{> parameter}} 54 | {{/with}} 55 | {{/if}} 56 | {{/if}} -------------------------------------------------------------------------------- /Node/docs/botframework/partials/member.signature.title.hbs: -------------------------------------------------------------------------------- 1 | {{#compact}} 2 | {{#unless hideName}}{{{wbr name}}}{{/unless}} 3 | {{#if typeParameters}} 4 | < 5 | {{#each typeParameters}} 6 | {{#if @index}}, {{/if}} 7 | {{name}} 8 | {{/each}} 9 | > 10 | {{/if}} 11 | ( 12 | {{#each parameters}} 13 | {{#if @index}}, {{/if}} 14 | {{#if flags.isRest}}...{{/if}} 15 | {{name}} 16 | 17 | {{#if flags.isOptional}}?{{/if}} 18 | {{#if defaultValue}}?{{/if}} 19 | :  20 | 21 | {{#with type}}{{>type}}{{/with}} 22 | {{/each}} 23 | ) 24 | {{#if type}} 25 | 26 | {{#with type}}{{>type}}{{/with}} 27 | {{/if}} 28 | {{/compact}} -------------------------------------------------------------------------------- /Node/docs/botframework/partials/member.signatures.hbs: -------------------------------------------------------------------------------- 1 |
      2 | {{#each signatures}} 3 |
    • {{> member.signature.title }}
    • 4 | {{/each}} 5 |
    6 | 7 |
      8 | {{#each signatures}} 9 |
    • 10 | {{> member.signature.body }} 11 |
    • 12 | {{/each}} 13 |
    -------------------------------------------------------------------------------- /Node/docs/botframework/partials/member.sources.hbs: -------------------------------------------------------------------------------- 1 | -------------------------------------------------------------------------------- /Node/docs/botframework/partials/members.group.hbs: -------------------------------------------------------------------------------- 1 |
    2 |

    {{title}}

    3 | {{#each children}} 4 | {{#unless hasOwnDocument}} 5 | {{> member}} 6 | {{/unless}} 7 | {{/each}} 8 |
    9 | -------------------------------------------------------------------------------- /Node/docs/botframework/partials/members.hbs: -------------------------------------------------------------------------------- 1 | {{#each groups}} 2 | {{#unless allChildrenHaveOwnDocument}} 3 | {{> members.group}} 4 | {{/unless}} 5 | {{/each}} -------------------------------------------------------------------------------- /Node/docs/botframework/partials/ms-footer.hbs: -------------------------------------------------------------------------------- 1 | 10 | -------------------------------------------------------------------------------- /Node/docs/botframework/partials/navigation.hbs: -------------------------------------------------------------------------------- 1 | {{#if isVisible}} 2 | {{#if isLabel}} 3 |
  • 4 | {{{wbr title}}} 5 |
  • 6 | {{else}} 7 | {{#if isGlobals}} 8 |
  • 9 | {{{wbr title}}} 10 |
  • 11 | {{else}} 12 |
  • 13 | {{{wbr title}}} 14 | {{#if isInPath}} 15 | {{#if children}} 16 |
      17 | {{#each children}} 18 | {{> navigation}} 19 | {{/each}} 20 |
    21 | {{/if}} 22 | {{/if}} 23 |
  • 24 | {{/if}} 25 | {{/if}} 26 | {{/if}} 27 | -------------------------------------------------------------------------------- /Node/docs/botframework/partials/parameter.hbs: -------------------------------------------------------------------------------- 1 |
      2 | {{#if signatures}} 3 |
    • 4 |
        5 | {{#each signatures}} 6 |
      • {{> member.signature.title hideName=true }}
      • 7 | {{/each}} 8 |
      9 | 10 |
        11 | {{#each signatures}} 12 |
      • {{> member.signature.body hideSources=true }}
      • 13 | {{/each}} 14 |
      15 |
    • 16 | {{/if}} 17 | {{#if indexSignature}} 18 |
    • 19 |
      {{#compact}} 20 | [ 21 | {{#each indexSignature.parameters}} 22 | {{#if flags.isRest}}...{{/if}}{{name}}: {{#with type}}{{>type}}{{/with}} 23 | {{/each}} 24 | ]:  25 | {{#with indexSignature.type}}{{>type}}{{/with}} 26 | {{/compact}}
      27 | 28 | {{#with indexSignature}} 29 | {{> comment}} 30 | {{/with}} 31 | 32 | {{#if indexSignature.type.declaration}} 33 | {{#with indexSignature.type.declaration}} 34 | {{> parameter}} 35 | {{/with}} 36 | {{/if}} 37 |
    • 38 | {{/if}} 39 | {{#each children}} 40 |
    • 41 | {{#if signatures}} 42 |
      {{#compact}} 43 | {{#if flags.isRest}}...{{/if}} 44 | {{{wbr name}}} 45 | 46 | {{#if isOptional}}?{{/if}} 47 | :  48 | 49 | function 50 | {{/compact}}
      51 | 52 | {{> member.signatures}} 53 | {{else}} 54 |
      {{#compact}} 55 | {{#each flags}} 56 | {{this}}  57 | {{/each}} 58 | {{#if flags.isRest}}...{{/if}} 59 | {{{wbr name}}} 60 | 61 | {{#if flags.isOptional}}?{{/if}} 62 | :  63 | 64 | {{#with type}}{{>type}}{{/with}} 65 | {{/compact}}
      66 | 67 | {{> comment}} 68 | 69 | {{#if children}} 70 | {{> parameter}} 71 | {{/if}} 72 | 73 | {{#if type.declaration}} 74 | {{#with type.declaration}} 75 | {{> parameter}} 76 | {{/with}} 77 | {{/if}} 78 | {{/if}} 79 |
    • 80 | {{/each}} 81 |
    82 | -------------------------------------------------------------------------------- /Node/docs/botframework/partials/toc.hbs: -------------------------------------------------------------------------------- 1 |
  • 2 | {{{wbr title}}} 3 | {{#if children}} 4 |
      5 | {{#each children}} 6 | {{> toc}} 7 | {{/each}} 8 |
    9 | {{/if}} 10 |
  • 11 | -------------------------------------------------------------------------------- /Node/docs/botframework/partials/toc.root.hbs: -------------------------------------------------------------------------------- 1 | {{#if isInPath}} 2 | 3 |
      4 | {{/if}} 5 |
    • 6 | {{{wbr title}}} 7 | {{#if children}} 8 |
        9 | {{#each children}} 10 | {{> toc}} 11 | {{/each}} 12 |
      13 | {{/if}} 14 |
    • 15 | {{#if isInPath}} 16 |
    17 |
      18 | {{/if}} 19 | -------------------------------------------------------------------------------- /Node/docs/botframework/partials/type.hbs: -------------------------------------------------------------------------------- 1 | {{#if this}} 2 | {{#if reflection}} 3 | {{#compact}} 4 | 5 | {{reflection.name}} 6 | 7 | {{#if typeArguments}} 8 | < 9 | 10 | {{#each typeArguments}} 11 | {{#if @index}} 12 | , 13 | {{/if}}{{> type}} 14 | {{/each}} 15 | 16 | > 17 | {{/if}} 18 | {{#if isArray}}[]{{/if}} 19 | {{/compact}} 20 | {{else}} 21 | {{#if types}} 22 | {{#each types}} 23 | {{#if @index}} 24 | | 25 | {{/if}}{{> type}} 26 | {{/each}} 27 | {{else}} 28 | {{#if elements}} 29 | {{#compact}} 30 | [ 31 | 32 | {{#each elements}} 33 | {{#if @index}} 34 | , 35 | {{/if}}{{> type}} 36 | {{/each}} 37 | 38 | ] 39 | {{/compact}} 40 | {{else}} 41 | {{#compact}} 42 | 43 | {{#if name}} 44 | {{name}} 45 | {{else}} 46 | {{#if value}} 47 | "{{value}}" 48 | {{else}} 49 | {{this}} 50 | {{/if}} 51 | {{/if}} 52 | 53 | {{#if typeArguments}} 54 | < 55 | 56 | {{#each typeArguments}} 57 | {{#if @index}} 58 | , 59 | {{/if}}{{> type}} 60 | {{/each}} 61 | 62 | > 63 | {{/if}} 64 | {{#if isArray}}[]{{/if}} 65 | {{/compact}} 66 | {{/if}} 67 | {{/if}} 68 | {{/if}} 69 | {{else}} 70 | void 71 | {{/if}} -------------------------------------------------------------------------------- /Node/docs/botframework/partials/typeAndParent.hbs: -------------------------------------------------------------------------------- 1 | {{#compact}} 2 | {{#if this}} 3 | {{#if reflection}} 4 | {{#ifSignature reflection}} 5 | {{#if reflection.parent.parent.url}} 6 | {{reflection.parent.parent.name}} 7 | {{else}} 8 | {{reflection.parent.parent.name}} 9 | {{/if}} 10 | . 11 | {{#if reflection.parent.url}} 12 | {{reflection.parent.name}} 13 | {{else}} 14 | {{reflection.parent.name}} 15 | {{/if}} 16 | {{else}} 17 | {{#if reflection.parent.url}} 18 | {{reflection.parent.name}} 19 | {{else}} 20 | {{reflection.parent.name}} 21 | {{/if}} 22 | . 23 | {{#if reflection.url}} 24 | {{reflection.name}} 25 | {{else}} 26 | {{reflection.name}} 27 | {{/if}} 28 | {{/ifSignature}} 29 | {{#if isArray}} 30 | [] 31 | {{/if}} 32 | {{else}} 33 | {{this}} 34 | {{/if}} 35 | {{else}} 36 | void 37 | {{/if}} 38 | {{/compact}} -------------------------------------------------------------------------------- /Node/docs/botframework/partials/typeParameters.hbs: -------------------------------------------------------------------------------- 1 |
        2 | {{#each typeParameters}} 3 |
      • 4 |

        {{#compact}} 5 | {{name}} 6 | {{#if type}} 7 | 8 | {{#with type}}{{> type}}{{/with}} 9 | {{/if}} 10 | {{/compact}}

        11 | {{> comment}} 12 |
      • 13 | {{/each}} 14 |
      -------------------------------------------------------------------------------- /Node/docs/botframework/templates/index.hbs: -------------------------------------------------------------------------------- 1 |
      2 | {{#markdown}}{{{model.readme}}}{{/markdown}} 3 |
      -------------------------------------------------------------------------------- /Node/docs/botframework/templates/reflection.hbs: -------------------------------------------------------------------------------- 1 | {{#with model}} 2 | {{#if hasComment}} 3 |
      4 | {{> comment}} 5 |
      6 | {{/if}} 7 | {{/with}} 8 | 9 | {{#if model.typeParameters}} 10 |
      11 |

      Type parameters

      12 | {{#with model}}{{> typeParameters}}{{/with}} 13 |
      14 | {{/if}} 15 | 16 | {{#if model.typeHierarchy}} 17 |
      18 |

      Hierarchy

      19 | {{#with model.typeHierarchy}}{{> hierarchy}}{{/with}} 20 |
      21 | {{/if}} 22 | 23 | {{#if model.implementedTypes}} 24 |
      25 |

      Implements

      26 |
        27 | {{#each model.implementedTypes}} 28 |
      • {{> type}}
      • 29 | {{/each}} 30 |
      31 |
      32 | {{/if}} 33 | 34 | {{#if model.implementedBy}} 35 |
      36 |

      Implemented by

      37 |
        38 | {{#each model.implementedBy}} 39 |
      • {{> type}}
      • 40 | {{/each}} 41 |
      42 |
      43 | {{/if}} 44 | 45 | {{#if model.signatures}} 46 |
      47 |

      Callable

      48 | {{#with model}}{{> member.signatures}}{{/with}} 49 |
      50 | {{/if}} 51 | 52 | {{#if model.indexSignature}} 53 |
      54 |

      Indexable

      55 |
      {{#compact}} 56 | [ 57 | {{#each model.indexSignature.parameters}} 58 | {{name}}: {{#with type}}{{>type}}{{/with}} 59 | {{/each}} 60 | ]:  61 | {{#with model.indexSignature.type}}{{>type}}{{/with}} 62 | {{/compact}}
      63 | 64 | {{#with model.indexSignature}} 65 | {{> comment}} 66 | {{/with}} 67 | 68 | {{#if model.indexSignature.type.declaration}} 69 | {{#with model.indexSignature.type.declaration}} 70 | {{> parameter}} 71 | {{/with}} 72 | {{/if}} 73 |
      74 | {{/if}} 75 | 76 | {{#with model}} 77 | {{> index}} 78 | {{> members}} 79 | {{/with}} -------------------------------------------------------------------------------- /Node/docs/build-docs.cmd: -------------------------------------------------------------------------------- 1 | @ECHO OFF 2 | ECHO [COMPILING DOCS] 3 | typedoc --includeDeclarations --module amd --out doc ..\src\botbuilder-azure.d.ts --theme .\botframework --hideGenerator --name "Bot Builder for Azure Reference Library" --readme none 4 | -------------------------------------------------------------------------------- /Node/examples/feature-azureSql/app.js: -------------------------------------------------------------------------------- 1 | /*----------------------------------------------------------------------------- 2 | This Bot demonstrates how to use Azure SQL for bot storage. 3 | 4 | # RUN THE BOT: 5 | 6 | -Using Azure SQL 7 | -Create an Azure SQL database (https://docs.microsoft.com/en-us/azure/sql-database/sql-database-get-started-portal) 8 | -Replace userName, password, server, database, and table to your preference in the code below. 9 | -IMPORTANT: You should create your table before attempting to connect your bot to it. 10 | If you wish for the table to be created if it isn't initially found, you must add the key-value pair `enforceTable: true` to your SQL configuration. See Line 25. 11 | The minimal SQL script used to create the table is: `CREATE TABLE your_specified_table_name (id NVARCHAR(200), data NVARCHAR(1000), isCompressed BIT` 12 | -Set rowCollectionOnRequestCompletion to true to retrieve row content. 13 | -Run the bot from the command line using "node app.js" 14 | -Type anything, and the bot will respond showing the text you typed 15 | 16 | -----------------------------------------------------------------------------*/ 17 | 18 | var builder = require('botbuilder'); 19 | var azure = require('../../'); 20 | var restify = require('restify'); 21 | 22 | var sqlConfig = { 23 | userName: '', 24 | password: '', 25 | server: '', 26 | // enforceTable: true, // If this property is not set to true it defaults to false. When false if the specified table is not found, the bot will throw an error. 27 | options: { 28 | database: '', 29 | table: '', 30 | encrypt: true, 31 | rowCollectionOnRequestCompletion: true 32 | } 33 | } 34 | 35 | var sqlClient = new azure.AzureSqlClient(sqlConfig); 36 | 37 | var sqlStorage = new azure.AzureBotStorage({ gzipData: false }, sqlClient); 38 | 39 | var connector = new builder.ChatConnector({ 40 | appId: process.env.MICROSOFT_APP_ID, 41 | appPassword: process.env.MICROSOFT_APP_PASSWORD 42 | }); 43 | 44 | var bot = new builder.UniversalBot(connector, function (session) { 45 | session.send("You said: %s", session.message.text); 46 | }).set('storage', sqlStorage); 47 | 48 | var server = restify.createServer(); 49 | server.listen(process.env.port || process.env.PORT || 3978, function () { 50 | console.log('%s listening to %s', server.name, server.url); 51 | }); 52 | 53 | server.post('/api/messages', connector.listen()); -------------------------------------------------------------------------------- /Node/examples/feature-azureTable/app.js: -------------------------------------------------------------------------------- 1 | /*----------------------------------------------------------------------------- 2 | This Bot demonstrates how to use Azure DocumentDb for bot storage. 3 | 4 | # RUN THE BOT: 5 | 6 | -Using local Azure Storage emulator: 7 | -Install Azure Storage emulator (https://docs.microsoft.com/en-us/azure/storage/storage-use-emulator) 8 | -Start the Azure Storage emulator 9 | -Run the bot from the command line using "node app.js" 10 | -Type anything, and the bot will respond showing the text you typed 11 | 12 | -Using Azure Table 13 | -Create an Azure storage account (https://docs.microsoft.com/en-us/azure/storage/storage-create-storage-account) 14 | -Pass your storage account name and key to the AzureTableClient constructor 15 | -Run the bot from the command line using "node app.js" 16 | -Type anything, and the bot will respond showing the text you typed 17 | 18 | -----------------------------------------------------------------------------*/ 19 | 20 | var builder = require('botbuilder'); 21 | var azure = require('../../'); 22 | 23 | var tableName = 'BotStore'; 24 | 25 | var azureTableClient = new azure.AzureTableClient(tableName, 'UseDevelopmentStorage=true'); 26 | 27 | var tableStorage = new azure.AzureBotStorage({ gzipData: false }, azureTableClient); 28 | 29 | // Setup bot 30 | var connector = new builder.ConsoleConnector().listen(); 31 | 32 | // Create your bot with a function to receive messages from the user 33 | var bot = new builder.UniversalBot(connector, function (session) { 34 | session.send("You said: %s", session.message.text); 35 | }).set('storage', tableStorage); 36 | -------------------------------------------------------------------------------- /Node/examples/feature-documentDb/app.js: -------------------------------------------------------------------------------- 1 | /*----------------------------------------------------------------------------- 2 | This Bot demonstrates how to use Azure DocumentDb for bot storage. 3 | 4 | # RUN THE BOT: 5 | 6 | -Using local DocumentDb emulator: 7 | -Install DocumentDb emulator (https://docs.microsoft.com/en-us/azure/documentdb/documentdb-nosql-local-emulator) 8 | -Start the DocumentDb emulator 9 | -Set the environment variable NODE_TLS_REJECT_UNAUTHORIZED to the value 0 10 | -Run the bot from the command line using "node app.js" 11 | -Type anything, and the bot will respond showing the text you typed 12 | 13 | -Using Azure DocumentDb 14 | -Create a DocumentDb database (https://azure.microsoft.com/en-us/resources/videos/create-documentdb-on-azure/) 15 | -Replace host, masterKey, database and collection to your preference in the code below 16 | -Run the bot from the command line using "node app.js" 17 | -Type anything, and the bot will respond showing the text you typed 18 | 19 | -----------------------------------------------------------------------------*/ 20 | 21 | var builder = require('botbuilder'); 22 | var azure = require('../../'); 23 | var restify = require('restify'); 24 | 25 | var documentDbOptions = { 26 | host: 'https://localhost:8081', // Host for local DocDb emulator 27 | masterKey: 'C2y6yDjf5/R+ob0N8A7Cgv30VRDJIWEHLM+4QDU5DE2nQ9nDuVTqobD4b8mGGyPMbIZnqyMsEcaGQy67XIw/Jw==', // Fixed key for local DocDb emulator 28 | database: 'botdocdb', 29 | collection: 'botdata' 30 | }; 31 | 32 | var docDbClient = new azure.DocumentDbClient(documentDbOptions); 33 | 34 | var tableStorage = new azure.AzureBotStorage({ gzipData: false }, docDbClient); 35 | 36 | var connector = new builder.ChatConnector({ 37 | appId: process.env.MICROSOFT_APP_ID, 38 | appPassword: process.env.MICROSOFT_APP_PASSWORD 39 | }); 40 | 41 | var bot = new builder.UniversalBot(connector, function (session) { 42 | session.send("You said: %s", session.message.text); 43 | }).set('storage', tableStorage); 44 | 45 | var server = restify.createServer(); 46 | server.listen(process.env.port || process.env.PORT || 3978, function () { 47 | console.log('%s listening to %s', server.name, server.url); 48 | }); 49 | 50 | server.post('/api/messages', connector.listen()); 51 | 52 | -------------------------------------------------------------------------------- /Node/lib/AzureTableClient.js: -------------------------------------------------------------------------------- 1 | "use strict"; 2 | Object.defineProperty(exports, "__esModule", { value: true }); 3 | var Consts = require("./Consts"); 4 | var azure = require('azure-storage'); 5 | var AzureTableClient = (function () { 6 | function AzureTableClient(tableName, accountName, accountKey) { 7 | if (!accountName && !accountKey) { 8 | this.useDevelopmentStorage = true; 9 | } 10 | else if (accountName && !accountKey) { 11 | this.connectionString = accountName; 12 | } 13 | else if (!accountName || !accountKey) { 14 | throw Error('Storage account name and account key are mandatory when not using development storage'); 15 | } 16 | this.accountName = accountName; 17 | this.accountKey = accountKey; 18 | this.tableName = tableName; 19 | } 20 | AzureTableClient.prototype.initialize = function (callback) { 21 | var tableService = this.buildTableService(); 22 | tableService.createTableIfNotExists(this.tableName, function (error, result, response) { 23 | callback(AzureTableClient.getError(error, response)); 24 | }); 25 | }; 26 | AzureTableClient.prototype.insertOrReplace = function (partitionKey, rowKey, data, isCompressed, callback) { 27 | var tableService = this.buildTableService(); 28 | var entityGenerator = azure.TableUtilities.entityGenerator; 29 | var entity = { 30 | PartitionKey: entityGenerator.String(partitionKey), 31 | RowKey: entityGenerator.String(rowKey), 32 | Data: entityGenerator.String((data instanceof String) ? data : JSON.stringify(data)), 33 | IsCompressed: entityGenerator.Boolean(isCompressed) 34 | }; 35 | tableService.insertOrReplaceEntity(this.tableName, entity, { checkEtag: false }, function (error, result, response) { 36 | callback(AzureTableClient.getError(error, response), result, response); 37 | }); 38 | }; 39 | AzureTableClient.prototype.retrieve = function (partitionKey, rowKey, callback) { 40 | var tableService = this.buildTableService(); 41 | tableService.retrieveEntity(this.tableName, partitionKey, rowKey, function (error, result, response) { 42 | if (response.statusCode == Consts.HttpStatusCodes.NotFound) { 43 | callback(null, null, response); 44 | } 45 | else { 46 | callback(AzureTableClient.getError(error, response), AzureTableClient.toBotEntity(result), response); 47 | } 48 | }); 49 | }; 50 | AzureTableClient.toBotEntity = function (tableResult) { 51 | if (!tableResult) { 52 | return null; 53 | } 54 | var entity = { 55 | data: {}, 56 | isCompressed: tableResult.IsCompressed['_'] || false, 57 | rowKey: tableResult.RowKey['_'] || '', 58 | partitionKey: tableResult.PartitionKey['_'] || '' 59 | }; 60 | if (tableResult.Data['_'] && entity.isCompressed) { 61 | entity.data = tableResult.Data['_']; 62 | } 63 | else if (tableResult.Data['_'] && !entity.isCompressed) { 64 | entity.data = JSON.parse(tableResult.Data['_']); 65 | } 66 | return entity; 67 | }; 68 | AzureTableClient.prototype.buildTableService = function () { 69 | var tableService = null; 70 | if (this.useDevelopmentStorage) { 71 | tableService = azure.createTableService(Consts.developmentConnectionString); 72 | } 73 | else if (this.connectionString) { 74 | tableService = azure.createTableService(this.connectionString); 75 | } 76 | else { 77 | tableService = azure.createTableService(this.accountName, this.accountKey); 78 | } 79 | return tableService.withFilter(new azure.ExponentialRetryPolicyFilter()); 80 | }; 81 | AzureTableClient.getError = function (error, response) { 82 | if (!error) 83 | return null; 84 | var message = 'Failed to perform the requested operation on Azure Table. Message: ' + error.message + '. Error code: ' + error.code; 85 | if (response) { 86 | message += '. Http status code: '; 87 | message += response.statusCode; 88 | } 89 | return new Error(message); 90 | }; 91 | return AzureTableClient; 92 | }()); 93 | exports.AzureTableClient = AzureTableClient; 94 | -------------------------------------------------------------------------------- /Node/lib/BotServiceConnector.js: -------------------------------------------------------------------------------- 1 | "use strict"; 2 | var __extends = (this && this.__extends) || (function () { 3 | var extendStatics = Object.setPrototypeOf || 4 | ({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) || 5 | function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; }; 6 | return function (d, b) { 7 | extendStatics(d, b); 8 | function __() { this.constructor = d; } 9 | d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __()); 10 | }; 11 | })(); 12 | Object.defineProperty(exports, "__esModule", { value: true }); 13 | var builder = require("botbuilder"); 14 | var BotServiceConnector = (function (_super) { 15 | __extends(BotServiceConnector, _super); 16 | function BotServiceConnector(settings) { 17 | return _super.call(this, settings) || this; 18 | } 19 | BotServiceConnector.prototype.listen = function () { 20 | var _listen = _super.prototype.listen.call(this); 21 | return function (context, req) { 22 | var response = {}; 23 | _listen(req, { 24 | send: function (status, body) { 25 | if (context) { 26 | response.status = status; 27 | if (body) { 28 | response.body = body; 29 | } 30 | context.res = response; 31 | context.done(); 32 | context = null; 33 | } 34 | }, 35 | status: function (val) { 36 | if (typeof val === 'number') { 37 | response.status = val; 38 | } 39 | return response.status || 200; 40 | }, 41 | end: function () { 42 | if (context) { 43 | context.res = response; 44 | context.done(); 45 | context = null; 46 | } 47 | } 48 | }); 49 | }; 50 | }; 51 | return BotServiceConnector; 52 | }(builder.ChatConnector)); 53 | exports.BotServiceConnector = BotServiceConnector; 54 | -------------------------------------------------------------------------------- /Node/lib/Consts.js: -------------------------------------------------------------------------------- 1 | "use strict"; 2 | Object.defineProperty(exports, "__esModule", { value: true }); 3 | exports.developmentConnectionString = 'UseDevelopmentStorage=true'; 4 | exports.maxDataLength = 65000; 5 | exports.Fields = { 6 | UserDataField: 'userData', 7 | ConversationDataField: 'conversationData', 8 | PrivateConversationDataField: 'privateConversationData' 9 | }; 10 | exports.tableName = 'BotStore'; 11 | exports.hash = 'Hash'; 12 | exports.base64 = 'base64'; 13 | exports.HttpStatusCodes = { 14 | NotFound: '404' 15 | }; 16 | exports.ErrorCodes = { 17 | MessageSize: 'EMSGSIZE', 18 | BadMessage: 'EBADMSG' 19 | }; 20 | exports.DocDbRootQuery = 'SELECT * FROM root r WHERE r.id = @id'; 21 | exports.DocDbIdParam = '@id'; 22 | -------------------------------------------------------------------------------- /Node/lib/IStorageClient.js: -------------------------------------------------------------------------------- 1 | "use strict"; 2 | Object.defineProperty(exports, "__esModule", { value: true }); 3 | -------------------------------------------------------------------------------- /Node/lib/botbuilder-azure.js: -------------------------------------------------------------------------------- 1 | "use strict"; 2 | Object.defineProperty(exports, "__esModule", { value: true }); 3 | var BotServiceConnector_1 = require("./BotServiceConnector"); 4 | var AzureBotStorage_1 = require("./AzureBotStorage"); 5 | var AzureTableClient_1 = require("./AzureTableClient"); 6 | var DocumentDbClient_1 = require("./DocumentDbClient"); 7 | var AzureSqlClient_1 = require("./AzureSqlClient"); 8 | exports.BotServiceConnector = BotServiceConnector_1.BotServiceConnector; 9 | exports.AzureBotStorage = AzureBotStorage_1.AzureBotStorage; 10 | exports.AzureTableClient = AzureTableClient_1.AzureTableClient; 11 | exports.DocumentDbClient = DocumentDbClient_1.DocumentDbClient; 12 | exports.AzureSqlClient = AzureSqlClient_1.AzureSqlClient; 13 | -------------------------------------------------------------------------------- /Node/package.json: -------------------------------------------------------------------------------- 1 | { 2 | "name": "botbuilder-azure", 3 | "version": "3.1.0", 4 | "description": "Bot Builder SDK Azure Extensions", 5 | "keywords": [ 6 | "botbuilder", 7 | "bots", 8 | "chatbots", 9 | "azure" 10 | ], 11 | "author": "Microsoft Corp.", 12 | "license": "MIT", 13 | "bugs": { 14 | "url": "https://github.com/Microsoft/BotBuilder-Azure/issues" 15 | }, 16 | "repository": { 17 | "type": "git", 18 | "url": "https://github.com/Microsoft/BotBuilder-Azure.git" 19 | }, 20 | "scripts": { 21 | "test": "echo \"Error: no test specified\" && exit 1" 22 | }, 23 | "main": "./lib/botbuilder-azure.js", 24 | "typings": "./lib/botbuilder-azure.d.ts", 25 | "dependencies": { 26 | "@types/tedious": "^1.8.31", 27 | "async": "^2.1.2", 28 | "azure-storage": "^2.6.0", 29 | "botbuilder": "^3.11.0", 30 | "documentdb": "^1.13.0", 31 | "promise": "^7.1.1", 32 | "tedious": "^2.0.0" 33 | }, 34 | "devDependencies": { 35 | "@types/async": "^2.0.44", 36 | "@types/documentdb": "0.0.33", 37 | "@types/node": "^7.0.64", 38 | "@types/promise": "^7.1.30", 39 | "@types/tedious": "^1.8.31" 40 | } 41 | } 42 | -------------------------------------------------------------------------------- /Node/readme.md: -------------------------------------------------------------------------------- 1 | # Bot Builder Azure Extensions for Node.js 2 | Bot Builder Azure Extensions for Node.js enable bot developers to integrate bots with specific Azure components. 3 | 4 | 5 | 6 | ## High level features: 7 | 8 | * Azure Table Storage: Allows bot developers to store bot state in their own Azure Storage accounts. For more information on Azure Table Storage, visit the **[Azure Table Storage Documentation](https://azure.microsoft.com/en-us/services/storage/tables/)** 9 | * Azure CosmosDb: Allows bot developers to store bot state in CosmosDb. For more information on Azure CosmosDb, visit the **[Azure CosmosDB Documentation](https://docs.microsoft.com/en-us/azure/cosmos-db/introduction)** 10 | * Azure SQL Database: Allows bot developers to store bot state using Azure SQL. For more information on Azure SQL, visit the **[Azure SQL Database Documentation](https://docs.microsoft.com/en-us/azure/sql-database/)** 11 | 12 | ## Prepare to Build a Bot 13 | 14 | Create a folder for your bot, cd into it, and run npm init. 15 | 16 | npm init 17 | 18 | Get the BotBuilder, BotBuilder-Azure and Restify modules using npm. 19 | 20 | npm install --save botbuilder 21 | npm install --save botbuilder-azure 22 | npm install --save restify 23 | 24 | ## Sample 25 | 26 | You can base your first bot on one of our samples, which showcase using [Azure Table Storage](examples/feature-azureTable/app.js), [CosmosDb](examples/feature-documentDb/app.js) and [Azure SQL Database](examples/feature-azureSql/app.js). Read the detailed steps in the sample to set up storage emulators or connect to Azure. 27 | 28 | ## Test your bot 29 | Use the [Bot Framework Emulator](http://docs.botframework.com/connector/tools/bot-framework-emulator/) to test your bot on localhost. 30 | 31 | Install the emulator from [here](http://aka.ms/bf-bc-emulator) and then start your bot in a console window. 32 | 33 | node app.js 34 | 35 | Start the emulator and say "hello" to your bot. 36 | 37 | ## Publish your bot 38 | Deploy your bot to the cloud and then [register it](http://docs.botframework.com/connector/getstarted/#registering-your-bot-with-the-microsoft-bot-framework) with the Microsoft Bot Framework. If you're deploying your bot to Microsoft Azure you can use this great guide for [Publishing a Node.js app to Azure using Continuous Integration](https://blogs.msdn.microsoft.com/sarahsays/2015/08/31/building-your-first-node-js-app-and-publishing-to-azure/). 39 | 40 | NOTE: When you register your bot with the Bot Framework you'll want to update the appId & appSecret for both your bot and the emulator with the values assigned to you by the portal. 41 | 42 | ## Bot Framework 43 | 44 | The Microsoft Bot Framework provides just what you need to build and connect intelligent bots that interact naturally wherever your users are talking, from text/sms to Skype, Slack, Office 365 mail and other popular services. 45 | 46 | Bots (or conversation agents) are rapidly becoming an integral part of one’s digital experience – they are as vital a way for users to interact with a service or application as is a web site or a mobile experience. Developers writing bots all face the same problems: bots require basic I/O; they must have language and dialog skills; and they must connect to users – preferably in any conversation experience and language the user chooses. The Bot Framework provides tools to easily solve these problems and more for developers e.g., automatic translation to more than 30 languages, user and conversation state management, debugging tools, an embeddable web chat control and a way for users to discover, try, and add bots to the conversation experiences they love. 47 | 48 | 49 | ## Dive deeper 50 | Learn how to build great bots. 51 | 52 | * [Core Concepts Guide](http://docs.botframework.com/builder/node/guides/core-concepts/) 53 | * [Bot Builder for Node.js Reference](http://docs.botframework.com/sdkreference/nodejs/modules/_botbuilder_d_.html) 54 | -------------------------------------------------------------------------------- /Node/src/BotServiceConnector.ts: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) Microsoft. All rights reserved. 3 | // Licensed under the MIT license. 4 | // 5 | // Microsoft Bot Framework: http://botframework.com 6 | // 7 | // Bot Builder SDK Github: 8 | // https://github.com/Microsoft/BotBuilder 9 | // 10 | // Copyright (c) Microsoft Corporation 11 | // All rights reserved. 12 | // 13 | // MIT License: 14 | // Permission is hereby granted, free of charge, to any person obtaining 15 | // a copy of this software and associated documentation files (the 16 | // "Software"), to deal in the Software without restriction, including 17 | // without limitation the rights to use, copy, modify, merge, publish, 18 | // distribute, sublicense, and/or sell copies of the Software, and to 19 | // permit persons to whom the Software is furnished to do so, subject to 20 | // the following conditions: 21 | // 22 | // The above copyright notice and this permission notice shall be 23 | // included in all copies or substantial portions of the Software. 24 | // 25 | // THE SOFTWARE IS PROVIDED ""AS IS"", WITHOUT WARRANTY OF ANY KIND, 26 | // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 27 | // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 28 | // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 29 | // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 30 | // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 31 | // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 32 | // 33 | 34 | import * as builder from 'botbuilder'; 35 | 36 | export class BotServiceConnector extends builder.ChatConnector { 37 | constructor(settings?: builder.IChatConnectorSettings) { 38 | super(settings); 39 | } 40 | 41 | public listen(): (context: any, req: any) => void { 42 | var _listen = super.listen(); 43 | return (context, req) => { 44 | var response: IFunctionResponse = {}; 45 | _listen(req, { 46 | send: function (status: number, body?: any): void { 47 | if (context) { 48 | response.status = status; 49 | if (body) { 50 | response.body = body; 51 | } 52 | context.res = response; 53 | context.done(); 54 | context = null; 55 | } 56 | }, 57 | status: function (val?: number): number { 58 | if (typeof val === 'number') { 59 | response.status = val; 60 | } 61 | return response.status || 200; 62 | }, 63 | end: function () { 64 | if (context) { 65 | context.res = response; 66 | context.done(); 67 | context = null; 68 | } 69 | } 70 | }); 71 | }; 72 | } 73 | } 74 | 75 | interface IFunctionResponse { 76 | status?: number; 77 | body?: any; 78 | } 79 | -------------------------------------------------------------------------------- /Node/src/Consts.ts: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) Microsoft. All rights reserved. 3 | // Licensed under the MIT license. 4 | // 5 | // Microsoft Bot Framework: http://botframework.com 6 | // 7 | // Bot Builder SDK Github: 8 | // https://github.com/Microsoft/BotBuilder 9 | // 10 | // Copyright (c) Microsoft Corporation 11 | // All rights reserved. 12 | // 13 | // MIT License: 14 | // Permission is hereby granted, free of charge, to any person obtaining 15 | // a copy of this software and associated documentation files (the 16 | // "Software"), to deal in the Software without restriction, including 17 | // without limitation the rights to use, copy, modify, merge, publish, 18 | // distribute, sublicense, and/or sell copies of the Software, and to 19 | // permit persons to whom the Software is furnished to do so, subject to 20 | // the following conditions: 21 | // 22 | // The above copyright notice and this permission notice shall be 23 | // included in all copies or substantial portions of the Software. 24 | // 25 | // THE SOFTWARE IS PROVIDED ""AS IS"", WITHOUT WARRANTY OF ANY KIND, 26 | // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 27 | // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 28 | // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 29 | // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 30 | // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 31 | // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 32 | // 33 | 34 | export var developmentConnectionString = 'UseDevelopmentStorage=true'; 35 | export var maxDataLength = 65000; 36 | 37 | export var Fields = { 38 | UserDataField: 'userData', 39 | ConversationDataField: 'conversationData', 40 | PrivateConversationDataField: 'privateConversationData' 41 | }; 42 | 43 | export var tableName = 'BotStore'; 44 | export var hash = 'Hash'; 45 | export var base64 = 'base64'; 46 | 47 | export var HttpStatusCodes = { 48 | NotFound: '404' 49 | }; 50 | 51 | export var ErrorCodes = { 52 | MessageSize: 'EMSGSIZE', 53 | BadMessage: 'EBADMSG' 54 | }; 55 | 56 | export var DocDbRootQuery = 'SELECT * FROM root r WHERE r.id = @id' 57 | export var DocDbIdParam = '@id' -------------------------------------------------------------------------------- /Node/src/IStorageClient.ts: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) Microsoft. All rights reserved. 3 | // Licensed under the MIT license. 4 | // 5 | // Microsoft Bot Framework: http://botframework.com 6 | // 7 | // Bot Builder SDK Github: 8 | // https://github.com/Microsoft/BotBuilder 9 | // 10 | // Copyright (c) Microsoft Corporation 11 | // All rights reserved. 12 | // 13 | // MIT License: 14 | // Permission is hereby granted, free of charge, to any person obtaining 15 | // a copy of this software and associated documentation files (the 16 | // "Software"), to deal in the Software without restriction, including 17 | // without limitation the rights to use, copy, modify, merge, publish, 18 | // distribute, sublicense, and/or sell copies of the Software, and to 19 | // permit persons to whom the Software is furnished to do so, subject to 20 | // the following conditions: 21 | // 22 | // The above copyright notice and this permission notice shall be 23 | // included in all copies or substantial portions of the Software. 24 | // 25 | // THE SOFTWARE IS PROVIDED ""AS IS"", WITHOUT WARRANTY OF ANY KIND, 26 | // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 27 | // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 28 | // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 29 | // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 30 | // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 31 | // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 32 | // 33 | 34 | import * as builder from 'botbuilder'; 35 | 36 | export interface IStorageClient { 37 | initialize(callback: (error: any) => void): void; 38 | insertOrReplace(partitionKey: string, rowKey: string, entity: any, isCompressed: boolean, callback: (error: any, etag: any, response: IHttpResponse) => void): void; 39 | retrieve(partitionKey: string, rowKey: string, callback: (error: any, entity: IBotEntity, response: IHttpResponse) => void): void; 40 | } 41 | 42 | export interface IBotEntity { 43 | data: any; 44 | isCompressed: boolean; 45 | } 46 | 47 | export interface IHttpResponse { 48 | isSuccessful: boolean; 49 | statusCode: string; 50 | } 51 | 52 | export interface IStorageError { 53 | code: string; 54 | message: string; 55 | statusCode: string; 56 | } 57 | 58 | export interface IAzureTableClient extends IStorageClient{ 59 | 60 | } 61 | -------------------------------------------------------------------------------- /Node/src/botbuilder-azure.ts: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) Microsoft. All rights reserved. 3 | // Licensed under the MIT license. 4 | // 5 | // Microsoft Bot Framework: http://botframework.com 6 | // 7 | // Bot Builder SDK Github: 8 | // https://github.com/Microsoft/BotBuilder 9 | // 10 | // Copyright (c) Microsoft Corporation 11 | // All rights reserved. 12 | // 13 | // MIT License: 14 | // Permission is hereby granted, free of charge, to any person obtaining 15 | // a copy of this software and associated documentation files (the 16 | // "Software"), to deal in the Software without restriction, including 17 | // without limitation the rights to use, copy, modify, merge, publish, 18 | // distribute, sublicense, and/or sell copies of the Software, and to 19 | // permit persons to whom the Software is furnished to do so, subject to 20 | // the following conditions: 21 | // 22 | // The above copyright notice and this permission notice shall be 23 | // included in all copies or substantial portions of the Software. 24 | // 25 | // THE SOFTWARE IS PROVIDED ""AS IS"", WITHOUT WARRANTY OF ANY KIND, 26 | // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 27 | // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 28 | // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 29 | // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 30 | // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 31 | // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 32 | // 33 | 34 | import { BotServiceConnector } from './BotServiceConnector'; 35 | import { AzureBotStorage } from './AzureBotStorage'; 36 | import { AzureTableClient } from './AzureTableClient'; 37 | import { DocumentDbClient } from './DocumentDbClient'; 38 | import { AzureSqlClient } from './AzureSqlClient'; 39 | 40 | declare var exports: any; 41 | 42 | exports.BotServiceConnector = BotServiceConnector; 43 | exports.AzureBotStorage = AzureBotStorage; 44 | exports.AzureTableClient = AzureTableClient; 45 | exports.DocumentDbClient = DocumentDbClient; 46 | exports.AzureSqlClient = AzureSqlClient; -------------------------------------------------------------------------------- /Node/src/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "es5", 4 | "module": "commonjs", 5 | "sourceMap": false, 6 | "noImplicitAny": true, 7 | "outDir": "../lib", 8 | "noEmitOnError": true, 9 | "removeComments": true 10 | }, 11 | "exclude": [ 12 | "botbuilder-azure.d.ts" 13 | ] 14 | } -------------------------------------------------------------------------------- /Node/test/.vscode/launch.json: -------------------------------------------------------------------------------- 1 | { 2 | // Use IntelliSense to learn about possible Node.js debug attributes. 3 | // Hover to view descriptions of existing attributes. 4 | // For more information, visit: https://go.microsoft.com/fwlink/?linkid=830387 5 | "version": "0.2.0", 6 | "configurations": [ 7 | { 8 | "type": "node", 9 | "request": "launch", 10 | "name": "Launch Program", 11 | "program": "${workspaceRoot}/DocumentDbClientTest.js", 12 | "cwd": "${workspaceRoot}" 13 | }, 14 | { 15 | "type": "node", 16 | "request": "attach", 17 | "name": "Attach to Process", 18 | "port": 5858 19 | } 20 | ], 21 | "env": { 22 | "NODE_ENV": "development", 23 | "NODE_TLS_REJECT_UNAUTHORIZED": 0 24 | } 25 | } -------------------------------------------------------------------------------- /Node/test/.vscode/tasks.json: -------------------------------------------------------------------------------- 1 | { 2 | // See https://go.microsoft.com/fwlink/?LinkId=733558 3 | // for the documentation about the tasks.json format 4 | "version": "0.1.0", 5 | "command": "tsc", 6 | "isShellCommand": true, 7 | "args": ["-p", ".", "set NODE_TLS_REJECT_UNAUTHORIZED=0"], 8 | "showOutput": "silent", 9 | "problemMatcher": "$tsc" 10 | } -------------------------------------------------------------------------------- /Node/test/Readme.md: -------------------------------------------------------------------------------- 1 | #BotBuilder Node unit tests - Run instructions 2 | 3 | ## 1. Open the test project in Visual Studio Code 4 | ## 2. Start Azure Storage Emulator 5 | ## 3. In the file launch.json, under .vscode, edit the "program" attribute to run the test you want to execute. Example: 6 | 7 | `"program": "${workspaceRoot}/TableBotStorageFaultTest.js"` 8 | 9 | ## 4. In the Visual Studio Code interactive terminal, run the following command, specifying the same test file from step 3 10 | 11 | `mocha --debug-brk TableBotStorageFaultTest.js` 12 | 13 | ## 5. Open the debug view in Visual Studio Code 14 | ## 6. Make sure the debugger is configured to 'Attach to process' 15 | ## 7. Set breakpoints if needed and happy debugging! -------------------------------------------------------------------------------- /Node/test/lib/FaultyAzureTableClient.js: -------------------------------------------------------------------------------- 1 | "use strict"; 2 | var builderazure = require('../../'); 3 | var FaultyAzureTableClient = (function () { 4 | function FaultyAzureTableClient(client, faultSettings) { 5 | this.tableClient = client; 6 | this.faultSettings = faultSettings; 7 | } 8 | FaultyAzureTableClient.prototype.initialize = function (callback) { 9 | if (this.faultSettings.shouldFailInitialize) { 10 | callback(builderazure.AzureTableClient.getError(this.faultSettings.error, this.faultSettings.response)); 11 | } 12 | else { 13 | this.tableClient.initialize(callback); 14 | } 15 | }; 16 | FaultyAzureTableClient.prototype.insertOrReplace = function (partitionKey, rowKey, data, isCompressed, callback) { 17 | if (this.faultSettings.shouldFailInsert) { 18 | callback(builderazure.AzureTableClient.getError(this.faultSettings.error, this.faultSettings.response), null, this.faultSettings.response); 19 | } 20 | else { 21 | this.tableClient.insertOrReplace(partitionKey, rowKey, data, isCompressed, callback); 22 | } 23 | }; 24 | FaultyAzureTableClient.prototype.retrieve = function (partitionKey, rowKey, callback) { 25 | if (this.faultSettings.shouldFailRetrieve) { 26 | callback(builderazure.AzureTableClient.getError(this.faultSettings.error, this.faultSettings.response), null, this.faultSettings.response); 27 | } 28 | else { 29 | this.tableClient.retrieve(partitionKey, rowKey, callback); 30 | } 31 | }; 32 | return FaultyAzureTableClient; 33 | }()); 34 | exports.FaultyAzureTableClient = FaultyAzureTableClient; 35 | -------------------------------------------------------------------------------- /Node/test/src/FaultyAzureTableClient.ts: -------------------------------------------------------------------------------- 1 | // 2 | // Copyright (c) Microsoft. All rights reserved. 3 | // Licensed under the MIT license. 4 | // 5 | // Microsoft Bot Framework: http://botframework.com 6 | // 7 | // Bot Builder SDK Github: 8 | // https://github.com/Microsoft/BotBuilder 9 | // 10 | // Copyright (c) Microsoft Corporation 11 | // All rights reserved. 12 | // 13 | // MIT License: 14 | // Permission is hereby granted, free of charge, to any person obtaining 15 | // a copy of this software and associated documentation files (the 16 | // "Software"), to deal in the Software without restriction, including 17 | // without limitation the rights to use, copy, modify, merge, publish, 18 | // distribute, sublicense, and/or sell copies of the Software, and to 19 | // permit persons to whom the Software is furnished to do so, subject to 20 | // the following conditions: 21 | // 22 | // The above copyright notice and this permission notice shall be 23 | // included in all copies or substantial portions of the Software. 24 | // 25 | // THE SOFTWARE IS PROVIDED ""AS IS"", WITHOUT WARRANTY OF ANY KIND, 26 | // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF 27 | // MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND 28 | // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE 29 | // LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION 30 | // OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION 31 | // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. 32 | // 33 | 34 | import * as builder from 'botbuilder'; 35 | import * as builderazure from '../../'; 36 | 37 | export class FaultyAzureTableClient implements builderazure.IAzureTableClient { 38 | 39 | private readonly tableClient: builderazure.IAzureTableClient; 40 | private readonly faultSettings: IFaultSettings; 41 | 42 | constructor(client: builderazure.IAzureTableClient, faultSettings: IFaultSettings) { 43 | this.tableClient = client; 44 | this.faultSettings = faultSettings; 45 | } 46 | 47 | public initialize(callback: (error: Error) => void): void { 48 | 49 | if(this.faultSettings.shouldFailInitialize){ 50 | callback((builderazure.AzureTableClient).getError(this.faultSettings.error, this.faultSettings.response)); 51 | } 52 | else { 53 | this.tableClient.initialize(callback); 54 | } 55 | } 56 | 57 | public insertOrReplace(partitionKey: string, rowKey: string, data: string, isCompressed: boolean, callback: (error: Error, etag: any, response: builderazure.IHttpResponse) => void): void { 58 | 59 | if(this.faultSettings.shouldFailInsert){ 60 | callback((builderazure.AzureTableClient).getError(this.faultSettings.error, this.faultSettings.response), null, this.faultSettings.response); 61 | } 62 | else { 63 | this.tableClient.insertOrReplace(partitionKey, rowKey, data, isCompressed, callback); 64 | } 65 | } 66 | 67 | public retrieve(partitionKey: string, rowKey: string, callback: (error: Error, entity: any, response: builderazure.IHttpResponse) => void): void { 68 | 69 | if(this.faultSettings.shouldFailRetrieve){ 70 | callback((builderazure.AzureTableClient).getError(this.faultSettings.error, this.faultSettings.response), null, this.faultSettings.response); 71 | } 72 | else { 73 | this.tableClient.retrieve(partitionKey, rowKey, callback); 74 | } 75 | } 76 | } 77 | 78 | export interface IFaultSettings { 79 | shouldFailInsert: boolean; 80 | shouldFailInitialize: boolean; 81 | shouldFailRetrieve: boolean; 82 | error: builderazure.IStorageError; 83 | response: builderazure.IHttpResponse; 84 | } -------------------------------------------------------------------------------- /Node/test/src/tsconfig.json: -------------------------------------------------------------------------------- 1 | { 2 | "compilerOptions": { 3 | "target": "es5", 4 | "module": "commonjs", 5 | "sourceMap": false, 6 | "noImplicitAny": true, 7 | "outDir": "../lib", 8 | "noEmitOnError": true, 9 | "removeComments": true 10 | } 11 | } -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # V3 Deprecation Notification 2 | 3 | Microsoft Bot Framework SDK V4 was released in September 2018, and since then we have shipped a few dot-release improvements. As announced previously, the V3 SDK is being retired with final long-term support ending on December 31st, 2019. 4 | Accordingly, there will be no more development in this repo. **Existing V3 bot workloads will continue to run without interruption. We have no plans to disrupt any running workloads**. 5 | 6 | We highly recommend that you start migrating your V3 bots to V4. In order to support this migration we have produced migration documentation and will provide extended support for migration initiatives (via standard channels such as Stack Overflow and Microsoft Customer Support). 7 | 8 | For more information please refer to the following references: 9 | * Migration Documentation: https://aka.ms/v3v4-bot-migration 10 | * End of lifetime support announcement: https://aka.ms/bfmigfaq 11 | * Primary V4 Repositories to develop Bot Framework bots 12 | * [Botbuilder for dotnet](https://github.com/microsoft/botbuilder-dotnet) 13 | * [Botbuilder for JS](https://github.com/microsoft/botbuilder-js) 14 | * QnA Maker Libraries were replaced with the following V4 libraries: 15 | * [Libraries for dotnet](https://github.com/Microsoft/botbuilder-dotnet/tree/master/libraries/Microsoft.Bot.Builder.AI.QnA) 16 | * [Libraries for JS](https://github.com/Microsoft/botbuilder-js/blob/master/libraries/botbuilder-ai/src/qnaMaker.ts) 17 | * Azure Libraries were replaced with the following V4 libraries: 18 | * [Botbuilder for JS Azure](https://github.com/Microsoft/botbuilder-js/tree/master/libraries/botbuilder-azure) 19 | * [Botbuilder for dotnet Azure](https://github.com/Microsoft/botbuilder-dotnet/tree/master/libraries/Microsoft.Bot.Builder.Azure) 20 | 21 | 22 | # Bot Builder SDK Azure Extensions 23 | 24 | The Microsoft Bot Builder SDK Azure Extensions allow for interactions with specific Azure components. 25 | 26 | ## Bot Builder SDK 27 | 28 | For More information about the Bot Builder SDK, which is one of the three main components of the Microsoft Bot Framework, please **[Review the documentation](http://docs.botframework.com)**. 29 | 30 | The Microsoft Bot Framework provides just what you need to build and connect intelligent bots that interact naturally wherever your users are talking, from text/sms to Skype, Slack, Office 365 mail and other popular services. 31 | 32 | Bots (or conversation agents) are rapidly becoming an integral part of one’s digital experience – they are as vital a way for users to interact with a service or application as is a web site or a mobile experience. Developers writing bots all face the same problems: bots require basic I/O; they must have language and dialog skills; and they must connect to users – preferably in any conversation experience and language the user chooses. The Bot Framework provides tools to easily solve these problems and more for developers e.g., automatic translation to more than 30 languages, user and conversation state management, debugging tools, an embeddable web chat control and a way for users to discover, try, and add bots to the conversation experiences they love. 33 | 34 | ## Azure Extensions 35 | 36 | ### Bot Azure Storage 37 | 38 | The Bot Builder SDK Azure Extensions enable bot developers to integrate bots with specific Azure components. 39 | 40 | * Azure Table Storage: Allows bot developers to store bot state in their own Azure Storage accounts. For more information on Azure Table Storage, visit the **[Azure Table Storage 41 | Documentation](https://azure.microsoft.com/en-us/services/storage/tables/)** 42 | * Azure CosmosDB: Allows bot developers to store bot state in CosmosDB. For more information on Azure CosmosDb, visit the **[Azure CosmosDB Documentation](https://docs.microsoft.com/en-us/azure/cosmos-db/introduction)** 43 | 44 | ### Azure Table Logging 45 | 46 | The Bot Builder SDK Azure Extensions also include [TableLogger](CSharp/Library/Microsoft.Bot.Builder.Azure/TableLogger.cs), an implementation of IActivityLogger which will log activities to the specified Azure Table. 47 | 48 | ## Azure Extensions Samples 49 | 50 | Get started quickly with our samples: 51 | 52 | * Azure Table [C#](CSharp/Samples/AzureTable) [Node.js](Node/examples/feature-azureTable) 53 | * CosmosDb [C#](CSharp/Samples/DocumentDb) [Node.js](Node/examples/feature-documentDb) 54 | 55 | See all the support options **[here](https://docs.botframework.com/en-us/support/)**. 56 | 57 | ## Published Libraries 58 | * Nuget package for .NET [Microsoft.Bot.Builder.Azure](https://www.nuget.org/packages/Microsoft.Bot.Builder.Azure/) 59 | * NPM package for nodejs [botbuilder-azure](https://www.npmjs.com/package/botbuilder-azure) 60 | 61 | ## Botbuilder v4 62 | 63 | * V4 for botbuilder-azure [Node.js](https://github.com/Microsoft/botbuilder-js/tree/master/libraries/botbuilder-azure) 64 | * V4 for botbuilder-azure [CSharp](https://github.com/Microsoft/botbuilder-dotnet/tree/master/libraries/Microsoft.Bot.Builder.Azure) 65 | --------------------------------------------------------------------------------