fix
This commit is contained in:
1 parent
44f7d9acfc
commit
ec7e66555d
4 files changed
+100
-4
No files matched your search
@@ -131,6 +131,10 @@ export default class CwmpController {
|
||||
const paramValues = informData?.ParameterList?.ParameterValueStruct || []
|
||||
if (paramValues.length > 0) {
|
||||
device.updateFromValues(paramValues)
|
||||
// Some writable parameters arrive in the Inform before GPN has classified them.
|
||||
// updateFromValues falls back to storing unknowns as read-only properties.
|
||||
// Reclassify known-writable Inform parameters as parameters (writable).
|
||||
device.reclassifyInformWritables(paramValues)
|
||||
}
|
||||
|
||||
device.setTmpParamValues(paramValues)
|
||||
|
||||
@@ -255,6 +255,33 @@ export class Device {
|
||||
this._properties.delete(name)
|
||||
}
|
||||
|
||||
/**
|
||||
* Parameters that arrive in the Inform payload are writable by definition
|
||||
* (the CPE reports them because the ACS is supposed to manage them).
|
||||
* updateFromValues() defaults unknowns to properties (read-only), so we
|
||||
* promote the known-writable Inform params back to parameters here.
|
||||
*
|
||||
* Known writable Inform parameters (TR-098 and TR-181):
|
||||
* - *.ProvisioningCode
|
||||
* - *.ParameterKey
|
||||
*/
|
||||
public reclassifyInformWritables(paramValues: any[]): void {
|
||||
const WRITABLE_PATTERNS = [
|
||||
/(^|\.)ProvisioningCode$/,
|
||||
/(^|\.)ParameterKey$/,
|
||||
]
|
||||
for (const pv of paramValues || []) {
|
||||
const name = typeof pv?.Name === 'string' ? pv.Name : pv?.Name?._ || null
|
||||
if (!name) continue
|
||||
if (!WRITABLE_PATTERNS.some((re) => re.test(name))) continue
|
||||
// Only act if it ended up as a property (wrong classification)
|
||||
if (!this._properties.has(name)) continue
|
||||
const prop = this._properties.get(name)!
|
||||
this._properties.delete(name)
|
||||
this._parameters.set(name, new DeviceParameter(name, prop.value, prop.type))
|
||||
}
|
||||
}
|
||||
|
||||
public getConnectionRequestURL(): URL | null {
|
||||
for (const property of this._properties.values()) {
|
||||
const url = property.getConnectionRequestURL()
|
||||
|
||||
@@ -59,9 +59,10 @@ class IdleState extends DeviceState {
|
||||
'[IdleState] GPN allowed — proceeding to discovery'
|
||||
)
|
||||
|
||||
// Discover mandatory subtrees via GPN.
|
||||
// DeviceInfo is always included so that HardwareVersion, SoftwareVersion,
|
||||
// ModelName, etc. are classified (writable vs read-only) on every session.
|
||||
// GPN is supported: discover mandatory subtrees to classify parameters.
|
||||
// DeviceInfo. is always included so HardwareVersion, SoftwareVersion, ModelName etc.
|
||||
// are classified (writable vs read-only) from the device itself.
|
||||
// If GPN is not supported, the catalog handles classification (reclassifyDeviceFromCatalog).
|
||||
const dataModel = device.dataModel
|
||||
if (dataModel === 'tr-181') {
|
||||
return {
|
||||
@@ -80,7 +81,7 @@ class IdleState extends DeviceState {
|
||||
response: '',
|
||||
}
|
||||
}
|
||||
// Unknown data model — skip GPN test, go to CriticalReadsState
|
||||
// Unknown data model — skip GPN, go to CriticalReadsState
|
||||
return { nextState: new CriticalReadsState(), response: '' }
|
||||
}
|
||||
}
|
||||
|
||||
@@ -226,3 +226,67 @@ describe('Device', () => {
|
||||
expect(d.getParameter('Device.X')!.value).toBe('new')
|
||||
})
|
||||
})
|
||||
|
||||
describe('Device.reclassifyInformWritables', () => {
|
||||
it('promotes ProvisioningCode from property to parameter', () => {
|
||||
const d = makeDevice()
|
||||
// Simulate what updateFromValues does on Inform: stores as property (unknown writability)
|
||||
d.setProperty(new DeviceProperty('InternetGatewayDevice.DeviceInfo.ProvisioningCode', 'abc'))
|
||||
|
||||
d.reclassifyInformWritables([
|
||||
{ Name: 'InternetGatewayDevice.DeviceInfo.ProvisioningCode', Value: { _: 'abc' } },
|
||||
])
|
||||
|
||||
expect(d.getParameter('InternetGatewayDevice.DeviceInfo.ProvisioningCode')).not.toBeNull()
|
||||
expect(d.getProperty('InternetGatewayDevice.DeviceInfo.ProvisioningCode')).toBeNull()
|
||||
})
|
||||
|
||||
it('promotes ParameterKey from property to parameter', () => {
|
||||
const d = makeDevice()
|
||||
d.setProperty(new DeviceProperty('InternetGatewayDevice.ManagementServer.ParameterKey', ''))
|
||||
|
||||
d.reclassifyInformWritables([
|
||||
{ Name: 'InternetGatewayDevice.ManagementServer.ParameterKey', Value: { _: '' } },
|
||||
])
|
||||
|
||||
expect(d.getParameter('InternetGatewayDevice.ManagementServer.ParameterKey')).not.toBeNull()
|
||||
expect(d.getProperty('InternetGatewayDevice.ManagementServer.ParameterKey')).toBeNull()
|
||||
})
|
||||
|
||||
it('does not touch params that are already parameters', () => {
|
||||
const d = makeDevice()
|
||||
d.setParameter(new DeviceParameter('Device.DeviceInfo.ProvisioningCode', 'existing'))
|
||||
|
||||
d.reclassifyInformWritables([
|
||||
{ Name: 'Device.DeviceInfo.ProvisioningCode', Value: { _: 'existing' } },
|
||||
])
|
||||
|
||||
expect(d.getParameter('Device.DeviceInfo.ProvisioningCode')!.value).toBe('existing')
|
||||
expect(d.getProperty('Device.DeviceInfo.ProvisioningCode')).toBeNull()
|
||||
})
|
||||
|
||||
it('does not reclassify unknown names (e.g. SoftwareVersion stays property)', () => {
|
||||
const d = makeDevice()
|
||||
d.setProperty(new DeviceProperty('InternetGatewayDevice.DeviceInfo.SoftwareVersion', 'v1'))
|
||||
|
||||
d.reclassifyInformWritables([
|
||||
{ Name: 'InternetGatewayDevice.DeviceInfo.SoftwareVersion', Value: { _: 'v1' } },
|
||||
])
|
||||
|
||||
// SoftwareVersion is NOT in the writable list — should stay as property
|
||||
expect(d.getProperty('InternetGatewayDevice.DeviceInfo.SoftwareVersion')).not.toBeNull()
|
||||
expect(d.getParameter('InternetGatewayDevice.DeviceInfo.SoftwareVersion')).toBeNull()
|
||||
})
|
||||
|
||||
it('handles Name as object node (XMLParser artefact)', () => {
|
||||
const d = makeDevice()
|
||||
d.setProperty(new DeviceProperty('Device.DeviceInfo.ProvisioningCode', 'code'))
|
||||
|
||||
d.reclassifyInformWritables([
|
||||
{ Name: { _: 'Device.DeviceInfo.ProvisioningCode' }, Value: { _: 'code' } },
|
||||
])
|
||||
|
||||
expect(d.getParameter('Device.DeviceInfo.ProvisioningCode')).not.toBeNull()
|
||||
expect(d.getProperty('Device.DeviceInfo.ProvisioningCode')).toBeNull()
|
||||
})
|
||||
})
|
||||
Reference in new issue
Block a user