Hey Habr!
In this article, we will begin a story about how it works inside and what technologies are used in its development.

Why do we think it's interesting? Firstly, because the 1C:Enterprise 8 platform is a large (more than 10 million lines of code) application written in C++ (client, server, etc.), JavaScript (web client), and, more recently, And . Large projects are interesting, if only because of their scale, because issues that are invisible in a small code base, in such projects, rise to their full height. Secondly, 1C:Enterprise is a replicated, “boxed” product, and there are very few articles about such developments on Habré. And it's always interesting to find out how they live in other teams and firms.
So let's get started. In this article, we will give an overview of some of the technologies that are used in the platform, outline the landscape, without diving deep into the implementation. Indeed, for many mechanisms, a detailed story will draw on a separate article, and for some - on a whole book!
To begin with, it is worth deciding on the basic things - what is the 1C:Enterprise platform and what components it consists of. The answer to this question is not so simple, because the term "Platform" (for brevity, we will call it that way) is understood as a tool for developing business applications, and an execution environment, and administration tools. Conditionally, the following components can be distinguished:
- server cluster
- "thin" client capable of connecting to the server via http and its own binary protocol
- client for working in a two-tier architecture with a database located on a hard disk or network folder
- web client
- application server administration tools
- development environment (known as Configurator)
- runtime environment for iOS, Android и Windows Phone (1C mobile platform)
All of these parts, with the exception of the web client, are written in C++. In addition, there is the recently announced , written in Java.
Native apps
C++03 is used for developing native applications. Windows Microsoft Visual C++ 12 (profile compatible with) is used as a compiler Windows XP), and under Linux и Android — gcc 4.8, for iOS — clang 5.0. The standard library used is the same for all operating systems and compilers: STLPort. This solution reduces the likelihood of implementation-specific errors. We are currently planning to migrate to the STL implementation supplied with CLang, as STLPort has ceased development and is incompatible with C++11 support enabled in gcc.
The code base of the server is 99% common, the client - 95% percent. Moreover, even the mobile platform uses the same C++ code as the "large" one, although the percentage of unification is somewhat lower there.
Like most C++ users, we do not claim to use 100% of the language and its libraries. So, we practically do not use Boost, and from the possibilities of the language - dynamic type casting. In doing so, we actively use:
- STL (specifically strings, containers and algorithms)
- multiple inheritance, incl. multiple implementation inheritance
- Patterns
- exceptions
- smart pointers (native implementation)
Through the use of multiple inheritance of interfaces (completely abstract classes), the component model becomes possible, which will be discussed below.
Components
To ensure modularity, all functionality is divided into components, which are dynamic libraries (*.dll under Windows, *.so — under Linux). There are more than one hundred and fifty components in total; here are descriptions of some of them:
backend
Contains the "engine" of the platform metadata
accnt
Objects that application developers use to build accounting (charts of accounts and accounting registers)
bsl
Embedded Language Execution Engine
nuke
Own implementation of the memory allocator
dbeng8
File base engine. A simple ISAM-based file server database engine that also includes a simple SQL processor
wbase
Contains base classes and functions for implementing the user interface Windows — window classes, access to GDI, etc.
Splitting into many components is useful in several ways:
- Separation promotes better design, in particular better code isolation
- From a set of components, you can flexibly assemble different delivery options:
- For example, a thin client installation will contain wbase but no backend
- and on the wbase server, on the contrary, it will not
- both will of course contain nuke and bsl
All the components required for this launch option are loaded when the program starts. This, in particular, is necessary for registering SCOM classes, which will be discussed below.
SCOM
For decomposition at a lower level, the SCOM system is used - a library similar in ideology to ATL. For those who have not worked with ATL, briefly list the main features and features.
For a custom-styled SCOM class:
- Provides factory methods that allow you to create a class from another component knowing only its name (without revealing the implementation)
- Provides a reference-counted smart pointer infrastructure. The lifetime of an SCOM class does not need to be monitored manually
- Allows you to find out if an object implements a specific interface and automatically cast the pointer to the object to the pointer to the interface
- Create a service object that is always available via the get_service method, etc.
For example, you can define a class for reading JSON (for example, JSONStreamReader) in the json.dll component.
Classes, instances can be created from other components, you need to register in the SCOM machine:
SCOM_CLASS_ENTRY(JSONStreamReader)
This macro will describe a special static registrar class whose constructor will be called when the component is loaded into memory.
After that, you can create an instance of it in another component:
IJSONStreamReaderPtr jsonReader = create_instance<IJSONStreamReader>(SCOM_CLSIDOF(JSONStreamReader));
To support services, SCOM offers an additional, rather complex infrastructure. Central to it is the concept of an SCOM process, which serves as a container for running services (that is, acts as a Service Locator), and also contains a binding to localizable resources. An SCOM process is bound to an OS thread. Thanks to this, inside the application, you can receive services like this:
SCOM_Process* process = core::current_process();
if (process)
return get_service<IMyService>(process);
Moreover, by switching logical (SCOM) processes attached to a thread, you can get applications that are practically independent from the point of view of the information space and run within the same thread. This is how our thin client works with the file base - inside one OS process there are two SCOM processes, one is connected to the client, and the second to the server. This approach allows you to unify writing code that will work both on a local file base and in a “real” client-server version. The price for such uniformity is overhead, but practice shows that they are worth it.
Based on the SCOM component model, both the business logic and the interface part of 1C: Enterprise are implemented.
User interface
Speaking of interfaces, we don't use standard controls. Windows, our controls are implemented directly on Windows API. For Linux-version has a layer that works through the wxWidgets library.
The library of controls does not depend on other parts of 1C:Enterprise and is used by us in several other small internal utilities.
Over the years of development of 1C:Enterprise, the appearance of controls has changed, but a serious change in principles occurred only once, in 2009, with the release of version 8.2 and the advent of "managed forms". In addition to changing the appearance, the principle of form layout has fundamentally changed - there has been a rejection of pixel-by-pixel positioning of elements in favor of the flow-layout of elements. In addition, in the new model, controls do not work directly with domain objects, but with special DTOs ().
These changes made it possible to create a 1C:Enterprise web client that replicates the C++ logic of JavaScript controls. We strive to maintain functional equivalence between the thin and web clients. In cases where this is impossible, for example due to limitations of the JavaScript API (for example, file handling capabilities are very limited), we often implement the required functionality using browser extensions written in C++. We currently support Internet Explorer and Microsoft Edge (Windows), Google Chrome(Windows), firefox (Windows и Linux) and Safari (MacOS).
In addition, the technology of managed forms is used to create the interface of mobile applications on the 1C platform. On mobile devices, the drawing of controls is implemented using technologies native to the operating system, but the same code is used for the form layout logic and interface response as in the "large" 1C:Enterprise platform.

