Wechat applets

The project structure

The figure above shows the project structure of wechat applets. The following pages contains each page in the applets, and each page is composed of four parts: page structure, page style, page configuration and logical code.

  • Page structure

The page structure file is index. WXML, which is written by wechat’s self-defined tag.

  • Page logic

The page logic is written in JavaScript.

  • Page style sheet

Like a CSS file, to define the style of elements in a page.

  • Configuration page

Configure information such as permissions on the page.

Technical selection of micro channel small program

The positioning characteristics of small programs are light and fast. In view of these two characteristics, wechat has made some considerations in the selection of technology.

Techniques for rendering interfaces
  • Render using pure client-side native techniques

Disadvantages: Cannot be dynamically packaged and delivered.

  • Render using pure Web techniques

Disadvantages: If we use pure Web technology to render applets, we may face some performance problems on pages with complex interactions. This is because in Web technology, UI rendering and JavaScript script execution are executed in a single thread, which can easily cause some logical tasks to seize the RESOURCES of UI rendering.

  • Between client-side native technology and Web technology, combined with their own characteristics of the technology to render

PhoneGap is similar to wechat JS-SDK in that they both end up using the browser kernel to render the interface. RN, on the other hand, is client-side native rendering at the bottom, although it is written in Web-related technology and also uses JavaScript to interpret execution. We choose Hybrid technology like wechat JSSDK, that is, the interface is mainly rendered by mature Web technology, supplemented by a large number of interfaces to provide rich client side native capabilities. At the same time, each small program page is rendered with a different WebView, which can provide better interactive experience, more close to the native experience, but also avoid the task of a single WebView is too heavy.

The reason why wechat did not choose RN
  1. The styles RN supports are subsets of CSS, which cannot meet the growing needs of Web developers, and the transformation of RN is costly and risky.

  2. RN has some unstable problems with its current capabilities, such as performance and bugs. RN leaves all of the rendering work to the client’s native rendering. In fact, some simple interface elements can be rendered using Web technologies and are very stable.

  3. RN has some unexpected factors, such as licensing issues

How native components are rendered

On Android, a native method is injected into the Window object of the WebView, which is eventually encapsulated into a compatibility layer such as WeiXinJSBridge, which mainly provides two methods: invoke and on. The developer inserts a native component. Typically, the component is inserted into the DOM tree at runtime, and the client interface is called to tell the client where to render a native interface. When subsequent developers update component properties, they also invoke the update interface provided by the client to update parts of the native interface.

Problems and solutions brought by Web rendering
  • Provides a clean and pure JavaScript execution environment

Due to the flexibility of JavaScript and rich functions of the browser, it will lead to a lot of uncontrollable privacy. Therefore, wechat provides a simple JS execution environment, through which the controls are also customized. Therefore, the complete adoption of this sandbox environment does not have any browser-specific interfaces, and only provides a pure JavaScript interpretation execution environment. Features such as ServiceWorker and WebWorker in HTML5 meet this condition, both of which enable another thread to execute JavaScript. However, considering that the applet is a multi-WebView architecture, and each applet page is rendered by a different WebView, it is difficult for us to use a ServiceWorker in a WebView to manage all the applet pages under this architecture. Thanks to the JavaScript interpretation engine in the client system (in iOS using the built-in JavaScriptCore framework, in Android using the JsCore environment provided by Tencent X5 kernel), we can create a separate thread to execute JavaScript. In this environment, all the code is about the business logic of the applet, which is the logic layer we’ve been talking about. And interface rendering related tasks are all performed in the WebView thread, through the logic layer code to control which interface rendering, so this layer is of course called the rendering layer. This is where the two-threaded model of applets comes in.

  • Tag Customization

In order to prevent some problems caused by tag definition, wechat has customized a set of tag language, WXML, which, after compilation, will eventually generate Html.

Separation of rendering and logic

