AppiumTestDistribution / appium-interceptor-plugin

Appium 2.0 plugin to mock api calls for android apps
27 stars 11 forks source link

Issue : The following script arguments are not known and will be ignored: url,statusCode | Encountered internal error running command: UnknownCommandError: Unknown mobile command "interceptor:addMock" #33

Closed AnilPatidar closed 4 months ago

AnilPatidar commented 4 months ago

Example 1 :

<---------Java Code------------>

Map<String, String> config = new HashMap(); config.put("url", "**/api/lobbyApi/v1/getMatches"); config.put("statusCode","500"); ((JavascriptExecutor)driver).executeScript("interceptor: addMock",config);

Example 2 :

Object authorizationMock = driver.executeScript("interceptor:addMock", new Object[]{ "config", new Object[]{ "url", "**/api/lobbyApi/v1/getMatches", "statusCode", 500 } });

<---------Example 1 Logs------------>

[HTTP] {"script":"interceptor: addMock","args":[{"url":"/api/lobbyApi/v1/getMatches","statusCode":"500"}]} [device-farm-/Users/anil-patidar/.appium] Updating lastCmdExecutedAt for device EQJZH6VONZA6TSWW in session fe666a72-0305-42a4-b7bd-e8d12e75e14c [AndroidUiautomator2Driver@3e8a (fe666a72)] Calling AppiumDriver.execute() with args: ["interceptor: addMock",[{"url":"/api/lobbyApi/v1/getMatches","statusCode":"500"}],"fe666a72-0305-42a4-b7bd-e8d12e75e14c"]

