Skip to content

Commit

Permalink
脚本生命周期回调通过线程方式实现
Browse files Browse the repository at this point in the history
  • Loading branch information
TonyJiangWJ committed Sep 24, 2020
1 parent 87e1d0f commit 4a5095d
Show file tree
Hide file tree
Showing 2 changed files with 61 additions and 107 deletions.
156 changes: 54 additions & 102 deletions lib/prototype/CommonFunction.js
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
* @Author: TonyJiangWJ
* @Date: 2020-04-25 20:16:09
* @Last Modified by: TonyJiangWJ
* @Last Modified time: 2020-09-23 23:57:25
* @Last Modified time: 2020-09-24 22:10:35
* @Description: 通用工具
*/
importClass(android.content.Context)
Expand All @@ -28,59 +28,58 @@ let TIMER_AUTO_START = "timerAutoStart"

let lifecycleDeamonThreadPool = null
let lifecycleCallbacks = []
if (!_config.is_pro) {
importClass(com.stardust.autojs.ScriptEngineService)
importClass(com.stardust.autojs.engine.ScriptEngineManager)
} else {
_config.isRunning = true
importClass(java.util.concurrent.LinkedBlockingQueue)
importClass(java.util.concurrent.ThreadPoolExecutor)
importClass(java.util.concurrent.TimeUnit)
importClass(java.util.concurrent.ThreadFactory)
importClass(java.util.concurrent.Executors)
let ENGINE_ID = engines.myEngine().id
// Pro版因为无法注册脚本生命周期回调,创建一个单独的线程来监听当前脚本是否已经执行完毕
lifecycleDeamonThreadPool = new ThreadPoolExecutor(1, 1, 60, TimeUnit.SECONDS, new LinkedBlockingQueue(10), new ThreadFactory({
newThread: function (runnable) {
let thread = Executors.defaultThreadFactory().newThread(runnable)
thread.setName(ENGINE_ID + '-lifecycle-deamon-' + thread.getName())
return thread
}
}))
lifecycleDeamonThreadPool.execute(function () {
let count = 0
while (_config.isRunning) {
// 每五秒检测一次isRunning
sleep(5000)
if (count++ % 5) {
// 每25秒执行一次,其实在LogUtils中已经有了校验,这里增加判断,冗余一下
let currentEngine = engines.all().filter(engine => engine.id === ENGINE_ID)
_config.isRunning = currentEngine && currentEngine.length > 0
let lifecycleLock = threads.lock()
_config.isRunning = true
importClass(java.util.concurrent.LinkedBlockingQueue)
importClass(java.util.concurrent.ThreadPoolExecutor)
importClass(java.util.concurrent.TimeUnit)
importClass(java.util.concurrent.ThreadFactory)
importClass(java.util.concurrent.Executors)
let ENGINE_ID = engines.myEngine().id
// 注册脚本生命周期回调,创建一个单独的线程来监听当前脚本是否已经执行完毕
lifecycleDeamonThreadPool = new ThreadPoolExecutor(1, 1, 60, TimeUnit.SECONDS, new LinkedBlockingQueue(10), new ThreadFactory({
newThread: function (runnable) {
let thread = Executors.defaultThreadFactory().newThread(runnable)
thread.setName(ENGINE_ID + '-lifecycle-deamon-' + thread.getName())
return thread
}
}))
lifecycleDeamonThreadPool.execute(function () {
let count = 0
while (_config.isRunning) {
// 每五秒检测一次isRunning
sleep(5000)
if (count++ % 5) {
// 每25秒执行一次,其实在LogUtils中已经有了校验,这里增加判断,冗余一下
let currentEngine = engines.all().filter(engine => engine.id === ENGINE_ID)
_config.isRunning = currentEngine && currentEngine.length > 0
}
}
console.verbose('脚本已经中止执行,执行生命周期回调')
// 脚本已经结束,执行callbacks
if (lifecycleCallbacks && lifecycleCallbacks.length > 0) {
lifecycleCallbacks.forEach(callback => {
callback()
})
}
// 新建线程 关闭线程池
let thread = new Thread(new java.lang.Runnable({
run: function () {
try {
lifecycleDeamonThreadPool.shutdown()
let flag = lifecycleDeamonThreadPool.awaitTermination(5, java.util.concurrent.TimeUnit.SECONDS)
console.verbose('lifecycleDeamon线程池关闭:' + flag)
} catch (e) {
console.error('关闭lifecycleDeamon线程池异常:' + e)
} finally {
lifecycleDeamonThreadPool = null
}
}
console.verbose('脚本已经中止执行,执行生命周期回调')
// 脚本已经结束,执行callbacks
if (lifecycleCallbacks && lifecycleCallbacks.length > 0) {
lifecycleCallbacks.forEach(callback => {
callback()
})
}
// 新建线程 关闭线程池
new Thread(new java.lang.Runnable({
run: function () {
try {
lifecycleDeamonThreadPool.shutdown()
let flag = lifecycleDeamonThreadPool.awaitTermination(5, java.util.concurrent.TimeUnit.SECONDS)
console.verbose('lifecycleDeamon线程池关闭:' + flag)
} catch (e) {
console.error('关闭lifecycleDeamon线程池异常:' + e)
} finally {
lifecycleDeamonThreadPool = null
}
}
})).start()
})
}
}))
thread.setName(ENGINE_ID + "_shutdown_lifecycle_thread")
thread.start()
})


function CommonFunctions () {

Expand Down Expand Up @@ -132,63 +131,16 @@ function CommonFunctions () {
}
}

/**
* 脚本引擎退出成功后回调,将callback从生命周期回调中移除
*
* @param {Object} callback 待移除的callback对象
* @param {String} desc 过程描述
*/
this.removeCallback = function(callback, desc) {
let removeThreads = new java.lang.Thread(new java.lang.Runnable({
run: function () {
// 避免并发修改异常
_logUtils.debugForDev(['unregisterEngineLifecycleCallback {}', desc])
try {
ScriptEngineService.getInstance().unregisterEngineLifecycleCallback(callback)
} catch (e) {
_logUtils.errorInfo(['{} 移除异常:' + e, desc])
}
_logUtils.debugForDev(['unregisterEngineLifecycleCallback {} done', desc])
}
}))
let start = new Date().getTime()
try {
removeThreads.start()
} catch (e) {
_logUtils.errorInfo(['{} fucked', desc])
}
_logUtils.debugForDev(['{} cost: {}ms', desc, new Date().getTime() - start])
}

/**
* 注册生命周期回调,在退出时执行func
* @param {function} func 回调方法
* @param {String} desc 过程描述
*/
this.registerOnEngineRemoved = function (func, desc) {
desc = desc || 'common func'
if (!_config.is_pro) {
// 监听运行周期,脚本结束后执行 func
let engineService = ScriptEngineService.getInstance()
let _this = this
let myEngineId = engines.myEngine().id
engineService.registerEngineLifecycleCallback(
new ScriptEngineManager.EngineLifecycleCallback({
onEngineCreate: function (engine) {
},
onEngineRemove: function (engine) {
if (engine.id === myEngineId) {
func()
// 回调成功后将当前callback注销
_this.removeCallback(this, desc)
}
}
})
)
} else {
// _logUtils.errorInfo('Pro版暂无法实现生命周期监听,请尽量使用免费版!')
lifecycleCallbacks.push(func)
}
lifecycleLock.lock()
lifecycleCallbacks.push(func)
lifecycleLock.unlock()
}

/**
Expand Down
12 changes: 7 additions & 5 deletions lib/prototype/LogUtils.js
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
/*
* @Author: TonyJiangWJ
* @Last Modified by: TonyJiangWJ
* @Last Modified time: 2020-09-24 09:43:05
* @Last Modified time: 2020-09-24 22:11:13
* @Description: 日志工具
*/
importClass(java.lang.Thread)
Expand Down Expand Up @@ -156,19 +156,21 @@ function AsyncLogger () {
console.warn('脚本执行结束,日志文件写入线程关闭')
self.showCostingInfo()
// 新建线程 关闭线程池
new Thread(new java.lang.Runnable({
let thread = new Thread(new java.lang.Runnable({
run: function () {
try {
self.executeThreadPool.shutdown()
let flag = self.executeThreadPool.awaitTermination(5, java.util.concurrent.TimeUnit.SECONDS)
console.verbose('线程池关闭:' + flag)
console.verbose('日志线程池关闭:' + flag)
} catch (e) {
console.error('关闭线程池异常:' + e)
console.error('关闭日志线程池异常:' + e)
} finally {
self.executeThreadPool = null
}
}
})).start()
}))
thread.setName(ENGINE_ID + '_shutdown_logging_thread')
thread.start()
})

this.flushAllLogs = function () {
Expand Down

0 comments on commit 4a5095d

Please sign in to comment.