When working on the 1C:Enterprise 8.x platform, there is often a need to bind in the program code to ordinary (not predefined) directory elements. For example, an organization may have five types of prices that are used in almost all mechanisms. In this case, programmatic access to a specific price is, at best, carried out either by squeaking by code in the directory, or by the name of the element, at worst.

I witnessed how in reports, to obtain the required price, selection was used by type of price in a request by its name (see the following screenshot).

As a result, we get an unstable report that will stop working if the name of the price type is changed. If you are tied to the element code, then there is always the possibility of changing it. For example, due to a violation of the uniqueness of directory codes, the administrator can start renumbering objects, which will lead to changes in element codes and the report will stop working correctly.

In addition, if you link to the name or code of directory elements, then when you receive a link to an element, a search will always be carried out in the directory table. Despite the fact that standard system details are indexed by the DBMS, searching for them in some cases can take up significant resources. Moreover, it would be more rational not to perform search query according to the reference table, if, let’s say, the link to the element is already “known in advance”.

As a way out, you can store a link to each frequently used element of the “Item Price Types” directory in separate constants and obtain values ​​from them in the request. However, in this case the developer will have to add a separate constant for each such element. The situation will become significantly more complicated if such elements are not only in the directory “Item Price Types”, but also in other directories (“Object Categories”, “Quality”, “Nomenclature” and others). Then the number of constants in the system can increase several times!

Of course, it would be possible to add predefined elements to each of the directories and accessing them would become much easier. However, changing the default objects would make it more difficult to update the configuration from vendor packages.

There is a more optimal approach both in terms of developing the configuration metadata structure and in terms of system performance. This is what we will talk about today.

Universal solution

The essence universal solution will be as follows: a directory will be created into which the developer will add predefined elements. The "Value" attribute has been added to the lookup, the type of which depends on the values ​​for which the correspondence "Predefined lookup element -> Associated value" will be created. The directory metadata structure looks like this (see the following screenshot).

To get a predefined element the best option is to use the global method "PredefinedValue(<Имя>)" . The full path to the predefined element is passed as a parameter to the method. The syntax is similar to the VALUE() query language function.

For ease of development, I recommend adding a function to get the value associated with a predefined element in common module. IN test configuration, available for download via the link at the end of the article, a common module “Values ​​of Predefined Elements” with an export function has been created "GetValue of PredefinedElement(<ИмяПредопределенногоЭлемента>)" . The function's program code receives a reference to a predefined element, then receives the values ​​of the "Value" attribute using a request. The following screenshot shows the complete function listing.

As we can see, the function generates a request for the “Value” attribute of the predefined element passed as a parameter. The function parameter is a string with the name of a predefined element.
For proper operation the created mechanism must be linked into user mode a predefined element with a regular directory element by selecting the corresponding element in the “Value” attribute. Let's move on to the issue of impact on performance.

Performance Impact

I conducted a speed test for both search options: by name and by link from a predefined element. The search took place in the "Products" directory with 20,000 entries. When conducting tests for file database the following results were obtained:

The results showed that for the file version of work, using predefined elements to obtain frequently used elements of other directories is almost 4 times slower!

In the client-server version of work, the test results show a completely different picture. The speed of obtaining a link to the desired element has not decreased significantly (one of the tests showed 0.002 seconds for searching by name and 0.0008 seconds when working through a predefined element), but the reliability of the program has increased significantly!

conclusions

In cases where it is often necessary to link to ordinary directory elements, I recommend not using binding by code or name. This approach reduces system reliability and performance.

During my time working with the platform, I have more than once encountered situations where, after changing the name, for example, the directory element “PriceNomenclature Types,” the work of most non-standard reports failed.

The more algorithms are connected to ordinary directory elements through a code or name, the less stable the system is.

In addition, this approach will allow you not to change standard configuration objects if you need to add a predefined element to them. This will make the process of updating the configuration somewhat easier in the future.