[HTTP] --> POST /wd/hub/session/fe666a72-0305-42a4-b7bd-e8d12e75e14c/execute/sync [HTTP] {"script":"interceptor: addMock","args":[{"url":"/api/lobbyApi/v1/getMatches","statusCode":"500"}]} [device-farm-/Users/anil-patidar/.appium] Updating lastCmdExecutedAt for device EQJZH6VONZA6TSWW in session fe666a72-0305-42a4-b7bd-e8d12e75e14c [AndroidUiautomator2Driver@3e8a (fe666a72)] Calling AppiumDriver.execute() with args: ["interceptor: addMock",[{"url":"/api/lobbyApi/v1/getMatches","statusCode":"500"}],"fe666a72-0305-42a4-b7bd-e8d12e75e14c"] [AppiumDriver@e6c7] Clearing new command timeout pre-emptively since plugin(s) will handle this command [AppiumDriver@e6c7] Plugins which can handle cmd 'execute': device-farm,appium-dashboard,gestures,appium-interceptor [AppiumDriver@e6c7] Plugin appium-interceptor is now handling cmd 'execute' [BaseDriver] The following script arguments are not known and will be ignored: url,statusCode [AppiumDriver@e6c7] Command 'execute' was not handled by the following behaviours or plugins, even though they were registered to handle it: ["default","device-farm","appium-dashboard","gestures"]. The command was handled by these: ["appium-interceptor"]. [AppiumDriver@e6c7] Restarting new command timeout via umbrella driver since plugin did not allow default handler to execute [AndroidUiautomator2Driver@3e8a (fe666a72)] Encountered internal error running command: BadParametersError: The following required parameter is missing: ["config"] [AndroidUiautomator2Driver@3e8a (fe666a72)] Known required parameters are: ["config"] [AndroidUiautomator2Driver@3e8a (fe666a72)] You have provided none [AndroidUiautomator2Driver@3e8a (fe666a72)] at checkParams (/Users/anil-patidar/node_modules/@appium/base-driver/lib/protocol/protocol.js:159:9) [AndroidUiautomator2Driver@3e8a (fe666a72)] at validateExecuteMethodParams (/Users/anil-patidar/node_modules/@appium/base-driver/lib/protocol/protocol.js:246:5) [AndroidUiautomator2Driver@3e8a (fe666a72)] at AppiumInterceptorPlugin.executeMethod (/Users/anil-patidar/node_modules/@appium/base-plugin/lib/plugin.js:79:45) [AndroidUiautomator2Driver@3e8a (fe666a72)] at AppiumInterceptorPlugin. (/Users/anil-patidar/.appium/node_modules/appium-interceptor/src/plugin.ts:165:23) [AndroidUiautomator2Driver@3e8a (fe666a72)] at Generator.next () [AndroidUiautomator2Driver@3e8a (fe666a72)] at /Users/anil-patidar/.appium/node_modules/appium-interceptor/lib/plugin.js:8:71 [AndroidUiautomator2Driver@3e8a (fe666a72)] at new Promise () [AndroidUiautomator2Driver@3e8a (fe666a72)] at __awaiter (/Users/anil-patidar/.appium/node_modules/appium-interceptor/lib/plugin.js:4:12) [AndroidUiautomator2Driver@3e8a (fe666a72)] at AppiumInterceptorPlugin.execute (/Users/anil-patidar/.appium/node_modules/appium-interceptor/lib/plugin.js:142:16) [AndroidUiautomator2Driver@3e8a (fe666a72)] at /Users/anil-patidar/.nvm/versions/node/v16.15.1/lib/node_modules/appium/lib/appium.js:1175:35 [AndroidUiautomator2Driver@3e8a (fe666a72)] at AppiumDriver.executeWrappedCommand (/Users/anil-patidar/.nvm/versions/node/v16.15.1/lib/node_modules/appium/lib/appium.js:1215:22) [AndroidUiautomator2Driver@3e8a (fe666a72)] at AppiumDriver.executeCommand (/Users/anil-patidar/.nvm/versions/node/v16.15.1/lib/node_modules/appium/lib/appium.js:1121:28) [AndroidUiautomator2Driver@3e8a (fe666a72)] at runMicrotasks () [AndroidUiautomator2Driver@3e8a (fe666a72)] at processTicksAndRejections (node:internal/process/task_queues:96:5) [AndroidUiautomator2Driver@3e8a (fe666a72)] at asyncHandler (/Users/anil-patidar/.nvm/versions/node/v16.15.1/lib/node_modules/appium/node_modules/@appium/base-driver/lib/protocol/protocol.js:393:19) [W3C] Bad parameters: BadParametersError: The following required parameter is missing: ["config"] [W3C] Known required parameters are: ["config"] [W3C] You have provided none [HTTP] <-- POST /wd/hub/session/fe666a72-0305-42a4-b7bd-e8d12e75e14c/execute/sync 400 214 ms - 1839 [HTTP] [device-farm-/Users/anil-patidar/.appium] Found 1 device candidates to be released [device-farm-/Users/anil-patidar/.appium] Cleaning pending sessions... [device-farm-/Users/anil-patidar/.appium] No pending sessions to clean [device-farm-/Users/anil-patidar/.appium] Found 1 device candidates to be released [device-farm-/Users/anil-patidar/.appium] Cleaning pending sessions... [device-farm-/Users/anil-patidar/.appium] No pending sessions to clean HTTPS_CLIENT_ERROR [Error: 4388980096:error:14094416:SSL routines:ssl3_read_bytes:sslv3 alert certificate unknown:../deps/openssl/openssl/ssl/record/rec_layer_s3.c:1546:SSL alert number 46 ] { library: 'SSL routines', function: 'ssl3_read_bytes', reason: 'sslv3 alert certificate unknown', code: 'ERR_SSL_SSLV3_ALERT_CERTIFICATE_UNKNOWN' }

<---------Example 2 Logs------------>

