浏览代码

Include query parameters and headers in the generated Postman collection. (#537)

* Include query parameters in the generated Postman collection.

* Style fixes

* Also include headers in the Postman collection.

* Also include JSON content type headers for good measure.

* Update the tests.

* Add a test to validate the body parameters in a Postman collection.

* Remove the "Content-Type" header again, as we are actually sending content as form data.

* Add a query test and make the tests more deterministic.

* PR fixes.
Daniel Alm 6 年之前
父节点
当前提交
573e9efb63

+ 17 - 2
src/Postman/CollectionWriter.php

@@ -56,14 +56,29 @@ class CollectionWriter
                         return [
                             'name' => $route['title'] != '' ? $route['title'] : url($route['uri']),
                             'request' => [
-                                'url' => url($route['uri']),
+                                'url' => url($route['uri']).(collect($route['queryParameters'])->isEmpty()
+                                    ? ''
+                                    : ('?'.implode('&', collect($route['queryParameters'])->map(function ($parameter, $key) {
+                                        return $key.'='.($parameter['value'] ?? '');
+                                    })->all()))),
                                 'method' => $route['methods'][0],
+                                'header' => collect($route['headers'])
+                                    ->union([
+                                        'Accept' => 'application/json',
+                                    ])
+                                    ->map(function ($value, $header) {
+                                        return [
+                                            'key' => $header,
+                                            'value' => $value,
+                                        ];
+                                    })
+                                    ->values()->all(),
                                 'body' => [
                                     'mode' => $mode,
                                     $mode => collect($route['bodyParameters'])->map(function ($parameter, $key) {
                                         return [
                                             'key' => $key,
-                                            'value' => isset($parameter['value']) ? $parameter['value'] : '',
+                                            'value' => $parameter['value'] ?? '',
                                             'type' => 'text',
                                             'enabled' => true,
                                         ];

+ 55 - 1
tests/Fixtures/collection.json

@@ -1 +1,55 @@
-{"variables":[],"info":{"name":"Laravel API","_postman_id":"","description":"","schema":"https:\/\/schema.getpostman.com\/json\/collection\/v2.0.0\/collection.json"},"item":[{"name":"Group A","description":"","item":[{"name":"Example title.","request":{"url":"http:\/\/localhost\/api\/test","method":"GET","body":{"mode":"formdata","formdata":[]},"description":"This will be the long description.\nIt can also be multiple lines long.","response":[]}},{"name":"http:\/\/localhost\/api\/responseTag","request":{"url":"http:\/\/localhost\/api\/responseTag","method":"POST","body":{"mode":"formdata","formdata":[]},"description":"","response":[]}}]}]}
+{
+    "variables": [],
+    "info": {
+        "name": "Laravel API",
+        "_postman_id": "",
+        "description": "",
+        "schema": "https:\/\/schema.getpostman.com\/json\/collection\/v2.0.0\/collection.json"
+    },
+    "item": [
+        {
+            "name": "Group A",
+            "description": "",
+            "item": [
+                {
+                    "name": "Example title.",
+                    "request": {
+                        "url": "http:\/\/localhost\/api\/test",
+                        "method": "GET",
+                        "header": [
+                            {
+                                "key": "Accept",
+                                "value": "application/json"
+                            }
+                        ],
+                        "body": {
+                            "mode": "formdata",
+                            "formdata": []
+                        },
+                        "description": "This will be the long description.\nIt can also be multiple lines long.",
+                        "response": []
+                    }
+                },
+                {
+                    "name": "http:\/\/localhost\/api\/responseTag",
+                    "request": {
+                        "url": "http:\/\/localhost\/api\/responseTag",
+                        "method": "POST",
+                        "header": [
+                            {
+                                "key": "Accept",
+                                "value": "application/json"
+                            }
+                        ],
+                        "body": {
+                            "mode": "formdata",
+                            "formdata": []
+                        },
+                        "description": "",
+                        "response": []
+                    }
+                }
+            ]
+        }
+    ]
+}

+ 55 - 1
tests/Fixtures/collection_updated_url.json

@@ -1 +1,55 @@
-{"variables":[],"info":{"name":"Laravel API","_postman_id":"","description":"","schema":"https:\/\/schema.getpostman.com\/json\/collection\/v2.0.0\/collection.json"},"item":[{"name":"Group A","description":"","item":[{"name":"Example title.","request":{"url":"http:\/\/yourapp.app\/api\/test","method":"GET","body":{"mode":"formdata","formdata":[]},"description":"This will be the long description.\nIt can also be multiple lines long.","response":[]}},{"name":"http:\/\/yourapp.app\/api\/responseTag","request":{"url":"http:\/\/yourapp.app\/api\/responseTag","method":"POST","body":{"mode":"formdata","formdata":[]},"description":"","response":[]}}]}]}
+{
+    "variables": [],
+    "info": {
+        "name": "Laravel API",
+        "_postman_id": "",
+        "description": "",
+        "schema": "https:\/\/schema.getpostman.com\/json\/collection\/v2.0.0\/collection.json"
+    },
+    "item": [
+        {
+            "name": "Group A",
+            "description": "",
+            "item": [
+                {
+                    "name": "Example title.",
+                    "request": {
+                        "url": "http:\/\/yourapp.app\/api\/test",
+                        "method": "GET",
+                        "header": [
+                            {
+                                "key": "Accept",
+                                "value": "application/json"
+                            }
+                        ],
+                        "body": {
+                            "mode": "formdata",
+                            "formdata": []
+                        },
+                        "description": "This will be the long description.\nIt can also be multiple lines long.",
+                        "response": []
+                    }
+                },
+                {
+                    "name": "http:\/\/yourapp.app\/api\/responseTag",
+                    "request": {
+                        "url": "http:\/\/yourapp.app\/api\/responseTag",
+                        "method": "POST",
+                        "header": [
+                            {
+                                "key": "Accept",
+                                "value": "application/json"
+                            }
+                        ],
+                        "body": {
+                            "mode": "formdata",
+                            "formdata": []
+                        },
+                        "description": "",
+                        "response": []
+                    }
+                }
+            ]
+        }
+    ]
+}

+ 109 - 0
tests/Fixtures/collection_with_body_parameters.json

@@ -0,0 +1,109 @@
+{
+    "variables": [],
+    "info": {
+        "name": "Laravel API",
+        "_postman_id": "",
+        "description": "",
+        "schema": "https:\/\/schema.getpostman.com\/json\/collection\/v2.0.0\/collection.json"
+    },
+    "item": [
+        {
+            "name": "Group A",
+            "description": "",
+            "item": [
+                {
+                    "name": "http://localhost/api/withBodyParameters",
+                    "request": {
+                        "url": "http:\/\/localhost\/api\/withBodyParameters",
+                        "method": "GET",
+                        "header": [
+                            {
+                                "key": "Accept",
+                                "value": "application/json"
+                            }
+                        ],
+                        "body": {
+                            "mode": "formdata",
+                            "formdata": [
+                                {
+                                    "key": "user_id",
+                                    "value": 9,
+                                    "type": "text",
+                                    "enabled": true
+                                },
+                                {
+                                    "key": "room_id",
+                                    "value": "consequatur",
+                                    "type": "text",
+                                    "enabled": true
+                                },
+                                {
+                                    "key": "forever",
+                                    "value": false,
+                                    "type": "text",
+                                    "enabled": true
+                                },
+                                {
+                                    "key": "another_one",
+                                    "value": 11613.31890586,
+                                    "type": "text",
+                                    "enabled": true
+                                },
+                                {
+                                    "key": "yet_another_param",
+                                    "value": [],
+                                    "type": "text",
+                                    "enabled": true
+                                },
+                                {
+                                    "key": "even_more_param",
+                                    "value": [],
+                                    "type": "text",
+                                    "enabled": true
+                                },
+                                {
+                                    "key": "book.name",
+                                    "value": "consequatur",
+                                    "type": "text",
+                                    "enabled": true
+                                },
+                                {
+                                    "key": "book.author_id",
+                                    "value": 17,
+                                    "type": "text",
+                                    "enabled": true
+                                },
+                                {
+                                    "key": "book[pages_count]",
+                                    "value": 17,
+                                    "type": "text",
+                                    "enabled": true
+                                },
+                                {
+                                    "key": "ids.*",
+                                    "value": 17,
+                                    "type": "text",
+                                    "enabled": true
+                                },
+                                {
+                                    "key": "users.*.first_name",
+                                    "value": "John",
+                                    "type": "text",
+                                    "enabled": true
+                                },
+                                {
+                                    "key": "users.*.last_name",
+                                    "value": "Doe",
+                                    "type": "text",
+                                    "enabled": true
+                                }
+                            ]
+                        },
+                        "description": "",
+                        "response": []
+                    }
+                }
+            ]
+        }
+    ]
+}

+ 44 - 0
tests/Fixtures/collection_with_custom_headers.json

@@ -0,0 +1,44 @@
+{
+    "variables": [],
+    "info": {
+        "name": "Laravel API",
+        "_postman_id": "",
+        "description": "",
+        "schema": "https:\/\/schema.getpostman.com\/json\/collection\/v2.0.0\/collection.json"
+    },
+    "item": [
+        {
+            "name": "Group A",
+            "description": "",
+            "item": [
+                {
+                    "name": "http://localhost/api/headers",
+                    "request": {
+                        "url": "http:\/\/localhost\/api\/headers",
+                        "method": "GET",
+                        "header": [
+                            {
+                                "key": "Authorization",
+                                "value": "customAuthToken"
+                            },
+                            {
+                                "key": "Custom-Header",
+                                "value": "NotSoCustom"
+                            },
+                            {
+                                "key": "Accept",
+                                "value": "application/json"
+                            }
+                        ],
+                        "body": {
+                            "mode": "formdata",
+                            "formdata": []
+                        },
+                        "description": "",
+                        "response": []
+                    }
+                }
+            ]
+        }
+    ]
+}

+ 36 - 0
tests/Fixtures/collection_with_query_parameters.json

@@ -0,0 +1,36 @@
+{
+    "variables": [],
+    "info": {
+        "name": "Laravel API",
+        "_postman_id": "",
+        "description": "",
+        "schema": "https:\/\/schema.getpostman.com\/json\/collection\/v2.0.0\/collection.json"
+    },
+    "item": [
+        {
+            "name": "Group A",
+            "description": "",
+            "item": [
+                {
+                    "name": "http://localhost/api/withQueryParameters",
+                    "request": {
+                        "url": "http:\/\/localhost\/api\/withQueryParameters?location_id=consequatur&user_id=me&page=4&filters=consequatur",
+                        "method": "GET",
+                        "header": [
+                            {
+                                "key": "Accept",
+                                "value": "application/json"
+                            }
+                        ],
+                        "body": {
+                            "mode": "formdata",
+                            "formdata": []
+                        },
+                        "description": "",
+                        "response": []
+                    }
+                }
+            ]
+        }
+    ]
+}

+ 60 - 6
tests/GenerateDocumentationTest.php

@@ -242,9 +242,10 @@ class GenerateDocumentationTest extends TestCase
         config(['apidoc.routes.0.match.prefixes' => ['api/*']]);
         $this->artisan('apidoc:generate');
 
-        $generatedCollection = json_decode(file_get_contents(__DIR__.'/../public/docs/collection.json'));
-        $generatedCollection->info->_postman_id = '';
-        $fixtureCollection = json_decode(file_get_contents(__DIR__.'/Fixtures/collection.json'));
+        $generatedCollection = json_decode(file_get_contents(__DIR__.'/../public/docs/collection.json'), true);
+        // The Postman ID varies from call to call; erase it to make the test data reproducible.
+        $generatedCollection['info']['_postman_id'] = '';
+        $fixtureCollection = json_decode(file_get_contents(__DIR__.'/Fixtures/collection.json'), true);
         $this->assertEquals($generatedCollection, $fixtureCollection);
     }
 
@@ -273,9 +274,62 @@ class GenerateDocumentationTest extends TestCase
         config(['apidoc.routes.0.match.prefixes' => ['api/*']]);
         $this->artisan('apidoc:generate');
 
-        $generatedCollection = json_decode(file_get_contents(__DIR__.'/../public/docs/collection.json'));
-        $generatedCollection->info->_postman_id = '';
-        $fixtureCollection = json_decode(file_get_contents(__DIR__.'/Fixtures/collection_updated_url.json'));
+        $generatedCollection = json_decode(file_get_contents(__DIR__.'/../public/docs/collection.json'), true);
+        // The Postman ID varies from call to call; erase it to make the test data reproducible.
+        $generatedCollection['info']['_postman_id'] = '';
+        $fixtureCollection = json_decode(file_get_contents(__DIR__.'/Fixtures/collection_updated_url.json'), true);
+        $this->assertEquals($generatedCollection, $fixtureCollection);
+    }
+
+    /** @test */
+    public function generated_postman_collection_can_append_custom_http_headers()
+    {
+        RouteFacade::get('/api/headers', TestController::class.'@checkCustomHeaders');
+        config(['apidoc.routes.0.match.prefixes' => ['api/*']]);
+        config([
+            'apidoc.routes.0.apply.headers' => [
+                'Authorization' => 'customAuthToken',
+                'Custom-Header' => 'NotSoCustom',
+            ],
+        ]);
+        $this->artisan('apidoc:generate');
+
+        $generatedCollection = json_decode(file_get_contents(__DIR__.'/../public/docs/collection.json'), true);
+        // The Postman ID varies from call to call; erase it to make the test data reproducible.
+        $generatedCollection['info']['_postman_id'] = '';
+        $fixtureCollection = json_decode(file_get_contents(__DIR__.'/Fixtures/collection_with_custom_headers.json'), true);
+        $this->assertEquals($generatedCollection, $fixtureCollection);
+    }
+
+    /** @test */
+    public function generated_postman_collection_can_have_query_parameters()
+    {
+        RouteFacade::get('/api/withQueryParameters', TestController::class.'@withQueryParameters');
+        // We want to have the same values for params each time
+        config(['apidoc.faker_seed' => 1234]);
+        config(['apidoc.routes.0.match.prefixes' => ['api/*']]);
+        $this->artisan('apidoc:generate');
+
+        $generatedCollection = json_decode(file_get_contents(__DIR__.'/../public/docs/collection.json'), true);
+        // The Postman ID varies from call to call; erase it to make the test data reproducible.
+        $generatedCollection['info']['_postman_id'] = '';
+        $fixtureCollection = json_decode(file_get_contents(__DIR__.'/Fixtures/collection_with_query_parameters.json'), true);
+        $this->assertEquals($generatedCollection, $fixtureCollection);
+    }
+
+    /** @test */
+    public function generated_postman_collection_can_add_body_parameters()
+    {
+        RouteFacade::get('/api/withBodyParameters', TestController::class.'@withBodyParameters');
+        // We want to have the same values for params each time
+        config(['apidoc.faker_seed' => 1234]);
+        config(['apidoc.routes.0.match.prefixes' => ['api/*']]);
+        $this->artisan('apidoc:generate');
+
+        $generatedCollection = json_decode(file_get_contents(__DIR__.'/../public/docs/collection.json'), true);
+        // The Postman ID varies from call to call; erase it to make the test data reproducible.
+        $generatedCollection['info']['_postman_id'] = '';
+        $fixtureCollection = json_decode(file_get_contents(__DIR__.'/Fixtures/collection_with_body_parameters.json'), true);
         $this->assertEquals($generatedCollection, $fixtureCollection);
     }