Files for download:

  1. Uploading a test database with examples from the article.

In the fourth lesson of our we will continue to get acquainted with the program. Today we are on practical examples let's meet andhierarchical directories, and also learn how to create predefined elements.

Timing of 4 lessons of the course:

00:19 Changes in the Employees directory after completing homework for lesson 3 of the course
00:35 Editing the order of details in directories
02:54 Creating a directory Nomenclature
03:40 Creating and setting up a hierarchical directory
05:10 Creating groups Services and Products in the Nomenclature directory
06:05 Filling out the Nomenclature directory
07:14 3 ways to transfer a directory item to another group
08:21 Creating the Warehouses directory
09:19 Creating predefined directory elements
11:25 Filling out the Warehouses directory
12:20 Take the test on lesson 4 material

Hierarchical directory– a directory with the possibility of hierarchical arrangement of its elements. For example, in the Nomenclature directory, groups can be created: Products, Services, etc., in which elements belonging to these groups are located. In addition, directory groups can include other groups, thereby creating a multi-level hierarchical structure.

In addition, directories also support another type of hierarchy, in which directory elements will relate not to groups, but to other elements of the same directory. This type of hierarchy ( element hierarchy) can be used, for example, when creating a directory of Divisions, where one division (a division in this case is an element of the directory, not a group) can include several other divisions. This type of hierarchy is used quite rarely.

Directory forms– visual representation of the directory. Depending on what specific actions we want to perform with our directory, we need to display the directory in “ various types" So, in lesson 4 of the course, we edited the order of details in the form of a list and in the form of a directory element.

The system creates (generates) forms automatically, but, if necessary, the developer can “draw” the forms independently.

There are a total of 5 forms (types of forms) for directories:

  • element shape– to create or edit a directory element;
  • group shape- to create or edit a directory group;
  • list form– to display a list of directory elements;
  • selection form- used to select one of the elements in a field of a certain form this guide. For example, in order to select a specific warehouse from the Warehouses directory in the Goods Receipt document in the warehouse field;
  • group selection form– is used to select one of the groups of this directory in a field of a certain form.

Predefined directory elements– directory elements created by the developer in Configurator mode, and which can be accessed from the built-in 1c language by Name.

There is a fundamental difference between regular and predefined directory elements. Ordinary elements are not constant in configuration. During the user's work, they can be created, edited and deleted and, for this reason, they should not be relied upon when executing any algorithms (the code and name of the element can be changed by the user).Predefined elements, on the other hand, are permanent. During operation, even if the user renames such an element, it can be accessed from the built-in 1c language. This is achieved by having the predefined element have props Name, which is not available to the user. U ordinary elements There is no reference book for such details.

Important! Technically, the user has the ability to delete a predefined directory element, but, as a rule, users are denied rights to delete predefined directory elements.

Homework for lesson 4 of the course

Homework for the fourth lesson of the course will be available to you immediately after successfully solving the theoretical test.

The very idea of ​​programmatic work with predefined elements, in my opinion, is very correct. There are simply nuances that need to be taken into account when working.

First, you need to clearly understand for yourself that there are predefined elements in the configuration and there are predefined elements in the information base (IS). Technically, predefined information security elements are the most common elements of directories, in which the “Name of Predefined Data” attribute indicates which predefined configuration element they correspond to. They are no different from ordinary elements. Accordingly, any ordinary information security element can be made predefined, any predefined element can be made ordinary. To do this, just enter the desired value in the attribute "PredefinedDataName".

From time to time, this property contains a value that is not the one the developer intended. As a result, errors occur in the operation of 1C. From critical, in which work is basically impossible, to non-critical, in which the logic of the algorithms is disrupted.

Conditionally we can distinguish three types of errors:
1. "The predefined element is not in the data";

3. Incorrect specification of a predefined element;

1. "The predefined element is not in the data" - o absence of a predefined element described in the configuration in the information security data.