creating SNI context for conff.dc.oppomobile.com [HTTP] --> POST /wd/hub/session/291f75ec-9509-4e27-9b0f-7649e84804b9/execute/sync [HTTP] {"script":"interceptor:addMock","args":["config",["url","/api/lobbyApi/v1/getMatches","statusCode",500]]} [device-farm-/Users/anil-patidar/.appium] Updating lastCmdExecutedAt for device EQJZH6VONZA6TSWW in session 291f75ec-9509-4e27-9b0f-7649e84804b9 [AndroidUiautomator2Driver@a6fb (291f75ec)] Calling AppiumDriver.execute() with args: ["interceptor:addMock",["config",["url","/api/lobbyApi/v1/getMatches","statusCode",500]],"291f75ec-9509-4e27-9b0f-7649e84804b9"] [AppiumDriver@f5c9] Clearing new command timeout pre-emptively since plugin(s) will handle this command [AppiumDriver@f5c9] Plugins which can handle cmd 'execute': device-farm,appium-dashboard,gestures,appium-interceptor [AppiumDriver@f5c9] Plugin appium-interceptor is now handling cmd 'execute' [Plugin [appium-interceptor]] Plugin did not know how to handle method 'interceptor:addMock'. Passing control to next [AppiumDriver@f5c9] Plugin gestures is now handling cmd 'execute' [Plugin [gestures]] Plugin did not know how to handle method 'interceptor:addMock'. Passing control to next [AppiumDriver@f5c9] Plugin appium-dashboard is now handling cmd 'execute' [AppiumDriver@f5c9] Plugin device-farm is now handling cmd 'execute' [AppiumDriver@f5c9] Executing default handling behavior for command 'execute' [device-farm-/Users/anil-patidar/.appium] Updating lastCmdExecutedAt for device EQJZH6VONZA6TSWW in session 291f75ec-9509-4e27-9b0f-7649e84804b9 [AndroidUiautomator2Driver@a6fb (291f75ec)] Encountered internal error running command: UnknownCommandError: Unknown mobile command "interceptor:addMock". Only shell, execEmuConsoleCommand, dragGesture, flingGesture, doubleClickGesture, clickGesture, longClickGesture, pinchCloseGesture, pinchOpenGesture, swipeGesture, scrollGesture, scrollBackTo, scroll, viewportScreenshot, viewportRect, deepLink, startLogsBroadcast, stopLogsBroadcast, deviceidle, acceptAlert, dismissAlert, batteryInfo, deviceInfo, getDeviceTime, changePermissions, getPermissions, performEditorAction, startScreenStreaming, stopScreenStreaming, getNotifications, openNotifications, listSms, type, replaceElementValue, pushFile, pullFile, pullFolder, deleteFile, isAppInstalled, queryAppState, activateApp, removeApp, terminateApp, installApp, clearApp, backgroundApp, getCurrentActivity, getCurrentPackage, startActivity, startService, stopService, broadcast, getContexts, getAppStrings, installMultipleApks, lock, unlock, isLocked, refreshGpsCache, startMediaProjectionRecording, isMediaProjectionRecordingRunning, stopMediaProjectionRecording, getConnectivity, setConnectivity, toggleGps, isGpsEnabled, hideKeyboard, isKeyboardShown, pressKey, getDisplayDensity, getSystemBars, fingerprint, sendSms, gsmCall, gsmSignal, gsmVoice, powerAc, powerCapacity, networkSpeed, sensorSet, getPerformanceData, getPerformanceDataTypes, statusBar, screenshots, scheduleAction, getActionHistory, unscheduleAction, getUiMode, setUiMode, sendTrimMemory commands are supported. [AndroidUiautomator2Driver@a6fb (291f75ec)] at AndroidUiautomator2Driver.executeMobile (/Users/anil-patidar/.appium/node_modules/appium-uiautomator2-driver/lib/commands/execute.js:56:11) [AndroidUiautomator2Driver@a6fb (291f75ec)] at AndroidUiautomator2Driver.execute (/Users/anil-patidar/.appium/node_modules/appium-uiautomator2-driver/lib/commands/execute.js:27:23) [AndroidUiautomator2Driver@a6fb (291f75ec)] at commandExecutor (/Users/anil-patidar/node_modules/@appium/base-driver/lib/basedriver/driver.ts:106:18) [AndroidUiautomator2Driver@a6fb (291f75ec)] at /Users/anil-patidar/node_modules/async-lock/lib/index.js:171:12 [AndroidUiautomator2Driver@a6fb (291f75ec)] at AsyncLock._promiseTry (/Users/anil-patidar/node_modules/async-lock/lib/index.js:306:31) [AndroidUiautomator2Driver@a6fb (291f75ec)] at exec (/Users/anil-patidar/node_modules/async-lock/lib/index.js:170:9) [AndroidUiautomator2Driver@a6fb (291f75ec)] at AsyncLock.acquire (/Users/anil-patidar/node_modules/async-lock/lib/index.js:189:3) [AndroidUiautomator2Driver@a6fb (291f75ec)] at AndroidUiautomator2Driver.executeCommand (/Users/anil-patidar/node_modules/@appium/base-driver/lib/basedriver/driver.ts:122:39) [AndroidUiautomator2Driver@a6fb (291f75ec)] at runMicrotasks () [AndroidUiautomator2Driver@a6fb (291f75ec)] at processTicksAndRejections (node:internal/process/task_queues:96:5) [AndroidUiautomator2Driver@a6fb (291f75ec)] at defaultBehavior (/Users/anil-patidar/.nvm/versions/node/v16.15.1/lib/node_modules/appium/lib/appium.js:1109:14) [HTTP] <-- POST /wd/hub/session/291f75ec-9509-4e27-9b0f-7649e84804b9/execute/sync 404 144 ms - 4048 [HTTP] HTTPS_CLIENT_ERROR [Error: 4411344256:error:14094416:SSL routines:ssl3_read_bytes:sslv3 alert certificate unknown:../deps/openssl/openssl/ssl/record/rec_layer_s3.c:1546:SSL alert number 46 ] { library: 'SSL routines', function: 'ssl3_read_bytes', reason: 'sslv3 alert certificate unknown', code: 'ERR_SSL_SSLV3_ALERT_CERTIFICATE_UNKNOWN'

AnilPatidar commented 4 months ago

One point to note is that, Mobile App traffic is being logged by Appium, I am able to open and login to the app. just mocking is not working.

AnilPatidar commented 4 months ago

Appium Versions :

Appium v2.5.4 Device-farm 8.4.7-rc.18 appium-interceptor@1.0.0-beta.9

AnilPatidar commented 4 months ago

@saikrishna321 I know you must be busy , but need some help to get started , Your help will be appreciated.

AnilPatidar commented 4 months ago

Also I am seeing 1 error in logs, hope this can be ignored ?

HTTPS_CLIENT_ERROR [Error: 4411344256:error:14094416:SSL routines:ssl3_read_bytes:sslv3 alert certificate unknown:../deps/openssl/openssl/ssl/record/rec_layer_s3.c:1546:SSL alert number 46 ] { library: 'SSL routines', function: 'ssl3_read_bytes', reason: 'sslv3 alert certificate unknown', code: 'ERR_SSL_SSLV3_ALERT_CERTIFICATE_UNKNOWN' }

sudharsan-selvaraj commented 4 months ago

@AnilPatidar Could you please try with below code and check of it works

Modification of example 1:

Map<String, String> config = new HashMap();
config.put("url", "**/api/lobbyApi/v1/getMatches");
config.put("statusCode","500");
((JavascriptExecutor)driver).executeScript("interceptor: addMock", new HashMap(){{ put("config", config) }});

Modification of example 2: - You missed a blankspace( ) (interceptor: addMock) in-between the command name.

Object authorizationMock = driver.executeScript("interceptor: addMock", new Object[]{
"config", new Object[]{
"url", "**/api/lobbyApi/v1/getMatches",
"statusCode", 500
}
});
AnilPatidar commented 4 months ago

Thanks @sudharsan-selvaraj , it worked, i think i will have to raise a PR with this modification for our documentations, i will do it today.

AnilPatidar commented 4 months ago

Raised https://github.com/AppiumTestDistribution/appium-interceptor-plugin/pull/34/files

sudharsan-selvaraj commented 4 months ago

@AnilPatidar Glad it worked. Will close the issue for now!

ansonliao commented 1 week ago

Hi @sudharsan-selvaraj , I also facing this problem currently, and I no idea how to solve the problem.

My test framework is WebdriverIO, and my mock script as below:

const mockId = await driver.execute("interceptor: addMock", {
      config: {
        url: "**/essmobile-auth/api/v5/mobile/auth/requestOTP?format=new",
        responseBody: JSON.stringify({
          detailedError: {
            errors: [
              {
                staffId: "mock encrypted staff ID"
              }
            ]
          },
          error: "Unauthorized",
          message: "No AD Profile",
          code: "AU0008",
          status: 401,
          timestamp: "2024-08-21T00:00:000"
        })
      }
    });

My error message:

HTTPS_CLIENT_ERROR
[Error: 400F8CED01000000:error:0A000416:SSL routines:ssl3_read_bytes:sslv3 alert certificate unknown:../deps/openssl/openssl/ssl/record/rec_layer_s3.c:1586:SSL alert number 46
] {
  library: 'SSL routines',
  reason: 'sslv3 alert certificate unknown',
  code: 'ERR_SSL_SSLV3_ALERT_CERTIFICATE_UNKNOWN'
}
[ab37311c][AppiumInterceptorPlugin] HTTPS_CLIENT_ERROR: Error: 400F8CED01000000:error:0A000416:SSL routines:ssl3_read_bytes:sslv3 alert certificate unknown:../deps/openssl/openssl/ssl/record/rec_layer_s3.c:1586:SSL alert number 46

Could you kindly help to advise what is the problem and how can I solve it?

Thanks.

sudharsan-selvaraj commented 1 week ago

@ansonliao The console errors you’re seeing are expected. Does the code above mock the relevant API requests? If not, please verify the setup on your mobile device by following the instructions in the certificate installation guide.

When you run the appium plugin run appium-interceptor test-connection command, you should see the mock screen as described in the guide. If you don’t, there may be an issue with the certificate installation.

If the certificate installation is successful, ensure that your application has the necessary permissions to trust user-installed certificates. You can do this by updating the manifest.xml file. For more details, refer to this Stack Overflow thread.

Follow these steps and let us know if you continue to encounter any issues. We’ll investigate further if needed.

ansonliao commented 1 week ago

Hi @sudharsan-selvaraj, thanks for your reply. Yes the command is successful: appium plugin run appium-interceptor test-connection.

Now the app can't connect to the network during the test when the interception add mock executed and the test failed, after the test, run the app manually to play around, it can connect the network to load the data as normal.

Let me follow your instruction for make sure the application has the necessary permissions to trust user-installed certificates.

ansonliao commented 1 week ago

Hi @sudharsan-selvaraj , I just follow this Stack Overflow thread, and the app can connect to the network to load the data from my backend now. But have another issue. My interception as below:

const mockId = await driver.execute("interceptor: addMock", {
      config: {
        url: "/essmobile-auth/api/v5/mobile/auth/requestOTP?format=new",
        responseBody: JSON.stringify({
          detailedError: {
            errors: [
              {
                staffId: "mock encrypted staff ID"
              }
            ]
          },
          error: "Unauthorized",
          message: "No AD Profile",
          code: "AU0008",
          status: 401,
          timestamp: "2024-08-21T00:00:000"
        })
      }
    });

In app, in the user ID input screen when login, input the user ID, and press done button, the app will trigger the HTTP request to backend, the this HTTP request API is ended with /essmobile-auth/api/v5/mobile/auth/requestOTP?format=new, I would like to mock the response with some error such as the User is not found case, so I rewrite the response body as the mock script. When the mock script applied when the test execution, looks like the mock script is works but doesn't work as well. It works because when input the valid user ID and press done button, the app doesn't navigate to the next screen. It doesn't work because, because the mock script will change the response with User not found response JSON content (this response JSON content is verified by Charles with iOS simulator already), but after press done button of the screen, nothing happen, expect will displays a popup with User not found error message, but now nothing displays.

Could you kindly help to advise what is the problem?

Thanks.

ansonliao commented 5 days ago

Hi @sudharsan-selvaraj , I found the root cause, it's my mock code issue, thanks for your reply.

ansonliao commented 5 days ago

Hi @sudharsan-selvaraj , I have some questions to this plugin:

  1. How can we retrieve the request information? for example, the body, the URL, the headers, the query param, etc.
  2. Could we intercept the iOS simulator testing?

Thanks.