17
头图

Project Background

Partial back office management system or integrated application platform entrance, often need to be applied in the entrance personalized display . From the user's point of view, supporting personalized customization can effectively improve the user's happiness and use or work efficiency; from the product provider's point of view, the ability to provide personalized customized services is also a way to enhance product strength.

image001.png

How to provide personalized customization capabilities

  • Custom development (that is, secondary development that has been criticized by developers)

    • Excellent: Respond quickly to individual needs
    • inferior:

      • The development cost is high, indicating that its own product strength is limited
      • Risks in source code control
  • Open configuration items

    • Excellent: No need for secondary development, saving cost
    • inferior:

      • Configuration items are difficult to abstract, granularity is difficult to grasp, and there are often places where configuration items cannot cover requirements
      • Do everything then do nothing.

solution

Is there a way to quickly respond to individual needs and control development costs? Here are two : 160ed724398208 visualization build , Low Code low code .
  • process visualization by dragging and dropping page modules on the designated configuration platform, and output personalized pages or modules.
  • Low Code Low Code: developers through a small amount of coding or No Code, you can quickly meet the individual needs, and the results were used in coding configuration.

In fact, the comparison between these two concepts is not a new word. There are shadows in the Dreamwaver era (return to ancestors?), and it is difficult for the Low Code solution to leave the visual construction and complement each other. In the portal's "thousands of people and thousands of faces" demand, the above scheme was adopted.

Target Audience

Who uses this program? How to divide responsibilities?
Visualized constructionCoding development
AudienceTechnical Support/Project Manager/...Baseline Developer/Project Developer
DutiesDrag and drop page/personalized configurationRapid module development/customized development

Portal practice plan

In practice, the portal uses: split the entire page into modules ( part ), just like building blocks, you can build personalized pages through different permutations, combinations, and layouts.

Widget-Visually build the smallest unit

Widgets are actually the "building blocks" in this solution, which can be flexibly placed or individually developed.

When we think about how to split the entire page, we will naturally find that the front end components of coincides thought. Any split module unit has its own view HTML, interactive logic JavaScript, and style CSS .
One of the most basic components is composed of HTML/Javascript/CSS, plus some static resources (such as pictures/language files/...).

image003.png

Of course, we hope this component has the following characteristics:

  • Independent development : Developers can develop Coding outside the host environment (portal)
  • independent deployment : that can be deployed anywhere, as long as the component resource can be accessed through the address, it can be loaded
  • Dynamic loading : Load when used, do not need to not load.

How to achieve

Modern front-end frameworks (React/Vue/Angular) can basically achieve component-based development, but the ideal solution is framework free , that is, free from framework constraints.
For development cost considerations, combined with the internal front-end unified technology stack, the portal components use the Vue.js dynamic component . That is, a component is an SFC single file component (Single File Component), through the Webpack modular packaging tool, the component source code is packaged, and a resource package is output.
In the host environment, acquired by the interface means address resources dynamically parsed and executed string, then the dynamic loading (by way of the dynamic component Vue <component> the is attribute).

<component v-bind:is="widgetActiveComponent"></component>

Visualized building layout design

Currently, the portal uses xy coordinate system as the rule of front-end page layout.
As shown in the figure, the vertex coordinates of the upper left corner of the component container are used as the positioning point of the component.

image.png

PS: For the layout design here, we actually considered the grid layout , but each has its own advantages and disadvantages. The coordinate layout is more granular, which is suitable for more personalized scenes. However, the grid layout is less costly and more efficient. Finally, by adding the function of grid adsorption optimizes the coordinate layout experience . This code worth one hundred million can be provided free of charge if needed.

image.png

The overall process of the program

As shown in the figure below, abstract from the page module, build and deploy through packaging, and finally load and render, forming a closed loop. :)

wdg_process.aa2802e2.png

summary

Through component drag and drop configuration ( visualized building ) and Low Code low code development (using the provided scaffolding to quickly develop components, independent development, independent deployment, dynamic loading), to achieve the personalized needs of the portal.

Technology precipitation-visual construction

The realization of this piece in the portal is not difficult and cumbersome. List a few points that may be trampled on.

image012.png

1. Drag in the canvas

The difficulty here, in addition to taking into account the native onmousedown / onmousemove / onmouseup some of the border issue and other mouse event, stop event bubbling, and, in particular, the mouse in a different canvas scaling in the case of drift . It will be mentioned in the pseudo code below.

// 伪代码
<div class="dragItemBox">
  <div class="dragCover" @mousemove="drag($event)" @click.stop></div>
</div>