1C interface on OS Linux

1C interface on a mobile device
1C interface on other platforms 
1C interface on OS Windows

Interface 1C - web client
Open source
Although we do not use standard C++ developer libraries, Windows (MFC, WinAPI controls), we don't write all the components ourselves. The library has already been mentioned. and we also use:
- to work with HTTP and FTP.
- for working with cryptography and establishing TLS connections
- for XML parsing
- to work with mail protocols (POP3, SMTP, IMAP)
- to parse email messages
- for storing user logs
- for internationalization
The list can still be continued.
In addition, we use a heavily modified version и when developing unit tests.
The libraries required adaptation to be compatible with the SCOM component organization model.
The prevalence of 1C makes the platform an excellent strength test for the libraries used in it. A variety of users and scripts quickly find errors in even the most rarely used parts of the code. We fix them at home and try to give them back to the authors of the libraries. The interaction experience is very different.
Developers и quickly respond to a pull-request, but the patch, for example, in we never got to give it back.
Conclusion
In the article, we touched on several main aspects of the development of the 1C: Enterprise platform. In the limited volume of the article, we touched on only some interesting, in our opinion, aspects.
A general description of the various mechanisms of the platform can be viewed .
What topics would be of interest to you in future articles?
How is the 1C mobile platform implemented?
Description of the internal device of the web client?
Or maybe you are interested in the process of feature selection for new releases, development and testing?
Write in the comments!
Source: habr.com
