Release v2.12.0
This commit is contained in:
1 parent
bdb5ab4bac
commit
0a03cdd0b7
32 files changed
+2211
-18
No files matched your search
@@ -0,0 +1,59 @@
|
||||
const { collectLocalControlUsers } = require('../../local-control-users');
|
||||
|
||||
const TASK = {
|
||||
key: 'player-control-sync',
|
||||
title: 'Player Local Control auth refresh',
|
||||
category: 'player-sync',
|
||||
trigger: 'scheduled recurring task, every fifteen minutes',
|
||||
purpose: 'push eligible Client Control users to connected players.',
|
||||
taskType: 'recurring-run',
|
||||
intervalMs: 15 * 60 * 1000
|
||||
};
|
||||
|
||||
function registerPlayerControlSyncTask(options) {
|
||||
const pool = options && options.pool;
|
||||
const common = options && options.common;
|
||||
const backgroundTaskQueue = options && options.backgroundTaskQueue;
|
||||
const forwardPlayerCommandToDevice = options && options.forwardPlayerCommandToDevice;
|
||||
const localPlayerInternalUrl = String(options && options.localPlayerInternalUrl || '').trim().replace(/\/$/, '');
|
||||
|
||||
if (!pool || !common || !backgroundTaskQueue || typeof common.fetchPlayerRegistrations !== 'function' || typeof forwardPlayerCommandToDevice !== 'function') {
|
||||
throw new Error('registerPlayerControlSyncTask requires player control sync dependencies.');
|
||||
}
|
||||
|
||||
backgroundTaskQueue.registerRecurringTask({
|
||||
key: TASK.key,
|
||||
title: TASK.title,
|
||||
category: TASK.category,
|
||||
intervalMs: TASK.intervalMs,
|
||||
metadata: {},
|
||||
run: async function () {
|
||||
const cachedUsers = await collectLocalControlUsers(pool);
|
||||
const players = await common.fetchPlayerRegistrations(pool);
|
||||
const results = await Promise.all((Array.isArray(players) ? players : []).filter(function (player) {
|
||||
const playerInternalUrl = String(player && player.internal_base_url || '').trim().replace(/\/$/, '');
|
||||
return !localPlayerInternalUrl || playerInternalUrl !== localPlayerInternalUrl;
|
||||
}).map(async function (player) {
|
||||
const deviceId = String(player && (player.identifier || player.device_id) || '').trim();
|
||||
if (!deviceId) {
|
||||
return { ok: false, skipped: true };
|
||||
}
|
||||
try {
|
||||
await forwardPlayerCommandToDevice(deviceId, {
|
||||
command: 'sync-local-control',
|
||||
users: cachedUsers
|
||||
});
|
||||
return { ok: true };
|
||||
} catch (_error) {
|
||||
return { ok: false };
|
||||
}
|
||||
}));
|
||||
return {
|
||||
playerCount: results.length,
|
||||
syncedCount: results.filter(function (result) { return result.ok; }).length
|
||||
};
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
module.exports = { registerPlayerControlSyncTask };
|
||||
@@ -0,0 +1,26 @@
|
||||
const crypto = require('crypto');
|
||||
|
||||
async function collectLocalControlUsers(pool) {
|
||||
const [rows] = await pool.query(
|
||||
`SELECT DISTINCT u.username, u.password_hash, u.password_salt
|
||||
FROM a_users u
|
||||
JOIN a_user_roles ur ON ur.user_id = u.id
|
||||
JOIN a_role_permissions rp ON rp.role_id = ur.role_id
|
||||
JOIN a_permissions p ON p.id = rp.permission_id
|
||||
WHERE u.account_locked = 0
|
||||
AND u.must_change_password = 0
|
||||
AND p.permission_key = 'clients.allow'
|
||||
ORDER BY u.username ASC`
|
||||
);
|
||||
return (rows || []).map(function (user) {
|
||||
return {
|
||||
username_hash: crypto.createHash('sha256').update(String(user && user.username || '').trim()).digest('hex'),
|
||||
password_hash: String(user && user.password_hash || '').trim(),
|
||||
password_salt: String(user && user.password_salt || '').trim()
|
||||
};
|
||||
}).filter(function (user) {
|
||||
return Boolean(user.username_hash && user.password_hash && user.password_salt);
|
||||
});
|
||||
}
|
||||
|
||||
module.exports = { collectLocalControlUsers };
|
||||
@@ -9,6 +9,8 @@ async function initializeWebServer(options) {
|
||||
const loadCurrentUser = options && options.loadCurrentUser;
|
||||
const initializeBackgroundTasks = options && options.initializeBackgroundTasks;
|
||||
const captureSlideThumbnail = options && options.captureSlideThumbnail;
|
||||
const forwardPlayerCommandToDevice = options && options.forwardPlayerCommandToDevice;
|
||||
const localPlayerInternalUrl = options && options.localPlayerInternalUrl;
|
||||
const dataSourceStartupRefreshStaggerMs = Math.max(100, Number(options && options.dataSourceStartupRefreshStaggerMs || 250));
|
||||
const server = options && options.server;
|
||||
|
||||
@@ -25,9 +27,11 @@ async function initializeWebServer(options) {
|
||||
common: common,
|
||||
backgroundTaskQueue: backgroundTaskQueue,
|
||||
notifyPlayerScreens: options && options.notifyPlayerScreens ? options.notifyPlayerScreens : null,
|
||||
forwardPlayerCommandToDevice: forwardPlayerCommandToDevice,
|
||||
uploadSyncService: webBootstrap.uploadSyncService,
|
||||
captureSlideThumbnail: captureSlideThumbnail,
|
||||
mediaDir: mediaDir,
|
||||
localPlayerInternalUrl: localPlayerInternalUrl,
|
||||
webBaseUrl: options && options.webBaseUrl ? options.webBaseUrl : null,
|
||||
dataSourceStartupRefreshStaggerMs: dataSourceStartupRefreshStaggerMs
|
||||
});
|
||||
|
||||
Reference in new issue
Block a user