<script>
  drag(e) {
        e.onmousedown = e => {
      // 记录鼠标按下时的坐标
        document.onmousemove = e => {
        // 记录鼠标移动时的xy坐标差
        // 重点来了,这里差值要考虑画布的缩放比例,不然在不同的缩放比例下,会造成鼠标漂移哦
        // 边界问题,这里可以约束拖拽的范围
          document.onmouseup = e => {
            // 将坐标差赋给目标元素,改变其布局样式
        }
      }
      document.onmouseup = e => {
        // 按下不移动鼠标,对事件状态进行重置
      }
    }
    }
</script>

2. Drag and resize in the canvas

And when resize components, the logic of each anchor point (a total of 8 anchor points) needs to be strictly abstracted. Just give a chestnut to understand.

The component has width/height/top/left , first look at anchor point 1 and anchor point 8. When dragging anchor point 8 , only the two attributes width/height When dragging the anchor point 1 , the width/height/top/left are , 160ed724399922, so the logic of each anchor point is different, how to abstract and how to encapsulate, it depends on your own play. Pay special attention here, otherwise there will be various inexplicable drift problems.
image.png

3. Pure CSS to achieve a dotted line grid

Dotted line is not, nor is the dotted line, but dotted line . I thought of this name myself. at the picture below, the 160ed724399d04 intersection point of the will be a bit bigger than the rest!
saw this visual draft and almost pulled out a machete 40 meters under the table. This is not for death, why not use pictures? The main reason is that the size and color of the grid can be adjusted, so it should only be implemented with pure CSS, right.
If you are interested, you can try to implement it yourself. The code here, really, I don’t sell for 500 yuan :(

image.png

CSS API involved:

  • linear-gradient() ): linear gradient
  • radial-gradient() ): radial gradient
  • The background-size attribute specifies the size of the background image.
  • The background-position property sets the starting position of the background image.

Realization of decomposition

  • Step.1 stripes
  • solid line grid
  • Step.3 dotted grid
  • Step.4 dotted line grid

The following is the DOM structure and front style of the legend below.

<style>
.bg {
  width: 100px;
  height: 100px;
  background-color: black;
}
.basegrid {
  width: 100%;
  height: 100%;
}
</style>
<div class="bg">
  <div class="grid basegrid"></div>
</div>
  1. Step.1 First use linear-gradient() draw the stripes. Key: boundary significantly (linear-gradient will produce a gradient effect under normal circumstances, but the streak here obviously needs borders, so before you need after a gradient color gradient After a location, specifically refer to this article )

image017.png

  1. grid can be understood as a combination of horizontal and vertical stripes. Key point: background-image can be set with multiple gradient overlays, and horizontal and vertical stripes can be superimposed separately.

image019.png

The thickness of the grid lines: you can control linear-gradient background-size and 060ed72439a174 to control the thickness of the grid lines.

image021.png

  1. Step.3 The dashed line of 160ed72439a23a can continue to superimpose stripes that are consistent with the background color. Two gradients can be used to superimpose (horizontal and vertical stripes).

image.png
image.png

What I think of here is that you can use diagonal stripes to achieve a dashed line, which can save a gradient overlay.

image.png

  1. Step.4 dashed grid has been implemented, then dotted line grid? Split! Split into dot matrix and dotted grid , so that the two overlap. The lattice uses radial-gradient() ) radial gradient.

image.png

The two are superimposed, Finally!

image.png

Low Code practice

The following will introduce the low code and the related content of the micro front end. During the process, the landing plan of the portal part will be inserted ( * in front of the title). From the results, low-code low-code is the result. All roads lead to Rome, but some key points are always inseparable, such as the above-mentioned visual construction and module isolation. In terms of module isolation, the micro front end Provides a lot of solutions worth learning. Complement each other, the birth of technology to solve specific problems .

Low-Code introduction

A low-code development platform (LCDP) is software that provides a development environment used to create application software through graphical user interfaces and configuration instead of traditional hand-coded computer programming. A low-code model enables developers of varied experience levels to create applications using a visual user interface in combination with model-driven logic.

In one sentence, the key element to realize a low-code platform is model-driven design , code automatic generation and visual programming .

Scenes

From the earliest use of modular construction to solve the problems in the field of marketing activities, it has developed to the present. Low-code can be used to solve the internal complex middle and back-office business needs. It is not only suitable for product operations for C-side users, but also suitable for B-side users. Data management needs.

Core competence

  • Construction and access of basic materials

    • Customized component access
    • Custom component
  • Layout ability: page layout/logical layout

    • Real-time visualization
    • Multi-terminal adaptation
    • Multi-scene adaptation
  • Pro-code and low-code code conversion capabilities

    • The ability to re-develop the output programming products
  • Collaboration
  • Data analysis capabilities