This is the easiest type of error to debug and correct. Its simplicity is that the platform quite correctly reports this situation “The predefined element is missing in the data” and it is quite clear how to fix it.

When accessing a missing element in the code "Directories.Types of Contact Information.Email of the Contact Person" a message is displayed

When accessing an element in the request "VALUE(Directory.Types of Contact Information.Email of the Contact Person)" the following message is displayed:

This error occurs if an element is described in the configuration, but the element is not associated with it in the database.

To begin with, let us clarify that this situation is not always wrong. It is quite possible to use predefined data in some kind of program logic, which for most users may not be used. In this case, in order not to clutter up the directory for all users of the configuration, it is logical to define predefined elements in the configuration, but not to create them in all information security systems, but only for those information security systems in which the required configuration logic is used. In this case, the programmer can specify the “Do not update predefined data” property for the directory and create elements programmatically when accessing the module functionality. Or allow the user to independently bind predefined module elements to existing regular elements.

Also, automatic creation of predefined elements is not used when working in RIB mode. Since new elements must be transferred from central base, and not be created in nodes with different UIDs.

Those. Sometimes the error is the reference to an unmatched element, not the presence of such an element itself.

It is necessary to analyze why the element was not created. Perhaps it should be created when some program mode is executed. For example, after completing an exchange in RIB. Or perhaps it was just accidentally deleted.

If the logic provides for filling predefined elements not automatically, but in a separate mode, then before using access by name " Directories.Types of Contact Information.Email of the Contact Person"To prevent an exceptional situation, it is advisable to check that the element is already in the database. If the element is missing, then inform the user about this and explain what mode he needs to perform to fill the element. For such a check, you can run a data query.

Request = New Request; Request.Text = "SELECT | Types of Contact Information. Link | FROM | Directory. Types of Contact Information HOW Types of Contact Information | WHERE | Types of Contact Information. Name of Predefined Data = "" EmailContactPerson"""; Item Is MissingInData = Query.Execute().Empty();

If this is still an error in the database data, then it is necessary to bind to a predefined element of the information security element. Those. it is necessary to explain to the system which information security element the program code should access given name. Technically, a binding is simply specifying the name of a predefined element in the " propertyPredefinedDataName" of the IS element. To install it, just run the code:

2. "The predefined element is not unique" - h double predefined elements:

This situation is that several information security elements are attached to one predefined element. In this case, when accessing a predefined name, the element will be selected randomly. This situation is always wrong. Its difficulty is that the platform does not report it in any way. The algorithms just start working incorrectly.

The platform will report the error "The predefined element is not unique" only when you try to edit a duplicate element.

As long as no one needs to edit the element, no one will know about the error.

Such duplicates can be created, for example, if RIB is used for the directory and the “Update automatically” mode is specified in the properties for predefined data. In this case, when performing an exchange, one instance of the predefined data will be created when the configuration is updated. A second instance of predefined elements with the same name will be transferred from the central database during the exchange.

Also, these duplicates will arise when using exchange processing between configurations if different information security elements correspond to predefined elements in different databases. In this case, one copy of the predefined data already exists in the database, the second will come when loading data with a different UID. If you are performing data transfers, you need to decide which database elements are considered primary and use them in the subordinate database. In the subordinate database, it is necessary to replace the use of old elements with elements of the main database.

Such errors in the database can be identified with a query like:

SELECT Types of Contact Information.Name of Predefined Data, QUANTITY(DIFFERENT Types of Contact Information.Link) AS Number of Predefined FROM Directory.Types of Contact Information AS Types of Contact Information GROUP BY Types of Contact Information.Name of Predefined Data HAVING QUANTITY(DIFFERENT Types of Contact noInformation.Link) > 1

This query will return a list of predefined elements with which more than one information security element is associated.

If such elements are present, it is necessary to remove the connection with the predefined one for one of them. Those. It is necessary to unambiguously determine for the system which information security element the program code should refer to when using this name. To do this, just run the code.

