Handle unsupported ACS methods gracefully

This commit is contained in:
Zaid Abdulla committed 2021-10-15 16:21:08 -07:00
1 parent 7f295beeec
commit 0188ac860b
3 files changed
+55 -1

No files matched your search

+36
View File
@@ -45,6 +45,7 @@ import {
InformRequest, InformRequest,
Preset, Preset,
GetRPCMethodsResponse, GetRPCMethodsResponse,
CpeFault,
} from "./types"; } from "./types";
import { IncomingMessage, ServerResponse } from "http"; import { IncomingMessage, ServerResponse } from "http";
import { Readable } from "stream"; import { Readable } from "stream";
@@ -1256,6 +1257,41 @@ async function processRequest(
session.clearProvisions(sessionContext); session.clearProvisions(sessionContext);
} }
return nextRpc(sessionContext); return nextRpc(sessionContext);
} else if (rpc.unknownMethod) {
if (sessionContext.state === 1) {
logger.accessWarn({
sessionContext: sessionContext,
message: "Method not supported",
method: rpc.unknownMethod,
});
const f: CpeFault = {
faultCode: "Server",
faultString: "CWMP fault",
detail: {
faultCode: "8000",
faultString: "Method not supported",
},
};
const res = soap.response({
id: rpc.id,
acsFault: f,
cwmpVersion: sessionContext.cwmpVersion,
});
return writeResponse(sessionContext, res);
} else if (sessionContext.state === 2) {
const fault = {
code: "invalid_response",
message: "Response name does not match request name",
};
recordFault(sessionContext, fault);
session.clearProvisions(sessionContext);
return nextRpc(sessionContext);
} else {
return reportBadState(sessionContext);
}
} else { } else {
// CPE sent empty response // CPE sent empty response
if (sessionContext.state !== 1) return reportBadState(sessionContext); if (sessionContext.state !== 1) return reportBadState(sessionContext);
+18 -1
View File
@@ -730,6 +730,18 @@ function RequestDownloadResponse(): string {
return "<cwmp:RequestDownloadResponse></cwmp:RequestDownloadResponse>"; return "<cwmp:RequestDownloadResponse></cwmp:RequestDownloadResponse>";
} }
function AcsFault(f: CpeFault): string {
return `<soap-env:Body:Fault><faultcode>${encodeEntities(
f.faultCode
)}</faultcode><faultstring>${encodeEntities(
f.faultString
)}</faultstring><detail><cwmp:Fault><FaultCode>${encodeEntities(
f.detail.faultCode
)}</FaultCode><FaultString>${encodeEntities(
f.detail.faultString
)}</FaultString></cwmp:Fault></detail></soap-env:Body:Fault>`;
}
function faultStruct(xml: Element): FaultStruct { function faultStruct(xml: Element): FaultStruct {
let faultCode: string, let faultCode: string,
faultString: string, faultString: string,
@@ -838,6 +850,7 @@ export function request(
cpeRequest: null, cpeRequest: null,
cpeFault: null, cpeFault: null,
cpeResponse: null, cpeResponse: null,
unknownMethod: null,
}; };
if (!body.length) return rpc; if (!body.length) return rpc;
@@ -959,7 +972,8 @@ export function request(
rpc.cpeFault = fault(methodElement); rpc.cpeFault = fault(methodElement);
break; break;
default: default:
throw new Error(`8000 Method not supported ${methodElement.localName}`); rpc.unknownMethod = methodElement.localName;
break;
} }
return rpc; return rpc;
@@ -987,6 +1001,7 @@ export function response(rpc: {
id: string; id: string;
acsRequest?: AcsRequest; acsRequest?: AcsRequest;
acsResponse?: AcsResponse; acsResponse?: AcsResponse;
acsFault?: CpeFault;
cwmpVersion?: string; cwmpVersion?: string;
}): { code: number; headers: Record<string, string>; data: string } { }): { code: number; headers: Record<string, string>; data: string } {
const headers = { const headers = {
@@ -1055,6 +1070,8 @@ export function response(rpc: {
`Unknown method request ${(rpc.acsRequest as AcsRequest).name}` `Unknown method request ${(rpc.acsRequest as AcsRequest).name}`
); );
} }
} else if (rpc.acsFault) {
body = AcsFault(rpc.acsFault);
} }
headers["Content-Type"] = 'text/xml; charset="utf-8"'; headers["Content-Type"] = 'text/xml; charset="utf-8"';
+1
View File
@@ -526,6 +526,7 @@ export interface SoapMessage {
cpeRequest?: CpeRequest; cpeRequest?: CpeRequest;
cpeFault?: CpeFault; cpeFault?: CpeFault;
cpeResponse?: CpeResponse; cpeResponse?: CpeResponse;
unknownMethod?: string;
} }
export interface ScriptResult { export interface ScriptResult {