Flutter Analysis and Practice: Evolution and Innovation of Flutter-Based Architecture
With the booming development of mobile smart devices, a mobile multi-terminal development framework has become a general trend. Download the Flutter Analysis and Practice: Evolution and Innovation of Xianyu Technologies eBook for step-by-step analyses based on real-life problems, as well as clear explanations of the important concepts of Flutter.
5.1.1 Advantages and Challenges of Flutter
In addition to excellent cross-end rendering consistency, Flutter also provides highly efficient development experience, a wide range of out-of-the-box UI components, and a performance experience comparable to that provided by native. The numerous advantages of Flutter have made it a popular technology in recent years, as shown in Figure 5–1.
Based on the features shown in the figure, Flutter can greatly accelerate client development and provide excellent performance experience. We think that Flutter will bring great benefits to the following teams:
1) Small- and medium-sized client teams: Developers can develop a project in Flutter but output it in both Flutter and native environments, which effectively breaks the limitation that a small team requires nearly equal numbers of developers at the iOS and Android ends. This helps maximize the production capacity of the whole team during the rapid progress of a project.
2) The team with most of its developed apps to be sold in the Android market: For example, more than 90% of the apps sold in Southeast Asian countries or regions are Android-based. Flutter allows more input to the Android market and less input to the iOS market, to ultimately achieve the effect of “buy one get one free.”
3) The team that focuses on mass production of apps: Any company, whether it mass produces ToB apps or produces ToC apps in different fields, can significantly improve its production capacity through the one-end development multi-end production feature of Flutter.
However, Flutter also causes new problems. All new technologies come from old ones. Flutter has many similarities with Chrome. If we consider Flutter as a browser container that uses the Dart language, how do we solve the following two problems?
- If Flutter is added to an existing app, how do we seamlessly connect native and Flutter while maintaining the isolation of development?
- If you use existing native UI components in the Flutter container, how can you ensure the seamless connection and high performance under the different rendering mechanisms of Flutter and native?
5.1.2 Architecture Evolution and Innovation of Xianyu
This section describes the specific cases of Xianyu and the evolution of related solutions.
184.108.40.206 Existing Apps and Flutter Container
As shown in Figure 5–2, when an app and the Flutter container exist, Xianyu first needs to avoid memory overflow after introducing the Flutter container. In addition, we hope to make the switching between Flutter and native pages smooth and transparent to full-stack developers. Therefore, we have conducted many targeted iterations.
Without any modifications, we can create a Flutter container by creating a
FlutterViewController on iOS. In this solution, while multiple
FlutterViewControllers are created, multiple Flutter engine runtimes are created in the memory (although there is still only one Dart VM at the underlying layer.) This brings considerable memory consumption. In addition, the data in multiple Flutter engine runtimes cannot be directly shared, resulting in difficult data synchronization.
In this case, Xianyu chooses to share one
FlutterViewController globally, ensuring minimum memory usage. In addition, Xianyu uses the basic framework
FlutterBoost to provide the communication and management between the native stack and Flutter stack. In this way, the navigator on the Dart side can automatically open or close a new widget when the native container opens or closes a new Flutter page. The solution provided by Google is implemented based on this earlier version provided by Xianyu.
However, if multiple tabs appear, as shown in Figure 5–2, the entire stack logic is confusing. Therefore, Xianyu upgrades the
FlutterBoost solution by providing a
BoostContainerManager on the Dart side to manage multiple navigators. This provides a WebView-like
OpenWindow function for the Flutter container. Each time the
OpenWindow function is called, a new navigator is generated. In this way, developers can implement push and pop in the navigator or directly open a new navigator through
FlutterBoost for independent management.
220.127.116.11 Flutter Pages and Native UIs
As a second-hand trading platform, Xianyu involves many images and videos and therefore has strict requirements on the online performance and memory usage of images and videos. The several available Flutter solutions (platform view and Flutter plug-in) still have some memory usage and online smoothness problems. This may cause memory overflow when most developers implement a complex image-text feed recommendation scenario like Xianyu. Therefore, Xianyu made significant optimizations.
We used the
FlutterTextureRegistry function provided in the Flutter plug-in to connect the entire native UI component to the Flutter rendering engine. In the first half of 2018, we made video optimization by modifying the external texture interfaces at the underlying layer of the Flutter engine. We extended the limitation that a
PixelBuffer memory object must be loaded into the original interface. Specifically, we added a new interface to load the
TextureID of a GPU object.
As shown in Figure 5–3, after the optimization, the Flutter engine can directly render the Flutter side based on the
TextureID generated on the native side. The process changes to:
directly generate TextureID on the native side > render (the original process is: generate TextureID on the native side > copy the memory object PixelBuffer > generate a new TextureID > render). The entire process is greatly shortened, ensuring the overall efficiency of rendering and reducing memory consumption. Xianyu launched the solution and applied it to image rendering scenarios, integrating the solutions such as image caching, CDN optimization, and image cropping with native solutions. This allows developers to enjoy Alibaba's middleware performance optimization and reduce memory usage. Memory overflows have been greatly reduced after the solution is implemented.
18.104.22.168 Architecture Innovation Practices in Complex Business Scenarios
After solving the preceding problems, Xianyu began to fully implement Flutter on the business side. However, Xianyu soon encountered new problems, as shown in Figure 5–4. In the process of multi-person collaboration, Xianyu wonders:
- How can we provide standards as a reference to ensure code consistency
- How can we effectively break down complex businesses into sub-problems
- How can we ensure that more developers get started quickly and write code with good performance and stability
In the early stage, we used the community’s Flutter Redux solution. Due to the complexity of the first implemented details and publishing pages, we split the views based on components. However, due to the business complexity, a new problem occurred: For a single page, there were many State attributes and Reducers, making it difficult to modify when new requirements were stacked, as shown in Figure 5–5.
In this case, we conducted the second iteration of the entire solution to introduce the Component concept based on the original Page. In this way, each Component has a complete Redux element, ensuring the isolation of UIs, logic, and data. Each Component contains only a small amount of code, which is easy to maintain and develop. However, when data synchronization is required for the pages, the complexity soars, affecting the unified status management on Page.
In this case, Xianyu looks at the client-side architecture design from a different perspective. By referring to the idea of Connect in the React Redux framework, we remove the Store from Component, and use a new Connector for data exchange between the Page and Component. On this basis, we have implemented the conversion from Page State to Component State and the automatic synchronization of Page State after Component State changes. This allows complex businesses to be split into sub-problems while maintaining the advantage of unified status management, as shown in Figure 5–6. Based on the unified development standards, the new framework also provides targeted performance optimization for long-list and multi-list splicing at the bottom layer. This ensures that each developer that makes development according to the standards can obtain better performance than other Flutter business frameworks on the market.
5.1.3 Application of Development Intelligence on Xianyu
Xianyu experienced rapid business growth in 2018. We carried out a large number of Flutter technical transformations and upgrades. While trying new technologies, we need more time to try and implement new technologies offline to ensure online stability. We also need new ideas and changes in working methods, as shown in Figure 5–7.
In our daily work, Flutter developers need to compile the Flutter output locally and upload it to the remote repository after each development, so that it is transparent to native developers. This ensures that daily development is not disturbed by Flutter transformation. In this process, the business developers on the Flutter side encounter a lot of tedious work, such as packaging, uploading, update, and synchronization, which are error-prone. It will take a long time to troubleshoot the errors. In addition, it is unknown whether Flutter has solved the problem of development efficiency, and whether developers comply with the business architecture standards during app implementation.
Xianyu believes that digitization and automation is a better way to solve these problems, as shown in Figure 5–8. Therefore, we first control the source code and run the git commit command to associate the code with the back-end requirements and bugs. For the commit information that does not meet the requirements, code merging is not allowed. This ensures that there is a healthy data source for subsequent data report analysis.
After the code and tasks are associated, you can easily complete the subsequent work through webhooks. Each commit is effectively associated with continuous integration (CI) platform tasks, and the packaging and automatic testing processes are automated through Xianyu’s CI platform, greatly reducing the daily workload. According to rough statistics, with the implementation of the automation system in 2008, each developer could save more than an hour every day by automating the Flutter packaging, uploading, and app packaging. In addition, this code association-based system can more easily construct data reports for detailed analysis of the entire process and results and drive the process improvement through data. This better supports the benefits of new technologies.
Flutter is very suitable for small- and medium-sized client teams, teams with most of the developed apps sold in the Android market and teams focusing on mass app production. However, Flutter has some disadvantages in hybrid development scenarios.
The Xianyu team provides solutions for several typical problems in hybrid development scenarios, so the entire solution can meet the launch requirements.
To comprehensively promote the implementation of Flutter in business scenarios, the Xianyu team has performed multiple iterations of the Fish Redux framework to ensure that every developer can quickly write excellent Flutter code.
The digitization and automation solution has greatly improved the efficiency of implementing new technologies and laid a solid foundation for implementing Flutter on Xianyu.
In addition to various solutions mentioned in this topic, Xianyu is making efforts in various aspects and continues to focus on the future development of the Flutter ecosystem.
- Standardized evolution of Flutter’s upper-layer infrastructure: This determines whether the hybrid project system can complete a comprehensive architecture like Spring Boot on the upper layer, and help more Flutter teams solve the problems of difficulty getting started and lack of industry standards.
- Extension of dynamic capabilities: This helps to improve the operational efficiency of businesses and ensures business efficiency when the standards of the app stores are met. Xianyu’s current dynamic solution combines dynamic component capabilities with tool chain systems for Fish Redux scalability.
- Fish Redux + UI2CODE: This streamlines code generation and business frameworks, ensuring that the UI work is completed by machines according to the unified team standards.
- Flutter + FaaS: This allows client developers to be full-stack engineers: The integrated front-end and back-end architecture design can greatly reduce collaboration and improve efficiency.
Allowing engineers to engage in more creative work is our goal. The Xianyu team will also continue to improve the Flutter system, contribute more to the Flutter community, and grow steadily with the community.