3. Incorrect specification of a predefined element.

The error is that the predefined element corresponds to an element that is not provided by the program logic. Such errors are the most difficult to diagnose. Unlike the first two types, the configuration cannot be automatically checked for these errors. They can only be identified by analyzing the logic of work. If in doubt, you can check whether the correct element is being used.

To do this, just run one of the commands.

//Defining an information security element that is linked to the desired predefined Notify (Directories.Types of Contact Information.Email of the ContactPerson) //Defining a predefined element to which the selected Notify is attached (Link to Element.Name of Predefined Data)

If such errors are identified, it is necessary to remove the incorrect connection with the old element and add a connection with the new element. The operation code is similar to the code for correcting the first two types of errors.

Well, briefly about errors when program work or in configurator mode:

"The predefined element does not belong to<Имя справочника>" - an error occurs when trying to write a predefined element with a name that does not match the name in the configurator.

"Non-predefined objects cannot have predefined subconto view records" - an error occurs when trying to make an element of a predefined chart of accounts unpredefined. To eliminate errors, it is necessary to remove the “Predefined” flag from each element subcontact line.

"Non-predefined objects cannot have predefined records of leading calculation types"- an error occurs when trying to make a predefined element of the plan of calculation types unpredefined. To eliminate errors, it is necessary to remove the “Predefined” checkbox for each line of the element’s leading calculation type.

"Predefined elements are not unique"- an error appears in the configurator when updating information base to release the configuration without compatibility mode with 8.3.4. It is necessary to check for duplicates and eliminate them before updating.

"The name of the predefined element is not unique" - the error occurs when there are several predefined elements of the same name in the configuration when updating to the platform8.3.6.2332 and higher. It is necessary to eliminate duplicates in the configuration.

To work with predefined data, I recommend processing. It can perform any actions with predefined data, and can also check the configuration as a whole for the presence of errors of the first two types (duplicated and missing elements) in all information security objects (directories, charts of accounts, PVC, PVR).

Everyone knows the difference between predefined elements and regular ones: “Predefined elements are created in the Configurator mode and cannot be deleted in 1C:Enterprise mode.” In user mode, you can distinguish a predefined element from those added by users using a special icon (see the following screenshot).

Basically, predefined elements are created by developers in order to bind algorithms to them in various configuration objects. For example, in the “Manufacturing Enterprise Management” configuration in the “Quality” directory, the developers added a predefined element “New”.

This element is used in many configuration modules. So in the document “Receipt of goods and services”, when posting in all registers where there is a “Quality” dimension, the value of a predefined element is substituted. The following is a listing of filling out the posting table for the "Goods of Organizations" register:

// PRODUCTS BY REGISTER ProductsOrganizations. MoveSet = Moves. ProductsOrganizations; If Receipt Type = Transfers. Types of Receipts of Goods. To the warehouse then // Get a table of values ​​that matches the structure of the register recordset. MotionTable = MotionSet. Unload() ; // Fill in the motion table. General Purpose. LoadValueTable(ProductTable, MovementTable) ; // Missing fields. Movement Table. FillValues(Organization, "Organization" ) ; Movement Table. FillValues(Undefined, "Commission Agent"); Movement Table. FillValues(Directories. Quality. New, "Quality" ) ; // Fill the quality from a predefined element

Thus, the characteristics of predefined elements and their purpose are quite simple. Let's look at the way they are stored in database tables and how they differ from ordinary elements.

Differences

In the test configuration, the "Products" directory was created. The "Test Elements" group has been created in it. You could see the contents of the group in the screenshot at the beginning of the article. For the "Products" directory, the SQL database has a corresponding table "_Reference37" with the following structure:

But how can we determine whether the details correspond to the configuration tree and the fields in the SQL table?

Let's take advantage standard method global context “GetDatabaseStorageStructure()”, which will return us a table of values ​​with a description of the structure of the tables.

