SmoothLingua
A .NET library for building conversational agents powered by intent recognition, story-based dialogue management, and rule-based responses.
SmoothLingua is designed for teams that want a lightweight, code-first alternative to heavy conversational AI frameworks — you define your agent entirely in C# and run it anywhere .NET runs, with no external services required.
Installation
Install SmoothLingua via the .NET CLI:
dotnet add package SmoothLingua
Or via the NuGet Package Manager Console:
Install-Package SmoothLingua
Quick Start
Define a domain, train it, load the agent, and start handling messages:
using SmoothLingua;
using SmoothLingua.Abstractions;
using SmoothLingua.Abstractions.Stories;
// 1. Define and train the domain in memory
MemoryStream memoryStream = new();
Trainer trainer = new();
await trainer.Train(new Domain(
[
new("Greeting", ["Hello", "Hi"]),
new("Good", ["I am fine", "I am good, thank you"]),
new("Bad", ["I am feeling bad", "I am not good"]),
new("Bye", ["Good bye", "Bye"]),
new("IAmFrom", ["I am from USA", "I am from Bulgaria", "I am from Germany"])
],
[
new("Good",
[
new IntentStep("Greeting"),
new ResponseStep("Hello! How are you?"),
new IntentStep("Good"),
new ResponseStep("Glad to hear that! Where are you from?"),
new IntentStep("IAmFrom"),
new ResponseStep("It is nice in {country}!")
]),
new("Bad",
[
new IntentStep("Greeting"),
new ResponseStep("Hello! How are you?"),
new IntentStep("Bad"),
new ResponseStep("I am sorry to hear that.")
])
],
[new("Bye", "Bye", "Bye")],
[new Slot("country", "IAmFrom", "country", "")],
[new Entity("country", new HashSet<string> { "Bulgaria", "USA", "Germany" })]
), memoryStream, default);
// 2. Load the trained agent and start a conversation
var agent = await AgentLoader.Load(new MemoryStream(memoryStream.GetBuffer()));
var conversationId = Guid.NewGuid().ToString();
var r = agent.Handle(conversationId, "bye");
// r.IntentName == "Bye", r.Messages == ["Bye"]
r = agent.Handle(conversationId, "hello");
// r.IntentName == "Greeting", r.Messages == ["Hello! How are you?"]
r = agent.Handle(conversationId, "I am fine");
// r.IntentName == "Good", r.Messages == ["Glad to hear that! Where are you from?"]
r = agent.Handle(conversationId, "I am from Bulgaria");
// r.IntentName == "IAmFrom", r.Messages == ["It is nice in Bulgaria!"]
Load a model from file
Train once and persist to disk — no retraining needed on subsequent starts:
// Train and save
await trainer.Train(domain, "model.zip", default);
// Load on every restart
var agent = await AgentLoader.Load("model.zip");
Concepts
Intent
A named category of user utterances. You supply example phrases and the ML trainer learns to recognise
them. An Intent named Greeting with examples ["Hello", "Hi"] will
match any similar greeting at runtime.
Story
A multi-turn conversation flow defined as an ordered list of IntentStep and
ResponseStep entries. Stories model sequences: "after the user greets, reply; if they say
they're fine, reply differently than if they say they're sad."
Rule
An always-active, single-turn shortcut. A rule fires whenever its intent is predicted, regardless of
conversation context. Use rules for commands like Bye that should always produce the same
response.
Domain
The bundle that groups all intents, stories, rules, slots, and entities into one trainable unit. Pass a
Domain to Trainer.Train, which serialises it (together with the trained ML
model) into a zip archive you can store anywhere.
Agent
The runtime object that handles user input. Obtain one via AgentLoader.Load. It predicts
the intent, advances the conversation state, and returns a Response containing the matched
intent name and the bot's reply messages.
When SmoothLingua, when not
Good fit
- .NET applications that need embedded conversational logic with no external services
- Prototypes and internal tools where you want full control over training data and model lifecycle
- Chatbots with a finite, well-defined intent set (up to ~50 intents)
- Offline or air-gapped environments
Not a good fit
- Large-scale open-domain conversation — use a hosted LLM instead
- Use cases that require deep semantic understanding beyond the ML.NET SDCA classifier
- Teams that need a visual or no-code dialogue editor
Changelog
See what's new added, changed, fixed, improved or updated in the latest versions.
Version 2.1.0 (9 June, 2026)
- Added
IConversationStoreabstraction in the core package — no ASP.NET dependency. ExposesGet,Save, andReset; works identically in a console app, a desktop tool, or a web service. - Added
InMemoryConversationStore— default implementation, existing behaviour preserved exactly. - Added
FileConversationStore— durable implementation that serialises each conversation as a JSON file. State survives process restarts with no external dependencies. - Added
SmoothLingua.Server— minimal ASP.NET Core Web API:POST /conversations/{id}/messages,POST /conversations/{id}/reset,GET /health, and anAddSmoothLinguaDI extension. - Added Dockerfile for
SmoothLingua.Server— multi-stage build,/app/datavolume for model and store. - Updated
AgentLoader.LoadandConversationManageraccept an optionalIConversationStore— fully backward compatible.
Version 2.0.0 (8 June, 2026)
- Added Confidence score on every prediction (softmax-normalised, range 0–1)
- Added Fallback intent when confidence falls below a configurable threshold (default 0.4)
- Added Lookup-based entity extraction — matched values returned in
Response.ExtractedEntities - Added
Domain.ConfidenceThresholdandDomain.FallbackIntentNameconfiguration fields - Breaking
Responsegains a requiredConfidencefield — see migration notes in the GitHub release - Breaking
IPredictor.Predictnow returns(string IntentName, float Confidence)
Version 1.2.0 (2026)
- Added Rewritten README with Concepts, Quick Start, and When/Not guidance
- Added XML documentation on all public types — improves IntelliSense for consumers
- Added File-based model loading example in QuickStart
- Added Automated website deploy workflow
- Updated Website content aligned with library documentation
Version 1.1.0 (6 June, 2026)
- Added Automated release pipeline — push a
v*tag to build, test, pack, and publish to NuGet automatically - Added GitHub Releases auto-generated on each tag push
- Added CHANGELOG.md and CONTRIBUTING.md
- Added GitHub issue and pull request templates
- Added Code coverage via Coverlet
- Updated CI split into build-and-test and release workflows
Version 1.0.6 (1 January, 2024)
Initial public release — intent recognition, story management, rule-based responses, Trainer, Agent, AgentLoader, NuGet package.