史上最强egg框架的error处理机制
最强搬运工
异常处理
框架文章阅读
得益于框架支持的异步编程模型,错误完全可以用 try catch
来捕获。在编写应用代码时,所有地方都可以直接用 try catch
来捕获异常。
按照正常代码写法,所有的异常都可以用这个方式进行捕获并处理,但是一定要注意一些特殊的写法可能带来的问题。打一个不太正式的比方,我们的代码全部都在一个异步调用链上,所有的异步操作都通过 await 串接起来了,但是只要有一个地方跳出了异步调用链,异常就捕获不到了。
如果 service.trade.check
方法中代码有问题,导致执行时抛出了异常,尽管框架会在最外层通过 try catch
统一捕获错误,但是由于 setImmediate
中的代码『跳出』了异步链,它里面的错误就无法被捕捉到了。因此在编写类似代码的时候一定要注意。
框架也考虑到了这类场景,提供了 ctx.runInBackground(scope)
辅助方法,通过它又包装了一个异步链,所有在这个 scope 里面的错误都会统一捕获。
class HomeController extends Controller {async buy () {const request = {};const config = await ctx.service.trade.buy(request);// 下单后需要进行一次核对,且不阻塞当前请求ctx.runInBackground(async () => {// 这里面的异常都会统统被 Backgroud 捕获掉,并打印错误日志await ctx.service.trade.check(request);});}
}
了保证异常可追踪,必须保证所有抛出的异常都是 Error 类型,因为只有 Error 类型才会带上堆栈信息,定位到问题。
框架通过 onerror 插件提供了统一的错误处理机制。对一个请求的所有处理方法(Middleware、Controller、Service)中抛出的任何异常都会被它捕获,并自动根据请求想要获取的类型返回不同类型的错误(基于 Content Negotiation)。
onerror 插件的配置中支持 errorPageUrl 属性,当配置了 errorPageUrl 时,一旦用户请求线上应用的 HTML 页面异常,就会重定向到这个地址。
请求需求的格式 | 环境 | errorPageUrl 是否配置 | 返回内容 |
---|---|---|---|
HTML & TEXT | local & unittest | - | onerror 自带的错误页面,展示详细的错误信息 |
HTML & TEXT | 其他 | 是 | 重定向到 errorPageUrl |
HTML & TEXT | 其他 | 否 | onerror 自带的没有错误信息的简单错误页(不推荐) |
JSON & JSONP | local & unittest | - | JSON 对象或对应的 JSONP 格式响应,带详细的错误信息 |
JSON & JSONP | 其他 | - | JSON 对象或对应的 JSONP 格式响应,不带详细的错误信息 |
// config/config.default.js
module.exports = {onerror: {// 线上页面发生异常时,重定向到这个页面上errorPageUrl: '/50x.html',},
};
尽管框架提供了默认的统一异常处理机制,但是应用开发中经常需要对异常时的响应做自定义,特别是在做一些接口开发的时候。框架自带的 onerror 插件支持自定义配置错误处理方法,可以覆盖默认的错误处理方法。
✋404
框架并不会将服务端返回的 404 状态当做异常来处理,但是框架提供了当响应为 404 且没有返回 body 时的默认响应。
-
当请求被框架判定为需要 JSON 格式的响应时,会返回一段 JSON:
{ "message": "Not Found" }
-
当请求被框架判定为需要 HTML 格式的响应时,会返回一段 HTML:
<h1>404 Not Found</h1>
但是能够支持配置,将默认的 HTML 请求的 404 响应重定向到指定的页面。
// config/config.default.js
module.exports = {notfound: {pageUrl: '/404.html',},
};
自定义响应404
// app/middleware/notfound_handler.js 中间件
module.exports = () => {return async function notFoundHandler(ctx, next) {await next();if (ctx.status === 404 && !ctx.body) {if (ctx.acceptJSON) {ctx.body = { error: 'Not Found' };} else {ctx.body = '<h1>Page Not Found</h1>';}}};
};
配置中间件:
// config/config.default.js
module.exports = {middleware: [ 'notfoundHandler' ],
};
统一错误处理——中间件的形式
Controller 和 Service 都有可能抛出异常,这也是我们推荐的编码方式,当发现客户端参数传递错误或者调用后端服务异常时,通过抛出异常的方式来进行中断。
- Controller 中
this.ctx.validate()
进行参数校验,失败抛出异常。 - Service 中调用
this.ctx.curl()
方法访问 CNode 服务,可能由于网络问题等原因抛出服务端异常。 - Service 中拿到 CNode 服务端返回的结果后,可能会收到请求调用失败的返回结果,此时也会抛出异常。
在 app/middleware
目录下新建一个 error_handler.js
的文件来新建一个 middleware
// app/middleware/error_handler.js
module.exports = () => {return async function errorHandler(ctx, next) {try {await next();} catch (err) {// 所有的异常都在 app 上触发一个 error 事件,框架会记录一条错误日志ctx.app.emit('error', err, ctx);const status = err.status || 500;// 生产环境时 500 错误的详细错误内容不返回给客户端,因为可能包含敏感信息const error = status === 500 && ctx.app.config.env === 'prod'? 'Internal Server Error': err.message;// 从 error 对象上读出各个属性,设置到响应中ctx.body = { error };if (status === 422) {ctx.body.detail = err.errors;}ctx.status = status;}};
};
加载中间件config/config.default.js
// config/config.default.js
module.exports = {// 加载 errorHandler 中间件middleware: [ 'errorHandler' ],// 只对 /api 前缀的 url 路径生效errorHandler: {match: '/api',},
};
对error的类型进行判断,返回自定义的message
- 框架级的错误,一般也不会丢给用户的,egg-onerror 那边兜底统一回复个信息即可,主要还是看日志来修复。
- 某些在你们业务中并不视为框架级的错误,是可以在 Service 层统一封装抛出的错误类型。
- 通用的错误可以在 egg-onerror 或者 自定义 Controller 基类里面提供
throwBizErr
这类的方式去处理。
应用自定义
- onerror 主要处理全局异常,这类基本都是未捕获异常,也就是应用开发者不知道哪里会抛异常,onerror 是用来兜底的。
- 业务错误一般是应用开发者已知的, 所以都会有对应的处理,常见的就是反回对应的错误文案。这些错误尤其不能出现在错误大盘上,应该使用其他的监控方式,比如 xxx 业务的成功率。
RFC:应用自定义 4xx 和 5xx 的方案
定制特殊响应的功能,而不是通过 302 跳转到其他地方。
兼容性的考虑
notfound throw 404 error
框架和应用都可以覆盖 app/onerror.js
来实现统一处理逻辑。
- 优先选择准确的 status handler
- 找不到就找 4xx,5xx 这种通用 handler
- 如果有 all,优先使用 all,否则根据 accepts 判断来选择 html,json
- 都找不到就找全局默认 onerror 处理
// app/onerror.jsmodule.exports = {'404': {* html(ctx, err) {// 这里可以使用 renderyield ctx.render('404.html');},* json(ctx, err) {// 不处理或者不配置或者返回 null, undefined,都会使用默认的 json 逻辑来处理},},'403': function* (ctx, err) {// all 的精简版本写法},'4xx': {* all(ctx, err) {// all 不区分 accepts,由开发者自行处理},},};
错误分为三种未捕获异常、系统异常、业务异常,以下是分类比较
定义 | 未捕获异常 | 系统异常 | 业务错误 |
---|---|---|---|
类名 | Error | xxxException | xxxBizError |
说明 | js 内置错误,未做任何处理 | 自己抛出的系统异常 | 自己抛出的业务异常 |
错误处理方 | 由 onerror 插件处理 | 业务可扩展处理 | 业务可扩展处理 |
可识别 | 否 | 是 | 是 |
属性扩展 | 否 | 是 | 是 |
所有的类均继承自Error类,并定义BaseError类,继承自 BaseError 的错误是可以被识别的,而其他三方继承 Error 的类都无法被识别。
类名只是用来区分三种错误,继承可以自定义
业务错误处理封装成插件,比如egg-bizerror:
npm上的解释:
usage:
// config/plugin.js
exports.bizerror = {enable: true,package: 'egg-bizerror',
};
// config/config.default.js
exports.bizerror = {breakDefault: false, // disable default error handler禁用默认错误处理sendClientAllParams: false, // return error bizParams to user,返回错误参数给用户interceptAllError: false, // handle all exception, not only bizError exception处理所有的异常,不仅是业务异常。
};
// config/errorcode.js
module.exports = {'USER_NOT_EXIST': {status: 400,code: '400' // override code value,覆盖code value。message: 'can`t find user info',errorPageUrl: '', // app will redirect this url when accepts is html addtion1: 'a', // any, will return to browser 附件性的},'NOT_FOUND': {errorPageUrl: (ctx, error) => {return '/404.html';}}'404': (ctx, error) => {ctx.redirect('/404.html');return false; // you can return false, break default logic,打断默认的逻辑}
}
API:
ctx.throwBizError(code, error, bizParams)–业务逻辑
throw an biz error
- code -
error.code
, defaultSYSTEM_EXCEPTION
, read errorcode config with this value when handle error. - error - error message or
Error
object. - bizParams -
error.bizParams
, extra data, can help you solve the problem.
bizParams还有下面的三个参数:
- bizParams.sendClient - object, this object will copy to the property
errors
of json object and send to client. - bizParams.code - it will cover
error.code
. - bizParams.log -
error.log
, if false, not log this error, defalut true.
// throw an error object
// error.code
// error.message
// error.log
// error.bizParams
// error.bizError
ctx.throwBizError('system_exception')
ctx.throwBizError(new Error())
ctx.throwBizError({ code: 'system_exception', log: false })
ctx.throwBizError('system_exception', { userId: 1, log: false })
ctx.throwBizError('system_exception', 'error message')
ctx.throwBizError('system_exception', new Error())
ctx.throwBizError(new Error(), { userId: 1, log: false })
ctx.throwBizError('system_exception', 'error message', { userId: 1, log: false })
try {this.ctx.body = {data: this.ctx.request.body,};throw new Error('hahahah');} catch (error) {this.ctx.throwBizError({ code: '-9999', userId: 1, log: false });
}
的結果是:
{"code":"-9999","message":"System Exception","errors":{"userId":1}}
-
ctx.responseBizError(error, bizParams)—返回响应
handle the error
- bizParams - supports the above
- bizParams.bizError - if you want the plugin to handle this error, you must be set
bizError: true
, otherwise, the plugin will throw this error.
第三种调用方法:
-
app.on(‘responseBizError’, (ctx, error) => {})
you can add listener to do some thing.
第四种重写:
- app.BizErrorHandler - default handler class, you can override it
example:
// app/service/user.js
module.exports = app => {class User extends app.Service {async getUserId() {let userInfo;try {userInfo = await this.getUser();} catch (error) {ctx.responseBizError(error, { bizError: true, code: 'USER_NOT_EXIST' })return;}if (!userInfo || !userInfo.id) {ctx.throwBizError('USER_NOT_EXIST');}return userInfo.id;}}return User;
};// app.js
// add handle logic
module.exports = app => {app.on('responseBizError', (ctx, error) => {if (error.bizParams && error.bizParams.bizType === 'getUser') {errorCount++;}});
};// app.js
// override default handler
module.exports = app => {app.BizErrorHandler = class extends app.BizErrorHandler {json(ctx, error, config) {ctx.body = {code: config.code,msg: config.message,};}}
};
egg-onerror:用来兜底
egg-onerror
默认在egg框架中。 但是你仍旧需要设置选项来匹配你的场景。.
errorPageUrl: String or Function
- 如果用户请求html页面在生产环境上,并抛出了未捕获的错误,他将定向到错误页面errorPageUrl
.accepts: Function
- 检测用户的请求json
orhtml
.all: Function
- 定制错误处理器 如果all
存在, 其他的将被忽略.html: Function
- 定制html错误处理器.text: Function
- 定制text错误处理器.json: Function
- 定制json错误处理器.jsonp: Function
- 定制jsonp错误处理器.
/ config.default.js
// errorPageUrl support funtion
exports.onerror = {errorPageUrl: (err, ctx) => ctx.errorPageUrl || '/500',
};// an accept detect function that mark all request with `x-requested-with=XMLHttpRequest` header accepts json.
function accepts(ctx) {if (ctx.get('x-requested-with') === 'XMLHttpRequest') return 'json';return 'html';
}
一般性错误处理的原则:
- egg-onerror 是框架做兜底的
- 你自己的处理,可以在 Controller / Service 等地方自己 catch
- 或者通过 Middleware 结合 match 来做范围的 catch
现在的错误处理插件是 egg-onerror,但这个插件主要是优雅处理未捕获异常,也就是了为了让应用不挂进行兜底,但是现在没有一种统一的业务错误处理方案。
业务校验:
比如参数校验、业务验证等等,这些并不属于异常,一般会在响应时转成对应的数据格式。常见的处理方式是接口返回错误,并在 response 转换
class User extends Controller {async show() {const error = this.check(this.params.id);if (error) {this.ctx.status = 422;this.ctx.body {message: error.message,};return;}// 继续处理}check(id) {if (!id) return { message: 'id is required' };}
}
异常类型的区分:
将已知异常和未捕获异常做差异化处理。
例如状态码未捕获时返回500,已知异常需要返回422等~
标准化响应:
如果业务抛出自定义的系统异常和业务错误,可直接在错误处理里面处理,未捕获异常在 onerror 中处理。
继承的错误可增加额外属性,比如 HttpError 可增加 status 属性作为处理函数的输入。
字段:
- 标准字段包括
name: 一般为类名,如 NotFoundError
message: 错误的具体信息,可读的,如 404 Not Found
code: 大写的字符串,描述错误,如 NOT_FOUND
- http 扩展
status: http 状态码,400
- 错误处理的一般原则:
错误处理是最核心的功能,有如下规则
- 未捕获异常不做处理,向上抛
- 系统异常会打印错误日志,但是会按照标准格式 format
- 业务异常根据标准格式 format
- 根据内容协商,返回对应的 format 值
- 可自定义 format
egg-erros
errors for eggjs
提供两种类型的错误:错误,异常
创建Error
const { EggError, EggException } = require('egg-errors');
let err = new EggError('egg error');
console.log(EggError.getType(err)); // ERROR
创建Exception
err = new EggException('egg exception');
console.log(EggException.getType(err)); // EXCEPTION
也能引入一个错误从普通的错误对象
err = new Error('normal error');
console.log(EggError.getType(err)); // BUILTIN
err = EggError.from(err);
console.log(EggError.getType(err)); // ERROR
错误也能被扩展:
const { EggBaseError } = require('egg-errors');class CustomError extends EggBaseError {constructor(message) {super({ message, code: 'CUSTOM_CODE' });}}
或者使用ts能够扩展错误选项:
import { EggBaseError, ErrorOptions } from 'egg-errors';class CustomErrorOptions extends ErrorOptions {public data: object;
}
class CustomError extends EggBaseError<CustomErrorOptions> {public data: object;protected options: CustomErrorOptions;constructor(options?: CustomErrorOptions) {super(options);this.data = this.options.data;}
}
建议使用message代替options在用户的地方,他能够很简单的被开发者理解。
HTTP错误,是固有的错误,转变成400~500状态码的错误对象,HTTPError扩展EggBaseError提供了两个,status
和headers
.
const { ForbiddenError } = require('egg-errors');
const err = new ForbiddenError('your request is forbidden');
console.log(err.status); // 403
可获得的错误:
BaseError
|- EggBaseError
| |- EggError
| |- HttpError
| | |- NotFoundError
| | `- ...
| `- CustomError
`- EggBaseException|- EggException`- CustomException
RFC:How To Create An Error
前置资料:
所有由egg和egg插件以前的已知的error异常,都需要规范err.code。
意见建议稿:
- built-in Error
const errors = require('egg').errors;
const err = new errors.TypeError('ERR_EGG_SOME_ERROR_CODE_STRING', 'Some error haha');
console.log(err.code); // 'ERR_EGG_SOME_ERROR_CODE_STRING'
- custom Error
const errors = require('egg').errors;// 使用'ERR_EGG_MY_ERROR'注册一个新的子类
// 如果'ERR_EGG_MY_ERROR'存在, 将抛出一个类型错误,错误码是 'ERR_EGG_DUPLICATE_CODE'
errors.E('ERR_EGG_MY_ERROR', TypeError);const err = new errors.ERR_EGG_MY_ERROR('my error here');
console.log(err.name); // 'TypeError'
console.log(err.code); // 'ERR_EGG_MY_ERROR'
message & code✋
错误包含两个信息,message&code,message是能够改变的,但是他不将有大的改变,它有补丁或者微小的变化,代码首次出现后应保持稳定。
天猪大佬的话:
- 规范化错误名
- 报错提示可以 i18n
- 便于开发者 google 检索报错
- 可以提供类似 angular 这样的指引: [https://docs.angularjs.org/error/compile/baddir,即](https://docs.angularjs.org/error/compile/baddir,即](https://docs.angularjs.org/error/compile/baddir,即](https://docs.angularjs.org/error/compile/baddir%EF%BC%8C%E5%8D%B3) error 输出简单的提示,并输出一条链接,开发者点击后可以访问官网看详细的指引。
koa中的ctx( ctx.throw() )
koa context包装了request和response对象在,并提供了非常有用的方法来写api和web应用。这些操作疆场用在HTTP服务开发,在这个级别上添加而不是更高级别的框架,迫使中间件执行这个普通的函数。
一个context创建每个request,在中间件中医用座位接收者或者ctx识别,示例:
app.use(async ctx => {ctx; // is the Contextctx.request; // is a Koa Requestctx.response; // is a Koa Response
});
很多context的存取和方法都可表示为ctx.request
orctx.response
,为了使用起来方便,是相似的。ctx.type
&ctx.length
代表着response
,ctx.path
&ctx.method
代表着request
ctx.req
ctx.res
避免使用node中的属性:
res.statusCode
res.writeHead()
res.write()
res.end()
ctx.request
&ctx.response
是koa中的object
ctx.state
推荐的命名空间,通过中间件和前端视图来进行传递信息。
ctx.state.user = await User.find(id);
ctx.app
ctx.cookies.get(name[,options])
signed
cookie应该被签名
koa使用cookie模块选项简单通过。
ctx.cookies.set(name,value,[options])
设置cookie得键值对的选项:
maxAge
以毫秒为单位设置过期时间signed
签名cookie的值expires
一个日期为cookie的满期path
cookie path,/'
by defaultdomain
cookie域secure
secure cookiehttpOnly
server-accessible cookie, true by defaultoverwrite
一个boolean值,是否覆盖以前设置的同名cookie,默认为false,如果设置为true,所有的cookie都会被同名的替代,无论是path还是域
ctx.throw([status,msg,propertioes])
抛出错误,默认是500,
ctx.throw(400);
ctx.throw(400, 'name required');
ctx.throw(400, 'name required', { user: user });
相同的效力:
const err = new Error('name required');
err.status = 400;
err.expose = true;
throw err;
这是用户级的错误,并使用err.expose标记,消息适合客户端的响应,这通常不是错误信息,因为不想泄露信息。
ctx.throw(401, 'access_denied', { user: user });
您可以选择传递一个属性对象,该对象按原样合并到错误中,对于装饰向上游请求者报告的机器友好错误很有用。
ctx.assert(value,[status],[msg],[properties])
ctx.assert(ctx.state.user, 401, 'User not found. Please login!');
ctx.response
能够设为ctx.response=false
如果要写入原始res对象而不是让Koa为您处理响应,请使用此选项。
request aliases
ctx.header
ctx.headers
ctx.method
ctx.method=
ctx.url
ctx.url=
ctx.originalUrl
ctx.origin
ctx.href
ctx.path
ctx.path=
ctx.query
ctx.query=
ctx.querystring
ctx.querystring=
ctx.host
ctx.hostname
ctx.fresh
ctx.stale
ctx.socket
ctx.protocol
ctx.secure
ctx.ip
ctx.ips
ctx.subdomains
ctx.is()
ctx.accepts()
ctx.acceptsEncodings()
ctx.acceptsCharsets()
ctx.acceptsLanguages()
ctx.get()
response aliases
ctx.body
ctx.body=
ctx.status
ctx.status=
ctx.message
ctx.message=
ctx.length=
ctx.length
ctx.type=
ctx.type
ctx.headerSent
ctx.redirect()
ctx.attachment()
ctx.set()
ctx.append()
ctx.remove()
ctx.lastModified=
ctx.etag=
2018年11月22日
javascript中的Error知识
- 通过Error的构造器可以创建一个错误对象。当运行时错误产生时,Error的实例对象会被抛出。
Error对象也可用于用户自定义的异常的基础对象
new Error([message[,filename[,lineNumber]]])
filename:默认是调用Error构造器代码所在的文件 的名字
lineNumber:默认是调用Error构造器代码所在的文件的行号
- 描述:
当代码运行时的发生错误,会创建新的Error对象,并将其抛出。
- 除了通用的Error构造函数外,JavaScript还有6个其他类型的错误构造函数。
EvalError
:创建一个error实例,表示错误的原因:与 eval()
有关。
InternalError
:创建一个代表Javascript引擎内部错误的异常抛出的实例。 如: “递归太多”.
RangeError
:创建一个error实例,表示错误的原因:数值变量或参数超出其有效范围.
ReferenceError
:创建一个error实例,表示错误的原因:无效引用。
SyntaxError
:创建一个error实例,表示错误的原因:eval()
在解析代码的过程中发生的语法错误。
TypeError
:创建一个error实例,表示错误的原因:变量或参数不属于有效类型。
URIError
:创建一个error实例,表示错误的原因:给 encodeURI()
或 decodeURl()
传递的参数无效。
- 标准属性:
Error.prototype.constructor
Error.prototype.message
Error.prototype.name
厂家扩展:
Microsoft
Error.prototype.description
类似于message
Error.prototype.number
错误码
Mozilla
Error.prototype.fileName
产生该错误的文件名
Error.prototype.lineNumber
产生该错误的行号
Error.prototype.columnNumber
产生该错误的列号。
Error.prototype.stack
错误堆栈
- 方法
Error.prototype.toSource()
返回一个包含特定 Error
对象的源代码字符串,你可以用该值新建一个新的对象,重写自 Object.prototype.toSource()
方法。
Error.prototype.toString()
返回一个表示该对象的字符串,重写自 Object.prototype.toString()
方法
处理基本错误
try {throw new Error("Whoops!");
} catch (e) {alert(e.name + ": " + e.message);
}
处理特定的错误:
判断异常的类型来特定处理某一类的异常,即判断 constructor
属性,当使用现代Javascript引擎时,可使用instanceof
关键字:
try {foo.bar();
} catch (e) {if (e instanceof EvalError) {alert(e.name + ": " + e.message);} else if (e instanceof RangeError) {alert(e.name + ": " + e.message);}// ... etc
}
共有7个类型的错误构造函数,上述。
自定义异常类型:
自定义基于Error的异常类型,使得你能够 throw new MyError() 并可以使用 instanceof MyError
来检查某个异常的类型. 这种需求的通用解决方法如下.
注意,在FireFox中抛出自定义类型的异常会显示不正确的行号和文件名。
// Create a new object, that prototypally inherits from the Error constructor.
function MyError(message) {this.name = 'MyError';this.message = message || 'Default Message'; this.stack = (new Error()).stack;
}
MyError.prototype = Object.create(Error.prototype);
MyError.prototype.constructor = MyError;try {throw new MyError();
} catch (e) {console.log(e.name); // 'MyError'console.log(e.message); // 'Default Message'
}try {throw new MyError('custom message');
} catch (e) {console.log(e.name); // 'MyError'console.log(e.message); // 'custom message'
}
如若内容造成侵权/违法违规/事实不符,请联系编程学习网邮箱:809451989@qq.com进行投诉反馈,一经查实,立即删除!
相关文章
- Angular集成Sentry
本文档使用Angular来指代Angular 2。 sentry / browser本身会报告从您的应用程序触发的任何未捕获的异常。 此外, sentry / browser可以配置为捕获通过 angular / core / ErrorHandler组件报告的任何Angular特定(2.x)异常。 import { Brows…...
2024/4/12 6:14:45 - 埋线双眼皮做完图片
...
2024/4/12 6:15:09 - 埋线双眼皮做完内双
...
2024/4/12 6:14:39 - angular分类的那种点击
先说一种最直接了当的不需要js控制,方法一:直接在用ng-class就可以控制: <p ng-click"state1;" ng-class"{active:state1}">浮伤年华</p> <p ng-click"state2;" ng-class"{active:state2}…...
2024/4/12 6:15:03 - 埋线双眼皮做完好吓人
...
2024/4/16 23:08:44 - 埋线双眼皮做深了图片
...
2024/4/12 6:15:03 - 埋线双眼皮做三次
...
2024/4/11 17:28:44 - 【Web加密系列:一】手把手带你入门 Spring Security!
Spring Security 是 Spring 家族中的一个安全管理框架,实际上,在 Spring Boot 出现之前,Spring Security 就已经发展了多年了,但是使用的并不多,安全管理这个领域,一直是 Shiro 的天下。相对于 Shiro,在 SSM/SSH 中整合 Spring Security 都是比较麻烦的操作,所以,Spri…...
2024/4/19 18:56:27 - 埋线双眼皮做了30年了
...
2024/4/20 15:20:12 - 埋线双眼皮做宽的图片
...
2024/4/20 15:20:11 - 埋线双眼皮做过三次了
...
2024/4/20 15:20:09 - 埋线双眼皮做短了
...
2024/4/20 15:20:08 - 使用自定义关联实体类,无法接收参数
在项目中,页面使用的angular entity后面跟的是Specification 自定义实体类的名称是tbSpecification 导致控制层接收不到参数 结果在服务层中,for循环这里报了空指针异常 结果将页面的Specification改为和实体类一样的tbSpecification后成功接收到页面传过来的参数....
2024/4/20 15:20:07 - 埋线双眼皮做的太宽了
...
2024/4/20 15:20:06 - 埋线双眼皮做成了三层
...
2024/4/20 15:20:06 - [前端自动化]grunt的简单使用
前言 现在前端自动化已经是家常便饭,各种工具也是层出不穷,grunt、gulp、webpack是应用最广的三种工具,虽然grunt看似已垂垂老矣,但是以前写的很多项目一直用的就是grunt,温故方能知新,这里把grunt的基本操…...
2024/4/12 17:08:21 - 2018前端开发值得关注的技术趋势--摘抄
1.前言 2017悄然过去,2018已经来到。人在进步,技术在发展。2018年前端有哪些领域,技术值得关注,哪些技术会兴起,哪些技术会没落。下面就我个人的判断进行一个预测判断,希望能对大家起到一个参考作用&#x…...
2024/4/12 6:16:03 - AngularJS实践(介绍)
公共的部分抽取成服务,让控制层来调用,而不是继承 html: <!doctype html> <html ng-app"MyModule"> //相当于java 中的main函数<head><meta charset"utf-8"></head><body><hello></…...
2024/4/18 8:11:00 - 前端基础技术总结
1.如何理解 DOCTYPE? 声明位于文档中的最前面的位置,处于标签之前。此标签可告知浏览器文档使用哪种HTML或XHTML规范。 该标签可声明三种DTD类型,分别表示严格版本、过渡版本以及基于框架的HTML版本。 的用法: 解析:在上面的声明…...
2024/4/13 15:20:26 - 埋线双眼皮总肿怎么办
...
2024/4/20 10:37:08
最新文章
- 【鸿蒙NEXT】web组件debug模式
官方文档 使用Devtools工具调试前端页面 打开web debug模式 webview.WebviewController.setWebDebuggingAccess(true)chrome 访问 chrome://inspect/#devices Discover network targets 中添加 localhost:9222 创建cat.sh name$(hdc shell ps -ef | grep com.cib.qdzg | …...
2024/4/20 17:28:21 - 梯度消失和梯度爆炸的一些处理方法
在这里是记录一下梯度消失或梯度爆炸的一些处理技巧。全当学习总结了如有错误还请留言,在此感激不尽。 权重和梯度的更新公式如下: w w − η ⋅ ∇ w w w - \eta \cdot \nabla w ww−η⋅∇w 个人通俗的理解梯度消失就是网络模型在反向求导的时候出…...
2024/3/20 10:50:27 - javaWeb网上零食销售系统
1 绪 论 目前,我国的网民数量已经达到7.31亿人,随着互联网购物和互联网支付的普及,使得人类的经济活动进入了一个崭新的时代。淘宝,京东等网络消费平台功能的日益完善,使得人们足不出户就可以得到自己想要的东西。如今…...
2024/4/17 15:16:52 - 解析大语言模型训练三阶段
大语言模型的训练过程一般包括3个阶段:预训练(Pre-training)、SFT(有监督的微调,Supervised-Finetuning)以及RLHF(基于人类反馈的强化学习,Reinforcement Learning from Human Feedb…...
2024/4/17 22:18:45 - 【外汇早评】美通胀数据走低,美元调整
原标题:【外汇早评】美通胀数据走低,美元调整昨日美国方面公布了新一期的核心PCE物价指数数据,同比增长1.6%,低于前值和预期值的1.7%,距离美联储的通胀目标2%继续走低,通胀压力较低,且此前美国一季度GDP初值中的消费部分下滑明显,因此市场对美联储后续更可能降息的政策…...
2024/4/19 14:24:02 - 【原油贵金属周评】原油多头拥挤,价格调整
原标题:【原油贵金属周评】原油多头拥挤,价格调整本周国际劳动节,我们喜迎四天假期,但是整个金融市场确实流动性充沛,大事频发,各个商品波动剧烈。美国方面,在本周四凌晨公布5月份的利率决议和新闻发布会,维持联邦基金利率在2.25%-2.50%不变,符合市场预期。同时美联储…...
2024/4/19 18:20:22 - 【外汇周评】靓丽非农不及疲软通胀影响
原标题:【外汇周评】靓丽非农不及疲软通胀影响在刚结束的周五,美国方面公布了新一期的非农就业数据,大幅好于前值和预期,新增就业重新回到20万以上。具体数据: 美国4月非农就业人口变动 26.3万人,预期 19万人,前值 19.6万人。 美国4月失业率 3.6%,预期 3.8%,前值 3…...
2024/4/19 11:57:31 - 【原油贵金属早评】库存继续增加,油价收跌
原标题:【原油贵金属早评】库存继续增加,油价收跌周三清晨公布美国当周API原油库存数据,上周原油库存增加281万桶至4.692亿桶,增幅超过预期的74.4万桶。且有消息人士称,沙特阿美据悉将于6月向亚洲炼油厂额外出售更多原油,印度炼油商预计将每日获得至多20万桶的额外原油供…...
2024/4/19 11:57:31 - 【外汇早评】日本央行会议纪要不改日元强势
原标题:【外汇早评】日本央行会议纪要不改日元强势近两日日元大幅走强与近期市场风险情绪上升,避险资金回流日元有关,也与前一段时间的美日贸易谈判给日本缓冲期,日本方面对汇率问题也避免继续贬值有关。虽然今日早间日本央行公布的利率会议纪要仍然是支持宽松政策,但这符…...
2024/4/19 11:57:52 - 【原油贵金属早评】欧佩克稳定市场,填补伊朗问题的影响
原标题:【原油贵金属早评】欧佩克稳定市场,填补伊朗问题的影响近日伊朗局势升温,导致市场担忧影响原油供给,油价试图反弹。此时OPEC表态稳定市场。据消息人士透露,沙特6月石油出口料将低于700万桶/日,沙特已经收到石油消费国提出的6月份扩大出口的“适度要求”,沙特将满…...
2024/4/19 11:57:53 - 【外汇早评】美欲与伊朗重谈协议
原标题:【外汇早评】美欲与伊朗重谈协议美国对伊朗的制裁遭到伊朗的抗议,昨日伊朗方面提出将部分退出伊核协议。而此行为又遭到欧洲方面对伊朗的谴责和警告,伊朗外长昨日回应称,欧洲国家履行它们的义务,伊核协议就能保证存续。据传闻伊朗的导弹已经对准了以色列和美国的航…...
2024/4/19 11:58:14 - 【原油贵金属早评】波动率飙升,市场情绪动荡
原标题:【原油贵金属早评】波动率飙升,市场情绪动荡因中美贸易谈判不安情绪影响,金融市场各资产品种出现明显的波动。随着美国与中方开启第十一轮谈判之际,美国按照既定计划向中国2000亿商品征收25%的关税,市场情绪有所平复,已经开始接受这一事实。虽然波动率-恐慌指数VI…...
2024/4/19 11:58:20 - 【原油贵金属周评】伊朗局势升温,黄金多头跃跃欲试
原标题:【原油贵金属周评】伊朗局势升温,黄金多头跃跃欲试美国和伊朗的局势继续升温,市场风险情绪上升,避险黄金有向上突破阻力的迹象。原油方面稍显平稳,近期美国和OPEC加大供给及市场需求回落的影响,伊朗局势并未推升油价走强。近期中美贸易谈判摩擦再度升级,美国对中…...
2024/4/20 7:40:48 - 【原油贵金属早评】市场情绪继续恶化,黄金上破
原标题:【原油贵金属早评】市场情绪继续恶化,黄金上破周初中国针对于美国加征关税的进行的反制措施引发市场情绪的大幅波动,人民币汇率出现大幅的贬值动能,金融市场受到非常明显的冲击。尤其是波动率起来之后,对于股市的表现尤其不安。隔夜美国股市出现明显的下行走势,这…...
2024/4/19 11:58:39 - 【外汇早评】美伊僵持,风险情绪继续升温
原标题:【外汇早评】美伊僵持,风险情绪继续升温昨日沙特两艘油轮再次发生爆炸事件,导致波斯湾局势进一步恶化,市场担忧美伊可能会出现摩擦生火,避险品种获得支撑,黄金和日元大幅走强。美指受中美贸易问题影响而在低位震荡。继5月12日,四艘商船在阿联酋领海附近的阿曼湾、…...
2024/4/19 11:58:51 - 【原油贵金属早评】贸易冲突导致需求低迷,油价弱势
原标题:【原油贵金属早评】贸易冲突导致需求低迷,油价弱势近日虽然伊朗局势升温,中东地区几起油船被袭击事件影响,但油价并未走高,而是出于调整结构中。由于市场预期局势失控的可能性较低,而中美贸易问题导致的全球经济衰退风险更大,需求会持续低迷,因此油价调整压力较…...
2024/4/20 3:12:02 - 氧生福地 玩美北湖(上)——为时光守候两千年
原标题:氧生福地 玩美北湖(上)——为时光守候两千年一次说走就走的旅行,只有一张高铁票的距离~ 所以,湖南郴州,我来了~ 从广州南站出发,一个半小时就到达郴州西站了。在动车上,同时改票的南风兄和我居然被分到了一个车厢,所以一路非常愉快地聊了过来。 挺好,最起…...
2024/4/19 11:59:15 - 氧生福地 玩美北湖(中)——永春梯田里的美与鲜
原标题:氧生福地 玩美北湖(中)——永春梯田里的美与鲜一觉醒来,因为大家太爱“美”照,在柳毅山庄去寻找龙女而错过了早餐时间。近十点,向导坏坏还是带着饥肠辘辘的我们去吃郴州最富有盛名的“鱼头粉”。说这是“十二分推荐”,到郴州必吃的美食之一。 哇塞!那个味美香甜…...
2024/4/19 11:59:23 - 氧生福地 玩美北湖(下)——奔跑吧骚年!
原标题:氧生福地 玩美北湖(下)——奔跑吧骚年!让我们红尘做伴 活得潇潇洒洒 策马奔腾共享人世繁华 对酒当歌唱出心中喜悦 轰轰烈烈把握青春年华 让我们红尘做伴 活得潇潇洒洒 策马奔腾共享人世繁华 对酒当歌唱出心中喜悦 轰轰烈烈把握青春年华 啊……啊……啊 两…...
2024/4/19 11:59:44 - 扒开伪装医用面膜,翻六倍价格宰客,小姐姐注意了!
原标题:扒开伪装医用面膜,翻六倍价格宰客,小姐姐注意了!扒开伪装医用面膜,翻六倍价格宰客!当行业里的某一品项火爆了,就会有很多商家蹭热度,装逼忽悠,最近火爆朋友圈的医用面膜,被沾上了污点,到底怎么回事呢? “比普通面膜安全、效果好!痘痘、痘印、敏感肌都能用…...
2024/4/19 11:59:48 - 「发现」铁皮石斛仙草之神奇功效用于医用面膜
原标题:「发现」铁皮石斛仙草之神奇功效用于医用面膜丽彦妆铁皮石斛医用面膜|石斛多糖无菌修护补水贴19大优势: 1、铁皮石斛:自唐宋以来,一直被列为皇室贡品,铁皮石斛生于海拔1600米的悬崖峭壁之上,繁殖力差,产量极低,所以古代仅供皇室、贵族享用 2、铁皮石斛自古民间…...
2024/4/19 12:00:06 - 丽彦妆\医用面膜\冷敷贴轻奢医学护肤引导者
原标题:丽彦妆\医用面膜\冷敷贴轻奢医学护肤引导者【公司简介】 广州华彬企业隶属香港华彬集团有限公司,专注美业21年,其旗下品牌: 「圣茵美」私密荷尔蒙抗衰,产后修复 「圣仪轩」私密荷尔蒙抗衰,产后修复 「花茵莳」私密荷尔蒙抗衰,产后修复 「丽彦妆」专注医学护…...
2024/4/19 16:57:22 - 广州械字号面膜生产厂家OEM/ODM4项须知!
原标题:广州械字号面膜生产厂家OEM/ODM4项须知!广州械字号面膜生产厂家OEM/ODM流程及注意事项解读: 械字号医用面膜,其实在我国并没有严格的定义,通常我们说的医美面膜指的应该是一种「医用敷料」,也就是说,医用面膜其实算作「医疗器械」的一种,又称「医用冷敷贴」。 …...
2024/4/19 12:00:25 - 械字号医用眼膜缓解用眼过度到底有无作用?
原标题:械字号医用眼膜缓解用眼过度到底有无作用?医用眼膜/械字号眼膜/医用冷敷眼贴 凝胶层为亲水高分子材料,含70%以上的水分。体表皮肤温度传导到本产品的凝胶层,热量被凝胶内水分子吸收,通过水分的蒸发带走大量的热量,可迅速地降低体表皮肤局部温度,减轻局部皮肤的灼…...
2024/4/19 12:00:40 - 配置失败还原请勿关闭计算机,电脑开机屏幕上面显示,配置失败还原更改 请勿关闭计算机 开不了机 这个问题怎么办...
解析如下:1、长按电脑电源键直至关机,然后再按一次电源健重启电脑,按F8健进入安全模式2、安全模式下进入Windows系统桌面后,按住“winR”打开运行窗口,输入“services.msc”打开服务设置3、在服务界面,选中…...
2022/11/19 21:17:18 - 错误使用 reshape要执行 RESHAPE,请勿更改元素数目。
%读入6幅图像(每一幅图像的大小是564*564) f1 imread(WashingtonDC_Band1_564.tif); subplot(3,2,1),imshow(f1); f2 imread(WashingtonDC_Band2_564.tif); subplot(3,2,2),imshow(f2); f3 imread(WashingtonDC_Band3_564.tif); subplot(3,2,3),imsho…...
2022/11/19 21:17:16 - 配置 已完成 请勿关闭计算机,win7系统关机提示“配置Windows Update已完成30%请勿关闭计算机...
win7系统关机提示“配置Windows Update已完成30%请勿关闭计算机”问题的解决方法在win7系统关机时如果有升级系统的或者其他需要会直接进入一个 等待界面,在等待界面中我们需要等待操作结束才能关机,虽然这比较麻烦,但是对系统进行配置和升级…...
2022/11/19 21:17:15 - 台式电脑显示配置100%请勿关闭计算机,“准备配置windows 请勿关闭计算机”的解决方法...
有不少用户在重装Win7系统或更新系统后会遇到“准备配置windows,请勿关闭计算机”的提示,要过很久才能进入系统,有的用户甚至几个小时也无法进入,下面就教大家这个问题的解决方法。第一种方法:我们首先在左下角的“开始…...
2022/11/19 21:17:14 - win7 正在配置 请勿关闭计算机,怎么办Win7开机显示正在配置Windows Update请勿关机...
置信有很多用户都跟小编一样遇到过这样的问题,电脑时发现开机屏幕显现“正在配置Windows Update,请勿关机”(如下图所示),而且还需求等大约5分钟才干进入系统。这是怎样回事呢?一切都是正常操作的,为什么开时机呈现“正…...
2022/11/19 21:17:13 - 准备配置windows 请勿关闭计算机 蓝屏,Win7开机总是出现提示“配置Windows请勿关机”...
Win7系统开机启动时总是出现“配置Windows请勿关机”的提示,没过几秒后电脑自动重启,每次开机都这样无法进入系统,此时碰到这种现象的用户就可以使用以下5种方法解决问题。方法一:开机按下F8,在出现的Windows高级启动选…...
2022/11/19 21:17:12 - 准备windows请勿关闭计算机要多久,windows10系统提示正在准备windows请勿关闭计算机怎么办...
有不少windows10系统用户反映说碰到这样一个情况,就是电脑提示正在准备windows请勿关闭计算机,碰到这样的问题该怎么解决呢,现在小编就给大家分享一下windows10系统提示正在准备windows请勿关闭计算机的具体第一种方法:1、2、依次…...
2022/11/19 21:17:11 - 配置 已完成 请勿关闭计算机,win7系统关机提示“配置Windows Update已完成30%请勿关闭计算机”的解决方法...
今天和大家分享一下win7系统重装了Win7旗舰版系统后,每次关机的时候桌面上都会显示一个“配置Windows Update的界面,提示请勿关闭计算机”,每次停留好几分钟才能正常关机,导致什么情况引起的呢?出现配置Windows Update…...
2022/11/19 21:17:10 - 电脑桌面一直是清理请关闭计算机,windows7一直卡在清理 请勿关闭计算机-win7清理请勿关机,win7配置更新35%不动...
只能是等着,别无他法。说是卡着如果你看硬盘灯应该在读写。如果从 Win 10 无法正常回滚,只能是考虑备份数据后重装系统了。解决来方案一:管理员运行cmd:net stop WuAuServcd %windir%ren SoftwareDistribution SDoldnet start WuA…...
2022/11/19 21:17:09 - 计算机配置更新不起,电脑提示“配置Windows Update请勿关闭计算机”怎么办?
原标题:电脑提示“配置Windows Update请勿关闭计算机”怎么办?win7系统中在开机与关闭的时候总是显示“配置windows update请勿关闭计算机”相信有不少朋友都曾遇到过一次两次还能忍但经常遇到就叫人感到心烦了遇到这种问题怎么办呢?一般的方…...
2022/11/19 21:17:08 - 计算机正在配置无法关机,关机提示 windows7 正在配置windows 请勿关闭计算机 ,然后等了一晚上也没有关掉。现在电脑无法正常关机...
关机提示 windows7 正在配置windows 请勿关闭计算机 ,然后等了一晚上也没有关掉。现在电脑无法正常关机以下文字资料是由(历史新知网www.lishixinzhi.com)小编为大家搜集整理后发布的内容,让我们赶快一起来看一下吧!关机提示 windows7 正在配…...
2022/11/19 21:17:05 - 钉钉提示请勿通过开发者调试模式_钉钉请勿通过开发者调试模式是真的吗好不好用...
钉钉请勿通过开发者调试模式是真的吗好不好用 更新时间:2020-04-20 22:24:19 浏览次数:729次 区域: 南阳 > 卧龙 列举网提醒您:为保障您的权益,请不要提前支付任何费用! 虚拟位置外设器!!轨迹模拟&虚拟位置外设神器 专业用于:钉钉,外勤365,红圈通,企业微信和…...
2022/11/19 21:17:05 - 配置失败还原请勿关闭计算机怎么办,win7系统出现“配置windows update失败 还原更改 请勿关闭计算机”,长时间没反应,无法进入系统的解决方案...
前几天班里有位学生电脑(windows 7系统)出问题了,具体表现是开机时一直停留在“配置windows update失败 还原更改 请勿关闭计算机”这个界面,长时间没反应,无法进入系统。这个问题原来帮其他同学也解决过,网上搜了不少资料&#x…...
2022/11/19 21:17:04 - 一个电脑无法关闭计算机你应该怎么办,电脑显示“清理请勿关闭计算机”怎么办?...
本文为你提供了3个有效解决电脑显示“清理请勿关闭计算机”问题的方法,并在最后教给你1种保护系统安全的好方法,一起来看看!电脑出现“清理请勿关闭计算机”在Windows 7(SP1)和Windows Server 2008 R2 SP1中,添加了1个新功能在“磁…...
2022/11/19 21:17:03 - 请勿关闭计算机还原更改要多久,电脑显示:配置windows更新失败,正在还原更改,请勿关闭计算机怎么办...
许多用户在长期不使用电脑的时候,开启电脑发现电脑显示:配置windows更新失败,正在还原更改,请勿关闭计算机。。.这要怎么办呢?下面小编就带着大家一起看看吧!如果能够正常进入系统,建议您暂时移…...
2022/11/19 21:17:02 - 还原更改请勿关闭计算机 要多久,配置windows update失败 还原更改 请勿关闭计算机,电脑开机后一直显示以...
配置windows update失败 还原更改 请勿关闭计算机,电脑开机后一直显示以以下文字资料是由(历史新知网www.lishixinzhi.com)小编为大家搜集整理后发布的内容,让我们赶快一起来看一下吧!配置windows update失败 还原更改 请勿关闭计算机&#x…...
2022/11/19 21:17:01 - 电脑配置中请勿关闭计算机怎么办,准备配置windows请勿关闭计算机一直显示怎么办【图解】...
不知道大家有没有遇到过这样的一个问题,就是我们的win7系统在关机的时候,总是喜欢显示“准备配置windows,请勿关机”这样的一个页面,没有什么大碍,但是如果一直等着的话就要两个小时甚至更久都关不了机,非常…...
2022/11/19 21:17:00 - 正在准备配置请勿关闭计算机,正在准备配置windows请勿关闭计算机时间长了解决教程...
当电脑出现正在准备配置windows请勿关闭计算机时,一般是您正对windows进行升级,但是这个要是长时间没有反应,我们不能再傻等下去了。可能是电脑出了别的问题了,来看看教程的说法。正在准备配置windows请勿关闭计算机时间长了方法一…...
2022/11/19 21:16:59 - 配置失败还原请勿关闭计算机,配置Windows Update失败,还原更改请勿关闭计算机...
我们使用电脑的过程中有时会遇到这种情况,当我们打开电脑之后,发现一直停留在一个界面:“配置Windows Update失败,还原更改请勿关闭计算机”,等了许久还是无法进入系统。如果我们遇到此类问题应该如何解决呢࿰…...
2022/11/19 21:16:58 - 如何在iPhone上关闭“请勿打扰”
Apple’s “Do Not Disturb While Driving” is a potentially lifesaving iPhone feature, but it doesn’t always turn on automatically at the appropriate time. For example, you might be a passenger in a moving car, but your iPhone may think you’re the one dri…...
2022/11/19 21:16:57