In the "Fields" table of values, we see the correspondence between the fields of the SQL table and the object details in the metadata tree. In our example, we consider the structure of the “Products” directory. All directories have a standard attribute "Predefined" of the Boolean type, which is set to TRUE for predefined elements:

Based on the table with the directory storage structure in the database, we can definitely say that the “Predefined” field corresponds to the “IsMetadata” field. If we look at the contents of the "_Reference37" table in the SQL database, we will see the following:

In the entry for the predefined element, the value of the "IsMetadata" field is set to "0x01", which corresponds to the TRUE flag. For normal elements the value is set to "0x00". This is the main difference between predefined elements and ordinary ones. All other fields are stored in the database in the same way as fields in regular items added by users.

Predefined elements can have very interesting uses. With their help, you can prevent groups of elements from being deleted/marked for deletion in the directory and other objects where they can be added. If we try to delete or mark for deletion the "Test Elements" group. then we get the following errors:

Thus, predefined elements make the group in which they are placed also "predefined".

Completion

Predefined elements are an integral part of most configurations. Their use simplifies development and makes the construction of functionality logically more “harmonious” and integral.

Print (Ctrl+P)

Working with Predefined Values ​​Using the Object Manager

You can get a predefined value on the 1C:Enterprise server side using the manager of the corresponding object. The line defining the received attribute has the following form:

PredefinedValueType.MetadataObjectName.Value


PredefinedValueType– to obtain predefined values, the following data types are available (written in
plural):
● Directories,
● Plans of Types of Characteristics,
● Charts of Accounts,
● Plans of Types of Calculation,
● Transfers.
ObjectNameMetadata

● Value – can be one of the following:
● for enumerations, the name of the enumeration value is indicated;

● Route Points.Point Name – business process route point.
If you need to get a business process route point, the line describing the value you get will look like this:

BusinessProcesses.MetadataObjectName.RoutePoints.RoutePointName
Example:


Type = Listings.Types of Products.Product;
// Obtaining predefined directory data.
Element = Directories.Currency.Ruble;
// Business process route point
Point = BusinessProcess.Approval.RoutePoints.Approval;

Working with Predefined Values ​​Using a Function PredefinedValue()

Due to the fact that application objects are not available on the client side, obtaining predefined details using object managers becomes impossible. Therefore, to obtain them, there is a global context method PredefinedValue(). The parameter to this method is a string describing what predefined value is to be retrieved. The syntax for describing a predefined value is the same as the syntax for the VALUE operator in the query language.
The line defining the received attribute has the following form:

Let's look at the components of this line in more detail:
PredefinedValueType– to obtain predefined values, the following data types are available (written in
singular):
● Directory,
Plan of Types of Characteristics,
● Chart of Accounts,
Plan of Types of Calculation,
● Transfer,
● Business Process.
● AND nameObjectMetadata– the name of the metadata object is indicated as it is specified in the configurator.
● Value – can be one of the following

● for enumerations, the name of the enumeration value is indicated;
● to obtain a predefined value, indicate its name, as it is specified in the configurator;
● RoutePoint.PointName – business process route point;
● EmptyLink – to get an empty link.
If you need to get the value of a system enumeration, the method parameter will look like this:
SystemEnumerationName.SystemEnumerationValue.
For example:

ChartType = PredefinedValue(“ChartType.ConcaveSurface“);
If you need to get a business process route point, the line describing the value you get will look like this:
Example:

// Get the enumeration value.
View = PredefinedValue(“List.Types of Products.Product”);
// Get the value of an empty link.
EmptyLink =
PredefinedValue(“Document.ConsumableInvoice.EmptyLink”);
// Obtaining predefined directory data.
Item = PredefinedValue(“Directory.Currency.Ruble”);
// Business process route point
Point = PredefinedValue(“Business Process. Approval. Route Point. Approval”);