The twenty-eight principle

  • Achieve coverage of 80% of business scenarios through the low-code platform
  • 20% of the ability is realized through pro-code customization

Intersection with micro front end

Why is the micro front end mentioned? Because the front-end micro-architecture, the front-end application can operate independently, independent development, independent deployment . coincides with the portal component program . Of course, we also refer to the Single-SPA and qiankun in the module isolation program.

Micro front end solution

The micro-front-end architecture is an architecture similar to micro-services. It applies the concept of micro-services to the browser side, that is, a web application is transformed from a single monolithic application to an application in which multiple small front-end applications are aggregated into one.
the wayDevelopment costsMaintenance costfeasibilitySame framework requirementsDifficulty of realization
Route distributionlowlowhighno
iFramelowlowhighno
Application microserviceshighlowinno★★★★
WidgetizationhighinlowYes★★★★★
Micro-applicationininhighYes★★★
Pure Web Componentshighlowhighno★★
Combine Web Componentshighlowhighno★★

Widgetization-modular integration

In the front-end component (or application) integration solution, there are several ways:

  1. Build components and applications independently, generate chunk files, and use scripts to merge them after building.
  2. Develop components or applications independently during development, merge components and applications during integration, and finally generate a single application.
  3. is running, it loads the Runtime of the application, and then loads the corresponding application code and template.

* Portlet combination integration scheme

The portal component integration solution is similar to the second and third methods, based on the scaffolding tool independently developed components, packaged and constructed, and output static results. In the host environment, Vue components can be dynamically loaded according to the static resource path. If the homepage is understood as an application, then the whole export of the homepage theme package and the integration of the component results into the whole theme are very close to the second method mentioned above.

cli.cbedc959.gif

Module isolation

When multiple modules (components) are integrated on the same page, module isolation must be considered, including the isolation of sub-modules from the host environment, and the isolation between sub-modules.

Possible problems

  • Sub-modules may modify the logic of the host environment, thereby affecting the operation of the entire system, xss security issues;
  • The sub-modules can be accessed and modified each other, and it is difficult to locate the problem;
  • Style pollution between modules;

Application integration

In the front-end application integration micro, if you want to be independent and deploy applications with the decoupling technology stack, you have to consider sub-applications load runtime .

App EntryDescriptionadvantageDisadvantage
JS EntryThe sub-application types the resources into an entry script, and all the resources of the sub-application are packaged into a js bundler.The main application and sub-applications are built together to facilitate bundler optimization.1. The update of the sub-application will cause the entire main application to be updated, and the update cost is high. 2. The static resources of the sub-application need to be bundled as a bundler, and the loading efficiency is low
HTML EntryType the HTML of the sub-application as the entrance, and the main frame can obtain the static resources of the sub-application by fetch html, and at the same time plug the HTML document as a child node into the container of the main frame.Independent development of sub-applications, independent deployment and release;1. The network request cost is large. 2. The bundler construction and optimization are more difficult, such as public dependency extraction

js isolation

JavaScript sandbox
沙箱机制的核心是让局部的JavaScript运行时,对外部对象的访问和修改处在可控的范围内,即无论内部怎么运行,都不会影响外部的对象。通常在Node.js端可以采用`vm`模块,而对于浏览器,则需要结合`with`关键字和`window.Proxy`对象来实现浏览器端的沙箱。以下为简易的实现:
function sandbox(code) {
    code = 'with (sandbox) {' + code + '}';
    const fn = new Function('sandbox', code);
    return (sandbox) => {
        const proxy = new Proxy(sandbox, {
            has(target, key) {
                return true;
            },
            get(target, key, receiver) {
                if (key === Symbol.unscopables) {
                    return undefined;
                }
            }
        });
        return fn(proxy);
    }
}
let str = 'let a = 10;console.log(a)'
sandbox(str)({})
Web Worker
For specific content, please refer to the article Web Worker and JavaScript sandbox

The form of Web Worker sub-threads is also a natural sandbox isolation. It draws on the Browser-VM idea. In the compilation stage, each sub-application is wrapped with a layer of code that creates the Worker object through the Webpack plug-in, so that the sub-application runs on its corresponding In a single Worker instance, such as:

__WRAP_WORKER__(`/* 打包代码 */ }`);

function __WRAP_WORKER__(appCode) {
    var blob = new Blob([appCode]);
    var appWorker = new Worker(window.URL.createObjectURL(blob));
} 

