Skip to content

Instantly share code, notes, and snippets.

@flxxyz
Created April 22, 2020 09:26
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save flxxyz/95a5ff850c190ec88820ba353d870e5b to your computer and use it in GitHub Desktop.
Save flxxyz/95a5ff850c190ec88820ba353d870e5b to your computer and use it in GitHub Desktop.
开箱即用的ajax
! function (e) {
var r,
u,
t = [
'Object',
'Array',
'String',
'Number',
'Boolean',
'Function',
'RegExp',
'Date',
'Undefined',
'Null',
'Symbol',
'Blob',
'ArrayBuffer'
]
t.forEach(type => {
e[`is${type}`] = (p) => Object.prototype.toString.call(p).slice(8, -1) === type
})
u = function (data, masterKey = '') {
if (isObject(data)) {
let p = []
for (let [key, value] of Object.entries(data)) {
if (masterKey != '') {
key = `${masterKey}[${key}]`
}
p.push(`${u(value, key)}`)
}
return p.join('&')
} else {
if (Array.isArray(data)) {
return Array.from(data, value => u(value, `${masterKey}[]`)).join('&')
} else {
if (isString(data) || isNumber(data) || isBoolean(data)) {
return `${encodeURIComponent(masterKey)}=${encodeURIComponent(data.toString())}`
} else {
return ''
}
}
}
}
r = function (opts) {
opts = opts || {}
opts.method = (opts.method || 'get').toLocaleUpperCase()
opts.url = opts.url || ''
opts.async = opts.async || true
opts.timeout = opts.async ? (opts.timeout || 5000) : 0
opts.dataType = opts.async ? (opts.dataType || 'text') : ''
opts.data = opts.data || {}
opts.queryString = (opts.queryString || opts.qs) || {}
opts.header = opts.header || {}
opts.success = opts.success || function () {}
opts.fail = opts.fail || function (err) {
console.log('请求错误', err)
}
opts.complete = opts.complete || function () {}
opts.ontimeout = function (e) {
console.log('请求超时', e)
}
if (!opts.url || !isString(opts.url)) {
return
}
return new r.prototype.init(opts)
}
r.prototype.init = function (opts) {
this.blob = function (data) {
return new Blob([JSON.stringify(data)], {
type: 'text/plain'
})
}
var st = 0
var xhr = new XMLHttpRequest()
xhr.timeout = opts.timeout
xhr.responseType = opts.dataType
xhr.withCredentials = true
xhr.addEventListener('readystatechange', function () {
if (this.readyState === this.DONE) {
if ((new Date().getTime() - st) <= this.timeout) {
if (this.status >= 200 && this.status < 300) {
opts.success.call(undefined, this.response)
} else {
opts.fail.call(undefined, this)
}
}
}
})
xhr.addEventListener('load', opts.complete.bind(xhr))
xhr.addEventListener('timeout', opts.ontimeout.bind(xhr))
switch (opts.dataType) {
case 'blob':
console.log('[dataType] blob')
opts.data = this.blob(opt.data || {})
break;
case 'arraybuffer':
console.log('[dataType] arraybuffer')
break;
case 'json':
console.log('[dataType] json')
opts.header['Content-Type'] = 'application/json; charset=UTF-8'
opts.data = JSON.stringify(opts.data || {})
break;
default:
console.log('[dataType] default')
break;
}
switch (opts.method) {
case 'PUT':
break;
case 'PATCH':
break;
case 'COPY':
break;
case 'HEAD':
break;
case 'OPTIONS':
break;
case 'LINK':
break;
case 'DELETE':
break;
case 'POST':
console.log('[method] POST')
if (!(Object.keys(opts.header)
.map(v => v.toLocaleLowerCase())
.includes('content-type'))) {
opts.header['content-type'] = 'application/x-www-form-urlencoded'
opts.data = u(opts.data)
}
break;
case 'GET':
default:
console.log('[method] GET')
opts.data = null
break;
}
opts.queryString = u(opts.queryString)
opts.url += opts.queryString ? `?${opts.queryString}` : ''
xhr.open(opts.method, opts.url, opts.async)
Object.keys(opts.header).forEach(key => {
xhr.setRequestHeader(key, opts.header[key])
})
console.log('[send]', opts.url)
st = new Date().getTime()
xhr.send(opts.data)
}
e.$ajax = e.$request = r
}(window)
@flxxyz
Copy link
Author

flxxyz commented Apr 22, 2020

演示(restful)

GET

$request({
    method: 'get',
    url: '/api/user',
    success: function (res) {
        // res === XMLHttpRequest.response
    },
    complete: function () {
        // this === XMLHttpRequest
    }
})

POST

$request({
    method: 'post',
    url: '/api/user',
    data: {
        name: 'Tom',
        age: 18,
    },
    success: function (res) {
        console.log(res)
    }
})

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment