简体中文 | English
This solution will show you how to use React
stack in IE8, then you don't have to change the technology stack when the customer uses legacy browser. It uses ES6, Webpack, Babel, ESLint, Ant Design 1.x, React 16, Reach, Rematch, etc. See Reactie Todo.
Choose the shims and polyfills you need.
- es5-shim: A patch that provides all ES5 methods which can be faithfully emulated for the legacy browser;
- console-polyfill: Browser console polyfill. Makes it safe to run
console.log()
etc always; - @babel/polyfill: A patch emulates a full ES2015+ environment;
- es6-proxy-polyfill:
Proxy
polyfill based on ES3 supports IE8, Node.js, etc; - es6-promise: A polyfill of the ES6
Promise
; - bluebird: A full featured
Promise
library with unmatched performance; - fetch-ie8: A
window.fetch
JavaScript polyfill supporting IE8; - fetch-polyfill2: The
fetch
polyfill which supports all mainstream browsers, even IE6, IE7, IE8; - html5shiv: This library enables use of HTML5 sectioning elements in legacy Internet Explorer and provides basic HTML5 styling for Internet Explorer 6-9, Safari 4.x (and iPhone 3.x), and Firefox 3.x;
- matchmedia-polyfill: A polyfill for testing whether a CSS media type or media query applies;
- Respond.js: A fast & lightweight polyfill for min/max-width CSS3 Media Queries (for IE 6-8, and more);
- ...
- es5-shim: A patch emulates the ES5 environment;
- @babel/polyfill: A patch emulates the ES6+ environment;
- anujs: A React-like library, supports most features of React 16, works well in IE8, created by Shitou Nasami;
- reach: A React router library. I use the compatible version provided by anujs, which is modified to support IE8's hashchange;
- rematch: A state manager for React. Anujs also provided a compatible version;
- antd: A React UI framework. Antd 1.x is the last version that supports IE8.
Object.defineProperty
: It can't be emulated in IE8, you must not use this method;- ES Module: To avoid ES Module being transformed into
Object.defineProperty
, the preset@babel/preset-env
should be configured as follows;
{
loader: 'babel-loader',
options: {
presets: [
['@babel/preset-env', {
loose: true,
modules: 'commonjs',
}]
]
}
}
- Reserved Words: Use es3ify, es3ify-loader or UglifyJS to transform your code;
// Config
[
new UglifyJsPlugin({
uglifyOptions: {
ie8: true,
...
}
})
]
// Before
var obj = { default: 1 };
// After
var obj = { "default": 1 };
- Module Alias: Create aliases to
import
orrequire
certain modules more easily, for example usinganujs
instead ofReact
.
// Config
{
resolve: {
alias: {
'react': 'anujs/dist/ReactIE',
'react-dom': 'anujs/dist/ReactIE',
...
}
}
}
// Code
import React from 'react'; // `anujs` was loaded, actually
Error | Reason | Resolve |
---|---|---|
'JSON' is undefined |
Need to use IE8 Standards Mode | Add <!DOCTYPE html> and <meta http-equiv="X-UA-Compatible" content="IE=EDGE"/> |
无法获取未定义或 null 引用的属性“appendChild” |
document.head isn't exist in IE8 |
Add document.head = document.getElementsByTagName('head')[0] |
无法获取未定义或 null 引用的属性“focus” , happen in this.calendarInstance.focus() (Use antd 1.11.6) |
calendarInstance is undefined, caused by this.saveCalendarRef = refFn.bind(this, 'calendarInstance') |
Use this.saveCalendarRef = refFn.bind(this, 'calendarInstance', this) |
Object.prototype.propertyIsEnumerable: 'this' 不是 JavaScript 对象 , happen in the function getLocation of Reach (Use anujs 1.4.8) |
After transforming by Babel, getLocation uses Object.prototype.propertyIsEnumerable.call(location, prop) to judge whether window.location has certain properties, and it doesn't work in IE8 |
See anujs issue #344 |
Accessors not supported! |
Your code is transformed into Object.defineProperty .For example, Redux uses a library symbol-observable , which is transformed into Object.defineProperty |
Find it, and change it. I have rewritten the library symbol-observable |
IE8 sinks into endless loop, happen in the function isPlainObject of Redux |
isPlainObject uses the function getPrototypeOf of es5-shim to traverse the prototype chain, that causes endless loop |
See es5-shim issue #458 |