The script library was gated on applications.*, so anyone holding the software-delivery grant could rewrite the bytes of a script that a separately trusted operator later pushed to a bay. The push was gated on endpoints.runscript; the CONTENT of what got pushed was not. An installer is a vendor artefact, but a script here is arbitrary PowerShell this site wrote that the agent runs as SYSTEM, so the write and the push must require the same trust. All six script routes now require endpoints.runscript, including the body download - reading the bytes is not a lesser act than listing them. Core names the permission as a string rather than importing it from the endpoints plugin so the module stays importable with the plugin absent. This tightens access and there is deliberately no backfill: the operator scope reaches applications.create/edit, so operator-scope holders lose the library. Granting them endpoints.runscript on upgrade would undo the change and hand every operator remote SYSTEM code execution, since the same grant gates the push. A test pins that no prebuilt scope confers it. Adds the System Scripts settings page and card. The route requires the permission rather than admin, because the grant is meant for non-admin operators and the sibling admin gate would lock them out of the library the grant exists for. The settings icon map gains terminal and key; the agent-key card had been asking for key since it shipped and silently drawing a puzzle piece. The library had no test coverage before this.
47 lines
1.6 KiB
JavaScript
47 lines
1.6 KiB
JavaScript
/**
|
|
* Endpoints plugin routes
|
|
*
|
|
* Groundwork for the fleet view. There is no endpoint-specific detail route
|
|
* yet: rows link into the existing PC detail page (/pcs/:id) so telemetry
|
|
* stays interoperable with the computers plugin instead of duplicating it.
|
|
*/
|
|
export default [
|
|
{
|
|
path: 'endpoints',
|
|
name: 'endpoints',
|
|
component: () => import('./views/EndpointsList.vue'),
|
|
meta: { plugin: 'endpoints' }
|
|
},
|
|
{
|
|
path: 'settings/endpoints/agentkey',
|
|
name: 'endpoints-agentkey-settings',
|
|
component: () => import('./views/AgentKeySettings.vue'),
|
|
meta: { requiresAuth: true, requiresAdmin: true, plugin: 'endpoints' }
|
|
},
|
|
{
|
|
path: 'settings/endpoints/monitors',
|
|
name: 'endpoints-monitors-settings',
|
|
component: () => import('./views/MonitorsSettings.vue'),
|
|
meta: { requiresAuth: true, requiresAdmin: true, plugin: 'endpoints' }
|
|
},
|
|
// requiresPermission, not requiresAdmin: endpoints.runscript is grantable to
|
|
// non-admin operators, and the sibling pages' admin gate would lock the
|
|
// holders of the grant out of the library they are trusted to manage. The
|
|
// API enforces the same permission, so this only keeps the menu honest.
|
|
{
|
|
path: 'settings/endpoints/scripts',
|
|
name: 'endpoints-scripts-settings',
|
|
component: () => import('./views/SystemScriptsSettings.vue'),
|
|
meta: {
|
|
requiresAuth: true,
|
|
requiresPermission: 'endpoints.runscript',
|
|
plugin: 'endpoints'
|
|
}
|
|
}
|
|
]
|
|
|
|
// No full-screen routes: every view in this plugin renders inside
|
|
// AppLayout. Declared so routes.gen.js can read `.toplevel` off the module
|
|
// without Rollup warning about a missing export.
|
|
export const toplevel = []
|