Welcome to the Alliance Business Suite Documentation!
Aiming to help organizations reach beyond expectations, the Alliance Business Suite is designed to augment businesses across industries worldwide through a low-code, and fully customizable business development platform.
At a very high level, the Alliance Business Suite is a set of powerful, extensible, multi-tenant applications built to enable businesses to jumpstart their digitalization process through powerful business applications built to cover the core processes of any given business.
The Alliance Business Suite provides customers with a Full-Stack, Low-Code, Modular, and Multi-Tenant Business Application Framework built on top of the Alliance Business Platform.
The Alliance Business Suite relies on five major components designed to separate different functionalities into layers; these components are:
The Alliance Core Libraries contain the core abstractions and default implementations required by the Alliance Business Model and dependent components. It is also the external dependency source for the entire Alliance Business Suite, which means that external dependencies, which are dependencies outside the FenixAlliance.*
namespace, are referenced by the FenixAlliance.ACL.Deps
Package, which is the base ACL Package and, therefore, it could be referred to as the Core Package.
For more information on the dependency tree, design overview, and external dependencies, please refer to Advanced Topics.
The Alliance Business Model is a declarative specification and definition of standard entities that represent commonly used concepts and activities across business and productivity applications and is being extended to observational and analytical data as well. ABM provides well-defined, modular, and extensible business entities such as Accounts, Business Units, cases, Contact, Leads, Opportunity, and Items (Products/Services) and interactions with vendors, workers, and customers, such as activities and service level agreements. that serve as the dynamic data layer for the entire Alliance Business Suite.
Anyone can build on and extend ABM definitions to capture additional business-specific scenarios.
The Alliance Passport Service enables developers and non-developers alike The Alliance Passport Service is an Authentication/Authorization Engine designed to enable customers to easily configure and manage business identity scenarios by assigning (or connecting) a digital identity to their contacts, whether they are customers, employees, partners, guests, and more.
It also provides common features for managing authentication, authorization, data protection, HTTPS enforcement, app secrets, XSRF/CSRF prevention, and CORS management. These security features allow you to build robust, yet secure Alliance Business Suite apps.
The Alliance Business Platform is a Modular API Framework. It leverages .NET 5.0 with the best of REST, SignalR, GraphQl y gRPCto transact with the Alliance Business Model Schema (AMB). The Alliance Business Platform is an open-source and cross-platform framework for integrating next-generation functionalities into your applications. It allows you to build spectacular single-page apps using .NET and C# with or without JavaScript. ABP apps can connect and transact to the data layer (The Alliance Business Modal Schema) using any language through standard requests through the various GrPC, HTTP, and GraphQL Endpoints.
To capture additional business-specific scenarios, you can easily build on and extend The Alliance Business Platform through ASP.NET + Angular / React (And pretty much any Web Stack Framework).
The Alliance Business Studio is the Graphical Administration Engine for the Alliance Business Suite. It allows users to manage their implementations, transact data through the Alliance Business Platform, generate and consume views, and reports, customize and extend the system, and much more.
You can build on top of, and extend The Alliance Business Studio to capture additional business-specific scenarios.
How to build applications on top of the Alliance Business Suite?
Client and server code are written in C#, allowing users to extend the product with their code through Module libraries. It builds upon next-generation technologies such as Blazor, SignalR, Razor Pages, and MVC through .NET, an open-source and cross-platform framework for building web-mobile apps using C#, with or without the use of JavaScript.
The power of the Alliance Business Suite can be leveraged from small personal blogs, eCommerce platforms, and professional portfolios to the infrastructure of large corporations.
User Guide
Getting Started
- Install .NET 6 SDK (v6.0.*).
For Business Use.
- Download or Clone the latest Alliance Business Suite release. Decompress the downloaded
.zip
on a folder on your PC, navigate to that folder and execute theFenixAlliance.ABS.Web.exe
file.
A console window will pop up, providing information about the initialization process. Open your server on the provided URL, go through the installation wizard, and start using the Alliance Business Suite. For more information about hosting your Alliance Business Suite instance, please refer to Hosting your Alliance Business Suite.
For Developer Users
-
Install the latest edition (v16.8 or higher) of Visual Studio 2019 (Community, Professional, or Enterprise Editions) with the ASP.NET and web development workload enabled. Alliance Business Suite works with ALL editions of Visual Studio from Community to Enterprise. If you do not have a SQL Server installation available already and you wish to use LocalDB for development, you must also install the .NET desktop development workload.
-
Download a release or Clone the ABS. Portal repository to your local system using Git. Open the FenixAlliance.ABS.Portal.sln solution file and Build the solution. Make sure you specify FenixAlliance.ABS.Portal as the Startup Project and then Run the application.
Installing an official release:
- A detailed set of instructions for installing Alliance Business Suite on IIS is located here: Installing Alliance Business Suite on IIS
- Instructions for upgrading Alliance Business Suite are located here: Upgrading Alliance Business Suite
Additional Instructions
-
If you have already installed a previous version of Alliance Business Suite and you wish to do a clean database install, simply point the DefaultConnection value in the ABS Portal Settings Manager to a fresh database record. This will trigger a re-install when you run the application which will execute the database installation scripts.
-
Every ABS Repo ignores appsettings.json by default, so as long as you don't delete the directive from .gitignore, you're cleared to submit a pull request.
Video Series
- If you are getting started with Alliance Business Suite, a series of videos are available that explain how to install the product, interact with the user interface, and develop custom modules.
Documentation
There is a separate Documentation repository, which contains various types of documentation for the Alliance Business Suite, including the C# API documentation for every class on every library. The contents of the repository are available at https://docs.absuite.net as interactive documentation.
Easy Install
The Easy Way: As a Docker Container.
docker pull FenixAlliance.ABS:latest
Conventional Install
git clone https://github.com/FenixAlliance/ABS.Bin
cd ABS.Bin
./FenixAlliance.ABS.Web.exe
or
dotnet FenixAlliance.ABS.Web.dll
Installing as an application dependency
dotnet nuget add source https://nuget.absuite.net/nuget -n absuite.net
dotnet add package FenixAlliance.ABS.Hub --version latest
dotnet add package FenixAlliance.ABS.Assets --version latest
using FenixAlliance.ABS.Hub.Extensions;
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting.Server.Features;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using System;
namespace FenixAlliance.ABS
{
public class Startup
{
public IHostEnvironment Environment { get; set; }
public IConfiguration Configuration { get; }
// Constructor
public Startup(IConfiguration Configuration, IHostEnvironment Environment)
{
this.Environment = Environment;
this.Configuration = Configuration;
}
// This method gets called by the runtime. Use this method to add services to the container.
public void ConfigureServices(IServiceCollection services)
{
services.AddAllianceBusinessSuite(Configuration, Environment);
}
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
public void Configure(IApplicationBuilder app)
{
app.UseAllianceBusinessSuite(Configuration, Environment);
}
}
}
using FenixAlliance.ABS.Hub.Extensions;
var builder = WebApplication.CreateBuilder(args);
builder.Services.AddAllianceBusinessSuite(builder.Configuration, builder.Environment);
var app = builder.Build();
app.UseAllianceBusinessSuite(builder.Configuration, builder.Environment);
app.Run();
Release Announcements
Example Screenshots
ABS Studio Dashboard:
ABS Extensions:
The ABS is modular. Whether you need to add pages, products, or posts with no code at all (using the ABS Web Designer), modify the style or layout, or add your Types, Controllers, Pages, Views, Components, or Tag Helpers
ABS Commander Terminal:
The ABS Commander Terminal is a Built-In functionality that allows users to execute commands against the ABP set of APIs.
ABS WOPI Connector:
The ABS Workplace Module allows users to create, view, and edit Office files with Office for the web, right from their ABS Instances. It also allows users to manage files for pretty much every entity type.
ACS Bot Maker:
The Alliance Conversational Services Bot Maker Platform is an ABS extension that allows users to create conversational flows using NLP and a graphical UI.
Versioning
Maintaining forward and backward compatibility is a key goal of the ABS. Therefore, the ABS now uses only additive versioning, which means any revision of the ABM following the "2.0" release will not:
- Introduce new mandatory attributes on previously published entities, or change an optional attribute to be mandatory
- Rename previously published attributes or entities
- Remove previously published attributes
🤝 Contributing
Contributions, issues, and feature requests are welcome!
Feel free to check issues page. You can also take a look at the contributing guide.
- Issue Guidelines
- Report Security Vulnerabilities
- Pull Request Requirements
- Translations
- Chart of Accounts
Show your support
Give this project a ⭐️ if this project helped you!
Author
👤 Fenix Alliance Inc.
- Website: https://fenix-alliance.com
- Twitter: @fenixalliance
- Github: @fenixalliance
- LinkedIn: Fenix Alliance on LinkedIn
Logo and Trademark
The brand name Alliance Business Suite and its logos are trademarks of Fenix Alliance S.A.S in Colombia and Fenix Alliance Inc in other countries ("Fenix Alliance").
Fenix Alliance owns and oversees the trademarks for the ABS name and logos. We have developed this trademark usage policy with the following goals in mind:
- We’d like to make it easy for anyone to use the ABS name or logo for community-oriented efforts that help spread and improve ABS.
- We’d like to make it clear how ABS-related businesses and projects can (and cannot) use the ABS name and logo.
- We’d like to make it hard for anyone to use the ABS name and logo to unfairly profit from, trick, or confuse people who are looking for official ABS resources.
Licensing and Contributions
Your access to and use of the Alliance Business Suite's source code is governed by the Fenix Alliance's End User License Agreement "EULA". If you don't agree to those terms, as amended from time to time, you are not permitted to access or use the Alliance Business Suite.
We welcome any contributions to the Alliance Business Suite development through pull requests on GitHub. Most of our active development is in the development branch, so we prefer to take pull requests there (particularly for new features). We try to make sure that all new code adheres to the Fenix Alliance coding standards. All contributions are governed by the terms of the EULA.
Legal Notices
Fenix Alliance and any contributors grant you a license to the documentation and other content in this repository under the Creative Commons Attribution 4.0 International Public License and grant you a license to any code or binary form Fenix Alliance through the ABS EULA.
Fenix Alliance, Alliance Business Suite, Infinity Comex, and/or other Fenix Alliance products and services referenced in the documentation may be trademarks or registered trademarks of Fenix Alliance Inc. in the United States/or other countries. The licenses for this project do not grant you rights to use any of Fenix Alliance's names, logos, or trademarks. Fenix Alliance's general trademark guidelines can be found at http://docs.fenix-alliance.com.
Privacy information can be found at https://fenix-alliance.com/legal/policies/privacypolicy
Fenix Alliance and any contributors reserve all other rights, whether under their respective copyrights, patents, or trademarks, whether by implication, estoppel, or otherwise.
About this Documentation
Welcome to the Alliance Business Suite documentation! We are on the mission to create the Ultimate Business Development Platform to provide you an unprecedented suite of capabilities to ensure your business can exceed customer's expectations through next-generation experiences.
We believe that knowing your customers and your business enables you to personalize each experience and optimizes efficiencies so you can earn customers for life.
This documentation is constantly being developed and adapted to the latest version of the Alliance Business Suite and its goal is to provide an extensive guide for technical and non-technical audiences alike. At a very high level, this documentation provides guides on how to perform common tasks within the Alliance Business Suite, but it also digs deeper, sometimes, into technical details; but don't worry, we'll let you know the technical difficulty at the beginning of every guide.
Some guides contained in this documentation require special Business Permissions or installable software. Requirements, if any, will be highlighted at the beginning of each guide.
Some parts of this documentation are still being developed and changes are made to it every day, so please feel free to request further explanation or provide feedback about features you would like us to explain in more detail.
Contributing to the Alliance Business Suite and/or its documentation
Woohoo! You've decided to contribute? That's amazing! We want to make contributions to the Alliance Business Suite as easy and frictionless as we can. Contributing requires a GitHub account. If you don't have an account, follow the instructions for the GitHub account setup.
Then, you just need to create an Issue to report bugs, propose APIs, request features and tooling, propose designs and improvements.
All of these contributions will be filled as Issues on the Alliance Business Suite Documentation Repository and they adhere to the Issue Management Policy.
Roadmap
This project is a work in progress and the schedule for implementing enhancements is dependent upon the availability of community members who are willing/able to assist. For a more comprehensive look at our roadmap, please visit our Progess Board.
Proposed:
- Node.js SDK
- PowerShell SDK
- Agreement Template Definitions
- Email Signature Template Definitions
- Document Template Definitions
- Article Template Definitions
- gRPC Modularization
- Reporting Dashboard
- Dynamic Dashboards
- gRPC Modularization
- ACS Modularization
- UBL 2.1 Support
- Process Canvas.
- Granular Property Set Access
- Custom Includes Definitions
- Virtual Entity Data Sources
- In-Portal Live Chat Widget
- ML-Based Search Results Ranking Engine
- ML-Based Fraud Detection Engine (Anomaly Detection), (Binary Classification)
- ML-Based Price Prediction Engine
- ML-Based Sales Spike Detection Engine (Anomaly Detection)
- ML-Based Sales Forecasting Engine (Regression), (Time Series)
- ML-Based Sentiment Analysis Engine
- ML-Based Customer Segregation Engine (Clustering)
Planned:
- Node Package for Static Assets distribution & version management
- New IService interface & Default Implementation as an optional base for Service Interfaces.
Achieved:
- ✅ MudBlazor Integration is now available for Studio Modules
- ✅ Fluent UI Integration is now available for Studio Modules
- ✅ FAST Design Integration is now available for Studio Modules
- ✅ New IDateTimeService interface & Default Implementation for Date/Time Localization.
- ✅ New IServicesService interface & Default Implementation for service resolution helpers through DI.
- ✅ New IService interface & Default Implementation as an optional base for Service Interfaces.
- ✅ .NET 6.0 LTS Update
- ✅ Studio Layout Localization
- ✅ Code Editor: Razor Syntax Highlighting
- ✅ ML-Based Natural Language Processing Engine
- ✅ ML-Based eCommerce Recommendation Engine
- ✅ Template Definitions
- ✅ ML-Based Spam Detection Engine
- ✅ In-Studio Live Chat Manager
- ✅ Code Editor: Diagnostics Highlighting
- ✅ Workflow Manager Engine (Experimental)
- ✅ Workflow Visual Designer (Experimental)
- ✅ ML-Based Language Detection Engine
- ✅ Fluid Support (Experimental)
- ✅ Email Template Definitions
- ✅ Blazor Support (Experimental)
- ✅ Options & Settings API
- ✅ .NET SDK
- ✅ Custom Options Manager
- ✅ Custom Portal Option Definitions
- ✅ Virtual SPA Support (Angular/React)
- ✅ Razor Templating Engine
- ✅ Live Web Designer Integration
- ✅ Dynamic Entity Views
- ✅ Content Live Builder
- ✅ Custom Controller Definitions
- ✅ Portal Settings Manager UI
- ✅ Custom Option Definitions
- ✅ Custom Service Endpoint Definitions
- ✅ Custom Web Portal Resources
- ✅ Alliance Passport Services (Auth Engine)
- ✅ TOTP MFA Enabled
- ✅ Local Account Support
- ✅ Microsoft Identity Integration
- ✅ Twitter Identity Integration
- ✅ Facebook Identity Integration
- ✅ Google Identity Integration
- ✅ Azure AD Identity Integration
- ✅ Azure AD B2C Identity Integration
- ✅ Okta Identity Integration (Preview)
- ✅ AWS Cognito Identity Integration
- ✅ Default Identity Management
- ✅ Module Manager Dashboard
- ✅ Trusted Publisher Rules
- ✅ Module Assembly Manager
- ✅ Managed Module Support
- ✅ Unmanaged Module Support
- ✅ Authentication / User Management / Profile Management
- ✅ Authorization / Roles Management / Granular Permissions
- ✅ Blazor Support
- ✅ Cross-Platform Database Support ( MySQL, MSSQL )
- ✅ Dynamic CSS/Lazy Loading
- ✅ Dynamic Page Compositing Model / Site & Page Management
- ✅ Dynamic Routing
- ✅ Dynamic Swagger Specs
- ✅ EF Core Migrations for Database Installation / Upgrade
- ✅ Enabled for Infinity Comex (eCommerce Extension)
- ✅ Event Logging / Audit Trail
- ✅ Extensibility via Custom Modules
- ✅ Extensibility via Custom Themes
- ✅ Folder / File Management (Azure Storage, File System)
- ✅ GraphQl API with Voyager, GraphiQl y GraphQl Playground
- ✅ Headless API with Swagger Support
- ✅ HealthCheck Rules with UI Support
- ✅ i18n Enabled (Based on GeoAPI and Custom Settings)
- ✅ Improved JavaScript reference support
- ✅ In-App CLI (Studio Commander)
- ✅ Infinity Comex Support (ABS' eCommerce Engine)
- ✅ JavaScript Lazy Loading
- ✅ Modular Architecture
- ✅ Multi-Currency Support
- ✅ Multi-Portal ( Monolith & Microservice Distributed )
- ✅ Multi-Tenant ( Shared Database & Isolated Database )
- ✅ Notifications / Email Delivery
- ✅ Notifications / SMTP Delivery
- ✅ Progressive Web Application Support
- ✅ Recycle Bin
- ✅ REST API with Swagger Support
- ✅ Scheduled Flows ( Background Processing )
- ✅ Scheduled Jobs ( Background Processing )
- ✅ Seamless Upgrade Experience
- ✅ Slack integration (OAuth)
- ✅ Support For Additional Authentication Providers (OAuth)
Constant Considerations
- ✅ Code Annotations
- ✅ A11y Improvements
- ✅ i18n Improvements
- ✅ UI/UX Improvements
- ✅ 100% Code Coverage
- ✅ Security Improvements
- ✅ SOLID Code Improvements
- ✅ Performance Improvements
- ✅ Scalability Improvements
- ✅ Extensibility Improvements
- ✅ Generic Integrations Improvements
- ✅ Developer productivity enhancements
- ✅ Separation of Concerns Improvements
- ✅ Bug fixes & core Dependency Management
Alliance Business Suite API References
- Version 1.1.0
- Version 1.1.0
- Version 1.2.0
- Version 1.3.0
- Version 1.4.0
- Version 1.5.0
- Version 1.6.0
- Current: Version (1.7.0)
System requirements
The following browsers are supported:
- Google Chrome
- Microsoft Edge (supported on Windows 10)
- Apple Safari 11
- Internet Explorer 11
Recommended Server Hardware (Minimum)
- Quad-core x64 2 GHz CPU or higher (x64 compatible dual-core 1.5 GHz processor)
- 16GB Memory (8GB Memory)
- 40GB free hard disk space (10GB free hard disk) SSD Recommended
Supported Operating Systems
The following operating systems are supported with the recommendation that the latest Windows updates are applied.
- Windows Server 2012 R2 x64 Datacenter / Standard
- Windows Server 2016 x64 Datacenter w/ Containers
- Windows Server 2016 x64 Datacenter w/ Containers
Supported SQL Server Editions
The following SQL Server Editions are supported with the recommendation that the latest Windows updates are applied.
- SQL Server 2019
- SQL Server 2017
- SQL Server 2016
- Azure SQL Service
Internet Information Services (IIS)
- IIS 10, Windows Server 2016
- IIS 10.0, Windows 10 & Windows Server 2019
Optional Software Components
- SQL – SQL Word Breakers
- SQL – SQL Server Agent Service
- SQL – Server Full-Text Indexing
Getting Started with the Alliance Business Suite
Data is at the center of every modern business, unlocking new paths and ideas for operational performance and customer experience, but gathering and analyzing data is rather a complicated, time-consuming task. In an increasingly globalized world, technology is a key differentiator between those who stay ahead and those who don't.
To help businesses across the world to harness this promise, we've created a digital solution aimed to give organizations the ability to cover their main operations without constraining our customers with opinionated business development platforms.
The Alliance Business Suite lets you build outstanding and secure web and mobile apps. This is what you need to get started:
-
Get an Alliance Business Suite license:
-
Install the Alliance Business Suite
-
Start building your business
Alliance Business Suite Fundamentals
This article provides an overview of key topics for understanding how to develop Alliance Business Suite apps.
Tutorial: Get started with the Alliance Business Suite
This tutorial shows how to create and run your first Alliance Business Suite instance.
You'll learn how to:
- [✔] Install an Alliance Business Suite instance.
- [✔] (optional) Trust the development certificate.
- [✔] Run the app.
In the end, you'll have a working Alliance Business Suite instance running on your local machine.
Prerequisites
- .NET Core 6.0 SDK or later
- MySQL Server 8.0 or later
Installation
Conventional Install
git clone https://github.com/FenixAlliance/ABS.Bin
cd ABS.Bin
./FenixAlliance.ABS.Studio.exe
or
dotnet FenixAlliance.ABS.Studio.dll
Development Install
Install as a Docker Container.
docker pull FenixAlliance.ABS:latest
Install as an Application Extension
There are certain cases where customers prefer to install the Alliance Business Suite so that they can extend the standard functionalities, create modules, integrations, SPAs, or really, any kind of extensions without having to worry about all the required wiring for it to work properly.
In these cases, the best approach is to install the Alliance Business Suite as an application extension into a new or existing ASP.NET Application.
To do this:
- Add the NuGet package
dotnet add package FenixAlliance.ABS.Hub --version latest
- Register Services and Configuration
using FenixAlliance.ABS.Hub.Extensions;
using Microsoft.AspNetCore.Builder;
using Microsoft.AspNetCore.Hosting.Server.Features;
using Microsoft.Extensions.Configuration;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Hosting;
using System;
namespace FenixAlliance.ABS
{
public class Startup
{
public IHostEnvironment Environment { get; set; }
public IConfiguration Configuration { get; set; }
// Constructor
public Startup(IConfiguration Configuration, IHostEnvironment Environment)
{
this.Environment = Environment;
this.Configuration = Configuration;
}
// This method gets called by the runtime. Use this method to add services to the container.
public void ConfigureServices(IServiceCollection services)
{
services.AddAllianceBusinessSuite(Configuration, Environment);
}
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
public void Configure(IApplicationBuilder app)
{
app.UseAllianceBusinessSuite(Configuration, Environment);
}
}
}
- Trust the HTTPS development certificate:
Select Yes if you agree to trust the development certificate.
Installation wizard
The Alliance Business Suite uses the suitesettings.json
configuration file to determine whether or not the Alliance Business Suite instance is already configured to work. The Status section of the configuration file is used to instruct the system on the current configuration step.
The first step towards having an operational instance is to set up the basic options such as Database Connections Strings, seeding the database, create the primary Business Tenant, and the root account holder.
Customers can achieve this installation through a web wizard aimed to beat WordPress's 5 Minutes installation.
On this wizard, you'll be prompted with a few configuration steps:
1. Primary Database Options
2. Business Tenant Basic Information
3. Primary Portal Basic Information
4. Identity Provider Options
5. Root Account Credentials
Fill in the required information on each step and click on "Install". This will create the ABM Scheme to the Database, seed data such as countries, currencies, states, cities, timezones, the selected COA, and other important, standardized data. The creation and seeding process might take up to 5 minutes, depending on your connection and system's specifications.
Let the application finish this process, reload the page & log in with the Root Account credentials defined in previous steps.
Configuring an Alliance Business Suite Instance
Short Notation for this page
- Acting Business Tenant ("ABT")
- Current Web Portal ("CWP")
The Alliance Business Suite is designed to be as easy to use as it can be by abstracting complexity through a clean UI and multiple navigation features designed to take you where you need to perform.
Once installed, your instance will be functional, but not quite yet ready for production. For this reason, new instances are created with a Not Operational Status. This Status means that even new users can be created and pretty much every functionality will work right out of the box, several unconfigured functionalities won't be available until proper setup.
In order to get your instance to an Operational State, you should first configure for the first time the Alliance Passport Service, perform some internal configurations, and properly set up your Root Web Portal.
Configuring your instance
One of the most important files in your Alliance Business Suite instance is the suitesettings.json file. This file is located in the root of your instance's file directory and contains your website’s base configuration details, such as database-connection information.
When you first download the Alliance Business Suite, this file does not exist, as it will be created during the initial setup process.
Although you can manually provide a suitesettings.json file for your instance (bypassing like so the initial setup process), you will be required to run this initial setup process at least once to create your initial database schema and insert required records.
Once this installation process has been completed, multiple instances can retrieve their configuration files through the ABS Management API from the root instance, and thus sharing the data layer, allowing customers to scale both the data and application layer independently, depending on their specific requirements.
Each Alliance Business Suite instance contains its own administrator portal. Instances are bounded each a Business Tenant's Primary Web Portal's configuration.
The first towards configuring your Root Web Portal is to finish creating information for your Business Tenant. The amount of configuration required will depend on the number of Modules included in your instance.
Note: Although currently possible, it is not recommended to edit the suitesettings.json
file directly unless required.
Administration Flow Optimization
Due to the massive amount of different types of data that the Alliance Business Suite is built to manage, and the tremendous amount of control given to our customers, it can be easy to get lost among all the different options and configurations available. We understand this and We want your workflow to be as fluid as possible, so we've been tackling this issue through several shortcuts and UI optimizations that will help you manage your business tenant's with an incredibly high APM ("Actions per Minute") rate.
These optimizations include:
- Drastically reducing the number of page loads required to manage everything inside the Alliance Business Suite: Our goal is to bring this number to 1, meaning that once you're into the Alliance Business Studio,
- Drastically reducing the number of clicks required to get from point A to point B inside the application: Our goal is to provide multiple ways to get you where you need to be across your business tenants.
- Optimizing performance and improving both UX/UI to deliver clear, readable interfaces to manage data across Business Tenants.
- Including accessibility features to improve the way people with limitations interact with the application.
- Delivering additional interfaces other than the Studio to help Customers to automate and extend
Understanding the GenericOption Table and the Options API.
The GenericOption Table
To maximize your ability to extend the Alliance Business Suite, we've created the a generic data persistance mechanism, which is a table containing a few columns to store optional and configuration data for external applications without the need to modify nor extend the Alliance Business Model Schema, not to bring another data persistence mechanism.
The options table stores data as encrypted JSON data. Data is written to the options table using the Options API, both of which consist of a set of functions used to add, update and delete data from this table.
The Options API
To make it easier for developers to create custom configurations, we've created a set of methods specified into the IOptionsService
interface. This interface comes configured with its default implementation right out of the box, but custom implementations could override this default implementation.
As the GenericOption table stores data which is related to the setup and administration of the site as a whole, access to it is restricted. The Alliance Business Studio gives users the ability to modify the value of each configuration given the proper permissions to do so.
To be able to amend settings and options, users will need to have the manage_options Business Permission. The only default user role with this capability is the root role.
This means that if you need to add options that other user roles have access to, you'll have to assign the manage_options capability to them. This carries risks, so only do it if you're sure!
Structure of the GenericOption Table
The options table has a similar structure to the three metadata tables. It has the following fields:
- ID: The Global Unique Identifier for every option.
- Name: The Option Name for Friendly Access
- Value: The option value, usually stored in JSON format.
- Autoload: (boolean) whether or not this option would be loaded on memory cache.
- Timestamp: The time for the last option update.
- Transient: whether or not this option is a temporal option.
- WebPortalID: The ID for the Web Portal who owns this option.
- Discriminator: The Option Type.
Option Types.
GenericOptins have different types (also called scopes). As of v1.3.0, the following types are available:
- AccountHolderOption: An option that's bound to an account holder and, optionally, to a Web Portal.
- BusinessOption: An option that's bound to a Business Tenant and, optionally, to a Web Portal.
- BusinessApplicationOption: An option that's bound to a Business Application and, optionally, to a Web Portal.
Aditional considerations
One of the important things to understand about the GenericOption table is the autoload field. This contains a boolean value (yes or a no). This essentially controls whether or not it is loaded on cached memory by the OptionsService.LoadOptions()
function. Autoloaded data is data that is loaded on every page of your Alliance Business Suite instance. Just like we showed you how to disable certain scripts from loading sitewide, the same idea applies here. The autoload attribute is set to “yes” by default for developers, but not every option should be loaded on every page.
Hosting the Alliance Business Suite
You can deploy the Alliance Business Suite on-premises (self-hosted). Unlike cloud deployments, when you choose an on-premises deployment, different system requirements like hardware type, sizing, and functionality needs to be considered. This chapter contains guides on self-hosted/on-premise deployments.
Getting Started
Hosting the Alliance Business Suite on IIS
Internet Information Services (IIS) is a flexible, secure and manageable Web Server for hosting web apps, including ASP.NET Core.
Supported platforms
The following operating systems are supported:
- Windows 10 or later
- Windows Server 2012 R2 or later
The Alliance Business Suite is a 64-bit (x64) for the following reasons:
- Requires the larger virtual memory address space available to a 64-bit app.
- Requires the larger IIS stack size.
- Has 64-bit native dependencies.
Install the ASP.NET Core Module/Hosting Bundle
Download the installer using the following link:
Current .NET Core Hosting Bundle installer (direct download)
For more detailed instructions on how to install the ASP.NET Core Module, or installing different versions, see Install the .NET Core Hosting Bundle.
Publish an Alliance Business Suite instance to IIS
Create the IIS site
-
On the IIS server, create a folder to contain the Alliance Business Suite folders and files. In a further step, the folder's path is provided to IIS as the physical path to the app. For more information on an app's deployment folder and file layout, see ASP.NET Core directory structure.
-
In IIS Manager, open the server's node in the Connections panel. Right-click the Sites folder. Select Add Website from the contextual menu.
-
Provide a Site name and set the Physical path to the app's deployment folder that you created. Provide the Binding configuration and create the website by selecting OK.
-
Confirm the process model identity has the proper permissions: If the default identity of the app pool (Process Model > Identity) is changed from ApplicationPoolIdentity to another identity, verify that the new identity has the required permissions to access the app's folder, database, and other required resources. For example, the app pool requires read and write access to folders where the app reads and writes files.
Warning
Top-level wildcard bindings (http://*:80/ and http://+:80) should not be used. Top-level wildcard bindings can open up your app to security vulnerabilities. This applies to both strong and weak wildcards. Use explicit hostnames rather than wildcards. Subdomain wildcard binding (for example, *.mysub.com) doesn't have this security risk if you control the entire parent domain (as opposed to *.com, which is vulnerable).
Clone the Alliance Business Suite Distributable
The best way to manage the Alliance Business Suite Update Flow is to clone the Alliance Business Suite to the publish directory using Git.
- Navigate to the Publish Directory, make sure is empty, and open a CLI into it.
- Run the following command:
git clone https://github.com/fenixalliance/abs.bin .
- If you're unable to deploy directly to the IIS site folder on the IIS server, pick your desired ring from the Releases Repo and clone on removable media and physically move them to the IIS site folder on the server, which is the site's Physical path in IIS Manager. Move the contents of the cloned repository to the IIS site folder on the server, which is the site's Physical path in IIS Manager.
- If you're unable to use git, you'll face additional considerations regarding the Update Process.
- Restart the IIS Site.
Browse the website
The app is accessible in a browser after it receives the first request. Make a request to the app at the endpoint binding that you established in IIS Manager for the site.
Logging across the Alliance Business Suite
The Alliance Business Suite contains a powerful logging engine based on Serilog, a popular .NET library that provides diagnostic logging that's built with powerful structured event data in mind.
using Serilog;
var position = new { Latitude = 25, Longitude = 134 };
var elapsedMs = 34;
Log.Information("Processed {@Position} in {Elapsed:000} ms.", position, elapsedMs);
This example records two properties, Position and Elapsed along with the log event. The properties captured in the example, in JSON format, would appear like:
{"Position": {"Latitude": 25, "Longitude": 134}, "Elapsed": 34}
The @ operator in front of Position tells Serilog to serialize the object passed in, rather than convert it using ToString().
The :000 segment following Elapsed is a standard .NET format string that affects how the property is rendered. The console sink included with Serilog will display the above message as:
09:14:22 [Information] Processed { Latitude: 25, Longitude: 134 } in 034 ms.
Through the Alliance Business Studio, customers are able to manage these logs without the need to access the server directly.
To manage logs for your Alliance Business Suite instance, navigate to the /Studio/Network/Logs
route on any configured Web Portal.
Understanding Request Routing through the Alliance Business Suite
The Alliance Business Suite contains a powerful routing engine based on .NET's Routing System.
At a high level, routing is responsible for matching incoming HTTP requests and dispatching those requests to the Alliance Business Suite's executable endpoints. Endpoints are the app's units of executable request-handling code. Endpoints are defined in the app and configured when the app starts. The endpoint matching process extracts values from the request's URL and provides those values for request processing. Using endpoint information from the app, routing is also able to generate URLs that map to endpoints.
The Alliance Business Suite's routing configurations abstract the complexities out of the routing process through several techniques depending on the execution context. This means that routing is as simple as providing a relative URL ("Slug") when creating a page.
In cases where customers might want to create a custom Module, they can expose custom endpoints while still taking advantage of the Routing Engine, meaning they can create and manage routing rules through the Alliance Business Studio and apply them to their custom endpoints.
Rate limiting
The Alliance Business Platform contains a rate-limiting solution designed to control the rate of requests that clients can make to a Web API or MVC app based on IP address or client ID. Through the Alliance Business Studio, you can configure the rate-limiting middleware and set multiple limits for different scenarios like allowing an IP or Client to make a maximum number of calls in a time interval. You can define these limits to address all requests made to an API or you can scope the limits to each executable API URL or HTTP verb and path.
Working with static files.
This topic describes the overall functionality for the Alliance Business Platform | File System Engine, how to upload static files into an Alliance Business Suite instance, and how to retrieve the URL and file name that can be used to request that file.
About Uploading Files on Studio
The Alliance Business Platform contains a powerful file system engine called ABP-FS. Through ABP-FS, users can upload files and relate them to almost any ABM Record. By exposing several API endpoints on both code and REST APIs, users can upload files of any kind. Default restrictions are provided for security purposes, and files can also be uploaded through FTP or through the Alliance Business Studio (using the GUI file manager).
File Upload Scopes
By leveraging the ABP-FS APIs, customers and developers can upload files scoped to an Alliance Business Model Record; this allows customers to access, manage, and share files related to, for example, an Account, a Contact, or a Portal, in one place.
Public Files.
Scoped Public Files
The ABP-FS allows customers to upload public files within the scope of a Web Portal. These files are exposed through the /Public/{PortalID}
endpoint available to every portal.
Unscoped Public Files
When developing single or multiple portals, customers might want to share common files between them. To do so, they can now upload Unscoped Public Files that will be available through the /Public
endpoint.
Unscoped files are marked as read-only files by default and can only be uploaded by an Account Holder with global_admin
Business Permission.
Public Files URL
Regardless of how you upload a file, you can retrieve the file URL by using the Alliance Business Studio File Manager or by recomposing the URL from the File Path by prepending the /Public/
endpoint to it, so that it is relative to the /AppData/Public
folder where both Scoped and Unscoped Public Files are uploaded.
Accessing data from the Alliance Business Model engine.
If you've ever had to bring data from multiple systems and applications together, you know what an expensive and time-consuming task that can be. Without being able to share and understand the same data easily, each application or data integration project requires a custom implementation.
The Alliance Business Model simplifies this process by providing a common data model that includes entities that represent commonly used business concepts and activities, such as Contact, Invoice, and Account, to simplify the creation, aggregation, and analysis of data.
Why use the Alliance Business Model?
Commonly, businesses have more than one application to cover specific business operations such as eCommerce, Accounting, Sales, Marketing, CRM, and more. These are a lot of applications and they consume time and money, but that's not it! they all have different representations for the Contact Entity. This can be frustrating when trying to integrate these applications together to produce better and automated outcomes. To solve this issue, you can build those apps on top of a standardized data schema, allowing you to share the same entities across applications. Of course, your application might have different data requirements between them, so you can extend the predefined schemas and even create new schemas!
One cool thing about this is that when it comes the time to create a new business application, your data schemas will be ready to provide the required data infrastructure for your application and share this data with every other application.
Alliance Business Model simplifies data management and app development by unifying data into a known form and applying structural and semantic consistency across multiple apps and deployments. To summarize the benefits:
- A unified shape, where data integrations can combine existing enterprise data with other sources and use that data holistically to develop apps or derive insights.
- Structural and semantic consistency across applications and deployments.
- Simplified integration and disambiguation of data that's collected from processes, digital interactions, product telemetry, people interactions, and so on.
- The ability to extend the Alliance Business Model schema standard entities to tailor the model to your organization. This is enabled thanks to both the ABM Mongo Interop Service and the ABS Virtual Entities functionalities.
Alliance Business Model in action
The Alliance Business Model is influenced by data schemas that are present in both UBL Schema and Common Data Model, covering a range of business areas. If you are a customer or a partner of Fenix Alliance Group, you are already using the Alliance Business Model.
Businesses, institutions, Partners, and independent software vendors (ISVs) use the Alliance Business Model to extend and interoperate with any given Alliance Business Suite instance.
Organizations from industries such as manufacturing, government, and education are working closely with Fenix Alliance Group to extend the Alliance Business Model to their specific business scenarios, and the dynamic ABM Engine allows seamless data integration even when schemas are not exactly the same. This allows customers from an unlimited range of industries to leverage the benefit of the Alliance Business Model's standard entities and extend to their specific verticals so that industry solutions can interoperate more easily.
// Get all the contacts from the configured ABM Provider.
var contacts = await DataContext.Contact.ToListAsync();
foreach(var contact in contacts){
Console.WriteLine(contact.ID);
}
Introduction to Razor Templating Engine
Portal Pages can make coding page-focused scenarios easier and more productive than using controllers and views.
This document provides an introduction to the Alliance Business Suite - Razor Templating Engine
#Rendering HTML The default Razor language is HTML. Rendering HTML from Razor markup is no different than rendering HTML from an HTML file. HTML markup in .cshtml Razor files is rendered by the server unchanged.
#Razor syntax Razor supports C# and uses the @ symbol to transition from HTML to C#. Razor evaluates C# expressions and renders them in the HTML output.
When an @ symbol is followed by a Razor reserved keyword, it transitions into Razor-specific markup. Otherwise, it transitions into plain C#.
To escape an @ symbol in Razor markup, use a second @ symbol:
<p>@@Username</p>
The code is rendered in HTML with a single @ symbol:
<p>@Username</p>
HTML attributes and content containing email addresses don't treat the @ symbol as a transition character. The email addresses in the following example are untouched by Razor parsing:
<a href="mailto:Support@contoso.com">Support@contoso.com</a>
Implicit Razor expressions
Implicit Razor expressions start with @ followed by C# code:
<p>@DateTime.Now</p>
<p>@DateTime.IsLeapYear(2016)</p>
With the exception of the C# await keyword, implicit expressions must not contain spaces. If the C# statement has a clear ending, spaces can be intermingled:
<p>@await DoSomething("hello", "world")</p>
Getting Started with Alliance Business Suite Web Portals
The Alliance Business Suite includes a powerful multi-portal CMS to help businesses to offer external-facing websites that allow users outside their organizations to sign in with a wide variety of identities, create and view data in and from the Alliance Business Model, or even browse content anonymously. The full capabilities of Alliance Business Suite Portals are available as of Version 1.2.
You have the ability to create a Portals Web Portals Network ("WPN") for each Business Tenant by using the multi-portal feature. Business tenants can create as many Web Portals under the same instance as they need.
Web Portals are scoped to a Business Tenant to allow customers to deliver experiences that directly transact data with the Alliance Business Model and additional Data Sources. This means that users can perform a controlled (yet extensible) number of actions (like adding products to their cart, update their profile, create addresses, generate orders, access quotes, invoices and so much more)
How do Portals Work?
Web Portals are content sets that belong to a Business Tenant. Portals make use of the powerful Alliance Business Suite Razor Engine to group Web Content under a single domain.
Configuring Domains
Compared with a typical single-portal ABS instance, a WPN installation has additional considerations.
Every fresh Alliance Business Suite instance comes with one default Portal owned by the Business Tenant that was created through the installation process. This Root Portal must exist and is defined by your instance's settings file.
Alliance Business Suite Portals can have additional related domains/subdomains.
Domains should resolve to your instance's public IP Address. Also, domains should be related to a portal for the multi-tenant data router to work properly.
Themes and Modules
When you enable a WPN Instance: each Web Portal of a network can activate both modules and themes individually, but installation is done at an instance scope, which means they are available to every Web Portal present on your instance.
You must have access to your domain's DNS settings.
Configuring a Multi-Portal Network
1. Preparing your instance
Unless this is a fresh install and you have no data to lose, please backup your database and file system.
2. Select a Business Tenant
When you create a new portal, you do so under the scope of a Business Tenant. This means that you should have permissions from the Business Tenant to access the Studio and "create_portals" at the very least.
3. Create Web Portal
To create a Web Portal, login as an authorized user and select the Business Tenant that will own the Web Portal.
Acting as the selected Business Tenant, click on the cogs icon on the top-right hand side of the Studio Header.
Click on Portals and provide a Title and a root domain (the Root Domain should be a Subdomain of the Root Portal's Root Domain. This means that every portal's Root Domain is relative to the domain that you used to install your instance).
E.g: If you installed your instance under the https://example.com domain, each subsequent Web Portal will have a Root Domain that's scoped to the Root Portal's domain, like so: https://NewPortalRootDomain.example.com
4. Create a Primary Domain (optional)
In order to set up another domain that's not related to the Root PortalDomain, you should create a security rule to allow traffic through certain domains and then map the rule to your new Web Portal.
5. Create Additional Domains (optional)
You can have more than one domain mapping to the same Web Portal. You can choose whether or not this mapping should be performed through an HTTP redirection. To create and map an additional domain to a Web Portal, create the new domain under the Admin section for your Business Tenant, under Admin > Security > Domains. Then, navigate to the portal that this Domain should map to and select it from the domains tab.
Working with Web Pages
Web pages are meant to represent content located at a particular URL, scoped to a Web Portal (and therefore to a Business Tenant), and is based on one of the core tables of the Alliance Business Model Schema.
Web Pages are related through parent and child relationships to other web pages, this structure forms the hierarchy of a website, and therefore, its site map is automatically generated.
Web pages also form the basis for including other, specialized table types in the portal site map – web files, shortcuts, forums, advanced forms, and blogs are all situated in the portal site map through – and thus derive their URLs from – a relationship to a parent web page.
Manage web pages
Web pages can be created, edited, and deleted from the Alliance Business Platform REST API. However, the Media Portals Module provides advanced customization that can be performed from the Alliance Business Studio.
-
Open the Alliance Business Studio.
-
Go to Modules > Media Portals > Web Pages.
- To edit an existing web page using the standard editor, select the "Edit" option below the web page name.
- To edit an existing web page using the Visual WYSIWYG editor, select the "Live Edit" option below the web page name.
- To create a new Web Page, click on the Create Button.
-
Enter appropriate values in, at least, the required fields.
-
Select Save & Close.
Content Engines
The Alliance Business Suite contains a powerful content engine to provide the level of customizability required to give the highest level of control over every bit that's to be presented to a user on a Web Page. These engines are meant to work with Web Content records and they have several capability sets.
Razor Engine:
The Razor Engine is a derivate from .NET's Server Side Markup Language. Web Content marked as .razor will be compiled and rendered using a Service Abstraction which means that its default can be replaced by a custom implementation.
Razor is a markup syntax that lets you embed server-based code (Visual Basic and C#) into web pages at a very high level.
Server-based code can use every available service inside any given Alliance Business Suite instance to dynamically generate web content on the fly, while a web page is written to the browser.
When a web page is called (either by slug or id), the server executes the server-based code inside the page before it returns the page to the browser. The code can perform complex tasks by running on the server, like accessing the Alliance Business Model or leveraging our extensive set of APIs.
Razor is based on ASP.NET and designed for creating web applications. The ABS Razor Engine has the power of traditional Razor, but it is easier to use.
Blazor Engine
The Alliance Business Suite lets you build interactive web UIs using C# instead of JavaScript. By using Blazor under the hood, apps are composed of reusable web UI components implemented using C#, HTML, and CSS. Both client and server code is written in C#, allowing you to share code and libraries already present.
Liquid Engine (Experimental)
The Alliance Business Suite supports Liquid template language, which is a secure template language that is also very accessible for non-programmer audiences.
HTML Engine
In cases where customers decide to use plain HTML5, the Alliance Business Suite contains the ability to bypass all Content Engines and render HTML fragments whenever they are called. This is also the most efficient type of Web Content.
Markdown Engine
The last Content Engine, and therefore the least privileged, is the Markdown Engine, which is a lightweight markup language for creating formatted plain text using an embedded markdown-text editor.
Razor Pages Introduction
Pages are very important components for the Alliance Business Suite. They allow customers to implement unique, visually outstanding web pages by using a templating engine that's based on .NET's Razor Syntax.
Pages in the Alliance Business Suite can be added through the Admin Portal of your ABS instance and live edited through the ABS Web Builder.
Pages are WebContent Components, which makes them extremely powerful. They are stored in the Alliance Business Model Database provider and C# is server-side evaluated to then render the output as HTML, CSS, and JavaScript.
Although pages can inject services and even interact with the ABM Database Provider through the DataContext instance present at every page, pages can optionally contain a caller method. This method's responsibility is to produce the model that's going to be used to fill the page's Model property, sort of like a controller method passing a Model to a view.
Creating a Web Page
To create a Web Page in the Alliance Business Suite you must have Studio Access (access_studio) permission and the create WebContent entities permission (create_webcontent).
- Head to your ABS Instance's Admin Portal at https://{yourdomain}/admin
- Select the Business Tenant for which you want to create a Web Page.
- Click on the Add button of your Command Bar and Select Web Page
- Give the entry a Title, a Slug, and (optionally) select a template and parent page to use on the page.
- Write some code using the Razor Syntax and the Code Editor.
- Validate your code for errors.
- Save Changes.
Once you've saved changes for your Web Page, the system will automatically redirect you to the Edition page. Here you will be able to edit everything about your page, and new options will be available, such as categorization and tags.
Page Routing
Pages must define a "Slug". This relative route gets combined with the parent's page slug to produce the Absolute Slug of the page and defines the route over which your page will be located and invoked. It can be changed at any time.
Currently, Pages other than the Home Page are available at the /Pages/{AbsoluteSlug} route.
Home Page
Each portal on the Alliance Business Suite must be provided with a Home Page. this can be any page you've created and it will allow each portal to find the page that will be rendered at the root of the portal. Customers can mark a page as the Home Page by ticking the respective option on a portal-related or by setting the page on each Portal's Options Manager.
If you set a portal-related page as the home page by ticking the "Is Home Page" option, that will replace any other Home Page related to that specific portal, becoming, like so, the Active Home Page.
The above is a legacy method for Home page discovery. To improve consistency across portals, we've implemented a new method to select the Home Page on the Portal's Options Manager. To use the new method, head to your Instance's administration portal and over General Settings, select the page you would like to render at the root of each portal.
Client-Side UI Frameworks
The Alliance Business Suite is configured to allow customers to use, right out of the box, several UI Frameworks such as:
- Bootstrap
- Foundation
- Bulma
- Fast
- Fabric (deprecated)
- Fluent UI
- Tailwind CSS
- Materialize CSS
- Semantic UI
These frameworks can be enabled or disabled on a template basis to allow customers to create and combine unique experiences with the tools they already use and love.
ABS Razor Syntax
Razor is a markup syntax for embedding server-based code into web pages. The Razor syntax consists of Razor markup, C#, and HTML. Files containing Razor generally have a .cshtml file extension. Razor is also found in Razor components files (.razor).
Razor syntax
Razor supports C# and uses the @ symbol to transition from HTML to C#. Razor evaluates C# expressions and renders them in the HTML output.
When an @ symbol is followed by a Razor reserved keyword, it transitions into Razor-specific markup. Otherwise, it transitions into plain C#.
To escape an @ symbol in Razor markup, use a second @ symbol:
<p>@@Username</p>
The code is rendered in HTML with a single @ symbol:
<p>@Username</p>
HTML attributes and content containing email addresses don't treat the @ symbol as a transition character. The email addresses in the following example are untouched by Razor parsing:
<a href="mailto:Support@contoso.com">Support@contoso.com</a>
Implicit Razor expressions
Implicit Razor expressions start with @ followed by C# code:
<p>@DateTime.Now</p>
<p>@DateTime.IsLeapYear(2016)</p>
With the exception of the C# await keyword, implicit expressions must not contain spaces. If the C# statement has a clear ending, spaces can be intermingled:
<p>@await DoSomething("hello", "world")</p>
Implicit expressions cannot contain C# generics, as the characters inside the brackets (<>) are interpreted as an HTML tag. The following code is not valid:
<p>@GenericMethod<int>()</p>
The preceding code generates a compiler error similar to one of the following:
- The "int" element wasn't closed. All elements must be either self-closing or have a matching end-tag.
- Cannot convert method group 'GenericMethod' to non-delegate type 'object'. Did you intend to invoke the method?`
Generic method calls must be wrapped in an explicit Razor expression or a Razor code block.
Templated Razor delegates
Razor templates allow you to define a UI snippet with the following format:
Explicit Razor expressions
Explicit Razor expressions consist of an @ symbol with balanced parenthesis. To render last week's time, the following Razor markup is used:
<p>Last week this time: @(DateTime.Now - TimeSpan.FromDays(7))</p>
Any content within the @() parenthesis is evaluated and rendered to the output.
Implicit expressions, described in the previous section, generally can't contain spaces. In the following code, one week isn't subtracted from the current time:
<p>Last week: @DateTime.Now - TimeSpan.FromDays(7)</p>
The code renders the following HTML:
<p>Last week: 7/7/2016 4:39:52 PM - TimeSpan.FromDays(7)</p>
Explicit expressions can be used to concatenate text with an expression result:
@{
var joe = new Person("Joe", 33);
}
<p>Age@(joe.Age)</p>
Without the explicit expression, <p>Age@joe.Age</p>
is treated as an email address, and <p>Age@joe.Age</p>
is rendered. When written as an explicit expression,
Age33
is rendered.Explicit expressions can be used to render output from generic methods in .cshtml files. The following markup shows how to correct the error shown earlier caused by the brackets of a C# generic. The code is written as an explicit expression:
<p>@(GenericMethod<int>())</p>
Expression encoding
C# expressions that evaluate to a string are HTML encoded. C# expressions that evaluate to IHtmlContent are rendered directly through IHtmlContent.WriteTo. C# expressions that don't evaluate to IHtmlContent are converted to a string by ToString and encoded before they're rendered.
@("<span>Hello World</span>")
The preceding code renders the following HTML:
<span>Hello World</span>
The HTML is shown in the browser as plain text: Hello World
HtmlHelper.Raw
output isn't encoded but rendered as HTML markup.
Warning: Using HtmlHelper.Raw on unsanitized user input is a security risk. User input might contain malicious JavaScript or other exploits. Sanitizing user input is difficult. Avoid using HtmlHelper.Raw with user input.
@Html.Raw("<span>Hello World</span>")
The code renders the following HTML:
<span>Hello World</span>
Razor code blocks
Razor code blocks start with @ and are enclosed by {}. Unlike expressions, C# code inside code blocks isn't rendered. Code blocks and expressions in a view share the same scope and are defined in order:
@{
var quote = "The future depends on what you do today. - Mahatma Gandhi";
}
<p>@quote</p>
@{
quote = "Hate cannot drive out hate, only love can do that. - Martin Luther King, Jr.";
}
<p>@quote</p>
The code renders the following HTML:
<p>The future depends on what you do today. - Mahatma Gandhi</p>
<p>Hate cannot drive out hate, only love can do that. - Martin Luther King, Jr.</p>
In code blocks, declare local functions with markup to serve as templating methods:
@{
void RenderName(string name)
{
<p>Name: <strong>@name</strong></p>
}
RenderName("Mahatma Gandhi");
RenderName("Martin Luther King, Jr.");
}
The code renders the following HTML:
<p>Name: <strong>Mahatma Gandhi</strong></p>
<p>Name: <strong>Martin Luther King, Jr.</strong></p>
Implicit transitions
The default language in a code block is C#, but the Razor Page can transition back to HTML:
@{
var inCSharp = true;
<p>Now in HTML, was in C# @inCSharp</p>
}
Explicit delimited transition
To define a subsection of a code block that should render HTML, surround the characters for rendering with the Razor
@for (var i = 0; i < people.Length; i++)
{
var person = people[i];
<text>Name: @person.Name</text>
}
Use this approach to render HTML that isn't surrounded by an HTML tag. Without an HTML or Razor tag, a Razor runtime error occurs.
The <text>
tag is useful to control whitespace when rendering content:
- Only the content between the
tag is rendered. - No whitespace before or after the
tag appears in the HTML output.
Explicit line transition
To render the rest of an entire line as HTML inside a code block, use @: syntax:
@for (var i = 0; i < people.Length; i++)
{
var person = people[i];
@:Name: @person.Name
}
Without the @:
in the code, a Razor runtime error is generated.
Extra @
characters in a Razor file can cause compiler errors at statements later in the block. These compiler errors can be difficult to understand because the actual error occurs before the reported error. This error is common after combining multiple implicit/explicit expressions into a single code block.
Control structures
Control structures are an extension of code blocks. All aspects of code blocks (transitioning to markup, inline C#) also apply to the following structures:
Conditionals @if, else if, else, and @switch
@if
controls when code runs:
@if (value % 2 == 0)
{
<p>The value was even.</p>
}
else
and else if
don't require the @ symbol:
@if (value % 2 == 0)
{
<p>The value was even.</p>
}
else if (value >= 1337)
{
<p>The value is large.</p>
}
else
{
<p>The value is odd and small.</p>
}
The following markup shows how to use a switch statement:
@switch (value)
{
case 1:
<p>The value is 1!</p>
break;
case 1337:
<p>Your number is 1337!</p>
break;
default:
<p>Your number wasn't 1 or 1337.</p>
break;
}
Looping @for, @foreach, @while, and @do while
Templated HTML can be rendered with looping control statements. To render a list of people:
@{
var people = new AccountHolder[]
{
new AccountHolder(){...},
new AccountHolder(){...},
...
};
}
The following looping statements are supported:
@for
@for (var i = 0; i < people.Length; i++)
{
var person = people[i];
<p>Name: @person.Name</p>
<p>Age: @person.Age</p>
}
@foreach
@foreach (var person in people)
{
<p>Name: @person.Name</p>
<p>Age: @person.Age</p>
}
@while
@{ var i = 0; }
@while (i < people.Length)
{
var person = people[i];
<p>Name: @person.Name</p>
<p>Age: @person.Age</p>
i++;
}
@do while
@{ var i = 0; }
@do
{
var person = people[i];
<p>Name: @person.Name</p>
<p>Age: @person.Age</p>
i++;
} while (i < people.Length);
Compound @using
In C#, a using statement is used to ensure an object is disposed. In Razor, the same mechanism is used to create HTML Helpers that contain additional content. In the following code, HTML Helpers render a