The above is the selection of the rendering technology of the small program. After the selection, because the rendering and logic are no longer executed by the same browser, one in the pure JS environment, one through WebView rendering, so the running environment of the small program is divided into the rendering layer and the logic layer, WXML template and WXSS style work in the rendering layer, JS script work in the logic layer.

The rendering layer and logic layer of the small program are managed by two threads respectively: the interface of the rendering layer uses WebView to render; The logic layer uses JsCore thread to run JS script. A small program has multiple interfaces, so there are multiple WebView threads in the rendering layer. The communication of the two threads will be transferred through the wechat client, and the network request sent by the logical layer will also be forwarded through the Native. The communication model of the small program is shown in the figure.

Data-driven view changes

In the process of developing THE UI interface, the program needs to maintain many variable states and operate the corresponding UI elements. As the interface becomes more complex, we need to maintain many variable states and deal with many interactive events on the interface at the same time, and the whole program becomes more and more complex. Interface views are usually associated with variable states, and if there were some “way” to bind the state to the view (the view would automatically change when the state changes), then we would not have to modify the view manually.

The logic layer and the rendering layer of the applet are separate threads. In the rendering layer, the host environment will convert WXML into the corresponding JS objects. When the data changes in the logical layer, we need to transfer the data from the logical layer to the rendering layer through the setData method provided by the host environment. After comparing the differences before and after, the differences are applied to the original Dom tree to render the correct UI interface.

By changing MSG data from “Hello World” to “Goodbye” through setData, the corresponding node of the generated JS object will change. At this time, the two JS objects can be compared to obtain the changed part, and then the difference can be applied to the original Dom tree to achieve the purpose of updating UI. This is how “data driven” works.

Event handling

UI applications need to interact with the user. For example, a user may click a button on your interface or hold down an area. This feedback should be communicated to the developer logic layer and the corresponding processing status should be presented to the user. Because WebView now has only the function of rendering, so for the event distribution processing, wechat has a special processing, all events are intercepted, thrown to the logic layer to JavaScript for processing.

Event distribution processing, with event capture and bubbling mechanisms. After passing it to JSCore through Native and responding to the event through JS, Dom is modified, which will be reflected in the virtual Dom, and then real rendering is carried out.

Data communication

Applets are based on a two-threaded model, which means that any data transfer is a communication between threads, meaning that there is a certain amount of delay. Unlike the traditional Web, when the interface needs to be updated, the UI is rendered synchronously by calling the update interface. In applets, all of this becomes asynchronous.

Asynchrony complicates the timing of the parts. For example, when rendering the first screen, the logical layer and the rendering layer will start the initialization work at the same time, but the rendering layer needs the data of the logical layer to render the interface. If the initialization work of the rendering layer is completed quickly, the next work can be carried out only after the instruction of the logical layer. So the logic layer and the rendering layer need to have some mechanism to keep the timing correct,

During the life cycle of each applet page, there are several times of page data communication. The logical layer sends page data (the contents of data and setData) to the view layer, and the view layer feeds back user events to the logical layer.

The way to improve performance by transferring data using Json is to reduce the amount of data exchanged.

Caching mechanisms

The local cache space of different applets is separated. The maximum cache space of each applets is 10MB. If the current cache has reached 10MB, writing to the cache through wx.setStorage triggers the fail callback.

The local cache of small programs not only isolates the space through the dimension of small programs, but also isolates the cache of different users in the host environment considering that the same device can log in to different wechat users to avoid data privacy disclosure between users.

Because the local cache is stored on the current device, users cannot read the current device data from another device after changing devices. Therefore, you are advised to store key user information on the server for persistent storage instead of the local cache.

Alipay small program

Alipay small program introduction

The implementation of Alipay applets and the implementation of wechat applets are roughly the same, so this is mainly aimed at the differences between the two.

Alipay small program directory structure

Alipay small program business architecture diagram

In terms of rendering engine, Alipay applet not only provides JavaScript+Webview, but also JavaScript+Native. In scenes with high performance requirements, Native rendering mode can be selected to give users a better experience.

