Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

eachKeyLike() creates wrong matchingRules #1077

Closed
5 tasks done
eburi opened this issue Mar 23, 2023 · 4 comments
Closed
5 tasks done

eachKeyLike() creates wrong matchingRules #1077

eburi opened this issue Mar 23, 2023 · 4 comments
Labels
bug Indicates an unexpected problem or unintended behavior

Comments

@eburi
Copy link

eburi commented Mar 23, 2023

Software versions

Please provide at least OS and version of pact-js

  • OS: Mac OSX 13.1 (tested on Windows 11 as well)
  • Consumer Pact library: 11.0.2 (same with latest v10.x)
  • Provider Pact library: n/a
  • Node Version: v18.15.0
    "pactRust": {
      "ffi": "0.4.0",
      "models": "1.0.4"
    },

Issue Checklist

Please confirm the following:

  • I have upgraded to the latest
  • I have the read the FAQs in the Readme
  • I have triple checked, that there are no unhandled promises in my code and have read the section on intermittent test failures
  • I have set my log level to debug and attached a log file showing the complete request/response cycle
  • For bonus points and virtual high fives, I have created a reproduceable git repository (see below) to illustrate the problem

Expected behaviour

Given this interaction:

  interaction('pact integration', ({ provider, execute }) => {
    beforeEach(() =>
      provider
        .given('A pet 1845563262948980200 exists')
        .uponReceiving('A get request to get a pet 1845563262948980200')
        .withRequest({
          method: 'GET',
          path: '/v2/pet/1845563262948980200',
          headers: { api_key: '[]' },
        })
        .willRespondWith({
          status: 200,
          // Hypothetical response from an API
          // body: {
          //   options: {
          //     'DEFAULT': {
          //       value: MatchersV3.integer(12),
          //       selected: MatchersV3.boolean(false)
          //     },
          //     'SUPER': {
          //       value: MatchersV3.integer(120),
          //       selected: MatchersV3.boolean(true)
          //     },
          //     'LUXERY': {
          //       value: MatchersV3.integer(12000),
          //       selected: MatchersV3.boolean(false)
          //     }
          //   }
          // }

          // Pact for this API
            body: {
              options: MatchersV3.eachKeyLike('SUPER', {
                value: MatchersV3.integer(120),
                selected: MatchersV3.boolean(true),
              }),
              optionArray: MatchersV3.eachLike({
                value: MatchersV3.integer(120),
                selected: MatchersV3.boolean(true),
              }),
            },
        })
    );

I would expect matchingRules in the resulting pact-file for the body that look like this:

        "matchingRules": {
          "body": {
            "$.options": {
              "combine": "AND",
              "matchers": [
                {
                  "match": "values"
                }
              ]
            },
            "$.options.*.selected": {
              "combine": "AND",
              "matchers": [
                {
                  "match": "type"
                },
              ]
            },
            "$.options.*.value": {
              "combine": "AND",
              "matchers": [
                {
                  "match": "integer"
                }
              ]
            }
          }
        },

Similar to the result from eachLike() used in the example for optionArray:

            "$.optionArray[*].selected": {
              "combine": "AND",
              "matchers": [
                {
                  "match": "type"
                }
              ]
            },
            "$.optionArray[*].value": {
              "combine": "AND",
              "matchers": [
                {
                  "match": "integer"
                }
              ]
            },

Actual behaviour

        "matchingRules": {
          "body": {
            "$.options": {
              "combine": "AND",
              "matchers": [
                {
                  "match": "values"
                }
              ]
            },
            "$.options.*.*": {
              "combine": "AND",
              "matchers": [
                {
                  "match": "type"
                },
                {
                  "match": "integer"
                }
              ]
            }
          }
        },

Note: $.options.*.* with the accumulated matchers for all the fields.
Nesting of eachKeyLike() works and results in more paths with *. in combination with eachLike() down the body I get paths like this $.options.*.*.*[*].*[*].*.*.* and all the paths contain just contain all the matchers for the respective fields together.

Here is a excerpt from a more complex example:

            "$.angebote.*.*": {
              "combine": "AND",
              "matchers": [
                {
                  "match": "type"
                },
                {
                  "match": "type"
                },
                {
                  "match": "type"
                },
                {
                  "match": "type"
                },
                {
                  "match": "type"
                },
                {
                  "match": "type"
                },
                {
                  "match": "type"
                },
                {
                  "match": "type"
                }
              ]
            },

Together with "combine": "AND", there is no way this will ever properly match.

I think it's related to this issue here: pact-foundation/pact-reference#216 but I lack the necessary Rust Knowhow to dive into that.

Steps to reproduce

I forked the jest-pact Repository and adapted the v3 test to show the issue. I also added the resulting pact-file for easier reference here:
Repo: https://github.com/eburi/jest-pact
=> npm install && npm run test

https://github.com/eburi/jest-pact/blob/master/src/v3/pactwith.v3.test.ts#L18

Resulting Pact File:
https://github.com/eburi/jest-pact/blob/master/pact/pacts/MyConsumer-pactWith%20v3.json

Relevant log files

debug.log

@eburi eburi added the bug Indicates an unexpected problem or unintended behavior label Mar 23, 2023
@eburi
Copy link
Author

eburi commented Mar 23, 2023

debug.log
Updates log-file as I added the optionArray to show the difference in the result from eachKeyLike() and eachLike()

@mefellows
Copy link
Member

Thanks @eburi. Just a note to say that there is a separate issue with eachKeyLike - see #952 #662.

The fix for those might address this, but we'd need to chek.

@github-actions
Copy link

👋 Hi! The 'smartbear-supported' label has just been added to this issue, which will create an internal tracking ticket in PactFlow's Jira (PACT-1138). We will use this to prioritise and assign a team member to this task. All activity will be public on this ticket. For now, sit tight and we'll update this ticket once we have more information on the next steps.

See our documentation for more information.

@mefellows
Copy link
Member

Fixed in #1103 and pact-foundation/pact-js-core#462. Latest release in the core going out shortly, which is a transitive dependency that will get pulled in with new installs/updates.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
bug Indicates an unexpected problem or unintended behavior
Projects
None yet
Development

No branches or pull requests

2 participants