But there are several flaws:

  • Does not support DOM operation, it must be implemented by postMessage notifying the UI main thread
  • Cannot access browser global objects such as window and document
  • Unable to access page global variables and functions, unable to call alert , confirm etc. BOM API

Module Federation - Webpack 5

webpack5-Module Federation Chinese document is defined as follows: Multiple independent builds can form an application. These independent builds do not depend on each other, so they can be developed and deployed separately. This is often referred to as a micro front end, but it is not limited to this.

In fact, MF is based on modules, which are essentially JS code fragments, which are chunks. In order to solve the dependency problem, the implementation of webpack5 is to rewrite the webpack_require.e that loads the chunk, so as to pre-load the dependency; in order to solve the sharing problem of modules, global variables are used to hook. But there are pros and cons:

  • Advantages: It can be loaded at runtime, and the shared code does not need to be manually packaged and built by yourself
  • Disadvantages: It may affect the performance of the page when it is running; you need to consider the version control of the module; the cost of old projects is relatively high;

css isolation

当主应用和子应用同屏渲染时,就可能会有一些样式会相互污染,如果要彻底隔离CSS污染,可以采用**CSS Module** 或者**命名空间**的方式,给每个子应用模块以特定前缀,即可保证不会互相干扰,可以采用webpack的postcss插件,在打包时**添加特定的前缀**。
而对于子应用与子应用之间的CSS隔离,采用**动态加载**,即在每次子应用加载时,将该应用所有的`link`和`style`内容进行标记,在应用卸载后,同步卸载页面上对应的`link`和`style`即可。
另一种推荐的方式是 **shadow DOM**,是可以彻底隔离 css 的一个思路。可将子应用包裹在 Shadow DOM 节点中,只需要将 [shadowRoot ](https://developer.mozilla.org/zh-CN/docs/Web/API/ShadowRoot)的 API 设置为 true。但**存在一些问题**,比如 Shadow DOM 的 css 隔离、dom 事件冒泡终止在 Shadow DOM 父节点的问题,会导致子应用内部在调用一些UI组件库的时候显示异常。

* Portlet module isolation scheme

The simple description is to use the isolation of vue components, including style scoped and component instance isolation, which is not a particularly complete consideration.

Because the portal excludes public dependencies such as UI component libraries and vue.js from the component scaffolding (webpack externals), all components use the same set of UI component libraries. On the one hand, it is for control the development cost and specification , on the other hand, it is also as much as possible the member logic simplification , each member logic function as a single .

However, the sub-module has the reference authority that the host environment depends on, which does not meet the isolation requirements. In addition, the sub-module and the host environment share a window object, and the space that can be used is greater, but the reason why it is open is that there is such a requirement in the real situation, for example, the sub-module needs to access the variables of the host environment ( The userName of the portal login? etc.). We try our best to pass the data through the prop of the dynamic component to communicate <component :prop="widget.option" ... /> , and try to restrict the internal access to the host by the means such as specification and lint as much as possible.

In terms of CSS style, it is relatively simple. Use the vue component <style scoped></style> to generate a unique data value for the component. If you want to change the style of the host UI component library, you can use the ::v-deep style to penetrate to set it, so that it will not affect the UI component styles of other modules.

Module communication

For separate modules, the communication mechanism of the message subscription (pub/sub) mode is very suitable. The event center Event is defined in the base application. Each micro-application registers the event separately, and the event is triggered when the event is triggered. The center distributes uniformly, which constitutes the basic communication mechanism.
image.png
You can introduce the Flux-based state management machine, Redux/Vuex, so that each sub-application maintains its own store.

qiankun inter-application communication scheme

The official inter-application communication method provided by qiankun-Actions communication, as shown in the following figure, first register observers to observer pool , and then modify globalState to trigger all observer functions to achieve the effect of communication between components.
image.png

* Portlet communication

The components of the portal are based on Vue.js components, so the communication mechanism also depends on the Vue component's own communication mechanism, that is, using the host environment this.$root.$widgetEventBus empty Vue instance as the message bus, and the components send and monitor events $emit/$on

to sum up

The above introduces the practice of portal portal application in visual construction and Low Code, and also introduces the related content of the micro front end of the community. Standing on the shoulders of giants, you will see that there are still many possible parts of the portal based on Vue components. Areas for improvement, such as component isolation, integration capabilities, runtime loading performance, etc. Of course, the choice of all solutions needs to be combined with actual scenarios and actual needs, comprehensive considerations, balance the pros and cons, there is no silver bullet!


【reference】


palmerye
1.2k 声望82 粉丝

焊得一手好PCB板的前端er