Runtime architecture

The small program programming model is divided into multiple pages, each page has its own template, CSS and JS. In practice, the JS code of business logic is run in an independent JavaScript engine. The template and CSS of each page are run in separate WebView, and the function navigateTo is used to switch between pages.

The way that the page in each WebView interacts with the logic in the common JavaScript engine is through the message service, and some of the page’s events are passed through this message channel to the JavaScript engine environment, which responds to the event by making some API calls, Adjustable to the client alipay small program to provide some ability, after processing will send this data to the corresponding page rendering container to process, the data and template together to produce the final user interface.

Alipay small program virtual machine isolation

The usual way to do this is to run the Render code in the WebView, and then run the ServiceWorker in another thread. When the Serviceworker needs to update the DOM, it sends the event and data to the Render thread via Messagechannel for execution. When the business needs to be transferred to the Render layer with a large amount of data and complex objects, the interaction performance will be poor. Therefore, we propose an optimized solution for this situation.

The solution redesigns the ORIGINAL JS VIRTUAL machine instances (known as Isolate) into two parts: Global Runtime and Local Runtime.

  • The Global Runtime section houses shared devices and data, globally an instance.

  • The Local Runtime holds the instance’s own modules and private data, which will not be shared.

Under the new isolation model, the v8 instance in webView is a Local Runtime, and the V8 instance in worker thread is also a Local Runtime. When the worker layer interacts with the Render layer, SetData objects are created directly in the Shared Heap, so the Render layer’s Local Runtime can read the object directly and use it for render layer, reducing object serialization and network transfer, and greatly improving startup and rendering performance.

First screen speed optimization

Since the start of small programs is controlled by the life cycle, from onLaunch -> onLoad -> onShow -> onReady -> user action -> leaving the home page, any link in this process may be interrupted by objective or subjective reasons. It is possible to save inaccurate offline pages and present the wrong page to the user at startup.

Therefore, for the effect of offline cache rendering of the home page, the timing of saving the page is very important. We provide developers with the opportunity to configure, the timing of configuration has two: the rendering is completed and before leaving the home page. For rendering completed is the home page rendering completed, the user has not performed any operation before the page is saved as an offline cache page. Before leaving the home page, a user performs a series of operations on the home page and then switches to another page. The page is saved as an offline cache.

To the problem of the splash screen scene because cache pages are separate from the real rendering of the page, are two separate page, cache pages are static pages, real page is a dynamic page created by js, so it is normal when real page after replacing the cached pages created, this case will occur the splash screen.

To solve this problem, we adopted virtual DOM. When loading the cached page, we put the cached page into the initial virtual DOM. The virtual DOM generated after the creation of the real page is dom diff with the virtual DOM of the cached page, and the changed content is transmitted to the browser kernel through patch. Render the corresponding page, so that you can only update the local changes of the page content, avoid the update of the whole page, but also ensure the accuracy and real-time content.

Alipay uses UC browser kernel advantages

1. Picture memory: for low-end computers, stricter picture cache limits are made, and the use of picture cache is further restricted while maintaining performance experience; Image cache pool shared by multiple WebViews; Fully support WebP, APNG this more memory – saving and size of the picture format.

2. Rendering memory: In the invisible state of Webview, the native memory management has no special treatment, and the UC kernel will release the rendering memory of the invisible Webview; Reasonable Settings and tuning of render memory to avoid scrolling performance degradation and excessive memory usage.

3.JS memory: v8 memory GC is handled more reasonably, and full GC is delayed at startup to avoid affecting startup time.

4. Peak memory management: when the system is short of memory, it will notify the kernel. UC kernel can release non-critical memory occupying modules when the system is low in memory, avoiding OOM and rendering black blocks caused by excessive release. In some OOM cases, avoid the native kernel active crash logic, and in extremely low memory cases, some features are unavailable, rather than crashing.

Refer to the article

  • Alipay small procedures to achieve

  • Wechat applets development document

  • Micro channel applet principle document