@goast/kotlin 0.4.4-beta2 → 0.4.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/LICENSE +21 -21
- package/README.md +45 -45
- package/assets/client/okhttp3/ApiClient.kt +250 -250
- package/esm/_dnt.test_polyfills.d.ts +29 -0
- package/esm/_dnt.test_polyfills.d.ts.map +1 -0
- package/esm/_dnt.test_polyfills.js +31 -0
- package/esm/_dnt.test_shims.d.ts +6 -0
- package/esm/_dnt.test_shims.d.ts.map +1 -0
- package/esm/_dnt.test_shims.js +61 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/assertion_error.d.ts +26 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/assertion_error.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/assertion_error.js +30 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/equal.d.ts +17 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/equal.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/equal.js +183 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/equals.d.ts +22 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/equals.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/equals.js +45 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/false.d.ts +18 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/false.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/false.js +22 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/instance_of.d.ts +23 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/instance_of.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/instance_of.js +53 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/is_error.d.ts +25 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/is_error.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/is_error.js +54 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/match.d.ts +18 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/match.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/match.js +26 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/not_instance_of.d.ts +20 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/not_instance_of.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/not_instance_of.js +29 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/not_match.d.ts +18 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/not_match.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/not_match.js +26 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/not_strict_equals.d.ts +23 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/not_strict_equals.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/not_strict_equals.js +32 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/rejects.d.ts +42 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/rejects.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/rejects.js +53 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/strict_equals.d.ts +24 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/strict_equals.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/assert/1.0.8/strict_equals.js +57 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_assert_equals.d.ts +20 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_assert_equals.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_assert_equals.js +29 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_assert_not_equals.d.ts +17 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_assert_not_equals.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_assert_not_equals.js +26 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_assertions.d.ts +4 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_assertions.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_assertions.js +13 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_asymmetric_matchers.d.ts +46 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_asymmetric_matchers.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_asymmetric_matchers.js +160 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_build_message.d.ts +6 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_build_message.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_build_message.js +29 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_custom_equality_tester.d.ts +4 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_custom_equality_tester.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_custom_equality_tester.js +11 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_equal.d.ts +9 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_equal.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_equal.js +191 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_extend.d.ts +4 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_extend.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_extend.js +11 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_inspect_args.d.ts +3 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_inspect_args.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_inspect_args.js +12 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_matchers.d.ts +34 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_matchers.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_matchers.js +563 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_mock_util.d.ts +11 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_mock_util.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_mock_util.js +10 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_serializer.d.ts +4 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_serializer.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_serializer.js +10 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_types.d.ts +839 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_types.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_types.js +3 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_utils.d.ts +9 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_utils.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/_utils.js +218 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/expect.d.ts +60 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/expect.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/expect/1.0.8/expect.js +523 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/assertion_state.d.ts +160 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/assertion_state.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/assertion_state.js +199 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/build_message.d.ts +82 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/build_message.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/build_message.js +111 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/diff.d.ts +140 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/diff.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/diff.js +277 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/diff_str.d.ts +99 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/diff_str.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/diff_str.js +180 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/format.d.ts +2 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/format.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/format.js +37 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/styles.d.ts +159 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/styles.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/styles.js +207 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/types.d.ts +16 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/types.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/internal/1.0.5/types.js +2 -0
- package/esm/deps/jsr.io/@std/testing/1.0.5/_mock_utils.d.ts +15 -0
- package/esm/deps/jsr.io/@std/testing/1.0.5/_mock_utils.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/testing/1.0.5/_mock_utils.js +35 -0
- package/esm/deps/jsr.io/@std/testing/1.0.5/_test_suite.d.ts +74 -0
- package/esm/deps/jsr.io/@std/testing/1.0.5/_test_suite.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/testing/1.0.5/_test_suite.js +350 -0
- package/esm/deps/jsr.io/@std/testing/1.0.5/bdd.d.ts +731 -0
- package/esm/deps/jsr.io/@std/testing/1.0.5/bdd.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/testing/1.0.5/bdd.js +581 -0
- package/esm/deps/jsr.io/@std/testing/1.0.5/mock.d.ts +674 -0
- package/esm/deps/jsr.io/@std/testing/1.0.5/mock.d.ts.map +1 -0
- package/esm/deps/jsr.io/@std/testing/1.0.5/mock.js +1083 -0
- package/esm/src/ast/nodes/annotation.test.d.ts +2 -0
- package/esm/src/ast/nodes/annotation.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/annotation.test.js +56 -0
- package/esm/src/ast/nodes/argument.test.d.ts +2 -0
- package/esm/src/ast/nodes/argument.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/argument.test.js +33 -0
- package/esm/src/ast/nodes/call.test.d.ts +2 -0
- package/esm/src/ast/nodes/call.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/call.test.js +35 -0
- package/esm/src/ast/nodes/class.test.d.ts +2 -0
- package/esm/src/ast/nodes/class.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/class.test.js +219 -0
- package/esm/src/ast/nodes/constructor.test.d.ts +2 -0
- package/esm/src/ast/nodes/constructor.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/constructor.test.js +139 -0
- package/esm/src/ast/nodes/doc-tag.test.d.ts +2 -0
- package/esm/src/ast/nodes/doc-tag.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/doc-tag.test.js +67 -0
- package/esm/src/ast/nodes/doc.test.d.ts +2 -0
- package/esm/src/ast/nodes/doc.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/doc.test.js +33 -0
- package/esm/src/ast/nodes/enum-value.test.d.ts +2 -0
- package/esm/src/ast/nodes/enum-value.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/enum-value.test.js +115 -0
- package/esm/src/ast/nodes/enum.test.d.ts +2 -0
- package/esm/src/ast/nodes/enum.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/enum.test.js +129 -0
- package/esm/src/ast/nodes/function.test.d.ts +2 -0
- package/esm/src/ast/nodes/function.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/function.test.js +160 -0
- package/esm/src/ast/nodes/generic-parameter.test.d.ts +2 -0
- package/esm/src/ast/nodes/generic-parameter.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/generic-parameter.test.js +49 -0
- package/esm/src/ast/nodes/init-block.test.d.ts +2 -0
- package/esm/src/ast/nodes/init-block.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/init-block.test.js +28 -0
- package/esm/src/ast/nodes/interface.test.d.ts +2 -0
- package/esm/src/ast/nodes/interface.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/interface.test.js +121 -0
- package/esm/src/ast/nodes/object.test.d.ts +2 -0
- package/esm/src/ast/nodes/object.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/object.test.js +78 -0
- package/esm/src/ast/nodes/parameter.test.d.ts +2 -0
- package/esm/src/ast/nodes/parameter.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/parameter.test.js +152 -0
- package/esm/src/ast/nodes/property.test.d.ts +2 -0
- package/esm/src/ast/nodes/property.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/property.test.js +206 -0
- package/esm/src/ast/nodes/reference.test.d.ts +2 -0
- package/esm/src/ast/nodes/reference.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/reference.test.js +36 -0
- package/esm/src/ast/nodes/string.test.d.ts +2 -0
- package/esm/src/ast/nodes/string.test.d.ts.map +1 -0
- package/esm/src/ast/nodes/string.test.js +48 -0
- package/esm/src/config.d.ts +1 -0
- package/esm/src/config.d.ts.map +1 -1
- package/esm/src/config.js +1 -0
- package/esm/src/generators/services/okhttp3-clients/okhttp3-client-generator.js +26 -26
- package/esm/src/generators/services/spring-controllers/args.d.ts +3 -0
- package/esm/src/generators/services/spring-controllers/args.d.ts.map +1 -1
- package/esm/src/generators/services/spring-controllers/spring-controller-generator.d.ts +1 -0
- package/esm/src/generators/services/spring-controllers/spring-controller-generator.d.ts.map +1 -1
- package/esm/src/generators/services/spring-controllers/spring-controller-generator.js +11 -1
- package/esm/src/import-collection.test.d.ts +2 -0
- package/esm/src/import-collection.test.d.ts.map +1 -0
- package/esm/src/import-collection.test.js +99 -0
- package/esm/tests/openapi-models.test.d.ts +2 -0
- package/esm/tests/openapi-models.test.d.ts.map +1 -0
- package/esm/tests/openapi-models.test.js +45 -0
- package/package.json +2 -2
- package/script/_dnt.test_polyfills.d.ts +29 -0
- package/script/_dnt.test_polyfills.d.ts.map +1 -0
- package/script/_dnt.test_polyfills.js +32 -0
- package/script/_dnt.test_shims.d.ts +6 -0
- package/script/_dnt.test_shims.d.ts.map +1 -0
- package/script/_dnt.test_shims.js +65 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/assertion_error.d.ts +26 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/assertion_error.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/assertion_error.js +34 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/equal.d.ts +17 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/equal.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/equal.js +187 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/equals.d.ts +22 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/equals.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/equals.js +48 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/false.d.ts +18 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/false.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/false.js +25 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/instance_of.d.ts +23 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/instance_of.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/instance_of.js +56 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/is_error.d.ts +25 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/is_error.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/is_error.js +57 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/match.d.ts +18 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/match.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/match.js +29 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/not_instance_of.d.ts +20 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/not_instance_of.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/not_instance_of.js +32 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/not_match.d.ts +18 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/not_match.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/not_match.js +29 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/not_strict_equals.d.ts +23 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/not_strict_equals.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/not_strict_equals.js +35 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/rejects.d.ts +42 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/rejects.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/rejects.js +56 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/strict_equals.d.ts +24 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/strict_equals.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/assert/1.0.8/strict_equals.js +60 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_assert_equals.d.ts +20 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_assert_equals.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_assert_equals.js +32 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_assert_not_equals.d.ts +17 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_assert_not_equals.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_assert_not_equals.js +29 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_assertions.d.ts +4 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_assertions.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_assertions.js +18 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_asymmetric_matchers.d.ts +46 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_asymmetric_matchers.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_asymmetric_matchers.js +182 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_build_message.d.ts +6 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_build_message.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_build_message.js +33 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_custom_equality_tester.d.ts +4 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_custom_equality_tester.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_custom_equality_tester.js +15 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_equal.d.ts +9 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_equal.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_equal.js +194 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_extend.d.ts +4 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_extend.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_extend.js +15 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_inspect_args.d.ts +3 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_inspect_args.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_inspect_args.js +17 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_matchers.d.ts +34 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_matchers.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_matchers.js +597 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_mock_util.d.ts +11 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_mock_util.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_mock_util.js +14 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_serializer.d.ts +4 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_serializer.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_serializer.js +14 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_types.d.ts +839 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_types.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_types.js +4 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_utils.d.ts +9 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_utils.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/_utils.js +226 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/expect.d.ts +60 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/expect.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/expect/1.0.8/expect.js +527 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/assertion_state.d.ts +160 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/assertion_state.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/assertion_state.js +204 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/build_message.d.ts +82 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/build_message.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/build_message.js +116 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/diff.d.ts +140 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/diff.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/diff.js +284 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/diff_str.d.ts +99 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/diff_str.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/diff_str.js +186 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/format.d.ts +2 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/format.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/format.js +41 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/styles.d.ts +159 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/styles.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/styles.js +220 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/types.d.ts +16 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/types.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/internal/1.0.5/types.js +3 -0
- package/script/deps/jsr.io/@std/testing/1.0.5/_mock_utils.d.ts +15 -0
- package/script/deps/jsr.io/@std/testing/1.0.5/_mock_utils.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/testing/1.0.5/_mock_utils.js +41 -0
- package/script/deps/jsr.io/@std/testing/1.0.5/_test_suite.d.ts +74 -0
- package/script/deps/jsr.io/@std/testing/1.0.5/_test_suite.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/testing/1.0.5/_test_suite.js +355 -0
- package/script/deps/jsr.io/@std/testing/1.0.5/bdd.d.ts +731 -0
- package/script/deps/jsr.io/@std/testing/1.0.5/bdd.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/testing/1.0.5/bdd.js +592 -0
- package/script/deps/jsr.io/@std/testing/1.0.5/mock.d.ts +674 -0
- package/script/deps/jsr.io/@std/testing/1.0.5/mock.d.ts.map +1 -0
- package/script/deps/jsr.io/@std/testing/1.0.5/mock.js +1102 -0
- package/script/src/ast/nodes/annotation.test.d.ts +2 -0
- package/script/src/ast/nodes/annotation.test.d.ts.map +1 -0
- package/script/src/ast/nodes/annotation.test.js +58 -0
- package/script/src/ast/nodes/argument.test.d.ts +2 -0
- package/script/src/ast/nodes/argument.test.d.ts.map +1 -0
- package/script/src/ast/nodes/argument.test.js +35 -0
- package/script/src/ast/nodes/call.test.d.ts +2 -0
- package/script/src/ast/nodes/call.test.d.ts.map +1 -0
- package/script/src/ast/nodes/call.test.js +37 -0
- package/script/src/ast/nodes/class.test.d.ts +2 -0
- package/script/src/ast/nodes/class.test.d.ts.map +1 -0
- package/script/src/ast/nodes/class.test.js +221 -0
- package/script/src/ast/nodes/constructor.test.d.ts +2 -0
- package/script/src/ast/nodes/constructor.test.d.ts.map +1 -0
- package/script/src/ast/nodes/constructor.test.js +141 -0
- package/script/src/ast/nodes/doc-tag.test.d.ts +2 -0
- package/script/src/ast/nodes/doc-tag.test.d.ts.map +1 -0
- package/script/src/ast/nodes/doc-tag.test.js +69 -0
- package/script/src/ast/nodes/doc.test.d.ts +2 -0
- package/script/src/ast/nodes/doc.test.d.ts.map +1 -0
- package/script/src/ast/nodes/doc.test.js +35 -0
- package/script/src/ast/nodes/enum-value.test.d.ts +2 -0
- package/script/src/ast/nodes/enum-value.test.d.ts.map +1 -0
- package/script/src/ast/nodes/enum-value.test.js +117 -0
- package/script/src/ast/nodes/enum.test.d.ts +2 -0
- package/script/src/ast/nodes/enum.test.d.ts.map +1 -0
- package/script/src/ast/nodes/enum.test.js +131 -0
- package/script/src/ast/nodes/function.test.d.ts +2 -0
- package/script/src/ast/nodes/function.test.d.ts.map +1 -0
- package/script/src/ast/nodes/function.test.js +162 -0
- package/script/src/ast/nodes/generic-parameter.test.d.ts +2 -0
- package/script/src/ast/nodes/generic-parameter.test.d.ts.map +1 -0
- package/script/src/ast/nodes/generic-parameter.test.js +51 -0
- package/script/src/ast/nodes/init-block.test.d.ts +2 -0
- package/script/src/ast/nodes/init-block.test.d.ts.map +1 -0
- package/script/src/ast/nodes/init-block.test.js +30 -0
- package/script/src/ast/nodes/interface.test.d.ts +2 -0
- package/script/src/ast/nodes/interface.test.d.ts.map +1 -0
- package/script/src/ast/nodes/interface.test.js +123 -0
- package/script/src/ast/nodes/object.test.d.ts +2 -0
- package/script/src/ast/nodes/object.test.d.ts.map +1 -0
- package/script/src/ast/nodes/object.test.js +80 -0
- package/script/src/ast/nodes/parameter.test.d.ts +2 -0
- package/script/src/ast/nodes/parameter.test.d.ts.map +1 -0
- package/script/src/ast/nodes/parameter.test.js +154 -0
- package/script/src/ast/nodes/property.test.d.ts +2 -0
- package/script/src/ast/nodes/property.test.d.ts.map +1 -0
- package/script/src/ast/nodes/property.test.js +208 -0
- package/script/src/ast/nodes/reference.test.d.ts +2 -0
- package/script/src/ast/nodes/reference.test.d.ts.map +1 -0
- package/script/src/ast/nodes/reference.test.js +38 -0
- package/script/src/ast/nodes/string.test.d.ts +2 -0
- package/script/src/ast/nodes/string.test.d.ts.map +1 -0
- package/script/src/ast/nodes/string.test.js +50 -0
- package/script/src/config.d.ts +1 -0
- package/script/src/config.d.ts.map +1 -1
- package/script/src/config.js +1 -0
- package/script/src/generators/services/okhttp3-clients/okhttp3-client-generator.js +26 -26
- package/script/src/generators/services/spring-controllers/args.d.ts +3 -0
- package/script/src/generators/services/spring-controllers/args.d.ts.map +1 -1
- package/script/src/generators/services/spring-controllers/spring-controller-generator.d.ts +1 -0
- package/script/src/generators/services/spring-controllers/spring-controller-generator.d.ts.map +1 -1
- package/script/src/generators/services/spring-controllers/spring-controller-generator.js +11 -1
- package/script/src/import-collection.test.d.ts +2 -0
- package/script/src/import-collection.test.d.ts.map +1 -0
- package/script/src/import-collection.test.js +101 -0
- package/script/tests/openapi-models.test.d.ts +2 -0
- package/script/tests/openapi-models.test.d.ts.map +1 -0
- package/script/tests/openapi-models.test.js +48 -0
- package/src/_dnt.test_polyfills.ts +70 -0
- package/src/_dnt.test_shims.ts +64 -0
- package/src/deps/jsr.io/@std/assert/1.0.8/assertion_error.ts +31 -0
- package/src/deps/jsr.io/@std/assert/1.0.8/equal.ts +210 -0
- package/src/deps/jsr.io/@std/assert/1.0.8/equals.ts +52 -0
- package/src/deps/jsr.io/@std/assert/1.0.8/false.ts +26 -0
- package/src/deps/jsr.io/@std/assert/1.0.8/instance_of.ts +64 -0
- package/src/deps/jsr.io/@std/assert/1.0.8/is_error.ts +65 -0
- package/src/deps/jsr.io/@std/assert/1.0.8/match.ts +30 -0
- package/src/deps/jsr.io/@std/assert/1.0.8/not_instance_of.ts +33 -0
- package/src/deps/jsr.io/@std/assert/1.0.8/not_match.ts +30 -0
- package/src/deps/jsr.io/@std/assert/1.0.8/not_strict_equals.ts +42 -0
- package/src/deps/jsr.io/@std/assert/1.0.8/rejects.ts +123 -0
- package/src/deps/jsr.io/@std/assert/1.0.8/strict_equals.ts +67 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_assert_equals.ts +38 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_assert_not_equals.ts +35 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_assertions.ts +18 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_asymmetric_matchers.ts +193 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_build_message.ts +51 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_custom_equality_tester.ts +19 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_equal.ts +230 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_extend.ts +16 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_inspect_args.ts +15 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_matchers.ts +832 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_mock_util.ts +22 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_serializer.ts +15 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_types.ts +919 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/_utils.ts +283 -0
- package/src/deps/jsr.io/@std/expect/1.0.8/expect.ts +620 -0
- package/src/deps/jsr.io/@std/internal/1.0.5/assertion_state.ts +214 -0
- package/src/deps/jsr.io/@std/internal/1.0.5/build_message.ts +134 -0
- package/src/deps/jsr.io/@std/internal/1.0.5/diff.ts +317 -0
- package/src/deps/jsr.io/@std/internal/1.0.5/diff_str.ts +204 -0
- package/src/deps/jsr.io/@std/internal/1.0.5/format.ts +39 -0
- package/src/deps/jsr.io/@std/internal/1.0.5/styles.ts +233 -0
- package/src/deps/jsr.io/@std/internal/1.0.5/types.ts +18 -0
- package/src/deps/jsr.io/@std/testing/1.0.5/_mock_utils.ts +43 -0
- package/src/deps/jsr.io/@std/testing/1.0.5/_test_suite.ts +410 -0
- package/src/deps/jsr.io/@std/testing/1.0.5/bdd.ts +1211 -0
- package/src/deps/jsr.io/@std/testing/1.0.5/mock.ts +1807 -0
- package/src/mod.ts +8 -0
- package/src/src/assets.ts +9 -0
- package/src/src/ast/_index.ts +66 -0
- package/src/src/ast/common.ts +1 -0
- package/src/src/ast/index.ts +1 -0
- package/src/src/ast/node.ts +10 -0
- package/src/src/ast/nodes/annotation.test.ts +69 -0
- package/src/src/ast/nodes/annotation.ts +79 -0
- package/src/src/ast/nodes/argument.test.ts +41 -0
- package/src/src/ast/nodes/argument.ts +62 -0
- package/src/src/ast/nodes/call.test.ts +44 -0
- package/src/src/ast/nodes/call.ts +66 -0
- package/src/src/ast/nodes/class.test.ts +274 -0
- package/src/src/ast/nodes/class.ts +178 -0
- package/src/src/ast/nodes/collection-literal.ts +49 -0
- package/src/src/ast/nodes/constructor.test.ts +178 -0
- package/src/src/ast/nodes/constructor.ts +126 -0
- package/src/src/ast/nodes/doc-tag.test.ts +84 -0
- package/src/src/ast/nodes/doc-tag.ts +138 -0
- package/src/src/ast/nodes/doc.test.ts +42 -0
- package/src/src/ast/nodes/doc.ts +111 -0
- package/src/src/ast/nodes/enum-value.test.ts +146 -0
- package/src/src/ast/nodes/enum-value.ts +100 -0
- package/src/src/ast/nodes/enum.test.ts +167 -0
- package/src/src/ast/nodes/enum.ts +163 -0
- package/src/src/ast/nodes/function.test.ts +194 -0
- package/src/src/ast/nodes/function.ts +176 -0
- package/src/src/ast/nodes/generic-parameter.test.ts +60 -0
- package/src/src/ast/nodes/generic-parameter.ts +54 -0
- package/src/src/ast/nodes/init-block.test.ts +36 -0
- package/src/src/ast/nodes/init-block.ts +38 -0
- package/src/src/ast/nodes/interface.test.ts +151 -0
- package/src/src/ast/nodes/interface.ts +133 -0
- package/src/src/ast/nodes/lambda-type.ts +68 -0
- package/src/src/ast/nodes/lambda.ts +68 -0
- package/src/src/ast/nodes/object.test.ts +101 -0
- package/src/src/ast/nodes/object.ts +102 -0
- package/src/src/ast/nodes/parameter.test.ts +191 -0
- package/src/src/ast/nodes/parameter.ts +118 -0
- package/src/src/ast/nodes/property.test.ts +253 -0
- package/src/src/ast/nodes/property.ts +225 -0
- package/src/src/ast/nodes/reference.test.ts +47 -0
- package/src/src/ast/nodes/reference.ts +178 -0
- package/src/src/ast/nodes/string.test.ts +61 -0
- package/src/src/ast/nodes/string.ts +114 -0
- package/src/src/ast/nodes/types.ts +23 -0
- package/src/src/ast/references/index.ts +8 -0
- package/src/src/ast/references/jackson.ts +16 -0
- package/src/src/ast/references/jakarta.ts +10 -0
- package/src/src/ast/references/java.ts +19 -0
- package/src/src/ast/references/kotlin.ts +40 -0
- package/src/src/ast/references/okhttp3.ts +5 -0
- package/src/src/ast/references/reactor.ts +5 -0
- package/src/src/ast/references/spring.ts +58 -0
- package/src/src/ast/references/swagger.ts +23 -0
- package/src/src/ast/utils/get-kotlin-builder-options.ts +19 -0
- package/src/src/ast/utils/to-kt-node.ts +31 -0
- package/src/src/ast/utils/write-kt-annotations.ts +15 -0
- package/src/src/ast/utils/write-kt-arguments.ts +45 -0
- package/src/src/ast/utils/write-kt-enum-values.ts +27 -0
- package/src/src/ast/utils/write-kt-generic-parameters.ts +12 -0
- package/src/src/ast/utils/write-kt-members.ts +25 -0
- package/src/src/ast/utils/write-kt-node.ts +37 -0
- package/src/src/ast/utils/write-kt-parameters.ts +25 -0
- package/src/src/common-results.ts +4 -0
- package/src/src/config.ts +41 -0
- package/src/src/file-builder.ts +108 -0
- package/src/src/generators/file-generator.ts +29 -0
- package/src/src/generators/index.ts +4 -0
- package/src/src/generators/models/args.ts +128 -0
- package/src/src/generators/models/index.ts +4 -0
- package/src/src/generators/models/model-generator.ts +602 -0
- package/src/src/generators/models/models-generator.ts +65 -0
- package/src/src/generators/models/models.ts +95 -0
- package/src/src/generators/services/okhttp3-clients/args.ts +78 -0
- package/src/src/generators/services/okhttp3-clients/index.ts +4 -0
- package/src/src/generators/services/okhttp3-clients/models.ts +60 -0
- package/src/src/generators/services/okhttp3-clients/okhttp3-client-generator.ts +557 -0
- package/src/src/generators/services/okhttp3-clients/okhttp3-clients-generator.ts +128 -0
- package/src/src/generators/services/okhttp3-clients/refs.ts +55 -0
- package/src/src/generators/services/spring-controllers/args.ts +73 -0
- package/src/src/generators/services/spring-controllers/index.ts +4 -0
- package/src/src/generators/services/spring-controllers/models.ts +58 -0
- package/src/src/generators/services/spring-controllers/spring-controller-generator.ts +653 -0
- package/src/src/generators/services/spring-controllers/spring-controllers-generator.ts +70 -0
- package/src/src/import-collection.test.ts +116 -0
- package/src/src/import-collection.ts +98 -0
- package/src/src/types.ts +3 -0
- package/src/src/utils.ts +39 -0
- package/src/tests/openapi-models.test.ts +63 -0
- package/test_runner.js +227 -0
|
@@ -0,0 +1,1807 @@
|
|
|
1
|
+
// Copyright 2018-2024 the Deno authors. All rights reserved. MIT license.
|
|
2
|
+
|
|
3
|
+
/** A mocking and spying library.
|
|
4
|
+
*
|
|
5
|
+
* Test spies are function stand-ins that are used to assert if a function's
|
|
6
|
+
* internal behavior matches expectations. Test spies on methods keep the original
|
|
7
|
+
* behavior but allow you to test how the method is called and what it returns.
|
|
8
|
+
* Test stubs are an extension of test spies that also replaces the original
|
|
9
|
+
* methods behavior.
|
|
10
|
+
*
|
|
11
|
+
* ## Spying
|
|
12
|
+
*
|
|
13
|
+
* Say we have two functions, `square` and `multiply`, if we want to assert that
|
|
14
|
+
* the `multiply` function is called during execution of the `square` function we
|
|
15
|
+
* need a way to spy on the `multiply` function. There are a few ways to achieve
|
|
16
|
+
* this with Spies, one is to have the `square` function take the `multiply`
|
|
17
|
+
* multiply as a parameter.
|
|
18
|
+
*
|
|
19
|
+
* This way, we can call `square(multiply, value)` in the application code or wrap
|
|
20
|
+
* a spy function around the `multiply` function and call
|
|
21
|
+
* `square(multiplySpy, value)` in the testing code.
|
|
22
|
+
*
|
|
23
|
+
* ```ts
|
|
24
|
+
* import {
|
|
25
|
+
* assertSpyCall,
|
|
26
|
+
* assertSpyCalls,
|
|
27
|
+
* spy,
|
|
28
|
+
* } from "@std/testing/mock";
|
|
29
|
+
* import { assertEquals } from "@std/assert";
|
|
30
|
+
*
|
|
31
|
+
* function multiply(a: number, b: number): number {
|
|
32
|
+
* return a * b;
|
|
33
|
+
* }
|
|
34
|
+
*
|
|
35
|
+
* function square(
|
|
36
|
+
* multiplyFn: (a: number, b: number) => number,
|
|
37
|
+
* value: number,
|
|
38
|
+
* ): number {
|
|
39
|
+
* return multiplyFn(value, value);
|
|
40
|
+
* }
|
|
41
|
+
*
|
|
42
|
+
* Deno.test("square calls multiply and returns results", () => {
|
|
43
|
+
* const multiplySpy = spy(multiply);
|
|
44
|
+
*
|
|
45
|
+
* assertEquals(square(multiplySpy, 5), 25);
|
|
46
|
+
*
|
|
47
|
+
* // asserts that multiplySpy was called at least once and details about the first call.
|
|
48
|
+
* assertSpyCall(multiplySpy, 0, {
|
|
49
|
+
* args: [5, 5],
|
|
50
|
+
* returned: 25,
|
|
51
|
+
* });
|
|
52
|
+
*
|
|
53
|
+
* // asserts that multiplySpy was only called once.
|
|
54
|
+
* assertSpyCalls(multiplySpy, 1);
|
|
55
|
+
* });
|
|
56
|
+
* ```
|
|
57
|
+
*
|
|
58
|
+
* If you prefer not adding additional parameters for testing purposes only, you
|
|
59
|
+
* can use spy to wrap a method on an object instead. In the following example, the
|
|
60
|
+
* exported `_internals` object has the `multiply` function we want to call as a
|
|
61
|
+
* method and the `square` function calls `_internals.multiply` instead of
|
|
62
|
+
* `multiply`.
|
|
63
|
+
*
|
|
64
|
+
* This way, we can call `square(value)` in both the application code and testing
|
|
65
|
+
* code. Then spy on the `multiply` method on the `_internals` object in the
|
|
66
|
+
* testing code to be able to spy on how the `square` function calls the `multiply`
|
|
67
|
+
* function.
|
|
68
|
+
*
|
|
69
|
+
* ```ts
|
|
70
|
+
* import {
|
|
71
|
+
* assertSpyCall,
|
|
72
|
+
* assertSpyCalls,
|
|
73
|
+
* spy,
|
|
74
|
+
* } from "@std/testing/mock";
|
|
75
|
+
* import { assertEquals } from "@std/assert";
|
|
76
|
+
*
|
|
77
|
+
* function multiply(a: number, b: number): number {
|
|
78
|
+
* return a * b;
|
|
79
|
+
* }
|
|
80
|
+
*
|
|
81
|
+
* function square(value: number): number {
|
|
82
|
+
* return _internals.multiply(value, value);
|
|
83
|
+
* }
|
|
84
|
+
*
|
|
85
|
+
* const _internals = { multiply };
|
|
86
|
+
*
|
|
87
|
+
* Deno.test("square calls multiply and returns results", () => {
|
|
88
|
+
* const multiplySpy = spy(_internals, "multiply");
|
|
89
|
+
*
|
|
90
|
+
* try {
|
|
91
|
+
* assertEquals(square(5), 25);
|
|
92
|
+
* } finally {
|
|
93
|
+
* // unwraps the multiply method on the _internals object
|
|
94
|
+
* multiplySpy.restore();
|
|
95
|
+
* }
|
|
96
|
+
*
|
|
97
|
+
* // asserts that multiplySpy was called at least once and details about the first call.
|
|
98
|
+
* assertSpyCall(multiplySpy, 0, {
|
|
99
|
+
* args: [5, 5],
|
|
100
|
+
* returned: 25,
|
|
101
|
+
* });
|
|
102
|
+
*
|
|
103
|
+
* // asserts that multiplySpy was only called once.
|
|
104
|
+
* assertSpyCalls(multiplySpy, 1);
|
|
105
|
+
* });
|
|
106
|
+
* ```
|
|
107
|
+
*
|
|
108
|
+
* One difference you may have noticed between these two examples is that in the
|
|
109
|
+
* second we call the `restore` method on `multiplySpy` function. That is needed to
|
|
110
|
+
* remove the spy wrapper from the `_internals` object's `multiply` method. The
|
|
111
|
+
* `restore` method is called in a finally block to ensure that it is restored
|
|
112
|
+
* whether or not the assertion in the try block is successful. The `restore`
|
|
113
|
+
* method didn't need to be called in the first example because the `multiply`
|
|
114
|
+
* function was not modified in any way like the `_internals` object was in the
|
|
115
|
+
* second example.
|
|
116
|
+
*
|
|
117
|
+
* Method spys are disposable, meaning that you can have them automatically restore
|
|
118
|
+
* themselves with the `using` keyword. Using this approach is cleaner because you
|
|
119
|
+
* do not need to wrap your assertions in a try statement to ensure you restore the
|
|
120
|
+
* methods before the tests finish.
|
|
121
|
+
*
|
|
122
|
+
* ```ts
|
|
123
|
+
* import {
|
|
124
|
+
* assertSpyCall,
|
|
125
|
+
* assertSpyCalls,
|
|
126
|
+
* spy,
|
|
127
|
+
* } from "@std/testing/mock";
|
|
128
|
+
* import { assertEquals } from "@std/assert";
|
|
129
|
+
*
|
|
130
|
+
* function multiply(a: number, b: number): number {
|
|
131
|
+
* return a * b;
|
|
132
|
+
* }
|
|
133
|
+
*
|
|
134
|
+
* function square(value: number): number {
|
|
135
|
+
* return _internals.multiply(value, value);
|
|
136
|
+
* }
|
|
137
|
+
*
|
|
138
|
+
* const _internals = { multiply };
|
|
139
|
+
*
|
|
140
|
+
* Deno.test("square calls multiply and returns results", () => {
|
|
141
|
+
* using multiplySpy = spy(_internals, "multiply");
|
|
142
|
+
*
|
|
143
|
+
* assertEquals(square(5), 25);
|
|
144
|
+
*
|
|
145
|
+
* // asserts that multiplySpy was called at least once and details about the first call.
|
|
146
|
+
* assertSpyCall(multiplySpy, 0, {
|
|
147
|
+
* args: [5, 5],
|
|
148
|
+
* returned: 25,
|
|
149
|
+
* });
|
|
150
|
+
*
|
|
151
|
+
* // asserts that multiplySpy was only called once.
|
|
152
|
+
* assertSpyCalls(multiplySpy, 1);
|
|
153
|
+
* });
|
|
154
|
+
* ```
|
|
155
|
+
*
|
|
156
|
+
* ## Stubbing
|
|
157
|
+
*
|
|
158
|
+
* Say we have two functions, `randomMultiple` and `randomInt`, if we want to
|
|
159
|
+
* assert that `randomInt` is called during execution of `randomMultiple` we need a
|
|
160
|
+
* way to spy on the `randomInt` function. That could be done with either of the
|
|
161
|
+
* spying techniques previously mentioned. To be able to verify that the
|
|
162
|
+
* `randomMultiple` function returns the value we expect it to for what `randomInt`
|
|
163
|
+
* returns, the easiest way would be to replace the `randomInt` function's behavior
|
|
164
|
+
* with more predictable behavior.
|
|
165
|
+
*
|
|
166
|
+
* You could use the first spying technique to do that but that would require
|
|
167
|
+
* adding a `randomInt` parameter to the `randomMultiple` function.
|
|
168
|
+
*
|
|
169
|
+
* You could also use the second spying technique to do that, but your assertions
|
|
170
|
+
* would not be as predictable due to the `randomInt` function returning random
|
|
171
|
+
* values.
|
|
172
|
+
*
|
|
173
|
+
* Say we want to verify it returns correct values for both negative and positive
|
|
174
|
+
* random integers. We could easily do that with stubbing. The below example is
|
|
175
|
+
* similar to the second spying technique example but instead of passing the call
|
|
176
|
+
* through to the original `randomInt` function, we are going to replace
|
|
177
|
+
* `randomInt` with a function that returns pre-defined values.
|
|
178
|
+
*
|
|
179
|
+
* The mock module includes some helper functions to make creating common stubs
|
|
180
|
+
* easy. The `returnsNext` function takes an array of values we want it to return
|
|
181
|
+
* on consecutive calls.
|
|
182
|
+
*
|
|
183
|
+
* ```ts
|
|
184
|
+
* import {
|
|
185
|
+
* assertSpyCall,
|
|
186
|
+
* assertSpyCalls,
|
|
187
|
+
* returnsNext,
|
|
188
|
+
* stub,
|
|
189
|
+
* } from "@std/testing/mock";
|
|
190
|
+
* import { assertEquals } from "@std/assert";
|
|
191
|
+
*
|
|
192
|
+
* function randomInt(lowerBound: number, upperBound: number): number {
|
|
193
|
+
* return lowerBound + Math.floor(Math.random() * (upperBound - lowerBound));
|
|
194
|
+
* }
|
|
195
|
+
*
|
|
196
|
+
* function randomMultiple(value: number): number {
|
|
197
|
+
* return value * _internals.randomInt(-10, 10);
|
|
198
|
+
* }
|
|
199
|
+
*
|
|
200
|
+
* const _internals = { randomInt };
|
|
201
|
+
*
|
|
202
|
+
* Deno.test("randomMultiple uses randomInt to generate random multiples between -10 and 10 times the value", () => {
|
|
203
|
+
* const randomIntStub = stub(_internals, "randomInt", returnsNext([-3, 3]));
|
|
204
|
+
*
|
|
205
|
+
* try {
|
|
206
|
+
* assertEquals(randomMultiple(5), -15);
|
|
207
|
+
* assertEquals(randomMultiple(5), 15);
|
|
208
|
+
* } finally {
|
|
209
|
+
* // unwraps the randomInt method on the _internals object
|
|
210
|
+
* randomIntStub.restore();
|
|
211
|
+
* }
|
|
212
|
+
*
|
|
213
|
+
* // asserts that randomIntStub was called at least once and details about the first call.
|
|
214
|
+
* assertSpyCall(randomIntStub, 0, {
|
|
215
|
+
* args: [-10, 10],
|
|
216
|
+
* returned: -3,
|
|
217
|
+
* });
|
|
218
|
+
* // asserts that randomIntStub was called at least twice and details about the second call.
|
|
219
|
+
* assertSpyCall(randomIntStub, 1, {
|
|
220
|
+
* args: [-10, 10],
|
|
221
|
+
* returned: 3,
|
|
222
|
+
* });
|
|
223
|
+
*
|
|
224
|
+
* // asserts that randomIntStub was only called twice.
|
|
225
|
+
* assertSpyCalls(randomIntStub, 2);
|
|
226
|
+
* });
|
|
227
|
+
* ```
|
|
228
|
+
*
|
|
229
|
+
* Like method spys, stubs are disposable, meaning that you can have them automatically
|
|
230
|
+
* restore themselves with the `using` keyword. Using this approach is cleaner because
|
|
231
|
+
* you do not need to wrap your assertions in a try statement to ensure you restore the
|
|
232
|
+
* methods before the tests finish.
|
|
233
|
+
*
|
|
234
|
+
* ```ts
|
|
235
|
+
* import {
|
|
236
|
+
* assertSpyCall,
|
|
237
|
+
* assertSpyCalls,
|
|
238
|
+
* returnsNext,
|
|
239
|
+
* stub,
|
|
240
|
+
* } from "@std/testing/mock";
|
|
241
|
+
* import { assertEquals } from "@std/assert";
|
|
242
|
+
*
|
|
243
|
+
* function randomInt(lowerBound: number, upperBound: number): number {
|
|
244
|
+
* return lowerBound + Math.floor(Math.random() * (upperBound - lowerBound));
|
|
245
|
+
* }
|
|
246
|
+
*
|
|
247
|
+
* function randomMultiple(value: number): number {
|
|
248
|
+
* return value * _internals.randomInt(-10, 10);
|
|
249
|
+
* }
|
|
250
|
+
*
|
|
251
|
+
* const _internals = { randomInt };
|
|
252
|
+
*
|
|
253
|
+
* Deno.test("randomMultiple uses randomInt to generate random multiples between -10 and 10 times the value", () => {
|
|
254
|
+
* using randomIntStub = stub(_internals, "randomInt", returnsNext([-3, 3]));
|
|
255
|
+
*
|
|
256
|
+
* assertEquals(randomMultiple(5), -15);
|
|
257
|
+
* assertEquals(randomMultiple(5), 15);
|
|
258
|
+
*
|
|
259
|
+
* // asserts that randomIntStub was called at least once and details about the first call.
|
|
260
|
+
* assertSpyCall(randomIntStub, 0, {
|
|
261
|
+
* args: [-10, 10],
|
|
262
|
+
* returned: -3,
|
|
263
|
+
* });
|
|
264
|
+
* // asserts that randomIntStub was called at least twice and details about the second call.
|
|
265
|
+
* assertSpyCall(randomIntStub, 1, {
|
|
266
|
+
* args: [-10, 10],
|
|
267
|
+
* returned: 3,
|
|
268
|
+
* });
|
|
269
|
+
*
|
|
270
|
+
* // asserts that randomIntStub was only called twice.
|
|
271
|
+
* assertSpyCalls(randomIntStub, 2);
|
|
272
|
+
* });
|
|
273
|
+
* ```
|
|
274
|
+
*
|
|
275
|
+
* ## Faking time
|
|
276
|
+
*
|
|
277
|
+
* Say we have a function that has time based behavior that we would like to test.
|
|
278
|
+
* With real time, that could cause tests to take much longer than they should. If
|
|
279
|
+
* you fake time, you could simulate how your function would behave over time
|
|
280
|
+
* starting from any point in time. Below is an example where we want to test that
|
|
281
|
+
* the callback is called every second.
|
|
282
|
+
*
|
|
283
|
+
* With `FakeTime` we can do that. When the `FakeTime` instance is created, it
|
|
284
|
+
* splits from real time. The `Date`, `setTimeout`, `clearTimeout`, `setInterval`
|
|
285
|
+
* and `clearInterval` globals are replaced with versions that use the fake time
|
|
286
|
+
* until real time is restored. You can control how time ticks forward with the
|
|
287
|
+
* `tick` method on the `FakeTime` instance.
|
|
288
|
+
*
|
|
289
|
+
* ```ts
|
|
290
|
+
* import {
|
|
291
|
+
* assertSpyCalls,
|
|
292
|
+
* spy,
|
|
293
|
+
* } from "@std/testing/mock";
|
|
294
|
+
* import { FakeTime } from "@std/testing/time";
|
|
295
|
+
*
|
|
296
|
+
* function secondInterval(cb: () => void): number {
|
|
297
|
+
* return setInterval(cb, 1000);
|
|
298
|
+
* }
|
|
299
|
+
*
|
|
300
|
+
* Deno.test("secondInterval calls callback every second and stops after being cleared", () => {
|
|
301
|
+
* using time = new FakeTime();
|
|
302
|
+
*
|
|
303
|
+
* const cb = spy();
|
|
304
|
+
* const intervalId = secondInterval(cb);
|
|
305
|
+
* assertSpyCalls(cb, 0);
|
|
306
|
+
* time.tick(500);
|
|
307
|
+
* assertSpyCalls(cb, 0);
|
|
308
|
+
* time.tick(500);
|
|
309
|
+
* assertSpyCalls(cb, 1);
|
|
310
|
+
* time.tick(3500);
|
|
311
|
+
* assertSpyCalls(cb, 4);
|
|
312
|
+
*
|
|
313
|
+
* clearInterval(intervalId);
|
|
314
|
+
* time.tick(1000);
|
|
315
|
+
* assertSpyCalls(cb, 4);
|
|
316
|
+
* });
|
|
317
|
+
* ```
|
|
318
|
+
*
|
|
319
|
+
* @module
|
|
320
|
+
*/
|
|
321
|
+
|
|
322
|
+
import { assertEquals } from "../../assert/1.0.8/equals.js";
|
|
323
|
+
import { assertIsError } from "../../assert/1.0.8/is_error.js";
|
|
324
|
+
import { assertRejects } from "../../assert/1.0.8/rejects.js";
|
|
325
|
+
import { AssertionError } from "../../assert/1.0.8/assertion_error.js";
|
|
326
|
+
import {
|
|
327
|
+
isSpy,
|
|
328
|
+
registerMock,
|
|
329
|
+
sessions,
|
|
330
|
+
unregisterMock,
|
|
331
|
+
} from "./_mock_utils.js";
|
|
332
|
+
|
|
333
|
+
/**
|
|
334
|
+
* An error related to spying on a function or instance method.
|
|
335
|
+
*
|
|
336
|
+
* @example Usage
|
|
337
|
+
* ```ts
|
|
338
|
+
* import { MockError, spy } from "@std/testing/mock";
|
|
339
|
+
* import { assertThrows } from "@std/assert";
|
|
340
|
+
*
|
|
341
|
+
* assertThrows(() => {
|
|
342
|
+
* spy({} as any, "no-such-method");
|
|
343
|
+
* }, MockError);
|
|
344
|
+
* ```
|
|
345
|
+
*/
|
|
346
|
+
export class MockError extends Error {
|
|
347
|
+
/**
|
|
348
|
+
* Construct MockError
|
|
349
|
+
*
|
|
350
|
+
* @param message The error message.
|
|
351
|
+
*/
|
|
352
|
+
constructor(message: string) {
|
|
353
|
+
super(message);
|
|
354
|
+
this.name = "MockError";
|
|
355
|
+
}
|
|
356
|
+
}
|
|
357
|
+
|
|
358
|
+
/** Call information recorded by a spy. */
|
|
359
|
+
export interface SpyCall<
|
|
360
|
+
// deno-lint-ignore no-explicit-any
|
|
361
|
+
Self = any,
|
|
362
|
+
// deno-lint-ignore no-explicit-any
|
|
363
|
+
Args extends unknown[] = any[],
|
|
364
|
+
// deno-lint-ignore no-explicit-any
|
|
365
|
+
Return = any,
|
|
366
|
+
> {
|
|
367
|
+
/** Arguments passed to a function when called. */
|
|
368
|
+
args: Args;
|
|
369
|
+
/** The value that was returned by a function. */
|
|
370
|
+
returned?: Return;
|
|
371
|
+
/** The error value that was thrown by a function. */
|
|
372
|
+
error?: Error;
|
|
373
|
+
/** The instance that a method was called on. */
|
|
374
|
+
self?: Self;
|
|
375
|
+
}
|
|
376
|
+
|
|
377
|
+
/** A function or instance method wrapper that records all calls made to it. */
|
|
378
|
+
export interface Spy<
|
|
379
|
+
// deno-lint-ignore no-explicit-any
|
|
380
|
+
Self = any,
|
|
381
|
+
// deno-lint-ignore no-explicit-any
|
|
382
|
+
Args extends unknown[] = any[],
|
|
383
|
+
// deno-lint-ignore no-explicit-any
|
|
384
|
+
Return = any,
|
|
385
|
+
> {
|
|
386
|
+
(this: Self, ...args: Args): Return;
|
|
387
|
+
/** The function that is being spied on. */
|
|
388
|
+
original: (this: Self, ...args: Args) => Return;
|
|
389
|
+
/** Information about calls made to the function or instance method. */
|
|
390
|
+
calls: SpyCall<Self, Args, Return>[];
|
|
391
|
+
/** Whether or not the original instance method has been restored. */
|
|
392
|
+
restored: boolean;
|
|
393
|
+
/** If spying on an instance method, this restores the original instance method. */
|
|
394
|
+
restore(): void;
|
|
395
|
+
}
|
|
396
|
+
|
|
397
|
+
/** An instance method wrapper that records all calls made to it. */
|
|
398
|
+
export interface MethodSpy<
|
|
399
|
+
// deno-lint-ignore no-explicit-any
|
|
400
|
+
Self = any,
|
|
401
|
+
// deno-lint-ignore no-explicit-any
|
|
402
|
+
Args extends unknown[] = any[],
|
|
403
|
+
// deno-lint-ignore no-explicit-any
|
|
404
|
+
Return = any,
|
|
405
|
+
> extends Spy<Self, Args, Return>, Disposable {}
|
|
406
|
+
|
|
407
|
+
/** Wraps a function with a Spy. */
|
|
408
|
+
function functionSpy<
|
|
409
|
+
Self,
|
|
410
|
+
Args extends unknown[],
|
|
411
|
+
Return,
|
|
412
|
+
>(func?: (this: Self, ...args: Args) => Return): Spy<Self, Args, Return> {
|
|
413
|
+
const original = func ?? (() => {}) as (this: Self, ...args: Args) => Return;
|
|
414
|
+
const calls: SpyCall<Self, Args, Return>[] = [];
|
|
415
|
+
const spy = function (this: Self, ...args: Args): Return {
|
|
416
|
+
const call: SpyCall<Self, Args, Return> = { args };
|
|
417
|
+
if (this) call.self = this;
|
|
418
|
+
try {
|
|
419
|
+
call.returned = original.apply(this, args);
|
|
420
|
+
} catch (error) {
|
|
421
|
+
call.error = error as Error;
|
|
422
|
+
calls.push(call);
|
|
423
|
+
throw error;
|
|
424
|
+
}
|
|
425
|
+
calls.push(call);
|
|
426
|
+
return call.returned;
|
|
427
|
+
} as Spy<Self, Args, Return>;
|
|
428
|
+
Object.defineProperties(spy, {
|
|
429
|
+
original: {
|
|
430
|
+
enumerable: true,
|
|
431
|
+
value: original,
|
|
432
|
+
},
|
|
433
|
+
calls: {
|
|
434
|
+
enumerable: true,
|
|
435
|
+
value: calls,
|
|
436
|
+
},
|
|
437
|
+
restored: {
|
|
438
|
+
enumerable: true,
|
|
439
|
+
get: () => false,
|
|
440
|
+
},
|
|
441
|
+
restore: {
|
|
442
|
+
enumerable: true,
|
|
443
|
+
value: () => {
|
|
444
|
+
throw new MockError(
|
|
445
|
+
"Cannot restore: function cannot be restored",
|
|
446
|
+
);
|
|
447
|
+
},
|
|
448
|
+
},
|
|
449
|
+
});
|
|
450
|
+
return spy;
|
|
451
|
+
}
|
|
452
|
+
|
|
453
|
+
/**
|
|
454
|
+
* Creates a session that tracks all mocks created before it's restored.
|
|
455
|
+
* If a callback is provided, it restores all mocks created within it.
|
|
456
|
+
*
|
|
457
|
+
* @example Usage
|
|
458
|
+
* ```ts
|
|
459
|
+
* import { mockSession, restore, stub } from "@std/testing/mock";
|
|
460
|
+
* import { assertEquals, assertNotEquals } from "@std/assert";
|
|
461
|
+
*
|
|
462
|
+
* const setTimeout = globalThis.setTimeout;
|
|
463
|
+
* const id = mockSession();
|
|
464
|
+
*
|
|
465
|
+
* stub(globalThis, "setTimeout");
|
|
466
|
+
*
|
|
467
|
+
* assertNotEquals(globalThis.setTimeout, setTimeout);
|
|
468
|
+
*
|
|
469
|
+
* restore(id);
|
|
470
|
+
*
|
|
471
|
+
* assertEquals(globalThis.setTimeout, setTimeout);
|
|
472
|
+
* ```
|
|
473
|
+
*
|
|
474
|
+
* @returns The id of the created session.
|
|
475
|
+
*/
|
|
476
|
+
export function mockSession(): number;
|
|
477
|
+
/**
|
|
478
|
+
* Creates a session that tracks all mocks created before it's restored.
|
|
479
|
+
* If a callback is provided, it restores all mocks created within it.
|
|
480
|
+
*
|
|
481
|
+
* @example Usage
|
|
482
|
+
* ```ts
|
|
483
|
+
* import { mockSession, restore, stub } from "@std/testing/mock";
|
|
484
|
+
* import { assertEquals, assertNotEquals } from "@std/assert";
|
|
485
|
+
*
|
|
486
|
+
* const setTimeout = globalThis.setTimeout;
|
|
487
|
+
* const session = mockSession(() => {
|
|
488
|
+
* stub(globalThis, "setTimeout");
|
|
489
|
+
* assertNotEquals(globalThis.setTimeout, setTimeout);
|
|
490
|
+
* });
|
|
491
|
+
*
|
|
492
|
+
* session();
|
|
493
|
+
*
|
|
494
|
+
* assertEquals(globalThis.setTimeout, setTimeout); // stub is restored
|
|
495
|
+
* ```
|
|
496
|
+
*
|
|
497
|
+
* @typeParam Self The self type of the function.
|
|
498
|
+
* @typeParam Args The arguments type of the function.
|
|
499
|
+
* @typeParam Return The return type of the function.
|
|
500
|
+
* @param func The function to be used for the created session.
|
|
501
|
+
* @returns The function to execute the session.
|
|
502
|
+
*/
|
|
503
|
+
export function mockSession<
|
|
504
|
+
Self,
|
|
505
|
+
Args extends unknown[],
|
|
506
|
+
Return,
|
|
507
|
+
>(
|
|
508
|
+
func: (this: Self, ...args: Args) => Return,
|
|
509
|
+
): (this: Self, ...args: Args) => Return;
|
|
510
|
+
export function mockSession<
|
|
511
|
+
Self,
|
|
512
|
+
Args extends unknown[],
|
|
513
|
+
Return,
|
|
514
|
+
>(
|
|
515
|
+
func?: (this: Self, ...args: Args) => Return,
|
|
516
|
+
): number | ((this: Self, ...args: Args) => Return) {
|
|
517
|
+
if (func) {
|
|
518
|
+
return function (this: Self, ...args: Args): Return {
|
|
519
|
+
const id = sessions.length;
|
|
520
|
+
sessions.push(new Set());
|
|
521
|
+
try {
|
|
522
|
+
return func.apply(this, args);
|
|
523
|
+
} finally {
|
|
524
|
+
restore(id);
|
|
525
|
+
}
|
|
526
|
+
};
|
|
527
|
+
} else {
|
|
528
|
+
sessions.push(new Set());
|
|
529
|
+
return sessions.length - 1;
|
|
530
|
+
}
|
|
531
|
+
}
|
|
532
|
+
|
|
533
|
+
/**
|
|
534
|
+
* Creates an async session that tracks all mocks created before the promise resolves.
|
|
535
|
+
*
|
|
536
|
+
* @example Usage
|
|
537
|
+
* ```ts
|
|
538
|
+
* import { mockSessionAsync, restore, stub } from "@std/testing/mock";
|
|
539
|
+
* import { assertEquals, assertNotEquals } from "@std/assert";
|
|
540
|
+
*
|
|
541
|
+
* const setTimeout = globalThis.setTimeout;
|
|
542
|
+
* const session = mockSessionAsync(async () => {
|
|
543
|
+
* stub(globalThis, "setTimeout");
|
|
544
|
+
* assertNotEquals(globalThis.setTimeout, setTimeout);
|
|
545
|
+
* });
|
|
546
|
+
*
|
|
547
|
+
* await session();
|
|
548
|
+
*
|
|
549
|
+
* assertEquals(globalThis.setTimeout, setTimeout); // stub is restored
|
|
550
|
+
* ```
|
|
551
|
+
* @typeParam Self The self type of the function.
|
|
552
|
+
* @typeParam Args The arguments type of the function.
|
|
553
|
+
* @typeParam Return The return type of the function.
|
|
554
|
+
* @param func The function.
|
|
555
|
+
* @returns The return value of the function.
|
|
556
|
+
*/
|
|
557
|
+
export function mockSessionAsync<
|
|
558
|
+
Self,
|
|
559
|
+
Args extends unknown[],
|
|
560
|
+
Return,
|
|
561
|
+
>(
|
|
562
|
+
func: (this: Self, ...args: Args) => Promise<Return>,
|
|
563
|
+
): (this: Self, ...args: Args) => Promise<Return> {
|
|
564
|
+
return async function (this: Self, ...args: Args): Promise<Return> {
|
|
565
|
+
const id = sessions.length;
|
|
566
|
+
sessions.push(new Set());
|
|
567
|
+
try {
|
|
568
|
+
return await func.apply(this, args);
|
|
569
|
+
} finally {
|
|
570
|
+
restore(id);
|
|
571
|
+
}
|
|
572
|
+
};
|
|
573
|
+
}
|
|
574
|
+
|
|
575
|
+
/**
|
|
576
|
+
* Restores all mocks registered in the current session that have not already been restored.
|
|
577
|
+
* If an id is provided, it will restore all mocks registered in the session associed with that id that have not already been restored.
|
|
578
|
+
*
|
|
579
|
+
* @example Usage
|
|
580
|
+
* ```ts
|
|
581
|
+
* import { mockSession, restore, stub } from "@std/testing/mock";
|
|
582
|
+
* import { assertEquals, assertNotEquals } from "@std/assert";
|
|
583
|
+
*
|
|
584
|
+
* const setTimeout = globalThis.setTimeout;
|
|
585
|
+
*
|
|
586
|
+
* stub(globalThis, "setTimeout");
|
|
587
|
+
*
|
|
588
|
+
* assertNotEquals(globalThis.setTimeout, setTimeout);
|
|
589
|
+
*
|
|
590
|
+
* restore();
|
|
591
|
+
*
|
|
592
|
+
* assertEquals(globalThis.setTimeout, setTimeout);
|
|
593
|
+
* ```
|
|
594
|
+
*
|
|
595
|
+
* @param id The id of the session to restore. If not provided, all mocks registered in the current session are restored.
|
|
596
|
+
*/
|
|
597
|
+
export function restore(id?: number) {
|
|
598
|
+
id ??= (sessions.length || 1) - 1;
|
|
599
|
+
while (id < sessions.length) {
|
|
600
|
+
const session = sessions.pop();
|
|
601
|
+
if (session) {
|
|
602
|
+
for (const value of session) {
|
|
603
|
+
value.restore();
|
|
604
|
+
}
|
|
605
|
+
}
|
|
606
|
+
}
|
|
607
|
+
}
|
|
608
|
+
|
|
609
|
+
/** Wraps an instance method with a Spy. */
|
|
610
|
+
function methodSpy<
|
|
611
|
+
Self,
|
|
612
|
+
Args extends unknown[],
|
|
613
|
+
Return,
|
|
614
|
+
>(self: Self, property: keyof Self): MethodSpy<Self, Args, Return> {
|
|
615
|
+
if (typeof self[property] !== "function") {
|
|
616
|
+
throw new MockError(
|
|
617
|
+
"Cannot spy: property is not an instance method",
|
|
618
|
+
);
|
|
619
|
+
}
|
|
620
|
+
if (isSpy(self[property])) {
|
|
621
|
+
throw new MockError(
|
|
622
|
+
"Cannot spy: already spying on instance method",
|
|
623
|
+
);
|
|
624
|
+
}
|
|
625
|
+
|
|
626
|
+
const propertyDescriptor = Object.getOwnPropertyDescriptor(self, property);
|
|
627
|
+
if (propertyDescriptor && !propertyDescriptor.configurable) {
|
|
628
|
+
throw new MockError(
|
|
629
|
+
"Cannot spy: non-configurable instance method",
|
|
630
|
+
);
|
|
631
|
+
}
|
|
632
|
+
|
|
633
|
+
const original = self[property] as unknown as (
|
|
634
|
+
this: Self,
|
|
635
|
+
...args: Args
|
|
636
|
+
) => Return;
|
|
637
|
+
const calls: SpyCall<Self, Args, Return>[] = [];
|
|
638
|
+
let restored = false;
|
|
639
|
+
const spy = function (this: Self, ...args: Args): Return {
|
|
640
|
+
const call: SpyCall<Self, Args, Return> = { args };
|
|
641
|
+
if (this) call.self = this;
|
|
642
|
+
try {
|
|
643
|
+
call.returned = original.apply(this, args);
|
|
644
|
+
} catch (error) {
|
|
645
|
+
call.error = error as Error;
|
|
646
|
+
calls.push(call);
|
|
647
|
+
throw error;
|
|
648
|
+
}
|
|
649
|
+
calls.push(call);
|
|
650
|
+
return call.returned;
|
|
651
|
+
} as MethodSpy<Self, Args, Return>;
|
|
652
|
+
Object.defineProperties(spy, {
|
|
653
|
+
original: {
|
|
654
|
+
enumerable: true,
|
|
655
|
+
value: original,
|
|
656
|
+
},
|
|
657
|
+
calls: {
|
|
658
|
+
enumerable: true,
|
|
659
|
+
value: calls,
|
|
660
|
+
},
|
|
661
|
+
restored: {
|
|
662
|
+
enumerable: true,
|
|
663
|
+
get: () => restored,
|
|
664
|
+
},
|
|
665
|
+
restore: {
|
|
666
|
+
enumerable: true,
|
|
667
|
+
value: () => {
|
|
668
|
+
if (restored) {
|
|
669
|
+
throw new MockError(
|
|
670
|
+
"Cannot restore: instance method already restored",
|
|
671
|
+
);
|
|
672
|
+
}
|
|
673
|
+
if (propertyDescriptor) {
|
|
674
|
+
Object.defineProperty(self, property, propertyDescriptor);
|
|
675
|
+
} else {
|
|
676
|
+
delete self[property];
|
|
677
|
+
}
|
|
678
|
+
restored = true;
|
|
679
|
+
unregisterMock(spy);
|
|
680
|
+
},
|
|
681
|
+
},
|
|
682
|
+
[Symbol.dispose]: {
|
|
683
|
+
value: () => {
|
|
684
|
+
spy.restore();
|
|
685
|
+
},
|
|
686
|
+
},
|
|
687
|
+
});
|
|
688
|
+
|
|
689
|
+
Object.defineProperty(self, property, {
|
|
690
|
+
configurable: true,
|
|
691
|
+
enumerable: propertyDescriptor?.enumerable ?? false,
|
|
692
|
+
writable: propertyDescriptor?.writable ?? false,
|
|
693
|
+
value: spy,
|
|
694
|
+
});
|
|
695
|
+
|
|
696
|
+
registerMock(spy);
|
|
697
|
+
return spy;
|
|
698
|
+
}
|
|
699
|
+
|
|
700
|
+
/** A constructor wrapper that records all calls made to it. */
|
|
701
|
+
export interface ConstructorSpy<
|
|
702
|
+
// deno-lint-ignore no-explicit-any
|
|
703
|
+
Self = any,
|
|
704
|
+
// deno-lint-ignore no-explicit-any
|
|
705
|
+
Args extends unknown[] = any[],
|
|
706
|
+
> {
|
|
707
|
+
/** Construct an instance. */
|
|
708
|
+
new (...args: Args): Self;
|
|
709
|
+
/** The function that is being spied on. */
|
|
710
|
+
original: new (...args: Args) => Self;
|
|
711
|
+
/** Information about calls made to the function or instance method. */
|
|
712
|
+
calls: SpyCall<Self, Args, Self>[];
|
|
713
|
+
/** Whether or not the original instance method has been restored. */
|
|
714
|
+
restored: boolean;
|
|
715
|
+
/** If spying on an instance method, this restores the original instance method. */
|
|
716
|
+
restore(): void;
|
|
717
|
+
}
|
|
718
|
+
|
|
719
|
+
/** Wraps a constructor with a Spy. */
|
|
720
|
+
function constructorSpy<
|
|
721
|
+
Self,
|
|
722
|
+
Args extends unknown[],
|
|
723
|
+
>(
|
|
724
|
+
constructor: new (...args: Args) => Self,
|
|
725
|
+
): ConstructorSpy<Self, Args> {
|
|
726
|
+
const original = constructor;
|
|
727
|
+
const calls: SpyCall<Self, Args, Self>[] = [];
|
|
728
|
+
// @ts-ignore TS2509: Can't know the type of `original` statically.
|
|
729
|
+
const spy = class extends original {
|
|
730
|
+
// deno-lint-ignore constructor-super
|
|
731
|
+
constructor(...args: Args) {
|
|
732
|
+
const call: SpyCall<Self, Args, Self> = { args };
|
|
733
|
+
try {
|
|
734
|
+
super(...args);
|
|
735
|
+
call.returned = this as unknown as Self;
|
|
736
|
+
} catch (error) {
|
|
737
|
+
call.error = error as Error;
|
|
738
|
+
calls.push(call);
|
|
739
|
+
throw error;
|
|
740
|
+
}
|
|
741
|
+
calls.push(call);
|
|
742
|
+
}
|
|
743
|
+
static readonly name = original.name;
|
|
744
|
+
static readonly original = original;
|
|
745
|
+
static readonly calls = calls;
|
|
746
|
+
static readonly restored = false;
|
|
747
|
+
static restore() {
|
|
748
|
+
throw new MockError(
|
|
749
|
+
"Cannot restore: constructor cannot be restored",
|
|
750
|
+
);
|
|
751
|
+
}
|
|
752
|
+
} as ConstructorSpy<Self, Args>;
|
|
753
|
+
return spy;
|
|
754
|
+
}
|
|
755
|
+
|
|
756
|
+
/**
|
|
757
|
+
* Utility for extracting the arguments type from a property
|
|
758
|
+
*
|
|
759
|
+
* @internal
|
|
760
|
+
*/
|
|
761
|
+
export type GetParametersFromProp<
|
|
762
|
+
Self,
|
|
763
|
+
Prop extends keyof Self,
|
|
764
|
+
> = Self[Prop] extends (...args: infer Args) => unknown ? Args
|
|
765
|
+
: unknown[];
|
|
766
|
+
|
|
767
|
+
/**
|
|
768
|
+
* Utility for extracting the return type from a property
|
|
769
|
+
*
|
|
770
|
+
* @internal
|
|
771
|
+
*/
|
|
772
|
+
export type GetReturnFromProp<
|
|
773
|
+
Self,
|
|
774
|
+
Prop extends keyof Self,
|
|
775
|
+
> // deno-lint-ignore no-explicit-any
|
|
776
|
+
= Self[Prop] extends (...args: any[]) => infer Return ? Return
|
|
777
|
+
: unknown;
|
|
778
|
+
|
|
779
|
+
/** SpyLink object type. */
|
|
780
|
+
export type SpyLike<
|
|
781
|
+
// deno-lint-ignore no-explicit-any
|
|
782
|
+
Self = any,
|
|
783
|
+
// deno-lint-ignore no-explicit-any
|
|
784
|
+
Args extends unknown[] = any[],
|
|
785
|
+
// deno-lint-ignore no-explicit-any
|
|
786
|
+
Return = any,
|
|
787
|
+
> = Spy<Self, Args, Return> | ConstructorSpy<Self, Args>;
|
|
788
|
+
|
|
789
|
+
/** Creates a spy function.
|
|
790
|
+
*
|
|
791
|
+
* @example Usage
|
|
792
|
+
* ```ts
|
|
793
|
+
* import {
|
|
794
|
+
* assertSpyCall,
|
|
795
|
+
* assertSpyCalls,
|
|
796
|
+
* spy,
|
|
797
|
+
* } from "@std/testing/mock";
|
|
798
|
+
*
|
|
799
|
+
* const func = spy();
|
|
800
|
+
*
|
|
801
|
+
* func();
|
|
802
|
+
* func(1);
|
|
803
|
+
* func(2, 3);
|
|
804
|
+
*
|
|
805
|
+
* assertSpyCalls(func, 3);
|
|
806
|
+
*
|
|
807
|
+
* // asserts each call made to the spy function.
|
|
808
|
+
* assertSpyCall(func, 0, { args: [] });
|
|
809
|
+
* assertSpyCall(func, 1, { args: [1] });
|
|
810
|
+
* assertSpyCall(func, 2, { args: [2, 3] });
|
|
811
|
+
* ```
|
|
812
|
+
*
|
|
813
|
+
* @typeParam Self The self type of the function.
|
|
814
|
+
* @typeParam Args The arguments type of the function.
|
|
815
|
+
* @typeParam Return The return type of the function.
|
|
816
|
+
* @returns The spy function.
|
|
817
|
+
*/
|
|
818
|
+
export function spy<
|
|
819
|
+
// deno-lint-ignore no-explicit-any
|
|
820
|
+
Self = any,
|
|
821
|
+
// deno-lint-ignore no-explicit-any
|
|
822
|
+
Args extends unknown[] = any[],
|
|
823
|
+
Return = undefined,
|
|
824
|
+
>(): Spy<Self, Args, Return>;
|
|
825
|
+
/**
|
|
826
|
+
* Create a spy function with the given implementation.
|
|
827
|
+
*
|
|
828
|
+
* @example Usage
|
|
829
|
+
* ```ts
|
|
830
|
+
* import {
|
|
831
|
+
* assertSpyCall,
|
|
832
|
+
* assertSpyCalls,
|
|
833
|
+
* spy,
|
|
834
|
+
* } from "@std/testing/mock";
|
|
835
|
+
*
|
|
836
|
+
* const func = spy((a: number, b: number) => a + b);
|
|
837
|
+
*
|
|
838
|
+
* func(3, 4);
|
|
839
|
+
* func(5, 6);
|
|
840
|
+
*
|
|
841
|
+
* assertSpyCalls(func, 2);
|
|
842
|
+
*
|
|
843
|
+
* // asserts each call made to the spy function.
|
|
844
|
+
* assertSpyCall(func, 0, { args: [3, 4], returned: 7 });
|
|
845
|
+
* assertSpyCall(func, 1, { args: [5, 6], returned: 11 });
|
|
846
|
+
* ```
|
|
847
|
+
*
|
|
848
|
+
* @typeParam Self The self type of the function to wrap
|
|
849
|
+
* @typeParam Args The arguments type of the function to wrap
|
|
850
|
+
* @typeParam Return The return type of the function to wrap
|
|
851
|
+
* @param func The function to wrap
|
|
852
|
+
* @returns The wrapped function.
|
|
853
|
+
*/
|
|
854
|
+
export function spy<
|
|
855
|
+
Self,
|
|
856
|
+
Args extends unknown[],
|
|
857
|
+
Return,
|
|
858
|
+
>(func: (this: Self, ...args: Args) => Return): Spy<Self, Args, Return>;
|
|
859
|
+
/**
|
|
860
|
+
* Create a spy constructor.
|
|
861
|
+
*
|
|
862
|
+
* @example Usage
|
|
863
|
+
* ```ts
|
|
864
|
+
* import {
|
|
865
|
+
* assertSpyCall,
|
|
866
|
+
* assertSpyCalls,
|
|
867
|
+
* spy,
|
|
868
|
+
* } from "@std/testing/mock";
|
|
869
|
+
*
|
|
870
|
+
* class Foo {
|
|
871
|
+
* constructor(value: string) {}
|
|
872
|
+
* };
|
|
873
|
+
*
|
|
874
|
+
* const Constructor = spy(Foo);
|
|
875
|
+
*
|
|
876
|
+
* new Constructor("foo");
|
|
877
|
+
* new Constructor("bar");
|
|
878
|
+
*
|
|
879
|
+
* assertSpyCalls(Constructor, 2);
|
|
880
|
+
*
|
|
881
|
+
* // asserts each call made to the spy function.
|
|
882
|
+
* assertSpyCall(Constructor, 0, { args: ["foo"] });
|
|
883
|
+
* assertSpyCall(Constructor, 1, { args: ["bar"] });
|
|
884
|
+
* ```
|
|
885
|
+
*
|
|
886
|
+
* @typeParam Self The type of the instance of the class.
|
|
887
|
+
* @typeParam Args The arguments type of the constructor
|
|
888
|
+
* @param constructor The constructor to spy.
|
|
889
|
+
* @returns The wrapped constructor.
|
|
890
|
+
*/
|
|
891
|
+
export function spy<
|
|
892
|
+
Self,
|
|
893
|
+
Args extends unknown[],
|
|
894
|
+
>(
|
|
895
|
+
constructor: new (...args: Args) => Self,
|
|
896
|
+
): ConstructorSpy<Self, Args>;
|
|
897
|
+
/**
|
|
898
|
+
* Wraps a instance method with a Spy.
|
|
899
|
+
*
|
|
900
|
+
* @example Usage
|
|
901
|
+
* ```ts
|
|
902
|
+
* import {
|
|
903
|
+
* assertSpyCall,
|
|
904
|
+
* assertSpyCalls,
|
|
905
|
+
* spy,
|
|
906
|
+
* } from "@std/testing/mock";
|
|
907
|
+
*
|
|
908
|
+
* const obj = {
|
|
909
|
+
* method(a: number, b: number): number {
|
|
910
|
+
* return a + b;
|
|
911
|
+
* },
|
|
912
|
+
* };
|
|
913
|
+
*
|
|
914
|
+
* const methodSpy = spy(obj, "method");
|
|
915
|
+
*
|
|
916
|
+
* obj.method(1, 2);
|
|
917
|
+
* obj.method(3, 4);
|
|
918
|
+
*
|
|
919
|
+
* assertSpyCalls(methodSpy, 2);
|
|
920
|
+
*
|
|
921
|
+
* // asserts each call made to the spy function.
|
|
922
|
+
* assertSpyCall(methodSpy, 0, { args: [1, 2], returned: 3 });
|
|
923
|
+
* assertSpyCall(methodSpy, 1, { args: [3, 4], returned: 7 });
|
|
924
|
+
* ```
|
|
925
|
+
*
|
|
926
|
+
* @typeParam Self The type of the instance to spy the method of.
|
|
927
|
+
* @typeParam Prop The property to spy.
|
|
928
|
+
* @param self The instance to spy.
|
|
929
|
+
* @param property The property of the method to spy.
|
|
930
|
+
* @returns The spy function.
|
|
931
|
+
*/
|
|
932
|
+
export function spy<
|
|
933
|
+
Self,
|
|
934
|
+
Prop extends keyof Self,
|
|
935
|
+
>(
|
|
936
|
+
self: Self,
|
|
937
|
+
property: Prop,
|
|
938
|
+
): MethodSpy<
|
|
939
|
+
Self,
|
|
940
|
+
GetParametersFromProp<Self, Prop>,
|
|
941
|
+
GetReturnFromProp<Self, Prop>
|
|
942
|
+
>;
|
|
943
|
+
export function spy<
|
|
944
|
+
Self,
|
|
945
|
+
Args extends unknown[],
|
|
946
|
+
Return,
|
|
947
|
+
>(
|
|
948
|
+
funcOrConstOrSelf?:
|
|
949
|
+
| ((this: Self, ...args: Args) => Return)
|
|
950
|
+
| (new (...args: Args) => Self)
|
|
951
|
+
| Self,
|
|
952
|
+
property?: keyof Self,
|
|
953
|
+
): SpyLike<Self, Args, Return> {
|
|
954
|
+
if (!funcOrConstOrSelf) {
|
|
955
|
+
return functionSpy<Self, Args, Return>();
|
|
956
|
+
} else if (property !== undefined) {
|
|
957
|
+
return methodSpy<Self, Args, Return>(funcOrConstOrSelf as Self, property);
|
|
958
|
+
} else if (funcOrConstOrSelf.toString().startsWith("class")) {
|
|
959
|
+
return constructorSpy<Self, Args>(
|
|
960
|
+
funcOrConstOrSelf as new (...args: Args) => Self,
|
|
961
|
+
);
|
|
962
|
+
} else {
|
|
963
|
+
return functionSpy<Self, Args, Return>(
|
|
964
|
+
funcOrConstOrSelf as (this: Self, ...args: Args) => Return,
|
|
965
|
+
);
|
|
966
|
+
}
|
|
967
|
+
}
|
|
968
|
+
|
|
969
|
+
/** An instance method replacement that records all calls made to it. */
|
|
970
|
+
export interface Stub<
|
|
971
|
+
// deno-lint-ignore no-explicit-any
|
|
972
|
+
Self = any,
|
|
973
|
+
// deno-lint-ignore no-explicit-any
|
|
974
|
+
Args extends unknown[] = any[],
|
|
975
|
+
// deno-lint-ignore no-explicit-any
|
|
976
|
+
Return = any,
|
|
977
|
+
> extends MethodSpy<Self, Args, Return> {
|
|
978
|
+
/** The function that is used instead of the original. */
|
|
979
|
+
fake: (this: Self, ...args: Args) => Return;
|
|
980
|
+
}
|
|
981
|
+
|
|
982
|
+
/**
|
|
983
|
+
* Replaces an instance method with a Stub with empty implementation.
|
|
984
|
+
*
|
|
985
|
+
* @example Usage
|
|
986
|
+
* ```ts
|
|
987
|
+
* import { stub, assertSpyCalls } from "@std/testing/mock";
|
|
988
|
+
*
|
|
989
|
+
* const obj = {
|
|
990
|
+
* method() {
|
|
991
|
+
* // some inconventient feature for testing
|
|
992
|
+
* },
|
|
993
|
+
* };
|
|
994
|
+
*
|
|
995
|
+
* const methodStub = stub(obj, "method");
|
|
996
|
+
*
|
|
997
|
+
* for (const _ of Array(5)) {
|
|
998
|
+
* obj.method();
|
|
999
|
+
* }
|
|
1000
|
+
*
|
|
1001
|
+
* assertSpyCalls(methodStub, 5);
|
|
1002
|
+
* ```
|
|
1003
|
+
|
|
1004
|
+
*
|
|
1005
|
+
* @typeParam Self The self type of the instance to replace a method of.
|
|
1006
|
+
* @typeParam Prop The property of the instance to replace.
|
|
1007
|
+
* @param self The instance to replace a method of.
|
|
1008
|
+
* @param property The property of the instance to replace.
|
|
1009
|
+
* @returns The stub function which replaced the original.
|
|
1010
|
+
*/
|
|
1011
|
+
export function stub<
|
|
1012
|
+
Self,
|
|
1013
|
+
Prop extends keyof Self,
|
|
1014
|
+
>(
|
|
1015
|
+
self: Self,
|
|
1016
|
+
property: Prop,
|
|
1017
|
+
): Stub<Self, GetParametersFromProp<Self, Prop>, GetReturnFromProp<Self, Prop>>;
|
|
1018
|
+
/**
|
|
1019
|
+
* Replaces an instance method with a Stub with the given implementation.
|
|
1020
|
+
*
|
|
1021
|
+
* @example Usage
|
|
1022
|
+
* ```ts
|
|
1023
|
+
* import { stub } from "@std/testing/mock";
|
|
1024
|
+
* import { assertEquals } from "@std/assert";
|
|
1025
|
+
*
|
|
1026
|
+
* const obj = {
|
|
1027
|
+
* method(): number {
|
|
1028
|
+
* return Math.random();
|
|
1029
|
+
* },
|
|
1030
|
+
* };
|
|
1031
|
+
*
|
|
1032
|
+
* const methodStub = stub(obj, "method", () => 0.5);
|
|
1033
|
+
*
|
|
1034
|
+
* assertEquals(obj.method(), 0.5);
|
|
1035
|
+
* ```
|
|
1036
|
+
*
|
|
1037
|
+
* @typeParam Self The self type of the instance to replace a method of.
|
|
1038
|
+
* @typeParam Prop The property of the instance to replace.
|
|
1039
|
+
* @param self The instance to replace a method of.
|
|
1040
|
+
* @param property The property of the instance to replace.
|
|
1041
|
+
* @param func The fake implementation of the function.
|
|
1042
|
+
* @returns The stub function which replaced the original.
|
|
1043
|
+
*/
|
|
1044
|
+
export function stub<
|
|
1045
|
+
Self,
|
|
1046
|
+
Prop extends keyof Self,
|
|
1047
|
+
>(
|
|
1048
|
+
self: Self,
|
|
1049
|
+
property: Prop,
|
|
1050
|
+
func: (
|
|
1051
|
+
this: Self,
|
|
1052
|
+
...args: GetParametersFromProp<Self, Prop>
|
|
1053
|
+
) => GetReturnFromProp<Self, Prop>,
|
|
1054
|
+
): Stub<Self, GetParametersFromProp<Self, Prop>, GetReturnFromProp<Self, Prop>>;
|
|
1055
|
+
export function stub<
|
|
1056
|
+
Self,
|
|
1057
|
+
Args extends unknown[],
|
|
1058
|
+
Return,
|
|
1059
|
+
>(
|
|
1060
|
+
self: Self,
|
|
1061
|
+
property: keyof Self,
|
|
1062
|
+
func?: (this: Self, ...args: Args) => Return,
|
|
1063
|
+
): Stub<Self, Args, Return> {
|
|
1064
|
+
if (self[property] !== undefined && typeof self[property] !== "function") {
|
|
1065
|
+
throw new MockError(
|
|
1066
|
+
"Cannot stub: property is not an instance method",
|
|
1067
|
+
);
|
|
1068
|
+
}
|
|
1069
|
+
if (isSpy(self[property])) {
|
|
1070
|
+
throw new MockError(
|
|
1071
|
+
"Cannot stub: already spying on instance method",
|
|
1072
|
+
);
|
|
1073
|
+
}
|
|
1074
|
+
|
|
1075
|
+
const propertyDescriptor = Object.getOwnPropertyDescriptor(self, property);
|
|
1076
|
+
if (propertyDescriptor && !propertyDescriptor.configurable) {
|
|
1077
|
+
throw new MockError("Cannot stub: non-configurable instance method");
|
|
1078
|
+
}
|
|
1079
|
+
|
|
1080
|
+
const fake = func ?? (() => {}) as (this: Self, ...args: Args) => Return;
|
|
1081
|
+
|
|
1082
|
+
const original = self[property] as unknown as (
|
|
1083
|
+
this: Self,
|
|
1084
|
+
...args: Args
|
|
1085
|
+
) => Return;
|
|
1086
|
+
const calls: SpyCall<Self, Args, Return>[] = [];
|
|
1087
|
+
let restored = false;
|
|
1088
|
+
const stub = function (this: Self, ...args: Args): Return {
|
|
1089
|
+
const call: SpyCall<Self, Args, Return> = { args };
|
|
1090
|
+
if (this) call.self = this;
|
|
1091
|
+
try {
|
|
1092
|
+
call.returned = fake.apply(this, args);
|
|
1093
|
+
} catch (error) {
|
|
1094
|
+
call.error = error as Error;
|
|
1095
|
+
calls.push(call);
|
|
1096
|
+
throw error;
|
|
1097
|
+
}
|
|
1098
|
+
calls.push(call);
|
|
1099
|
+
return call.returned;
|
|
1100
|
+
} as Stub<Self, Args, Return>;
|
|
1101
|
+
Object.defineProperties(stub, {
|
|
1102
|
+
original: {
|
|
1103
|
+
enumerable: true,
|
|
1104
|
+
value: original,
|
|
1105
|
+
},
|
|
1106
|
+
fake: {
|
|
1107
|
+
enumerable: true,
|
|
1108
|
+
value: fake,
|
|
1109
|
+
},
|
|
1110
|
+
calls: {
|
|
1111
|
+
enumerable: true,
|
|
1112
|
+
value: calls,
|
|
1113
|
+
},
|
|
1114
|
+
restored: {
|
|
1115
|
+
enumerable: true,
|
|
1116
|
+
get: () => restored,
|
|
1117
|
+
},
|
|
1118
|
+
restore: {
|
|
1119
|
+
enumerable: true,
|
|
1120
|
+
value: () => {
|
|
1121
|
+
if (restored) {
|
|
1122
|
+
throw new MockError(
|
|
1123
|
+
"Cannot restore: instance method already restored",
|
|
1124
|
+
);
|
|
1125
|
+
}
|
|
1126
|
+
if (propertyDescriptor) {
|
|
1127
|
+
Object.defineProperty(self, property, propertyDescriptor);
|
|
1128
|
+
} else {
|
|
1129
|
+
delete self[property];
|
|
1130
|
+
}
|
|
1131
|
+
restored = true;
|
|
1132
|
+
unregisterMock(stub);
|
|
1133
|
+
},
|
|
1134
|
+
},
|
|
1135
|
+
[Symbol.dispose]: {
|
|
1136
|
+
value: () => {
|
|
1137
|
+
stub.restore();
|
|
1138
|
+
},
|
|
1139
|
+
},
|
|
1140
|
+
});
|
|
1141
|
+
|
|
1142
|
+
Object.defineProperty(self, property, {
|
|
1143
|
+
configurable: true,
|
|
1144
|
+
enumerable: propertyDescriptor?.enumerable ?? false,
|
|
1145
|
+
writable: propertyDescriptor?.writable ?? false,
|
|
1146
|
+
value: stub,
|
|
1147
|
+
});
|
|
1148
|
+
|
|
1149
|
+
registerMock(stub);
|
|
1150
|
+
return stub;
|
|
1151
|
+
}
|
|
1152
|
+
|
|
1153
|
+
/**
|
|
1154
|
+
* Asserts that a spy is called as much as expected and no more.
|
|
1155
|
+
*
|
|
1156
|
+
* @example Usage
|
|
1157
|
+
* ```ts
|
|
1158
|
+
* import { assertSpyCalls, spy } from "@std/testing/mock";
|
|
1159
|
+
*
|
|
1160
|
+
* const func = spy();
|
|
1161
|
+
*
|
|
1162
|
+
* func();
|
|
1163
|
+
* func();
|
|
1164
|
+
*
|
|
1165
|
+
* assertSpyCalls(func, 2);
|
|
1166
|
+
* ```
|
|
1167
|
+
*
|
|
1168
|
+
* @typeParam Self The self type of the spy function.
|
|
1169
|
+
* @typeParam Args The arguments type of the spy function.
|
|
1170
|
+
* @typeParam Return The return type of the spy function.
|
|
1171
|
+
* @param spy The spy to check
|
|
1172
|
+
* @param expectedCalls The number of the expected calls.
|
|
1173
|
+
*/
|
|
1174
|
+
export function assertSpyCalls<
|
|
1175
|
+
Self,
|
|
1176
|
+
Args extends unknown[],
|
|
1177
|
+
Return,
|
|
1178
|
+
>(
|
|
1179
|
+
spy: SpyLike<Self, Args, Return>,
|
|
1180
|
+
expectedCalls: number,
|
|
1181
|
+
) {
|
|
1182
|
+
try {
|
|
1183
|
+
assertEquals(spy.calls.length, expectedCalls);
|
|
1184
|
+
} catch (e) {
|
|
1185
|
+
assertIsError(e);
|
|
1186
|
+
let message = spy.calls.length < expectedCalls
|
|
1187
|
+
? "Spy not called as much as expected:\n"
|
|
1188
|
+
: "Spy called more than expected:\n";
|
|
1189
|
+
message += e.message.split("\n").slice(1).join("\n");
|
|
1190
|
+
throw new AssertionError(message);
|
|
1191
|
+
}
|
|
1192
|
+
}
|
|
1193
|
+
|
|
1194
|
+
/** Call information recorded by a spy. */
|
|
1195
|
+
export interface ExpectedSpyCall<
|
|
1196
|
+
// deno-lint-ignore no-explicit-any
|
|
1197
|
+
Self = any,
|
|
1198
|
+
// deno-lint-ignore no-explicit-any
|
|
1199
|
+
Args extends unknown[] = any[],
|
|
1200
|
+
// deno-lint-ignore no-explicit-any
|
|
1201
|
+
Return = any,
|
|
1202
|
+
> {
|
|
1203
|
+
/** Arguments passed to a function when called. */
|
|
1204
|
+
args?: [...Args, ...unknown[]];
|
|
1205
|
+
/** The instance that a method was called on. */
|
|
1206
|
+
self?: Self;
|
|
1207
|
+
/**
|
|
1208
|
+
* The value that was returned by a function.
|
|
1209
|
+
* If you expect a promise to reject, expect error instead.
|
|
1210
|
+
*/
|
|
1211
|
+
returned?: Return;
|
|
1212
|
+
/** The expected thrown error. */
|
|
1213
|
+
error?: {
|
|
1214
|
+
/** The class for the error that was thrown by a function. */
|
|
1215
|
+
// deno-lint-ignore no-explicit-any
|
|
1216
|
+
Class?: new (...args: any[]) => Error;
|
|
1217
|
+
/** Part of the message for the error that was thrown by a function. */
|
|
1218
|
+
msgIncludes?: string;
|
|
1219
|
+
};
|
|
1220
|
+
}
|
|
1221
|
+
|
|
1222
|
+
function getSpyCall<
|
|
1223
|
+
Self,
|
|
1224
|
+
Args extends unknown[],
|
|
1225
|
+
Return,
|
|
1226
|
+
>(
|
|
1227
|
+
spy: SpyLike<Self, Args, Return>,
|
|
1228
|
+
callIndex: number,
|
|
1229
|
+
): SpyCall {
|
|
1230
|
+
if (spy.calls.length < (callIndex + 1)) {
|
|
1231
|
+
throw new AssertionError("Spy not called as much as expected");
|
|
1232
|
+
}
|
|
1233
|
+
return spy.calls[callIndex]!;
|
|
1234
|
+
}
|
|
1235
|
+
/**
|
|
1236
|
+
* Asserts that a spy is called as expected.
|
|
1237
|
+
*
|
|
1238
|
+
* @example Usage
|
|
1239
|
+
* ```ts
|
|
1240
|
+
* import { assertSpyCall, spy } from "@std/testing/mock";
|
|
1241
|
+
*
|
|
1242
|
+
* const func = spy((a: number, b: number) => a + b);
|
|
1243
|
+
*
|
|
1244
|
+
* func(3, 4);
|
|
1245
|
+
* func(5, 6);
|
|
1246
|
+
*
|
|
1247
|
+
* // asserts each call made to the spy function.
|
|
1248
|
+
* assertSpyCall(func, 0, { args: [3, 4], returned: 7 });
|
|
1249
|
+
* assertSpyCall(func, 1, { args: [5, 6], returned: 11 });
|
|
1250
|
+
* ```
|
|
1251
|
+
*
|
|
1252
|
+
* @typeParam Self The self type of the spy function.
|
|
1253
|
+
* @typeParam Args The arguments type of the spy function.
|
|
1254
|
+
* @typeParam Return The return type of the spy function.
|
|
1255
|
+
* @param spy The spy to check
|
|
1256
|
+
* @param callIndex The index of the call to check
|
|
1257
|
+
* @param expected The expected spy call.
|
|
1258
|
+
*/
|
|
1259
|
+
export function assertSpyCall<
|
|
1260
|
+
Self,
|
|
1261
|
+
Args extends unknown[],
|
|
1262
|
+
Return,
|
|
1263
|
+
>(
|
|
1264
|
+
spy: SpyLike<Self, Args, Return>,
|
|
1265
|
+
callIndex: number,
|
|
1266
|
+
expected?: ExpectedSpyCall<Self, Args, Return>,
|
|
1267
|
+
) {
|
|
1268
|
+
const call = getSpyCall(spy, callIndex);
|
|
1269
|
+
if (expected) {
|
|
1270
|
+
if (expected.args) {
|
|
1271
|
+
try {
|
|
1272
|
+
assertEquals(call.args, expected.args);
|
|
1273
|
+
} catch (e) {
|
|
1274
|
+
assertIsError(e);
|
|
1275
|
+
throw new AssertionError(
|
|
1276
|
+
"Spy not called with expected args:\n" +
|
|
1277
|
+
e.message.split("\n").slice(1).join("\n"),
|
|
1278
|
+
);
|
|
1279
|
+
}
|
|
1280
|
+
}
|
|
1281
|
+
|
|
1282
|
+
if ("self" in expected) {
|
|
1283
|
+
try {
|
|
1284
|
+
assertEquals(call.self, expected.self);
|
|
1285
|
+
} catch (e) {
|
|
1286
|
+
assertIsError(e);
|
|
1287
|
+
let message = expected.self
|
|
1288
|
+
? "Spy not called as method on expected self:\n"
|
|
1289
|
+
: "Spy not expected to be called as method on object:\n";
|
|
1290
|
+
message += e.message.split("\n").slice(1).join("\n");
|
|
1291
|
+
throw new AssertionError(message);
|
|
1292
|
+
}
|
|
1293
|
+
}
|
|
1294
|
+
|
|
1295
|
+
if ("returned" in expected) {
|
|
1296
|
+
if ("error" in expected) {
|
|
1297
|
+
throw new TypeError(
|
|
1298
|
+
"Do not expect error and return, only one should be expected",
|
|
1299
|
+
);
|
|
1300
|
+
}
|
|
1301
|
+
if (call.error) {
|
|
1302
|
+
throw new AssertionError(
|
|
1303
|
+
"Spy call did not return expected value, an error was thrown.",
|
|
1304
|
+
);
|
|
1305
|
+
}
|
|
1306
|
+
try {
|
|
1307
|
+
assertEquals(call.returned, expected.returned);
|
|
1308
|
+
} catch (e) {
|
|
1309
|
+
assertIsError(e);
|
|
1310
|
+
throw new AssertionError(
|
|
1311
|
+
"Spy call did not return expected value:\n" +
|
|
1312
|
+
e.message.split("\n").slice(1).join("\n"),
|
|
1313
|
+
);
|
|
1314
|
+
}
|
|
1315
|
+
}
|
|
1316
|
+
|
|
1317
|
+
if ("error" in expected) {
|
|
1318
|
+
if ("returned" in call) {
|
|
1319
|
+
throw new AssertionError(
|
|
1320
|
+
"Spy call did not throw an error, a value was returned.",
|
|
1321
|
+
);
|
|
1322
|
+
}
|
|
1323
|
+
assertIsError(
|
|
1324
|
+
call.error,
|
|
1325
|
+
expected.error?.Class,
|
|
1326
|
+
expected.error?.msgIncludes,
|
|
1327
|
+
);
|
|
1328
|
+
}
|
|
1329
|
+
}
|
|
1330
|
+
}
|
|
1331
|
+
|
|
1332
|
+
/**
|
|
1333
|
+
* Asserts that an async spy is called as expected.
|
|
1334
|
+
*
|
|
1335
|
+
* @example Usage
|
|
1336
|
+
* ```ts
|
|
1337
|
+
* import { assertSpyCallAsync, spy } from "@std/testing/mock";
|
|
1338
|
+
*
|
|
1339
|
+
* const func = spy((a: number, b: number) => new Promise((resolve) => {
|
|
1340
|
+
* setTimeout(() => resolve(a + b), 100)
|
|
1341
|
+
* }));
|
|
1342
|
+
*
|
|
1343
|
+
* await func(3, 4);
|
|
1344
|
+
* await func(5, 6);
|
|
1345
|
+
*
|
|
1346
|
+
* // asserts each call made to the spy function.
|
|
1347
|
+
* await assertSpyCallAsync(func, 0, { args: [3, 4], returned: 7 });
|
|
1348
|
+
* await assertSpyCallAsync(func, 1, { args: [5, 6], returned: 11 });
|
|
1349
|
+
* ```
|
|
1350
|
+
*
|
|
1351
|
+
* @typeParam Self The self type of the spy function.
|
|
1352
|
+
* @typeParam Args The arguments type of the spy function.
|
|
1353
|
+
* @typeParam Return The return type of the spy function.
|
|
1354
|
+
* @param spy The spy to check
|
|
1355
|
+
* @param callIndex The index of the call to check
|
|
1356
|
+
* @param expected The expected spy call.
|
|
1357
|
+
*/
|
|
1358
|
+
export async function assertSpyCallAsync<
|
|
1359
|
+
Self,
|
|
1360
|
+
Args extends unknown[],
|
|
1361
|
+
Return,
|
|
1362
|
+
>(
|
|
1363
|
+
spy: SpyLike<Self, Args, Promise<Return>>,
|
|
1364
|
+
callIndex: number,
|
|
1365
|
+
expected?: ExpectedSpyCall<Self, Args, Promise<Return> | Return>,
|
|
1366
|
+
) {
|
|
1367
|
+
const expectedSync = expected && { ...expected };
|
|
1368
|
+
if (expectedSync) {
|
|
1369
|
+
delete expectedSync.returned;
|
|
1370
|
+
delete expectedSync.error;
|
|
1371
|
+
}
|
|
1372
|
+
assertSpyCall(spy, callIndex, expectedSync);
|
|
1373
|
+
const call = getSpyCall(spy, callIndex);
|
|
1374
|
+
|
|
1375
|
+
if (call.error) {
|
|
1376
|
+
throw new AssertionError(
|
|
1377
|
+
"Spy call did not return a promise, an error was thrown.",
|
|
1378
|
+
);
|
|
1379
|
+
}
|
|
1380
|
+
if (call.returned !== Promise.resolve(call.returned)) {
|
|
1381
|
+
throw new AssertionError(
|
|
1382
|
+
"Spy call did not return a promise, a value was returned.",
|
|
1383
|
+
);
|
|
1384
|
+
}
|
|
1385
|
+
|
|
1386
|
+
if (expected) {
|
|
1387
|
+
if ("returned" in expected) {
|
|
1388
|
+
if ("error" in expected) {
|
|
1389
|
+
throw new TypeError(
|
|
1390
|
+
"Do not expect error and return, only one should be expected",
|
|
1391
|
+
);
|
|
1392
|
+
}
|
|
1393
|
+
let expectedResolved;
|
|
1394
|
+
try {
|
|
1395
|
+
expectedResolved = await expected.returned;
|
|
1396
|
+
} catch {
|
|
1397
|
+
throw new TypeError(
|
|
1398
|
+
"Do not expect rejected promise, expect error instead",
|
|
1399
|
+
);
|
|
1400
|
+
}
|
|
1401
|
+
|
|
1402
|
+
let resolved;
|
|
1403
|
+
try {
|
|
1404
|
+
resolved = await call.returned;
|
|
1405
|
+
} catch {
|
|
1406
|
+
throw new AssertionError("Spy call returned promise was rejected");
|
|
1407
|
+
}
|
|
1408
|
+
|
|
1409
|
+
try {
|
|
1410
|
+
assertEquals(resolved, expectedResolved);
|
|
1411
|
+
} catch (e) {
|
|
1412
|
+
assertIsError(e);
|
|
1413
|
+
throw new AssertionError(
|
|
1414
|
+
"Spy call did not resolve to expected value:\n" +
|
|
1415
|
+
e.message.split("\n").slice(1).join("\n"),
|
|
1416
|
+
);
|
|
1417
|
+
}
|
|
1418
|
+
}
|
|
1419
|
+
|
|
1420
|
+
if ("error" in expected) {
|
|
1421
|
+
await assertRejects(
|
|
1422
|
+
() => Promise.resolve(call.returned),
|
|
1423
|
+
expected.error?.Class ?? Error,
|
|
1424
|
+
expected.error?.msgIncludes ?? "",
|
|
1425
|
+
);
|
|
1426
|
+
}
|
|
1427
|
+
}
|
|
1428
|
+
}
|
|
1429
|
+
|
|
1430
|
+
/**
|
|
1431
|
+
* Asserts that a spy is called with a specific arg as expected.
|
|
1432
|
+
*
|
|
1433
|
+
* @example Usage
|
|
1434
|
+
* ```ts
|
|
1435
|
+
* import { assertSpyCallArg, spy } from "@std/testing/mock";
|
|
1436
|
+
*
|
|
1437
|
+
* const func = spy((a: number, b: number) => a + b);
|
|
1438
|
+
*
|
|
1439
|
+
* func(3, 4);
|
|
1440
|
+
* func(5, 6);
|
|
1441
|
+
*
|
|
1442
|
+
* // asserts each call made to the spy function.
|
|
1443
|
+
* assertSpyCallArg(func, 0, 0, 3);
|
|
1444
|
+
* assertSpyCallArg(func, 0, 1, 4);
|
|
1445
|
+
* assertSpyCallArg(func, 1, 0, 5);
|
|
1446
|
+
* assertSpyCallArg(func, 1, 1, 6);
|
|
1447
|
+
* ```
|
|
1448
|
+
*
|
|
1449
|
+
* @typeParam Self The self type of the spy function.
|
|
1450
|
+
* @typeParam Args The arguments type of the spy function.
|
|
1451
|
+
* @typeParam Return The return type of the spy function.
|
|
1452
|
+
* @typeParam ExpectedArg The expected type of the argument for the spy to be called.
|
|
1453
|
+
* @param spy The spy to check.
|
|
1454
|
+
* @param callIndex The index of the call to check.
|
|
1455
|
+
* @param argIndex The index of the arguments to check.
|
|
1456
|
+
* @param expected The expected argument.
|
|
1457
|
+
* @returns The actual argument.
|
|
1458
|
+
*/
|
|
1459
|
+
export function assertSpyCallArg<
|
|
1460
|
+
Self,
|
|
1461
|
+
Args extends unknown[],
|
|
1462
|
+
Return,
|
|
1463
|
+
ExpectedArg,
|
|
1464
|
+
>(
|
|
1465
|
+
spy: SpyLike<Self, Args, Return>,
|
|
1466
|
+
callIndex: number,
|
|
1467
|
+
argIndex: number,
|
|
1468
|
+
expected: ExpectedArg,
|
|
1469
|
+
): ExpectedArg {
|
|
1470
|
+
const call = getSpyCall(spy, callIndex);
|
|
1471
|
+
const arg = call?.args[argIndex];
|
|
1472
|
+
assertEquals(arg, expected);
|
|
1473
|
+
return arg as ExpectedArg;
|
|
1474
|
+
}
|
|
1475
|
+
|
|
1476
|
+
/**
|
|
1477
|
+
* Asserts that an spy is called with a specific range of args as expected.
|
|
1478
|
+
* If a start and end index is not provided, the expected will be compared against all args.
|
|
1479
|
+
* If a start is provided without an end index, the expected will be compared against all args from the start index to the end.
|
|
1480
|
+
* The end index is not included in the range of args that are compared.
|
|
1481
|
+
*
|
|
1482
|
+
* @example Usage
|
|
1483
|
+
* ```ts
|
|
1484
|
+
* import { assertSpyCallArgs, spy } from "@std/testing/mock";
|
|
1485
|
+
*
|
|
1486
|
+
* const func = spy((a: number, b: number) => a + b);
|
|
1487
|
+
*
|
|
1488
|
+
* func(3, 4);
|
|
1489
|
+
* func(5, 6);
|
|
1490
|
+
*
|
|
1491
|
+
* // asserts each call made to the spy function.
|
|
1492
|
+
* assertSpyCallArgs(func, 0, [3, 4]);
|
|
1493
|
+
* assertSpyCallArgs(func, 1, [5, 6]);
|
|
1494
|
+
* ```
|
|
1495
|
+
*
|
|
1496
|
+
* @typeParam Self The self type of the spy function.
|
|
1497
|
+
* @typeParam Args The arguments type of the spy function.
|
|
1498
|
+
* @typeParam Return The return type of the spy function.
|
|
1499
|
+
* @typeParam ExpectedArgs The expected type of the arguments for the spy to be called.
|
|
1500
|
+
* @param spy The spy to check.
|
|
1501
|
+
* @param callIndex The index of the call to check.
|
|
1502
|
+
* @param expected The expected arguments.
|
|
1503
|
+
* @returns The actual arguments.
|
|
1504
|
+
*/
|
|
1505
|
+
export function assertSpyCallArgs<
|
|
1506
|
+
Self,
|
|
1507
|
+
Args extends unknown[],
|
|
1508
|
+
Return,
|
|
1509
|
+
ExpectedArgs extends unknown[],
|
|
1510
|
+
>(
|
|
1511
|
+
spy: SpyLike<Self, Args, Return>,
|
|
1512
|
+
callIndex: number,
|
|
1513
|
+
expected: ExpectedArgs,
|
|
1514
|
+
): ExpectedArgs;
|
|
1515
|
+
/**
|
|
1516
|
+
* Asserts that an spy is called with a specific range of args as expected.
|
|
1517
|
+
* If a start and end index is not provided, the expected will be compared against all args.
|
|
1518
|
+
* If a start is provided without an end index, the expected will be compared against all args from the start index to the end.
|
|
1519
|
+
* The end index is not included in the range of args that are compared.
|
|
1520
|
+
*
|
|
1521
|
+
* @example Usage
|
|
1522
|
+
* ```ts
|
|
1523
|
+
* import { assertSpyCallArgs, spy } from "@std/testing/mock";
|
|
1524
|
+
*
|
|
1525
|
+
* const func = spy((...args) => {});
|
|
1526
|
+
*
|
|
1527
|
+
* func(0, 1, 2, 3, 4, 5);
|
|
1528
|
+
*
|
|
1529
|
+
* assertSpyCallArgs(func, 0, 3, [3, 4, 5]);
|
|
1530
|
+
* ```
|
|
1531
|
+
*
|
|
1532
|
+
* @typeParam Self The self type of the spy function.
|
|
1533
|
+
* @typeParam Args The arguments type of the spy function.
|
|
1534
|
+
* @typeParam Return The return type of the spy function.
|
|
1535
|
+
* @typeParam ExpectedArgs The expected type of the arguments for the spy to be called.
|
|
1536
|
+
* @param spy The spy to check.
|
|
1537
|
+
* @param callIndex The index of the call to check.
|
|
1538
|
+
* @param argsStart The start index of the arguments to check. If not specified, it checks the arguments from the beignning.
|
|
1539
|
+
* @param expected The expected arguments.
|
|
1540
|
+
* @returns The actual arguments.
|
|
1541
|
+
*/
|
|
1542
|
+
export function assertSpyCallArgs<
|
|
1543
|
+
Self,
|
|
1544
|
+
Args extends unknown[],
|
|
1545
|
+
Return,
|
|
1546
|
+
ExpectedArgs extends unknown[],
|
|
1547
|
+
>(
|
|
1548
|
+
spy: SpyLike<Self, Args, Return>,
|
|
1549
|
+
callIndex: number,
|
|
1550
|
+
argsStart: number,
|
|
1551
|
+
expected: ExpectedArgs,
|
|
1552
|
+
): ExpectedArgs;
|
|
1553
|
+
/**
|
|
1554
|
+
* Asserts that an spy is called with a specific range of args as expected.
|
|
1555
|
+
* If a start and end index is not provided, the expected will be compared against all args.
|
|
1556
|
+
* If a start is provided without an end index, the expected will be compared against all args from the start index to the end.
|
|
1557
|
+
* The end index is not included in the range of args that are compared.
|
|
1558
|
+
*
|
|
1559
|
+
* @example Usage
|
|
1560
|
+
* ```ts
|
|
1561
|
+
* import { assertSpyCallArgs, spy } from "@std/testing/mock";
|
|
1562
|
+
*
|
|
1563
|
+
* const func = spy((...args) => {});
|
|
1564
|
+
*
|
|
1565
|
+
* func(0, 1, 2, 3, 4, 5);
|
|
1566
|
+
*
|
|
1567
|
+
* assertSpyCallArgs(func, 0, 3, 4, [3]);
|
|
1568
|
+
* ```
|
|
1569
|
+
*
|
|
1570
|
+
* @typeParam Self The self type of the spy function.
|
|
1571
|
+
* @typeParam Args The arguments type of the spy function.
|
|
1572
|
+
* @typeParam Return The return type of the spy function.
|
|
1573
|
+
* @typeParam ExpectedArgs The expected type of the arguments for the spy to be called.
|
|
1574
|
+
* @param spy The spy to check
|
|
1575
|
+
* @param callIndex The index of the call to check
|
|
1576
|
+
* @param argsStart The start index of the arguments to check. If not specified, it checks the arguments from the beignning.
|
|
1577
|
+
* @param argsEnd The end index of the arguments to check. If not specified, it checks the arguments until the end.
|
|
1578
|
+
* @param expected The expected arguments.
|
|
1579
|
+
* @returns The actual arguments
|
|
1580
|
+
*/
|
|
1581
|
+
export function assertSpyCallArgs<
|
|
1582
|
+
Self,
|
|
1583
|
+
Args extends unknown[],
|
|
1584
|
+
Return,
|
|
1585
|
+
ExpectedArgs extends unknown[],
|
|
1586
|
+
>(
|
|
1587
|
+
spy: SpyLike<Self, Args, Return>,
|
|
1588
|
+
callIndex: number,
|
|
1589
|
+
argsStart: number,
|
|
1590
|
+
argsEnd: number,
|
|
1591
|
+
expected: ExpectedArgs,
|
|
1592
|
+
): ExpectedArgs;
|
|
1593
|
+
export function assertSpyCallArgs<
|
|
1594
|
+
ExpectedArgs extends unknown[],
|
|
1595
|
+
Args extends unknown[],
|
|
1596
|
+
Return,
|
|
1597
|
+
Self,
|
|
1598
|
+
>(
|
|
1599
|
+
spy: SpyLike<Self, Args, Return>,
|
|
1600
|
+
callIndex: number,
|
|
1601
|
+
argsStart?: number | ExpectedArgs,
|
|
1602
|
+
argsEnd?: number | ExpectedArgs,
|
|
1603
|
+
expected?: ExpectedArgs,
|
|
1604
|
+
): ExpectedArgs {
|
|
1605
|
+
const call = getSpyCall(spy, callIndex);
|
|
1606
|
+
if (!expected) {
|
|
1607
|
+
expected = argsEnd as ExpectedArgs;
|
|
1608
|
+
argsEnd = undefined;
|
|
1609
|
+
}
|
|
1610
|
+
if (!expected) {
|
|
1611
|
+
expected = argsStart as ExpectedArgs;
|
|
1612
|
+
argsStart = undefined;
|
|
1613
|
+
}
|
|
1614
|
+
const args = typeof argsEnd === "number"
|
|
1615
|
+
? call.args.slice(argsStart as number, argsEnd)
|
|
1616
|
+
: typeof argsStart === "number"
|
|
1617
|
+
? call.args.slice(argsStart)
|
|
1618
|
+
: call.args;
|
|
1619
|
+
assertEquals(args, expected);
|
|
1620
|
+
return args as ExpectedArgs;
|
|
1621
|
+
}
|
|
1622
|
+
|
|
1623
|
+
/**
|
|
1624
|
+
* Creates a function that returns the instance the method was called on.
|
|
1625
|
+
*
|
|
1626
|
+
* @example Usage
|
|
1627
|
+
* ```ts
|
|
1628
|
+
* import { returnsThis } from "@std/testing/mock";
|
|
1629
|
+
* import { assertEquals } from "@std/assert";
|
|
1630
|
+
*
|
|
1631
|
+
* const func = returnsThis();
|
|
1632
|
+
* const obj = { func };
|
|
1633
|
+
* assertEquals(obj.func(), obj);
|
|
1634
|
+
* ```
|
|
1635
|
+
*
|
|
1636
|
+
* @typeParam Self The self type of the returned function.
|
|
1637
|
+
* @typeParam Args The arguments type of the returned function.
|
|
1638
|
+
* @returns A function that returns the instance the method was called on.
|
|
1639
|
+
*/
|
|
1640
|
+
export function returnsThis<
|
|
1641
|
+
// deno-lint-ignore no-explicit-any
|
|
1642
|
+
Self = any,
|
|
1643
|
+
// deno-lint-ignore no-explicit-any
|
|
1644
|
+
Args extends unknown[] = any[],
|
|
1645
|
+
>(): (this: Self, ...args: Args) => Self {
|
|
1646
|
+
return function (this: Self): Self {
|
|
1647
|
+
return this;
|
|
1648
|
+
};
|
|
1649
|
+
}
|
|
1650
|
+
|
|
1651
|
+
/**
|
|
1652
|
+
* Creates a function that returns one of its arguments.
|
|
1653
|
+
*
|
|
1654
|
+
* @example Usage
|
|
1655
|
+
* ```ts
|
|
1656
|
+
* import { returnsArg } from "@std/testing/mock";
|
|
1657
|
+
* import { assertEquals } from "@std/assert";
|
|
1658
|
+
*
|
|
1659
|
+
* const func = returnsArg(1);
|
|
1660
|
+
* assertEquals(func(1, 2, 3), 2);
|
|
1661
|
+
* ```
|
|
1662
|
+
*
|
|
1663
|
+
* @typeParam Arg The type of returned argument.
|
|
1664
|
+
* @typeParam Self The self type of the returned function.
|
|
1665
|
+
* @param idx The index of the arguments to use.
|
|
1666
|
+
* @returns A function that returns one of its arguments.
|
|
1667
|
+
*/
|
|
1668
|
+
export function returnsArg<
|
|
1669
|
+
Arg,
|
|
1670
|
+
// deno-lint-ignore no-explicit-any
|
|
1671
|
+
Self = any,
|
|
1672
|
+
>(
|
|
1673
|
+
idx: number,
|
|
1674
|
+
): (this: Self, ...args: Arg[]) => Arg | undefined {
|
|
1675
|
+
return function (...args: Arg[]): Arg | undefined {
|
|
1676
|
+
return args[idx];
|
|
1677
|
+
};
|
|
1678
|
+
}
|
|
1679
|
+
|
|
1680
|
+
/**
|
|
1681
|
+
* Creates a function that returns its arguments or a subset of them. If end is specified, it will return arguments up to but not including the end.
|
|
1682
|
+
*
|
|
1683
|
+
* @example Usage
|
|
1684
|
+
* ```ts
|
|
1685
|
+
* import { returnsArgs } from "@std/testing/mock";
|
|
1686
|
+
* import { assertEquals } from "@std/assert";
|
|
1687
|
+
*
|
|
1688
|
+
* const func = returnsArgs();
|
|
1689
|
+
* assertEquals(func(1, 2, 3), [1, 2, 3]);
|
|
1690
|
+
* ```
|
|
1691
|
+
*
|
|
1692
|
+
* @typeParam Args The arguments type of the returned function
|
|
1693
|
+
* @typeParam Self The self type of the returned function
|
|
1694
|
+
* @param start The start index of the arguments to return. Default is 0.
|
|
1695
|
+
* @param end The end index of the arguments to return.
|
|
1696
|
+
* @returns A function that returns its arguments or a subset of them.
|
|
1697
|
+
*/
|
|
1698
|
+
export function returnsArgs<
|
|
1699
|
+
Args extends unknown[],
|
|
1700
|
+
// deno-lint-ignore no-explicit-any
|
|
1701
|
+
Self = any,
|
|
1702
|
+
>(
|
|
1703
|
+
start = 0,
|
|
1704
|
+
end?: number,
|
|
1705
|
+
): (this: Self, ...args: Args) => Args {
|
|
1706
|
+
return function (this: Self, ...args: Args): Args {
|
|
1707
|
+
return args.slice(start, end) as Args;
|
|
1708
|
+
};
|
|
1709
|
+
}
|
|
1710
|
+
|
|
1711
|
+
/**
|
|
1712
|
+
* Creates a function that returns the iterable values. Any iterable values that are errors will be thrown.
|
|
1713
|
+
*
|
|
1714
|
+
* @example Usage
|
|
1715
|
+
* ```ts
|
|
1716
|
+
* import { returnsNext } from "@std/testing/mock";
|
|
1717
|
+
* import { assertEquals, assertThrows } from "@std/assert";
|
|
1718
|
+
*
|
|
1719
|
+
* const func = returnsNext([1, 2, new Error("foo"), 3]);
|
|
1720
|
+
* assertEquals(func(), 1);
|
|
1721
|
+
* assertEquals(func(), 2);
|
|
1722
|
+
* assertThrows(() => func(), Error, "foo");
|
|
1723
|
+
* assertEquals(func(), 3);
|
|
1724
|
+
* ```
|
|
1725
|
+
*
|
|
1726
|
+
* @typeParam Return The type of each item of the iterable
|
|
1727
|
+
* @typeParam Self The self type of the returned function
|
|
1728
|
+
* @typeParam Args The arguments type of the returned function
|
|
1729
|
+
* @param values The iterable values
|
|
1730
|
+
* @return A function that returns the iterable values
|
|
1731
|
+
*/
|
|
1732
|
+
export function returnsNext<
|
|
1733
|
+
Return,
|
|
1734
|
+
// deno-lint-ignore no-explicit-any
|
|
1735
|
+
Self = any,
|
|
1736
|
+
// deno-lint-ignore no-explicit-any
|
|
1737
|
+
Args extends unknown[] = any[],
|
|
1738
|
+
>(
|
|
1739
|
+
values: Iterable<Return | Error>,
|
|
1740
|
+
): (this: Self, ...args: Args) => Return {
|
|
1741
|
+
const gen = (function* returnsValue() {
|
|
1742
|
+
yield* values;
|
|
1743
|
+
})();
|
|
1744
|
+
let calls = 0;
|
|
1745
|
+
return function () {
|
|
1746
|
+
const next = gen.next();
|
|
1747
|
+
if (next.done) {
|
|
1748
|
+
throw new MockError(
|
|
1749
|
+
`Not expected to be called more than ${calls} time(s)`,
|
|
1750
|
+
);
|
|
1751
|
+
}
|
|
1752
|
+
calls++;
|
|
1753
|
+
const { value } = next;
|
|
1754
|
+
if (value instanceof Error) throw value;
|
|
1755
|
+
return value;
|
|
1756
|
+
};
|
|
1757
|
+
}
|
|
1758
|
+
|
|
1759
|
+
/**
|
|
1760
|
+
* Creates a function that resolves the awaited iterable values. Any awaited iterable values that are errors will be thrown.
|
|
1761
|
+
*
|
|
1762
|
+
* @example Usage
|
|
1763
|
+
* ```ts
|
|
1764
|
+
* import { resolvesNext } from "@std/testing/mock";
|
|
1765
|
+
* import { assertEquals, assertRejects } from "@std/assert";
|
|
1766
|
+
*
|
|
1767
|
+
* const func = resolvesNext([1, 2, new Error("foo"), 3]);
|
|
1768
|
+
* assertEquals(await func(), 1);
|
|
1769
|
+
* assertEquals(await func(), 2);
|
|
1770
|
+
* assertRejects(() => func(), Error, "foo");
|
|
1771
|
+
* assertEquals(await func(), 3);
|
|
1772
|
+
* ```
|
|
1773
|
+
*
|
|
1774
|
+
* @typeParam Return The type of each item of the iterable
|
|
1775
|
+
* @typeParam Self The self type of the returned function
|
|
1776
|
+
* @typeParam Args The type of arguments of the returned function
|
|
1777
|
+
* @param iterable The iterable to use
|
|
1778
|
+
* @returns A function that resolves the awaited iterable values
|
|
1779
|
+
*/
|
|
1780
|
+
export function resolvesNext<
|
|
1781
|
+
Return,
|
|
1782
|
+
// deno-lint-ignore no-explicit-any
|
|
1783
|
+
Self = any,
|
|
1784
|
+
// deno-lint-ignore no-explicit-any
|
|
1785
|
+
Args extends unknown[] = any[],
|
|
1786
|
+
>(
|
|
1787
|
+
iterable:
|
|
1788
|
+
| Iterable<Return | Error | Promise<Return | Error>>
|
|
1789
|
+
| AsyncIterable<Return | Error | Promise<Return | Error>>,
|
|
1790
|
+
): (this: Self, ...args: Args) => Promise<Return> {
|
|
1791
|
+
const gen = (async function* returnsValue() {
|
|
1792
|
+
yield* iterable;
|
|
1793
|
+
})();
|
|
1794
|
+
let calls = 0;
|
|
1795
|
+
return async function () {
|
|
1796
|
+
const next = await gen.next();
|
|
1797
|
+
if (next.done) {
|
|
1798
|
+
throw new MockError(
|
|
1799
|
+
`Not expected to be called more than ${calls} time(s)`,
|
|
1800
|
+
);
|
|
1801
|
+
}
|
|
1802
|
+
calls++;
|
|
1803
|
+
const { value } = next;
|
|
1804
|
+
if (value instanceof Error) throw value;
|
|
1805
|
+
return value;
|
|
1806
|
+
};
|
|
1807
|
+
}
|